X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/blobdiff_plain/fe304706848f0a64477d4687b3ea97d5b9a0c35c..e1552e8f04faf687626d1849f52e67981f1169b7:/src/smpi/mpi/smpi_topo.cpp diff --git a/src/smpi/mpi/smpi_topo.cpp b/src/smpi/mpi/smpi_topo.cpp index 3376a52b97..592850187e 100644 --- a/src/smpi/mpi/smpi_topo.cpp +++ b/src/smpi/mpi/smpi_topo.cpp @@ -1,4 +1,4 @@ -/* Copyright (c) 2014-2019. The SimGrid Team. All rights reserved. */ +/* Copyright (c) 2014-2020. The SimGrid Team. All rights reserved. */ /* This program is free software; you can redistribute it and/or modify it * under the terms of the license (GNU LGPL) which comes with this package. */ @@ -12,13 +12,19 @@ #include /* static functions */ -static int assignnodes(int ndim, int nfactor, int *pfacts,int **pdims); +static int assignnodes(int ndim, int nfactor, const int* pfacts, int** pdims); static int getfactors(int num, int *nfators, int **factors); namespace simgrid{ namespace smpi{ +void Topo::setComm(MPI_Comm comm) +{ + xbt_assert(not comm_); + comm_ = comm; +} + /******************************************************************************* * Cartesian topologies ******************************************************************************/ @@ -43,14 +49,10 @@ Topo_Cart::Topo_Cart(MPI_Comm comm_old, int ndims, const int dims[], const int p newSize *= dims[i]; } if(rank >= newSize) { - *comm_cart = MPI_COMM_NULL; + if(comm_cart != nullptr) + *comm_cart = MPI_COMM_NULL; return; } - oldGroup = comm_old->group(); - newGroup = new Group(newSize); - for (int i = 0 ; i < newSize ; i++) { - newGroup->set_mapping(oldGroup->actor(i), i); - } nnodes_ = newSize; @@ -64,16 +66,28 @@ Topo_Cart::Topo_Cart(MPI_Comm comm_old, int ndims, const int dims[], const int p position_[i] = rank / nranks; rank = rank % nranks; } - - *comm_cart = new Comm(newGroup, this); + + if(comm_cart != nullptr){ + oldGroup = comm_old->group(); + newGroup = new Group(newSize); + for (int i = 0 ; i < newSize ; i++) { + newGroup->set_mapping(oldGroup->actor(i), i); + } + *comm_cart = new Comm(newGroup, std::shared_ptr(this)); + } } else { - if (rank == 0) { - *comm_cart = new Comm(new Group(MPI_COMM_SELF->group()), this); - } else { - *comm_cart = MPI_COMM_NULL; + if(comm_cart != nullptr){ + if (rank == 0) { + MPI_Group group = new Group(MPI_COMM_SELF->group()); + *comm_cart = new Comm(group, std::shared_ptr(this)); + } else { + *comm_cart = MPI_COMM_NULL; + } } } - setComm(*comm_cart); + if(comm_cart != nullptr){ + setComm(*comm_cart); + } } Topo_Cart* Topo_Cart::sub(const int remain_dims[], MPI_Comm *newcomm) { @@ -96,7 +110,7 @@ Topo_Cart* Topo_Cart::sub(const int remain_dims[], MPI_Comm *newcomm) { // that should not segfault int j = 0; - for (int i = 0 ; j < newNDims ; i++) { + for (int i = 0; i < oldNDims; i++) { if(remain_dims[i]) { newDims[j] =dims_[i]; newPeriodic[j] =periodic_[i]; @@ -104,7 +118,24 @@ Topo_Cart* Topo_Cart::sub(const int remain_dims[], MPI_Comm *newcomm) { } } } - Topo_Cart* res = new Topo_Cart(getComm(), newNDims, newDims, newPeriodic, 0, newcomm); + + //split into several communicators + int color = 0; + for (int i = 0; i < oldNDims; i++) { + if (not remain_dims[i]) { + color = (color * dims_[i] + position_[i]); + } + } + Topo_Cart* res; + if (newNDims == 0){ + res = new Topo_Cart(getComm(), newNDims, newDims, newPeriodic, 0, newcomm); + } else { + *newcomm = getComm()->split(color, getComm()->rank()); + res = new Topo_Cart(getComm(), newNDims, newDims, newPeriodic, 0, nullptr); + std::shared_ptr topo=std::shared_ptr(res); + res->setComm(*newcomm); + (*newcomm)->set_topo(topo); + } delete[] newDims; delete[] newPeriodic; return res; @@ -167,10 +198,8 @@ int Topo_Cart::rank(const int* coords, int* rank) { return MPI_SUCCESS; } -int Topo_Cart::shift(int direction, int disp, int *rank_source, int *rank_dest) { - - int position[ndims_]; - +int Topo_Cart::shift(int direction, int disp, int* rank_source, int* rank_dest) +{ if(ndims_ == 0) { return MPI_ERR_ARG; } @@ -178,6 +207,7 @@ int Topo_Cart::shift(int direction, int disp, int *rank_source, int *rank_dest) return MPI_ERR_DIMS; } + int* position = new int[ndims_]; this->coords(getComm()->rank(), ndims_, position); position[direction] += disp; @@ -204,7 +234,7 @@ int Topo_Cart::shift(int direction, int disp, int *rank_source, int *rank_dest) } else { this->rank(position, rank_source); } - + delete[] position; return MPI_SUCCESS; } @@ -244,7 +274,7 @@ int Topo_Cart::Dims_create(int nnodes, int ndims, int dims[]) /* Get # of free-to-be-assigned processes and # of free dimensions */ int freeprocs = nnodes; int freedims = 0; - int *p = dims; + const int* p = dims; for (int i = 0; i < ndims; ++i) { if (*p == 0) { ++freedims; @@ -320,7 +350,7 @@ int Topo_Cart::Dims_create(int nnodes, int ndims, int dims[]) * - ptr to array of dimensions (returned value) * Returns: - 0 or ERROR */ -static int assignnodes(int ndim, int nfactor, int *pfacts, int **pdims) +static int assignnodes(int ndim, int nfactor, const int* pfacts, int** pdims) { int *pmin;