PE文件解析-区段头

 

 

有几个区段,就会有几个对应的区段头。区段头存放区段的信息,相当于一本书的目录。

如何访问区段头

通过DOS头拿到NT头,然后再通过NT头拿到标准PE头,标准PE头中存放了PE头的大小,然后通过内存偏移来找到区段头。

也可以利用Windows封装的结构体来处理

void CPeUtil::PrintSectionHeaders()
{
PIMAGE_SECTION_HEADER pSectionHeader = IMAGE_FIRST_SECTION(pNtHeader);
for (int i = 0; i < this->pFileHeader->NumberOfSections; i++)
{
char name[9]{ 0 };
for (int i = 0; i < 8; i++)
{
name[i] = pSectionHeader->Name[i];
}
std::cout << "区段名称:" << name<<std::endl;
pSectionHeader++;
}
}

 

区段头解析

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;
#define IMAGE_SIZEOF_SECTION_HEADER          40 
#define IMAGE_SIZEOF_SHORT_NAME              8
 
typedef struct _IMAGE_SECTION_HEADER {
  BYTE    Name[IMAGE_SIZEOF_SHORT_NAME];  //节表名称.大小8字节.一般情况下是以"\0"结尾的ASCII码字符串.内容可自定义.
  union {
    DWORD   PhysicalAddress;         //联合体.
    DWORD   VirtualSize;             //节在内存中按照内存对齐前的大小(该值可以不准确).
  } Misc;
  DWORD   VirtualAddress;            //(RVA)节在内存中的偏移地址.加上ImageBase才是在内存中的地址.
  DWORD   SizeOfRawData;             //节在文件中按照文件对齐后的大小.
  DWORD   PointerToRawData;          //(FOA)节在文件中的偏移地址.
  DWORD   PointerToRelocations;      //.OBJ文件中使用,指向重定位表的指针.
  DWORD   PointerToLinenumbers;      //行号表的偏移,提供调试.
  WORD    NumberOfRelocations;       //.OBJ文件中使用,重定位项数目.
  WORD    NumberOfLinenumbers;       //行号表中行号的数量.
  DWORD   Characteristics;           //节的属性.
} IMAGE_SECTION_HEADER, * PIMAGE_SECTION_HEADER;

该结构体参考:IMAGE_SECTION_HEADER (winnt.h) - Win32 应用 |微软文档 (microsoft.com)

PE文件解析-各种头解析代码实现

https://www.cnblogs.com/Sna1lGo/p/14452114.html