My use case is as follows.

I have a class template `S` with implicit inline functions in `lib.h`.
To improve compilation times, I want to explicitly instantiate common 
specializations of this class template in `lib.cpp`.
In order to do so, I want to provide an explicit instantiation declaration 
(`extern template`) of `S<int>` in `lib.h`, and an explicit instantiation 
definition of `S<int>` in `lib.cpp`.
Now, I expect that every consumer linking against `lib` should be able to use 
`S<int>` without having to fully instantiate it.

The example I provided in my bug report cleanly compiles and links with 
clang++, regardless of whether I have `__declspec(dllexport)` or not in the 
declaration.
The example does not link when compiling `lib` with g++, if I have 
`__declspec(dllexport)` in the declaration. It does link if I enable 
`-Wl,--export-all-symbols` or if I remove the `__declspec(dllexport)` 
altogether.
Putting the `__declspec(dllexport)` on the explicit template instantiation 
definition results in a compiler warning telling me that it is ignored.
These results make me believe that we are experiencing a g++ bug related to 
symbol exporting when targeting MinGW.

In my real project (see 
https://github.com/vittorioromeo/SFML/tree/feature/remove_windows_h_dependency_for_gl_h,
 Vector2 class), where I have the same use case, there's nothing I can do.
Regardless of whether I have `__declspec(dllexport)` or not, I get linker 
errors on the explicit template instantation for `constexpr` member functions 
such as `sf::Vector2<unsigned int>::Vector2()`, which are declared and defined 
as follows:

//
// ----------------------------------------------------------------------------
// Vector2.hpp (sfml-system library)
namespace sf
{
    template <typename T>
    class Vector2
    {
    public:
        SFML_SYSTEM_API constexpr Vector2();
        // ...
    };
}

extern template sf::Vector2<unsigned int>::Vector2();

template <typename T>
constexpr sf::Vector2<T>::Vector2() = default;

//
// ----------------------------------------------------------------------------
// Vector2.cpp (sfml-system library)
template sf::Vector2<unsigned int>::Vector2();

//
// ----------------------------------------------------------------------------
// GlContext.cpp (sfml-window library, depends on sfml-system)
// ...
std::make_unique<ContextType>(/* ... */, Vector2<unsigned int>(1, 1));
//                                       ^^^^^^^^^^^^^^^^^^^^^^^^^^^
//                                       linker error here with g++
// ...

Removing `SFML_SYSTEM_API` or adding it to the explicit template definition has 
no effect at all.
Removing the `extern template` results in another GCC bug, see 
(https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109387).

Therefore I see no possible solution to my problem.
Hope this helps -- cheers,


Vittorio Romeo

https://vittorioromeo.com

________________________________
From: LIU Hao
Sent: Monday, April 03, 2023 12:04 PM
To: mingw-w64-public@lists.sourceforge.net; Vittorio Romeo
Subject: Re: [Mingw-w64-public] GCC bugs with explicit template instantiation 
and dllexport targeting MinGW

在 2023/4/3 16:55, Vittorio Romeo 写道:
> Hello everyone,
> Hope you are doing well.
>
> I've encountered and reported a bug related to explicit template 
> instantiations and dllexport using the latest version of GCC on MinGW/MSYS2:
> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109380

I don't think it's a bug. There are two issues in your testcase, one is that

    extern template struct __declspec(dllexport) S<int>;

is a declaration, and nothing can be exported from a declaration (you export 
the definition instead).

The other is that `g()` is an implicit inline function. An inline function can 
only be exported when
it is emitted as a non-inline copy, for example, when optimization is not 
enabled, or when its
address is taken, or when it is virtual and the class has a non-pure non-inline 
virtual function
(a.k.a. the key function) which instantiates its vtable.



--
Best regards,
LIU Hao


_______________________________________________
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public

Reply via email to