[llvm] r240339 - [Object] Search for architecures by name in MachOUniversalBinary::getObjectForArch()

Frederic Riss friss at apple.com
Mon Jun 22 14:33:25 PDT 2015


Author: friss
Date: Mon Jun 22 16:33:24 2015
New Revision: 240339

URL: http://llvm.org/viewvc/llvm-project?rev=240339&view=rev
Log:
[Object] Search for architecures by name in MachOUniversalBinary::getObjectForArch()

The reason we need to search by name rather than by Triple::ArchType
is to handle subarchitecture correclty. There is no different ArchType
for the x86_64h architecture (it identifies itself as x86_64), or for
the various ARM subarches. The only way to get to the subarch slice
in an universal binary is to search by name.

This issue led to hard to debug and transient symbolication failures
in Asan tests (it mostly works, because the files are very similar).

This also affects the Profiling infrastucture as it is the other user
of that API.

Reviewers: samsonov, bogner

Subscribers: llvm-commits

Differential Revision: http://reviews.llvm.org/D10604

Added:
    llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.c
    llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.o
    llvm/trunk/test/tools/llvm-symbolizer/fat.test
Modified:
    llvm/trunk/include/llvm/Object/MachOUniversal.h
    llvm/trunk/include/llvm/ProfileData/CoverageMapping.h
    llvm/trunk/include/llvm/ProfileData/CoverageMappingReader.h
    llvm/trunk/lib/Object/MachOUniversal.cpp
    llvm/trunk/lib/ProfileData/CoverageMapping.cpp
    llvm/trunk/lib/ProfileData/CoverageMappingReader.cpp
    llvm/trunk/tools/llvm-cov/CodeCoverage.cpp
    llvm/trunk/tools/llvm-symbolizer/LLVMSymbolize.cpp

Modified: llvm/trunk/include/llvm/Object/MachOUniversal.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Object/MachOUniversal.h?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/include/llvm/Object/MachOUniversal.h (original)
+++ llvm/trunk/include/llvm/Object/MachOUniversal.h Mon Jun 22 16:33:24 2015
@@ -109,7 +109,7 @@ public:
   }
 
   ErrorOr<std::unique_ptr<MachOObjectFile>>
-  getObjectForArch(Triple::ArchType Arch) const;
+  getObjectForArch(StringRef ArchName) const;
 };
 
 } // namespace object

Modified: llvm/trunk/include/llvm/ProfileData/CoverageMapping.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ProfileData/CoverageMapping.h?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/include/llvm/ProfileData/CoverageMapping.h (original)
+++ llvm/trunk/include/llvm/ProfileData/CoverageMapping.h Mon Jun 22 16:33:24 2015
@@ -410,7 +410,7 @@ public:
   /// \brief Load the coverage mapping from the given files.
   static ErrorOr<std::unique_ptr<CoverageMapping>>
   load(StringRef ObjectFilename, StringRef ProfileFilename,
-       Triple::ArchType Arch = Triple::ArchType::UnknownArch);
+       StringRef Arch = StringRef());
 
   /// \brief The number of functions that couldn't have their profiles mapped.
   ///

Modified: llvm/trunk/include/llvm/ProfileData/CoverageMappingReader.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ProfileData/CoverageMappingReader.h?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/include/llvm/ProfileData/CoverageMappingReader.h (original)
+++ llvm/trunk/include/llvm/ProfileData/CoverageMappingReader.h Mon Jun 22 16:33:24 2015
@@ -171,7 +171,7 @@ private:
 public:
   static ErrorOr<std::unique_ptr<BinaryCoverageReader>>
   create(std::unique_ptr<MemoryBuffer> &ObjectBuffer,
-         Triple::ArchType Arch = Triple::ArchType::UnknownArch);
+         StringRef Arch);
 
   std::error_code readNextRecord(CoverageMappingRecord &Record) override;
 };

Modified: llvm/trunk/lib/Object/MachOUniversal.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Object/MachOUniversal.cpp?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/lib/Object/MachOUniversal.cpp (original)
+++ llvm/trunk/lib/Object/MachOUniversal.cpp Mon Jun 22 16:33:24 2015
@@ -123,25 +123,13 @@ MachOUniversalBinary::MachOUniversalBina
   ec = std::error_code();
 }
 
