Excel VBAでファイル解析(EXEファイル編)

2024-01-06

■EXEファイルの概要

EXEファイルは、MS-DOSやWindowsで使用される実行形式ファイルで、代表的な拡張子は「.EXE」「.DLL」です。

本稿ではWindows用のPE(Portable Executable)フォーマットについて、概要を説明します。
⇒詳細はMicrosoftのサイト(PE形式)を参照して下さい。

EXEファイルの構成

EXEファイルの構成は下図のようになっており、「MS-DOS Header」「Image NT Headers」「Image Section Header」「セクション・データ」の順に配置されています。

(EXEファイルの構成)

MS-DOS Header Image NT Headers Image Data Directory セクション・データ

MS-DOS Headerのフォーマット

MS-DOS HeaderはMS-DOSとの互換性を保つために設けられており、先頭のヘッダ部分はMS-DOS時代のEXEヘッダとほぼ同形式です。
フォーマットは下表の通りですが、この形式のEXEファイルをMS-DOS(またはWindowsのコマンド・プロンプト)で実行すると、MS-DOS Stubに格納されているプログラムが実行されます。

(MS-DOS Headerのフォーマット)

オフセット 長さ 説明
X’0000′ 2 Magic number('MZ’)
X’0002′ 2 Bytes on last page of file
X’0004′ 2 Pages in file
X’0006′ 2 Relocations
X’0008′ 2 Size of header in paragraphs
X’000A’ 2 Minimum extra paragraphs needed
X’000C’ 2 Maximum extra paragraphs needed
X’000E’ 2 Initial (relative) SS value
X’0010′ 2 Initial SP value
X’0012′ 2 Checksum
X’0014′ 2 Initial IP value
X’0016′ 2 Initial (relative) CS value
X’0018′ 2 File address of relocation table(X’0040′)
↑MS-DOS Stubの開始位置
X’001A’ 2 Overlay number
X’001C’ 8 Reserved words
X’0024′ 2 OEM identifier (for e_oeminfo)
X’0026′ 2 OEM information; e_oemid specific
X’0028′ 20 Reserved words
X’003C’ 4 File address of new exe header(X’00000100′)
↑Image NT Headersの開始位置
X’0040′ 192 MS-DOS Stub

Image NT Headersのフォーマット

Image NT Headersは、「Image File Header」と「Image Optional Header」の2つの部分に分かれており、フォーマットは下表の通りです。

(Image NT Headersのフォーマット)

オフセット 長さ 説明
X’0100′ 4 Signature('PE’+X’0000’)
Image File Header
X’0104′ 2 Machine
X’0106′ 2 NumberOfSections
↑セクションの個数
X’0108′ 4 TimeDateStamp
X’010C’ 4 PointerToSymbolTable
X’0110′ 4 NumberOfSymbols
X’0114′ 2 SizeOfOptionalHeader
↑Image Optional Headerのサイズ
X’0116′ 2 Characteristics
Image Optional Header
X’0118′ 2 Magic
X’011A’ 1 MajorLinkerVersion
X’011B’ 1 MinorLinkerVersion
X’011C’ 4 SizeOfCode
X’0120′ 4 SizeOfInitializedData
X’0124′ 4 SizeOfUninitializedData
X’0128′ 4 AddressOfEntryPoint
X’012C’ 4 BaseOfCode
X’0130′ 4 BaseOfData
X’0134′ 4 ImageBase
X’0138′ 4 SectionAlignment
X’013C’ 4 FileAlignment
X’0140′ 2 MajorOperatingSystemVersion
X’0142′ 2 MinorOperatingSystemVersion
X’0144′ 2 MajorImageVersion
X’0146′ 2 MinorImageVersion
X’0148′ 2 MajorSubsystemVersion
X’014A’ 2 MinorSubsystemVersion
X’014C’ 4 Win32VersionValue
X’0150′ 4 SizeOfUninitializedData
X’0124′ 4 SizeOfImage
X’0154′ 4 SizeOfHeaders
X’0158′ 4 CheckSum
X’015C’ 2 Subsystem
X’015E’ 2 DllCharacteristics
X’0160′ 4 SizeOfStackReserve
X’0164′ 4 SizeOfStackCommit
X’0168′ 4 SizeOfHeapReserve
X’016C’ 4 SizeOfHeapCommit
X’0170′ 4 LoaderFlags
X’0174′ 4 NumberOfRvaAndSizes
X’0178′ Image Data Directory(次項参照)

Image Data Directoryのフォーマット

Image Data Directoryは下表の16エントリから成り、各エントリは「VirtualAddress(4バイト)」「Size(4バイト)」の2項目から成っています。

(Image Data Directoryのフォーマット)

オフセット 長さ 説明
IMAGE_DIRECTORY_ENTRY_EXPORT
X’0178′ 4 VirtualAddress
X’017C’ 4 Size
IMAGE_DIRECTORY_ENTRY_IMPORT
X’0180′ 4 VirtualAddress
X’0184′ 4 Size
IMAGE_DIRECTORY_ENTRY_RESOURCE
X’0188′ 4 VirtualAddress
X’018C’ 4 Size
IMAGE_DIRECTORY_ENTRY_EXCEPTION
X’0190′ 4 VirtualAddress
X’0194′ 4 Size
IMAGE_DIRECTORY_ENTRY_SECURITY
X’0198′ 4 VirtualAddress
X’019C’ 4 Size
IMAGE_DIRECTORY_ENTRY_BASERELOC
X’01A0′ 4 VirtualAddress
X’01A4′ 4 Size
IMAGE_DIRECTORY_ENTRY_DEBUG
X’01A8′ 4 VirtualAddress
X’01AC’ 4 Size
IMAGE_DIRECTORY_ENTRY_COPYRIGHT
X’01B0′ 4 VirtualAddress
X’01B4′ 4 Size
IMAGE_DIRECTORY_ENTRY_GLOBALPTR
X’01B8′ 4 VirtualAddress
X’01BC’ 4 Size
IMAGE_DIRECTORY_ENTRY_TLS
X’01C0′ 4 VirtualAddress
X’01C4′ 4 Size
IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG
X’01C8′ 4 VirtualAddress
X’01CC’ 4 Size
IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT
X’01D0′ 4 VirtualAddress
X’01D4′ 4 Size
IMAGE_DIRECTORY_ENTRY_IAT
X’01D8′ 4 VirtualAddress
X’01DC’ 4 Size
IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT
X’01E0′ 4 VirtualAddress
X’01E4′ 4 Size
IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR
X’01E8′ 4 VirtualAddress
X’01EC’ 4 Size
Reserved
X’01F0′ 4 VirtualAddress
X’01F4′ 4 Size

Image Section Headerのフォーマット

Image Section Headerは、Image File Headerの「NumberOfSections」の数だけエントリを持ち、各エントリのフォーマットは下表の通りです。

(Image Section Headerのフォーマット)

オフセット 長さ 説明
X’0000′ 8 Name
X’0008′ 4 PhysicalAddress&VirtualSize
X’000C’ 4 VirtualAddress
X’0010′ 4 SizeOfRawData
X’0014′ 4 PointerToRawData
X’0018′ 4 PointerToRelocations
X’001C’ 4 PointerToLinenumbers
X’0020′ 2 NumberOfRelocations
X’0022′ 2 NumberOfLinenumbers
X’0024′ 4 Characteristics

■EXEファイルのヘッダ情報をExcelシートに表示する処理

EXEファイルのヘッダを読み込み、Excelシートに「オフセット」「長さ」「項目」「値」を表示するプログラムです。
⇒サンプル・プログラムで使用している、Binary Fileクラスの詳細については、Excel VBAでファイル解析(事前準備編)を参照して下さい。

処理の概要

処理の流れは以下の通りです。
①Binary Fileオブジェクトをインスタンス化し、EXEファイルを読み込み
②EXEファイルのヘッダを解析し、必要な情報を取得してExcelシートにセット
③使用済のオブジェクトを破棄

プログラムが少し大きいので、4つに分けて掲載します。
⇒フォーマットに従って項目を表示しているだけなので、規模は大きめですが、難易度は低いです。

データ宣言部とMS-DOS Headerに関する処理

行番号16でBinary Fileオブジェクトをインスタンス化し、行番号17でEXEファイルを読み込んでいます。
行番号22~97でMS-DOS Headerの各項目を順に表示し、行番号98~116でMS-DOS Stubを16進ダンプ形式で表示しています。
行番号98でImage NT Headersの開始位置を取得し、行番号101でCurrentPositionとの差を求め、その範囲をMS-DOS Stubとみなしています。

(※)EXEファイルの数値データ(サイズ、オフセット等)は全てリトル・エンディアンで格納されているため、計算に使用する場合はエンディアン変換が必要です。

  1. Dim sht, bf As Object
  2. Dim wLoc As String
  3. Dim wID As String
  4. Dim wSize As Long
  5. Dim wLen As Long
  6. Dim EntNum As Long
  7. Dim EntLen As Long
  8. Dim SectionHeadderPtr As Long
  9. Dim NumberOfSections As Integer
  10. Dim lcnt As Long
  11. Dim i As Long
  12. Private Sub Sample1()
  13.     Set sht = ActiveSheet
  14.     sht.Cells.NumberFormatLocal = “@"
  15.     Set bf = New BinaryFile
  16.     bf.InputFile (“C:\work\xxx.exe")
  17.     lcnt = 0
  18.     lcnt = lcnt + 1
  19.     sht.Cells(lcnt, 1) = “[MS-DOS Header]"
  20.     lcnt = lcnt + 1
  21.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  22.     sht.Cells(lcnt, 2) = “Magic number"
  23.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  24.     lcnt = lcnt + 1
  25.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  26.     sht.Cells(lcnt, 2) = “Bytes on last page of file"
  27.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  28.     lcnt = lcnt + 1
  29.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  30.     sht.Cells(lcnt, 2) = “Pages in file"
  31.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  32.     lcnt = lcnt + 1
  33.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  34.     sht.Cells(lcnt, 2) = “Relocations"
  35.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  36.     lcnt = lcnt + 1
  37.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  38.     sht.Cells(lcnt, 2) = “Size of header in paragraphs"
  39.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  40.     lcnt = lcnt + 1
  41.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  42.     sht.Cells(lcnt, 2) = “Minimum extra paragraphs needed"
  43.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  44.     lcnt = lcnt + 1
  45.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  46.     sht.Cells(lcnt, 2) = “Maximum extra paragraphs needed"
  47.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  48.     lcnt = lcnt + 1
  49.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  50.     sht.Cells(lcnt, 2) = “Initial (relative) SS value"
  51.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  52.     lcnt = lcnt + 1
  53.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  54.     sht.Cells(lcnt, 2) = “Initial SP value"
  55.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  56.     lcnt = lcnt + 1
  57.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  58.     sht.Cells(lcnt, 2) = “Checksum"
  59.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  60.     lcnt = lcnt + 1
  61.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  62.     sht.Cells(lcnt, 2) = “Initial IP value"
  63.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  64.     lcnt = lcnt + 1
  65.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  66.     sht.Cells(lcnt, 2) = “Initial (relative) CS value"
  67.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  68.     lcnt = lcnt + 1
  69.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  70.     sht.Cells(lcnt, 2) = “File address of relocation table"
  71.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  72.     lcnt = lcnt + 1
  73.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  74.     sht.Cells(lcnt, 2) = “Overlay number"
  75.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  76.     lcnt = lcnt + 1
  77.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  78.     sht.Cells(lcnt, 2) = “Reserved words"
  79.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(8), 16)
  80.     lcnt = lcnt + 1
  81.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  82.     sht.Cells(lcnt, 2) = “OEM identifier (for e_oeminfo)"
  83.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  84.     lcnt = lcnt + 1
  85.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  86.     sht.Cells(lcnt, 2) = “OEM information; e_oemid specific"
  87.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  88.     lcnt = lcnt + 1
  89.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  90.     sht.Cells(lcnt, 2) = “Reserved words"
  91.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(20), 40)
  92.     lcnt = lcnt + 1
  93.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  94.     sht.Cells(lcnt, 2) = “File address of new exe header"
  95.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  96.     wLen = CLng(“&H" & Mid(sht.Cells(lcnt, 3), 1, 2)) + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 3, 2)) * 256 + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 5, 2)) * 32768 + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 7, 2)) * 4194304
  97.     lcnt = lcnt + 1
  98.     sht.Cells(lcnt, 1) = “[MS-DOS Stub]"
  99.     wSize = wLen – bf.CurrentPosition
  100.     EntNum = wSize / 16
  101.     If wSize Mod 16 <> 0 Then
  102.         EntNum = EntNum + 1
  103.     End If
  104.     For i = 1 To EntNum
  105.         lcnt = lcnt + 1
  106.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  107.         sht.Cells(lcnt, 2) = “MS-DOS Program(" & Format(i, “000") & “)"
  108.         If wSize > 16 Then
  109.             sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(16), 32)
  110.             wSize = wSize – 16
  111.         Else
  112.             sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(wSize), wSize * 2)
  113.         End If
  114.     Next i

