Difference between revisions of "Prova pratica 21 01 15"

From Sistemi Operativi
Jump to navigation Jump to search
 
(4 intermediate revisions by the same user not shown)
Line 21: Line 21:
 
#include <s2argv.h>
 
#include <s2argv.h>
 
#include <string.h>
 
#include <string.h>
 
+
 
int main(int argc, char *argv[]){
 
int main(int argc, char *argv[]){
 
int pfd[2];
 
int pfd[2];
Line 27: Line 27:
 
char cmd1[256];
 
char cmd1[256];
 
char cmd2[256];
 
char cmd2[256];
+
 
fgets(cmd1, sizeof(cmd1), file);//memorizzo il primo comando in cmd1
 
fgets(cmd1, sizeof(cmd1), file);//memorizzo il primo comando in cmd1
 
fgets(cmd2, sizeof(cmd2), file);//memorizzo il 2 comando in cmd2
 
fgets(cmd2, sizeof(cmd2), file);//memorizzo il 2 comando in cmd2
 
+
cmd1[strlen(cmd1)-2]='\0';//tronco la stringa eliminando l'EOL
 
cmd2[strlen(cmd2)-2]='\0';
 
 
 
pipe(pfd);//creo i 2 descrittori
 
pipe(pfd);//creo i 2 descrittori
+
 
switch(fork()){
 
switch(fork()){
 
case 0: //figlio fornisce output
 
case 0: //figlio fornisce output
Line 43: Line 40:
 
execsp(cmd1);  
 
execsp(cmd1);  
 
exit(1);
 
exit(1);
+
 
case -1: exit(1);
 
case -1: exit(1);
 
}
 
}
Line 53: Line 50:
 
execsp(cmd2);  
 
execsp(cmd2);  
 
exit(1);
 
exit(1);
+
 
case -1: exit(1);
 
case -1: exit(1);
 
}
 
}
 
int status;
 
int status;
 +
close(pfd[0]);
 +
close(pfd[1]);
 
wait(&status);
 
wait(&status);
 +
wait(&status);
 +
fclose(file);
 +
}
 +
</source>
 +
 +
 +
<source lang="text">
 +
Es 2: Il secondo esercizio estende il primo. Il file passato come parametro in questo caso ha un numero arbitario di righe e non solo due come nell'esercizio1.
 +
Ogni riga contiene un comando con I rispettivi parametri. Il programma deve attivare tutti I comandi del file in modo concorrente, e terminare quando tutti finiscono.
 +
L'output di tutti I comandi, tranne l'ultimo, deve essere fornito in input all'ultimo comando
 +
(quello nell'ultima riga significativa del file).
 +
 +
Es: se il file contenesse:
 +
ls -l
 +
ls -l
 +
ls -l
 +
cat
 +
l'output dovrebbe essere la lista dei file della corrente directory 3 volte (nell'output puo' capitare che righe di comandi diversi vengano frapposte, l'accesso alla pipe e' conteso).
 +
</source>
 +
 +
<source lang="c">#include <stdio.h>
 +
#include <stdio.h>
 +
#include <unistd.h>
 +
#include <stdlib.h>
 +
#include <fcntl.h>
 +
#include <s2argv.h>
 +
#include <string.h>
 +
 +
int main(int argc, char *argv[]){
 +
int pfd[2], num_righe=0, tmp=0;
 +
FILE *file=fopen(argv[1], "r");//apro file in lettura
 +
char buff[256];
 +
pipe(pfd);
 +
 +
while(fgets(buff, sizeof(buff), file)!=NULL){//calcolo il numero di righe del file
 +
num_righe++;
 +
}
 +
char comandi[num_righe][256];//array di stringhe
 +
rewind(file);
 +
 +
for(tmp=0; tmp<num_righe; tmp++){
 +
fgets(comandi[tmp], sizeof(comandi[tmp]), file);//copio ogni comando per riga
 +
//printf("comando num %d: %s\n", tmp, comandi[tmp]);
 +
switch(fork()){
 +
case 0:
 +
if(tmp<num_righe-1){
 +
dup2(pfd[1], STDOUT_FILENO);
 +
close(pfd[0]);
 +
close(pfd[1]);
 +
execsp(comandi[tmp]);
 +
exit(1);
 +
}
 +
if(tmp==num_righe-1){
 +
dup2(pfd[0], STDIN_FILENO);
 +
close(pfd[0]);
 +
close(pfd[1]);
 +
execsp(comandi[tmp]);
 +
exit(1);
 +
}
 +
case -1: exit(1);
 +
 +
}
 +
}
 +
int status;
 +
close(pfd[0]);
 +
close(pfd[1]);
 +
for(tmp=0; tmp<num_righe; tmp++)
 +
wait(&status);
 
fclose(file);
 
fclose(file);
 
}
 
}
 +
</source>
 +
 +
 +
<source lang="text">
 +
Esercizio 3: Script bash o Python:
 +
Scrivere un programma python o uno script bash che scandisca il sottoalbero relativo alle directory passate come parametri (o alla direcotry corrente se non ci sono parametri) e
 +
fornisca in output l'elenco dei file che hanno la stessa somma MD5 (i.e. l'output del comando md5sum).
 +
In output ogni riga deve mostrare un elenco di pathname realtivi a file che hanno la stessa somma MD5 (che quindi sono molto molto probabilmente uguali).
 +
</source>
 +
 +
<source lang="bash">
 +
#! /bin/bash
 +
