Sistemi di Calcolo

Corso di Laurea in Ingegneria Informatica e Automatica

Home | Avvisi | Diario Lezioni | Esercitazioni | Esami | Materiale Didattico | Valutazioni Studenti | Lezioni di Camil Demetrescu |

Palestra L8: preparazione per l’esercitazione T8

Esercizio 1 (Somma word di un file)

Si vuole scrivere un programma che calcola la somma dei valori senza segno a 32 bit contenuti in un file, ignorando eventuali byte finali resto della divisione per 4, se la lunghezza del file in byte non è divisibile per 4. La lettura deve avvenire 4 byte alla volta.

La funzione deve essere incapsulata nel file E1-sum/e1.c in int sum(const char* filename, unsigned long *psum) che prende il nome di un file e l’indirizzo di una variabile dove scrivere il numero calcolato.

Una sessione di uso basata sul file e1_main.c fornito potrebbe essere:

E1-sum > gcc e1_main.c e1.c -o e1
E1-sum > ./e1
Sintassi: ./e1 filename
E1-sum > ./e1 README
Somma: 1D31E8B07E
E1-sum > 

Il codice è munito di soluzione in E1-sum/sol. Per generare sia la versione studente che quella corretta di riferimento si può usare make, dove E1-sum/e1 è la versione studente e E1-sum/e1-sol è quella docente.

Esercizio 2 (File casuale)

Lo scopo dell’esercizio è quello di scrivere file binari con la seguente struttura composti da numeri pseudo-casuali:

 0 |magic number|
 4 |   size     |
 8 |   rnd 1    |
12 |   rnd 2    |
16 |    ...     |

Il magic number deve essere 0xEFBEADDE per tutti i file generati con questo programma. I magic number sono codici associati ai tipi di file, specialmente se binari, per identificarli univocamente al momento dell’apertura, e sono disposti all’inizio del file. Il magic number è considerato a scopo di appredimento. SUbito dopo c’è il numero di valori casuali del file.

Si richiede di scrivere nel file E2-make-rnd-file/e2.c una funzione int make_rnd_file(int size, int seed, int mod, char *filename); con i seguenti parametri:

Compilare con e2_main.c e2-sol.c -o e2-sol (oppure usando make). Il programma genera il file a partire dai dati forniti da riga di comando. Ad esempio, per generare un file chiamato test.dat con 1000 valori pseudo-casuali inferiori a 10 con seme 5651 si digita:

> ./e2-sol test.dat 1000 10 5651
Risultato: 1/1

Si consiglia di esplorare anche il file creato anche con il programma xxd:

> xxd test.dat | head
00000000: dead beef e803 0000 0700 0000 0800 0000  ................
00000010: 0000 0000 0100 0000 0000 0000 0300 0000  ................
00000020: 0900 0000 0600 0000 0700 0000 0200 0000  ................
00000030: 0100 0000 0000 0000 0700 0000 0700 0000  ................
00000040: 0300 0000 0200 0000 0300 0000 0800 0000  ................
00000050: 0800 0000 0300 0000 0000 0000 0900 0000  ................
00000060: 0300 0000 0800 0000 0300 0000 0400 0000  ................
00000070: 0600 0000 0300 0000 0600 0000 0100 0000  ................
00000080: 0900 0000 0700 0000 0100 0000 0100 0000  ................
00000090: 0700 0000 0500 0000 0400 0000 0100 0000  ................

Si noti che letto in little-endian il magic code 0xEFBEADDE è dead beef, la mascotte esadecimale del corso. Si noti inoltre che i successivi 2 byte sono e803 che, essendo riportati nel file in formato little-endian rappresentano 0x03e8, cioè 1000 in base 10.

Esercizio 3 - (Somma file ottimizzata)

Ottimizzare la soluzione dell’esercizon T1 leggendo a blocchi di 4KB e non a word di 32 bit.

P8> cd E3-sum-opt
P8/E3-sum-opt> dd if=/dev/random of=file.txt count=8192 bs=4096    <---- crea file di 8192*4096 ~ 34KB random
P8/E3-sum-opt> time ./e3 file.txt                                  <---- misura tempo versione ottimizzata (E3)
P8/E3-sum-opt> time ../E1-sum/e1 ../E1-sum/file.txt                <---- misura tempo versione originaria (E1)
Esercizio 4 - (Uguaglianza di file)

Scrivere nel file E4-file-eq/e4.c una funzione int file_eq(char* f1, char* f2) che, dati i percorsi di due file f1 e f2, restituisce zero se i file sono uguali, un valore maggiore di zero se i file sono diversi, e -1 in caso di errore.

Codice e soluzioni