[PATCH] D124865: [AIX] support read global symbol of big archive

Digger Lin via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Tue May 3 10:33:27 PDT 2022


DiggerLin created this revision.
DiggerLin added reviewers: jhenderson, Esme, hubert.reinterpretcast, MaskRay.
Herald added subscribers: StephenFan, rupprecht, hiraditya.
Herald added a project: All.
DiggerLin requested review of this revision.
Herald added a project: LLVM.
Herald added a subscriber: llvm-commits.

Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D124865

Files:
  llvm/include/llvm/Object/Archive.h
  llvm/lib/Object/Archive.cpp
  llvm/test/tools/llvm-ar/delete.test


Index: llvm/test/tools/llvm-ar/delete.test
===================================================================
--- llvm/test/tools/llvm-ar/delete.test
+++ llvm/test/tools/llvm-ar/delete.test
@@ -1,4 +1,3 @@
-# XFAIL: system-aix
 ## Test the deletion of members and that symbols are removed from the symbol table.
 
 # RUN: yaml2obj %s -o %t-delete.o --docnum=1
Index: llvm/lib/Object/Archive.cpp
===================================================================
--- llvm/lib/Object/Archive.cpp
+++ llvm/lib/Object/Archive.cpp
@@ -952,14 +952,15 @@
 Expected<Archive::Child> Archive::Symbol::getMember() const {
   const char *Buf = Parent->getSymbolTable().begin();
   const char *Offsets = Buf;
-  if (Parent->kind() == K_GNU64 || Parent->kind() == K_DARWIN64)
+  if (Parent->kind() == K_GNU64 || Parent->kind() == K_DARWIN64 ||
+      Parent->kind() == K_AIXBIG)
     Offsets += sizeof(uint64_t);
   else
     Offsets += sizeof(uint32_t);
   uint64_t Offset = 0;
   if (Parent->kind() == K_GNU) {
     Offset = read32be(Offsets + SymbolIndex * 4);
-  } else if (Parent->kind() == K_GNU64) {
+  } else if (Parent->kind() == K_GNU64 || Parent->kind() == K_AIXBIG) {
     Offset = read64be(Offsets + SymbolIndex * 8);
   } else if (Parent->kind() == K_BSD) {
     // The SymbolIndex is an index into the ranlib structs that start at
@@ -1092,7 +1093,9 @@
     // Skip the byte count of the string table.
     buf += sizeof(uint64_t);
     buf += ran_strx;
-  } else {
+  } else if (kind() == K_AIXBIG)
+    buf = getStringTable().begin();
+  else {
     uint32_t member_count = 0;
     uint32_t symbol_count = 0;
     member_count = read32le(buf);
@@ -1114,7 +1117,7 @@
   const char *buf = getSymbolTable().begin();
   if (kind() == K_GNU)
     return read32be(buf);
-  if (kind() == K_GNU64)
+  if (kind() == K_GNU64 || kind() == K_AIXBIG)
     return read64be(buf);
   if (kind() == K_BSD)
     return read32le(buf) / 8;
@@ -1167,6 +1170,31 @@
     Err = malformedError("malformed AIX big archive: last member offset \"" +
                          RawOffset + "\" is not a number");
 
+  // Calculate the global symbol table.
+  uint64_t GlobSymOffset = 0;
+  RawOffset = getFieldRawString(ArFixLenHdr->GlobSymOffset);
+  if (RawOffset.getAsInteger(10, GlobSymOffset))
+    Err = malformedError(
+        "malformed AIX big archive: global symbol tables offset \"" +
+        RawOffset + "\" is not a number");
+  if (GlobSymOffset > 0) {
+    const char *GlobSymTblLoc = Data.getBufferStart() + GlobSymOffset;
+    const BigArMemHdrType *GlobalSymHdr =
+        reinterpret_cast<const BigArMemHdrType *>(GlobSymTblLoc);
+    RawOffset = getFieldRawString(GlobalSymHdr->Size);
+    uint64_t Size;
+    if (RawOffset.getAsInteger(10, Size))
+      Err = malformedError(
+          "malformed AIX big archive: global symbol tables size \"" +
+          RawOffset + "\" is not a number");
+    SymbolTable = StringRef(GlobSymTblLoc + sizeof(BigArMemHdrType), Size);
+    unsigned SymNum = getNumberOfSymbols();
+    uint64_t SymbolTableStringSize = Size - 8 * (SymNum + 1);
+    StringTable =
+        StringRef(GlobSymTblLoc + sizeof(BigArMemHdrType) + 8 * (SymNum + 1),
+                  SymbolTableStringSize);
+  }
+
   child_iterator I = child_begin(Err, false);
   if (Err)
     return;
Index: llvm/include/llvm/Object/Archive.h
===================================================================
--- llvm/include/llvm/Object/Archive.h
+++ llvm/include/llvm/Object/Archive.h
@@ -378,10 +378,10 @@
   uint64_t getArchiveMagicLen() const;
   void setFirstRegular(const Child &C);
 
-private:
   StringRef SymbolTable;
   StringRef StringTable;
 
+private:
   StringRef FirstRegularData;
   uint16_t FirstRegularStartOfFile = -1;
 


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D124865.426765.patch
Type: text/x-patch
Size: 3738 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20220503/d9e44459/attachment.bin>


More information about the llvm-commits mailing list