#include #include "mpi.h" int bcast_knary_segment_size; int knary = 2; int bcast_knary(void *buf,int count, MPI_Datatype datatype, int root, MPI_Comm comm) { int tag = 5000; MPI_Status status; MPI_Request req[10]; int rank; int i,j; int total_node; int target; MPI_Comm_rank(MPI_COMM_WORLD,&rank); MPI_Comm_size(MPI_COMM_WORLD,&total_node); int **send_to; int *recv_from; int *sequence; int bcast_knary_phase; //MALLOC recv_from = (int *) malloc (total_node * sizeof (int)); sequence = (int *) malloc (total_node * sizeof (int)); send_to = (int **) malloc (knary * sizeof (int *)); for (i=0;i= total_node) { break; } } level++; } // number of phase of this knary tree is equal to a level of the last node bcast_knary_phase = sequence[total_node-1]; // non-pipeline if (count <= bcast_knary_segment_size) { for (i=0;i= sequence[rank]) && (i < (pipe_length + sequence[rank]))) MPI_Send(buf+(bcast_knary_segment_size * (i-sequence[rank])),bcast_knary_segment_size,datatype,send_to[j][rank],tag,MPI_COMM_WORLD); } // receive if ((recv_from[rank] != -1) && (i >= (sequence[rank]-1)) && (i < pipe_length + sequence[rank] -1)) MPI_Recv(buf+(bcast_knary_segment_size*(i-sequence[rank]+1)),bcast_knary_segment_size,datatype,recv_from[rank],tag,MPI_COMM_WORLD,&status); } } // last message has smaller size than the rest else { count = bcast_knary_segment_size; for (i=0;i= sequence[rank]) && (i < (pipe_length + sequence[rank]))) { if (i == (pipe_length + sequence[rank] -1)) count = last_count; MPI_Send(buf+(bcast_knary_segment_size * (i-sequence[rank])),count,datatype,send_to[j][rank],tag,MPI_COMM_WORLD); } } // receive if ((recv_from[rank] != -1) && (i >= (sequence[rank]-1)) && (i < pipe_length + sequence[rank] -1)) { if (i == (pipe_length + sequence[rank] -2)) count = last_count; MPI_Recv(buf+(bcast_knary_segment_size*(i-sequence[rank]+1)),count,datatype,recv_from[rank],tag,MPI_COMM_WORLD,&status); } } } for (i=0;i