[llvm] [SystemZ][z/OS] Add goffdumper/llvm-readobj tools (PR #71071)
via llvm-commits
llvm-commits at lists.llvm.org
Thu Nov 2 08:59:20 PDT 2023
llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-llvm-binary-utilities
Author: Yusra Syeda (ysyeda)
<details>
<summary>Changes</summary>
This PR adds the GOFFDumper. It contains a test which uses llvm-readobj to check the symbols of the provided GOFF object file.
---
Full diff: https://github.com/llvm/llvm-project/pull/71071.diff
8 Files Affected:
- (modified) llvm/lib/Object/GOFFObjectFile.cpp (+9)
- (modified) llvm/lib/Object/ObjectFile.cpp (+2-1)
- (added) llvm/test/tools/llvm-readobj/GOFF/Inputs/goff-basics.o ()
- (added) llvm/test/tools/llvm-readobj/GOFF/goff-basics.test (+69)
- (modified) llvm/tools/llvm-readobj/CMakeLists.txt (+1)
- (added) llvm/tools/llvm-readobj/GOFFDumper.cpp (+94)
- (modified) llvm/tools/llvm-readobj/ObjDumper.h (+4)
- (modified) llvm/tools/llvm-readobj/llvm-readobj.cpp (+4)
``````````diff
diff --git a/llvm/lib/Object/GOFFObjectFile.cpp b/llvm/lib/Object/GOFFObjectFile.cpp
index 76a13559ebfe352..03f86f303668457 100644
--- a/llvm/lib/Object/GOFFObjectFile.cpp
+++ b/llvm/lib/Object/GOFFObjectFile.cpp
@@ -168,6 +168,15 @@ GOFFObjectFile::GOFFObjectFile(MemoryBufferRef Object, Error &Err)
LLVM_DEBUG(dbgs() << " -- ESD " << EsdId << "\n");
break;
}
+ case GOFF::RT_TXT:
+ LLVM_DEBUG(dbgs() << " -- TXT (GOFF record type) unhandled\n");
+ break;
+ case GOFF::RT_RLD:
+ LLVM_DEBUG(dbgs() << " -- RLD (GOFF record type) unhandled\n");
+ break;
+ case GOFF::RT_LEN:
+ LLVM_DEBUG(dbgs() << " -- LEN (GOFF record type) unhandled\n");
+ break;
case GOFF::RT_END:
LLVM_DEBUG(dbgs() << " -- END (GOFF record type) unhandled\n");
break;
diff --git a/llvm/lib/Object/ObjectFile.cpp b/llvm/lib/Object/ObjectFile.cpp
index 428166f58070d0b..16c6003db4810ac 100644
--- a/llvm/lib/Object/ObjectFile.cpp
+++ b/llvm/lib/Object/ObjectFile.cpp
@@ -154,7 +154,6 @@ ObjectFile::createObjectFile(MemoryBufferRef Object, file_magic Type,
case file_magic::windows_resource:
case file_magic::pdb:
case file_magic::minidump:
- case file_magic::goff_object:
case file_magic::cuda_fatbinary:
case file_magic::offload_binary:
case file_magic::dxcontainer_object:
@@ -182,6 +181,8 @@ ObjectFile::createObjectFile(MemoryBufferRef Object, file_magic Type,
case file_magic::macho_kext_bundle:
case file_magic::macho_file_set:
return createMachOObjectFile(Object);
+ case file_magic::goff_object:
+ return createGOFFObjectFile(Object);
case file_magic::coff_object:
case file_magic::coff_import_library:
case file_magic::pecoff_executable:
diff --git a/llvm/test/tools/llvm-readobj/GOFF/Inputs/goff-basics.o b/llvm/test/tools/llvm-readobj/GOFF/Inputs/goff-basics.o
new file mode 100644
index 000000000000000..4988c29ef3dc2f2
Binary files /dev/null and b/llvm/test/tools/llvm-readobj/GOFF/Inputs/goff-basics.o differ
diff --git a/llvm/test/tools/llvm-readobj/GOFF/goff-basics.test b/llvm/test/tools/llvm-readobj/GOFF/goff-basics.test
new file mode 100644
index 000000000000000..812cadd3c9b2654
--- /dev/null
+++ b/llvm/test/tools/llvm-readobj/GOFF/goff-basics.test
@@ -0,0 +1,69 @@
+# RUN: llvm-readobj --symbols %p/Inputs/goff-basics.o | \
+# RUN: FileCheck --check-prefix=SYMBOLSEXP %s
+
+# SYMBOLSEXP: File: {{.*}}goff-basics.o
+# SYMBOLSEXP-NEXT: Format: GOFF-SystemZ
+# SYMBOLSEXP-NEXT: Arch: s390x
+# SYMBOLSEXP-NEXT: AddressSize: 64bit
+# SYMBOLSEXP-NEXT: Symbols [
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: goff-basics#S
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: goff-basics#C
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: .&ppa2
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: a
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: b
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: d
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: CELQSTRT
+# SYMBOLSEXP-NEXT: Value: 0
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: A
+# SYMBOLSEXP-NEXT: Value: 16
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: B
+# SYMBOLSEXP-NEXT: Value: 48
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: Symbol {
+# SYMBOLSEXP-NEXT: Name: D
+# SYMBOLSEXP-NEXT: Value: 80
+# SYMBOLSEXP-NEXT: Alignment: 0
+# SYMBOLSEXP-NEXT: }
+# SYMBOLSEXP-NEXT: ]
+
+
+# goff-basics.o was compiled with `clang -c goff-basics.c`
+# from the following source:
+# int a = 55;
+# int b;
+# double d;
+# int A() { return a; }
+# int B() { return b; }
+# double D() { return d; }
diff --git a/llvm/tools/llvm-readobj/CMakeLists.txt b/llvm/tools/llvm-readobj/CMakeLists.txt
index 0051f87b3c1039f..90637084ae7afa2 100644
--- a/llvm/tools/llvm-readobj/CMakeLists.txt
+++ b/llvm/tools/llvm-readobj/CMakeLists.txt
@@ -18,6 +18,7 @@ add_llvm_tool(llvm-readobj
COFFDumper.cpp
COFFImportDumper.cpp
ELFDumper.cpp
+ GOFFDumper.cpp
llvm-readobj.cpp
MachODumper.cpp
ObjDumper.cpp
diff --git a/llvm/tools/llvm-readobj/GOFFDumper.cpp b/llvm/tools/llvm-readobj/GOFFDumper.cpp
new file mode 100644
index 000000000000000..3cd3fd3866348e2
--- /dev/null
+++ b/llvm/tools/llvm-readobj/GOFFDumper.cpp
@@ -0,0 +1,94 @@
+#include "ObjDumper.h"
+#include "llvm-readobj.h"
+#include "llvm/Object/GOFFObjectFile.h"
+#include "llvm/Support/ScopedPrinter.h"
+
+using namespace llvm;
+using namespace llvm::object;
+
+namespace {
+
+class GOFFDumper : public ObjDumper {
+public:
+ GOFFDumper(const GOFFObjectFile *Obj, ScopedPrinter &Writer)
+ : ObjDumper(Writer, Obj->getFileName()), Obj(Obj) {}
+
+ void printFileHeaders() override {}
+ void printSectionHeaders() override;
+ void printRelocations() override;
+ void printSymbols(bool ExtraSymInfo) override;
+ void printDynamicSymbols() override;
+ void printUnwindInfo() override {}
+ void printStackMap() const override {}
+
+ const object::GOFFObjectFile *getGOFFObject() const { return Obj; };
+
+private:
+ void printSymbol(const SymbolRef &Sym);
+
+ const GOFFObjectFile *Obj;
+};
+
+} // End anonymous namespace
+
+namespace llvm {
+std::unique_ptr<ObjDumper> createGOFFDumper(const object::GOFFObjectFile &Obj,
+ ScopedPrinter &Writer) {
+ return std::make_unique<GOFFDumper>(&Obj, Writer);
+}
+
+} // namespace llvm
+
+void GOFFDumper::printSymbol(const SymbolRef &Symbol) {
+ DictScope D(W, "Symbol");
+
+ Expected<StringRef> SymbolNameOrErr = Obj->getSymbolName(Symbol);
+ if (!SymbolNameOrErr)
+ reportError(SymbolNameOrErr.takeError(), Obj->getFileName());
+ W.printString("Name", SymbolNameOrErr.get());
+ Expected<uint64_t> SymVal = Symbol.getValue();
+ if (!SymVal)
+ reportError(SymVal.takeError(), Obj->getFileName());
+ W.printNumber("Value", *SymVal);
+ W.printNumber("Alignment", Symbol.getAlignment());
+}
+
+void GOFFDumper::printSectionHeaders() {
+ ListScope SectionsD(W, "Sections");
+ for (const SectionRef &Sec : Obj->sections()) {
+ StringRef Name = unwrapOrError(Obj->getFileName(), Sec.getName());
+
+ DictScope D(W, "Section");
+ W.printNumber("Index", Sec.getIndex());
+ W.printString("Name", Name);
+ W.printHex("Address", Sec.getAddress());
+ W.printHex("Size", Sec.getSize());
+ W.printNumber("Alignment", Sec.getAlignment().value());
+
+ if (opts::SectionSymbols) {
+ ListScope D(W, "Symbols");
+ for (const SymbolRef &Symbol : Obj->symbols()) {
+ if (!Sec.containsSymbol(Symbol))
+ continue;
+
+ printSymbol(Symbol);
+ }
+ }
+
+ if (opts::SectionData) {
+ StringRef Data = unwrapOrError(Obj->getFileName(), Sec.getContents());
+ W.printBinaryBlock("SectionData", Data);
+ }
+ }
+}
+
+void GOFFDumper::printSymbols(bool) {
+ ListScope Group(W, "Symbols");
+
+ for (const SymbolRef &Symbol : Obj->symbols())
+ printSymbol(Symbol);
+}
+
+void GOFFDumper::printDynamicSymbols() { ListScope Group(W, "DynamicSymbols"); }
+
+void GOFFDumper::printRelocations() {}
diff --git a/llvm/tools/llvm-readobj/ObjDumper.h b/llvm/tools/llvm-readobj/ObjDumper.h
index 1d679453581bc84..a457e3bab331518 100644
--- a/llvm/tools/llvm-readobj/ObjDumper.h
+++ b/llvm/tools/llvm-readobj/ObjDumper.h
@@ -25,6 +25,7 @@ namespace object {
class Archive;
class COFFImportFile;
class ObjectFile;
+class GOFFObjectFile;
class XCOFFObjectFile;
class ELFObjectFileBase;
} // namespace object
@@ -206,6 +207,9 @@ std::unique_ptr<ObjDumper> createELFDumper(const object::ELFObjectFileBase &Obj,
std::unique_ptr<ObjDumper> createMachODumper(const object::MachOObjectFile &Obj,
ScopedPrinter &Writer);
+std::unique_ptr<ObjDumper> createGOFFDumper(const object::GOFFObjectFile &Obj,
+ ScopedPrinter &Writer);
+
std::unique_ptr<ObjDumper> createWasmDumper(const object::WasmObjectFile &Obj,
ScopedPrinter &Writer);
diff --git a/llvm/tools/llvm-readobj/llvm-readobj.cpp b/llvm/tools/llvm-readobj/llvm-readobj.cpp
index ca633ceff90800e..472fdfa882b6059 100644
--- a/llvm/tools/llvm-readobj/llvm-readobj.cpp
+++ b/llvm/tools/llvm-readobj/llvm-readobj.cpp
@@ -27,6 +27,7 @@
#include "llvm/Object/Archive.h"
#include "llvm/Object/COFFImportFile.h"
#include "llvm/Object/ELFObjectFile.h"
+#include "llvm/Object/GOFFObjectFile.h"
#include "llvm/Object/MachOUniversal.h"
#include "llvm/Object/ObjectFile.h"
#include "llvm/Object/Wasm.h"
@@ -344,6 +345,9 @@ createDumper(const ObjectFile &Obj, ScopedPrinter &Writer) {
if (const MachOObjectFile *MachOObj = dyn_cast<MachOObjectFile>(&Obj))
return createMachODumper(*MachOObj, Writer);
+ if (const GOFFObjectFile *GOFFObj = dyn_cast<GOFFObjectFile>(&Obj))
+ return createGOFFDumper(*GOFFObj, Writer);
+
if (const WasmObjectFile *WasmObj = dyn_cast<WasmObjectFile>(&Obj))
return createWasmDumper(*WasmObj, Writer);
``````````
</details>
https://github.com/llvm/llvm-project/pull/71071
More information about the llvm-commits
mailing list