Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /**
- [dawid@freeone ~/silnia]$ cat kompiluj.sh
- #!/bin/sh
- DIR="/home/dawid/silnia"
- WORKER="silnia_worker"
- MASTER="silnia"
- echo "Kompiluje"
- /usr/local/bin/gcc47 -lpvm3 "$DIR/$MASTER.c" -o "$DIR/$MASTER"
- /usr/local/bin/gcc47 -lpvm3 "$DIR/$WORKER.c" -o "$DIR/$WORKER"
- echo "Kopiowanie do freetwo.com"
- scp "$DIR/$WORKER" [email protected]:$DIR
- echo "Kopiowanie do freethree.com"
- scp "$DIR/$WORKER" [email protected]:$DIR
- */
- /***
- * [dawid@freeone ~/silnia]$ cat config.h
- */
- // n zostawiam na 99 bo to i tak za duzo a pvm nie obsluguje jako tako unsigned long long - jest tyko unsigned long
- #define N 20
- #define FLAGA_ROZPOZNAWCZA_WORKERA 1111
- #define FLAGA_ROZPOZNAWCZA_MASTERA 999
- #define WORKER_PATH "/home/dawid/silnia/silnia_worker"
- // zatem nasz typ dla talibcy z silniami jest taki: ulong
- typedef unsigned long ulong;
- /***
- * [dawid@freeone ~/silnia]$ cat silnia.c
- *
- * Master
- * Dawid Mocek
- *
- *
- */
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <pvm3.h>
- #include <sys/unistd.h>
- #include <limits.h>
- #include "config.h"
- int *podziel_na_czesci(int liczba_elementow, int liczba_hostow) {
- int i, j, k, *tab = NULL;
- tab = (int *)calloc(liczba_hostow, sizeof(int));
- // tu mamy po rowno elementow
- if ((liczba_elementow % liczba_hostow) == 0) {
- k = (liczba_elementow / liczba_hostow);
- for (i = 0; i < liczba_hostow; ++i)
- tab[i] = k;
- }
- // a tu nie
- else {
- k = liczba_elementow / liczba_hostow;
- for (i = 0; i < liczba_hostow ; ++i)
- tab[i] = k;
- tab[i - 1] += liczba_elementow - (k * liczba_hostow);
- }
- return tab;
- }
- int main(void) {
- int ilhost, ilarch, mytid, indeks, id_procesu, i, j, len, pvm_res, bytes, msgtag;
- ulong silnia;
- int *nasze_procesy = NULL;
- int *ilosc = NULL;
- struct pvmhostinfo *info = NULL;
- char hostname[128];
- // Tablica z liczbami = unsgined long
- ulong *liczby = NULL;
- liczby = (ulong *)calloc(N, sizeof(ulong));
- // Wypelniamy tablice
- for(i = 0; i < N; i++)
- liczby[i] = i;
- // Dla wiedzy skad gdzie co leci
- gethostname(hostname, sizeof hostname);
- // PVM
- mytid = pvm_mytid();
- // Dla debugu - lapiemy co rzygajaja spawn'owane procesy
- pvm_catchout(stdout);
- // Pobieram konfig. pvma - najwazniesza stad to ilosc hostow(ILe HOSTow) i struct info
- pvm_config(&ilhost, &ilarch, &info);
- // Musimy rozlozyc ilosc liczb jakie wysylamy w zaleznosci od ilosc hostow(bo kazdy host ma tylko 1 proces)
- ilosc = podziel_na_czesci(N, ilhost);
- // Tu trzymamy id procesow
- nasze_procesy = (int *)calloc(ilhost, sizeof(int));
- indeks = 0;
- for(i = 0; i < ilhost; i++) {
- // Spawn`ujemy proces na remote hoscie
- printf("[%s] Spawnuje proces na hoscie: %s\n", hostname, info[i].hi_name);
- pvm_spawn(WORKER_PATH, (char **)0, PvmTaskHost, info[i].hi_name, 1, &id_procesu);
- // Zapamietuje id procesu
- printf("[%s] Numer procesu: %d @ %s\n", hostname, id_procesu, info[i].hi_name);
- nasze_procesy[i] = id_procesu;
- // Przygotowujemy sie do wysylki danych
- pvm_initsend(PvmDataDefault);
- printf("[%s] Iteracja = %d. Wysylam liczb = %d\n", hostname, i, ilosc[i]);
- // Nasz worker musi wiedziec ile pakietow do niego dojdzie
- pvm_pkint(&ilosc[i], 1, 1);
- printf("[%s] Pakuje ilosc: %d\n", hostname, ilosc[i]);
- for(j = 0; j < ilosc[i]; indeks++, j++) {
- // Pakuje indeks tablicy *liczby
- pvm_pkint(&indeks, 1, 1);
- // Pakuje liczbe - to jej liczmy silnie
- pvm_pkulong(&liczby[indeks], 1, 1); // mozemy pakwoac unsigned long bo taak funk. jest dostepna w pvm
- // unsigned long printjumey za pomoca %lu:
- printf("[%s] Pakuje liczbe: '%lu' z pod indeksu: %d\n", hostname, liczby[indeks], indeks);
- }
- // Wysylam
- pvm_send(id_procesu, FLAGA_ROZPOZNAWCZA_MASTERA);
- }
- // koniec wysylania
- // teraz czas to odebrac
- // Czekamy na rezultaty
- printf("[%s] Odbieram dane...\n", hostname);
- for(i = 0; i < N; i++) {
- // Pobieram
- pvm_res = pvm_recv(-1, -1);
- // Informacje skad odebralismy i ile
- pvm_bufinfo(pvm_res, &bytes, &msgtag, &id_procesu);
- // Sam worker musi nam opdowiedziec dwoma pakietami - indeksem i wynikiem
- printf("[%s] Dostalem bajtow: %d od procesu: %d z tagiem %d\n", hostname, bytes, id_procesu, msgtag);
- // Wypakowuje indeks:
- pvm_upkint(&indeks, 1, 1);
- // Wypakowuje wygenerowa silnie
- pvm_upkulong(&silnia, 1, 1);
- // Zapisuje
- liczby[indeks] = silnia;
- // zabijam proces
- pvm_kill(id_procesu);
- }
- // Druk wyniku
- printf("--------------------\n");
- for(j = 0; j < N; ++j)
- printf("Silnia dla '%d' = '%lu'\n", j, liczby[j]);
- free(nasze_procesy);
- free(info);
- free(ilosc);
- free(liczby);
- pvm_exit();
- }
- /**
- * [dawid@freeone ~/silnia]$ cat silnia_worker.c
- */
- #include <stdlib.h>
- #include <stdio.h>
- #include <string.h>
- #include <sys/unistd.h>
- #include <pvm3.h>
- #include "config.h"
- ulong factorial(int);
- // silnia
- ulong factorial(int liczba) {
- int c;
- ulong wynik = 1;
- for(c = 1; c <= liczba; c++)
- wynik *= c;
- return wynik;
- }
- int main(void) {
- int mytid;
- int i, j, cnt;
- ulong silnia, liczba;
- int indeks, master, pvm_res;
- char hostname[128];
- gethostname(hostname, sizeof hostname);
- // Ja
- mytid = pvm_mytid();
- // Odbieramy dane
- pvm_recv(-1, -1);
- // Ilosc pakietow
- pvm_upkint(&cnt,1 ,1);
- printf("[%s][%d] Dostalem pakietow %d.\n", hostname, mytid, cnt);
- for(j = 0; j < cnt; j++) {
- // Wypakowuje indeks
- pvm_upkint(&indeks, 1, 1);
- // Wypakowuje liczbe
- pvm_upkulong(&liczba, 1, 1);
- printf("[%s][%d] Dostalem liczbe: '%lu' z pod indeksu: %d\n", hostname, mytid, liczba, indeks);
- // Licze silnie
- silnia = factorial(liczba);
- // Master
- master = pvm_parent();
- pvm_initsend(PvmDataDefault);
- // Pakuje indeks
- pvm_pkint(&indeks, 1, 1);
- // Pakuje silnie
- pvm_pkulong(&silnia, 1, 1);
- // Wysylam
- pvm_res = pvm_send(master, FLAGA_ROZPOZNAWCZA_WORKERA);
- }
- pvm_exit();
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement