Estratto del documento

Paradigmi concorrenti

Lezione 1

Sistema concorrente

Sistema concorrente, caratteristiche:

  • Competizione per l’accesso a risorse condivise.
  • Cooperazione per uno scopo comune.
  • Coordinamento di attività diverse.
  • Sincronia (c’è un cronometro comune) / asincronia (no cronometro comune).

Sistema sequenziale: esegue un’azione alla volta.

Proprietà dei programmi concorrenti

  • Safety: nulla di male potrà accadere (mai nessun processo sarà contemporaneamente nella stessa sezione critica).
  • Liveness: qualcosa di buono prima o poi accadrà (prima o poi raggiungeremo uno stato desiderabile).
  • Deadlock: situazione di blocco (processi in esecuzione bloccati, in attesa che un altro compia una certa azione).
  • Livelock: ci possono essere dei processi bloccati, ma il sistema non è fermo; i processi cambiano continuamente di stato senza mai progredire realmente nell’elaborazione.
  • Starvation: un processo pronto non viene mai eseguito.

Proprietà invarianti: proprietà vere costantemente.

Modello: rappresentazione semplificata della realtà; astrazione dei dettagli non rilevanti.

Notazione formale => tecniche e strumenti di analisi.

Thread: flusso (sequenziale) di controllo, processo sequenziale.

Programmi multithread: composti da più flussi di controllo paralleli.

Java Virtual Machine: programma multithreaded.

Ciclo di vita di un thread

Ciclo di vita di un thread: 1 – start BORN 2 – dispatch 1 3 – quantum expiration READY yield 6 10 interrupt 8 4 – complete 2 3 WAITING SLEEPING BLOCKED 5 – wait 6 - notify 7 9 5 notify All RUNNING 7 – sleep 4 8 – sleep interval expires DEAD 9 – issue I/O 1 10 – I/O completion.

Automi a stati finiti

Automi a stati finiti = sistemi di transizioni.

A = (S, E, T, s0)

S = insieme di stati.

E = insieme delle etichette (nomi di azioni).

T = insieme delle transizioni di stato.

T ⊆ S x E x S.

Stato di partenza, stato d’arrivo.

s0 ∈ S = stato iniziale.

0 1 a b c 2 d 3 5 b a 4 b a d b c.

Tracce di esecuzione: 1 5.

Un processo ha uno stato (che determina quali operazioni sono eseguibili) ed esegue delle operazioni (che determinano il comportamento di un processo).

Processi sequenziali

Rappresentati come Automi a stati finiti.

LTS (Labelled Transition Systems).

Stato “globale”.

Azione atomica.

Transizione di stato.

Es.: la lampadina accendi 0 = spento 0 1 1 = acceso spegni.

Es.: una lampadina che può guastarsi 0 = spento accendi guasto 1 = acceso 0 1 2 2 = guasto (si guasta solo quando la lampadina è accesa) spegni.

FSP (Finite State Processes): un linguaggio per specificare processi sequenziali e sistemi di processi sequenziali interagenti.

Elementi principali di FSP per la specifica dei processi:

  • Alfabeto: insieme delle azioni atomiche che un processo può eseguire o alle quali “partecipa”.
  • Strutture di controllo: operatori che esprimono il comportamento di un processo.
  • Sequenza (action prefix) a -> P.
  • Selezione (scelta non deterministica) | 2.
  • Ricorsione (solo in coda: iterazione).
  • STOP, ERROR => sono processi.
  • Composizione parallela ||.

Es.: le lampadine.

L = (accendi -> (spegni -> L)).

L è il nome del processo. La lampadina può eseguire solo l’azione “accendi”; in seguito può eseguire “spegni”, poi può comportarsi come all’inizio.

LG = (accendi -> LA), chiamata di processo.

LA = (spegni -> LG | guasto -> STOP).

Lezione 2

Finite state processes (FSP)

Action prefix a -> P.

Scelta a -> P | b -> Q.

Ricorsione (il processo esegue a, poi b, e poi ricomincia).

P = (a -> b -> P).

STOP, ERROR.

STOP corrisponde alla terminazione per stato finale di un’esecuzione corretta; ERROR corrisponde alla terminazione di un’esecuzione errata.

Es.: P = (a -> (b -> (c -> STOP ))).

P = (a -> STOP | b -> STOP).

P = (a -> Q), ricorsione indiretta.

Q = (b -> P).

Composizione parallela

Composizione parallela: ||S = (P || Q).

Es.: lampadina.

L = (accendi -> spegni -> L).

La = (acA -> spA -> La).

Lb = (acB -> spB -> Lb).

||S = (La || Lb).

L La Lb accendi acA acB 0 0 1 0 1 1 spegni spA spB.

Per costruire ||S devo operare con il prodotto fra stati di La e Lb.

2.

Quanti stati ha ||S? La e Lb hanno 2 stati, quindi 22 = 4 stati.

acA 0 0 1 0 spA acB spB spB acB acA 1 1 0 1 spA.

