多线程对象中的堆损坏
heap corruption in multi-threaded object
我试图建立一个单例类,它将保持一个循环缓冲区,每次一些函数想要转储发送一些东西到调试客户端(例如DBGview或类似)该函数将其信息存储在循环缓冲区内。该对象还将运行一个线程,该线程将休眠一段时间,然后唤醒并将缓冲区内容转储到调试客户端。
这是每个人在需要发送一些东西进行调试时调用的函数:
TTFW_LogRet PrintToLogger (std::string Str)
{
Logger *Log;
if(Instance_Mutex == NULL)
{
Instance_Mutex = CreateMutex(NULL,FALSE,NULL);
if (Instance_Mutex == NULL)
{
OutputDebugStringA("CreateMutex error! the Logger will close n");
return GENERAL_ERROR;
}
}
Log = Logger::getLogInstance();
Log->LogStringToOutput(Str);
return SUCCESS;
}
由于某种原因,我总是在返回SUCCESS语句后得到堆损坏错误
这是Getinstance()函数:
Logger* Logger::getLogInstance()
{
if(_instance == NULL)
{
MutexLock(Instance_Mutex);
if(_instance == NULL)
{
_instance = new Logger();
}
MutexUnlock(Instance_Mutex);
}
return _instance;
}
,线程函数为
DWORD WINAPI Logger::WorkerThread (LPVOID lpParam )
{
Logger *log = static_cast <Logger*> (lpParam);
for(;;)
{
Sleep(2000);
if(log->getOutputMethod() == odBuffer && log->CyclicBuffer1.size() >= log->Thresh && !log->CyclicBuffer1.empty())
{
TTFW_LogRet ret;
ret = log->FullBufferDump();
if (ret != SUCCESS)
{
log->LogStringToOutput("Error occured in dumping cyclic buffer , the buffer will be clearedn");
}
}
}
}
有人知道为什么堆损坏会发生在这段代码中吗?请注意,要调试的函数会被调用很多次,并且它不会与转储缓冲区的线程同步。
您使用了双重检查锁定,这可能会导致您所看到的那种微妙的问题。特别地,c++允许
行_instance = new Logger();
可能导致_instance
在Logger
构造函数完成之前得到非null值。然后,如果另一个线程调用getLogInstance
,条件if(_instance == NULL)
将不满足,线程将使用未完全初始化的对象。考虑使用直接锁定而不进行双重检查,或者使用其他技术(可能依赖于实现)。在c++ 11中,您可以安全地使用静态变量来实现这些目的。
我的通灵调试技能告诉我LogStringToOutput
不是线程安全的,并且在从多个线程调用时导致堆损坏。
相关文章:
- 构造函数初始化和对象损坏
- 从本机代码返回到托管代码会损坏返回的对象
- 在向量中使用不带复制且没有 noexcept 移动构造函数的对象.实际损坏的内容以及我如何确认它
- 引用可能已损坏的静态对象
- 部分损坏的对象
- 对同一对象的多个shared_ptrs,一个已损坏
- C 用向量序列化对象会导致双重自由损坏
- 如何在不存在任何数据损坏风险的情况下序列化对象
- 对象, 在 Vector 中, 在'For Loop'初始化中损坏
- 我的 QNX/BB10 C++应用程序崩溃,一个简单的C++对象似乎已损坏
- 从映射中检索后,映射中的对象已损坏
- 删除对象(另一个..)时双重释放或损坏
- 多线程对象中的堆损坏
- 对象的c++内存副本出现损坏
- 对象周围的堆栈已损坏
- 在Visual Studio调试模式下运行时,c++对象引用已损坏
- 为什么在返回对象时堆损坏?
- 使用内存复制对象时出现双自由或损坏错误
- 从复制构造函数外部修改对象成员时导致向量内存损坏,但从复制构造函数内部修改时不会
- C++对象引用损坏