본문 바로가기

CS/Operating System

프로세스와 스레드

스레드

프로세스는 메모리에 할당된 프로그램, 즉 실행 중인 프로그램으로 운영체제의 관리의 단위이다. 반면, 스레드는 프로세스 내부에서의 CPU 수행 단위를 의미한다.

 

그 전에 프로세스가 어떻게 관리되는지 정리해보자. 프로그램을 실행하게 되면 프로세스가 생성된다. 프로세스가 생성되면 각 프로세스의 주소 공간(code, data, stack)과 PCB(Process Control Block)가 생성된다. 만약 동일 프로그램을 여러 개 실행하는 경우 그만큼 프로세스가 생성된다. 즉 그만큼 메모리를 차지하고 동일 프로그램이기 때문에 각 프로세스들의 실행 코드는 같다. 따라서 굉장히 비효율적이다. 따라서 여기서 스레드가 등장한다. 동일 프로그램에 대한 프로세스가 여러 개 있을 경우 하나의 프로세스에 여러 개의 스레드를 두어 각 스레드 별로 구분되어야 하는 자원만 별도로 구분하고 공유할 수 있는 자원은 공유한다.

스레드의 구성

각 스레드 별로 구분되는 부분은 다음과 같다.

  • 프로그램 카운터(Program Counter, PC)
  • 레지스터 
  • stack

쓰레드가 동료 쓰레드와 공유하는 부분(task)은 다음과 같다.

  • code
  • data
  • OS resources

스레드의 장점

  • 높은 응답성: 예를 들어 웹 페이지를 읽어 들이는 프로세스가 실행된다고 하자. 이것 또한 I/O 작업이기 때문에 읽어 오는 동안에는 blocked 상태가 될 것이다. 그렇게 되면 우리는 답답함을 느끼게 될 것이다. 해당 페이지를 읽어 오기 전까지는 해당 웹 페이지의 빈 화면만 바라보고 있어야 할 것이기 때문이다. 이러한 문제를 해결하기 위해 스레드를 사용할 수 있다. 만약 그림을 읽어 들이는 스레드, 텍스트를 읽어 들이는 스레드를 따로 둔다면 그림을 읽어 오는데 많은 시간이 걸리기 때문에 그림을 읽어 들이는 동안 텍스트라도 먼저 화면에 띄우는 작업을 해 준다면 사용자 입장에서는 프로세스가 진행되고 있다는 느낌을 받으며 높은 응답성을 달성할 수 있게 될 것이다.
  • 자원 공유를 통한 자원 절약: 같은 일을 하는 프로세스를 여러 개 만드는 것은 각 프로세스의 주소 공간을 전부 메모리에 할당해야 하기 때문에 메모리 낭비가 심해진다. 만약 웹 브라우저를 여러 개 띄우거나 한글 파일을 여러 개 띄울 때 그 개수만큼 프로세스를 만든다면 엄청난 메모리 낭비가 일어날 것이다. 이를 해결하기 위해 스레드를 생성한다면, 한 프로세스 내에서 code와 data를 공유하며 stack 또한 스레드마다 나누어 쓰기 때문에 자원을 아주 compact 하게 사용할 수 있게 될 것이다.
  • 프로세스 실행 속도 향상을 통한 경제성: 스레드를 새로 생성하는 것은 프로세스를 새로 생성하는 것보다 그 비용이 적게 든다. 뿐만 아니라 스레드 간에 문맥 교환시 발생하는 오버헤드는 프로세스 간 문맥 교환시 발생하는 오버헤드보다 적게 든다.
  • 병렬성: 위 설명까지는 싱글 코어(CPU가 1개인 컴퓨터)에서도 활용 가능한 스레드의 장점이다. Multiprocessor architecture에서는 병렬성을 활용하여 효율성을 극대화 할 수 있다. 예를 들어 1000*1000 행렬의 곱셈을 진행할 때, 여러 개의 코어를 병렬로 처리하여 동시에 계산한다면 훨씬 빠르게 작업을 처리할 수 있다.

스레드를 구현하는 방법

  • 커널 스레드: 운영체제 커널에 의해 지원받는 스레드이다. 운영체제 커널은 스레드가 여러 개 있다는 사실을 알고 있으며, 하나의 스레드에서 다른 스레드로 CPU 제어권이 넘어가는 것도 커널이 CPU 스케줄링을 하듯 스케줄링하도록 구현되는 것이다.
  • 유저 스레드: 커널의 지원을 받지 않으며, 운영체제 커널은 스레드가 여러 개 있다는 사실을 알지 못한다. 사용자 프로그램이 스스로 라이브러리의 지원을 받아 스레드를 관리한다. 

Reference