생산자 소비자 문제
| topics | 700-컴퓨터과학 704 운영체제 |
| types | 이론 학습 |
| tags |
생산자 소비자 문제
여러 개의 프로세스를 어떻게 동기화할 것인가에 관한 고전적인 문제다. **한정 버퍼 문제(bounded-buffer problem)**라고도 한다.
해결 방법에는 뮤텍스와 세마포어가 있다.
뮤텍스 (Mutex)
각각 단독으로 상호 배제될 수 있게 하여 동시 접근을 제한한다. 해당 뮤텍스 객체를 동시에 사용이 불가능하다.
세마포어 (Semaphore)
최대 허용치만큼 사용자가 접근할 수 있다. 각각 인덱스에서 자원을 사용 중인지 확인하고 자원을 사용하지 않을 때 접근이 가능하다. 사용 중일 때는 특정 값으로 변경하여 사용 중임을 알려야 한다.
세마포어를 이용한 구현
더 효율적인 세마포어를 이용한 알고리즘이다.
#include <stdio.h>
#include <pthread.h>
#include <semaphore.h>
#define BUFFER_SIZE 10
typedef int item;
item buffer[BUFFER_SIZE];
int in = 0;
int out = 0;
sem_t empty;
sem_t full;
pthread_mutex_t mutex;
void *producer(void *param) {
item newItem;
while (1) {
// 새로운 아이템 생성
newItem = produce_item();
sem_wait(&empty); // 빈 공간에 대한 세마포어 감소
pthread_mutex_lock(&mutex); // 임계 영역 진입
// 아이템을 버퍼에 추가
buffer[in] = newItem;
in = (in + 1) % BUFFER_SIZE;
pthread_mutex_unlock(&mutex); // 임계 영역 탈출
sem_post(&full); // 채워진 공간에 대한 세마포어 증가
}
}
void *consumer(void *param) {
item consumedItem;
while (1) {
sem_wait(&full); // 채워진 공간에 대한 세마포어 감소
pthread_mutex_lock(&mutex); // 임계 영역 진입
// 버퍼에서 아이템을 가져옴
consumedItem = buffer[out];
out = (out + 1) % BUFFER_SIZE;
pthread_mutex_unlock(&mutex); // 임계 영역 탈출
sem_post(&empty); // 빈 공간에 대한 세마포어 증가
// 아이템 소비
consume_item(consumedItem);
}
}
int main() {
pthread_t tid1, tid2;
pthread_mutex_init(&mutex, NULL);
sem_init(&empty, 0, BUFFER_SIZE);
sem_init(&full, 0, 0);
pthread_create(&tid1, NULL, producer, NULL);
pthread_create(&tid2, NULL, consumer, NULL);
pthread_join(tid1, NULL);
pthread_join(tid2, NULL);
pthread_mutex_destroy(&mutex);
sem_destroy(&empty);
sem_destroy(&full);
return 0;
}
핵심 포인트
| 세마포어 | 역할 |
|---|---|
empty |
버퍼의 빈 공간 개수를 추적. 초기값은 BUFFER_SIZE |
full |
버퍼의 채워진 공간 개수를 추적. 초기값은 0 |
mutex |
임계 영역 보호 |
동작 흐름
Producer:
sem_wait(&empty): 빈 공간이 있을 때까지 대기pthread_mutex_lock(&mutex): 임계 영역 진입- 버퍼에 아이템 추가
pthread_mutex_unlock(&mutex): 임계 영역 탈출sem_post(&full): 채워진 공간 개수 증가
Consumer:
sem_wait(&full): 채워진 공간이 있을 때까지 대기pthread_mutex_lock(&mutex): 임계 영역 진입- 버퍼에서 아이템 가져옴
pthread_mutex_unlock(&mutex): 임계 영역 탈출sem_post(&empty): 빈 공간 개수 증가
관련 문서
- OS-7) 프로세스 동기화-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4-%EB%8F%99%EA%B8%B0%ED%99%94.html) - 동기화 기법과 세마포어
- OS-8) 프로세스 교착상태-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4-%EA%B5%90%EC%B0%A9%EC%83%81%ED%83%9C.html) - 교착 상태와 해결