variable - ¿Cuál se llama primero, DllMain() o constructor de objeto estático global?
static constructors (1)
Estoy escribiendo un archivo DLL que define un objeto estático global.
En el constructor del objeto estoy haciendo una inicialización que puede o no tener éxito.
¿Es posible señalar el éxito o el fracaso del proceso de inicialización en DllMain ()? ¿Cuál de los dos se llama primero?
Gracias.
La documentación de DllMain de MSDN dice:
Si su DLL está vinculado con la biblioteca en tiempo de ejecución de C (CRT), el punto de entrada proporcionado por la CRT llama a los constructores y destructores para objetos de C ++ globales y estáticos. Por lo tanto, estas restricciones para DllMain también se aplican a constructores y destructores y a cualquier código que se invoque desde ellos.
Dado que el código dentro de DllMain puede usar los objetos estáticos, los objetos estáticos deben construirse antes de que DllMain se ejecute para DLL_PROCESS_ATTACH, y destruirse después de que se ejecute para DLL_PROCESS_DETACH.
Puede verificar esto con un simple test exe y test dll.
EXE:
int _tmain(int argc, _TCHAR* argv[])
{
wprintf(L"Main, loading library/n");
HMODULE h = LoadLibrary(L"Test.dll");
if (h)
{
wprintf(L"Main, freeing library/n");
FreeLibrary(h);
}
wprintf(L"Main, exiting/n");
return 0;
}
DLL:
struct Moo
{
Moo() { wprintf(L"Moo, constructor/n"); }
~Moo() { wprintf(L"Moo, destructor/n"); }
};
Moo m;
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
wprintf(L"DllMain, DLL_PROCESS_ATTACH/n");
break;
case DLL_THREAD_ATTACH:
wprintf(L"DllMain, DLL_THREAD_ATTACH/n");
break;
case DLL_THREAD_DETACH:
wprintf(L"DllMain, DLL_THREAD_DETACH/n");
break;
case DLL_PROCESS_DETACH:
wprintf(L"DllMain, DLL_PROCESS_DETACH/n");
break;
default:
wprintf(L"DllMain, ????/n");
break;
}
return TRUE;
}
Juntos los imprimirán:
Main, loading library
Moo, constructor
DllMain, DLL_PROCESS_ATTACH
Main, freeing library
DllMain, DLL_PROCESS_DETACH
Moo, destructor
Main, exiting
Como puede ver, el objeto estático se construye antes de DllMain(...,DLL_PROCESS_ATTACH,...)
y se destruye después de DllMain(...,DLL_PROCESS_DETACH,...)