From caca157c08c0e9433e21c76d9ebcad39c2e600b9 Mon Sep 17 00:00:00 2001 From: suter Date: Thu, 8 May 2014 01:49:13 +0200 Subject: [PATCH] add support of MPI_Test in smpi_replay and TRACING-TI --- src/instr/instr_TI_trace.c | 3 +++ src/instr/instr_private.h | 1 + src/smpi/instr_smpi.c | 26 +++++++++++++++++++++++++ src/smpi/private.h | 2 ++ src/smpi/smpi_pmpi.c | 13 ++++++++++++- src/smpi/smpi_replay.c | 39 +++++++++++++++++++++++++++++++++++++- 6 files changed, 82 insertions(+), 2 deletions(-) diff --git a/src/instr/instr_TI_trace.c b/src/instr/instr_TI_trace.c index 29754729df..7c32c7de9f 100644 --- a/src/instr/instr_TI_trace.c +++ b/src/instr/instr_TI_trace.c @@ -149,6 +149,9 @@ void print_TIPushState(paje_event_t event) fprintf(trace_file, "%s irecv %d %d %s\n", process_id, extra->src, extra->send_size, extra->datatype1); break; + case TRACING_TEST: + fprintf(trace_file, "%s test\n", process_id); + break; case TRACING_WAIT: fprintf(trace_file, "%s wait\n", process_id); break; diff --git a/src/instr/instr_private.h b/src/instr/instr_private.h index 908ecd6cc3..80ba7b9a9c 100644 --- a/src/instr/instr_private.h +++ b/src/instr/instr_private.h @@ -421,6 +421,7 @@ typedef enum{ TRACING_RECV, TRACING_IRECV, TRACING_SENDRECV, + TRACING_TEST, TRACING_WAIT, TRACING_WAITALL, TRACING_WAITANY, diff --git a/src/smpi/instr_smpi.c b/src/smpi/instr_smpi.c index a097ed6dbf..31597feea5 100644 --- a/src/smpi/instr_smpi.c +++ b/src/smpi/instr_smpi.c @@ -281,6 +281,32 @@ void TRACE_smpi_computing_out(int rank) new_pajePopState (SIMIX_get_clock(), container, type); } +void TRACE_smpi_testing_in(int rank, instr_extra_data extra) +{ + //do not forget to set the color first, otherwise this will explode + if (!TRACE_smpi_is_enabled()) { + cleanup_extra_data(extra); + return; + } + + char str[INSTR_DEFAULT_STR_SIZE]; + smpi_container(rank, str, INSTR_DEFAULT_STR_SIZE); + container_t container = PJ_container_get (str); + type_t type = PJ_type_get ("MPI_STATE", container->type); + val_t value = PJ_value_get_or_new ("test", NULL, type); + new_pajePushStateWithExtra (SIMIX_get_clock(), container, type, value, (void*)extra); +} + +void TRACE_smpi_testing_out(int rank) +{ + if (!TRACE_smpi_is_enabled()) return; + char str[INSTR_DEFAULT_STR_SIZE]; + smpi_container(rank, str, INSTR_DEFAULT_STR_SIZE); + container_t container = PJ_container_get (str); + type_t type = PJ_type_get ("MPI_STATE", container->type); + new_pajePopState (SIMIX_get_clock(), container, type); +} + void TRACE_smpi_ptp_in(int rank, int src, int dst, const char *operation, instr_extra_data extra) { if (!TRACE_smpi_is_enabled()) { diff --git a/src/smpi/private.h b/src/smpi/private.h index aec9e4b49b..09e66faf84 100644 --- a/src/smpi/private.h +++ b/src/smpi/private.h @@ -602,6 +602,8 @@ void TRACE_smpi_collective_out(int rank, int root, const char *operation); void TRACE_smpi_computing_init(int rank); void TRACE_smpi_computing_out(int rank); void TRACE_smpi_computing_in(int rank, instr_extra_data extra); +void TRACE_smpi_testing_out(int rank); +void TRACE_smpi_testing_in(int rank, instr_extra_data extra); void TRACE_smpi_alloc(void); void TRACE_smpi_release(void); void TRACE_smpi_ptp_in(int rank, int src, int dst, const char *operation, instr_extra_data extra); diff --git a/src/smpi/smpi_pmpi.c b/src/smpi/smpi_pmpi.c index b42f6a623f..63e69db0f8 100644 --- a/src/smpi/smpi_pmpi.c +++ b/src/smpi/smpi_pmpi.c @@ -1362,7 +1362,6 @@ int PMPI_Sendrecv_replace(void *buf, int count, MPI_Datatype datatype, int PMPI_Test(MPI_Request * request, int *flag, MPI_Status * status) { int retval = 0; - smpi_bench_end(); if (request == NULL || flag == NULL) { retval = MPI_ERR_ARG; @@ -1371,7 +1370,19 @@ int PMPI_Test(MPI_Request * request, int *flag, MPI_Status * status) smpi_empty_status(status); retval = MPI_ERR_REQUEST; } else { +#ifdef HAVE_TRACING + int rank = request && (*request)->comm != MPI_COMM_NULL + ? smpi_process_index() + : -1; + + instr_extra_data extra = xbt_new0(s_instr_extra_data_t,1); + extra->type = TRACING_TEST; + TRACE_smpi_testing_in(rank, extra); +#endif *flag = smpi_mpi_test(request, status); +#ifdef HAVE_TRACING + TRACE_smpi_testing_out(rank); +#endif retval = MPI_SUCCESS; } smpi_bench_begin(); diff --git a/src/smpi/smpi_replay.c b/src/smpi/smpi_replay.c index 9e00ae97bd..df4f3f5b27 100644 --- a/src/smpi/smpi_replay.c +++ b/src/smpi/smpi_replay.c @@ -313,6 +313,35 @@ static void action_Irecv(const char *const *action) log_timed_action (action, clock); } +static void action_test(const char *const *action){ + double clock = smpi_process_simulated_elapsed(); + MPI_Request request; + MPI_Status status; + int flag = TRUE; + + request = xbt_dynar_pop_as(reqq[smpi_comm_rank(MPI_COMM_WORLD)],MPI_Request); + xbt_assert(request != NULL, "found null request in reqq"); + +#ifdef HAVE_TRACING + int rank = smpi_comm_rank(MPI_COMM_WORLD); + instr_extra_data extra = xbt_new0(s_instr_extra_data_t,1); + extra->type=TRACING_TEST; + TRACE_smpi_testing_in(rank, extra); +#endif + flag = smpi_mpi_test(&request, &status); + XBT_DEBUG("MPI_Test result: %d", flag); + /* push back request in dynar to be caught by a subsequent wait. if the test + * did succeed, the request is now NULL. + */ + xbt_dynar_push_as(reqq[smpi_comm_rank(MPI_COMM_WORLD)],MPI_Request, request); + +#ifdef HAVE_TRACING + TRACE_smpi_testing_out(rank); +#endif + + log_timed_action (action, clock); +} + static void action_wait(const char *const *action){ double clock = smpi_process_simulated_elapsed(); MPI_Request request; @@ -322,7 +351,14 @@ static void action_wait(const char *const *action){ "action wait not preceded by any irecv or isend: %s", xbt_str_join_array(action," ")); request = xbt_dynar_pop_as(reqq[smpi_comm_rank(MPI_COMM_WORLD)],MPI_Request); - xbt_assert(request != NULL, "found null request in reqq"); + + if (!request){ + /* Assuming that the trace is well formed, this mean the comm might have + * been caught by a MPI_test. Then just return. + */ + return; + } + #ifdef HAVE_TRACING int rank = request->comm != MPI_COMM_NULL ? smpi_comm_rank(request->comm) @@ -955,6 +991,7 @@ void smpi_replay_init(int *argc, char***argv){ xbt_replay_action_register("Isend", action_Isend); xbt_replay_action_register("recv", action_recv); xbt_replay_action_register("Irecv", action_Irecv); + xbt_replay_action_register("test", action_test); xbt_replay_action_register("wait", action_wait); xbt_replay_action_register("waitAll", action_waitall); xbt_replay_action_register("barrier", action_barrier); -- 2.20.1