windowscmakemingwdllexportdeclspec

Windows export/import symbols under MinGW vs MSVS; CMake's WINDOWS_EXPORT_ALL_SYMBOLS ignored


To build a C library with Visual Studio, the CMake command

set(WINDOWS_EXPORT_ALL_SYMBOLS ON)

saves me from adding __declspec(dllexport) or __declspec(dllimport) in front of function declarations; explicit import/export symbols are only required for global variables.

Under MinGW (read: either MinGW or its recommendable replacement Mingw-w64) this does not work. Linking applications (also built with MinGW) to my library failed until I had pasted import/export symbols in front of each function. Whereas the long answer https://stackoverflow.com/a/32284832/1017348 suggests the contrary: no need for import/export symbols under MinGW. Is that answer right? How then to get rid of the need for import/export symbols?


Solution

  • I just encountered the same problem. After poking through CMake source code, the fix that worked for me was to also add:

    set( CMAKE_SUPPORT_WINDOWS_EXPORT_ALL_SYMBOLS 1 )
    

    CMake says:

    This property is implemented only for MS-compatible tools on Windows.

    CMake enables this capability by setting CMAKE_SUPPORT_WINDOWS_EXPORT_ALL_SYMBOLS in each "Platform" file in <cmake install>/Modules/Platform that they know supports it. However, CMake doesn't model MinGW as a "Platform". Instead you just pick "Windows Makefile", "Windows Ninja", etc. and manually set the C/C++/Fortran compilers to point to the MinGW gcc compilers. Ideally CMake should recognize when the OS is Windows and the compiler is gcc and set this for us, but for now we can help it by setting it ourselves.

    Incidentally CMake implements this feature with a hidden cmake -E __create_def <output-def> <input-list-of-obj-files> command. I previously thought of adding a custom rule to run that command. Though as it starts with __, it's meant for internal use and might change from one release to the next.