OS) Process Synchronization
๐ Process Synchronization ๋ฌธ์
- ์ปดํจํฐ์ ์ ์ฅ๋์ด ์๋ ์ด๋ค ๋ฐ์ดํฐ๋ฅผ ๋ณ๊ฒฝํ๋ ค๋ฉด ๊ทธ ๋ฐ์ดํฐ์ ์ ๊ทผํด์ ๋ณ๊ฒฝํ๋ ์ฐ์ฐ์ ํ ๋ค ์ฐ์ฐ ๊ฒฐ๊ณผ๋ฅผ ๋ค์ ๊ทธ ๋ฐ์ดํฐ๊ฐ ์๋ ์๋ฆฌ์ ๊ฐฑ์ ์์ผ์ค์ผ ํ๋ค.
- ๊ทธ๋ฐ๋ฐ ์ด ๋ ํ๋์ ํ๋ก์ธ์ค๋ง ์ ๊ทผํด์ ์์ ์ ํ๋ฉด ๋ฌธ์ ๊ฐ ์์ง๋ง ์ปดํจํฐ์๋ ์๋ง์ ํ๋ก์ธ์ค๊ฐ ์๊ณ ํ๋์ ๋ฐ์ดํฐ์ ์ฌ๋ฌ ํ๋ก์ธ์ค๊ฐ ์ ๊ทผํ๋ ์ํฉ์ด ์๊ธธ ์ ์๋ค.
- ์ด ๋ ์๋ฌด๋ฐ ์ ์ด ์์ด ์ฌ๋ฌ ํ๋ก์ธ์ค๊ฐ ์ ๊ทผํด์ ํ๋์ ๋ฐ์ดํฐ๋ฅผ ๋ณ๊ฒฝ์ํค๋ฉด ์๋ก ๋ค๋ฅธ ์์ ์ ๋ฐ์ดํฐ๋ฅผ ๋ณ๊ฒฝํ๊ฒ ๋ ์ ์๊ณ ๊ทธ๋ฌ๋ค๋ณด๋ฉด ๋ฐ์ดํฐ๊ฐ ์ฌ์ฉ์์ ์๋์ ๋ค๋ฅด๊ฒ ๋ณ๊ฒฝ๋ ์ ์๋ค(๋ฐ์ดํฐ ๋ถ์ผ์น ๋ฌธ์ ). ๊ทธ๋์ ์ด๊ฑธ ๋ง๊ณ ๋ฐ์ดํฐ์ ์ผ๊ด์ฑ ์ ์ง๋ฅผ ์ํด์ ๊ณต์ ๋ฐ์ดํฐ์ ์ ๊ทผํ ๋ ํ๋ ฅ ํ๋ก์ธ์ค ๊ฐ์ ์คํ ์์๋ฅผ ์ ํด์ฃผ์ด์ผ ํ๋ค.
๐ธ Race condition
- ์ฌ๋ฌ ํ๋ก์ธ์ค๋ค์ด ๋์์ ๊ณต์ ๋ฐ์ดํฐ์ ์ ๊ทผํ๋ ์ํฉ
- ๋ฐ์ดํฐ์ ์ต์ข ์ฐ์ฐ ๊ฒฐ๊ณผ๋ ๋ง์ง๋ง์ ๊ทธ ๋ฐ์ดํฐ๋ฅผ ๋ค๋ฃฌ ํ๋ก์ธ์ค์ ๋ฐ๋ผ ๋ฌ๋ผ์ง
Race condition
์ ๋ง๊ธฐ ์ํดconcurrent process(๋์ ์ ๊ทผ)
๋๋๊ธฐํ(synchronize)
๋์ด์ผ ํ๋ค.
Race Condition์ด ๋ฐ์ํ๋ ์ํฉ
1. ์ปค๋ ์ํ ์ค ์ธํฐ๋ฝํธ ๋ฐ์ ์
- ์ปค๋ ๋ฐ์ดํฐ๋ฅผ ์ฒ๋ฆฌํ๋ ๋์ค์
์ธํฐ๋ฝํธ
๊ฐ ์๊ธด ๊ฒฝ์ฐ - ํด๊ฒฐ์ฑ
: ๋จผ์ ์์
์ค์ด๋ ์ปค๋ ์ฝ๋์ ์์
์ด ๋๋๊ธฐ ์ ๊น์ง๋
์ธํฐ๋ฝํธ
๋ฅผ ๋ฐ์ง ์๋๋ค.
2. ํ๋ก์ธ์ค๊ฐ ์์คํ ์ฝ์ ํ์ฌ ์ปค๋ ๋ชจ๋๋ก ์ํ ์ค์ธ๋ฐ context switch๊ฐ ์ผ์ด๋๋ ๊ฒฝ์ฐ
- A ํ๋ก์ธ์ค๊ฐ
PC
๋ฅผ ์ฆ๊ฐ์ํค๋ ๋์ค์ ๋ค๋ฅธ ์ปค๋ ์ฝ๋ B์๊ฒCPU
๋ฅผ ๋บ๊ฒผ๋ค๊ฐ ๋บ์ด๊ฐ ์ชฝ์ ์์ ์ด ๋๋ ํ ๋ค์ ๋๋ ค ๋ฐ์ผ๋ฉด A๋ B๊ฐ ์ฆ๊ฐ์ํค๊ธฐ ์ ์PC
์ ๋ณด๋ฅผ ๊ฐ์ง๊ณ ์๊ธฐ ๋๋ฌธ์ A๊ฐ ์ฆ๊ฐ์ํค๋PC
๋ ์ ํํ ๊ฐ์ผ๋ก ์ฆ๊ฐ๋์ง ์๋๋ค. - ํด๊ฒฐ์ฑ
: ์ปค๋ ๋ชจ๋์์ ์ํ ์ค์ผ ๋๋
CPU
๋ฅผpreempt
ํ์ง ์๊ณ ์ปค๋ ๋ชจ๋์์ ์ฌ์ฉ์ ๋ชจ๋๋ก ๋์๊ฐ ๋preempt
ํ๋ค.
3. Multiprocessor์์ shared memory ๋ด์ ์ปค๋ ๋ฐ์ดํฐ
- ์ ๊ฒฝ์ฐ๋ค์ ๊ฐ์
CPU
๋ด์์๋ง ํ ์ ์๋ ๋์๋ค์ด๊ธฐ ๋๋ฌธ์ ๋ฉํฐ ํ๋ก์ธ์ ํ๊ฒฝ์์๋ ์ ์ฉ์ด ์ด๋ ต๋ค. - ์ฌ๋ฌ ํ๋ก์ธ์ค๋ค์ด ํ๋์ ๊ณต์ ๋ฉ๋ชจ๋ฆฌ์ ์ ๊ทผํด์ผ ํ ๋ ๊ฐ๊ฐ์
CPU
์์ ๋์์ ์ ๊ทผํด์ ๋ฐ์ดํฐ๋ฅผ ๋ณ๊ฒฝํ ์ ์๋ค. - ํด๊ฒฐ์ฑ
1 : ํ ๋ฒ์ ํ๋์
CPU
๋ง์ด ์ปค๋์ ๋ค์ด๊ฐ ์ ์๊ฒ ํ๋ ๋ฐฉ๋ฒ - ํด๊ฒฐ์ฑ
2 : ์ปค๋ ๋ด๋ถ์ ์๋ ๊ฐ ๊ณต์ ๋ฐ์ดํฐ์ ์ ๊ทผํ ๋๋ง๋ค ๊ทธ ๋ฐ์ดํฐ์ ๋ํ
lock/unlock
์ ํ๋ ๋ฐฉ๋ฒ
The Critical-Section Problem
- n๊ฐ์ ํ๋ก์ธ์ค๊ฐ ๊ณต์ ๋ฐ์ดํฐ๋ฅผ ๋์์ ์ฌ์ฉํ๊ธฐ๋ฅผ ์ํ๋ ๊ฒฝ์ฐ
- ๊ฐ ํ๋ก์ธ์ค์
code segment
์๋ ๊ณต์ ๋ฐ์ดํฐ๋ฅผ ์ ๊ทผํ๋ ์ฝ๋์ธcritical section
์ด ์กด์ฌ - ํ๋์ ํ๋ก์ธ์ค๊ฐ
critical section
์ ์์ ๋ ๋ค๋ฅธ ๋ชจ๋ ํ๋ก์ธ์ค๋critical section
์ ๋ค์ด๊ฐ ์ ์์ด์ผ ํ๋ค.
ํ๋ก๊ทธ๋จ์ ํด๊ฒฐ๋ฒ์ ์ถฉ์กฑ ์กฐ๊ฑด
Mutual Exclusion(์ํธ ๋ฐฐ์ /๋ฐฐํ์ ์ ๊ทผ)
- ํ๋ก์ธ์ค Pirk
critical section
๋ถ๋ถ์ ์ํ ์ค์ด๋ฉด ๋ค๋ฅธ ๋ชจ๋ ํ๋ก์ธ์ค๋ค์ ๊ทธ๋ค์critical section
์ ๋ค์ด๊ฐ๋ฉด ์ ๋๋ค.
- ํ๋ก์ธ์ค Pirk
Progress(์งํ)
- ์๋ฌด๋
critical section
์ ์์ง ์์ ์ํ์์critical section
์ ๋ค์ด๊ฐ๊ณ ์ ํ๋ ํ๋ก์ธ์ค๊ฐ ์์ผ๋ฉดcritical section
์ ๋ค์ด๊ฐ๊ฒ ํด ์ฃผ์ด์ผ ํ๋ค.
- ์๋ฌด๋
Bounded Waiting(์ ํ ๋๊ธฐ)
- ํ๋ก์ธ์ค๊ฐ
critical section
์ ๋ค์ด๊ฐ๋ ค๊ณ ์์ฒญํ ํ๋ถํฐ ๊ทธ ์์ฒญ์ด ํ์ฉ๋ ๋๊น์ง ๋ค๋ฅธ ํ๋ก์ธ์ค๋ค์ดcritical section
์ ๋ค์ด๊ฐ๋ ํ์์ ํ๊ณ๊ฐ ์์ด์ผ ํ๋ค. - ๋ฌดํ๋๋ก ๊ธฐ๋ค๋ฆฌ์ง ์๊ฒ ํด์
starvation
์ ๋ฐฉ์ง
- ํ๋ก์ธ์ค๊ฐ
- ๊ฐ์
- ๋ชจ๋ ํ๋ก์ธ์ค์ ์ํ ์๋๋ 0๋ณด๋ค ํฌ๋ค.
- ํ๋ก์ธ์ค๋ค ๊ฐ์ ์๋์ ์ธ ์ํ ์๋๋ ๊ฐ์ ํ์ง ์๋๋ค.
๊ธฐ๋ณธ์ ์ธ ํด๊ฒฐ ๋ฐฉ๋ฒ
- ๋ ๊ฐ์ ํ๋ก์ธ์ค
P0
,P1
์ด ์๋ค๊ณ ๊ฐ์ ํ์ ๋
do {
entry section /* lock */
critical section
exti section /* unlock */
remainder section
} while(1);
- ํ๋ก์ธ์ค๋ค์ ์ํ์ ๋๊ธฐํ๋ฅผ ์ํด ๋ช๋ช ๋ณ์๋ฅผ ๊ณต์ ํ ์ ์๋ค. -
Synchronization variable
Algorithm 1
int turn; /* ๋๊ตฌ ์ฐจ๋ก์ธ์ง ํ์ํ ๋ณ์. Synchronization variable */
initially turn = 0;
do {
while (turn != 0); /* ๋ด ํด์ด ์๋ ๋์ ๋๊ธฐ */
critical section
turn = 1; /* ์๋ํธ์ผ๋ก ํด ๋๊น */
remainder section
} while (1);
- ์ ์ฝ๋๋๋ก๋ง ์งํ๋๋ฉด ๋ฌธ์ ๊ฐ ์์ด ๋ณด์ด์ง๋ง ๋ฐ๋์ ์๋ ํ๋ก์ธ์ค๊ฐ ๋ค์ด์์
turn
์ ๋ฐ๊ฟ ์ฃผ์ด์ผ๋ง ๋ค๋ฅธ ํ๋ก์ธ์ค๊ฐcritical section
์ ๋ค์ด๊ฐ ์ ์๊ธฐ ๋๋ฌธ์ ๋ง์ฝ A ํ๋ก์ธ์ค๊ฐ ๋ ๋น๋ฒํ๊ฒcritical section
์ ๋ค์ด๊ฐ์ผ ํ๋ ๊ฒฝ์ฐ B ํ๋ก์ธ์ค๋ ์๋์ ์ผ๋ก ๋ ๋ค์ด๊ฐ๊ธฐ ๋๋ฌธ์turn
์ด ๋ฐ๋์ง ์์ A ํ๋ก์ธ์ค๊ฐ ๋ค์ด๊ฐ ์ ์๋ ์ํฉ์ด ์๊ธด๋ค.
Algorithm 2
boolean flag[2]; /* critical section์ ๋ค์ด๊ฐ๊ณ ์ ํ๋ ์์ค์ ํ์ํ๋ flag */
initially flag[๋ชจ๋] = false; /* ์ฒ์์ critical section์ ์๋ฌด๋ ์์ */
do {
flag[i] = true; /* ์ง์
ํ์ */
while (flag[j]); /* ์๋ ํ๋ก์ธ์ค๋ ์ง์
ํด ์์ผ๋ฉด ๋๊ธฐ */
critical section
flag[i] = false; /* ๋์๋ค๊ณ ํ์ */
remainder section
} while (1);
- ์ ์ฝ๋์์๋ ๋ง์ฝ A ํ๋ก์ธ์ค๊ฐ ์ฒซ๋ฒ์งธ ์ค๋ง ์คํํ๊ณ
CPU
๋ฅผ ๋บ๊ธด ๊ฒฝ์ฐ ์๋ ํ๋ก์ธ์ค๋ ์ฒซ๋ฒ์งธ ์ค์ ์คํํ๊ณ ๋๋ฒ์งธ ์ค์์ ๋๊ธฐํ๊ฒ ๋ ๊ฒ์ด๋ค. ์ฆ ๋ ๋ค ๋ฌดํํ ๋๊ธฐํ๊ฒ ๋๋ค.
Algorithm 3 (Petersonโs Algorithm)
do {
flag[i] = true; /* ์ง์
ํ์ */
turn = j; /* ์๋ํธ์ผ๋ก ํด ๋ณ๊ฒฝ */
while (flag[j] && turn == j); /* ๋ค์ด๊ฐ๊ณ ์ ํ๋ ํ๋ก์ธ์ค์ ํด ๋ชจ๋ ํ์ธ */
critical section
flag[i] = false;
remainder section
} while (1);
- ์๊ณ ๋ฆฌ์ฆ 1๊ณผ 2๋ฅผ ํฉ์น ๋ฐฉ๋ฒ์ผ๋ก ์์ ๋ ๊ฐ์ง ๋ฐฉ๋ฒ์์ ์์๋ ๋ฌธ์ ๋ค์ ๋ชจ๋ ํด๊ฒฐํ ์ ์๋ค.
Busy Waiting(= spin lock)
- ํ์ง๋ง
critical section
์ ํ๋ก์ธ์ค๊ฐ ์ด๋ฏธ ์์ด์ ๋ชป ๋ค์ด๊ฐ๋ ๊ฒ์ด ํ์คํ ์ํฉ์์๋ ๊ณ์CPU
๋ฅผ ์ป์ด์while
๋ฌธ ์กฐ๊ฑด์ ํ์ธํด์ผ ํ๊ธฐ ๋๋ฌธ์ ์ง์์ ์ผ๋กCPU
์memory
๋ฅผ ์๋ชจํ๊ฒ ๋๋ค.
- ํ์ง๋ง
ํ๋์จ์ด์ ์ผ๋ก ํด๊ฒฐํ๊ธฐ
Instruction
ํ๋๋กSynchronization variable
์ฝ๊ธฐ์ ์ฐ๊ธฐ๋ฅผ ๋์์ ์คํํ๋ฉด ์์ ์๊ณ ๋ฆฌ์ฆ์ผ๋ก ํด๊ฒฐํ๊ณ ์ ํ๋ ๋ฌธ์ ๋ค์ ๊ฐ๋จํ ํด๊ฒฐํ ์ ์๋ค.
boolean lock = false;
do {
while (Test_and_set(lock); /* lock์ด ๊ฑธ๋ ค์๋ค๋ฉด lock์ ๊ฑธ๊ณ ๊ธฐ๋ค๋ฆด ๊ฒ์ด๊ณ ๊ฑธ๋ ค์์ง ์๋ค๋ฉด lock์ ๊ฑธ๊ณ ๋ค์ด๊ฐ ๊ฒ์ */
critical section
lock = false;
remainder section
} while (1);
Semaphores
- ํ๋ก๊ทธ๋๋จธ๊ฐ ๋งค๋ฒ ์์ ์์ ๋ค์ ํ๋ ค๋ฉด ๊ท์ฐฎ์ผ๋๊น ๊ทธ ์์ ๋ค์ ์ถ์ํ์ํจ ๊ฒ
integer variable
ํํ๋ก ์์์ ๊ฐฏ์๋ฅผ ๊ฐ์ง๊ณ ์๋ค.- ์๋์ ๋ ๊ฐ์ง
atomic
์ฐ์ฐ์ ์ํด์๋ง ์ ๊ทผํ ์ ์๋ค.
/* P(S) : ๊ณต์ ๋ฐ์ดํฐ๋ฅผ ํ๋ํ๋ ์ฐ์ฐ */
while (S <= 0) do wait; /* ์ฌ์ฉํ ์ ์๋ ์์์ด ์์ผ๋ฉด ๋๊ธฐ */
S--;
/* V(S) : ๊ณต์ ๋ฐ์ดํฐ๋ฅผ ์ฌ์ฉ ํ ๋ฐ๋ฉ */
S++;
์ธ๋งํฌ์ด๋ฅผ ์ด์ฉํ ์ฝ๋ - Busy-wait
semaphore mutex; /* initially 1 : 1๊ฐ๊ฐ critical section์ ๋ค์ด๊ฐ ์ ์๋ค */
do {
P(mutex); /* ์์์ด ๋จ์ ์์ผ๋ฉด ํ๋ ๊ฐ์์ํค๊ณ ์
์ฅ */
critical section
V(mutex); /* ์์ ๋ฐ๋ฉ ๋ฐ ์ฆ๊ฐ */
remainder section
} while (1);
- ๋๊ธฐํ๋ ํ๋ก์ธ์ค๊ฐ ์์ผ๋ฉด ์์์ด ์๊ฒผ๋์ง ๊ณ์ ํ์ธํด์ผ ํ๊ธฐ ๋๋ฌธ์
busy-wait
ํ๊ฒ ๋๋ค.
์ธ๋งํฌ์ด๋ฅผ ์ด์ฉํ ์ฝ๋ - Block & wekeup
- ์ธ๋งํฌ์ด๋ฅผ ๋ค์๊ณผ ๊ฐ์ด ์ ์ํ๋ค.
typedef struct
{
int value; /* semaphore */
struct process *L; /* ํ๋ก์ธ์ค ๋๊ธฐ์ด */
} semaphore;
block
๊ณผwakeup
์ ๋ค์๊ณผ ๊ฐ์ด ๊ฐ์ ํ๋ค.block
: ์ปค๋์block
์ ํธ์ถํ ํ๋ก์ธ์ค๋ฅผsuspend
์ํจ ํ ์ด ํ๋ก์ธ์ค์PCB
๋ฅผ ์ธ๋งํฌ์ด์ ๋ํ ๋๊ธฐ์ด์ ๋ฃ์wakeup
:block
๋ ํ๋ก์ธ์ค๋ฅผwakeup
์ํจ ํ ์ด ํ๋ก์ธ์ค์PCB
๋ฅผready queue
๋ก ์ฎ๊น
- ์ธ๋งํฌ์ด ์ฐ์ฐ ์ ์
/* P(S) */
S.value--; /* ์
์ฅ ์ ์ ์์์ ์๋ฅผ ๊ฐ์์ํด */
if (S.value < 0) /* ํ์ฌ ์ธ ์ ์๋ ์์์ด ์์ผ๋ฉด ๋๊ธฐ์ํจ๋ค */
{
add this process to S.L;
block();
}
/* V(S) */
S.value++;
if (S.value <= 0) /* P ์ฐ์ฐ์์ ์์์ ๋ฏธ๋ฆฌ ๊ฐ์์ํค๊ณ ๋ค์ด๊ฐ๊ธฐ ๋๋ฌธ์ ์์์ ๋ฐ๋ฉํ๋๋ฐ๋ ๊ฐฏ์๊ฐ 0 ์ดํ๋ผ๋ฉด ๊ธฐ๋ค๋ฆฌ๊ณ ์๋ ํ๋ก์ธ์ค๊ฐ ์๋ ๊ฒ */
{
remove a process P from S.L;
wakeup(P);
}
๐ Busy-wait vs. Block/wakeup
critical section
์ ๊ธธ์ด๊ฐ ๊ธด ๊ฒฝ์ฐBlock/wakeup
์ด ์ ๋นcritical section
์ ๊ธธ์ด๊ฐ ๋งค์ฐ ์งง์ ๊ฒฝ์ฐBlock/wakeup
์ค๋ฒํค๋๊ฐBusy-wait
์ค๋ฒํค๋๋ณด๋ค ๋ ์ปค์ง ์ ์๋ค.- ์ผ๋ฐ์ ์ผ๋ก๋
Block/wakeup
๋ฐฉ์์ด ์ข๋ค.
์ธ๋งํฌ์ด์ ๋ ์ข ๋ฅ
Counting semaphore
- ๋๋ฉ์ธ์ด 0 ์ด์์ธ ์์์ ์ ์๊ฐ
- ์ฃผ๋ก ๋ฆฌ์์ค์ ๊ฐฏ์๋ฅผ ์ธ๋ ๋ฐ ์ฌ์ฉํ๋ค.
Binary semaphore
- 0 ๋๋ 1 ๊ฐ๋ง ๊ฐ์ง ์ ์๋ ์ธ๋งํฌ์ด
- ์ฃผ๋ก
mutual exclusion (lock/unlock)
์ ์ฌ์ฉ
Deadlock and Starvation
Deadlock
- ๋ ์ด์์ ํ๋ก์ธ์ค๊ฐ ์๋ก ์๋๋ฐฉ์ ์ํด ์ถฉ์กฑ๋ ์ ์๋ event๋ฅผ ๋ฌดํํ ๊ธฐ๋ค๋ฆฌ๋ ํ์
- 1๊ณผ 2 ๋ ๊ฐ์ ์์์ ์ป์ด์ผ ํ๋ A ํ๋ก์ธ์ค๊ฐ ์์ ๋ ๋ง์ฝ A ํ๋ก์ธ์ค๊ฐ 1๋ฒ ์์๋ง ์ป๊ณ B ํ๋ก์ธ์ค์๊ฒ
CPU
๋ฅผ ๋บ๊ธด ํ B ํ๋ก์ธ์ค๊ฐ 2๋ฒ ์์์ ์ป์ผ๋ฉด A ํ๋ก์ธ์ค๋CPU
๋ฅผ ๋ค์ ๋๋ ค๋ฐ์๋ 2๋ฒ ์์์ ์ป์ง ๋ชปํด์ ๋ค์์ผ๋ก ์งํํ ์ ์๋ค. B ํ๋ก์ธ์ค ๋ํ 1๋ฒ ์์์ด ํ์ํ๋ค๋ฉด ์์ํ ๊ธฐ๋ค๋ฆฌ๊ฒ ๋๋ค. - ์ด๋ฌํ ํ์์ ํด๊ฒฐํ๊ธฐ ์ํด์ ์์์ ํ๋ํ๋ ์์๋ฅผ ์ ํด์ค์ 1๋ฒ ์์์ ๋จผ์ ์ป์ด์ผ๋ง 2๋ฒ ์์์ ์ป์ ์ ์๊ฒ ํ๋ ๋ฐฉ์์ ์ฌ์ฉํ ์ ์๋ค.
Starvation
indefinite blocking
- ํ๋ก์ธ์ค๊ฐ
suspend
๋ ์ด์ ์ ํด๋นํ๋ ์ธ๋งํฌ์ด ํ์์ ๋น ์ ธ๋๊ฐ ์ ์๋ ํ์
Classical Problems of Synchronization
๐ธ Bounded buffer problem
Producer-Consumer Problem
์ด๋ผ๊ณ ๋ ํ๋ฉฐ ๋ฐ์ดํฐ ์ ๋ ฅ์ ์ํ ๋ฒํผ๋ฅผ ์์ฑํ๋ ์์ฐ์์ ๊ทธ ๋ฒํผ๋ฅผ ์ฝ์ด์ ์์ ๋ ๋ฐ์ดํฐ๋ฅผ ๋ฐ์ํ ์๋น์๋ก ๋๋๋ ๊ฐ๋ ์ด๋ค.- ์์ฐ์๋ ๋น ๋ฒํผ๊ฐ ์๋์ง ํ์ธ ํ(์์ผ๋ฉด ๊ธฐ๋ค๋ฆผ) ๊ณต์ ๋ฐ์ดํฐ์ lock์ ๊ฑธ๊ณ ๋ฒํผ์ ๋ฐ์ดํฐ๋ฅผ ์ ๋ ฅํ ๋ค์ lock์ ํ๊ณ ๋ ๋ฒํผ๋ฅผ ํ๋ ์ฆ๊ฐ์ํจ๋ค.
- ์๋น์๋ ๋ ๋ฒํผ๊ฐ ์๋์ง ํ์ธ ํ(์์ผ๋ฉด ๊ธฐ๋ค๋ฆผ) ๊ณต์ ๋ฐ์ดํฐ์ lock์ ๊ฑธ๊ณ ๋ฒํผ์์ ๋ฐ์ดํฐ๋ฅผ ๊บผ๋ธ ๋ค lock์ ํ๊ณ ๋น ๋ฒํผ๋ฅผ ํ๋ ์ฆ๊ฐ์ํจ๋ค.
๊ณต์ ๋ฐ์ดํฐ
- ๋ฒํผ ๋ฐ ๋ฒํผ ์กฐ์ ๋ณ์(empty/full buffer์ ์์ ์์น)
๋๊ธฐํ ๋ณ์
- mutual exclusion : ๊ณต์ ๋ฐ์ดํฐ์ mutual exclusion์ ์ํด ํ์
- resource count : ๋จ์ empty/full buffer์ ์๋ฅผ ํ์ํ๊ธฐ ์ํด ํ์
/* Producer */
do {
produce an item in x
...
P(empty);
P(mutex);
...
add x to buffer
...
V(mutex);
V(full);
} while (1);
/* Consumer */
do {
P(full);
P(mutex);
...
remove an item from buffer to y
...
V(mutex);
V(empty);
...
consume the item in y
...
} while (1);
๐ธ Readers-Writers Problem
- ํ ํ๋ก์ธ์ค๊ฐ
DB
์write
์ค์ผ ๋ ๋ค๋ฅธ ํ๋ก์ธ์ค๊ฐ ์ ๊ทผํ๋ฉด ์ ๋จ read
๋ ๋์์ ์ฌ๋ฟ์ด ํด๋ ๋จ- solution
Writer
๊ฐDB
์ ์ ๊ทผ ํ๊ฐ๋ฅผ ์์ง ์ป์ง ๋ชปํ ์ํ์์๋ ๋ชจ๋ ๋๊ธฐ ์ค์ธReader
๋ค์ ๋คDB
์ ์ ๊ทผํ๊ฒ ํด์ค๋ค.Writer
๋ ๋๊ธฐ ์ค์ธReader
๊ฐ ํ๋๋ ์์ ๋DB
์ ๊ทผ์ด ํ์ฉ๋๋ค.- ์ผ๋จ
Writer
๊ฐDB
์ ์ ๊ทผ ์ค์ด๋ฉดReader
๋ค์ ์ ๊ทผ์ด ๊ธ์ง๋๋ค. Writer
๊ฐDB
์์ ๋น ์ ธ ๋๊ฐ์ผ๋งReader
์ ์ ๊ทผ์ด ํ์ฉ๋๋ค.
๊ณต์ ๋ฐ์ดํฐ
DB
์์ฒดreadcount
: ํ์ฌDB
์ ์ ๊ทผ ์ค์ธReader
์ ์
๋๊ธฐํ ๋ณ์
mutex
: ๊ณต์ ๋ณ์readcount
๋ฅผ ์ ๊ทผํ๋ ์ฝ๋(critical section)์mutual exclusion
๋ณด์ฅ์ ์ํด ์ฌ์ฉdb
:Reader
์Writer
๊ฐ ๊ณต์DB
์์ฒด๋ฅผ ์ฌ๋ฐ๋ฅด๊ฒ ์ ๊ทผํ๋ ์ญํ
int readcount = 0;
DB ์์ฒด;
semaphore mutex = 1, db = 1;
/* Writer */
P(db);
...
writing DB ...
...
V(db);
/* Reader */
P(mutex);
readcount++;
if (readcount == 1) P(db); /* Writer ๋๊ธฐ์ํด */
V(mutex);
...
reading DB ...
...
P(mutex);
readcount--;
if (readcount == 0) V(db); /* Writer ์
์ฅ ๊ฐ๋ฅ */
V(mutex);
- ํ์ง๋ง ์ ์ฝ๋๋๋ก๋ง ํ๋ฉด
Reader
๊ฐ ๊ณ์ ๋ค์ด์์Writer
๊ฐ ์์ํ ๊ธฐ๋ค๋ฆฌ๊ฒ ๋ ์ ์๊ธฐ ๋๋ฌธ์(starvation)Writer
์ ์ฐ์ ์์๋ฅผ ๋์ฌ์ค์ ๋๋ฌด ์ค๋ ๊ธฐ๋ค๋ฆฌ์ง ์๊ฒ ํ๋ค.
๐ธ Dining-Philosophers Problem
- ๋ค์ฏ ๋ช ์ ์ฒ ํ์๊ฐ ์ํ ํ ์ด๋ธ์ ์์์ ์๊ฐ๊ณผ ์์ฌ๋ฅผ ๋ฐ๋ณตํ๋๋ฐ ์ ๊ฐ๋ฝ์ด 5๊ฐ(2๊ฐ ์ธํธ ์๋)๋ฐ์ ์์
- ์ฒ ํ์๋ ๋ด ์ ์์ ์๋ ์ ๊ฐ๋ฝ์ ์์ ์๋ ์ฒ ํ์๋ค์ด ์ฐ๊ณ ์์ง ์์์ผ ์ ๊ฐ๋ฝ์ ์ฌ์ฉํด ๋ฐฅ์ ๋จน์ ์ ์๋ค.
- ์ด ๋ ์ด๋ค ์ฒ ํ์์ ์ ์์ ์๋ ์ฒ ํ์๋ค์ด ๊ณ์ ๋ฐฅ์ ๋จน์ด์ ์ด๋ค ์ฒ ํ์๊ฐ ์ ๊ฐ๋ฝ์ ์์ํ ์ฐ์ง ๋ชปํ๋ฉด ๊ตถ์ด ์ฃฝ๋๋ค๋.. ๊ทธ๋ฐ ๋ฌธ์ ์ด๋ค.
- ํด๊ฒฐ ๋ฐฉ์
- 4๋ช ์ ์ฒ ํ์๋ง ํ ์ด๋ธ์ ๋์์ ์์ ์ ์๋๋ก ํ๋ค.
- ์ ๊ฐ๋ฝ์ ๋ ๊ฐ ๋ชจ๋ ์ง์ ์ ์์ ๋์๋ง ์ ๊ฐ๋ฝ์ ์ง์ ์ ์๊ฒ ํ๋ค.
- ๋น๋์นญ : ์ง์(ํ์) ์ฒ ํ์๋ ์ผ์ชฝ(์ค๋ฅธ์ชฝ) ์ ๊ฐ๋ฝ๋ถํฐ ์ง๋๋ก ํ๋ค.
Monitor
์ธ๋งํฌ์ด์ ๋ฌธ์ ์
- ์ฝ๋ฉํ๊ธฐ ํ๋ค๋ค. - ๋ฌธ์ ๊ฐ ์๊ฒผ์ ๋ ๋ฒ๊ทธ ์ก๊ธฐ ํ๋ฆ
- ์ ํ์ฑ(correctness)์ ์ ์ฆ์ด ์ด๋ ต๋ค.
- ์๋ฐ์ ํ๋ ฅ(voluntary cooperation)์ด ํ์ํ๋ค.
- ํ ๋ฒ์ ์ค์๊ฐ ๋ชจ๋ ์์คํ ์ด ์น๋ช ์ ์ธ ์ํฅ์ ๋ผ์น๋ค.
์
V(mutex)
critical section
P(mutex)
Mutual exclusion
์ด ๊นจ์ง
P(mutex)
critical section
P(mutex)
-
Deadlock
-
์ ๊ฒฝ์ฐ๋ค์ฒ๋ผ ์์๊ฐ ๋ฐ๋๊ฑฐ๋ ๊ฐ์ ์ฐ์ฐ์ ๋ ๋ฒ ์ฐ๋ ์ค์๊ฐ ์๊ธฐ๋ฉด ์ค์๋์ด ์๊ธด๋ค.
Monitor
- ๋์ ์ํ ์ค์ธ ํ๋ก์ธ์ค ์ฌ์ด์์
abstract data type
์ ์์ ํ ๊ณต์ ๋ฅผ ๋ณด์ฅํ๊ธฐ ์ํhigh-level synchronization construct
- ๊ฐ์ฒด ์งํฅ ํ๋ก๊ทธ๋๋ฐ์์
class
์ ๋ฉค๋ฒ ๋ณ์์ ํจ์๋ฅผ ๋ด์์ ์ฌ์ฉํ๋ฏ์ด ๊ณต์ ๋ฐ์ดํฐ๋ฅผ ๋ชจ๋ํฐ ์์ ์ ์ธํ๊ณ ๊ณต์ ๋ฐ์ดํฐ์ ์ ๊ทผํ๋ ค๋ฉด ๋ชจ๋ํฐ ๋ด๋ถ์ ํจ์๋ฅผ ํตํด์๋ง ํ๋๋ก ํ๋ ๋ฐฉ๋ฒ - ๋ชจ๋ํฐ ๋ด์ ํจ์๋ ํ ๋ฒ์ ํ๋๋ง ์คํํ ์ ์๊ธฐ ๋๋ฌธ์
lock
์ ๊ฑธ ํ์๊ฐ ์๋ค. ๊ทธ๋์ ํ๋ก๊ทธ๋๋จธ ์ ์ฅ์์๋ ์ข ๋ ๊ฐํธํ๊ฒ ํ๋ก๊ทธ๋จ์ ์งค ์ ์๋ค.