这是我尝试过的一个简单实验:
给定一个名为“sim.exe”的任务,该任务进行模型模拟,然后我使用 MPI 在一个节点(共享内存系统)上同时启动 x“sim.exe”。我尝试了四种不同的运行,其中 x 为不同的值(例如,1、4、8、16)。然后我通过 PBS 报告“使用的内存”和“使用的 Vmem”检查内存使用情况。我观察到,对于这些不同的运行,“使用的内存”和“使用的 Vmem”保持不变,“mem”= 8,432 KB 和“vmem”= 489,716 KB。
根据帖子,我对“mem”和“vmem”的理解是作业使用的内存资源关于mem和vmem和进程实际内存使用情况。那么为什么即使作业的任务增加了x倍,“mem”和“vmem”仍然保持不变呢?
所有这些作业都是通过 PBS 作业调度程序提交的。对于每个作业,在提交作业时都会请求所有核心和 RAM#PBS -l select=1:ncpus=24:mem=96GB
此问题的更新:
我已经threading
在 python 中进行了测试,作为mpi
同时启动 x“sim.exe”的替代方案。所以我启动了x线程,并在每个线程中使用子进程来调用“sim.exe”模型模拟。我再次尝试了 x=1,4,8,16 的四个实验。我观察到作业使用的“mem”和“vmem”随着 x 的增加而线性增加,这接近我的预期。
那么,PBS 是否有可能没有正确计算“mem”和“vmen”?看来PBS只统计一个实例的内存使用情况。
答案1
我不确定,但据我记得 MPI 每个节点仅启动一个实例,然后在进行一些初始化后,将进程分叉到所请求的x
副本中。这意味着,如果sim.exe
在分叉后不分配任何额外的内存,则所有内存都将在副本之间共享,并且除了操作系统中用于跟踪进程的微小开销之外,x
数量对内存使用没有影响。x
如果您在分叉后加载一些数据或分配一些内存,您应该会看到内存使用率和x
.
在线程子进程场景中,所有x
进程都会进行自己的初始化,因此不会像 MPI 场景中那样共享那么多内存。 (它们仍将共享库内存和类似的内存映射 I/O。)
为了完全理解这种行为,我建议您编写一个小型 MPI 程序来替换sim.exe
它,该程序具有几 MB 的静态数据(例如某种类型的静态数组)和动态分配的内存,并且您可以尝试实例的大小和数量。我的猜测是,静态数据在同一节点上的并行 MPI 实例之间共享,而动态数据(在 MPI 分叉实例后分配)则不然。
进一步阅读: fork() 中的写时复制如何处理多个 fork?