Image NT Headers(Image Data Directoryを除く)に関する処理

行番号1~6でSignature、行番号7~38でImage File Header、行番号39~162でImage Optional Headerの各項目を順に表示しています。
後続の処理で使用するため、行番号17でセクション数、行番号34と44でImage Section Headerの開始位置を取得しています。

  1.     lcnt = lcnt + 1
  2.     sht.Cells(lcnt, 1) = “[IMAGE_NT_HEADERS]"
  3.     lcnt = lcnt + 1
  4.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  5.     sht.Cells(lcnt, 2) = “Signature"
  6.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  7.     lcnt = lcnt + 1
  8.     sht.Cells(lcnt, 1) = “[IMAGE_FILE_HEADER]"
  9.     lcnt = lcnt + 1
  10.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  11.     sht.Cells(lcnt, 2) = “Machine"
  12.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  13.     lcnt = lcnt + 1
  14.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  15.     sht.Cells(lcnt, 2) = “NumberOfSections"
  16.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  17.     NumberOfSections = CLng(“&H" & Mid(sht.Cells(lcnt, 3), 1, 2)) + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 3, 2)) * 256
  18.     lcnt = lcnt + 1
  19.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  20.     sht.Cells(lcnt, 2) = “TimeDateStamp"
  21.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  22.     lcnt = lcnt + 1
  23.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  24.     sht.Cells(lcnt, 2) = “PointerToSymbolTable"
  25.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  26.     lcnt = lcnt + 1
  27.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  28.     sht.Cells(lcnt, 2) = “NumberOfSymbols"
  29.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  30.     lcnt = lcnt + 1
  31.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  32.     sht.Cells(lcnt, 2) = “SizeOfOptionalHeader"
  33.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  34.     SectionHeadderPtr = CLng(“&H" & Mid(sht.Cells(lcnt, 3), 1, 2)) + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 3, 2)) * 256
  35.     lcnt = lcnt + 1
  36.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  37.     sht.Cells(lcnt, 2) = “Characteristics"
  38.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  39.     lcnt = lcnt + 1
  40.     sht.Cells(lcnt, 1) = “[IMAGE_OPTIONAL_HEADER]"
  41.     lcnt = lcnt + 1
  42.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  43.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetPositionHex, 8)
  44.     SectionHeadderPtr = SectionHeadderPtr + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 1, 2)) * 4194304 + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 3, 2)) * 32768 + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 5, 2)) * 256 + CLng(“&H" & Mid(sht.Cells(lcnt, 3), 7, 2))
  45.     sht.Cells(lcnt, 2) = “Magic"
  46.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  47.     lcnt = lcnt + 1
  48.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  49.     sht.Cells(lcnt, 2) = “MajorLinkerVersion"
  50.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(1), 2)
  51.     lcnt = lcnt + 1
  52.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  53.     sht.Cells(lcnt, 2) = “MinorLinkerVersion"
  54.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(1), 2)
  55.     lcnt = lcnt + 1
  56.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  57.     sht.Cells(lcnt, 2) = “SizeOfCode"
  58.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  59.     lcnt = lcnt + 1
  60.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  61.     sht.Cells(lcnt, 2) = “SizeOfInitializedData"
  62.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  63.     lcnt = lcnt + 1
  64.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  65.     sht.Cells(lcnt, 2) = “SizeOfUninitializedData"
  66.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  67.     lcnt = lcnt + 1
  68.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  69.     sht.Cells(lcnt, 2) = “AddressOfEntryPoint"
  70.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  71.     lcnt = lcnt + 1
  72.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  73.     sht.Cells(lcnt, 2) = “BaseOfCode"
  74.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  75.     lcnt = lcnt + 1
  76.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  77.     sht.Cells(lcnt, 2) = “BaseOfData"
  78.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  79.     lcnt = lcnt + 1
  80.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  81.     sht.Cells(lcnt, 2) = “ImageBase"
  82.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  83.     lcnt = lcnt + 1
  84.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  85.     sht.Cells(lcnt, 2) = “SectionAlignment"
  86.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  87.     lcnt = lcnt + 1
  88.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  89.     sht.Cells(lcnt, 2) = “FileAlignment"
  90.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  91.     lcnt = lcnt + 1
  92.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  93.     sht.Cells(lcnt, 2) = “MajorOperatingSystemVersion"
  94.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  95.     lcnt = lcnt + 1
  96.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  97.     sht.Cells(lcnt, 2) = “MinorOperatingSystemVersion"
  98.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  99.     lcnt = lcnt + 1
  100.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  101.     sht.Cells(lcnt, 2) = “MajorImageVersion"
  102.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  103.     lcnt = lcnt + 1
  104.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  105.     sht.Cells(lcnt, 2) = “MinorImageVersion"
  106.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  107.     lcnt = lcnt + 1
  108.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  109.     sht.Cells(lcnt, 2) = “MajorSubsystemVersion"
  110.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  111.     lcnt = lcnt + 1
  112.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  113.     sht.Cells(lcnt, 2) = “MinorSubsystemVersion"
  114.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  115.     lcnt = lcnt + 1
  116.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  117.     sht.Cells(lcnt, 2) = “Win32VersionValue"
  118.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  119.     lcnt = lcnt + 1
  120.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  121.     sht.Cells(lcnt, 2) = “SizeOfImage"
  122.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  123.     lcnt = lcnt + 1
  124.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  125.     sht.Cells(lcnt, 2) = “SizeOfHeaders"
  126.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  127.     lcnt = lcnt + 1
  128.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  129.     sht.Cells(lcnt, 2) = “CheckSum"
  130.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  131.     lcnt = lcnt + 1
  132.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  133.     sht.Cells(lcnt, 2) = “Subsystem"
  134.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  135.     lcnt = lcnt + 1
  136.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  137.     sht.Cells(lcnt, 2) = “DllCharacteristics"
  138.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  139.     lcnt = lcnt + 1
  140.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  141.     sht.Cells(lcnt, 2) = “SizeOfStackReserve"
  142.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  143.     lcnt = lcnt + 1
  144.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  145.     sht.Cells(lcnt, 2) = “SizeOfStackCommit"
  146.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  147.     lcnt = lcnt + 1
  148.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  149.     sht.Cells(lcnt, 2) = “SizeOfHeapReserve"
  150.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  151.     lcnt = lcnt + 1
  152.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  153.     sht.Cells(lcnt, 2) = “SizeOfHeapCommit"
  154.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  155.     lcnt = lcnt + 1
  156.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  157.     sht.Cells(lcnt, 2) = “LoaderFlags"
  158.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  159.     lcnt = lcnt + 1
  160.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  161.     sht.Cells(lcnt, 2) = “NumberOfRvaAndSizes"
  162.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)