Alfabeto = insieme di tutti i nomi delle azioni che compaiono nella specifica del processo.

Alfabeto(La) = {acA, spA}.

Alfabeto(Lb) = {acB, spB}.

Alfabeto(S) = {acA, spA, acB, spB}.

Azioni locali = azioni che un processo compie da solo.

Es.: comportamento di due bambini.

A = (compitiA -> gioco -> dormeA -> A). compitiA.

B = (compitiB -> gioco -> dormeB -> B). 0 1.

||S = (A || B). gioco dormeA 2 compitiA 0 0 1 0 dormeB dormeA compitiB compitiB compitiA dormeB 0 1 1 1 1 2 dormeA 2 1 gioco compitiA compitiB 2 0 2 2 0 2 dormeB dormeA.

Es.: P = (a -> b -> c -> STOP).

Q = (d -> b -> e -> STOP).

||S = (P || Q). a b c 0 1 2 3 d e b 0 1 2 3.

3.

||S = 2 processi, 3 stati, quindi 23 = 8 stati.

a c 0 0 1 0 2 2 3 2 b e e d d 0 1 1 1 2 3 3 3 a c.

Thread in Java

THREAD -> è una classe “attiva”, quindi in Java si traduce in un thread.

La = (acA -> spA -> La).

Lb = (acB -> spB -> Lb).

||S = (La || Lb).

public class La extends Thread {
private boolean accesa;
private int id;
public La(int id) {
this.id = id;
accesa = false;
}
private void acA() { private -> perché è un metodo eseguito solo all’interno di questa classe
accesa = true;
System.out.println(id + “ accesa”);
}
public void run() { -> cosa fa il thread una volta invocato
while(true) {
acA(); ciclo infinito
spA();
}
}
}

public static void main(String[] args) {
La lamp = new La(1);
lamp.start(); run -> provoca la chiamata del metodo e si interrompe immediatamente
}

main che crea 2 lampadine:

La lamp_1 = new La(1);

La lamp_2 = new La(2);

lamp_1.start(); lamp_1, -> viene avviato il thread corrispondente all’oggetto il secondo.

lamp_2.start(); lamp_2 oggetto però non aspetta che l’altro finisca la sua esecuzione, quindi andranno contemporaneamente.

Se prima (con una sola lampadina) l’output era:

accesa, spenta, accesa, spenta, …

ora l’esecuzione contemporanea è:

accesa, accesa, spenta, spenta, accesa, spenta, accesa, …

(gli stati si mischiano, e non sempre in modo omogeneo).

Lezione 3

Es.: Due tornelli ogni volta che passa un visitatore girano e incrementano una variabile.

T = (rileva -> inc -> T).

V = (inc -> stampa -> V).

||A = (a:T || b:T).

a, b = identificatori; “:” è un operatore che trasforma un processo, quindi si ottiene:

T = (a.rileva -> a.inc -> a.T)

a.rileva 0 0 1 0 a.inc b.rileva b.inc b.inc b.rileva a.rileva 0 1 1 1 a.inc.

V = (a.inc -> stampa -> V | b.inc -> stampa -> V).

a.inc a.inc 0 1 b.inc stampa 0 1 b.inc stampa stampa 2.

||S = (A || V).

||S = (a:T || b:T || V).

Nell’implementazione in Java, per ogni processo distinto nel modello ci sarà una classe.

Ogni azione si traduce in metodo.

public class Tornello extends Thread {
private Var var;
private int id;
public Tornello(int id) {
this.id = id;
}
public void rileva() {
System.out.println(“Rilevata una persona”);
}
public void run() {
while(true) {
rileva();
Var.inc(id);
}
}
}

public class Var {
private int valore;
Object lock = new Object();
public Var() { valore = 0; }
synchronized(lock) interferenza -> si utilizza
public void inc(int id) {
synchronized(lock) { per regolare l’accesso a una sezione critica
valore = valore+1;
System.out.println(id + “ “ + valore);
}
}
}

si può scrivere anche:

public synchronized void inc(…){ … }

public static void main(String[] args) {
Var v = new Var();
Tornello a = new Tornello(1);
Tornello b = new Tornello(2);
a.start();
b.start();
}

Lezione 4

Produttore – Consumatore

Es.: Produttore – Consumatore.

3 processi:

  • Processo Produttore (produce risorse e le deposita nel buffer).
  • Processo Consumatore (preleva le risorse dal buffer e le elabora).
  • Processo Buffer (riceve risorse dal produttore e le dà al consumatore, coordina le azioni).

P = (produce -> deposita -> P).

C = (preleva -> elabora -> C).

B = (deposita -> preleva -> B).

||S = (P || C || B). produce produce deposita preleva B.

Bvuoto = (deposita -> Bpieno), Bpieno = (preleva -> Bvuoto).

Bisogna stabilire le condizioni per la quale il buffer esegue “deposita” o “preleva” in base al suo stato:

B[0] = buffer vuoto, B[1] = buffer pieno -> stato iniziale del processo.

B = B[0],

