1.시스템&인프라/개발 입문자를 위한 운영체제

3편. CPU는 어떻게 일할까? – 시간 분할과 문맥 교환의 원리

쿼드큐브 2025. 11. 14. 11:45
반응형
반응형

3편. CPU는 어떻게 일할까? – 시간 분할과 문맥 교환의 원리

 

📚 목차
1. 시간 분할(Time Sharing)이란 - CPU가 여러 작업을 순차 처리하는 방식
2. 컨텍스트 스위칭(Context Switching) - 문맥을 저장하고 복원하는 전환 기술
3. 멀티코어 시스템에서 운영체제는 무엇을 조율할까?
4. 실습: htop으로 CPU 스케쥴링과 문맥 전환 관찰하기
5. CPU 병목 현상의 원인과 실시간 대응 전략
✔ 마무리 - CPU 이해는 실무 문제 해결의 출발점

 

유튜브로 음악을 들으면서 코딩도 하고, 메신저 알림도 받는 경험은 누구나 해보셨을 겁니다.
하지만 실제로는 대부분의 작업이 단 하나의 CPU에서 실행되고 있습니다.


그렇다면 어떻게 동시에 여러 앱이 실행되는 듯한 느낌이 들까요?


그 중심에는 운영체제의 시간 분할(Time Sharing) 과 문맥 교환(Context Switching) 이라는 기술이 있습니다.
이번 글에서는 이 두 개념이 어떻게 작동하며, 우리가 체감하는 '동시 실행'이 어떤 방식으로 구현되는지 자세히 살펴봅니다.

 

1. 시간 분할(Time Sharing)이란 – CPU가 여러 작업을 순차 처리하는 방식

현대 운영체제는 여러 개의 프로그램이 동시에 실행되는 것처럼 느껴지도록 CPU 자원을 효율적으로 분배하는 기능을 제공합니다.

이때 핵심이 되는 원리가 바로 시간 분할(Time Sharing) 입니다.


✔️ 타임 슬라이스 개념

CPU는 각 작업에 일정 시간 동안 실행 권한을 주고 다음 작업으로 전환합니다.

이 짧은 실행 시간을 타임 슬라이스(Time Slice) 또는 타임 퀀텀(Time Quantum) 이라고 부릅니다.

일반적으로는 10~50ms(밀리초) 정도로 설정됩니다.


사용자는 이렇게 짧은 전환을 감지하지 못하기 때문에, 실제로는 동시 실행처럼 느껴집니다.

 

✔️ 비유로 이해하기

한 명의 선생님이 여러 학생의 질문을 듣는 상황을 떠올려보세요. 학생들이 동시에 말하는 건 불가능하므로, 선생님은 1분씩 시간을 나눠 돌아가며 질문을 듣습니다. 이 방식은 실제로는 한 번에 한 명만 말하지만, 학생들은 전체적으로 “동시에 응답받는 듯한” 경험을 하게 됩니다. CPU와 프로세스의 관계도 이와 유사합니다.

 

✔️ 시간 분할 방식 개념도

시간 분할 방식의 개념도
시간 분할 방식의 개념도

하나의 CPU가 A, B, C 프로세스에 일정 시간씩 번갈아 CPU를 할당하며 실행하는 모습을 타임라인 형태로 표현한 시각화 이미지입니다.

각 프로세스는 자신의 타임 슬라이스가 도래하면 CPU를 사용하고, 끝나면 대기 상태로 전환됩니다.

 

✔️ 예시

➤ Ubuntu 환경

웹 브라우저에서 유튜브 영상을 재생하면서 동시에 터미널에서 sudo apt update 명령어를 실행해도 둘 다 “끊김 없이 동작”합니다. 실제로는 CPU가 짧은 간격으로 두 프로세스를 오가며 실행 기회를 주고 있기 때문입니다.

➤ Windows 환경

OneDrive가 백그라운드에서 파일을 동기화하고 있을 때도, 사용자는 엑셀에서 문서 작업을 문제없이 수행할 수 있습니다. 이 역시 운영체제가 두 작업에 번갈아 CPU 시간을 분배하는 시간 분할 기법 덕분입니다.

 

