【问题标题】:What happens to a lock on a boost interprocess mutex if a process forks while the lock is acquired?如果在获取锁时进程分叉,那么在 boost 进程间互斥锁上的锁会发生什么?
【发布时间】:2014-11-07 21:27:45
【问题描述】:

假设我们有一个有两个线程的进程。一个线程在一些共享资源上做一些工作,并定期在 boost::interprocess::mutex 上取出一个作用域锁。另一个线程在某个随机时间导致 fork/exec。

线程 1

void takeLockDoWork() {
    using namespace boost::interprocess;
    managed_shared_memory segment(open_only, "xxx");
    interprocess_sharable_mutex *mutex = segment.find<interprocess_sharable_mutex>("mymutex").first;
    scoped_lock<interprocess_sharable_mutex> lock(*mutex);
    // access or do work on a shared resource here
    //lock automatically unlocks when scope is left.
}

假设线程 2 在 scoped_lock 被取出后立即分叉。大概子进程和父进程有相同的锁状态。

会发生什么?现在是否会出现与父进程的竞争条件?

【问题讨论】:

  • 一个更有趣的问题是,如果在共享资源被写入中间时发生分叉会发生什么。即使系统足够聪明,可以让其中一个线程等待再次获取互斥锁,但当该线程确实获取了互斥锁时,它对共享资源的看法可能与它启动时不同(因为另一个线程可能已经完成了任何操作任务它在它分叉的中间)。我强烈建议将分叉与读/写锁同步;所有线程都可以持有一个读锁来防止分叉,并获得一个写锁来分叉。
  • 我强烈建议不要在有多个线程时分叉。如果需要,在每个子进程中打开 shmem。或者从一开始就将共享进程与分叉进程隔离开来。任何不依赖于平台相关/未指定行为的东西。

标签: c++ boost concurrency boost-interprocess


【解决方案1】:

只要您不从持有interprocess_sharable_mutex 的线程派生或访问受互斥锁保护的内存,就可以。

互斥体存在于共享内存中,这意味着即使您分叉,互斥体状态也不会重复;它存在于一个地方,两个进程都可以访问。

因为forking只在child中维护forking线程,只有parent中的其他线程认为自己拥有mutex的所有权,所以没有问题。即使你在分叉后尝试获取互斥体,你仍然可以;它只会阻塞,直到父级释放它。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-11-18
    • 2012-12-25
    • 2021-10-10
    • 1970-01-01
    • 2010-11-05
    相关资源
    最近更新 更多