C++ Linux共享内存

来自泡泡学习笔记
BrainBs讨论 | 贡献2024年12月4日 (三) 12:39的版本 (创建页面,内容为“==概念与原理== 共享内存是一种高效的进程间通信机制,允许多个进程直接访问同一块物理内存。共享内存是所有IPC机制中最快的,因为数据不需要在内核和用户空间之间进行复制。 ==核心点== * 创建共享内存:使用shmget系统调用创建。 * 附加共享内存:使用shmat系统调用将共享内存附加到进程地址空间。 * 分离共享内存:使用shmdt系统调用分离共享…”)
(差异) ←上一版本 | 最后版本 (差异) | 下一版本→ (差异)
跳到导航 跳到搜索

概念与原理

共享内存是一种高效的进程间通信机制,允许多个进程直接访问同一块物理内存。共享内存是所有IPC机制中最快的,因为数据不需要在内核和用户空间之间进行复制。


核心点

  • 创建共享内存:使用shmget系统调用创建。
  • 附加共享内存:使用shmat系统调用将共享内存附加到进程地址空间。
  • 分离共享内存:使用shmdt系统调用分离共享内存。
  • 删除共享内存:使用shmctl系统调用删除共享内存。


实现实例

#include <iostream>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/wait.h>
#include <cstring>
#include <unistd.h>

#define SHM_SIZE 1024  // 共享内存大小

int main() {
    key_t key = ftok("shmfile", 65);  // 生成唯一键
    int shmid = shmget(key, SHM_SIZE, 0666|IPC_CREAT);  // 创建共享内存段
    char *str = (char*) shmat(shmid, nullptr, 0);  // 附加到共享内存
 
    pid_t cpid = fork();
    if (cpid == -1) {
        perror("fork");
        exit(EXIT_FAILURE);
    }
 
    if (cpid == 0) {    // 子进程
        sleep(1);  // 确保父进程先写入
        std::cout << "子进程从共享内存读取数据:\n";
        std::cout << str << std::endl;
        shmdt(str);  // 分离共享内存
        _exit(EXIT_SUCCESS);
    } else {            // 父进程
        std::cout << "父进程写入共享内存:\n";
        const char* msg = "来自父进程的消息";
        strncpy(str, msg, SHM_SIZE);
        wait(NULL);  // 等待子进程
        shmdt(str);  // 分离共享内存
        shmctl(shmid, IPC_RMID, nullptr);  // 删除共享内存
        exit(EXIT_SUCCESS);
    }
}


解析:

ftok("shmfile", 65):生成一个唯一键。

shmget(key, SHM_SIZE, 0666 | IPC_CREAT):创建共享内存段。

shmat(shmid, NULL, 0):将共享内存段附加到进程地址空间。


子进程:等待父进程将数据写入共享内存,从共享内存读取数据并显示。

父进程:将数据写入共享内存,等待子进程结束,分离并删除共享内存段。


运行结果:

父进程写入共享内存:
子进程从共享内存读取数据:
来自父进程的消息