You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

能否为MPI行通信子内的进程使用shmget创建共享内存?

能否用shmget()为MPI行通信子内的进程创建共享内存?

shmget函数用于基于键值创建新共享内存段或查找现有共享内存段,共享内存段是可被多个进程共享的内存区域。目前已通过MPI_Comm_split创建了行通信子,计划使用shmget而非MPI_win_allocate函数,想问是否可行?

核心结论

可以,但有严格的前提条件和需要注意的实现细节:

前提条件

行通信子内的所有进程必须运行在同一物理节点上。因为shmget属于System V共享内存机制,仅支持同一节点内的进程共享,跨节点进程无法通过该方式访问共享内存。

实现步骤

  1. 指定创建者:选择行通信子内的某一个进程(比如rank为0的进程)作为共享内存的创建者,调用shmget()创建内存段。可以选择IPC_PRIVATE作为键值(仅能通过传递shmid共享,避免键冲突),或者用ftok()生成唯一自定义键。
  2. 传递共享内存标识符:创建者通过MPI通信(比如MPI_Bcast)将生成的shmid发送给行通信子内的所有其他进程。
  3. 映射内存段:所有进程调用shmat()将共享内存段映射到自身的地址空间,之后即可像访问普通内存一样操作该区域。
  4. 清理资源:使用完毕后,所有进程调用shmdt()解除内存映射,最后由创建者调用shmctl()删除共享内存段。

关键注意事项

  • 同步机制:shmget不提供进程间同步,需要自行通过System V信号量(semget())或MPI同步操作(比如MPI_Barrier)保证内存访问的有序性,避免竞态条件。
  • 权限设置:调用shmget时需设置正确的权限位(如0666),确保行通信子内所有进程都能访问该共享内存段。
  • 键值冲突:如果使用自定义键,务必保证键值全局唯一,避免与系统中其他共享内存段冲突。

已实现的MPI行通信子代码

// 获取原始通信子中的进程rank和总数量
int world_rank, world_size;
MPI_Comm_rank(MPI_COMM_WORLD, &world_rank);
MPI_Comm_size(MPI_COMM_WORLD, &world_size);

int color = world_rank / 4; // 根据进程所在行确定color值

// 根据color拆分通信子,用原始rank排序
MPI_Comm row_comm;
MPI_Comm_split(MPI_COMM_WORLD, color, world_rank, &row_comm);

int row_rank, row_size;
MPI_Comm_rank(row_comm, &row_rank);
MPI_Comm_size(row_comm, &row_size);

printf("全局进程RANK/SIZE: %d/%d \t 行通信子RANK/SIZE: %d/%d\n",
world_rank, world_size, row_rank, row_size);

MPI_Comm_free(&row_comm);

内容的提问来源于stack exchange,提问作者Ishan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.24 19:44:57