1 //===- SymbolRecordMapping.cpp -----------------------------------*- 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 #include "llvm/DebugInfo/CodeView/SymbolRecordMapping.h" 11 12 using namespace llvm; 13 using namespace llvm::codeview; 14 15 #define error(X) \ 16 if (auto EC = X) \ 17 return EC; 18 19 namespace { 20 struct MapGap { 21 Error operator()(CodeViewRecordIO &IO, LocalVariableAddrGap &Gap) const { 22 error(IO.mapInteger(Gap.GapStartOffset)); 23 error(IO.mapInteger(Gap.Range)); 24 return Error::success(); 25 } 26 }; 27 } 28 29 static Error mapLocalVariableAddrRange(CodeViewRecordIO &IO, 30 LocalVariableAddrRange &Range) { 31 error(IO.mapInteger(Range.OffsetStart)); 32 error(IO.mapInteger(Range.ISectStart)); 33 error(IO.mapInteger(Range.Range)); 34 return Error::success(); 35 } 36 37 Error SymbolRecordMapping::visitSymbolBegin(CVSymbol &Record) { 38 error(IO.beginRecord(MaxRecordLength - sizeof(RecordPrefix))); 39 return Error::success(); 40 } 41 42 Error SymbolRecordMapping::visitSymbolEnd(CVSymbol &Record) { 43 error(IO.padToAlignment(alignOf(Container))); 44 error(IO.endRecord()); 45 return Error::success(); 46 } 47 48 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, BlockSym &Block) { 49 50 error(IO.mapInteger(Block.Parent)); 51 error(IO.mapInteger(Block.End)); 52 error(IO.mapInteger(Block.CodeSize)); 53 error(IO.mapInteger(Block.CodeOffset)); 54 error(IO.mapInteger(Block.Segment)); 55 error(IO.mapStringZ(Block.Name)); 56 57 return Error::success(); 58 } 59 60 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, Thunk32Sym &Thunk) { 61 62 error(IO.mapInteger(Thunk.Parent)); 63 error(IO.mapInteger(Thunk.End)); 64 error(IO.mapInteger(Thunk.Next)); 65 error(IO.mapInteger(Thunk.Offset)); 66 error(IO.mapInteger(Thunk.Segment)); 67 error(IO.mapInteger(Thunk.Length)); 68 error(IO.mapEnum(Thunk.Thunk)); 69 error(IO.mapStringZ(Thunk.Name)); 70 error(IO.mapByteVectorTail(Thunk.VariantData)); 71 72 return Error::success(); 73 } 74 75 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 76 TrampolineSym &Tramp) { 77 78 error(IO.mapEnum(Tramp.Type)); 79 error(IO.mapInteger(Tramp.Size)); 80 error(IO.mapInteger(Tramp.ThunkOffset)); 81 error(IO.mapInteger(Tramp.TargetOffset)); 82 error(IO.mapInteger(Tramp.ThunkSection)); 83 error(IO.mapInteger(Tramp.TargetSection)); 84 85 return Error::success(); 86 } 87 88 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 89 SectionSym &Section) { 90 uint8_t Padding = 0; 91 92 error(IO.mapInteger(Section.SectionNumber)); 93 error(IO.mapInteger(Section.Alignment)); 94 error(IO.mapInteger(Padding)); 95 error(IO.mapInteger(Section.Rva)); 96 error(IO.mapInteger(Section.Length)); 97 error(IO.mapInteger(Section.Characteristics)); 98 error(IO.mapStringZ(Section.Name)); 99 100 return Error::success(); 101 } 102 103 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 104 CoffGroupSym &CoffGroup) { 105 106 error(IO.mapInteger(CoffGroup.Size)); 107 error(IO.mapInteger(CoffGroup.Characteristics)); 108 error(IO.mapInteger(CoffGroup.Offset)); 109 error(IO.mapInteger(CoffGroup.Segment)); 110 error(IO.mapStringZ(CoffGroup.Name)); 111 112 return Error::success(); 113 } 114 115 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 116 BPRelativeSym &BPRel) { 117 118 error(IO.mapInteger(BPRel.Offset)); 119 error(IO.mapInteger(BPRel.Type)); 120 error(IO.mapStringZ(BPRel.Name)); 121 122 return Error::success(); 123 } 124 125 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 126 BuildInfoSym &BuildInfo) { 127 128 error(IO.mapInteger(BuildInfo.BuildId)); 129 130 return Error::success(); 131 } 132 133 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 134 CallSiteInfoSym &CallSiteInfo) { 135 uint16_t Padding = 0; 136 137 error(IO.mapInteger(CallSiteInfo.CodeOffset)); 138 error(IO.mapInteger(CallSiteInfo.Segment)); 139 error(IO.mapInteger(Padding)); 140 error(IO.mapInteger(CallSiteInfo.Type)); 141 142 return Error::success(); 143 } 144 145 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 146 EnvBlockSym &EnvBlock) { 147 148 uint8_t Reserved = 0; 149 error(IO.mapInteger(Reserved)); 150 error(IO.mapStringZVectorZ(EnvBlock.Fields)); 151 152 return Error::success(); 153 } 154 155 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 156 FileStaticSym &FileStatic) { 157 158 error(IO.mapInteger(FileStatic.Index)); 159 error(IO.mapInteger(FileStatic.ModFilenameOffset)); 160 error(IO.mapEnum(FileStatic.Flags)); 161 error(IO.mapStringZ(FileStatic.Name)); 162 163 return Error::success(); 164 } 165 166 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, ExportSym &Export) { 167 168 error(IO.mapInteger(Export.Ordinal)); 169 error(IO.mapEnum(Export.Flags)); 170 error(IO.mapStringZ(Export.Name)); 171 172 return Error::success(); 173 } 174 175 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 176 Compile2Sym &Compile2) { 177 178 error(IO.mapEnum(Compile2.Flags)); 179 error(IO.mapEnum(Compile2.Machine)); 180 error(IO.mapInteger(Compile2.VersionFrontendMajor)); 181 error(IO.mapInteger(Compile2.VersionFrontendMinor)); 182 error(IO.mapInteger(Compile2.VersionFrontendBuild)); 183 error(IO.mapInteger(Compile2.VersionBackendMajor)); 184 error(IO.mapInteger(Compile2.VersionBackendMinor)); 185 error(IO.mapInteger(Compile2.VersionBackendBuild)); 186 error(IO.mapStringZ(Compile2.Version)); 187 error(IO.mapStringZVectorZ(Compile2.ExtraStrings)); 188 189 return Error::success(); 190 } 191 192 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 193 Compile3Sym &Compile3) { 194 195 error(IO.mapEnum(Compile3.Flags)); 196 error(IO.mapEnum(Compile3.Machine)); 197 error(IO.mapInteger(Compile3.VersionFrontendMajor)); 198 error(IO.mapInteger(Compile3.VersionFrontendMinor)); 199 error(IO.mapInteger(Compile3.VersionFrontendBuild)); 200 error(IO.mapInteger(Compile3.VersionFrontendQFE)); 201 error(IO.mapInteger(Compile3.VersionBackendMajor)); 202 error(IO.mapInteger(Compile3.VersionBackendMinor)); 203 error(IO.mapInteger(Compile3.VersionBackendBuild)); 204 error(IO.mapInteger(Compile3.VersionBackendQFE)); 205 error(IO.mapStringZ(Compile3.Version)); 206 207 return Error::success(); 208 } 209 210 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 211 ConstantSym &Constant) { 212 213 error(IO.mapInteger(Constant.Type)); 214 error(IO.mapEncodedInteger(Constant.Value)); 215 error(IO.mapStringZ(Constant.Name)); 216 217 return Error::success(); 218 } 219 220 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, DataSym &Data) { 221 222 error(IO.mapInteger(Data.Type)); 223 error(IO.mapInteger(Data.DataOffset)); 224 error(IO.mapInteger(Data.Segment)); 225 error(IO.mapStringZ(Data.Name)); 226 227 return Error::success(); 228 } 229 230 Error SymbolRecordMapping::visitKnownRecord( 231 CVSymbol &CVR, DefRangeFramePointerRelSym &DefRangeFramePointerRel) { 232 233 error(IO.mapInteger(DefRangeFramePointerRel.Offset)); 234 error(mapLocalVariableAddrRange(IO, DefRangeFramePointerRel.Range)); 235 error(IO.mapVectorTail(DefRangeFramePointerRel.Gaps, MapGap())); 236 237 return Error::success(); 238 } 239 240 Error SymbolRecordMapping::visitKnownRecord( 241 CVSymbol &CVR, 242 DefRangeFramePointerRelFullScopeSym &DefRangeFramePointerRelFullScope) { 243 244 error(IO.mapInteger(DefRangeFramePointerRelFullScope.Offset)); 245 246 return Error::success(); 247 } 248 249 Error SymbolRecordMapping::visitKnownRecord( 250 CVSymbol &CVR, DefRangeRegisterRelSym &DefRangeRegisterRel) { 251 252 error(IO.mapObject(DefRangeRegisterRel.Hdr.Register)); 253 error(IO.mapObject(DefRangeRegisterRel.Hdr.Flags)); 254 error(IO.mapObject(DefRangeRegisterRel.Hdr.BasePointerOffset)); 255 error(mapLocalVariableAddrRange(IO, DefRangeRegisterRel.Range)); 256 error(IO.mapVectorTail(DefRangeRegisterRel.Gaps, MapGap())); 257 258 return Error::success(); 259 } 260 261 Error SymbolRecordMapping::visitKnownRecord( 262 CVSymbol &CVR, DefRangeRegisterSym &DefRangeRegister) { 263 264 error(IO.mapObject(DefRangeRegister.Hdr.Register)); 265 error(IO.mapObject(DefRangeRegister.Hdr.MayHaveNoName)); 266 error(mapLocalVariableAddrRange(IO, DefRangeRegister.Range)); 267 error(IO.mapVectorTail(DefRangeRegister.Gaps, MapGap())); 268 269 return Error::success(); 270 } 271 272 Error SymbolRecordMapping::visitKnownRecord( 273 CVSymbol &CVR, DefRangeSubfieldRegisterSym &DefRangeSubfieldRegister) { 274 275 error(IO.mapObject(DefRangeSubfieldRegister.Hdr.Register)); 276 error(IO.mapObject(DefRangeSubfieldRegister.Hdr.MayHaveNoName)); 277 error(IO.mapObject(DefRangeSubfieldRegister.Hdr.OffsetInParent)); 278 error(mapLocalVariableAddrRange(IO, DefRangeSubfieldRegister.Range)); 279 error(IO.mapVectorTail(DefRangeSubfieldRegister.Gaps, MapGap())); 280 281 return Error::success(); 282 } 283 284 Error SymbolRecordMapping::visitKnownRecord( 285 CVSymbol &CVR, DefRangeSubfieldSym &DefRangeSubfield) { 286 287 error(IO.mapInteger(DefRangeSubfield.Program)); 288 error(IO.mapInteger(DefRangeSubfield.OffsetInParent)); 289 error(mapLocalVariableAddrRange(IO, DefRangeSubfield.Range)); 290 error(IO.mapVectorTail(DefRangeSubfield.Gaps, MapGap())); 291 292 return Error::success(); 293 } 294 295 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 296 DefRangeSym &DefRange) { 297 298 error(IO.mapInteger(DefRange.Program)); 299 error(mapLocalVariableAddrRange(IO, DefRange.Range)); 300 error(IO.mapVectorTail(DefRange.Gaps, MapGap())); 301 302 return Error::success(); 303 } 304 305 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 306 FrameCookieSym &FrameCookie) { 307 308 error(IO.mapInteger(FrameCookie.CodeOffset)); 309 error(IO.mapInteger(FrameCookie.Register)); 310 error(IO.mapEnum(FrameCookie.CookieKind)); 311 error(IO.mapInteger(FrameCookie.Flags)); 312 313 return Error::success(); 314 } 315 316 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 317 FrameProcSym &FrameProc) { 318 error(IO.mapInteger(FrameProc.TotalFrameBytes)); 319 error(IO.mapInteger(FrameProc.PaddingFrameBytes)); 320 error(IO.mapInteger(FrameProc.OffsetToPadding)); 321 error(IO.mapInteger(FrameProc.BytesOfCalleeSavedRegisters)); 322 error(IO.mapInteger(FrameProc.OffsetOfExceptionHandler)); 323 error(IO.mapInteger(FrameProc.SectionIdOfExceptionHandler)); 324 error(IO.mapEnum(FrameProc.Flags)); 325 326 return Error::success(); 327 } 328 329 Error SymbolRecordMapping::visitKnownRecord( 330 CVSymbol &CVR, HeapAllocationSiteSym &HeapAllocSite) { 331 332 error(IO.mapInteger(HeapAllocSite.CodeOffset)); 333 error(IO.mapInteger(HeapAllocSite.Segment)); 334 error(IO.mapInteger(HeapAllocSite.CallInstructionSize)); 335 error(IO.mapInteger(HeapAllocSite.Type)); 336 337 return Error::success(); 338 } 339 340 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 341 InlineSiteSym &InlineSite) { 342 343 error(IO.mapInteger(InlineSite.Parent)); 344 error(IO.mapInteger(InlineSite.End)); 345 error(IO.mapInteger(InlineSite.Inlinee)); 346 error(IO.mapByteVectorTail(InlineSite.AnnotationData)); 347 348 return Error::success(); 349 } 350 351 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 352 RegisterSym &Register) { 353 354 error(IO.mapInteger(Register.Index)); 355 error(IO.mapEnum(Register.Register)); 356 error(IO.mapStringZ(Register.Name)); 357 358 return Error::success(); 359 } 360 361 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 362 PublicSym32 &Public) { 363 364 error(IO.mapEnum(Public.Flags)); 365 error(IO.mapInteger(Public.Offset)); 366 error(IO.mapInteger(Public.Segment)); 367 error(IO.mapStringZ(Public.Name)); 368 369 return Error::success(); 370 } 371 372 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 373 ProcRefSym &ProcRef) { 374 375 error(IO.mapInteger(ProcRef.SumName)); 376 error(IO.mapInteger(ProcRef.SymOffset)); 377 error(IO.mapInteger(ProcRef.Module)); 378 error(IO.mapStringZ(ProcRef.Name)); 379 380 return Error::success(); 381 } 382 383 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, LabelSym &Label) { 384 385 error(IO.mapInteger(Label.CodeOffset)); 386 error(IO.mapInteger(Label.Segment)); 387 error(IO.mapEnum(Label.Flags)); 388 error(IO.mapStringZ(Label.Name)); 389 390 return Error::success(); 391 } 392 393 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, LocalSym &Local) { 394 error(IO.mapInteger(Local.Type)); 395 error(IO.mapEnum(Local.Flags)); 396 error(IO.mapStringZ(Local.Name)); 397 398 return Error::success(); 399 } 400 401 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 402 ObjNameSym &ObjName) { 403 404 error(IO.mapInteger(ObjName.Signature)); 405 error(IO.mapStringZ(ObjName.Name)); 406 407 return Error::success(); 408 } 409 410 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, ProcSym &Proc) { 411 error(IO.mapInteger(Proc.Parent)); 412 error(IO.mapInteger(Proc.End)); 413 error(IO.mapInteger(Proc.Next)); 414 error(IO.mapInteger(Proc.CodeSize)); 415 error(IO.mapInteger(Proc.DbgStart)); 416 error(IO.mapInteger(Proc.DbgEnd)); 417 error(IO.mapInteger(Proc.FunctionType)); 418 error(IO.mapInteger(Proc.CodeOffset)); 419 error(IO.mapInteger(Proc.Segment)); 420 error(IO.mapEnum(Proc.Flags)); 421 error(IO.mapStringZ(Proc.Name)); 422 return Error::success(); 423 } 424 425 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 426 ScopeEndSym &ScopeEnd) { 427 return Error::success(); 428 } 429 430 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, CallerSym &Caller) { 431 error(IO.mapVectorN<uint32_t>( 432 Caller.Indices, 433 [](CodeViewRecordIO &IO, TypeIndex &N) { return IO.mapInteger(N); })); 434 return Error::success(); 435 } 436 437 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 438 RegRelativeSym &RegRel) { 439 440 error(IO.mapInteger(RegRel.Offset)); 441 error(IO.mapInteger(RegRel.Type)); 442 error(IO.mapEnum(RegRel.Register)); 443 error(IO.mapStringZ(RegRel.Name)); 444 445 return Error::success(); 446 } 447 448 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 449 ThreadLocalDataSym &Data) { 450 451 error(IO.mapInteger(Data.Type)); 452 error(IO.mapInteger(Data.DataOffset)); 453 error(IO.mapInteger(Data.Segment)); 454 error(IO.mapStringZ(Data.Name)); 455 456 return Error::success(); 457 } 458 459 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, UDTSym &UDT) { 460 461 error(IO.mapInteger(UDT.Type)); 462 error(IO.mapStringZ(UDT.Name)); 463 464 return Error::success(); 465 } 466 467 Error SymbolRecordMapping::visitKnownRecord(CVSymbol &CVR, 468 UsingNamespaceSym &UN) { 469 470 error(IO.mapStringZ(UN.Name)); 471 472 return Error::success(); 473 } 474 475 RegisterId codeview::decodeFramePtrReg(EncodedFramePtrReg EncodedReg, 476 CPUType CPU) { 477 assert(unsigned(EncodedReg) < 4); 478 switch (CPU) { 479 // FIXME: Add ARM and AArch64 variants here. 480 default: 481 break; 482 case CPUType::Intel8080: 483 case CPUType::Intel8086: 484 case CPUType::Intel80286: 485 case CPUType::Intel80386: 486 case CPUType::Intel80486: 487 case CPUType::Pentium: 488 case CPUType::PentiumPro: 489 case CPUType::Pentium3: 490 switch (EncodedReg) { 491 case EncodedFramePtrReg::None: return RegisterId::NONE; 492 case EncodedFramePtrReg::StackPtr: return RegisterId::VFRAME; 493 case EncodedFramePtrReg::FramePtr: return RegisterId::EBP; 494 case EncodedFramePtrReg::BasePtr: return RegisterId::EBX; 495 } 496 llvm_unreachable("bad encoding"); 497 case CPUType::X64: 498 switch (EncodedReg) { 499 case EncodedFramePtrReg::None: return RegisterId::NONE; 500 case EncodedFramePtrReg::StackPtr: return RegisterId::RSP; 501 case EncodedFramePtrReg::FramePtr: return RegisterId::RBP; 502 case EncodedFramePtrReg::BasePtr: return RegisterId::R13; 503 } 504 llvm_unreachable("bad encoding"); 505 } 506 return RegisterId::NONE; 507 } 508 509 EncodedFramePtrReg codeview::encodeFramePtrReg(RegisterId Reg, CPUType CPU) { 510 switch (CPU) { 511 // FIXME: Add ARM and AArch64 variants here. 512 default: 513 break; 514 case CPUType::Intel8080: 515 case CPUType::Intel8086: 516 case CPUType::Intel80286: 517 case CPUType::Intel80386: 518 case CPUType::Intel80486: 519 case CPUType::Pentium: 520 case CPUType::PentiumPro: 521 case CPUType::Pentium3: 522 switch (Reg) { 523 case RegisterId::VFRAME: 524 return EncodedFramePtrReg::StackPtr; 525 case RegisterId::EBP: 526 return EncodedFramePtrReg::FramePtr; 527 case RegisterId::EBX: 528 return EncodedFramePtrReg::BasePtr; 529 default: 530 break; 531 } 532 case CPUType::X64: 533 switch (Reg) { 534 case RegisterId::RSP: 535 return EncodedFramePtrReg::StackPtr; 536 case RegisterId::RBP: 537 return EncodedFramePtrReg::FramePtr; 538 case RegisterId::R13: 539 return EncodedFramePtrReg::BasePtr; 540 default: 541 break; 542 } 543 } 544 return EncodedFramePtrReg::None; 545 } 546