[lld] [llvm] [ICF] Add a NOP after branch in ICF thunk to improve debugability (PR #154986)
Peter Rong via llvm-commits
llvm-commits at lists.llvm.org
Fri Aug 22 16:53:32 PDT 2025
https://github.com/DataCorrupted updated https://github.com/llvm/llvm-project/pull/154986
>From 35082deba3dd6f306ceefa8bd4a46f79674a327c Mon Sep 17 00:00:00 2001
From: Peter Rong <PeterRong at meta.com>
Date: Fri, 22 Aug 2025 09:48:56 -0700
Subject: [PATCH 1/4] [ICF] Add a NOP after branch in ICF thunk to improve
debugability
---
lld/MachO/Arch/ARM64.cpp | 1 +
1 file changed, 1 insertion(+)
diff --git a/lld/MachO/Arch/ARM64.cpp b/lld/MachO/Arch/ARM64.cpp
index 04da702b48764..2479c2e2c72b8 100644
--- a/lld/MachO/Arch/ARM64.cpp
+++ b/lld/MachO/Arch/ARM64.cpp
@@ -176,6 +176,7 @@ void ARM64::populateThunk(InputSection *thunk, Symbol *funcSym) {
// Just a single direct branch to the target function.
static constexpr uint32_t icfSafeThunkCode[] = {
0x14000000, // 08: b target
+ 0xD503201F, // 0c: nop
};
void ARM64::initICFSafeThunkBody(InputSection *thunk, Symbol *targetSym) const {
>From 3d9e6866b7f9203e1f63254bf989092e4d9559c4 Mon Sep 17 00:00:00 2001
From: Peter Rong <PeterRong at meta.com>
Date: Fri, 22 Aug 2025 11:19:10 -0700
Subject: [PATCH 2/4] Update comment and test
---
lld/MachO/Arch/ARM64.cpp | 8 +++++++-
lld/test/MachO/icf-safe-thunks.ll | 11 +++++++----
2 files changed, 14 insertions(+), 5 deletions(-)
diff --git a/lld/MachO/Arch/ARM64.cpp b/lld/MachO/Arch/ARM64.cpp
index 2479c2e2c72b8..d819839fea438 100644
--- a/lld/MachO/Arch/ARM64.cpp
+++ b/lld/MachO/Arch/ARM64.cpp
@@ -173,7 +173,13 @@ void ARM64::populateThunk(InputSection *thunk, Symbol *funcSym) {
/*offset=*/0, /*addend=*/0,
/*referent=*/funcSym);
}
-// Just a single direct branch to the target function.
+// Just a single direct branch to the target function and a nop.
+// The nop will improve the debuggability.
+//
+// Debug lines in DWARF does not recognize one-instruction sequence, and this
+// thunk will be merged into other sequences if it only had one instruction.
+// Adding a nop after the branch has no runtime cost, and little size impact,
+// but it would make DWARF linker and debuggers happier.
static constexpr uint32_t icfSafeThunkCode[] = {
0x14000000, // 08: b target
0xD503201F, // 0c: nop
diff --git a/lld/test/MachO/icf-safe-thunks.ll b/lld/test/MachO/icf-safe-thunks.ll
index 12f1e81bdf3e8..384716eb667a2 100644
--- a/lld/test/MachO/icf-safe-thunks.ll
+++ b/lld/test/MachO/icf-safe-thunks.ll
@@ -39,12 +39,15 @@
;
; CHECK-ARM64: _func_2identical_v2:
; CHECK-ARM64-NEXT: b _func_2identical_v1
+; CHECK-ARM64-NEXT: nop
; CHECK-ARM64-NEXT: _func_3identical_v2:
; CHECK-ARM64-NEXT: b _func_3identical_v1
+; CHECK-ARM64-NEXT: nop
; CHECK-ARM64-NEXT: _func_3identical_v3:
; CHECK-ARM64-NEXT: b _func_3identical_v1
+; CHECK-ARM64-NEXT: nop
-
+; Check the size of each functions. Thunks' size will change from 4-> 8 because of added nop.
; CHECK-ARM64-MAP: 0x00000010 [ 2] _func_unique_1
; CHECK-ARM64-MAP-NEXT: 0x00000010 [ 2] _func_2identical_v1
; CHECK-ARM64-MAP-NEXT: 0x00000000 [ 2] _func_unique_2_canmerge
@@ -57,9 +60,9 @@
; CHECK-ARM64-MAP-NEXT: 0x00000000 [ 2] _func_call_thunked_2_merge
; CHECK-ARM64-MAP-NEXT: 0x00000034 [ 2] _call_all_funcs
; CHECK-ARM64-MAP-NEXT: 0x00000050 [ 2] _take_func_addr
-; CHECK-ARM64-MAP-NEXT: 0x00000004 [ 2] _func_2identical_v2
-; CHECK-ARM64-MAP-NEXT: 0x00000004 [ 2] _func_3identical_v2
-; CHECK-ARM64-MAP-NEXT: 0x00000004 [ 2] _func_3identical_v3
+; CHECK-ARM64-MAP-NEXT: 0x00000008 [ 2] _func_2identical_v2
+; CHECK-ARM64-MAP-NEXT: 0x00000008 [ 2] _func_3identical_v2
+; CHECK-ARM64-MAP-NEXT: 0x00000008 [ 2] _func_3identical_v3
;--- a.cpp
#define ATTR __attribute__((noinline)) extern "C"
>From decd0786e7053e750202e0a50b9dc8ef558cd036 Mon Sep 17 00:00:00 2001
From: Peter Rong <PeterRong at meta.com>
Date: Fri, 22 Aug 2025 16:08:12 -0700
Subject: [PATCH 3/4] Dont emit for single line functions
Signed-off-by: Peter Rong <PeterRong at meta.com>
---
llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp | 15 ++++++++++++---
1 file changed, 12 insertions(+), 3 deletions(-)
diff --git a/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp b/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
index 67f526fe91464..861a74091e8eb 100644
--- a/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
+++ b/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
@@ -553,9 +553,18 @@ DIE &DwarfCompileUnit::updateSubprogramScopeDIE(const DISubprogram *SP,
addFlag(*SPDie, dwarf::DW_AT_APPLE_omit_frame_ptr);
if (emitFuncLineTableOffsets() && LineTableSym) {
- addSectionLabel(
- *SPDie, dwarf::DW_AT_LLVM_stmt_sequence, LineTableSym,
- Asm->getObjFileLowering().getDwarfLineSection()->getBeginSymbol());
+ // Check if we have meaningful code ranges before adding LLVM_stmt_sequence
+ // Only add it if there are multiple basic block sections or if the single
+ // range represents substantial code (not just a trivial function)
+ bool hasSubstantialCode =
+ BB_List.size() > 1 ||
+ (BB_List.size() == 1 && BB_List[0].Begin != BB_List[0].End);
+
+ if (hasSubstantialCode) {
+ addSectionLabel(
+ *SPDie, dwarf::DW_AT_LLVM_stmt_sequence, LineTableSym,
+ Asm->getObjFileLowering().getDwarfLineSection()->getBeginSymbol());
+ }
}
// Only include DW_AT_frame_base in full debug info
>From 261a8cf039a795bff72fda628846ff6d4d0a8224 Mon Sep 17 00:00:00 2001
From: Peter Rong <PeterRong at meta.com>
Date: Fri, 22 Aug 2025 16:53:13 -0700
Subject: [PATCH 4/4] Update test
Signed-off-by: Peter Rong <PeterRong at meta.com>
---
lld/test/MachO/icf-safe-thunks-dwarf.ll | 237 ++++++++++++------
.../CodeGen/AsmPrinter/DwarfCompileUnit.cpp | 4 +-
2 files changed, 159 insertions(+), 82 deletions(-)
diff --git a/lld/test/MachO/icf-safe-thunks-dwarf.ll b/lld/test/MachO/icf-safe-thunks-dwarf.ll
index 7fae4124f793b..615fecdd06854 100644
--- a/lld/test/MachO/icf-safe-thunks-dwarf.ll
+++ b/lld/test/MachO/icf-safe-thunks-dwarf.ll
@@ -41,11 +41,11 @@
# Functions from the first object file - all functions share the same address but belong to a.o
# VERIFY-MULTI-STABS: N_FUN{{.*}}[[FUNC_ADDR:[0-9a-f]+]] '_func_A'
-# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
+# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}[[FUNC_ADDR]] '_func_B'
-# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
+# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}[[FUNC_ADDR]] '_func_C'
-# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
+# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
# VERIFY-MULTI-STABS-NEXT-NEXT: N_FUN{{.*}}[0-9a-f]+ '_take_func_addr'
# End of first object file's entries
@@ -57,11 +57,11 @@
# Functions from the second object file - same addresses but different object file
# VERIFY-MULTI-STABS: N_FUN{{.*}}[[FUNC_ADDR]] '_func_D'
-# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
+# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}[[FUNC_ADDR]] '_func_E'
-# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
+# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}[[FUNC_ADDR]] '_func_F'
-# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
+# VERIFY-MULTI-STABS-NEXT: N_FUN{{.*}}00 0000 {{.*}}
# VERIFY-MULTI-STABS-NEXT-NEXT: N_FUN{{.*}}[0-9a-f]+ '_take_func_addr_b'
; RUN: dsymutil --flat --verify-dwarf=none %t/a_thunks.dylib -o %t/a_thunks.dSYM
@@ -117,9 +117,21 @@
#define ATTR __attribute__((noinline)) extern "C"
typedef unsigned long long ULL;
-ATTR int func_A() { return 1; }
-ATTR int func_B() { return 1; }
-ATTR int func_C() { return 1; }
+// Now that safe thunk has two instructions, trivial one-instruction
+// functions will not be ICF'ed anymore. We need to make the functions
+// more non-trivial to ensure that they are ICF'ed
+ATTR int func_A(int A) {
+ int tmp = A + 1;
+ return tmp / 2;
+}
+ATTR int func_B(int B) {
+ int tmp = B + 1;
+ return tmp / 2;
+}
+ATTR int func_C(int C) {
+ int tmp = C + 1;
+ return tmp / 2;
+}
ATTR ULL take_func_addr() {
ULL val = 0;
@@ -134,9 +146,18 @@ ATTR ULL take_func_addr() {
typedef unsigned long long ULL;
// Identical functions in a different object file
-ATTR int func_D() { return 1; }
-ATTR int func_E() { return 1; }
-ATTR int func_F() { return 1; }
+ATTR int func_D(int D) {
+ int tmp = D + 1;
+ return tmp / 2;
+}
+ATTR int func_E(int E) {
+ int tmp = E + 1;
+ return tmp / 2;
+}
+ATTR int func_F(int F) {
+ int tmp = F + 1;
+ return tmp / 2;
+}
ATTR ULL take_func_addr_b() {
ULL val = 0;
@@ -159,39 +180,48 @@ target datalayout = "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-n32:
target triple = "arm64-apple-macosx11.0.0"
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i32 @func_A() #0 !dbg !12 {
-entry:
- ret i32 1, !dbg !16
+define range(i32 -1073741823, 1073741824) i32 @func_A(i32 noundef %0) #0 !dbg !13 {
+ #dbg_value(i32 %0, !18, !DIExpression(), !20)
+ %2 = add nsw i32 %0, 1, !dbg !21
+ #dbg_value(i32 %2, !19, !DIExpression(), !20)
+ %3 = sdiv i32 %2, 2, !dbg !22
+ ret i32 %3, !dbg !23
}
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i32 @func_B() #0 !dbg !17 {
-entry:
- ret i32 1, !dbg !18
+define range(i32 -1073741823, 1073741824) i32 @func_B(i32 noundef %0) #0 !dbg !24 {
+ #dbg_value(i32 %0, !26, !DIExpression(), !28)
+ %2 = add nsw i32 %0, 1, !dbg !29
+ #dbg_value(i32 %2, !27, !DIExpression(), !28)
+ %3 = sdiv i32 %2, 2, !dbg !30
+ ret i32 %3, !dbg !31
}
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i32 @func_C() #0 !dbg !19 {
-entry:
- ret i32 1, !dbg !20
+define range(i32 -1073741823, 1073741824) i32 @func_C(i32 noundef %0) #0 !dbg !32 {
+ #dbg_value(i32 %0, !34, !DIExpression(), !36)
+ %2 = add nsw i32 %0, 1, !dbg !37
+ #dbg_value(i32 %2, !35, !DIExpression(), !36)
+ %3 = sdiv i32 %2, 2, !dbg !38
+ ret i32 %3, !dbg !39
}
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i64 @take_func_addr() local_unnamed_addr #0 !dbg !21 {
-entry:
- #dbg_value(i64 0, !25, !DIExpression(), !26)
- #dbg_value(i64 ptrtoint (ptr @func_A to i64), !25, !DIExpression(), !26)
- #dbg_value(i64 add (i64 ptrtoint (ptr @func_A to i64), i64 ptrtoint (ptr @func_B to i64)), !25, !DIExpression(), !26)
- #dbg_value(i64 add (i64 add (i64 ptrtoint (ptr @func_A to i64), i64 ptrtoint (ptr @func_B to i64)), i64 ptrtoint (ptr @func_C to i64)), !25, !DIExpression(), !26)
- ret i64 add (i64 add (i64 ptrtoint (ptr @func_A to i64), i64 ptrtoint (ptr @func_B to i64)), i64 ptrtoint (ptr @func_C to i64)), !dbg !27
+define noundef i64 @take_func_addr() local_unnamed_addr #0 !dbg !40 {
+ #dbg_value(i64 0, !44, !DIExpression(), !45)
+ #dbg_value(i64 ptrtoint (ptr @func_A to i64), !44, !DIExpression(), !45)
+ #dbg_value(i64 add (i64 ptrtoint (ptr @func_A to i64), i64 ptrtoint (ptr @func_B to i64)), !44, !DIExpression(), !45)
+ #dbg_value(i64 add (i64 add (i64 ptrtoint (ptr @func_A to i64), i64 ptrtoint (ptr @func_B to i64)), i64 ptrtoint (ptr @func_C to i64)), !44, !DIExpression(), !45)
+ ret i64 add (i64 add (i64 ptrtoint (ptr @func_A to i64), i64 ptrtoint (ptr @func_B to i64)), i64 ptrtoint (ptr @func_C to i64)), !dbg !46
}
-attributes #0 = { mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync) "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+ccpp,+complxnum,+crc,+dit,+dotprod,+flagm,+fp-armv8,+fp16fml,+fptoint,+fullfp16,+jsconv,+lse,+neon,+pauth,+perfmon,+predres,+ras,+rcpc,+rdm,+sb,+sha2,+sha3,+specrestrict,+ssbs,+v8.1a,+v8.2a,+v8.3a,+v8.4a,+v8a" }
+attributes #0 = { mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync) "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+ccpp,+complxnum,+crc,+dit,+dotprod,+flagm,+fp-armv8,+fp16fml,+fptoint,+fullfp16,+jsconv,+lse,+neon,+pauth,+perfmon,+predres,+ras,+rcpc,+rdm,+sb,+sha2,+sha3,+specrestrict,+ssbs,+v8.1a,+v8.2a,+v8.3a,+v8.4a,+v8a,+zcm,+zcz" }
!llvm.dbg.cu = !{!0}
!llvm.module.flags = !{!6, !7, !8, !9, !10, !11}
+!llvm.ident = !{!12}
-!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus_14, file: !1, isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, retainedTypes: !2, splitDebugInlining: false, nameTableKind: Apple, sysroot: "/")
+!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus_14, file: !1, producer: "Facebook clang version 15.0.0 (https://git.internal.tfbnw.net/repos/git/ro/osmeta/external/llvm-project a85823b9dd90d425da12e921b64332583924ef3b)", isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, retainedTypes: !2, splitDebugInlining: false, nameTableKind: Apple, sysroot: "/")
!1 = !DIFile(filename: "a.cpp", directory: "/proc/self/cwd")
!2 = !{!3, !5}
!3 = !DIDerivedType(tag: DW_TAG_typedef, name: "ULL", file: !1, line: 2, baseType: !4)
@@ -203,22 +233,41 @@ attributes #0 = { mustprogress nofree noinline norecurse nosync nounwind ssp wil
!9 = !{i32 8, !"PIC Level", i32 2}
!10 = !{i32 7, !"uwtable", i32 1}
!11 = !{i32 7, !"frame-pointer", i32 1}
-!12 = distinct !DISubprogram(name: "func_A", scope: !1, file: !1, line: 4, type: !13, scopeLine: 4, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
-!13 = !DISubroutineType(types: !14)
-!14 = !{!15}
-!15 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
-!16 = !DILocation(line: 4, column: 21, scope: !12)
-!17 = distinct !DISubprogram(name: "func_B", scope: !1, file: !1, line: 5, type: !13, scopeLine: 5, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
-!18 = !DILocation(line: 5, column: 21, scope: !17)
-!19 = distinct !DISubprogram(name: "func_C", scope: !1, file: !1, line: 6, type: !13, scopeLine: 6, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
-!20 = !DILocation(line: 6, column: 21, scope: !19)
-!21 = distinct !DISubprogram(name: "take_func_addr", scope: !1, file: !1, line: 8, type: !22, scopeLine: 8, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !24)
-!22 = !DISubroutineType(types: !23)
-!23 = !{!3}
-!24 = !{!25}
-!25 = !DILocalVariable(name: "val", scope: !21, file: !1, line: 9, type: !3)
-!26 = !DILocation(line: 0, scope: !21)
-!27 = !DILocation(line: 13, column: 5, scope: !21)
+!12 = !{!"Facebook clang version 15.0.0 (https://git.internal.tfbnw.net/repos/git/ro/osmeta/external/llvm-project a85823b9dd90d425da12e921b64332583924ef3b)"}
+!13 = distinct !DISubprogram(name: "func_A", scope: !1, file: !1, line: 4, type: !14, scopeLine: 4, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !17)
+!14 = !DISubroutineType(types: !15)
+!15 = !{!16, !16}
+!16 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+!17 = !{!18, !19}
+!18 = !DILocalVariable(name: "A", arg: 1, scope: !13, file: !1, line: 4, type: !16)
+!19 = !DILocalVariable(name: "tmp", scope: !13, file: !1, line: 5, type: !16)
+!20 = !DILocation(line: 0, scope: !13)
+!21 = !DILocation(line: 5, column: 15, scope: !13)
+!22 = !DILocation(line: 6, column: 14, scope: !13)
+!23 = !DILocation(line: 6, column: 3, scope: !13)
+!24 = distinct !DISubprogram(name: "func_B", scope: !1, file: !1, line: 8, type: !14, scopeLine: 8, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !25)
+!25 = !{!26, !27}
+!26 = !DILocalVariable(name: "B", arg: 1, scope: !24, file: !1, line: 8, type: !16)
+!27 = !DILocalVariable(name: "tmp", scope: !24, file: !1, line: 9, type: !16)
+!28 = !DILocation(line: 0, scope: !24)
+!29 = !DILocation(line: 9, column: 15, scope: !24)
+!30 = !DILocation(line: 10, column: 14, scope: !24)
+!31 = !DILocation(line: 10, column: 3, scope: !24)
+!32 = distinct !DISubprogram(name: "func_C", scope: !1, file: !1, line: 12, type: !14, scopeLine: 12, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !33)
+!33 = !{!34, !35}
+!34 = !DILocalVariable(name: "C", arg: 1, scope: !32, file: !1, line: 12, type: !16)
+!35 = !DILocalVariable(name: "tmp", scope: !32, file: !1, line: 13, type: !16)
+!36 = !DILocation(line: 0, scope: !32)
+!37 = !DILocation(line: 13, column: 15, scope: !32)
+!38 = !DILocation(line: 14, column: 14, scope: !32)
+!39 = !DILocation(line: 14, column: 3, scope: !32)
+!40 = distinct !DISubprogram(name: "take_func_addr", scope: !1, file: !1, line: 17, type: !41, scopeLine: 17, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !43)
+!41 = !DISubroutineType(types: !42)
+!42 = !{!3}
+!43 = !{!44}
+!44 = !DILocalVariable(name: "val", scope: !40, file: !1, line: 18, type: !3)
+!45 = !DILocation(line: 0, scope: !40)
+!46 = !DILocation(line: 22, column: 5, scope: !40)
;--- b.ll
; ModuleID = 'b.cpp'
@@ -227,39 +276,48 @@ target datalayout = "e-m:o-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-n32:
target triple = "arm64-apple-macosx11.0.0"
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i32 @func_D() #0 !dbg !12 {
-entry:
- ret i32 1, !dbg !16
+define range(i32 -1073741823, 1073741824) i32 @func_D(i32 noundef %0) #0 !dbg !13 {
+ #dbg_value(i32 %0, !18, !DIExpression(), !20)
+ %2 = add nsw i32 %0, 1, !dbg !21
+ #dbg_value(i32 %2, !19, !DIExpression(), !20)
+ %3 = sdiv i32 %2, 2, !dbg !22
+ ret i32 %3, !dbg !23
}
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i32 @func_E() #0 !dbg !17 {
-entry:
- ret i32 1, !dbg !18
+define range(i32 -1073741823, 1073741824) i32 @func_E(i32 noundef %0) #0 !dbg !24 {
+ #dbg_value(i32 %0, !26, !DIExpression(), !28)
+ %2 = add nsw i32 %0, 1, !dbg !29
+ #dbg_value(i32 %2, !27, !DIExpression(), !28)
+ %3 = sdiv i32 %2, 2, !dbg !30
+ ret i32 %3, !dbg !31
}
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i32 @func_F() #0 !dbg !19 {
-entry:
- ret i32 1, !dbg !20
+define range(i32 -1073741823, 1073741824) i32 @func_F(i32 noundef %0) #0 !dbg !32 {
+ #dbg_value(i32 %0, !34, !DIExpression(), !36)
+ %2 = add nsw i32 %0, 1, !dbg !37
+ #dbg_value(i32 %2, !35, !DIExpression(), !36)
+ %3 = sdiv i32 %2, 2, !dbg !38
+ ret i32 %3, !dbg !39
}
; Function Attrs: mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync)
-define noundef i64 @take_func_addr_b() local_unnamed_addr #0 !dbg !21 {
-entry:
- #dbg_value(i64 0, !25, !DIExpression(), !26)
- #dbg_value(i64 ptrtoint (ptr @func_D to i64), !25, !DIExpression(), !26)
- #dbg_value(i64 add (i64 ptrtoint (ptr @func_D to i64), i64 ptrtoint (ptr @func_E to i64)), !25, !DIExpression(), !26)
- #dbg_value(i64 add (i64 add (i64 ptrtoint (ptr @func_D to i64), i64 ptrtoint (ptr @func_E to i64)), i64 ptrtoint (ptr @func_F to i64)), !25, !DIExpression(), !26)
- ret i64 add (i64 add (i64 ptrtoint (ptr @func_D to i64), i64 ptrtoint (ptr @func_E to i64)), i64 ptrtoint (ptr @func_F to i64)), !dbg !27
+define noundef i64 @take_func_addr_b() local_unnamed_addr #0 !dbg !40 {
+ #dbg_value(i64 0, !44, !DIExpression(), !45)
+ #dbg_value(i64 ptrtoint (ptr @func_D to i64), !44, !DIExpression(), !45)
+ #dbg_value(i64 add (i64 ptrtoint (ptr @func_D to i64), i64 ptrtoint (ptr @func_E to i64)), !44, !DIExpression(), !45)
+ #dbg_value(i64 add (i64 add (i64 ptrtoint (ptr @func_D to i64), i64 ptrtoint (ptr @func_E to i64)), i64 ptrtoint (ptr @func_F to i64)), !44, !DIExpression(), !45)
+ ret i64 add (i64 add (i64 ptrtoint (ptr @func_D to i64), i64 ptrtoint (ptr @func_E to i64)), i64 ptrtoint (ptr @func_F to i64)), !dbg !46
}
-attributes #0 = { mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync) "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+ccpp,+complxnum,+crc,+dit,+dotprod,+flagm,+fp-armv8,+fp16fml,+fptoint,+fullfp16,+jsconv,+lse,+neon,+pauth,+perfmon,+predres,+ras,+rcpc,+rdm,+sb,+sha2,+sha3,+specrestrict,+ssbs,+v8.1a,+v8.2a,+v8.3a,+v8.4a,+v8a" }
+attributes #0 = { mustprogress nofree noinline norecurse nosync nounwind ssp willreturn memory(none) uwtable(sync) "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+ccpp,+complxnum,+crc,+dit,+dotprod,+flagm,+fp-armv8,+fp16fml,+fptoint,+fullfp16,+jsconv,+lse,+neon,+pauth,+perfmon,+predres,+ras,+rcpc,+rdm,+sb,+sha2,+sha3,+specrestrict,+ssbs,+v8.1a,+v8.2a,+v8.3a,+v8.4a,+v8a,+zcm,+zcz" }
!llvm.dbg.cu = !{!0}
!llvm.module.flags = !{!6, !7, !8, !9, !10, !11}
+!llvm.ident = !{!12}
-!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus_14, file: !1, isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, retainedTypes: !2, splitDebugInlining: false, nameTableKind: Apple, sysroot: "/")
+!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus_14, file: !1, producer: "Facebook clang version 15.0.0 (https://git.internal.tfbnw.net/repos/git/ro/osmeta/external/llvm-project a85823b9dd90d425da12e921b64332583924ef3b)", isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, retainedTypes: !2, splitDebugInlining: false, nameTableKind: Apple, sysroot: "/")
!1 = !DIFile(filename: "b.cpp", directory: "/proc/self/cwd")
!2 = !{!3, !5}
!3 = !DIDerivedType(tag: DW_TAG_typedef, name: "ULL", file: !1, line: 2, baseType: !4)
@@ -271,19 +329,38 @@ attributes #0 = { mustprogress nofree noinline norecurse nosync nounwind ssp wil
!9 = !{i32 8, !"PIC Level", i32 2}
!10 = !{i32 7, !"uwtable", i32 1}
!11 = !{i32 7, !"frame-pointer", i32 1}
-!12 = distinct !DISubprogram(name: "func_D", scope: !1, file: !1, line: 5, type: !13, scopeLine: 5, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
-!13 = !DISubroutineType(types: !14)
-!14 = !{!15}
-!15 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
-!16 = !DILocation(line: 5, column: 21, scope: !12)
-!17 = distinct !DISubprogram(name: "func_E", scope: !1, file: !1, line: 6, type: !13, scopeLine: 6, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
-!18 = !DILocation(line: 6, column: 21, scope: !17)
-!19 = distinct !DISubprogram(name: "func_F", scope: !1, file: !1, line: 7, type: !13, scopeLine: 7, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
-!20 = !DILocation(line: 7, column: 21, scope: !19)
-!21 = distinct !DISubprogram(name: "take_func_addr_b", scope: !1, file: !1, line: 9, type: !22, scopeLine: 9, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !24)
-!22 = !DISubroutineType(types: !23)
-!23 = !{!3}
-!24 = !{!25}
-!25 = !DILocalVariable(name: "val", scope: !21, file: !1, line: 10, type: !3)
-!26 = !DILocation(line: 0, scope: !21)
-!27 = !DILocation(line: 14, column: 5, scope: !21)
+!12 = !{!"Facebook clang version 15.0.0 (https://git.internal.tfbnw.net/repos/git/ro/osmeta/external/llvm-project a85823b9dd90d425da12e921b64332583924ef3b)"}
+!13 = distinct !DISubprogram(name: "func_D", scope: !1, file: !1, line: 5, type: !14, scopeLine: 5, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !17)
+!14 = !DISubroutineType(types: !15)
+!15 = !{!16, !16}
+!16 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+!17 = !{!18, !19}
+!18 = !DILocalVariable(name: "D", arg: 1, scope: !13, file: !1, line: 5, type: !16)
+!19 = !DILocalVariable(name: "tmp", scope: !13, file: !1, line: 6, type: !16)
+!20 = !DILocation(line: 0, scope: !13)
+!21 = !DILocation(line: 6, column: 15, scope: !13)
+!22 = !DILocation(line: 7, column: 14, scope: !13)
+!23 = !DILocation(line: 7, column: 3, scope: !13)
+!24 = distinct !DISubprogram(name: "func_E", scope: !1, file: !1, line: 9, type: !14, scopeLine: 9, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !25)
+!25 = !{!26, !27}
+!26 = !DILocalVariable(name: "E", arg: 1, scope: !24, file: !1, line: 9, type: !16)
+!27 = !DILocalVariable(name: "tmp", scope: !24, file: !1, line: 10, type: !16)
+!28 = !DILocation(line: 0, scope: !24)
+!29 = !DILocation(line: 10, column: 15, scope: !24)
+!30 = !DILocation(line: 11, column: 14, scope: !24)
+!31 = !DILocation(line: 11, column: 3, scope: !24)
+!32 = distinct !DISubprogram(name: "func_F", scope: !1, file: !1, line: 13, type: !14, scopeLine: 13, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !33)
+!33 = !{!34, !35}
+!34 = !DILocalVariable(name: "F", arg: 1, scope: !32, file: !1, line: 13, type: !16)
+!35 = !DILocalVariable(name: "tmp", scope: !32, file: !1, line: 14, type: !16)
+!36 = !DILocation(line: 0, scope: !32)
+!37 = !DILocation(line: 14, column: 15, scope: !32)
+!38 = !DILocation(line: 15, column: 14, scope: !32)
+!39 = !DILocation(line: 15, column: 3, scope: !32)
+!40 = distinct !DISubprogram(name: "take_func_addr_b", scope: !1, file: !1, line: 18, type: !41, scopeLine: 18, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !43)
+!41 = !DISubroutineType(types: !42)
+!42 = !{!3}
+!43 = !{!44}
+!44 = !DILocalVariable(name: "val", scope: !40, file: !1, line: 19, type: !3)
+!45 = !DILocation(line: 0, scope: !40)
+!46 = !DILocation(line: 23, column: 5, scope: !40)
diff --git a/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp b/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
index 861a74091e8eb..8e7bd2bd32a67 100644
--- a/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
+++ b/llvm/lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp
@@ -556,11 +556,11 @@ DIE &DwarfCompileUnit::updateSubprogramScopeDIE(const DISubprogram *SP,
// Check if we have meaningful code ranges before adding LLVM_stmt_sequence
// Only add it if there are multiple basic block sections or if the single
// range represents substantial code (not just a trivial function)
- bool hasSubstantialCode =
+ bool HasSubstantialCode =
BB_List.size() > 1 ||
(BB_List.size() == 1 && BB_List[0].Begin != BB_List[0].End);
- if (hasSubstantialCode) {
+ if (HasSubstantialCode) {
addSectionLabel(
*SPDie, dwarf::DW_AT_LLVM_stmt_sequence, LineTableSym,
Asm->getObjFileLowering().getDwarfLineSection()->getBeginSymbol());
More information about the llvm-commits
mailing list