#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <sys/sem.h>
#include <sys/ipc.h>
#include <errno.h>
union semun
{
int val;
struct semid_ds *buf;
unsigned short int *array;
//struct seminfo * __buf;
};
static int init_sem( int id );
static int close_sem( int id );
static int sem_p( int id );
static int sem_v( int id );
int main( int argc , char *argv[] )
{
char *message = "X";
int sem_id = 0;
sem_id = semget( (key_t)1234, 1, 0666 | IPC_CREAT );
printf("sem_id = %d\n" , sem_id);
if( argc > 1 )
{
if( init_sem( sem_id ) == 0 )
{
printf("sem init error return!\n");
exit(1);
}
message = argv[1];
}
while(1)
{
if( sem_p( sem_id ) == -1 )
{
exit(1);
}
printf("%s\n" , message);
sleep(rand() % 3);
printf("%s\n" , message);
if( sem_v( sem_id ) == -1 )
{
exit(1);
}
sleep( rand() %3 );
}
if( argc > 1 )
{
close_sem( sem_id );
}
return 0;
}
static int init_sem( int id )
{
union semun sem_union;
sem_union.val = 1;
if( semctl( id, 0, SETVAL, sem_union ) == -1 )
{
printf(" semctl:%s\n" , strerror(errno));
return 0;
}
return 1;
}
static int close_sem( int id )
{
if( semctl( id, IPC_RMID, 0 ) == -1 )
{
printf("delete sem error!\n");
return 0;
}
return 1;
}
static int sem_p( int id )
{
//-1 wait for p
struct sembuf sem_buf;
sem_buf.sem_num = 0;
sem_buf.sem_op = -1;
sem_buf.sem_flg = SEM_UNDO;
if( semop( id, &sem_buf, 1 ) == -1 )
{
printf(" semop:%s\n" , strerror(errno));
printf("sem_p set error!\n");
return -1;
}
return 1;
}
static int sem_v( int id )
{
//1 send singal v
struct sembuf sem_buf;
sem_buf.sem_num = 0;
sem_buf.sem_op = 1;
sem_buf.sem_flg = SEM_UNDO;
if( semop( id, &sem_buf, 1 ) == -1 )
{
printf(" semop:%s\n" , strerror(errno));
printf("sem_v set error!\n");
return -1;
}
return 1;
}
参考:https://blog.csdn.net/ljianhui/article/details/10243617
以上代码为改正后的代码。
实验结果和参考的博客一致,功能相当于两个进程之间的互斥锁。
出现的问题:
1.semctl函数报错:numerical result out of range
原因是原来的代码子进程的运行流程没有semget,导致传给semctl的id是0,超出范围。
2.semop函数报错:Invalid argument,同理也是因为id号为0导致非法参数。