[리버싱 - 6] : PE Header - ③

마지막 IMAGE_SECTION_HEADER 구조체와 IAT 알아보기


IMAGE_SECTION_HEADER

마지막으로 알아 볼 PE 헤더 구조체는 IMAGE_SECTION_HEADER이다. 섹션 헤더는 주로 각 섹션에 대한 이름을 비롯해 시작 주소와 사이즈 등의 정보를 관리하는 구조체로 코드 섹션이나 데이터 섹션에 대한 정보를 구할 수 있다. 코드는 아래와 같다.

#define IMAGE_SIZEOF_SHORT_NAME 8
 
typedef struct _IMAGE_SECTION_HEADER {
  BYTE  Name[IMAGE_SIZEOF_SHORT_NAME];
  union {
    DWORD PhysicalAddress;
    DWORD VirtualSize;
  } Misc;
  DWORD VirtualAddress;
  DWORD SizeOfRawData;
  DWORD PointerToRawData;
  DWORD PointerToRelocations;
  DWORD PointerToLinenumbers;
  WORD  NumberOfRelocations;
  WORD  NumberOfLinenumbers;
  DWORD Characteristics;
} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER;

section-header PEview로 프로그램을 열고 IMAGE_SECTION_HEADER들 중 하나를 누르면 위와같이 값이 나온다.

각각의 값들이 무엇을 의미하는지 알아보자.

Name

단어 그대로 섹션의 이름을 나타낸다. 매크로 상수로 사전에 정의해둔 8 바이트를 사용하고 8 바이트보다 짧은 문자열이 들어올 경우 남은 공간은 00으로 채운다.

Virtual Size

메모리에 로드될 때 섹션의 총 크기(바이트)이다. 이 값이 SizeOfRawData보다 크면 섹션이 0으로 채워진다.

VirtualAddress

해당 섹션이 메모리에 로드될 때의 RVA을 가지고 있다.

예를 들어 .data 섹션의 RVA 값이 0x156000이고 ImageBase가 0x400000이라면 IDA등의 디버거로 열었을때 0x556000부터 .data 부분이 나올 것이다.

SizeOfRawData

디스크에서 초기화된 데이터의 크기(바이트)이다. 이 값은 FileAlignment 멤버의 배수여야 한다. FileAlignment에 대한 내용은 이전 장에서 다뤘다. 섹션에 초기화되지 않은 데이터만 있는 경우 이 멤버가 0으로 설정된다.

PointerToRawData

PE 파일 내에서 해당 섹션의 시작하는 번지 수를 알려주는 값이다. pe https://kw470.tistory.com/18 위 사진의 오른쪽 offset값들이 PointerToRawData의 값이라고 보면 된다.

Characteristics

섹션의 속성(권한)을 나타내는 플래그들이다. WinNT.h 헤더 파일에 매크로로 정의되어 있고 전체 플래그는 MSDN에서 확인 가능하다.


마지막 4가지 멤버들은 MSDN의 내용을 옮겨 적음.

PointerToRelocations

섹션에 대한 재배치 항목의 시작 부분에 대한 파일 포인터입니다. 재배치가 없으면 이 값은 0입니다.

PointerToLinenumbers

섹션에 대한 줄 번호 항목의 시작 부분에 대한 파일 포인터입니다. COFF 줄 번호가 없으면 이 값은 0입니다.

NumberOfRelocations

섹션에 대한 재배치 항목의 수입니다. 이 값은 실행 파일 이미지에 대해 0입니다.

NumberOfLinenumbers

섹션에 대한 줄 번호 항목의 수입니다.