Advertisement
Vladpepe

Untitled

May 23rd, 2019
111
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 6.19 KB | None | 0 0
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <unistd.h>
  4. #include <fcntl.h>
  5. #include <sys/types.h>
  6. #include <sys/wait.h>
  7. #include <string.h>
  8. /*Esame 11 Luglio 2012*/
  9.  
  10. /*Tipo di Dato pipe*/
  11. typedef int pipe_t[2];
  12. /*Dichiarazione Esplicita Funzione Figlio*/
  13. int figlio(char *Fi,int indice);
  14.  
  15. /*Variabili Globali*/
  16. int K; /*Numero passato come ultimo Parametro*/
  17. int N; /*Numero di file passati come parametri*/
  18. int dim,retval;
  19. int pid;/*PID per creazione figli*/
  20. char Fout[256];/*Nome file creato dal padre*/
  21. int fdout;/*File decriptor file Fout*/
  22. char Media[12];/*Stringa contenente la scritta Equal-Sopra-Sotto Media*/
  23. char str[256];/*Stringa di appoggio per scrittura in stdout*/
  24. pipe_t *pfd_p;
  25. pipe_t *pfd_f;
  26. /*NOTA:Si utilizzano 2N pipe !!*/
  27. /*N pipe pfd_p per la comunicazione figli-padre*/
  28. /*N pipe pfd_f per la comunicazione padre-figli*/
  29.  
  30. int main(int argc,char **argv ){
  31.     /*Variabili Locali*/
  32.     int i,st;
  33.     long int cont_ch;/*Variabile long int per lettura da pipe pfd_f*/
  34.  
  35.     /*Controllo numero parametri*/
  36.     dim=argc-1;
  37.     if (dim<3){
  38.         snprintf(str,256,"USO scheletro F1 F2 FN M \n");
  39.         write(1,str,strlen(str));
  40.         return(1);
  41.     }
  42.  
  43.     /*Controllo sul numero K*/
  44.     K=atoi(argv[dim]);
  45.  
  46.     if (K <= 0){
  47.         snprintf(str,256,"Inserire K intero strettamente positivo \n");
  48.         write(1,str,strlen(str));
  49.         return(2);
  50.     }
  51.  
  52.     /*Creazione file Fout*/
  53.     snprintf(Fout,256,"output.%d",K);
  54.     fdout=creat(Fout,0644);
  55.     if (fdout<0){
  56.         snprintf(str,256,"Impossibile creare il file %s \n",Fout);
  57.         write(1,str,strlen(str));
  58.         return(3);
  59.     }
  60.  
  61.     /*Assegno Numero di figli*/
  62.     N=dim-1;
  63.     /*Allocazione dinamica pipe pfd_p*/
  64.     pfd_p=(pipe_t*)malloc(sizeof(pipe_t)*N);
  65.     if (pfd_p==NULL){
  66.         snprintf(str,100,"Errore allocazione pipe pfd_p \n ");
  67.         write(1,str,strlen(str));
  68.         return(4);
  69.     }
  70.     /*Creazione Pipe pfd_p*/
  71.     for (i=0;i<N;i++){
  72.         retval=pipe(pfd_p[i]);
  73.         if (retval!=0){
  74.             snprintf(str,100,"Errore nella creazione della pipe pfd_p %d \n ",i);
  75.             write(1,str,strlen(str));
  76.             return(5);
  77.         }
  78.  
  79.     }
  80.     /*Allocazione dinamica pipe pfd_f*/
  81.     pfd_f=(pipe_t*)malloc(sizeof(pipe_t)*N);
  82.     if (pfd_f==NULL){
  83.         snprintf(str,100,"Errore allocazione pipe pfd_f \n ");
  84.         write(1,str,strlen(str));
  85.         return(6);
  86.     }
  87.     /*Creazione Pipe pfd_f*/
  88.     for (i=0;i<N;i++){
  89.         retval=pipe(pfd_f[i]);
  90.         if (retval!=0){
  91.             snprintf(str,100,"Errore nella creazione della pipe pfd_f %d \n ",i);
  92.             write(1,str,strlen(str));
  93.             return(7);
  94.         }
  95.  
  96.     }
  97.     /*Creazione figli*/
  98.     for (i=0;i<N;i++){
  99.         pid=fork();
  100.         switch(pid){
  101.             case 0: /*Figlio*/
  102.                 return (figlio(argv[i+1],i));
  103.  
  104.             case -1:/*Errore*/
  105.                 snprintf(str,100,"Errore creazione figlio numero %d PID %d \n ",i,pid);
  106.                 write(1,str,strlen(str));
  107.                 return(8);
  108.         }
  109.  
  110.     }
  111.     /*Se arrivo qui sono il padre*/
  112.     /*Chiudo i lati delle pipe che il padre non usa*/
  113.     /*Il padre scrive solo sulle pipe pfd_p*/
  114.     /*Il padre legge solo dalle pipe pfd_f*/
  115.  
  116.     for (i=0;i<N;i++){
  117.         close(pfd_f[i][1]);
  118.         close(pfd_p[i][0]);
  119.     }
  120.     /*Per ogni figlio*/
  121.     for (i=0;i<N;i++){
  122.         /*Leggo il valore dalla pipe pfd_f*/
  123.         if (read(pfd_f[i][0],&cont_ch,sizeof(long int))!=sizeof(long int)) {
  124.             fprintf(stderr,"Impossibile leggere cont_ch\n");
  125.             abort();
  126.         }
  127.         if (cont_ch>K){
  128.             /*Preparo la stringa Sopra Media per il figlio */
  129.             snprintf(Media,12,"Sopra Media");
  130.         }
  131.  
  132.         if (cont_ch==K){
  133.             /*Preparo la stringa Equal Media per il figlio */
  134.             snprintf(Media,12,"Equal Media");
  135.         }
  136.         if (cont_ch<K){
  137.             /*Preparo la stringa Sotto Media per il figlio */
  138.             snprintf(Media,12,"Sotto Media");
  139.         }
  140.         /*Scrivo stringa al figlio su pfd_p[i]*/
  141.         write(pfd_p[i][1],Media,12);
  142.     }
  143.     /*Stampo i valori di uscita dei figli*/
  144.     for (i=0;i<N;i++){
  145.         /*Attendo i figli e stampo il valori di uscita*/
  146.         pid=wait(&st);
  147.         snprintf(str,256,"Figlio con PID %d RITORNA %d \n",pid,WEXITSTATUS(st));
  148.         write(1,str,strlen(str));
  149.     }
  150.  
  151.  
  152.     return(0);
  153.  
  154. }
  155.  
  156. int figlio(char *Fi,int indice){
  157. /*Ogni figlio e' associato a un file Fi*/
  158. /*Ogni figlio calcola la lunghezza del file Fi*/
  159. /*Comunica la lunghezza al processo padre su pfd_f[indice]*/
  160. /*Riceve la stringa comunicata dal padre su pfd_p[indice]*/
  161. /*Scrive la stringa su Fout*/
  162.  
  163. int i;/*Indice generico*/
  164. int fd;/*File descriptor file Fi*/
  165. char ch;/*Carattere di appoggio per lettura dal file Fi*/
  166. long int cont_ch;/*Contatore caratteri*/
  167. char temp[256];/*Buffer per scrittura su Fout*/
  168.  
  169. /*Stampa di Controllo*/
  170. snprintf(str,256,"Figlio INDICE %d FILE %s \n",indice,Fi);
  171. write(1,str,strlen(str));
  172. /*Chiusura lati pipe non utilizzati pfd_f*/
  173. /*Ogni figlio usa solo la pipe pfd_f[indice]*/
  174. for (i=0;i<N;i++){
  175.         if (i!=indice){
  176.                 close(pfd_f[i][0]);
  177.                 close(pfd_f[i][1]);
  178.         }
  179. }
  180.  
  181. /*Scrivo SOLO sulla mia pipe pfd_f*/
  182. close(pfd_f[indice][0]);
  183.  
  184. /*Chiusura lati pipe non utilizzati pfd_p*/
  185. /*Ogni figlio usa solo la pipe pfd_p[indice]*/
  186. for (i=0;i<N;i++){
  187.         if (i!=indice){
  188.                 close(pfd_p[i][0]);
  189.                 close(pfd_p[i][1]);
  190.         }
  191. }
  192.  
  193. /*Leggo SOLO dalla mia pipe pfd_p*/
  194. close(pfd_p[indice][1]);
  195.  
  196. /*Apertura file associato Fi*/
  197. fd=open(Fi,O_RDONLY);
  198. if (fd<0){
  199.         snprintf(str,256,"Figlio INDICE %d Impossibile aprire file %s \n",indice,Fi);
  200.         write(1,str,strlen(str));
  201. }
  202.  
  203. /*Inizializzo variabile contatore caratteri*/
  204. cont_ch=0;
  205. /*Scansione file fd per conteggio caratteri*/
  206. while(read(fd,&ch,1)>0){
  207.         /*Ho letto un carattere*/
  208.         /*Incremento contatore*/
  209.         cont_ch++;
  210. }
  211. /*oppure molto piu' semplicemente si poteva usare la funzione lseek*/
  212. /* cont_ch=lseed(fd, 0L, 2) */
  213. /*Comunico al padre la lunghezza in caratteri del file*/
  214. write(pfd_f[indice][1],&cont_ch,sizeof(long int));
  215. /*Attendo la stringa che mi scrive il padre*/
  216. if (read(pfd_p[indice][0],Media,12)!=12) {
  217.     fprintf(stderr,"Lettura invalida da pdf_d[%d][0]\n",indice);
  218.     exit(-1);
  219. }
  220. /*Scrivo sul file Fout stringa concatenata*/
  221. snprintf(temp,256,"%s %s\n",Fi,Media);
  222. write(fdout,&temp,strlen(temp));
  223. /*Controllo valore scritto dal padre su pipe pfd_p*/
  224. if(strcmp(Media,"Sopra Media")==0){
  225.         retval=2;
  226. }
  227.  
  228. if(strcmp(Media,"Sotto Media")==0){
  229.         retval=1;
  230. }
  231.  
  232. if(strcmp(Media,"Equal Media")==0){
  233.         retval=0;
  234. }
  235. /*Ritorno retval al padre*/
  236. return(retval);
  237.  
  238. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement