生产者和消费者(PV操作、共享内存)

生产者一直在往共享内存中写数据

#include
#include
#include
#include
#include
#include"shm.h"

int main()
{
    int ret;
    int shmid;
    int semid;
    int running;

    void *share_memory;
    struct shm *shm_buf;


    //创建信号量
    semid = semget(ftok(".",'a'),1,IPC_CREAT);
    if(semid < 0)
    {
        perror("semid:");
    exit(1);
    }
    //初始化信号量
    sem_init(semid,1);

    //创建共享内存
    shmid = shmget(ftok(".",'b'),sizeof(struct shm),IPC_CREAT);
    if(shmid < 0)
    {
        perror("shmget:");
    exit(1);
    }
    //映射共享内存
    share_memory = shmat(shmid,NULL,0);
    if(share_memory == (void *)-1)
    {
        perror("shmat:");
    sem_del(semid);
    exit(1);
    }

    printf("share_memory = %p\n",share_memory);
    //指向共享内存
    shm_buf = (struct shm*)share_memory;

    while(running)
    {
        p_sem(semid);//
    printf("please input something to memory:\n");
    scanf("%s",&shm_buf->buf);

    shm_buf->flag = getpid();

    if(strcmp(shm_buf->buf,"end") == 0)
    {
        running = 0;
    }

    v_sem(semid);//做加法

    }

    sem_del(semid);

    if(shmdt(share_memory) == -1)
    {
        perror("shmdt:");
    exit(1);
    }

    return 0;
}

消费者一直从内存中读取数据,一次读完之后就把内存清空

#include
#include
#include
#include
#include
#include
#include
#include"shm.h"

int main()
{
    struct shm *shm_buf;
    void *share_memory;

    int semid;
    int shmid;
    int running = 1;
//创建信号量,生产者和消费者的key值要对应相等
    semid = semget(ftok(".",'a'),1,0666);
    if(semid == -1)
    {
        perror("producer do not exit:");
    exit(1);
    } 

    shmid = shmget(ftok(".",'b'),sizeof(struct shm),IPC_CREAT);
    if(shmid == -1)
    {
        perror("shmget error:");
    exit(1);
    }

    share_memory = shmat(shmid,NULL,0);
    if(share_memory == (void *)-1)
    {
        perror("shmat failed:");
    exit(1);
    }

    printf("share_memory = %p\n",share_memory);

    shm_buf = (struct shm*)share_memory;

    while(running)
    {
        p_sem(semid);  

    printf("process write memory %d: %s\n",shm_buf->flag,shm_buf->buf);

    if(strcmp(shm_buf->buf,"end") == 0)
    {
        //running = 0;
        exit(1);
    }

    shm_buf->flag = 0;
    memset(shm_buf->buf,0,BUF_SIZE);
    v_sem(semid);
    }

    if(shmdt(share_memory) == -1)
    {
        perror("share_memory:");
    exit(1);
    }

    if(shmctl(shmid,IPC_RMID,NULL) == -1)
    {
        perror("shmctl:");
    exit(1);
    }
    exit(0);
}

头文件:

#include
#include
#include
#include
#include
#include
#include
#include"shm.h"

int main()
{
    struct shm *shm_buf;
    void *share_memory;

    int semid;
    int shmid;
    int running = 1;

    semid = semget(ftok(".",'a'),1,0666);
    if(semid == -1)
    {
        perror("producer do not exit:");
    exit(1);
    } 

    shmid = shmget(ftok(".",'b'),sizeof(struct shm),IPC_CREAT);
    if(shmid == -1)
    {
        perror("shmget error:");
    exit(1);
    }

    share_memory = shmat(shmid,NULL,0);
    if(share_memory == (void *)-1)
    {
        perror("shmat failed:");
    exit(1);
    }

    printf("share_memory = %p\n",share_memory);

    shm_buf = (struct shm*)share_memory;

    while(running)
    {
        p_sem(semid);  

    printf("process write memory %d: %s\n",shm_buf->flag,shm_buf->buf);

    if(strcmp(shm_buf->buf,"end") == 0)
    {
        //running = 0;
        exit(1);
    }

    shm_buf->flag = 0;
    memset(shm_buf->buf,0,BUF_SIZE);
    v_sem(semid);
    }

    if(shmdt(share_memory) == -1)
    {
        perror("share_memory:");
    exit(1);
    }

    if(shmctl(shmid,IPC_RMID,NULL) == -1)
    {
        perror("shmctl:");
    exit(1);
    }
    exit(0);
}

重写的pv操作、删除信号量和初始化信号量的函数

#include
#include
#include
#include

#include"shm.h"

int sem_init(int semid,int pid)
{
    union semnum sem_num;
    sem_num.pid = pid;

    if(semctl(semid,0,SETVAL,sem_num) == -1)
    {
        perror("fail sem_init");
    exit(1);
    }
    return 0;
}

int sem_del(int semid)
{
    union semnum sem_num;

    if(semctl(semid,0,IPC_RMID,sem_num) == -1)
    {
        perror("fail sem_del:");
    exit(1);
    }
    return 0;
}

int p_sem(int semid)
{
    struct sembuf sem;
    sem.sem_num = 0;
    sem.sem_op = -1;
    sem.sem_flg = SEM_UNDO;

    if(semop(semid,&sem,1) == -1)
    {
        perror("fail to p:");
    exit(1);
    }
    return 0;
}

你可能感兴趣的:(linux,c,C语言,面试笔试题)