程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> 更多編程語言 >> Delphi >> 對PE資源的研究

對PE資源的研究

編輯:Delphi

  前言:沒什麼好說的,發現這方面的資料全是英文的,於是我一邊研究,一邊翻譯,一邊寫出自己的心得。
  希望大家尊重我的勞動成果,轉貼保持完整。

  資源一般使用樹來保存,通常包含3層,在NT下,最高層是類型,然後是名字,最後是語言。一個PE文件是否包含資源文件,通常檢測塊表(Section Table)中是否含有'.rsrc',不過這個方法對有些PE文件無效。


  

  一個類型表結構如下
  ―――――――――――――
  |  RESOURCE DIRECTORY  |
  ―――――――――――――
  |  RESOURCE DATA             |
  ―――――――――――――
   資源表1(Resource File Layout)


  

  其中的資源目錄(RESOURCE DIRECTORY)結構如下:


  

  ――――――――――――――――――――――――――
  |  RESOURCE FLAGS   |
  ――――――――――――――――――――――――――
  |  TIME/DATE STAMP   |
  ――――――――――――――――――――――――――
  | MAJOR VERSION | MINOR VERSION |
  ――――――――――――――――――――――――――
  | # NAME ENTRY | # ID ENTRY |
  ――――――――――――――――――――――――――
  |  RESOURCE DIR ENTRIES  |
  ――――――――――――――――――――――――――
   資源表2(Resource Table Entry)


  

  在Delphi中的申明
  { Resources }
    PIMAGE_RESOURCE_DIRECTORY = ^IMAGE_RESOURCE_DIRECTORY;
    IMAGE_RESOURCE_DIRECTORY = packed record
      Characteristics : DWord;
      TimeDateStamp   : DWord;
      MajorVersion    : Word;
      MinorVersion    : Word;
      NumberOfNamedEntrIEs : Word;
      NumberOfIdEntrIEs : Word;
    end


  

  其中:


  

  RESOURCE FLAGS
  通常設置為0


  

  TIME/DATE STAMP
  資源編譯器建立此資源的時間/日期,可能為0


  

  MAJOR/MINOR VERSION
  版本信息


  

  # NAME ENTRY
  使用名字的資源條目的個數,包含一個使用名字的目錄條目的數組。
  # ID ENTRY
  使用ID數字的資源條目的個數,包含一個32位的整數ID號,同用名字一樣。
  這個目錄緊接著會是一個不定長度的目錄條目,不管用的名字還是ID,都是用升序排列。


  

  這個不定長度的目錄結構如下:


  

  31     0
  ――――――――――――――――――――――
  | NAME RVA/INTEGER ID  |
  ――――――――――――――――――――――
  | E | DATA ENTRY RVA/SUBDIR RVA |
  ――――――――――――――――――――――
   資源表3(Resource Directory Entry)


  

  在Delphi中的申明:
    PIMAGE_RESOURCE_DIRECTORY_ENTRY = ^IMAGE_RESOURCE_DIRECTORY_ENTRY;
    IMAGE_RESOURCE_DIRECTORY_ENTRY = packed record
      Name: DWORD;        // Or ID: Word (Union)
      OffsetToData: DWord;


  

  INTEGER ID
  包含一個識別資源的整數ID
  如果在根目錄,這個ID表示的意義如下
  資源類型
      1: cursor
      2: bitmap
      3: icon
      4: menu
      5: dialog
      6: string table
      7: font directory
      8: font
      9: accelerators
      10: unformatted resource data
      11: message table
      12: group cursor
      14: group icon
      16: version information


  

  NAME RVA
  名字的相對實際地址,包含一個31位的相對資源的Image Base的地址。表的形式見表4


  

  E 一位的不可缺少的識別碼(mask 80000000h)
  如果這位為0,則為Resource Data EntrIEs,其中DATA RVA = 31位的(mask 7fffffffh) 數據條目的地址。結構見表5
  如果這位為1,則表示接另一個子目錄(Subdirectory Entry)。


  

  { 此函數檢驗 offset 是一個字符串名還是一個目錄 }
  { IMAGE_RESOURCE_NAME_IS_STRING
  = IMAGE_RESOURCE_DATA_IS_DIRECTORY
  = $80000000 }
  function HighBitSet(L: Longint): Boolean;
  begin
    Result := (L and IMAGE_RESOURCE_DATA_IS_DIRECTORY) <> 0;
  end;


  

  { 下面兩個函數用於去掉E位剩下的值或者指針 }
  {IMAGE_OFFSET_STRIP_HIGH = $7FFFFFFF;}
  function StripHighBit(L: Longint): Longint;
  begin
    Result := L and IMAGE_OFFSET_STRIP_HIGH;
  end;


  

  function StripHighPtr(L: Longint): Pointer;
  begin
    Result := Pointer(L and IMAGE_OFFSET_STRIP_HIGH);
  end;


  

  每一個資源目錄名為如下格式
  ――――――――――――――――――――――
  | LENGTH | UNICODE STRING |
  ――――――――――――――――――――――
  | LENGTH | UNICODE STRING |
  ――――――――――――――――――――――
   表4(Resource Directory String Entry)


  

  在Delphi中的申明
    PIMAGE_RESOURCE_DIR_STRING_U = ^IMAGE_RESOURCE_DIR_STRING_U;
    IMAGE_RESOURCE_DIR_STRING_U = packed record
      Length          : Word;
      NameString      : array [0..0] of WCHAR;
    end;


  

  LENGTH
  就是字符串的長度
  UNICODE STRING
  Unicode的字符串.


  

  資源數據表結構:
  ―――――――――――――
  | DATA RVA |
  ―――――――――――――
  | SIZE  |
  ―――――――――――――
  | CODEPAGE |
  ―――――――――――――
  | RESERVED |
  ―――――――――――――
   表5(Resource Data Entry)


  

  在Delphi中的申明
    PIMAGE_RESOURCE_DATA_ENTRY = ^IMAGE_RESOURCE_DATA_ENTRY;
    IMAGE_RESOURCE_DATA_ENTRY = packed record
      OffsetToData    : DWord;
      Size            : DWord;
      CodePage        : DWord;
      Reserved        : DWord;
    end;


  

  DATA RVA
  資源的相對實際地址,包含一個32位相對於資源Image Base的地址。
  SIZE
  資源的大小。
  CODEPAGE
  沒什麼說的,好像為譯碼方面設置的。
  RESERVED
  一定為0


  

  好了,差不多資源這部分分析玩了,其它部分我還在研究:)

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved