와 이번 주차는 너무 흥미로운 주제이네요!
동기화 영어 단어로만 알고 있었지 프로세스 측면에서는 처음 공부해보는거 같아요.
게다가 이번 차시에서는 저자분의 깃허브에 있는 코드 부분도 더 봐봤는데 확실히 복잡하네요 ㅎㅎ...
⚠ 아래 내용은 책 개념 + 인터넷 정보 등이 포함되어있습니다. ⚠
( 📢 수정할 내용이 있다면 알려주세요! )
한 프로그램을 실행시키는데 여러 프로세스가 필요할 수 있다. 이러한 독립적 프로세스들을 공동의 목표인 프로그램 실행을 위해 협력하는 존재로 볼 수 있다.
Process Synchronization
: 프로세스(+스레드)들의 수행 시기를 맞추는 것
동기화의 큰 틀 =
shared resource
: 프로세스들이 같이 쓰는 자원. 전역변수나 파일, 입출력장치, 보조기억장치가 될 수 있음.
Critical Section
: 동시에 실행하면 문제가 발생하는 자원에 접근하는 코드 영역. 즉, 임계구역에서는 여러 프로세스가 접근하면 안 된다! => 여러 프로세스가 동시 다발적으로 임계구역의 코드를 실행하면 race condition
발생.
따라서 운영체제는 Critical section에서 발생할 수 있는 문제들을 아래 원칙으로 해결한다.
뮤텍스 락
은 이미 접근한 프로세스가 있는 임계 구역에 다른 프로세스가 접근하지 못하도록 만든 도구로, 상호 배제를 위한 도구이다.
acquire() {
while (lock == true)
; //임계구역 잠겨있음(ture)을 계속 확인
lock = true; // lock == false였을 경우 다시 lock을 잠금(true)
}
release() {
lock = false; //잠금 해제
}
위의 두 함수들로 lock의 값을 상황에 따라 true/false로 바꾸면서 제어를 합니다.
따라서 acquire( ) 함수로 임계구역 접근이 가능한 지 확인 및 대기, false가 뜬다면 다시 잠그고 들어가서 임계구역 내에서 작업을 수행합니다.
이후 release( ) 함수로 lock을 해제하며 반환을 해줍니다.
세마포
는 일반화된 방식의 동기화 도구입니다.
즉, 뮤텍스 락은 하나의 shared resource를 가정한 것이라면 세마포는 여러 공유 자원이 존재함을 가정한 상황에 적용 가능한 동기화 도구입니다.
**이진 세마포, 카운팅 세마포
wait(){
while (S<=0) //임계구역 진입 가능한 프로세스의 개수가 0개 이하일 경우
; //사용 가능한 자원 확인을 반복적으로 수행
S--; //진입 가능한 프로세스 개수가 1개 이상이면 S를 1 감소시키고 해당 프로세스를 임계구역에 진입한다.
}
signal(){
S++; //임게 구역엥서 작업을 마치고 S를 1 증가시킨다.
}
여기서 뮤텍스 락의 acquire( )에서나 세마포의 wait( )에서 각 전역변수의 값을 while문으로 계속 확인하는 과정에서 바쁜 대기(busy wait
) 상태가 지속되면 CPU cycle을 낭비시킬 수 있습니다.
이에 코드를 다음과 같이 수정합니다.
wait(){
S--;
if (S<0){
add this process to Queue; //해당 프로세스 PCB를 대기 큐에 삽입.
sleep(); //대기 상태로 접어든다.
}
}
signal(){
S++;
if (S<=0){
remove a process p from Queue; //대기 큐에 있는 프로세스 p를 제거.
wakeup(p); //프로세스 p를 대기 상태에서 준비 상태로 전환시킨다.
}
}
프로세스의 순서 제어는 전역변수 S=0으로 설정한 후에 먼저 실행할 프로세스 뒤에 signal( ) 함수를 두고, 그 다음으로 실행할 프로세스 앞에 wait( )함수를 붙입니다.
**
세마포는 이진 값을 가질 수 있으며 이를 뮤텍스로 볼 수 있다. 따라서 세마포는 뮤텍스가 될 수 있으며 동기화 대상이 여러개일 때 사용된다!
세마포는 위처럼 wait와 signal을 임계구역에 앞뒤로 순서에 맞게 지정하는 것이 번거롭고 코드를 잘못 작성할 경우가 생깁니다.
이에 모니터
는 shared source에 접근하기 위한 인터페이스를 묶어 관리합니다. 또한 프로세스는 반드시 이 인터페이스를 통해서만 공유 자원에 접근 가능하도록 합니다.
모니터를 통해 공유 자원에 접근하고자 하는 프로세스들을 큐에 삽입하고 순서대로 진입시킵니다. 이에 상호 배제를 위한 동기화와 실행 순서 제어를 위한 동기화를 제공합니다.
상호 배제를 위한 큐
와 조건 변수에 대한 큐
가 존재하는데 조건 변수에 대한 큐는 모니터에 이미 진입한 프로세스의 실행 조건이 만족될 때 까지 잠시 실행이 중단되어 기다리기 위해 만들어진 큐이다.
즉, 조건 변수를 사용하여 프로세스를 실행하고 일시 중단시키는데 조건 변수로는 wait와 signal 연산을 수행할 수 있습니다. x.wait()을 통해 조건 변수 x에 대한 wait를 호출했다면 wait 연산으로 일시 중지된 프로세스는 이후에 다른 프로세스의 signal연산으로 실행이 재개됩니다.
모니터 안에는 한 프로세스만 존재할 수 있으며 wait 메서드를 실행시킨 프로세스는 signal 메서드를 실행시킨 프로세스가 모니터를 나온 뒤에 실행되거나 혹은 signal을 실행한 프로세스의 실행이 중단되고 자신을 실행시킨 후에 다시 signal을 수행한 프로세스를 재개합니다.
위 깃허브 링크를 통해 책 저자인 강민철 선생님의 동기화 파트를 코드를 통해 자세히 공부할 수 있습니다.
모니터를 지원하는 대표적 언어는 java라고 하네요. 다음과 같이 매서드 앞에 synchronized 키워드
를 붙임으로써 사용 가능하다고 합니다.
다음과 같이 동기화를 해주지 않았다면 두 메서드(insert( )와 remove( ) 메서드)는 버퍼에 대해 공유 자원을 가지므로 race condition이 발생할 수 있겠네요!
1 public class BoundedBuffer<E>
2 {
3 private static final int BUFFER_SIZE = 5;
4 private E[] buffer;
5
6 public BoundedBuffer() {
7 count = 0;
8 in = 0;
9 out = 0;
10 buffer = (E[]) new Object[BUFFER_SIZE];
11 }
12
13 /* 생산자가 호출하는 코드 */
14 public synchronized void insert(E item) {
15 while (count == BUFFER_SIZE) {
16 try {
17 wait();
18 }
19 catch (InterruptedException ie) {}
20 }
21
22 buffer[in] = item;
23 in = (in + 1) % BUFFER_SIZE;
24 count++;
25
26 notify();
27 }
28
29 /* 소비자가 호출하는 코드 */
30 public synchronized E remove() {
31 E item;
32
33 while (count == 0) {
34 try {
35 wait();
36 }
37 catch (InterruptedException ie){}
38 }
39
40 item = buffer[out];
41 out = (out + 1) % BUFFER_SIZE;
42 count--;
43 notify();
44
45 return item;
46 }
47 }
**예제 코드 출처는 Operating System Concepts, Abraham Silberschatz (10th edition) 이라고 합니다.
Deadlock
: 두 개 이상의 작업이 서로 상대방의 작업이 끝나기 만을 기다리고 있기 때문에 결과적으로 아무것도 완료되지 못하는 상태
교착 상태의 원인:
위 경우들이 모두 충족되었을 때야 비로소 교착 상태에 도달합니다.
p. 363의 확인 문제 1번 풀고 인증하기 Ch.12(12-1) 임계 구역, 상호 배제 개념을 정리하기
Q: 뮤텍스 락과 세마포에 대한 설명으로 옳지 않은 것을 고르세요.
1. 뮤텍스 락은 임계 구역을 잠근 뒤 임계 구역에 진입함으로써 상호 배제를 위한 동기화를 이룹니다.
2. 세마포는 공유 자원이 여러 개 있는 상황에서도 이용할 수 있습니다.
3. 세마포를 이용해 프로세스 실행 순서 제어를 위한 동기화를 이룰 수 있습니다.
4. 세마포를 이용하면 반드시 바쁜 대기를 해야합니다.
A: 4
뮤텍스 락에서는 acquire( )에서 바쁜 대기가 일어났고 세마포에서도 wait( )에서 바쁜 대기가 일어날 수 있었지만 세마포는 wait에서 프로세스를 queue로의 삽입과 sleep을 통해 대기상태로 접어들게 할 수 있으며 이를 통해 CPU 주기 사용 문제를 해결할 수 있었습니다.
임계 구역(Critical Section) : 공유 자원에 접근하는 코드 영역으로 동기화 문제를 해결하기 위한 개념 중 하나이다.
상호 배제 : 교착상태 발생 조건 중 하나로 자원은 동시에 하나의 프로세스만 사용할 수 있는 상태를 의미한다.
ps.
컴퓨터구조를 공부하시는데 영어원문 lecture 책을 찾으시다면 다음을 추천🙃
한국어 교재를 찾으신다면 다음을 추천드립니다. 🙂
https://www.hanbit.co.kr/store/books/look.php?p_code=B9177037040