Linux进程通信之semaphore(信号量)

首先,写一个通用的头文件myutili.h:

#ifndef _MYUTILI_H
#define _MYUTILI_H
#include<stdio.h>
#include<unistd.h>
#include<string.h>
#include<stdlib.h>
#include<sys/ipc.h>
#include<sys/sem.h>

union semun//联合
{
    int val;
    struct semid_ds *buf;
    unsigned short *array;
    struct seminfo *__buf;
};
key_t Ftok(const char *pathname, int proj_id)//包裹函数
{
    key_t key = ftok(pathname, proj_id);
    if(key== -1)
    {
        perror("fork.");
        exit(1);
    }
    return key;
}
int Semget(key_t key, int nsems, int semflg)//包裹函数
{
    int id = semget(key, nsems, semflg);
    if(id == -1)
    {
        perror("semget.");
        exit(1);
    }
    return id;
}
#endif

创建信号量的.c文件(create_sem.c):

#include"myutili.h"
int main(int argc, char *argv[])//用main()函数的参数来传执行参数
{
    key_t key = Ftok(argv[1], atoi(argv[2]));
    printf("sem key = 0x%x\n",key);

    int sem_id = Semget(key, 1, IPC_CREAT|IPC_EXCL|0755);
    printf("sem id = %d\n",sem_id);
    return 0;
}


删除信号量的.c文件(remove_sem.c):

#include"myutili.h"
int main(int argc, char *argv[])
{
    key_t key = Ftok(argv[1], atoi(argv[2]));
    int sem_id = Semget(key, 0, 0);
    int ret = semctl(sem_id,0, IPC_RMID);
    if(ret == -1)
        printf("remove sem Error.\n");
    else
        printf("remove sem ok.\n");
    return 0;
}


设置信号量的.c文件(set_sem.c):

#include"myutili.h"
int main(int argc, char *argv[])
{
    key_t key = Ftok(argv[1], atoi(argv[2]));
    int sem_id = Semget(key, 0, 0);
    union semun info;
    info.val = atoi(argv[3]);
    int ret = semctl(sem_id,0,SETVAL, info);
    if(ret == -1)
        printf("set sem Error.\n");
    else
        printf("set sem ok.\n");
    return 0;
}


获得信号量的.c文件(get_sem.c):

#include"myutili.h"
int main(int argc, char *argv[])
{
    key_t key = Ftok(argv[1], atoi(argv[2]));
    int sem_id = Semget(key, 0, 0);

    int val = semctl(sem_id, 0, GETVAL);
    printf("sem value = %d \n",val);
    return 0;
}


p操作的.c文件(p_sem.c):

#include"myutili.h"
int main(int argc, char *argv[])
{
    key_t key = Ftok(argv[1], atoi(argv[2]));
    int sem_id = Semget(key, 0, 0);

    struct sembuf arg;
    arg.sem_num = 0;
    arg.sem_op = -1;

    arg.sem_flg = 0;
    semop(sem_id,&arg, 1);
    return 0;
}


v操作的.c文件(v_sem.c):

#include"myutili.h"
int main(int argc, char *argv[])
{
    key_t key = Ftok(argv[1], atoi(argv[2]));
    int sem_id = Semget(key, 0, 0);

    struct sembuf arg;
    arg.sem_num = 0;
    arg.sem_op = 1;

    arg.sem_flg = 0;
    semop(sem_id,&arg, 1);
    return 0;
}


Makefile文件:

Obj=create_sem remove_sem set_sem get_sem p_sem v_sem
all:$(Obj)
create_sem:create_sem.c
	gcc -o create_sem create_sem.c
remove_sem:remove_sem.c	
	gcc -o remove_sem remove_sem.c
set_sem:set_sem.c
	gcc -o set_sem set_sem.c
get_sem:get_sem.c
	gcc -o get_sem get_sem.c
p_sem:p_sem.c
	gcc -o p_sem p_sem.c
v_sem:v_sem.c
	gcc -o v_sem v_sem.c
.PHONY:clean
clean:
	rm $(Obj) -fr

在CentOS 7环境下可以实现。都是关于semphore的基本操作。

semget函数创建一个信号灯集或是访问一个已经存在的信号灯集。

#inlude<sys/sem.h>
int semget(kty_t key, int nsems, int oflag);//返回:成功时为非负标识符,出错时为-1

猜你喜欢

转载自blog.csdn.net/qq_35353824/article/details/88642144