article thumbnail image
Published 2020. 4. 23. 17:23

 

 

  1. Pthread (POSIX thread) : 병렬적으로 작동하는 소프트웨어의 작성을 위해서 제공되는 표준 API이다.
                                            즉 쓰레드를 편하게 만들 수 있도록 도와주는 API이다.
  2. Multithreading model
    1. User thread
      • Kernel 영역 위, User space에서 동작하는 thread
      • User thread가 작동하기 위해서는 Kernel thread와의 매핑이 이루어져야 한다.
      • 즉 User thread는 Kernel thread를 통해서 프로세서를 사용할 수 있다. 
    2. Kernel thread 
      • Kernel 영역에서 동작하는 쓰레드
      • 운영체제가 Kernel 영역에서 쓰레드를 생성 및 관리한다.
      • 운영체제가 스케줄링하는 Thread 단위는 Kernel thread이다. ****
      • CPU 스케줄링에서 프로세스가 기본 단위이지만, 쓰레드를 고려한다면 Kernel thread가 CPU 스케줄링의 기본 단위이다.
      • 스케줄링은 프로세스를 누가 사용할지 결정하는 것이다.
  3. User thread - Kernel thread 간의 mapping
    1. One to One
      1. 하나의 User thread가 하나의 Kernel thread와 매핑되는 형태
      2. User thread가 형성되면 그에따른 Kernel thread가 생성된다.
        • 장점 : 여러개의 쓰레드를 동시에 수행할 수 있다.
        • 단점 : Kernel thread 도 한정되어 있어서 무한정으로 생성할 수 없다. 
    2. Many to One
      1. 여러개의 User thread가 하나의 Kernel thread에 매핑되는 형태
      2. thread 관리는 User level에서 이루어진다.
      3. 한번에 하나의 thread만 Kernel thread에 접근할 수 있으므로, 하나의 thread가 System call을 호출하는 등 Kernel에 접근하면 나머지 thread들은 대기하여야 한다. 
    3. Many to Many
      1. 여러개의 User thread가 여러개의 Kernel thread에 매핑되는 형태
      2. Many to One 처럼 하나의 thread가 System call을 호출할 경우 다른 thread가 bock되거나 waiting하는 현상을 보완함
      3. Many to One과 One to One의 문제점을 해결한다.

 


 

 


 

 

처리할 수 있는 코어가 하나라면 Single-core processor

처리할 수 있느 코어가 여러개면 Multicore processor

processor가 4개니까 Multiprocessor system

 

한 컴퓨터에서 실행중인 프로그램이 여러개인 상황 = Multiprogramming environment ≠ Multiprocessor system

 

프로세스 안에 Thread가 있을 수 있다.

Thread 가 하나라면 Single-threaded process 

Thread 가 여러개면 Multi-threaded process 

 

스케쥴러가 이 쓰레드를 단위로 각 프로세스의 코어에다가 매핑을 시키는 것이다.

 

코어 : 요리사

쓰레드 : 프라이팬 수

요리사 1명이 2개의 프라이팬으로 요리한다 = Muticore

 

프로세스(process) vs 프로세서(processor)

더보기

*****************************************************************************************************************************************

Processor (프로세서)는 하드웨어적인 측면에서 "컴퓨터 내에서 프로그램을 수행하는 하드웨어 유닛"이다.  이는 중앙처리장치(Central Processing Unit)를 뜻하며 폰노이만 아키텍쳐에 의해 만들어졌다면 적어도 하나 이상의 ALU (Arithmetic Logic Unit)와 처리 레지스터(Register)를 내장하고 있어야 한다.

 

Process (프로세스)는 특정 목적을 수행하기 위해 나열된 작업의 목록이라고 생각하여야 합니다. 즉 프로그램이죠. 컴퓨터에서 프로그램은 프로그래밍 언어로 작성된 작업 수행 과정일 분입니다. 프로그래머가 작성한 소스코드와 소스코드가 컴파일되어 기계어로 번역된 바이너리파일도 그저 작업 과정이 기록된 파일일 뿐입니다.

 

작업의 과정이 파일로 저장되어 있으면 그것을 "프로그램"이라고 부르고

메모리에 적재되어 실행 중 이거나 실행 대기 중일 땐 "프로세스"라고 구별하여 부를 뿐입니다.

즉 프로세스는 "메모리에 적재되어 프로세서에 의해 실행중인 프로그램" 이라고 정의하는 것이 정확할 것입니다.

*****************************************************************************************************************************************


 

 

 

프로세서는 멀티코어 프로세서인데 

두개의 코어에 서로 다른 쓰레드가 돌 수 있다.

서로 다른 프로세스이지만 서로 다른 코어로 매핑돼서 돌 수 있다.

 

 

 

 

 

 

 

 이 프로세스는 3개의 쓰레드가 있는데

3개의 쓰레드가 하나의 프로세서에 매핑될 필요가 없다.

2개는 다른쪽 프로세서, 1개는 다른쪽 프로세서로 매핑될 수 있다.

 

 

 


Thread를 구현하는 법은 운영체제가 제공해준다.

운영체제마다 달라서 Library로 Thread를 만들도록 제공해준다.


그게 Pthread이다.  

 

 

*tid >> Thread의 상태를 가리킴

pthread_t *tid  pthread_t 의 data structure에다가 채워서 달라

 

