[llvm] db06088 - [llvm-ifs] Add option to use InterfaceStub library

Haowei Wu via llvm-commits llvm-commits at lists.llvm.org
Thu Mar 4 11:29:51 PST 2021


Author: Haowei Wu
Date: 2021-03-04T11:28:49-08:00
New Revision: db06088d63f823e5a4894eea291baf5a449ed406

URL: https://github.com/llvm/llvm-project/commit/db06088d63f823e5a4894eea291baf5a449ed406
DIFF: https://github.com/llvm/llvm-project/commit/db06088d63f823e5a4894eea291baf5a449ed406.diff

LOG: [llvm-ifs] Add option to use InterfaceStub library

This change adds '-use-interfacestub' option to allow llvm-ifs
to use InterfaceStub lib when generating ELF binary.

Differential Revision: https://reviews.llvm.org/D94461

Added: 
    

Modified: 
    llvm/test/tools/llvm-ifs/func.ifs
    llvm/tools/llvm-ifs/CMakeLists.txt
    llvm/tools/llvm-ifs/llvm-ifs.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/test/tools/llvm-ifs/func.ifs b/llvm/test/tools/llvm-ifs/func.ifs
index 6a5aede21e25..e4844920bd18 100644
--- a/llvm/test/tools/llvm-ifs/func.ifs
+++ b/llvm/test/tools/llvm-ifs/func.ifs
@@ -4,6 +4,9 @@
 # RUN: llvm-ifs -action write-bin -o - %s %S/object.ifs | \
 # RUN: llvm-readelf --all - | FileCheck %s --check-prefixes=CHECK-ELF
 
+# RUN: llvm-ifs -action write-bin -o - %s %S/object.ifs -use-interfacestub | \
+# RUN: llvm-readelf --all - | FileCheck %s --check-prefixes=CHECK-ELF
+
 # RUN: llvm-ifs -action write-bin -force-format TBD -o - %s %S/object.ifs | \
 # RUN: FileCheck %s --check-prefixes=CHECK-DARWIN-TBD3
 

