使用c语言中的exe文件



(适用于Windows 8)我试图用c在exe文件(PE32格式)中获得节头的大小。从我读到的,这个字段的偏移量是60,所以我试着从那里读取。

这是我使用的代码:

unsigned char offset;
fseek(file, 60, SEEK_SET);
fread(&offset, sizeof(offset), 1, file);
printf("%hu", offset);

我的问题是我怎么能得到部分标题的大小?如果它不在偏移量60上,我怎么找到它?

应该可以:

void main()
{
  FILE *file = fopen("your_exe_file.exe", "rb") ;
  long peheaderoffset ;
  // read the offset of the PE header which is located at offset 0x3c
  fseek(file, 0x3c, SEEK_SET) ;
  fread(&peheaderoffset, sizeof(long), 1, file) ;
  char PEHeader[4] ;  // PE header: contains normally 'P','E',0,0
  fseek(file, peheaderoffset, SEEK_SET) ;
  fread(&PEHeader, 4, 1, file) ;
  short machine ;
  short NumberofSections ;
  fread(&machine, sizeof(short), 1, file) ;  // read machine identifier
  fread(&NumberofSections, sizeof(short), 1, file) ;  // read Number of sections
  printf ("PE Header = %sn", PEHeader) ; // should always print "PE"
                                          // we should check if PEHEeader actually
                                          // contains "PE". If not it's not a PE file
  printf ("machine = %xn", machine) ;    // 14c for Intel x86
  printf ("Number of sections = %dn", NumberofSections) ; 
  // skip to size of optional header
  fseek(file, 12, SEEK_CUR) ;
  short SizeOfOptionalHeader ;
  fread (&SizeOfOptionalHeader, sizeof(short), 1, file) ;
  printf ("Sizeof optional PE header = %dn", SizeOfOptionalHeader) ;  
  short characteristics ;
  fread (&characteristics, sizeof(short), 1, file) ;
  printf ("Characteristics = %xn", characteristics) ;  
  // now we are at the PE optional header
  short signature ;
  fread (&signature, sizeof(short), 1, file) ;
  printf ("Signature of optioan PE Header = %d (should be 267)n", signature) ;  
  // skip to image Base at offset 0x1c
  // (the -2 is because we have already read the signature just above)
  fseek(file, 0x1c - 2, SEEK_CUR) ;
  long imageBase ;
  fread (&imageBase, sizeof(long), 1, file) ;
  printf ("Image base = %xn", imageBase) ;   
}

尝试使用fread而不是fscanf,并且(正如Joachim所指出的)它是一个二进制文件,因此确保您以二进制模式打开该文件(file=fopen (filename, "rb"))

您试图读取的字段是4字节长,但您正试图从那里读取NULL终止的字符串。你可能得到了正确的值,但是你把它当作一个可打印的字符串来打印(也许你期望打印像"216"或"D8"这样的东西,但是这样的字符串不是存储的)。

可打印字符串包含一系列代码,每个代码代表一个字符(至少在ASCII中),后跟一个''结束符。这就是"%s"scanf/printf格式化选项所处理的。但数据通常不是这样存储在二进制文件中的。你可以试着找到你想要的号码:

unsigned int offset;
fseek(file, 60, SEEK_SET);
fread(&offset, sizeof(offset), 1, file);
printf("%u", offset);

可能最好的名字是uint32_t,但这需要你包括<inttype.h>工作。

fscanf()是不合适的-它读取ASCII数据,而PE32是二进制格式-您希望读取单个32位整数,而不是数字字符串(类似于打印"%s"是不合适的格式说明符)。

您还必须确保以二进制模式打开文件,否则和序列将被翻译为单个并且fseek()将无法按预期工作。

uint32_t sizeOfHeaders = 0 ;
FILE* file = fopen( filename, "rb" ) ; // Open in binary mode
fseek( file, 60, SEEK_SET ) ;
fread( &sizeOfHeaders, sizeof(sizeOfHeaders), 1, file ) ;
printf("%u", sizeOfHeaders ) ;

相关内容

  • 没有找到相关文章

最新更新