1P by neo 2달전 | favorite | 댓글 1개
  • 사람들은 복잡한 것과 단순히 복잡한 것을 구분함. 복잡성은 흥미롭다고 여겨지지만, 복잡함은 해롭다고 여겨짐. x86_64 CPU 설정 과정은 대부분 복잡함.
  • BIOS에 의해 로드된 부트 섹터에서 CPU를 16비트 실모드에서 64비트 롱모드로 설정하는 방법을 설명함. 이 설정은 기본적인 것이며, 더 많은 작업이 필요함.
  • Intel 64 및 IA-32 아키텍처 소프트웨어 개발자 매뉴얼, 어셈블러(nasm 사용), QEMU가 필요함. x86 어셈블리와 nasm 문법을 알고 있어야 함.

시작점: BIOS

  • 리셋 후 x86 CPU는 "실모드"에 있음. 이 모드는 16비트 기본 피연산자 크기를 가짐. 세그먼테이션을 사용하여 1MB 메모리를 주소 지정할 수 있음.
  • BIOS 후 첫 번째 실행 코드는 부트 섹터에 있음. BIOS는 시스템에서 0xaa55로 끝나는 첫 번째 섹터를 찾고, 해당 부트 섹터를 메모리 주소 0x7c00에 로드함.
  • BIOS는 512바이트를 제공하며, 이를 사용하여 부트로더의 나머지 부분을 부트스트랩해야 함.

부트 섹터 설정

  • 간단한 부트 섹터를 설정하여 BIOS 루틴을 사용해 화면에 메시지를 출력하고 멈추게 함. 이를 통해 도구가 작동하는지 확인할 수 있음.
  • 어셈블리 코드와 Makefile을 사용하여 부트 섹터를 설정함.

1단계 – 디스크에서 2단계 로드

  • 부트로더를 두 단계로 나눌 수 있음. 1단계는 부트 섹터의 코드로, BIOS가 로드하는 모든 것임. 1단계의 유일한 목적은 2단계를 메모리에 로드하는 것임.
  • 2단계에서는 16비트 실모드에서 32비트 보호 모드로 전환함. 보호 모드에서는 BIOS 루틴을 사용할 수 없음. 디스크에서 섹터를 로드하는 것은 훨씬 더 복잡해짐.
  • BIOS를 사용하여 디스크에 접근하는 방법을 설명함.

32비트 보호 모드

  • CPU를 실모드(16비트)에서 보호 모드(32비트)로 전환함. 보호 모드에서는 세그먼테이션을 사용하여 메모리 보호를 구현함.
  • 보호 모드로 전환하기 전에 글로벌 디스크립터 테이블(GDT)을 정의해야 함. GDT는 메모리에 연속적인 구조로 정의됨.
  • GDT를 정의하고 보호 모드로 전환하는 방법을 설명함.

64비트 롱모드

  • 롱모드로 전환하기 전에 CPU는 보호 모드에 있어야 하며 페이징이 활성화되어야 함. 보호 모드는 이미 설정되었으나 페이징이 필요함.
  • 페이징은 세그먼테이션을 대체하여 가상 주소 공간, 권한 등을 관리함. 롱모드 전환을 위한 페이지 테이블을 생성하는 방법을 설명함.
  • 롱모드 전환을 위한 GDT를 정의하고, 보호 모드에서 롱모드로 전환하는 방법을 설명함.

GN⁺의 정리

  • 이 글은 x86_64 CPU를 16비트 실모드에서 64비트 롱모드로 설정하는 과정을 자세히 설명함. 이를 통해 부트로더와 운영체제 커널 개발에 대한 이해를 높일 수 있음.
  • BIOS, 부트 섹터, 보호 모드, 롱모드 등 다양한 개념을 다루며, 각 단계별로 필요한 어셈블리 코드와 설정 방법을 제공함.
  • 이 글은 운영체제 개발에 관심 있는 사람들에게 유용하며, 특히 x86 아키텍처에 대한 깊은 이해를 제공함. 비슷한 기능을 가진 프로젝트로는 "Writing a Simple Operating System – from Scratch"가 있음.
Hacker News 의견
  • 직접 보호 모드로 전환하지 않고도 긴 모드로 전환할 수 있는 방법이 있음
    • 부트섹터에 작은 64비트 커널을 로드하는 부트로더를 만들었음
    • 디스크에서 커널을 로드하고 VESA 모드를 설정하는 과정 포함
  • 80286은 16비트 레지스터인 MSW를 가지고 있고, 80386은 이를 32비트 CR0로 확장했음
    • 64비트 긴 모드는 EFER MSR을 추가하고 CR0를 64비트로 확장했음
    • 현재 CR0의 11비트와 EFER의 8비트만 사용 중임
    • 왜 Intel/AMD가 기존 레지스터의 빈 비트를 사용하지 않았는지 궁금함
  • 이 글에서 가장 불필요하게 복잡한 부분은 Makefile과 링커 스크립트임
    • NASM은 평면 바이너리 출력을 생성할 수 있지만, 이를 사용하는 것이 너무 "해킹적"이라고 생각하는 듯함
  • CPU를 올바른 모드로 전환하기 위해 필요한 모든 단계가 불필요하게 복잡함
    • 모두 하위 호환성을 위해 필요한 단계로 보임
    • Intel이 처음부터 올바른 모드로 시작할 수 있는 플래그나 명령을 제공할 수 있었을 것임
    • 또는 모든 하위 호환성을 제거할 수 있었음
    • ARM64도 비슷한 문제가 있는지 연구한 기억이 있음
    • 처음부터 64비트로 설계된 CPU가 있는지 궁금함
    • Itanium의 목표/설계가 그런 것이었을 것임
  • 새로운 부트로더 접근 방식을 만든 이유를 이해하지 못하는 UEFI 지지자들이 있을 수 있음
    • 글쓴이가 말하듯이, "여기까지 왔다면 멋진 일임"
  • UEFI가 얼마나 오래되었는지 궁금함
    • 긴 모드와 함께 BIOS를 폐기하지 않은 것이 아쉬움
  • 이 부트 절차가 EFI/UEFI와 호환되는지 궁금함
    • UEFI 감독자가 실제 하드웨어에서 실모드/보호모드/긴 모드를 에뮬레이트하는지 궁금함
  • ARM에서 이 과정이 더 간단한지 궁금함