One Way of Eliminating C4251 Warning When Using Stl-Classes in the Dll-Interface

One way of eliminating C4251 warning when using stl-classes in the dll-interface

I think you've got at least 5 possible options to solve this problem:

  1. You could still keep STL/template classes for your fields and also use them as parameter types, as long as you keep all the fields private (which is a good practice anyway). Here is a discussion about this. To remove the warnings you could simply use according #pragma statements.

  2. You could create small wrapper classes with private STL fields and expose fields of your wrapper class types to the public instead, but this would most probably only move the warnings to another places.

  3. You could use the PIMPL idiom to hide your STL fields in a private implementation class, which will not even be exported from your library nor be visible outside of it.

  4. Or you could actually export all the required template class specializations, as suggested in the C4251 warning, in a way that is described here. In short you would have to insert following lines of code before your HelloWorld class:

    ...
    #include <vector>

    template class __declspec(dllexport) std::allocator<int>;
    template class __declspec(dllexport) std::vector<int>;
    template class __declspec(dllexport) std::string;

    class __declspec(dllexport) HelloWorld
    ...

    By the way, the order of those exports seems to be important: the vector class template uses the allocator class template internally, so the allocator instantiation has to be exported before the vector instantiation.

  5. The direct use of intrinsics is probably your worst option, but if you encapsulate your fields

    int *p_abc;
    int abc_len;

    in something like class MyFancyDataArray and the fields

    char *p_str;
    int str_len;

    in something like class MyFancyString, then this would be a more decent solution (similar to the one described at the second point). But it is probably not the best habit to reinvent the wheel too often.

Warning C4251 when building a DLL that exports a class containing an ATL::CString member

This thread gives what I consider a better answer, by Doug Harrison (VC++ MVP):

[This warning is] emitted when you use
a non-dllexported class X in a
dllexported class Y. What's so bad
about that? Well, suppose Y has an
inline function y_f that calls a
function x_f belonging to X that is
not also inline. If y_f is inlined
inside some client that doesn't
statically link X, the link will fail,
because x_f won't be found.

std::vector needs to have dll-interface to be used by clients of class 'XT warning

Exporting from a DLL is platform-specific. You will have to fix this for Windows (basically use declspec(dllexport/dllimport) on the instantiated class template) and encapsulate the required code in your Windows-specific preprocessor macro.

My experience is that exporting STL classes from DLLs on Windows is fraught with pain, generally I try to design the interface such that this is not needed.



Related Topics



Leave a reply



Submit