/* * grid.c * * build a 2d grid * */ #include <stdio.h> #include <stdlib.h> #include <math.h> #include "lalib.h" Lalib_grid * lalib_build_grid(MPI_Comm comm, int rows, int cols) { Lalib_grid * grid; int nproc; /* total number of procs in comm */ int my_rank; int dims[LALIB_NDIMS]; /* array of dimensions */ int local[LALIB_NDIMS]; /* local positions */ int period[LALIB_NDIMS]; /* periodicities */ int remain_dims[LALIB_NDIMS]; /* flags for row/col subgrids */ /* check whether the processor count is correct */ MPI_Comm_size(comm, &nproc); if (rows * cols != nproc) { fprintf(stderr, "wrong number of processes to build grid.\n"); MPI_Abort(MPI_COMM_WORLD, -1); exit(-1); } grid = (Lalib_grid *) calloc(1, sizeof(Lalib_grid)); grid->rows = rows; grid->cols = cols; /* generate new communicator with topology */ dims[0] = rows; dims[1] = cols; period[0] = FALSE; period[1] = FALSE; MPI_Cart_create(comm, LALIB_NDIMS, dims, period, TRUE, &(grid->grid_comm)); /* get local coordinates */ MPI_Comm_rank(grid->grid_comm, &my_rank); MPI_Cart_coords(grid->grid_comm, my_rank, LALIB_NDIMS, local); grid->myrow = local[0]; grid->mycol = local[1]; /* split comm into row and column comm */ remain_dims[0] = TRUE; remain_dims[1] = FALSE; MPI_Cart_sub(grid->grid_comm, remain_dims, &(grid->col_comm)); remain_dims[0] = FALSE; remain_dims[1] = TRUE; MPI_Cart_sub(grid->grid_comm, remain_dims, &(grid->row_comm)); return(grid); }