[llvm] [llvm-objdump] Fix --source with --macho flag (PR #163810)
Ryan Mansfield via llvm-commits
llvm-commits at lists.llvm.org
Mon Oct 20 06:05:39 PDT 2025
https://github.com/rjmansfield updated https://github.com/llvm/llvm-project/pull/163810
>From d02ad93cf9ae153a9191485fadf950cc2b1a2878 Mon Sep 17 00:00:00 2001
From: Ryan Mansfield <ryan_mansfield at apple.com>
Date: Thu, 16 Oct 2025 09:06:52 -0400
Subject: [PATCH 1/2] [llvm-objdump] Fix --source with --macho flag
The --source option was broken when using the --macho flag because
DisassembleMachO() only initialized debug info when UseDbg was true,
and would return early if no dSYM was found.
---
.../MachO/disassemble-source-dsym.test | 12 +++++++
llvm/tools/llvm-objdump/MachODump.cpp | 32 +++++++++++++++----
2 files changed, 37 insertions(+), 7 deletions(-)
diff --git a/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test b/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test
index aaaf6bffe4a33..f7fb621244338 100644
--- a/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test
+++ b/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test
@@ -13,4 +13,16 @@
# RUN: dsymutil -f -oso-prepend-path=%p/../../dsymutil/ %t3 -o %t3.dSYM
# RUN: llvm-objdump --source --prefix=%p/../../dsymutil %t3 | FileCheck --check-prefix=SOURCE %s
+## Test that --source works with --macho flag
+
+## --macho w/ explicit .dSYM
+# RUN: llvm-objdump < %p/../../dsymutil/Inputs/basic.macho.x86_64 - --source --macho --dsym=%t1.dSYM --prefix=%p/../../dsymutil | \
+# RUN: FileCheck --check-prefix=SOURCE %s
+
+## --macho w/ auto-detected .dSYM (dir)
+# RUN: llvm-objdump --source --macho --prefix=%p/../../dsymutil %t2 | FileCheck --check-prefix=SOURCE %s
+
+## --macho w/ auto-detected .dSYM (file)
+# RUN: llvm-objdump --source --macho --prefix=%p/../../dsymutil %t3 | FileCheck --check-prefix=SOURCE %s
+
# SOURCE: ; int bar(int arg) {
diff --git a/llvm/tools/llvm-objdump/MachODump.cpp b/llvm/tools/llvm-objdump/MachODump.cpp
index 8e9c91fde544d..2d1259191c580 100644
--- a/llvm/tools/llvm-objdump/MachODump.cpp
+++ b/llvm/tools/llvm-objdump/MachODump.cpp
@@ -13,6 +13,7 @@
#include "MachODump.h"
#include "ObjdumpOptID.h"
+#include "SourcePrinter.h"
#include "llvm-objdump.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/StringExtras.h"
@@ -7415,18 +7416,24 @@ static void DisassembleMachO(StringRef Filename, MachOObjectFile *MachOOF,
std::unique_ptr<DIContext> diContext;
std::unique_ptr<Binary> DSYMBinary;
std::unique_ptr<MemoryBuffer> DSYMBuf;
- if (UseDbg) {
- // If separate DSym file path was specified, parse it as a macho file,
- // get the sections and supply it to the section name parsing machinery.
- if (const ObjectFile *DbgObj =
- getMachODSymObject(MachOOF, Filename, DSYMBinary, DSYMBuf)) {
+ const ObjectFile *DbgObj = MachOOF;
+ if (UseDbg || PrintSource || PrintLines) {
+ // Look for debug info in external dSYM file or embedded in the object.
+ // getMachODSymObject returns MachOOF by default if no external dSYM found.
+ const ObjectFile *DSym =
+ getMachODSymObject(MachOOF, Filename, DSYMBinary, DSYMBuf);
+ if (!DSym)
+ return;
+ DbgObj = DSym;
+ if (UseDbg) {
// Setup the DIContext
diContext = DWARFContext::create(*DbgObj);
- } else {
- return;
}
}
+ SourcePrinter SP(DbgObj, TheTarget->getName());
+ LiveElementPrinter LEP(*MRI, *STI);
+
if (FilterSections.empty())
outs() << "(" << DisSegName << "," << DisSectName << ") section\n";
@@ -7605,6 +7612,12 @@ static void DisassembleMachO(StringRef Filename, MachOObjectFile *MachOOF,
outs() << SymName << ":\n";
uint64_t PC = SectAddress + Index;
+
+ if (PrintSource || PrintLines) {
+ formatted_raw_ostream FOS(outs());
+ SP.printSourceLine(FOS, {PC, SectIdx}, Filename, LEP);
+ }
+
if (LeadingAddr) {
if (FullLeadingAddr) {
if (MachOOF->is64Bit())
@@ -7696,6 +7709,11 @@ static void DisassembleMachO(StringRef Filename, MachOObjectFile *MachOOF,
uint64_t PC = SectAddress + Index;
+ if (PrintSource || PrintLines) {
+ formatted_raw_ostream FOS(outs());
+ SP.printSourceLine(FOS, {PC, SectIdx}, Filename, LEP);
+ }
+
if (DumpAndSkipDataInCode(PC, Bytes.data() + Index, Dices, InstSize))
continue;
>From 3ac6dbfe5785f95b2400b8e06d30ffeea3e68f59 Mon Sep 17 00:00:00 2001
From: Ryan Mansfield <ryan_mansfield at apple.com>
Date: Mon, 20 Oct 2025 08:45:08 -0400
Subject: [PATCH 2/2] Address reviewer feedback.
Fix --line-numbers with --macho and add test.
Use std::optional to defer initialization of SourcePrinter/LiveElementPrinter.
---
.../MachO/disassemble-source-dsym.test | 21 ++++++++++++++++++-
llvm/tools/llvm-objdump/MachODump.cpp | 14 ++++++++-----
2 files changed, 29 insertions(+), 6 deletions(-)
diff --git a/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test b/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test
index f7fb621244338..9899dc5d41043 100644
--- a/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test
+++ b/llvm/test/tools/llvm-objdump/MachO/disassemble-source-dsym.test
@@ -13,7 +13,7 @@
# RUN: dsymutil -f -oso-prepend-path=%p/../../dsymutil/ %t3 -o %t3.dSYM
# RUN: llvm-objdump --source --prefix=%p/../../dsymutil %t3 | FileCheck --check-prefix=SOURCE %s
-## Test that --source works with --macho flag
+## Test that --source works with --macho flag.
## --macho w/ explicit .dSYM
# RUN: llvm-objdump < %p/../../dsymutil/Inputs/basic.macho.x86_64 - --source --macho --dsym=%t1.dSYM --prefix=%p/../../dsymutil | \
@@ -26,3 +26,22 @@
# RUN: llvm-objdump --source --macho --prefix=%p/../../dsymutil %t3 | FileCheck --check-prefix=SOURCE %s
# SOURCE: ; int bar(int arg) {
+
+## Test that --line-numbers works with --macho flag.
+
+## --macho -l w/ explicit .dSYM
+# RUN: llvm-objdump -d -l --macho --dsym=%t1.dSYM %p/../../dsymutil/Inputs/basic.macho.x86_64 | FileCheck --check-prefix=LINE %s
+
+## --macho -l w/ object file (embedded debug info)
+# RUN: llvm-objdump -d -l --macho %p/../../dsymutil/Inputs/basic1.macho.x86_64.o | FileCheck --check-prefix=LINE_OBJ %s
+
+# LINE: (__TEXT,__text) section
+# LINE: _bar:
+# LINE: ; bar():
+# LINE: ; {{.*}}basic3.c:
+
+# LINE_OBJ: (__TEXT,__text) section
+# LINE_OBJ: _main:
+# LINE_OBJ: ; main():
+# LINE_OBJ: ; {{.*}}basic1.c:23
+# LINE_OBJ: pushq %rbp ## basic1.c:23:0
diff --git a/llvm/tools/llvm-objdump/MachODump.cpp b/llvm/tools/llvm-objdump/MachODump.cpp
index 2d1259191c580..f633ed52943da 100644
--- a/llvm/tools/llvm-objdump/MachODump.cpp
+++ b/llvm/tools/llvm-objdump/MachODump.cpp
@@ -7425,14 +7425,18 @@ static void DisassembleMachO(StringRef Filename, MachOObjectFile *MachOOF,
if (!DSym)
return;
DbgObj = DSym;
- if (UseDbg) {
+ if (UseDbg || PrintLines) {
// Setup the DIContext
diContext = DWARFContext::create(*DbgObj);
}
}
- SourcePrinter SP(DbgObj, TheTarget->getName());
- LiveElementPrinter LEP(*MRI, *STI);
+ std::optional<SourcePrinter> SP;
+ std::optional<LiveElementPrinter> LEP;
+ if (PrintSource || PrintLines) {
+ SP.emplace(DbgObj, TheTarget->getName());
+ LEP.emplace(*MRI, *STI);
+ }
if (FilterSections.empty())
outs() << "(" << DisSegName << "," << DisSectName << ") section\n";
@@ -7615,7 +7619,7 @@ static void DisassembleMachO(StringRef Filename, MachOObjectFile *MachOOF,
if (PrintSource || PrintLines) {
formatted_raw_ostream FOS(outs());
- SP.printSourceLine(FOS, {PC, SectIdx}, Filename, LEP);
+ SP->printSourceLine(FOS, {PC, SectIdx}, Filename, *LEP);
}
if (LeadingAddr) {
@@ -7711,7 +7715,7 @@ static void DisassembleMachO(StringRef Filename, MachOObjectFile *MachOOF,
if (PrintSource || PrintLines) {
formatted_raw_ostream FOS(outs());
- SP.printSourceLine(FOS, {PC, SectIdx}, Filename, LEP);
+ SP->printSourceLine(FOS, {PC, SectIdx}, Filename, *LEP);
}
if (DumpAndSkipDataInCode(PC, Bytes.data() + Index, Dices, InstSize))
More information about the llvm-commits
mailing list