Image Data Directoryに関する処理

行番号3~162でImage Data Directory(16エントリ)の各項目を順に表示しています。
行番号163~178は、Image Section Headerまでのデータ(パディング・エリア)に関する処理です。

  1.     lcnt = lcnt + 1
  2.     sht.Cells(lcnt, 1) = “[IMAGE_DATA_DIRECTORY DataDirectory[16]]"
  3.     lcnt = lcnt + 1
  4.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_EXPORT]"
  5.     lcnt = lcnt + 1
  6.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  7.     sht.Cells(lcnt, 2) = “VirtualAddress"
  8.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  9.     lcnt = lcnt + 1
  10.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  11.     sht.Cells(lcnt, 2) = “Size"
  12.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  13.     lcnt = lcnt + 1
  14.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_IMPORT]"
  15.     lcnt = lcnt + 1
  16.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  17.     sht.Cells(lcnt, 2) = “VirtualAddress"
  18.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  19.     lcnt = lcnt + 1
  20.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  21.     sht.Cells(lcnt, 2) = “Size"
  22.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  23.     lcnt = lcnt + 1
  24.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_RESOURCE]"
  25.     lcnt = lcnt + 1
  26.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  27.     sht.Cells(lcnt, 2) = “VirtualAddress"
  28.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  29.     lcnt = lcnt + 1
  30.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  31.     sht.Cells(lcnt, 2) = “Size"
  32.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  33.     lcnt = lcnt + 1
  34.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_EXCEPTION]"
  35.     lcnt = lcnt + 1
  36.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  37.     sht.Cells(lcnt, 2) = “VirtualAddress"
  38.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  39.     lcnt = lcnt + 1
  40.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  41.     sht.Cells(lcnt, 2) = “Size"
  42.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  43.     lcnt = lcnt + 1
  44.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_SECURITY]"
  45.     lcnt = lcnt + 1
  46.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  47.     sht.Cells(lcnt, 2) = “VirtualAddress"
  48.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  49.     lcnt = lcnt + 1
  50.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  51.     sht.Cells(lcnt, 2) = “Size"
  52.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  53.     lcnt = lcnt + 1
  54.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_BASERELOC]"
  55.     lcnt = lcnt + 1
  56.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  57.     sht.Cells(lcnt, 2) = “VirtualAddress"
  58.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  59.     lcnt = lcnt + 1
  60.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  61.     sht.Cells(lcnt, 2) = “Size"
  62.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  63.     lcnt = lcnt + 1
  64.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_DEBUG]"
  65.     lcnt = lcnt + 1
  66.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  67.     sht.Cells(lcnt, 2) = “VirtualAddress"
  68.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  69.     lcnt = lcnt + 1
  70.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  71.     sht.Cells(lcnt, 2) = “Size"
  72.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  73.     lcnt = lcnt + 1
  74.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_COPYRIGHT]"
  75.     lcnt = lcnt + 1
  76.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  77.     sht.Cells(lcnt, 2) = “VirtualAddress"
  78.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  79.     lcnt = lcnt + 1
  80.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  81.     sht.Cells(lcnt, 2) = “Size"
  82.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  83.     lcnt = lcnt + 1
  84.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_GLOBALPTR]"
  85.     lcnt = lcnt + 1
  86.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  87.     sht.Cells(lcnt, 2) = “VirtualAddress"
  88.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  89.     lcnt = lcnt + 1
  90.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  91.     sht.Cells(lcnt, 2) = “Size"
  92.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  93.     lcnt = lcnt + 1
  94.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_TLS]"
  95.     lcnt = lcnt + 1
  96.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  97.     sht.Cells(lcnt, 2) = “VirtualAddress"
  98.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  99.     lcnt = lcnt + 1
  100.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  101.     sht.Cells(lcnt, 2) = “Size"
  102.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  103.     lcnt = lcnt + 1
  104.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG]"
  105.     lcnt = lcnt + 1
  106.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  107.     sht.Cells(lcnt, 2) = “VirtualAddress"
  108.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  109.     lcnt = lcnt + 1
  110.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  111.     sht.Cells(lcnt, 2) = “Size"
  112.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  113.     lcnt = lcnt + 1
  114.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT]"
  115.     lcnt = lcnt + 1
  116.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  117.     sht.Cells(lcnt, 2) = “VirtualAddress"
  118.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  119.     lcnt = lcnt + 1
  120.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  121.     sht.Cells(lcnt, 2) = “Size"
  122.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  123.     lcnt = lcnt + 1
  124.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_IAT]"
  125.     lcnt = lcnt + 1
  126.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  127.     sht.Cells(lcnt, 2) = “VirtualAddress"
  128.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  129.     lcnt = lcnt + 1
  130.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  131.     sht.Cells(lcnt, 2) = “Size"
  132.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  133.     lcnt = lcnt + 1
  134.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT]"
  135.     lcnt = lcnt + 1
  136.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  137.     sht.Cells(lcnt, 2) = “VirtualAddress"
  138.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  139.     lcnt = lcnt + 1
  140.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  141.     sht.Cells(lcnt, 2) = “Size"
  142.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  143.     lcnt = lcnt + 1
  144.     sht.Cells(lcnt, 1) = “[IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR]"
  145.     lcnt = lcnt + 1
  146.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  147.     sht.Cells(lcnt, 2) = “VirtualAddress"
  148.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  149.     lcnt = lcnt + 1
  150.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  151.     sht.Cells(lcnt, 2) = “Size"
  152.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  153.     lcnt = lcnt + 1
  154.     sht.Cells(lcnt, 1) = “[Reserved]"
  155.     lcnt = lcnt + 1
  156.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  157.     sht.Cells(lcnt, 2) = “VirtualAddress"
  158.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  159.     lcnt = lcnt + 1
  160.     sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  161.     sht.Cells(lcnt, 2) = “Size"
  162.     sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  163.     wSize = SectionHeadderPtr – bf.CurrentPosition
  164.     EntNum = wSize / 16
  165.     If wSize Mod 16 <> 0 Then
  166.         EntNum = EntNum + 1
  167.     End If
  168.     For i = 1 To EntNum
  169.         lcnt = lcnt + 1
  170.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  171.         sht.Cells(lcnt, 2) = “予備(" & Format(i, “000") & “)"
  172.         If wSize > 16 Then
  173.             sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(16), 32)
  174.             wSize = wSize – 16
  175.         Else
  176.             sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(wSize), wSize * 2)
  177.         End If
  178.     Next i

