Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding locality-aware mpi #1122

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 16 additions & 0 deletions src/parcsr_ls/par_amg_setup.c
Original file line number Diff line number Diff line change
Expand Up @@ -3139,6 +3139,22 @@ hypre_BoomerAMGSetup( void *amg_vdata,
#if defined(HYPRE_USING_GPU)
if (exec == HYPRE_EXEC_HOST)
#endif

#ifdef HYPRE_USING_NODE_AWARE_MPI
//hypre_printf("%d\n", hypre_HandleNodeAwareSwitchoverThreshold(hypre_handle()));
if (level >= hypre_HandleNodeAwareSwitchoverThreshold(hypre_handle()))
{
hypre_ParCSRMatrixCommPkg(A_array[level])->use_neighbor = 1;
//hypre_printf("Level %d: use neighbor\n", level);
hypre_ParCSRCreateCommGraph( hypre_ParCSRMatrixFirstColDiag(A_array[level]),
hypre_ParCSRMatrixColMapOffd(A_array[level]),
hypre_ParCSRMatrixComm(A_array[level]),
hypre_ParCSRMatrixCommPkg(A_array[level]));
// Create comm handle in setup, so cost doesn't contribute to solve time
hypre_ParCSRCommPkgGetPersistentCommHandle(1, hypre_ParCSRMatrixCommPkg(A_array[level]));
}
#endif

{
HYPRE_Real size = ((HYPRE_Real)fine_size) * .75;
if (coarsen_type > 0 && coarse_size >= (HYPRE_BigInt)size)
Expand Down
23 changes: 23 additions & 0 deletions src/parcsr_mv/_hypre_parcsr_mv.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,10 @@ extern "C" {
#ifndef HYPRE_PAR_CSR_COMMUNICATION_HEADER
#define HYPRE_PAR_CSR_COMMUNICATION_HEADER

#ifdef HYPRE_USING_NODE_AWARE_MPI
#include "mpi_advance.h"
#endif

/*--------------------------------------------------------------------------
* hypre_ParCSRCommPkg:
* Structure containing information for doing communications
Expand Down Expand Up @@ -60,13 +64,21 @@ typedef struct
void *recv_data_buffer;
HYPRE_Int num_requests;
hypre_MPI_Request *requests;
#ifdef HYPRE_USING_NODE_AWARE_MPI
MPIX_Request *Xrequest;
#endif
} hypre_ParCSRCommHandle;

typedef hypre_ParCSRCommHandle hypre_ParCSRPersistentCommHandle;

typedef struct _hypre_ParCSRCommPkg
{
MPI_Comm comm;
#ifdef HYPRE_USING_NODE_AWARE_MPI
MPIX_Comm *neighbor_comm;
MPIX_Topo *neighbor_topo;
MPIX_Topo *neighborT_topo;
#endif
HYPRE_Int num_components;
HYPRE_Int num_sends;
HYPRE_Int *send_procs;
Expand All @@ -76,6 +88,11 @@ typedef struct _hypre_ParCSRCommPkg
HYPRE_Int num_recvs;
HYPRE_Int *recv_procs;
HYPRE_Int *recv_vec_starts;
#ifdef HYPRE_USING_NODE_AWARE_MPI
HYPRE_Int use_neighbor;
long *global_send_indices;
long *global_recv_indices;
#endif
/* remote communication information */
hypre_MPI_Datatype *send_mpi_types;
hypre_MPI_Datatype *recv_mpi_types;
Expand Down Expand Up @@ -798,6 +815,12 @@ HYPRE_Int hypre_RangeFillResponseIJDetermineRecvProcs ( void *p_recv_contact_buf
HYPRE_Int hypre_FillResponseIJDetermineSendProcs ( void *p_recv_contact_buf, HYPRE_Int contact_size,
HYPRE_Int contact_proc, void *ro, MPI_Comm comm, void **p_send_response_buf,
HYPRE_Int *response_message_size );
#ifdef HYPRE_USING_NODE_AWARE_MPI
void hypre_ParCSRCreateCommGraph( HYPRE_BigInt first_col_diag,
HYPRE_BigInt *col_map_offd,
MPI_Comm comm,
hypre_ParCSRCommPkg *comm_pkg );
#endif

/* numbers.c */
hypre_NumbersNode *hypre_NumbersNewNode ( void );
Expand Down
74 changes: 74 additions & 0 deletions src/parcsr_mv/new_commpkg.c
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,9 @@
*-----------------------------------------------------*/

#include "_hypre_parcsr_mv.h"
#ifdef HYPRE_USING_NODE_AWARE_MPI
#include <mpi.h>
#endif

/* some debugging tools*/
#define mydebug 0
Expand Down Expand Up @@ -584,6 +587,18 @@ hypre_NewCommPkgDestroy( hypre_ParCSRMatrix *parcsr_A )
hypre_TFree(hypre_ParCSRCommPkgRecvVecStarts(comm_pkg), HYPRE_MEMORY_HOST);
}

HYPRE_ANNOTATE_REGION_BEGIN("%s", "MPI graph free");
if (comm_pkg->neighbor_topo) {
MPIX_Topo_free(comm_pkg->neighbor_topo);
}
if (comm_pkg->neighborT_topo) {
MPIX_Topo_free(comm_pkg->neighborT_topo);
}
if (comm_pkg->neighbor_comm) {
MPIX_Comm_free(comm_pkg->neighbor_comm);
}
HYPRE_ANNOTATE_REGION_END("%s", "MPI graph free");

hypre_TFree(comm_pkg, HYPRE_MEMORY_HOST);
hypre_ParCSRMatrixCommPkg(parcsr_A) = NULL;

Expand Down Expand Up @@ -757,3 +772,62 @@ hypre_FillResponseIJDetermineSendProcs(void *p_recv_contact_buf,

return hypre_error_flag;
}

/*--------------------------------------------------------------------
* hypre_ParCSRCreateCommGraph
*
* Create communication topology graph for MPI neighborhood
* collectives
*--------------------------------------------------------------------*/

#ifdef HYPRE_USING_NODE_AWARE_MPI
void
hypre_ParCSRCreateCommGraph(HYPRE_BigInt first_col_diag,
HYPRE_BigInt *col_map_offd,
MPI_Comm comm,
hypre_ParCSRCommPkg *comm_pkg) {
HYPRE_Int num_sends = hypre_ParCSRCommPkgNumSends(comm_pkg);
HYPRE_Int num_recvs = hypre_ParCSRCommPkgNumRecvs(comm_pkg);
HYPRE_Int *send_map_starts = hypre_ParCSRCommPkgSendMapStarts(comm_pkg);
HYPRE_Int *recv_vec_starts = hypre_ParCSRCommPkgRecvVecStarts(comm_pkg);
HYPRE_Int *send_map_elmts = hypre_ParCSRCommPkgSendMapElmts(comm_pkg);

int *sendcounts = (int *)malloc(num_sends * sizeof(int));
int *recvcounts = (int *)malloc(num_recvs * sizeof(int));
for (int i = 0; i < num_sends; i++) {
sendcounts[i] = send_map_starts[i+1] - send_map_starts[i];
}
for (int i = 0; i < num_recvs; i++) {
recvcounts[i] = recv_vec_starts[i+1] - recv_vec_starts[i];
}

HYPRE_ANNOTATE_REGION_BEGIN("%s", "MPI topo creation");
MPIX_Comm_init(&comm_pkg->neighbor_comm, comm);
MPIX_Topo_dist_graph_create_adjacent(num_recvs, hypre_ParCSRCommPkgRecvProcs(comm_pkg),
recvcounts,
num_sends, hypre_ParCSRCommPkgSendProcs(comm_pkg),
sendcounts,
MPI_INFO_NULL, 0, &(comm_pkg->neighbor_topo));
MPIX_Topo_dist_graph_create_adjacent(num_sends, hypre_ParCSRCommPkgSendProcs(comm_pkg),
sendcounts,
num_recvs, hypre_ParCSRCommPkgRecvProcs(comm_pkg),
recvcounts,
MPI_INFO_NULL, 0, &(comm_pkg->neighborT_topo));
HYPRE_ANNOTATE_REGION_END("%s", "MPI topo creation");

HYPRE_Int num_send_elmts = send_map_starts[num_sends];
comm_pkg->global_send_indices = hypre_CTAlloc(long, num_send_elmts, HYPRE_MEMORY_HOST);
for (int i = 0; i < num_sends; i++) {
for (int j = send_map_starts[i]; j < send_map_starts[i+1]; j++) {
comm_pkg->global_send_indices[j] = send_map_elmts[j] + first_col_diag;
}
}
HYPRE_Int num_recv_elmts = recv_vec_starts[num_recvs];
comm_pkg->global_recv_indices = hypre_CTAlloc(long, num_recv_elmts, HYPRE_MEMORY_HOST);
for (int i = 0; i < num_recvs; i++) {
for (int j = recv_vec_starts[i]; j < recv_vec_starts[i+1]; j++) {
comm_pkg->global_recv_indices[j] = col_map_offd[j];
}
}
}
#endif
Loading