이처럼 사용자는 여러 작업을 동시에 하고 있다고 느끼지만, 실제로는 운영체제가 짧은 시간 단위로 빠르게 작업을 전환하며 CPU를 공유하고 있는 것입니다. 이 구조가 바로 현대 멀티태스킹의 핵심 기반이라 할 수 있습니다.

 

2. 컨텍스트 스위칭 – 문맥을 저장하고 복원하는 전환 기술

운영체제가 시간 분할 방식을 구현하려면, CPU에서 실행 중인 작업을 언제든지 멈추고 다른 작업으로 전환할 수 있어야 합니다.

이 전환 과정을 가능하게 해주는 핵심 기술이 바로 컨텍스트 스위칭(Context Switching)입니다.

 

✔️ 컨텍스트란 무엇인가요?

컨텍스트(Context) 란 CPU가 현재 실행 중인 프로세스의 모든 상태 정보를 의미합니다.

예를 들어 다음과 같은 정보가 포함됩니다.

▸ 프로그램 카운터 (현재 실행 위치)
▸ 레지스터 값 (계산 중간 결과 등)
▸ 스택 포인터 (함수 호출 상태)
▸ CPU 플래그 등

이 정보는 PCB(Process Control Block) 에 저장됩니다.

 

운영체제는 프로세스를 전환할 때마다 이 상태 정보를 저장하고, 새로운 프로세스의 정보를 불러와 복원해야 합니다.

이 과정을 우리는 문맥 교환(Context Switching)이라고 부릅니다.

 

✔️ 비유로 이해하기

마치 선생님이 학생 A의 질문을 듣다가, 중간에 학생 B의 질문으로 넘어가는 상황을 떠올려보세요.

선생님은 A의 질문이 어디까지 진행됐는지를 메모해 둔 후 B의 질문을 듣고, 다시 A에게 돌아와야 합니다.

이때 A의 질문 내용을 잊지 않으려면, 상태를 정확히 기록하고 복원해야 하겠죠? 운영체제도 마찬가지입니다.

 

✔️ 컨텍스트 스위칭 흐름도

컨텍스트 스위칭 흐름도
컨텍스트 스위칭 흐름도

이 그림은 운영체제가 하나의 CPU를 이용해 두 개의 프로세스(Process A, Process B)를 번갈아 실행하는 과정을 시각적으로 보여줍니다. Chrome(프로세스 A)과 음악 앱(프로세스 B)을 예시로 들고 있으며, 이들이 CPU에서 교대로 실행되는 모습을 아래 3단계로 나눠 설명할 수 있습니다.

 

① 프로세스 A 실행 중
초기 상태에서는 Chrome 앱(Process A)이 CPU에서 실행 중입니다.
이때 CPU는 프로세스 A의 컨텍스트(현재 상태)를 내부에 가지고 있으며, 실행 명령을 처리 중입니다.
프로세스 B는 대기 상태에 있습니다

 

② 문맥 교환 발생 (A → B)

일정 시간이 지나거나 외부 이벤트(예: 입출력 요청)로 인해 CPU는 A의 실행을 중단합니다.

이때 운영체제는 프로세스 A의 상태 정보를 PCB(Process Control Block)에 저장하고, 동시에 프로세스 B의 상태를 PCB에서 불러와 복원합니다.

PCB는 각 프로세스의 컨텍스트(레지스터 값, 스택 포인터, 프로그램 카운터 등)를 저장하는 메모리 공간입니다.

 

③ 프로세스 B 실행 중

CPU는 복원된 B의 상태를 기반으로 프로세스 B의 실행을 시작합니다.
이 상태에서는 음악 앱(Process B)이 실행 중이며, 프로세스 A는 PCB에 상태만 저장된 채 대기 중입니다.

 

이후에도 다시 프로세스 A로 전환이 필요하면 동일한 과정이 반복됩니다.

 

✔️ 컨텍스트 스위칭의 비용: 오버헤드(Overhead)

문맥 교환은 시스템의 다중 작업 처리에 필수적인 기술이지만, 자주 발생하면 오히려 성능 저하를 유발할 수 있습니다. 이때 발생하는 부하를 오버헤드(Overhead)라고 부릅니다.

