Program w standardzie MPI

0

Witam wszystkich. Miałem ostatnio zaliczenie z oprogramowania klastrowego niestety nie poszło mi zbyt dobrze. Zadanie polegało na symulacji działania programu w C++ z wykorzystaniem MPI. Nigdy nie byłem dobry z C++ a do tego jeszcze to MPI... Niżej przedstawiam treść zadania i cały program:

Dla podanego niżej programu w standardzie MPI określić, symulując jego działanie, jaka liczba zostanie wyświetlona na ekranie jako wynik działania tego programu, jeżeli jako parametr -np w wywołaniu polecenia "mpirun" podano wartość równą 4 a 1 parametr wywołania programu 3.

#include<mpi.h>
#include<iostream>

using namespace std;
int main(int grac, char **argv)
{
int rank,size;
MPI_Status status;

MPI_Init(&grac,&argv);
MPI_Comm_rank(MPI_COMM_WORLD,&rank);
MPI_Comm_size(MPI_COMM_WORLD,&size);
int lewy=rank-1;
int prawy=rank+1;
int a=atoi(argv[1]);
int b=0;
if(rank==size-1) prawy=0;
if(rank==0) lewy=size-1;

for (int i=0;i<size;i++)
{
MPI_Send(&a,1,MPI_INT,lewy,99,MPI_COMM_WORLD);
a++;
MPI_Recv(&b,1,MPI_INT,prawy,99,MPI_COMM_WORLD,&status);
a-=2*b;
}

if(rank==1)
cout<<"wynik="<<a<<endl;

MPI_Finalize();
}

Chodzi o to, że nie wiem w jaki sposób przebiega komunikacja między komunikatorami a co za tym idzie jak po kolei program jest wykonywany.
Oczywiście sam wynik działania programu nie jest najważniejszy. Interesuje mnie w jaki sposób obliczyć wynik bez korzystania z kompilatora. Będę wdzięczny za wszelką pomoc.

pozdrawiam

0

procesy sa 4ty (mpirun, procesy:0123) ulozone sa w "tasme", sklejona koncami i komunikuja sie tylko z sasiadami, tzn:

( 3 < - ...)...-> 0 <-> 1 <-> 2 <-> 3 <-...(...-> 0)

kazdy proces startuje z dwiema liczbami:
a = 3 (parametr)
b = 0

po starcie i okresleniu kto jest czyim sasiadem, kazdy proces wykonuje N=4 (liczba procesow) razy:

  • wysylam do lewego moje A
  • A++
  • odbieram od prawego B
  • zmniejszam A o 2*B

innymi slowy, fazy wygladaja tak (kazda linijka w dol to chwila pozniej w czasie!):

faza 0 :        0[a=3, b=0]          1[a=3, b=0]          2[a=3, b=0]          3[a=3, b=0]
wysyl:    ..<- A                 ..<-A                ..<-A                ..<-A
A++:                A++       ...         A++      ...         A++      ...         A++
odbior:                  B<-..                B<-..                B<-..                B<-..
zmniejsz:         A-=2*B               A-=2*B               A-=2*B               A-=2*B
                                         
faza 1 :        0[a=-2, b=3]         1[a=-2, b=3]         2[a=-2, b=3]         3[a=-2, b=3]
wysyl:    ..<- A                 ..<-A                ..<-A                ..<-A
A++:                A++       ...         A++      ...         A++      ...         A++
odbior:                  B<-..                B<-..                B<-..                B<-..
zmniejsz:         A-=2*B               A-=2*B               A-=2*B               A-=2*B

faza 2 :        0[a=5, b=-2]          1[a=5, b=-2]        2[a=5, b=-2]        3[a=5, b=-2]
faza 3 :        0[a=10, b=-2]         1[a=10, b=-2]       2[a=10, b=-2]       3[a=10, b=-2]

edit: Marek - dzieki za podpowiedz co do formatowania;)

0

Dzięki wielkie. Nie łapie jeszcze jednego: jak zmienia się b i dlaczego w fazie 1 b=3?

0

dlatego, ze w kodzie jest wyrazny przykaz:

MPI_Send(   --->> &a <<---- ,1,MPI_INT,lewy,99,MPI_COMM_WORLD);
MPI_Recv(   --->> &b <<---- ,1,MPI_INT,prawy,99,MPI_COMM_WORLD,&status);

czyli kazdy proces wysyla A, a to co odbierze pakuje do B.. czyli jesli proces nr 1 wysle A=3, to proces nr 0 odbierze te trojke i wsadzi do B

ps. specjalnie w celu objasnienia tego robilem 'ukosne' strzaleczki: B <--- .. ... .. <-- A :)

0

Jeśli dobrze zrozumiałem to powinno to wyglądać w skrócie tak:

Faza 0 a=3 b=0 wysyła do lewego a=3
zwiększa a o 1 czyli a=4 odbiera od prawego b=3
zmniejsza a czyli a=4-2*3=-2

Faza 1 a=-2 b=3 wysyła do lewego a=-2
zwiększa a o 1 czyli a=-1 odbiera od prawego b=-2
zmniejsza a czyli a=-1-2*(-2)=3

Faza 2 a=3 b=-2 wysyła do lewego a=3
zwiększa a o 1 czyli a=4 odbiera od prawego b=3
zmniejsza a czyli a=4-2*3=-2

Faza 3 a=-2 b=3 wysyła do lewego a=-2
zwiększa a o 1 czyli a=-1 odbiera od prawego b=-2
zmniejsza a czyli a=-1-2*(-2)=3

wynik: a=3 b=-2
więc chyba walnąłeś się w liczeniu :)

0
radeon_231 napisał(a)

więc chyba walnąłeś się w liczeniu :)

tiaa.. rzeczywiscie, w fazie 1 nie wiem czemu policzylem jakby wysylalo sie -3 a nie -2

1 użytkowników online, w tym zalogowanych: 0, gości: 1