-static bool getCTMForArch(Triple::ArchType Arch, MachO::CPUType &CTM) {
-  switch (Arch) {
-    case Triple::x86:    CTM = MachO::CPU_TYPE_I386; return true;
-    case Triple::x86_64: CTM = MachO::CPU_TYPE_X86_64; return true;
-    case Triple::arm:    CTM = MachO::CPU_TYPE_ARM; return true;
-    case Triple::sparc:  CTM = MachO::CPU_TYPE_SPARC; return true;
-    case Triple::ppc:    CTM = MachO::CPU_TYPE_POWERPC; return true;
-    case Triple::ppc64:  CTM = MachO::CPU_TYPE_POWERPC64; return true;
-    default: return false;
-  }
-}
-
 ErrorOr<std::unique_ptr<MachOObjectFile>>
-MachOUniversalBinary::getObjectForArch(Triple::ArchType Arch) const {
-  MachO::CPUType CTM;
-  if (!getCTMForArch(Arch, CTM))
+MachOUniversalBinary::getObjectForArch(StringRef ArchName) const {
+  if (Triple(ArchName).getArch() == Triple::ArchType::UnknownArch)
     return object_error::arch_not_found;
+
   for (object_iterator I = begin_objects(), E = end_objects(); I != E; ++I) {
-    if (I->getCPUType() == static_cast<uint32_t>(CTM))
+    if (I->getArchTypeName() == ArchName)
       return I->getAsObjectFile();
   }
   return object_error::arch_not_found;

Modified: llvm/trunk/lib/ProfileData/CoverageMapping.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ProfileData/CoverageMapping.cpp?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/lib/ProfileData/CoverageMapping.cpp (original)
+++ llvm/trunk/lib/ProfileData/CoverageMapping.cpp Mon Jun 22 16:33:24 2015
@@ -236,7 +236,7 @@ CoverageMapping::load(CoverageMappingRea
 
 ErrorOr<std::unique_ptr<CoverageMapping>>
 CoverageMapping::load(StringRef ObjectFilename, StringRef ProfileFilename,
-                      Triple::ArchType Arch) {
+                      StringRef Arch) {
   auto CounterMappingBuff = MemoryBuffer::getFileOrSTDIN(ObjectFilename);
   if (std::error_code EC = CounterMappingBuff.getError())
     return EC;

Modified: llvm/trunk/lib/ProfileData/CoverageMappingReader.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ProfileData/CoverageMappingReader.cpp?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/lib/ProfileData/CoverageMappingReader.cpp (original)
+++ llvm/trunk/lib/ProfileData/CoverageMappingReader.cpp Mon Jun 22 16:33:24 2015
@@ -448,7 +448,7 @@ static std::error_code loadBinaryFormat(
                                         StringRef &CoverageMapping,
                                         uint8_t &BytesInAddress,
                                         support::endianness &Endian,
-                                        Triple::ArchType Arch) {
+                                        StringRef Arch) {
   auto BinOrErr = object::createBinary(ObjectBuffer);
   if (std::error_code EC = BinOrErr.getError())
     return EC;
@@ -465,7 +465,7 @@ static std::error_code loadBinaryFormat(
     // For any other object file, upcast and take ownership.
     OF.reset(cast<object::ObjectFile>(Bin.release()));
     // If we've asked for a particular arch, make sure they match.
-    if (Arch != Triple::ArchType::UnknownArch && OF->getArch() != Arch)
+    if (!Arch.empty() && OF->getArch() != Triple(Arch).getArch())
       return object_error::arch_not_found;
   } else
     // We can only handle object files.
@@ -495,7 +495,7 @@ static std::error_code loadBinaryFormat(
 
 ErrorOr<std::unique_ptr<BinaryCoverageReader>>
 BinaryCoverageReader::create(std::unique_ptr<MemoryBuffer> &ObjectBuffer,
-                             Triple::ArchType Arch) {
+                             StringRef Arch) {
   std::unique_ptr<BinaryCoverageReader> Reader(new BinaryCoverageReader());
 
   SectionData Profile;

Added: llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.c
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.c?rev=240339&view=auto
==============================================================================
--- llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.c (added)
+++ llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.c Mon Jun 22 16:33:24 2015
@@ -0,0 +1,15 @@
+/* Compile with:
+   clang -arch armv7 -arch armv7m -arch armv7em -arch x86_64 -arch x86_64h -c
+*/
+
+#ifdef __x86_64h__
+void x86_64h_function() {}
+#elif defined(__x86_64__)
+void x86_64_function() {}
+#elif defined(__ARM_ARCH_7EM__)
+void armv7em_function() {}
+#elif defined(__ARM_ARCH_7M__)
+void armv7m_function() {}
+#elif defined(__ARM_ARCH_7A__)
+void armv7_function() {}
+#endif

Added: llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.o
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.o?rev=240339&view=auto
==============================================================================
Binary files llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.o (added) and llvm/trunk/test/tools/llvm-symbolizer/Inputs/fat.o Mon Jun 22 16:33:24 2015 differ

Added: llvm/trunk/test/tools/llvm-symbolizer/fat.test
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-symbolizer/fat.test?rev=240339&view=auto
==============================================================================
--- llvm/trunk/test/tools/llvm-symbolizer/fat.test (added)
+++ llvm/trunk/test/tools/llvm-symbolizer/fat.test Mon Jun 22 16:33:24 2015
@@ -0,0 +1,11 @@
+RUN: echo 0 | llvm-symbolizer -obj=%p/Inputs/fat.o -default-arch=x86_64 | FileCheck --check-prefix=X86_64 %s
+RUN: echo 0 | llvm-symbolizer -obj=%p/Inputs/fat.o -default-arch=x86_64h | FileCheck --check-prefix=X86_64H %s
+RUN: echo 0 | llvm-symbolizer -obj=%p/Inputs/fat.o -default-arch=armv7 | FileCheck --check-prefix=ARMV7 %s
+RUN: echo 0 | llvm-symbolizer -obj=%p/Inputs/fat.o -default-arch=armv7em | FileCheck --check-prefix=ARMV7EM %s
+RUN: echo 0 | llvm-symbolizer -obj=%p/Inputs/fat.o -default-arch=armv7m | FileCheck --check-prefix=ARMV7M %s
+
+X86_64: x86_64_function
+X86_64H: x86_64h_function
+ARMV7: armv7_function
+ARMV7EM: armv7em_function
+ARMV7M: armv7m_function

Modified: llvm/trunk/tools/llvm-cov/CodeCoverage.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-cov/CodeCoverage.cpp?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/tools/llvm-cov/CodeCoverage.cpp (original)
+++ llvm/trunk/tools/llvm-cov/CodeCoverage.cpp Mon Jun 22 16:33:24 2015
@@ -89,7 +89,7 @@ public:
       LoadedSourceFiles;
   bool CompareFilenamesOnly;
   StringMap<std::string> RemappedFilenames;
-  llvm::Triple::ArchType CoverageArch;
+  std::string CoverageArch;
 };
 }
 
@@ -349,15 +349,12 @@ int CodeCoverageTool::run(Command Cmd, i
       Filters.push_back(std::unique_ptr<CoverageFilter>(StatFilterer));
     }
 
-    if (Arch.empty())
-      CoverageArch = llvm::Triple::ArchType::UnknownArch;
-    else {
-      CoverageArch = Triple(Arch).getArch();
-      if (CoverageArch == llvm::Triple::ArchType::UnknownArch) {
-        errs() << "error: Unknown architecture: " << Arch << "\n";
-        return 1;
-      }
+    if (!Arch.empty() &&
+        Triple(Arch).getArch() == llvm::Triple::ArchType::UnknownArch) {
+      errs() << "error: Unknown architecture: " << Arch << "\n";
+      return 1;
     }
+    CoverageArch = Arch;
 
     for (const auto &File : InputSourceFiles) {
       SmallString<128> Path(File);

Modified: llvm/trunk/tools/llvm-symbolizer/LLVMSymbolize.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-symbolizer/LLVMSymbolize.cpp?rev=240339&r1=240338&r2=240339&view=diff
==============================================================================
--- llvm/trunk/tools/llvm-symbolizer/LLVMSymbolize.cpp (original)
+++ llvm/trunk/tools/llvm-symbolizer/LLVMSymbolize.cpp Mon Jun 22 16:33:24 2015
@@ -436,7 +436,7 @@ LLVMSymbolizer::getObjectFileFromBinary(
     if (I != ObjectFileForArch.end())
       return I->second;
     ErrorOr<std::unique_ptr<ObjectFile>> ParsedObj =
-        UB->getObjectForArch(Triple(ArchName).getArch());
+        UB->getObjectForArch(ArchName);
     if (ParsedObj) {
       Res = ParsedObj.get().get();
       ParsedBinariesAndObjects.push_back(std::move(ParsedObj.get()));





More information about the llvm-commits mailing list