1 //===- Archive.cpp - ar File Format implementation ------------------------===// 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 file defines the ArchiveObjectFile class. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "llvm/Object/Archive.h" 14 #include "llvm/ADT/SmallString.h" 15 #include "llvm/ADT/StringRef.h" 16 #include "llvm/ADT/Twine.h" 17 #include "llvm/Object/Binary.h" 18 #include "llvm/Object/Error.h" 19 #include "llvm/Support/Chrono.h" 20 #include "llvm/Support/Endian.h" 21 #include "llvm/Support/EndianStream.h" 22 #include "llvm/Support/Error.h" 23 #include "llvm/Support/ErrorOr.h" 24 #include "llvm/Support/FileSystem.h" 25 #include "llvm/Support/MathExtras.h" 26 #include "llvm/Support/MemoryBuffer.h" 27 #include "llvm/Support/Path.h" 28 #include "llvm/Support/raw_ostream.h" 29 #include "llvm/TargetParser/Host.h" 30 #include <algorithm> 31 #include <cassert> 32 #include <cstddef> 33 #include <cstdint> 34 #include <memory> 35 #include <string> 36 #include <system_error> 37 38 using namespace llvm; 39 using namespace object; 40 using namespace llvm::support::endian; 41 42 void Archive::anchor() {} 43 44 static Error malformedError(Twine Msg) { 45 std::string StringMsg = "truncated or malformed archive (" + Msg.str() + ")"; 46 return make_error<GenericBinaryError>(std::move(StringMsg), 47 object_error::parse_failed); 48 } 49 50 static Error 51 createMemberHeaderParseError(const AbstractArchiveMemberHeader *ArMemHeader, 52 const char *RawHeaderPtr, uint64_t Size) { 53 StringRef Msg("remaining size of archive too small for next archive " 54 "member header "); 55 56 Expected<StringRef> NameOrErr = ArMemHeader->getName(Size); 57 if (NameOrErr) 58 return malformedError(Msg + "for " + *NameOrErr); 59 60 consumeError(NameOrErr.takeError()); 61 uint64_t Offset = RawHeaderPtr - ArMemHeader->Parent->getData().data(); 62 return malformedError(Msg + "at offset " + Twine(Offset)); 63 } 64 65 template <class T, std::size_t N> 66 StringRef getFieldRawString(const T (&Field)[N]) { 67 return StringRef(Field, N).rtrim(" "); 68 } 69 70 template <class T> 71 StringRef CommonArchiveMemberHeader<T>::getRawAccessMode() const { 72 return getFieldRawString(ArMemHdr->AccessMode); 73 } 74 75 template <class T> 76 StringRef CommonArchiveMemberHeader<T>::getRawLastModified() const { 77 return getFieldRawString(ArMemHdr->LastModified); 78 } 79 80 template <class T> StringRef CommonArchiveMemberHeader<T>::getRawUID() const { 81 return getFieldRawString(ArMemHdr->UID); 82 } 83 84 template <class T> StringRef CommonArchiveMemberHeader<T>::getRawGID() const { 85 return getFieldRawString(ArMemHdr->GID); 86 } 87 88 template <class T> uint64_t CommonArchiveMemberHeader<T>::getOffset() const { 89 return reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 90 } 91 92 template class object::CommonArchiveMemberHeader<UnixArMemHdrType>; 93 template class object::CommonArchiveMemberHeader<BigArMemHdrType>; 94 95 ArchiveMemberHeader::ArchiveMemberHeader(const Archive *Parent, 96 const char *RawHeaderPtr, 97 uint64_t Size, Error *Err) 98 : CommonArchiveMemberHeader<UnixArMemHdrType>( 99 Parent, reinterpret_cast<const UnixArMemHdrType *>(RawHeaderPtr)) { 100 if (RawHeaderPtr == nullptr) 101 return; 102 ErrorAsOutParameter ErrAsOutParam(Err); 103 104 if (Size < getSizeOf()) { 105 *Err = createMemberHeaderParseError(this, RawHeaderPtr, Size); 106 return; 107 } 108 if (ArMemHdr->Terminator[0] != '`' || ArMemHdr->Terminator[1] != '\n') { 109 if (Err) { 110 std::string Buf; 111 raw_string_ostream OS(Buf); 112 OS.write_escaped( 113 StringRef(ArMemHdr->Terminator, sizeof(ArMemHdr->Terminator))); 114 OS.flush(); 115 std::string Msg("terminator characters in archive member \"" + Buf + 116 "\" not the correct \"`\\n\" values for the archive " 117 "member header "); 118 Expected<StringRef> NameOrErr = getName(Size); 119 if (!NameOrErr) { 120 consumeError(NameOrErr.takeError()); 121 uint64_t Offset = RawHeaderPtr - Parent->getData().data(); 122 *Err = malformedError(Msg + "at offset " + Twine(Offset)); 123 } else 124 *Err = malformedError(Msg + "for " + NameOrErr.get()); 125 } 126 return; 127 } 128 } 129 130 BigArchiveMemberHeader::BigArchiveMemberHeader(const Archive *Parent, 131 const char *RawHeaderPtr, 132 uint64_t Size, Error *Err) 133 : CommonArchiveMemberHeader<BigArMemHdrType>( 134 Parent, reinterpret_cast<const BigArMemHdrType *>(RawHeaderPtr)) { 135 if (RawHeaderPtr == nullptr) 136 return; 137 ErrorAsOutParameter ErrAsOutParam(Err); 138 139 if (RawHeaderPtr + getSizeOf() >= Parent->getData().end()) { 140 if (Err) 141 *Err = malformedError("malformed AIX big archive: remaining buffer is " 142 "unable to contain next archive member"); 143 return; 144 } 145 146 if (Size < getSizeOf()) { 147 Error SubErr = createMemberHeaderParseError(this, RawHeaderPtr, Size); 148 if (Err) 149 *Err = std::move(SubErr); 150 } 151 } 152 153 // This gets the raw name from the ArMemHdr->Name field and checks that it is 154 // valid for the kind of archive. If it is not valid it returns an Error. 155 Expected<StringRef> ArchiveMemberHeader::getRawName() const { 156 char EndCond; 157 auto Kind = Parent->kind(); 158 if (Kind == Archive::K_BSD || Kind == Archive::K_DARWIN64) { 159 if (ArMemHdr->Name[0] == ' ') { 160 uint64_t Offset = 161 reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 162 return malformedError("name contains a leading space for archive member " 163 "header at offset " + 164 Twine(Offset)); 165 } 166 EndCond = ' '; 167 } else if (ArMemHdr->Name[0] == '/' || ArMemHdr->Name[0] == '#') 168 EndCond = ' '; 169 else 170 EndCond = '/'; 171 StringRef::size_type end = 172 StringRef(ArMemHdr->Name, sizeof(ArMemHdr->Name)).find(EndCond); 173 if (end == StringRef::npos) 174 end = sizeof(ArMemHdr->Name); 175 assert(end <= sizeof(ArMemHdr->Name) && end > 0); 176 // Don't include the EndCond if there is one. 177 return StringRef(ArMemHdr->Name, end); 178 } 179 180 Expected<uint64_t> 181 getArchiveMemberDecField(Twine FieldName, const StringRef RawField, 182 const Archive *Parent, 183 const AbstractArchiveMemberHeader *MemHeader) { 184 uint64_t Value; 185 if (RawField.getAsInteger(10, Value)) { 186 uint64_t Offset = MemHeader->getOffset(); 187 return malformedError("characters in " + FieldName + 188 " field in archive member header are not " 189 "all decimal numbers: '" + 190 RawField + 191 "' for the archive " 192 "member header at offset " + 193 Twine(Offset)); 194 } 195 return Value; 196 } 197 198 Expected<uint64_t> 199 getArchiveMemberOctField(Twine FieldName, const StringRef RawField, 200 const Archive *Parent, 201 const AbstractArchiveMemberHeader *MemHeader) { 202 uint64_t Value; 203 if (RawField.getAsInteger(8, Value)) { 204 uint64_t Offset = MemHeader->getOffset(); 205 return malformedError("characters in " + FieldName + 206 " field in archive member header are not " 207 "all octal numbers: '" + 208 RawField + 209 "' for the archive " 210 "member header at offset " + 211 Twine(Offset)); 212 } 213 return Value; 214 } 215 216 Expected<StringRef> BigArchiveMemberHeader::getRawName() const { 217 Expected<uint64_t> NameLenOrErr = getArchiveMemberDecField( 218 "NameLen", getFieldRawString(ArMemHdr->NameLen), Parent, this); 219 if (!NameLenOrErr) 220 // TODO: Out-of-line. 221 return NameLenOrErr.takeError(); 222 uint64_t NameLen = NameLenOrErr.get(); 223 224 // If the name length is odd, pad with '\0' to get an even length. After 225 // padding, there is the name terminator "`\n". 226 uint64_t NameLenWithPadding = alignTo(NameLen, 2); 227 StringRef NameTerminator = "`\n"; 228 StringRef NameStringWithNameTerminator = 229 StringRef(ArMemHdr->Name, NameLenWithPadding + NameTerminator.size()); 230 if (!NameStringWithNameTerminator.ends_with(NameTerminator)) { 231 uint64_t Offset = 232 reinterpret_cast<const char *>(ArMemHdr->Name + NameLenWithPadding) - 233 Parent->getData().data(); 234 // TODO: Out-of-line. 235 return malformedError( 236 "name does not have name terminator \"`\\n\" for archive member" 237 "header at offset " + 238 Twine(Offset)); 239 } 240 return StringRef(ArMemHdr->Name, NameLen); 241 } 242 243 // member including the header, so the size of any name following the header 244 // is checked to make sure it does not overflow. 245 Expected<StringRef> ArchiveMemberHeader::getName(uint64_t Size) const { 246 247 // This can be called from the ArchiveMemberHeader constructor when the 248 // archive header is truncated to produce an error message with the name. 249 // Make sure the name field is not truncated. 250 if (Size < offsetof(UnixArMemHdrType, Name) + sizeof(ArMemHdr->Name)) { 251 uint64_t ArchiveOffset = 252 reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 253 return malformedError("archive header truncated before the name field " 254 "for archive member header at offset " + 255 Twine(ArchiveOffset)); 256 } 257 258 // The raw name itself can be invalid. 259 Expected<StringRef> NameOrErr = getRawName(); 260 if (!NameOrErr) 261 return NameOrErr.takeError(); 262 StringRef Name = NameOrErr.get(); 263 264 // Check if it's a special name. 265 if (Name[0] == '/') { 266 if (Name.size() == 1) // Linker member. 267 return Name; 268 if (Name.size() == 2 && Name[1] == '/') // String table. 269 return Name; 270 // System libraries from the Windows SDK for Windows 11 contain this symbol. 271 // It looks like a CFG guard: we just skip it for now. 272 if (Name == "/<XFGHASHMAP>/") 273 return Name; 274 // Some libraries (e.g., arm64rt.lib) from the Windows WDK 275 // (version 10.0.22000.0) contain this undocumented special member. 276 if (Name == "/<ECSYMBOLS>/") 277 return Name; 278 // It's a long name. 279 // Get the string table offset. 280 std::size_t StringOffset; 281 if (Name.substr(1).rtrim(' ').getAsInteger(10, StringOffset)) { 282 std::string Buf; 283 raw_string_ostream OS(Buf); 284 OS.write_escaped(Name.substr(1).rtrim(' ')); 285 OS.flush(); 286 uint64_t ArchiveOffset = 287 reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 288 return malformedError("long name offset characters after the '/' are " 289 "not all decimal numbers: '" + 290 Buf + "' for archive member header at offset " + 291 Twine(ArchiveOffset)); 292 } 293 294 // Verify it. 295 if (StringOffset >= Parent->getStringTable().size()) { 296 uint64_t ArchiveOffset = 297 reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 298 return malformedError("long name offset " + Twine(StringOffset) + 299 " past the end of the string table for archive " 300 "member header at offset " + 301 Twine(ArchiveOffset)); 302 } 303 304 // GNU long file names end with a "/\n". 305 if (Parent->kind() == Archive::K_GNU || 306 Parent->kind() == Archive::K_GNU64) { 307 size_t End = Parent->getStringTable().find('\n', /*From=*/StringOffset); 308 if (End == StringRef::npos || End < 1 || 309 Parent->getStringTable()[End - 1] != '/') { 310 return malformedError("string table at long name offset " + 311 Twine(StringOffset) + "not terminated"); 312 } 313 return Parent->getStringTable().slice(StringOffset, End - 1); 314 } 315 return Parent->getStringTable().begin() + StringOffset; 316 } 317 318 if (Name.starts_with("#1/")) { 319 uint64_t NameLength; 320 if (Name.substr(3).rtrim(' ').getAsInteger(10, NameLength)) { 321 std::string Buf; 322 raw_string_ostream OS(Buf); 323 OS.write_escaped(Name.substr(3).rtrim(' ')); 324 OS.flush(); 325 uint64_t ArchiveOffset = 326 reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 327 return malformedError("long name length characters after the #1/ are " 328 "not all decimal numbers: '" + 329 Buf + "' for archive member header at offset " + 330 Twine(ArchiveOffset)); 331 } 332 if (getSizeOf() + NameLength > Size) { 333 uint64_t ArchiveOffset = 334 reinterpret_cast<const char *>(ArMemHdr) - Parent->getData().data(); 335 return malformedError("long name length: " + Twine(NameLength) + 336 " extends past the end of the member or archive " 337 "for archive member header at offset " + 338 Twine(ArchiveOffset)); 339 } 340 return StringRef(reinterpret_cast<const char *>(ArMemHdr) + getSizeOf(), 341 NameLength) 342 .rtrim('\0'); 343 } 344 345 // It is not a long name so trim the blanks at the end of the name. 346 if (Name[Name.size() - 1] != '/') 347 return Name.rtrim(' '); 348 349 // It's a simple name. 350 return Name.drop_back(1); 351 } 352 353 Expected<StringRef> BigArchiveMemberHeader::getName(uint64_t Size) const { 354 return getRawName(); 355 } 356 357 Expected<uint64_t> ArchiveMemberHeader::getSize() const { 358 return getArchiveMemberDecField("size", getFieldRawString(ArMemHdr->Size), 359 Parent, this); 360 } 361 362 Expected<uint64_t> BigArchiveMemberHeader::getSize() const { 363 Expected<uint64_t> SizeOrErr = getArchiveMemberDecField( 364 "size", getFieldRawString(ArMemHdr->Size), Parent, this); 365 if (!SizeOrErr) 366 return SizeOrErr.takeError(); 367 368 Expected<uint64_t> NameLenOrErr = getRawNameSize(); 369 if (!NameLenOrErr) 370 return NameLenOrErr.takeError(); 371 372 return *SizeOrErr + alignTo(*NameLenOrErr, 2); 373 } 374 375 Expected<uint64_t> BigArchiveMemberHeader::getRawNameSize() const { 376 return getArchiveMemberDecField( 377 "NameLen", getFieldRawString(ArMemHdr->NameLen), Parent, this); 378 } 379 380 Expected<uint64_t> BigArchiveMemberHeader::getNextOffset() const { 381 return getArchiveMemberDecField( 382 "NextOffset", getFieldRawString(ArMemHdr->NextOffset), Parent, this); 383 } 384 385 Expected<sys::fs::perms> AbstractArchiveMemberHeader::getAccessMode() const { 386 Expected<uint64_t> AccessModeOrErr = 387 getArchiveMemberOctField("AccessMode", getRawAccessMode(), Parent, this); 388 if (!AccessModeOrErr) 389 return AccessModeOrErr.takeError(); 390 return static_cast<sys::fs::perms>(*AccessModeOrErr); 391 } 392 393 Expected<sys::TimePoint<std::chrono::seconds>> 394 AbstractArchiveMemberHeader::getLastModified() const { 395 Expected<uint64_t> SecondsOrErr = getArchiveMemberDecField( 396 "LastModified", getRawLastModified(), Parent, this); 397 398 if (!SecondsOrErr) 399 return SecondsOrErr.takeError(); 400 401 return sys::toTimePoint(*SecondsOrErr); 402 } 403 404 Expected<unsigned> AbstractArchiveMemberHeader::getUID() const { 405 StringRef User = getRawUID(); 406 if (User.empty()) 407 return 0; 408 return getArchiveMemberDecField("UID", User, Parent, this); 409 } 410 411 Expected<unsigned> AbstractArchiveMemberHeader::getGID() const { 412 StringRef Group = getRawGID(); 413 if (Group.empty()) 414 return 0; 415 return getArchiveMemberDecField("GID", Group, Parent, this); 416 } 417 418 Expected<bool> ArchiveMemberHeader::isThin() const { 419 Expected<StringRef> NameOrErr = getRawName(); 420 if (!NameOrErr) 421 return NameOrErr.takeError(); 422 StringRef Name = NameOrErr.get(); 423 return Parent->isThin() && Name != "/" && Name != "//" && Name != "/SYM64/"; 424 } 425 426 Expected<const char *> ArchiveMemberHeader::getNextChildLoc() const { 427 uint64_t Size = getSizeOf(); 428 Expected<bool> isThinOrErr = isThin(); 429 if (!isThinOrErr) 430 return isThinOrErr.takeError(); 431 432 bool isThin = isThinOrErr.get(); 433 if (!isThin) { 434 Expected<uint64_t> MemberSize = getSize(); 435 if (!MemberSize) 436 return MemberSize.takeError(); 437 438 Size += MemberSize.get(); 439 } 440 441 // If Size is odd, add 1 to make it even. 442 const char *NextLoc = 443 reinterpret_cast<const char *>(ArMemHdr) + alignTo(Size, 2); 444 445 if (NextLoc == Parent->getMemoryBufferRef().getBufferEnd()) 446 return nullptr; 447 448 return NextLoc; 449 } 450 451 Expected<const char *> BigArchiveMemberHeader::getNextChildLoc() const { 452 if (getOffset() == 453 static_cast<const BigArchive *>(Parent)->getLastChildOffset()) 454 return nullptr; 455 456 Expected<uint64_t> NextOffsetOrErr = getNextOffset(); 457 if (!NextOffsetOrErr) 458 return NextOffsetOrErr.takeError(); 459 return Parent->getData().data() + NextOffsetOrErr.get(); 460 } 461 462 Archive::Child::Child(const Archive *Parent, StringRef Data, 463 uint16_t StartOfFile) 464 : Parent(Parent), Data(Data), StartOfFile(StartOfFile) { 465 Header = Parent->createArchiveMemberHeader(Data.data(), Data.size(), nullptr); 466 } 467 468 Archive::Child::Child(const Archive *Parent, const char *Start, Error *Err) 469 : Parent(Parent) { 470 if (!Start) { 471 Header = nullptr; 472 StartOfFile = -1; 473 return; 474 } 475 476 Header = Parent->createArchiveMemberHeader( 477 Start, 478 Parent ? Parent->getData().size() - (Start - Parent->getData().data()) 479 : 0, 480 Err); 481 482 // If we are pointed to real data, Start is not a nullptr, then there must be 483 // a non-null Err pointer available to report malformed data on. Only in 484 // the case sentinel value is being constructed is Err is permitted to be a 485 // nullptr. 486 assert(Err && "Err can't be nullptr if Start is not a nullptr"); 487 488 ErrorAsOutParameter ErrAsOutParam(Err); 489 490 // If there was an error in the construction of the Header 491 // then just return with the error now set. 492 if (*Err) 493 return; 494 495 uint64_t Size = Header->getSizeOf(); 496 Data = StringRef(Start, Size); 497 Expected<bool> isThinOrErr = isThinMember(); 498 if (!isThinOrErr) { 499 *Err = isThinOrErr.takeError(); 500 return; 501 } 502 bool isThin = isThinOrErr.get(); 503 if (!isThin) { 504 Expected<uint64_t> MemberSize = getRawSize(); 505 if (!MemberSize) { 506 *Err = MemberSize.takeError(); 507 return; 508 } 509 Size += MemberSize.get(); 510 Data = StringRef(Start, Size); 511 } 512 513 // Setup StartOfFile and PaddingBytes. 514 StartOfFile = Header->getSizeOf(); 515 // Don't include attached name. 516 Expected<StringRef> NameOrErr = getRawName(); 517 if (!NameOrErr) { 518 *Err = NameOrErr.takeError(); 519 return; 520 } 521 StringRef Name = NameOrErr.get(); 522 523 if (Parent->kind() == Archive::K_AIXBIG) { 524 // The actual start of the file is after the name and any necessary 525 // even-alignment padding. 526 StartOfFile += ((Name.size() + 1) >> 1) << 1; 527 } else if (Name.starts_with("#1/")) { 528 uint64_t NameSize; 529 StringRef RawNameSize = Name.substr(3).rtrim(' '); 530 if (RawNameSize.getAsInteger(10, NameSize)) { 531 uint64_t Offset = Start - Parent->getData().data(); 532 *Err = malformedError("long name length characters after the #1/ are " 533 "not all decimal numbers: '" + 534 RawNameSize + 535 "' for archive member header at offset " + 536 Twine(Offset)); 537 return; 538 } 539 StartOfFile += NameSize; 540 } 541 } 542 543 Expected<uint64_t> Archive::Child::getSize() const { 544 if (Parent->IsThin) 545 return Header->getSize(); 546 return Data.size() - StartOfFile; 547 } 548 549 Expected<uint64_t> Archive::Child::getRawSize() const { 550 return Header->getSize(); 551 } 552 553 Expected<bool> Archive::Child::isThinMember() const { return Header->isThin(); } 554 555 Expected<std::string> Archive::Child::getFullName() const { 556 Expected<bool> isThin = isThinMember(); 557 if (!isThin) 558 return isThin.takeError(); 559 assert(isThin.get()); 560 Expected<StringRef> NameOrErr = getName(); 561 if (!NameOrErr) 562 return NameOrErr.takeError(); 563 StringRef Name = *NameOrErr; 564 if (sys::path::is_absolute(Name)) 565 return std::string(Name); 566 567 SmallString<128> FullName = sys::path::parent_path( 568 Parent->getMemoryBufferRef().getBufferIdentifier()); 569 sys::path::append(FullName, Name); 570 return std::string(FullName); 571 } 572 573 Expected<StringRef> Archive::Child::getBuffer() const { 574 Expected<bool> isThinOrErr = isThinMember(); 575 if (!isThinOrErr) 576 return isThinOrErr.takeError(); 577 bool isThin = isThinOrErr.get(); 578 if (!isThin) { 579 Expected<uint64_t> Size = getSize(); 580 if (!Size) 581 return Size.takeError(); 582 return StringRef(Data.data() + StartOfFile, Size.get()); 583 } 584 Expected<std::string> FullNameOrErr = getFullName(); 585 if (!FullNameOrErr) 586 return FullNameOrErr.takeError(); 587 const std::string &FullName = *FullNameOrErr; 588 ErrorOr<std::unique_ptr<MemoryBuffer>> Buf = MemoryBuffer::getFile(FullName); 589 if (std::error_code EC = Buf.getError()) 590 return errorCodeToError(EC); 591 Parent->ThinBuffers.push_back(std::move(*Buf)); 592 return Parent->ThinBuffers.back()->getBuffer(); 593 } 594 595 Expected<Archive::Child> Archive::Child::getNext() const { 596 Expected<const char *> NextLocOrErr = Header->getNextChildLoc(); 597 if (!NextLocOrErr) 598 return NextLocOrErr.takeError(); 599 600 const char *NextLoc = *NextLocOrErr; 601 602 // Check to see if this is at the end of the archive. 603 if (NextLoc == nullptr) 604 return Child(nullptr, nullptr, nullptr); 605 606 // Check to see if this is past the end of the archive. 607 if (NextLoc > Parent->Data.getBufferEnd()) { 608 std::string Msg("offset to next archive member past the end of the archive " 609 "after member "); 610 Expected<StringRef> NameOrErr = getName(); 611 if (!NameOrErr) { 612 consumeError(NameOrErr.takeError()); 613 uint64_t Offset = Data.data() - Parent->getData().data(); 614 return malformedError(Msg + "at offset " + Twine(Offset)); 615 } else 616 return malformedError(Msg + NameOrErr.get()); 617 } 618 619 Error Err = Error::success(); 620 Child Ret(Parent, NextLoc, &Err); 621 if (Err) 622 return std::move(Err); 623 return Ret; 624 } 625 626 uint64_t Archive::Child::getChildOffset() const { 627 const char *a = Parent->Data.getBuffer().data(); 628 const char *c = Data.data(); 629 uint64_t offset = c - a; 630 return offset; 631 } 632 633 Expected<StringRef> Archive::Child::getName() const { 634 Expected<uint64_t> RawSizeOrErr = getRawSize(); 635 if (!RawSizeOrErr) 636 return RawSizeOrErr.takeError(); 637 uint64_t RawSize = RawSizeOrErr.get(); 638 Expected<StringRef> NameOrErr = 639 Header->getName(Header->getSizeOf() + RawSize); 640 if (!NameOrErr) 641 return NameOrErr.takeError(); 642 StringRef Name = NameOrErr.get(); 643 return Name; 644 } 645 646 Expected<MemoryBufferRef> Archive::Child::getMemoryBufferRef() const { 647 Expected<StringRef> NameOrErr = getName(); 648 if (!NameOrErr) 649 return NameOrErr.takeError(); 650 StringRef Name = NameOrErr.get(); 651 Expected<StringRef> Buf = getBuffer(); 652 if (!Buf) 653 return createFileError(Name, Buf.takeError()); 654 return MemoryBufferRef(*Buf, Name); 655 } 656 657 Expected<std::unique_ptr<Binary>> 658 Archive::Child::getAsBinary(LLVMContext *Context) const { 659 Expected<MemoryBufferRef> BuffOrErr = getMemoryBufferRef(); 660 if (!BuffOrErr) 661 return BuffOrErr.takeError(); 662 663 auto BinaryOrErr = createBinary(BuffOrErr.get(), Context); 664 if (BinaryOrErr) 665 return std::move(*BinaryOrErr); 666 return BinaryOrErr.takeError(); 667 } 668 669 Expected<std::unique_ptr<Archive>> Archive::create(MemoryBufferRef Source) { 670 Error Err = Error::success(); 671 std::unique_ptr<Archive> Ret; 672 StringRef Buffer = Source.getBuffer(); 673 674 if (Buffer.starts_with(BigArchiveMagic)) 675 Ret = std::make_unique<BigArchive>(Source, Err); 676 else 677 Ret = std::make_unique<Archive>(Source, Err); 678 679 if (Err) 680 return std::move(Err); 681 return std::move(Ret); 682 } 683 684 std::unique_ptr<AbstractArchiveMemberHeader> 685 Archive::createArchiveMemberHeader(const char *RawHeaderPtr, uint64_t Size, 686 Error *Err) const { 687 ErrorAsOutParameter ErrAsOutParam(Err); 688 if (kind() != K_AIXBIG) 689 return std::make_unique<ArchiveMemberHeader>(this, RawHeaderPtr, Size, Err); 690 return std::make_unique<BigArchiveMemberHeader>(this, RawHeaderPtr, Size, 691 Err); 692 } 693 694 uint64_t Archive::getArchiveMagicLen() const { 695 if (isThin()) 696 return sizeof(ThinArchiveMagic) - 1; 697 698 if (Kind() == K_AIXBIG) 699 return sizeof(BigArchiveMagic) - 1; 700 701 return sizeof(ArchiveMagic) - 1; 702 } 703 704 void Archive::setFirstRegular(const Child &C) { 705 FirstRegularData = C.Data; 706 FirstRegularStartOfFile = C.StartOfFile; 707 } 708 709 Archive::Archive(MemoryBufferRef Source, Error &Err) 710 : Binary(Binary::ID_Archive, Source) { 711 ErrorAsOutParameter ErrAsOutParam(&Err); 712 StringRef Buffer = Data.getBuffer(); 713 // Check for sufficient magic. 714 if (Buffer.starts_with(ThinArchiveMagic)) { 715 IsThin = true; 716 } else if (Buffer.starts_with(ArchiveMagic)) { 717 IsThin = false; 718 } else if (Buffer.starts_with(BigArchiveMagic)) { 719 Format = K_AIXBIG; 720 IsThin = false; 721 return; 722 } else { 723 Err = make_error<GenericBinaryError>("file too small to be an archive", 724 object_error::invalid_file_type); 725 return; 726 } 727 728 // Make sure Format is initialized before any call to 729 // ArchiveMemberHeader::getName() is made. This could be a valid empty 730 // archive which is the same in all formats. So claiming it to be gnu to is 731 // fine if not totally correct before we look for a string table or table of 732 // contents. 733 Format = K_GNU; 734 735 // Get the special members. 736 child_iterator I = child_begin(Err, false); 737 if (Err) 738 return; 739 child_iterator E = child_end(); 740 741 // See if this is a valid empty archive and if so return. 742 if (I == E) { 743 Err = Error::success(); 744 return; 745 } 746 const Child *C = &*I; 747 748 auto Increment = [&]() { 749 ++I; 750 if (Err) 751 return true; 752 C = &*I; 753 return false; 754 }; 755 756 Expected<StringRef> NameOrErr = C->getRawName(); 757 if (!NameOrErr) { 758 Err = NameOrErr.takeError(); 759 return; 760 } 761 StringRef Name = NameOrErr.get(); 762 763 // Below is the pattern that is used to figure out the archive format 764 // GNU archive format 765 // First member : / (may exist, if it exists, points to the symbol table ) 766 // Second member : // (may exist, if it exists, points to the string table) 767 // Note : The string table is used if the filename exceeds 15 characters 768 // BSD archive format 769 // First member : __.SYMDEF or "__.SYMDEF SORTED" (the symbol table) 770 // There is no string table, if the filename exceeds 15 characters or has a 771 // embedded space, the filename has #1/<size>, The size represents the size 772 // of the filename that needs to be read after the archive header 773 // COFF archive format 774 // First member : / 775 // Second member : / (provides a directory of symbols) 776 // Third member : // (may exist, if it exists, contains the string table) 777 // Note: Microsoft PE/COFF Spec 8.3 says that the third member is present 778 // even if the string table is empty. However, lib.exe does not in fact 779 // seem to create the third member if there's no member whose filename 780 // exceeds 15 characters. So the third member is optional. 781 782 if (Name == "__.SYMDEF" || Name == "__.SYMDEF_64") { 783 if (Name == "__.SYMDEF") 784 Format = K_BSD; 785 else // Name == "__.SYMDEF_64" 786 Format = K_DARWIN64; 787 // We know that the symbol table is not an external file, but we still must 788 // check any Expected<> return value. 789 Expected<StringRef> BufOrErr = C->getBuffer(); 790 if (!BufOrErr) { 791 Err = BufOrErr.takeError(); 792 return; 793 } 794 SymbolTable = BufOrErr.get(); 795 if (Increment()) 796 return; 797 setFirstRegular(*C); 798 799 Err = Error::success(); 800 return; 801 } 802 803 if (Name.starts_with("#1/")) { 804 Format = K_BSD; 805 // We know this is BSD, so getName will work since there is no string table. 806 Expected<StringRef> NameOrErr = C->getName(); 807 if (!NameOrErr) { 808 Err = NameOrErr.takeError(); 809 return; 810 } 811 Name = NameOrErr.get(); 812 if (Name == "__.SYMDEF SORTED" || Name == "__.SYMDEF") { 813 // We know that the symbol table is not an external file, but we still 814 // must check any Expected<> return value. 815 Expected<StringRef> BufOrErr = C->getBuffer(); 816 if (!BufOrErr) { 817 Err = BufOrErr.takeError(); 818 return; 819 } 820 SymbolTable = BufOrErr.get(); 821 if (Increment()) 822 return; 823 } else if (Name == "__.SYMDEF_64 SORTED" || Name == "__.SYMDEF_64") { 824 Format = K_DARWIN64; 825 // We know that the symbol table is not an external file, but we still 826 // must check any Expected<> return value. 827 Expected<StringRef> BufOrErr = C->getBuffer(); 828 if (!BufOrErr) { 829 Err = BufOrErr.takeError(); 830 return; 831 } 832 SymbolTable = BufOrErr.get(); 833 if (Increment()) 834 return; 835 } 836 setFirstRegular(*C); 837 return; 838 } 839 840 // MIPS 64-bit ELF archives use a special format of a symbol table. 841 // This format is marked by `ar_name` field equals to "/SYM64/". 842 // For detailed description see page 96 in the following document: 843 // http://techpubs.sgi.com/library/manuals/4000/007-4658-001/pdf/007-4658-001.pdf 844 845 bool has64SymTable = false; 846 if (Name == "/" || Name == "/SYM64/") { 847 // We know that the symbol table is not an external file, but we still 848 // must check any Expected<> return value. 849 Expected<StringRef> BufOrErr = C->getBuffer(); 850 if (!BufOrErr) { 851 Err = BufOrErr.takeError(); 852 return; 853 } 854 SymbolTable = BufOrErr.get(); 855 if (Name == "/SYM64/") 856 has64SymTable = true; 857 858 if (Increment()) 859 return; 860 if (I == E) { 861 Err = Error::success(); 862 return; 863 } 864 Expected<StringRef> NameOrErr = C->getRawName(); 865 if (!NameOrErr) { 866 Err = NameOrErr.takeError(); 867 return; 868 } 869 Name = NameOrErr.get(); 870 } 871 872 if (Name == "//") { 873 Format = has64SymTable ? K_GNU64 : K_GNU; 874 // The string table is never an external member, but we still 875 // must check any Expected<> return value. 876 Expected<StringRef> BufOrErr = C->getBuffer(); 877 if (!BufOrErr) { 878 Err = BufOrErr.takeError(); 879 return; 880 } 881 StringTable = BufOrErr.get(); 882 if (Increment()) 883 return; 884 setFirstRegular(*C); 885 Err = Error::success(); 886 return; 887 } 888 889 if (Name[0] != '/') { 890 Format = has64SymTable ? K_GNU64 : K_GNU; 891 setFirstRegular(*C); 892 Err = Error::success(); 893 return; 894 } 895 896 if (Name != "/") { 897 Err = errorCodeToError(object_error::parse_failed); 898 return; 899 } 900 901 Format = K_COFF; 902 // We know that the symbol table is not an external file, but we still 903 // must check any Expected<> return value. 904 Expected<StringRef> BufOrErr = C->getBuffer(); 905 if (!BufOrErr) { 906 Err = BufOrErr.takeError(); 907 return; 908 } 909 SymbolTable = BufOrErr.get(); 910 911 if (Increment()) 912 return; 913 914 if (I == E) { 915 setFirstRegular(*C); 916 Err = Error::success(); 917 return; 918 } 919 920 NameOrErr = C->getRawName(); 921 if (!NameOrErr) { 922 Err = NameOrErr.takeError(); 923 return; 924 } 925 Name = NameOrErr.get(); 926 927 if (Name == "//") { 928 // The string table is never an external member, but we still 929 // must check any Expected<> return value. 930 Expected<StringRef> BufOrErr = C->getBuffer(); 931 if (!BufOrErr) { 932 Err = BufOrErr.takeError(); 933 return; 934 } 935 StringTable = BufOrErr.get(); 936 if (Increment()) 937 return; 938 939 if (I == E) { 940 setFirstRegular(*C); 941 Err = Error::success(); 942 return; 943 } 944 945 NameOrErr = C->getRawName(); 946 if (!NameOrErr) { 947 Err = NameOrErr.takeError(); 948 return; 949 } 950 Name = NameOrErr.get(); 951 } 952 953 if (Name == "/<ECSYMBOLS>/") { 954 // ARM64EC-aware libraries contain an additional special member with 955 // an EC symbol map after the string table. Its format is similar to a 956 // regular symbol map, except it doesn't contain member offsets. Its indexes 957 // refer to member offsets from the regular symbol table instead. 958 Expected<StringRef> BufOrErr = C->getBuffer(); 959 if (!BufOrErr) { 960 Err = BufOrErr.takeError(); 961 return; 962 } 963 ECSymbolTable = BufOrErr.get(); 964 if (Increment()) 965 return; 966 } 967 968 setFirstRegular(*C); 969 Err = Error::success(); 970 } 971 972 object::Archive::Kind Archive::getDefaultKindForTriple(Triple &T) { 973 if (T.isOSDarwin()) 974 return object::Archive::K_DARWIN; 975 if (T.isOSAIX()) 976 return object::Archive::K_AIXBIG; 977 if (T.isOSWindows()) 978 return object::Archive::K_COFF; 979 return object::Archive::K_GNU; 980 } 981 982 object::Archive::Kind Archive::getDefaultKind() { 983 Triple HostTriple(sys::getDefaultTargetTriple()); 984 return getDefaultKindForTriple(HostTriple); 985 } 986 987 Archive::child_iterator Archive::child_begin(Error &Err, 988 bool SkipInternal) const { 989 if (isEmpty()) 990 return child_end(); 991 992 if (SkipInternal) 993 return child_iterator::itr( 994 Child(this, FirstRegularData, FirstRegularStartOfFile), Err); 995 996 const char *Loc = Data.getBufferStart() + getFirstChildOffset(); 997 Child C(this, Loc, &Err); 998 if (Err) 999 return child_end(); 1000 return child_iterator::itr(C, Err); 1001 } 1002 1003 Archive::child_iterator Archive::child_end() const { 1004 return child_iterator::end(Child(nullptr, nullptr, nullptr)); 1005 } 1006 1007 bool Archive::Symbol::isECSymbol() const { 1008 // Symbols use SymbolCount..SymbolCount+getNumberOfECSymbols() for EC symbol 1009 // indexes. 1010 uint32_t SymbolCount = Parent->getNumberOfSymbols(); 1011 return SymbolCount <= SymbolIndex && 1012 SymbolIndex < SymbolCount + Parent->getNumberOfECSymbols(); 1013 } 1014 1015 StringRef Archive::Symbol::getName() const { 1016 if (isECSymbol()) 1017 return Parent->ECSymbolTable.begin() + StringIndex; 1018 return Parent->getSymbolTable().begin() + StringIndex; 1019 } 1020 1021 Expected<Archive::Child> Archive::Symbol::getMember() const { 1022 const char *Buf = Parent->getSymbolTable().begin(); 1023 const char *Offsets = Buf; 1024 if (Parent->kind() == K_GNU64 || Parent->kind() == K_DARWIN64 || 1025 Parent->kind() == K_AIXBIG) 1026 Offsets += sizeof(uint64_t); 1027 else 1028 Offsets += sizeof(uint32_t); 1029 uint64_t Offset = 0; 1030 if (Parent->kind() == K_GNU) { 1031 Offset = read32be(Offsets + SymbolIndex * 4); 1032 } else if (Parent->kind() == K_GNU64 || Parent->kind() == K_AIXBIG) { 1033 Offset = read64be(Offsets + SymbolIndex * 8); 1034 } else if (Parent->kind() == K_BSD) { 1035 // The SymbolIndex is an index into the ranlib structs that start at 1036 // Offsets (the first uint32_t is the number of bytes of the ranlib 1037 // structs). The ranlib structs are a pair of uint32_t's the first 1038 // being a string table offset and the second being the offset into 1039 // the archive of the member that defines the symbol. Which is what 1040 // is needed here. 1041 Offset = read32le(Offsets + SymbolIndex * 8 + 4); 1042 } else if (Parent->kind() == K_DARWIN64) { 1043 // The SymbolIndex is an index into the ranlib_64 structs that start at 1044 // Offsets (the first uint64_t is the number of bytes of the ranlib_64 1045 // structs). The ranlib_64 structs are a pair of uint64_t's the first 1046 // being a string table offset and the second being the offset into 1047 // the archive of the member that defines the symbol. Which is what 1048 // is needed here. 1049 Offset = read64le(Offsets + SymbolIndex * 16 + 8); 1050 } else { 1051 // Skip offsets. 1052 uint32_t MemberCount = read32le(Buf); 1053 Buf += MemberCount * 4 + 4; 1054 1055 uint32_t SymbolCount = read32le(Buf); 1056 uint16_t OffsetIndex; 1057 if (SymbolIndex < SymbolCount) { 1058 // Skip SymbolCount to get to the indices table. 1059 const char *Indices = Buf + 4; 1060 1061 // Get the index of the offset in the file member offset table for this 1062 // symbol. 1063 OffsetIndex = read16le(Indices + SymbolIndex * 2); 1064 } else if (isECSymbol()) { 1065 // Skip SymbolCount to get to the indices table. 1066 const char *Indices = Parent->ECSymbolTable.begin() + 4; 1067 1068 // Get the index of the offset in the file member offset table for this 1069 // symbol. 1070 OffsetIndex = read16le(Indices + (SymbolIndex - SymbolCount) * 2); 1071 } else { 1072 return errorCodeToError(object_error::parse_failed); 1073 } 1074 // Subtract 1 since OffsetIndex is 1 based. 1075 --OffsetIndex; 1076 1077 if (OffsetIndex >= MemberCount) 1078 return errorCodeToError(object_error::parse_failed); 1079 1080 Offset = read32le(Offsets + OffsetIndex * 4); 1081 } 1082 1083 const char *Loc = Parent->getData().begin() + Offset; 1084 Error Err = Error::success(); 1085 Child C(Parent, Loc, &Err); 1086 if (Err) 1087 return std::move(Err); 1088 return C; 1089 } 1090 1091 Archive::Symbol Archive::Symbol::getNext() const { 1092 Symbol t(*this); 1093 if (Parent->kind() == K_BSD) { 1094 // t.StringIndex is an offset from the start of the __.SYMDEF or 1095 // "__.SYMDEF SORTED" member into the string table for the ranlib 1096 // struct indexed by t.SymbolIndex . To change t.StringIndex to the 1097 // offset in the string table for t.SymbolIndex+1 we subtract the 1098 // its offset from the start of the string table for t.SymbolIndex 1099 // and add the offset of the string table for t.SymbolIndex+1. 1100 1101 // The __.SYMDEF or "__.SYMDEF SORTED" member starts with a uint32_t 1102 // which is the number of bytes of ranlib structs that follow. The ranlib 1103 // structs are a pair of uint32_t's the first being a string table offset 1104 // and the second being the offset into the archive of the member that 1105 // define the symbol. After that the next uint32_t is the byte count of 1106 // the string table followed by the string table. 1107 const char *Buf = Parent->getSymbolTable().begin(); 1108 uint32_t RanlibCount = 0; 1109 RanlibCount = read32le(Buf) / 8; 1110 // If t.SymbolIndex + 1 will be past the count of symbols (the RanlibCount) 1111 // don't change the t.StringIndex as we don't want to reference a ranlib 1112 // past RanlibCount. 1113 if (t.SymbolIndex + 1 < RanlibCount) { 1114 const char *Ranlibs = Buf + 4; 1115 uint32_t CurRanStrx = 0; 1116 uint32_t NextRanStrx = 0; 1117 CurRanStrx = read32le(Ranlibs + t.SymbolIndex * 8); 1118 NextRanStrx = read32le(Ranlibs + (t.SymbolIndex + 1) * 8); 1119 t.StringIndex -= CurRanStrx; 1120 t.StringIndex += NextRanStrx; 1121 } 1122 } else if (t.isECSymbol()) { 1123 // Go to one past next null. 1124 t.StringIndex = Parent->ECSymbolTable.find('\0', t.StringIndex) + 1; 1125 } else { 1126 // Go to one past next null. 1127 t.StringIndex = Parent->getSymbolTable().find('\0', t.StringIndex) + 1; 1128 } 1129 ++t.SymbolIndex; 1130 return t; 1131 } 1132 1133 Archive::symbol_iterator Archive::symbol_begin() const { 1134 if (!hasSymbolTable()) 1135 return symbol_iterator(Symbol(this, 0, 0)); 1136 1137 const char *buf = getSymbolTable().begin(); 1138 if (kind() == K_GNU) { 1139 uint32_t symbol_count = 0; 1140 symbol_count = read32be(buf); 1141 buf += sizeof(uint32_t) + (symbol_count * (sizeof(uint32_t))); 1142 } else if (kind() == K_GNU64) { 1143 uint64_t symbol_count = read64be(buf); 1144 buf += sizeof(uint64_t) + (symbol_count * (sizeof(uint64_t))); 1145 } else if (kind() == K_BSD) { 1146 // The __.SYMDEF or "__.SYMDEF SORTED" member starts with a uint32_t 1147 // which is the number of bytes of ranlib structs that follow. The ranlib 1148 // structs are a pair of uint32_t's the first being a string table offset 1149 // and the second being the offset into the archive of the member that 1150 // define the symbol. After that the next uint32_t is the byte count of 1151 // the string table followed by the string table. 1152 uint32_t ranlib_count = 0; 1153 ranlib_count = read32le(buf) / 8; 1154 const char *ranlibs = buf + 4; 1155 uint32_t ran_strx = 0; 1156 ran_strx = read32le(ranlibs); 1157 buf += sizeof(uint32_t) + (ranlib_count * (2 * (sizeof(uint32_t)))); 1158 // Skip the byte count of the string table. 1159 buf += sizeof(uint32_t); 1160 buf += ran_strx; 1161 } else if (kind() == K_DARWIN64) { 1162 // The __.SYMDEF_64 or "__.SYMDEF_64 SORTED" member starts with a uint64_t 1163 // which is the number of bytes of ranlib_64 structs that follow. The 1164 // ranlib_64 structs are a pair of uint64_t's the first being a string 1165 // table offset and the second being the offset into the archive of the 1166 // member that define the symbol. After that the next uint64_t is the byte 1167 // count of the string table followed by the string table. 1168 uint64_t ranlib_count = 0; 1169 ranlib_count = read64le(buf) / 16; 1170 const char *ranlibs = buf + 8; 1171 uint64_t ran_strx = 0; 1172 ran_strx = read64le(ranlibs); 1173 buf += sizeof(uint64_t) + (ranlib_count * (2 * (sizeof(uint64_t)))); 1174 // Skip the byte count of the string table. 1175 buf += sizeof(uint64_t); 1176 buf += ran_strx; 1177 } else if (kind() == K_AIXBIG) { 1178 buf = getStringTable().begin(); 1179 } else { 1180 uint32_t member_count = 0; 1181 uint32_t symbol_count = 0; 1182 member_count = read32le(buf); 1183 buf += 4 + (member_count * 4); // Skip offsets. 1184 symbol_count = read32le(buf); 1185 buf += 4 + (symbol_count * 2); // Skip indices. 1186 } 1187 uint32_t string_start_offset = buf - getSymbolTable().begin(); 1188 return symbol_iterator(Symbol(this, 0, string_start_offset)); 1189 } 1190 1191 Archive::symbol_iterator Archive::symbol_end() const { 1192 return symbol_iterator(Symbol(this, getNumberOfSymbols(), 0)); 1193 } 1194 1195 Expected<iterator_range<Archive::symbol_iterator>> Archive::ec_symbols() const { 1196 uint32_t Count = 0; 1197 1198 // Validate EC symbol table. 1199 if (!ECSymbolTable.empty()) { 1200 if (ECSymbolTable.size() < sizeof(uint32_t)) 1201 return malformedError("invalid EC symbols size (" + 1202 Twine(ECSymbolTable.size()) + ")"); 1203 if (SymbolTable.size() < sizeof(uint32_t)) 1204 return malformedError("invalid symbols size (" + 1205 Twine(ECSymbolTable.size()) + ")"); 1206 1207 Count = read32le(ECSymbolTable.begin()); 1208 size_t StringIndex = sizeof(uint32_t) + Count * sizeof(uint16_t); 1209 if (ECSymbolTable.size() < StringIndex) 1210 return malformedError("invalid EC symbols size. Size was " + 1211 Twine(ECSymbolTable.size()) + ", but expected " + 1212 Twine(StringIndex)); 1213 1214 uint32_t MemberCount = read32le(SymbolTable.begin()); 1215 const char *Indexes = ECSymbolTable.begin() + sizeof(uint32_t); 1216 1217 for (uint32_t i = 0; i < Count; ++i) { 1218 uint16_t Index = read16le(Indexes + i * sizeof(uint16_t)); 1219 if (!Index) 1220 return malformedError("invalid EC symbol index 0"); 1221 if (Index > MemberCount) 1222 return malformedError("invalid EC symbol index " + Twine(Index) + 1223 " is larger than member count " + 1224 Twine(MemberCount)); 1225 1226 StringIndex = ECSymbolTable.find('\0', StringIndex); 1227 if (StringIndex == StringRef::npos) 1228 return malformedError("malformed EC symbol names: not null-terminated"); 1229 ++StringIndex; 1230 } 1231 } 1232 1233 uint32_t SymbolCount = getNumberOfSymbols(); 1234 return make_range( 1235 symbol_iterator(Symbol(this, SymbolCount, 1236 sizeof(uint32_t) + Count * sizeof(uint16_t))), 1237 symbol_iterator(Symbol(this, SymbolCount + Count, 0))); 1238 } 1239 1240 uint32_t Archive::getNumberOfSymbols() const { 1241 if (!hasSymbolTable()) 1242 return 0; 1243 const char *buf = getSymbolTable().begin(); 1244 if (kind() == K_GNU) 1245 return read32be(buf); 1246 if (kind() == K_GNU64 || kind() == K_AIXBIG) 1247 return read64be(buf); 1248 if (kind() == K_BSD) 1249 return read32le(buf) / 8; 1250 if (kind() == K_DARWIN64) 1251 return read64le(buf) / 16; 1252 uint32_t member_count = 0; 1253 member_count = read32le(buf); 1254 buf += 4 + (member_count * 4); // Skip offsets. 1255 return read32le(buf); 1256 } 1257 1258 uint32_t Archive::getNumberOfECSymbols() const { 1259 if (ECSymbolTable.size() < sizeof(uint32_t)) 1260 return 0; 1261 return read32le(ECSymbolTable.begin()); 1262 } 1263 1264 Expected<std::optional<Archive::Child>> Archive::findSym(StringRef name) const { 1265 Archive::symbol_iterator bs = symbol_begin(); 1266 Archive::symbol_iterator es = symbol_end(); 1267 1268 for (; bs != es; ++bs) { 1269 StringRef SymName = bs->getName(); 1270 if (SymName == name) { 1271 if (auto MemberOrErr = bs->getMember()) 1272 return Child(*MemberOrErr); 1273 else 1274 return MemberOrErr.takeError(); 1275 } 1276 } 1277 return std::nullopt; 1278 } 1279 1280 // Returns true if archive file contains no member file. 1281 bool Archive::isEmpty() const { 1282 return Data.getBufferSize() == getArchiveMagicLen(); 1283 } 1284 1285 bool Archive::hasSymbolTable() const { return !SymbolTable.empty(); } 1286 1287 static Error getGlobalSymtabLocAndSize(const MemoryBufferRef &Data, 1288 uint64_t GlobalSymtabOffset, 1289 const char *&GlobalSymtabLoc, 1290 uint64_t &Size, const char *BitMessage) { 1291 uint64_t BufferSize = Data.getBufferSize(); 1292 uint64_t GlobalSymtabContentOffset = 1293 GlobalSymtabOffset + sizeof(BigArMemHdrType); 1294 if (GlobalSymtabContentOffset > BufferSize) 1295 return malformedError( 1296 Twine(BitMessage) + " global symbol table header at offset 0x" + 1297 Twine::utohexstr(GlobalSymtabOffset) + " and size 0x" + 1298 Twine::utohexstr(sizeof(BigArMemHdrType)) + 1299 " goes past the end of file"); 1300 1301 GlobalSymtabLoc = Data.getBufferStart() + GlobalSymtabOffset; 1302 const BigArMemHdrType *GlobalSymHdr = 1303 reinterpret_cast<const BigArMemHdrType *>(GlobalSymtabLoc); 1304 StringRef RawOffset = getFieldRawString(GlobalSymHdr->Size); 1305 if (RawOffset.getAsInteger(10, Size)) 1306 return malformedError(Twine(BitMessage) + " global symbol table size \"" + 1307 RawOffset + "\" is not a number"); 1308 1309 if (GlobalSymtabContentOffset + Size > BufferSize) 1310 return malformedError( 1311 Twine(BitMessage) + " global symbol table content at offset 0x" + 1312 Twine::utohexstr(GlobalSymtabContentOffset) + " and size 0x" + 1313 Twine::utohexstr(Size) + " goes past the end of file"); 1314 1315 return Error::success(); 1316 } 1317 1318 struct GlobalSymtabInfo { 1319 uint64_t SymNum; 1320 StringRef SymbolTable; 1321 StringRef SymbolOffsetTable; 1322 StringRef StringTable; 1323 }; 1324 1325 static void 1326 appendGlobalSymbolTableInfo(SmallVector<GlobalSymtabInfo> &SymtabInfos, 1327 const char *GlobalSymtabLoc, uint64_t Size) { 1328 // In a big archive, a global symbol table contains the following information: 1329 // - The number of symbols. 1330 // - The array of offsets into the archive file. The length is eight 1331 // times the number of symbols. 1332 // - The name-string table. The size is: 1333 // Size-(8*(the number of symbols + 1)). 1334 1335 StringRef SymbolTable = 1336 StringRef(GlobalSymtabLoc + sizeof(BigArMemHdrType), Size); 1337 uint64_t SymNum = read64be(GlobalSymtabLoc + sizeof(BigArMemHdrType)); 1338 StringRef SymbolOffsetTable = StringRef(SymbolTable.data() + 8, 8 * SymNum); 1339 unsigned SymOffsetsSize = 8 * (SymNum + 1); 1340 uint64_t SymbolTableStringSize = Size - SymOffsetsSize; 1341 StringRef StringTable = 1342 StringRef(SymbolTable.data() + SymOffsetsSize, SymbolTableStringSize); 1343 SymtabInfos.push_back({SymNum, SymbolTable, SymbolOffsetTable, StringTable}); 1344 } 1345 1346 BigArchive::BigArchive(MemoryBufferRef Source, Error &Err) 1347 : Archive(Source, Err) { 1348 ErrorAsOutParameter ErrAsOutParam(&Err); 1349 StringRef Buffer = Data.getBuffer(); 1350 ArFixLenHdr = reinterpret_cast<const FixLenHdr *>(Buffer.data()); 1351 uint64_t BufferSize = Data.getBufferSize(); 1352 1353 if (BufferSize < sizeof(FixLenHdr)) { 1354 Err = malformedError("malformed AIX big archive: incomplete fixed length " 1355 "header, the archive is only" + 1356 Twine(BufferSize) + " byte(s)"); 1357 return; 1358 } 1359 1360 StringRef RawOffset = getFieldRawString(ArFixLenHdr->FirstChildOffset); 1361 if (RawOffset.getAsInteger(10, FirstChildOffset)) 1362 // TODO: Out-of-line. 1363 Err = malformedError("malformed AIX big archive: first member offset \"" + 1364 RawOffset + "\" is not a number"); 1365 1366 RawOffset = getFieldRawString(ArFixLenHdr->LastChildOffset); 1367 if (RawOffset.getAsInteger(10, LastChildOffset)) 1368 // TODO: Out-of-line. 1369 Err = malformedError("malformed AIX big archive: last member offset \"" + 1370 RawOffset + "\" is not a number"); 1371 1372 uint64_t GlobSymtab32Offset = 0; 1373 RawOffset = getFieldRawString(ArFixLenHdr->GlobSymOffset); 1374 if (RawOffset.getAsInteger(10, GlobSymtab32Offset)) { 1375 Err = malformedError("global symbol table " 1376 "offset of 32-bit members \"" + 1377 RawOffset + "\" is not a number"); 1378 return; 1379 } 1380 1381 uint64_t GlobSymtab64Offset = 0; 1382 RawOffset = getFieldRawString(ArFixLenHdr->GlobSym64Offset); 1383 if (RawOffset.getAsInteger(10, GlobSymtab64Offset)) { 1384 Err = malformedError("global symbol table " 1385 "offset of 64-bit members\"" + 1386 RawOffset + "\" is not a number"); 1387 return; 1388 } 1389 1390 const char *GlobSymtab32Loc = nullptr; 1391 const char *GlobSymtab64Loc = nullptr; 1392 uint64_t GlobSymtab32Size = 0; 1393 uint64_t GlobSymtab64Size = 0; 1394 const MemoryBufferRef &MemBuffRef = getMemoryBufferRef(); 1395 1396 if (GlobSymtab32Offset) { 1397 Err = 1398 getGlobalSymtabLocAndSize(MemBuffRef, GlobSymtab32Offset, 1399 GlobSymtab32Loc, GlobSymtab32Size, "32-bit"); 1400 if (Err) 1401 return; 1402 1403 Has32BitGlobalSymtab = true; 1404 } 1405 1406 if (GlobSymtab64Offset) { 1407 Err = 1408 getGlobalSymtabLocAndSize(MemBuffRef, GlobSymtab64Offset, 1409 GlobSymtab64Loc, GlobSymtab64Size, "64-bit"); 1410 if (Err) 1411 return; 1412 1413 Has64BitGlobalSymtab = true; 1414 } 1415 1416 SmallVector<GlobalSymtabInfo> SymtabInfos; 1417 1418 if (GlobSymtab32Offset) 1419 appendGlobalSymbolTableInfo(SymtabInfos, GlobSymtab32Loc, GlobSymtab32Size); 1420 if (GlobSymtab64Offset) 1421 appendGlobalSymbolTableInfo(SymtabInfos, GlobSymtab64Loc, GlobSymtab64Size); 1422 1423 if (SymtabInfos.size() == 1) { 1424 SymbolTable = SymtabInfos[0].SymbolTable; 1425 StringTable = SymtabInfos[0].StringTable; 1426 } else if (SymtabInfos.size() == 2) { 1427 // In order to let the Archive::Symbol::getNext() work for both 32-bit and 1428 // 64-bit global symbol tables, we need to merge them into a single table. 1429 raw_string_ostream Out(MergedGlobalSymtabBuf); 1430 uint64_t SymNum = SymtabInfos[0].SymNum + SymtabInfos[1].SymNum; 1431 write(Out, SymNum, llvm::endianness::big); 1432 // Merge symbol offset. 1433 Out << SymtabInfos[0].SymbolOffsetTable; 1434 Out << SymtabInfos[1].SymbolOffsetTable; 1435 // Merge string table. 1436 Out << SymtabInfos[0].StringTable; 1437 Out << SymtabInfos[1].StringTable; 1438 SymbolTable = MergedGlobalSymtabBuf; 1439 // The size of the symbol offset to the member file is 8 bytes. 1440 StringTable = StringRef(SymbolTable.begin() + (SymNum + 1) * 8, 1441 SymtabInfos[0].StringTable.size() + 1442 SymtabInfos[1].StringTable.size()); 1443 } 1444 1445 child_iterator I = child_begin(Err, false); 1446 if (Err) 1447 return; 1448 child_iterator E = child_end(); 1449 if (I == E) { 1450 Err = Error::success(); 1451 return; 1452 } 1453 setFirstRegular(*I); 1454 Err = Error::success(); 1455 } 1456