trova () {
 +
  find $1 -type f -exec md5sum {} \; | sort > md5.txt #calcola l'md5 di tutto il sottoalbero, lo ordina e lo salva in un file
 +
  cat md5.txt | grep "`cut -d ' ' -f 1 md5.txt | uniq -d`" #stampa le righe del file, nelle quali in primo campo ha valore(md5) duplicato
 +
}
 +
 +
if [[ $# -eq 0 ]] ; then #se num argomenti è 0
 +
  trova
 +
else
 +
  for parametro in $* #chiamo la funzione per ogni argomento
 +
  do
 +
      trova $parametro
 +
  done
 +
fi
 +
exit
 
</source>
 
</source>

Latest revision as of 12:32, 3 April 2015

Es 1: scrivere un programma C di nome filepipe che abbia come unico parametro il pathname di un file di testo.
Questo file contiene due comandi con i rispettivi parametri, uno per riga.

Il programma deve mettere in esecuzione concorrente I due comandi in modo che l'output del primo venga fornito come input del secondo usando una pipe.
Il programma deve terminare quando entrambi i comandi sono terminati.
Esempio: se il file ffff contiene:
ls -l
tac
il comando:
filepipe ffff
deve restituire lo stesso output del comando:
ls -l | tac
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <fcntl.h>
#include <s2argv.h>
#include <string.h>
 
int main(int argc, char *argv[]){
	int pfd[2];
	FILE *file=fopen(argv[1], "r");//apro file in lettura
	char cmd1[256];
	char cmd2[256];
 
	fgets(cmd1, sizeof(cmd1), file);//memorizzo il primo comando in cmd1
	fgets(cmd2, sizeof(cmd2), file);//memorizzo il 2 comando in cmd2
 
	pipe(pfd);//creo i 2 descrittori
 
	switch(fork()){
		case 0:	//figlio fornisce output
			dup2(pfd[1], STDOUT_FILENO);
			close(pfd[0]);
			close(pfd[1]);
			execsp(cmd1); 
			exit(1);
 
		case -1: exit(1);
	}
	switch(fork()){//figlio prende input
		case 0:	
			dup2(pfd[0], STDIN_FILENO);
			close(pfd[0]);
			close(pfd[1]);
			execsp(cmd2); 
			exit(1);
 
		case -1: exit(1);
	}
	int status;
	close(pfd[0]);
	close(pfd[1]);
	wait(&status);
	wait(&status);
	fclose(file);
}


Es 2: Il secondo esercizio estende il primo. Il file passato come parametro in questo caso ha un numero arbitario di righe e non solo due come nell'esercizio1. 
Ogni riga contiene un comando con I rispettivi parametri. Il programma deve attivare tutti I comandi del file in modo concorrente, e terminare quando tutti finiscono.
L'output di tutti I comandi, tranne l'ultimo, deve essere fornito in input all'ultimo comando
(quello nell'ultima riga significativa del file).

Es: se il file contenesse:
ls -l
ls -l
ls -l
cat
l'output dovrebbe essere la lista dei file della corrente directory 3 volte (nell'output puo' capitare che righe di comandi diversi vengano frapposte, l'accesso alla pipe e' conteso).
#include <stdio.h>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <fcntl.h>
#include <s2argv.h>
#include <string.h>

int main(int argc, char *argv[]){
	int pfd[2], num_righe=0, tmp=0;
	FILE *file=fopen(argv[1], "r");//apro file in lettura
	char buff[256];
	pipe(pfd);
	
	while(fgets(buff, sizeof(buff), file)!=NULL){//calcolo il numero di righe del file
		num_righe++;
	}
	char comandi[num_righe][256];//array di stringhe
	rewind(file);
	
	for(tmp=0; tmp<num_righe; tmp++){
		fgets(comandi[tmp], sizeof(comandi[tmp]), file);//copio ogni comando per riga
		//printf("comando num %d: %s\n", tmp, comandi[tmp]);
		switch(fork()){
			case 0:	
				if(tmp<num_righe-1){
					dup2(pfd[1], STDOUT_FILENO);
					close(pfd[0]);
					close(pfd[1]);
					execsp(comandi[tmp]); 
					exit(1);
				}
				if(tmp==num_righe-1){
					dup2(pfd[0], STDIN_FILENO);
					close(pfd[0]);
					close(pfd[1]);
					execsp(comandi[tmp]); 
					exit(1);
				}
			case -1: exit(1);

		}
	}
	int status;
	close(pfd[0]);
	close(pfd[1]);
	for(tmp=0; tmp<num_righe; tmp++)
		wait(&status);
	fclose(file);
}


Esercizio 3: Script bash o Python:
Scrivere un programma python o uno script bash che scandisca il sottoalbero relativo alle directory passate come parametri (o alla direcotry corrente se non ci sono parametri) e
fornisca in output l'elenco dei file che hanno la stessa somma MD5 (i.e. l'output del comando md5sum). 
In output ogni riga deve mostrare un elenco di pathname realtivi a file che hanno la stessa somma MD5 (che quindi sono molto molto probabilmente uguali).
#! /bin/bash
trova () {
   find $1 -type f -exec md5sum {} \; | sort > md5.txt #calcola l'md5 di tutto il sottoalbero, lo ordina e lo salva in un file
   cat md5.txt | grep "`cut -d ' ' -f 1 md5.txt | uniq -d`" #stampa le righe del file, nelle quali in primo campo ha valore(md5) duplicato 
}

if [[ $# -eq 0 ]] ; then #se num argomenti è 0
   trova
else
   for parametro in $* #chiamo la funzione per ogni argomento
   do
      trova $parametro
   done
fi
exit