Parallel processing Fortran MPI不';t在所有给定数量的处理器上运行

Parallel processing Fortran MPI不';t在所有给定数量的处理器上运行,parallel-processing,fortran,mpi,Parallel Processing,Fortran,Mpi,我目前正在运行一个程序,其中必须处理模型网格。当我想使用例如10个处理器作为工作进程来运行程序时(mpirun-np 11-machinefile host civil\u mpi.exe),只有3个处理器运行程序,其余的在程序开始时停止,没有任何错误 如果减小模型网格的大小,则一切都正常工作。机器的总RAM超过30 GB,每个进程所需的内存大小(基于模型网格大小)小于1 GB,因此理论上RAM应该没有问题。有人能帮我处理这个案子吗 操作系统是Linux OpenSuse,我在一台有16个双核C

我目前正在运行一个程序,其中必须处理模型网格。当我想使用例如10个处理器作为工作进程来运行程序时(
mpirun-np 11-machinefile host civil\u mpi.exe
),只有3个处理器运行程序,其余的在程序开始时停止,没有任何错误

如果减小模型网格的大小,则一切都正常工作。机器的总RAM超过30 GB,每个进程所需的内存大小(基于模型网格大小)小于1 GB,因此理论上RAM应该没有问题。有人能帮我处理这个案子吗

操作系统是Linux OpenSuse,我在一台有16个双核CPU的机器上运行MPI。代码是:

      call MPI_INIT(ierror)

      call mpi_comm_rank(MPI_COMM_WORLD, procid, ierror)

      call mpi_comm_size(MPI_COMM_WORLD, nproc, ierror)
      nworker = nproc - 1

      call mpi_get_processor_name (procname, len, ierror)


      n_slice = 280
      ny0(1) = 1
      ny(1) = 2 

      do i = 2,n_slice
       ny0(i) = ny0(i-1) + 2
       ny(i) = ny(i-1) + 2
      end do

      nx = 461
      nx0 = 1
      nz = 421
      nz0 = 1

      nwork = 1

      do i = 1,280
         if(nworker*nwork .lt. n_slice) then
         nwork = nwork + 1
         end if
      end do

      if (procid .eq. masterid) then

      worker_job = 1

      do q = 1,nworker

         iwork = q

         call mpi_send(worker_job, 1, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD,ierror)

        call mpi_send(nx0, 1, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD,ierror)

        call mpi_send(ny0, 280, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD, ierror)

        call mpi_send(nz0, 1, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD,ierror)

        call mpi_send(nx, 1, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD, ierror)

        call mpi_send(ny, 280, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD,ierror)

        call mpi_send(nz, 1, MPI_INTEGER, iwork, tag,
     $                MPI_COMM_WORLD, ierror)


      worker_job = worker_job + nwork

      end do

      end if

c ------------------ worker task -----------

      if (procid .gt. masterid) then
c      write(*,*)'processor',procid,'is working....'

      call mpi_recv(worker_job, 1, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)

      call mpi_recv(nx0, 1, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)

      call mpi_recv(ny0, 280, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)

      call mpi_recv(nz0, 1, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)

      call mpi_recv(nx, 1, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)

      call mpi_recv(ny, 280, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)

      call mpi_recv(nz, 1, MPI_INTEGER, masterid, tag,
     $                MPI_COMM_WORLD, status, ierror)


       do j = worker_job, worker_job + nwork - 1

         if (j .le. 280) then
         write(*,*) '****************processor',procid,'is working'
         call rawmig(j,nx0,ny0(j),nz0,nx,ny(j),nz)
         end if  
       end do
      end if

      call mpi_finalize(ierror)

      end 

问题解决了!谢谢大家的评论,最后我意识到主程序中的一个矩阵必须与处理器提交的新维度同步!Gilles Gouaillardet,在你的建议之后,我试图制作一个简短易读的程序版本来发布它,在这期间,我看到这个矩阵的形式是构建一个iy=ny0,ny(可变维度)的输出,必须是iy=1,2。但首先,定义中的矩阵维度必须已更正,因为它是使用来自每个处理器的直接提交变量定义的,所以某些处理器在没有任何erorr消息的情况下被停止

您应该至少发布一些关于操作系统和MPI实现的代码和详细信息。这可能会出错的原因有很多。文章已编辑,现在带有代码。您是否在所有主机上运行了dmesg?你看到杀人凶手在行动了吗?一个简单的技巧是
mpi运行civil\u mpi.sh
,其中
civil\u mpi.sh
执行
/civil\u mpi.exe;echo mpi任务已退出,状态为$?
。这应该告诉您mpi任务返回了多少,您使用的是哪个mpi?例如,使用“英特尔MPI”,您可以在运行程序时尝试使用-check,看看这是否说明了什么。我刚刚使用dmesg作为:mpirun-np 11-machinefile host civil_MPI.exe dmesg-K进行了尝试,但没有从处理器发出错误消息。也没有杀人凶手。另一方面,我在显示屏上看到check消息(processor#x正在工作),这意味着最后一个do循环,在该循环中调用的子例程将为所有处理器启动!很高兴知道!当你写“停止而没有任何错误消息”时,你是说这些MPI任务基本上挂起了吗?或者你的意思是这些MPI任务退出,而
mpirun
没有注意到这一点?事实上,MPI工作没有问题,但不是第一个问题(或前两个处理器,其余处理器在开始运行主程序时停止运行,没有任何错误。这些内核试图以更高的ny0和ny调用主程序,但由于在主程序中,矩阵维数没有得到纠正,无法从MPI转换输入的ny(例如,对于ny0=450&ny=452,主程序中的ny必须被解释为2(=452-450)),由于矩阵维数,内存已满(通过MPI拆分主程序的原因)进程停止了。当然,第一个处理器正在运行,但输出错误!这是我能很快识别的,但更糟糕的是,向量被定义为k(nx*ny),我把它改为k(nx*ny-ny0+1),关于大括号的愚蠢错误,它一定是k(nx*(ny-ny0+1,nz))。