os computer_science cs 운영체제 OS 가상메모리

[CS/Computer Science][운영체제 / OS] 가상메모리

Kwangjin Park

May 13, 2025 · 9 min read

Follow

1. 개요

  • “CPU와 프로세스가 메모리 몇 번지에 무엇이 저장되어 있는지 모두 알고 있다?” ⇒ 그렇지 않음
    1. 위의 말처럼, 모든 정보를 다 알고 있기 위해서는 레지스터(CPU 내부 저장공간)가 메모리만큼 커야함 → 실제로는 훨씬 작은 용량만을 갖고 있음
    2. 메모리 정보는 시시각각 변할 수 있음
      • 새로운 프로세스는 새롭게 메모리에 적재
      • 사용되지 않는 프로세스는 메모리에서 삭제
      • 이처럼, 실시간으로 변하는 정보를 모두 기억하고 있기는 어려움
    3. 그렇기 때문에, CPU는 메모리에 적재된 프로세스의 주소를 인식하고 관리하나? → ‘가상 메모리의 필요성’

2. 물리 주소와 논리 주소

  • 물리 주소(Physical address): 하드웨어 상, 메모리의 실제 주소
  • 논리 주소(Logical address): CPU와 프로세스가 이용하는 주소 체계, 프로세스마다 부여되는 0번지부터 시작하는 주소 체계
    • 각각의 프로세스는 각각의 논리주소를 지님
    • 각 프로세스의 논리주소의 번지수는 겹칠 수 있음
  • 하드웨어 상의 메모리와 상호작용하기 위해서는, 반드시 논리 주소↔물리 주소 간 변환이 이루어져야 함
    • 마치, 다른 언어로 소통하면 당연히 말이 안 통하는 사람처럼 (CPU는 논리 주소로 말하고, 메모리는 물리 주소로 말하고)
    • MMU(Memory Management Unit, 메모리 관리 장치): 논리 주소↔물리 주소간 주소 변환을 위해 존재하는 하드웨어
      • 메모리와 CPU 사이에 위치
      • CPU가 이해하는 논리주소를 메모리가 이해하는 물리주소로 변환해줌 image1

3. 스와핑과 연속 메모리 할당

  • MMU를 기준으로 물리 주소와 논리 주소가 서로 변환됨 → 이를 통해 프로세스가 메모리 할당 수행

  • 가장 기본적인 메모리 할당 방식: 스와핑 / 연속 메모리 할당

스와핑

  • 메모리에 적재된 프로세스들 중, 현재 실행되지 않는 프로세스를 임시로 보조기억장치로 쫒아내는 작업
    • 대상 프로세스: 대기 상태가 된 프로세스 / 오랫동안 사용하지 않는 프로세스 등
    • 스왑 영역(swap space): 현재 실행되지 않는 프로세스들을 임시로 쫒아낸 보조기억장치 내의 영역명
      • 스왑 아웃: 현재 실행되지 않는 프로세스가 메모리 → 스왑 영역으로 옮겨지는 것
      • 스왑 인: 스왑 영역에 있는 프로세스 → 메모리로 옮겨오는 것
      • 스왑 아웃 되었다가 스왑 인이 된다면, 스왑 아웃 이전의 물리 주소와는 다른 주소에 적재될 수 있음
  • 스와핑(swapping): 프로세스를 쫒아내면, 메모리 상 빈 공간이 생김 → 이곳에 다른 프로세스를 적재하여 실행하는 메모리 관리 방식 image2

연속 메모리 할당과 외부 단편화

  • 연속 메모리 할당: 프로세스에 연속적인 메모리 공간을 할당하는 방식
    • ex) 프로세스 A는 A의 크기만큼 메모리 주소를 할당 받아 배치 → 프로세스 B는 A 이후에 B의 크기만큼 연속적으로 배치 image3
  • 외부 단편화 문제(external fragmentation)
    • 연속 메모리 할당의 가장 큰 문제는 외부 단편화 문제를 내포하고 있다는 점
    • ex) 아래 사진과 같이 메모리가 할당되어 있다고 가정
      • 현재 이 메모리에 새로운 프로세스가 적재될 수 있는 빈 공간은 50MB
      • 하지만 크기가 50MB인 프로세스를 아래 메모리에 적재할 수 없음 → 남은 공간이 20/30 각각 분리되어 남아있기 때문 → 메모리 낭비 초래 image4
    • 외부 단편화 문제가 발생하는 조건
      • 프로세스들이 메모리에 연속적으로 할당되는 환경에서, 프로그램의 실행과 종료를 반복하며 메모리 사이 사이에 빈 공간이 생김

