Prova pratica 2014.09.25

From Sistemi Operativi
Revision as of 17:53, 30 April 2017 by LeonardoF (talk | contribs)
Jump to navigation Jump to search

Testo: [1]

Esercizio 2

//ESERCIZIO 2
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "execs.h"  //https://github.com/rd235/s2argv-execs
#include <fcntl.h>

#define AOI_LENSTEP 8
#define BUFFLEN  256


struct array_of_integers {
    int **integers;
    size_t currentlength; //the length of number of integers in memory
    size_t arraylength; //the length of memory allocated
};
 
typedef struct array_of_integers array_of_integers;
 
void array_of_integers_add(array_of_integers *arrayOfIntegers, int val) {
   
    if (arrayOfIntegers->currentlength >= arrayOfIntegers->arraylength) {
        size_t newlength = arrayOfIntegers->arraylength + AOI_LENSTEP;
         int **new_vec = realloc(arrayOfIntegers->integers, newlength * sizeof(arrayOfIntegers->integers[0]));

        if (new_vec != NULL) {
            arrayOfIntegers->arraylength = newlength;
            arrayOfIntegers->integers = new_vec;
        }
    }
    if (arrayOfIntegers->currentlength < arrayOfIntegers->arraylength)  
        arrayOfIntegers->integers[arrayOfIntegers->currentlength] = malloc(sizeof(int));
        *(arrayOfIntegers->integers[arrayOfIntegers->currentlength++]) = val;


}
 
void array_of_integers_print(array_of_integers *v) {
    size_t i;
    for (i = 0; i < v->currentlength; i++)
        printf("[%3lu]: %d\n", i, *(v->integers[i]));
}


int main(int argc, char *argv[]) {
	/*opening and reading the file*/
    char* line = NULL;
    size_t lineLength = 0;
	ssize_t numberOfCharactersRead;
  

    FILE* fd1 = fopen(argv[1],"r");

    static array_of_integers arrayOfPid;
    static array_of_integers arrayOfFd;
    int fd; //file descriptor
    int i = 0; //iterator
    char concat[BUFFLEN];

    while ((numberOfCharactersRead = getline(&line, &lineLength, fd1)) >= 0) {
        if (line[numberOfCharactersRead - 1] == '\n')
            line[numberOfCharactersRead - 1] = 0;
       
 	///
 	/*done*/
 	/* opening output files, forking , saving pids and file descriptors*/
    sprintf(concat,"./temp%d",i);
    fd = open(concat,O_RDWR | O_CREAT | O_TRUNC , 0666);

 	int pid = fork();
 	switch(pid){
 		case 0: //children
                        //children stdio = file fd
                        dup2(fd,STDOUT_FILENO);
			//execution of the command
			execsp(line);
 		        exit(-1); // in case of execsp failure
 		default: //parent 
                         //must save all the pids
                         array_of_integers_add(&arrayOfPid,pid);
                         //must save all the fds. ( they will have the same order of the pids);
                         array_of_integers_add(&arrayOfFd,fd); 
 			
                         i ++;
 			 break;
 			}
 		
 	}
    free(line);
    /*done*/
    
    /*waiting first process and killing the others*/
    int firstpid;
    size_t j; //iterator
    size_t firstpid_pos; //position of the first pid in the array
    //wait the first process
    firstpid = wait(NULL);
 
    /*sigterm the other processes iterating the pids vector*/
    for (j = 0; j < (&arrayOfPid)->currentlength; j++){
        int temp = *((&arrayOfPid)->integers[j]);

        if(temp != firstpid)
            kill( temp,SIGTERM);
        else 
        	firstpid_pos = j ;
    }
    /*done*/

    /*printing the file of the "fisrt pid" process , unlinking the file and closing them*/
    for (j = 0; j < (&arrayOfFd)->currentlength; j++){
    	 fd = *((&arrayOfFd)->integers[j]);
    
    	sprintf(concat,"./temp%lu",j);

    	if (j == firstpid_pos){
    		int c;
    		//lseek is needed because the file is inherited
    		lseek(fd,0,SEEK_SET);
    		
    		FILE *fdp = fdopen(fd,"r");
    		while ((c = getc(fdp)) != EOF)
        		putchar(c);
    	}   	
    	//unlink file fd
    	unlink(concat);
    	//close file fd
    	close(fd);
    }
    /*done*/
    return 0;
}

--LeonardoF (talk) 11:33, 26 April 2017 (CEST)LeonardoF