본문으로 이동
  • 현재 모든 문서는 작성 중입니다. 보시는 데 불편함이 있더라도 양해 부탁드립니다.

운영체제 기본/프로세스와 스레드

~ldmsys
관리자 (토론 | 기여)님의 2026년 10월 31일 (토) 06:31 판 (프로세스 생성, exec, 스레드 공유와 상태 관찰을 독립 챕터로 분리)
(차이) ← 이전 판 | 최신판 (차이) | 다음 판 → (차이)

목차 · 이전: 보호와 시스템 호출 · 다음: 가상 메모리

디스크에 있는 실행 파일과 실행 중인 프로세스는 구분해야 한다. 같은 실행 파일을 두 번 실행하면 서로 다른 PID와 실행 상태를 가진 프로세스가 생길 수 있다. 프로세스에는 주소 공간, 열린 파일, 자격 정보 등 실행에 필요한 자원이 연결되어 있다.

새 프로세스와 새 프로그램

셸에서 외부 명령을 실행하는 전형적인 흐름은 자식 프로세스를 만들고, 그 프로세스가 실행할 프로그램을 교체하는 것이다. Linux에서는 이를 이해할 때 fork()와 execve()를 함께 보면 좋다. 실제 셸 구현에는 다른 생성 방식이나 최적화가 쓰일 수 있고, 셸 내장 명령은 이 흐름을 따르지 않을 수도 있다.

fork()는 새 프로세스를 만드는 호출이고, execve()는 호출한 프로세스의 프로그램 이미지를 교체하는 호출이다. execve() 자체가 새 PID를 만드는 것은 아니다. 이 둘을 구별하면 “새 프로그램 실행”과 “새 프로세스 생성”을 혼동하지 않게 된다. fork(2) · execve(2)

스레드가 공유하는 것

프로세스 안에는 하나 이상의 스레드가 있을 수 있다. 같은 프로세스의 스레드는 주소 공간과 열린 파일 등의 자원을 공유하면서 각자의 실행 위치와 스택을 갖는다. 스택이 따로 있다는 말은 다른 스레드가 그 메모리에 절대로 접근할 수 없다는 뜻은 아니다. 같은 주소 공간을 공유하므로 포인터를 잘못 다루면 서로의 작업을 망가뜨릴 수 있다.

여러 스레드가 공유 변수에 접근할 때에는 실행 순서를 조정해야 할 수 있다. 스레드를 늘리는 것만으로 처리 속도가 비례해서 올라가지도 않는다. 같은 잠금을 기다리거나 같은 자원을 놓고 경쟁하면 기다리는 시간도 늘어난다. pthreads(7)

CPU를 기다리는가, 다른 일을 기다리는가

프로그램이 종료되지 않았다고 해서 계속 CPU에서 실행되는 것은 아니다. 터미널 입력, 네트워크 응답, 저장장치의 입출력, 다른 스레드의 잠금 해제를 기다릴 수 있다. 기다리는 동안 실행을 멈추고 다른 작업에 CPU를 내줄 수 있다.

스케줄러는 실행 가능한 작업 중에서 다음에 실행할 작업을 고른다. 따라서 CPU 사용률이 낮은데 프로그램이 느리다면 무조건 CPU 성능부터 의심할 일은 아니다. 무엇을 기다리고 있는지 살펴봐야 한다. 반대로 실행 가능한 작업이 많으면 자기 차례를 기다리는 시간도 길어질 수 있다. sched(7)

Linux의 상태 표시에서 R은 실행 중이거나 실행 가능한 상태를 포함한다. S는 인터럽트 가능한 수면, D는 인터럽트 불가능한 대기 상태이며 입출력 대기에서 흔히 보인다. 상태 한 글자만으로 정확히 어떤 파일이나 잠금을 기다리는지까지 알 수 있는 것은 아니다.

현재 셸을 관찰하기

Bash에서 다음 명령을 실행해 보자. $$는 현재 셸의 PID다.

cat /proc/$$/status

Pid와 PPid로 프로세스와 부모의 ID를, Threads로 스레드 수를 확인할 수 있다. State가 S (sleeping)로 보여도 셸이 멈췄다는 뜻은 아니다. 셸이 자식 명령인 cat의 종료를 기다리는 중일 수 있다. 이 명령은 cat의 상태가 아니라 셸의 상태를 읽는다.

출력은 관찰 순간의 값이므로 상태가 바뀔 수 있다. 프로세스가 존재하는지, 지금 실행 가능한지, 실제 CPU 시간을 얼마나 썼는지는 서로 다른 질문이다.

참고 문헌