如何在 exe 中手动初始化 c 运行时?
How to manually initialise the c runtime in an exe?
我正在尝试使用 linker 开关“/entry”为可视化 C++ 可执行文件提供我自己的入口点。相关的 Microsoft 文档详细介绍了如何在 dll 中手动初始化 c 运行时,但我无法掌握如何在我的 exe 中初始化它。我得到的最好的是我需要调用 _CRT_init,但我不知道那是一个函数还是一个宏,或者它可能在哪里定义,并且 Visual Studio(和 msbuild)不' 识别标识符,所以那里没有提示。
这里的基本原理是我正在尝试使用 Google Test 对可执行文件进行单元测试,但不会 link 因为 main() 冲突。 GTest FAQ 中提到的两种方法并不是真正通用的,需要对大约 30 个遗留可执行文件进行大量修改才能实现。重命名每个单元测试应用程序的 main() 似乎是一种超级简单的方法,如果我能初始化 c 运行时就好了。
所以我今天下午搜索了C Runtime源码,答案是"no"。如果要使用 C 运行时,则不能提供自己未命名为 main
的可执行入口点。除了 _CRT_INIT()
是 dll 的初始化函数(mainCRTStartup()
是可执行文件的初始化函数之一),mainCRTStartup()
及其类似的名称调用 main()
。
- 您可以在独立的包装器模块中初始化 CRT,该模块具有
主要的; obj1
- 将所有现有的 exe 模块的 main 重命名为 xx_main; obj2, obj3.... objn
- Link obj1(主要) 与 (obj2, obj3.... objn).
To test a foo.cc file, you need to compile and link it into your unit
test program
这个方案有什么问题?
虽然没有具体记录,但可以像在 DLL 中一样在可执行文件中初始化 CRT。
EXTERN_C BOOL WINAPI _CRT_INIT( HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpReserved );
// ThreadProc for CreateRemoteThread, a possible use case.
DWORD WINAPI ArbitraryAlternateEntryPoint( LPVOID )
{
_CRT_INIT( GetModuleHandle( NULL ), DLL_PROCESS_ATTACH, NULL );
// CRT functions can be used here.
_CRT_INIT( GetModuleHandle( NULL ), DLL_PROCESS_DETACH, NULL );
return 0;
}
documentation 建议除了初始调用之外,还应为每个新线程调用 _CRT_INIT,但实际上这不是必需的。
我正在尝试使用 linker 开关“/entry”为可视化 C++ 可执行文件提供我自己的入口点。相关的 Microsoft 文档详细介绍了如何在 dll 中手动初始化 c 运行时,但我无法掌握如何在我的 exe 中初始化它。我得到的最好的是我需要调用 _CRT_init,但我不知道那是一个函数还是一个宏,或者它可能在哪里定义,并且 Visual Studio(和 msbuild)不' 识别标识符,所以那里没有提示。
这里的基本原理是我正在尝试使用 Google Test 对可执行文件进行单元测试,但不会 link 因为 main() 冲突。 GTest FAQ 中提到的两种方法并不是真正通用的,需要对大约 30 个遗留可执行文件进行大量修改才能实现。重命名每个单元测试应用程序的 main() 似乎是一种超级简单的方法,如果我能初始化 c 运行时就好了。
所以我今天下午搜索了C Runtime源码,答案是"no"。如果要使用 C 运行时,则不能提供自己未命名为 main
的可执行入口点。除了 _CRT_INIT()
是 dll 的初始化函数(mainCRTStartup()
是可执行文件的初始化函数之一),mainCRTStartup()
及其类似的名称调用 main()
。
- 您可以在独立的包装器模块中初始化 CRT,该模块具有 主要的; obj1
- 将所有现有的 exe 模块的 main 重命名为 xx_main; obj2, obj3.... objn
- Link obj1(主要) 与 (obj2, obj3.... objn).
To test a foo.cc file, you need to compile and link it into your unit test program
这个方案有什么问题?
虽然没有具体记录,但可以像在 DLL 中一样在可执行文件中初始化 CRT。
EXTERN_C BOOL WINAPI _CRT_INIT( HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpReserved );
// ThreadProc for CreateRemoteThread, a possible use case.
DWORD WINAPI ArbitraryAlternateEntryPoint( LPVOID )
{
_CRT_INIT( GetModuleHandle( NULL ), DLL_PROCESS_ATTACH, NULL );
// CRT functions can be used here.
_CRT_INIT( GetModuleHandle( NULL ), DLL_PROCESS_DETACH, NULL );
return 0;
}
documentation 建议除了初始调用之外,还应为每个新线程调用 _CRT_INIT,但实际上这不是必需的。