1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4
5 #include <stdio.h>
6 #include <stdint.h>
7 #include <windows.h>
8 #include <dbghelp.h>
9
10 const DWORD CV_SIGNATURE_RSDS = 0x53445352; // 'SDSR'
11
12 struct CV_INFO_PDB70 {
13 DWORD CvSignature;
14 GUID Signature;
15 DWORD Age;
16 BYTE PdbFileName[1];
17 };
18
print_guid(const GUID & guid,DWORD age)19 void print_guid(const GUID& guid, DWORD age)
20 {
21 printf("%08X%04X%04X%02X%02X%02X%02X%02X%02X%02X%02X%X",
22 guid.Data1, guid.Data2, guid.Data3,
23 guid.Data4[0], guid.Data4[1], guid.Data4[2], guid.Data4[3],
24 guid.Data4[4], guid.Data4[5], guid.Data4[6], guid.Data4[7],
25 age);
26 }
27
main(int argc,char ** argv)28 int main(int argc, char** argv)
29 {
30 if (argc != 2) {
31 fprintf(stderr, "usage: fileid <file>\n");
32 return 1;
33 }
34
35 HANDLE file = CreateFileA(argv[1],
36 GENERIC_READ,
37 FILE_SHARE_READ,
38 nullptr,
39 OPEN_EXISTING,
40 FILE_ATTRIBUTE_NORMAL,
41 nullptr);
42 if (file == INVALID_HANDLE_VALUE) {
43 fprintf(stderr, "Couldn't open file: %s\n", argv[1]);
44 return 1;
45 }
46
47 HANDLE mapFile = CreateFileMappingA(file, NULL, PAGE_READONLY, 0, 0, 0);
48 if (mapFile == nullptr) {
49 fprintf(stderr, "Couldn't create file mapping\n");
50 CloseHandle(file);
51 return 1;
52 }
53
54 uint8_t* base = reinterpret_cast<uint8_t*>(MapViewOfFile(mapFile,
55 FILE_MAP_READ,
56 0,
57 0,
58 0));
59 if (base == nullptr) {
60 fprintf(stderr, "Couldn't map file\n");
61 CloseHandle(mapFile);
62 CloseHandle(file);
63 return 1;
64 }
65
66 DWORD size;
67 PIMAGE_DEBUG_DIRECTORY debug_dir =
68 reinterpret_cast<PIMAGE_DEBUG_DIRECTORY>(
69 ImageDirectoryEntryToDataEx(base,
70 FALSE,
71 IMAGE_DIRECTORY_ENTRY_DEBUG,
72 &size,
73 nullptr));
74
75 bool found = false;
76 if (debug_dir->Type == IMAGE_DEBUG_TYPE_CODEVIEW) {
77 CV_INFO_PDB70* cv =
78 reinterpret_cast<CV_INFO_PDB70*>(base + debug_dir->PointerToRawData);
79 if (cv->CvSignature == CV_SIGNATURE_RSDS) {
80 found = true;
81 print_guid(cv->Signature, cv->Age);
82 }
83 }
84
85 UnmapViewOfFile(base);
86 CloseHandle(mapFile);
87 CloseHandle(file);
88
89 return found ? 0 : 1;
90 }
91