1 //===-- llvm-nm.cpp - Symbol table dumping utility for llvm ---------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This program is a utility that works like traditional Unix "nm", that is, it 10 // prints out the names of symbols in a bitcode or object file, along with some 11 // information about each symbol. 12 // 13 // This "nm" supports many of the features of GNU "nm", including its different 14 // output formats. 15 // 16 //===----------------------------------------------------------------------===// 17 18 #include "llvm/ADT/StringSwitch.h" 19 #include "llvm/BinaryFormat/COFF.h" 20 #include "llvm/Demangle/Demangle.h" 21 #include "llvm/IR/Function.h" 22 #include "llvm/IR/LLVMContext.h" 23 #include "llvm/Object/Archive.h" 24 #include "llvm/Object/COFF.h" 25 #include "llvm/Object/COFFImportFile.h" 26 #include "llvm/Object/ELFObjectFile.h" 27 #include "llvm/Object/IRObjectFile.h" 28 #include "llvm/Object/MachO.h" 29 #include "llvm/Object/MachOUniversal.h" 30 #include "llvm/Object/ObjectFile.h" 31 #include "llvm/Object/TapiFile.h" 32 #include "llvm/Object/TapiUniversal.h" 33 #include "llvm/Object/Wasm.h" 34 #include "llvm/Option/Arg.h" 35 #include "llvm/Option/ArgList.h" 36 #include "llvm/Option/Option.h" 37 #include "llvm/Support/CommandLine.h" 38 #include "llvm/Support/FileSystem.h" 39 #include "llvm/Support/Format.h" 40 #include "llvm/Support/InitLLVM.h" 41 #include "llvm/Support/MemoryBuffer.h" 42 #include "llvm/Support/Program.h" 43 #include "llvm/Support/Signals.h" 44 #include "llvm/Support/TargetSelect.h" 45 #include "llvm/Support/WithColor.h" 46 #include "llvm/Support/raw_ostream.h" 47 #include <vector> 48 49 using namespace llvm; 50 using namespace object; 51 52 namespace { 53 using namespace llvm::opt; // for HelpHidden in Opts.inc 54 enum ID { 55 OPT_INVALID = 0, // This is not an option ID. 56 #define OPTION(PREFIX, NAME, ID, KIND, GROUP, ALIAS, ALIASARGS, FLAGS, PARAM, \ 57 HELPTEXT, METAVAR, VALUES) \ 58 OPT_##ID, 59 #include "Opts.inc" 60 #undef OPTION 61 }; 62 63 #define PREFIX(NAME, VALUE) const char *const NAME[] = VALUE; 64 #include "Opts.inc" 65 #undef PREFIX 66 67 const opt::OptTable::Info InfoTable[] = { 68 #define OPTION(PREFIX, NAME, ID, KIND, GROUP, ALIAS, ALIASARGS, FLAGS, PARAM, \ 69 HELPTEXT, METAVAR, VALUES) \ 70 { \ 71 PREFIX, NAME, HELPTEXT, \ 72 METAVAR, OPT_##ID, opt::Option::KIND##Class, \ 73 PARAM, FLAGS, OPT_##GROUP, \ 74 OPT_##ALIAS, ALIASARGS, VALUES}, 75 #include "Opts.inc" 76 #undef OPTION 77 }; 78 79 class NmOptTable : public opt::OptTable { 80 public: 81 NmOptTable() : OptTable(InfoTable) { setGroupedShortOptions(true); } 82 }; 83 84 enum OutputFormatTy { bsd, sysv, posix, darwin, just_symbols }; 85 } // namespace 86 87 static bool ArchiveMap; 88 static bool DebugSyms; 89 static bool DefinedOnly; 90 static bool Demangle; 91 static bool DynamicSyms; 92 static bool ExternalOnly; 93 static OutputFormatTy OutputFormat; 94 static bool NoLLVMBitcode; 95 static bool NoSort; 96 static bool NoWeakSymbols; 97 static bool NumericSort; 98 static bool PrintFileName; 99 static bool PrintSize; 100 static bool Quiet; 101 static bool ReverseSort; 102 static bool SpecialSyms; 103 static bool SizeSort; 104 static bool UndefinedOnly; 105 static bool WithoutAliases; 106 107 namespace { 108 enum Radix { d, o, x }; 109 } // namespace 110 static Radix AddressRadix; 111 112 // Mach-O specific options. 113 static bool ArchAll = false; 114 static std::vector<StringRef> ArchFlags; 115 static bool AddDyldInfo; 116 static bool AddInlinedInfo; 117 static bool DyldInfoOnly; 118 static bool FormatMachOasHex; 119 static bool NoDyldInfo; 120 static std::vector<StringRef> SegSect; 121 static bool MachOPrintSizeWarning = false; 122 123 // Miscellaneous states. 124 static bool PrintAddress = true; 125 static bool MultipleFiles = false; 126 static bool HadError = false; 127 128 static StringRef ToolName; 129 130 static void error(Twine Message, Twine Path = Twine()) { 131 HadError = true; 132 WithColor::error(errs(), ToolName) << Path << ": " << Message << "\n"; 133 } 134 135 static bool error(std::error_code EC, Twine Path = Twine()) { 136 if (EC) { 137 error(EC.message(), Path); 138 return true; 139 } 140 return false; 141 } 142 143 // This version of error() prints the archive name and member name, for example: 144 // "libx.a(foo.o)" after the ToolName before the error message. It sets 145 // HadError but returns allowing the code to move on to other archive members. 146 static void error(llvm::Error E, StringRef FileName, const Archive::Child &C, 147 StringRef ArchitectureName = StringRef()) { 148 HadError = true; 149 WithColor::error(errs(), ToolName) << FileName; 150 151 Expected<StringRef> NameOrErr = C.getName(); 152 // TODO: if we have a error getting the name then it would be nice to print 153 // the index of which archive member this is and or its offset in the 154 // archive instead of "???" as the name. 155 if (!NameOrErr) { 156 consumeError(NameOrErr.takeError()); 157 errs() << "(" << "???" << ")"; 158 } else 159 errs() << "(" << NameOrErr.get() << ")"; 160 161 if (!ArchitectureName.empty()) 162 errs() << " (for architecture " << ArchitectureName << ")"; 163 164 std::string Buf; 165 raw_string_ostream OS(Buf); 166 logAllUnhandledErrors(std::move(E), OS); 167 OS.flush(); 168 errs() << ": " << Buf << "\n"; 169 } 170 171 // This version of error() prints the file name and which architecture slice it 172 // is from, for example: "foo.o (for architecture i386)" after the ToolName 173 // before the error message. It sets HadError but returns allowing the code to 174 // move on to other architecture slices. 175 static void error(llvm::Error E, StringRef FileName, 176 StringRef ArchitectureName = StringRef()) { 177 HadError = true; 178 WithColor::error(errs(), ToolName) << FileName; 179 180 if (!ArchitectureName.empty()) 181 errs() << " (for architecture " << ArchitectureName << ")"; 182 183 std::string Buf; 184 raw_string_ostream OS(Buf); 185 logAllUnhandledErrors(std::move(E), OS); 186 OS.flush(); 187 errs() << ": " << Buf << "\n"; 188 } 189 190 namespace { 191 struct NMSymbol { 192 uint64_t Address; 193 uint64_t Size; 194 char TypeChar; 195 std::string Name; 196 StringRef SectionName; 197 StringRef TypeName; 198 BasicSymbolRef Sym; 199 // The Sym field above points to the native symbol in the object file, 200 // for Mach-O when we are creating symbols from the dyld info the above 201 // pointer is null as there is no native symbol. In these cases the fields 202 // below are filled in to represent what would have been a Mach-O nlist 203 // native symbol. 204 uint32_t SymFlags; 205 SectionRef Section; 206 uint8_t NType; 207 uint8_t NSect; 208 uint16_t NDesc; 209 std::string IndirectName; 210 }; 211 } // anonymous namespace 212 213 static bool compareSymbolAddress(const NMSymbol &A, const NMSymbol &B) { 214 bool ADefined; 215 // Symbol flags have been checked in the caller. 216 if (A.Sym.getRawDataRefImpl().p) { 217 uint32_t AFlags = cantFail(A.Sym.getFlags()); 218 ADefined = !(AFlags & SymbolRef::SF_Undefined); 219 } else { 220 ADefined = A.TypeChar != 'U'; 221 } 222 bool BDefined; 223 // Symbol flags have been checked in the caller. 224 if (B.Sym.getRawDataRefImpl().p) { 225 uint32_t BFlags = cantFail(B.Sym.getFlags()); 226 BDefined = !(BFlags & SymbolRef::SF_Undefined); 227 } else { 228 BDefined = B.TypeChar != 'U'; 229 } 230 return std::make_tuple(ADefined, A.Address, A.Name, A.Size) < 231 std::make_tuple(BDefined, B.Address, B.Name, B.Size); 232 } 233 234 static bool compareSymbolSize(const NMSymbol &A, const NMSymbol &B) { 235 return std::make_tuple(A.Size, A.Name, A.Address) < 236 std::make_tuple(B.Size, B.Name, B.Address); 237 } 238 239 static bool compareSymbolName(const NMSymbol &A, const NMSymbol &B) { 240 return std::make_tuple(A.Name, A.Size, A.Address) < 241 std::make_tuple(B.Name, B.Size, B.Address); 242 } 243 244 static char isSymbolList64Bit(SymbolicFile &Obj) { 245 if (auto *IRObj = dyn_cast<IRObjectFile>(&Obj)) 246 return Triple(IRObj->getTargetTriple()).isArch64Bit(); 247 if (isa<COFFObjectFile>(Obj) || isa<COFFImportFile>(Obj)) 248 return false; 249 if (isa<WasmObjectFile>(Obj)) 250 return false; 251 if (TapiFile *Tapi = dyn_cast<TapiFile>(&Obj)) 252 return Tapi->is64Bit(); 253 if (MachOObjectFile *MachO = dyn_cast<MachOObjectFile>(&Obj)) 254 return MachO->is64Bit(); 255 return cast<ELFObjectFileBase>(Obj).getBytesInAddress() == 8; 256 } 257 258 static StringRef CurrentFilename; 259 static std::vector<NMSymbol> SymbolList; 260 261 static char getSymbolNMTypeChar(IRObjectFile &Obj, basic_symbol_iterator I); 262 263 // darwinPrintSymbol() is used to print a symbol from a Mach-O file when the 264 // the OutputFormat is darwin or we are printing Mach-O symbols in hex. For 265 // the darwin format it produces the same output as darwin's nm(1) -m output 266 // and when printing Mach-O symbols in hex it produces the same output as 267 // darwin's nm(1) -x format. 268 static void darwinPrintSymbol(SymbolicFile &Obj, const NMSymbol &S, 269 char *SymbolAddrStr, const char *printBlanks, 270 const char *printDashes, 271 const char *printFormat) { 272 MachO::mach_header H; 273 MachO::mach_header_64 H_64; 274 uint32_t Filetype = MachO::MH_OBJECT; 275 uint32_t Flags = 0; 276 uint8_t NType = 0; 277 uint8_t NSect = 0; 278 uint16_t NDesc = 0; 279 uint32_t NStrx = 0; 280 uint64_t NValue = 0; 281 MachOObjectFile *MachO = dyn_cast<MachOObjectFile>(&Obj); 282 if (Obj.isIR()) { 283 uint32_t SymFlags = cantFail(S.Sym.getFlags()); 284 if (SymFlags & SymbolRef::SF_Global) 285 NType |= MachO::N_EXT; 286 if (SymFlags & SymbolRef::SF_Hidden) 287 NType |= MachO::N_PEXT; 288 if (SymFlags & SymbolRef::SF_Undefined) 289 NType |= MachO::N_EXT | MachO::N_UNDF; 290 else { 291 // Here we have a symbol definition. So to fake out a section name we 292 // use 1, 2 and 3 for section numbers. See below where they are used to 293 // print out fake section names. 294 NType |= MachO::N_SECT; 295 if (SymFlags & SymbolRef::SF_Const) 296 NSect = 3; 297 else if (SymFlags & SymbolRef::SF_Executable) 298 NSect = 1; 299 else 300 NSect = 2; 301 } 302 if (SymFlags & SymbolRef::SF_Weak) 303 NDesc |= MachO::N_WEAK_DEF; 304 } else { 305 DataRefImpl SymDRI = S.Sym.getRawDataRefImpl(); 306 if (MachO->is64Bit()) { 307 H_64 = MachO->MachOObjectFile::getHeader64(); 308 Filetype = H_64.filetype; 309 Flags = H_64.flags; 310 if (SymDRI.p){ 311 MachO::nlist_64 STE_64 = MachO->getSymbol64TableEntry(SymDRI); 312 NType = STE_64.n_type; 313 NSect = STE_64.n_sect; 314 NDesc = STE_64.n_desc; 315 NStrx = STE_64.n_strx; 316 NValue = STE_64.n_value; 317 } else { 318 NType = S.NType; 319 NSect = S.NSect; 320 NDesc = S.NDesc; 321 NStrx = 0; 322 NValue = S.Address; 323 } 324 } else { 325 H = MachO->MachOObjectFile::getHeader(); 326 Filetype = H.filetype; 327 Flags = H.flags; 328 if (SymDRI.p){ 329 MachO::nlist STE = MachO->getSymbolTableEntry(SymDRI); 330 NType = STE.n_type; 331 NSect = STE.n_sect; 332 NDesc = STE.n_desc; 333 NStrx = STE.n_strx; 334 NValue = STE.n_value; 335 } else { 336 NType = S.NType; 337 NSect = S.NSect; 338 NDesc = S.NDesc; 339 NStrx = 0; 340 NValue = S.Address; 341 } 342 } 343 } 344 345 // If we are printing Mach-O symbols in hex do that and return. 346 if (FormatMachOasHex) { 347 outs() << format(printFormat, NValue) << ' ' 348 << format("%02x %02x %04x %08x", NType, NSect, NDesc, NStrx) << ' ' 349 << S.Name; 350 if ((NType & MachO::N_TYPE) == MachO::N_INDR) { 351 outs() << " (indirect for "; 352 outs() << format(printFormat, NValue) << ' '; 353 StringRef IndirectName; 354 if (S.Sym.getRawDataRefImpl().p) { 355 if (MachO->getIndirectName(S.Sym.getRawDataRefImpl(), IndirectName)) 356 outs() << "?)"; 357 else 358 outs() << IndirectName << ")"; 359 } else 360 outs() << S.IndirectName << ")"; 361 } 362 outs() << "\n"; 363 return; 364 } 365 366 if (PrintAddress) { 367 if ((NType & MachO::N_TYPE) == MachO::N_INDR) 368 strcpy(SymbolAddrStr, printBlanks); 369 if (Obj.isIR() && (NType & MachO::N_TYPE) == MachO::N_TYPE) 370 strcpy(SymbolAddrStr, printDashes); 371 outs() << SymbolAddrStr << ' '; 372 } 373 374 switch (NType & MachO::N_TYPE) { 375 case MachO::N_UNDF: 376 if (NValue != 0) { 377 outs() << "(common) "; 378 if (MachO::GET_COMM_ALIGN(NDesc) != 0) 379 outs() << "(alignment 2^" << (int)MachO::GET_COMM_ALIGN(NDesc) << ") "; 380 } else { 381 if ((NType & MachO::N_TYPE) == MachO::N_PBUD) 382 outs() << "(prebound "; 383 else 384 outs() << "("; 385 if ((NDesc & MachO::REFERENCE_TYPE) == 386 MachO::REFERENCE_FLAG_UNDEFINED_LAZY) 387 outs() << "undefined [lazy bound]) "; 388 else if ((NDesc & MachO::REFERENCE_TYPE) == 389 MachO::REFERENCE_FLAG_PRIVATE_UNDEFINED_LAZY) 390 outs() << "undefined [private lazy bound]) "; 391 else if ((NDesc & MachO::REFERENCE_TYPE) == 392 MachO::REFERENCE_FLAG_PRIVATE_UNDEFINED_NON_LAZY) 393 outs() << "undefined [private]) "; 394 else 395 outs() << "undefined) "; 396 } 397 break; 398 case MachO::N_ABS: 399 outs() << "(absolute) "; 400 break; 401 case MachO::N_INDR: 402 outs() << "(indirect) "; 403 break; 404 case MachO::N_SECT: { 405 if (Obj.isIR()) { 406 // For llvm bitcode files print out a fake section name using the values 407 // use 1, 2 and 3 for section numbers as set above. 408 if (NSect == 1) 409 outs() << "(LTO,CODE) "; 410 else if (NSect == 2) 411 outs() << "(LTO,DATA) "; 412 else if (NSect == 3) 413 outs() << "(LTO,RODATA) "; 414 else 415 outs() << "(?,?) "; 416 break; 417 } 418 section_iterator Sec = SectionRef(); 419 if (S.Sym.getRawDataRefImpl().p) { 420 Expected<section_iterator> SecOrErr = 421 MachO->getSymbolSection(S.Sym.getRawDataRefImpl()); 422 if (!SecOrErr) { 423 consumeError(SecOrErr.takeError()); 424 outs() << "(?,?) "; 425 break; 426 } 427 Sec = *SecOrErr; 428 if (Sec == MachO->section_end()) { 429 outs() << "(?,?) "; 430 break; 431 } 432 } else { 433 Sec = S.Section; 434 } 435 DataRefImpl Ref = Sec->getRawDataRefImpl(); 436 StringRef SectionName; 437 if (Expected<StringRef> NameOrErr = MachO->getSectionName(Ref)) 438 SectionName = *NameOrErr; 439 StringRef SegmentName = MachO->getSectionFinalSegmentName(Ref); 440 outs() << "(" << SegmentName << "," << SectionName << ") "; 441 break; 442 } 443 default: 444 outs() << "(?) "; 445 break; 446 } 447 448 if (NType & MachO::N_EXT) { 449 if (NDesc & MachO::REFERENCED_DYNAMICALLY) 450 outs() << "[referenced dynamically] "; 451 if (NType & MachO::N_PEXT) { 452 if ((NDesc & MachO::N_WEAK_DEF) == MachO::N_WEAK_DEF) 453 outs() << "weak private external "; 454 else 455 outs() << "private external "; 456 } else { 457 if ((NDesc & MachO::N_WEAK_REF) == MachO::N_WEAK_REF || 458 (NDesc & MachO::N_WEAK_DEF) == MachO::N_WEAK_DEF) { 459 if ((NDesc & (MachO::N_WEAK_REF | MachO::N_WEAK_DEF)) == 460 (MachO::N_WEAK_REF | MachO::N_WEAK_DEF)) 461 outs() << "weak external automatically hidden "; 462 else 463 outs() << "weak external "; 464 } else 465 outs() << "external "; 466 } 467 } else { 468 if (NType & MachO::N_PEXT) 469 outs() << "non-external (was a private external) "; 470 else 471 outs() << "non-external "; 472 } 473 474 if (Filetype == MachO::MH_OBJECT) { 475 if (NDesc & MachO::N_NO_DEAD_STRIP) 476 outs() << "[no dead strip] "; 477 if ((NType & MachO::N_TYPE) != MachO::N_UNDF && 478 NDesc & MachO::N_SYMBOL_RESOLVER) 479 outs() << "[symbol resolver] "; 480 if ((NType & MachO::N_TYPE) != MachO::N_UNDF && NDesc & MachO::N_ALT_ENTRY) 481 outs() << "[alt entry] "; 482 if ((NType & MachO::N_TYPE) != MachO::N_UNDF && NDesc & MachO::N_COLD_FUNC) 483 outs() << "[cold func] "; 484 } 485 486 if ((NDesc & MachO::N_ARM_THUMB_DEF) == MachO::N_ARM_THUMB_DEF) 487 outs() << "[Thumb] "; 488 489 if ((NType & MachO::N_TYPE) == MachO::N_INDR) { 490 outs() << S.Name << " (for "; 491 StringRef IndirectName; 492 if (MachO) { 493 if (S.Sym.getRawDataRefImpl().p) { 494 if (MachO->getIndirectName(S.Sym.getRawDataRefImpl(), IndirectName)) 495 outs() << "?)"; 496 else 497 outs() << IndirectName << ")"; 498 } else 499 outs() << S.IndirectName << ")"; 500 } else 501 outs() << "?)"; 502 } else 503 outs() << S.Name; 504 505 if ((Flags & MachO::MH_TWOLEVEL) == MachO::MH_TWOLEVEL && 506 (((NType & MachO::N_TYPE) == MachO::N_UNDF && NValue == 0) || 507 (NType & MachO::N_TYPE) == MachO::N_PBUD)) { 508 uint32_t LibraryOrdinal = MachO::GET_LIBRARY_ORDINAL(NDesc); 509 if (LibraryOrdinal != 0) { 510 if (LibraryOrdinal == MachO::EXECUTABLE_ORDINAL) 511 outs() << " (from executable)"; 512 else if (LibraryOrdinal == MachO::DYNAMIC_LOOKUP_ORDINAL) 513 outs() << " (dynamically looked up)"; 514 else { 515 StringRef LibraryName; 516 if (!MachO || 517 MachO->getLibraryShortNameByIndex(LibraryOrdinal - 1, LibraryName)) 518 outs() << " (from bad library ordinal " << LibraryOrdinal << ")"; 519 else 520 outs() << " (from " << LibraryName << ")"; 521 } 522 } 523 } 524 525 outs() << "\n"; 526 } 527 528 // Table that maps Darwin's Mach-O stab constants to strings to allow printing. 529 struct DarwinStabName { 530 uint8_t NType; 531 const char *Name; 532 }; 533 const struct DarwinStabName DarwinStabNames[] = { 534 {MachO::N_GSYM, "GSYM"}, 535 {MachO::N_FNAME, "FNAME"}, 536 {MachO::N_FUN, "FUN"}, 537 {MachO::N_STSYM, "STSYM"}, 538 {MachO::N_LCSYM, "LCSYM"}, 539 {MachO::N_BNSYM, "BNSYM"}, 540 {MachO::N_PC, "PC"}, 541 {MachO::N_AST, "AST"}, 542 {MachO::N_OPT, "OPT"}, 543 {MachO::N_RSYM, "RSYM"}, 544 {MachO::N_SLINE, "SLINE"}, 545 {MachO::N_ENSYM, "ENSYM"}, 546 {MachO::N_SSYM, "SSYM"}, 547 {MachO::N_SO, "SO"}, 548 {MachO::N_OSO, "OSO"}, 549 {MachO::N_LSYM, "LSYM"}, 550 {MachO::N_BINCL, "BINCL"}, 551 {MachO::N_SOL, "SOL"}, 552 {MachO::N_PARAMS, "PARAM"}, 553 {MachO::N_VERSION, "VERS"}, 554 {MachO::N_OLEVEL, "OLEV"}, 555 {MachO::N_PSYM, "PSYM"}, 556 {MachO::N_EINCL, "EINCL"}, 557 {MachO::N_ENTRY, "ENTRY"}, 558 {MachO::N_LBRAC, "LBRAC"}, 559 {MachO::N_EXCL, "EXCL"}, 560 {MachO::N_RBRAC, "RBRAC"}, 561 {MachO::N_BCOMM, "BCOMM"}, 562 {MachO::N_ECOMM, "ECOMM"}, 563 {MachO::N_ECOML, "ECOML"}, 564 {MachO::N_LENG, "LENG"}, 565 }; 566 567 static const char *getDarwinStabString(uint8_t NType) { 568 for (auto I : makeArrayRef(DarwinStabNames)) 569 if (I.NType == NType) 570 return I.Name; 571 return nullptr; 572 } 573 574 // darwinPrintStab() prints the n_sect, n_desc along with a symbolic name of 575 // a stab n_type value in a Mach-O file. 576 static void darwinPrintStab(MachOObjectFile *MachO, const NMSymbol &S) { 577 MachO::nlist_64 STE_64; 578 MachO::nlist STE; 579 uint8_t NType; 580 uint8_t NSect; 581 uint16_t NDesc; 582 DataRefImpl SymDRI = S.Sym.getRawDataRefImpl(); 583 if (MachO->is64Bit()) { 584 STE_64 = MachO->getSymbol64TableEntry(SymDRI); 585 NType = STE_64.n_type; 586 NSect = STE_64.n_sect; 587 NDesc = STE_64.n_desc; 588 } else { 589 STE = MachO->getSymbolTableEntry(SymDRI); 590 NType = STE.n_type; 591 NSect = STE.n_sect; 592 NDesc = STE.n_desc; 593 } 594 595 outs() << format(" %02x %04x ", NSect, NDesc); 596 if (const char *stabString = getDarwinStabString(NType)) 597 outs() << format("%5.5s", stabString); 598 else 599 outs() << format(" %02x", NType); 600 } 601 602 static Optional<std::string> demangle(const std::string &Name, 603 bool StripUnderscore) { 604 const char *Mangled = Name.c_str(); 605 if (StripUnderscore && Mangled[0] == '_') 606 Mangled = Mangled + 1; 607 608 std::string Demangled; 609 if (nonMicrosoftDemangle(Mangled, Demangled)) 610 return Demangled; 611 return None; 612 } 613 614 static bool symbolIsDefined(const NMSymbol &Sym) { 615 return Sym.TypeChar != 'U' && Sym.TypeChar != 'w' && Sym.TypeChar != 'v'; 616 } 617 618 static void writeFileName(raw_ostream &S, StringRef ArchiveName, 619 StringRef ArchitectureName) { 620 if (!ArchitectureName.empty()) 621 S << "(for architecture " << ArchitectureName << "):"; 622 if (OutputFormat == posix && !ArchiveName.empty()) 623 S << ArchiveName << "[" << CurrentFilename << "]: "; 624 else { 625 if (!ArchiveName.empty()) 626 S << ArchiveName << ":"; 627 S << CurrentFilename << ": "; 628 } 629 } 630 631 static void sortAndPrintSymbolList(SymbolicFile &Obj, bool printName, 632 StringRef ArchiveName, 633 StringRef ArchitectureName) { 634 if (!NoSort) { 635 using Comparator = bool (*)(const NMSymbol &, const NMSymbol &); 636 Comparator Cmp; 637 if (NumericSort) 638 Cmp = &compareSymbolAddress; 639 else if (SizeSort) 640 Cmp = &compareSymbolSize; 641 else 642 Cmp = &compareSymbolName; 643 644 if (ReverseSort) 645 llvm::sort(SymbolList, [=](const NMSymbol &A, const NMSymbol &B) -> bool { 646 return Cmp(B, A); 647 }); 648 else 649 llvm::sort(SymbolList, Cmp); 650 } 651 652 if (!PrintFileName) { 653 if ((OutputFormat == bsd || OutputFormat == posix || 654 OutputFormat == just_symbols) && 655 MultipleFiles && printName) { 656 outs() << '\n' << CurrentFilename << ":\n"; 657 } else if (OutputFormat == sysv) { 658 outs() << "\n\nSymbols from " << CurrentFilename << ":\n\n"; 659 if (isSymbolList64Bit(Obj)) 660 outs() << "Name Value Class Type" 661 << " Size Line Section\n"; 662 else 663 outs() << "Name Value Class Type" 664 << " Size Line Section\n"; 665 } 666 } 667 668 const char *printBlanks, *printDashes, *printFormat; 669 if (isSymbolList64Bit(Obj)) { 670 printBlanks = " "; 671 printDashes = "----------------"; 672 switch (AddressRadix) { 673 case Radix::o: 674 printFormat = OutputFormat == posix ? "%" PRIo64 : "%016" PRIo64; 675 break; 676 case Radix::x: 677 printFormat = OutputFormat == posix ? "%" PRIx64 : "%016" PRIx64; 678 break; 679 default: 680 printFormat = OutputFormat == posix ? "%" PRId64 : "%016" PRId64; 681 } 682 } else { 683 printBlanks = " "; 684 printDashes = "--------"; 685 switch (AddressRadix) { 686 case Radix::o: 687 printFormat = OutputFormat == posix ? "%" PRIo64 : "%08" PRIo64; 688 break; 689 case Radix::x: 690 printFormat = OutputFormat == posix ? "%" PRIx64 : "%08" PRIx64; 691 break; 692 default: 693 printFormat = OutputFormat == posix ? "%" PRId64 : "%08" PRId64; 694 } 695 } 696 697 for (const NMSymbol &S : SymbolList) { 698 uint32_t SymFlags; 699 std::string Name = S.Name; 700 MachOObjectFile *MachO = dyn_cast<MachOObjectFile>(&Obj); 701 if (Demangle) { 702 if (Optional<std::string> Opt = demangle(S.Name, MachO)) 703 Name = *Opt; 704 } 705 if (S.Sym.getRawDataRefImpl().p) { 706 Expected<uint32_t> SymFlagsOrErr = S.Sym.getFlags(); 707 if (!SymFlagsOrErr) { 708 // TODO: Test this error. 709 error(SymFlagsOrErr.takeError(), Obj.getFileName()); 710 return; 711 } 712 SymFlags = *SymFlagsOrErr; 713 } else 714 SymFlags = S.SymFlags; 715 716 bool Undefined = SymFlags & SymbolRef::SF_Undefined; 717 bool Global = SymFlags & SymbolRef::SF_Global; 718 bool Weak = SymFlags & SymbolRef::SF_Weak; 719 bool FormatSpecific = SymFlags & SymbolRef::SF_FormatSpecific; 720 if ((!Undefined && UndefinedOnly) || (Undefined && DefinedOnly) || 721 (!Global && ExternalOnly) || (Weak && NoWeakSymbols) || 722 (FormatSpecific && !(SpecialSyms || DebugSyms))) 723 continue; 724 if (PrintFileName) 725 writeFileName(outs(), ArchiveName, ArchitectureName); 726 if ((OutputFormat == just_symbols || 727 (UndefinedOnly && MachO && OutputFormat != darwin)) && 728 OutputFormat != posix) { 729 outs() << Name << "\n"; 730 continue; 731 } 732 733 char SymbolAddrStr[23], SymbolSizeStr[23]; 734 735 // If the format is SysV or the symbol isn't defined, then print spaces. 736 if (OutputFormat == sysv || !symbolIsDefined(S)) { 737 if (OutputFormat == posix) { 738 format(printFormat, S.Address) 739 .print(SymbolAddrStr, sizeof(SymbolAddrStr)); 740 format(printFormat, S.Size).print(SymbolSizeStr, sizeof(SymbolSizeStr)); 741 } else { 742 strcpy(SymbolAddrStr, printBlanks); 743 strcpy(SymbolSizeStr, printBlanks); 744 } 745 } 746 747 if (symbolIsDefined(S)) { 748 // Otherwise, print the symbol address and size. 749 if (Obj.isIR()) 750 strcpy(SymbolAddrStr, printDashes); 751 else if (MachO && S.TypeChar == 'I') 752 strcpy(SymbolAddrStr, printBlanks); 753 else 754 format(printFormat, S.Address) 755 .print(SymbolAddrStr, sizeof(SymbolAddrStr)); 756 format(printFormat, S.Size).print(SymbolSizeStr, sizeof(SymbolSizeStr)); 757 } 758 759 // If OutputFormat is darwin or we are printing Mach-O symbols in hex and 760 // we have a MachOObjectFile, call darwinPrintSymbol to print as darwin's 761 // nm(1) -m output or hex, else if OutputFormat is darwin or we are 762 // printing Mach-O symbols in hex and not a Mach-O object fall back to 763 // OutputFormat bsd (see below). 764 if ((OutputFormat == darwin || FormatMachOasHex) && (MachO || Obj.isIR())) { 765 darwinPrintSymbol(Obj, S, SymbolAddrStr, printBlanks, printDashes, 766 printFormat); 767 } else if (OutputFormat == posix) { 768 outs() << Name << " " << S.TypeChar << " " << SymbolAddrStr << " " 769 << (MachO ? "0" : SymbolSizeStr) << "\n"; 770 } else if (OutputFormat == bsd || (OutputFormat == darwin && !MachO)) { 771 if (PrintAddress) 772 outs() << SymbolAddrStr << ' '; 773 if (PrintSize) 774 outs() << SymbolSizeStr << ' '; 775 outs() << S.TypeChar; 776 if (S.TypeChar == '-' && MachO) 777 darwinPrintStab(MachO, S); 778 outs() << " " << Name; 779 if (S.TypeChar == 'I' && MachO) { 780 outs() << " (indirect for "; 781 if (S.Sym.getRawDataRefImpl().p) { 782 StringRef IndirectName; 783 if (MachO->getIndirectName(S.Sym.getRawDataRefImpl(), IndirectName)) 784 outs() << "?)"; 785 else 786 outs() << IndirectName << ")"; 787 } else 788 outs() << S.IndirectName << ")"; 789 } 790 outs() << "\n"; 791 } else if (OutputFormat == sysv) { 792 outs() << left_justify(Name, 20) << "|" << SymbolAddrStr << "| " 793 << S.TypeChar << " |" << right_justify(S.TypeName, 18) << "|" 794 << SymbolSizeStr << "| |" << S.SectionName << "\n"; 795 } 796 } 797 798 SymbolList.clear(); 799 } 800 801 static char getSymbolNMTypeChar(ELFObjectFileBase &Obj, 802 basic_symbol_iterator I) { 803 // OK, this is ELF 804 elf_symbol_iterator SymI(I); 805 806 Expected<elf_section_iterator> SecIOrErr = SymI->getSection(); 807 if (!SecIOrErr) { 808 consumeError(SecIOrErr.takeError()); 809 return '?'; 810 } 811 812 uint8_t Binding = SymI->getBinding(); 813 if (Binding == ELF::STB_GNU_UNIQUE) 814 return 'u'; 815 816 assert(Binding != ELF::STB_WEAK && "STB_WEAK not tested in calling function"); 817 if (Binding != ELF::STB_GLOBAL && Binding != ELF::STB_LOCAL) 818 return '?'; 819 820 elf_section_iterator SecI = *SecIOrErr; 821 if (SecI != Obj.section_end()) { 822 uint32_t Type = SecI->getType(); 823 uint64_t Flags = SecI->getFlags(); 824 if (Flags & ELF::SHF_EXECINSTR) 825 return 't'; 826 if (Type == ELF::SHT_NOBITS) 827 return 'b'; 828 if (Flags & ELF::SHF_ALLOC) 829 return Flags & ELF::SHF_WRITE ? 'd' : 'r'; 830 831 auto NameOrErr = SecI->getName(); 832 if (!NameOrErr) { 833 consumeError(NameOrErr.takeError()); 834 return '?'; 835 } 836 if ((*NameOrErr).startswith(".debug")) 837 return 'N'; 838 if (!(Flags & ELF::SHF_WRITE)) 839 return 'n'; 840 } 841 842 return '?'; 843 } 844 845 static char getSymbolNMTypeChar(COFFObjectFile &Obj, symbol_iterator I) { 846 COFFSymbolRef Symb = Obj.getCOFFSymbol(*I); 847 // OK, this is COFF. 848 symbol_iterator SymI(I); 849 850 Expected<StringRef> Name = SymI->getName(); 851 if (!Name) { 852 consumeError(Name.takeError()); 853 return '?'; 854 } 855 856 char Ret = StringSwitch<char>(*Name) 857 .StartsWith(".debug", 'N') 858 .StartsWith(".sxdata", 'N') 859 .Default('?'); 860 861 if (Ret != '?') 862 return Ret; 863 864 uint32_t Characteristics = 0; 865 if (!COFF::isReservedSectionNumber(Symb.getSectionNumber())) { 866 Expected<section_iterator> SecIOrErr = SymI->getSection(); 867 if (!SecIOrErr) { 868 consumeError(SecIOrErr.takeError()); 869 return '?'; 870 } 871 section_iterator SecI = *SecIOrErr; 872 const coff_section *Section = Obj.getCOFFSection(*SecI); 873 Characteristics = Section->Characteristics; 874 if (Expected<StringRef> NameOrErr = Obj.getSectionName(Section)) 875 if (NameOrErr->startswith(".idata")) 876 return 'i'; 877 } 878 879 switch (Symb.getSectionNumber()) { 880 case COFF::IMAGE_SYM_DEBUG: 881 return 'n'; 882 default: 883 // Check section type. 884 if (Characteristics & COFF::IMAGE_SCN_CNT_CODE) 885 return 't'; 886 if (Characteristics & COFF::IMAGE_SCN_CNT_INITIALIZED_DATA) 887 return Characteristics & COFF::IMAGE_SCN_MEM_WRITE ? 'd' : 'r'; 888 if (Characteristics & COFF::IMAGE_SCN_CNT_UNINITIALIZED_DATA) 889 return 'b'; 890 if (Characteristics & COFF::IMAGE_SCN_LNK_INFO) 891 return 'i'; 892 // Check for section symbol. 893 if (Symb.isSectionDefinition()) 894 return 's'; 895 } 896 897 return '?'; 898 } 899 900 static char getSymbolNMTypeChar(COFFImportFile &Obj) { 901 switch (Obj.getCOFFImportHeader()->getType()) { 902 case COFF::IMPORT_CODE: 903 return 't'; 904 case COFF::IMPORT_DATA: 905 return 'd'; 906 case COFF::IMPORT_CONST: 907 return 'r'; 908 } 909 return '?'; 910 } 911 912 static char getSymbolNMTypeChar(MachOObjectFile &Obj, basic_symbol_iterator I) { 913 DataRefImpl Symb = I->getRawDataRefImpl(); 914 uint8_t NType = Obj.is64Bit() ? Obj.getSymbol64TableEntry(Symb).n_type 915 : Obj.getSymbolTableEntry(Symb).n_type; 916 917 if (NType & MachO::N_STAB) 918 return '-'; 919 920 switch (NType & MachO::N_TYPE) { 921 case MachO::N_ABS: 922 return 's'; 923 case MachO::N_INDR: 924 return 'i'; 925 case MachO::N_SECT: { 926 Expected<section_iterator> SecOrErr = Obj.getSymbolSection(Symb); 927 if (!SecOrErr) { 928 consumeError(SecOrErr.takeError()); 929 return 's'; 930 } 931 section_iterator Sec = *SecOrErr; 932 if (Sec == Obj.section_end()) 933 return 's'; 934 DataRefImpl Ref = Sec->getRawDataRefImpl(); 935 StringRef SectionName; 936 if (Expected<StringRef> NameOrErr = Obj.getSectionName(Ref)) 937 SectionName = *NameOrErr; 938 StringRef SegmentName = Obj.getSectionFinalSegmentName(Ref); 939 if (Obj.is64Bit() && Obj.getHeader64().filetype == MachO::MH_KEXT_BUNDLE && 940 SegmentName == "__TEXT_EXEC" && SectionName == "__text") 941 return 't'; 942 if (SegmentName == "__TEXT" && SectionName == "__text") 943 return 't'; 944 if (SegmentName == "__DATA" && SectionName == "__data") 945 return 'd'; 946 if (SegmentName == "__DATA" && SectionName == "__bss") 947 return 'b'; 948 return 's'; 949 } 950 } 951 952 return '?'; 953 } 954 955 static char getSymbolNMTypeChar(TapiFile &Obj, basic_symbol_iterator I) { 956 return 's'; 957 } 958 959 static char getSymbolNMTypeChar(WasmObjectFile &Obj, basic_symbol_iterator I) { 960 uint32_t Flags = cantFail(I->getFlags()); 961 if (Flags & SymbolRef::SF_Executable) 962 return 't'; 963 return 'd'; 964 } 965 966 static char getSymbolNMTypeChar(IRObjectFile &Obj, basic_symbol_iterator I) { 967 uint32_t Flags = cantFail(I->getFlags()); 968 // FIXME: should we print 'b'? At the IR level we cannot be sure if this 969 // will be in bss or not, but we could approximate. 970 if (Flags & SymbolRef::SF_Executable) 971 return 't'; 972 else if (Triple(Obj.getTargetTriple()).isOSDarwin() && 973 (Flags & SymbolRef::SF_Const)) 974 return 's'; 975 else 976 return 'd'; 977 } 978 979 static bool isObject(SymbolicFile &Obj, basic_symbol_iterator I) { 980 return isa<ELFObjectFileBase>(&Obj) && 981 elf_symbol_iterator(I)->getELFType() == ELF::STT_OBJECT; 982 } 983 984 // For ELF object files, Set TypeName to the symbol typename, to be printed 985 // in the 'Type' column of the SYSV format output. 986 static StringRef getNMTypeName(SymbolicFile &Obj, basic_symbol_iterator I) { 987 if (isa<ELFObjectFileBase>(&Obj)) { 988 elf_symbol_iterator SymI(I); 989 return SymI->getELFTypeName(); 990 } 991 return ""; 992 } 993 994 // Return Posix nm class type tag (single letter), but also set SecName and 995 // section and name, to be used in format=sysv output. 996 static char getNMSectionTagAndName(SymbolicFile &Obj, basic_symbol_iterator I, 997 StringRef &SecName) { 998 // Symbol Flags have been checked in the caller. 999 uint32_t Symflags = cantFail(I->getFlags()); 1000 if (ELFObjectFileBase *ELFObj = dyn_cast<ELFObjectFileBase>(&Obj)) { 1001 if (Symflags & object::SymbolRef::SF_Absolute) 1002 SecName = "*ABS*"; 1003 else if (Symflags & object::SymbolRef::SF_Common) 1004 SecName = "*COM*"; 1005 else if (Symflags & object::SymbolRef::SF_Undefined) 1006 SecName = "*UND*"; 1007 else { 1008 elf_symbol_iterator SymI(I); 1009 Expected<elf_section_iterator> SecIOrErr = SymI->getSection(); 1010 if (!SecIOrErr) { 1011 consumeError(SecIOrErr.takeError()); 1012 return '?'; 1013 } 1014 1015 if (*SecIOrErr == ELFObj->section_end()) 1016 return '?'; 1017 1018 Expected<StringRef> NameOrErr = (*SecIOrErr)->getName(); 1019 if (!NameOrErr) { 1020 consumeError(NameOrErr.takeError()); 1021 return '?'; 1022 } 1023 SecName = *NameOrErr; 1024 } 1025 } 1026 1027 if (Symflags & object::SymbolRef::SF_Undefined) { 1028 if (isa<MachOObjectFile>(Obj) || !(Symflags & object::SymbolRef::SF_Weak)) 1029 return 'U'; 1030 return isObject(Obj, I) ? 'v' : 'w'; 1031 } 1032 if (isa<ELFObjectFileBase>(&Obj)) 1033 if (ELFSymbolRef(*I).getELFType() == ELF::STT_GNU_IFUNC) 1034 return 'i'; 1035 if (!isa<MachOObjectFile>(Obj) && (Symflags & object::SymbolRef::SF_Weak)) 1036 return isObject(Obj, I) ? 'V' : 'W'; 1037 1038 if (Symflags & object::SymbolRef::SF_Common) 1039 return 'C'; 1040 1041 char Ret = '?'; 1042 if (Symflags & object::SymbolRef::SF_Absolute) 1043 Ret = 'a'; 1044 else if (IRObjectFile *IR = dyn_cast<IRObjectFile>(&Obj)) 1045 Ret = getSymbolNMTypeChar(*IR, I); 1046 else if (COFFObjectFile *COFF = dyn_cast<COFFObjectFile>(&Obj)) 1047 Ret = getSymbolNMTypeChar(*COFF, I); 1048 else if (COFFImportFile *COFFImport = dyn_cast<COFFImportFile>(&Obj)) 1049 Ret = getSymbolNMTypeChar(*COFFImport); 1050 else if (MachOObjectFile *MachO = dyn_cast<MachOObjectFile>(&Obj)) 1051 Ret = getSymbolNMTypeChar(*MachO, I); 1052 else if (WasmObjectFile *Wasm = dyn_cast<WasmObjectFile>(&Obj)) 1053 Ret = getSymbolNMTypeChar(*Wasm, I); 1054 else if (TapiFile *Tapi = dyn_cast<TapiFile>(&Obj)) 1055 Ret = getSymbolNMTypeChar(*Tapi, I); 1056 else if (ELFObjectFileBase *ELF = dyn_cast<ELFObjectFileBase>(&Obj)) { 1057 Ret = getSymbolNMTypeChar(*ELF, I); 1058 if (ELFSymbolRef(*I).getBinding() == ELF::STB_GNU_UNIQUE) 1059 return Ret; 1060 } else 1061 llvm_unreachable("unknown binary format"); 1062 1063 if (!(Symflags & object::SymbolRef::SF_Global)) 1064 return Ret; 1065 1066 return toupper(Ret); 1067 } 1068 1069 // getNsectForSegSect() is used to implement the Mach-O "-s segname sectname" 1070 // option to dump only those symbols from that section in a Mach-O file. 1071 // It is called once for each Mach-O file from dumpSymbolNamesFromObject() 1072 // to get the section number for that named section from the command line 1073 // arguments. It returns the section number for that section in the Mach-O 1074 // file or zero it is not present. 1075 static unsigned getNsectForSegSect(MachOObjectFile *Obj) { 1076 unsigned Nsect = 1; 1077 for (auto &S : Obj->sections()) { 1078 DataRefImpl Ref = S.getRawDataRefImpl(); 1079 StringRef SectionName; 1080 if (Expected<StringRef> NameOrErr = Obj->getSectionName(Ref)) 1081 SectionName = *NameOrErr; 1082 StringRef SegmentName = Obj->getSectionFinalSegmentName(Ref); 1083 if (SegmentName == SegSect[0] && SectionName == SegSect[1]) 1084 return Nsect; 1085 Nsect++; 1086 } 1087 return 0; 1088 } 1089 1090 // getNsectInMachO() is used to implement the Mach-O "-s segname sectname" 1091 // option to dump only those symbols from that section in a Mach-O file. 1092 // It is called once for each symbol in a Mach-O file from 1093 // dumpSymbolNamesFromObject() and returns the section number for that symbol 1094 // if it is in a section, else it returns 0. 1095 static unsigned getNsectInMachO(MachOObjectFile &Obj, BasicSymbolRef Sym) { 1096 DataRefImpl Symb = Sym.getRawDataRefImpl(); 1097 if (Obj.is64Bit()) { 1098 MachO::nlist_64 STE = Obj.getSymbol64TableEntry(Symb); 1099 return (STE.n_type & MachO::N_TYPE) == MachO::N_SECT ? STE.n_sect : 0; 1100 } 1101 MachO::nlist STE = Obj.getSymbolTableEntry(Symb); 1102 return (STE.n_type & MachO::N_TYPE) == MachO::N_SECT ? STE.n_sect : 0; 1103 } 1104 1105 static void dumpSymbolsFromDLInfoMachO(MachOObjectFile &MachO) { 1106 size_t I = SymbolList.size(); 1107 std::string ExportsNameBuffer; 1108 raw_string_ostream EOS(ExportsNameBuffer); 1109 std::string BindsNameBuffer; 1110 raw_string_ostream BOS(BindsNameBuffer); 1111 std::string LazysNameBuffer; 1112 raw_string_ostream LOS(LazysNameBuffer); 1113 std::string WeaksNameBuffer; 1114 raw_string_ostream WOS(WeaksNameBuffer); 1115 std::string FunctionStartsNameBuffer; 1116 raw_string_ostream FOS(FunctionStartsNameBuffer); 1117 1118 MachO::mach_header H; 1119 MachO::mach_header_64 H_64; 1120 uint32_t HFlags = 0; 1121 if (MachO.is64Bit()) { 1122 H_64 = MachO.MachOObjectFile::getHeader64(); 1123 HFlags = H_64.flags; 1124 } else { 1125 H = MachO.MachOObjectFile::getHeader(); 1126 HFlags = H.flags; 1127 } 1128 uint64_t BaseSegmentAddress = 0; 1129 for (const auto &Command : MachO.load_commands()) { 1130 if (Command.C.cmd == MachO::LC_SEGMENT) { 1131 MachO::segment_command Seg = MachO.getSegmentLoadCommand(Command); 1132 if (Seg.fileoff == 0 && Seg.filesize != 0) { 1133 BaseSegmentAddress = Seg.vmaddr; 1134 break; 1135 } 1136 } else if (Command.C.cmd == MachO::LC_SEGMENT_64) { 1137 MachO::segment_command_64 Seg = MachO.getSegment64LoadCommand(Command); 1138 if (Seg.fileoff == 0 && Seg.filesize != 0) { 1139 BaseSegmentAddress = Seg.vmaddr; 1140 break; 1141 } 1142 } 1143 } 1144 if (DyldInfoOnly || AddDyldInfo || 1145 HFlags & MachO::MH_NLIST_OUTOFSYNC_WITH_DYLDINFO) { 1146 unsigned ExportsAdded = 0; 1147 Error Err = Error::success(); 1148 for (const llvm::object::ExportEntry &Entry : MachO.exports(Err)) { 1149 bool found = false; 1150 bool ReExport = false; 1151 if (!DyldInfoOnly) { 1152 for (const NMSymbol &S : SymbolList) 1153 if (S.Address == Entry.address() + BaseSegmentAddress && 1154 S.Name == Entry.name()) { 1155 found = true; 1156 break; 1157 } 1158 } 1159 if (!found) { 1160 NMSymbol S = {}; 1161 S.Address = Entry.address() + BaseSegmentAddress; 1162 S.Size = 0; 1163 S.TypeChar = '\0'; 1164 S.Name = Entry.name().str(); 1165 // There is no symbol in the nlist symbol table for this so we set 1166 // Sym effectivly to null and the rest of code in here must test for 1167 // it and not do things like Sym.getFlags() for it. 1168 S.Sym = BasicSymbolRef(); 1169 S.SymFlags = SymbolRef::SF_Global; 1170 S.Section = SectionRef(); 1171 S.NType = 0; 1172 S.NSect = 0; 1173 S.NDesc = 0; 1174 1175 uint64_t EFlags = Entry.flags(); 1176 bool Abs = ((EFlags & MachO::EXPORT_SYMBOL_FLAGS_KIND_MASK) == 1177 MachO::EXPORT_SYMBOL_FLAGS_KIND_ABSOLUTE); 1178 bool Resolver = (EFlags & MachO::EXPORT_SYMBOL_FLAGS_STUB_AND_RESOLVER); 1179 ReExport = (EFlags & MachO::EXPORT_SYMBOL_FLAGS_REEXPORT); 1180 bool WeakDef = (EFlags & MachO::EXPORT_SYMBOL_FLAGS_WEAK_DEFINITION); 1181 if (WeakDef) 1182 S.NDesc |= MachO::N_WEAK_DEF; 1183 if (Abs) { 1184 S.NType = MachO::N_EXT | MachO::N_ABS; 1185 S.TypeChar = 'A'; 1186 } else if (ReExport) { 1187 S.NType = MachO::N_EXT | MachO::N_INDR; 1188 S.TypeChar = 'I'; 1189 } else { 1190 S.NType = MachO::N_EXT | MachO::N_SECT; 1191 if (Resolver) { 1192 S.Address = Entry.other() + BaseSegmentAddress; 1193 if ((S.Address & 1) != 0 && !MachO.is64Bit() && 1194 H.cputype == MachO::CPU_TYPE_ARM) { 1195 S.Address &= ~1LL; 1196 S.NDesc |= MachO::N_ARM_THUMB_DEF; 1197 } 1198 } else { 1199 S.Address = Entry.address() + BaseSegmentAddress; 1200 } 1201 StringRef SegmentName = StringRef(); 1202 StringRef SectionName = StringRef(); 1203 for (const SectionRef &Section : MachO.sections()) { 1204 S.NSect++; 1205 1206 if (Expected<StringRef> NameOrErr = Section.getName()) 1207 SectionName = *NameOrErr; 1208 else 1209 consumeError(NameOrErr.takeError()); 1210 1211 SegmentName = 1212 MachO.getSectionFinalSegmentName(Section.getRawDataRefImpl()); 1213 if (S.Address >= Section.getAddress() && 1214 S.Address < Section.getAddress() + Section.getSize()) { 1215 S.Section = Section; 1216 break; 1217 } else if (Entry.name() == "__mh_execute_header" && 1218 SegmentName == "__TEXT" && SectionName == "__text") { 1219 S.Section = Section; 1220 S.NDesc |= MachO::REFERENCED_DYNAMICALLY; 1221 break; 1222 } 1223 } 1224 if (SegmentName == "__TEXT" && SectionName == "__text") 1225 S.TypeChar = 'T'; 1226 else if (SegmentName == "__DATA" && SectionName == "__data") 1227 S.TypeChar = 'D'; 1228 else if (SegmentName == "__DATA" && SectionName == "__bss") 1229 S.TypeChar = 'B'; 1230 else 1231 S.TypeChar = 'S'; 1232 } 1233 SymbolList.push_back(S); 1234 1235 EOS << Entry.name(); 1236 EOS << '\0'; 1237 ExportsAdded++; 1238 1239 // For ReExports there are a two more things to do, first add the 1240 // indirect name and second create the undefined symbol using the 1241 // referened dynamic library. 1242 if (ReExport) { 1243 1244 // Add the indirect name. 1245 if (Entry.otherName().empty()) 1246 EOS << Entry.name(); 1247 else 1248 EOS << Entry.otherName(); 1249 EOS << '\0'; 1250 1251 // Now create the undefined symbol using the referened dynamic 1252 // library. 1253 NMSymbol U = {}; 1254 U.Address = 0; 1255 U.Size = 0; 1256 U.TypeChar = 'U'; 1257 if (Entry.otherName().empty()) 1258 U.Name = Entry.name().str(); 1259 else 1260 U.Name = Entry.otherName().str(); 1261 // Again there is no symbol in the nlist symbol table for this so 1262 // we set Sym effectivly to null and the rest of code in here must 1263 // test for it and not do things like Sym.getFlags() for it. 1264 U.Sym = BasicSymbolRef(); 1265 U.SymFlags = SymbolRef::SF_Global | SymbolRef::SF_Undefined; 1266 U.Section = SectionRef(); 1267 U.NType = MachO::N_EXT | MachO::N_UNDF; 1268 U.NSect = 0; 1269 U.NDesc = 0; 1270 // The library ordinal for this undefined symbol is in the export 1271 // trie Entry.other(). 1272 MachO::SET_LIBRARY_ORDINAL(U.NDesc, Entry.other()); 1273 SymbolList.push_back(U); 1274 1275 // Finally add the undefined symbol's name. 1276 if (Entry.otherName().empty()) 1277 EOS << Entry.name(); 1278 else 1279 EOS << Entry.otherName(); 1280 EOS << '\0'; 1281 ExportsAdded++; 1282 } 1283 } 1284 } 1285 if (Err) 1286 error(std::move(Err), MachO.getFileName()); 1287 // Set the symbol names and indirect names for the added symbols. 1288 if (ExportsAdded) { 1289 EOS.flush(); 1290 const char *Q = ExportsNameBuffer.c_str(); 1291 for (unsigned K = 0; K < ExportsAdded; K++) { 1292 SymbolList[I].Name = Q; 1293 Q += strlen(Q) + 1; 1294 if (SymbolList[I].TypeChar == 'I') { 1295 SymbolList[I].IndirectName = Q; 1296 Q += strlen(Q) + 1; 1297 } 1298 I++; 1299 } 1300 } 1301 1302 // Add the undefined symbols from the bind entries. 1303 unsigned BindsAdded = 0; 1304 Error BErr = Error::success(); 1305 StringRef LastSymbolName = StringRef(); 1306 for (const llvm::object::MachOBindEntry &Entry : MachO.bindTable(BErr)) { 1307 bool found = false; 1308 if (LastSymbolName == Entry.symbolName()) 1309 found = true; 1310 else if (!DyldInfoOnly) { 1311 for (unsigned J = 0; J < SymbolList.size() && !found; ++J) { 1312 if (SymbolList[J].Name == Entry.symbolName()) 1313 found = true; 1314 } 1315 } 1316 if (!found) { 1317 LastSymbolName = Entry.symbolName(); 1318 NMSymbol B = {}; 1319 B.Address = 0; 1320 B.Size = 0; 1321 B.TypeChar = 'U'; 1322 // There is no symbol in the nlist symbol table for this so we set 1323 // Sym effectivly to null and the rest of code in here must test for 1324 // it and not do things like Sym.getFlags() for it. 1325 B.Sym = BasicSymbolRef(); 1326 B.SymFlags = SymbolRef::SF_Global | SymbolRef::SF_Undefined; 1327 B.NType = MachO::N_EXT | MachO::N_UNDF; 1328 B.NSect = 0; 1329 B.NDesc = 0; 1330 MachO::SET_LIBRARY_ORDINAL(B.NDesc, Entry.ordinal()); 1331 B.Name = Entry.symbolName().str(); 1332 SymbolList.push_back(B); 1333 BOS << Entry.symbolName(); 1334 BOS << '\0'; 1335 BindsAdded++; 1336 } 1337 } 1338 if (BErr) 1339 error(std::move(BErr), MachO.getFileName()); 1340 // Set the symbol names and indirect names for the added symbols. 1341 if (BindsAdded) { 1342 BOS.flush(); 1343 const char *Q = BindsNameBuffer.c_str(); 1344 for (unsigned K = 0; K < BindsAdded; K++) { 1345 SymbolList[I].Name = Q; 1346 Q += strlen(Q) + 1; 1347 if (SymbolList[I].TypeChar == 'I') { 1348 SymbolList[I].IndirectName = Q; 1349 Q += strlen(Q) + 1; 1350 } 1351 I++; 1352 } 1353 } 1354 1355 // Add the undefined symbols from the lazy bind entries. 1356 unsigned LazysAdded = 0; 1357 Error LErr = Error::success(); 1358 LastSymbolName = StringRef(); 1359 for (const llvm::object::MachOBindEntry &Entry : 1360 MachO.lazyBindTable(LErr)) { 1361 bool found = false; 1362 if (LastSymbolName == Entry.symbolName()) 1363 found = true; 1364 else { 1365 // Here we must check to see it this symbol is already in the 1366 // SymbolList as it might have already have been added above via a 1367 // non-lazy (bind) entry. 1368 for (unsigned J = 0; J < SymbolList.size() && !found; ++J) { 1369 if (SymbolList[J].Name == Entry.symbolName()) 1370 found = true; 1371 } 1372 } 1373 if (!found) { 1374 LastSymbolName = Entry.symbolName(); 1375 NMSymbol L = {}; 1376 L.Name = Entry.symbolName().str(); 1377 L.Address = 0; 1378 L.Size = 0; 1379 L.TypeChar = 'U'; 1380 // There is no symbol in the nlist symbol table for this so we set 1381 // Sym effectivly to null and the rest of code in here must test for 1382 // it and not do things like Sym.getFlags() for it. 1383 L.Sym = BasicSymbolRef(); 1384 L.SymFlags = SymbolRef::SF_Global | SymbolRef::SF_Undefined; 1385 L.NType = MachO::N_EXT | MachO::N_UNDF; 1386 L.NSect = 0; 1387 // The REFERENCE_FLAG_UNDEFINED_LAZY is no longer used but here it 1388 // makes sence since we are creating this from a lazy bind entry. 1389 L.NDesc = MachO::REFERENCE_FLAG_UNDEFINED_LAZY; 1390 MachO::SET_LIBRARY_ORDINAL(L.NDesc, Entry.ordinal()); 1391 SymbolList.push_back(L); 1392 LOS << Entry.symbolName(); 1393 LOS << '\0'; 1394 LazysAdded++; 1395 } 1396 } 1397 if (LErr) 1398 error(std::move(LErr), MachO.getFileName()); 1399 // Set the symbol names and indirect names for the added symbols. 1400 if (LazysAdded) { 1401 LOS.flush(); 1402 const char *Q = LazysNameBuffer.c_str(); 1403 for (unsigned K = 0; K < LazysAdded; K++) { 1404 SymbolList[I].Name = Q; 1405 Q += strlen(Q) + 1; 1406 if (SymbolList[I].TypeChar == 'I') { 1407 SymbolList[I].IndirectName = Q; 1408 Q += strlen(Q) + 1; 1409 } 1410 I++; 1411 } 1412 } 1413 1414 // Add the undefineds symbol from the weak bind entries which are not 1415 // strong symbols. 1416 unsigned WeaksAdded = 0; 1417 Error WErr = Error::success(); 1418 LastSymbolName = StringRef(); 1419 for (const llvm::object::MachOBindEntry &Entry : 1420 MachO.weakBindTable(WErr)) { 1421 bool found = false; 1422 unsigned J = 0; 1423 if (LastSymbolName == Entry.symbolName() || 1424 Entry.flags() & MachO::BIND_SYMBOL_FLAGS_NON_WEAK_DEFINITION) { 1425 found = true; 1426 } else { 1427 for (J = 0; J < SymbolList.size() && !found; ++J) { 1428 if (SymbolList[J].Name == Entry.symbolName()) { 1429 found = true; 1430 break; 1431 } 1432 } 1433 } 1434 if (!found) { 1435 LastSymbolName = Entry.symbolName(); 1436 NMSymbol W = {}; 1437 W.Name = Entry.symbolName().str(); 1438 W.Address = 0; 1439 W.Size = 0; 1440 W.TypeChar = 'U'; 1441 // There is no symbol in the nlist symbol table for this so we set 1442 // Sym effectivly to null and the rest of code in here must test for 1443 // it and not do things like Sym.getFlags() for it. 1444 W.Sym = BasicSymbolRef(); 1445 W.SymFlags = SymbolRef::SF_Global | SymbolRef::SF_Undefined; 1446 W.NType = MachO::N_EXT | MachO::N_UNDF; 1447 W.NSect = 0; 1448 // Odd that we are using N_WEAK_DEF on an undefined symbol but that is 1449 // what is created in this case by the linker when there are real 1450 // symbols in the nlist structs. 1451 W.NDesc = MachO::N_WEAK_DEF; 1452 SymbolList.push_back(W); 1453 WOS << Entry.symbolName(); 1454 WOS << '\0'; 1455 WeaksAdded++; 1456 } else { 1457 // This is the case the symbol was previously been found and it could 1458 // have been added from a bind or lazy bind symbol. If so and not 1459 // a definition also mark it as weak. 1460 if (SymbolList[J].TypeChar == 'U') 1461 // See comment above about N_WEAK_DEF. 1462 SymbolList[J].NDesc |= MachO::N_WEAK_DEF; 1463 } 1464 } 1465 if (WErr) 1466 error(std::move(WErr), MachO.getFileName()); 1467 // Set the symbol names and indirect names for the added symbols. 1468 if (WeaksAdded) { 1469 WOS.flush(); 1470 const char *Q = WeaksNameBuffer.c_str(); 1471 for (unsigned K = 0; K < WeaksAdded; K++) { 1472 SymbolList[I].Name = Q; 1473 Q += strlen(Q) + 1; 1474 if (SymbolList[I].TypeChar == 'I') { 1475 SymbolList[I].IndirectName = Q; 1476 Q += strlen(Q) + 1; 1477 } 1478 I++; 1479 } 1480 } 1481 1482 // Trying adding symbol from the function starts table and LC_MAIN entry 1483 // point. 1484 SmallVector<uint64_t, 8> FoundFns; 1485 uint64_t lc_main_offset = UINT64_MAX; 1486 for (const auto &Command : MachO.load_commands()) { 1487 if (Command.C.cmd == MachO::LC_FUNCTION_STARTS) { 1488 // We found a function starts segment, parse the addresses for 1489 // consumption. 1490 MachO::linkedit_data_command LLC = 1491 MachO.getLinkeditDataLoadCommand(Command); 1492 1493 MachO.ReadULEB128s(LLC.dataoff, FoundFns); 1494 } else if (Command.C.cmd == MachO::LC_MAIN) { 1495 MachO::entry_point_command LCmain = MachO.getEntryPointCommand(Command); 1496 lc_main_offset = LCmain.entryoff; 1497 } 1498 } 1499 // See if these addresses are already in the symbol table. 1500 unsigned FunctionStartsAdded = 0; 1501 for (uint64_t f = 0; f < FoundFns.size(); f++) { 1502 bool found = false; 1503 for (unsigned J = 0; J < SymbolList.size() && !found; ++J) { 1504 if (SymbolList[J].Address == FoundFns[f] + BaseSegmentAddress) 1505 found = true; 1506 } 1507 // See this address is not already in the symbol table fake up an 1508 // nlist for it. 1509 if (!found) { 1510 NMSymbol F = {}; 1511 F.Name = "<redacted function X>"; 1512 F.Address = FoundFns[f] + BaseSegmentAddress; 1513 F.Size = 0; 1514 // There is no symbol in the nlist symbol table for this so we set 1515 // Sym effectivly to null and the rest of code in here must test for 1516 // it and not do things like Sym.getFlags() for it. 1517 F.Sym = BasicSymbolRef(); 1518 F.SymFlags = 0; 1519 F.NType = MachO::N_SECT; 1520 F.NSect = 0; 1521 StringRef SegmentName = StringRef(); 1522 StringRef SectionName = StringRef(); 1523 for (const SectionRef &Section : MachO.sections()) { 1524 if (Expected<StringRef> NameOrErr = Section.getName()) 1525 SectionName = *NameOrErr; 1526 else 1527 consumeError(NameOrErr.takeError()); 1528 1529 SegmentName = 1530 MachO.getSectionFinalSegmentName(Section.getRawDataRefImpl()); 1531 F.NSect++; 1532 if (F.Address >= Section.getAddress() && 1533 F.Address < Section.getAddress() + Section.getSize()) { 1534 F.Section = Section; 1535 break; 1536 } 1537 } 1538 if (SegmentName == "__TEXT" && SectionName == "__text") 1539 F.TypeChar = 't'; 1540 else if (SegmentName == "__DATA" && SectionName == "__data") 1541 F.TypeChar = 'd'; 1542 else if (SegmentName == "__DATA" && SectionName == "__bss") 1543 F.TypeChar = 'b'; 1544 else 1545 F.TypeChar = 's'; 1546 F.NDesc = 0; 1547 SymbolList.push_back(F); 1548 if (FoundFns[f] == lc_main_offset) 1549 FOS << "<redacted LC_MAIN>"; 1550 else 1551 FOS << "<redacted function " << f << ">"; 1552 FOS << '\0'; 1553 FunctionStartsAdded++; 1554 } 1555 } 1556 if (FunctionStartsAdded) { 1557 FOS.flush(); 1558 const char *Q = FunctionStartsNameBuffer.c_str(); 1559 for (unsigned K = 0; K < FunctionStartsAdded; K++) { 1560 SymbolList[I].Name = Q; 1561 Q += strlen(Q) + 1; 1562 if (SymbolList[I].TypeChar == 'I') { 1563 SymbolList[I].IndirectName = Q; 1564 Q += strlen(Q) + 1; 1565 } 1566 I++; 1567 } 1568 } 1569 } 1570 } 1571 1572 static void dumpSymbolNamesFromObject(SymbolicFile &Obj, bool printName, 1573 StringRef ArchiveName = {}, 1574 StringRef ArchitectureName = {}) { 1575 auto Symbols = Obj.symbols(); 1576 std::vector<VersionEntry> SymbolVersions; 1577 if (DynamicSyms) { 1578 const auto *E = dyn_cast<ELFObjectFileBase>(&Obj); 1579 if (!E) { 1580 error("File format has no dynamic symbol table", Obj.getFileName()); 1581 return; 1582 } 1583 Symbols = E->getDynamicSymbolIterators(); 1584 1585 if (Expected<std::vector<VersionEntry>> VersionsOrErr = 1586 E->readDynsymVersions()) 1587 SymbolVersions = std::move(*VersionsOrErr); 1588 else 1589 WithColor::warning(errs(), ToolName) 1590 << "unable to read symbol versions: " 1591 << toString(VersionsOrErr.takeError()) << "\n"; 1592 } 1593 1594 // If a "-s segname sectname" option was specified and this is a Mach-O 1595 // file get the section number for that section in this object file. 1596 unsigned int Nsect = 0; 1597 MachOObjectFile *MachO = dyn_cast<MachOObjectFile>(&Obj); 1598 if (!SegSect.empty() && MachO) { 1599 Nsect = getNsectForSegSect(MachO); 1600 // If this section is not in the object file no symbols are printed. 1601 if (Nsect == 0) 1602 return; 1603 } 1604 if (!(MachO && DyldInfoOnly)) { 1605 size_t I = -1; 1606 for (BasicSymbolRef Sym : Symbols) { 1607 ++I; 1608 Expected<uint32_t> SymFlagsOrErr = Sym.getFlags(); 1609 if (!SymFlagsOrErr) { 1610 error(SymFlagsOrErr.takeError(), Obj.getFileName()); 1611 return; 1612 } 1613 1614 // Don't drop format specifc symbols for ARM and AArch64 ELF targets, they 1615 // are used to repesent mapping symbols and needed to honor the 1616 // --special-syms option. 1617 auto *ELFObj = dyn_cast<ELFObjectFileBase>(&Obj); 1618 if ((!ELFObj || (ELFObj->getEMachine() != ELF::EM_ARM && 1619 ELFObj->getEMachine() != ELF::EM_AARCH64)) && 1620 !DebugSyms && (*SymFlagsOrErr & SymbolRef::SF_FormatSpecific)) 1621 continue; 1622 if (WithoutAliases && (*SymFlagsOrErr & SymbolRef::SF_Indirect)) 1623 continue; 1624 // If a "-s segname sectname" option was specified and this is a Mach-O 1625 // file and this section appears in this file, Nsect will be non-zero then 1626 // see if this symbol is a symbol from that section and if not skip it. 1627 if (Nsect && Nsect != getNsectInMachO(*MachO, Sym)) 1628 continue; 1629 NMSymbol S = {}; 1630 S.Size = 0; 1631 S.Address = 0; 1632 if (isa<ELFObjectFileBase>(&Obj)) 1633 S.Size = ELFSymbolRef(Sym).getSize(); 1634 if (PrintAddress && isa<ObjectFile>(Obj)) { 1635 SymbolRef SymRef(Sym); 1636 Expected<uint64_t> AddressOrErr = SymRef.getAddress(); 1637 if (!AddressOrErr) { 1638 consumeError(AddressOrErr.takeError()); 1639 break; 1640 } 1641 S.Address = *AddressOrErr; 1642 } 1643 S.TypeName = getNMTypeName(Obj, Sym); 1644 S.TypeChar = getNMSectionTagAndName(Obj, Sym, S.SectionName); 1645 1646 raw_string_ostream OS(S.Name); 1647 if (Error E = Sym.printName(OS)) { 1648 if (MachO) { 1649 OS << "bad string index"; 1650 consumeError(std::move(E)); 1651 } else 1652 error(std::move(E), Obj.getFileName()); 1653 } 1654 if (!SymbolVersions.empty() && !SymbolVersions[I].Name.empty()) 1655 S.Name += 1656 (SymbolVersions[I].IsVerDef ? "@@" : "@") + SymbolVersions[I].Name; 1657 1658 S.Sym = Sym; 1659 SymbolList.push_back(S); 1660 } 1661 } 1662 1663 // If this is a Mach-O file where the nlist symbol table is out of sync 1664 // with the dyld export trie then look through exports and fake up symbols 1665 // for the ones that are missing (also done with the -add-dyldinfo flag). 1666 // This is needed if strip(1) -T is run on a binary containing swift 1667 // language symbols for example. The option -only-dyldinfo will fake up 1668 // all symbols from the dyld export trie as well as the bind info. 1669 if (MachO && !NoDyldInfo) 1670 dumpSymbolsFromDLInfoMachO(*MachO); 1671 1672 CurrentFilename = Obj.getFileName(); 1673 1674 if (Symbols.empty() && SymbolList.empty() && !Quiet) { 1675 writeFileName(errs(), ArchiveName, ArchitectureName); 1676 errs() << "no symbols\n"; 1677 } 1678 1679 sortAndPrintSymbolList(Obj, printName, ArchiveName, ArchitectureName); 1680 } 1681 1682 // checkMachOAndArchFlags() checks to see if the SymbolicFile is a Mach-O file 1683 // and if it is and there is a list of architecture flags is specified then 1684 // check to make sure this Mach-O file is one of those architectures or all 1685 // architectures was specificed. If not then an error is generated and this 1686 // routine returns false. Else it returns true. 1687 static bool checkMachOAndArchFlags(SymbolicFile *O, std::string &Filename) { 1688 auto *MachO = dyn_cast<MachOObjectFile>(O); 1689 1690 if (!MachO || ArchAll || ArchFlags.empty()) 1691 return true; 1692 1693 MachO::mach_header H; 1694 MachO::mach_header_64 H_64; 1695 Triple T; 1696 const char *McpuDefault, *ArchFlag; 1697 if (MachO->is64Bit()) { 1698 H_64 = MachO->MachOObjectFile::getHeader64(); 1699 T = MachOObjectFile::getArchTriple(H_64.cputype, H_64.cpusubtype, 1700 &McpuDefault, &ArchFlag); 1701 } else { 1702 H = MachO->MachOObjectFile::getHeader(); 1703 T = MachOObjectFile::getArchTriple(H.cputype, H.cpusubtype, 1704 &McpuDefault, &ArchFlag); 1705 } 1706 const std::string ArchFlagName(ArchFlag); 1707 if (!llvm::is_contained(ArchFlags, ArchFlagName)) { 1708 error("No architecture specified", Filename); 1709 return false; 1710 } 1711 return true; 1712 } 1713 1714 static void dumpSymbolNamesFromFile(std::string &Filename) { 1715 ErrorOr<std::unique_ptr<MemoryBuffer>> BufferOrErr = 1716 MemoryBuffer::getFileOrSTDIN(Filename); 1717 if (error(BufferOrErr.getError(), Filename)) 1718 return; 1719 1720 LLVMContext Context; 1721 LLVMContext *ContextPtr = NoLLVMBitcode ? nullptr : &Context; 1722 Expected<std::unique_ptr<Binary>> BinaryOrErr = 1723 createBinary(BufferOrErr.get()->getMemBufferRef(), ContextPtr); 1724 if (!BinaryOrErr) { 1725 error(BinaryOrErr.takeError(), Filename); 1726 return; 1727 } 1728 Binary &Bin = *BinaryOrErr.get(); 1729 1730 if (Archive *A = dyn_cast<Archive>(&Bin)) { 1731 if (ArchiveMap) { 1732 Archive::symbol_iterator I = A->symbol_begin(); 1733 Archive::symbol_iterator E = A->symbol_end(); 1734 if (I != E) { 1735 outs() << "Archive map\n"; 1736 for (; I != E; ++I) { 1737 Expected<Archive::Child> C = I->getMember(); 1738 if (!C) { 1739 error(C.takeError(), Filename); 1740 break; 1741 } 1742 Expected<StringRef> FileNameOrErr = C->getName(); 1743 if (!FileNameOrErr) { 1744 error(FileNameOrErr.takeError(), Filename); 1745 break; 1746 } 1747 StringRef SymName = I->getName(); 1748 outs() << SymName << " in " << FileNameOrErr.get() << "\n"; 1749 } 1750 outs() << "\n"; 1751 } 1752 } 1753 1754 { 1755 Error Err = Error::success(); 1756 for (auto &C : A->children(Err)) { 1757 Expected<std::unique_ptr<Binary>> ChildOrErr = 1758 C.getAsBinary(ContextPtr); 1759 if (!ChildOrErr) { 1760 if (auto E = isNotObjectErrorInvalidFileType(ChildOrErr.takeError())) 1761 error(std::move(E), Filename, C); 1762 continue; 1763 } 1764 if (SymbolicFile *O = dyn_cast<SymbolicFile>(&*ChildOrErr.get())) { 1765 if (!MachOPrintSizeWarning && PrintSize && isa<MachOObjectFile>(O)) { 1766 WithColor::warning(errs(), ToolName) 1767 << "sizes with -print-size for Mach-O files are always zero.\n"; 1768 MachOPrintSizeWarning = true; 1769 } 1770 if (!checkMachOAndArchFlags(O, Filename)) 1771 return; 1772 if (!PrintFileName) { 1773 outs() << "\n"; 1774 if (isa<MachOObjectFile>(O)) { 1775 outs() << Filename << "(" << O->getFileName() << ")"; 1776 } else 1777 outs() << O->getFileName(); 1778 outs() << ":\n"; 1779 } 1780 dumpSymbolNamesFromObject(*O, false, Filename); 1781 } 1782 } 1783 if (Err) 1784 error(std::move(Err), A->getFileName()); 1785 } 1786 return; 1787 } 1788 if (MachOUniversalBinary *UB = dyn_cast<MachOUniversalBinary>(&Bin)) { 1789 // If we have a list of architecture flags specified dump only those. 1790 if (!ArchAll && !ArchFlags.empty()) { 1791 // Look for a slice in the universal binary that matches each ArchFlag. 1792 bool ArchFound; 1793 for (unsigned i = 0; i < ArchFlags.size(); ++i) { 1794 ArchFound = false; 1795 for (MachOUniversalBinary::object_iterator I = UB->begin_objects(), 1796 E = UB->end_objects(); 1797 I != E; ++I) { 1798 if (ArchFlags[i] == I->getArchFlagName()) { 1799 ArchFound = true; 1800 Expected<std::unique_ptr<ObjectFile>> ObjOrErr = 1801 I->getAsObjectFile(); 1802 std::string ArchiveName; 1803 std::string ArchitectureName; 1804 ArchiveName.clear(); 1805 ArchitectureName.clear(); 1806 if (ObjOrErr) { 1807 ObjectFile &Obj = *ObjOrErr.get(); 1808 if (ArchFlags.size() > 1) { 1809 if (PrintFileName) 1810 ArchitectureName = I->getArchFlagName(); 1811 else 1812 outs() << "\n" << Obj.getFileName() << " (for architecture " 1813 << I->getArchFlagName() << ")" 1814 << ":\n"; 1815 } 1816 dumpSymbolNamesFromObject(Obj, false, ArchiveName, 1817 ArchitectureName); 1818 } else if (auto E = isNotObjectErrorInvalidFileType( 1819 ObjOrErr.takeError())) { 1820 error(std::move(E), Filename, ArchFlags.size() > 1 ? 1821 StringRef(I->getArchFlagName()) : StringRef()); 1822 continue; 1823 } else if (Expected<std::unique_ptr<Archive>> AOrErr = 1824 I->getAsArchive()) { 1825 std::unique_ptr<Archive> &A = *AOrErr; 1826 Error Err = Error::success(); 1827 for (auto &C : A->children(Err)) { 1828 Expected<std::unique_ptr<Binary>> ChildOrErr = 1829 C.getAsBinary(ContextPtr); 1830 if (!ChildOrErr) { 1831 if (auto E = isNotObjectErrorInvalidFileType( 1832 ChildOrErr.takeError())) { 1833 error(std::move(E), Filename, C, ArchFlags.size() > 1 ? 1834 StringRef(I->getArchFlagName()) : StringRef()); 1835 } 1836 continue; 1837 } 1838 if (SymbolicFile *O = 1839 dyn_cast<SymbolicFile>(&*ChildOrErr.get())) { 1840 if (PrintFileName) { 1841 ArchiveName = std::string(A->getFileName()); 1842 if (ArchFlags.size() > 1) 1843 ArchitectureName = I->getArchFlagName(); 1844 } else { 1845 outs() << "\n" << A->getFileName(); 1846 outs() << "(" << O->getFileName() << ")"; 1847 if (ArchFlags.size() > 1) { 1848 outs() << " (for architecture " << I->getArchFlagName() 1849 << ")"; 1850 } 1851 outs() << ":\n"; 1852 } 1853 dumpSymbolNamesFromObject(*O, false, ArchiveName, 1854 ArchitectureName); 1855 } 1856 } 1857 if (Err) 1858 error(std::move(Err), A->getFileName()); 1859 } else { 1860 consumeError(AOrErr.takeError()); 1861 error(Filename + " for architecture " + 1862 StringRef(I->getArchFlagName()) + 1863 " is not a Mach-O file or an archive file", 1864 "Mach-O universal file"); 1865 } 1866 } 1867 } 1868 if (!ArchFound) { 1869 error(ArchFlags[i], 1870 "file: " + Filename + " does not contain architecture"); 1871 return; 1872 } 1873 } 1874 return; 1875 } 1876 // No architecture flags were specified so if this contains a slice that 1877 // matches the host architecture dump only that. 1878 if (!ArchAll) { 1879 Triple HostTriple = MachOObjectFile::getHostArch(); 1880 StringRef HostArchName = HostTriple.getArchName(); 1881 for (MachOUniversalBinary::object_iterator I = UB->begin_objects(), 1882 E = UB->end_objects(); 1883 I != E; ++I) { 1884 if (HostArchName == I->getArchFlagName()) { 1885 Expected<std::unique_ptr<ObjectFile>> ObjOrErr = I->getAsObjectFile(); 1886 std::string ArchiveName; 1887 if (ObjOrErr) { 1888 ObjectFile &Obj = *ObjOrErr.get(); 1889 dumpSymbolNamesFromObject(Obj, false); 1890 } else if (auto E = isNotObjectErrorInvalidFileType( 1891 ObjOrErr.takeError())) { 1892 error(std::move(E), Filename); 1893 return; 1894 } else if (Expected<std::unique_ptr<Archive>> AOrErr = 1895 I->getAsArchive()) { 1896 std::unique_ptr<Archive> &A = *AOrErr; 1897 Error Err = Error::success(); 1898 for (auto &C : A->children(Err)) { 1899 Expected<std::unique_ptr<Binary>> ChildOrErr = 1900 C.getAsBinary(ContextPtr); 1901 if (!ChildOrErr) { 1902 if (auto E = isNotObjectErrorInvalidFileType( 1903 ChildOrErr.takeError())) 1904 error(std::move(E), Filename, C); 1905 continue; 1906 } 1907 if (SymbolicFile *O = 1908 dyn_cast<SymbolicFile>(&*ChildOrErr.get())) { 1909 if (PrintFileName) 1910 ArchiveName = std::string(A->getFileName()); 1911 else 1912 outs() << "\n" << A->getFileName() << "(" << O->getFileName() 1913 << ")" 1914 << ":\n"; 1915 dumpSymbolNamesFromObject(*O, false, ArchiveName); 1916 } 1917 } 1918 if (Err) 1919 error(std::move(Err), A->getFileName()); 1920 } else { 1921 consumeError(AOrErr.takeError()); 1922 error(Filename + " for architecture " + 1923 StringRef(I->getArchFlagName()) + 1924 " is not a Mach-O file or an archive file", 1925 "Mach-O universal file"); 1926 } 1927 return; 1928 } 1929 } 1930 } 1931 // Either all architectures have been specified or none have been specified 1932 // and this does not contain the host architecture so dump all the slices. 1933 bool moreThanOneArch = UB->getNumberOfObjects() > 1; 1934 for (const MachOUniversalBinary::ObjectForArch &O : UB->objects()) { 1935 Expected<std::unique_ptr<ObjectFile>> ObjOrErr = O.getAsObjectFile(); 1936 std::string ArchiveName; 1937 std::string ArchitectureName; 1938 ArchiveName.clear(); 1939 ArchitectureName.clear(); 1940 if (ObjOrErr) { 1941 ObjectFile &Obj = *ObjOrErr.get(); 1942 if (PrintFileName) { 1943 if (isa<MachOObjectFile>(Obj) && moreThanOneArch) 1944 ArchitectureName = O.getArchFlagName(); 1945 } else { 1946 if (moreThanOneArch) 1947 outs() << "\n"; 1948 outs() << Obj.getFileName(); 1949 if (isa<MachOObjectFile>(Obj) && moreThanOneArch) 1950 outs() << " (for architecture " << O.getArchFlagName() << ")"; 1951 outs() << ":\n"; 1952 } 1953 dumpSymbolNamesFromObject(Obj, false, ArchiveName, ArchitectureName); 1954 } else if (auto E = isNotObjectErrorInvalidFileType( 1955 ObjOrErr.takeError())) { 1956 error(std::move(E), Filename, moreThanOneArch ? 1957 StringRef(O.getArchFlagName()) : StringRef()); 1958 continue; 1959 } else if (Expected<std::unique_ptr<Archive>> AOrErr = 1960 O.getAsArchive()) { 1961 std::unique_ptr<Archive> &A = *AOrErr; 1962 Error Err = Error::success(); 1963 for (auto &C : A->children(Err)) { 1964 Expected<std::unique_ptr<Binary>> ChildOrErr = 1965 C.getAsBinary(ContextPtr); 1966 if (!ChildOrErr) { 1967 if (auto E = isNotObjectErrorInvalidFileType( 1968 ChildOrErr.takeError())) 1969 error(std::move(E), Filename, C, moreThanOneArch ? 1970 StringRef(ArchitectureName) : StringRef()); 1971 continue; 1972 } 1973 if (SymbolicFile *F = dyn_cast<SymbolicFile>(&*ChildOrErr.get())) { 1974 if (PrintFileName) { 1975 ArchiveName = std::string(A->getFileName()); 1976 if (isa<MachOObjectFile>(F) && moreThanOneArch) 1977 ArchitectureName = O.getArchFlagName(); 1978 } else { 1979 outs() << "\n" << A->getFileName(); 1980 if (isa<MachOObjectFile>(F)) { 1981 outs() << "(" << F->getFileName() << ")"; 1982 if (moreThanOneArch) 1983 outs() << " (for architecture " << O.getArchFlagName() 1984 << ")"; 1985 } else 1986 outs() << ":" << F->getFileName(); 1987 outs() << ":\n"; 1988 } 1989 dumpSymbolNamesFromObject(*F, false, ArchiveName, ArchitectureName); 1990 } 1991 } 1992 if (Err) 1993 error(std::move(Err), A->getFileName()); 1994 } else { 1995 consumeError(AOrErr.takeError()); 1996 error(Filename + " for architecture " + 1997 StringRef(O.getArchFlagName()) + 1998 " is not a Mach-O file or an archive file", 1999 "Mach-O universal file"); 2000 } 2001 } 2002 return; 2003 } 2004 2005 if (TapiUniversal *TU = dyn_cast<TapiUniversal>(&Bin)) { 2006 for (const TapiUniversal::ObjectForArch &I : TU->objects()) { 2007 StringRef ArchName = I.getArchFlagName(); 2008 const bool ShowArch = 2009 ArchFlags.empty() || llvm::is_contained(ArchFlags, ArchName); 2010 if (!ShowArch) 2011 continue; 2012 if (!AddInlinedInfo && !I.isTopLevelLib()) 2013 continue; 2014 if (auto ObjOrErr = I.getAsObjectFile()) { 2015 outs() << "\n" 2016 << I.getInstallName() << " (for architecture " << ArchName << ")" 2017 << ":\n"; 2018 dumpSymbolNamesFromObject(*ObjOrErr.get(), false, {}, ArchName); 2019 } else if (Error E = 2020 isNotObjectErrorInvalidFileType(ObjOrErr.takeError())) { 2021 error(std::move(E), Filename, ArchName); 2022 } 2023 } 2024 2025 return; 2026 } 2027 2028 if (SymbolicFile *O = dyn_cast<SymbolicFile>(&Bin)) { 2029 if (!MachOPrintSizeWarning && PrintSize && isa<MachOObjectFile>(O)) { 2030 WithColor::warning(errs(), ToolName) 2031 << "sizes with --print-size for Mach-O files are always zero.\n"; 2032 MachOPrintSizeWarning = true; 2033 } 2034 if (!checkMachOAndArchFlags(O, Filename)) 2035 return; 2036 dumpSymbolNamesFromObject(*O, true); 2037 } 2038 } 2039 2040 int main(int argc, char **argv) { 2041 InitLLVM X(argc, argv); 2042 BumpPtrAllocator A; 2043 StringSaver Saver(A); 2044 NmOptTable Tbl; 2045 ToolName = argv[0]; 2046 opt::InputArgList Args = 2047 Tbl.parseArgs(argc, argv, OPT_UNKNOWN, Saver, [&](StringRef Msg) { 2048 error(Msg); 2049 exit(1); 2050 }); 2051 if (Args.hasArg(OPT_help)) { 2052 Tbl.printHelp( 2053 outs(), 2054 (Twine(ToolName) + " [options] <input object files>").str().c_str(), 2055 "LLVM symbol table dumper"); 2056 // TODO Replace this with OptTable API once it adds extrahelp support. 2057 outs() << "\nPass @FILE as argument to read options from FILE.\n"; 2058 return 0; 2059 } 2060 if (Args.hasArg(OPT_version)) { 2061 // This needs to contain the word "GNU", libtool looks for that string. 2062 outs() << "llvm-nm, compatible with GNU nm" << '\n'; 2063 cl::PrintVersionMessage(); 2064 return 0; 2065 } 2066 2067 DebugSyms = Args.hasArg(OPT_debug_syms); 2068 DefinedOnly = Args.hasArg(OPT_defined_only); 2069 Demangle = Args.hasFlag(OPT_demangle, OPT_no_demangle, false); 2070 DynamicSyms = Args.hasArg(OPT_dynamic); 2071 ExternalOnly = Args.hasArg(OPT_extern_only); 2072 StringRef V = Args.getLastArgValue(OPT_format_EQ, "bsd"); 2073 if (V == "bsd") 2074 OutputFormat = bsd; 2075 else if (V == "posix") 2076 OutputFormat = posix; 2077 else if (V == "sysv") 2078 OutputFormat = sysv; 2079 else if (V == "darwin") 2080 OutputFormat = darwin; 2081 else if (V == "just-symbols") 2082 OutputFormat = just_symbols; 2083 else 2084 error("--format value should be one of: bsd, posix, sysv, darwin, " 2085 "just-symbols"); 2086 NoLLVMBitcode = Args.hasArg(OPT_no_llvm_bc); 2087 NoSort = Args.hasArg(OPT_no_sort); 2088 NoWeakSymbols = Args.hasArg(OPT_no_weak); 2089 NumericSort = Args.hasArg(OPT_numeric_sort); 2090 ArchiveMap = Args.hasArg(OPT_print_armap); 2091 PrintFileName = Args.hasArg(OPT_print_file_name); 2092 PrintSize = Args.hasArg(OPT_print_size); 2093 ReverseSort = Args.hasArg(OPT_reverse_sort); 2094 Quiet = Args.hasArg(OPT_quiet); 2095 V = Args.getLastArgValue(OPT_radix_EQ, "x"); 2096 if (V == "o") 2097 AddressRadix = Radix::o; 2098 else if (V == "d") 2099 AddressRadix = Radix::d; 2100 else if (V == "x") 2101 AddressRadix = Radix::x; 2102 else 2103 error("--radix value should be one of: 'o' (octal), 'd' (decimal), 'x' " 2104 "(hexadecimal)"); 2105 SizeSort = Args.hasArg(OPT_size_sort); 2106 SpecialSyms = Args.hasArg(OPT_special_syms); 2107 UndefinedOnly = Args.hasArg(OPT_undefined_only); 2108 WithoutAliases = Args.hasArg(OPT_without_aliases); 2109 2110 // Mach-O specific options. 2111 FormatMachOasHex = Args.hasArg(OPT_x); 2112 AddDyldInfo = Args.hasArg(OPT_add_dyldinfo); 2113 AddInlinedInfo = Args.hasArg(OPT_add_inlinedinfo); 2114 DyldInfoOnly = Args.hasArg(OPT_dyldinfo_only); 2115 NoDyldInfo = Args.hasArg(OPT_no_dyldinfo); 2116 2117 // llvm-nm only reads binary files. 2118 if (error(sys::ChangeStdinToBinary())) 2119 return 1; 2120 2121 // These calls are needed so that we can read bitcode correctly. 2122 llvm::InitializeAllTargetInfos(); 2123 llvm::InitializeAllTargetMCs(); 2124 llvm::InitializeAllAsmParsers(); 2125 2126 // The relative order of these is important. If you pass --size-sort it should 2127 // only print out the size. However, if you pass -S --size-sort, it should 2128 // print out both the size and address. 2129 if (SizeSort && !PrintSize) 2130 PrintAddress = false; 2131 if (OutputFormat == sysv || SizeSort) 2132 PrintSize = true; 2133 2134 for (const auto *A : Args.filtered(OPT_arch_EQ)) { 2135 SmallVector<StringRef, 2> Values; 2136 llvm::SplitString(A->getValue(), Values, ","); 2137 for (StringRef V : Values) { 2138 if (V == "all") 2139 ArchAll = true; 2140 else if (MachOObjectFile::isValidArch(V)) 2141 ArchFlags.push_back(V); 2142 else 2143 error("Unknown architecture named '" + V + "'", 2144 "for the --arch option"); 2145 } 2146 } 2147 2148 // Mach-O takes -s to accept two arguments. We emulate this by iterating over 2149 // both OPT_s and OPT_INPUT. 2150 std::vector<std::string> InputFilenames; 2151 int SegSectArgs = 0; 2152 for (opt::Arg *A : Args.filtered(OPT_s, OPT_INPUT)) { 2153 if (SegSectArgs > 0) { 2154 --SegSectArgs; 2155 SegSect.push_back(A->getValue()); 2156 } else if (A->getOption().matches(OPT_s)) { 2157 SegSectArgs = 2; 2158 } else { 2159 InputFilenames.push_back(A->getValue()); 2160 } 2161 } 2162 if (!SegSect.empty() && SegSect.size() != 2) 2163 error("bad number of arguments (must be two arguments)", 2164 "for the -s option"); 2165 2166 if (InputFilenames.empty()) 2167 InputFilenames.push_back("a.out"); 2168 if (InputFilenames.size() > 1) 2169 MultipleFiles = true; 2170 2171 if (NoDyldInfo && (AddDyldInfo || DyldInfoOnly)) 2172 error("--no-dyldinfo can't be used with --add-dyldinfo or --dyldinfo-only"); 2173 2174 llvm::for_each(InputFilenames, dumpSymbolNamesFromFile); 2175 2176 if (HadError) 2177 return 1; 2178 } 2179