🔸컨텍스트 정보를 저장하고 복원하는 데도 CPU 시간이 소모됩니다.
🔸작업이 많을수록 문맥 교환 횟수가 증가해 실제 작업보다 ‘스위칭’에 더 많은 리소스를 사용할 수 있습니다.
🔸특히 스레드가 수십 개 이상 실행되는 서버 환경에서는 문맥 교환 오버헤드가 눈에 띄게 커질 수 있습니다.

 

✔️ 실습: 컨텍스트 스위칭 관찰 (Ubuntu)

➤ Ubuntu 환경

터미널에서 동시에 여러 개의 백그라운드 작업(sleep, ping, python 스크립트 등)을 실행하면 CPU 점유율은 낮게 유지되더라도 htop이나 vmstat에서 context switches 수치가 빠르게 증가하는 것을 볼 수 있습니다.

예를 들어, 다음과 같이 간단한 스크립트를 여러 개 실행해 보세요:

for i in {1..10}; do
  (while true; do echo "task $i"; sleep 1; done) &
done

위와 같이 CPU를 점유하는 경량 프로세스를 여러 개 실행하면, vmstat 1에서 cs 수치가 수천 단위까지 급증합니다.

$ vmstat 1

procs -----------memory---------- ---swap-- -----io---- -system-- ------cpu-----
 r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st
 1  0      0 1223456  84560 403520    0    0     1     2  250  410  5  1 94  0  0
 1  0      0 1222800  84560 403520    0    0     0     0  420 1100 10  2 88  0  0
 0  0      0 1222652  84560 403520    0    0     0     0  390 1050  7  1 92  0  0
 1  0      0 1222588  84560 403520    0    0     0     0  515 1900 15  4 81  0  0
 2  0      0 1222440  84560 403520    0    0     0     0  600 2300 18  6 76  0  0

🔸 cs : 초당 컨텍스트 스위칭 수 (context switches/sec)

이렇게 cs 수치가 증가했다는 것은, 운영체제가 여러 프로세스를 빠르게 전환하면서 실행하고 있다는 뜻입니다.

이는 멀티태스킹을 활발히 수행 중이거나, 백그라운드에서 다수의 프로세스가 짧은 주기로 실행되고 있음을 보여줍니다.

 

이후 killall bash 또는 pkill -f while로 정리합니다.

 

➤ Windows 환경

작업 관리자를 열고 세부 정보 탭 → 열 추가 → "스레드 수" 항목을 활성화해 보세요.
스레드 수가 많은 앱(예: 브라우저, IDE, 게임 등)은 CPU를 많이 쓰지 않아도 문맥 교환이 빈번하게 발생합니다.
이로 인해 앱이 느려지거나, 다른 앱 실행에 영향을 줄 수 있습니다.

Windows 작업관리자 스레드 보기
Windows 작업관리자 스레드 보기

반응형

 

 

3. 멀티코어 시스템에서 운영체제는 무엇을 조율할까?

오늘날 대부분의 데스크톱과 노트북에는 2 코어, 4 코어, 많게는 16 코어 이상의 멀티코어 CPU가 탑재되어 있습니다. 멀티코어 구조는 말 그대로 여러 개의 CPU 코어가 하나의 칩에 통합된 형태로, 물리적으로 여러 작업을 동시에 병렬로 처리할 수 있는 환경을 제공합니다.


하지만 멀티코어 환경이 도입되었다고 해서 운영체제의 역할이 줄어드는 것은 아닙니다. 오히려 운영체제는 더 복잡하고 정교한 조정자 역할을 수행하게 됩니다.

 

✔️ 운영체제의 핵심 역할은 다음과 같습니다

🔸 CPU 스케줄링

각 코어에 어떤 작업(프로세스 또는 스레드)을 언제 할당할지를 결정합니다.
🔸 코어 간 작업 분배 전략

어떤 코어는 I/O 처리에, 또 다른 코어는 계산 중심 작업에 최적화하도록 분배 전략을 설정할 수 있습니다.

🔸 예외 처리 및 회복

특정 코어에서 장애나 오류가 발생했을 경우, 다른 코어로 작업을 재배치하는 등의 예외 대응도 운영체제가 책임집니다.

 

이러한 조율이 없다면, 일부 코어에 작업이 과중되고 다른 코어는 유휴 상태로 방치되어 전체 시스템 효율이 크게 떨어질 수 있습니다.

 

✔️비유로 이해하기