4. 페이징을 통한 가상 메모리 관리

  • 스와핑과 연속 메모리 할당의 두 가지 문제
    1. 외부 단편화 문제
    2. 물리 메모리보다 더 큰 프로세스는 실행 불가능

가상 메모리의 등장

  • 위와 같이 스와핑과 연속 메모리 할당의 두가지 문제를 해결하기 위한 메모리 관리 기술이 바로 가상 메모리
  • 가상 메모리(virtual memory)
    • 실행하고자 하는 프로그램의 일부만 메모리에 적재 → 실제 메모리보다 더 큰 프로세스를 실행할 수 있도록
    • 다양한 방식으로, 메모리를 실제 크기보다 더 크게 보이게 하는 기술
      1. 보조기억장치의 일부를 메모리처럼 활용
      2. 프로세스의 일부만 메모리에 적재
    • 가상 주소 공간(virtual address space): 가상 메모리 기법으로 생성된 논리 주소 공간
  • 가상 메모리 관리 기법의 종류
    • 페이징 - 많은 운영체제에서 더 범용적으로 활용
    • 세그멘테이션

페이징

  • 페이징(paging)이란?
    1. 프로세스의 논리 주소 공간 → 페이지라는 일정한 단위로 나누고,
    2. 메모리의 물리 주소 공간 → 페이지와 동일한 크기프레임이라는 일정한 단위로 나눈 뒤,
    3. 페이지를 프레임에 할당함
      • 페이지는 물리 메모리 내에 불연속적으로 할당 가능 image5
  • 페이징과 스와핑
    • 페이징을 사용하는 시스템에서는, 프로세스 전체가 아닌 페이지 단위로 스왑 아웃/인 작업이 발생
    • 페이징 시스템에서의 스왑 아웃/인: 페이지 아웃 / 페이지 인

세그멘테이션

  • 프로세스를 일정한 크기의 페이지 단위가 아닌 가변적 크기의 세그먼트(segment) 단위로 분할 하는 방법
  • 세그먼트는 일정한 단위로 분할되지는 않지만, 유의미한 논리적 단위로 분할 image6

페이지 테이블

  • 페이지 테이블?
    • 프로세스를 구성하는 페이지는 물리 메모리 내 불연속적으로 배치될 수 있음
      • 이럴 경우, CPU는 다음으로 실행할 페이지의 위치를 찾기가 어려움 (어떤 페이지가 어떤 프레임에 적재되었는지 모두 알고 있기는 어려움)
      • 이를 해결하기 위해 ‘페이지- 적재된 프레임’을 짝지어주는 페이지 테이블 활용
    • 페이지 테이블에는 페이지 번호와 실재 적재된 프레임 번호가 대응되어 있음 image7
  • 페이지 테이블의 구성요소
    • 페이지 테이블 엔트리(PTE, Page Table Entry): 페이지 테이블을 구성하는 각각의 행
    • 페이지 테이블 엔트리에 담기는 정보의 종류
      • 가장 중요: ‘페이지 번호 - 실재 적재된 프레임 번호’ 대응 데이터
      • 그 외 대표적 정보: 프레임 번호, 유효 비트, 보호 비트, 참조 비트, 수정 비트 등
        1. 유효 비트(valid bit): 해당 페이지에 접근이 가능한지 여부를 담은 정보(중요)
          • 현재 페이지가 보조기억장치에 저장되어 있는지, 메모리에 저장되어 있는지
          • 페이지가 메모리에 적재되어 있다면 1, 그렇지 않다면 0으로 표기
        2. 페이지 폴트(page fault)
          • 메모리에 적재되지 않은 페이지(=유효 비트가 0인 페이지)에 접근하려 할 때 발생하는 예외(Exception)
        3. 보호 비트(protection bit)
          • 페이지 보호 기능을 위해 존재하는 비트
          • 읽기: r / 쓰기: w / 실행: x 의 조합으로 페이지 접근 권한 제한하여 보호
        4. 참조 비트(reference bit)
          • CPU가 해당 페이지에 접근한 적이 있는지 여부를 나타낸 비트
          • 페이지 적재 이후,
            • CPU가 읽거나 쓴 페이지: 1
            • CPU가 한 번도 읽거나 쓰지 않은 페이지: 0
        5. 수정 비트(modified bit, 더티 비트)
          • 해당 페이지에 데이터를 쓴 적이 있는지 여부를 나타낸 비트
            • 수정 비트가 1: 변경된 적이 있는 페이지
              • 페이지를 메모리에서 삭제해야 할 때, 페이지의 수정내역을 보조기억장치에도 반영해 두어야 함 → 보조 기억 장치에 대한 쓰기 작업 필요
            • 수정 비트가 0: 변경된 적이 없는 페이지
              • 이 경우에는 보조기억장치에 반영할 수정 내역이 없음 → 쓰기 작업 없이 페이지를 메모리에서 삭제만 하면 됨 image8

