Line data Source code
1 : //===- RawTypes.h -----------------------------------------------*- C++ -*-===//
2 : //
3 : // The LLVM Compiler Infrastructure
4 : //
5 : // This file is distributed under the University of Illinois Open Source
6 : // License. See LICENSE.TXT for details.
7 : //
8 : //===----------------------------------------------------------------------===//
9 :
10 : #ifndef LLVM_DEBUGINFO_PDB_RAW_RAWTYPES_H
11 : #define LLVM_DEBUGINFO_PDB_RAW_RAWTYPES_H
12 :
13 : #include "llvm/DebugInfo/CodeView/GUID.h"
14 : #include "llvm/DebugInfo/CodeView/TypeRecord.h"
15 : #include "llvm/Support/Endian.h"
16 :
17 : namespace llvm {
18 : namespace pdb {
19 : // This struct is defined as "SO" in langapi/include/pdb.h.
20 : struct SectionOffset {
21 : support::ulittle32_t Off;
22 : support::ulittle16_t Isect;
23 : char Padding[2];
24 : };
25 :
26 : /// Header of the hash tables found in the globals and publics sections.
27 : /// Based on GSIHashHdr in
28 : /// https://github.com/Microsoft/microsoft-pdb/blob/master/PDB/dbi/gsi.h
29 78 : struct GSIHashHeader {
30 : enum : unsigned {
31 : HdrSignature = ~0U,
32 : HdrVersion = 0xeffe0000 + 19990810,
33 : };
34 : support::ulittle32_t VerSignature;
35 : support::ulittle32_t VerHdr;
36 : support::ulittle32_t HrSize;
37 : support::ulittle32_t NumBuckets;
38 : };
39 :
40 : // This is HRFile.
41 136 : struct PSHashRecord {
42 : support::ulittle32_t Off; // Offset in the symbol record stream
43 : support::ulittle32_t CRef;
44 : };
45 :
46 : // This struct is defined as `SC` in include/dbicommon.h
47 273 : struct SectionContrib {
48 : support::ulittle16_t ISect;
49 : char Padding[2];
50 : support::little32_t Off;
51 : support::little32_t Size;
52 : support::ulittle32_t Characteristics;
53 : support::ulittle16_t Imod;
54 : char Padding2[2];
55 : support::ulittle32_t DataCrc;
56 : support::ulittle32_t RelocCrc;
57 : };
58 :
59 : // This struct is defined as `SC2` in include/dbicommon.h
60 : struct SectionContrib2 {
61 : // To guarantee SectionContrib2 is standard layout, we cannot use inheritance.
62 : SectionContrib Base;
63 : support::ulittle32_t ISectCoff;
64 : };
65 :
66 : // This corresponds to the `OMFSegMap` structure.
67 : struct SecMapHeader {
68 : support::ulittle16_t SecCount; // Number of segment descriptors in table
69 : support::ulittle16_t SecCountLog; // Number of logical segment descriptors
70 : };
71 :
72 : // This corresponds to the `OMFSegMapDesc` structure. The definition is not
73 : // present in the reference implementation, but the layout is derived from
74 : // code that accesses the fields.
75 : struct SecMapEntry {
76 : support::ulittle16_t Flags; // Descriptor flags. See OMFSegDescFlags
77 : support::ulittle16_t Ovl; // Logical overlay number.
78 : support::ulittle16_t Group; // Group index into descriptor array.
79 : support::ulittle16_t Frame;
80 : support::ulittle16_t SecName; // Byte index of the segment or group name
81 : // in the sstSegName table, or 0xFFFF.
82 : support::ulittle16_t ClassName; // Byte index of the class name in the
83 : // sstSegName table, or 0xFFFF.
84 : support::ulittle32_t Offset; // Byte offset of the logical segment
85 : // within the specified physical segment.
86 : // If group is set in flags, offset is the
87 : // offset of the group.
88 : support::ulittle32_t SecByteLength; // Byte count of the segment or group.
89 : };
90 :
91 : /// Some of the values are stored in bitfields. Since this needs to be portable
92 : /// across compilers and architectures (big / little endian in particular) we
93 : /// can't use the actual structures below, but must instead do the shifting
94 : /// and masking ourselves. The struct definitions are provided for reference.
95 : struct DbiFlags {
96 : /// uint16_t IncrementalLinking : 1; // True if linked incrementally
97 : /// uint16_t IsStripped : 1; // True if private symbols were
98 : /// stripped.
99 : /// uint16_t HasCTypes : 1; // True if linked with /debug:ctypes.
100 : /// uint16_t Reserved : 13;
101 : static const uint16_t FlagIncrementalMask = 0x0001;
102 : static const uint16_t FlagStrippedMask = 0x0002;
103 : static const uint16_t FlagHasCTypesMask = 0x0004;
104 : };
105 :
106 : struct DbiBuildNo {
107 : /// uint16_t MinorVersion : 8;
108 : /// uint16_t MajorVersion : 7;
109 : /// uint16_t NewVersionFormat : 1;
110 : static const uint16_t BuildMinorMask = 0x00FF;
111 : static const uint16_t BuildMinorShift = 0;
112 :
113 : static const uint16_t BuildMajorMask = 0x7F00;
114 : static const uint16_t BuildMajorShift = 8;
115 : };
116 :
117 : /// The fixed size header that appears at the beginning of the DBI Stream.
118 : struct DbiStreamHeader {
119 : support::little32_t VersionSignature;
120 : support::ulittle32_t VersionHeader;
121 :
122 : /// How "old" is this DBI Stream. Should match the age of the PDB InfoStream.
123 : support::ulittle32_t Age;
124 :
125 : /// Global symbol stream #
126 : support::ulittle16_t GlobalSymbolStreamIndex;
127 :
128 : /// See DbiBuildNo structure.
129 : support::ulittle16_t BuildNumber;
130 :
131 : /// Public symbols stream #
132 : support::ulittle16_t PublicSymbolStreamIndex;
133 :
134 : /// version of mspdbNNN.dll
135 : support::ulittle16_t PdbDllVersion;
136 :
137 : /// Symbol records stream #
138 : support::ulittle16_t SymRecordStreamIndex;
139 :
140 : /// rbld number of mspdbNNN.dll
141 : support::ulittle16_t PdbDllRbld;
142 :
143 : /// Size of module info stream
144 : support::little32_t ModiSubstreamSize;
145 :
146 : /// Size of sec. contrib stream
147 : support::little32_t SecContrSubstreamSize;
148 :
149 : /// Size of sec. map substream
150 : support::little32_t SectionMapSize;
151 :
152 : /// Size of file info substream
153 : support::little32_t FileInfoSize;
154 :
155 : /// Size of type server map
156 : support::little32_t TypeServerSize;
157 :
158 : /// Index of MFC Type Server
159 : support::ulittle32_t MFCTypeServerIndex;
160 :
161 : /// Size of DbgHeader info
162 : support::little32_t OptionalDbgHdrSize;
163 :
164 : /// Size of EC stream (what is EC?)
165 : support::little32_t ECSubstreamSize;
166 :
167 : /// See DbiFlags enum.
168 : support::ulittle16_t Flags;
169 :
170 : /// See PDB_MachineType enum.
171 : support::ulittle16_t MachineType;
172 :
173 : /// Pad to 64 bytes
174 : support::ulittle32_t Reserved;
175 : };
176 : static_assert(sizeof(DbiStreamHeader) == 64, "Invalid DbiStreamHeader size!");
177 :
178 105 : struct SectionContribEntry {
179 : support::ulittle16_t Section;
180 : char Padding1[2];
181 : support::little32_t Offset;
182 : support::little32_t Size;
183 : support::ulittle32_t Characteristics;
184 : support::ulittle16_t ModuleIndex;
185 : char Padding2[2];
186 : support::ulittle32_t DataCrc;
187 : support::ulittle32_t RelocCrc;
188 : };
189 :
190 : /// The header preceeding the File Info Substream of the DBI stream.
191 : struct FileInfoSubstreamHeader {
192 : /// Total # of modules, should match number of records in the ModuleInfo
193 : /// substream.
194 : support::ulittle16_t NumModules;
195 :
196 : /// Total # of source files. This value is not accurate because PDB actually
197 : /// supports more than 64k source files, so we ignore it and compute the value
198 : /// from other stream fields.
199 : support::ulittle16_t NumSourceFiles;
200 :
201 : /// Following this header the File Info Substream is laid out as follows:
202 : /// ulittle16_t ModIndices[NumModules];
203 : /// ulittle16_t ModFileCounts[NumModules];
204 : /// ulittle32_t FileNameOffsets[NumSourceFiles];
205 : /// char Names[][NumSourceFiles];
206 : /// with the caveat that `NumSourceFiles` cannot be trusted, so
207 : /// it is computed by summing the `ModFileCounts` array.
208 : };
209 :
210 : struct ModInfoFlags {
211 : /// uint16_t fWritten : 1; // True if DbiModuleDescriptor is dirty
212 : /// uint16_t fECEnabled : 1; // Is EC symbolic info present? (What is EC?)
213 : /// uint16_t unused : 6; // Reserved
214 : /// uint16_t iTSM : 8; // Type Server Index for this module
215 : static const uint16_t HasECFlagMask = 0x2;
216 :
217 : static const uint16_t TypeServerIndexMask = 0xFF00;
218 : static const uint16_t TypeServerIndexShift = 8;
219 : };
220 :
221 : /// The header preceeding each entry in the Module Info substream of the DBI
222 : /// stream. Corresponds to the type MODI in the reference implementation.
223 210 : struct ModuleInfoHeader {
224 : /// Currently opened module. This field is a pointer in the reference
225 : /// implementation, but that won't work on 64-bit systems, and anyway it
226 : /// doesn't make sense to read a pointer from a file. For now it is unused,
227 : /// so just ignore it.
228 : support::ulittle32_t Mod;
229 :
230 : /// First section contribution of this module.
231 : SectionContribEntry SC;
232 :
233 : /// See ModInfoFlags definition.
234 : support::ulittle16_t Flags;
235 :
236 : /// Stream Number of module debug info
237 : support::ulittle16_t ModDiStream;
238 :
239 : /// Size of local symbol debug info in above stream
240 : support::ulittle32_t SymBytes;
241 :
242 : /// Size of C11 line number info in above stream
243 : support::ulittle32_t C11Bytes;
244 :
245 : /// Size of C13 line number info in above stream
246 : support::ulittle32_t C13Bytes;
247 :
248 : /// Number of files contributing to this module
249 : support::ulittle16_t NumFiles;
250 :
251 : /// Padding so the next field is 4-byte aligned.
252 : char Padding1[2];
253 :
254 : /// Array of [0..NumFiles) DBI name buffer offsets. In the reference
255 : /// implementation this field is a pointer. But since you can't portably
256 : /// serialize a pointer, on 64-bit platforms they copy all the values except
257 : /// this one into the 32-bit version of the struct and use that for
258 : /// serialization. Regardless, this field is unused, it is only there to
259 : /// store a pointer that can be accessed at runtime.
260 : support::ulittle32_t FileNameOffs;
261 :
262 : /// Name Index for src file name
263 : support::ulittle32_t SrcFileNameNI;
264 :
265 : /// Name Index for path to compiler PDB
266 : support::ulittle32_t PdbFilePathNI;
267 :
268 : /// Following this header are two zero terminated strings.
269 : /// char ModuleName[];
270 : /// char ObjFileName[];
271 : };
272 :
273 : // This is PSGSIHDR struct defined in
274 : // https://github.com/Microsoft/microsoft-pdb/blob/master/PDB/dbi/gsi.h
275 39 : struct PublicsStreamHeader {
276 : support::ulittle32_t SymHash;
277 : support::ulittle32_t AddrMap;
278 : support::ulittle32_t NumThunks;
279 : support::ulittle32_t SizeOfThunk;
280 : support::ulittle16_t ISectThunkTable;
281 : char Padding[2];
282 : support::ulittle32_t OffThunkTable;
283 : support::ulittle32_t NumSections;
284 : };
285 :
286 : // The header preceeding the global TPI stream.
287 : // This corresponds to `HDR` in PDB/dbi/tpi.h.
288 : struct TpiStreamHeader {
289 : struct EmbeddedBuf {
290 : support::little32_t Off;
291 : support::ulittle32_t Length;
292 : };
293 :
294 : support::ulittle32_t Version;
295 : support::ulittle32_t HeaderSize;
296 : support::ulittle32_t TypeIndexBegin;
297 : support::ulittle32_t TypeIndexEnd;
298 : support::ulittle32_t TypeRecordBytes;
299 :
300 : // The following members correspond to `TpiHash` in PDB/dbi/tpi.h.
301 : support::ulittle16_t HashStreamIndex;
302 : support::ulittle16_t HashAuxStreamIndex;
303 : support::ulittle32_t HashKeySize;
304 : support::ulittle32_t NumHashBuckets;
305 :
306 : EmbeddedBuf HashValueBuffer;
307 : EmbeddedBuf IndexOffsetBuffer;
308 : EmbeddedBuf HashAdjBuffer;
309 : };
310 :
311 : const uint32_t MinTpiHashBuckets = 0x1000;
312 : const uint32_t MaxTpiHashBuckets = 0x40000;
313 :
314 : /// The header preceeding the global PDB Stream (Stream 1)
315 59 : struct InfoStreamHeader {
316 : support::ulittle32_t Version;
317 : support::ulittle32_t Signature;
318 : support::ulittle32_t Age;
319 : codeview::GUID Guid;
320 : };
321 :
322 : /// The header preceeding the /names stream.
323 116 : struct PDBStringTableHeader {
324 : support::ulittle32_t Signature; // PDBStringTableSignature
325 : support::ulittle32_t HashVersion; // 1 or 2
326 : support::ulittle32_t ByteSize; // Number of bytes of names buffer.
327 : };
328 :
329 : const uint32_t PDBStringTableSignature = 0xEFFEEFFE;
330 :
331 : } // namespace pdb
332 : } // namespace llvm
333 :
334 : #endif
|