Exporting STL Classes

Started by
4 comments, last by NullSeraph 22 years, 2 months ago
I've been working on a DLL for the last few weeks, and I've recently run into a problem. In one of my classes, I use a "string" to hold a filename (nothing extraordinary). It looks something like this. (btw I use MSVC++ 6.0 in win2k)
  
class __declspec(dllexport) MyClass
{
protected:
   string Filename;

public:
   //Constructors, destructors, etc.

};
  
Alright, so this creates a compiler warning C4251, which means that you need to export any classes that are used inside another class. So I followed the directions in this article: http://support.microsoft.com/default.aspx?scid=kb;en-us;Q168958 This got everything working except for one problem. The article mentions that previously instantiated templates cannot be re-instantiated for export. string (which is a previously instantiated template) will not export properly. So after this long winded explanation...my question. Is there any possible way to force MSVC to not instantiate "string"? And if there isn't anyway to do this, is there another solution? I'd really appreciate some help with this. STL is incredibly useful, and I don't want to sacrifice one of the most useful components IMO. Edited by - doombunny on February 18, 2002 11:15:21 PM
Advertisement
Use basic_string. Instantiate it as basic_string<char>. Make string a typedef for basic_string<char>.

I wanna work for Microsoft!
[ GDNet Start Here | GDNet Search Tool | GDNet FAQ | MS RTFM [MSDN] | SGI STL Docs | Google! ]
Thanks to Kylotan for the idea!
Actually, that''s the method I was using to export the templates. Here is an example.

  template class __declspec(dllexport) std::basic_string<char>;template class __declspec(dllexport) std::basic_string<wchar_t>;  


When I export like this, any "wstring" variable works fine. However, the "string" variables give debug assertions. MSVC apparently doesn''t instantiate "wstring", but it does instantiate "string".
Another way to get around it is to change the C++ Code Generation of the application to Debug Multithreaded DLL. This will add the appropriate compilier flags to link in the STL code.

-----------------------------
kevin@mayday-anime.com
http://games.mayday-anime.com
-----------------------------kevin@mayday-anime.comhttp://www.mayday-anime.com
Thanks for the comments Oluseyi and grasshopa. I''m going to try and eliminate any interaction between the client application and DLL-defined templates. If I can''t then I''ll switch to the multi-threaded DLL. I''m reluctant to switch right now because I assume it will mean having to include another DLL with my application, and dependencies always worry me.
I personally never statically link to MSVCRT, because:
1) this DLL is present on virtually every computer there is, and you don''t need to install it
2) using DLL makes your program smaller, especially if you are using EXE and DLL, they share CRT code in MSVCRT instead of each having a copy
3) even if you don''t use the CRT DLL, most likely one of the DLL you load does. So there is no advantage in not linking dynamically to it, as it''s in your address space anyway.

That said, when I use strings, I get them from msvcp60.dll. If you look at it with dependency viewer from PSDK, you can see that it exports 2k+ member functions for classes like basic_string, basic_Xstream<...>, etc. So both your DLL and EXE will use the template functions from that DLL, if you link to CRT dynamically.
---visit #directxdev on afternet <- not just for directx, despite the name

This topic is closed to new replies.

Advertisement