학습 주제
symbol과 symbol table, 그리고 항목은 어떤 타입으로 되어 있고, 어떻게 저장되는지를 학습했다.
정리한 내용
7.5 Symbols and Symbol Tables(심볼과 심볼테이블)
각 relocatable object module m은 m에 의해 정의되고 참조되는 symbol들에 대한 정보를 가지는 symbol table이 있다. linker의 입장에서 봤을 때, 이들은 3가지 종류로 나뉜다.
3가지 종류의 symbol
- global symbols - module m에서 정의되었고, 다른 모듈에서 참조 가능한 것
- non-static 함수나 non-static 전역 변수를 말한다.
- global symbols - 다른 모듈에서 정의되었고, 모듈 m에서 참조되는 것
- externals라고 부르기도 한다.
- 다른 모듈에서 정의된 non static 함수나 non static 전역 변수를 말한다.
- local symbols - 오직 m에서만 정의되고 참조될 수 있는 것
- static 함수나 static 전역변수를 말한다.
- 모듈 m에서는 어디서든 참조 가능하지만, 다른 모듈에서는 전혀 참조할 수 없다.
- 여기서 말하는 local symbol은 프로그램에서의 지역 변수와는 아예 다르다는 것을 알 수 있다. 이 non-static 지역변수는 .symtab 에서 저장하지 않고 있다. 이는 run-time stack에서 관리되는 것이기 때문, linker의 관심사가 아니다.
- static local 변수의 경우, stack에서 관리되지 않는다. 대신, compiler에 의해 .data 또는 .bss 영역에 공간을 할당하고, symbol table에 유일한 이름과 함께 local linker symbol을 생성한다.
- 즉, 다른 여러 함수들에서 동일한 이름의 static 변수들을 정의했을 때, 각각의 stack이 아닌 .data 또는 .bss 영역에서 관리된다고 해서 이름이 같을 때 전역변수처럼 오류가 나는 것이 아닌, compiler는 유일한 이름으로 만들어주어 assembler에게 전달한다.
- 위 그림에서 알 수 있다시피 저 x들은 stack에서 관리되는 것이 아니다. 하지만 이름이 중복된다고 해서 오류가 나지 않는다. 그 이유는 compiler가 이 이름들을 각각 x.1 과 x.2 로 변형하여 assembler에게 보내지고, assembler는 이를 바탕으로 symbol table을 만들게 된다. 이 symbol table은 ELF object file에서는 .symtab 에서 찾을 수 있다.
ELF symbol table들의 각 항목의 format
ELF symbol의 각 항목들에 대한 타입으로 구조체를 갖는 것을 볼 수 있다. 구조체 안의 변수들에서 : 과 함께 적힌 숫자는 각 변수들의 bit수를 정의한 것이다. 이렇게 bit를 지정한 구조체를 비트 구조체라고 한다.
위에서는 ELF symbol table의 각 항목들에 대한 형식을 나타내고 있다. 이 내용들을 하나씩 살펴보려 한다(참고로 여기서 볼 symbol들에서는 non-static 지역변수는 살펴보지 않는 다는 것을 다시 한번 기억하자).
- name : string table에서의 byte offset(위치)를 가진다.
- value : 해당 symbol의 주소값을 가진다.
- relocatable module일 경우(relocatable object file에 대한 ELF를 볼때면은), 이 value는 해당 object(symbol)이 정의된 section의 시작 부분으로부터의 offset을 갖는다.
- object module일 경우, 이 value는 run-time에서의 절대 주솟값을 갖는다.
- size : object(symbol)의 size를 말한다. 단위는 byte이다.
- type : 보통 data인지, function인지를 나타낸다.
- binding : symbol이 local symbol인지, global symbol인지를 나타낸다.
- section : section header table에서의 index를 담고 있다.
- 각 symbol들은 object file 안에 있는 section에 할당된다.
- ABS : relocate(재배치) 되면 안되는 symbol들이 저장됨
- UNDEF : undefined symbol이다. 이 object module에서 참조하고 있지만, 다른 곳에서 정의된 것들을 말한다.
- COMMON : 초기화 되지 않은 global 변수가 저장됨.(.bss에서와 동일한 역할이라고 생각한다면, 아래에서 이에 대해 더 살펴보고 있다).
- → 이 경우에는, value 필드에는 alignment 요구사항을, 그리고 size 필드에는 최소의 크기를 저장한다.
💡 symbol table의 항목으로는 각 section들에 대한 정보나 original 소스 파일의 path name까지 저장할 수 있다. 이러한 항목들을 위해 구별되는 타입(구조체)가 따로 있다.
COMMON 영역과 V.S. .bss 영역
- COMMON : 초기화 되지 않은 global 변수를 저장
- .bss : 초기화 되지 않은 static 변수, 또는 0으로 초기화된 전역 또는 static 변수
왜 이렇게 구분하는가? ⇒ linker가 symbol resolution을 수행하는 방법에 따라 이렇게 구분하게 되었다. symbol resolution에 관해서는 7.6장에서 더 자세히 살펴볼 것
7.1에서의 프로그램에 대한 symbol table 분석
GNU의 READELF라는 프로그램으로 main.o(relocatable object file)를 출력해본 모습
이제 위에서 설명한 symbol table을 바탕으로 위 symbol table을 살펴볼 것이다. 위에서 총 11가지의 symbol이 있었지만, 앞의 8개 항목은 linker가 내부적으로 쓰는 local symbol에 관한 것이라 제거했다고 한다.
- Num8
- Name이 main인 것으로 보아 main 함수에 대한 symbol이다.
- value가 0이고, Ndx가 1이므로 .text 영역에서 0번 offset(제일 처음)에 위치한다.
- 이 때, READELF프로그램은 각 section을 숫자로 나타내는데, Ndx가 1이라면 .text 영역을, 3이라면 .data 영역을 뜻한다.
- 총 24byte의 크기를 갖는 것을 볼 수 있다.
- Num9
- array에 관한 symbol이다.
- int형 배열에 요소는 2개이므로 위에서 적혀진 8-byte 사이즈가 맞다.
- Ndx가 3인 것으로 보아 .data 영역에 위치하고 있고, value가 0인것으로 보아 첫번째에 저장되어 있는 것을 알 수 있다.
- Num10
- external symbol인 sum에 관한 것이다.
'Computer Science > 컴퓨터 구조' 카테고리의 다른 글
[CSAPP] 7.11 Loading and Linking Shared Libraries from Applications (응용 프로그램으로부터 공유 라이브러리를 로드하고 링크하기) (0) | 2023.02.17 |
---|---|
[CSAPP] 7.10 Dynamic Linking with Shared Libraries(공유 라이브러리 동적 링크) (0) | 2023.02.17 |
[CSAPP] 7.4 Relocatable Object Files(재배치 가능 목적 파일) (0) | 2023.02.15 |
[CSAPP] 7.3 Object Files(목적 파일) (0) | 2023.02.15 |
[CSAPP] 7.2 Static Linking(정적연결) (0) | 2023.02.15 |