【问题标题】:MPI kill unwanted processesMPI 杀死不需要的进程
【发布时间】:2012-12-08 05:57:41
【问题描述】:

我将 OpenMPI 与 C 绑定一起使用。在我的代码中,有一定数量的进程。如果执行 MPI 时打开的进程多于所需进程,我希望终止或终止额外的进程。我该怎么做?

当我尝试用我能想到的几种方法时,我收到以下错误:

mpirun has exited due to process rank 3 with PID 24388 on
node pc15-373 exiting without calling "finalize". This may
have caused other processes in the application to be
terminated by signals sent by mpirun (as reported here).

【问题讨论】:

    标签: c mpi


    【解决方案1】:

    除了以下内容外,我没有太多要补充的内容。您实际上可以调用MPI_FINALIZE 并退出多余的进程,但您必须意识到这将破坏世界通信器MPI_COMM_WORLD 上所有进一步的集体操作 - 其中大多数根本无法完成(@987654323 @ 是肯定会挂起的那个)。为了防止这种情况,您可能需要首先创建一个排除所有不必要进程的新通信器:

    int rank, size;    
    MPI_Comm_rank(MPI_COMM_WORLD, &rank);
    MPI_Comm_size(MPI_COMM_WORLD, &size);
    
    // Obtain the group of processes in the world communicator
    MPI_Group world_group;
    MPI_Comm_group(MPI_COMM_WORLD, &world_group);
    
    // Remove all unnecessary ranks
    MPI_Group new_group;
    int ranges[3] = { process_limit, size-1, 1 };
    MPI_Group_range_excl(world_group, 1, ranges, &new_group);
    
    // Create a new communicator
    MPI_Comm newworld;
    MPI_Comm_create(MPI_COMM_WORLD, new_group, &newworld);
    
    if (newworld == MPI_COMM_NULL)
    {
       // Bye bye cruel world
       MPI_Finalize();
       exit(0);
    }
    
    // From now on use newworld instead of MPI_COMM_WORLD
    

    此代码首先获取MPI_COMM_WORLD 中的进程组,然后创建一个排除process_limit 以后所有进程的新组。然后它从新的进程组创建一个新的通信器。 MPI_COMM_CREATE 操作将在这些不属于新组的进程中返回MPI_COMM_NULL,并且此事实用于终止此类进程。鉴于在此之后某些进程将从MPI_COMM_WORLD“消失”,它不再可用于广播、屏障等集体操作,而应使用newworld

    另外,正如 Mark 所指出的,在某些架构上,额外的进程实际上可能会在它们从 main 返回之后仍然存在。例如,在 Blue Gene、Cray 或任何其他使用硬件分区来管理 MPI 作业的系统上,在整个 MPI 作业完成之前不会释放额外的资源。如果程序在资源管理器(例如 SGE、LSF、Torque、PBS、SLURM 等)控制下的集群或其他系统上运行,也会出现这种情况。

    我通常处理这种情况的方法是非常务实的:

    int size, rank;
    
    MPI_Comm_rank(MPI_COMM_WORLD, &rank);
    MPI_Comm_size(MPI_COMM_WORLD, &size);
    if (size != process_limit)
    {
       if (rank == 0)
          printf("Please run this program with %d MPI processes\n", process_limit);
       MPI_Finalize();
       exit(1);
    }
    

    您也可以使用MPI_Abort(MPI_COMM_WORLD, 0); 代替MPI_Finalize() 来惹恼用户:)

    您还可以使用 MPI 的进程生成功能,但这会使代码变得更加复杂,因为您必须处理相互通信器。

    【讨论】:

    • 感谢您和 HP Mark 提供的帮助 cmets。我最终只是简单地允许额外的进程完成并从 main 中返回。这释放了我桌面上的资源,但是,当然,这并不能很好地表明它在“真实”环境中的表现。我将提交我的工作(在我正在使用的 IBM Bladecenter 上使用 LSF)并看看会发生什么。但是,您的高度务实的方法可能只是门票,特别是因为在我的情况下,我总是事先知道要生成多少进程,并且只有我会运行代码。
    【解决方案2】:

    这可能是一个扩展评论而不是答案,但在 Hristo Iliev 出现之前,这可能会有所帮助......

    我不确定你能不能做你想做的事。我相信,如果您尝试使用非 MPI 功能(例如 Linux kill)终止 MPI 进程,则 MPI 运行时将崩溃,因为其中一个进程意外退出。您报告的错误消息往往支持我的想法。

    您可以在不需要的进程上调用MPI_FINALIZE,但请注意,MPI 标准不要求底层操作系统进程(或线程或其他)实际停止。对MPI_FINALIZE 的调用完成了挂起的 MPI 操作,并阻止了对该进程的(几乎所有)MPI 函数的进一步调用。这也可能不是您想要的。我想你可能会很幸运kill一个已经完成的进程,MPI 运行时可能不会崩溃;这不是我曾经尝试过的东西。

    您可以采用不同的方法并使用 MPI 的功能来生成新进程;在一个进程上启动程序,然后通过调用MPI_SPAWN_PROCESS 及其关系生成程序使用的数字。除了 MPI 例程之外,您还需要调查生成如何与平台的进程管理进行交互。您可能会发现您的系统未配置为允许通过运行 MPI 作业进行动态进程管理。

    【讨论】:

    • 谢谢,惠普马克。我前天刚开始学习 MPI,很高兴听到那些显然有丰富经验的人的意见。
    【解决方案3】:

    简单

    杀死 mpiexec.exe

    在 Windows 上,所有连接的进程(mpiexec.exe、PMI proxy.exe、IMB MPI1.exe)都将被终止。

    【讨论】:

      猜你喜欢
      • 2011-07-28
      • 2018-11-05
      • 2021-07-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-06-12
      相关资源
      最近更新 更多