내부 단편화

  • 페이징을 통해 외부 단편화 문제를 해결할 수 있지만, 이의 반대급부로 내부 단편화라는 또 다른 문제를 야기할 수 있음
  • 내부 단편화?
    • 모든 프로세스가 페이지의 크기로 딱 맞게 잘리지 않음 (=모든 프로세스의 크기가 페이지 크기의 배수가 아님)
    • 이러한 현상으로 인해 발생하게 되는 메모리 낭비: 내부 단편화(internal fragmentation) image9

페이지 테이블 베이스 레지스터(PTBR)

  • 프로세스 실행을 위해서는 해당 프로세스의 테이블 메모리가 적재된 위치를 알아야 함 → 이를 가리기는 특별한 레지스터: PTBR(Page Table Base Register)
  • PTBR은 프로세스 마다 갖는 정보 → 각 PCB에 기록, 다른 프로세스로 문맥 교환 시 변경 image10
  • 운영체제에서, PTBR은 가급적 메모리에 적재하는 것을 지양함
    • 이유 1: 메모리 접근 횟수가 많아짐
      • 모든 프로세스의 PTBR이 메모리에 적재되어 있다면, 실제 프레임에 접근하기 위해서는 한 프레임 당 두 번씩 메모리에 접근해야됨
        1. 페이지 테이블에 접근하기 위해 한 번
        2. 실제 프레임에 접근하기 위해 한 번 → 메모리에 접근하는 시간이 두 배로 불어남
      • 해결책: TLB(Translation Look-aside Buffer) → “페이지 테이블의 캐시 메모리”
        • ‘참조 지역성의 원리’에 근거해 자주 사용할 법한 페이지 위주로 페이지 테이블의 일부 내용 저장
        • TLB 히트: CPU가 접근하려는 논리 주소의 페이지 번호가 TLB에 있는 경우, TLB가 CPU에 해당 페이지 번호를 알려주는 것 → 이 경우에는 한 번만 메모리에 접근하면 됨
        • TLB 미스: 페이지 번호가 TLB에 없는 경우, 페이지에 적재된 프레임을 알아내기 위해 메모리 내의 페이지 테이블에 접근하는 수밖에 없음 → 추가적인 메모리 접근 필요 ⇒ 메모리 접근 횟수를 낮추려면 TLB 히트율을 높여야 함 image11
    • 이유 2: 메모리 용량 비효율
      • 프로세스 크기가 커지면 자연스레 페이지 테이블의 크기도 커짐 → 모든 페이지 테이블 엔트리를 그대로 메모리에 두는 것은 매우 비효율적인 메모리 관리
      • 해결책: 계층적 페이징(Hierarchical paging)
        • 간단하게 말하면, 페이지 테이블을 페이징하는 방식
        • 여러 단계의 페이지를 둠 → “다단계 페이지 테이블 기법”
        • 과정(아래 사진 예시)
          1. 우선, 프로세스의 페이지 테이블을 여러 개의 페이지로 자름
          2. 이후, CPU와 가까이 위치한 바깥 쪽에 페이지 테이블(Outer 페이지 테이블)을 하나 더 두어 잘린 페이지 테이블들을 가리키게 함
          3. 이렇게 구성하게 되면, Outer 메모리 테이블만 메모리에 유지하여 언제든 페이지 테이블에 접근 가능해짐
            • 잘린 테이블의 일부가 보조기억장치에 있어도, Outer 페이지 테이블을 통해 언제든 접근 가능 image12