B[i:0..1] = ( when i == 0 deposita -> B[1] | when i == 1 preleva -> B[0] ).

guardia = indica quando l’azione può essere svolta.

nuovo valore del parametro.

i = nome del parametro; 0..1 = possibili valori del parametro.

Produttore e Consumatore sono due processi “attivi”, quindi in Java si tradurranno in thread; Buffer invece è un processo “passivo” (le azioni che contiene infatti appartengono a Produttore e Consumatore), quindi non è un thread.

public class Produttore extends Thread {
private Buffer buffer;
private Object item;
private Object produce() { … }
public void run() {
while(true) {
item = produce();
buffer.deposita(item);
}
}
}

public class Consumatore extends Thread {
private Buffer buffer;
private Object item;
private void elabora(Object item) { … }
public void run() {
while(true) {
item = buffer.preleva();
elabora(item);
}
}
}

public class Buffer {
private Object item;
private boolean pieno = false;
synchronized(lock) {
wait(); Il thread che sta eseguendo queste azioni viene sospeso.
}
Uno dei thread sospesi sull’oggetto lock si “risveglia”, synchronized(lock) { lock diventa pronto.
notify() notifyAll() invece risveglia tutti i thread sospesi.
}

public void deposita(Object x) {
synchronized(this) {
if(pieno) condizione per la quale non si possono più depositare
wait(); oggetti (dovranno rimanere in attesa finché non si libera
item = x; spazio nel buffer)
pieno = true;
notify(); si risveglia un processo in attesa
}
}

public Object preleva() {
synchronized(this) {
if(!pieno)
wait();
pieno = false;
notify();
return item;
}
}
}

Lezione 5

Posteggio con numero di posti limitato

Es.: Posteggio con numero di posti limitato, numero automobili > numero posti.

-> costante che indica il numero di macchine.

const N = 6

-> costante che indica il numero di posti.

const M = 3

AUTO = (arriva -> parte -> AUTO). arriva parte.

||A = (a[1..N] : AUTO). a.2.arriva a.2.parte.

POSTEGGIO = P[0],

P[occ:0..M] = ( when occ < M arriva -> P[occ+1] | when occ > 0 parte -> P[occ-1] ).

||S = (A || POSTEGGIO). arriva arriva arriva POSTEGGIO: 0 1 2 3 parte parte parte.

Bisognerebbe modificare il nome delle azioni del processo POSTEGGIO per indicare azioni differenti.

Tre possibili soluzioni:

  • Aggiungendo il prefisso a[1..N].
  • Modificando il nome delle azioni.
  • Rinominando tutte le azioni “arriva” e “parte” in “a.1.arriva”, “a.1.parte”, e così via.

Soluzione 1

Modifichiamo S in:

||S = (A || a[1..N]::POSTEGGIO).

“::” è un operatore che permette di aggiungere il prefisso “a*1..N+” a tutte le azioni del processo POSTEGGIO.

a.6.arriva…

a.2.arriva

POSTEGGIO: a.1.arriva a[1..6].arriva a[1..6].arriva 0 1 2 3 a.1.parte a[1..6].parte a[1..6].parte.

a.2.parte…

a.6.parte

Soluzione 2

Modifichiamo il processo POSTEGGIO in:

POSTEGGIO

Anteprima
Vedrai una selezione di 8 pagine su 35
Paradigmi Concorrenti - Appunti Pag. 1 Paradigmi Concorrenti - Appunti Pag. 2
Anteprima di 8 pagg. su 35.
Scarica il documento per vederlo tutto.
Paradigmi Concorrenti - Appunti Pag. 6
Anteprima di 8 pagg. su 35.
Scarica il documento per vederlo tutto.
Paradigmi Concorrenti - Appunti Pag. 11
Anteprima di 8 pagg. su 35.
Scarica il documento per vederlo tutto.
Paradigmi Concorrenti - Appunti Pag. 16
Anteprima di 8 pagg. su 35.
Scarica il documento per vederlo tutto.
Paradigmi Concorrenti - Appunti Pag. 21
Anteprima di 8 pagg. su 35.
Scarica il documento per vederlo tutto.
Paradigmi Concorrenti - Appunti Pag. 26
Anteprima di 8 pagg. su 35.
Scarica il documento per vederlo tutto.
Paradigmi Concorrenti - Appunti Pag. 31
1 su 35
D/illustrazione/soddisfatti o rimborsati
Acquista con carta o PayPal
Scarica i documenti tutte le volte che vuoi
Dettagli
SSD
Scienze matematiche e informatiche INF/01 Informatica

I contenuti di questa pagina costituiscono rielaborazioni personali del Publisher loreld06 di informazioni apprese con la frequenza delle lezioni di Sistemi operativi e reti e studio autonomo di eventuali libri di riferimento in preparazione dell'esame finale o della tesi. Non devono intendersi come materiale ufficiale dell'università Università degli Studi di Milano - Bicocca o del prof Bernadinello Luca.
Appunti correlati Invia appunti e guadagna

Domande e risposte

Hai bisogno di aiuto?
Chiedi alla community