1 //===- DWARFFormValue.cpp -------------------------------------------------===// 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/DWARF/DWARFFormValue.h" 11 #include "SyntaxHighlighting.h" 12 #include "llvm/ADT/ArrayRef.h" 13 #include "llvm/ADT/None.h" 14 #include "llvm/ADT/Optional.h" 15 #include "llvm/ADT/StringRef.h" 16 #include "llvm/BinaryFormat/Dwarf.h" 17 #include "llvm/DebugInfo/DWARF/DWARFContext.h" 18 #include "llvm/DebugInfo/DWARF/DWARFRelocMap.h" 19 #include "llvm/DebugInfo/DWARF/DWARFUnit.h" 20 #include "llvm/Support/ErrorHandling.h" 21 #include "llvm/Support/Format.h" 22 #include "llvm/Support/raw_ostream.h" 23 #include <cinttypes> 24 #include <cstdint> 25 #include <limits> 26 27 using namespace llvm; 28 using namespace dwarf; 29 using namespace syntax; 30 31 static const DWARFFormValue::FormClass DWARF4FormClasses[] = { 32 DWARFFormValue::FC_Unknown, // 0x0 33 DWARFFormValue::FC_Address, // 0x01 DW_FORM_addr 34 DWARFFormValue::FC_Unknown, // 0x02 unused 35 DWARFFormValue::FC_Block, // 0x03 DW_FORM_block2 36 DWARFFormValue::FC_Block, // 0x04 DW_FORM_block4 37 DWARFFormValue::FC_Constant, // 0x05 DW_FORM_data2 38 // --- These can be FC_SectionOffset in DWARF3 and below: 39 DWARFFormValue::FC_Constant, // 0x06 DW_FORM_data4 40 DWARFFormValue::FC_Constant, // 0x07 DW_FORM_data8 41 // --- 42 DWARFFormValue::FC_String, // 0x08 DW_FORM_string 43 DWARFFormValue::FC_Block, // 0x09 DW_FORM_block 44 DWARFFormValue::FC_Block, // 0x0a DW_FORM_block1 45 DWARFFormValue::FC_Constant, // 0x0b DW_FORM_data1 46 DWARFFormValue::FC_Flag, // 0x0c DW_FORM_flag 47 DWARFFormValue::FC_Constant, // 0x0d DW_FORM_sdata 48 DWARFFormValue::FC_String, // 0x0e DW_FORM_strp 49 DWARFFormValue::FC_Constant, // 0x0f DW_FORM_udata 50 DWARFFormValue::FC_Reference, // 0x10 DW_FORM_ref_addr 51 DWARFFormValue::FC_Reference, // 0x11 DW_FORM_ref1 52 DWARFFormValue::FC_Reference, // 0x12 DW_FORM_ref2 53 DWARFFormValue::FC_Reference, // 0x13 DW_FORM_ref4 54 DWARFFormValue::FC_Reference, // 0x14 DW_FORM_ref8 55 DWARFFormValue::FC_Reference, // 0x15 DW_FORM_ref_udata 56 DWARFFormValue::FC_Indirect, // 0x16 DW_FORM_indirect 57 DWARFFormValue::FC_SectionOffset, // 0x17 DW_FORM_sec_offset 58 DWARFFormValue::FC_Exprloc, // 0x18 DW_FORM_exprloc 59 DWARFFormValue::FC_Flag, // 0x19 DW_FORM_flag_present 60 }; 61 62 Optional<uint8_t> 63 DWARFFormValue::getFixedByteSize(dwarf::Form Form, 64 const DWARFFormParams Params) { 65 switch (Form) { 66 case DW_FORM_addr: 67 if (Params) 68 return Params.AddrSize; 69 return None; 70 71 case DW_FORM_block: // ULEB128 length L followed by L bytes. 72 case DW_FORM_block1: // 1 byte length L followed by L bytes. 73 case DW_FORM_block2: // 2 byte length L followed by L bytes. 74 case DW_FORM_block4: // 4 byte length L followed by L bytes. 75 case DW_FORM_string: // C-string with null terminator. 76 case DW_FORM_sdata: // SLEB128. 77 case DW_FORM_udata: // ULEB128. 78 case DW_FORM_ref_udata: // ULEB128. 79 case DW_FORM_indirect: // ULEB128. 80 case DW_FORM_exprloc: // ULEB128 length L followed by L bytes. 81 case DW_FORM_strx: // ULEB128. 82 case DW_FORM_addrx: // ULEB128. 83 case DW_FORM_loclistx: // ULEB128. 84 case DW_FORM_rnglistx: // ULEB128. 85 case DW_FORM_GNU_addr_index: // ULEB128. 86 case DW_FORM_GNU_str_index: // ULEB128. 87 return None; 88 89 case DW_FORM_ref_addr: 90 if (Params) 91 return Params.getRefAddrByteSize(); 92 return None; 93 94 case DW_FORM_flag: 95 case DW_FORM_data1: 96 case DW_FORM_ref1: 97 case DW_FORM_strx1: 98 case DW_FORM_addrx1: 99 return 1; 100 101 case DW_FORM_data2: 102 case DW_FORM_ref2: 103 case DW_FORM_strx2: 104 case DW_FORM_addrx2: 105 return 2; 106 107 case DW_FORM_strx3: 108 return 3; 109 110 case DW_FORM_data4: 111 case DW_FORM_ref4: 112 case DW_FORM_ref_sup4: 113 case DW_FORM_strx4: 114 case DW_FORM_addrx4: 115 return 4; 116 117 case DW_FORM_strp: 118 case DW_FORM_GNU_ref_alt: 119 case DW_FORM_GNU_strp_alt: 120 case DW_FORM_line_strp: 121 case DW_FORM_sec_offset: 122 case DW_FORM_strp_sup: 123 if (Params) 124 return Params.getDwarfOffsetByteSize(); 125 return None; 126 127 case DW_FORM_data8: 128 case DW_FORM_ref8: 129 case DW_FORM_ref_sig8: 130 case DW_FORM_ref_sup8: 131 return 8; 132 133 case DW_FORM_flag_present: 134 return 0; 135 136 case DW_FORM_data16: 137 return 16; 138 139 case DW_FORM_implicit_const: 140 // The implicit value is stored in the abbreviation as a SLEB128, and 141 // there no data in debug info. 142 return 0; 143 144 default: 145 llvm_unreachable("Handle this form in this switch statement"); 146 } 147 return None; 148 } 149 150 bool DWARFFormValue::skipValue(dwarf::Form Form, DataExtractor DebugInfoData, 151 uint32_t *OffsetPtr, 152 const DWARFFormParams Params) { 153 bool Indirect = false; 154 do { 155 switch (Form) { 156 // Blocks of inlined data that have a length field and the data bytes 157 // inlined in the .debug_info. 158 case DW_FORM_exprloc: 159 case DW_FORM_block: { 160 uint64_t size = DebugInfoData.getULEB128(OffsetPtr); 161 *OffsetPtr += size; 162 return true; 163 } 164 case DW_FORM_block1: { 165 uint8_t size = DebugInfoData.getU8(OffsetPtr); 166 *OffsetPtr += size; 167 return true; 168 } 169 case DW_FORM_block2: { 170 uint16_t size = DebugInfoData.getU16(OffsetPtr); 171 *OffsetPtr += size; 172 return true; 173 } 174 case DW_FORM_block4: { 175 uint32_t size = DebugInfoData.getU32(OffsetPtr); 176 *OffsetPtr += size; 177 return true; 178 } 179 180 // Inlined NULL terminated C-strings. 181 case DW_FORM_string: 182 DebugInfoData.getCStr(OffsetPtr); 183 return true; 184 185 case DW_FORM_addr: 186 case DW_FORM_ref_addr: 187 case DW_FORM_flag_present: 188 case DW_FORM_data1: 189 case DW_FORM_data2: 190 case DW_FORM_data4: 191 case DW_FORM_data8: 192 case DW_FORM_data16: 193 case DW_FORM_flag: 194 case DW_FORM_ref1: 195 case DW_FORM_ref2: 196 case DW_FORM_ref4: 197 case DW_FORM_ref8: 198 case DW_FORM_ref_sig8: 199 case DW_FORM_ref_sup4: 200 case DW_FORM_ref_sup8: 201 case DW_FORM_strx1: 202 case DW_FORM_strx2: 203 case DW_FORM_strx4: 204 case DW_FORM_addrx1: 205 case DW_FORM_addrx2: 206 case DW_FORM_addrx4: 207 case DW_FORM_sec_offset: 208 case DW_FORM_strp: 209 case DW_FORM_strp_sup: 210 case DW_FORM_line_strp: 211 case DW_FORM_GNU_ref_alt: 212 case DW_FORM_GNU_strp_alt: 213 if (Optional<uint8_t> FixedSize = 214 DWARFFormValue::getFixedByteSize(Form, Params)) { 215 *OffsetPtr += *FixedSize; 216 return true; 217 } 218 return false; 219 220 // signed or unsigned LEB 128 values. 221 case DW_FORM_sdata: 222 DebugInfoData.getSLEB128(OffsetPtr); 223 return true; 224 225 case DW_FORM_udata: 226 case DW_FORM_ref_udata: 227 case DW_FORM_strx: 228 case DW_FORM_addrx: 229 case DW_FORM_loclistx: 230 case DW_FORM_rnglistx: 231 case DW_FORM_GNU_addr_index: 232 case DW_FORM_GNU_str_index: 233 DebugInfoData.getULEB128(OffsetPtr); 234 return true; 235 236 case DW_FORM_indirect: 237 Indirect = true; 238 Form = static_cast<dwarf::Form>(DebugInfoData.getULEB128(OffsetPtr)); 239 break; 240 241 default: 242 return false; 243 } 244 } while (Indirect); 245 return true; 246 } 247 248 bool DWARFFormValue::isFormClass(DWARFFormValue::FormClass FC) const { 249 // First, check DWARF4 form classes. 250 if (Form < makeArrayRef(DWARF4FormClasses).size() && 251 DWARF4FormClasses[Form] == FC) 252 return true; 253 // Check more forms from DWARF4 and DWARF5 proposals. 254 switch (Form) { 255 case DW_FORM_ref_sig8: 256 case DW_FORM_GNU_ref_alt: 257 return (FC == FC_Reference); 258 case DW_FORM_GNU_addr_index: 259 return (FC == FC_Address); 260 case DW_FORM_GNU_str_index: 261 case DW_FORM_GNU_strp_alt: 262 case DW_FORM_strx: 263 case DW_FORM_strx1: 264 case DW_FORM_strx2: 265 case DW_FORM_strx3: 266 case DW_FORM_strx4: 267 return (FC == FC_String); 268 case DW_FORM_implicit_const: 269 return (FC == FC_Constant); 270 default: 271 break; 272 } 273 // In DWARF3 DW_FORM_data4 and DW_FORM_data8 served also as a section offset. 274 // Don't check for DWARF version here, as some producers may still do this 275 // by mistake. Also accept DW_FORM_strp since this is .debug_str section 276 // offset. 277 return (Form == DW_FORM_data4 || Form == DW_FORM_data8 || 278 Form == DW_FORM_strp) && 279 FC == FC_SectionOffset; 280 } 281 282 bool DWARFFormValue::extractValue(const DWARFDataExtractor &Data, 283 uint32_t *OffsetPtr, DWARFFormParams FP, 284 const DWARFUnit *CU) { 285 U = CU; 286 bool Indirect = false; 287 bool IsBlock = false; 288 Value.data = nullptr; 289 // Read the value for the form into value and follow and DW_FORM_indirect 290 // instances we run into 291 do { 292 Indirect = false; 293 switch (Form) { 294 case DW_FORM_addr: 295 case DW_FORM_ref_addr: { 296 uint16_t Size = 297 (Form == DW_FORM_addr) ? FP.AddrSize : FP.getRefAddrByteSize(); 298 Value.uval = Data.getRelocatedValue(Size, OffsetPtr, &Value.SectionIndex); 299 break; 300 } 301 case DW_FORM_exprloc: 302 case DW_FORM_block: 303 Value.uval = Data.getULEB128(OffsetPtr); 304 IsBlock = true; 305 break; 306 case DW_FORM_block1: 307 Value.uval = Data.getU8(OffsetPtr); 308 IsBlock = true; 309 break; 310 case DW_FORM_block2: 311 Value.uval = Data.getU16(OffsetPtr); 312 IsBlock = true; 313 break; 314 case DW_FORM_block4: 315 Value.uval = Data.getU32(OffsetPtr); 316 IsBlock = true; 317 break; 318 case DW_FORM_data1: 319 case DW_FORM_ref1: 320 case DW_FORM_flag: 321 case DW_FORM_strx1: 322 case DW_FORM_addrx1: 323 Value.uval = Data.getU8(OffsetPtr); 324 break; 325 case DW_FORM_data2: 326 case DW_FORM_ref2: 327 case DW_FORM_strx2: 328 case DW_FORM_addrx2: 329 Value.uval = Data.getU16(OffsetPtr); 330 break; 331 case DW_FORM_strx3: 332 Value.uval = Data.getU24(OffsetPtr); 333 break; 334 case DW_FORM_data4: 335 case DW_FORM_ref4: 336 case DW_FORM_ref_sup4: 337 case DW_FORM_strx4: 338 case DW_FORM_addrx4: 339 Value.uval = Data.getRelocatedValue(4, OffsetPtr); 340 break; 341 case DW_FORM_data8: 342 case DW_FORM_ref8: 343 case DW_FORM_ref_sup8: 344 Value.uval = Data.getU64(OffsetPtr); 345 break; 346 case DW_FORM_data16: 347 // Treat this like a 16-byte block. 348 Value.uval = 16; 349 IsBlock = true; 350 break; 351 case DW_FORM_sdata: 352 Value.sval = Data.getSLEB128(OffsetPtr); 353 break; 354 case DW_FORM_udata: 355 case DW_FORM_ref_udata: 356 Value.uval = Data.getULEB128(OffsetPtr); 357 break; 358 case DW_FORM_string: 359 Value.cstr = Data.getCStr(OffsetPtr); 360 break; 361 case DW_FORM_indirect: 362 Form = static_cast<dwarf::Form>(Data.getULEB128(OffsetPtr)); 363 Indirect = true; 364 break; 365 case DW_FORM_strp: 366 case DW_FORM_sec_offset: 367 case DW_FORM_GNU_ref_alt: 368 case DW_FORM_GNU_strp_alt: 369 case DW_FORM_line_strp: 370 case DW_FORM_strp_sup: { 371 Value.uval = 372 Data.getRelocatedValue(FP.getDwarfOffsetByteSize(), OffsetPtr); 373 break; 374 } 375 case DW_FORM_flag_present: 376 Value.uval = 1; 377 break; 378 case DW_FORM_ref_sig8: 379 Value.uval = Data.getU64(OffsetPtr); 380 break; 381 case DW_FORM_GNU_addr_index: 382 case DW_FORM_GNU_str_index: 383 case DW_FORM_strx: 384 Value.uval = Data.getULEB128(OffsetPtr); 385 break; 386 default: 387 // DWARFFormValue::skipValue() will have caught this and caused all 388 // DWARF DIEs to fail to be parsed, so this code is not be reachable. 389 llvm_unreachable("unsupported form"); 390 } 391 } while (Indirect); 392 393 if (IsBlock) { 394 StringRef Str = Data.getData().substr(*OffsetPtr, Value.uval); 395 Value.data = nullptr; 396 if (!Str.empty()) { 397 Value.data = reinterpret_cast<const uint8_t *>(Str.data()); 398 *OffsetPtr += Value.uval; 399 } 400 } 401 402 return true; 403 } 404 405 void DWARFFormValue::dump(raw_ostream &OS, DIDumpOptions DumpOpts) const { 406 uint64_t UValue = Value.uval; 407 bool CURelativeOffset = false; 408 raw_ostream &AddrOS = 409 DumpOpts.ShowAddresses ? WithColor(OS, syntax::Address).get() : nulls(); 410 switch (Form) { 411 case DW_FORM_addr: 412 AddrOS << format("0x%016" PRIx64, UValue); 413 break; 414 case DW_FORM_GNU_addr_index: { 415 AddrOS << format(" indexed (%8.8x) address = ", (uint32_t)UValue); 416 uint64_t Address; 417 if (U == nullptr) 418 OS << "<invalid dwarf unit>"; 419 else if (U->getAddrOffsetSectionItem(UValue, Address)) 420 AddrOS << format("0x%016" PRIx64, Address); 421 else 422 OS << "<no .debug_addr section>"; 423 break; 424 } 425 case DW_FORM_flag_present: 426 OS << "true"; 427 break; 428 case DW_FORM_flag: 429 case DW_FORM_data1: 430 OS << format("0x%02x", (uint8_t)UValue); 431 break; 432 case DW_FORM_data2: 433 OS << format("0x%04x", (uint16_t)UValue); 434 break; 435 case DW_FORM_data4: 436 OS << format("0x%08x", (uint32_t)UValue); 437 break; 438 case DW_FORM_ref_sig8: 439 AddrOS << format("0x%016" PRIx64, UValue); 440 break; 441 case DW_FORM_data8: 442 OS << format("0x%016" PRIx64, UValue); 443 break; 444 case DW_FORM_data16: 445 OS << format_bytes(ArrayRef<uint8_t>(Value.data, 16), None, 16, 16); 446 break; 447 case DW_FORM_string: 448 OS << '"'; 449 OS.write_escaped(Value.cstr); 450 OS << '"'; 451 break; 452 case DW_FORM_exprloc: 453 case DW_FORM_block: 454 case DW_FORM_block1: 455 case DW_FORM_block2: 456 case DW_FORM_block4: 457 if (UValue > 0) { 458 switch (Form) { 459 case DW_FORM_exprloc: 460 case DW_FORM_block: 461 OS << format("<0x%" PRIx64 "> ", UValue); 462 break; 463 case DW_FORM_block1: 464 OS << format("<0x%2.2x> ", (uint8_t)UValue); 465 break; 466 case DW_FORM_block2: 467 OS << format("<0x%4.4x> ", (uint16_t)UValue); 468 break; 469 case DW_FORM_block4: 470 OS << format("<0x%8.8x> ", (uint32_t)UValue); 471 break; 472 default: 473 break; 474 } 475 476 const uint8_t *DataPtr = Value.data; 477 if (DataPtr) { 478 // UValue contains size of block 479 const uint8_t *EndDataPtr = DataPtr + UValue; 480 while (DataPtr < EndDataPtr) { 481 OS << format("%2.2x ", *DataPtr); 482 ++DataPtr; 483 } 484 } else 485 OS << "NULL"; 486 } 487 break; 488 489 case DW_FORM_sdata: 490 OS << Value.sval; 491 break; 492 case DW_FORM_udata: 493 OS << Value.uval; 494 break; 495 case DW_FORM_strp: 496 if (DumpOpts.Verbose) 497 OS << format(" .debug_str[0x%8.8x] = ", (uint32_t)UValue); 498 dumpString(OS); 499 break; 500 case DW_FORM_strx: 501 case DW_FORM_strx1: 502 case DW_FORM_strx2: 503 case DW_FORM_strx3: 504 case DW_FORM_strx4: 505 case DW_FORM_GNU_str_index: 506 if (DumpOpts.Verbose) 507 OS << format(" indexed (%8.8x) string = ", (uint32_t)UValue); 508 dumpString(OS); 509 break; 510 case DW_FORM_GNU_strp_alt: 511 if (DumpOpts.Verbose) 512 OS << format("alt indirect string, offset: 0x%" PRIx64 "", UValue); 513 dumpString(OS); 514 break; 515 case DW_FORM_ref_addr: 516 AddrOS << format("0x%016" PRIx64, UValue); 517 break; 518 case DW_FORM_ref1: 519 CURelativeOffset = true; 520 AddrOS << format("cu + 0x%2.2x", (uint8_t)UValue); 521 break; 522 case DW_FORM_ref2: 523 CURelativeOffset = true; 524 AddrOS << format("cu + 0x%4.4x", (uint16_t)UValue); 525 break; 526 case DW_FORM_ref4: 527 CURelativeOffset = true; 528 AddrOS << format("cu + 0x%4.4x", (uint32_t)UValue); 529 break; 530 case DW_FORM_ref8: 531 CURelativeOffset = true; 532 AddrOS << format("cu + 0x%8.8" PRIx64, UValue); 533 break; 534 case DW_FORM_ref_udata: 535 CURelativeOffset = true; 536 AddrOS << format("cu + 0x%" PRIx64, UValue); 537 break; 538 case DW_FORM_GNU_ref_alt: 539 AddrOS << format("<alt 0x%" PRIx64 ">", UValue); 540 break; 541 542 // All DW_FORM_indirect attributes should be resolved prior to calling 543 // this function 544 case DW_FORM_indirect: 545 OS << "DW_FORM_indirect"; 546 break; 547 548 // Should be formatted to 64-bit for DWARF64. 549 case DW_FORM_sec_offset: 550 AddrOS << format("0x%08x", (uint32_t)UValue); 551 break; 552 553 default: 554 OS << format("DW_FORM(0x%4.4x)", Form); 555 break; 556 } 557 558 if (CURelativeOffset && DumpOpts.Verbose) { 559 OS << " => {"; 560 WithColor(OS, syntax::Address).get() 561 << format("0x%8.8" PRIx64, UValue + (U ? U->getOffset() : 0)); 562 OS << "}"; 563 } 564 } 565 566 void DWARFFormValue::dumpString(raw_ostream &OS) const { 567 Optional<const char *> DbgStr = getAsCString(); 568 if (DbgStr.hasValue()) { 569 raw_ostream &COS = WithColor(OS, syntax::String); 570 COS << '"'; 571 COS.write_escaped(DbgStr.getValue()); 572 COS << '"'; 573 } 574 } 575 576 Optional<const char *> DWARFFormValue::getAsCString() const { 577 if (!isFormClass(FC_String)) 578 return None; 579 if (Form == DW_FORM_string) 580 return Value.cstr; 581 // FIXME: Add support for DW_FORM_GNU_strp_alt 582 if (Form == DW_FORM_GNU_strp_alt || U == nullptr) 583 return None; 584 uint32_t Offset = Value.uval; 585 if (Form == DW_FORM_GNU_str_index || Form == DW_FORM_strx || 586 Form == DW_FORM_strx1 || Form == DW_FORM_strx2 || Form == DW_FORM_strx3 || 587 Form == DW_FORM_strx4) { 588 uint64_t StrOffset; 589 if (!U->getStringOffsetSectionItem(Offset, StrOffset)) 590 return None; 591 Offset = StrOffset; 592 } 593 if (const char *Str = U->getStringExtractor().getCStr(&Offset)) { 594 return Str; 595 } 596 return None; 597 } 598 599 Optional<uint64_t> DWARFFormValue::getAsAddress() const { 600 if (!isFormClass(FC_Address)) 601 return None; 602 if (Form == DW_FORM_GNU_addr_index) { 603 uint32_t Index = Value.uval; 604 uint64_t Result; 605 if (!U || !U->getAddrOffsetSectionItem(Index, Result)) 606 return None; 607 return Result; 608 } 609 return Value.uval; 610 } 611 612 Optional<uint64_t> DWARFFormValue::getAsReference() const { 613 if (!isFormClass(FC_Reference)) 614 return None; 615 switch (Form) { 616 case DW_FORM_ref1: 617 case DW_FORM_ref2: 618 case DW_FORM_ref4: 619 case DW_FORM_ref8: 620 case DW_FORM_ref_udata: 621 if (!U) 622 return None; 623 return Value.uval + U->getOffset(); 624 case DW_FORM_ref_addr: 625 case DW_FORM_ref_sig8: 626 case DW_FORM_GNU_ref_alt: 627 return Value.uval; 628 default: 629 return None; 630 } 631 } 632 633 Optional<uint64_t> DWARFFormValue::getAsSectionOffset() const { 634 if (!isFormClass(FC_SectionOffset)) 635 return None; 636 return Value.uval; 637 } 638 639 Optional<uint64_t> DWARFFormValue::getAsUnsignedConstant() const { 640 if ((!isFormClass(FC_Constant) && !isFormClass(FC_Flag)) || 641 Form == DW_FORM_sdata) 642 return None; 643 return Value.uval; 644 } 645 646 Optional<int64_t> DWARFFormValue::getAsSignedConstant() const { 647 if ((!isFormClass(FC_Constant) && !isFormClass(FC_Flag)) || 648 (Form == DW_FORM_udata && 649 uint64_t(std::numeric_limits<int64_t>::max()) < Value.uval)) 650 return None; 651 switch (Form) { 652 case DW_FORM_data4: 653 return int32_t(Value.uval); 654 case DW_FORM_data2: 655 return int16_t(Value.uval); 656 case DW_FORM_data1: 657 return int8_t(Value.uval); 658 case DW_FORM_sdata: 659 case DW_FORM_data8: 660 default: 661 return Value.sval; 662 } 663 } 664 665 Optional<ArrayRef<uint8_t>> DWARFFormValue::getAsBlock() const { 666 if (!isFormClass(FC_Block) && !isFormClass(FC_Exprloc) && 667 Form != DW_FORM_data16) 668 return None; 669 return makeArrayRef(Value.data, Value.uval); 670 } 671 672 Optional<uint64_t> DWARFFormValue::getAsCStringOffset() const { 673 if (!isFormClass(FC_String) && Form == DW_FORM_string) 674 return None; 675 return Value.uval; 676 } 677 678 Optional<uint64_t> DWARFFormValue::getAsReferenceUVal() const { 679 if (!isFormClass(FC_Reference)) 680 return None; 681 return Value.uval; 682 } 683