From: Bronek Kozicki (brok_at_[hidden])
Date: 2004-07-29 07:02:18
> Wrong. I assumed nothing about how B is packaged.
> To be more precise I Assume static lib (no DLL). And I am linking
> statically to c-runtime.
I misunderstood you, then. I thought that you meant B to be dynamic link
> mainCRTStartup initializes the lib, and calls your main in turn.
>>You may find this function in CRT sources (if you installed it together
>>with MSVC). In multi-threaded, statically linked version of CRT this
>>function will indirectly call TlsAlloc (or actually FlsAlloc - if
>>present in "kernel32.dll", at least in CRT delivered with MSVC71).
> I don't believe so. TlsAlloc is called from within mainCRTStartup for
> the main thread. (Not from DllMainCRTStartUp.)
_DllMainCRTStartup is in crtdll.c (when your DLL library is dynamically
linked to CRT) or dllcrt0.c (when your DLL library is statically linked
to CRT). In both files you will find _CRT_INIT, called from
_DllMainCRTStartup just before user entry point (DllMain) is executed.
In _CRT_INIT in dllcrt0.c you will find call to _mtinit, which is
defined in tidtable.c. Here you will find "__tlsindex =
FLS_ALLOC(&_freefls)". But I think that's all irrelevant in your case,
as your library B (being static library) does not have an entry point.
> How should this ever work? When you link the CRT statically there is
> no chance of even exposing DllMainCRTStartup! You may only assign
> _one_ entrypoint into your executable, and this is already mainCRTStartup.
Of course this will work, if you linked CRT statically to your *dynamic*
library. Things are much different with static libraries, as you pointed
out. In this case linker will see symbol "__tlsindex" in static runtime
library that your static library is linked with (ie. indirectly in your
library), and when linking your library with code of your client (ie.
user of your static library) it will match it with __tlsindex in his CRT
(whenever he's using static or dynamic runtime). When his mainCRTStartup
(or DllMainCRTStartup) is executed, this symbol will be initialized by
call to TlsAlloc (ie. inside function _mtinit). This is enough to
initialize TLS index for CRT. Because this index is shared (linker did
this) with static CRT your static library is linked with, effectively it
will share TLS with CRT linked (statially or dynamically) with code of
your client. At least this is my idea of what linker is doing, and I've
confirmed that with debugger. And this is enough; execution of
TlsSetValue and initialization of CRT data is delayed to first access of
CRT TLS data through _getptd function (defined in tidtable.c).
> Give it a try. Set a breakpoint to your entry function while statically linked.
> I bet you will never arrive there :-(
... and it's not required by CRT to initialize its stuff in TLS.
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk