1

CRITICAL_SECTIONのように、静的に初期化することは可能pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZERですか?

言い換えれば、CでCRITICAL_SECTIONライブラリ内のグローバルをいじる必要なく初期化することは可能DllMainですか?

4

4 に答える 4

1

はい、単純に DLL_PROCESS_ATTACH で初期化し、DLL_PROCESS_DETACH で削除します

CRITICAL_SECTION g_cs = {0};

BOOL WINAPI DllMain(
    HINSTANCE hinstDLL,  // handle to DLL module
    DWORD fdwReason,     // reason for calling function
    LPVOID lpReserved )  // reserved
{
    // Perform actions based on the reason for calling.
    switch( fdwReason ) 
    { 
        case DLL_PROCESS_ATTACH:
         // Initialize once for each new process.
         // Return FALSE to fail DLL load.
            InitializeCriticalSection(&g_cs);
            break;

        case DLL_THREAD_ATTACH:
         // Do thread-specific initialization.
            break;

        case DLL_THREAD_DETACH:
         // Do thread-specific cleanup.
            break;

        case DLL_PROCESS_DETACH:
         // Perform any necessary cleanup.
          DeleteCriticalSection(&g_cs);
            break;
    }
    return TRUE;  // Successful DLL_PROCESS_ATTACH.
}

参考文献:

InitializeCriticalSection

重要なセクションの削除

于 2012-10-12T12:20:33.017 に答える
1

はい!ただし、プロセスごとに 1 回だけ実行する必要があります。ただし、これは通常、DLLMain switch( fdwReason )ステートメントの DLL_PROCESS_ATTACH ケースを使用することによって実現するのが最も簡単です。

于 2012-10-12T09:54:38.813 に答える
0

以前のバージョンでの別の可能性は、初期化関数へのポインターをユーザー定義のグローバル初期化子として設定するようリンカーに指示することです。これについては、次のような議論があります。

http://msdn.microsoft.com/en-us/library/bb918180.aspx

以下に例を示します。

CRITICAL_SECTION criticalSection;

static void __cdecl Initialize(void) {
    InitializeCriticalSection(&criticalSection);
}
#pragma section(".CRT$XCU", read)
__declspec(allocate(".CRT$XCU"))
const void (__cdecl *pInitialize)(void) = Initialize;
于 2014-08-03T07:06:34.297 に答える
0

Raymond Chen からの上記の回答は、この問題を解決しますPTHREAD_MUTEX_INITIALIZER

これは Vista 以降でのみ動作することに注意してください --- @rkosegi

を使用して独自のInitOnceExecuteOnce関数をInterlockedCompareExchange作成することにより、古いバージョンの Windows でこれを行うことができます。--- @RaymondChen

于 2012-10-15T05:56:16.243 に答える