Witam wszystkich,
Mam 3 procesy,pierwszy czyta linie ze stdin i wysyla je do drugiego procesu przez pipe. Drugi proces liczy liczbe znakow w linii i zapisuja ja do pliku.Trzeci proces odczytuje te liczbe z pliku i wypisuja ja na ekran. Dostem do pliku synchronizuje za pomoca semafów. Mój program nie do konca działa tak jak powinien tzn pierwsza linie czyta dobrze ale kiedy wpisuje kolejna zawiesza sie tzn:
na przyklad wpisuje:
aaa
3 // tu dziala dobrze
xx
//tutaj nic sie nie dzieje,nic nie wypisuje
mysle że problem jest z synchronizacja
Proszę o pomoc
Oto kod:
#include <sys/ipc.h>
#include <sys/msg.h>
#include <sys/sem.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <signal.h>
#define SEMNUMB 2
#define KEYNB 11 // numer unikalnego identyfikatora dla pliku (ftok)
int pid1, pid2, pid3, i;
union semun{
int val;
struct semid_ds *buf;
unsigned short int* array;
struct seminfo *__buf;
};
struct sembuf write_lock = { 0, -1, 0 };
struct sembuf write_unlock = { 0, 1, 0 };
struct sembuf read_lock = { 1, -1, 0 };
struct sembuf read_unlock = { 1, 1, 0 };
int semid; // semafor
typedef void (*sighandler_t)(int);
void sig_handler(int signum)
{
if(signum == 1)
{
kill(pid2, 9);
kill(pid3, 9);
kill(pid1, 9);
}
}
int main(int argc, char** argv) {
int fd[2];
char buf[PIPE_BUF];
FILE *test;
key_t semkey = ftok(".", KEYNB); // generowanie unikalnego klucza dla semafora
semid = semget(semkey, SEMNUMB, IPC_CREAT | 0666); // utworzenie semafora
union semun op;
op.val = 1; // zapis
semctl(semid, 0, SETVAL, op);
op.val = 0; // odczyt
semctl(semid, 1, SETVAL, op);
if (pipe(fd) < 0)
{
perror("blad przygotowywania lacza");
exit(EXIT_FAILURE);
}
for(i=1; i<64; i++)
{
sighandler_t f = signal(i, sig_handler);
}
pid1=fork(); // utworzenie pierwszego potomka
if (pid1!=0)
{
pid2=fork(); // utworzenie drugiego potomka
if (pid2!=0)
{
pid3=fork(); // utworzenie trzeciego potomka
if (pid3!=0)
{
//Zakonczenie procesu wywolującego
return 0;
}
else ///////// third child ////////////
{
int dlugosc=0;
semop(semid, &read_lock, 1);
test = fopen("kkk.txt","r");
fscanf(test,"%d",&dlugosc);
fclose(test);
semop(semid, &write_unlock, 1);
printf("%d",dlugosc);
}
}
else ////////// second child /////////
{
int dlugosc = 0;
close(fd[1]);
while((read(fd[0] , buf, PIPE_BUF)>0))
{
dlugosc = strlen(buf)-1;
semop(semid, &write_lock, 1);
test = fopen("kkk.txt","w");
fprintf(test,"%d",dlugosc);
fclose (test);
semop(semid, &read_unlock, 1);
}
printf("Brak danych - zakonczenie procesu odbierajacego\n");
close(fd[0]);
}
}
else ////////// First child /////////
{
close(fd[0]);
while (!feof(stdin))
{
fgets(buf, PIPE_BUF, stdin);
int dlugosc = strlen(buf)-1;
if (!feof(stdin) && dlugosc!=0) write(fd[1], buf, PIPE_BUF);
}
close(fd[1]);
printf("Zakonczenie procesu wysylajacego\n");
}
}