1
1

Add the MPI 2.2 MPI_Dist_graph functionality.

This patch reshape the way we deal with topologies completely. Where
our topologies were mainly storage components (they were not capable
of creating the new communicator), the new version is built around a
[possibly] common representation (in mca/topo/topo.h), but the functions
to attach and retrieve the topological information are specific to each
component. As a result the ompi_create_cart and ompi_create_graph functions
become useless and have been removed.

In addition to adding the internal infrastructure to manage the topology
information, it updates the MPI interface, and the debuggers support and
provides all Fortran interfaces.

This commit was SVN r28687.
Этот коммит содержится в:
George Bosilca 2013-07-01 12:40:08 +00:00
родитель b82abf6bef
Коммит 5fae72b9aa
83 изменённых файлов: 2899 добавлений и 1871 удалений

1
NEWS
Просмотреть файл

@ -54,6 +54,7 @@ included in the vX.Y.Z section and be denoted as:
Trunk (not on release branches yet)
-----------------------------------
- Add support for MPI_Dist_graph functionality (MPI 2.2).
- Do not build the MPI C++ bindings by default. They must be enabled
via --enable-mpi-cxx.
- Adding a new parallel I/O component and multiple new frameworks to

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2011 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -12,6 +12,8 @@
* Copyright (c) 2007-2011 University of Houston. All rights reserved.
* Copyright (c) 2007-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2009 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2011-2013 INRIA. All rights reserved.
* Copyright (c) 2011-2013 Universite Bordeaux 1
* Copyright (c) 2012 Oak Ridge National Labs. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, LLC.
* All rights reserved.
@ -50,8 +52,7 @@
static int rankkeycompare(const void *, const void *);
/**
* to fill the rest of the stuff for the communicator when either
* MPI_Cart_create or MPI_Graph_create is used
* to fill the rest of the stuff for the communicator
*/
static int ompi_comm_fill_rest (ompi_communicator_t *comm,
int num_procs,
@ -94,12 +95,11 @@ int ompi_comm_set ( ompi_communicator_t **ncomm,
int *remote_ranks,
opal_hash_table_t *attr,
ompi_errhandler_t *errh,
mca_base_component_t *topocomponent,
bool copy_topocomponent,
ompi_group_t *local_group,
ompi_group_t *remote_group )
{
ompi_communicator_t *newcomm=NULL;
ompi_communicator_t *newcomm = NULL;
int ret;
/* ompi_comm_allocate */
@ -114,8 +114,7 @@ int ompi_comm_set ( ompi_communicator_t **ncomm,
efficiently */
ret = ompi_group_incl(oldcomm->c_local_group, local_size,
local_ranks, &newcomm->c_local_group);
}
else {
} else {
newcomm->c_local_group = local_group;
OBJ_RETAIN(newcomm->c_local_group);
ompi_group_increment_proc_count(newcomm->c_local_group);
@ -127,8 +126,7 @@ int ompi_comm_set ( ompi_communicator_t **ncomm,
if ( NULL == remote_group ) {
ret = ompi_group_incl(oldcomm->c_remote_group, remote_size,
remote_ranks, &newcomm->c_remote_group);
}
else {
} else {
newcomm->c_remote_group = remote_group;
OBJ_RETAIN(newcomm->c_remote_group);
ompi_group_increment_proc_count(newcomm->c_remote_group);
@ -139,8 +137,7 @@ int ompi_comm_set ( ompi_communicator_t **ncomm,
} else {
ompi_comm_dup(oldcomm->c_local_comm, &newcomm->c_local_comm);
}
}
else {
} else {
newcomm->c_remote_group = newcomm->c_local_group;
OBJ_RETAIN(newcomm->c_remote_group);
}
@ -149,74 +146,33 @@ int ompi_comm_set ( ompi_communicator_t **ncomm,
Necessary for the disconnect of dynamic communicators. */
if ( 0 < local_size ) {
ompi_dpm.mark_dyncomm (newcomm);
ompi_dpm.mark_dyncomm (newcomm);
}
/* Set error handler */
newcomm->error_handler = errh;
OBJ_RETAIN ( newcomm->error_handler );
/* Set Topology, if required */
if ( NULL != topocomponent ) {
/*
* This functions is never used to determine the topology
* component. The topology component is determined only by the
* ompi_cart_create and ompi_comm_create functions. Have to
* see what ahppens during MPI_Comm_dup though. During this
* the topology information has to be copied into the new
* communicator which includes selecting a new topology
* component and setting the information which is on that
* communicator into this communicator. This probably is
* another function in this file.
*/
if (OMPI_COMM_IS_CART ( oldcomm ) ) {
newcomm->c_flags |= OMPI_COMM_CART;
}
if (OMPI_COMM_IS_GRAPH ( oldcomm ) ) {
newcomm->c_flags |= OMPI_COMM_GRAPH;
}
/*
* Now I have to set the information on the topology from the previous
* communicator
*/
/* allocate the data for the common good */
newcomm->c_topo_comm = (mca_topo_base_comm_t *)malloc(sizeof(mca_topo_base_comm_t));
if (NULL == newcomm->c_topo_comm) {
OBJ_RELEASE(newcomm);
return OMPI_ERROR;
}
if (OMPI_SUCCESS != (ret = mca_topo_base_comm_select (newcomm,
oldcomm->c_topo_component))) {
free(newcomm->c_topo_comm);
OBJ_RELEASE(newcomm);
return ret;
}
/*
* Should copy over the information from the previous communicator
/* Set Topology, if required and if available */
if ( copy_topocomponent && (NULL != oldcomm->c_topo) ) {
/**
* The MPI standard is pretty clear on this, the topology information
* behave as info keys, and is copied only on MPI_Comm_dup.
*/
if (OMPI_SUCCESS != (ret = ompi_comm_copy_topo (oldcomm, newcomm))) {
OBJ_RELEASE(newcomm);
if (OMPI_SUCCESS != (ret = ompi_comm_copy_topo(oldcomm, newcomm))) {
ompi_comm_free(&newcomm);
return ret;
}
}
/* Copy attributes and call according copy functions, if
required */
/* Copy attributes and call according copy functions, if required */
if (NULL != oldcomm->c_keyhash) {
if (NULL != attr) {
ompi_attr_hash_init(&newcomm->c_keyhash);
if (OMPI_SUCCESS != (ret = ompi_attr_copy_all (COMM_ATTR, oldcomm,
newcomm, attr,
newcomm->c_keyhash))) {
OBJ_RELEASE(newcomm);
ompi_comm_free(&newcomm);
return ret;
}
}
@ -325,7 +281,7 @@ int ompi_comm_create ( ompi_communicator_t *comm, ompi_group_t *group,
rranks, /* remote_ranks */
NULL, /* attrs */
comm->error_handler, /* error handler */
NULL, /* topo component */
false, /* dont copy the topo */
group, /* local group */
NULL /* remote group */
);
@ -396,8 +352,8 @@ int ompi_comm_create ( ompi_communicator_t *comm, ompi_group_t *group,
/*
** Counterpart to MPI_Comm_split. To be used within OMPI (e.g. MPI_Cart_sub).
*/
int ompi_comm_split ( ompi_communicator_t* comm, int color, int key,
ompi_communicator_t **newcomm, bool pass_on_topo )
int ompi_comm_split( ompi_communicator_t* comm, int color, int key,
ompi_communicator_t **newcomm, bool pass_on_topo )
{
int myinfo[2];
int size, my_size;
@ -552,14 +508,12 @@ int ompi_comm_split ( ompi_communicator_t* comm, int color, int key,
rranks, /* remote_ranks */
NULL, /* attrs */
comm->error_handler,/* error handler */
(pass_on_topo)?
(mca_base_component_t *)comm->c_topo_component:
NULL, /* topo component */
pass_on_topo,
NULL, /* local group */
NULL /* remote group */
);
if ( NULL == newcomm ) {
if ( NULL == newcomp ) {
rc = MPI_ERR_INTERN;
goto exit;
}
@ -805,10 +759,9 @@ ompi_comm_split_type(ompi_communicator_t *comm,
rranks, /* remote_ranks */
NULL, /* attrs */
comm->error_handler,/* error handler */
NULL, /* topo component */
false, /* don't copy the topo */
NULL, /* local group */
NULL /* remote group */
);
NULL ); /* remote group */
if ( NULL == newcomm ) {
rc = MPI_ERR_INTERN;
@ -892,32 +845,27 @@ ompi_comm_split_type(ompi_communicator_t *comm,
/**********************************************************************/
int ompi_comm_dup ( ompi_communicator_t * comm, ompi_communicator_t **newcomm )
{
ompi_communicator_t *comp=NULL;
ompi_communicator_t *newcomp=NULL;
int rsize, mode, rc=OMPI_SUCCESS;
ompi_communicator_t *newcomp = NULL;
int rsize = 0, mode = OMPI_COMM_CID_INTRA, rc = OMPI_SUCCESS;
comp = (ompi_communicator_t *) comm;
if ( OMPI_COMM_IS_INTER ( comp ) ){
rsize = comp->c_remote_group->grp_proc_count;
if ( OMPI_COMM_IS_INTER ( comm ) ){
rsize = comm->c_remote_group->grp_proc_count;
mode = OMPI_COMM_CID_INTER;
} else {
rsize = 0;
mode = OMPI_COMM_CID_INTRA;
}
*newcomm = MPI_COMM_NULL;
rc = ompi_comm_set ( &newcomp, /* new comm */
comp, /* old comm */
comp->c_local_group->grp_proc_count, /* local_size */
comm, /* old comm */
comm->c_local_group->grp_proc_count, /* local_size */
NULL, /* local_procs*/
rsize, /* remote_size */
NULL, /* remote_procs */
comp->c_keyhash, /* attrs */
comp->error_handler, /* error handler */
(mca_base_component_t *) comp->c_topo_component, /* topo component */
comp->c_local_group, /* local group */
comp ->c_remote_group ); /* remote group */
comm->c_keyhash, /* attrs */
comm->error_handler, /* error handler */
true, /* copy the topo */
comm->c_local_group, /* local group */
comm->c_remote_group ); /* remote group */
if ( NULL == newcomp ) {
rc = MPI_ERR_INTERN;
return rc;
@ -928,7 +876,7 @@ int ompi_comm_dup ( ompi_communicator_t * comm, ompi_communicator_t **newcomm )
/* Determine context id. It is identical to f_2_c_handle */
rc = ompi_comm_nextcid ( newcomp, /* new communicator */
comp, /* old comm */
comm, /* old comm */
NULL, /* bridge comm */
NULL, /* local leader */
NULL, /* remote_leader */
@ -944,7 +892,7 @@ int ompi_comm_dup ( ompi_communicator_t * comm, ompi_communicator_t **newcomm )
/* activate communicator and init coll-module */
rc = ompi_comm_activate( &newcomp, /* new communicator */
comp,
comm,
NULL,
NULL,
NULL,
@ -1157,7 +1105,7 @@ static int ompi_comm_allgather_emulate_intra( void *inbuf, int incount,
** The freeing of all attached objects (groups, errhandlers
** etc. ) has moved to the destructor.
*/
int ompi_comm_free ( ompi_communicator_t **comm )
int ompi_comm_free( ompi_communicator_t **comm )
{
int ret;
int cid = (*comm)->c_contextid;
@ -1206,7 +1154,7 @@ int ompi_comm_free ( ompi_communicator_t **comm )
if ( OMPI_COMM_IS_DYNAMIC (*comm) ) {
ompi_comm_num_dyncomm --;
}
OBJ_RELEASE ( (*comm) );
OBJ_RELEASE( (*comm) );
if ( is_extra_retain) {
/* This communicator has been marked as an "extra retain"
@ -1227,11 +1175,10 @@ int ompi_comm_free ( ompi_communicator_t **comm )
*/
ompi_communicator_t *tmpcomm = (ompi_communicator_t *) opal_pointer_array_get_item(&ompi_mpi_communicators, cid);
if ( NULL != tmpcomm ){
OBJ_RELEASE (tmpcomm);
ompi_comm_free(&tmpcomm);
}
}
*comm = MPI_COMM_NULL;
return OMPI_SUCCESS;
}
@ -1496,10 +1443,12 @@ int ompi_comm_dump ( ompi_communicator_t *comm )
if ( OMPI_COMM_IS_INTER(comm) )
opal_output(0," inter-comm,");
if ( OMPI_COMM_IS_CART(comm))
opal_output(0," topo-cart,");
if ( OMPI_COMM_IS_GRAPH(comm))
opal_output(0," topo-cart");
else if ( OMPI_COMM_IS_GRAPH(comm))
opal_output(0," topo-graph");
opal_output(0,"\n");
else if ( OMPI_COMM_IS_DIST_GRAPH(comm))
opal_output(0," topo-dist-graph");
opal_output(0,"\n");
if (OMPI_COMM_IS_INTER(comm)) {
opal_output(0," Remote group size:%d\n", comm->c_remote_group->grp_proc_count);
@ -1547,7 +1496,7 @@ static int rankkeycompare (const void *p, const void *q)
}
/*************************************************************************************
/***********************************************************************
* Counterpart of MPI_Cart/Graph_create. This will be called from the
* top level MPI. The condition for INTER communicator is already
* checked by the time this has been invoked. This function should do
@ -1558,195 +1507,33 @@ static int rankkeycompare (const void *p, const void *q)
* use this proc structure to create the communicator using
* ompi_comm_set.
*/
int ompi_topo_create (ompi_communicator_t *old_comm,
int ndims_or_nnodes,
int *dims_or_index,
int *periods_or_edges,
bool reorder,
ompi_communicator_t **comm_topo,
int cart_or_graph){
ompi_communicator_t *new_comm;
int new_rank;
ompi_proc_t **topo_procs;
int num_procs;
int ret;
ompi_proc_t **proc_list=NULL;
int i;
/* allocate a new communicator */
new_comm = ompi_comm_allocate(ompi_comm_size(old_comm), 0);
if (NULL == new_comm) {
return MPI_ERR_INTERN;
}
/* allocate the data for the common good */
new_comm->c_topo_comm = (mca_topo_base_comm_t*)malloc(sizeof(mca_topo_base_comm_t));
if (NULL == new_comm->c_topo_comm) {
OBJ_RELEASE(new_comm);
return OMPI_ERR_OUT_OF_RESOURCE;
}
/* select the topology component on the communicator */
if (OMPI_SUCCESS != (ret = mca_topo_base_comm_select (new_comm, NULL))) {
/* OBJ_RELEASE also frees new_comm->c_topo_comm */
OBJ_RELEASE(new_comm);
return ret;
}
/* since the topo component has initialised, let us now initialise
* the topo comm structure */
new_comm->c_flags |= cart_or_graph;
new_comm->c_topo_comm->mtc_ndims_or_nnodes = ndims_or_nnodes;
new_comm->c_topo_comm->mtc_dims_or_index = NULL;
new_comm->c_topo_comm->mtc_periods_or_edges = NULL;
new_comm->c_topo_comm->mtc_reorder = reorder;
new_comm->c_topo_comm->mtc_coords = NULL;
/* MPI-2.1 allows 0-dimension cartesian communicators, so prevent
a 0-byte malloc -- leave dims_or_index as NULL */
if (!(OMPI_COMM_CART == cart_or_graph && 0 == ndims_or_nnodes)) {
new_comm->c_topo_comm->mtc_dims_or_index =
(int *) malloc(sizeof(int) * ndims_or_nnodes);
if (NULL == new_comm->c_topo_comm->mtc_dims_or_index) {
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
return OMPI_ERROR;
}
memcpy (new_comm->c_topo_comm->mtc_dims_or_index,
dims_or_index, ndims_or_nnodes * sizeof(int));
}
/* Now the topology component has been selected, let the component
* re-arrange the proc ranks if need be. This is a down-call into
* the topo component and does not have anything to do with this
* level */
/* first, copy the proc structure from the previous communicator
* over to the new one. the topology component can then work on
* this and rearrange it as it deems fit.
*/
num_procs = old_comm->c_local_group->grp_proc_count;
topo_procs = (ompi_proc_t **)malloc (num_procs * sizeof(ompi_proc_t *));
if(OMPI_GROUP_IS_DENSE(old_comm->c_local_group)) {
memcpy (topo_procs,
old_comm->c_local_group->grp_proc_pointers,
num_procs * sizeof(ompi_proc_t *));
}
else {
proc_list = (ompi_proc_t **) calloc (old_comm->c_local_group->grp_proc_count,
sizeof (ompi_proc_t *));
for(i=0 ; i<old_comm->c_local_group->grp_proc_count ; i++) {
proc_list[i] = ompi_group_peer_lookup(old_comm->c_local_group,i);
}
memcpy (topo_procs,
proc_list,
num_procs * sizeof(ompi_proc_t *));
}
if ( NULL != proc_list ) {
free ( proc_list );
}
new_rank = old_comm->c_local_group->grp_my_rank;
if (OMPI_COMM_CART == cart_or_graph) {
/* A cartesian system has been requested. Call the right function */
/* Note that we fill in the basic information, i.e, copy the
* information which was provided to us over into the
* structure. The base component functions are free to change
* it as they deem fit */
if (ndims_or_nnodes > 0) {
new_comm->c_topo_comm->mtc_periods_or_edges =
(int*) malloc(sizeof(int) * ndims_or_nnodes);
if (NULL == new_comm->c_topo_comm->mtc_periods_or_edges) {
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
return OMPI_ERR_OUT_OF_RESOURCE;
}
memcpy (new_comm->c_topo_comm->mtc_periods_or_edges,
periods_or_edges, ndims_or_nnodes * sizeof(int));
new_comm->c_topo_comm->mtc_coords =
(int *) malloc(sizeof(int) * ndims_or_nnodes);
if (NULL == new_comm->c_topo_comm->mtc_coords) {
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
return OMPI_ERR_OUT_OF_RESOURCE;
}
}
if (OMPI_SUCCESS !=
(ret = new_comm->c_topo->topo_cart_create (new_comm->c_topo_comm,
&num_procs,
topo_procs,
&new_rank,
ndims_or_nnodes,
dims_or_index,
periods_or_edges,
reorder))) {
return ret;
}
} else if (OMPI_COMM_GRAPH == cart_or_graph) {
/* A graph system has been requested. Call the right function */
/* Note that we fill in the basic information, i.e, copy the
* information which was provided to us over into the
* structure. The base component functions are free to change
* it as they deem fit */
new_comm->c_topo_comm->mtc_periods_or_edges = (int *)
malloc (sizeof(int) * dims_or_index[ndims_or_nnodes-1]);
if (NULL == new_comm->c_topo_comm->mtc_periods_or_edges) {
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
return OMPI_ERROR;
}
memcpy (new_comm->c_topo_comm->mtc_periods_or_edges,
periods_or_edges, dims_or_index[ndims_or_nnodes-1] * sizeof(int));
if (OMPI_SUCCESS !=
(ret = new_comm->c_topo->topo_graph_create (new_comm->c_topo_comm,
&num_procs,
topo_procs,
&new_rank,
ndims_or_nnodes,
dims_or_index,
periods_or_edges,
reorder))) {
return ret;
}
}
/**
* Take an almost complete communicator and reserve the CID as well
* as activate it (initialize the collective and the topologies).
*/
int ompi_comm_enable(ompi_communicator_t *old_comm,
ompi_communicator_t *new_comm,
int new_rank,
int num_procs,
ompi_proc_t** topo_procs)
{
int ret = OMPI_SUCCESS;
/* Determine context id. It is identical to f_2_c_handle */
ret = ompi_comm_nextcid ( new_comm, /* new communicator */
old_comm, /* old comm */
ret = ompi_comm_nextcid ( new_comm, /* new communicator */
old_comm, /* old comm */
NULL, /* bridge comm */
NULL, /* local leader */
NULL, /* remote_leader */
OMPI_COMM_CID_INTRA, /* mode */
-1 ); /* send first, doesn't matter */
if (OMPI_SUCCESS != ret) {
/* something wrong happened during setting the communicator */
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
return ret;
/* something wrong happened while setting the communicator */
goto complete_and_return;
}
/* Now, the topology component has been selected and the group
/* Now, the topology module has been selected and the group
* which has the topology information has been created. All we
* need to do now is to fill the rest of the information into the
* communicator. The following steps are not just similar to
@ -1759,53 +1546,42 @@ int ompi_topo_create (ompi_communicator_t *old_comm,
old_comm->error_handler); /* error handler */
if (OMPI_SUCCESS != ret) {
/* something wrong happened during setting the communicator */
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
return ret;
/* something wrong happened while setting the communicator */
goto complete_and_return;
}
ret = ompi_comm_activate( &new_comm, /* new communicator */
old_comm, /* old comm */
NULL, /* bridge comm */
NULL, /* local leader */
NULL, /* remote_leader */
old_comm, /* old comm */
NULL, /* bridge comm */
NULL, /* local leader */
NULL, /* remote_leader */
OMPI_COMM_CID_INTRA, /* mode */
-1 ); /* send first, doesn't matter */
-1 ); /* send first, doesn't matter */
if (OMPI_SUCCESS != ret) {
/* something wrong happened during setting the communicator */
*comm_topo = new_comm;
return ret;
}
/* if the returned rank is -1, then this process is not in the
* new topology, so free everything we have allocated and return */
if (MPI_UNDEFINED == new_rank) {
ompi_comm_free (&new_comm);
*comm_topo = new_comm;
} else {
*comm_topo = new_comm;
/* something wrong happened while setting the communicator */
goto complete_and_return;
}
return OMPI_SUCCESS;
complete_and_return:
return ret;
}
static int ompi_comm_fill_rest (ompi_communicator_t *comm,
int num_procs,
ompi_proc_t **proc_pointers,
int my_rank,
ompi_errhandler_t *errh )
static int ompi_comm_fill_rest(ompi_communicator_t *comm,
int num_procs,
ompi_proc_t **proc_pointers,
int my_rank,
ompi_errhandler_t *errh)
{
/* properly decrement the ref counts on the groups.
We are doing this because this function is sort of a redo
of what is done in comm.c.. No need to decrement the ref
of what is done in comm.c. No need to decrement the ref
count on the proc pointers
This is just a quick fix, and will be looking for a
better solution */
OBJ_RELEASE ( comm->c_local_group );
OBJ_RELEASE ( comm->c_local_group );
OBJ_RELEASE( comm->c_local_group );
OBJ_RELEASE( comm->c_local_group );
/* allocate a group structure for the new communicator */
comm->c_local_group = ompi_group_allocate(num_procs);
@ -1818,7 +1594,7 @@ static int ompi_comm_fill_rest (ompi_communicator_t *comm,
/* set the remote group to be the same as local group */
comm->c_remote_group = comm->c_local_group;
OBJ_RETAIN ( comm->c_remote_group );
OBJ_RETAIN( comm->c_remote_group );
/* retain these proc pointers */
ompi_group_increment_proc_count(comm->c_local_group);
@ -1827,9 +1603,11 @@ static int ompi_comm_fill_rest (ompi_communicator_t *comm,
comm->c_local_group->grp_my_rank = my_rank;
comm->c_my_rank = my_rank;
/* verify whether to set the flag, that this comm
contains process from more than one jobid. */
ompi_dpm.mark_dyncomm (comm);
if( MPI_UNDEFINED != my_rank ) {
/* verify whether to set the flag, that this comm
contains process from more than one jobid. */
ompi_dpm.mark_dyncomm (comm);
}
/* set the error handler */
comm->error_handler = errh;
@ -1848,68 +1626,14 @@ static int ompi_comm_fill_rest (ompi_communicator_t *comm,
return OMPI_SUCCESS;
}
static int ompi_comm_copy_topo (ompi_communicator_t *oldcomm,
ompi_communicator_t *newcomm)
static int ompi_comm_copy_topo(ompi_communicator_t *oldcomm,
ompi_communicator_t *newcomm)
{
mca_topo_base_comm_t *oldt = oldcomm->c_topo_comm;
mca_topo_base_comm_t *newt = newcomm->c_topo_comm;
/* pointers for the rest of the information have been set
up.... simply allocate enough space and copy all the
information from the previous one. Remember that MPI-2.1
allows for 0-dimensional Cartesian communicators. */
newt->mtc_ndims_or_nnodes = oldt->mtc_ndims_or_nnodes;
newt->mtc_reorder = oldt->mtc_reorder;
if (OMPI_COMM_IS_CART(oldcomm) && 0 == oldt->mtc_ndims_or_nnodes) {
newt->mtc_dims_or_index = NULL;
newt->mtc_periods_or_edges = NULL;
newt->mtc_coords = NULL;
return MPI_SUCCESS;
}
newt->mtc_dims_or_index =
(int *)malloc(sizeof(int) * newt->mtc_ndims_or_nnodes);
if (NULL == newt->mtc_dims_or_index) {
return OMPI_ERR_OUT_OF_RESOURCE;
}
memcpy (newt->mtc_dims_or_index, oldt->mtc_dims_or_index,
newt->mtc_ndims_or_nnodes * sizeof(int));
/* Note that the length of the mtc_periods_or_edges array is
different depending whether it's a cartesian or graph */
if (OMPI_COMM_IS_CART(oldcomm)) {
newt->mtc_periods_or_edges =
(int*) malloc (sizeof(int) * oldt->mtc_ndims_or_nnodes);
if (NULL == newt->mtc_periods_or_edges) {
return OMPI_ERR_OUT_OF_RESOURCE;
}
newt->mtc_coords =
(int *)malloc(sizeof(int)*
newcomm->c_topo_comm->mtc_ndims_or_nnodes);
if (NULL == newt->mtc_coords) {
return OMPI_ERROR;
}
memcpy(newt->mtc_periods_or_edges, oldt->mtc_periods_or_edges,
sizeof(int) * oldt->mtc_ndims_or_nnodes);
memcpy (newt->mtc_coords, oldt->mtc_coords,
sizeof(int) * newt->mtc_ndims_or_nnodes);
} else {
int index = oldt->mtc_dims_or_index[oldt->mtc_ndims_or_nnodes-1];
index = (index > 0) ? index : -index;
newt->mtc_periods_or_edges =
(int*) malloc (sizeof(int)*index);
if (NULL == newt->mtc_periods_or_edges) {
return OMPI_ERR_OUT_OF_RESOURCE;
}
memcpy(newt->mtc_periods_or_edges, oldt->mtc_periods_or_edges,
sizeof(int) * index );
newt->mtc_coords = NULL;
}
if( NULL == oldcomm->c_topo )
return OMPI_ERR_NOT_FOUND;
newcomm->c_topo = oldcomm->c_topo;
OBJ_RETAIN(newcomm->c_topo);
newcomm->c_flags |= newcomm->c_topo->type;
return OMPI_SUCCESS;
}

Просмотреть файл

@ -3,7 +3,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -14,7 +14,9 @@
* Copyright (c) 2007-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2009 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, LLC.
* All rights reserved.
* Copyright (c) 2011-2013 INRIA. All rights reserved.
* Copyright (c) 2011-2013 Universite Bordeaux 1
* All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -60,7 +62,9 @@ ompi_predefined_communicator_t *ompi_mpi_comm_null_addr =
static void ompi_comm_construct(ompi_communicator_t* comm);
static void ompi_comm_destruct(ompi_communicator_t* comm);
OBJ_CLASS_INSTANCE(ompi_communicator_t,opal_object_t,ompi_comm_construct,ompi_comm_destruct);
OBJ_CLASS_INSTANCE(ompi_communicator_t, opal_object_t,
ompi_comm_construct,
ompi_comm_destruct);
/* This is the counter for the number of communicators, which contain
process with more than one jobid. This counter is a usefull
@ -323,17 +327,14 @@ static void ompi_comm_construct(ompi_communicator_t* comm)
comm->error_handler = NULL;
comm->c_pml_comm = NULL;
comm->c_topo = NULL;
comm->c_topo_component = NULL;
comm->c_topo_comm = NULL;
comm->c_topo_module = NULL;
/* A keyhash will be created if/when an attribute is cached on
this communiucator */
comm->c_keyhash = NULL;
this communicator */
comm->c_keyhash = NULL;
comm->errhandler_type = OMPI_ERRHANDLER_TYPE_COMM;
comm->errhandler_type = OMPI_ERRHANDLER_TYPE_COMM;
#ifdef OMPI_WANT_PERUSE
comm->c_peruse_handles = NULL;
comm->c_peruse_handles = NULL;
#endif
/* Need to zero out the collectives module because we sometimes
@ -356,39 +357,6 @@ static void ompi_comm_destruct(ompi_communicator_t* comm)
mca_coll_base_comm_unselect(comm);
}
/* Check if the communicator is a topology */
if ( MPI_COMM_NULL != comm &&
(OMPI_COMM_IS_CART(comm) || OMPI_COMM_IS_GRAPH(comm))) {
/* check and free individual things */
if (NULL != comm->c_topo_comm) {
/* check for all pointers and free them */
if (NULL != comm->c_topo_comm->mtc_dims_or_index) {
free(comm->c_topo_comm->mtc_dims_or_index);
comm->c_topo_comm->mtc_dims_or_index = NULL;
}
if (NULL != comm->c_topo_comm->mtc_periods_or_edges) {
free(comm->c_topo_comm->mtc_periods_or_edges);
comm->c_topo_comm->mtc_periods_or_edges = NULL;
}
if (NULL != comm->c_topo_comm->mtc_coords) {
free(comm->c_topo_comm->mtc_coords);
comm->c_topo_comm->mtc_coords = NULL;
}
free(comm->c_topo_comm);
comm->c_topo_comm = NULL;
}
}
comm->c_topo_component = NULL;
/* Tell the PML that this communicator is done.
MCA_PML_CALL(add_comm()) was called explicitly in
ompi_comm_init() when setting up COMM_WORLD and COMM_SELF; it's
@ -408,8 +376,11 @@ static void ompi_comm_destruct(ompi_communicator_t* comm)
MCA_PML_CALL(del_comm (comm));
}
/* Release topology information */
mca_topo_base_comm_unselect(comm);
/* Release topology module */
if (NULL != comm->c_topo) {
OBJ_RELEASE(comm->c_topo);
comm->c_topo = NULL;
}
if (NULL != comm->c_local_group) {
ompi_group_decrement_proc_count (comm->c_local_group);
@ -417,7 +388,8 @@ static void ompi_comm_destruct(ompi_communicator_t* comm)
comm->c_local_group = NULL;
if ( OMPI_COMM_IS_INTRA(comm) ) {
/* We have to decrement the ref count on the remote group
even if it is identical to the local one in case of intra-comm */
even if it is identical to the local one in case of
intra-comm */
OBJ_RELEASE ( comm->c_remote_group );
comm->c_remote_group = NULL;
}

Просмотреть файл

@ -3,7 +3,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2011 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -13,6 +13,8 @@
* Copyright (c) 2006-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2006-2010 University of Houston. All rights reserved.
* Copyright (c) 2009 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2011-2013 INRIA. All rights reserved.
* Copyright (c) 2011-2013 Universite Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -37,22 +39,24 @@ BEGIN_C_DECLS
OMPI_DECLSPEC OBJ_CLASS_DECLARATION(ompi_communicator_t);
#define OMPI_COMM_INTER 0x00000001
#define OMPI_COMM_CART 0x00000002
#define OMPI_COMM_GRAPH 0x00000004
#define OMPI_COMM_NAMEISSET 0x00000008
#define OMPI_COMM_ISFREED 0x00000010
#define OMPI_COMM_INTRINSIC 0x00000020
#define OMPI_COMM_DYNAMIC 0x00000040
#define OMPI_COMM_INVALID 0x00000080
#define OMPI_COMM_PML_ADDED 0x00000100
#define OMPI_COMM_EXTRA_RETAIN 0x00000200
#define OMPI_COMM_INTER 0x00000001
#define OMPI_COMM_NAMEISSET 0x00000002
#define OMPI_COMM_INTRINSIC 0x00000004
#define OMPI_COMM_DYNAMIC 0x00000008
#define OMPI_COMM_ISFREED 0x00000010
#define OMPI_COMM_INVALID 0x00000020
#define OMPI_COMM_CART 0x00000100
#define OMPI_COMM_GRAPH 0x00000200
#define OMPI_COMM_DIST_GRAPH 0x00000400
#define OMPI_COMM_PML_ADDED 0x00001000
#define OMPI_COMM_EXTRA_RETAIN 0x00004000
/* some utility #defines */
#define OMPI_COMM_IS_INTER(comm) ((comm)->c_flags & OMPI_COMM_INTER)
#define OMPI_COMM_IS_INTRA(comm) (!((comm)->c_flags & OMPI_COMM_INTER))
#define OMPI_COMM_IS_CART(comm) ((comm)->c_flags & OMPI_COMM_CART)
#define OMPI_COMM_IS_GRAPH(comm) ((comm)->c_flags & OMPI_COMM_GRAPH)
#define OMPI_COMM_IS_DIST_GRAPH(comm) ((comm)->c_flags & OMPI_COMM_DIST_GRAPH)
#define OMPI_COMM_IS_INTRINSIC(comm) ((comm)->c_flags & OMPI_COMM_INTRINSIC)
#define OMPI_COMM_IS_FREED(comm) ((comm)->c_flags & OMPI_COMM_ISFREED)
#define OMPI_COMM_IS_DYNAMIC(comm) ((comm)->c_flags & OMPI_COMM_DYNAMIC)
@ -60,6 +64,7 @@ OMPI_DECLSPEC OBJ_CLASS_DECLARATION(ompi_communicator_t);
#define OMPI_COMM_IS_PML_ADDED(comm) ((comm)->c_flags & OMPI_COMM_PML_ADDED)
#define OMPI_COMM_IS_EXTRA_RETAIN(comm) ((comm)->c_flags & OMPI_COMM_EXTRA_RETAIN)
#define OMPI_COMM_SET_DYNAMIC(comm) ((comm)->c_flags |= OMPI_COMM_DYNAMIC)
#define OMPI_COMM_SET_INVALID(comm) ((comm)->c_flags |= OMPI_COMM_INVALID)
@ -69,7 +74,6 @@ OMPI_DECLSPEC OBJ_CLASS_DECLARATION(ompi_communicator_t);
/* a set of special tags: */
/* to recognize an MPI_Comm_join in the comm_connect_accept routine. */
#define OMPI_COMM_ALLGATHER_TAG -31078
#define OMPI_COMM_BARRIER_TAG -31079
#define OMPI_COMM_ALLREDUCE_TAG -31080
@ -117,9 +121,10 @@ struct ompi_communicator_t {
ompi_group_t *c_local_group;
ompi_group_t *c_remote_group;
struct ompi_communicator_t *c_local_comm; /* a duplicate of the local
communicator in case the comm
is an inter-comm*/
struct ompi_communicator_t *c_local_comm; /* a duplicate of the
local communicator in
case the comm is an
inter-comm*/
/* Attributes */
struct opal_hash_table_t *c_keyhash;
@ -127,20 +132,11 @@ struct ompi_communicator_t {
/**< inscribing cube dimension */
int c_cube_dim;
/* Hooks for topo module to hang things */
mca_base_component_t *c_topo_component;
const struct mca_topo_base_module_1_0_0_t* c_topo;
/**< structure of function pointers */
struct mca_topo_base_comm_1_0_0_t* c_topo_comm;
/**< structure containing basic information about the topology */
struct mca_topo_base_module_comm_t *c_topo_module;
/**< module specific data */
/* Standard information about the selected topology module (or NULL
if this is not a cart, graph or dist graph communicator) */
struct mca_topo_base_module_t* c_topo;
/* index in Fortran <-> C translation array */
int c_f_to_c_index;
#ifdef OMPI_WANT_PERUSE
@ -361,17 +357,25 @@ OMPI_DECLSPEC int ompi_comm_group (ompi_communicator_t *comm, ompi_group_t **gro
int ompi_comm_create (ompi_communicator_t* comm, ompi_group_t *group,
ompi_communicator_t** newcomm);
/**
* Take an almost complete communicator and reserve the CID as well
* as activate it (initialize the collective and the topologies).
*/
int ompi_comm_enable(ompi_communicator_t *old_comm,
ompi_communicator_t *new_comm,
int new_rank,
int num_procs,
ompi_proc_t** topo_procs);
/**
* create a cartesian communicator
* Back end of MPI_DIST_GRAPH_CREATE_ADJACENT
*/
int ompi_topo_create (ompi_communicator_t *old_comm,
int ndims_or_nnodes,
int *dims_or_index,
int *periods_or_edges,
bool reorder,
ompi_communicator_t **comm_cart,
int cart_or_graph);
int ompi_topo_dist_graph_create_adjacent(ompi_communicator_t *old_comm,
int indegree, int sources[],
int sourceweights[], int outdegree,
int destinations[], int destweights[],
MPI_Info info, int reorder,
MPI_Comm *comm_dist_graph);
/**
* split a communicator based on color and key. Parameters
@ -480,7 +484,7 @@ OMPI_DECLSPEC int ompi_comm_set ( ompi_communicator_t** newcomm,
int *remote_ranks,
opal_hash_table_t *attr,
ompi_errhandler_t *errh,
mca_base_component_t *topocomponent,
bool copy_topocomponent,
ompi_group_t *local_group,
ompi_group_t *remote_group );
/**

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2007 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2007 The University of Tennessee and The University of
* Copyright (c) 2007-2013 The University of Tennessee and The University of
* Tennessee Research Foundation. All rights reserved.
* $COPYRIGHT$
*
@ -242,6 +242,8 @@ enum mpidbg_comm_info_bitmap_t {
MPIDBG_COMM_INFO_FREED_OBJECT = 0x40,
/* The queried communicator is MPI_COMM_NULL */
MPIDBG_COMM_INFO_COMM_NULL = 0x80,
/* The queried communicator has a distributed graph topology attached to it */
MPIDBG_COMM_INFO_DIST_GRAPH = 0x00000400,
/* Sentinel max value */
MPIDBG_COMM_INFO_MAX
};

Просмотреть файл

@ -1,6 +1,6 @@
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2004-2010 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2008-2009 Sun Microsystems, Inc. All rights reserved.
@ -325,27 +325,109 @@ int ompi_fill_in_type_info(mqs_image *image, char **message)
qh_type, ompi_communicator_t, c_flags);
ompi_field_offset(i_info->ompi_communicator_t.offset.c_f_to_c_index,
qh_type, ompi_communicator_t, c_f_to_c_index);
ompi_field_offset(i_info->ompi_communicator_t.offset.c_topo_comm,
qh_type, ompi_communicator_t, c_topo_comm);
ompi_field_offset(i_info->ompi_communicator_t.offset.c_topo,
qh_type, ompi_communicator_t, c_topo);
ompi_field_offset(i_info->ompi_communicator_t.offset.c_keyhash,
qh_type, ompi_communicator_t, c_keyhash);
}
{
mqs_type* qh_type = mqs_find_type( image, "mca_topo_base_comm_1_0_0_t", mqs_lang_c );
mqs_type* qh_type, *cg_union_type, *cart_type, *graph_type, *dist_graph_type;
int offset = 0;
missing_in_action = "mca_topo_base_module_2_1_0_t";
qh_type = mqs_find_type(image, missing_in_action, mqs_lang_c);
if( !qh_type ) {
missing_in_action = "mca_topo_base_comm_1_0_0_t";
goto type_missing;
}
i_info->ompi_mca_topo_base_comm_1_0_0_t.type = qh_type;
i_info->ompi_mca_topo_base_comm_1_0_0_t.size = mqs_sizeof(qh_type);
ompi_field_offset(i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_ndims_or_nnodes,
qh_type, mca_topo_base_comm_1_0_0_t, mtc_ndims_or_nnodes);
ompi_field_offset(i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_dims_or_index,
qh_type, mca_topo_base_comm_1_0_0_t, mtc_dims_or_index);
ompi_field_offset(i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_periods_or_edges,
qh_type, mca_topo_base_comm_1_0_0_t, mtc_periods_or_edges);
ompi_field_offset(i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_reorder,
qh_type, mca_topo_base_comm_1_0_0_t, mtc_reorder);
i_info->ompi_mca_topo_base_module_t.type = qh_type;
i_info->ompi_mca_topo_base_module_t.size = mqs_sizeof(qh_type);
/* There is a union of 2 structs in this struct -- get the
offsets for fields of both of them. */
/* Union type */
missing_in_action = "mca_topo_base_comm_cgd_union_2_1_0_t";
cg_union_type = mqs_find_type(image, missing_in_action, mqs_lang_c);
if (!cg_union_type) {
goto type_missing;
}
ompi_field_offset(offset, cg_union_type,
mca_topo_base_module_t, mtc);
/* By definition, the cart and base offsets are 0 in the
union. We've got the base union offset, so now look up the
individual fields in the cart and graph structs and add
them to the base union offset. Then we have the offset of
that field from the mca_topo_base_module_2_1_0_t type. */
/* Cart type */
missing_in_action = "mca_topo_base_comm_cart_2_1_0_t";
cart_type = mqs_find_type(image, missing_in_action, mqs_lang_c);
if (!cart_type) {
goto type_missing;
}
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_cart.ndims,
cart_type, mca_topo_base_comm_cart_2_1_0_t,
ndims);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_cart.dims,
cart_type, mca_topo_base_comm_cart_2_1_0_t,
dims);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_cart.periods,
cart_type, mca_topo_base_comm_cart_2_1_0_t,
periods);
i_info->ompi_mca_topo_base_module_t.offset.mtc_cart.ndims += offset;
i_info->ompi_mca_topo_base_module_t.offset.mtc_cart.dims += offset;
i_info->ompi_mca_topo_base_module_t.offset.mtc_cart.periods += offset;
/* Graph type */
missing_in_action = "mca_topo_base_comm_graph_2_1_0_t";
graph_type = mqs_find_type(image, missing_in_action, mqs_lang_c);
if (!graph_type) {
goto type_missing;
}
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_graph.nnodes,
graph_type, mca_topo_base_comm_graph_2_1_0_t,
nnodes);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_graph.index,
graph_type, mca_topo_base_comm_graph_2_1_0_t,
index);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_graph.edges,
graph_type, mca_topo_base_comm_graph_2_1_0_t,
edges);
i_info->ompi_mca_topo_base_module_t.offset.mtc_graph.nnodes += offset;
i_info->ompi_mca_topo_base_module_t.offset.mtc_graph.index += offset;
i_info->ompi_mca_topo_base_module_t.offset.mtc_graph.edges += offset;
/* Distributed Graph type */
missing_in_action = "mca_topo_base_comm_dist_graph_2_1_0_t";
dist_graph_type = mqs_find_type(image, missing_in_action, mqs_lang_c);
if (!dist_graph_type) {
goto type_missing;
}
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.in,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
in);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.inw,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
inw);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.out,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
out);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.outw,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
outw);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.indegree,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
indegree);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.outdegree,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
outdegree);
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.mtc_dist_graph.weighted,
dist_graph_type, mca_topo_base_comm_dist_graph_2_1_0_t,
weighted);
/* These fields are outside of the union */
ompi_field_offset(i_info->ompi_mca_topo_base_module_t.offset.reorder,
qh_type, mca_topo_base_module_t, reorder);
}
{
mqs_type* qh_type = mqs_find_type( image, "ompi_group_t", mqs_lang_c );

Просмотреть файл

@ -1,6 +1,6 @@
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2004-2010 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* $COPYRIGHT$
@ -197,7 +197,7 @@ typedef struct
int c_remote_group;
int c_flags;
int c_f_to_c_index;
int c_topo_comm;
int c_topo;
int c_keyhash;
} offset;
} ompi_communicator_t;
@ -206,12 +206,28 @@ typedef struct
mqs_type *type;
int size;
struct {
int mtc_ndims_or_nnodes;
int mtc_dims_or_index;
int mtc_periods_or_edges;
int mtc_reorder;
struct {
int ndims;
int dims;
int periods;
} mtc_cart;
struct {
int nnodes;
int index;
int edges;
} mtc_graph;
struct {
int in;
int inw;
int out;
int outw;
int indegree;
int outdegree;
int weighted;
} mtc_dist_graph;
int reorder;
} offset;
} ompi_mca_topo_base_comm_1_0_0_t;
} ompi_mca_topo_base_module_t;
/* MPI_Status */
struct {
mqs_type *type;

Просмотреть файл

@ -1,6 +1,6 @@
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2008 Sun Microsystems, Inc. All rights reserved.
@ -537,7 +537,7 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
[slightly] easier (and less confusing!) to have separate
retrieval code blocks. */
topo = ompi_fetch_pointer(process,
c_comm + i_info->ompi_communicator_t.offset.c_topo_comm,
c_comm + i_info->ompi_communicator_t.offset.c_topo,
p_info);
if (0 != topo &&
0 != ((*info)->comm_bitflags & MPIDBG_COMM_INFO_CARTESIAN)) {
@ -547,7 +547,7 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
/* Alloc space for copying arrays */
(*info)->comm_cart_num_dims = ndims =
ompi_fetch_int(process,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_ndims_or_nnodes,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc.cart.ndims,
p_info);
(*info)->comm_cart_dims = mqs_malloc(ndims * sizeof(int));
if (NULL == (*info)->comm_cart_dims) {
@ -563,10 +563,10 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
/* Retrieve the dimension and periodic description data from
the two arrays on the image's communicator */
dims = ompi_fetch_pointer(process,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_dims_or_index,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc.cart.dims,
p_info);
periods = ompi_fetch_pointer(process,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_periods_or_edges,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc.cart.periods,
p_info);
for (i = 0; i < ndims; ++i) {
@ -584,7 +584,7 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
/* Alloc space for copying the indexes */
(*info)->comm_graph_num_nodes = nnodes =
ompi_fetch_int(process,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_ndims_or_nnodes,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc.graph.nnodes,
p_info);
(*info)->comm_graph_index = mqs_malloc(nnodes * sizeof(int));
if (NULL == (*info)->comm_graph_index) {
@ -593,7 +593,7 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
/* Retrieve the index data */
index = ompi_fetch_pointer(process,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_dims_or_index,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc.graph.index,
p_info);
for (i = 0; i < nnodes; ++i) {
(*info)->comm_graph_index[i] =
@ -610,7 +610,7 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
/* Retrieve the edge data */
edges = ompi_fetch_pointer(process,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc_periods_or_edges,
topo + i_info->ompi_mca_topo_base_comm_1_0_0_t.offset.mtc.graph.edges,
p_info);
for (i = 0;
i < (*info)->comm_graph_index[(*info)->comm_graph_num_nodes - 1];
@ -618,6 +618,9 @@ int mpidbg_comm_query(mqs_image *image, mqs_image_info *image_info,
(*info)->comm_graph_edges[i] =
ompi_fetch_int(process, edges + (sizeof(int) * i), p_info);
}
} else if (0 != topo &&
0 != ((*info)->comm_bitflags & MPIDBG_COMM_INFO_DIST_GRAPH)) {
/* TODO: Complete the info if the communicator has a distributed graph topology */
}
/* Fortran handle */

Просмотреть файл

@ -1,7 +1,10 @@
/*
* Copyright (c) 2009 Sun Microsystems, Inc All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc All rights reserved.
* $COPYRIGHT$
* Copyright (c) 2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
@ -54,11 +57,8 @@ int main(int argc, char **argv) {
GAP_CHECK("c_local_comm", test_comm, c_local_comm, c_remote_group, 1);
GAP_CHECK("c_keyhash", test_comm, c_keyhash, c_local_comm, 1);
GAP_CHECK("c_cube_dim", test_comm, c_cube_dim, c_keyhash, 1);
GAP_CHECK("c_topo_component", test_comm, c_topo_component, c_cube_dim, 1);
GAP_CHECK("c_topo", test_comm, c_topo, c_topo_component, 1);
GAP_CHECK("c_topo_comm", test_comm, c_topo_comm, c_topo, 1);
GAP_CHECK("c_topo_module", test_comm, c_topo_module, c_topo_comm, 1);
GAP_CHECK("c_f_to_c_index", test_comm, c_f_to_c_index, c_topo_module, 1);
GAP_CHECK("c_topo", test_comm, c_topo, c_cube_dim, 1);
GAP_CHECK("c_f_to_c_index", test_comm, c_f_to_c_index, c_topo, 1);
#ifdef OMPI_WANT_PERUSE
GAP_CHECK("c_peruse_handles", test_comm, c_peruse_handles, c_f_to_c_index, 1);
GAP_CHECK("error_handler", test_comm, error_handler, c_peruse_handles, 1);

Просмотреть файл

@ -102,7 +102,7 @@ int ompi_group_translate_ranks ( ompi_group_t *group1,
/* initialize to no "match" */
ranks2[proc] = MPI_UNDEFINED;
for (proc2 = 0; proc2 < group2->grp_proc_count; proc2++) {
proc2_pointer= ompi_group_peer_lookup(group2 ,proc2);
proc2_pointer= ompi_group_peer_lookup(group2, proc2);
if ( proc1_pointer == proc2_pointer) {
ranks2[proc] = proc2;
break;

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2010 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2007 High Performance Computing Center Stuttgart,
@ -14,6 +14,7 @@
* Copyright (c) 2009-2012 Oak Rigde National Laboratory. All rights reserved.
* Copyright (c) 2011 Sandia National Laboratories. All rights reserved.
* Copyright (c) 2012 Los Alamos Nat Security, LLC. All rights reserved.
* Copyright (c) 2011-2013 INRIA. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -416,6 +417,7 @@ typedef int (MPI_Grequest_cancel_function)(void *, int);
#define MPI_MAX_OBJECT_NAME OPAL_MAX_OBJECT_NAME /* max object name length */
#define MPI_MAX_LIBRARY_VERSION_STRING 256 /* max length of library version string */
#define MPI_UNDEFINED -32766 /* undefined stuff */
#define MPI_DIST_GRAPH 3 /* dist graph topology */
#define MPI_CART 1 /* cartesian topology */
#define MPI_GRAPH 2 /* graph topology */
#define MPI_KEYVAL_INVALID -1 /* invalid key value */
@ -423,6 +425,7 @@ typedef int (MPI_Grequest_cancel_function)(void *, int);
/*
* More constants
*/
#define MPI_UNWEIGHTED ((void *) 2) /* unweighted graph */
#define MPI_BOTTOM ((void *) 0) /* base reference address */
#define MPI_IN_PLACE ((void *) 1) /* in place buffer */
#define MPI_BSEND_OVERHEAD 128 /* size of bsend header + ptr */
@ -1227,6 +1230,27 @@ OMPI_DECLSPEC int MPI_Comm_free_keyval(int *comm_keyval);
OMPI_DECLSPEC int MPI_Comm_free(MPI_Comm *comm);
OMPI_DECLSPEC int MPI_Comm_get_attr(MPI_Comm comm, int comm_keyval,
void *attribute_val, int *flag);
OMPI_DECLSPEC int MPI_Dist_graph_create(MPI_Comm comm_old, int n, int nodes[],
int degrees[], int targets[],
int weights[], MPI_Info info,
int reorder, MPI_Comm * newcomm);
OMPI_DECLSPEC int MPI_Dist_graph_create_adjacent(MPI_Comm comm_old,
int indegree, int sources[],
int sourceweights[],
int outdegree,
int destinations[],
int destweights[],
MPI_Info info, int reorder,
MPI_Comm *comm_dist_graph);
OMPI_DECLSPEC int MPI_Dist_graph_neighbors(MPI_Comm comm, int maxindegree,
int sources[], int sourceweights[],
int maxoutdegree,
int destinations[],
int destweights[]);
OMPI_DECLSPEC int MPI_Dist_graph_neighbors_count(MPI_Comm comm,
int *inneighbors,
int *outneighbors,
int *weighted);
OMPI_DECLSPEC int MPI_Comm_get_errhandler(MPI_Comm comm, MPI_Errhandler *erhandler);
OMPI_DECLSPEC int MPI_Comm_get_name(MPI_Comm comm, char *comm_name, int *resultlen);
OMPI_DECLSPEC int MPI_Comm_get_parent(MPI_Comm *parent);
@ -1766,6 +1790,27 @@ OMPI_DECLSPEC int PMPI_Attr_delete(MPI_Comm comm, int keyval)
__mpi_interface_deprecated__("MPI_Attr_delete is superseded by MPI_Comm_delete_attr in MPI-2.0");
OMPI_DECLSPEC int PMPI_Attr_get(MPI_Comm comm, int keyval, void *attribute_val, int *flag)
__mpi_interface_deprecated__("MPI_Attr_get is superseded by MPI_Comm_get_attr in MPI-2.0");
OMPI_DECLSPEC int PMPI_Dist_graph_create(MPI_Comm comm_old, int n, int nodes[],
int degrees[], int targets[],
int weights[], MPI_Info info,
int reorder, MPI_Comm * newcomm);
OMPI_DECLSPEC int PMPI_Dist_graph_create_adjacent(MPI_Comm comm_old,
int indegree, int sources[],
int sourceweights[],
int outdegree,
int destinations[],
int destweights[],
MPI_Info info, int reorder,
MPI_Comm *comm_dist_graph);
OMPI_DECLSPEC int PMPI_Dist_graph_neighbors(MPI_Comm comm, int maxindegree,
int sources[], int sourceweights[],
int maxoutdegree,
int destinations[],
int destweights[]);
OMPI_DECLSPEC int PMPI_Dist_graph_neighbors_count(MPI_Comm comm,
int *inneighbors,
int *outneighbors,
int *weighted);
OMPI_DECLSPEC int PMPI_Attr_put(MPI_Comm comm, int keyval, void *attribute_val)
__mpi_interface_deprecated__("MPI_Attr_put is superseded by MPI_Comm_set_attr in MPI-2.0");
OMPI_DECLSPEC int PMPI_Barrier(MPI_Comm comm);

Просмотреть файл

@ -1,7 +1,7 @@
/*
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2010 The University of Tennessee and The University
* Copyright (c) 2010-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2009 Oak Ridge National Labs. All rights reserved.
@ -163,7 +163,7 @@ static inline int memchecker_comm(MPI_Comm comm)
}
/*
* We should not check unterlying objects in this way -- either another opal/include/memchecker.h
* We should not check underlying objects in this way -- either another opal/include/memchecker.h
* However, let us assume, that underlying objects are initialized correctly
*/
#if 0
@ -211,10 +211,7 @@ static inline int memchecker_comm(MPI_Comm comm)
opal_memchecker_base_isdefined (&comm->c_remote_group, sizeof(ompi_group_t *));
opal_memchecker_base_isdefined (&comm->c_keyhash, sizeof(struct opal_hash_table_t *));
opal_memchecker_base_isdefined (&comm->c_cube_dim, sizeof(int));
opal_memchecker_base_isdefined (&comm->c_topo_component, sizeof(mca_base_component_t *));
opal_memchecker_base_isdefined (&comm->c_topo, sizeof(const struct mca_topo_base_module_1_0_0_t *));
opal_memchecker_base_isdefined (&comm->c_topo_comm, sizeof(struct mca_topo_base_comm_1_0_0_t *));
opal_memchecker_base_isdefined (&comm->c_topo_module, sizeof(struct mca_topo_base_module_comm_t *));
opal_memchecker_base_isdefined (&comm->c_topo, sizeof(const struct mca_topo_base_module_t *));
opal_memchecker_base_isdefined (&comm->c_f_to_c_index, sizeof(int));
#ifdef OMPI_WANT_PERUSE
opal_memchecker_base_isdefined (&comm->c_peruse_handles, sizeof(struct ompi_peruse_handle_t **));

Просмотреть файл

@ -3,7 +3,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -12,6 +12,7 @@
* All rights reserved.
* Copyright (c) 2008-2013 University of Houston. All rights reserved.
* Copyright (c) 2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 INRIA. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -918,7 +919,7 @@ int ompi_io_ompio_set_aggregator_props (mca_io_ompio_file_t *fh,
if (-1 == num_aggregators) {
/* Determine Topology Information */
if (fh->f_comm->c_flags & OMPI_COMM_CART) {
fh->f_comm->c_topo->topo_cartdim_get(fh->f_comm, &ndims);
fh->f_comm->c_topo->topo.cart.cartdim_get(fh->f_comm, &ndims);
dims = (int*)malloc (ndims * sizeof(int));
if (NULL == dims) {
@ -944,7 +945,7 @@ int ompi_io_ompio_set_aggregator_props (mca_io_ompio_file_t *fh,
return OMPI_ERR_OUT_OF_RESOURCE;
}
fh->f_comm->c_topo->topo_cart_get(fh->f_comm, ndims, dims, periods, coords);
fh->f_comm->c_topo->topo.cart.cart_get(fh->f_comm, ndims, dims, periods, coords);
/*
printf ("NDIMS = %d\n", ndims);
@ -1007,7 +1008,7 @@ int ompi_io_ompio_set_aggregator_props (mca_io_ompio_file_t *fh,
}
for (j=0 ; j<fh->f_size ; j++) {
fh->f_comm->c_topo->topo_cart_coords (fh->f_comm, j, ndims, coords_tmp);
fh->f_comm->c_topo->topo.cart.cart_coords (fh->f_comm, j, ndims, coords_tmp);
if (coords_tmp[0]/i == coords[0]/i) {
if ((coords_tmp[1]/root_offset)*root_offset ==
(coords[1]/root_offset)*root_offset) {

Просмотреть файл

@ -455,4 +455,37 @@ ob1_hdr_hton_intr(mca_pml_ob1_hdr_t *hdr, const uint8_t hdr_type,
#else
#define ob1_hdr_hton(h, t, p) do{}while(0)
#endif
#endif
static inline __opal_attribute_always_inline__ void
ob1_hdr_copy(mca_pml_ob1_hdr_t *src, mca_pml_ob1_hdr_t *dst)
{
switch(src->hdr_common.hdr_type) {
case MCA_PML_OB1_HDR_TYPE_MATCH:
memcpy( &(dst->hdr_match), &(src->hdr_match), sizeof(mca_pml_ob1_match_hdr_t) );
break;
case MCA_PML_OB1_HDR_TYPE_RNDV:
memcpy( &(dst->hdr_rndv), &(src->hdr_rndv), sizeof(mca_pml_ob1_rendezvous_hdr_t) );
break;
case MCA_PML_OB1_HDR_TYPE_RGET:
memcpy( &(dst->hdr_rget), &(src->hdr_rget), sizeof(mca_pml_ob1_rget_hdr_t) );
break;
case MCA_PML_OB1_HDR_TYPE_ACK:
memcpy( &(dst->hdr_ack), &(src->hdr_ack), sizeof(mca_pml_ob1_ack_hdr_t) );
break;
case MCA_PML_OB1_HDR_TYPE_FRAG:
memcpy( &(dst->hdr_frag), &(src->hdr_frag), sizeof(mca_pml_ob1_frag_hdr_t) );
break;
case MCA_PML_OB1_HDR_TYPE_PUT:
memcpy( &(dst->hdr_rdma), &(src->hdr_rdma), sizeof(mca_pml_ob1_rdma_hdr_t) );
break;
case MCA_PML_OB1_HDR_TYPE_FIN:
memcpy( &(dst->hdr_fin), &(src->hdr_fin), sizeof(mca_pml_ob1_fin_hdr_t) );
break;
default:
memcpy( &(dst->hdr_common), &(src->hdr_common), sizeof(mca_pml_ob1_common_hdr_t) );
break;
}
}
#endif /* MCA_PML_OB1_HEADER_H */

Просмотреть файл

@ -69,7 +69,7 @@ do { \
unsigned char* _ptr = (unsigned char*)frag->addr; \
/* init recv_frag */ \
frag->btl = btl; \
frag->hdr = *(mca_pml_ob1_hdr_t*)hdr; \
ob1_hdr_copy( (mca_pml_ob1_hdr_t*)hdr, &frag->hdr ); \
frag->num_segments = 1; \
_size = segs[0].seg_len; \
for( i = 1; i < cnt; i++ ) { \

Просмотреть файл

@ -2,7 +2,7 @@
# Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
# University Research and Technology
# Corporation. All rights reserved.
# Copyright (c) 2004-2005 The University of Tennessee and The University
# Copyright (c) 2004-2013 The University of Tennessee and The University
# of Tennessee Research Foundation. All rights
# reserved.
# Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -16,23 +16,28 @@
# $HEADER$
#
headers += \
base/base.h
headers += base/base.h
libmca_topo_la_SOURCES += \
base/topo_base_cart_coords.c \
base/topo_base_cart_create.c \
base/topo_base_cartdim_get.c \
base/topo_base_cart_get.c \
base/topo_base_cart_rank.c \
base/topo_base_cart_map.c \
base/topo_base_cart_shift.c \
base/topo_base_cart_sub.c \
base/topo_base_cartdim_get.c \
base/topo_base_comm_select.c \
base/topo_base_dist_graph_create.c \
base/topo_base_dist_graph_create_adjacent.c \
base/topo_base_dist_graph_neighbors.c \
base/topo_base_dist_graph_neighbors_count.c \
base/topo_base_find_available.c \
base/topo_base_frame.c \
base/topo_base_graph_create.c \
base/topo_base_graphdims_get.c \
base/topo_base_graph_get.c \
base/topo_base_graph_map.c \
base/topo_base_graph_neighbors.c \
base/topo_base_graph_neighbors_count.c \
base/topo_base_frame.c \
base/topo_base_comm_select.c \
base/topo_base_comm_unselect.c
base/topo_base_graphdims_get.c \
base/topo_base_lazy_init.c

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -29,6 +29,7 @@
#include "ompi/mca/topo/topo.h"
#include "ompi/proc/proc.h"
#include "ompi/communicator/communicator.h"
#include "ompi/info/info.h"
/*
* All stuff goes in here
@ -36,97 +37,159 @@
BEGIN_C_DECLS
/* Lazily initialize the framework (if it wasn't already) */
OMPI_DECLSPEC int mca_topo_base_lazy_init(void);
/*
* MCA Framework
*/
OMPI_DECLSPEC extern mca_base_framework_t ompi_topo_base_framework;
/* select a component */
int mca_topo_base_comm_select(ompi_communicator_t *comm,
mca_base_component_t *preferred);
int mca_topo_base_comm_unselect(ompi_communicator_t *comm);
int mca_topo_base_find_available (bool enable_progress_threads,
bool enable_mpi_threads);
/* Select a topo module for a particular type of topology */
OMPI_DECLSPEC int
mca_topo_base_comm_select(const ompi_communicator_t* comm,
mca_topo_base_module_t* preferred_module,
mca_topo_base_module_t** selected_module,
uint32_t type);
/* Find all components that want to be considered in this job */
OMPI_DECLSPEC int
mca_topo_base_find_available(bool enable_progress_threads,
bool enable_mpi_threads);
OMPI_DECLSPEC int mca_topo_base_init_comm (ompi_communicator_t *comm);
OMPI_DECLSPEC int mca_topo_base_get_param (ompi_communicator_t *comm, int keyval);
/*
* All the glue functions which we will provide to the users by
* default. The component authors need to only write back-end
* functions for cart_create(), graph_create(), graph_map(), and
* cart_map() for their topology components. But they can implement
* these glue functions if they want.
*
* These glue functions
*/
OMPI_DECLSPEC int
mca_topo_base_cart_create(mca_topo_base_module_t *topo_module,
ompi_communicator_t* old_comm,
int ndims,
int *dims,
int *periods,
bool reorder,
ompi_communicator_t** comm_topo);
/*
* All the glue functions which we will provide to the users by
* default. The component authors need to only write back-end
* functions for graph_map() and cart_map() for their topology
* components. But they can implement these glue functions if
* they want.
*/
OMPI_DECLSPEC int mca_topo_base_cart_coords (ompi_communicator_t *comm,
int rank,
int maxdims,
int *coords);
OMPI_DECLSPEC int
mca_topo_base_cart_coords(ompi_communicator_t *comm,
int rank,
int maxdims,
int *coords);
OMPI_DECLSPEC int mca_topo_base_cart_create (mca_topo_base_comm_t *topo_data,
int *proc_count,
ompi_proc_t **proc_pointers,
int *new_rank,
int ndims,
int *dims,
int *periods,
bool reorder);
OMPI_DECLSPEC int
mca_topo_base_cartdim_get(ompi_communicator_t *comm,
int *ndims);
OMPI_DECLSPEC int mca_topo_base_cartdim_get (ompi_communicator_t *comm,
int *ndims);
OMPI_DECLSPEC int
mca_topo_base_cart_get(ompi_communicator_t *comm,
int maxdims,
int *dims,
int *periods,
int *coords);
OMPI_DECLSPEC int mca_topo_base_cart_get (ompi_communicator_t *comm,
int maxdims,
int *dims,
int *periods,
int *coords);
OMPI_DECLSPEC int
mca_topo_base_cart_map(ompi_communicator_t * comm,
int ndims,
int *dims, int *periods, int *newrank);
OMPI_DECLSPEC int mca_topo_base_cart_rank (ompi_communicator_t *comm,
int *coords,
int *rank);
OMPI_DECLSPEC int
mca_topo_base_cart_rank(ompi_communicator_t *comm,
int *coords,
int *rank);
OMPI_DECLSPEC int mca_topo_base_cart_shift (ompi_communicator_t *comm,
int direction,
int disp,
int *rank_source,
int *rank_dest);
OMPI_DECLSPEC int
mca_topo_base_cart_shift(ompi_communicator_t *comm,
int direction,
int disp,
int *rank_source,
int *rank_dest);
OMPI_DECLSPEC int mca_topo_base_cart_sub (ompi_communicator_t *comm,
int *remain_dims,
OMPI_DECLSPEC int
mca_topo_base_cart_sub(ompi_communicator_t *comm,
int *remain_dims,
ompi_communicator_t **new_comm);
OMPI_DECLSPEC int
mca_topo_base_graphdims_get(ompi_communicator_t *comm,
int *nodes,
int *nedges);
OMPI_DECLSPEC int
mca_topo_base_graph_create(mca_topo_base_module_t *topo_module,
ompi_communicator_t* old_comm,
int nnodes,
int *index,
int *edges,
bool reorder,
ompi_communicator_t** new_comm);
OMPI_DECLSPEC int
mca_topo_base_graph_get(ompi_communicator_t *comm,
int maxindex,
int maxedges,
int *index,
int *edges);
OMPI_DECLSPEC int
mca_topo_base_graph_map(ompi_communicator_t * comm,
int nnodes,
int *index, int *edges, int *newrank);
OMPI_DECLSPEC int
mca_topo_base_graph_neighbors(ompi_communicator_t *comm,
int rank,
int maxneighbors,
int *neighbors);
OMPI_DECLSPEC int
mca_topo_base_graph_neighbors_count(ompi_communicator_t *comm,
int rank,
int *nneighbors);
/**
* Efficiently distribute the information about the distributed graph as
* submitted through the distributed graph interface.
*/
OMPI_DECLSPEC int
mca_topo_base_dist_graph_distribute(mca_topo_base_module_t* module,
ompi_communicator_t *comm,
int n, int nodes[],
int degrees[], int targets[],
int weights[],
mca_topo_base_comm_dist_graph_2_1_0_t** ptopo);
OMPI_DECLSPEC int
mca_topo_base_dist_graph_create(mca_topo_base_module_t* module,
ompi_communicator_t *old_comm,
int n, int nodes[],
int degrees[], int targets[], int weights[],
ompi_info_t *info, int reorder,
ompi_communicator_t **new_comm);
OMPI_DECLSPEC int mca_topo_base_graph_create (mca_topo_base_comm_t *topo_data,
int *proc_count,
ompi_proc_t **proc_pointers,
int *new_rank,
int nnodes,
int *index,
int *edges,
bool reorder);
OMPI_DECLSPEC int mca_topo_base_graphdims_get (ompi_communicator_t *comm,
int *nodes,
int *nedges);
OMPI_DECLSPEC int mca_topo_base_graph_get (ompi_communicator_t *comm,
int maxindex,
int maxedges,
int *index,
int *edges);
OMPI_DECLSPEC int mca_topo_base_graph_neighbors (ompi_communicator_t *comm,
int rank,
int maxneighbors,
int *neighbors);
OMPI_DECLSPEC int mca_topo_base_graph_neighbors_count (ompi_communicator_t *comm,
int rank,
int *nneighbors);
OMPI_DECLSPEC int
mca_topo_base_dist_graph_create_adjacent(mca_topo_base_module_t* module,
ompi_communicator_t *old_comm,
int indegree, int sources[],
int sourceweights[], int outdegree,
int destinations[], int destweights[],
ompi_info_t *info, int reorder,
ompi_communicator_t **comm_dist_graph);
OMPI_DECLSPEC int
mca_topo_base_dist_graph_neighbors(ompi_communicator_t *comm,
int maxindegree,
int sources[], int sourceweights[],
int maxoutdegree, int destinations[],
int destweights[]);
OMPI_DECLSPEC int
mca_topo_base_dist_graph_neighbors_count(ompi_communicator_t *comm,
int *inneighbors, int *outneighbors, int *weighted);
END_C_DECLS

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -32,30 +32,23 @@
* coordinates of specified process (integer)
*
* @retval MPI_SUCCESS
* @retval MPI_ERR_COMM
* @retval MPI_ERR_TOPOLOGY
* @retval MPI_ERR_RANK
* @retval MPI_ERR_DIMS
* @retval MPI_ERR_ARG
*/
int mca_topo_base_cart_coords (ompi_communicator_t* comm,
int rank,
int maxdims,
int *coords){
int dim;
int remprocs;
int i;
int *d;
int mca_topo_base_cart_coords(ompi_communicator_t* comm,
int rank,
int maxdims,
int *coords)
{
int dim, remprocs, i, *d;
/*
* loop computing the co-ordinates
*/
d = comm->c_topo_comm->mtc_dims_or_index;
d = comm->c_topo->mtc.cart->dims;
remprocs = ompi_comm_size(comm);
for (i = 0;
(i < comm->c_topo_comm->mtc_ndims_or_nnodes) && (i < maxdims);
(i < comm->c_topo->mtc.cart->ndims) && (i < maxdims);
++i, ++d) {
dim = *d;
remprocs /= dim;

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -41,64 +41,140 @@
* @retval OMPI_SUCCESS
*/
int mca_topo_base_cart_create (mca_topo_base_comm_t *topo_data,
int *proc_count,
ompi_proc_t **proc_pointers,
int *new_rank,
int ndims,
int *dims,
int *periods,
bool reorder) {
int mca_topo_base_cart_create(mca_topo_base_module_t *topo,
ompi_communicator_t* old_comm,
int ndims,
int *dims,
int *periods,
bool reorder,
ompi_communicator_t** comm_topo)
{
int nprocs = 1, i, *p, new_rank, num_procs, ret;
ompi_communicator_t *new_comm;
ompi_proc_t **topo_procs = NULL;
mca_topo_base_comm_cart_2_1_0_t* cart;
int nprocs;
int dim;
int i;
int *p;
int *coords = topo_data->mtc_coords;
int dummy_rank;
num_procs = old_comm->c_local_group->grp_proc_count;
new_rank = old_comm->c_local_group->grp_my_rank;
assert(topo->type == OMPI_COMM_CART);
nprocs = 1;
p = topo_data->mtc_dims_or_index;
/* Calculate the number of processes in this grid */
for (i = 0; i < topo_data->mtc_ndims_or_nnodes; ++i, ++p) {
if(*p <= 0) {
return OMPI_ERROR;
}
nprocs *= *p;
}
/* check for the error condition */
if (*proc_count < nprocs) {
return MPI_ERR_DIMS;
}
/* check if we have to trim the list of processes */
if (nprocs < *proc_count) {
*proc_count = nprocs;
}
if (*new_rank > (nprocs-1)) {
/* sorry, but in our scheme this process is cut off */
*new_rank = MPI_UNDEFINED;
return OMPI_SUCCESS;
}
/* Have to replace this with the actual function body itself */
p = topo_data->mtc_dims_or_index;
coords = topo_data->mtc_coords;
dummy_rank = *new_rank;
for (i=0;
(i < topo_data->mtc_ndims_or_nnodes && i < ndims);
++i, ++p) {
dim = *p;
nprocs /= dim;
*coords++ = dummy_rank / nprocs;
dummy_rank %= nprocs;
/* Calculate the number of processes in this grid */
p = dims;
for (i = 0; i < ndims; ++i, ++p) {
if(*p <= 0) {
return OMPI_ERROR;
}
nprocs *= *p;
}
/* end here */
return OMPI_SUCCESS;
/* check for the error condition */
if (num_procs < nprocs) {
return MPI_ERR_DIMS;
}
/* check if we have to trim the list of processes */
if (nprocs < num_procs) {
num_procs = nprocs;
}
if (new_rank > (nprocs-1)) {
ndims = 0;
new_rank = MPI_UNDEFINED;
num_procs = 0;
}
cart = (mca_topo_base_comm_cart_2_1_0_t*)calloc(1, sizeof(mca_topo_base_comm_cart_2_1_0_t));
if( NULL == cart ) {
ompi_comm_free(&new_comm);
return OMPI_ERR_OUT_OF_RESOURCE;
}
cart->ndims = ndims;
/* MPI-2.1 allows 0-dimension cartesian communicators, so prevent
a 0-byte malloc -- leave dims as NULL */
if( ndims > 0 ) {
cart->dims = (int*)malloc(sizeof(int) * ndims);
if (NULL == cart->dims) {
free(cart);
return OMPI_ERROR;
}
memcpy(cart->dims, dims, ndims * sizeof(int));
/* Cartesian communicator; copy the right data to the common information */
cart->periods = (int*)malloc(sizeof(int) * ndims);
if (NULL == cart->periods) {
if(NULL != cart->dims) free(cart->dims);
free(cart);
return OMPI_ERR_OUT_OF_RESOURCE;
}
memcpy(cart->periods, periods, ndims * sizeof(int));
cart->coords = (int*)malloc(sizeof(int) * ndims);
if (NULL == cart->coords) {
free(cart->periods);
if(NULL != cart->dims) free(cart->dims);
free(cart);
return OMPI_ERR_OUT_OF_RESOURCE;
}
{ /* setup the cartesian topology */
int nprocs = num_procs, rank = new_rank;
for (i = 0; i < ndims; ++i) {
nprocs /= cart->dims[i];
cart->coords[i] = rank / nprocs;
rank %= nprocs;
}
}
}
/* Copy the proc structure from the previous communicator over to
the new one. The topology module is then able to work on this
copy and rearrange it as it deems fit. */
topo_procs = (ompi_proc_t**)malloc(num_procs * sizeof(ompi_proc_t *));
if(OMPI_GROUP_IS_DENSE(old_comm->c_local_group)) {
memcpy(topo_procs,
old_comm->c_local_group->grp_proc_pointers,
num_procs * sizeof(ompi_proc_t *));
} else {
for(i = 0 ; i < num_procs; i++) {
topo_procs[i] = ompi_group_peer_lookup(old_comm->c_local_group,i);
}
}
/* allocate a new communicator */
new_comm = ompi_comm_allocate(num_procs, 0);
if (NULL == new_comm) {
free(topo_procs);
if(NULL != cart->periods) free(cart->periods);
if(NULL != cart->coords) free(cart->coords);
if(NULL != cart->dims) free(cart->dims);
free(cart);
return MPI_ERR_INTERN;
}
ret = ompi_comm_enable(old_comm, new_comm,
new_rank, num_procs, topo_procs);
if (OMPI_SUCCESS != ret) {
/* something wrong happened during setting the communicator */
ompi_comm_free (&new_comm);
if(NULL != cart->periods) free(cart->periods);
if(NULL != cart->coords) free(cart->coords);
if(NULL != cart->dims) free(cart->dims);
free(cart);
return ret;
}
new_comm->c_topo = topo;
new_comm->c_topo->mtc.cart = cart;
new_comm->c_topo->reorder = reorder;
new_comm->c_flags |= OMPI_COMM_CART;
*comm_topo = new_comm;
if( MPI_UNDEFINED == new_rank ) {
ompi_comm_free(&new_comm);
*comm_topo = MPI_COMM_NULL;
}
/* end here */
return OMPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -41,18 +41,18 @@
*
* @retval MPI_SUCCESS
*/
int mca_topo_base_cart_get (ompi_communicator_t* comm,
int maxdims,
int *dims,
int *periods,
int *coords)
int mca_topo_base_cart_get(ompi_communicator_t* comm,
int maxdims,
int *dims,
int *periods,
int *coords)
{
int m = (maxdims <= comm->c_topo_comm->mtc_ndims_or_nnodes) ?
maxdims : comm->c_topo_comm->mtc_ndims_or_nnodes;
int m = (maxdims <= comm->c_topo->mtc.cart->ndims) ?
maxdims : comm->c_topo->mtc.cart->ndims;
memcpy(dims, comm->c_topo_comm->mtc_dims_or_index, m * sizeof(int));
memcpy(periods, comm->c_topo_comm->mtc_periods_or_edges, m * sizeof(int));
memcpy(coords, comm->c_topo_comm->mtc_coords, m * sizeof(int));
memcpy(dims, comm->c_topo->mtc.cart->dims, m * sizeof(int));
memcpy(periods, comm->c_topo->mtc.cart->periods, m * sizeof(int));
memcpy(coords, comm->c_topo->mtc.cart->coords, m * sizeof(int));
return MPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -14,15 +14,14 @@
* Additional copyrights may follow
*
* $HEADER$
*/
*/
#include "ompi_config.h"
#include "ompi/mca/topo/unity/topo_unity.h"
#include "ompi/mca/topo/base/base.h"
#include "ompi/communicator/communicator.h"
/*
* function - mca_topo_unity_cart_map
* function - mca_topo_base_cart_map
*
* @param comm input communicator (handle)
* @param ndims number of dimensions of cartesian structure (integer)
@ -37,17 +36,11 @@
* @retval MPI_ERR_DIMS
*/
int mca_topo_unity_cart_map (ompi_communicator_t* comm,
int ndims,
int *dims,
int *periods,
int *newrank)
int mca_topo_base_cart_map(ompi_communicator_t* comm,
int ndims,
int *dims, int *periods, int *newrank)
{
int nprocs;
int rank;
int size;
int i;
int *p;
int nprocs, rank, size, i, *p;
/*
* Compute the # of processes in the grid.

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -36,9 +36,10 @@
* @retval MPI_ERR_ARG
*/
int mca_topo_base_cart_rank (ompi_communicator_t* comm,
int *coords,
int *rank){
int mca_topo_base_cart_rank(ompi_communicator_t* comm,
int *coords,
int *rank)
{
int prank;
int dim;
int ord;
@ -53,8 +54,8 @@ int mca_topo_base_cart_rank (ompi_communicator_t* comm,
factor = 1;
prank = 0;
i = comm->c_topo_comm->mtc_ndims_or_nnodes - 1;
d = comm->c_topo_comm->mtc_dims_or_index + i;
i = comm->c_topo->mtc.cart->ndims - 1;
d = comm->c_topo->mtc.cart->dims + i;
c = coords + i;
for (; i >= 0; --i, --c, --d) {

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -35,47 +35,38 @@
* Cartesian mesh.
*
* @retval MPI_SUCCESS
* @retval MPI_ERR_TOPOLOGY
* @retval MPI_ERR_DIMS
* @retval MPI_ERR_COMM
* @retval MPI_ERR_ARG
*/
int mca_topo_base_cart_shift (ompi_communicator_t* comm,
int direction,
int disp,
int *rank_source,
int *rank_dest){
int factor;
int thisdirection = 0;
int thisperiod = 0;
int ord;
int srcord;
int destord;
int i;
int *d, *q;
int mca_topo_base_cart_shift(ompi_communicator_t* comm,
int direction,
int disp,
int *rank_source,
int *rank_dest)
{
int factor, thisdirection = 0, thisperiod = 0, ord;
int srcord, destord, i, *d, *q;
/*
* Handle the trivial case.
*/
/*
* Handle the trivial case.
*/
ord = ompi_comm_rank(comm);
if (disp == 0) {
*rank_dest = *rank_source = ord;
return MPI_SUCCESS;
}
/*
* Compute the rank factor and ordinate.
*/
/*
* Compute the rank factor and ordinate.
*/
factor = ompi_comm_size(comm);
d = comm->c_topo_comm->mtc_dims_or_index;
q = comm->c_topo_comm->mtc_periods_or_edges;
for (i = 0; (i < comm->c_topo_comm->mtc_ndims_or_nnodes) && (i <= direction); ++i, ++d, ++q) {
d = comm->c_topo->mtc.cart->dims;
q = comm->c_topo->mtc.cart->periods;
for (i = 0; (i < comm->c_topo->mtc.cart->ndims) && (i <= direction); ++i, ++d, ++q) {
thisdirection = *d;
thisperiod = *q;
ord %= factor;
factor /= thisdirection;
}
}
ord /= factor;
/*
@ -86,20 +77,20 @@ int mca_topo_base_cart_shift (ompi_communicator_t* comm,
srcord = ord - disp;
destord = ord + disp;
if ( ((destord < 0) || (destord >= thisdirection)) && (!thisperiod) ) {
*rank_dest = MPI_PROC_NULL;
*rank_dest = MPI_PROC_NULL;
} else {
destord %= thisdirection;
if (destord < 0) destord += thisdirection;
*rank_dest = ompi_comm_rank(comm);
*rank_dest += ((destord - ord) * factor);
destord %= thisdirection;
if (destord < 0) destord += thisdirection;
*rank_dest = ompi_comm_rank(comm);
*rank_dest += ((destord - ord) * factor);
}
if ( ((srcord < 0) || (srcord >= thisdirection)) && (!thisperiod) ) {
*rank_source = MPI_PROC_NULL;
*rank_source = MPI_PROC_NULL;
} else {
srcord %= thisdirection;
if (srcord < 0) srcord += thisdirection;
*rank_source= ompi_comm_rank(comm);
*rank_source += ((srcord - ord) * factor);
srcord %= thisdirection;
if (srcord < 0) srcord += thisdirection;
*rank_source= ompi_comm_rank(comm);
*rank_source += ((srcord - ord) * factor);
}
return MPI_SUCCESS;

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -37,109 +37,112 @@
* @retval MPI_ERR_COMM
*/
int mca_topo_base_cart_sub (ompi_communicator_t* comm,
int *remain_dims,
ompi_communicator_t** new_comm){
int *remain_dims,
ompi_communicator_t** new_comm)
{
struct ompi_communicator_t *temp_comm;
mca_topo_base_comm_cart_2_1_0_t *old_cart;
int errcode, colour, key, colfactor, keyfactor;
int ndim, dim, i;
int *d, *dorig = NULL, *dold, *c, *r, *p, *porig = NULL, *pold;
mca_topo_base_module_t* topo;
mca_topo_base_comm_cart_2_1_0_t* cart;
struct ompi_communicator_t *temp_comm;
int errcode;
int colour;
int key;
int colfactor;
int keyfactor;
int rank;
int ndim;
int dim;
int i;
int *d, *dold;
int *c;
int *r;
int *p, *pold;
*new_comm = MPI_COMM_NULL;
*new_comm = MPI_COMM_NULL;
old_cart = comm->c_topo->mtc.cart;
/*
* Compute colour and key used in splitting the communicator.
*/
colour = key = 0;
colfactor = keyfactor = 1;
ndim = 0;
colour = key = 0;
colfactor = keyfactor = 1;
ndim = 0;
i = comm->c_topo_comm->mtc_ndims_or_nnodes - 1;
d = comm->c_topo_comm->mtc_dims_or_index + i;
c = comm->c_topo_comm->mtc_coords + i;
r = remain_dims + i;
i = old_cart->ndims - 1;
d = old_cart->dims + i;
c = comm->c_topo->mtc.cart->coords + i;
r = remain_dims + i;
for (; i >= 0; --i, --d, --c, --r) {
for (; i >= 0; --i, --d, --c, --r) {
dim = *d;
if (*r == 0) {
colour += colfactor * (*c);
colfactor *= dim;
colour += colfactor * (*c);
colfactor *= dim;
} else {
++ndim;
key += keyfactor * (*c);
keyfactor *= dim;
++ndim;
key += keyfactor * (*c);
keyfactor *= dim;
}
}
}
/* Special case: if all of remain_dims were false, we need to make
a 0-dimension cartesian communicator with just ourselves in it
(you can't have a communicator unless you're in it). */
if (0 == ndim) {
colour = ompi_comm_rank (comm);
}
/*
* Split the communicator.
*/
errcode = ompi_comm_split (comm, colour, key, &temp_comm, true);
if (errcode != MPI_SUCCESS) {
if (0 == ndim) {
colour = ompi_comm_rank (comm);
}
/* Split the communicator. */
errcode = ompi_comm_split(comm, colour, key, &temp_comm, false);
if (errcode != OMPI_SUCCESS) {
return errcode;
}
/*
* Fill the communicator with topology information.
*/
if (temp_comm != MPI_COMM_NULL) {
temp_comm->c_topo_comm->mtc_ndims_or_nnodes = ndim;
}
/* Fill the communicator with topology information. */
if (temp_comm != MPI_COMM_NULL) {
assert( NULL == temp_comm->c_topo );
if (OMPI_SUCCESS != (errcode = mca_topo_base_comm_select(temp_comm,
comm->c_topo,
&topo,
OMPI_COMM_CART))) {
ompi_comm_free(&temp_comm);
return OMPI_ERR_OUT_OF_RESOURCE;
}
if (ndim >= 1) {
/* Copy the dimensions */
d = temp_comm->c_topo_comm->mtc_dims_or_index;
dold = comm->c_topo_comm->mtc_dims_or_index;
dorig = d = (int*)malloc(ndim * sizeof(int));
dold = old_cart->dims;
/* Copy the periods */
porig = p = (int*)malloc(ndim * sizeof(int));
pold = old_cart->periods;
r = remain_dims;
for (i = 0; i < comm->c_topo_comm->mtc_ndims_or_nnodes;
++i, ++dold, ++r) {
for (i = 0; i < old_cart->ndims; ++i, ++dold, ++pold, ++r) {
if (*r) {
*d++ = *dold;
}
}
/* Copy the periods */
p = temp_comm->c_topo_comm->mtc_periods_or_edges;
pold = comm->c_topo_comm->mtc_periods_or_edges;
r = remain_dims;
for (i = 0; i < comm->c_topo_comm->mtc_ndims_or_nnodes;
++i, ++pold, ++r) {
if (*r) {
*p++ = *pold;
}
}
}
cart = (mca_topo_base_comm_cart_2_1_0_t*)calloc(1, sizeof(mca_topo_base_comm_cart_2_1_0_t));
if( NULL == cart ) {
ompi_comm_free(&temp_comm);
return OMPI_ERR_OUT_OF_RESOURCE;
}
cart->ndims = ndim;
cart->dims = dorig;
cart->periods = porig;
cart->coords = (int*)malloc(sizeof(int) * ndim);
if (NULL == cart->coords) {
free(cart->periods);
if(NULL != cart->dims) free(cart->dims);
free(cart);
return OMPI_ERR_OUT_OF_RESOURCE;
}
{ /* setup the cartesian topology */
int nprocs = temp_comm->c_local_group->grp_proc_count,
rank = temp_comm->c_local_group->grp_my_rank;
/*
* Compute the caller's coordinates, if ndims>0
*/
rank = ompi_comm_rank (temp_comm);
if (MPI_SUCCESS != errcode) {
OBJ_RELEASE(temp_comm);
return errcode;
}
errcode = temp_comm->c_topo->topo_cart_coords (temp_comm, rank,
ndim, temp_comm->c_topo_comm->mtc_coords);
if (MPI_SUCCESS != errcode) {
OBJ_RELEASE(temp_comm);
return errcode;
for (i = 0; i < ndim; ++i) {
nprocs /= cart->dims[i];
cart->coords[i] = rank / nprocs;
rank %= nprocs;
}
}
}
temp_comm->c_topo = topo;
temp_comm->c_topo->mtc.cart = cart;
temp_comm->c_topo->reorder = false;
temp_comm->c_flags |= OMPI_COMM_CART;
}
*new_comm = temp_comm;
*new_comm = temp_comm;
return MPI_SUCCESS;
return MPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -30,10 +30,9 @@
* @retval MPI_SUCCESS
* @retval MPI_ERR_COMM
*/
int mca_topo_base_cartdim_get (ompi_communicator_t* comm,
int *ndims){
*ndims = comm->c_topo_comm->mtc_ndims_or_nnodes;
int mca_topo_base_cartdim_get(ompi_communicator_t* comm, int *ndims)
{
*ndims = comm->c_topo->mtc.cart->ndims;
return MPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -26,19 +26,19 @@
#include "opal/util/output.h"
#include "opal/mca/mca.h"
#include "opal/mca/base/base.h"
#include "ompi/mca/topo/topo.h"
#include "ompi/mca/topo/base/base.h"
#include "ompi/communicator/communicator.h"
/*
* Local functions
*/
static void fill_null_pointers(mca_topo_base_module_t *module);
static void fill_null_pointers(int type, mca_topo_base_module_t *module);
/*
* This structure is needed so that we can close the modules
* This structure is needed so that we can close the modules
* which are not selected but were opened. mca_base_modules_close
* which does this job for us requires a opal_list_t which contains
* these modules
@ -51,31 +51,28 @@ struct queried_module_t {
typedef struct queried_module_t queried_module_t;
static OBJ_CLASS_INSTANCE(queried_module_t, opal_list_item_t, NULL, NULL);
/*
* Only one topo module can be attached to each communicator.
* Only one topo module can be attached to each communicator. The
* communicator provided as argument is the old communicator, and the
* newly selected topology is __not__ supposed to be attached to it.
*
* This module calls the query funtion on all the components that were
* detected by topo_base_open. This function is called on a
* per-communicator basis. This function has the following function.
*
* 1. Iterate over the list of available_components
* 1. Iterate over the list of available_components.
* 2. Call the query function on each of these components.
* 3. query function returns the structure containing pointers
* to its module and its priority
* 4. Select the module with the highest priority
* 5. Call the init function on the selected module so that it does the
* right setup for the communicator
* 6. Call finalize on all the other modules which returned
* their module but were unfortunate to not get selected
* 3. The query function returns a module and its priority.
* 4. Select the module with the highest priority.
* 5. OBJ_RELEASE all the "losing" modules.
*/
int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
mca_base_component_t *preferred)
int mca_topo_base_comm_select(const ompi_communicator_t* comm,
mca_topo_base_module_t* preferred_module,
mca_topo_base_module_t** selected_module,
uint32_t type)
{
int priority;
int best_priority;
char name[MPI_MAX_OBJECT_NAME+32];
int priority;
int best_priority;
opal_list_item_t *item;
mca_base_component_list_item_t *cli;
mca_topo_base_component_t *component;
@ -83,68 +80,52 @@ int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
mca_topo_base_module_t *module;
opal_list_t queried;
queried_module_t *om;
char *str;
int err = MPI_SUCCESS;
/* Announce */
/* ANJU:
* check for names array .... mca_base_var_ */
snprintf(name, sizeof(name), "%s (cid %d)", comm->c_name,
comm->c_contextid);
name[sizeof(name) - 1] = '\0';
/* Ensure the topo framework is initialized */
if (OMPI_SUCCESS != (err = mca_topo_base_lazy_init())) {
return err;
}
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"topo:base:comm_select: new communicator: %s",
name);
"topo:base:comm_select: new communicator: %s (cid %d)",
comm->c_name, comm->c_contextid);
/* Check and see if a preferred component was provided. If it was
provided then it should be used (if possible) */
provided then it should be used (if possible) */
if (NULL != preferred_module) {
if (NULL != preferred) {
/* We have a preferred component. Check if it is available
/* We have a preferred module. Check if it is available
and if so, whether it wants to run */
str = &(preferred->mca_component_name[0]);
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"topo:base:comm_select: Checking preferred component: %s",
str);
preferred_module->topo_component->topoc_version.mca_component_name);
/* query the component for its priority and get its module
structure. This is necessary to proceed */
component = (mca_topo_base_component_t *)preferred;
module = component->topom_comm_query (&priority);
if (NULL != module &&
NULL != module->topo_module_init &&
NULL != module->topo_graph_map &&
NULL != module->topo_cart_map) {
component = (mca_topo_base_component_t *)preferred_module->topo_component;
module = component->topoc_comm_query(comm, &priority, type);
if (NULL != module) {
/* this query seems to have returned something legitimate
* and we can now go ahead and initialize the
* communicator with it * but first, the functions which
* are null need to be filled in */
fill_null_pointers (module);
comm->c_topo = module;
comm->c_topo_component = preferred;
return module->topo_module_init(comm);
* and we can now go ahead fill the NULL functions with the
* corresponding base version and then return.
*/
fill_null_pointers(type, module);
*selected_module = module;
module->topo_component = component;
return OMPI_SUCCESS;
}
/* His preferred component is present, but is unable to
* run. This is not a good sign. We should try selecting
* some other component We let it fall through and select
* from the list of available components
*/
} /*end of selection for preferred component */
/* If we get here, the preferred component is present, but is
unable to run. This is not a good sign. We should try
selecting some other component. We let it fall through
and select from the list of available components */
}
/*
* We fall till here if one of the two things happened:
* We fall here if one of the two things happened:
* 1. The preferred component was provided but for some reason was
* not able to be selected
* not able to be selected
* 2. No preferred component was provided
*
* All we need to do is to go through the list of available
@ -160,25 +141,22 @@ int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
component = (mca_topo_base_component_t *) cli->cli_component;
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"select: initialising %s component %s",
component->topom_version.mca_type_name,
component->topom_version.mca_component_name);
component->topoc_version.mca_type_name,
component->topoc_version.mca_component_name);
/*
* we can call the query function only if there is a function :-)
*/
if (NULL == component->topom_comm_query) {
if (NULL == component->topoc_comm_query) {
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"select: no query, ignoring the component");
} else {
/*
* call the query function and see what it returns
*/
module = component->topom_comm_query (&priority);
module = component->topoc_comm_query(comm, &priority, type);
if (NULL == module ||
NULL == module->topo_module_init ||
NULL == module->topo_graph_map ||
NULL == module->topo_cart_map) {
if (NULL == module) {
/*
* query did not return any action which can be used
*/
@ -208,7 +186,7 @@ int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
om->om_module = module;
opal_list_append(&queried, (opal_list_item_t *)om);
} /* end else of if (NULL == module) */
} /* end else of if (NULL == component->topom_init) */
} /* end else of if (NULL == component->init) */
} /* end for ... end of traversal */
/*
@ -219,13 +197,7 @@ int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
* components which should are initialized.
*/
if (NULL == best_component) {
/*
* This typically means that there was no component which was
* able to run properly this time. So, we need to abort
* JMS replace with show_help
*/
OBJ_DESTRUCT(&queried);
return OMPI_ERROR;
return OMPI_ERR_NOT_FOUND;
}
/*
@ -248,43 +220,23 @@ int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
* module structure we need to fill it in with the base
* structure function pointers. This is yet to be done
*/
/*
* We don return here coz we still need to go through and
* elease the other objects
*/
fill_null_pointers (om->om_module);
comm->c_topo = om->om_module;
err = om->om_module->topo_module_init(comm);
comm->c_topo_component = (mca_base_component_t *)best_component;
fill_null_pointers(type, om->om_module);
om->om_module->topo_component = best_component;
*selected_module = om->om_module;
} else {
/*
* this is not the "choosen one", finalize
*/
if (NULL != om->om_component->topom_comm_unquery) {
/* unquery the component only if they have some clean
* up job to do. Components which are queried but do
* not actually do anything typically do not have a
* unquery. Hence this check is necessary
*/
(void) om->om_component->topom_comm_unquery(comm);
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"select: component %s is not selected",
om->om_component->topom_version.mca_component_name);
} /* end if */
} /* if not best component */
/* this is not the "choosen one", finalize */
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"select: component %s is not selected",
om->om_component->topoc_version.mca_component_name);
OBJ_RELEASE(om->om_module);
}
OBJ_RELEASE(om);
} /* traversing through the entire list */
opal_output_verbose(10, ompi_topo_base_framework.framework_output,
"select: component %s selected",
best_component->topom_version.mca_component_name);
OBJ_DESTRUCT(&queried);
return err;
best_component->topoc_version.mca_component_name);
return OMPI_SUCCESS;
}
@ -293,27 +245,70 @@ int mca_topo_base_comm_select (struct ompi_communicator_t *comm,
* those functions which are not implemented by the module with the
* pointers from the base function. Somewhere, I need to incoroporate
* a check for the common minimum funtions being implemented by the
* module atleast. If not, this module cannot be considered.
*/
static void fill_null_pointers(mca_topo_base_module_t *module)
* module.
*/
static void fill_null_pointers(int type, mca_topo_base_module_t *module)
{
#define CHECK_FOR_NULL_FUNCTION_POINTER(name) \
if (NULL == module->topo_##name) { \
module->topo_##name = mca_topo_base_##name; \
}
CHECK_FOR_NULL_FUNCTION_POINTER(cart_coords);
CHECK_FOR_NULL_FUNCTION_POINTER(cart_create);
CHECK_FOR_NULL_FUNCTION_POINTER(cart_get);
CHECK_FOR_NULL_FUNCTION_POINTER(cartdim_get);
CHECK_FOR_NULL_FUNCTION_POINTER(cart_rank);
CHECK_FOR_NULL_FUNCTION_POINTER(cart_shift);
CHECK_FOR_NULL_FUNCTION_POINTER(cart_sub);
CHECK_FOR_NULL_FUNCTION_POINTER(graph_create);
CHECK_FOR_NULL_FUNCTION_POINTER(graph_get);
CHECK_FOR_NULL_FUNCTION_POINTER(graphdims_get);
CHECK_FOR_NULL_FUNCTION_POINTER(graph_neighbors);
CHECK_FOR_NULL_FUNCTION_POINTER(graph_neighbors_count);
#undef CHECK_FOR_NULL_FUNCTION_POINTER
if( OMPI_COMM_CART == type ) {
if (NULL == module->topo.cart.cart_coords) {
module->topo.cart.cart_coords = mca_topo_base_cart_coords;
}
if (NULL == module->topo.cart.cart_create) {
module->topo.cart.cart_create = mca_topo_base_cart_create;
}
if (NULL == module->topo.cart.cart_get) {
module->topo.cart.cart_get = mca_topo_base_cart_get;
}
if (NULL == module->topo.cart.cartdim_get) {
module->topo.cart.cartdim_get = mca_topo_base_cartdim_get;
}
/*
if (NULL == module->topo.cart.cart_map) {
module->topo.cart.cart_map = mca_topo_base_cart_map;
}
*/
if (NULL == module->topo.cart.cart_rank) {
module->topo.cart.cart_rank = mca_topo_base_cart_rank;
}
if (NULL == module->topo.cart.cart_shift) {
module->topo.cart.cart_shift = mca_topo_base_cart_shift;
}
if (NULL == module->topo.cart.cart_sub) {
module->topo.cart.cart_sub = mca_topo_base_cart_sub;
}
} else if( OMPI_COMM_GRAPH == type ) {
if (NULL == module->topo.graph.graph_create) {
module->topo.graph.graph_create = mca_topo_base_graph_create;
}
if (NULL == module->topo.graph.graph_get) {
module->topo.graph.graph_get = mca_topo_base_graph_get;
}
/*
if (NULL == module->topo.graph.graph_map) {
module->topo.graph.graph_map = mca_topo_base_graph_map;
}
*/
if (NULL == module->topo.graph.graphdims_get) {
module->topo.graph.graphdims_get = mca_topo_base_graphdims_get;
}
if (NULL == module->topo.graph.graph_neighbors) {
module->topo.graph.graph_neighbors = mca_topo_base_graph_neighbors;
}
if (NULL == module->topo.graph.graph_neighbors_count) {
module->topo.graph.graph_neighbors_count = mca_topo_base_graph_neighbors_count;
}
} else if( OMPI_COMM_DIST_GRAPH == type ) {
if (NULL == module->topo.dist_graph.dist_graph_create) {
module->topo.dist_graph.dist_graph_create = mca_topo_base_dist_graph_create;
}
if (NULL == module->topo.dist_graph.dist_graph_create_adjacent) {
module->topo.dist_graph.dist_graph_create_adjacent = mca_topo_base_dist_graph_create_adjacent;
}
if (NULL == module->topo.dist_graph.dist_graph_neighbors) {
module->topo.dist_graph.dist_graph_neighbors = mca_topo_base_dist_graph_neighbors;
}
if (NULL == module->topo.dist_graph.dist_graph_neighbors_count) {
module->topo.dist_graph.dist_graph_neighbors_count = mca_topo_base_dist_graph_neighbors_count;
}
}
}

Просмотреть файл

@ -1,45 +0,0 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#include "ompi_config.h"
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "opal/mca/mca.h"
#include "opal/mca/base/base.h"
#include "ompi/mca/topo/base/base.h"
#include "ompi/communicator/communicator.h"
/*
* This function is used to shut down a topology module
* on a communicator. As of now, this should do nothing
* more than just invoke the finalize on the module which
* was selected. There is nothing fancy which we need to
* do as is the case with collectives.
*/
int mca_topo_base_comm_unselect(struct ompi_communicator_t *comm) {
if (NULL != comm->c_topo && NULL != comm->c_topo->topo_module_finalize) {
return comm->c_topo->topo_module_finalize(comm);
}
/* we fall here if there was no topolog module or the selected module
* did not have anything to finalize (its func pointer was NULL) */
return OMPI_SUCCESS;
}

Просмотреть файл

@ -0,0 +1,303 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2011-2013 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011-2013 INRIA. All rights reserved.
* Copyright (c) 2011-2013 Université Bordeaux 1
*/
#include "ompi_config.h"
#include "ompi/communicator/communicator.h"
#include "ompi/info/info.h"
#include "ompi/mca/topo/base/base.h"
#include "ompi/datatype/ompi_datatype.h"
#include "ompi/mca/pml/pml.h"
#include "ompi/request/request.h"
#define IN_INDEX 0
#define OUT_INDEX 1
#define MCA_TOPO_BASE_TAG_DIST_EDGE_IN -50
#define MCA_TOPO_BASE_TAG_DIST_EDGE_OUT -51
typedef struct _dist_graph_elem {
int in;
int out;
} mca_topo_base_dist_graph_elem_t;
int mca_topo_base_dist_graph_distribute(mca_topo_base_module_t* module,
ompi_communicator_t *comm,
int n, int nodes[],
int degrees[], int targets[],
int weights[],
mca_topo_base_comm_dist_graph_2_1_0_t** ptopo)
{
int i, j, err, count, left_over, pending_reqs, current_pos, index, csize;
int *rin = NULL, *rout, *temp = NULL;
mca_topo_base_dist_graph_elem_t *pos, *cnt, *idx;
size_t int_size, how_much;
ompi_status_public_t status;
ompi_request_t **reqs = NULL;
mca_topo_base_comm_dist_graph_2_1_0_t* topo;
ompi_datatype_type_size( (ompi_datatype_t*)&ompi_mpi_int, &int_size);
csize = ompi_comm_size(comm);
/**
* We compress the counts: for each peer we maintain an in and an out.
* In addition we compute 3 arrays (that are allocated in one go):
* - cnt: the number of elements for a peer
* - pos: the position of the first element for a peer
* - idx: temporaru indexes and message count after the reduce.
*/
cnt = (mca_topo_base_dist_graph_elem_t*)calloc(3 * csize, sizeof(mca_topo_base_dist_graph_elem_t));
if( NULL == cnt ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
pos = cnt + csize;
idx = pos + csize;
for( index = i = 0; i < n; i++ ) {
cnt[nodes[i]].out += degrees[i];
for( j = 0; j < degrees[i]; ++j ) {
cnt[targets[index]].in++;
index++;
}
}
/**
* Prepare the positions array. The ith element is the corresponding
* starting position of the ith neighbor in the global array.
*/
pos[0].in = 0;
pos[0].out = 0;
for( i = 0; i < (csize - 1); i++ ) {
pos[i + 1].in = pos[i].in + cnt[i].in;
pos[i + 1].out = pos[i].out + cnt[i].out;
}
rin = (int*)calloc(2 * (pos[csize - 1].in + cnt[csize - 1].in +
pos[csize - 1].out + cnt[csize - 1].out), sizeof(int));
if( NULL == rin ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
rout = &rin[2 * (pos[csize - 1].in + cnt[csize - 1].in)];
for( index = i = 0; i < n; ++i ) { /* for each of the nodes */
for( j = 0; j < degrees[i]; ++j ) { /* for each node's degree */
int position = pos[nodes[i]].out + idx[nodes[i]].out;
if( MPI_UNWEIGHTED != weights ) {
position *= 2;
rout[position + 1] = weights[index];
}
rout[position + 0] = targets[index];
idx[nodes[i]].out++;
position = pos[targets[index]].in + idx[targets[index]].in;
if( MPI_UNWEIGHTED != weights ) {
position *= 2;
rin[position + 1] = weights[index];
}
rin[position + 0] = nodes[i];
idx[targets[index]].in++;
index++;
}
}
err = comm->c_coll.coll_reduce_scatter_block( MPI_IN_PLACE, idx, 2,
(ompi_datatype_t*)&ompi_mpi_int, MPI_SUM, comm,
comm->c_coll.coll_allreduce_module);
/**
* At this point in the indexes array we have:
* - indexes[0] total number of in edges
* - indexes[1] total number of out edges
*/
topo = (mca_topo_base_comm_dist_graph_2_1_0_t*)malloc(sizeof(mca_topo_base_comm_dist_graph_2_1_0_t));
if( NULL == topo ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
topo->indegree = idx[0].in;
topo->outdegree = idx[0].out;
topo->weighted = (weights != MPI_UNWEIGHTED);
topo->in = (int*)malloc(sizeof(int) * topo->indegree);
topo->out = (int*)malloc(sizeof(int) * topo->outdegree);
if( (NULL == topo->in) || (NULL == topo->out) ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
topo->inw = NULL;
topo->outw = NULL;
if (MPI_UNWEIGHTED != weights) {
topo->inw = (int*)malloc(sizeof(int) * topo->indegree);
topo->outw = (int*)malloc(sizeof(int) * topo->outdegree);
if( (NULL == topo->inw) || (NULL == topo->outw) ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
}
reqs = (ompi_request_t**)malloc(sizeof(ompi_request_t*) * 2 * csize);
for (pending_reqs = i = 0; i < csize; ++i) {
int position;
if( 0 != (count = cnt[i].in) ) {
position = pos[i].in;
if (MPI_UNWEIGHTED != weights) {
count *= 2; /* don't forget the weights */
position *= 2;
}
err = MCA_PML_CALL(isend( &rin[position], count, (ompi_datatype_t*)&ompi_mpi_int,
i, MCA_TOPO_BASE_TAG_DIST_EDGE_IN, MCA_PML_BASE_SEND_STANDARD,
comm, &reqs[pending_reqs]));
pending_reqs++;
}
if( 0 != (count = cnt[i].out) ) {
position = pos[i].out;
if (MPI_UNWEIGHTED != weights) {
count *= 2; /* don't forget the weights */
position *= 2;
}
err = MCA_PML_CALL(isend(&rout[position], count, (ompi_datatype_t*)&ompi_mpi_int,
i, MCA_TOPO_BASE_TAG_DIST_EDGE_OUT, MCA_PML_BASE_SEND_STANDARD,
comm, &reqs[pending_reqs]));
pending_reqs++;
}
}
/**
* Now let's receive the input edges in a temporary array
* and then move them to their corresponding place.
*/
count = topo->indegree;
temp = topo->in;
if (MPI_UNWEIGHTED != weights) {
count *= 2; /* don't forget the weights */
temp = (int*)malloc(count*sizeof(int)); /* Allocate an array big enough to hold the edges and their weights */
if( NULL == temp ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
}
for( left_over = count, current_pos = i = 0; left_over > 0; i++ ) {
MCA_PML_CALL(recv( &temp[count - left_over], left_over, (ompi_datatype_t*)&ompi_mpi_int, /* keep receiving in the same buffer */
MPI_ANY_SOURCE, MCA_TOPO_BASE_TAG_DIST_EDGE_IN,
comm, &status ));
how_much = status._ucount / int_size;
if (MPI_UNWEIGHTED != weights) {
for( j = 0; j < ((int)how_much >> 1); j++, current_pos++ ) {
topo->in[current_pos] = temp[2 * j + 0 + (count - left_over)];
topo->inw[current_pos] = temp[2 * j + 1 + (count - left_over)];
}
}
left_over -= how_much;
}
if (MPI_UNWEIGHTED != weights) {
free(temp);
}
/**
* Now let's receive the output edges in a temporary array
* and then move them to their corresponding place.
*/
count = topo->outdegree;
temp = topo->out;
if (MPI_UNWEIGHTED != weights) {
count *= 2; /* don't forget the weights */
temp = (int*)malloc(count*sizeof(int)); /* Allocate an array big enough to hold the edges and their weights */
if( NULL == temp ) {
err = OMPI_ERR_OUT_OF_RESOURCE;
goto bail_out;
}
}
for( left_over = count, current_pos = i = 0; left_over > 0; i++ ) {
MCA_PML_CALL(recv( &temp[count - left_over], left_over, (ompi_datatype_t*)&ompi_mpi_int, /* keep receiving in the same buffer */
MPI_ANY_SOURCE, MCA_TOPO_BASE_TAG_DIST_EDGE_OUT,
comm, &status ));
how_much = status._ucount / int_size;
if (MPI_UNWEIGHTED != weights) {
for( j = 0; j < ((int)how_much >> 1); j++, current_pos++ ) {
topo->out[current_pos] = temp[2 * j + 0 + (count - left_over)];
topo->outw[current_pos] = temp[2 * j + 1 + (count - left_over)];
}
}
left_over -= how_much;
}
if (MPI_UNWEIGHTED != weights) {
free(temp);
}
err = ompi_request_wait_all(pending_reqs, reqs, MPI_STATUSES_IGNORE);
*ptopo = topo;
topo = NULL; /* don't free it below */
bail_out:
if( NULL != reqs ) {
free(reqs);
}
if( NULL != rin ) {
free(rin);
}
if( NULL != cnt ) {
free(cnt);
}
if( NULL != topo ) {
if ( NULL != topo->in ) {
free(topo->in);
}
if ( NULL != topo->out ) {
free(topo->out);
}
if ( NULL != topo->inw ) {
free(topo->inw);
}
if ( NULL != topo->outw ) {
free(topo->outw);
}
free(topo);
}
return err;
}
int mca_topo_base_dist_graph_create(mca_topo_base_module_t* module,
ompi_communicator_t *comm_old,
int n, int nodes[],
int degrees[], int targets[],
int weights[],
ompi_info_t *info, int reorder,
ompi_communicator_t **newcomm)
{
int err;
if( OMPI_SUCCESS != (err = ompi_comm_create(comm_old,
comm_old->c_local_group,
newcomm)) ) {
OBJ_RELEASE(module);
return err;
}
assert(NULL == (*newcomm)->c_topo);
(*newcomm)->c_topo = module;
(*newcomm)->c_topo->reorder = reorder;
(*newcomm)->c_flags |= OMPI_COMM_DIST_GRAPH;
err = mca_topo_base_dist_graph_distribute(module,
*newcomm,
n, nodes,
degrees, targets,
weights,
&((*newcomm)->c_topo->mtc.dist_graph));
if( OMPI_SUCCESS != err ) {
ompi_comm_free(newcomm);
}
return err;
}

Просмотреть файл

@ -0,0 +1,97 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2011-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011-2012 INRIA. All rights reserved.
* Copyright (c) 2011-2012 Université Bordeaux 1
*/
#include "ompi_config.h"
#include "ompi/communicator/communicator.h"
#include "ompi/info/info.h"
#include "ompi/mca/topo/base/base.h"
int mca_topo_base_dist_graph_create_adjacent(mca_topo_base_module_t* module,
ompi_communicator_t *comm_old,
int indegree, int sources[],
int sourceweights[],
int outdegree,
int destinations[],
int destweights[],
ompi_info_t *info, int reorder,
ompi_communicator_t **newcomm)
{
mca_topo_base_comm_dist_graph_2_1_0_t *topo = NULL;
int err;
if( OMPI_SUCCESS != (err = ompi_comm_create(comm_old,
comm_old->c_local_group,
newcomm)) ) {
return err;
}
err = OMPI_ERR_OUT_OF_RESOURCE; /* suppose by default something bad will happens */
assert( NULL == (*newcomm)->c_topo );
topo = (mca_topo_base_comm_dist_graph_2_1_0_t*)malloc(sizeof(mca_topo_base_comm_dist_graph_2_1_0_t));
if( NULL == topo ) {
goto bail_out;
}
topo->in = topo->inw = NULL;
topo->out = topo->outw = NULL;
topo->indegree = indegree;
topo->outdegree = outdegree;
topo->weighted = !((MPI_UNWEIGHTED == sourceweights) && (MPI_UNWEIGHTED == destweights));
topo->in = (int*)malloc(sizeof(int) * topo->indegree);
if( NULL == topo->in ) {
goto bail_out;
}
memcpy( topo->in, sources, sizeof(int) * topo->indegree );
if( MPI_UNWEIGHTED != sourceweights ) {
topo->inw = (int*)malloc(sizeof(int) * topo->indegree);
if( NULL == topo->inw ) {
goto bail_out;
}
memcpy( topo->inw, sourceweights, sizeof(int) * topo->indegree );
}
topo->out = (int*)malloc(sizeof(int) * topo->outdegree);
if( NULL == topo->out ) {
goto bail_out;
}
memcpy( topo->out, destinations, sizeof(int) * topo->outdegree );
topo->outw = NULL;
if( MPI_UNWEIGHTED != destweights ) {
topo->outw = (int*)malloc(sizeof(int) * topo->outdegree);
if( NULL == topo->outw ) {
goto bail_out;
}
memcpy( topo->outw, destweights, sizeof(int) * topo->outdegree );
}
(*newcomm)->c_topo = module;
(*newcomm)->c_topo->mtc.dist_graph = topo;
(*newcomm)->c_topo->reorder = reorder;
(*newcomm)->c_flags |= OMPI_COMM_DIST_GRAPH;
return OMPI_SUCCESS;
bail_out:
if( NULL != topo->in ) free(topo->in);
if( MPI_UNWEIGHTED != sourceweights ) {
if( NULL != topo->inw ) free(topo->inw);
}
if( NULL != topo->out ) free(topo->out);
if( MPI_UNWEIGHTED != destweights ) {
if( NULL != topo->outw ) free(topo->outw);
}
if( NULL != topo ) {
free(topo);
}
ompi_comm_free(newcomm);
return err;
}

Просмотреть файл

@ -0,0 +1,49 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2011-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011-2012 INRIA. All rights reserved.
* Copyright (c) 2011-2012 Universite Bordeaux 1
*/
#include "ompi_config.h"
#include "ompi/communicator/communicator.h"
#include "ompi/info/info.h"
#include "ompi/mca/topo/base/base.h"
int mca_topo_base_dist_graph_neighbors(ompi_communicator_t *comm,
int maxindegree,
int sources[], int sourceweights[],
int maxoutdegree,
int destinations[], int destweights[])
{
mca_topo_base_comm_dist_graph_2_1_0_t *dg = comm->c_topo->mtc.dist_graph;
int i;
if (!OMPI_COMM_IS_DIST_GRAPH(comm)) {
return OMPI_ERR_NOT_FOUND;
} else if (maxindegree > dg->indegree || maxoutdegree > dg->outdegree) {
return OMPI_ERR_BAD_PARAM;
}
for (i = 0; (i < dg->indegree) && (i < maxindegree); ++i) {
sources[i] = dg->in[i];
if (NULL != dg->inw) {
sourceweights[i] = dg->inw[i];
}
}
for (i = 0; (i < dg->outdegree) && (i < maxoutdegree); ++i) {
destinations[i] = dg->out[i];
if (NULL != dg->outw) {
destweights[i] = dg->outw[i];
}
}
return MPI_SUCCESS;
}

Просмотреть файл

@ -0,0 +1,30 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
*/
#include "ompi_config.h"
#include "ompi/communicator/communicator.h"
#include "ompi/info/info.h"
#include "ompi/mca/topo/base/base.h"
int mca_topo_base_dist_graph_neighbors_count(ompi_communicator_t *comm,
int *inneighbors,
int *outneighbors, int *weighted)
{
mca_topo_base_comm_dist_graph_2_1_0_t* dist_graph = comm->c_topo->mtc.dist_graph;
if (!OMPI_COMM_IS_DIST_GRAPH(comm)) {
return OMPI_ERR_NOT_FOUND;
}
*inneighbors = dist_graph->indegree;
*outneighbors = dist_graph->outdegree;
*weighted = (int)dist_graph->weighted;
return MPI_SUCCESS;
}

Просмотреть файл

@ -34,7 +34,7 @@ static int init_query(const mca_base_component_t *m,
mca_base_component_list_item_t *entry,
bool enable_progress_threads,
bool enable_mpi_threads);
static int init_query_2_0_0(const mca_base_component_t *component,
static int init_query_2_1_0(const mca_base_component_t *component,
mca_base_component_list_item_t *entry,
bool enable_progress_threads,
bool enable_mpi_threads);
@ -76,8 +76,8 @@ int mca_topo_base_find_available(bool enable_progress_threads,
return OMPI_ERROR;
}
/* All done */
return OMPI_SUCCESS;
/* All done */
return OMPI_SUCCESS;
}
@ -92,11 +92,14 @@ static int init_query(const mca_base_component_t *m,
"topo:find_available: querying topo component %s",
m->mca_component_name);
/* This component has been successfully opened, now try to query it */
/* This component has been successfully opened, now try to query
it and see if it wants to run in this job. Nothing interesting
happened in the topo framework before v2.1.0, so don't bother
supporting anything before then. */
if (2 == m->mca_type_major_version &&
0 == m->mca_type_minor_version &&
1 == m->mca_type_minor_version &&
0 == m->mca_type_release_version) {
ret = init_query_2_0_0(m, entry, enable_progress_threads,
ret = init_query_2_1_0(m, entry, enable_progress_threads,
enable_mpi_threads);
} else {
/* unrecognised API version */
@ -122,18 +125,20 @@ static int init_query(const mca_base_component_t *m,
m->mca_component_name);
}
/* All done */
return ret;
}
static int init_query_2_0_0(const mca_base_component_t *component,
static int init_query_2_1_0(const mca_base_component_t *component,
mca_base_component_list_item_t *entry,
bool enable_progress_threads,
bool enable_mpi_threads)
{
mca_topo_base_component_2_0_0_t *topo = (mca_topo_base_component_2_0_0_t *) component;
mca_topo_base_component_2_1_0_t *topo =
(mca_topo_base_component_2_1_0_t *) component;
return topo->topom_init_query(enable_progress_threads,
return topo->topoc_init_query(enable_progress_threads,
enable_mpi_threads);
}

Просмотреть файл

@ -37,12 +37,8 @@
*/
#include "ompi/mca/topo/base/static-components.h"
/*
* Global variables
*/
mca_topo_base_component_t mca_topo_base_selected_component;
mca_topo_base_module_t mca_topo;
OBJ_CLASS_INSTANCE(mca_topo_base_module_t, opal_object_t,
NULL, NULL);
static int mca_topo_base_close(void)
{

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -36,50 +36,101 @@
* @retval MPI_ERR_OUT_OF_RESOURCE
*/
int mca_topo_base_graph_create (mca_topo_base_comm_t *topo_data,
int *proc_count,
ompi_proc_t **proc_pointers,
int *new_rank,
int nnodes,
int *index,
int *edges,
bool reorder)
int mca_topo_base_graph_create(mca_topo_base_module_t *topo,
ompi_communicator_t* old_comm,
int nnodes,
int *index,
int *edges,
bool reorder,
ompi_communicator_t** comm_topo)
{
int nedges;
int i;
int *p;
ompi_communicator_t *new_comm;
int new_rank, num_procs, ret, i;
ompi_proc_t **topo_procs = NULL;
mca_topo_base_comm_graph_2_1_0_t* graph;
/* check if the number of nodes is more than the number of procs */
num_procs = old_comm->c_local_group->grp_proc_count;
new_rank = old_comm->c_local_group->grp_my_rank;
assert(topo->type == OMPI_COMM_GRAPH);
if (nnodes > *proc_count) {
if( num_procs < nnodes ) {
return MPI_ERR_DIMS;
}
if( num_procs > nnodes ) {
num_procs = nnodes;
}
if( new_rank > (nnodes - 1) ) {
new_rank = MPI_UNDEFINED;
num_procs = 0;
nnodes = 0;
}
/* Create and error check the topology information */
graph = (mca_topo_base_comm_graph_2_1_0_t*)malloc(sizeof(mca_topo_base_comm_graph_2_1_0_t));
if( NULL == graph ) {
return OMPI_ERR_OUT_OF_RESOURCE;
}
graph->nnodes = nnodes;
graph->index = NULL;
graph->edges = NULL;
nedges = topo_data->mtc_dims_or_index[nnodes-1];
graph->index = (int*)malloc(sizeof(int) * nnodes);
if (NULL == graph->index) {
free(graph);
return OMPI_ERR_OUT_OF_RESOURCE;
}
memcpy(graph->index, index, nnodes * sizeof(int));
/* Check if there are any negative values on the edges */
/* Graph communicator; copy the right data to the common information */
graph->edges = (int*)malloc(sizeof(int) * index[nnodes-1]);
if (NULL == graph->edges) {
free(graph->index);
free(graph);
return OMPI_ERR_OUT_OF_RESOURCE;
}
memcpy(graph->edges, edges, index[nnodes-1] * sizeof(int));
topo_procs = (ompi_proc_t**)malloc(num_procs * sizeof(ompi_proc_t *));
if(OMPI_GROUP_IS_DENSE(old_comm->c_local_group)) {
memcpy(topo_procs,
old_comm->c_local_group->grp_proc_pointers,
num_procs * sizeof(ompi_proc_t *));
} else {
for(i = 0 ; i < num_procs; i++) {
topo_procs[i] = ompi_group_peer_lookup(old_comm->c_local_group,i);
}
}
/* allocate a new communicator */
new_comm = ompi_comm_allocate(nnodes, 0);
if (NULL == new_comm) {
free(topo_procs);
free(graph->edges);
free(graph->index);
free(graph);
return OMPI_ERR_OUT_OF_RESOURCE;
}
ret = ompi_comm_enable(old_comm, new_comm,
new_rank, num_procs, topo_procs);
if (OMPI_SUCCESS != ret) {
free(topo_procs);
free(graph->edges);
free(graph->index);
free(graph);
ompi_comm_free (&new_comm);
return ret;
}
p = topo_data->mtc_periods_or_edges;
new_comm->c_topo = topo;
new_comm->c_topo->mtc.graph = graph;
new_comm->c_flags |= OMPI_COMM_GRAPH;
new_comm->c_topo->reorder = reorder;
*comm_topo = new_comm;
for (i = 0; i < nedges; ++i, ++p) {
if (*p < 0 || *p >= nnodes) {
return MPI_ERR_TOPOLOGY;
}
if( MPI_UNDEFINED == new_rank ) {
ompi_comm_free(&new_comm);
*comm_topo = MPI_COMM_NULL;
}
/* if the graph does not have to be trimmed, then nothing has to change */
if (nnodes < *proc_count) {
*proc_count = nnodes;
}
/* check if this rank makes the cut. if it does not return -1 */
if (*new_rank > (nnodes-1)) {
/* sorry but in our scheme, you are out */
*new_rank = MPI_UNDEFINED;
return MPI_SUCCESS;
}
return(MPI_SUCCESS);
return OMPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -33,27 +33,27 @@
* @retval MPI_SUCCESS
*/
int mca_topo_base_graph_get (ompi_communicator_t* comm,
int maxindex,
int maxedges,
int *index,
int *edges){
int i;
int *p;
int mca_topo_base_graph_get(ompi_communicator_t* comm,
int maxindex,
int maxedges,
int *index,
int *edges)
{
int i, *p;
int nprocs = ompi_comm_size(comm);
/*
* Fill the nodes and edges arrays.
*/
p = comm->c_topo_comm->mtc_dims_or_index;
p = comm->c_topo->mtc.graph->index;
for (i = 0; (i < nprocs) && (i < maxindex); ++i, ++p) {
*index++ = *p;
}
p = comm->c_topo_comm->mtc_periods_or_edges;
p = comm->c_topo->mtc.graph->edges;
for (i = 0;
(i < comm->c_topo_comm->mtc_dims_or_index[nprocs-1]) && (i < maxedges);
(i < comm->c_topo->mtc.graph->index[nprocs-1]) && (i < maxedges);
++i, ++p) {
*edges++ = *p;

Просмотреть файл

@ -14,15 +14,14 @@
* Additional copyrights may follow
*
* $HEADER$
*/
*/
#include "ompi_config.h"
#include "ompi/mca/topo/unity/topo_unity.h"
#include "ompi/mca/topo/base/base.h"
#include "ompi/communicator/communicator.h"
/*
* function - mca_topo_unity_graph_map
* function - mca_topo_base_graph_map
*
* @param comm input communicator (handle)
* @param nnodes number of graph nodes (integer)
@ -34,19 +33,17 @@
*
* @retval MPI_SUCCESS
* @retval MPI_UNDEFINED
*/
*/
int mca_topo_unity_graph_map (ompi_communicator_t* comm,
int nnodes,
int *index,
int *edges,
int *newrank)
int mca_topo_base_graph_map(ompi_communicator_t * comm,
int nnodes,
int *index, int *edges, int *newrank)
{
int myrank;
myrank = ompi_comm_rank(comm);
*newrank =
*newrank =
((0 > myrank) || (myrank >= nnodes)) ? MPI_UNDEFINED : myrank;
return OMPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -34,28 +34,28 @@
*/
int mca_topo_base_graph_neighbors (ompi_communicator_t* comm,
int rank,
int maxneighbors,
int *neighbors){
int nnbrs;
int i;
int *p;
int rank,
int maxneighbors,
int *neighbors)
{
mca_topo_base_comm_graph_2_1_0_t* graph = comm->c_topo->mtc.graph;
int nnbrs, i, *p;
/*
* Fill the neighbours.
*/
nnbrs = comm->c_topo_comm->mtc_dims_or_index[rank];
p = comm->c_topo_comm->mtc_periods_or_edges;
nnbrs = graph->index[rank];
p = graph->edges;
if (rank > 0) {
i = comm->c_topo_comm->mtc_dims_or_index[rank - 1];
if (rank > 0) {
i = graph->index[rank - 1];
nnbrs -= i;
p += i;
}
}
for (i = 0; (i < maxneighbors) && (i < nnbrs); ++i, ++p) {
for (i = 0; (i < maxneighbors) && (i < nnbrs); ++i, ++p) {
*neighbors++ = *p;
}
}
return MPI_SUCCESS;
return MPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -32,12 +32,13 @@
*/
int mca_topo_base_graph_neighbors_count (ompi_communicator_t* comm,
int rank,
int *nneighbors){
*nneighbors = comm->c_topo_comm->mtc_dims_or_index[rank];
if (rank > 0) {
*nneighbors -= comm->c_topo_comm->mtc_dims_or_index[rank - 1];
int rank,
int *nneighbors)
{
mca_topo_base_comm_graph_2_1_0_t* graph = comm->c_topo->mtc.graph;
*nneighbors = graph->index[rank];
if (rank > 0) {
*nneighbors -= graph->index[rank - 1];
}
return MPI_SUCCESS;

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -34,11 +34,12 @@
* @retval MPI_ERR_ARG
*/
int mca_topo_base_graphdims_get (ompi_communicator_t* comm,
int *nodes,
int *nedges){
int *nodes,
int *nedges)
{
mca_topo_base_comm_graph_2_1_0_t* graph = comm->c_topo->mtc.graph;
*nodes = ompi_comm_size(comm);
*nedges = comm->c_topo_comm->mtc_dims_or_index[*nodes -1];
*nedges = graph->index[*nodes -1];
return MPI_SUCCESS;
}

47
ompi/mca/topo/base/topo_base_lazy_init.c Обычный файл
Просмотреть файл

@ -0,0 +1,47 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#include "ompi_config.h"
#include <stdio.h>
#include "ompi/constants.h"
#include "ompi/mca/topo/base/base.h"
/* This function is invoked by the top-level MPI API functions to
lazily load the topo framework components (if it wasn't already --
it's safe to invoke this function multiple times). We do this
because most MPI apps don't use MPI topology functions, so we might
as well not load them unless we have to. */
int mca_topo_base_lazy_init(void)
{
int err;
if (0 == opal_list_get_size(&ompi_topo_base_framework.framework_components)) {
ompi_topo_base_framework.framework_open(MCA_BASE_OPEN_FIND_COMPONENTS);
if (OMPI_SUCCESS !=
(err = mca_topo_base_find_available(OMPI_ENABLE_PROGRESS_THREADS,
OMPI_ENABLE_THREAD_MULTIPLE))) {
return err;
}
}
return OMPI_SUCCESS;
}

Просмотреть файл

@ -26,146 +26,120 @@
#include "opal/mca/base/base.h"
#include "ompi/communicator/communicator.h"
/*
* ******************************************************************
* ********** Use in components that are of type topo v2.0.0 ********
* ******************************************************************
*/
#define MCA_TOPO_BASE_VERSION_2_0_0 \
MCA_BASE_VERSION_2_0_0, \
"topo", 2, 0, 0
/*
* ******************************************************************
* **************************** Macro ends **************************
* ******************************************************************
*/
/*
* These are the component function prototypes. These function pointers
* go into the component structure. These functions (query() and finalize()
* are called during topo_base_select(). Each component is query() ied
* and subsequently, all the unselected components are finalize() 'ed
* so that any *stuff* they did during query() can be undone. By
* similar logic, finalize() is also called on the component which
* was selected when the communicator is being destroyed.
*
* So, to sum it up, every component carries 4 functions:
* 1. open() - called during MPI_INIT
* 2. close() - called during MPI_FINALIZE
* 3. query() - called to select a particular component
* 4. finalize() - called when actions taken during query have
* to be undone
*/
/*
* **************** component struct *******************************
* *********** These functions go in the component struct **********
* **************** component struct *******************************
*/
typedef int (*mca_topo_base_component_init_query_1_0_0_fn_t)
(bool enable_progress_threads,
bool enable_mpi_threads);
typedef struct mca_topo_base_module_1_0_0_t*
(*mca_topo_base_component_comm_query_1_0_0_fn_t) (int *priority);
typedef int (*mca_topo_base_component_comm_unquery_1_0_0_fn_t)
(struct ompi_communicator_t *comm);
/*
* ****************** component struct ******************************
* Structure for topo v2.0.0 components.This is chained to MCA v2.0.0
* ****************** component struct ******************************
*/
struct mca_topo_base_component_2_0_0_t {
mca_base_component_t topom_version;
mca_base_component_data_t topom_data;
mca_topo_base_component_init_query_1_0_0_fn_t topom_init_query;
mca_topo_base_component_comm_query_1_0_0_fn_t topom_comm_query;
mca_topo_base_component_comm_unquery_1_0_0_fn_t topom_comm_unquery;
};
typedef struct mca_topo_base_component_2_0_0_t mca_topo_base_component_2_0_0_t;
typedef mca_topo_base_component_2_0_0_t mca_topo_base_component_t;
/*
* ******************************************************************
* *********************** component struct ends here ***************
* ******************************************************************
*/
/*
* ******************************************************************
* *********************** information structure *******************
* Note for component authors:
* If you find that this is not the most convinient form of
* representing your topology, then please feel free to define your
* own structure in which this struct is the first element. That way,
* type casting can be used to communicate between 2 different topo
* components. Note that this representation must be filled up no
* matter what the actual topo structure might be.
* ******************************************************************
*/
struct mca_topo_base_comm_1_0_0_t {
/* The first section represents data which is passed on to the
* structure by the user when creating the topology. This info
* is cached on so that if required another component can create the
* topology again when comm_dup fails to pick the same component */
int mtc_ndims_or_nnodes; /**< Number of cart dimensions or graph nodes */
int *mtc_dims_or_index; /**< Cart dimensions or graph indices */
int *mtc_periods_or_edges; /**< whether this was a periodic cart or graph */
bool mtc_reorder; /**< Whether the re-ordering is allowed */
/* The second section is used by the unity component since it does not
* hang its own structure off the communicator. Any component which wishes
* to use the base/topo_base* functions to fill in their unimplemented
* functions should and must fill this portion up */
int *mtc_coords; /**< Cart coordinates */
};
typedef struct mca_topo_base_comm_1_0_0_t mca_topo_base_comm_1_0_0_t;
typedef mca_topo_base_comm_1_0_0_t mca_topo_base_comm_t;
/*
* ******************************************************************
* *********************** information structure ******************
* ******************************************************************
*/
/* Forward reference to ompi_proc_t */
struct ompi_proc_t;
typedef struct mca_topo_base_module_t mca_topo_base_module_t;
/*
* Initial component query, called during mca_topo_base_open.
*/
typedef int (*mca_topo_base_component_init_query_2_1_0_fn_t)
(bool enable_progress_threads,
bool enable_mpi_threads);
/*
* ***********************************************************************
* ************************ Interface function definitions **************
* These are the typedefs for the function pointers to various topology
* backend functions which will be used by the various topology components
* ***********************************************************************
* Communicator query, called during cart and graph communicator
* creation.
*/
typedef int (*mca_topo_base_module_init_1_0_0_fn_t)
(struct ompi_communicator_t *comm);
typedef int (*mca_topo_base_module_finalize_1_0_0_fn_t)
(struct ompi_communicator_t *comm);
typedef struct mca_topo_base_module_t*
(*mca_topo_base_component_comm_query_2_1_0_fn_t)
(const ompi_communicator_t *comm, int *priority, uint32_t type);
/*
* Structure for topo v2.1.0 components.This is chained to MCA v2.0.0
*/
typedef struct mca_topo_base_component_2_1_0_t {
mca_base_component_t topoc_version;
mca_base_component_data_t topoc_data;
mca_topo_base_component_init_query_2_1_0_fn_t topoc_init_query;
mca_topo_base_component_comm_query_2_1_0_fn_t topoc_comm_query;
} mca_topo_base_component_2_1_0_t;
typedef mca_topo_base_component_2_1_0_t mca_topo_base_component_t;
/*
* Struct for holding graph communicator information
*/
typedef struct mca_topo_base_comm_graph_2_1_0_t {
int nnodes;
int *index;
int *edges;
} mca_topo_base_comm_graph_2_1_0_t;
typedef mca_topo_base_comm_graph_2_1_0_t mca_topo_base_comm_graph_t;
/*
* Struct for holding cartesian communicator information
*/
typedef struct mca_topo_base_comm_cart_2_1_0_t {
int ndims;
int *dims;
int *periods;
int *coords;
} mca_topo_base_comm_cart_2_1_0_t;
typedef mca_topo_base_comm_cart_2_1_0_t mca_topo_base_comm_cart_t;
/*
* Struct for holding distributed graph information
*/
typedef struct mca_topo_base_comm_dist_graph_2_1_0_t {
int *in;
int *inw;
int *out;
int *outw;
int indegree, outdegree;
bool weighted;
} mca_topo_base_comm_dist_graph_2_1_0_t;
typedef mca_topo_base_comm_dist_graph_2_1_0_t mca_topo_base_comm_dist_graph_t;
/*
* This union must be declared (can't be anonymous in the struct where
* it is used) because we need to be able to resolve it and find field
* offsets in the ompi/debuggers/ stuff (i.e., so that debuggers can
* parse/understand the individual fields on communicators).
*/
typedef union mca_topo_base_comm_cgd_union_2_1_0_t {
mca_topo_base_comm_graph_2_1_0_t* graph;
mca_topo_base_comm_cart_2_1_0_t* cart;
mca_topo_base_comm_dist_graph_2_1_0_t* dist_graph;
} mca_topo_base_comm_cgd_union_2_1_0_t;
typedef mca_topo_base_comm_cgd_union_2_1_0_t mca_topo_base_comm_cgd_union_t;
/**
* The logic for creating communicators with attached topologies is
* the following. A new placeholder communicator is prepared before
* the *_create function is called, and is initialized with minimal
* information. As an example, this communicator is not safe neither
* for point-to-point nor collective messages, it is provided only
* as a placeholder. However, the original communicator where the
* topology function was called upon is provided as well, in order to have
* a valid medium for messaging. In return from the *_create functions,
* a new group of processes is expected one containing all processes in
* the local_group of the new communicator. Once this information
* returned the new communicator will be fully initialized and activated.
*/
/*
* Module function typedefs
*/
/* Back end for MPI_CART_COORDS */
typedef int (*mca_topo_base_module_cart_coords_fn_t)
(struct ompi_communicator_t *comm,
int rank,
int maxdims,
int *coords);
/* Back end for MPI_CART_CREATE */
typedef int (*mca_topo_base_module_cart_create_fn_t)
(mca_topo_base_comm_t *topo_data,
int *proc_count,
struct ompi_proc_t **proc_pointers,
int *new_rank,
int ndims,
int *dims,
int *periods,
bool redorder);
(mca_topo_base_module_t *topo_module,
ompi_communicator_t* old_comm,
int ndims,
int *dims,
int *periods,
bool reorder,
ompi_communicator_t** comm_topo);
/* Back end for MPI_CART_GET */
typedef int (*mca_topo_base_module_cart_get_fn_t)
(struct ompi_communicator_t *comm,
int maxdims,
@ -173,10 +147,12 @@ typedef int (*mca_topo_base_module_cart_get_fn_t)
int *periods,
int *coords);
/* Back end for MPI_CARTDIM_GET */
typedef int (*mca_topo_base_module_cartdim_get_fn_t)
(struct ompi_communicator_t *comm,
int *ndims);
/* Back end for MPI_CART_MAP */
typedef int (*mca_topo_base_module_cart_map_fn_t)
(struct ompi_communicator_t *comm,
int ndims,
@ -184,11 +160,13 @@ typedef int (*mca_topo_base_module_cart_map_fn_t)
int *periods,
int *newrank);
/* Back end for MPI_CART_RANK */
typedef int (*mca_topo_base_module_cart_rank_fn_t)
(struct ompi_communicator_t *comm,
int *coords,
int *rank);
/* Back end for MPI_CART_SHIFT */
typedef int (*mca_topo_base_module_cart_shift_fn_t)
(struct ompi_communicator_t *comm,
int direction,
@ -196,21 +174,23 @@ typedef int (*mca_topo_base_module_cart_shift_fn_t)
int *rank_source,
int *rank_dest);
/* Back end for MPI_CART_SUB */
typedef int (*mca_topo_base_module_cart_sub_fn_t)
(struct ompi_communicator_t *comm,
int *remain_dims,
struct ompi_communicator_t ** new_comm);
/* Back end for MPI_GRAPH_CREATE */
typedef int (*mca_topo_base_module_graph_create_fn_t)
(mca_topo_base_comm_t *topo_data,
int *proc_count,
struct ompi_proc_t **proc_pointers,
int *new_rank,
int nnodes,
int *index,
int *edges,
bool reorder);
(mca_topo_base_module_t *topo_module,
ompi_communicator_t* old_comm,
int nnodes,
int *index,
int *edges,
bool reorder,
ompi_communicator_t** new_comm);
/* Back end for MPI_GRAPH_GET */
typedef int (*mca_topo_base_module_graph_get_fn_t)
(struct ompi_communicator_t *comm,
int maxindex,
@ -218,6 +198,7 @@ typedef int (*mca_topo_base_module_graph_get_fn_t)
int *index,
int *edges);
/* Back end for MPI_GRAPH_MAP */
typedef int (*mca_topo_base_module_graph_map_fn_t)
(struct ompi_communicator_t *comm,
int nnodes,
@ -225,65 +206,127 @@ typedef int (*mca_topo_base_module_graph_map_fn_t)
int *edges,
int *newrank);
/* Back end for MPI_GRAPHDIMS_GET */
typedef int (*mca_topo_base_module_graphdims_get_fn_t)
(struct ompi_communicator_t *comm,
int *nnodes,
int *nnedges);
/* Back end for MPI_GRAPH_NEIGHBORS */
typedef int (*mca_topo_base_module_graph_neighbors_fn_t)
(struct ompi_communicator_t *comm,
int rank,
int maxneighbors,
int *neighbors);
/* Back end for MPI_GRAPH_NEIGHBORS_COUNT */
typedef int (*mca_topo_base_module_graph_neighbors_count_fn_t)
(struct ompi_communicator_t *comm,
int rank,
int *nneighbors);
/*
* ***********************************************************************
* ******************** Interface function definitions end **************
* ***********************************************************************
*/
/* Back end for MPI_DIST_GRAPH_CREATE */
typedef int (*mca_topo_base_module_dist_graph_create_fn_t)
(struct mca_topo_base_module_t* module,
struct ompi_communicator_t *old_comm,
int n, int nodes[],
int degrees[], int targets[], int weights[],
struct ompi_info_t *info, int reorder,
struct ompi_communicator_t **new_comm);
/*
* ***********************************************************************
* *************************** module structure *************************
* ***********************************************************************
*/
struct mca_topo_base_module_1_0_0_t {
/*
* Per-communicator initialization function. This is called only
* on the module which is selected. The finalize corresponding to
* this function is present on the component struct above
*/
mca_topo_base_module_init_1_0_0_fn_t topo_module_init;
mca_topo_base_module_finalize_1_0_0_fn_t topo_module_finalize;
/* Graph related functions */
mca_topo_base_module_cart_coords_fn_t topo_cart_coords;
mca_topo_base_module_cart_create_fn_t topo_cart_create;
mca_topo_base_module_cart_get_fn_t topo_cart_get;
mca_topo_base_module_cartdim_get_fn_t topo_cartdim_get;
mca_topo_base_module_cart_map_fn_t topo_cart_map;
mca_topo_base_module_cart_rank_fn_t topo_cart_rank;
mca_topo_base_module_cart_shift_fn_t topo_cart_shift;
mca_topo_base_module_cart_sub_fn_t topo_cart_sub;
mca_topo_base_module_graph_create_fn_t topo_graph_create;
mca_topo_base_module_graph_get_fn_t topo_graph_get;
mca_topo_base_module_graph_map_fn_t topo_graph_map;
mca_topo_base_module_graphdims_get_fn_t topo_graphdims_get;
mca_topo_base_module_graph_neighbors_fn_t topo_graph_neighbors;
mca_topo_base_module_graph_neighbors_count_fn_t topo_graph_neighbors_count;
};
typedef struct mca_topo_base_module_1_0_0_t mca_topo_base_module_1_0_0_t;
typedef mca_topo_base_module_1_0_0_t mca_topo_base_module_t;
/*
* ***********************************************************************
* ******************* component actions structure ends *****************
* ***********************************************************************
*/
/* Back end for MPI_DIST_GRAPH_CREATE_ADJACENT */
typedef int (*mca_topo_base_module_dist_graph_create_adjacent_fn_t)
(struct mca_topo_base_module_t* module,
ompi_communicator_t *comm_old,
int indegree, int sources[],
int sourceweights[],
int outdegree,
int destinations[],
int destweights[],
struct ompi_info_t *info, int reorder,
ompi_communicator_t **comm_dist_graph);
/* Back end for MPI_DIST_GRAPH_NEIGHBORS */
typedef int (*mca_topo_base_module_dist_graph_neighbors_fn_t)
(struct ompi_communicator_t *comm,
int maxindegree,
int sources[], int sourceweights[],
int maxoutdegree, int destinations[],
int destweights[]);
/* Back end for MPI_DIST_GRAPH_NEIGHBORS_COUNT */
typedef int (*mca_topo_base_module_dist_graph_neighbors_count_fn_t)
(struct ompi_communicator_t *comm,
int *inneighbors, int *outneighbors, int *weighted);
/*
* Topo module structure. If a given topo module needs to cache more
* information than what is contained in the mca_topo_base_module_t, it should
* create its own module struct that uses mca_topo_base_module_t as a super.
*
* A module only needs to define two vital functions: the create and the map (or
* equivalent). However, if no specialized functions are provided, they will be
* automatically replaced by their default version. They will return the answers
* based on the base information stored in the associated module extra data.
*/
typedef struct mca_topo_base_cart_module_2_1_0_t {
mca_topo_base_module_cart_coords_fn_t cart_coords;
mca_topo_base_module_cart_create_fn_t cart_create;
mca_topo_base_module_cart_get_fn_t cart_get;
mca_topo_base_module_cartdim_get_fn_t cartdim_get;
mca_topo_base_module_cart_map_fn_t cart_map;
mca_topo_base_module_cart_rank_fn_t cart_rank;
mca_topo_base_module_cart_shift_fn_t cart_shift;
mca_topo_base_module_cart_sub_fn_t cart_sub;
} mca_topo_base_cart_module_2_1_0_t;
typedef struct mca_topo_base_graph_module_2_1_0_t {
mca_topo_base_module_graph_create_fn_t graph_create;
mca_topo_base_module_graph_get_fn_t graph_get;
mca_topo_base_module_graph_map_fn_t graph_map;
mca_topo_base_module_graphdims_get_fn_t graphdims_get;
mca_topo_base_module_graph_neighbors_fn_t graph_neighbors;
mca_topo_base_module_graph_neighbors_count_fn_t graph_neighbors_count;
} mca_topo_base_graph_module_2_1_0_t;
typedef struct mca_topo_base_dist_graph_module_2_1_0_t {
mca_topo_base_module_dist_graph_create_fn_t dist_graph_create;
mca_topo_base_module_dist_graph_create_adjacent_fn_t dist_graph_create_adjacent;
mca_topo_base_module_dist_graph_neighbors_fn_t dist_graph_neighbors;
mca_topo_base_module_dist_graph_neighbors_count_fn_t dist_graph_neighbors_count;
} mca_topo_base_dist_graph_module_2_1_0_t;
struct mca_topo_base_module_t {
/* Make this structure be an object so that it has a constructor
and destructor. */
opal_object_t super;
uint32_t type; /* type of topology */
bool reorder; /* reordering was required */
mca_topo_base_component_t* topo_component; /* Component of this topo module */
/* Cart, graph or dist graph related functions */
union {
mca_topo_base_cart_module_2_1_0_t cart;
mca_topo_base_graph_module_2_1_0_t graph;
mca_topo_base_dist_graph_module_2_1_0_t dist_graph;
} topo;
/* This union caches the parameters passed when the communicator
was created. Look in comm->c_flags to figure out whether this
is a cartesian, graph, or dist graph communicator. */
mca_topo_base_comm_cgd_union_t mtc;
};
OMPI_DECLSPEC OBJ_CLASS_DECLARATION(mca_topo_base_module_t);
/*
* ******************************************************************
* ********** Use in components that are of type topo v2.1.0 ********
* ******************************************************************
*/
#define MCA_TOPO_BASE_VERSION_2_1_0 \
MCA_BASE_VERSION_2_0_0, \
"topo", 2, 1, 0
#endif /* MCA_TOPO_H */

Просмотреть файл

@ -1,51 +0,0 @@
#
# Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
# University Research and Technology
# Corporation. All rights reserved.
# Copyright (c) 2004-2005 The University of Tennessee and The University
# of Tennessee Research Foundation. All rights
# reserved.
# Copyright (c) 2004-2009 High Performance Computing Center Stuttgart,
# University of Stuttgart. All rights reserved.
# Copyright (c) 2004-2005 The Regents of the University of California.
# All rights reserved.
# Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
# $COPYRIGHT$
#
# Additional copyrights may follow
#
# $HEADER$
#
sources = \
topo_unity.h \
topo_unity_cart_map.c \
topo_unity_graph_map.c \
topo_unity.c \
topo_unity_component.c
# Make the output library in this directory, and name it either
# mca_<type>_<name>.la (for DSO builds) or libmca_<type>_<name>.la
# (for static builds).
if MCA_BUILD_ompi_topo_unity_DSO
lib =
lib_sources =
component = mca_topo_unity.la
component_sources = $(sources)
else
lib = libmca_topo_unity.la
lib_sources = $(sources)
component =
component_sources =
endif
mcacomponentdir = $(pkglibdir)
mcacomponent_LTLIBRARIES = $(component)
mca_topo_unity_la_SOURCES = $(component_sources)
mca_topo_unity_la_LDFLAGS = -module -avoid-version
noinst_LTLIBRARIES = $(lib)
libmca_topo_unity_la_SOURCES = $(lib_sources)
libmca_topo_unity_la_LDFLAGS = -module -avoid-version

Просмотреть файл

@ -1,110 +0,0 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Cisco Systems, Inc. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* These symbols are in a file by themselves to provide nice linker
* semantics. Since linkers generally pull in symbols by object fules,
* keeping these symbols as the only symbols in this file prevents
* utility programs such as "ompi_info" from having to import entire
* modules just to query their version and parameters
*/
#include "ompi_config.h"
#include <stdio.h>
#include "mpi.h"
#include "ompi/communicator/communicator.h"
#include "ompi/mca/topo/topo.h"
#include "ompi/mca/topo/base/base.h"
#include "ompi/mca/topo/unity/topo_unity.h"
/*
* *******************************************************************
* ************************ actions structure ************************
* *******************************************************************
*/
static mca_topo_base_module_1_0_0_t unity = {
mca_topo_unity_module_init, /* initalise after being selected */
mca_topo_unity_module_finalize, /* close a module on a communicator */
NULL, /* topo_cart_coords */
NULL, /* topo_cart_create */
NULL, /* topo_cart_get */
NULL, /* topo_cartdim_get */
mca_topo_unity_cart_map,
NULL, /* topo_cart_rank */
NULL, /* topo_cart_shift */
NULL, /* topo_cart_sub */
NULL, /* topo_graph_create */
NULL, /* topo_graph_get */
mca_topo_unity_graph_map,
NULL, /* topo_graphdims_get */
NULL, /* topo_graph_neighbors */
NULL /* topo_graph_neighbors_count */
};
/*
* *******************************************************************
* ************************* structure ends **************************
* *******************************************************************
*/
int mca_topo_unity_component_init_query(bool enable_progress_threads,
bool enable_mpi_threads)
{
/* Nothing to do */
return OMPI_SUCCESS;
}
struct mca_topo_base_module_1_0_0_t *
mca_topo_unity_component_comm_query (int *priority)
{
/* this is the lowest module on the totem pole */
*priority = 0;
/* the check as to whether this is an inter communicator
* or and intra communicator has to be done before reaching
* here. this is my solemn opinion. Therefore I am ignoring
* the checks here */
return &unity;
}
int mca_topo_unity_component_comm_unquery (struct ompi_communicator_t *comm)
{
/* This function might be needed for some purposes later. for now it
* does not have anything to do since there are no steps which need
* to be undone if this module is not selected */
return OMPI_SUCCESS;
}
int mca_topo_unity_module_init (struct ompi_communicator_t *comm)
{
/* Nothing to do -- the setup is done in communicator/comm.c
(setup the comm->c_topo_comm data) */
return OMPI_SUCCESS;
}
int mca_topo_unity_module_finalize (struct ompi_communicator_t *comm)
{
/* Nothing to do -- the teardown is done in
communicator/comm_init.c (free the comm->c_topo_comm data) */
return OMPI_SUCCESS;
}

Просмотреть файл

@ -1,82 +0,0 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef MCA_TOPO_UNTIY_H
#define MCA_TOPO_UNTIY_H
#include "ompi_config.h"
#include "ompi/mca/topo/topo.h"
/*
* ******************************************************************
* ******** functions which provide MCA interface comppliance *******
* ******************************************************************
* These functions are:
* - mca_topo_unity_module_open
* - mca_topo_unity_module_close
* - mca_topo_unity_module_query
* - mca_topo_unity_module_finalize
* These functions are always found on the mca_topo_unity_module
* structure. They are the "meta" functions to ensure smooth op.
* ******************************************************************
*/
BEGIN_C_DECLS
int mca_topo_unity_component_init_query(bool enable_progress_threads,
bool enable_mpi_threads);
struct mca_topo_base_module_1_0_0_t *
mca_topo_unity_component_comm_query (int *priority);
int mca_topo_unity_component_comm_unquery (struct ompi_communicator_t *comm);
int mca_topo_unity_module_init (struct ompi_communicator_t *comm);
int mca_topo_unity_module_finalize (struct ompi_communicator_t *comm);
OMPI_MODULE_DECLSPEC extern mca_topo_base_component_2_0_0_t mca_topo_unity_component;
/*
* ******************************************************************
* ********* functions which are implemented in this module *********
* ******************************************************************
* This module defines just 2 functions:
* - graph_map
* - cart_map
* rest of the functions are filled in from the "base" module. Authors
* of other such topology modules are required to define only these 2
* functions. They are ofcourse free to implement all of them too :-)
* ******************************************************************
*/
int mca_topo_unity_cart_map (struct ompi_communicator_t *comm,
int ndims,
int *dims,
int *periods,
int *newrank);
int mca_topo_unity_graph_map (struct ompi_communicator_t *comm,
int nnodes,
int *index,
int *edges,
int *newrank);
/*
* ******************************************************************
* ************ functions implemented in this module end ************
* ******************************************************************
*/
END_C_DECLS
#endif /* MCA_TOPO_UNITY_H */

Просмотреть файл

@ -1,65 +0,0 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* These symbols are in a file by themselves to provide nice linker
* semantics. Since linkers generally pull in symbols by object fules,
* keeping these symbols as the only symbols in this file prevents
* utility programs such as "ompi_info" from having to import entire
* modules just to query their version and parameters
*/
#include "ompi_config.h"
#include "ompi/mca/topo/unity/topo_unity.h"
/*
* Public string showing the topo unity module version number
*/
const char *mca_topo_unity_component_version_string =
"Open MPI unity topology MCA component version" OMPI_VERSION;
/*
* *******************************************************************
* ****** this is the structure that defines the component **************
* *******************************************************************
* this structure contains the component version information along with
* some meta data and function pointers which allow a component to
* interact with the MCA framework. component open() and close() are
* called during MPI_INIT and MPI_FINALIZE respectively and query()
* and finalize() are called during creation/destruction of a comm
* *******************************************************************
*/
mca_topo_base_component_2_0_0_t mca_topo_unity_component =
{
{
MCA_TOPO_BASE_VERSION_2_0_0,
"unity", /* component name */
OMPI_MAJOR_VERSION, /* major version */
OMPI_MINOR_VERSION, /* minor version */
OMPI_RELEASE_VERSION, /* release version */
NULL, /* fp to open the component */
NULL /* fp to close the component */
},
{
/* The component is checkpoint ready */
MCA_BASE_METADATA_PARAM_CHECKPOINT
},
mca_topo_unity_component_init_query, /* get thread level */
mca_topo_unity_component_comm_query, /* get priority and actions */
mca_topo_unity_component_comm_unquery /* undo what was done by previous function */
};

Просмотреть файл

@ -123,6 +123,10 @@ libmpi_c_mpi_la_SOURCES = \
comm_remote_group.c \
comm_remote_size.c \
comm_set_attr.c \
dist_graph_create.c \
dist_graph_create_adjacent.c \
dist_graph_neighbors.c \
dist_graph_neighbors_count.c \
comm_set_errhandler.c \
comm_set_name.c \
comm_size.c \

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -38,11 +38,9 @@
static const char FUNC_NAME[] = "MPI_Cart_coords";
int MPI_Cart_coords(MPI_Comm comm, int rank, int maxdims, int coords[])
{
int err;
mca_topo_base_module_cart_coords_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -59,10 +57,6 @@ int MPI_Cart_coords(MPI_Comm comm, int rank, int maxdims, int coords[])
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if ( (0 > maxdims) || ((0 < maxdims) && (NULL == coords))) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
@ -73,18 +67,14 @@ int MPI_Cart_coords(MPI_Comm comm, int rank, int maxdims, int coords[])
}
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer on this communicator */
func = comm->c_topo->topo_cart_coords;
/* call the function */
err = func(comm, rank, maxdims, coords);
err = comm->c_topo->topo.cart.cart_coords(comm, rank, maxdims, coords);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* all done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -40,10 +40,10 @@ static const char FUNC_NAME[] = "MPI_Cart_create";
int MPI_Cart_create(MPI_Comm old_comm, int ndims, int dims[],
int periods[], int reorder, MPI_Comm *comm_cart) {
int periods[], int reorder, MPI_Comm *comm_cart)
{
mca_topo_base_module_t* topo;
int err;
bool re_order = false;
MEMCHECKER(
memchecker_comm(old_comm);
@ -55,9 +55,8 @@ int MPI_Cart_create(MPI_Comm old_comm, int ndims, int dims[],
if (ompi_comm_invalid(old_comm)) {
return OMPI_ERRHANDLER_INVOKE (MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
}
if (OMPI_COMM_IS_INTER(old_comm)) {
return OMPI_ERRHANDLER_INVOKE (old_comm, MPI_ERR_COMM,
} else if (OMPI_COMM_IS_INTER(old_comm)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
}
if (ndims < 0) {
@ -71,14 +70,12 @@ int MPI_Cart_create(MPI_Comm old_comm, int ndims, int dims[],
/* check if the number of processes on the grid are correct */
{
int i;
int i, count_nodes = 1;
int *p = dims;
int count_nodes = 1;
int parent_procs = ompi_comm_size(old_comm);
for (i=0; i < ndims; i++) {
for (i=0; i < ndims; i++, p++) {
count_nodes *= *p;
p++;
}
if (parent_procs < count_nodes) {
@ -88,43 +85,29 @@ int MPI_Cart_create(MPI_Comm old_comm, int ndims, int dims[],
}
}
/*
* Now we have to check if the topo module exists or not. This has been
* removed from initialization since most of the MPI calls do not use
* this module
*/
if (OMPI_SUCCESS != (err = mca_base_framework_open(&ompi_topo_base_framework, 0))) {
return OMPI_ERRHANDLER_INVOKE(old_comm, err, FUNC_NAME);
}
if (OMPI_SUCCESS !=
(err = mca_topo_base_find_available(OMPI_ENABLE_PROGRESS_THREADS,
OMPI_ENABLE_THREAD_MULTIPLE))) {
return OMPI_ERRHANDLER_INVOKE(old_comm, err, FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* everything seems to be alright with the communicator, we can go
/*
* everything seems to be alright with the communicator, we can go
* ahead and select a topology module for this purpose and create
* the new cartesian communicator
* the new graph communicator
*/
if (OMPI_SUCCESS != (err = mca_topo_base_comm_select(old_comm,
NULL,
&topo,
OMPI_COMM_CART))) {
return err;
}
re_order = (0 == reorder)? false : true;
err = ompi_topo_create (old_comm,
ndims,
dims,
periods,
re_order,
comm_cart,
OMPI_COMM_CART);
/* Now let that topology module rearrange procs/ranks if it wants to */
err = topo->topo.cart.cart_create(topo, old_comm,
ndims, dims, periods,
(0 == reorder) ? false : true, comm_cart);
OPAL_CR_EXIT_LIBRARY();
/* check the error status */
if (MPI_SUCCESS != err) {
OBJ_RELEASE(topo);
return OMPI_ERRHANDLER_INVOKE(old_comm, err, FUNC_NAME);
}
/* All done */
return MPI_SUCCESS;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -37,12 +37,9 @@
static const char FUNC_NAME[] = "MPI_Cart_get";
int MPI_Cart_get(MPI_Comm comm, int maxdims, int dims[],
int periods[], int coords[])
{
/* local variables */
mca_topo_base_module_cart_get_fn_t func;
int err;
MEMCHECKER(
@ -56,10 +53,6 @@ int MPI_Cart_get(MPI_Comm comm, int maxdims, int dims[],
return OMPI_ERRHANDLER_INVOKE (MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if ((0 > maxdims) || (0 < maxdims &&
((NULL == dims) || (NULL == periods) ||
(NULL == coords)))) {
@ -68,18 +61,14 @@ int MPI_Cart_get(MPI_Comm comm, int maxdims, int dims[],
}
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer to do the right thing */
func = comm->c_topo->topo_cart_get;
/* all arguments are checked and now call the back end function */
err = func(comm, maxdims, dims, periods, coords);
err = comm->c_topo->topo.cart.cart_get(comm, maxdims, dims, periods, coords);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* All done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -42,8 +42,7 @@ static const char FUNC_NAME[] = "MPI_Cart_map";
int MPI_Cart_map(MPI_Comm comm, int ndims, int dims[],
int periods[], int *newrank)
{
int err;
mca_topo_base_module_cart_map_fn_t func;
int err = MPI_SUCCESS;
MEMCHECKER(
memchecker_comm(comm);
@ -73,19 +72,10 @@ int MPI_Cart_map(MPI_Comm comm, int ndims, int dims[],
it, we just return the "default" value suggested by MPI:
newrank = rank */
*newrank = ompi_comm_rank(comm);
}
else {
/* get the function pointer on this communicator */
func = comm->c_topo->topo_cart_map;
/* call the function */
err = func(comm, ndims, dims, periods, newrank);
if ( MPI_SUCCESS != err ) {
OPAL_CR_EXIT_LIBRARY();
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
} else {
err = comm->c_topo->topo.cart.cart_map(comm, ndims, dims, periods, newrank);
}
OPAL_CR_EXIT_LIBRARY();
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -38,11 +38,9 @@
static const char FUNC_NAME[] = "MPI_Cart_rank";
int MPI_Cart_rank(MPI_Comm comm, int coords[], int *rank)
{
int i, err;
mca_topo_base_module_cart_rank_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -50,6 +48,7 @@ int MPI_Cart_rank(MPI_Comm comm, int coords[], int *rank)
/* check the arguments */
if (MPI_PARAM_CHECK) {
mca_topo_base_comm_cart_2_1_0_t* cart;
OMPI_ERR_INIT_FINALIZE(FUNC_NAME);
if (ompi_comm_invalid(comm)) {
return OMPI_ERRHANDLER_INVOKE (MPI_COMM_WORLD, MPI_ERR_COMM,
@ -59,13 +58,12 @@ int MPI_Cart_rank(MPI_Comm comm, int coords[], int *rank)
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
cart = comm->c_topo->mtc.cart;
/* Per MPI-2.1, coords is only relevant if the dimension of
the cartesian comm is >0 */
if ((NULL == coords && comm->c_topo_comm->mtc_ndims_or_nnodes >= 1) ||
if (((NULL == coords) &&
(NULL != cart) &&
(cart->ndims >= 1)) ||
(NULL == rank)){
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
@ -73,26 +71,23 @@ int MPI_Cart_rank(MPI_Comm comm, int coords[], int *rank)
/* Check if coords[i] is within the acceptable range if
dimension i is not periodic */
for (i = 0; i < comm->c_topo_comm->mtc_ndims_or_nnodes; ++i) {
if (!comm->c_topo_comm->mtc_periods_or_edges[i] &&
for (i = 0; i < cart->ndims; ++i) {
if (!cart->periods[i] &&
(coords[i] < 0 ||
coords[i] >= comm->c_topo_comm->mtc_dims_or_index[i])) {
coords[i] >= cart->dims[i])) {
return OMPI_ERRHANDLER_INVOKE(comm, MPI_ERR_ARG, FUNC_NAME);
}
}
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer on this communicator */
func = comm->c_topo->topo_cart_rank;
/* call the function */
err = func(comm, coords, rank);
err = comm->c_topo->topo.cart.cart_rank(comm, coords, rank);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -41,7 +41,6 @@ int MPI_Cart_shift(MPI_Comm comm, int direction, int disp,
int *rank_source, int *rank_dest)
{
int err;
mca_topo_base_module_cart_shift_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -58,10 +57,6 @@ int MPI_Cart_shift(MPI_Comm comm, int direction, int disp,
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if (0 > direction) { /* yet to detect direction >= comm->c_topo_ndims */
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_DIMS,
FUNC_NAME);
@ -72,18 +67,15 @@ int MPI_Cart_shift(MPI_Comm comm, int direction, int disp,
}
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer on this communicator */
func = comm->c_topo->topo_cart_shift;
/* call the function */
err = func(comm, direction, disp, rank_source, rank_dest);
err = comm->c_topo->topo.cart.cart_shift(comm, direction, disp, rank_source, rank_dest);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* all done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,14 +2,14 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2007-2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, LLC. All rights
* reserved.
* $COPYRIGHT$
@ -42,7 +42,6 @@ static const char FUNC_NAME[] = "MPI_Cart_sub";
int MPI_Cart_sub(MPI_Comm comm, int remain_dims[], MPI_Comm *new_comm)
{
int err;
mca_topo_base_module_cart_sub_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -59,28 +58,20 @@ int MPI_Cart_sub(MPI_Comm comm, int remain_dims[], MPI_Comm *new_comm)
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if (NULL == remain_dims || NULL == new_comm) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
}
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer on this communicator */
func = comm->c_topo->topo_cart_sub;
/* call the function */
err = func(comm, remain_dims, new_comm);
err = comm->c_topo->topo.cart.cart_sub(comm, remain_dims, new_comm);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* all done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,13 +2,14 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -39,7 +40,6 @@ static const char FUNC_NAME[] = "MPI_Cartdim_get";
int MPI_Cartdim_get(MPI_Comm comm, int *ndims)
{
mca_topo_base_module_cartdim_get_fn_t func;
int err;
MEMCHECKER(
@ -56,27 +56,20 @@ int MPI_Cartdim_get(MPI_Comm comm, int *ndims)
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if (NULL == ndims) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
}
}
if (!OMPI_COMM_IS_CART(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer on this communicator */
func = comm->c_topo->topo_cartdim_get;
/* call the function */
err = func(comm, ndims);
err = comm->c_topo->topo.cart.cartdim_get(comm, ndims);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

86
ompi/mpi/c/dist_graph_create.c Обычный файл
Просмотреть файл

@ -0,0 +1,86 @@
/*
* Copyright (c) 2011-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
*
*/
#include "ompi_config.h"
#include "ompi/mpi/c/bindings.h"
#include "ompi/runtime/params.h"
#include "ompi/communicator/communicator.h"
#include "ompi/errhandler/errhandler.h"
#include "ompi/memchecker.h"
#include "ompi/mca/topo/topo.h"
#include "ompi/mca/topo/base/base.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILING_DEFINES
#pragma weak MPI_Dist_graph_create = PMPI_Dist_graph_create
#endif
#if OMPI_PROFILING_DEFINES
#include "ompi/mpi/c/profile/defines.h"
#endif
static const char FUNC_NAME[] = "MPI_Dist_graph_create";
int MPI_Dist_graph_create(MPI_Comm comm_old, int n, int sources[],
int degrees[], int destinations[], int weights[],
MPI_Info info, int reorder, MPI_Comm * newcomm)
{
mca_topo_base_module_t* topo;
int i, j, index, err, comm_size;
MEMCHECKER(
memchecker_comm(comm_old);
);
if (MPI_PARAM_CHECK) {
OMPI_ERR_INIT_FINALIZE(FUNC_NAME);
if (ompi_comm_invalid(comm_old)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
} else if (OMPI_COMM_IS_INTER(comm_old)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
} else if (n < 0 || NULL == newcomm) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG, FUNC_NAME);
} else if (n > 0 && (NULL == sources || NULL == degrees ||
NULL == destinations || NULL == weights)) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG, FUNC_NAME);
}
/* Ensure the arrays are full of valid-valued integers */
comm_size = ompi_comm_size(comm_old);
for( i = index = 0; i < n; ++i ) {
if (sources[i] < 0 || sources[i] >= comm_size) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
FUNC_NAME);
} else if (degrees[i] < 0) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
FUNC_NAME);
}
for( j = 0; j < degrees[i]; ++j ) {
if (destinations[index] < 0 || destinations[index] >= comm_size) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
FUNC_NAME);
} else if (MPI_UNWEIGHTED != weights && weights[index] < 0) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
FUNC_NAME);
}
index++;
}
}
}
/* Ensure there is a topo attached to this communicator */
if(OMPI_SUCCESS != (err = mca_topo_base_comm_select(comm_old, NULL,
&topo, OMPI_COMM_DIST_GRAPH))) {
return OMPI_ERRHANDLER_INVOKE(comm_old, err, FUNC_NAME);
}
err = topo->topo.dist_graph.dist_graph_create(topo, comm_old, n, sources, degrees,
destinations, weights, info,
reorder, newcomm);
OMPI_ERRHANDLER_RETURN(err, comm_old, err, FUNC_NAME);
}

97
ompi/mpi/c/dist_graph_create_adjacent.c Обычный файл
Просмотреть файл

@ -0,0 +1,97 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2011-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
*
* Author(s): Torsten Hoefler
*
*/
#include "ompi_config.h"
#include "ompi/mpi/c/bindings.h"
#include "ompi/runtime/params.h"
#include "ompi/communicator/communicator.h"
#include "ompi/errhandler/errhandler.h"
#include "ompi/memchecker.h"
#include "ompi/mca/topo/topo.h"
#include "ompi/mca/topo/base/base.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILING_DEFINES
#pragma weak MPI_Dist_graph_create_adjacent = PMPI_Dist_graph_create_adjacent
#endif
#if OMPI_PROFILING_DEFINES
#include "ompi/mpi/c/profile/defines.h"
#endif
static const char FUNC_NAME[] = "MPI_Dist_graph_create_adjacent";
int MPI_Dist_graph_create_adjacent(MPI_Comm comm_old,
int indegree, int sources[],
int sourceweights[], int outdegree,
int destinations[], int destweights[],
MPI_Info info, int reorder,
MPI_Comm *comm_dist_graph)
{
mca_topo_base_module_t* topo;
int i, comm_size, err;
MEMCHECKER(
memchecker_comm(comm_old);
);
if (MPI_PARAM_CHECK) {
OMPI_ERR_INIT_FINALIZE(FUNC_NAME);
if (ompi_comm_invalid(comm_old)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
} else if (OMPI_COMM_IS_INTER(comm_old)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
} else if (indegree < 0 || outdegree < 0 || NULL == comm_dist_graph) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG, "MPI_Dist_create_graph_adjacent 1");
} else if ((indegree > 0 &&
(NULL == sources || NULL == sourceweights)) ||
(outdegree > 0 &&
(NULL == destinations || NULL == destweights))) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG, "MPI_Dist_create_graph adjacent 2");
}
comm_size = ompi_comm_size(comm_old);
for (i = 0; i < indegree; ++i) {
if (sources[i] < 0 || sources[i] >= comm_size) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
FUNC_NAME);
} else if (MPI_UNWEIGHTED != sourceweights && sourceweights[i] < 0) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
"MPI_Dist_create_graph adjacent 3");
}
}
for (i = 0; i < outdegree; ++i) {
if (destinations[i] < 0 || destinations[i] >= comm_size) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
FUNC_NAME);
} else if (MPI_UNWEIGHTED != destweights && destweights[i] < 0) {
return OMPI_ERRHANDLER_INVOKE(comm_old, MPI_ERR_ARG,
"MPI_Dist_create_graph_adjacent 4\n");
}
}
}
/* Ensure there is a topo attached to this communicator */
if(OMPI_SUCCESS != (err = mca_topo_base_comm_select(comm_old, NULL,
&topo, OMPI_COMM_DIST_GRAPH))) {
return OMPI_ERRHANDLER_INVOKE(comm_old, err, FUNC_NAME);
}
err = topo->topo.dist_graph.dist_graph_create_adjacent(topo, comm_old, indegree,
sources, sourceweights, outdegree,
destinations, destweights, info,
reorder, comm_dist_graph);
OMPI_ERRHANDLER_RETURN(err, comm_old, err, FUNC_NAME);
}

69
ompi/mpi/c/dist_graph_neighbors.c Обычный файл
Просмотреть файл

@ -0,0 +1,69 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2011-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
*
* Author(s): Torsten Hoefler
*
*/
#include "ompi_config.h"
#include "ompi/mpi/c/bindings.h"
#include "ompi/runtime/params.h"
#include "ompi/communicator/communicator.h"
#include "ompi/errhandler/errhandler.h"
#include "ompi/memchecker.h"
#include "ompi/mca/topo/topo.h"
#include "ompi/mca/topo/base/base.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILING_DEFINES
#pragma weak MPI_Dist_graph_neighbors = PMPI_Dist_graph_neighbors
#endif
#if OMPI_PROFILING_DEFINES
#include "ompi/mpi/c/profile/defines.h"
#endif
static const char FUNC_NAME[] = "MPI_Dist_graph_neighbors";
int MPI_Dist_graph_neighbors(MPI_Comm comm, int maxindegree,
int sources[], int sourceweights[],
int maxoutdegree, int destinations[],
int destweights[])
{
int err;
MEMCHECKER(
memchecker_comm(comm);
);
if (MPI_PARAM_CHECK) {
OMPI_ERR_INIT_FINALIZE(FUNC_NAME);
if (ompi_comm_invalid(comm)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
} else if (maxindegree < 0 || maxoutdegree < 0 ||
(maxindegree > 0 &&
(NULL == sources || NULL == sourceweights)) ||
(maxoutdegree > 0 &&
(NULL == destinations || NULL == destweights))) {
return OMPI_ERRHANDLER_INVOKE(comm, MPI_ERR_ARG, FUNC_NAME);
}
}
if (!OMPI_COMM_IS_DIST_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
err = comm->c_topo->topo.dist_graph.dist_graph_neighbors(comm, maxindegree,
sources, sourceweights, maxoutdegree,
destinations, destweights);
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

64
ompi/mpi/c/dist_graph_neighbors_count.c Обычный файл
Просмотреть файл

@ -0,0 +1,64 @@
/*
* Copyright (c) 2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2011-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
*
* Author(s): Torsten Hoefler
*
*/
#include <assert.h>
#include <stdlib.h>
#include "ompi_config.h"
#include "ompi/mpi/c/bindings.h"
#include "ompi/runtime/params.h"
#include "ompi/communicator/communicator.h"
#include "ompi/errhandler/errhandler.h"
#include "ompi/memchecker.h"
#include "ompi/mca/topo/topo.h"
#include "ompi/mca/topo/base/base.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILING_DEFINES
#pragma weak MPI_Dist_graph_neighbors_count = PMPI_Dist_graph_neighbors_count
#endif
#if OMPI_PROFILING_DEFINES
#include "ompi/mpi/c/profile/defines.h"
#endif
static const char FUNC_NAME[] = "MPI_Dist_graph_neighbors_count";
int MPI_Dist_graph_neighbors_count(MPI_Comm comm, int *inneighbors,
int *outneighbors, int *weighted)
{
int err;
MEMCHECKER(
memchecker_comm(comm);
);
if (MPI_PARAM_CHECK) {
OMPI_ERR_INIT_FINALIZE(FUNC_NAME);
if (ompi_comm_invalid(comm)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
} else if (NULL == inneighbors || NULL == outneighbors ||
NULL == weighted) {
return OMPI_ERRHANDLER_INVOKE(comm, MPI_ERR_ARG, FUNC_NAME);
}
}
if (!OMPI_COMM_IS_DIST_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
err = comm->c_topo->topo.dist_graph.dist_graph_neighbors_count(comm, inneighbors,
outneighbors, weighted);
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -42,9 +42,8 @@ static const char FUNC_NAME[] = "MPI_Graph_create";
int MPI_Graph_create(MPI_Comm old_comm, int nnodes, int indx[],
int edges[], int reorder, MPI_Comm *comm_graph)
{
mca_topo_base_module_t* topo;
int err;
bool re_order = false;
MEMCHECKER(
memchecker_comm(old_comm);
@ -56,10 +55,9 @@ int MPI_Graph_create(MPI_Comm old_comm, int nnodes, int indx[],
if (ompi_comm_invalid(old_comm)) {
return OMPI_ERRHANDLER_INVOKE (MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
}
if (OMPI_COMM_IS_INTER(old_comm)) {
return OMPI_ERRHANDLER_INVOKE (old_comm, MPI_ERR_COMM,
FUNC_NAME);
} else if (OMPI_COMM_IS_INTER(old_comm)) {
return OMPI_ERRHANDLER_INVOKE(MPI_COMM_WORLD, MPI_ERR_COMM,
FUNC_NAME);
}
if (nnodes < 0) {
return OMPI_ERRHANDLER_INVOKE (old_comm, MPI_ERR_ARG,
@ -81,42 +79,32 @@ int MPI_Graph_create(MPI_Comm old_comm, int nnodes, int indx[],
*comm_graph = MPI_COMM_NULL;
return MPI_SUCCESS;
}
/*
* Now we have to check if the topo module exists or not. This has been
* removed from initialization since most of the MPI calls do not use
* this module
*/
if (OMPI_SUCCESS != (err = mca_base_framework_open(&ompi_topo_base_framework, 0))) {
return OMPI_ERRHANDLER_INVOKE(old_comm, err, FUNC_NAME);
}
if (OMPI_SUCCESS !=
(err = mca_topo_base_find_available(OMPI_ENABLE_PROGRESS_THREADS,
OMPI_ENABLE_THREAD_MULTIPLE))) {
return OMPI_ERRHANDLER_INVOKE(old_comm, err, FUNC_NAME);
if( nnodes > old_comm->c_local_group->grp_proc_count ) {
return OMPI_ERRHANDLER_INVOKE (old_comm, MPI_ERR_ARG,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/*
* everything seems to be alright with the communicator, we can go
* ahead and select a topology module for this purpose and create
* the new graph communicator
*/
if (OMPI_SUCCESS != (err = mca_topo_base_comm_select(old_comm,
NULL,
&topo,
OMPI_COMM_GRAPH))) {
return err;
}
re_order = (0 == reorder) ? false : true;
err = ompi_topo_create ((struct ompi_communicator_t *)old_comm,
nnodes,
indx,
edges,
re_order,
(struct ompi_communicator_t **)comm_graph,
OMPI_COMM_GRAPH);
/* Now let that topology module rearrange procs/ranks if it wants to */
err = topo->topo.graph.graph_create(topo, old_comm,
nnodes, indx, edges,
(0 == reorder) ? false : true, comm_graph);
OPAL_CR_EXIT_LIBRARY();
/* check the error status */
if (MPI_SUCCESS != err) {
OBJ_RELEASE(topo);
return OMPI_ERRHANDLER_INVOKE(old_comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -42,7 +42,6 @@ int MPI_Graph_get(MPI_Comm comm, int maxindx, int maxedges,
int indx[], int edges[])
{
int err;
mca_topo_base_module_graph_get_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -58,28 +57,21 @@ int MPI_Graph_get(MPI_Comm comm, int maxindx, int maxedges,
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if (0 > maxindx || 0 > maxedges || NULL == indx || NULL == edges) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
}
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer to do the right thing */
func = comm->c_topo->topo_graph_get;
/* call the function */
err = func(comm, maxindx, maxedges, indx, edges);
err = comm->c_topo->topo.graph.graph_get(comm, maxindx, maxedges, indx, edges);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* All done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -42,8 +42,7 @@ static const char FUNC_NAME[] = "MPI_Graph_map";
int MPI_Graph_map(MPI_Comm comm, int nnodes, int indx[], int edges[],
int *newrank)
{
int err;
mca_topo_base_module_graph_map_fn_t func;
int err = MPI_SUCCESS;
MEMCHECKER(
memchecker_comm(comm);
@ -73,20 +72,10 @@ int MPI_Graph_map(MPI_Comm comm, int nnodes, int indx[], int edges[],
it, we just return the "default" value suggested by MPI:
newrank = rank */
*newrank = ompi_comm_rank(comm);
} else {
err = comm->c_topo->topo.graph.graph_map(comm, nnodes, indx, edges, newrank);
}
else {
/* map the function pointer to do the right thing */
func = comm->c_topo->topo_graph_map;
/* call the function */
if ( MPI_SUCCESS !=
(err = func(comm, nnodes, indx, edges, newrank))) {
OPAL_CR_EXIT_LIBRARY();
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
}
/* All done */
OPAL_CR_EXIT_LIBRARY();
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -42,7 +42,6 @@ int MPI_Graph_neighbors(MPI_Comm comm, int rank, int maxneighbors,
int neighbors[])
{
int err;
mca_topo_base_module_graph_neighbors_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -59,11 +58,6 @@ int MPI_Graph_neighbors(MPI_Comm comm, int rank, int maxneighbors,
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if ((0 > maxneighbors) || ((0 < maxneighbors) && NULL == neighbors)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
@ -74,18 +68,15 @@ int MPI_Graph_neighbors(MPI_Comm comm, int rank, int maxneighbors,
}
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* neighbors the function pointer to do the right thing */
func = comm->c_topo->topo_graph_neighbors;
/* call the function */
err = func(comm, rank, maxneighbors, neighbors);
err = comm->c_topo->topo.graph.graph_neighbors(comm, rank, maxneighbors, neighbors);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* All done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -40,7 +40,6 @@ static const char FUNC_NAME[] = "MPI_Graph_neighbors_count";
int MPI_Graph_neighbors_count(MPI_Comm comm, int rank, int *nneighbors)
{
int err;
mca_topo_base_module_graph_neighbors_count_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -57,10 +56,6 @@ int MPI_Graph_neighbors_count(MPI_Comm comm, int rank, int *nneighbors)
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if ((0 > rank) || (rank > ompi_group_size(comm->c_local_group))) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_RANK,
FUNC_NAME);
@ -71,18 +66,14 @@ int MPI_Graph_neighbors_count(MPI_Comm comm, int rank, int *nneighbors)
}
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer to do the right thing */
func = comm->c_topo->topo_graph_neighbors_count;
/* call the function */
err = func(comm, rank, nneighbors);
err = comm->c_topo->topo.graph.graph_neighbors_count(comm, rank, nneighbors);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* All done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
@ -40,7 +40,6 @@ static const char FUNC_NAME[] = "MPI_Graphdims_get";
int MPI_Graphdims_get(MPI_Comm comm, int *nnodes, int *nedges)
{
int err;
mca_topo_base_module_graphdims_get_fn_t func;
MEMCHECKER(
memchecker_comm(comm);
@ -57,28 +56,20 @@ int MPI_Graphdims_get(MPI_Comm comm, int *nnodes, int *nedges)
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_COMM,
FUNC_NAME);
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
if (NULL == nnodes || NULL == nedges) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_ARG,
FUNC_NAME);
}
}
if (!OMPI_COMM_IS_GRAPH(comm)) {
return OMPI_ERRHANDLER_INVOKE (comm, MPI_ERR_TOPOLOGY,
FUNC_NAME);
}
OPAL_CR_ENTER_LIBRARY();
/* get the function pointer to do the right thing */
func = comm->c_topo->topo_graphdims_get;
/* call the function */
err = func(comm, nnodes, nedges);
err = comm->c_topo->topo.graph.graphdims_get(comm, nnodes, nedges);
OPAL_CR_EXIT_LIBRARY();
if ( MPI_SUCCESS != err ) {
return OMPI_ERRHANDLER_INVOKE(comm, err, FUNC_NAME);
}
/* All done */
return MPI_SUCCESS;
OMPI_ERRHANDLER_RETURN(err, comm, err, FUNC_NAME);
}

Просмотреть файл

@ -52,8 +52,8 @@ static const char FUNC_NAME[] = "MPI_Info_set";
* @retval MPI_ERR_NO_MEM
*
* MPI_Info_set adds the (key,value) pair to info, and overrides
* teh value if for the same key a previsou value was set. key and
* value must be NULL terminated strings in C. In fortan, leading
* the value if for the same key a previsou value was set. key and
* value must be NULL terminated strings in C. In Fortan, leading
* and trailing spaces in key and value are stripped. If either
* key or value is greater than the allowed maxima, MPI_ERR_INFO_KEY
* and MPI_ERR_INFO_VALUE are raised
@ -66,10 +66,10 @@ int MPI_Info_set(MPI_Info info, char *key, char *value)
/*
* Error conditions are
* - info is NULL
* - No storage space available for the new value
* - Key length exceeded MPI_MAX_KEY_VAL
* - value length exceeded MPI_MAX_KEY_VAL
* - info is NULL
* - No storage space available for the new value
* - Key length exceeded MPI_MAX_KEY_VAL
* - value length exceeded MPI_MAX_KEY_VAL
*/
if (MPI_PARAM_CHECK) {

Просмотреть файл

@ -181,7 +181,7 @@ int MPI_Intercomm_create(MPI_Comm local_comm, int local_leader,
NULL, /* remote_procs */
NULL, /* attrs */
local_comm->error_handler, /* error handler*/
NULL, /* topo mpodule */
false, /* dont copy the topo */
local_comm->c_local_group, /* local group */
new_group_pointer /* remote group */
);

Просмотреть файл

@ -101,7 +101,7 @@ int MPI_Intercomm_merge(MPI_Comm intercomm, int high,
NULL, /* remote_procs */
NULL, /* attrs */
intercomm->error_handler, /* error handler*/
NULL, /* topo mpodule */
false, /* don't copy the topo */
new_group_pointer, /* local group */
NULL /* remote group */
);

Просмотреть файл

@ -105,6 +105,10 @@ nodist_libmpi_c_pmpi_la_SOURCES = \
pcomm_remote_group.c \
pcomm_remote_size.c \
pcomm_set_attr.c \
pdist_graph_create.c \
pdist_graph_create_adjacent.c \
pdist_graph_neighbors.c \
pdist_graph_neighbors_count.c \
pcomm_set_errhandler.c \
pcomm_set_name.c \
pcomm_size.c \

Просмотреть файл

@ -91,6 +91,10 @@
#define MPI_Comm_remote_group PMPI_Comm_remote_group
#define MPI_Comm_remote_size PMPI_Comm_remote_size
#define MPI_Comm_set_attr PMPI_Comm_set_attr
#define MPI_Dist_graph_create PMPI_Dist_graph_create
#define MPI_Dist_graph_create_adjacent PMPI_Dist_graph_create_adjacent
#define MPI_Dist_graph_neighbors PMPI_Dist_graph_neighbors
#define MPI_Dist_graph_neighbors_count PMPI_Dist_graph_neighbors_count
#define MPI_Comm_set_errhandler PMPI_Comm_set_errhandler
#define MPI_Comm_set_name PMPI_Comm_set_name
#define MPI_Comm_size PMPI_Comm_size

Просмотреть файл

@ -15,15 +15,15 @@
*
* $HEADER$
*/
#include "ompi_config.h"
#include <stdio.h>
#include "ompi_config.h"
#include <stdio.h>
#include "ompi/mpi/c/bindings.h"
#include "ompi/runtime/params.h"
#include "ompi/communicator/communicator.h"
#include "ompi/errhandler/errhandler.h"
#include "ompi/memchecker.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILING_DEFINES
#pragma weak MPI_Topo_test = PMPI_Topo_test
#endif
@ -53,10 +53,12 @@ int MPI_Topo_test(MPI_Comm comm, int *status)
}
}
if ( comm->c_flags & OMPI_COMM_CART ) {
if (OMPI_COMM_IS_CART(comm)) {
*status = MPI_CART;
} else if ( comm->c_flags & OMPI_COMM_GRAPH ) {
} else if (OMPI_COMM_IS_GRAPH(comm)) {
*status = MPI_GRAPH;
} else if (OMPI_COMM_IS_DIST_GRAPH(comm)) {
*status = MPI_DIST_GRAPH;
} else {
*status = MPI_UNDEFINED;
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -10,6 +10,8 @@
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2006-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2011-2012 INRIA. All rights reserved.
* Copyright (c) 2011-2012 Universite Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -98,6 +100,8 @@ DECL(int, MPI_FORTRAN_BOTTOM, mpi_fortran_bottom,
mpi_fortran_bottom_, mpi_fortran_bottom__);
DECL(int, MPI_FORTRAN_IN_PLACE, mpi_fortran_in_place,
mpi_fortran_in_place_, mpi_fortran_in_place__);
DECL(int, MPI_FORTRAN_UNWEIGHTED, mpi_fortran_unweighted,
mpi_fortran_unweighted_, mpi_fortran_unweighted__);
DECL(char *, MPI_FORTRAN_ARGV_NULL, mpi_fortran_argv_null,
mpi_fortran_argv_null_, mpi_fortran_argv_null__);
DECL(char *, MPI_FORTRAN_ARGVS_NULL, mpi_fortran_argvs_null,
@ -124,6 +128,11 @@ DECL(int *, MPI_FORTRAN_STATUSES_IGNORE, mpi_fortran_statuses_ignore,
addr == (void*) &mpi_fortran_in_place || \
addr == (void*) &mpi_fortran_in_place_ || \
addr == (void*) &mpi_fortran_in_place__)
#define OMPI_IS_FORTRAN_UNWEIGHTED(addr) \
(addr == (void*) &MPI_FORTRAN_UNWEIGHTED || \
addr == (void*) &mpi_fortran_unweighted || \
addr == (void*) &mpi_fortran_unweighted_ || \
addr == (void*) &mpi_fortran_unweighted__)
#define OMPI_IS_FORTRAN_ARGV_NULL(addr) \
(addr == (void*) &MPI_FORTRAN_ARGV_NULL || \
addr == (void*) &mpi_fortran_argv_null || \
@ -155,6 +164,8 @@ DECL(int *, MPI_FORTRAN_STATUSES_IGNORE, mpi_fortran_statuses_ignore,
(addr == (void*) &MPI_FORTRAN_BOTTOM)
#define OMPI_IS_FORTRAN_IN_PLACE(addr) \
(addr == (void*) &MPI_FORTRAN_IN_PLACE)
#define OMPI_IS_FORTRAN_UNWEIGHTED(addr) \
(addr == (void*) &MPI_FORTRAN_UNWEIGHTED)
#define OMPI_IS_FORTRAN_ARGV_NULL(addr) \
(addr == (void*) &MPI_FORTRAN_ARGV_NULL)
#define OMPI_IS_FORTRAN_ARGVS_NULL(addr) \
@ -171,6 +182,8 @@ DECL(int *, MPI_FORTRAN_STATUSES_IGNORE, mpi_fortran_statuses_ignore,
(addr == (void*) &mpi_fortran_bottom)
#define OMPI_IS_FORTRAN_IN_PLACE(addr) \
(addr == (void*) &mpi_fortran_in_place)
#define OMPI_IS_FORTRAN_UNWEIGHTED(addr) \
(addr == (void*) &mpi_fortran_unweighted)
#define OMPI_IS_FORTRAN_ARGV_NULL(addr) \
(addr == (void*) &mpi_fortran_argv_null)
#define OMPI_IS_FORTRAN_ARGVS_NULL(addr) \
@ -187,6 +200,8 @@ DECL(int *, MPI_FORTRAN_STATUSES_IGNORE, mpi_fortran_statuses_ignore,
(addr == (void*) &mpi_fortran_bottom_)
#define OMPI_IS_FORTRAN_IN_PLACE(addr) \
(addr == (void*) &mpi_fortran_in_place_)
#define OMPI_IS_FORTRAN_UNWEIGHTED(addr) \
(addr == (void*) &mpi_fortran_unweighted_)
#define OMPI_IS_FORTRAN_ARGV_NULL(addr) \
(addr == (void*) &mpi_fortran_argv_null_)
#define OMPI_IS_FORTRAN_ARGVS_NULL(addr) \
@ -203,6 +218,8 @@ DECL(int *, MPI_FORTRAN_STATUSES_IGNORE, mpi_fortran_statuses_ignore,
(addr == (void*) &mpi_fortran_bottom__)
#define OMPI_IS_FORTRAN_IN_PLACE(addr) \
(addr == (void*) &mpi_fortran_in_place__)
#define OMPI_IS_FORTRAN_UNWEIGHTED(addr) \
(addr == (void*) &mpi_fortran_unweighted__)
#define OMPI_IS_FORTRAN_ARGV_NULL(addr) \
(addr == (void*) &mpi_fortran_argv_null__)
#define OMPI_IS_FORTRAN_ARGVS_NULL(addr) \
@ -217,7 +234,8 @@ DECL(int *, MPI_FORTRAN_STATUSES_IGNORE, mpi_fortran_statuses_ignore,
#endif /* weak / specific symbol type */
/* Convert between Fortran and C MPI_BOTTOM */
#define OMPI_F2C_BOTTOM(addr) (OMPI_IS_FORTRAN_BOTTOM(addr) ? MPI_BOTTOM : (addr))
#define OMPI_F2C_IN_PLACE(addr) (OMPI_IS_FORTRAN_IN_PLACE(addr) ? MPI_IN_PLACE : (addr))
#define OMPI_F2C_BOTTOM(addr) (OMPI_IS_FORTRAN_BOTTOM(addr) ? MPI_BOTTOM : (addr))
#define OMPI_F2C_IN_PLACE(addr) (OMPI_IS_FORTRAN_IN_PLACE(addr) ? MPI_IN_PLACE : (addr))
#define OMPI_F2C_UNWEIGHTED(addr) (OMPI_IS_FORTRAN_UNWEIGHTED(addr) ? MPI_UNWEIGHTED : (addr))
#endif /* OMPI_FORTRAN_BASE_CONSTANTS_H */

Просмотреть файл

@ -10,7 +10,8 @@
# Copyright (c) 2004-2005 The Regents of the University of California.
# All rights reserved.
# Copyright (c) 2006-2012 Cisco Systems, Inc. All rights reserved.
# Copyright (c) 2012 Inria. All rights reserved.
# Copyright (c) 2011-2012 Inria. All rights reserved.
# Copyright (c) 2011-2012 Universite Bordeaux 1
# $COPYRIGHT$
#
# Additional copyrights may follow
@ -135,6 +136,10 @@ libmpi_mpifh_la_SOURCES += \
comm_split_f.c \
comm_split_type_f.c \
comm_test_inter_f.c \
dist_graph_create_adjacent_f.c \
dist_graph_create_f.c \
dist_graph_neighbors_f.c \
dist_graph_neighbors_count_f.c \
dims_create_f.c \
errhandler_create_f.c \
errhandler_free_f.c \

Просмотреть файл

@ -0,0 +1,113 @@
/*
* Copyright (c) 2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011 INRIA. All rights reserved.
* Copyright (c) 2011 Université Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#include "ompi_config.h"
#include "ompi/mpi/fortran/mpif-h/bindings.h"
#include "ompi/mpi/fortran/base/constants.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILE_LAYER
#pragma weak PMPI_DIST_GRAPH_CREATE_ADJACENT = ompi_dist_graph_create_adjacent_f
#pragma weak pmpi_dist_graph_create_adjacent = ompi_dist_graph_create_adjacent_f
#pragma weak pmpi_dist_graph_create_adjacent_ = ompi_dist_graph_create_adjacent_f
#pragma weak pmpi_dist_graph_create_adjacent__ = ompi_dist_graph_create_adjacent_f
#pragma weak PMPI_Dist_graph_create_adjacent_f = ompi_dist_graph_create_adjacent_f
#pragma weak PMPI_Dist_graph_create_adjacent_f08 = ompi_dist_graph_create_adjacent_f
#elif OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (PMPI_DIST_GRAPH_CREATE_ADJACENT,
pmpi_dist_graph_create_adjacent,
pmpi_dist_graph_create_adjacent_,
pmpi_dist_graph_create_adjacent__,
pompi_dist_graph_create_adjacent_f,
(MPI_Fint *comm_old, MPI_Fint *indegree, MPI_Fint *sources, MPI_Fint *sourceweights, MPI_Fint *outdegree, MPI_Fint *destinations, MPI_Fint *destweights, MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph, MPI_Fint *ierr),
(comm_old, indegree, sources, sourceweights, outdegree, destinations, destweights, info, reorder, comm_graph, ierr) )
#endif
#if OPAL_HAVE_WEAK_SYMBOLS
#pragma weak MPI_DIST_GRAPH_CREATE_ADJACENT = ompi_dist_graph_create_adjacent_f
#pragma weak mpi_dist_graph_create_adjacent = ompi_dist_graph_create_adjacent_f
#pragma weak mpi_dist_graph_create_adjacent_ = ompi_dist_graph_create_adjacent_f
#pragma weak mpi_dist_graph_create_adjacent__ = ompi_dist_graph_create_adjacent_f
#pragma weak MPI_Dist_graph_create_adjacent_f = ompi_dist_graph_create_adjacent_f
#pragma weak MPI_Dist_graph_create_adjacent_f08 = ompi_dist_graph_create_adjacent_f
#endif
#if ! OPAL_HAVE_WEAK_SYMBOLS && ! OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (MPI_DIST_GRAPH_CREATE_ADJACENT,
mpi_dist_graph_create_adjacent,
mpi_dist_graph_create_adjacent_,
mpi_dist_graph_create_adjacent__,
ompi_dist_graph_create_adjacent_f,
(MPI_Fint *comm_old, MPI_Fint *indegree, MPI_Fint *sources, MPI_Fint *sourceweights, MPI_Fint *outdegree, MPI_Fint *destinations, MPI_Fint *destweights, MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph, MPI_Fint *ierr),
(comm_old, indegree, sources, sourceweights, outdegree, destinations, destweights, info, reorder, comm_graph, ierr) )
#endif
#if OMPI_PROFILE_LAYER && ! OPAL_HAVE_WEAK_SYMBOLS
#include "ompi/mpi/fortran/mpif-h/profile/defines.h"
#endif
static const char FUNC_NAME[] = "MPI_DIST_GRAPH_CREATE_ADJACENT";
void ompi_dist_graph_create_adjacent_f(MPI_Fint *comm_old, MPI_Fint *indegree,
MPI_Fint *sources, MPI_Fint *sourceweights,
MPI_Fint *outdegree,
MPI_Fint *destinations, MPI_Fint *destweights, MPI_Fint *info,
ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph,
MPI_Fint *ierr)
{
MPI_Info c_info;
MPI_Comm c_comm_old, c_comm_graph;
OMPI_ARRAY_NAME_DECL(sources);
OMPI_ARRAY_NAME_DECL(sourceweights);
OMPI_ARRAY_NAME_DECL(destinations);
OMPI_ARRAY_NAME_DECL(destweights);
c_comm_old = MPI_Comm_f2c(*comm_old);
c_info = MPI_Info_f2c(*info);
OMPI_ARRAY_FINT_2_INT(sources, *indegree);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ) {
OMPI_ARRAY_FINT_2_INT(sourceweights, *indegree);
}
OMPI_ARRAY_FINT_2_INT(destinations, *outdegree);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ) {
OMPI_ARRAY_FINT_2_INT(destweights, *outdegree);
}
/* Number of edges is equal to the last entry in the index array */
OMPI_ARRAY_FINT_2_INT(edges, index[*nnodes - 1]);
*ierr = OMPI_INT_2_FINT(MPI_Dist_graph_create_adjacent(c_comm_old, OMPI_FINT_2_INT(*indegree),
OMPI_ARRAY_NAME_CONVERT(sources),
OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ? MPI_UNWEIGHTED : OMPI_ARRAY_NAME_CONVERT(sourceweights),
OMPI_FINT_2_INT(*outdegree),
OMPI_ARRAY_NAME_CONVERT(destinations),
OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ? MPI_UNWEIGHTED : OMPI_ARRAY_NAME_CONVERT(destweights),
c_info,
OMPI_LOGICAL_2_INT(*reorder),
&c_comm_graph));
if (OMPI_SUCCESS == OMPI_FINT_2_INT(*ierr)) {
*comm_graph = MPI_Comm_c2f(c_comm_graph);
}
OMPI_ARRAY_FINT_2_INT_CLEANUP(sources);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ) {
OMPI_ARRAY_FINT_2_INT_CLEANUP(sourceweights);
}
OMPI_ARRAY_FINT_2_INT_CLEANUP(destinations);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ) {
OMPI_ARRAY_FINT_2_INT_CLEANUP(destweights);
}
}

100
ompi/mpi/fortran/mpif-h/dist_graph_create_f.c Обычный файл
Просмотреть файл

@ -0,0 +1,100 @@
/*
* Copyright (c) 2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011 INRIA. All rights reserved.
* Copyright (c) 2011 Université Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#include "ompi_config.h"
#include "ompi/mpi/fortran/mpif-h/bindings.h"
#include "ompi/mpi/fortran/base/constants.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILE_LAYER
#pragma weak PMPI_DIST_GRAPH_CREATE = ompi_dist_graph_create_f
#pragma weak pmpi_dist_graph_create = ompi_dist_graph_create_f
#pragma weak pmpi_dist_graph_create_ = ompi_dist_graph_create_f
#pragma weak pmpi_dist_graph_create__ = ompi_dist_graph_create_f
#pragma weak PMPI_Dist_graph_create_f = ompi_dist_graph_create_f
#pragma weak PMPI_Dist_graph_create_f08 = ompi_dist_graph_create_f
#elif OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (PMPI_DIST_GRAPH_CREATE,
pmpi_dist_graph_create,
pmpi_dist_graph_create_,
pmpi_dist_graph_create__,
pompi_dist_graph_create_f,
(MPI_Fint *comm_old, MPI_Fint *n, MPI_Fint *sources, MPI_Fint *degrees, MPI_Fint *destinations, MPI_Fint *weights, MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph, MPI_Fint *ierr),
(comm_old, n, sources, degrees, destinations, weights, info, reorder, comm_graph, ierr) )
#endif
#if OPAL_HAVE_WEAK_SYMBOLS
#pragma weak MPI_DIST_GRAPH_CREATE = ompi_dist_graph_create_f
#pragma weak mpi_dist_graph_create = ompi_dist_graph_create_f
#pragma weak mpi_dist_graph_create_ = ompi_dist_graph_create_f
#pragma weak mpi_dist_graph_create__ = ompi_dist_graph_create_f
#pragma weak MPI_Dist_graph_create_f = ompi_dist_graph_create_f
#pragma weak MPI_Dist_graph_create_f08 = ompi_dist_graph_create_f
#endif
#if ! OPAL_HAVE_WEAK_SYMBOLS && ! OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (MPI_DIST_GRAPH_CREATE,
mpi_dist_graph_create,
mpi_dist_graph_create_,
mpi_dist_graph_create__,
ompi_dist_graph_create_f,
(MPI_Fint *comm_old, MPI_Fint *n, MPI_Fint *sources, MPI_Fint *degrees, MPI_Fint *destinations, MPI_Fint *weights, MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph, MPI_Fint *ierr),
(comm_old, n, sources, degrees, destinations, weights, info, reorder, comm_graph, ierr) )
#endif
#if OMPI_PROFILE_LAYER && ! OPAL_HAVE_WEAK_SYMBOLS
#include "ompi/mpi/fortran/mpif-h/profile/defines.h"
#endif
void ompi_dist_graph_create_f(MPI_Fint *comm_old, MPI_Fint *n, MPI_Fint *sources,
MPI_Fint *degrees, MPI_Fint *destinations, MPI_Fint *weights,
MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph,
MPI_Fint *ierr)
{
MPI_Comm c_comm_old, c_comm_graph;
int count = 0, i;
MPI_Info c_info;
OMPI_ARRAY_NAME_DECL(sources);
OMPI_ARRAY_NAME_DECL(degrees);
OMPI_ARRAY_NAME_DECL(destinations);
OMPI_ARRAY_NAME_DECL(weights);
c_comm_old = MPI_Comm_f2c(*comm_old);
c_info = MPI_Info_f2c(*info);
OMPI_ARRAY_FINT_2_INT(sources, *n);
OMPI_ARRAY_FINT_2_INT(degrees, *n);
for( i = 0; i < OMPI_FINT_2_INT(*n); i++ )
count += OMPI_ARRAY_NAME_CONVERT(degrees)[i];
OMPI_ARRAY_FINT_2_INT(destinations, count);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(weights) ) {
OMPI_ARRAY_FINT_2_INT(weights, count);
}
*ierr = OMPI_INT_2_FINT(MPI_Dist_graph_create(c_comm_old, OMPI_FINT_2_INT(*n), OMPI_ARRAY_NAME_CONVERT(sources),
OMPI_ARRAY_NAME_CONVERT(degrees), OMPI_ARRAY_NAME_CONVERT(destinations),
OMPI_IS_FORTRAN_UNWEIGHTED(weights) ? MPI_UNWEIGHTED : OMPI_ARRAY_NAME_CONVERT(weights),
c_info, OMPI_LOGICAL_2_INT(*reorder), &c_comm_graph));
if (OMPI_SUCCESS == OMPI_FINT_2_INT(*ierr)) {
*comm_graph = MPI_Comm_c2f(c_comm_graph);
}
OMPI_ARRAY_FINT_2_INT_CLEANUP(sources);
OMPI_ARRAY_FINT_2_INT_CLEANUP(degrees);
OMPI_ARRAY_FINT_2_INT_CLEANUP(destinations);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(weights) ) {
OMPI_ARRAY_FINT_2_INT_CLEANUP(weights);
}
}

Просмотреть файл

@ -0,0 +1,82 @@
/*
* Copyright (c) 2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011 INRIA. All rights reserved.
* Copyright (c) 2011 Université Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#include "ompi_config.h"
#include "ompi/mpi/fortran/mpif-h/bindings.h"
#include "ompi/mpi/fortran/base/constants.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILE_LAYER
#pragma weak PMPI_DIST_GRAPH_NEIGHBORS_COUNT = ompi_dist_graph_neighbors_count_f
#pragma weak pmpi_dist_graph_neighbors_count = ompi_dist_graph_neighbors_count_f
#pragma weak pmpi_dist_graph_neighbors_count_ = ompi_dist_graph_neighbors_count_f
#pragma weak pmpi_dist_graph_neighbors_count__ = ompi_dist_graph_neighbors_count_f
#pragma weak PMPI_Dist_graph_neighbors_count_f = ompi_dist_graph_neighbors_count_f
#pragma weak PMPI_Dist_graph_neighbors_count_f08 = ompi_dist_graph_neighbors_count_f
#elif OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (PMPI_DIST_GRAPH_NEIGHBORS_COUNT,
pmpi_dist_graph_neighbors_count,
pmpi_dist_graph_neighbors_count_,
pmpi_dist_graph_neighbors_count__,
pompi_dist_graph_neighbors_count_f,
(MPI_Fint *comm, MPI_Fint *inneighbors, MPI_Fint *outneighbors, ompi_fortran_logical_t *weighted, MPI_Fint *ierr),
(comm, inneighbors, outneighbors, weighted, ierr) )
#endif
#if OPAL_HAVE_WEAK_SYMBOLS
#pragma weak MPI_DIST_GRAPH_NEIGHBORS_COUNT = ompi_dist_graph_neighbors_count_f
#pragma weak mpi_dist_graph_neighbors_count = ompi_dist_graph_neighbors_count_f
#pragma weak mpi_dist_graph_neighbors_count_ = ompi_dist_graph_neighbors_count_f
#pragma weak mpi_dist_graph_neighbors_count__ = ompi_dist_graph_neighbors_count_f
#pragma weak MPI_Dist_graph_neighbors_count_f = ompi_dist_graph_neighbors_count_f
#pragma weak MPI_Dist_graph_neighbors_count_f08 = ompi_dist_graph_neighbors_count_f
#endif
#if ! OPAL_HAVE_WEAK_SYMBOLS && ! OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (MPI_DIST_GRAPH_NEIGHBORS_COUNT,
mpi_dist_graph_neighbors_count,
mpi_dist_graph_neighbors_count_,
mpi_dist_graph_neighbors_count__,
ompi_dist_graph_neighbors_count_f,
(MPI_Fint *comm, MPI_Fint *inneighbors, MPI_Fint *outneighbors, ompi_fortran_logical_t *weighted, MPI_Fint *ierr),
(comm, inneighbors, outneighbors, weighted, ierr) )
#endif
#if OMPI_PROFILE_LAYER && ! OPAL_HAVE_WEAK_SYMBOLS
#include "ompi/mpi/fortran/mpif-h/profile/defines.h"
#endif
void ompi_dist_graph_neighbors_count_f(MPI_Fint *comm, MPI_Fint *inneighbors,
MPI_Fint *outneighbors, ompi_fortran_logical_t *weighted,
MPI_Fint *ierr)
{
MPI_Comm c_comm;
OMPI_SINGLE_NAME_DECL(inneighbors);
OMPI_SINGLE_NAME_DECL(outneighbors);
OMPI_LOGICAL_NAME_DECL(weighted);
c_comm = MPI_Comm_f2c(*comm);
*ierr = OMPI_INT_2_FINT(MPI_Dist_graph_neighbors_count(c_comm,
OMPI_SINGLE_NAME_CONVERT(inneighbors),
OMPI_SINGLE_NAME_CONVERT(outneighbors),
OMPI_LOGICAL_SINGLE_NAME_CONVERT(weighted)));
OMPI_SINGLE_INT_2_LOGICAL(weighted);
if (OMPI_SUCCESS == OMPI_FINT_2_INT(*ierr)) {
OMPI_SINGLE_INT_2_FINT(inneighbors);
OMPI_SINGLE_INT_2_FINT(outneighbors);
}
}

Просмотреть файл

@ -0,0 +1,108 @@
/*
* Copyright (c) 2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2011 INRIA. All rights reserved.
* Copyright (c) 2011 Université Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#include "ompi_config.h"
#include "ompi/mpi/fortran/mpif-h/bindings.h"
#include "ompi/mpi/fortran/base/constants.h"
#if OPAL_HAVE_WEAK_SYMBOLS && OMPI_PROFILE_LAYER
#pragma weak PMPI_DIST_GRAPH_NEIGHBORS = ompi_dist_graph_neighbors_f
#pragma weak pmpi_dist_graph_neighbors = ompi_dist_graph_neighbors_f
#pragma weak pmpi_dist_graph_neighbors_ = ompi_dist_graph_neighbors_f
#pragma weak pmpi_dist_graph_neighbors__ = ompi_dist_graph_neighbors_f
#pragma weak PMPI_Dist_graph_neighbors_f = ompi_dist_graph_neighbors_f
#pragma weak PMPI_Dist_graph_neighbors_f08 = ompi_dist_graph_neighbors_f
#elif OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (PMPI_DIST_GRAPH_NEIGHBORS,
pmpi_dist_graph_neighbors,
pmpi_dist_graph_neighbors_,
pmpi_dist_graph_neighbors__,
pompi_dist_graph_neighbors_f,
(MPI_Fint* comm, MPI_Fint* maxindegree, MPI_Fint* sources, MPI_Fint* sourceweights, MPI_Fint* maxoutdegree, MPI_Fint* destinations, MPI_Fint* destweights, MPI_Fint *ierr),
(comm, maxindegree, sources, sourceweights, maxoutdegree, destinations, destweights, ierr) )
#endif
#if OPAL_HAVE_WEAK_SYMBOLS
#pragma weak MPI_DIST_GRAPH_NEIGHBORS = ompi_dist_graph_neighbors_f
#pragma weak mpi_dist_graph_neighbors = ompi_dist_graph_neighbors_f
#pragma weak mpi_dist_graph_neighbors_ = ompi_dist_graph_neighbors_f
#pragma weak mpi_dist_graph_neighbors__ = ompi_dist_graph_neighbors_f
#pragma weak MPI_Dist_graph_neighbors_f = ompi_dist_graph_neighbors_f
#pragma weak MPI_Dist_graph_neighbors_f08 = ompi_dist_graph_neighbors_f
#endif
#if ! OPAL_HAVE_WEAK_SYMBOLS && ! OMPI_PROFILE_LAYER
OMPI_GENERATE_F77_BINDINGS (MPI_DIST_GRAPH_NEIGHBORS,
mpi_dist_graph_neighbors,
mpi_dist_graph_neighbors_,
mpi_dist_graph_neighbors__,
ompi_dist_graph_neighbors_f,
(MPI_Fint* comm, MPI_Fint* maxindegree, MPI_Fint* sources, MPI_Fint* sourceweights, MPI_Fint* maxoutdegree, MPI_Fint* destinations, MPI_Fint* destweights, MPI_Fint *ierr),
(comm, maxindegree, sources, sourceweights, maxoutdegree, destinations, destweights, ierr) )
#endif
#if OMPI_PROFILE_LAYER && ! OPAL_HAVE_WEAK_SYMBOLS
#include "ompi/mpi/fortran/mpif-h/profile/defines.h"
#endif
void ompi_dist_graph_neighbors_f(MPI_Fint* comm, MPI_Fint* maxindegree,
MPI_Fint* sources, MPI_Fint* sourceweights,
MPI_Fint* maxoutdegree, MPI_Fint* destinations,
MPI_Fint* destweights,
MPI_Fint *ierr)
{
MPI_Comm c_comm;
OMPI_ARRAY_NAME_DECL(sources);
OMPI_ARRAY_NAME_DECL(sourceweights);
OMPI_ARRAY_NAME_DECL(destinations);
OMPI_ARRAY_NAME_DECL(destweights);
c_comm = MPI_Comm_f2c(*comm);
OMPI_ARRAY_FINT_2_INT_ALLOC(sources, *maxindegree);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ) {
OMPI_ARRAY_FINT_2_INT_ALLOC(sourceweights, *maxindegree);
}
OMPI_ARRAY_FINT_2_INT_ALLOC(destinations, *maxoutdegree);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ) {
OMPI_ARRAY_FINT_2_INT_ALLOC(destweights, *maxoutdegree);
}
*ierr = OMPI_INT_2_FINT(MPI_Dist_graph_neighbors(c_comm, OMPI_FINT_2_INT(*maxindegree),
OMPI_ARRAY_NAME_CONVERT(sources),
OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ? MPI_UNWEIGHTED : OMPI_ARRAY_NAME_CONVERT(sourceweights),
OMPI_FINT_2_INT(*maxoutdegree), OMPI_ARRAY_NAME_CONVERT(destinations),
OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ? MPI_UNWEIGHTED : OMPI_ARRAY_NAME_CONVERT(destweights)));
if (OMPI_SUCCESS == OMPI_FINT_2_INT(*ierr)) {
OMPI_ARRAY_INT_2_FINT(sources, *maxindegree);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ) {
OMPI_ARRAY_INT_2_FINT(sourceweights, *maxindegree);
}
OMPI_ARRAY_INT_2_FINT(destinations, *maxoutdegree);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ) {
OMPI_ARRAY_INT_2_FINT(destweights, *maxoutdegree);
}
} else {
OMPI_ARRAY_FINT_2_INT_CLEANUP(sources);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(sourceweights) ) {
OMPI_ARRAY_FINT_2_INT_CLEANUP(sourceweights);
}
OMPI_ARRAY_FINT_2_INT_CLEANUP(destinations);
if( !OMPI_IS_FORTRAN_UNWEIGHTED(destweights) ) {
OMPI_ARRAY_FINT_2_INT_CLEANUP(destweights);
}
}
}

Просмотреть файл

@ -2,7 +2,7 @@
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* Copyright (c) 2004-2012 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
@ -10,6 +10,8 @@
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2011-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2011 Inria. All rights reserved.
* Copyright (c) 2011 Universite Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow

Просмотреть файл

@ -11,7 +11,8 @@
# Copyright (c) 2004-2005 The Regents of the University of California.
# All rights reserved.
# Copyright (c) 2009-2012 Cisco Systems, Inc. All rights reserved.
# Copyright (c) 2012 Inria. All rights reserved.
# Copyright (c) 2011-2012 Inria. All rights reserved.
# Copyright (c) 2011-2012 Universite Bordeaux 1
# $COPYRIGHT$
#
# Additional copyrights may follow
@ -106,6 +107,10 @@ nodist_libmpi_mpifh_pmpi_la_SOURCES = \
pcomm_split_type_f.c \
pcomm_test_inter_f.c \
pdims_create_f.c \
pdist_graph_create_adjacent_f.c \
pdist_graph_create_f.c \
pdist_graph_neighbors_f.c \
pdist_graph_neighbors_count_f.c \
perrhandler_create_f.c \
perrhandler_free_f.c \
perrhandler_get_f.c \

Просмотреть файл

@ -10,7 +10,8 @@
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2009-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012 Inria. All rights reserved.
* Copyright (c) 2011-2012 Inria. All rights reserved.
* Copyright (c) 2011 Universite Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -83,6 +84,10 @@
#define ompi_comm_split_type_f pompi_comm_split_type_f
#define ompi_comm_test_inter_f pompi_comm_test_inter_f
#define ompi_dims_create_f pompi_dims_create_f
#define ompi_dist_graph_create_f pompi_dist_graph_create_f
#define ompi_dist_graph_create_adjacent_f pompi_dist_graph_create_adjacent_f
#define ompi_dist_graph_neighbors_f pompi_dist_graph_neighbors_f
#define ompi_dist_graph_neighbors_count_f pompi_dist_graph_neighbors_count_f
#define ompi_errhandler_create_f pompi_errhandler_create_f
#define ompi_errhandler_free_f pompi_errhandler_free_f
#define ompi_errhandler_get_f pompi_errhandler_get_f

Просмотреть файл

@ -10,7 +10,8 @@
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2006-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012 Inria. All rights reserved.
* Copyright (c) 2011-2012 Inria. All rights reserved.
* Copyright (c) 2011-2012 Universite Bordeaux 1
* $COPYRIGHT$
*
* Additional copyrights may follow
@ -139,6 +140,10 @@ PN2(void, MPI_Comm_split, mpi_comm_split, MPI_COMM_SPLIT, (MPI_Fint *comm, MPI_F
PN2(void, MPI_Comm_split_type, mpi_comm_split_type, MPI_COMM_SPLIT_TYPE, (MPI_Fint *comm, MPI_Fint *split_type, MPI_Fint *key, MPI_Fint *info, MPI_Fint *newcomm, MPI_Fint *ierr));
PN2(void, MPI_Comm_test_inter, mpi_comm_test_inter, MPI_COMM_TEST_INTER, (MPI_Fint *comm, ompi_fortran_logical_t *flag, MPI_Fint *ierr));
PN2(void, MPI_Dims_create, mpi_dims_create, MPI_DIMS_CREATE, (MPI_Fint *nnodes, MPI_Fint *ndims, MPI_Fint *dims, MPI_Fint *ierr));
PN2(void, MPI_Dist_graph_create, mpi_dist_graph_create, MPI_DIST_GRAPH_CREATE, (MPI_Fint *comm_old, MPI_Fint *n, MPI_Fint *sources, MPI_Fint *degrees, MPI_Fint *destinations, MPI_Fint *weights, MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph, MPI_Fint *ierr));
PN2(void, MPI_Dist_graph_create_adjacent, mpi_dist_graph_create_adjacent, MPI_DIST_GRAPH_CREATE_ADJACENT, (MPI_Fint *comm_old, MPI_Fint *indegree, MPI_Fint *sources, MPI_Fint *sourceweights, MPI_Fint *outdegree, MPI_Fint *destinations, MPI_Fint *destweights, MPI_Fint *info, ompi_fortran_logical_t *reorder, MPI_Fint *comm_graph, MPI_Fint *ierr));
PN2(void, MPI_Dist_graph_neighbors, mpi_dist_graph_neighbors, MPI_DIST_GRAPH_NEIGHBORS, (MPI_Fint* comm, MPI_Fint* maxindegree, MPI_Fint* sources, MPI_Fint* sourceweights, MPI_Fint* maxoutdegree, MPI_Fint* destinations, MPI_Fint* destweights, MPI_Fint *ierr));
PN2(void, MPI_Dist_graph_neighbors_count, mpi_dist_graph_neighbors_count, MPI_DIST_GRAPH_NEIGHBORS_COUNT, (MPI_Fint *comm, MPI_Fint *inneighbors, MPI_Fint *outneighbors, ompi_fortran_logical_t *weighted, MPI_Fint *ierr));
PN2(void, MPI_Errhandler_create, mpi_errhandler_create, MPI_ERRHANDLER_CREATE, (ompi_errhandler_fortran_handler_fn_t* function, MPI_Fint *errhandler, MPI_Fint *ierr));
PN2(void, MPI_Errhandler_free, mpi_errhandler_free, MPI_ERRHANDLER_FREE, (MPI_Fint *errhandler, MPI_Fint *ierr));
PN2(void, MPI_Errhandler_get, mpi_errhandler_get, MPI_ERRHANDLER_GET, (MPI_Fint *comm, MPI_Fint *errhandler, MPI_Fint *ierr));

Просмотреть файл

@ -89,6 +89,10 @@ mpi_api_files = \
comm_spawn_multiple_f08.F90 \
comm_split_f08.F90 \
comm_test_inter_f08.F90 \
dist_graph_create_adjacent_f08.F90 \
dist_graph_create_f08.F90 \
dist_graph_neighbors_count_f08.F90 \
dist_graph_neighbors_f08.F90 \
dims_create_f08.F90 \
errhandler_free_f08.F90 \
error_class_f08.F90 \

Просмотреть файл

@ -10820,3 +10820,121 @@ output_291 MPI_Type_create_hindexed_block
end MPI_Type_create_hindexed_block
#------------------------------------------------------------------------
output_292() {
if test "$output" = "0"; then
return 0
fi
procedure=$1
cat <<EOF
subroutine ${procedure}(comm_old, n, sources, degrees, destinations, &
weights, info, reorder, comm_dist_graph, ierr)
integer, intent(in) :: comm_old
integer, intent(in) :: n
integer, dimension(n), intent(in) :: sources
integer, dimension(n), intent(in) :: degrees
integer, dimension(n), intent(in) :: destinations
integer, dimension(n), intent(in) :: weights
logical, intent(in) :: info
logical, intent(in) :: reorder
integer, intent(out) :: comm_dist_graph
integer, intent(out) :: ierr
end subroutine ${procedure}
EOF
}
start MPI_Dist_graph_create small
output_292 MPI_Dist_graph_create
end MPI_Dist_graph_create
#------------------------------------------------------------------------
output_293() {
if test "$output" = "0"; then
return 0
fi
procedure=$1
cat <<EOF
subroutine ${procedure}(comm_old, indegree, sources, sourceweights, &
outdegree, destinations, destweights, info, reorder, &
comm_dist_graph, ierr)
integer, intent(in) :: comm_old
integer, intent(in) :: indegree
integer, dimension(indegree), intent(in) :: sources
integer, dimension(indegree), intent(in) :: sourceweights
integer, intent(in) :: outdegree
integer, dimension(outdegree), intent(in) :: destinations
integer, dimension(outdegree), intent(in) :: destweights
logical, intent(in) :: info
logical, intent(in) :: reorder
integer, intent(out) :: comm_dist_graph
integer, intent(out) :: ierr
end subroutine ${procedure}
EOF
}
start MPI_Dist_graph_create_adjacent small
output_293 MPI_Dist_graph_create_adjacent
end MPI_Dist_graph_create_adjacent
#------------------------------------------------------------------------
output_294() {
if test "$output" = "0"; then
return 0
fi
procedure=$1
cat <<EOF
subroutine ${procedure}(comm, indegree, outdegree, weighted, ierr)
integer, intent(in) :: comm
integer, intent(out) :: indegree
integer, intent(out) :: outdegree
logical, intent(out) :: weighted
integer, intent(out) :: ierr
end subroutine ${procedure}
EOF
}
start MPI_Dist_graph_neighbors_count small
output_294 MPI_Dist_graph_neighbors_count
end MPI_Dist_graph_neighbors_count
#------------------------------------------------------------------------
output_295() {
if test "$output" = "0"; then
return 0
fi
procedure=$1
cat <<EOF
subroutine ${procedure}(comm, maxindegree, sources, sourceweights, &
maxoutdegree, destinations, destweights, ierr)
integer, intent(in) :: comm
integer, intent(in) :: maxindegree
integer, dimension(maxindegree), intent(out) :: sources
integer, dimension(maxindegree), intent(out) :: sourceweights
integer, intent(in) :: maxoutdegree
integer, dimension(maxoutdegree), intent(out) :: destinations
integer, dimension(maxoutdegree), intent(out) :: destweights
integer, intent(out) :: ierr
end subroutine ${procedure}
EOF
}
start MPI_Dist_graph_neighbors small
output_295 MPI_Dist_graph_neighbors
end MPI_Dist_graph_neighbors

Просмотреть файл

@ -284,6 +284,8 @@ INST(int, MPI_FORTRAN_BOTTOM, mpi_fortran_bottom,
mpi_fortran_bottom_, mpi_fortran_bottom__);
INST(int, MPI_FORTRAN_IN_PLACE, mpi_fortran_in_place,
mpi_fortran_in_place_, mpi_fortran_in_place__);
INST(int, MPI_FORTRAN_UNWEIGHTED, mpi_fortran_unweighted,
mpi_fortran_unweighted_, mpi_fortran_unweighted__);
INST(char *, MPI_FORTRAN_ARGV_NULL, mpi_fortran_argv_null,
mpi_fortran_argv_null_, mpi_fortran_argv_null__);
INST(char *, MPI_FORTRAN_ARGVS_NULL, mpi_fortran_argvs_null,