Principper for Samtidighed og Styresystemer - Processer og Tråde
Principper for Samtidighed og Styresystemer - Processer og Tråde
Principper for Samtidighed og Styresystemer - Processer og Tråde
You also want an ePaper? Increase the reach of your titles
YUMPU automatically turns print PDFs into web optimized ePapers that Google loves.
<strong>Principper</strong> <strong>for</strong> <strong>Samtidighed</strong> <strong>og</strong> <strong>Styresystemer</strong><br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
René Rydhof Hansen<br />
Feb 2009<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 1 / 17
Opgaver<br />
Opgave 1: Grundlæggende OS begreber<br />
Opgave 2: Fordele/ulemper ved monolitisk hhv. mini-kerne design<br />
Opgave 3: Race-condition/TOCTTOU<br />
Opgave 4: Grundlæggende filsystem-begreber<br />
Opgave 5: Filoperationer under Linux<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 2 / 17
Mål<br />
At kunne <strong>for</strong>klare <strong>for</strong>skellige allokeringsstrategier <strong>for</strong> blokke<br />
At kunne <strong>for</strong>klare udviklerperspektivet på filsystemer<br />
(API/interface/systemkald)<br />
At kunne <strong>for</strong>klare hvad tråde <strong>og</strong> processer er<br />
At kunne <strong>for</strong>klare hvad gensidig udelukkelse er <strong>og</strong> hvordan det opnås<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 3 / 17
<strong>Processer</strong> <strong>og</strong> Tråde<br />
Definition (Proces)<br />
Den omgivelse et pr<strong>og</strong>ram udføres i ([English])<br />
Et kørende pr<strong>og</strong>ram<br />
En “virtuel maskine”(?)<br />
Definition (Tråd)<br />
Den del af processen der udføres ([English])<br />
Den størrelse der udføres af styresystemet<br />
“Letvægtsprocesser”<br />
Example (Trådunderstøttelse i (moderne) styresystemer)<br />
Windows<br />
Linux(?)<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 4 / 17
2009-02-17<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
Definition (Proces)<br />
Den omgivelse et pr<strong>og</strong>ram udføres i ([English])<br />
Et kørende pr<strong>og</strong>ram<br />
En “virtuel maskine”(?)<br />
Definition (Tråd)<br />
Den del af processen der udføres ([English])<br />
Den størrelse der udføres af styresystemet<br />
“Letvægtsprocesser”<br />
Example (Trådunderstøttelse i (moderne) styresystemer)<br />
Windows<br />
Linux(?)<br />
1. Virtuel maskine med begrænset adgang til bl.a. processor, e.g., kan ikke<br />
udføre halt-instruktion<br />
2. Tråde tillader “letvægtsprocesser” at dele bl.a. hukommelse<br />
3. Linux understøtter tråde i modsætning til påstanden i [English].<br />
Forvirringen skyldes at Linux implementerer ægte letvægtsprocesser, med<br />
hurtig procesoprettelse, der kan bruges/opfattes som tråde
Multithreading <strong>og</strong> Multipr<strong>og</strong>rammering<br />
Definition (Multithreading)<br />
En opdeling af processer i flere tråde<br />
I systemer uden multithreading: kun processer<br />
Definition (Multipr<strong>og</strong>rammering)<br />
Opdeling af tasks der kan udføres samtidigt på delte processorer<br />
Implementeres ved hurtige skift mellem de enkelte tasks<br />
Kommunikation mellem tråde?<br />
Memory mapping (jvf. Opgave 5 (opgavesæt 2))<br />
COM<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 5 / 17
Tråde<br />
Thread 1<br />
Local<br />
data <strong>for</strong><br />
thread 1<br />
Pr<strong>og</strong>ram<br />
Thread 3<br />
Local<br />
data <strong>for</strong><br />
thread 3<br />
Thread 2<br />
Local<br />
data <strong>for</strong><br />
thread 2<br />
Process 1<br />
Process 2<br />
Tråd-lokale data?<br />
Proces-lokale data?<br />
Delte data?<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 6 / 17
Tråde<br />
Thread 1<br />
Local<br />
data <strong>for</strong><br />
thread 1<br />
Pr<strong>og</strong>ram<br />
Thread 3<br />
Local<br />
data <strong>for</strong><br />
thread 3<br />
Thread 2<br />
Local<br />
data <strong>for</strong><br />
thread 2<br />
Process 1<br />
Process 2<br />
Tråd-lokale data? tråd-ID, prioritet, stak<br />
Proces-lokale data? adresserum, heap, åbne filer, proces-ID, parent,<br />
ejerskab, CPU reg. (kopi)<br />
Delte data? Pr<strong>og</strong>ramtekst<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 6 / 17
2009-02-17<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
Tråde<br />
Tråde<br />
Thread 1<br />
Thread 3<br />
Local<br />
Local<br />
Pr<strong>og</strong>ram<br />
data <strong>for</strong><br />
data <strong>for</strong><br />
thread 1<br />
thread 3<br />
Thread 2<br />
Local<br />
data <strong>for</strong><br />
thread 2<br />
Process 1<br />
Process 2<br />
Tråd-lokale data? tråd-ID, prioritet, stak<br />
Proces-lokale data? adresserum, heap, åbne filer, proces-ID, parent,<br />
ejerskab, CPU reg. (kopi)<br />
Delte data? Pr<strong>og</strong>ramtekst<br />
• Prioritet: influerer på schedulering af tråd(e)<br />
• Proces skal gemme kopi af nødvendig kontekst (herunder CPU registre)
Tråde i Java<br />
public class MyThread extends Thread<br />
{<br />
public void run()<br />
{<br />
<strong>for</strong>(int i=1; i
Hvad er resultatet af følgende pr<strong>og</strong>ram?<br />
int i = 0;<br />
void thread()<br />
{<br />
<strong>for</strong>(int j = 0; j < 10000;j++)<br />
{<br />
i++;<br />
}<br />
}<br />
t1 = run(thread);<br />
t2 = run(thread);<br />
wait(t1);<br />
wait(t2);<br />
print(i);<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 8 / 17
Hvad er resultatet af følgende pr<strong>og</strong>ram?<br />
int i = 0;<br />
void thread()<br />
{<br />
<strong>for</strong>(int j = 0; j < 10000;j++)<br />
{<br />
i++; // i++ er ikke-atomisk<br />
}<br />
}<br />
t1 = run(thread);<br />
t2 = run(thread);<br />
wait(t1);<br />
wait(t2);<br />
print(i);<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 8 / 17
Gensidig udelukkelse — Vigtige begreber<br />
Race Condition<br />
Tilstand hvor resultatet afhænger af den relative hastighed af de<br />
enkelte tråde<br />
Det vil sige af den faktiske ordning (interleaving) af hændelserne i<br />
trådene<br />
Vanskeligt at fejlfinde<br />
Kritisk region<br />
Pr<strong>og</strong>ramfragment der giver anledning til race conditions<br />
Engelsk: “Critical sections” eller “critical regions”<br />
Gensidig udelukkelse<br />
En tilstand hvor der blandt en mængde tråde kun er en enkelt tråd der<br />
kan tilgå en bestemt ressource eller udføre en bestemt del af<br />
pr<strong>og</strong>ramteksten<br />
Engelsk: “mutual exclusion”<br />
Atomisk<br />
Hændelse eller sekvens af hændelser der sker uafbrydeligt<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 9 / 17
Højniveauspr<strong>og</strong><br />
a = a + 1<br />
ld a, r1<br />
add r1,1<br />
st r1,a<br />
Kommandoer/instruktioner i højniveauspr<strong>og</strong> er ikke atomiske<br />
Processorinstruktioner kan antages at være atomiske<br />
Parallel skrivning/læsning til/fra delt lagercelle har u<strong>for</strong>udsigeligt<br />
resultat<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 10 / 17
Gensidig udelukkelse<br />
Kritiske regioner skal udføres under gensidig udelukkelse!<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 11 / 17
mutex algoritmer<br />
bool flag[2] = { false, false };<br />
thread P0<br />
thread P1<br />
{ {<br />
while flag[1]<br />
while flag[0]<br />
{ {<br />
} }<br />
flag[0] = true;<br />
flag[1] = true;<br />
/* kritisk region */ /* kritisk region */<br />
flag[0] = false;<br />
} }<br />
flag[1] = false;<br />
Algoritmen er <strong>for</strong>kert!<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 12 / 17
mutex algoritmer<br />
bool flag[2] = { false, false };<br />
thread P0<br />
thread P1<br />
{ {<br />
while flag[1]<br />
while flag[0]<br />
{ {<br />
} }<br />
flag[0] = true;<br />
flag[1] = true;<br />
/* kritisk region */ /* kritisk region */<br />
flag[0] = false;<br />
} }<br />
flag[1] = false;<br />
Algoritmen er <strong>for</strong>kert!<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 12 / 17
2009-02-17<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
mutex algoritmer<br />
mutex algoritmer<br />
bool flag[2] = { false, false };<br />
thread P0<br />
thread P1<br />
{ {<br />
while flag[1]<br />
while flag[0]<br />
{ {<br />
} }<br />
flag[0] = true;<br />
flag[1] = true;<br />
/* kritisk region */ /* kritisk region */<br />
flag[0] = false;<br />
flag[1] = false;<br />
} }<br />
Algoritmen er <strong>for</strong>kert!<br />
• Race condition: når while-løkken slutter kan den “konkurrerende” proces<br />
igen overtage
Decker’s mutex-algoritme<br />
bool flag[2] = {false, false};<br />
int turn = 0;<br />
process P0 { process P1 {<br />
flag[0] = true;<br />
flag[1] = true;<br />
while flag[1] { while flag[0] {<br />
if turn == 1 { if turn == 0 {<br />
flag[0] = false;<br />
flag[1] = false;<br />
while turn == 1 { } while turn == 0 { }<br />
flag[0] = true;<br />
flag[1] = true;<br />
} }<br />
} }<br />
/* kritisk region */ /* kritisk region */<br />
turn = 1; turn = 0;<br />
flag[0] = false;<br />
flag[1] = false;<br />
} }<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 13 / 17
Decker’s mutex-algoritme<br />
bool flag[2] = {false, false};<br />
int turn = 0;<br />
process P0 { process P1 {<br />
flag[0] = true;<br />
flag[1] = true;<br />
while flag[1] { while flag[0] {<br />
if turn == 1 { if turn == 0 {<br />
flag[0] = false;<br />
flag[1] = false;<br />
while turn == 1 { } while turn == 0 { }<br />
flag[0] = true;<br />
flag[1] = true;<br />
} }<br />
} }<br />
/* kritisk region */ /* kritisk region */<br />
turn = 1; turn = 0;<br />
flag[0] = false;<br />
flag[1] = false;<br />
} }<br />
Ikke særlig effektiv<br />
Problem: compiler kan allokere visse variable til registre (dermed ikke<br />
delt mellem trådene)<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 13 / 17
2009-02-17<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
Decker’s mutex-algoritme<br />
Decker’s mutex-algoritme<br />
bool flag[2] = {false, false};<br />
int turn = 0;<br />
process P0 { process P1 {<br />
flag[0] = true;<br />
flag[1] = true;<br />
while flag[1] { while flag[0] {<br />
if turn == 1 { if turn == 0 {<br />
flag[0] = false;<br />
flag[1] = false;<br />
while turn == 1 { } while turn == 0 { }<br />
flag[0] = true;<br />
flag[1] = true;<br />
} }<br />
} }<br />
/* kritisk region */ /* kritisk region */<br />
turn = 1; turn = 0;<br />
flag[0] = false;<br />
flag[1] = false;<br />
} }<br />
Ikke særlig effektiv<br />
Problem: compiler kan allokere visse variable til registre (dermed ikke<br />
delt mellem trådene)<br />
• Vanskelig at skalere til mere en to processer<br />
• Nødvendig på systemer uden hardwareunderstøttelse
Test and Set<br />
int mutex = 0;<br />
thread P0<br />
thread P1<br />
{ {<br />
while test_and_set(mutex)==1 while test_and_set(mutex)==1<br />
{ {<br />
} }<br />
/* kritisk region */ /* kritisk region */<br />
mutex = 0; mutex = 0;<br />
} }<br />
test and set findes ofte som en atomisk processorinstruktion<br />
Busy waiting<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 14 / 17
2009-02-17<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
Test and Set<br />
Test and Set<br />
int mutex = 0;<br />
thread P0<br />
thread P1<br />
{ {<br />
while test_and_set(mutex)==1 while test_and_set(mutex)==1<br />
{ {<br />
} }<br />
/* kritisk region */ /* kritisk region */<br />
mutex = 0; mutex = 0;<br />
} }<br />
test and set findes ofte som en atomisk processorinstruktion<br />
Busy waiting<br />
• Sætter mutex til 1 <strong>og</strong> returnerer gammel værdi, i.e., 0 eller 1
Exchange<br />
xchange(a,b) bytter a <strong>og</strong> b<br />
Hvis xchange er atomisk, hvordan kan den så bruges til at sikre<br />
gensidig udelukkelse?<br />
Jvf. Opgave 1 i Opgavesæt 2<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 15 / 17
2009-02-17<br />
<strong>Processer</strong> <strong>og</strong> Tråde<br />
Exchange<br />
Exchange<br />
xchange(a,b) bytter a <strong>og</strong> b<br />
Hvis xchange er atomisk, hvordan kan den så bruges til at sikre<br />
gensidig udelukkelse?<br />
Jvf. Opgave 1 i Opgavesæt 2<br />
• Brug xchange til at sikre atomicitet <strong>for</strong> “token”
Opgaver<br />
Opgave 1: Gensidig udelukkelse med xchange<br />
Opgave 2: Tråde <strong>og</strong> gensidighed i Java<br />
Opgave 3: Tråde <strong>og</strong> gensidighed i Java<br />
Opgave 4: Implementation af gensidig udelukkelse<br />
Opgave 5: Memory mapping<br />
Fokusér på opgaverne 1–4.<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 16 / 17
Opsummering <strong>og</strong> næste gang<br />
Filsystemer fra et udviklerperspektiv<br />
API/interface/systemkald<br />
Allokeringsstrategier <strong>for</strong> diskblokke<br />
Katal<strong>og</strong>er<br />
<strong>Processer</strong> <strong>og</strong> tråde<br />
Gensidig udelukkelse (Decker’s algoritme)<br />
Næste gang: sema<strong>for</strong>er, synkronisering, ...<br />
PSS’09 (Forelæsning 02) <strong>Processer</strong> <strong>og</strong> Tråde Feb 2009 17 / 17