我正在尝试在我的Mac上使用semphore,当我尝试关闭一个打开的信号量时它会抛出一个错误。所有初始化都是成功的,但是当它尝试关闭第二个信号量时,它返回了错误的文件描述符错误。
下面的代码是打开和关闭的包装器:
void init_sem(sem_t * s, char * sema_name, int value)
{
if((s = sem_open(sema_name, O_CREAT, 0644, value)) == SEM_FAILED)
{
perror("sem_open");
exit(1);
}
printf("init semaphore %s\n", sema_name);
}
void destroy_sem(sem_t * s, char * sema_name)
{
printf("destroying, %s\n", sema_name);
if (sem_close(s) == -1) {
perror("sem_close");
exit(EXIT_FAILURE);
}
if (sem_unlink(sema_name) == -1) {
perror("sem_unlink");
exit(EXIT_FAILURE);
}
}
并在main.c
sem_t * s, *a, *b;
init_sem(s, "/cs", 0);
init_sem(a, "/ps", 0);
init_sem(b, "/bs", 0);
destroy_sem(s, "/cs");
destroy_sem(a, "/ps"); //got error here
destroy_sem(b, "/bs");
知道为什么它不起作用?
答案 0 :(得分:1)
您正在传递*s
,它将成为本地变量。为其分配值时,init_sem
返回时值将消失。然后,当您致电destroy_sim
时,您将未初始化的值传递给sem_close
。
您需要返回从sem_open
返回的值:
sem_t * init_sem(char * sema_name, int value)
{
sem_t * s;
if((s = sem_open(sema_name, O_CREAT, 0644, value)) == SEM_FAILED)
{
perror("sem_open");
exit(1);
}
printf("init semaphore %s\n", sema_name);
return s;
}
然后这样称呼:
s = init_sem("/cs", 0);
a = init_sem("/ps", 0);
b = init_sem("/bs", 0);
答案 1 :(得分:0)
加布的回答是正确的。
作为替代方案,您可以这样做:
void init_sem(sem_t ** s, char * sema_name, int value)
{
if((*s = sem_open(sema_name, O_CREAT, 0644, value)) == SEM_FAILED)
{
perror("sem_open");
exit(1);
}
printf("init semaphore %s\n", sema_name);
}
void destroy_sem(sem_t * s, char * sema_name)
{
printf("destroying, %s\n", sema_name);
if (sem_close(s) == -1) {
perror("sem_close");
exit(EXIT_FAILURE);
}
if (sem_unlink(sema_name) == -1) {
perror("sem_unlink");
exit(EXIT_FAILURE);
}
}
int main (int argc, const char * argv[])
{
sem_t * s, *a, *b;
init_sem(&s, "/cs", 0);
init_sem(&a, "/ps", 0);
init_sem(&b, "/bs", 0);
destroy_sem(s, "/cs");
destroy_sem(a, "/ps");
destroy_sem(b, "/bs");
}