페이징 시스템 프레임 테이블
핵심 인사이트 (3줄 요약)
- 본질: 페이징(Paging)은 프로세스의 가상 메모리를 고정된 크기(Page)로 썰고, 램(RAM)의 물리 메모리도 같은 크기(Frame)로 썰어서, "연속된 가상 주소가 흩어진 물리 주소의 어디든 매핑될 수 있게 하는" 현대 운영체제의 메모리 관리 근간이다.
- 테이블의 역할: 이를 위해 OS는 두 가지 장부를 쓴다. 프로세스마다 갖고 있는 '페이지 테이블(Page Table)'은 가상 주소를 물리 주소로 번역해 주고, OS가 단 1개만 갖고 있는 '프레임 테이블(Frame Table)'은 실제 물리 RAM의 어떤 칸이 비어있고 어떤 프로세스가 쓰고 있는지 전역적으로 관리한다.
- 가치: 이 4KB짜리 블록 매핑 기술 덕분에 외부 단편화(External Fragmentation)라는 고질병이 100% 멸종되었으며, 개발자들은 물리 메모리의 파편화 상태를 신경 쓰지 않고 무한한 연속된 메모리 공간이 있는 것처럼 착각(Illusion)하며 코딩할 수 있게 되었다.
Ⅰ. 개요 및 필요성 (Context & Necessity)
-
개념:
- 페이지 (Page): 가상 메모리를 자르는 고정된 블록 단위 (보통 4KB).
- 프레임 (Frame): 물리 메모리(RAM)를 자르는 고정된 블록 단위 (페이지와 크기가 무조건 100% 같다).
- 프레임 테이블 (Frame Table): 시스템 전체의 물리 프레임 상태(Free, Allocated)를 추적하는 운영체제의 메인 장부.
-
필요성 (연속 할당의 한계 돌파):
- 가변 분할(연속 할당) 방식은 외부 단편화 때문에 수기가바이트의 메모리가 낭비되었다.
- "왜 꼭 연속으로 줘야 하지? 프로그램 코드를 잘게 찢어서 빈 공간 아무 데나 흩뿌려 놓고, 실행할 때만 순서대로 조립해주면 안 될까?"
- 해결책: 메모리를 잘게 찢는 '페이징' 기법이 도입되었다. 찢어진 페이지들이 물리 램의 어느 프레임(빈칸)에 들어갔는지 기록하는 거대한 룩업 테이블(Look-up Table)이 필수적으로 요구되었다.
-
💡 비유:
- 연속 할당: 50페이지짜리 소설책 1권을 통째로 꽂을 수 있는 빈 책장을 찾는다. 책장이 조금씩 비어있어도 연속된 빈칸이 없으면 책을 꽂을 수 없다.
- 페이징: 소설책을 1장(Page)씩 뜯어버린다. 그리고 도서관 책장의 빈 곳(Frame) 아무 데나 마구잡이로 한 장씩 꽂아 넣는다.
- 페이지 테이블: "이 소설의 1페이지는 도서관 30번 칸에 있고, 2페이지는 80번 칸에 있다"고 적어놓은 개인용 인덱스.
- 프레임 테이블: 도서관 사서가 들고 있는 장부. "현재 도서관의 30번 칸은 사용 중, 31번 칸은 빔"이라고 전체 빈자리를 관리하는 지도.
-
발전 과정:
- 연속 메모리 할당: 단편화로 인해 OOM(Out of memory) 빈발.
- 단일 페이징: 외부 단편화는 잡았으나, 페이지 테이블 자체가 너무 커서 메모리를 다 잡아먹는 새로운 문제 발생.
- 계층적(Hierarchical) 페이징: 페이지 테이블의 용량 문제를 다단계 구조로 쪼개어 해결.
-
📢 섹션 요약 비유: 페이징은 거대한 레고 조립입니다. 완성된 성(가상 메모리)은 웅장하지만, 실제로는 수백만 개의 똑같은 크기의 레고 블록(프레임)들이 여기저기 흩어져서 조립된 완벽한 환상입니다.
Ⅱ. 아키텍처 및 핵심 원리 (Deep Dive)
페이징 주소 변환 (Address Translation) 메커니즘
CPU가 논리 주소 0x1234를 부르면 MMU가 이를 물리 주소로 번역하는 과정이다. (페이지 크기는 4KB = $2^{12}$ 바이트)
┌───────────────────────────────────────────────────────────────────┐
│ CPU의 페이징(Paging) 주소 변환 아키텍처 │
├───────────────────────────────────────────────────────────────────┤
│ [ 1. CPU가 논리 주소를 쏜다 ] │
│ - 논리 주소: 13비트 이진수 (예: `00001` + `010101010101`) │
│ - 상위 비트 (p): 페이지 번호 (Page Number) = `1`번 페이지 │
│ - 하위 비트 (d): 페이지 내 오프셋 (Offset) = `01010...` 번지 │
│ │
│ [ 2. MMU의 Page Table 조회 ] │
│ - MMU는 CR3 레지스터를 타고 메모리에 있는 '페이지 테이블'로 간다. │
│ - 테이블의 `1번` 인덱스를 찾아본다. │
│ - "가상 1번 페이지 ──매핑──▶ 물리 5번 프레임(Frame)에 있음!" 발견. │
│ │
│ [ 3. 물리 주소 조립 및 RAM 접근 ] │
│ - 물리 주소(f) = 프레임 번호(`5`) + 오프셋(d 그대로 복붙) │
│ - 오프셋은 **절대 변하지 않는다** (페이지와 프레임 크기가 100% 똑같기 때문)│
│ - 최종 물리 주소 `5` + `01010...` 번지의 램(RAM) 데이터를 읽어옴! │
└───────────────────────────────────────────────────────────────────┘
[다이어그램 해설] 오프셋(Offset)은 책의 '줄 번호'다. 소설책의 1페이지를 통째로 뜯어서 책장 5번째 칸에 넣었다 치자. 내가 "1페이지의 3번째 줄을 읽고 싶어"라고 할 때, 책이 몇 번째 책장 칸으로 이사 갔든 그 종이 안에서 **위에서부터 3번째 줄(Offset)**이라는 사실은 물리적으로 변하지 않는다. 따라서 MMU는 앞의 껍데기 번호(Page -> Frame)만 번역하고 꼬리표(Offset)는 그대로 갖다 붙이는 초고속 $O(1)$ 연산을 수행한다.
프레임 테이블 (Frame Table)의 역할과 관리
페이지 테이블이 프로세스마다 1개씩 존재한다면(사용자 관점), 프레임 테이블은 OS 전체에 딱 1개 존재한다(시스템 관점).
-
구조:
[프레임 번호] | [상태: Free / Allocated] | [어떤 프로세스의 어떤 페이지가 쓰고 있나?] -
역할 1 (할당): 프로세스가
malloc으로 4KB를 요구하면, OS는 프레임 테이블을 쓱 보고 상태가Free인 프레임 번호를 하나 던져준다. -
역할 2 (OOM 방어 및 Swapping): 램이 꽉 차서 빈 프레임이 없을 때, OS는 프레임 테이블을 뒤져서 "요즘 제일 안 쓴 프레임(LRU)이 누구지?"를 찾은 뒤, 그 놈을 하드디스크(Swap)로 쫓아내고 빈자리를 만든다.
-
📢 섹션 요약 비유: 페이지 테이블이 '투숙객이 들고 있는 방 번호표'라면, 프레임 테이블은 '호텔 프론트에 있는 마스터 객실 현황판'입니다. 프론트 직원은 현황판을 보고 빈 방을 내어주거나, 너무 오래 잔 손님을 깨워서 쫓아냅니다.
Ⅲ. 융합 비교 및 다각도 분석
페이징(Paging) vs 세그멘테이션(Segmentation)
연속 할당을 극복한 두 가지 라이벌 기법이다. (현재는 페이징의 압승)
| 비교 항목 | 페이징 (Paging) | 세그멘테이션 (Segmentation) |
|---|---|---|
| 자르는 기준 | 하드웨어가 정한 고정 크기 (예: 4KB) | 프로그래머가 정한 논리적 덩어리 (함수, 배열 등 크기 제각각) |
| 단편화 문제 | 외부 단편화 0%, 내부 단편화 발생 | 내부 단편화 0%, 외부 단편화(치명적) 발생 |
| 의미적(Semantic) 분할 | 무식하게 자르므로 코드 1줄이 반으로 갈리기도 함 | 함수나 객체 단위로 깔끔하게 잘림 (보안, 공유에 유리) |
| 현대 OS의 채택 | 표준 아키텍처 (100% 사용) | x86 아키텍처 호환을 위해 껍데기만 남고 실질적으로 사장됨 |
과목 융합 관점
-
자료구조 (Data Structure): 운영체제 커널(리눅스)은 프레임 테이블의 남은 빈 공간을 관리할 때 단순한 배열을 쓰지 않는다. 메모리가 조각나는 것을 막고 연속된 프레임을 초고속으로 뭉쳐서 내어주기 위해 **버디 시스템 (Buddy System)**이라는 이진 트리(Binary Tree) 형태의 특수 자료구조를 사용하여 프레임을 관리한다.
-
클라우드 / 가상화: 하이퍼바이저(KVM)는 게스트 OS가 "내 램은 8GB야"라고 믿게 만든다. 이를 위해 하이퍼바이저는 섀도우 페이지 테이블(Shadow Page Table)을 통해 가상머신의 가짜 프레임 주소를 물리 머신의 진짜 하드웨어 프레임으로 한 번 더 번역해 주는 이중 페이징(2-Stage Translation) 마술을 부린다.
-
📢 섹션 요약 비유: 소고기를 썰 때, 부위(등심, 안심)에 따라 다르게 써는 것이 세그멘테이션입니다. 고기 관리는 편하지만 포장하기가 애매합니다. 반면 무조건 가로세로 3cm 깍둑썰기를 해버리는 것이 페이징입니다. 부위는 섞일지 몰라도 상자에 담아 유통(메모리 할당)하기에는 우주에서 가장 완벽한 형태입니다.
Ⅳ. 실무 적용 및 기술사적 판단
실무 시나리오
-
시나리오 — 페이지 테이블 크기 폭발로 인한 메모리 낭비 (OOM): 32비트 OS 시절, 4KB 페이지를 쓰면 4GB 메모리를 커버하기 위해 100만 개의 페이지가 필요했다. 페이지 테이블 엔트리 1개가 4바이트면, 프로세스 1개당 '순수 지도를 그리는 데만' 4MB의 메모리를 먹었다. 프로세스가 1,000개 떠 있으면 지도 쪼가리가 램을 4GB나 잡아먹어 서버가 죽어버렸다.
- 원인 분석: 1차원 배열(Single-level) 페이지 테이블의 치명적 한계다. 안 쓰는 주소 영역(가운데 텅 빈 힙-스택 사이 공간)도 무조건 배열의 칸을 만들어 0으로 채워둬야 했기 때문이다.
- 아키텍처 적용 (다단계 페이징, Hierarchical Paging): 페이지 테이블을 책의 '목차'처럼 2단계, 3단계로 쪼갰다. 안 쓰는 챕터(메모리 영역)는 아예 2단계 페이지 테이블을 메모리에 생성하지 않는다(동적 할당). 이를 통해 페이지 테이블이 차지하는 메모리 용량을 수십 분의 일로 다이어트시켜 현대 64비트 시스템의 무한한 주소 공간을 지탱하게 만들었다.
-
시나리오 — Huge Page를 통한 페이지 테이블 워크(Page Walk) 오버헤드 최적화: 1TB 램을 쓰는 Oracle DB 서버. 4KB 페이징을 쓰니까, MMU가 주소를 번역하러 메모리의 다단계 페이지 테이블을 4번이나 거쳐서 내려가야 했다 (Page Walk). 번역 시간이 실제 데이터 읽는 시간보다 길어지는 주객전도 발생.
- 대응 (기술사적 가이드): 4KB 대신 2MB 또는 1GB짜리 Huge Page를 세팅한다. 페이지 크기가 500배 커지면, 페이지의 개수는 1/500로 줄어든다. 다단계 페이지 테이블의 깊이(Depth)가 4단계에서 2단계로 줄어들어 MMU의 번역 속도가 빛의 속도가 된다. 게다가 TLB 캐시 안에 모든 매핑이 다 들어가므로 캐시 적중률(Hit Ratio)이 99.9%를 찍으며 DB 트랜잭션 속도가 수직 상승한다.
의사결정 및 튜닝 플로우
┌───────────────────────────────────────────────────────────────────┐
│ 메모리 페이징 및 페이지 크기(Page Size) 튜닝 플로우 │
├───────────────────────────────────────────────────────────────────┤
│ │
│ [새로운 클라우드 인스턴스에서 애플리케이션 메모리 구조 튜닝] │
│ │ │
│ ▼ │
│ 애플리케이션이 거대한 연속된 메모리를 장시간 사용하는가? (예: DB, JVM) │
│ ├─ 예 ─────▶ [Transparent Huge Pages (THP) 제어 검토] │
│ │ - 2MB Huge Page 활성화로 TLB Miss를 완벽히 차단. │
│ │ - 단, JVM 같은 경우 OS의 THP(자동)와 충돌할 수 있으므로│
│ │ OS THP는 끄고, 앱(JVM) 파라미터에서 명시적 활성화 권장│
│ └─ 아니오 (웹 서버, 수만 개의 자잘한 컨테이너 프로세스) │
│ │ │
│ ▼ │
│ [기본 4KB 페이징 시스템 유지] │
│ - 작은 프로세스에 Huge Page를 주면 프로세스 끝에 수 MB의 빈 공간이 │
│ 남는 '내부 단편화(Internal Fragmentation)' 폭탄이 터져 OOM 발생. │
└───────────────────────────────────────────────────────────────────┘
[다이어그램 해설] "페이징 시스템은 OS가 알아서 하는 거니까 개발자는 몰라도 된다?" 절대 아니다. OS가 4KB로 썰어놓은 걸 무시하고, 개발자가 Java 배열을 수 기가바이트 단위로 랜덤 액세스하면 하드웨어의 TLB가 터져나가 성능이 10배 느려진다. 아키텍트는 캐시 친화적인(Cache-friendly) 메모리 접근 패턴과 적절한 페이지 사이즈 튜닝을 통해 하드웨어를 달래야 한다.
도입 체크리스트
-
공유 페이지 (Shared Page): 프로세스 100개가 크롬(Chrome)을 띄웠을 때, 크롬의 실행 코드(Text 영역) 100MB가 메모리에 100번 복사되면 10GB가 날아간다. OS는 물리 프레임 테이블에 크롬 코드를 딱 1번(100MB)만 올려두고, 100개 프로세스의 페이지 테이블이 모두 그 1개의 물리 프레임을 가리키도록 'Read-Only 공유' 처리를 했는지(메모리 맵핑 아키텍처) 이해하고 있는가?
-
📢 섹션 요약 비유: 작은 상자(4KB)는 물건을 담고 쌓기 편하지만, 수백만 개의 상자 번호를 장부에 적는 일(페이지 테이블)이 고통스럽습니다. 가끔은 냉장고만 한 큰 상자(Huge Page)를 섞어 써야 창고 관리자(MMU)가 퇴근할 수 있습니다.
Ⅴ. 기대효과 및 결론
정량/정성 기대효과
| 구분 | 연속 할당 (가변 분할) | 페이징 아키텍처 (Paging) | 개선 효과 |
|---|---|---|---|
| 정성 (외부 단편화) | OOM 잦음. 램 중간중간 구멍 발생 | 외부 단편화 100% 소멸 | 조각난 램을 영끌해서 쓸 수 있음 (메모리 활용 극대화) |
| 정량 (프로세스 적재) | 연속된 빈 공간 찾기에 $O(N)$ 지연 | Free List에서 아무 프레임이나 빼옴 $O(1)$ | 프로세스 로드 속도 및 멀티태스킹 스위칭 속도 향상 |
| 정성 (가상 메모리) | 디스크 스왑(Swap) 관리가 극도로 복잡 | 페이지 단위로 스왑 인/아웃 완벽 지원 | 현재 우리가 아는 완벽한 형태의 가상 메모리 완성 |
미래 전망
- 5단계 페이지 테이블 (5-Level Paging): 서버의 물리 메모리가 테라바이트(TB) 단위를 넘어서 페타바이트(PB)를 향해 가면서, 인텔은 최신 서버 칩셋(Ice Lake)에 무려 128PB의 가상 메모리를 지원하는 5단계 페이징을 도입했다. 주소 변환에 걸리는 단계가 4단계에서 5단계로 깊어졌지만, 하드웨어 캐시(TLB)의 극단적 성능 발전으로 그 오버헤드를 찍어 누르고 있다.
결론
페이징 시스템과 프레임 테이블은 "프로그램은 무조건 연속된 공간에 존재해야 한다"는 인간의 직관적 강박을 깨부순 혁명이다. 책을 갈기갈기 찢어 허공에 흩뿌리고도(프레임), 읽을 때마다 마법의 안경(페이지 테이블)을 쓰면 완벽하게 이어진 책으로 보이는 이 가상화(Virtualization) 기술이야말로 폰 노이만 아키텍처가 낳은 최고의 소프트웨어적 기만술이다. 이로 인해 메모리의 파편화(외부 단편화)라는 악마는 지옥으로 영구 추방되었고, 클라우드의 무한한 자원 할당이 가능해졌다.
- 📢 섹션 요약 비유: 산산조각 난 유리 조각(물리 프레임)들을 스테인드글라스 창문(페이지 테이블)에 끼워 넣으니, 밖에서 볼 때 하나의 아름답고 완벽한 그림(가상 메모리)으로 탄생한 운영체제의 예술 작품입니다.
📌 관련 개념 맵 (Knowledge Graph)
| 개념 명칭 | 관계 및 시너지 설명 |
|---|---|
| Page Table (페이지 테이블) | 유저 프로세스가 들고 있는 가상 주소를 물리 주소로 번역해 주는, 프로세스마다 1개씩 배정된 내비게이션 |
| Frame Table (프레임 테이블) | 운영체제가 시스템 전체 물리 RAM의 빈 공간과 사용 현황을 추적하는 단 1개의 거대한 마스터 장부 |
| Internal Fragmentation (내부 단편화) | 페이징의 유일한 단점. 4KB로 무식하게 썰다 보니 프로세스의 마지막 꼬투리에 발생하는 약간의 버려진 공간 |
| MMU (Memory Management Unit) | CPU 내부에 박혀서, 1나노초의 지연 없이 페이지 테이블을 룩업하여 주소를 번역해 주는 기적의 하드웨어 |
| Swapping (요구 페이징) | 램에 있는 프레임 중 안 쓰는 것을 디스크로 던져버리고(Swap Out), 필요할 때 그 페이지를 다시 램의 빈 프레임에 올리는 가상 메모리의 정수 |
👶 어린이를 위한 3줄 비유 설명
- 긴 기차 장난감(프로그램)을 통째로 넣을 긴 상자(연속 메모리)를 찾으려니 방안에 남는 공간이 없었어요.
- 그래서 똑똑한 철수는 기차를 똑같은 크기의 레고 블록(페이지) 단위로 다 부숴버렸어요!
- 부순 블록들을 책상 서랍, 장난감통 등 흩어진 좁은 공간(프레임)에 마구 쑤셔 넣고, 나중에 '보물지도(페이지 테이블)'를 보고 순서대로 꺼내어 다시 기차로 조립하며 놀았답니다!