3

Microsoft has had a fair amount of trouble in the past when passing STL containers like string and vector pointers and references to DLLs. See, for example, You may experience an access violation when you access an STL object through a pointer or reference in a different DLL or EXE.

Question: Are those types of problems still present today in Visual Studio 2010 and 2013?

I know the question is a bit open-ended. I am asking because I've experienced them in the past, I'm working on a new design, the design could include a plugin architecture, and I would like to to pass a string or vector reference to a plugin DLL. If the problems still plague Microsoft, then I have to change the design (or come up with a workaround to avoid the crash).


Related, Did C++11 address concerns passing std lib objects between dynamic/shared library boundaries? is similar (thanks for the link). But it does not really answer the question, though it does seem to acknowledge the same problem.

Also, Microsoft's KB Q168958, How to export an instantiation of a Standard Template Library (STL) class and a class that contains a data member that is an STL object, implies it can be done. But that's around the time I recall having the problems, so I am curious if it still applies (and if it actually works now in Visual Studio 2010 or 2013).

The problem I am running into was highlighted by Robert and Doc: I can test for the presence of bugs, but not the absence of them. So I might not be able to trigger problems during testing, but the problems may really exists (and surface at the worse time).

  • It would be easy enough to test. – Robert Harvey Apr 08 '15 at 05:22
  • 3
    @RobertHarvey: I do not think its *easy* to test - just because some small test case works does not proof passing STL containers between DLLs will be reliable. – Doc Brown Apr 08 '15 at 05:46
  • @Doc - I was think the same thing. We can test for the presence of bugs, and not the absence of them (sic, [Edsger W. Dijkstra](https://en.wikiquote.org/wiki/Edsger_W._Dijkstra)). –  Apr 08 '15 at 05:48
  • 2
    Short answer because I'm on my phone, yes, you'll have problems, because of a variety of reasons boiling down to no standard for binary compatibility. Possible solutions are to expose a pure C interface, or use COM. – whatsisname Apr 08 '15 at 05:57
  • 1
    Official position is still the same, no, all standard library objects which are not "standard layout" (formerly called plain-old-data types, or POD) may have layout changes across versions. https://msdn.microsoft.com/en-us/library/bb531344.aspx – rwong Apr 08 '15 at 07:42
  • 3
    Mixing and matching dynamic or static libraries compiled by different versions of compilers is always a no-no, unless only "standard layout" (POD) data structure is involved. In C++, typically one recompiles everything with the same version of compiler. This is why C++ really forces vendors to consider open-source because it is likely that customers will need to recompile from source code with a newer compiler version in the future, after the vendor's initial release. – rwong Apr 08 '15 at 07:45
  • Your linked article to Q168958 only applies to DLLs which were originally compiled with VC++ 5.0 or 6.0. – rwong Apr 08 '15 at 07:48
  • @rwong true, if only Stroustrup would consider a C++ ABI to be a useful thing, this problem would go away and we could stop using C interfaces to shared libs! – gbjbaanb Apr 08 '15 at 07:54
  • @rwong - yes, but Microsoft often fixes things and then places the document in some sort of purgatory. That is, they stop updating the "applies to" section (without saying "this was fixed in version XXX"). –  Apr 08 '15 at 08:23
  • @gbjbaanb - its not the ABI *per se* (or I don't think it is). For example, I don't think the string interface has changed in years. The problem seems to be behind the scene tricks like hidden state to reference count a string as an optimization. But, maybe I don't understand all the problems as well as I should. –  Apr 08 '15 at 10:36
  • @jww it is partly an ABI, though there are issues in things like template instantiation in the DLL but not in the calling code - so the code doesn't know what that template type actually is. Then there's implementation issues like a Release build exe calling into a Debug dll where the two have different memory models (eg guard pages etc). But .. an ABI would mean code binaries could be consumed by a different compiler and not always rebuilt. Just like C dlls work. – gbjbaanb Apr 08 '15 at 10:40
  • Thanks. whatsisname's answer kind of crushed me because I was going to build this thing out so that it builds/runs on Windows, Linux, OS X and the BSDs (I have a lot of experience with C/C++ sources and supporting multiple platforms from a single set of sources). I'm new to the plugin architecture for extensibility, and it looks like I'm going to have to abandon it. I'm not going to build it twice - once in C++ and once in COM (a single set of sources is that important to me to keep reliability up and bugs down). –  Apr 08 '15 at 10:43
  • @whatsisname - consensus is this won't work in 2015. If you answer, I'll accept to make it official. (You were the first to say it would not work). –  Apr 08 '15 at 16:17

1 Answers1

4

Export a C interface.

Not only does that solve the DLL problem, but it allows for plugins in languages other than C++.

Then write a C++ wrapper for the C API as a header only library.

You can't use C++ non-standard-layout objects in the API because there is no standard ABI for them, so you would be requiring the library and users to all be compiled with the same compiler and libraries. This is particularly bad for plugins -- it is less of an issue for libraries as the library user can statically link the library with the executable, or at least bundle the two in a single installer.

Note that a non-POD object can still be standard layout, starting with C++11.

Demi
  • 826
  • 7
  • 18