마치 회전 초밥 가게에서 손님 수와 재료 상황에 따라 셰프가 어떤 초밥을 먼저 만들지 실시간으로 판단하는 것과 같습니다.

 

✔️ 실무 예시

➤ Ubuntu 환경에서는 htop 명령어를 통해 실시간으로 각 코어의 사용률, 실행 중인 프로세스, 문맥 전환 횟수 등을 직관적으로 확인할 수 있습니다. 이는 멀티코어 시스템이 어떻게 작업을 분산 처리하고 있는지 이해하는 데 큰 도움이 됩니다.

➤ Windows에서는 작업 관리자(Task Manager) → 성능(Performance) 탭에서 각 논리 프로세서의 활동 그래프를 확인할 수 있습니다. 코어별 CPU 점유율 변화와 스레드 배분 현황을 통해 시스템이 어떻게 멀티코어를 활용하고 있는지 파악할 수 있습니다.

windows 논리프로세서의 활용 그래프
windows 논리프로세서의 활용 그래프

참고:
하이퍼스레딩 기술이 적용된 CPU는 하나의 물리 코어가 두 개의 논리 프로세서로 표시됩니다.
그래서 4코어 CPU인데도 작업 관리자에는 8개로 보일 수 있습니다.

 

4. 실습: htop으로 CPU 스케줄링과 문맥 전환 관찰하기

htop은 Ubuntu에서 사용할 수 있는 강력한 실시간 시스템 모니터링 도구입니다.

기본적인 CPU 사용률부터 프로세스 우선순위, 문맥 전환 횟수까지 한눈에 확인할 수 있어, 운영체제의 스케줄링 동작을 시각적으로 이해하는 데 매우 유용합니다

 

✔️ 설치 및 실행 방법

sudo apt update
sudo apt install htop
htop

명령어 실행 후 htop 화면이 열리면, 다양한 시스템 정보를 실시간으로 확인할 수 있습니다.

htop 실행화면 예시
htop 실행화면 예시

htop화면에서 다중 코어별 사용률, 프로세스별 점유율, 스레드 수, 문맥 전환 정보 등이 표시된 htop 화면을 통해 운영체제의 스케줄링 상황을 실시간으로 분석할 수 있습니다.

 

✔️ 확인 포인트

🔸각 코어별 CPU 사용률: 상단에 표시되는 막대그래프를 통해 각 코어의 부하 상태를 개별적으로 확인할 수 있습니다. 멀티코어 시스템에서는 이 정보를 통해 작업 분산 여부를 판단할 수 있습니다.


🔸실행 중인 프로세스와 우선순위: 하단에는 현재 실행 중인 모든 프로세스 목록과 각 프로세스의 우선순위(NI), CPU 점유율(%CPU), 메모리 사용량 등을 확인할 수 있습니다.


🔸문맥 전환 수치(Context Switches): htop 우측 또는 상세 항목에서 각 프로세스의 문맥 전환 횟수를 확인할 수 있으며, 프로세스 간 전환이 얼마나 빈번한지를 분석할 수 있습니다.

 

✔️ 활용 팁

🔸F6: 정렬 기준 변경 – CPU 점유율, 메모리 사용량 등 다양한 항목 기준으로 정렬할 수 있습니다.
🔸F4: 프로세스 검색 – 특정 프로그램 이름을 입력해 해당 프로세스를 빠르게 찾아볼 수 있습니다.
🔸F2: 설정 화면 진입 – 표시 항목을 추가하거나 색상을 조정하는 등 개인 설정이 가능합니다.

 

Ubuntu의 htop처럼, Windows에도 실시간으로 CPU 상태와 프로세스 정보를 모니터링할 수 있는 기본 도구와 고급 도구가 존재합니다. 대표적으로는 기본 제공되는 작업 관리자(Task Manager)와 Microsoft의 고급 도구인 Process Explorer가 있습니다.

 

5. CPU 병목 현상의 원인과 실시간 대응 전략

실제 개발 현장이나 일반 사용자 환경에서도 CPU 병목 현상은 자주 발생합니다.

이는 시스템에 실행 중인 프로세스가 너무 많거나, 하나의 특정 작업이 CPU 자원을 과도하게 독점할 때 발생합니다.

