我有一些 Fortran 代码,我正在与 MPI 并行化,它正在做真正奇怪的事情。首先,有一个变量 nstartg 我从老板进程广播给所有工人:
call mpi_bcast(nstartg,1,mpi_integer,0,mpi_comm_world,ierr)
该变量nstartg
在程序中不再更改。稍后,我让老板进程将eproc
数组的元素发送edge
给工人:
if (me==0) then
do n=1,ntasks-1
(determine the starting point estart and the number eproc
of values to send)
call mpi_send(edge(estart),eproc,mpi_integer,n,n,mpi_comm_world,ierr)
enddo
endif
me
如果非零,则带有匹配的接收语句。(为了便于阅读,我省略了一些其他代码;我不使用 scatterv 是有充分理由的。)
这就是事情变得奇怪的地方:变量nstartg
被更改为n
而不是保持其实际值。例如,在进程 1 上,在 mpi_recv 之后nstartg = 1
,在进程 2 上它等于 2,依此类推。此外,如果我将上面的代码更改为
call mpi_send(edge(estart),eproc,mpi_integer,n,n+1234567,mpi_comm_world,ierr)
并在对 mpi_recv 的匹配调用中相应地更改标签,然后在进程 1 上,nstartg = 1234568; 在进程 2 上,nstartg = 1234569 等。
到底是怎么回事?我改变的只是 mpi_send/recv 用来识别消息的标签;如果标签是唯一的,这样消息就不会混淆,这不应该改变任何东西,但它正在改变一个完全不相关的变量。
在boss进程中,nstartg
没有改变,所以我可以通过再次广播来解决这个问题,但这并不是一个真正的解决方案。最后,我应该提一下,使用电子围栏编译和运行这段代码并没有发现任何缓冲区溢出,-fbounds-check 也没有向我抛出任何东西。