【问题标题】:Parallelizing an Executable with I/O Text File in SLURM (C++)在 SLURM (C++) 中使用 I/O 文本文件并行化可执行文件
【发布时间】:2021-09-10 09:01:09
【问题描述】:

我有以下示意图并行化 for 循环(使用 OpenMP),

char command[200];
int thread_id;

# pragma omp parallel private(thread_id)
{
    thread_id = omp_get_thread_num();

    # pragma omp for
    for (int i = 0; i < max_value; i++) {
        // Generates a text file here (.inp) with a file name of node_(thread_id).inp

        std::sprintf(command, "executable.exe < node_%d.inp > node_%d.out", thread_id, thread_id);
        std::system(command);

        // Reads the output file node_(thread_id).out
    }
}

然后我使用 MPC 1.1.0 和 GCC 8.4.0 编译代码,并将其提交给 SLURM。该代码有时似乎运行良好,但我观察到有时文件名错误。例如,.inp 文件变为“nodee0.inp”或“node_0.o.o”。有时 SLURM 会引发分段错误错误,并且有时没有从节点 0 写入的文件,即文件名以节点 1 或 2 结尾,这与我期望的相反始终是“node_0”。

所以我的问题是,文件命名错误、分段错误错误以及丢失节点中的文件可能是什么原因?问题可能来自 SLURM,因为代码在其他时候运行良好,但我想知道是否应该在代码中编写或更改某些内容以减少这些错误的发生。

提前谢谢你。

【问题讨论】:

  • 我不会为此使用 OMP,而是使用一些外部库(例如 boost.process)来处理进程。这样多线程就会过时了。
  • 每个线程可能都使用同一个数组来存储命令。 command 定义在哪里?
  • @Marek R - 我还不熟悉 boost.process,但我发现这篇文章是 stackoverflow.com/questions/62602232/… 的开始。从这里开始,如果我的理解是正确的,我似乎需要先为所有迭代编写文件,然后将它们用作子进程的输入。但是max_value 太大了,可能会导致 50 万个输入文件。
  • @user253751 command 在循环外定义。
  • @mague_e 所以这是你的问题。

标签: c++ openmp slurm


【解决方案1】:

您只有一个 command 变量。每个线程都写入同一个数组,然后从该数组运行命令。如果线程幸运的话,同时没有其他线程更改数组。如果线程不走运,它会执行一些它想写的东西和其他线程想写的东西的混搭。

我对 OpenMP 或 SLURM 完全不熟悉,但您应该能够通过将其移动到循环内来解决这个问题,以便每次循环迭代都有自己的变量。

【讨论】:

  • 谢谢你!我在 for 循环中重新定位了 command 的定义,现在 .inp 和 .out 文件似乎没有问题。虽然我仍然遇到分段错误。
猜你喜欢
  • 1970-01-01
  • 2015-03-03
  • 2013-11-25
  • 2011-08-26
  • 2016-02-09
  • 2014-01-19
  • 1970-01-01
  • 1970-01-01
  • 2012-08-23
相关资源
最近更新 更多