/* Serwer wspolbiezny oparty na kolejekach komunikatow. */ #include #include #include #include #include #include #include #include #include #include typedef struct mymesg1 { long mtype; pid_t pid; } paczka1; typedef struct mymesg2 { long mtype; double melement; } paczka2; int f; paczka1 *wiad; char *sciezka; int czy_skasowac = 1; void ala(int i) { if (i == SIGTERM || i == SIGINT) { printf("Serwer: Koniec pracy serwera.\n"); free(wiad); msgctl(f, IPC_RMID, NULL); if (czy_skasowac) { unlink(sciezka); } free(sciezka); exit(0); } } int main(int argc, char *argv[]) { pid_t pid; key_t klucz_kolejka; const size_t wielkosc1 = sizeof(paczka1) - sizeof(long); ssize_t liczba_bajtow; int plik = 0; signal(SIGTERM, ala); signal(SIGINT, ala); sigignore(SIGCHLD); if (argc > 1) { sciezka = strndup(argv[1], strlen(argv[1])); } else { sciezka = strndup("/tmp/roboczy.kolejka_serwer", strlen("/tmp/roboczy.kolejka_serwer")); } if (access(sciezka, F_OK) == 0) { czy_skasowac = 0; } if (czy_skasowac && ((plik = open(sciezka, O_CREAT | O_EXCL, 0600)) == -1)) { fprintf(stderr, "Serwer: Blad utworzenia pliku %s: %s.\n", sciezka, strerror(errno)); free(sciezka); return -1; } else { close(plik); if ((klucz_kolejka = ftok(sciezka, 1)) == -1) { perror("Serwer: Blad funkcji ftok.\n"); if (czy_skasowac) { unlink(sciezka); } free(sciezka); return -1; } else { if ((f = msgget(klucz_kolejka, 0600 | IPC_CREAT | IPC_EXCL)) == -1) { perror("Serwer: Blad funkcji msgget.\n"); if (czy_skasowac) { unlink(sciezka); } free(sciezka); return -1; } else { for (;;) { wiad = (paczka1 *)malloc(sizeof(paczka1)); if ((liczba_bajtow = msgrcv(f, wiad, wielkosc1, 1, 0)) == -1) { perror("Serwer: Blad funkcji msgrcv.\n"); if (czy_skasowac) { unlink(sciezka); } free(sciezka); return -1; } else { printf("Serwer: Przeczytalem %ld bajtow od klienta na glownej kolejce.\n", liczba_bajtow); if ((pid = fork()) == -1) { perror("Serwer: Wywolanie funkcji fork nie powiodlo sie.\n"); return -1; } else { if (pid == 0) { int f1; if ((klucz_kolejka = ftok(sciezka, wiad->pid)) == -1) { free(sciezka); perror("Serwer, proces potomny: Blad funkcji ftok.\n"); return -1; } else { if ((f1 = msgget(klucz_kolejka, 0600)) == -1) { perror("Serwer, proces potomny : Nie moge utworzyc kolejki komunikatow dla klienta.\n"); return -1; } else { paczka2 *praca = (paczka2 *)malloc(sizeof(paczka2)); const size_t wielkosc2 = sizeof(paczka2) - sizeof(long); if ((liczba_bajtow = msgrcv(f1, praca, wielkosc2, 2, 0)) == -1) { perror("Serwer, proces potomny: Blad funkcji msgrcv.\n"); return -1; } else { printf("Serwer, proces potomny: Przeczytalem %ld bajtow od klienta.\n", liczba_bajtow); praca->melement *= praca->melement; praca->mtype = 3; if ((liczba_bajtow = msgsnd(f1, praca, wielkosc2, 0)) == -1) { perror("Serwer, proces potomny: Blad funkcji msgsnd.\n"); return -1; } else { free(praca); return 0; } } } } } else { sigignore(SIGCHLD); } } } } } } } }