HPC MPIcluster 上的 R 运行 foreach dopar 循环
R Running foreach dopar loop on HPC MPIcluster
我可以访问带有 MPI 分区的 HPC 集群。
我的问题是 - 无论我尝试什么 - 我的代码(在我的 PC 上运行良好)在 HPC 集群上都不 运行。代码如下所示:
library(tm)
library(qdap)
library(snow)
library(doSNOW)
library(foreach)
> cl<- makeCluster(30, type="MPI")
> registerDoSNOW(cl)
> np<-getDoParWorkers()
> np
> Base = "./Files1a/"
> files = list.files(path=Base,pattern="\.txt");
>
> for(i in 1:length(files)){
...some definitions and variable generation...
+ text<-foreach(k = 1:10, .combine='c') %do%{
+ text= if (file.exists(paste("./Files", k, "a/", files[i], sep=""))) paste(tolower(readLines(paste("./Files", k, "a/", files[i], sep=""))) , collapse=" ") else ""
+ }
+
+ docs <- Corpus(VectorSource(text))
+
+ for (k in 1:10){
+ ID[k] <- paste(files[i], k, sep="_")
+ }
+ data <- as.data.frame(docs)
+ data[["docs"]]=ID
+ rm(docs)
+ data <- sentSplit(data, "text")
+
+ frequency=NULL
+ cs <- ceiling(length(POLKEY$x) / getDoParWorkers())
+ opt <- list(chunkSize=cs)
+ frequency<-foreach(j = 2: length(POLKEY$x), .options.mpi=opt, .combine='cbind') %dopar% ...
+ write.csv(frequency, file =paste("./Result/output", i, ".csv", sep=""))
+ rm(data, frequency)
+ }
当我 运行 批处理作业时,会话在时间限制内被终止。而我在 MPI 集群初始化后收到以下消息:
Loading required namespace: Rmpi
--------------------------------------------------------------------------
PMI2 initialized but returned bad values for size and rank.
This is symptomatic of either a failure to use the
"--mpi=pmi2" flag in SLURM, or a borked PMI2 installation.
If running under SLURM, try adding "-mpi=pmi2" to your
srun command line. If that doesn't work, or if you are
not running under SLURM, try removing or renaming the
pmi2.h header file so PMI2 support will not automatically
be built, reconfigure and build OMPI, and then try again
with only PMI1 support enabled.
--------------------------------------------------------------------------
--------------------------------------------------------------------------
An MPI process has executed an operation involving a call to the
"fork()" system call to create a child process. Open MPI is currently
operating in a condition that could result in memory corruption or
other system errors; your MPI job may hang, crash, or produce silent
data corruption. The use of fork() (or system() or other calls that
create child processes) is strongly discouraged.
The process that invoked fork was:
Local host: ...
MPI_COMM_WORLD rank: 0
If you are *absolutely sure* that your application will successfully
and correctly survive a call to fork(), you may disable this warning
by setting the mpi_warn_on_fork MCA parameter to 0.
--------------------------------------------------------------------------
30 slaves are spawned successfully. 0 failed.
不幸的是,由于没有返回任何输出,因此循环似乎没有进行一次。
为了完整起见,我的批处理文件:
#!/bin/bash -l
#SBATCH --job-name MyR
#SBATCH --output MyR-%j.out
#SBATCH --nodes=5
#SBATCH --ntasks-per-node=6
#SBATCH --mem=24gb
#SBATCH --time=00:30:00
MyRProgram="$HOME/R/hpc_test2.R"
cd $HOME/R
export R_LIBS_USER=$HOME/R/Libs2
# start R with my R program
module load R
time R --vanilla -f $MyRProgram
有没有人有解决问题的建议?我做错了什么?
在此先感谢您的帮助!
您的脚本是一个 MPI 应用程序,因此您需要通过 Slurm 适当地执行它。 Open MPI FAQ 有专门的部分介绍如何做到这一点:
最重要的一点是你的脚本不应该直接执行 R,而是应该通过 mpirun 命令执行它,使用类似:
mpirun -np 1 R --vanilla -f $MyRProgram
我的猜测是"PMI2"错误是由于没有通过mpirun执行R造成的。我不认为 "fork" 消息表示真正的问题,它有时会发生在我身上。我认为这是因为 R 在初始化时调用 "fork",但这从来没有给我带来问题。我不确定为什么我只是偶尔收到此消息。
请注意,告诉 mpirun 仅启动一个进程非常重要,因为其他进程将被派生,因此您应该使用 mpirun -np 1
选项。如果 Open MPI 是使用 Slurm 支持正确构建的,那么 Open MPI 应该知道在生成这些进程时在哪里启动这些进程,但是如果你不使用 -np 1
,那么通过 mpirun 启动的所有 30 个进程将分别生成 30 个进程,造成了巨大的混乱。
最后,我认为您应该告诉 makeCluster
仅生成 29 个进程以避免 运行 总共 31 个 MPI 进程。根据您的网络配置,即使超额订阅也会导致问题。
我将按如下方式创建集群对象:
library(snow)
library(Rmpi)
cl<- makeCluster(mpi.universe.size() - 1, type="MPI")
这样更安全,更容易使 R 脚本和作业脚本保持同步。
我可以访问带有 MPI 分区的 HPC 集群。
我的问题是 - 无论我尝试什么 - 我的代码(在我的 PC 上运行良好)在 HPC 集群上都不 运行。代码如下所示:
library(tm) library(qdap) library(snow) library(doSNOW) library(foreach)
> cl<- makeCluster(30, type="MPI")
> registerDoSNOW(cl)
> np<-getDoParWorkers()
> np
> Base = "./Files1a/"
> files = list.files(path=Base,pattern="\.txt");
>
> for(i in 1:length(files)){
...some definitions and variable generation...
+ text<-foreach(k = 1:10, .combine='c') %do%{
+ text= if (file.exists(paste("./Files", k, "a/", files[i], sep=""))) paste(tolower(readLines(paste("./Files", k, "a/", files[i], sep=""))) , collapse=" ") else ""
+ }
+
+ docs <- Corpus(VectorSource(text))
+
+ for (k in 1:10){
+ ID[k] <- paste(files[i], k, sep="_")
+ }
+ data <- as.data.frame(docs)
+ data[["docs"]]=ID
+ rm(docs)
+ data <- sentSplit(data, "text")
+
+ frequency=NULL
+ cs <- ceiling(length(POLKEY$x) / getDoParWorkers())
+ opt <- list(chunkSize=cs)
+ frequency<-foreach(j = 2: length(POLKEY$x), .options.mpi=opt, .combine='cbind') %dopar% ...
+ write.csv(frequency, file =paste("./Result/output", i, ".csv", sep=""))
+ rm(data, frequency)
+ }
当我 运行 批处理作业时,会话在时间限制内被终止。而我在 MPI 集群初始化后收到以下消息:
Loading required namespace: Rmpi
--------------------------------------------------------------------------
PMI2 initialized but returned bad values for size and rank.
This is symptomatic of either a failure to use the
"--mpi=pmi2" flag in SLURM, or a borked PMI2 installation.
If running under SLURM, try adding "-mpi=pmi2" to your
srun command line. If that doesn't work, or if you are
not running under SLURM, try removing or renaming the
pmi2.h header file so PMI2 support will not automatically
be built, reconfigure and build OMPI, and then try again
with only PMI1 support enabled.
--------------------------------------------------------------------------
--------------------------------------------------------------------------
An MPI process has executed an operation involving a call to the
"fork()" system call to create a child process. Open MPI is currently
operating in a condition that could result in memory corruption or
other system errors; your MPI job may hang, crash, or produce silent
data corruption. The use of fork() (or system() or other calls that
create child processes) is strongly discouraged.
The process that invoked fork was:
Local host: ...
MPI_COMM_WORLD rank: 0
If you are *absolutely sure* that your application will successfully
and correctly survive a call to fork(), you may disable this warning
by setting the mpi_warn_on_fork MCA parameter to 0.
--------------------------------------------------------------------------
30 slaves are spawned successfully. 0 failed.
不幸的是,由于没有返回任何输出,因此循环似乎没有进行一次。
为了完整起见,我的批处理文件:
#!/bin/bash -l
#SBATCH --job-name MyR
#SBATCH --output MyR-%j.out
#SBATCH --nodes=5
#SBATCH --ntasks-per-node=6
#SBATCH --mem=24gb
#SBATCH --time=00:30:00
MyRProgram="$HOME/R/hpc_test2.R"
cd $HOME/R
export R_LIBS_USER=$HOME/R/Libs2
# start R with my R program
module load R
time R --vanilla -f $MyRProgram
有没有人有解决问题的建议?我做错了什么?
在此先感谢您的帮助!
您的脚本是一个 MPI 应用程序,因此您需要通过 Slurm 适当地执行它。 Open MPI FAQ 有专门的部分介绍如何做到这一点:
最重要的一点是你的脚本不应该直接执行 R,而是应该通过 mpirun 命令执行它,使用类似:
mpirun -np 1 R --vanilla -f $MyRProgram
我的猜测是"PMI2"错误是由于没有通过mpirun执行R造成的。我不认为 "fork" 消息表示真正的问题,它有时会发生在我身上。我认为这是因为 R 在初始化时调用 "fork",但这从来没有给我带来问题。我不确定为什么我只是偶尔收到此消息。
请注意,告诉 mpirun 仅启动一个进程非常重要,因为其他进程将被派生,因此您应该使用 mpirun -np 1
选项。如果 Open MPI 是使用 Slurm 支持正确构建的,那么 Open MPI 应该知道在生成这些进程时在哪里启动这些进程,但是如果你不使用 -np 1
,那么通过 mpirun 启动的所有 30 个进程将分别生成 30 个进程,造成了巨大的混乱。
最后,我认为您应该告诉 makeCluster
仅生成 29 个进程以避免 运行 总共 31 个 MPI 进程。根据您的网络配置,即使超额订阅也会导致问题。
我将按如下方式创建集群对象:
library(snow)
library(Rmpi)
cl<- makeCluster(mpi.universe.size() - 1, type="MPI")
这样更安全,更容易使 R 脚本和作业脚本保持同步。