[clangd] Re-land "support outgoing calls in call hierarchy" (#117673)
[llvm-project.git] / llvm / test / tools / llvm-gsymutil / ARM_AArch64 / macho-gsym-callsite-info-obj.test
blob2d082ed6477f1e0439bffcc1209d65760fbc186e
1 // RUN: split-file %s %t
3 // Assemble the input assembly code into an object file
4 // RUN: llc -enable-machine-outliner=never -mtriple arm64-apple-darwin -filetype=obj %t/call_sites.ll -o %t/call_sites.o
5 // RUN: llvm-gsymutil --convert=%t/call_sites.o --callsites-yaml-file=%t/callsites.yaml -o %t/call_sites_obj.gsym
7 // Dump the GSYM file and check the output for callsite information
8 // RUN: llvm-gsymutil %t/call_sites_obj.gsym | FileCheck --check-prefix=CHECK-GSYM %s
11 // CHECK-GSYM:      FunctionInfo @ 0x[[#%x,FUNC_INFO:]]: [0x[[#%x,FUNC_START:]] - 0x[[#%x,FUNC_END:]]) "func_mainBin_dec_call_everything"
12 // CHECK-GSYM-NEXT: LineTable:
13                       // func_mainBin_dec_call_everything() {
14 // CHECK-GSYM-NEXT:   0x[[#%x,ENTRY:]] {{.*}}/call_sites.cpp:16
15                       // func_mainBin_dec_01();
16 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_DEC_01_CALL:]] {{.*}}/call_sites.cpp:17
17                       // func_mainBin_dec_02();
18 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_DEC_02_CALL:]] {{.*}}/call_sites.cpp:18
19                       // func_mainBin_dec_03();
20 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_DEC_03_CALL:]] {{.*}}/call_sites.cpp:19
21                       // func_mainBin_inc_01();
22 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_INC_01_CALL:]] {{.*}}/call_sites.cpp:21
23                       // func_mainBin_inc_02();
24 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_INC_02_CALL:]] {{.*}}/call_sites.cpp:22
25                       // func_mainBin_inc_03();
26 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_INC_03_CALL:]] {{.*}}/call_sites.cpp:23
27                       // g_func_ptr();
28 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_FUNC_CALL:]] {{.*}}/call_sites.cpp:25
29                       // g_extern_func_ptr();
30 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_EXTERN_FUNC_CALL:]] {{.*}}/call_sites.cpp:26
31                       // g_volatile_var = 0;
32 // CHECK-GSYM-NEXT:   0x[[#%x,ADDR_VAR_ASSIGN:]] {{.*}}/call_sites.cpp:28
33                       // }
34 // CHECK-GSYM-NEXT:   0x[[#%x,]] {{.*}}/call_sites.cpp:29
35 // CHECK-GSYM-NEXT: CallSites (by relative return offset):
36 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_DEC_02_CALL,FUNC_START)]] Flags[InternalCall] MatchRegex[func_mainBin_dec_01]
37 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_DEC_03_CALL,FUNC_START)]] Flags[InternalCall] MatchRegex[func_mainBin_dec_02]
38 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_INC_01_CALL,FUNC_START)]] Flags[InternalCall] MatchRegex[func_mainBin_dec_03]
39 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_INC_02_CALL,FUNC_START)]] Flags[InternalCall] MatchRegex[func_mainBin_inc_01]
40 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_INC_03_CALL,FUNC_START)]] Flags[InternalCall] MatchRegex[func_mainBin_inc_02]
41 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_FUNC_CALL,FUNC_START)]] Flags[InternalCall] MatchRegex[func_mainBin_inc_03]
42 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_EXTERN_FUNC_CALL,FUNC_START)]] Flags[None] MatchRegex[.*func.*]
43 // CHECK-GSYM-NEXT:   0x[[#%.4x,sub(ADDR_VAR_ASSIGN,FUNC_START)]] Flags[ExternalCall] MatchRegex[.*extern_func.*]
46 //--- callsites.yaml
47 functions:
48   - name: func_mainBin_dec_call_everything
49     callsites:
50       - return_offset: 0x0C
51         match_regex: ["func_mainBin_dec_01"]
52         flags:
53           - "InternalCall"
54       - return_offset: 0x10
55         match_regex: ["func_mainBin_dec_02"]
56         flags:
57           - "InternalCall"
58       - return_offset: 0x14
59         match_regex: ["func_mainBin_dec_03"]
60         flags:
61           - "InternalCall"
62       - return_offset: 24
63         match_regex: ["func_mainBin_inc_01"]
64         flags:
65           - "InternalCall"
66       - return_offset: 28
67         match_regex: ["func_mainBin_inc_02"]
68         flags:
69           - "InternalCall"
70       - return_offset: 32
71         match_regex: ["func_mainBin_inc_03"]
72         flags:
73           - "InternalCall"
74       - return_offset: 44
75         match_regex: [".*func.*"]
76       - return_offset: 56
77         match_regex: [".*extern_func.*"]
78         flags:
79           - "ExternalCall"
82 //--- call_sites.ll
83 ; ModuleID = 'call_sites.cpp'
84 source_filename = "call_sites.cpp"
85 target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128-Fn32"
86 target triple = "arm64-unknown-macosx10.4.0"
88 @g_volatile_var = global i32 0, align 4, !dbg !0
89 @g_func_ptr = global ptr null, align 8, !dbg !5
90 @g_extern_func_ptr = global ptr null, align 8, !dbg !12
92 ; Function Attrs: minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none)
93 define void @func_mainBin_dec_01() local_unnamed_addr #0 !dbg !21 {
94 entry:
95   %0 = load volatile i32, ptr @g_volatile_var, align 4, !dbg !24, !tbaa !25
96   %dec = add nsw i32 %0, -1, !dbg !24
97   store volatile i32 %dec, ptr @g_volatile_var, align 4, !dbg !24, !tbaa !25
98   ret void, !dbg !29
101 ; Function Attrs: minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none)
102 define void @func_mainBin_dec_02() local_unnamed_addr #0 !dbg !30 {
103 entry:
104   %0 = load volatile i32, ptr @g_volatile_var, align 4, !dbg !31, !tbaa !25
105   %dec = add nsw i32 %0, -1, !dbg !31
106   store volatile i32 %dec, ptr @g_volatile_var, align 4, !dbg !31, !tbaa !25
107   ret void, !dbg !32
110 ; Function Attrs: minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none)
111 define void @func_mainBin_dec_03() local_unnamed_addr #0 !dbg !33 {
112 entry:
113   %0 = load volatile i32, ptr @g_volatile_var, align 4, !dbg !34, !tbaa !25
114   %dec = add nsw i32 %0, -1, !dbg !34
115   store volatile i32 %dec, ptr @g_volatile_var, align 4, !dbg !34, !tbaa !25
116   ret void, !dbg !35
119 ; Function Attrs: minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none)
120 define void @func_mainBin_inc_01() local_unnamed_addr #0 !dbg !36 {
121 entry:
122   %0 = load volatile i32, ptr @g_volatile_var, align 4, !dbg !37, !tbaa !25
123   %inc = add nsw i32 %0, 1, !dbg !37
124   store volatile i32 %inc, ptr @g_volatile_var, align 4, !dbg !37, !tbaa !25
125   ret void, !dbg !38
128 ; Function Attrs: minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none)
129 define void @func_mainBin_inc_02() local_unnamed_addr #0 !dbg !39 {
130 entry:
131   %0 = load volatile i32, ptr @g_volatile_var, align 4, !dbg !40, !tbaa !25
132   %inc = add nsw i32 %0, 1, !dbg !40
133   store volatile i32 %inc, ptr @g_volatile_var, align 4, !dbg !40, !tbaa !25
134   ret void, !dbg !41
137 ; Function Attrs: minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none)
138 define void @func_mainBin_inc_03() local_unnamed_addr #0 !dbg !42 {
139 entry:
140   %0 = load volatile i32, ptr @g_volatile_var, align 4, !dbg !43, !tbaa !25
141   %inc = add nsw i32 %0, 1, !dbg !43
142   store volatile i32 %inc, ptr @g_volatile_var, align 4, !dbg !43, !tbaa !25
143   ret void, !dbg !44
146 ; Function Attrs: minsize mustprogress noinline nounwind optsize ssp
147 define void @func_mainBin_dec_call_everything() local_unnamed_addr #1 !dbg !45 {
148 entry:
149   tail call void @func_mainBin_dec_01() #3, !dbg !46
150   tail call void @func_mainBin_dec_02() #3, !dbg !47
151   tail call void @func_mainBin_dec_03() #3, !dbg !48
152   tail call void @func_mainBin_inc_01() #3, !dbg !49
153   tail call void @func_mainBin_inc_02() #3, !dbg !50
154   tail call void @func_mainBin_inc_03() #3, !dbg !51
155   %0 = load volatile ptr, ptr @g_func_ptr, align 8, !dbg !52, !tbaa !53
156   %call = tail call noundef i32 %0() #4, !dbg !52
157   %1 = load volatile ptr, ptr @g_extern_func_ptr, align 8, !dbg !55, !tbaa !53
158   %call1 = tail call noundef i32 %1() #4, !dbg !55
159   store volatile i32 0, ptr @g_volatile_var, align 4, !dbg !56, !tbaa !25
160   ret void, !dbg !57
163 ; Function Attrs: minsize mustprogress norecurse nounwind optsize ssp
164 define noundef i32 @main() local_unnamed_addr #2 !dbg !58 {
165 entry:
166   tail call void @func_mainBin_dec_call_everything() #3, !dbg !59
167   ret i32 0, !dbg !60
170 attributes #0 = { minsize mustprogress nofree noinline norecurse nounwind optsize ssp memory(readwrite, argmem: none) "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+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" }
171 attributes #1 = { minsize mustprogress noinline nounwind optsize ssp "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+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" }
172 attributes #2 = { minsize mustprogress norecurse nounwind optsize ssp "frame-pointer"="non-leaf" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "target-cpu"="apple-m1" "target-features"="+aes,+altnzcv,+ccdp,+ccidx,+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" }
173 attributes #3 = { minsize optsize }
174 attributes #4 = { minsize nounwind optsize }
176 !llvm.dbg.cu = !{!2}
177 !llvm.module.flags = !{!15, !16, !17, !18, !19}
178 !llvm.ident = !{!20}
180 !0 = !DIGlobalVariableExpression(var: !1, expr: !DIExpression())
181 !1 = distinct !DIGlobalVariable(name: "g_volatile_var", scope: !2, file: !3, line: 4, type: !14, isLocal: false, isDefinition: true)
182 !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus_14, file: !3, producer: "clang version 20.0.0git (https://github.com/alx32/llvm-project.git f41f6ea1f33c4f5e7c94f3d155e44292d1809c50)", isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, globals: !4, splitDebugInlining: false, nameTableKind: None, sysroot: "/")
183 !3 = !DIFile(filename: "call_sites.cpp", directory: "/tmp/tst")
184 !4 = !{!0, !5, !12}
185 !5 = !DIGlobalVariableExpression(var: !6, expr: !DIExpression())
186 !6 = distinct !DIGlobalVariable(name: "g_func_ptr", scope: !2, file: !3, line: 5, type: !7, isLocal: false, isDefinition: true)
187 !7 = !DIDerivedType(tag: DW_TAG_volatile_type, baseType: !8)
188 !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: !9, size: 64)
189 !9 = !DISubroutineType(types: !10)
190 !10 = !{!11}
191 !11 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
192 !12 = !DIGlobalVariableExpression(var: !13, expr: !DIExpression())
193 !13 = distinct !DIGlobalVariable(name: "g_extern_func_ptr", scope: !2, file: !3, line: 6, type: !7, isLocal: false, isDefinition: true)
194 !14 = !DIDerivedType(tag: DW_TAG_volatile_type, baseType: !11)
195 !15 = !{i32 7, !"Dwarf Version", i32 4}
196 !16 = !{i32 2, !"Debug Info Version", i32 3}
197 !17 = !{i32 1, !"wchar_size", i32 4}
198 !18 = !{i32 8, !"PIC Level", i32 2}
199 !19 = !{i32 7, !"frame-pointer", i32 1}
200 !20 = !{!"clang version 20.0.0git (https://github.com/alx32/llvm-project.git f41f6ea1f33c4f5e7c94f3d155e44292d1809c50)"}
201 !21 = distinct !DISubprogram(name: "func_mainBin_dec_01", scope: !3, file: !3, line: 8, type: !22, scopeLine: 8, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
202 !22 = !DISubroutineType(types: !23)
203 !23 = !{null}
204 !24 = !DILocation(line: 8, column: 54, scope: !21)
205 !25 = !{!26, !26, i64 0}
206 !26 = !{!"int", !27, i64 0}
207 !27 = !{!"omnipotent char", !28, i64 0}
208 !28 = !{!"Simple C++ TBAA"}
209 !29 = !DILocation(line: 8, column: 58, scope: !21)
210 !30 = distinct !DISubprogram(name: "func_mainBin_dec_02", scope: !3, file: !3, line: 9, type: !22, scopeLine: 9, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
211 !31 = !DILocation(line: 9, column: 54, scope: !30)
212 !32 = !DILocation(line: 9, column: 58, scope: !30)
213 !33 = distinct !DISubprogram(name: "func_mainBin_dec_03", scope: !3, file: !3, line: 10, type: !22, scopeLine: 10, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
214 !34 = !DILocation(line: 10, column: 54, scope: !33)
215 !35 = !DILocation(line: 10, column: 58, scope: !33)
216 !36 = distinct !DISubprogram(name: "func_mainBin_inc_01", scope: !3, file: !3, line: 12, type: !22, scopeLine: 12, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
217 !37 = !DILocation(line: 12, column: 54, scope: !36)
218 !38 = !DILocation(line: 12, column: 58, scope: !36)
219 !39 = distinct !DISubprogram(name: "func_mainBin_inc_02", scope: !3, file: !3, line: 13, type: !22, scopeLine: 13, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
220 !40 = !DILocation(line: 13, column: 54, scope: !39)
221 !41 = !DILocation(line: 13, column: 58, scope: !39)
222 !42 = distinct !DISubprogram(name: "func_mainBin_inc_03", scope: !3, file: !3, line: 14, type: !22, scopeLine: 14, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
223 !43 = !DILocation(line: 14, column: 54, scope: !42)
224 !44 = !DILocation(line: 14, column: 58, scope: !42)
225 !45 = distinct !DISubprogram(name: "func_mainBin_dec_call_everything", scope: !3, file: !3, line: 16, type: !22, scopeLine: 16, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
226 !46 = !DILocation(line: 17, column: 5, scope: !45)
227 !47 = !DILocation(line: 18, column: 5, scope: !45)
228 !48 = !DILocation(line: 19, column: 5, scope: !45)
229 !49 = !DILocation(line: 21, column: 5, scope: !45)
230 !50 = !DILocation(line: 22, column: 5, scope: !45)
231 !51 = !DILocation(line: 23, column: 5, scope: !45)
232 !52 = !DILocation(line: 25, column: 5, scope: !45)
233 !53 = !{!54, !54, i64 0}
234 !54 = !{!"any pointer", !27, i64 0}
235 !55 = !DILocation(line: 26, column: 5, scope: !45)
236 !56 = !DILocation(line: 28, column: 20, scope: !45)
237 !57 = !DILocation(line: 29, column: 1, scope: !45)
238 !58 = distinct !DISubprogram(name: "main", scope: !3, file: !3, line: 31, type: !9, scopeLine: 31, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !2)
239 !59 = !DILocation(line: 32, column: 3, scope: !58)
240 !60 = !DILocation(line: 33, column: 3, scope: !58)
243 //--- generate-callsite-test-data.sh
244 #!/bin/bash
245 ## This is provided for reference only, if we need to modify the file and regenerate the assembly code
246 set -ex
248 TOOLCHAIN_DIR="llvm-project/build/Debug/bin"
250 # Create call_sites.cpp
251 cat > call_sites.cpp <<EOF
253 #define FUNC_ATTR extern "C" __attribute__((noinline))
255 volatile int g_volatile_var;
256 int (*volatile g_func_ptr)();
257 int (*volatile g_extern_func_ptr)();
259 FUNC_ATTR void func_mainBin_dec_01() { g_volatile_var--; }
260 FUNC_ATTR void func_mainBin_dec_02() { g_volatile_var--; }
261 FUNC_ATTR void func_mainBin_dec_03() { g_volatile_var--; }
263 FUNC_ATTR void func_mainBin_inc_01() { g_volatile_var++; }
264 FUNC_ATTR void func_mainBin_inc_02() { g_volatile_var++; }
265 FUNC_ATTR void func_mainBin_inc_03() { g_volatile_var++; }
267 FUNC_ATTR void func_mainBin_dec_call_everything() {
268     func_mainBin_dec_01();
269     func_mainBin_dec_02();
270     func_mainBin_dec_03();
272     func_mainBin_inc_01();
273     func_mainBin_inc_02();
274     func_mainBin_inc_03();
276     g_func_ptr();
277     g_extern_func_ptr();
279     g_volatile_var = 0;
282 int main() {
283   func_mainBin_dec_call_everything();
284   return 0;
288 # Generate IR from call_sites.cpp
289 "$TOOLCHAIN_DIR"/clang++ -mno-outline -target arm64-apple-macos -g -Oz -fno-exceptions -S -emit-llvm call_sites.cpp -o call_sites.ll
291 # Compile the assembly into an object file
292 "$TOOLCHAIN_DIR"/llc -filetype=obj call_sites.ll -o call_sites.o
294 # Link the object file into an executable using lld directly
295 "$TOOLCHAIN_DIR"/ld64.lld -arch arm64 -platform_version macos 11.0.0 11.0.0 -o call_sites call_sites.o -lSystem
297 # Create a dSYM file
298 "$TOOLCHAIN_DIR"/dsymutil call_sites -o call_sites.dSYM
300 # Dump the binary to YAML
301 "$TOOLCHAIN_DIR"/obj2yaml call_sites > call_sites_binary.yaml
303 # Dump the dSYM to YAML
304 "$TOOLCHAIN_DIR"/obj2yaml call_sites.dSYM/Contents/Resources/DWARF/call_sites > call_sites_dsym.yaml