Prova teorica 2014.09.24
Jump to navigation
Jump to search
Testo: [1]
Esercizio c.1
/*
* Esercizio c.1: Scrivere un monitor vBB che realizzi un bounded buffer a dimensione variabile.
* Le procedure entry da implementare sono read, write e resize. Read e write hanno gli stessi parametri del BB ordinario.
* La funzione resize ha come parametro un numero intero positivo che rappresenta la nuova dimensione del buffer espressa in numero
* di elementi. Inizialmente il bounded buffer ha dimensione DEFAULTSIZE. Se la dimensione viene incrementata I processi
* eventualmente in attesa di scrivere devono poter inserire I loro elementi nel buffer fino a che e' consentito della nuova dimensione.
* Se la dimensione diminuisce, nuovi scrittori potranno inserire elementi nel buffer solo quando sara' possibile farlo in modo coerente
* con il nuovo numero massimo di elementi.
*/
#define DEFAULTSIZE
monitor vbb{
generic_type bb[];
int i, size;
conditions W, R;
void vbb(void){
bb = new generic_type[DEFAULTSIZE];
i = 0;
size = DEFAULTSIZE;
}
procedure entry void write(generic_type val){
if(i == size){ // Il buffer è completamente pieno
W.wait(); // Metto in attesa il processo
}
// Il buffer non è pieno, scrivo
bb[i] = val;
i++;
R.signal();
}
procedure entry generic_type read(void){
generic_type retval;
if(i == 0){ // Il buffer è vuoto
R.wait(); // Metto in attesa il processo
}
// Il buffer non è vuoto, leggo
i--;
retval = bb[i];
W.signal(); // Riattivo uno scrittore in coda
return retval;
}
procedure entry void resize(unsigned int n){
int old_size, j;
old_size = size;
size = n;
newbb = new generic_type[n];
if(n > old_size){ // Se la nuova dim. è maggiore di quella vecchia
int ndiff = n - old_size; // Numero di celle libere su cui scrivere
for(j = 0; j < old_size; j++) // Copia gli elementi di bb nel nuovo vettore
newbb[j] = bb[j];
bb = newbb;
for(j = 0; j < ndiff; j++) // allora più scrittori possono scrivere perchè vi sono celle libere
W.signal();
}
else{ // Se la nuova dim. è minore o uguale a quella vecchia
for(j = 0; j < n; j++) // Copia gli elementi di bb nel nuovo vettore
newbb[j] = bb[j];
bb = newbb;
if(i >= n){ // se il buffer è comunque completamente pieno
if(i > n)
i = n;
R.signal(); // allora un lettore può leggere
}
else{ // se il buffer non è ancora pieno
W.signal(); // allora uno scrittore può scrivere
}
}
}
}