+
+static void action_gatherv(const char *const *action) {
+ /*
+ The structure of the gatherv action for the rank 0 (total 4 processes)
+ is the following:
+ 0 gather 68 68 10 10 10 0 0 0
+
+ where:
+ 1) 68 is the sendcount
+ 2) 68 10 10 10 is the recvcounts
+ 3) 0 is the root node
+ 4) 0 is the send datatype id, see decode_datatype()
+ 5) 0 is the recv datatype id, see decode_datatype()
+ */
+
+ double clock = smpi_process_simulated_elapsed();
+ int comm_size = smpi_comm_size(MPI_COMM_WORLD);
+ CHECK_ACTION_PARAMS(action, comm_size+1, 2);
+ int send_size = parse_double(action[2]);
+ int *disps = xbt_new0(int, comm_size);
+ int *recvcounts = xbt_new0(int, comm_size);
+ int i=0,recv_sum=0;
+
+ MPI_Datatype MPI_CURRENT_TYPE2;
+ if(action[4+comm_size]) {
+ MPI_CURRENT_TYPE=decode_datatype(action[4+comm_size]);
+ MPI_CURRENT_TYPE2=decode_datatype(action[5+comm_size]);
+ } else {
+ MPI_CURRENT_TYPE=MPI_DEFAULT_TYPE;
+ MPI_CURRENT_TYPE2=MPI_DEFAULT_TYPE;
+ }
+ void *send = smpi_get_tmp_sendbuffer(send_size* smpi_datatype_size(MPI_CURRENT_TYPE));
+ void *recv = NULL;
+ for(i=0;i<comm_size;i++) {
+ recvcounts[i] = atoi(action[i+3]);
+ recv_sum=recv_sum+recvcounts[i];
+ disps[i] = 0;
+ }
+
+ int root=atoi(action[3+comm_size]);
+ int rank = smpi_comm_rank(MPI_COMM_WORLD);;
+
+ if(rank==root)
+ recv = smpi_get_tmp_recvbuffer(recv_sum* smpi_datatype_size(MPI_CURRENT_TYPE2));
+
+ instr_extra_data extra = xbt_new0(s_instr_extra_data_t,1);
+ extra->type = TRACING_GATHERV;
+ extra->send_size = send_size;
+ extra->recvcounts= xbt_malloc(comm_size*sizeof(int));
+ for(i=0; i< comm_size; i++)//copy data to avoid bad free
+ extra->recvcounts[i] = recvcounts[i];
+ extra->root = root;
+ extra->num_processes = comm_size;
+ extra->datatype1 = encode_datatype(MPI_CURRENT_TYPE, NULL);
+ extra->datatype2 = encode_datatype(MPI_CURRENT_TYPE2, NULL);
+
+ TRACE_smpi_collective_in(smpi_process_index(), root, __FUNCTION__, extra);
+
+ smpi_mpi_gatherv(send, send_size, MPI_CURRENT_TYPE,
+ recv, recvcounts, disps, MPI_CURRENT_TYPE2,
+ root, MPI_COMM_WORLD);
+
+ TRACE_smpi_collective_out(smpi_process_index(), -1, __FUNCTION__);
+ log_timed_action (action, clock);
+ xbt_free(recvcounts);
+ xbt_free(disps);
+}
+