! split_ex.f90 ! An example from Rutgers. include "mpiSim.f90" program another include "useSim.f90" ! SIMPLE MPI PROGRAM TO SPLIT UP DATA AMONG PROCESSES AND ! DO A CALCULATION. RESULTS ARE SENT BACK TO PROCESS 0 ! AND SOME RESULTS ARE PRINTED. ASSUMPTION IS MADE THAT ! THE ARRAYSIZE IS EVENLY DISIBLE BY NUMBER OF PROCESSES ! include 'mpif.h' integer status(MPI_STATUS_SIZE) integer ARRAYSIZE parameter (ARRAYSIZE=60000) integer nprocs, taskid, dest, index, i, chunksize, ierror integer sendindex, source, sourceindex real data(ARRAYSIZE), reslt(ARRAYSIZE) ! START MPI call mpi_init(ierror) call mpi_comm_rank(MPI_COMM_WORLD,taskid,ierror) call mpi_comm_size(MPI_COMM_WORLD,nprocs,ierror) write(*,*)'taskid=',taskid, ' nprocs= ', nprocs chunksize=ARRAYSIZE/nprocs index=taskid*chunksize + 1 ! INITIALIZE DATA if (taskid .eq. 0) then do 20 i=1, ARRAYSIZE data(i)= i 20 continue print*, '*******Start MPI **********' ! SEND EACH PROCESS A CHUNK OF DATA do 30 dest=1,nprocs-1 write(*,*) 'Sending to processes ', dest ! Note, the following +1 is wrong and will cause a subscript range ! error (with compilers that trap this error.) sendindex=dest*chunksize + 1 ! F90 array notation is used instead F77 array segment, data(sendindex). call mpi_send(data(sendindex:sendindex+chunksize-1), & chunksize, MPI_REAL,dest,0,MPI_COMM_WORLD,ierror) 30 continue ! EACH PROCESS EXCEPT O RECEIVES A CHUNK OF DATA else ! F90 array notation is used instead F77 array segment, data(sendindex). call mpi_recv(data(index:index+chunksize-1), chunksize, & MPI_REAL, 0,0, MPI_COMM_WORLD, status,ierror) print*, taskid , ' received data ' , "index = ", index endif ! COMPUTE A VALUE (RESULT) FOR A CHUNK OF DATA do 40 i=index, index + chunksize - 1 reslt(i)= data(i) +1. 40 continue ! SEND COMPUTED VALUES BACK TO 0 if (taskid .gt. 0) then ! F90 array notation is used instead F77 array segment, data(sendindex). call mpi_send(reslt(index:index+chunksize-1), chunksize, & MPI_REAL, 0, 0, MPI_COMM_WORLD, ierrror) print *, taskid, ' sent values to 0' else ! PROCESS 0 RECEIVE THE RESULTS FROM OTHER PROCESSES AND ! PRINTS SOME VALUES. do 50 source= 1, nprocs-1 sourceindex= source*chunksize +1 ! F90 array notation is used instead F77 array segment, data(sendindex). call mpi_recv(reslt(sourceindex:sourceindex+chunksize-1), & chunksize, MPI_REAL, source,0, MPI_COMM_WORLD, status, & ierror) print *,'--------------------' print *,' Sample results from ', source print *, 'reslt(', sourceindex, ') = ', reslt(sourceindex) ! $$ The following sourceindex values of reslt have not been defined. print *, 'reslt(', sourceindex+100, ') = ', & reslt(sourceindex+100) print *, 'reslt(', sourceindex+1000, ') = ', & reslt(sourceindex+1000) print *, ' ' 50 continue endif ! ENDING MPI print *, 'process calling finalize ', taskid call mpi_finalize(ierror) end program another