int pthread_create 

더보기

*****************************************************************************************************************************************

첫번째 매개변수인 tid 는 쓰레드가 성공적으로 생성되었을때 생성된 쓰레드를 식별하기 위해서 사용되는 쓰레드 식별자이다.

두번째 매개변수인 attr 은 쓰레드 특성을 지정하기 위해서 사용하며, 기본 쓰레드 특성을 이용하고자 할경우에 NULL 을 사용한다. 

세번째 매개변수인 start_routine는 분기시켜서 실행할 쓰레드 함수이며, 

네번째 매개변수인 arg는 위 start_routine 쓰레드 함수의 매개변수로 넘겨집니다.

 

1. tid : 성공적으로 함수가 호출되면 이곳에 thread ID가 저장됩니다. 이 인자로 넘어온 값을 통해서 pthread_join과 같은 함수를 사용할 수 있습니다.

2. attr : 스레드의 특성을 정의합니다. 기본적으로 NULL을 지정합니다. 만약 스레드의 속성을 지정하려고 한다면 pthread_attr_init등의 함수로 초기화해야합니다.

3. start_routine : 어떤 로직을 할지 함수 포인터를 매개변수로 받습니다. 

4. arg : start_routine에 전달될 인자를 말합니다. start_routine에서 이 인자를 변환하여 사용합니다.

 

성공시에 thread를 초기화함과 동시에 0을 반환하게 됩니다. 실패시에는 thread인자가 설정되지 않고 에러 값을 반환하게 되지요.

*****************************************************************************************************************************************

 

void pthread_exit (void *retval);

쓰레드가 죽을때 return 값을 어딘가에 저장하고 포인터 형태로 넘겨준다.

 

int pthread_join (pthread_t tid, void **thread_return);

tid를 가지고 얘가 죽을 때까지 기다리고 싶어, 그리고 죽어서 리턴한 값을(retval을 ) **thread_return으로 넘겨받고 싶어

더보기

*****************************************************************************************************************************************

thread_join은 스레드를 생성했던 thread를 끝날때까지 기다려줍니다. 만약 thread가 이미 종료되었다면 즉시 리턴합니다.

 

1. thread : 우리가 join하려고 하는 thread를 명시해줍니다. pthread_create에서 첫번째 인자가 있었죠? 그 스레드가 join하길 원한다면 이 인자로 넘겨주면 됩니다.

2. retval : pthread_create에서 start_routine이 반환하는 반환값을 여기에 저장합니다. 

 

만약 성공적으로 호출이 되었다면 0을 반환합니다. 실패시 에러 넘버를 반환하게 되지요. 실패시에는 좀비 스레드가 되고 이 좀비 스레드는 자원을 소모하게 되어 더이상 스레드를 생성할 수 없게 된다고 하네요.

*****************************************************************************************************************************************

 


runner라는 함수로 실행하고 argv[1] 을 넣어서 돌려줘

runner로 돌리고 pthread_join으로 받는다.

 

코드 예제 설명

m.blog.naver.com/PostView.nhn?blogId=whtie5500&logNo=221692793640&categoryNo=9&proxyReferer=https:%2F%2Fwww.google.com%2F

 

 

 

 


 

 


어떤 형태로 동작 하느냐

 

Kernel thread : 운영체제가 지원하고 관리하는 쓰레드

운영체제가 스케줄링 하는 단위는 Kernel thread 이다. ****

운영체제의 스케쥴러라는 애가 Thread 단위로 Processor에다가 Thread를 매핑해서 스케줄링해서 돌린다.

고로 운영체제가 스케줄링 하는 Thread 단위는 Kernel thread 이다.

 

User thread :

진짜 쓰레드는 아닌데 가상으로 쓰레드처럼 만들어 주는 것


User가 보는 thread와 Kernel이 보는 thread는 같다.

기본적으로 One-to-One thread를 제공한다.


 

내가 내 나름대로 Thread 구현해서 쓸게

Many to One

하나의 커널 쓰레드 위에다가 user space library를 잘 쓰면 쓰레드 비스무리한 것을 만들 수 있다.

여러개의 쓰레드를 하나의 커널 쓰레드 위에서 동작하게 하는 것.

 

장점 :

1. 운영체제가 커널쓰레드를 하나만 줄 때

2. 운영체제가 커널을 하나만 스케줄링 했을 때 서로다른 쓰레드를 세밀하게 스케줄링할 때

context switch가 잘 된다.

 

단점 : 

1. 하나의 쓰레드가 진행을 못하고 멈춰버리면 다른 애들이 모두 다 멈춰버린다.

2. 하나의 kernel thread가 하나의 코어로 매핑될 때 user thread를 다른 코어로 매핑시킬 방법이 없다. 

 


융통성있게 하자 모델

 


하나는 bound 나머지는 자유롭게 하는 모델

 

자유도가 높아지면 컨트롤이 안돼서 잘 쓰이진 않는다.

 

 

'🚦 Server > Operating System' 카테고리의 다른 글

09. Threads (3)  (0) 2020.04.27
PA1: My Simple Shell  (0) 2020.04.27
07. Threads (1)  (0) 2020.04.21
06. Inter-Process Communication  (0) 2020.04.14
05. Processes  (0) 2020.04.06
복사했습니다!