MPI_ERR_TRUNCATE: в эфире

У меня есть int, который я собираюсь транслировать из root (rank==(FIELD=0)).

int winner

if (rank == FIELD) {
    winner = something;
}

MPI_Barrier(MPI_COMM_WORLD);
MPI_Bcast(&winner, 1, MPI_INT, FIELD, MPI_COMM_WORLD);
MPI_Barrier(MPI_COMM_WORLD);
if (rank != FIELD) {
    cout << rank << " informed that winner is " << winner << endl;
}

Но, кажется, я получаю

[JM:6892] *** An error occurred in MPI_Bcast
[JM:6892] *** on communicator MPI_COMM_WORLD
[JM:6892] *** MPI_ERR_TRUNCATE: message truncated
[JM:6892] *** MPI_ERRORS_ARE_FATAL: your MPI job will now abort

Обнаружил, что могу увеличить размер буфера в Bcast

MPI_Bcast(&winner, NUMPROCS, MPI_INT, FIELD, MPI_COMM_WORLD);

Где NUMPROCS количество запущенных процессов. (на самом деле кажется, что мне просто нужно, чтобы это было 2). Затем он запускается, но выдает неожиданный результат...

1 informed that winner is 103
2 informed that winner is 103
3 informed that winner is 103
5 informed that winner is 103
4 informed that winner is 103

Когда я cout winner, должно быть -1


person Jiew Meng    schedule 08.11.2012    source источник
comment
У меня нет проблем с написанным кодом; как вы определяете ПОЛЕ? Можете ли вы опубликовать больше кода; и вы абсолютно уверены, что проблема именно в этой трансляции?   -  person Jonathan Dursi    schedule 08.11.2012
comment
@JonathanDursi, вот он gist.github.com/4039617   -  person Jiew Meng    schedule 08.11.2012
comment
Я надеюсь, что после трех правок моего ответа основная причина вашей проблемы теперь читабельна и понятна :)   -  person Hristo Iliev    schedule 08.11.2012


Ответы (1)


В вашем коде есть ошибка:

if (rank == FIELD) {
   // randomly place ball, then broadcast to players
   ballPos[0] = rand() % 128;
   ballPos[1] = rand() % 64;
   MPI_Bcast(ballPos, 2, MPI_INT, FIELD, MPI_COMM_WORLD);
}

Это очень распространенная ошибка. MPI_Bcast — это коллективная операция, и для завершения ее должны вызывать все процессы. Что происходит в вашем случае, так это то, что эта трансляция вызывается не всеми процессами в MPI_COMM_WORLD (а только корнем) и, следовательно, мешает следующей широковещательной операции, а именно той, что находится внутри цикла. Вторая широковещательная операция фактически получает сообщения, отправленные первой (два элемента int), в буфер только для одного int и, следовательно, сообщение об ошибке усечения. В Open MPI каждая широковещательная рассылка использует внутри одни и те же значения тега сообщения, и, следовательно, разные широковещательные рассылки могут мешать друг другу, если они не выдаются последовательно. Это соответствует (старому) стандарту MPI - в MPI-2.2 не может быть более одной невыполненной коллективной операции (в MPI-3.0 может быть несколько невыполненных неблокирующих коллективных операций). Вы должны переписать код как:

if (rank == FIELD) {
   // randomly place ball, then broadcast to players
   ballPos[0] = rand() % 128;
   ballPos[1] = rand() % 64;
}
MPI_Bcast(ballPos, 2, MPI_INT, FIELD, MPI_COMM_WORLD);
person Hristo Iliev    schedule 08.11.2012