EnterCriticalSection 崩溃,线程超过 64 个

EnterCriticalSection crashes with more than 64 threads

本文关键字:线程 崩溃 EnterCriticalSection      更新时间:2023-10-16

是否有线程限制 EnterCriticalSection() 可以应付?以下代码适用于 64 个线程,但在使用 65 个或更多线程时崩溃:

CRITICAL_SECTION TestCritSection;
unsigned int threadId;
int getThreadId()
{
    int tid = -1;
    EnterCriticalSection(&TestCritSection);
    tid= threadId;
    threadId++;
    LeaveCriticalSection(&TestCritSection);
    return tid;
}
void parallelTest()
{
    int tid = getThreadId();
    cout << "Thread " << tid << " executed" << endl;
}

void
multiThreadTest()
{
    unsigned int numThreads = 64; // fine, but program crashes when numThreads is set to 65 or more
    HANDLE *threads = new HANDLE[numThreads];
    DWORD ThreadID;
    threadId = 1;
    if (!InitializeCriticalSectionAndSpinCount(&TestCritSection, 0x00000400)) return;
    for (int i=0; i<numThreads; ++i)
    {
        threads[i] = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) parallelTest, (LPVOID) NULL, 0, &ThreadID);
    }
    WaitForMultipleObjects(numThreads, threads, TRUE, INFINITE);
    DeleteCriticalSection(&TestCritSection);
    for (int i=0; i<numThreads; ++i)
    {
        CloseHandle(threads[i]);
    }
    delete [] threads;
}

我想CRITICAL_SECTION内部使用的是最大计数为 64 的信号量。我可以以某种方式改变它吗?

由于没有人愿意回答我的问题,我将根据HansPassant对我问题的评论自己做。

他指出,问题WaitForMultipleObjects(),它需要一个参数

n计数 [在]

The number of object handles in the array pointed to by lpHandles.

对象句柄的最大数量为 MAXIMUM_WAIT_OBJECTS。这 参数不能为零。

(来自MSDN)

MAXIMUM_WAIT_OBJECTS定义为 64,此线程中的详细信息。

这意味着:是的,线程数量有一个硬编码限制,但限制不是EnterCriticalSection而是WaitForMultipleObjects,它返回我应该检查的错误代码。

下面是有关如何让超过 64 个线程并行工作的更多信息。