Нужно дважды отправить сообщение MPI по какой-то причине

Я работал над проектом MPI, в котором все подчиненные устройства отправляют данные обратно на мастер. По какой-то причине мастер получит данные только в том случае, если я выполню две последовательные отправки подряд. Это очень странно, и я думаю, что это вызывает некоторые другие странные проблемы, которые я получаю. Есть идеи, что вызвало бы это? Я думаю, что первая отправка отправляет какие-то ненужные данные или что-то в этом роде. Посылки — это точно такая же строка кода.

РЕДАКТИРОВАТЬ: код ниже …

if (numProcs > 0)
MPI_Barrier( MPI_COMM_WORLD ) ; //only wait if there are other processes to wait for

if (rank != 0)
{
MPI_Send(handArray, 10, MPI_DOUBLE, 0, TAG_HAND, MPI_COMM_WORLD);
MPI_Send(handArray, 10, MPI_DOUBLE, 0, TAG_HAND, MPI_COMM_WORLD);
}
//8. After the main loop the master process receives and sums together the hand counts array
//   from each slave process.
else
{
int activeProcs = numProcs - 1;
getHandsFromSlaves( activeProcs, handArray );

Затем мастер приступает к печати некоторых данных …

Вот метод getHands FromSlaves. Обратите внимание, что я также пытался использовать для этого блокирующие вызовы с теми же проблемами.

void getHandsFromSlaves( int& activeCount, double handTotals[10] ){

static MPI_Request request;
static int msgBuff, recvFlag;
static double handBuff[10];
MPI_Status status;

while (activeCount > 0)
{
if( request )
{
// Already listening for a message

// Test to see if message has been received
MPI_Test( &request, &recvFlag, &status );
//cout << "TAG: " << status.MPI_TAG << " SOURCE: "<< status.MPI_SOURCE  << " ERROR: " << status.MPI_ERROR << endl;
if( recvFlag )
{
// Message received
if( status.MPI_TAG == TAG_HAND )
{
cout << "Hand Received!" << endl;

for(int m = 0; m < 10; ++m)
{
handTotals[m] += handBuff[m];
}

activeCount--;
}
else
{
//error report... what happened?
cout << "TAG: " << status.MPI_TAG << " SOURCE: "<< status.MPI_SOURCE  << " ERROR: " << status.MPI_ERROR << endl;
}

// Reset the request handle
request = 0;
}
}

if( !request && activeCount > 0 )
// Start listening again
MPI_Irecv(&handBuff, 10, MPI_DOUBLE, MPI_ANY_SOURCE, MPI_ANY_TAG, MPI_COMM_WORLD, &request);
}
}

0

Решение

Ну, вы, вероятно, пытаетесь обработать слишком много сообщений, потому что ваш request переменная не определена при вводе вашего getHandsFromSlaves() рутина. Так как на входе, request почти наверняка ненулевой, вы сразу попытаетесь MPI_Test за сообщение что-то, даже если вы не опубликовали Irecv,

На самом деле, здесь есть много действительно странных вещей в отрывке кода. Почему локальные переменные static? Почему бы вам реализовать свой напряженный MPI_Test() Вместо того, чтобы использовать MPI_Wait()? Почему вы используете неблокирующие приемы вообще, если между приемами не делаете ничего полезного? И действительно, если вы все равно просто суммируете все массивы, почему вы вообще делаете отдельные двухточечные приемы вместо того, чтобы делать MPI_Reduce()?

Следующий гораздо более короткий код, кажется, делает то, что вы пытаетесь сделать выше:

#include <stdio.h>
#include <mpi.h>int main (int argc, char **argv) {

int rank, numProcs;

MPI_Init(&argc, &argv);
MPI_Comm_rank(MPI_COMM_WORLD, &rank);
MPI_Comm_size(MPI_COMM_WORLD, &numProcs);
double handArray[10];
double handTotal[10];

for (int i=0; i<10; i++)
handArray[i] = rank + i;

if (rank == 0)  // Since apparently rank 0 doesn't do anything
{
for (int i=0; i<10; i++)
handArray[i] = 0;
}

MPI_Reduce(handArray, handTotal, 10, MPI_DOUBLE, MPI_SUM, 0, MPI_COMM_WORLD);

if (rank == 0) {
printf("Hand Totals= \n");
for (int i=0; i<10; i++)
printf(" %lf ", handTotal[i]);
printf("\n");
}

MPI_Finalize();
}
1

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]