修复FilesystemWatcher中的线程安全问题

note:
实际使用中发现发送信号的同时添加文件会导致fdCacheMap异常,所以发送信号的流程也需要加锁,另外还需要发送完信号释放锁,避免调用removeWatchFile()后死锁
This commit is contained in:
Yue-Lan 2024-04-02 11:18:07 +08:00 committed by shaozhimin
parent c02b6a80c1
commit db9df55d1a
1 changed files with 13 additions and 4 deletions

View File

@ -307,7 +307,9 @@ QStringList FileWatcher::getWatchList(int attr)
void FileWatcher::sendSignal(int wfd, QString name, int mask)
{
std::unique_lock<std::mutex> lock(this->listLocker);
QString url = this->fdCacheMap[wfd];
QString path = this->fdCacheMap[wfd];
// 丢弃那些已经被移除的或者设定为不触发的监视器的事件
if (! this->watchList.contains(this->fdCacheMap[wfd]) || this->watchList[this->fdCacheMap[wfd]].type == NEVER)
@ -372,18 +374,25 @@ void FileWatcher::sendSignal(int wfd, QString name, int mask)
emit this->fileIgnoredAutomatic(isSubFile ? name : this->fdCacheMap[wfd], isSubFile ? this->fdCacheMap[wfd] : QString());
qDebug() << "File: "<<url<<" is ignored by kernel automatic.";
this->removeWatchFile(this->fdCacheMap[wfd]);
lock.release();
this->listLocker.unlock();
this->removeWatchFile(path);
}
if (mask & IN_UNMOUNT)
{
emit this->fileUnmount(isSubFile ? name : this->fdCacheMap[wfd], isSubFile ? this->fdCacheMap[wfd] : QString());
qDebug() << "File: "<<url<<" base fs is umount.";
this->removeWatchFile(this->fdCacheMap[wfd]);
lock.release();
this->listLocker.unlock();
this->removeWatchFile(path);
}
// 处理ONESHOT情况做一个contains判断避免之前被autoremove的文件索引出错
if (this->fdCacheMap.contains(wfd) && this->watchList[this->fdCacheMap[wfd]].type == ONESHOT)
this->removeWatchFile(this->fdCacheMap[wfd]);
if (this->fdCacheMap.contains(wfd) && this->watchList[this->fdCacheMap[wfd]].type == ONESHOT) {
lock.release();
this->listLocker.unlock();
this->removeWatchFile(path);
}
}
int FileWatcher::addWatchFile(FileWatcher::FileDescription node)