이로 인해 다른 프로세스들이 CPU를 할당받지 못하고 대기하게 되며, 결과적으로 전체 시스템의 반응 속도가 급격히 저하됩니다.

 

✔️ 예시 시나리오

🔸데이터 분석 애플리케이션이 대규모 배열 연산을 수행하면서 CPU를 100% 가까이 점유합니다.
🔸그 결과, 웹 브라우저, 파일 탐색기 등 다른 프로그램들의 실행이 매우 느려지거나 멈춘 것처럼 보이게 됩니다.
🔸Ubuntu에서는 top이나 htop 명령어를 통해 해당 프로세스가 CPU 리소스를 거의 독점하고 있는 것을 실시간으로 확인할 수 있습니다.
🔸Windows에서는 작업 관리자(Task Manager) > ‘성능’ 또는 ‘세부 정보’ 탭에서 문제 프로세스를 식별할 수 있으며, 해당 프로세스를 종료하면 즉시 시스템 반응 속도가 회복되는 경우가 많습니다.

 

✔️ CPU 병목 대응 방법

CPU 병목이 발생했을 때는 다음과 같은 방법으로 대응할 수 있습니다:

🔸우선순위 조정

➤ Ubuntu에서는 nice 또는 renice 명령어를 사용해 특정 프로세스의 우선순위를 낮춰 다른 프로세스들이 더 많은 CPU 자원을 얻을 수 있도록 조정할 수 있습니다.

renice -n 10 -p <PID>

➤ Windows에서는 작업 관리자 > '세부 정보' 탭에서 해당 프로세스를 우클릭한 뒤, "우선순위 설정"을 통해 낮음/보통 등으로 조정할 수 있습니다.

Windows 우선순위 설정 예시
Windows 우선순위 설정 예시

🔸병렬처리 또는 멀티 스레딩 적용

➤ CPU를 많이 사용하는 작업이라면 단일 스레드가 아닌 멀티스레드 기반으로 작업을 분산시켜 코어들을 효율적으로 활용하는 것이 좋습니다.

➤ 예: Python에서 multiprocessing 모듈 사용 또는 C++/Java에서 스레드 풀 구현

 

🔸CPU 사용량 제한

➤ Linux에서는 cgroups(control groups)를 통해 특정 프로세스가 사용할 수 있는 CPU 자원을 제한할 수 있습니다. Docker와 Kubernetes에서도 이를 기반으로 리소스 제한을 설정합니다.

➤ Windows에서는 Job Object API를 활용하면 애플리케이션 레벨에서 CPU 사용 제한을 구현할 수 있습니다.

 

✔ 마무리 - CPU 이해는 실무 문제 해결의 출발점

CPU는 단순한 계산기가 아니라, 수많은 작업을 조율하는 운영체제의 중심 자원입니다.

이 글에서 다룬 시간 분할(Time Sharing)과 문맥 교환(Context Switching)은 현대 시스템이 ‘여러 프로그램이 동시에 실행되는 것처럼 보이게 하는 핵심 기술’입니다.


실제로 우리는 다음과 같은 실무 상황에서 이 개념들을 마주하게 됩니다:
🔸서버가 느려졌을 때, CPU 사용률만 보는 것이 아니라 문맥 교환 과잉이나 프로세스 우선순위 문제를 의심해야 합니다.
🔸CPU 집약적인 작업이 병목을 유발할 경우, 멀티스레딩, 우선순위 조정, 자원 제한(cgroups) 등의 대응 전략을 설계할 수 있어야 합니다.
🔸멀티코어 환경에서는 운영체제가 코어 간 작업을 어떻게 분배하는지를 이해해야 애플리케이션 성능을 최적화할 수 있습니다.


운영체제가 CPU를 어떤 원리로 관리하고 있는지 이해하는 것은 단순한 이론 지식이 아닙니다.

성능 튜닝, 병목 분석, 시스템 설계 등 실무 전반에 직결되는 역량입니다.


앞으로는 htop에서 보이는 숫자 하나하나가 ‘왜 그렇게 나타나는지’ 이해할 수 있고, 필요할 땐 적절한 조치를 취할 수 있는 실무형 개발자로 나아갈 수 있을 것입니다.

 

 


※ 게시된 글 및 이미지 중 일부는 AI 도구의 도움을 받아 생성되거나 다듬어졌습니다.

반응형

 

반응형