项目场景:
CicadaPlayer 在Windows平台下退出线程卡住问题分析@[toc]
问题描述
基于开源的CicadaPlayer封装Windows平台SDK, 在集成测试中发现程序退出后,后台进程会残留,导致进程无法完全退出。
在Windows任务管理器中转存Dump然后使用pdb进行分析,加载堆栈信息如下:
堆栈对应代码:
CurlEasyManager::~CurlEasyManager()
{
released = true;
{
std::unique_lock<std::mutex> idleLock(checkIdleMutex);
stop = true;
checkIdleCondition.notify_one();
}
checkIdleThread->stop();
}
int CurlEasyManager::checkIdleRun()
{
clearEasyContext(false);
{
std::unique_lock<std::mutex> idleLock(checkIdleMutex);
checkIdleCondition.wait_for(idleLock, std::chrono::milliseconds(10 * 1000), [this]() -> bool { return stop.load(); });
}
if (stop) {
clearEasyContext(true);
return -1;
}
return 0;
}
#原因分析:
在checkIdleCondition析构的时候被卡住了,具体根本原因暂未查明
等分析后更新
解决方案:
目前临时解决方案
当播放器停止的时候在析构函数中通知checkIdleThread线程,将调用clearEasyContext(true).
保留checkIdleThread线程,但是在~CurlEasyManager的时候不再使用condition,重新封装一个资源释放的接口stopEasy,在外层播放器停止的时候主动释放资源,不再在析构函数函数中使用condition。
CurlEasyManager::~CurlEasyManager()
{
released = true;
/*{
std::unique_lock<std::mutex> idleLock(checkIdleMutex);
stop = true;
checkIdleCondition.notify_one();
}
checkIdleThread->stop();*/
}
void CurlEasyManager::stopEasy()
{
{
std::unique_lock<std::mutex> idleLock(checkIdleMutex);
stop = true;
checkIdleCondition.notify_one();
}
checkIdleThread->stop();
}