diff  --git a/llvm/tools/llvm-ifs/CMakeLists.txt b/llvm/tools/llvm-ifs/CMakeLists.txt
index 544b0e41a5ed..456f88d2b761 100644
--- a/llvm/tools/llvm-ifs/CMakeLists.txt
+++ b/llvm/tools/llvm-ifs/CMakeLists.txt
@@ -1,4 +1,5 @@
 set(LLVM_LINK_COMPONENTS
+  InterfaceStub
   Object
   Support
   TextAPI

diff  --git a/llvm/tools/llvm-ifs/llvm-ifs.cpp b/llvm/tools/llvm-ifs/llvm-ifs.cpp
index 4d9a5c365a78..5eda7082a897 100644
--- a/llvm/tools/llvm-ifs/llvm-ifs.cpp
+++ b/llvm/tools/llvm-ifs/llvm-ifs.cpp
@@ -9,6 +9,7 @@
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/StringSwitch.h"
 #include "llvm/ADT/Triple.h"
+#include "llvm/InterfaceStub/ELFObjHandler.h"
 #include "llvm/ObjectYAML/yaml2obj.h"
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/Debug.h"
@@ -54,6 +55,11 @@ static cl::list<std::string> InputFilenames(cl::Positional,
 static cl::opt<std::string> OutputFilename("o", cl::desc("<output file>"),
                                            cl::value_desc("path"));
 
+static cl::opt<bool> UseInterfaceStub(
+    "use-interfacestub",
+    cl::desc("Write output ELF file using latest InterfaceStub backend"),
+    cl::init(false));
+
 enum class IFSSymbolType {
   NoType = 0,
   Object,
@@ -342,16 +348,82 @@ static int writeElfStub(const Triple &T, const std::vector<IFSSymbol> &Symbols,
   return convertYAML(YIn, Out, ErrHandler) ? 0 : 1;
 }
 
-static int writeIfso(const IFSStub &Stub, bool IsWriteIfs, raw_ostream &Out) {
+static elfabi::ELFTarget convertIFSStub(const IFSStub &IfsStub,
+                                        elfabi::ELFStub &ElfStub) {
+  ElfStub.TbeVersion = IfsStub.IfsVersion;
+  ElfStub.SoName = IfsStub.SOName;
+  // TODO: Support more archs and targets.
+  Triple IFSTriple(IfsStub.Triple);
+  elfabi::ELFTarget Target = elfabi::ELFTarget::ELF64LE;
+  switch (IFSTriple.getArch()) {
+  case Triple::ArchType::aarch64:
+    ElfStub.Arch = (elfabi::ELFArch)ELF::EM_AARCH64;
+    break;
+  case Triple::ArchType::x86_64:
+    ElfStub.Arch = (elfabi::ELFArch)ELF::EM_X86_64;
+    break;
+  default:
+    ElfStub.Arch = (elfabi::ELFArch)ELF::EM_NONE;
+  }
+  ElfStub.NeededLibs = IfsStub.NeededLibs;
+  for (const IFSSymbol &IfsSymbol : IfsStub.Symbols) {
+    elfabi::ELFSymbol ElfSymbol(IfsSymbol.Name);
+    switch (IfsSymbol.Type) {
+    case IFSSymbolType::Func:
+      ElfSymbol.Type = elfabi::ELFSymbolType::Func;
+      break;
+    case IFSSymbolType::NoType:
+      ElfSymbol.Type = elfabi::ELFSymbolType::NoType;
+      break;
+    case IFSSymbolType::Object:
+      ElfSymbol.Type = elfabi::ELFSymbolType::Object;
+      break;
+    default:
+      ElfSymbol.Type = elfabi::ELFSymbolType::Unknown;
+      break;
+      // TODO: Add support for TLS?
+    }
+    ElfSymbol.Size = IfsSymbol.Size;
+    ElfSymbol.Undefined = false;
+    ElfSymbol.Weak = IfsSymbol.Weak;
+    ElfSymbol.Warning = IfsSymbol.Warning;
+    ElfStub.Symbols.insert(ElfSymbol);
+  }
+  return Target;
+}
+
+static int writeIfso(const IFSStub &Stub, bool IsWriteIfs) {
+  std::string ObjectFileFormat =
+      ForceFormat.empty() ? Stub.ObjectFileFormat : ForceFormat;
+
+  // Use InterfaceStub library if the option is enabled and output
+  // format is ELF.
+  if (UseInterfaceStub && (!IsWriteIfs) && ObjectFileFormat != "TBD") {
+    elfabi::ELFStub ElfStub;
+    elfabi::ELFTarget Target = convertIFSStub(Stub, ElfStub);
+    Error BinaryWriteError =
+        elfabi::writeBinaryStub(OutputFilename, ElfStub, Target);
+    if (BinaryWriteError) {
+      return -1;
+    }
+    return 0;
+  }
+
+  // Open file for writing.
+  std::error_code SysErr;
+  raw_fd_ostream Out(OutputFilename, SysErr);
+  if (SysErr) {
+    WithColor::error() << "Couldn't open " << OutputFilename
+                       << " for writing.\n";
+    return -1;
+  }
+
   if (IsWriteIfs) {
     yaml::Output YamlOut(Out, NULL, /*WrapColumn =*/0);
     YamlOut << const_cast<IFSStub &>(Stub);
     return 0;
   }
 
-  std::string ObjectFileFormat =
-      ForceFormat.empty() ? Stub.ObjectFileFormat : ForceFormat;
-
   if (ObjectFileFormat == "ELF" || ForceFormat == "ELFOBJYAML")
     return writeElfStub(llvm::Triple(Stub.Triple), Stub.Symbols,
                         Stub.ObjectFileFormat, Out);
@@ -498,15 +570,5 @@ int main(int argc, char *argv[]) {
   for (auto &Entry : SymbolMap)
     Stub.Symbols.push_back(Entry.second);
 
-  std::error_code SysErr;
-
-  // Open file for writing.
-  raw_fd_ostream Out(OutputFilename, SysErr);
-  if (SysErr) {
-    WithColor::error() << "Couldn't open " << OutputFilename
-                       << " for writing.\n";
-    return -1;
-  }
-
-  return writeIfso(Stub, (Action == "write-ifs"), Out);
+  return writeIfso(Stub, (Action == "write-ifs"));
 }


        


More information about the llvm-commits mailing list