假设已经初始化了共享的POSIX互斥锁(使用PTHREAD_PROCESS_SHARED).
然后,请考虑以下过程:
typedef struct {
pthread_mutex_t mutex;
// ...
} Shared;
Shared *shared = (Shared *)mmap(...); // MAP
pthread_mutex_lock(&shared->mutex); // LOCK
// REMAP
munmap(shared, ...);
shared = (Shared *)mmap(...);
pthread_mutex_unlock(&shared->mutex); // UNLOCK
POSIX是否保证这会像“天真”一样工作?
据我所知,相关的手册页都没有提到这种情况.
另外,以下Linux特定的替代方案如何:
Shared *shared = (Shared *)mmap(...); // MAP
pthread_mutex_lock(&shared->mutex); // LOCK
shared = (Shared *)mremap(shared, ...); // MREMAP_MAYMOVE
pthread_mutex_unlock(&shared->mutex); // UNLOCK
我可以想象,例如,PTHREADS实现将在进程内某处存储指向锁定互斥锁的指针.如果将互斥锁配置为健壮(PTHREAD_MUTEX_ROBUST),则在互斥锁被锁定时,如果进程终止,则允许实现将互斥锁标记为“已放弃”.
我不知道这样的方案是否真的有效,是否允许POSIX,或者如何在任何平台上实际实现互斥健壮性,但是如果沿着这些线的实现可行,并且根据POSIX有效,那么重新映射上面的场景会有不确定的行为.
最佳答案 没有!
正如@Celada所指出的,Linux中强大的互斥锁的实现假设锁定的健壮互斥体仍然保留在固定地址:
http://www.kernel.org/doc/Documentation/robust-futexes.txt
由此我们可以肯定地得出结论,POSIX允许实现禁止重新映射锁定的互斥锁.否则Linux实现将是不正确的.
因此,我在我的问题中概述的程序应被视为不正确,并导致未定义的行为.