Image Section Headerに関する処理

行番号4~45の繰返し処理で、Image Section Headerの各エントリのデータを順に表示しています。

  1.     lcnt = lcnt + 1
  2.     sht.Cells(lcnt, 1) = “[IMAGE_SECTION_HEADER]"
  3.     For i = 1 To NumberOfSections
  4.         lcnt = lcnt + 1
  5.         sht.Cells(lcnt, 1) = “[SECTION(" & Format(i, “000") & “)]"
  6.         lcnt = lcnt + 1
  7.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  8.         sht.Cells(lcnt, 2) = “Name"
  9.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(8), 16)
  10.         lcnt = lcnt + 1
  11.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  12.         sht.Cells(lcnt, 2) = “PhysicalAddress&VirtualSize"
  13.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  14.         lcnt = lcnt + 1
  15.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  16.         sht.Cells(lcnt, 2) = “VirtualAddress"
  17.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  18.         lcnt = lcnt + 1
  19.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  20.         sht.Cells(lcnt, 2) = “SizeOfRawData"
  21.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  22.         lcnt = lcnt + 1
  23.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  24.         sht.Cells(lcnt, 2) = “PointerToRawData"
  25.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  26.         lcnt = lcnt + 1
  27.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  28.         sht.Cells(lcnt, 2) = “PointerToRelocations"
  29.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  30.         lcnt = lcnt + 1
  31.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  32.         sht.Cells(lcnt, 2) = “PointerToLinenumbers"
  33.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  34.         lcnt = lcnt + 1
  35.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  36.         sht.Cells(lcnt, 2) = “NumberOfRelocations"
  37.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  38.         lcnt = lcnt + 1
  39.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  40.         sht.Cells(lcnt, 2) = “NumberOfLinenumbers"
  41.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(2), 4)
  42.         lcnt = lcnt + 1
  43.         sht.Cells(lcnt, 1) = “'" & bf.GetPositionHex
  44.         sht.Cells(lcnt, 2) = “Characteristics"
  45.         sht.Cells(lcnt, 3) = Right(“000" & bf.GetDataHex(4), 8)
  46.     Next i
  47.     Set bf = Nothing
  48. End Sub

 

国本温子(著),緑川吉行(著),できるシリーズ編集部(著)
出版社:インプレス
発売日:2022/3/23
単行本(ソフトカバー):A5判/912ページ

大村あつし(著),古川順平(著)
出版社:技術評論社
発売日:2021/1/9
単行本(ソフトカバー):A5判/800ページ

高橋宣成(著)
出版社:技術評論社
発売日:2019/11/25
単行本(ソフトカバー):B5変形判/576ページ

ファイル解析

Posted by hides