// RUN: %empty-directory(%t) // RUN: %target-swift-frontend -parse-as-library -target %target-swift-5.1-abi-triple -g -emit-sil -o - %s | %FileCheck -check-prefix=SIL %s // RUN: %target-swift-frontend -parse-as-library -target %target-swift-5.1-abi-triple -g -emit-ir -o - %s | %FileCheck %s // RUN: %target-swift-frontend -parse-as-library -target %target-swift-5.1-abi-triple -g -c %s -o %t/out.o // This test checks that: // // 1. At the IR level, we insert the appropriate #dbg_value. // // 2. At the Dwarf that we have proper locations with PC validity ranges where // the value isn't valid. // We only run this on macOS right now since we would need to pattern match // slightly differently on other platforms. // REQUIRES: OS=macosx // REQUIRES: CPU=x86_64 || CPU=arm64 ////////////////// // Declarations // ////////////////// public class Klass { public func doSomething() {} } public protocol P { static var value: P { get } func doSomething() } public var trueValue: Bool { true } public var falseValue: Bool { false } public func use(_ t: T) {} public func forceSplit() async {} public func forceSplit1() async {} public func forceSplit2() async {} public func forceSplit3() async {} public func forceSplit4() async {} public func forceSplit5() async {} /////////// // Tests // /////////// // CHECK-LABEL: define swifttailcc void @"$s27move_function_dbginfo_async13letSimpleTestyyxnYalF"(ptr swiftasync %0, ptr noalias %1, ptr %T) // CHECK: entry: // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[SIMPLE_TEST_METADATA:[0-9]+]], !DIExpression(DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: musttail call swifttailcc void // CHECK-NEXT: ret void // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async13letSimpleTestyyxnYalFTQ0_"(ptr swiftasync %0) // CHECK: entryresume.0: // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[SIMPLE_TEST_METADATA_2:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), // CHECK: musttail call swifttailcc void // CHECK-NEXT: ret void // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async13letSimpleTestyyxnYalFTY1_"(ptr swiftasync %0) // CHECK: entryresume.1: // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[SIMPLE_TEST_METADATA_3:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[SIMPLE_TEST_METADATA_3]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void // CHECK-NEXT: ret void // RUN: %llvm-dwarfdump -c --name='$s3out13letSimpleTestyyxnYalF' %t/out.o | %FileCheck -check-prefix=DWARF1 %s // DWARF1: DW_AT_linkage_name ("$s3out13letSimpleTestyyxnYalF") // DWARF1: DW_TAG_formal_parameter // DWARF1-NEXT: DW_AT_location // DWARF1-NOT: OP_entry_value // DWARF1: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out13letSimpleTestyyxnYalFTQ0_' %t/out.o | %FileCheck -check-prefix=DWARF2 %s // DWARF2: DW_AT_linkage_name ("$s3out13letSimpleTestyyxnYalFTQ0_") // DWARF2: DW_AT_name ("letSimpleTest") // DWARF2: DW_TAG_formal_parameter // DWARF2-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:DW_OP_.*]]), DW_OP_deref, DW_OP_plus_uconst 0x[[MSG_LOC:[a-f0-9]+]], DW_OP_deref) // DWARF2-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out13letSimpleTestyyxnYalFTY1_' %t/out.o | %FileCheck -check-prefix=DWARF3 %s // DWARF3: DW_AT_linkage_name ("$s3out13letSimpleTestyyxnYalFTY1_") // DWARF3: DW_AT_name ("letSimpleTest") // DWARF3: DW_TAG_formal_parameter // DWARF3: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF3-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x[[MSG_LOC:[a-f0-9]+]], DW_OP_deref) // DWARF3-NEXT: DW_AT_name ("msg") public func letSimpleTest(_ msg: __owned T) async { await forceSplit() use(consume msg) } // CHECK-LABEL: define swifttailcc void @"$s27move_function_dbginfo_async13varSimpleTestyyxz_xtYalF"(ptr swiftasync %0, ptr %1, ptr noalias %2, ptr %T) // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref) // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async10forceSplityyYaF"(ptr swiftasync %{{[0-9]+}}) // CHECK-NEXT: ret void // CHECK-NEXT: } // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async13varSimpleTestyyxz_xtYalFTQ0_"(ptr swiftasync %0) // CHECK: entryresume.0: // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref) // CHECK: musttail call swifttailcc void @swift_task_switch(ptr swiftasync %{{[0-9]+}}, ptr @"$s27move_function_dbginfo_async13varSimpleTestyyxz_xtYalFTY1_", i64 0, i64 0) // CHECK-NEXT: ret void // CHECK-NEXT: } // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async13varSimpleTestyyxz_xtYalFTY1_"(ptr swiftasync %0) // CHECK: entryresume.1: // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async10forceSplityyYaF"(ptr swiftasync // CHECK-NEXT: ret void // CHECK-NEXT: } // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async13varSimpleTestyyxz_xtYalFTQ2_"(ptr swiftasync %0) // CHECK: entryresume.2: // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async13varSimpleTestyyxz_xtYalFTY3_"(ptr swiftasync %0) // CHECK: entryresume.3: // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async10forceSplityyYaF"( // CHECK-NEXT: ret void // CHECK-NEXT: } // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalF' %t/out.o | %FileCheck -check-prefix=DWARF4 %s // DWARF4: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalF") // DWARF4: DW_AT_name ("varSimpleTest") // DWARF4: DW_TAG_formal_parameter // DWARF4-NEXT: DW_AT_location // DWARF4-NOT: OP_entry_value // DWARF4: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalFTQ0_' %t/out.o | %FileCheck -check-prefix=DWARF5 %s // DWARF5: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalFTQ0_") // DWARF5: DW_AT_name ("varSimpleTest") // DWARF5: DW_TAG_formal_parameter // DWARF5-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_deref, DW_OP_plus_uconst 0x[[MSG_LOC:[a-f0-9]+]], DW_OP_deref) // DWARF5-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalFTY1_' %t/out.o | %FileCheck -check-prefix=DWARF6 %s // DWARF6: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalFTY1_") // DWARF6: DW_AT_name ("varSimpleTest") // DWARF6: DW_TAG_formal_parameter // DWARF6-NEXT: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF6-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x[[MSG_LOC:[a-f0-9]+]], DW_OP_deref) // DWARF6-NEXT: DW_AT_name ("msg") // // We were just moved and are not reinit yet. This is caused by us hopping twice // when we return from an async function. Once for the async function and then // for the hop to executor. // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalFTQ2_' %t/out.o | %FileCheck -check-prefix=DWARF7 %s // DWARF7: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalFTQ2_") // DWARF7: DW_AT_name ("varSimpleTest") // DWARF7: DW_TAG_formal_parameter // DWARF7-NEXT: DW_AT_name ("msg") // // We reinitialize our value in this funclet and then consume it and then // reinitialize it again. So we have two different live ranges. Sadly, we don't // validate that the first live range doesn't start at the beginning of the // function. But we have lldb tests to validate that. // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalFTY3_' %t/out.o | %FileCheck -check-prefix=DWARF8 %s // DWARF8: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalFTY3_") // DWARF8: DW_AT_name ("varSimpleTest") // DWARF8: DW_TAG_formal_parameter // DWARF8: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF8-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): // DWARF8-SAME: DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x[[MSG_LOC:[a-f0-9]+]], DW_OP_deref // DWARF8-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): // DWARF8-SAME: DW_OP_entry_value([[ASYNC_REG]]), DW_OP_plus_uconst 0x[[MSG_LOC]], DW_OP_deref // DWARF8-NEXT: DW_AT_name ("msg") // // We did not consume the value again here, so we just get a normal entry value for // the entire function. // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalFTQ4_' %t/out.o | %FileCheck -check-prefix=DWARF9 %s // DWARF9: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalFTQ4_") // DWARF9: DW_AT_name ("varSimpleTest") // DWARF9: DW_TAG_formal_parameter // DWARF9-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_deref, DW_OP_plus_uconst 0x[[MSG_LOC:[a-f0-9]+]], DW_OP_deref) // DWARF9-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out13varSimpleTestyyxz_xtYalFTY5_' %t/out.o | %FileCheck -check-prefix=DWARF10 %s // DWARF10: DW_AT_linkage_name ("$s3out13varSimpleTestyyxz_xtYalFTY5_") // DWARF10: DW_AT_name ("varSimpleTest") // DWARF10: DW_TAG_formal_parameter // DWARF10-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x18, DW_OP_deref // DWARF10-NEXT: DW_AT_name ("msg") // Change name to varSimpleTestArg public func varSimpleTest(_ msg: inout T, _ msg2: T) async { await forceSplit() use(consume msg) await forceSplit() msg = msg2 let msg3 = consume msg let _ = msg3 msg = msg2 await forceSplit() } // CHECK-LABEL: define swifttailcc void @"$s27move_function_dbginfo_async16varSimpleTestVaryyYaF"(ptr swiftasync %0) // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async16varSimpleTestVaryyYaFTY0_"(ptr swiftasync %0) // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref) // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async16varSimpleTestVaryyYaFTQ1_"(ptr swiftasync %0) // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 24, DW_OP_deref) // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async16varSimpleTestVaryyYaFTY2_"(ptr swiftasync %0) // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(), ![[ADDR_LOC]] // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async16varSimpleTestVaryyYaFTQ3_"(ptr swiftasync %0) // CHECK: #dbg_value(ptr undef, // // We should see first a #dbg_value to undef the value until we reinit. Then // we should see a #dbg_value to reinit. // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async16varSimpleTestVaryyYaFTY4_"(ptr swiftasync %0) // CHECK: #dbg_value(ptr undef, ![[METADATA:[0-9]+]], !DIExpression(), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref), ![[ADDR_LOC]] // We are not an argument, so no problem here. // // RUN: %llvm-dwarfdump -c --name='$s3out16varSimpleTestVaryyYaF' %t/out.o | %FileCheck -check-prefix=DWARF11 %s // DWARF11: DW_AT_linkage_name ("$s3out16varSimpleTestVaryyYaF") // // RUN: %llvm-dwarfdump -c --name='$s3out16varSimpleTestVaryyYaFTY0_' %t/out.o | %FileCheck -check-prefix=DWARF12 %s // DWARF12: DW_AT_linkage_name ("$s3out16varSimpleTestVaryyYaFTY0_") // // DWARF12: DW_TAG_variable // DWARF12-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x18) // DWARF12-NEXT: DW_AT_name ("k") // // MISSING-DWARF12: DW_TAG_variable // MISSING-DWARF12-NEXT: DW_AT_location // MISSING-DWARF12-NEXT: DW_AT_name ("m") // // RUN: %llvm-dwarfdump -c --name='$s3out16varSimpleTestVaryyYaFTQ1_' %t/out.o | %FileCheck -check-prefix=DWARF13 %s // DWARF13: DW_AT_linkage_name ("$s3out16varSimpleTestVaryyYaFTQ1_") // // DWARF13: DW_TAG_variable // DWARF13-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_deref, DW_OP_plus_uconst 0x18) // DWARF13-NEXT: DW_AT_name ("k") // // MISSING-DWARF13: DW_TAG_variable // We don't pattern match the actual entry value of "m" since we don't guarantee // it is an entry value since it isn't moved. // MISSING-DWARF13-NEXT: DW_AT_location // MISSING-DWARF13-NEXT: DW_AT_name ("m") // // RUN: %llvm-dwarfdump -c --name='$s3out16varSimpleTestVaryyYaFTY2_' %t/out.o | %FileCheck -check-prefix=DWARF14 %s // DWARF14: DW_AT_linkage_name ("$s3out16varSimpleTestVaryyYaFTY2_") // DWARF14: DW_TAG_variable // DWARF14-NEXT: DW_AT_location (0x{{[0-9a-f]+}}: // DWARF14-NEXT: [0x{{[0-9a-f]+}}, 0x{{[0-9a-f]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x18) // DWARF14-NEXT: DW_AT_name ("k") // DWARF14: DW_TAG_variable // DWARF14-NEXT: DW_AT_location // DWARF14-NEXT: DW_AT_name ("m") // // RUN: %llvm-dwarfdump -c --name='$s3out16varSimpleTestVaryyYaFTQ3_' %t/out.o | %FileCheck -check-prefix=DWARF15 %s // DWARF15: DW_AT_linkage_name ("$s3out16varSimpleTestVaryyYaFTQ3_") // MISSING-DWARF15: DW_TAG_variable // We don't pattern match the actual entry value of "m" since we don't guarantee // it is an entry value since it isn't moved. // MISSING-DWARF15-NEXT: DW_AT_location // MISSING-DWARF15-NEXT: DW_AT_name ("m") // K is dead here. // DWARF15: DW_TAG_variable // DWARF15-NEXT: DW_AT_name ("k") // // We reinitialize k in 4. // RUN: %llvm-dwarfdump -c --name='$s3out16varSimpleTestVaryyYaFTY4_' %t/out.o | %FileCheck -check-prefix=DWARF16 %s // DWARF16: DW_AT_linkage_name ("$s3out16varSimpleTestVaryyYaFTY4_") // MISSING-DWARF16: DW_TAG_variable // We don't pattern match the actual entry value of "m" since we don't guarantee // it is an entry value since it isn't moved. // MISSING-DWARF16-NEXT: DW_AT_location // MISSING-DWARF16-NEXT: DW_AT_name ("m") // DWARF16: DW_TAG_variable // DWARF16-NEXT: DW_AT_location (0x{{[0-9a-f]+}}: // DWARF16-NEXT: [0x{{[0-9a-f]+}}, 0x{{[0-9a-f]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x18) // DWARF16-NEXT: DW_AT_name ("k") public func varSimpleTestVar() async { var k = Klass() k.doSomething() await forceSplit() let m = consume k m.doSomething() await forceSplit() k = Klass() k.doSomething() print("stop here") } //////////////////////////////////// // Conditional Control Flow Tests // //////////////////////////////////// // CHECK-LABEL: define swifttailcc void @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalF"( // CHECK: #dbg_value( // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit1yyYaF"( // CHECK-NEXT: ret void // CHECK-NEXT: } // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalFTQ0_"( // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), // CHECK: musttail call swifttailcc void @swift_task_switch(ptr swiftasync %{{[0-9]+}}, ptr @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalFTY1_", i64 0, i64 0) // CHECK-NEXT: ret void // CHECK-NEXT: } // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalFTY1_"( // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA:[0-9]*]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]*]] // CHECK: br i1 %{{[0-9]}}, label %[[LHS_BLOCK:[a-zA-Z\.0-9]*]], label %[[RHS_BLOCK:[a-zA-Z\.0-9]*]], // // CHECK: [[LHS_BLOCK]]: // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit2yyYaF"( // CHECK-NEXT: ret void // // CHECK: [[RHS_BLOCK]]: // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit3yyYaF"( // CHECK-NEXT: ret void // // We have two undef here due to the coroutine cloner functionally tail // duplicating the true and the continuation. This causes us to have a // debug_value undef from the merge point and one that was propagated from the // _move. // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalFTQ2_"( // CHECK: #dbg_value(ptr undef, ![[METADATA:[0-9]*]], !DIExpression(DW_OP_deref), ![[ADDR_LOC:[0-9]*]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit4yyYaF"( // CHECK-NEXT: ret void // // This is the false branch. // // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalFTQ3_"( // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[msg_var:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 24, DW_OP_deref, DW_OP_deref) // CHECK-NEXT: #dbg_value(ptr undef, ![[msg_var]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit4yyYaF"( // CHECK-NEXT: ret void, // CHECK-NEXT: } // // This is the continuation block // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20letArgCCFlowTrueTestyyxnYalFTQ4_"( // CHECK: #dbg_value(ptr undef, !{{.*}}, !DIExpression(DW_OP_deref), // RUN: %llvm-dwarfdump -c --name='$s3out20letArgCCFlowTrueTestyyxnYalF' %t/out.o | %FileCheck -check-prefix=DWARF17 %s // DWARF17: DW_TAG_subprogram // DWARF17: DW_AT_linkage_name ("$s3out20letArgCCFlowTrueTestyyxnYalF") // DWARF17: DW_AT_name ("letArgCCFlowTrueTest") // DWARF17: DW_TAG_formal_parameter // DWARF17-NEXT: DW_AT_location // DWARF17-NOT: OP_entry_value // DWARF17: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20letArgCCFlowTrueTestyyxnYalFTQ0_' %t/out.o | %FileCheck -check-prefix=DWARF18 %s // DWARF18: DW_AT_linkage_name ("$s3out20letArgCCFlowTrueTestyyxnYalFTQ0_") // DWARF18-NEXT: DW_AT_name ("letArgCCFlowTrueTest") // DWARF18: DW_TAG_formal_parameter // DWARF18-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_deref, DW_OP_plus_uconst 0x18, DW_OP_deref) // DWARF18-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20letArgCCFlowTrueTestyyxnYalFTY1_' %t/out.o | %FileCheck -check-prefix=DWARF19 %s // DWARF19: DW_AT_linkage_name ("$s3out20letArgCCFlowTrueTestyyxnYalFTY1_") // DWARF19-NEXT: DW_AT_name ("letArgCCFlowTrueTest") // DWARF19: DW_TAG_formal_parameter // DWARF19-NEXT: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF19-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x18, DW_OP_deref // DWARF19-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG]]), DW_OP_plus_uconst 0x18, DW_OP_deref) // DWARF19-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20letArgCCFlowTrueTestyyxnYalFTQ2_' %t/out.o | %FileCheck -check-prefix=DWARF20 %s // DWARF20: DW_AT_linkage_name ("$s3out20letArgCCFlowTrueTestyyxnYalFTQ2_") // DWARF20-NEXT: DW_AT_name ("letArgCCFlowTrueTest") // DWARF20: DW_TAG_formal_parameter // DWARF20-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20letArgCCFlowTrueTestyyxnYalFTQ3_' %t/out.o | %FileCheck -check-prefix=DWARF21 %s // DWARF21: DW_AT_linkage_name ("$s3out20letArgCCFlowTrueTestyyxnYalFTQ3_") // DWARF21-NEXT: DW_AT_name ("letArgCCFlowTrueTest") // DWARF21: DW_TAG_formal_parameter // DWARF21-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20letArgCCFlowTrueTestyyxnYalFTQ4_' %t/out.o | %FileCheck -check-prefix=DWARF22 %s // DWARF22: DW_AT_linkage_name ("$s3out20letArgCCFlowTrueTestyyxnYalFTQ4_") // DWARF22-NEXT: DW_AT_name ("letArgCCFlowTrueTest") // DWARF22: DW_TAG_formal_parameter // DWARF22-NEXT: DW_AT_name ("msg") public func letArgCCFlowTrueTest(_ msg: __owned T) async { await forceSplit1() if trueValue { use(consume msg) await forceSplit2() } else { await forceSplit3() } await forceSplit4() } // We do an extra SIL check here to make sure we propagate merge points // correctly. // SIL-LABEL: sil @$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlF : $@convention(thin) @async (@inout T) -> () { // SIL: bb0([[ARG:%[0-9]+]] : $*T): // SIL: debug_value [moveable_value_debuginfo] [[ARG]] // SIL: [[FORCE_SPLIT_1:%[0-9]+]] = function_ref @$s27move_function_dbginfo_async11forceSplit1yyYaF : $@convention(thin) @async () -> () // SIL: apply [[FORCE_SPLIT_1]] // SIL-NEXT: debug_value [moveable_value_debuginfo] [[ARG]] // SIL: hop_to_executor // SIL-NEXT: debug_value [moveable_value_debuginfo] [[ARG]] // SIL: cond_br {{%[0-9]+}}, bb1, bb2 // // SIL: bb1: // SIL: debug_value [moveable_value_debuginfo] undef // SIL: [[FORCE_SPLIT_2:%[0-9]+]] = function_ref @$s27move_function_dbginfo_async11forceSplit2yyYaF : $@convention(thin) @async () -> () // SIL: apply [[FORCE_SPLIT_2]]() // SIL-NEXT: debug_value [moveable_value_debuginfo] undef // SIL: hop_to_executor // SIL-NEXT: debug_value [moveable_value_debuginfo] undef // SIL: br bb3 // // SIL: bb2: // SIL: [[FORCE_SPLIT_3:%[0-9]+]] = function_ref @$s27move_function_dbginfo_async11forceSplit3yyYaF : $@convention(thin) @async () -> () // SIL: apply [[FORCE_SPLIT_3]] // SIL-NEXT: debug_value [moveable_value_debuginfo] [[ARG]] // SIL: debug_value [moveable_value_debuginfo] undef // SIL: hop_to_executor // SIL-NEXT: debug_value [moveable_value_debuginfo] undef // // SIL: bb3: // SIL-NEXT: debug_value [moveable_value_debuginfo] undef // SIL: debug_value [moveable_value_debuginfo] [[ARG]] // SIL: [[FORCE_SPLIT_4:%[0-9]+]] = function_ref @$s27move_function_dbginfo_async11forceSplit4yyYaF : $@convention(thin) @async () -> () // SIL: apply [[FORCE_SPLIT_4]] // SIL-NEXT: debug_value [moveable_value_debuginfo] %0 // SIL: } // end sil function '$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlF' // CHECK-LABEL: define swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlF"( // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit1yyYaF"( // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ0_"( // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY1_"( // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: br i1 %{{[0-9]+}}, label %[[LHS_BLOCK:[a-zA-Z0-9]+]], label %[[RHS_BLOCK:[a-zA-Z0-9]+]] // CHECK: [[LHS_BLOCK]]: // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit2yyYaF"( // CHECK: [[RHS_BLOCK]]: // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit3yyYaF"( // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ2_"( // CHECK: #dbg_value(ptr undef, !{{[0-9]+}}, !DIExpression(DW_OP_deref), // CHECK: musttail call swifttailcc void @swift_task_switch(ptr swiftasync %{{[0-9]+}}, ptr @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY3_", i64 0, i64 0) // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY3_"( // CHECK: #dbg_value(ptr undef, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit4yyYaF"( // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ4_"( // CHECK-NOT: #dbg_value // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @swift_task_switch(ptr swiftasync %{{[0-9]+}}, ptr @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY5_", // CHECK: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY5_"( // CHECK: #dbg_value(ptr undef, ![[METADATA:[0-9]+]], !DIExpression(DW_OP_deref), ![[ADDR_LOC:[0-9]+]] // CHECK: #dbg_value(ptr undef, ![[METADATA]], !DIExpression(DW_OP_deref), ![[ADDR_LOC]] // CHECK: #dbg_value(ptr %{{[0-9]+}}, ![[METADATA]], !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), ![[ADDR_LOC]] // CHECK: musttail call swifttailcc void @"$s27move_function_dbginfo_async11forceSplit4yyYaF"( // CHECK-LABEL: define internal swifttailcc void @"$s27move_function_dbginfo_async20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ6_"( // CHECK-NOT: #dbg_value( // CHECK: #dbg_value(ptr %{{[0-9]+}}, !{{[0-9]+}}, !DIExpression(DW_OP_LLVM_entry_value, 1, DW_OP_deref, DW_OP_plus_uconst, 64, DW_OP_deref, DW_OP_deref), // CHECK-NOT: #dbg_value( // CHECK: musttail call swifttailcc void %{{[0-9]+}}(ptr swiftasync // CHECK-NEXT: ret void, // CHECK-NEXT: } // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlF' %t/out.o | %FileCheck -check-prefix=DWARF24 %s // DWARF24: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlF") // DWARF24: DW_AT_name ("varArgCCFlowTrueTest") // DWARF24: DW_TAG_formal_parameter // DWARF24-NEXT: DW_AT_location // DWARF24-NOT: OP_entry_value // DWARF24: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ0_' %t/out.o | %FileCheck -check-prefix=DWARF25 %s // DWARF25: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ0_") // DWARF25-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF25: DW_TAG_formal_parameter // DWARF25-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_deref, DW_OP_plus_uconst 0x40, DW_OP_deref) // DWARF25-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY1_' %t/out.o | %FileCheck -check-prefix=DWARF26 %s // DWARF26: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY1_") // DWARF26-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF26: DW_TAG_formal_parameter // DWARF26-NEXT: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF26-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x40, DW_OP_deref // DWARF26-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG]]), DW_OP_plus_uconst 0x40, DW_OP_deref) // DWARF26-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ2_' %t/out.o | %FileCheck -check-prefix=DWARF27 %s // DWARF27: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ2_") // DWARF-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF: DW_TAG_formal_parameter // DWARF-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY3_' %t/out.o | %FileCheck -check-prefix=DWARF28 %s // DWARF28: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY3_") // DWARF28-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF28: DW_TAG_formal_parameter // DWARF28-NEXT: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF28-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x40, DW_OP_deref) // DWARF28-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ4_' %t/out.o | %FileCheck -check-prefix=DWARF29 %s // DWARF29: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ4_") // DWARF29-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF29: DW_TAG_formal_parameter // DWARF29-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY5_' %t/out.o | %FileCheck -check-prefix=DWARF30 %s // DWARF30: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTY5_") // DWARF30-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF30: DW_TAG_formal_parameter // DWARF30-NEXT: DW_AT_location (0x{{[a-f0-9]+}}: // DWARF30-NEXT: [0x{{[a-f0-9]+}}, 0x{{[a-f0-9]+}}): DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_plus_uconst 0x40, DW_OP_deref) // DWARF30-NEXT: DW_AT_name ("msg") // // RUN: %llvm-dwarfdump -c --name='$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ6_' %t/out.o | %FileCheck -check-prefix=DWARF31 %s // DWARF31: DW_AT_linkage_name ("$s3out20varArgCCFlowTrueTestyyxzYaAA1PRzlFTQ6_") // DWARF31-NEXT: DW_AT_name ("varArgCCFlowTrueTest") // DWARF31: DW_TAG_formal_parameter // DWARF31-NEXT: DW_AT_location (DW_OP_entry_value([[ASYNC_REG:.*]]), DW_OP_deref, DW_OP_plus_uconst 0x40, DW_OP_deref) // DWARF31-NEXT: DW_AT_name ("msg") public func varArgCCFlowTrueTest(_ msg: inout T) async { await forceSplit1() if trueValue { use(consume msg) await forceSplit2() } else { await forceSplit3() } msg = T.value as! T await forceSplit4() }