2022.9.02 共享内存的特点,共享内存的原理示意图,共享内存的创建,实现共享内存传送消息完整代码。

发布于:2022-12-31 ⋅ 阅读:(294) ⋅ 点赞:(0)

共享内存

共享内存的特点:

  1. :共享内存是一种最为高效的进程间通信方式。
  2. :进程可直接读写内存,不需要数据的复制。
  3. :内核专门留出一块内存区,此内存区可以由需要访问的进程将其映射到自己私有的地址空间。
  4. :由于多个进程访问一块共享内存,因此,也需要某种同步机制,如互斥锁和信息量。

共享内存的原理示意图:

共享内存的创建

第一步:创建共享内存 shmget()函数,成功:返回共享内存标识符,失败:返回-1;

第二步:映射共享内存到具体的进程空间中: shmat()函数,成功:返回被映射的段地址

失败:返回-1。

第三步:解除与共享内存的映射关系 shmdt()函数,成功返回0,失败返回-1.

第四步:删除共享内存。

实现共享内存传送消息完整代码:

接收消息代码:

#include<stdio.h>
#include<sys/ipc.h>
#include<sys/shm.h>
#include<sys/types.h>
#include<unistd.h>
#include<signal.h>
void sigFunc(int signum)
{
    if(SIGUSR1 == signum)
    {
    }
}

int main()
{
    pid_t pid = 
    key_t key = ftok(".",10);
    if(key < 0)
    {
        perror("ftok error!");
        return -1;
    }
    printf("key = %d\n",key);
    int shmld = shmget(key,100,0666|IPC_CREAT);
    if(shmld < 0)
    {
        perror("shmget error!");
        return -1;
    }
    printf("shmld = %d\n",shmld);
    pid_t pid = getpid();
    printf("shm_r pid: %d\n",pid);
    pid_t *p1 = shmat(shmld,NULL,0);
    if((pid_t*)-1 == p1)
    {
        perror("shmat error!");
        shmctl(shmld,IPC_RMID,NULL);
        return -1;
    }
    *p1 = pid;
    shmdt(p1);
    void*p = shmat(shmld,NULL,0);
    if((void *)-1 == p)
    {
        perror("shmat error!");
        shmctl(shmld,IPC_RMID,NULL);
        return 0;
    }
    while(1)
    {
        signal(SIGUSR1,sigFunc);
        pause();
    printf("rec : %d\n",*((int *)p));
    }
    //shmdt(p);
//    shmctl(shmld,IPC_RMID,NULL);
    return 0;
}

发送消息代码:

#include<stdio.h>
#include<sys/types.h>
#include<sys/ipc.h>
#include<sys/shm.h>
#include<unistd.h>
#include<signal.h>

int main()
{
    key_t key = ftok(".",10);
    if(key < 0)
    {
        perror("ftok error!");
        return -1;
    }
    printf("key = %d\n",key);
    int shmld = shmget(key,100,0666|IPC_CREAT);
    if(shmld < 0)
    {
        perror("shmget error!");
        return -1;
    }
    printf("shmld = %d\n",shmld);
    void *p1 = shmat(shmld,NULL,0);
    if((void*)-1 ==p1)
    {
        perror("shmat error!");
        shmctl(shmld,IPC_RMID,NULL);
        return -1;
    }
    pid_t pid = *(pid_t*)p1;
    printf("shm_r pid :%d\n",pid);
    shmdt(p1);
       void *p =shmat(shmld,NULL,0);
    while(1)
    {
         if((void*)-1 ==p)
          {
             perror("shmat error!");
            shmctl(shmld,IPC_RMID,NULL);
            return 0;
        }
          printf("intput int:");
         scanf("%d",(int *)p);
         kill(pid,SIGUSR1);
    }
        shmdt(p);
       return 0;
}

运行操作:gcc shem_r.c -o r -lpthread   

                   gcc shem_wc -o w -lpthread

注意:先./r   再./w  因为首先先将shem_r创建的pid发送于shem_w,从而shem_w通过pid给进程shem_r发送消息。

实现结果:

 

 


网站公告

今日签到

点亮在社区的每一天
去签到