페이징 주소 체계

  • 하나의 페이지에는 여러 주소가 포함
  • 페이징 시스템의 논리 주소: <페이지 번호, 변위>
    • 페이지 번호(page number): “몇 번째 페이지에 접근할지”
    • 변위(offset): 접근하는 주소가 페이지(프레임)에서 얼마나 떨어져 있나 image13
    • 페이지 테이블을 통해, 논리주소 "페이지 번호, 변위" → 물리주소"프레임 번호, 변위"로 변환
  • ex) 하나의 페이지 및 프레임이 4개의 주소로 구성되어 있는, 아래와 같은 상황 가정
    • CPU가 <5, 2>라는 논리 주소에 접근한다면?(5번 페이지, 변위 2)
      1. 현재 5번 페이지는 1번 프레임에 있음(페이지 테이블 정보)
      2. CPU는 이에 따라 1번 프레임, 변위 2에 접근
      3. 1번 프레임은 물리 주소 공간 상에서는 8번지에서 시작하므로
      4. CPU는 8번지에서 변위 2를 더한 10번지에 접근 image14

5. 페이지 교체 알고리즘

  • 요구 페이징(Demand Paging): 처음부터 모든 페이지를 적재하지 않고, 메모리에 필요한 페이지만을 적재하는 기법
  • 발생 양상
    1. CPU가 특정 페이지에 접근하는 명령어 실행
    2. 유효 비트가 1일 경우
      • CPU는 페이지가 적재된 프레임에 접근
    3. 유효 비트가 0인 경우
      • 페이지 폴트 발생 → 페이지 폴트 루틴을 통해 해당 페이지를 메모리로 적재 → 유효 비트 1로 설정
    4. 과정 반복

      • 페이지 폴트의 종류 - 크게 아래와 같이 구분
      • 메이지 페이지 폴트
        • 입출력 작업이 필요한 페이지 폴트
        • CPU가 접근하고자 하는 페이지가 물리 메모리에 없을 경우 발생
      • 마이너 페이지 폴트
        • 입출력 작업이 불필요한 페이지 폴트
        • CPU가 접근하고자 하는 페이지가 물리 메모리에 존재하지만, 페이지 테이블 상에 반영되지 않은 경우 발생 → 일반적으로 성능 상 악영향이 메이저 페이지 폴트에 비해 덜함
  • 순수 요구 페이징(pure demand paging): 아무 페이지도 메모리에 적재하지 않고 무작정 프로세스를 실행하는 것
    • 이 경우, 첫 명령어를 실행한 순간부터 페이지 폴트 발생

  • 페이지 교체 알고리즘(Page replacement algorithm)
    • 여러 번의 요구 페이징을 거치며 수많은 페이지들이 메모리에 적재될 것임 → 언젠가는 메모리가 가득찬다면, 일부 페이지를 스왑 아웃 해야함
    • 여기서, 스왑 아웃 해낼 페이지를 선택하는 방법페이지 교체 알고리즘
    • 페이지 교체 알고리즘은, 곧 컴퓨터 전체 성능과 직결됨 → 페이지 폴트의 발생 빈도를 결정해주기 때문
      • 지나친 페이지 교체를 유발하는 알고리즘은 컴퓨터 성능 하락의 요인임 → “스래싱(thrashing) 문제 발생”
  • 페이지 교체 알고리즘의 종류
    1. FIFO 페이지 교체 알고리즘
      • 선입선출, 메모리에 가장 먼저 적재된 페이지부터 스왑 아웃하는 알고리즘
      • 간편 및 간단한 구현
      • 초기부터 줄곧 참조하고 있는 페이지를 스왑 아웃 시킬 우려
    2. 최적 페이지 교체 알고리즘
      • 앞으로의 사용 빈도가 가장 낮은 페이지를 교체하는 알고리즘 → “낮은 페이지 폴트율” 보장을 위한 알고리즘
      • “앞으로 가장 적게 사용할 페이지” 예측이 어렵기에, 실제 구현이 어려움
    3. LRU 페이지 교체 알고리즘
      • 그간 가장 적게 사용한 페이지를 교체하는 알고리즘
      • 보편적으로 활용, 이를 기반으로 한 다양한 파생 알고리즘 존재
chat_bubble 0

chat_bubble 댓글남기기

댓글남기기