      program example24b
      include 'mpif.h'
      integer ierr, rank, size, N, nl
      parameter (N = 8)
      double precision a(N, N), b(N, N)
      call MPI_INIT(ierr)
      call MPI_COMM_SIZE(MPI_COMM_WORLD, size, ierr)
      call MPI_COMM_RANK(MPI_COMM_WORLD, rank, ierr)
      nl = (N-1)/size+1
      call work(a, b, N, nl, size, rank)
      call MPI_FINALIZE(ierr)
      end
      subroutine work(a, b, n, nl, size, rank)
      include 'mpif.h'
      integer ierr, rank, size, n, nl, ii, matr_rev
      double precision a(n, nl), b(n, nl)
      integer i, j, status(MPI_STATUS_SIZE)
      do j = 1, nl
         do i = 1, n
            b(i, j) = 0.d0
            ii = j+rank*nl
            a(i, j) = 100*ii+i
         enddo
      enddo 
      call MPI_TYPE_VECTOR(nl, n, -n, MPI_DOUBLE_PRECISION,
     &                     matr_rev, ierr)
      call MPI_TYPE_COMMIT(matr_rev, ierr)
      call MPI_SENDRECV(a(1, nl), 1, matr_rev, size-rank-1, 1,
     &                  b, nl*n, MPI_DOUBLE_PRECISION,
     &                  size-rank-1, 1, MPI_COMM_WORLD,
     &                  status, ierr)
      do j = 1, nl
         do i = 1, n
            print *, 'process ', rank, ': ', 
     &               j+rank*nl, ' ', i, a(i,j), ' ', b(i,j)
         enddo
      enddo
      end
