Embedded/RaspberryPI

자원을 공유하는 다중 쓰레드 실습 소스코드 (뮤텍스-mutex 적용)

변화의 물결1 2025. 1. 18. 00:05

 

 

 

 

안녕하세요.

 

 "[도서]임베디드 소프트웨어 베이직, 13.1 자원을 공유하는 다중 쓰레드 실습" 중 마지막 내용에 전체 소스코드 내용이 없어서  공유합니다.

 

 거의 마지막 실습이고 소스코드 내용을 요약하자면 이전 내용에서 다루었던 pthread를 이용을 하는데 있어 공유하는 변수 2~4개의 다른 쓰레드에서 접근했을 때 어떻게 처리해야 하는지 간략하게 알려줍니다.

 세마포어, 뮤텍스 등 방법이 있지만 여기서는 뮤텍스(Mutex)를 활용해서 1씩 증가하고 감소하는 쓰레드와 값이 정상적으로 동작하는지 확인하는 코드입니다.

  


 

1. 뮤텍스 활성화 및 쓰레드 4개 테스트 소스코드

 

 100,000번 1씩 증가, 감소하는 쓰레드 함수와 300,000번 1씩 증가, 감소하는 쓰레드를 실행하고, 공유자원으로 사용할 변수(shareValue)로 선언 후 실행합니다.

 

 

#include <stdio.h>
#include <unistd.h>
#include <pthread.h>

#define NUM_OF_THREAD 4

static int shareValue;
pthread_mutex_t mutex;

void* addThread(void *arg) {
        pthread_t tid = pthread_self();

        printf("[START]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        pthread_mutex_lock(&mutex);
        printf("[MUTEX-IN]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        for(int i=0;i<100000;i++) {
                shareValue++;
        }

        printf("[MUTEX-OUT]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);
        pthread_mutex_unlock(&mutex);

        printf("[END]%s[%lu] shareValue = %d\n",__func__, tid, shareValue);

}

void* addX3Thread(void *arg) {
        pthread_t tid = pthread_self();

        printf("[START]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        pthread_mutex_lock(&mutex);
        printf("[MUTEX-IN]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        for(int i=0;i<300000;i++) {
                shareValue++;
        }

        printf("[MUTEX-OUT]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);
        pthread_mutex_unlock(&mutex);

        printf("[END]%s[%lu] shareValue = %d\n",__func__, tid, shareValue);
}

void* minusThread(void *arg) {
        pthread_t tid = pthread_self();

        printf("[START]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        pthread_mutex_lock(&mutex);
        printf("[MUTEX-IN]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        for(int i=0;i<100000;i++) {
                shareValue--;
        }

        printf("[MUTEX-OUT]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);
        pthread_mutex_unlock(&mutex);

        printf("[END]%s[%lu] shareValue = %d\n",__func__, tid, shareValue);

}

void* minusX3Thread(void *arg) {
        pthread_t tid = pthread_self();

        printf("[START]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        pthread_mutex_lock(&mutex);
        printf("[MUTEX-IN]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);

        for(int i=0;i<300000;i++) {
                shareValue--;
        }

        printf("[MUTEX-OUT]%s[%lu] shareValue = %d\n", __func__, tid, shareValue);
        pthread_mutex_unlock(&mutex);

        printf("[END]%s[%lu] shareValue = %d\n",__func__, tid, shareValue);

}


void main(void) {

        int result;

        pthread_t thread[NUM_OF_THREAD];
        shareValue = 0;

        pthread_mutex_init(&mutex,NULL);

    result = pthread_create(&thread[0],NULL,addThread,NULL);
    if(result) {
            printf(" ERROR [%d]\n", result);
                return;
    } //if

    result = pthread_create(&thread[1],NULL, minusThread,NULL);
    if(result) {
                printf(" ERROR [%d]\n", result);
                return;
    } //if

    result = pthread_create(&thread[2],NULL, addX3Thread,NULL);
    if(result) {
                printf(" ERROR [%d]\n", result);
                return;
    } //if

    result = pthread_create(&thread[3],NULL, minusX3Thread,NULL);
    if(result) {
                printf(" ERROR [%d]\n", result);
                return;
    } //if


        pthread_join(thread[0], NULL);
        pthread_join(thread[1], NULL);
        pthread_join(thread[2], NULL);
        pthread_join(thread[3], NULL);

        pthread_mutex_destroy(&mutex);

        printf("exit program. \n");
        return;

}//main

 

 

2. 실행 결과

 

 Thread의 시작순서와 종료순서는 시점에 따라 다를 수 있지만, Mutex활성화로 최종 결과 0이 되어 자원을 공유할 경우 발생하는 경쟁상태(race condition)를 방지할 수 있습니다.

 

 위의 코드가 완벽한 코드라고 할 수는 없습니다. 조금 더 보완이 필요하지만, 간단하게 이렇게 사용하는구나 참고정도로 생각하면 좋을 듯합니다.

 

 

 

감사합니다.

 

 

<참고 자료>

1. [도서] 임베디드 소프트웨어 베이직, 13.1 자원을 공유하는 다중 쓰레드 실습

 

 

반응형