컴퓨터 시스템 : CSAPP 9장 - 서술형 문제를 통해 이해하기 Part.2

지난 포스팅에 이어서 서술형 문제에 대한 답을 작성해 보고 이에 대해 수정이 필요한 내용을 담아 정리했다.


가상 메모리 기반의 메모리 보호(Memory Protection)

  1. 주소 공간의 격리 (Address Space Isolation)
    • 각 프로세스는 고유한 가상 주소 공간을 가진다.
    • 이 때문에 한 프로세스가 다른 프로세스의 메모리를 직접 접근하는 것이 불가능하다.
    • 동일한 주소(예: 0x400000)가 여러 프로세스에 존재하더라도, 실제 물리 주소는 완전히 다를 수 있다.
  2. 접근 권한 제어 (Access Permissions)
    • 각 페이지 테이블 항목에는 권한 비트(read/write/execute)가 포함되어 있다.
    • 예를 들어, 코드 영역은 실행만 가능하고, 데이터 영역은 쓰기가 가능하며, 읽기 전용 데이터는 쓰기를 허용하지 않는다.
    • 사용자 모드(user mode)에서 커널 영역 메모리 접근을 시도하면 보호 오류(fault)가 발생한다.
  3. 하드웨어 차원의 감시
    • MMU는 페이지 테이블의 권한 비트를 참조하여 허용되지 않은 접근을 자동 차단한다.
    • 권한 위반이 발생하면, CPU는 운영체제에 페이지 폴트 예외(interrupt)를 발생시켜 해당 프로세스를 종료하거나 예외 처리한다.

안정성과 보안에 대한 기여

  • 프로그램 버그로 인한 오동작 방지
    → 예: 버그로 잘못된 주소를 참조해도 다른 프로세스를 침범하지 않음.
  • 보안 취약점 완화
    → 악성 코드가 운영체제나 다른 사용자 프로세스의 데이터를 훔치거나 수정하는 것을 방지.
  • 커널 보호
    → 커널 메모리는 사용자 모드에서 접근할 수 없도록 보호되어 시스템의 안정성을 유지함.

가상 메모리에서의 공유 메모리 구현

  1. 메모리 매핑(mmap)
    • mmap() 시스템 호출을 이용하면 파일이나 익명 메모리 영역을 가상 주소 공간에 직접 매핑할 수 있다.
    • 이 매핑은 여러 프로세스에서 동일한 파일 혹은 메모리 객체에 대해 수행하면, 공통된 물리 메모리 페이지를 공유하게 된다.
    • 이로 인해 공유 메모리처럼 데이터를 읽고 쓸 수 있는 배열 형태의 인터페이스가 제공된다.
  2. 운영체제의 역할
    • 운영체제는 mmap() 요청을 처리하여 페이지 테이블에 공유 가능한 물리 페이지 번호를 여러 프로세스의 가상 주소에 연결한다.
    • 접근 권한(read/write)을 관리하고, 필요에 따라 Copy-on-Write(COW) 전략을 통해 보호 기능도 제공한다.
  3. 공유 메모리 객체 생성 방식
    • 파일 기반 공유: 일반 파일을 기반으로 매핑.
    • 익명 메모리 공유: MAP_ANONYMOUS 옵션과 shm_open/shm_unlink 등을 이용하여 파일 없이 공유.

공유 메모리의 장점

  • 빠른 통신: 프로세스 간 데이터 복사 없이 메모리 접근만으로 데이터 교환 가능 → IPC 중 가장 빠름.
  • 자원 절약: 하나의 물리 페이지를 여러 프로세스가 공유함으로써 메모리 사용량을 줄일 수 있음.

발생할 수 있는 문제점

  • 동기화 필요: 공유된 메모리를 동시에 접근하는 경우, 데이터 일관성을 보장하기 위해 뮤텍스, 세마포어 등 동기화 메커니즘이 필요하다.
  • 보안 위험: 실수로 다른 프로세스의 데이터를 덮어쓸 수 있고, 접근 권한이 잘못 설정되면 정보 유출 가능성도 있음.

. mmap: 메모리 매핑

  • mmap()은 파일이나 익명 메모리 객체를 프로세스의 가상 주소 공간에 매핑하는 시스템 호출이다.
  • 이 함수는 파일의 내용을 마치 배열처럼 접근할 수 있도록 하거나, 프로세스 간 공유 메모리 IPC(Inter-Process Communication)를 구현하는 데 쓰인다.
  • 페이지 테이블에 공유 가능 또는 읽기 전용/쓰기 가능 등의 권한을 설정하여, 메모리 보호와 효율적 공유를 동시에 실현할 수 있다.

2. fork: 프로세스 복제

  • fork()는 현재 프로세스를 거의 완전히 복사한 자식 프로세스를 생성한다.
  • 그러나 실제 메모리를 처음부터 복사하지 않고, 페이지 테이블만 복제하고 물리 메모리는 그대로 공유한다.
  • 이후 한쪽에서 데이터를 수정하려 할 때만 해당 페이지를 복사하는 Copy-On-Write (COW) 기술을 사용하여 메모리 효율성을 극대화한다.
  • 이는 fork() + execve() 조합에서 특히 유용함.

3. execve: 프로세스 메모리 초기화 및 교체

  • execve()는 현재 프로세스의 주소 공간을 완전히 제거하고, 새로운 실행 파일로 대체한다.
  • 새로운 실행 파일의 코드, 데이터, 스택, 힙 등이 새롭게 가상 메모리에 로드되며, 기존의 메모리는 모두 폐기된다.
  • 이는 프로그램을 완전히 다른 것으로 "변신"시키는 것이며, 보안적인 측면에서 매우 중요하다 (예: 사용자 인증 이후 안전한 실행 환경 확보).

종합적 기여

  • 효율성: fork()의 Copy-On-Write, mmap()의 파일 매핑은 메모리와 디스크 자원을 절약함.
  • 보안: execve()는 프로세스 메모리를 완전히 초기화하여 코드 인젝션, 데이터 유출 등의 보안 위험을 제거함.
  • 유연성: 다양한 방식의 프로세스 생성, 실행, 데이터 공유가 가능함.