When I compile with GCC 4.2 alone, it will.
Unfortunately, I have not been able to develop a simple application which reproduces the problem.
Problems with C++ exceptions (please read!)
Exception catching of a user defined type in a binary other than the one which threw the exception requires a typeinfo lookup. Go back and read that last statement again. When exceptions start mysteriously malfunctioning, the cause is exactly this one!
Just like functions and variables, types that are thrown between multiple shared objects are public interfaces and must have default visibility. The obvious first step is to mark all types throwable across shared object boundaries always as default visibility. You must do this because even if (e.g.) the exception type's implementation code lives in DLL A, when DLL B throws an instance of that type, the catch handler in DLL C will look for the typeinfo in DLL B.
However, this isn't the full story - it gets harder. Symbol visibility is "default" by default but if the linker encounters just one definition with it hidden - just one - that typeinfo symbol becomes permanently hidden (remember the C++ standard's ODR - one definition rule). This is true for all symbols, but is more likely to affect you with typeinfos; typeinfo symbols for classes without a vtable are defined on demand within each object file that uses the class for EH and are defined weakly so the definitions get merged at link time into one copy.
The upshot of this is that if you forget your preprocessor defines in just one object file, or if at any time a throwable type is not declared explicitly public, the -fvisibility=hidden will cause it to be marked hidden in that object file, which overrides all the other definitions with default visibility and causes the typeinfo to vanish in the outputted binary (which then causes any throws of that type to cause terminate() to be called in the catching binary). Your binaries will link perfectly and appear to work correctly, even though they don't.
While it would be lovely to have a warning for this, there are plenty of legitimate reasons to keep throwable types out of public view. And until whole program optimisation is added to GCC, the compiler can't know which throws are caught locally.
The same issue can arise with other vague linkage entities such as static data members of a class template. If the class has hidden visibility, the data member can be instantiated in multiple DSOs and referenced separately, causing havoc.
This issue also shows up with classes used as the operand of dynamic_cast. Make sure to export all such classes.
-----I do have ~6500 link warnings which look like:
ld: warning: typeinfo for MYTYPEA has different visibility (default) in XXX and (hidden) in YYY
regardless of which compiler I use. Assuming this would also apply to LLVM, I figure LLVM is doing things just a little differently and being a little more strict which is bringing out this crash and that I am mostly getting lucky with GCC 4.2, but this is only a guess on my part.
So, it seems possible that a typeinfo lookup is failing.
How would one go about confirming this is happening? How do you debug a C++ typeinfo check? How can one determine why a catch block is failing to capture an exception it should capture?
Thank you.