什么时候调用sem_unlink()?

use*_*642 13 linux semaphore

我对Linux API sem_unlink()感到有些困惑,主要是在何时或为何调用它.我在Windows中使用了多年的信号量.在Windows中,一旦关闭了命名信号量的最后一个句柄,系统就会删除底层内核对象.但是在Linux中,开发人员需要通过调用sem_unlink()来删除内核对象.如果不这样做,内核对象将保留在/ dev/shm文件夹中.

我遇到的问题是,如果进程A调用sem_unlink()而进程B锁定了信号量,它会立即销毁信号量,当进程C出现时,进程B不再被信号量"保护".更重要的是,手册页充其量令人困惑:

"信号量名称立即被删除.一旦所有其他具有信号量打开的进程关闭它,信号量就会被破坏."

如果它必须等待其他进程关闭信号量,它如何立即销毁对象?

显然,我不明白在Linux上正确使用信号量对象.谢谢你的帮助.下面是我用来测试它的一些示例代码.

int main(void)
{
    sem_t *pSemaphore = sem_open("/MyName", O_CREAT, S_IRUSR | S_IWUSR, 1);
    if(pSemaphore != SEM_FAILED)
    {
        if(sem_wait(pSemaphore) == 0)
        {
            // Perform "protected" operations here

            sem_post(pSemaphore);
        }

        sem_close(pSemaphore);
        sem_unlink("/MyName");
    }

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

小智 10

回答您的问题:

  1. 与您描述的窗口的信号量行为相比,POSIX信号量是内核持久性的.这意味着即使没有进程打开信号量,信号量也会保留它的值.(信号量的引用计数为0)

  2. 如果进程A调用sem_unlink()而进程B锁定了信号量.这意味着信号量的引用计数不为0且不会被破坏.

sem_close与sem_unlink的基本操作,我认为将有助于全面理解:

sem_close: close是一个信号量,这也是在进程退出时完成的.信号量仍然存在于系统中.

sem_unlink:仅当引用计数达到0时(即在所有打开它的进程之后,调用sem_close或退出)将从系统中删除.

参考文献: Book - Unix网络编程 - 进程间通信,作者:W.Richard Stevens,第2卷,第10章


小智 5

sem_unlink()函数删除由名称标识的信号量,并在所有进程停止使用该信号量后将其标记为销毁(这可能意味着立即,如果打开该信号量的所有进程都已关闭该信号量)。