본문 바로가기

Computer Science/Computer Systems

[Lecture 6] Linking and Loading - Part I

#Linking and Loading - Big Picture

The compilation, Linking and Loading in a typical System

#Compiler and Assembler

  • Preprocessor는 #include 파일들의 텍스트 삽입을 수행한다
  • 컴파일러는 다음과 같은 기호 이름을 확인한다:
    • 로컬 자동 변수 (Local automatic variables), 함수 매개 변수
    • Field names in structures
  • 어셈블러가 relative branches들에 대한 특정 레이블을 확인한다.
  • 결과로 나온 relocatable .o 파일은 범위가 전역인 모든 함수와 변수에 대한 기호 이름을 유지한다

#Relocatable Object Files – Text Section

  • 여러개의 섹션을 가지고 있음
  • 각 섹션은 0에서 시작하는 것처럼 레이아웃됨
  • Relocation records를 포함함: 플레이스홀더 및 실제 주소를 알고 나면 플레이스홀더를 패치하는 방법에 대한 meta information

#Executable and Linkable Format (ELF)

  • ELF는 시스템 V와 Linux [URL]를 포함한 derived systems에서 사용되는 재배치 가능한 객체 파일, 실행 파일 및 공유 객체(다이나믹 라이브러리)를 위한 표준 형식이다
  • 다른 형식으로는 Mach-O(OSX), PE(윈도우즈), a.out 등이 있다
  • 컴파일러 → 링커(linker) → 로더(loader) 간의 링크를 제공한다.
  • 다음 tool에 필요한 모든 정보 및 디버깅 및 예외 처리 정보 전달
  • 이 외에도 광범위한 도구 지원한다

#Treatment of Global Variables

#Relocatable Object Files – Data, BSS, Read-only Section

  • 프로그래머가 정의한 initial value가 있는 전역 변수(global-variable)는 데이터 섹션에 저장된다(const인 경우 readonly)
  • 프로그래머가 정의한  initial value이 없는 전역 변수는 소위 BSS 섹션에 나열된다.

#Linking Multiple Objects Files

  • 여러 .o 개체 파일이 링커에 의해 실행 파일로 병합(merge)된다.
  • 이 병합 프로세스는 프로세스의 코드와 데이터의 메모리 내 레이아웃을 만든다
  • 링커는 references를(definition과 일치시켜) 해결하고 reference의 기호를 계산된 주소로 재배치하고 해당 reference를 참조하는 모든 placeholders를 채운다.

#Resulting Symbol Table

결과 Symbol Table

#Conceptual Depiction of Merging

  • 링커는 유사한 섹션을 순차적 순서로 병합한다. (일반적으로 command-line에 제공됨)
  • 링커 스크립트가 가이드함 (ld --verbose)
  • 결과 실행 파일은 로드 시 프로세스의 가상 주소 공간에 효율적으로 로드(또는 매핑)되도록 설계되어있다.

병합 과정

#Content of Final Executable

Excerpts from .text and .data sections

#Virtual Address Space Layout (Linux x86 64, 48-bit)

#Address Space Layout Randomization (ASLR)

  • ASLR이란 원격 실행 취약성에 대한 방어를 강화하기 위해 최신 시스템은 가능한 한 많은 주소 공간을 랜덤화하려고 하는것이다
  • 예: 스택, 힙 location, 코드 + 데이터 랜덤화
  • 일반적으로 링커가 할당된 주소는 기계 코드에 "baked"되어 직접 로드할 수 있다.
  • 로더는 로드 시간 재배치(비용 부담)도 수행할 수 있다
  • 위치 독립 코드(Position-Independent Code / PIC)는 추가 재배치 없이 주소 공간의 모든 주소에 로드할 수 있다.
  • 일반적으로 PIC는 indirection이 필요하다. x8664의 IP 상대 어드레싱 모드 disp(%rip)는 이를 지원하기 위해 도입되었다

#Summary

  • 컴파일러는 특정 기호 이름을 확인하지만 전역적인 모든 이름을 재배치 가능한 개체 파일의 참조로 링커에 전달한다.
  • 링커는 객체 파일을 병합하여 실행 파일을 생성하고 프로세스에서 가상 주소 공간 레이아웃을 계산한다
  • 실행 파일은 프로그램을 메모리에 로드하는 데 필요한 텍스트와 데이터를 포함한다
  • 이 포스트에서는 아래의 요소들은 다루지 않았다
    • Lexical scoping rules (컴파일 장치에 대한 전역 대 로컬)
    • 외부 참조를 해결하는 방법을 결정할 때 링커가 적용하는 규칙
    • 정적 및 동적 라이브러리 (part III 참조)