Преглед изворни кода

Start plumbing through debug info type information with function parameters/return value (#6410)

This adds just enough debug info for i32/int parameters and return
values, with a path forward for adding DWARF type metadata for other
types.

As it happens, return type information is carried separately from
parameter information:
* Return type information is carried in the `type` of the `DISubprogram`
  (as a `DISubroutineType` - which does carry parameter type information
  as well, but that's unused when the DWARF is emitted by LLVM)
* Parameter information is carried by `DILocalVariable`s with a non-zero
  `arg` value (representing the order of function parameters)

In the absence of locations for the parameters (future work), nothing
would usually keep the `DILocalVariable` live/reachable when emitting
DWARF - so for cases where this can happen (for clang, this happens in
optimized builds where all references to the parameter variable might be
optimized away) the variables can be "retained" in a list on the
`DISubprogram` - achieved by passing `AlwaysPreserve` parameter to
`createParameterVariable` (adds them to a list, then that list gets
attached to the `DISubprogram` when it's finalized later)

For now, any unsupported types are emitted as `void*` (except void
return, which is implemented as void) as a placeholder.

Given this example:
```
import Core library "io";
class MyClass {
}
fn Unsupported(v: MyClass) {
}
fn Ret() -> i32 {
  return 42;
}
fn Arg(x: i32) {
  Core.Print(x);
}
fn Run() {
}
```
this is the resulting DWARF:
```
DW_TAG_compile_unit
  DW_AT_name    ("test.carbon")
  DW_TAG_subprogram
    DW_AT_name  ("Unsupported")
    DW_TAG_formal_parameter
      DW_AT_type        (0x00000066 "void *")
  DW_TAG_subprogram
    DW_AT_name  ("Ret")
    DW_AT_type  (0x00000062 "int")
  DW_TAG_subprogram
    DW_AT_name  ("Arg")
    DW_TAG_formal_parameter
      DW_AT_type        (0x00000062 "int")
  DW_TAG_subprogram
    DW_AT_name  ("Run")
  DW_TAG_base_type
    DW_AT_name  ("int")
  DW_TAG_pointer_type
```
And the debugger:
```
(gdb) p Ret()
$1 = 42
(gdb) p Arg(4)
4
$2 = void
```

I'm not sure if there's a way this logic should be merged with the logic
for making the `llvm::Function` type (which the `DISubroutineType`
building code was inspired by/copied from) - since they're done at
different times/places, I don't think there's an easy way to do it in
one pass, but maybe the code can be shared (even if it's run twice) in
some generic `SemIR::Function` type walker.

---------

Co-authored-by: Dana Jansens <danakj@orodu.net>
David Blaikie пре 5 месеци
родитељ
комит
a179bd461b
100 измењених фајлова са 5383 додато и 3939 уклоњено
  1. 6 5
      toolchain/driver/testdata/compile/optimize/clang_no_optimize_twice.carbon
  2. 55 40
      toolchain/driver/testdata/compile/optimize/optimize_debug.carbon
  3. 55 40
      toolchain/driver/testdata/compile/optimize/optimize_default.carbon
  4. 79 60
      toolchain/driver/testdata/compile/optimize/optimize_none.carbon
  5. 79 60
      toolchain/driver/testdata/compile/optimize/optimize_size.carbon
  6. 72 57
      toolchain/driver/testdata/compile/optimize/optimize_speed.carbon
  7. 147 57
      toolchain/lower/file_context.cpp
  8. 25 6
      toolchain/lower/file_context.h
  9. 10 9
      toolchain/lower/testdata/alias/local.carbon
  10. 1 1
      toolchain/lower/testdata/array/array_in_place.carbon
  11. 29 26
      toolchain/lower/testdata/array/assign_return_value.carbon
  12. 1 1
      toolchain/lower/testdata/array/base.carbon
  13. 37 29
      toolchain/lower/testdata/array/field.carbon
  14. 27 20
      toolchain/lower/testdata/array/function_param.carbon
  15. 147 105
      toolchain/lower/testdata/array/iterate.carbon
  16. 32 22
      toolchain/lower/testdata/builtins/bool.carbon
  17. 10 9
      toolchain/lower/testdata/builtins/char.carbon
  18. 183 122
      toolchain/lower/testdata/builtins/float.carbon
  19. 515 355
      toolchain/lower/testdata/builtins/int.carbon
  20. 22 16
      toolchain/lower/testdata/builtins/int_literal.carbon
  21. 78 62
      toolchain/lower/testdata/builtins/maybe_unformed.carbon
  22. 19 12
      toolchain/lower/testdata/builtins/method_vs_nonmethod.carbon
  23. 22 19
      toolchain/lower/testdata/builtins/no_op.carbon
  24. 12 7
      toolchain/lower/testdata/builtins/overloaded_operator.carbon
  25. 14 9
      toolchain/lower/testdata/builtins/pointer.carbon
  26. 1 1
      toolchain/lower/testdata/builtins/print_read.carbon
  27. 2 2
      toolchain/lower/testdata/builtins/type.carbon
  28. 1 1
      toolchain/lower/testdata/builtins/types.carbon
  29. 166 108
      toolchain/lower/testdata/builtins/uint.carbon
  30. 54 41
      toolchain/lower/testdata/class/adapt.carbon
  31. 37 30
      toolchain/lower/testdata/class/base.carbon
  32. 1 1
      toolchain/lower/testdata/class/basic.carbon
  33. 35 25
      toolchain/lower/testdata/class/convert.carbon
  34. 33 27
      toolchain/lower/testdata/class/field.carbon
  35. 214 179
      toolchain/lower/testdata/class/generic.carbon
  36. 1 1
      toolchain/lower/testdata/class/import.carbon
  37. 11 8
      toolchain/lower/testdata/class/method.carbon
  38. 22 14
      toolchain/lower/testdata/class/self.carbon
  39. 25 21
      toolchain/lower/testdata/class/value_access.carbon
  40. 106 76
      toolchain/lower/testdata/class/virtual.carbon
  41. 89 67
      toolchain/lower/testdata/for/bindings.carbon
  42. 155 113
      toolchain/lower/testdata/for/break_continue.carbon
  43. 155 113
      toolchain/lower/testdata/for/for.carbon
  44. 15 12
      toolchain/lower/testdata/function/call/empty_struct.carbon
  45. 15 12
      toolchain/lower/testdata/function/call/empty_tuple.carbon
  46. 19 14
      toolchain/lower/testdata/function/call/i32.carbon
  47. 20 17
      toolchain/lower/testdata/function/call/implicit_empty_tuple_as_arg.carbon
  48. 15 10
      toolchain/lower/testdata/function/call/params_one.carbon
  49. 17 12
      toolchain/lower/testdata/function/call/params_one_comma.carbon
  50. 16 10
      toolchain/lower/testdata/function/call/params_two.carbon
  51. 18 12
      toolchain/lower/testdata/function/call/params_two_comma.carbon
  52. 1 1
      toolchain/lower/testdata/function/call/params_zero.carbon
  53. 19 14
      toolchain/lower/testdata/function/call/ref_param.carbon
  54. 1 1
      toolchain/lower/testdata/function/call/return_implicit.carbon
  55. 16 10
      toolchain/lower/testdata/function/call/struct_param.carbon
  56. 16 10
      toolchain/lower/testdata/function/call/tuple_param.carbon
  57. 33 27
      toolchain/lower/testdata/function/call/tuple_param_with_return_slot.carbon
  58. 21 16
      toolchain/lower/testdata/function/call/var_param.carbon
  59. 9 6
      toolchain/lower/testdata/function/declaration/simple.carbon
  60. 76 63
      toolchain/lower/testdata/function/definition/destroy.carbon
  61. 1 1
      toolchain/lower/testdata/function/definition/empty_struct.carbon
  62. 7 4
      toolchain/lower/testdata/function/definition/params_one.carbon
  63. 8 4
      toolchain/lower/testdata/function/definition/params_two.carbon
  64. 1 1
      toolchain/lower/testdata/function/definition/params_zero.carbon
  65. 1 1
      toolchain/lower/testdata/function/definition/raw_name.carbon
  66. 83 62
      toolchain/lower/testdata/function/definition/var_param.carbon
  67. 30 16
      toolchain/lower/testdata/function/generic/call.carbon
  68. 217 187
      toolchain/lower/testdata/function/generic/call_basic.carbon
  69. 32 21
      toolchain/lower/testdata/function/generic/call_basic_depth.carbon
  70. 9 4
      toolchain/lower/testdata/function/generic/call_dedup_ptr.carbon
  71. 72 50
      toolchain/lower/testdata/function/generic/call_deref_ptr.carbon
  72. 1 1
      toolchain/lower/testdata/function/generic/call_different_associated_const.carbon
  73. 1 1
      toolchain/lower/testdata/function/generic/call_different_impls.carbon
  74. 47 41
      toolchain/lower/testdata/function/generic/call_different_impls_with_const.carbon
  75. 72 50
      toolchain/lower/testdata/function/generic/call_different_specific.carbon
  76. 25 18
      toolchain/lower/testdata/function/generic/call_impl_function.carbon
  77. 26 19
      toolchain/lower/testdata/function/generic/call_method.carbon
  78. 126 104
      toolchain/lower/testdata/function/generic/call_recursive_basic.carbon
  79. 177 135
      toolchain/lower/testdata/function/generic/call_recursive_diamond.carbon
  80. 39 32
      toolchain/lower/testdata/function/generic/call_recursive_impl.carbon
  81. 108 84
      toolchain/lower/testdata/function/generic/call_recursive_mutual.carbon
  82. 22 14
      toolchain/lower/testdata/function/generic/call_recursive_reorder.carbon
  83. 145 98
      toolchain/lower/testdata/function/generic/call_recursive_reorder_more.carbon
  84. 286 213
      toolchain/lower/testdata/function/generic/call_recursive_sccs_deep.carbon
  85. 114 76
      toolchain/lower/testdata/function/generic/call_specific_in_class.carbon
  86. 29 17
      toolchain/lower/testdata/function/generic/cross_library_name_collision_private.carbon
  87. 47 39
      toolchain/lower/testdata/function/generic/import.carbon
  88. 136 97
      toolchain/lower/testdata/function/generic/reverse_canonical.carbon
  89. 92 75
      toolchain/lower/testdata/function/generic/self_canonical.carbon
  90. 167 137
      toolchain/lower/testdata/function/generic/type_representation.carbon
  91. 1 1
      toolchain/lower/testdata/global/class_obj.carbon
  92. 13 10
      toolchain/lower/testdata/global/class_with_fun.carbon
  93. 1 1
      toolchain/lower/testdata/global/simple_init.carbon
  94. 14 11
      toolchain/lower/testdata/global/simple_with_fun.carbon
  95. 18 15
      toolchain/lower/testdata/global/use.carbon
  96. 20 15
      toolchain/lower/testdata/if/else.carbon
  97. 17 12
      toolchain/lower/testdata/if/no_else.carbon
  98. 25 19
      toolchain/lower/testdata/if_expr/basic.carbon
  99. 22 16
      toolchain/lower/testdata/if_expr/empty_block.carbon
  100. 19 13
      toolchain/lower/testdata/impl/assoc_fn_alias.carbon

+ 6 - 5
toolchain/driver/testdata/compile/optimize/clang_no_optimize_twice.carbon

@@ -36,8 +36,8 @@ fn Call() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
 // CHECK:STDOUT: define i32 @_CCall.Main() #0 !dbg !7 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %g.call = call i32 @_Z1gv(), !dbg !10
-// CHECK:STDOUT:   ret i32 %g.call, !dbg !11
+// CHECK:STDOUT:   %g.call = call i32 @_Z1gv(), !dbg !11
+// CHECK:STDOUT:   ret i32 %g.call, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: mustprogress noinline optnone
@@ -69,6 +69,7 @@ fn Call() -> i32 {
 // CHECK:STDOUT: !6 = !DIFile(filename: "foo.carbon", directory: "")
 // CHECK:STDOUT: !7 = distinct !DISubprogram(name: "Call", linkageName: "_CCall.Main", scope: null, file: !6, line: 12, type: !8, spFlags: DISPFlagDefinition, unit: !5)
 // CHECK:STDOUT: !8 = !DISubroutineType(types: !9)
-// CHECK:STDOUT: !9 = !{}
-// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 10, scope: !7)
-// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 3, scope: !7)
+// CHECK:STDOUT: !9 = !{!10}
+// CHECK:STDOUT: !10 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 10, scope: !7)
+// CHECK:STDOUT: !12 = !DILocation(line: 13, column: 3, scope: !7)

+ 55 - 40
toolchain/driver/testdata/compile/optimize/optimize_debug.carbon

@@ -43,39 +43,39 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CNoInlineWithOz.Main() local_unnamed_addr #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15 = tail call i32 @_CRand.Main() #0, !dbg !7
-// CHECK:STDOUT:   %Rand.call.loc7_24 = tail call i32 @_CRand.Main() #0, !dbg !8
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_24, %Rand.call.loc7_15, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !9
+// CHECK:STDOUT:   %Rand.call.loc7_15 = tail call i32 @_CRand.Main() #0, !dbg !8
+// CHECK:STDOUT:   %Rand.call.loc7_24 = tail call i32 @_CRand.Main() #0, !dbg !9
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_24, %Rand.call.loc7_15, !dbg !8
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() local_unnamed_addr #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() local_unnamed_addr #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15.i = tail call i32 @_CRand.Main() #0, !dbg !11
-// CHECK:STDOUT:   %Rand.call.loc7_24.i = tail call i32 @_CRand.Main() #0, !dbg !13
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.i = add i32 %Rand.call.loc7_24.i, %Rand.call.loc7_15.i, !dbg !11
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.i, !dbg !14
+// CHECK:STDOUT:   %Rand.call.loc7_15.i = tail call i32 @_CRand.Main() #0, !dbg !12
+// CHECK:STDOUT:   %Rand.call.loc7_24.i = tail call i32 @_CRand.Main() #0, !dbg !14
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.i = add i32 %Rand.call.loc7_24.i, %Rand.call.loc7_15.i, !dbg !12
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.i, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nofree norecurse nosync nounwind memory(argmem: readwrite)
-// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr captures(none) %a) local_unnamed_addr #1 !dbg !15 {
+// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr captures(none) %a) local_unnamed_addr #1 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br label %while.body, !dbg !16
+// CHECK:STDOUT:   br label %while.body, !dbg !22
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.body:                                       ; preds = %entry, %while.body
 // CHECK:STDOUT:   %n.var.03 = phi i32 [ 0, %entry ], [ %1, %while.body ]
-// CHECK:STDOUT:   %0 = zext nneg i32 %n.var.03 to i64, !dbg !17
-// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds nuw i32, ptr %a, i64 %0, !dbg !17
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !17
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = shl i32 %Int.as.MulAssignWith.impl.Op.call, 1, !dbg !17
-// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !17
-// CHECK:STDOUT:   %1 = add nuw nsw i32 %n.var.03, 1, !dbg !18
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp samesign ult i32 %n.var.03, 65535, !dbg !24
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !16
+// CHECK:STDOUT:   %0 = zext nneg i32 %n.var.03 to i64, !dbg !23
+// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds nuw i32, ptr %a, i64 %0, !dbg !23
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !23
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = shl i32 %Int.as.MulAssignWith.impl.Op.call, 1, !dbg !23
+// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !23
+// CHECK:STDOUT:   %1 = add nuw nsw i32 %n.var.03, 1, !dbg !24
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp samesign ult i32 %n.var.03, 65535, !dbg !39
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !22
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.done:                                       ; preds = %while.body
-// CHECK:STDOUT:   ret void, !dbg !25
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
 // CHECK:STDOUT:   uselistorder label %while.body, { 1, 0 }
@@ -95,23 +95,38 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "foo.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "NoInlineWithOz", linkageName: "_CNoInlineWithOz.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 7, column: 10, scope: !4, inlinedAt: !12)
-// CHECK:STDOUT: !12 = distinct !DILocation(line: 12, column: 10, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 7, column: 19, scope: !4, inlinedAt: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 12, column: 3, scope: !10)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 18, column: 9, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 5, scope: !15)
-// CHECK:STDOUT: !18 = !DILocation(line: 275, column: 3, scope: !19, inlinedAt: !21)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !20, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !21 = distinct !DILocation(line: 341, column: 5, scope: !22, inlinedAt: !23)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !20, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = distinct !DILocation(line: 20, column: 5, scope: !15)
-// CHECK:STDOUT: !24 = !DILocation(line: 18, column: 10, scope: !15)
-// CHECK:STDOUT: !25 = !DILocation(line: 15, column: 1, scope: !15)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DILocation(line: 7, column: 10, scope: !4, inlinedAt: !13)
+// CHECK:STDOUT: !13 = distinct !DILocation(line: 12, column: 10, scope: !11)
+// CHECK:STDOUT: !14 = !DILocation(line: 7, column: 19, scope: !4, inlinedAt: !13)
+// CHECK:STDOUT: !15 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{null, !19}
+// CHECK:STDOUT: !19 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !16, type: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 18, column: 9, scope: !16)
+// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 5, scope: !16)
+// CHECK:STDOUT: !24 = !DILocation(line: 275, column: 3, scope: !25, inlinedAt: !32)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !26, line: 275, type: !27, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !29)
+// CHECK:STDOUT: !26 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !27 = !DISubroutineType(types: !28)
+// CHECK:STDOUT: !28 = !{null, !7, !7}
+// CHECK:STDOUT: !29 = !{!30, !31}
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 1, scope: !25, type: !7)
+// CHECK:STDOUT: !31 = !DILocalVariable(arg: 2, scope: !25, type: !7)
+// CHECK:STDOUT: !32 = distinct !DILocation(line: 341, column: 5, scope: !33, inlinedAt: !38)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !26, line: 339, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !36)
+// CHECK:STDOUT: !34 = !DISubroutineType(types: !35)
+// CHECK:STDOUT: !35 = !{null, !7}
+// CHECK:STDOUT: !36 = !{!37}
+// CHECK:STDOUT: !37 = !DILocalVariable(arg: 1, scope: !33, type: !7)
+// CHECK:STDOUT: !38 = distinct !DILocation(line: 20, column: 5, scope: !16)
+// CHECK:STDOUT: !39 = !DILocation(line: 18, column: 10, scope: !16)
+// CHECK:STDOUT: !40 = !DILocation(line: 15, column: 1, scope: !16)

+ 55 - 40
toolchain/driver/testdata/compile/optimize/optimize_default.carbon

@@ -43,39 +43,39 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CNoInlineWithOz.Main() local_unnamed_addr #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15 = tail call i32 @_CRand.Main() #0, !dbg !7
-// CHECK:STDOUT:   %Rand.call.loc7_24 = tail call i32 @_CRand.Main() #0, !dbg !8
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_24, %Rand.call.loc7_15, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !9
+// CHECK:STDOUT:   %Rand.call.loc7_15 = tail call i32 @_CRand.Main() #0, !dbg !8
+// CHECK:STDOUT:   %Rand.call.loc7_24 = tail call i32 @_CRand.Main() #0, !dbg !9
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_24, %Rand.call.loc7_15, !dbg !8
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() local_unnamed_addr #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() local_unnamed_addr #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15.i = tail call i32 @_CRand.Main() #0, !dbg !11
-// CHECK:STDOUT:   %Rand.call.loc7_24.i = tail call i32 @_CRand.Main() #0, !dbg !13
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.i = add i32 %Rand.call.loc7_24.i, %Rand.call.loc7_15.i, !dbg !11
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.i, !dbg !14
+// CHECK:STDOUT:   %Rand.call.loc7_15.i = tail call i32 @_CRand.Main() #0, !dbg !12
+// CHECK:STDOUT:   %Rand.call.loc7_24.i = tail call i32 @_CRand.Main() #0, !dbg !14
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.i = add i32 %Rand.call.loc7_24.i, %Rand.call.loc7_15.i, !dbg !12
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.i, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nofree norecurse nosync nounwind memory(argmem: readwrite)
-// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr captures(none) %a) local_unnamed_addr #1 !dbg !15 {
+// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr captures(none) %a) local_unnamed_addr #1 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br label %while.body, !dbg !16
+// CHECK:STDOUT:   br label %while.body, !dbg !22
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.body:                                       ; preds = %entry, %while.body
 // CHECK:STDOUT:   %n.var.03 = phi i32 [ 0, %entry ], [ %1, %while.body ]
-// CHECK:STDOUT:   %0 = zext nneg i32 %n.var.03 to i64, !dbg !17
-// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds nuw i32, ptr %a, i64 %0, !dbg !17
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !17
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = shl i32 %Int.as.MulAssignWith.impl.Op.call, 1, !dbg !17
-// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !17
-// CHECK:STDOUT:   %1 = add nuw nsw i32 %n.var.03, 1, !dbg !18
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp samesign ult i32 %n.var.03, 65535, !dbg !24
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !16
+// CHECK:STDOUT:   %0 = zext nneg i32 %n.var.03 to i64, !dbg !23
+// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds nuw i32, ptr %a, i64 %0, !dbg !23
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !23
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = shl i32 %Int.as.MulAssignWith.impl.Op.call, 1, !dbg !23
+// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !23
+// CHECK:STDOUT:   %1 = add nuw nsw i32 %n.var.03, 1, !dbg !24
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp samesign ult i32 %n.var.03, 65535, !dbg !39
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !22
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.done:                                       ; preds = %while.body
-// CHECK:STDOUT:   ret void, !dbg !25
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
 // CHECK:STDOUT:   uselistorder label %while.body, { 1, 0 }
@@ -95,23 +95,38 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "foo.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "NoInlineWithOz", linkageName: "_CNoInlineWithOz.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 7, column: 10, scope: !4, inlinedAt: !12)
-// CHECK:STDOUT: !12 = distinct !DILocation(line: 12, column: 10, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 7, column: 19, scope: !4, inlinedAt: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 12, column: 3, scope: !10)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 18, column: 9, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 5, scope: !15)
-// CHECK:STDOUT: !18 = !DILocation(line: 275, column: 3, scope: !19, inlinedAt: !21)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !20, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !21 = distinct !DILocation(line: 341, column: 5, scope: !22, inlinedAt: !23)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !20, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = distinct !DILocation(line: 20, column: 5, scope: !15)
-// CHECK:STDOUT: !24 = !DILocation(line: 18, column: 10, scope: !15)
-// CHECK:STDOUT: !25 = !DILocation(line: 15, column: 1, scope: !15)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DILocation(line: 7, column: 10, scope: !4, inlinedAt: !13)
+// CHECK:STDOUT: !13 = distinct !DILocation(line: 12, column: 10, scope: !11)
+// CHECK:STDOUT: !14 = !DILocation(line: 7, column: 19, scope: !4, inlinedAt: !13)
+// CHECK:STDOUT: !15 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{null, !19}
+// CHECK:STDOUT: !19 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !16, type: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 18, column: 9, scope: !16)
+// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 5, scope: !16)
+// CHECK:STDOUT: !24 = !DILocation(line: 275, column: 3, scope: !25, inlinedAt: !32)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !26, line: 275, type: !27, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !29)
+// CHECK:STDOUT: !26 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !27 = !DISubroutineType(types: !28)
+// CHECK:STDOUT: !28 = !{null, !7, !7}
+// CHECK:STDOUT: !29 = !{!30, !31}
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 1, scope: !25, type: !7)
+// CHECK:STDOUT: !31 = !DILocalVariable(arg: 2, scope: !25, type: !7)
+// CHECK:STDOUT: !32 = distinct !DILocation(line: 341, column: 5, scope: !33, inlinedAt: !38)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !26, line: 339, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !36)
+// CHECK:STDOUT: !34 = !DISubroutineType(types: !35)
+// CHECK:STDOUT: !35 = !{null, !7}
+// CHECK:STDOUT: !36 = !{!37}
+// CHECK:STDOUT: !37 = !DILocalVariable(arg: 1, scope: !33, type: !7)
+// CHECK:STDOUT: !38 = distinct !DILocation(line: 20, column: 5, scope: !16)
+// CHECK:STDOUT: !39 = !DILocation(line: 18, column: 10, scope: !16)
+// CHECK:STDOUT: !40 = !DILocation(line: 15, column: 1, scope: !16)

+ 79 - 60
toolchain/driver/testdata/compile/optimize/optimize_none.carbon

@@ -43,66 +43,66 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
 // CHECK:STDOUT: define i32 @_CNoInlineWithOz.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15 = call i32 @_CRand.Main(), !dbg !7
-// CHECK:STDOUT:   %Rand.call.loc7_24 = call i32 @_CRand.Main(), !dbg !8
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_15, %Rand.call.loc7_24, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !9
+// CHECK:STDOUT:   %Rand.call.loc7_15 = call i32 @_CRand.Main(), !dbg !8
+// CHECK:STDOUT:   %Rand.call.loc7_24 = call i32 @_CRand.Main(), !dbg !9
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_15, %Rand.call.loc7_24, !dbg !8
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
-// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %NoInlineWithOz.call = call i32 @_CNoInlineWithOz.Main(), !dbg !11
-// CHECK:STDOUT:   ret i32 %NoInlineWithOz.call, !dbg !12
+// CHECK:STDOUT:   %NoInlineWithOz.call = call i32 @_CNoInlineWithOz.Main(), !dbg !12
+// CHECK:STDOUT:   ret i32 %NoInlineWithOz.call, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
-// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr %a) #0 !dbg !13 {
+// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr %a) #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !14
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !14
-// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !14
-// CHECK:STDOUT:   br label %while.cond, !dbg !15
+// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !20
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !20
+// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !20
+// CHECK:STDOUT:   br label %while.cond, !dbg !21
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.cond:                                       ; preds = %while.body, %entry
-// CHECK:STDOUT:   %.loc18_10 = load i32, ptr %n.var, align 4, !dbg !16
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp slt i32 %.loc18_10, 65536, !dbg !16
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !15
+// CHECK:STDOUT:   %.loc18_10 = load i32, ptr %n.var, align 4, !dbg !22
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp slt i32 %.loc18_10, 65536, !dbg !22
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !21
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.body:                                       ; preds = %while.cond
-// CHECK:STDOUT:   %.loc19_10 = load i32, ptr %n.var, align 4, !dbg !17
-// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds [65536 x i32], ptr %a, i32 0, i32 %.loc19_10, !dbg !18
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !18
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = mul i32 %Int.as.MulAssignWith.impl.Op.call, 2, !dbg !18
-// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !18
-// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %n.var), !dbg !19
-// CHECK:STDOUT:   br label %while.cond, !dbg !20
+// CHECK:STDOUT:   %.loc19_10 = load i32, ptr %n.var, align 4, !dbg !23
+// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds [65536 x i32], ptr %a, i32 0, i32 %.loc19_10, !dbg !24
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !24
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = mul i32 %Int.as.MulAssignWith.impl.Op.call, 2, !dbg !24
+// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !24
+// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %n.var), !dbg !25
+// CHECK:STDOUT:   br label %while.cond, !dbg !26
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.done:                                       ; preds = %while.cond
-// CHECK:STDOUT:   ret void, !dbg !21
+// CHECK:STDOUT:   ret void, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
 // CHECK:STDOUT: declare void @llvm.lifetime.start.p0(ptr captures(none)) #1
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
-// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !22 {
-// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 1), !dbg !24
-// CHECK:STDOUT:   ret void, !dbg !25
+// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !28 {
+// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 1), !dbg !34
+// CHECK:STDOUT:   ret void, !dbg !35
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
-// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 %other) #0 !dbg !26 {
-// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %other), !dbg !27
-// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !28
-// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !28
-// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !28
-// CHECK:STDOUT:   ret void, !dbg !28
+// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 %other) #0 !dbg !36 {
+// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %other), !dbg !42
+// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !43
+// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !43
+// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !43
+// CHECK:STDOUT:   ret void, !dbg !43
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: noinline nounwind optnone
-// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %self) #0 !dbg !29 {
-// CHECK:STDOUT:   ret i32 %self, !dbg !31
+// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %self) #0 !dbg !44 {
+// CHECK:STDOUT:   ret i32 %self, !dbg !50
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { noinline nounwind optnone }
@@ -117,29 +117,48 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "foo.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "NoInlineWithOz", linkageName: "_CNoInlineWithOz.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 12, column: 10, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 12, column: 3, scope: !10)
-// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 3, scope: !13)
-// CHECK:STDOUT: !15 = !DILocation(line: 18, column: 9, scope: !13)
-// CHECK:STDOUT: !16 = !DILocation(line: 18, column: 10, scope: !13)
-// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 10, scope: !13)
-// CHECK:STDOUT: !18 = !DILocation(line: 19, column: 5, scope: !13)
-// CHECK:STDOUT: !19 = !DILocation(line: 20, column: 5, scope: !13)
-// CHECK:STDOUT: !20 = !DILocation(line: 18, column: 3, scope: !13)
-// CHECK:STDOUT: !21 = !DILocation(line: 15, column: 1, scope: !13)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !23, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !24 = !DILocation(line: 341, column: 5, scope: !22)
-// CHECK:STDOUT: !25 = !DILocation(line: 339, column: 3, scope: !22)
-// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !23, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !27 = !DILocation(line: 4294967295, scope: !26)
-// CHECK:STDOUT: !28 = !DILocation(line: 275, column: 3, scope: !26)
-// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899", scope: null, file: !30, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !30 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
-// CHECK:STDOUT: !31 = !DILocation(line: 24, column: 38, scope: !29)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DILocation(line: 12, column: 10, scope: !11)
+// CHECK:STDOUT: !13 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{null, !17}
+// CHECK:STDOUT: !17 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !18 = !{!19}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !14, type: !17)
+// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 3, scope: !14)
+// CHECK:STDOUT: !21 = !DILocation(line: 18, column: 9, scope: !14)
+// CHECK:STDOUT: !22 = !DILocation(line: 18, column: 10, scope: !14)
+// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 10, scope: !14)
+// CHECK:STDOUT: !24 = !DILocation(line: 19, column: 5, scope: !14)
+// CHECK:STDOUT: !25 = !DILocation(line: 20, column: 5, scope: !14)
+// CHECK:STDOUT: !26 = !DILocation(line: 18, column: 3, scope: !14)
+// CHECK:STDOUT: !27 = !DILocation(line: 15, column: 1, scope: !14)
+// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !29, line: 339, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !32)
+// CHECK:STDOUT: !29 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !30 = !DISubroutineType(types: !31)
+// CHECK:STDOUT: !31 = !{null, !7}
+// CHECK:STDOUT: !32 = !{!33}
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 1, scope: !28, type: !7)
+// CHECK:STDOUT: !34 = !DILocation(line: 341, column: 5, scope: !28)
+// CHECK:STDOUT: !35 = !DILocation(line: 339, column: 3, scope: !28)
+// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !29, line: 275, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !39)
+// CHECK:STDOUT: !37 = !DISubroutineType(types: !38)
+// CHECK:STDOUT: !38 = !{null, !7, !7}
+// CHECK:STDOUT: !39 = !{!40, !41}
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 1, scope: !36, type: !7)
+// CHECK:STDOUT: !41 = !DILocalVariable(arg: 2, scope: !36, type: !7)
+// CHECK:STDOUT: !42 = !DILocation(line: 4294967295, scope: !36)
+// CHECK:STDOUT: !43 = !DILocation(line: 275, column: 3, scope: !36)
+// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899", scope: null, file: !45, line: 24, type: !46, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !48)
+// CHECK:STDOUT: !45 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
+// CHECK:STDOUT: !46 = !DISubroutineType(types: !47)
+// CHECK:STDOUT: !47 = !{!7, !7}
+// CHECK:STDOUT: !48 = !{!49}
+// CHECK:STDOUT: !49 = !DILocalVariable(arg: 1, scope: !44, type: !7)
+// CHECK:STDOUT: !50 = !DILocation(line: 24, column: 38, scope: !44)

+ 79 - 60
toolchain/driver/testdata/compile/optimize/optimize_size.carbon

@@ -42,66 +42,66 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: ; Function Attrs: minsize nounwind optsize
 // CHECK:STDOUT: define i32 @_CNoInlineWithOz.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15 = call i32 @_CRand.Main(), !dbg !7
-// CHECK:STDOUT:   %Rand.call.loc7_24 = call i32 @_CRand.Main(), !dbg !8
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_15, %Rand.call.loc7_24, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !9
+// CHECK:STDOUT:   %Rand.call.loc7_15 = call i32 @_CRand.Main(), !dbg !8
+// CHECK:STDOUT:   %Rand.call.loc7_24 = call i32 @_CRand.Main(), !dbg !9
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_15, %Rand.call.loc7_24, !dbg !8
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: minsize nounwind optsize
-// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %NoInlineWithOz.call = call i32 @_CNoInlineWithOz.Main(), !dbg !11
-// CHECK:STDOUT:   ret i32 %NoInlineWithOz.call, !dbg !12
+// CHECK:STDOUT:   %NoInlineWithOz.call = call i32 @_CNoInlineWithOz.Main(), !dbg !12
+// CHECK:STDOUT:   ret i32 %NoInlineWithOz.call, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: minsize nounwind optsize
-// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr %a) #0 !dbg !13 {
+// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr %a) #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !14
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !14
-// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !14
-// CHECK:STDOUT:   br label %while.cond, !dbg !15
+// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !20
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !20
+// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !20
+// CHECK:STDOUT:   br label %while.cond, !dbg !21
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.cond:                                       ; preds = %while.body, %entry
-// CHECK:STDOUT:   %.loc18_10 = load i32, ptr %n.var, align 4, !dbg !16
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp slt i32 %.loc18_10, 65536, !dbg !16
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !15
+// CHECK:STDOUT:   %.loc18_10 = load i32, ptr %n.var, align 4, !dbg !22
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Less.call = icmp slt i32 %.loc18_10, 65536, !dbg !22
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Less.call, label %while.body, label %while.done, !dbg !21
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.body:                                       ; preds = %while.cond
-// CHECK:STDOUT:   %.loc19_10 = load i32, ptr %n.var, align 4, !dbg !17
-// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds [65536 x i32], ptr %a, i32 0, i32 %.loc19_10, !dbg !18
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !18
-// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = mul i32 %Int.as.MulAssignWith.impl.Op.call, 2, !dbg !18
-// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !18
-// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %n.var), !dbg !19
-// CHECK:STDOUT:   br label %while.cond, !dbg !20
+// CHECK:STDOUT:   %.loc19_10 = load i32, ptr %n.var, align 4, !dbg !23
+// CHECK:STDOUT:   %.loc19_11.array.index = getelementptr inbounds [65536 x i32], ptr %a, i32 0, i32 %.loc19_10, !dbg !24
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call = load i32, ptr %.loc19_11.array.index, align 4, !dbg !24
+// CHECK:STDOUT:   %Int.as.MulAssignWith.impl.Op.call1 = mul i32 %Int.as.MulAssignWith.impl.Op.call, 2, !dbg !24
+// CHECK:STDOUT:   store i32 %Int.as.MulAssignWith.impl.Op.call1, ptr %.loc19_11.array.index, align 4, !dbg !24
+// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %n.var), !dbg !25
+// CHECK:STDOUT:   br label %while.cond, !dbg !26
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.done:                                       ; preds = %while.cond
-// CHECK:STDOUT:   ret void, !dbg !21
+// CHECK:STDOUT:   ret void, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
 // CHECK:STDOUT: declare void @llvm.lifetime.start.p0(ptr captures(none)) #1
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: minsize nounwind optsize
-// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !22 {
-// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 1), !dbg !24
-// CHECK:STDOUT:   ret void, !dbg !25
+// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !28 {
+// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 1), !dbg !34
+// CHECK:STDOUT:   ret void, !dbg !35
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: alwaysinline minsize nounwind optsize
-// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 %other) #2 !dbg !26 {
-// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %other), !dbg !27
-// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !28
-// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !28
-// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !28
-// CHECK:STDOUT:   ret void, !dbg !28
+// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e"(ptr %self, i32 %other) #2 !dbg !36 {
+// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %other), !dbg !42
+// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !43
+// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !43
+// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !43
+// CHECK:STDOUT:   ret void, !dbg !43
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: minsize nounwind optsize
-// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %self) #0 !dbg !29 {
-// CHECK:STDOUT:   ret i32 %self, !dbg !31
+// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899"(i32 %self) #0 !dbg !44 {
+// CHECK:STDOUT:   ret i32 %self, !dbg !50
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { minsize nounwind optsize }
@@ -117,29 +117,48 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "foo.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "NoInlineWithOz", linkageName: "_CNoInlineWithOz.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 12, column: 10, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 12, column: 3, scope: !10)
-// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 3, scope: !13)
-// CHECK:STDOUT: !15 = !DILocation(line: 18, column: 9, scope: !13)
-// CHECK:STDOUT: !16 = !DILocation(line: 18, column: 10, scope: !13)
-// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 10, scope: !13)
-// CHECK:STDOUT: !18 = !DILocation(line: 19, column: 5, scope: !13)
-// CHECK:STDOUT: !19 = !DILocation(line: 20, column: 5, scope: !13)
-// CHECK:STDOUT: !20 = !DILocation(line: 18, column: 3, scope: !13)
-// CHECK:STDOUT: !21 = !DILocation(line: 15, column: 1, scope: !13)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !23, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !24 = !DILocation(line: 341, column: 5, scope: !22)
-// CHECK:STDOUT: !25 = !DILocation(line: 339, column: 3, scope: !22)
-// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !23, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !27 = !DILocation(line: 4294967295, scope: !26)
-// CHECK:STDOUT: !28 = !DILocation(line: 275, column: 3, scope: !26)
-// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899", scope: null, file: !30, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !30 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
-// CHECK:STDOUT: !31 = !DILocation(line: 24, column: 38, scope: !29)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DILocation(line: 12, column: 10, scope: !11)
+// CHECK:STDOUT: !13 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{null, !17}
+// CHECK:STDOUT: !17 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !18 = !{!19}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !14, type: !17)
+// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 3, scope: !14)
+// CHECK:STDOUT: !21 = !DILocation(line: 18, column: 9, scope: !14)
+// CHECK:STDOUT: !22 = !DILocation(line: 18, column: 10, scope: !14)
+// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 10, scope: !14)
+// CHECK:STDOUT: !24 = !DILocation(line: 19, column: 5, scope: !14)
+// CHECK:STDOUT: !25 = !DILocation(line: 20, column: 5, scope: !14)
+// CHECK:STDOUT: !26 = !DILocation(line: 18, column: 3, scope: !14)
+// CHECK:STDOUT: !27 = !DILocation(line: 15, column: 1, scope: !14)
+// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !29, line: 339, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !32)
+// CHECK:STDOUT: !29 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !30 = !DISubroutineType(types: !31)
+// CHECK:STDOUT: !31 = !{null, !7}
+// CHECK:STDOUT: !32 = !{!33}
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 1, scope: !28, type: !7)
+// CHECK:STDOUT: !34 = !DILocation(line: 341, column: 5, scope: !28)
+// CHECK:STDOUT: !35 = !DILocation(line: 339, column: 3, scope: !28)
+// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !29, line: 275, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !39)
+// CHECK:STDOUT: !37 = !DISubroutineType(types: !38)
+// CHECK:STDOUT: !38 = !{null, !7, !7}
+// CHECK:STDOUT: !39 = !{!40, !41}
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 1, scope: !36, type: !7)
+// CHECK:STDOUT: !41 = !DILocalVariable(arg: 2, scope: !36, type: !7)
+// CHECK:STDOUT: !42 = !DILocation(line: 4294967295, scope: !36)
+// CHECK:STDOUT: !43 = !DILocation(line: 275, column: 3, scope: !36)
+// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.5450dc8e8b8e0899", scope: null, file: !45, line: 24, type: !46, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !48)
+// CHECK:STDOUT: !45 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
+// CHECK:STDOUT: !46 = !DISubroutineType(types: !47)
+// CHECK:STDOUT: !47 = !{!7, !7}
+// CHECK:STDOUT: !48 = !{!49}
+// CHECK:STDOUT: !49 = !DILocalVariable(arg: 1, scope: !44, type: !7)
+// CHECK:STDOUT: !50 = !DILocation(line: 24, column: 38, scope: !44)

+ 72 - 57
toolchain/driver/testdata/compile/optimize/optimize_speed.carbon

@@ -43,53 +43,53 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CNoInlineWithOz.Main() local_unnamed_addr #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15 = tail call i32 @_CRand.Main() #0, !dbg !7
-// CHECK:STDOUT:   %Rand.call.loc7_24 = tail call i32 @_CRand.Main() #0, !dbg !8
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_24, %Rand.call.loc7_15, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !9
+// CHECK:STDOUT:   %Rand.call.loc7_15 = tail call i32 @_CRand.Main() #0, !dbg !8
+// CHECK:STDOUT:   %Rand.call.loc7_24 = tail call i32 @_CRand.Main() #0, !dbg !9
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %Rand.call.loc7_24, %Rand.call.loc7_15, !dbg !8
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() local_unnamed_addr #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CCallNoInlineWithOptSize.Main() local_unnamed_addr #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Rand.call.loc7_15.i = tail call i32 @_CRand.Main() #0, !dbg !11
-// CHECK:STDOUT:   %Rand.call.loc7_24.i = tail call i32 @_CRand.Main() #0, !dbg !13
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.i = add i32 %Rand.call.loc7_24.i, %Rand.call.loc7_15.i, !dbg !11
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.i, !dbg !14
+// CHECK:STDOUT:   %Rand.call.loc7_15.i = tail call i32 @_CRand.Main() #0, !dbg !12
+// CHECK:STDOUT:   %Rand.call.loc7_24.i = tail call i32 @_CRand.Main() #0, !dbg !14
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.i = add i32 %Rand.call.loc7_24.i, %Rand.call.loc7_15.i, !dbg !12
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.i, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nofree norecurse nosync nounwind memory(argmem: readwrite)
-// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr captures(none) %a) local_unnamed_addr #1 !dbg !15 {
+// CHECK:STDOUT: define void @_CVectorizedWithOptSpeed.Main(ptr captures(none) %a) local_unnamed_addr #1 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br label %vector.body, !dbg !16
+// CHECK:STDOUT:   br label %vector.body, !dbg !22
 // CHECK:STDOUT:
 // CHECK:STDOUT: vector.body:                                      ; preds = %vector.body, %entry
-// CHECK:STDOUT:   %index = phi i32 [ 0, %entry ], [ %index.next.1, %vector.body ], !dbg !17
-// CHECK:STDOUT:   %0 = zext nneg i32 %index to i64, !dbg !23
-// CHECK:STDOUT:   %1 = getelementptr inbounds nuw i32, ptr %a, i64 %0, !dbg !23
-// CHECK:STDOUT:   %2 = getelementptr inbounds nuw i8, ptr %1, i64 16, !dbg !23
-// CHECK:STDOUT:   %wide.load = load <4 x i32>, ptr %1, align 4, !dbg !23
-// CHECK:STDOUT:   %wide.load4 = load <4 x i32>, ptr %2, align 4, !dbg !23
-// CHECK:STDOUT:   %3 = shl <4 x i32> %wide.load, splat (i32 1), !dbg !23
-// CHECK:STDOUT:   %4 = shl <4 x i32> %wide.load4, splat (i32 1), !dbg !23
-// CHECK:STDOUT:   store <4 x i32> %3, ptr %1, align 4, !dbg !23
-// CHECK:STDOUT:   store <4 x i32> %4, ptr %2, align 4, !dbg !23
-// CHECK:STDOUT:   %5 = zext nneg i32 %index to i64, !dbg !23
-// CHECK:STDOUT:   %6 = getelementptr inbounds nuw i32, ptr %a, i64 %5, !dbg !23
-// CHECK:STDOUT:   %7 = getelementptr inbounds nuw i8, ptr %6, i64 32, !dbg !23
-// CHECK:STDOUT:   %8 = getelementptr inbounds nuw i8, ptr %6, i64 48, !dbg !23
-// CHECK:STDOUT:   %wide.load.1 = load <4 x i32>, ptr %7, align 4, !dbg !23
-// CHECK:STDOUT:   %wide.load4.1 = load <4 x i32>, ptr %8, align 4, !dbg !23
-// CHECK:STDOUT:   %9 = shl <4 x i32> %wide.load.1, splat (i32 1), !dbg !23
-// CHECK:STDOUT:   %10 = shl <4 x i32> %wide.load4.1, splat (i32 1), !dbg !23
-// CHECK:STDOUT:   store <4 x i32> %9, ptr %7, align 4, !dbg !23
-// CHECK:STDOUT:   store <4 x i32> %10, ptr %8, align 4, !dbg !23
-// CHECK:STDOUT:   %index.next.1 = add nuw nsw i32 %index, 16, !dbg !17
-// CHECK:STDOUT:   %11 = icmp eq i32 %index.next.1, 65536, !dbg !16
-// CHECK:STDOUT:   br i1 %11, label %while.done, label %vector.body, !dbg !16, !llvm.loop !24
+// CHECK:STDOUT:   %index = phi i32 [ 0, %entry ], [ %index.next.1, %vector.body ], !dbg !23
+// CHECK:STDOUT:   %0 = zext nneg i32 %index to i64, !dbg !38
+// CHECK:STDOUT:   %1 = getelementptr inbounds nuw i32, ptr %a, i64 %0, !dbg !38
+// CHECK:STDOUT:   %2 = getelementptr inbounds nuw i8, ptr %1, i64 16, !dbg !38
+// CHECK:STDOUT:   %wide.load = load <4 x i32>, ptr %1, align 4, !dbg !38
+// CHECK:STDOUT:   %wide.load4 = load <4 x i32>, ptr %2, align 4, !dbg !38
+// CHECK:STDOUT:   %3 = shl <4 x i32> %wide.load, splat (i32 1), !dbg !38
+// CHECK:STDOUT:   %4 = shl <4 x i32> %wide.load4, splat (i32 1), !dbg !38
+// CHECK:STDOUT:   store <4 x i32> %3, ptr %1, align 4, !dbg !38
+// CHECK:STDOUT:   store <4 x i32> %4, ptr %2, align 4, !dbg !38
+// CHECK:STDOUT:   %5 = zext nneg i32 %index to i64, !dbg !38
+// CHECK:STDOUT:   %6 = getelementptr inbounds nuw i32, ptr %a, i64 %5, !dbg !38
+// CHECK:STDOUT:   %7 = getelementptr inbounds nuw i8, ptr %6, i64 32, !dbg !38
+// CHECK:STDOUT:   %8 = getelementptr inbounds nuw i8, ptr %6, i64 48, !dbg !38
+// CHECK:STDOUT:   %wide.load.1 = load <4 x i32>, ptr %7, align 4, !dbg !38
+// CHECK:STDOUT:   %wide.load4.1 = load <4 x i32>, ptr %8, align 4, !dbg !38
+// CHECK:STDOUT:   %9 = shl <4 x i32> %wide.load.1, splat (i32 1), !dbg !38
+// CHECK:STDOUT:   %10 = shl <4 x i32> %wide.load4.1, splat (i32 1), !dbg !38
+// CHECK:STDOUT:   store <4 x i32> %9, ptr %7, align 4, !dbg !38
+// CHECK:STDOUT:   store <4 x i32> %10, ptr %8, align 4, !dbg !38
+// CHECK:STDOUT:   %index.next.1 = add nuw nsw i32 %index, 16, !dbg !23
+// CHECK:STDOUT:   %11 = icmp eq i32 %index.next.1, 65536, !dbg !22
+// CHECK:STDOUT:   br i1 %11, label %while.done, label %vector.body, !dbg !22, !llvm.loop !39
 // CHECK:STDOUT:
 // CHECK:STDOUT: while.done:                                       ; preds = %vector.body
-// CHECK:STDOUT:   ret void, !dbg !27
+// CHECK:STDOUT:   ret void, !dbg !42
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
 // CHECK:STDOUT:   uselistorder i32 %index, { 1, 0, 2 }
@@ -111,25 +111,40 @@ fn VectorizedWithOptSpeed(a: array(i32, 65536)*) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "foo.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "NoInlineWithOz", linkageName: "_CNoInlineWithOz.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 7, column: 10, scope: !4, inlinedAt: !12)
-// CHECK:STDOUT: !12 = distinct !DILocation(line: 12, column: 10, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 7, column: 19, scope: !4, inlinedAt: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 12, column: 3, scope: !10)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 18, column: 9, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 275, column: 3, scope: !18, inlinedAt: !20)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !19, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !20 = distinct !DILocation(line: 341, column: 5, scope: !21, inlinedAt: !22)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !19, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = distinct !DILocation(line: 20, column: 5, scope: !15)
-// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 5, scope: !15)
-// CHECK:STDOUT: !24 = distinct !{!24, !25, !26}
-// CHECK:STDOUT: !25 = !{!"llvm.loop.isvectorized", i32 1}
-// CHECK:STDOUT: !26 = !{!"llvm.loop.unroll.runtime.disable"}
-// CHECK:STDOUT: !27 = !DILocation(line: 15, column: 1, scope: !15)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallNoInlineWithOptSize", linkageName: "_CCallNoInlineWithOptSize.Main", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DILocation(line: 7, column: 10, scope: !4, inlinedAt: !13)
+// CHECK:STDOUT: !13 = distinct !DILocation(line: 12, column: 10, scope: !11)
+// CHECK:STDOUT: !14 = !DILocation(line: 7, column: 19, scope: !4, inlinedAt: !13)
+// CHECK:STDOUT: !15 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "VectorizedWithOptSpeed", linkageName: "_CVectorizedWithOptSpeed.Main", scope: null, file: !3, line: 15, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{null, !19}
+// CHECK:STDOUT: !19 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !16, type: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 18, column: 9, scope: !16)
+// CHECK:STDOUT: !23 = !DILocation(line: 275, column: 3, scope: !24, inlinedAt: !31)
+// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.5dfb78ae56583d8e", scope: null, file: !25, line: 275, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !28)
+// CHECK:STDOUT: !25 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !26 = !DISubroutineType(types: !27)
+// CHECK:STDOUT: !27 = !{null, !7, !7}
+// CHECK:STDOUT: !28 = !{!29, !30}
+// CHECK:STDOUT: !29 = !DILocalVariable(arg: 1, scope: !24, type: !7)
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 2, scope: !24, type: !7)
+// CHECK:STDOUT: !31 = distinct !DILocation(line: 341, column: 5, scope: !32, inlinedAt: !37)
+// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !25, line: 339, type: !33, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !35)
+// CHECK:STDOUT: !33 = !DISubroutineType(types: !34)
+// CHECK:STDOUT: !34 = !{null, !7}
+// CHECK:STDOUT: !35 = !{!36}
+// CHECK:STDOUT: !36 = !DILocalVariable(arg: 1, scope: !32, type: !7)
+// CHECK:STDOUT: !37 = distinct !DILocation(line: 20, column: 5, scope: !16)
+// CHECK:STDOUT: !38 = !DILocation(line: 19, column: 5, scope: !16)
+// CHECK:STDOUT: !39 = distinct !{!39, !40, !41}
+// CHECK:STDOUT: !40 = !{!"llvm.loop.isvectorized", i32 1}
+// CHECK:STDOUT: !41 = !{!"llvm.loop.unroll.runtime.disable"}
+// CHECK:STDOUT: !42 = !DILocation(line: 15, column: 1, scope: !16)

+ 147 - 57
toolchain/lower/file_context.cpp

@@ -51,8 +51,9 @@ FileContext::FileContext(Context& context, const SemIR::File& sem_ir,
       vlog_stream_(vlog_stream),
       functions_(LoweredFunctionStore::MakeForOverwrite(sem_ir.functions())),
       specific_functions_(sem_ir.specifics(), nullptr),
-      types_(LoweredTypeStore::MakeWithExplicitSize(
-          sem_ir.insts().GetIdTag(), sem_ir.insts().size(), nullptr)),
+      types_(LoweredTypeStore::MakeWithExplicitSize(sem_ir.insts().GetIdTag(),
+                                                    sem_ir.insts().size(),
+                                                    {nullptr, nullptr})),
       constants_(LoweredConstantStore::MakeWithExplicitSize(
           sem_ir.insts().GetIdTag(), sem_ir.insts().size(), nullptr)),
       lowered_specifics_(sem_ir.generics(),
@@ -652,10 +653,11 @@ auto FileContext::BuildFunctionBody(SemIR::FunctionId function_id,
     llvm_function->addFnAttrs(attr_builder);
   }
 
+  auto* subprogram =
+      BuildDISubprogram(declaration_function, specific_id, llvm_function);
   FunctionContext function_lowering(
       definition_context, llvm_function, *this, specific_id,
-      coalescer_.InitializeFingerprintForSpecific(specific_id),
-      definition_context.BuildDISubprogram(definition_function, llvm_function),
+      coalescer_.InitializeFingerprintForSpecific(specific_id), subprogram,
       vlog_stream_);
 
   // Add parameters to locals.
@@ -766,9 +768,79 @@ auto FileContext::BuildFunctionBody(SemIR::FunctionId function_id,
 
   // Emit fingerprint accumulated inside the function context.
   function_lowering.EmitFinalFingerprint();
+  context().di_builder().finalizeSubprogram(subprogram);
+}
+
+auto FileContext::BuildDISubroutineType(const SemIR::Function& function,
+                                        SemIR::SpecificId specific_id)
+    -> llvm::DISubroutineType* {
+  auto implicit_param_patterns =
+      sem_ir().inst_blocks().GetOrEmpty(function.implicit_param_patterns_id);
+  auto param_patterns =
+      sem_ir().inst_blocks().GetOrEmpty(function.param_patterns_id);
+
+  auto* void_pointer_debug_type =
+      context().di_builder().createPointerType(nullptr, 8);
+
+  auto get_debug_type = [&](SemIR::TypeId type_id) -> llvm::DIType* {
+    CARBON_CHECK(type_id.has_value());
+    if (auto* type = GetTypeAndDIType(type_id).llvm_di_type) {
+      return type;
+    }
+    return void_pointer_debug_type;
+  };
+
+  auto return_info =
+      SemIR::ReturnTypeInfo::ForFunction(sem_ir(), function, specific_id);
+  if (function.return_slot_pattern_id.has_value()) {
+    // TODO: If int_repr.kind == SemIR::InitRepr::ByCopy - be sure the return
+    // type is tagged with indirect calling convention.
+  }
+
+  // TODO: Expose the `Call` parameter patterns in `Function`, and use them
+  // here.
+  llvm::SmallVector<llvm::Metadata*, 16> element_types;
+  element_types.push_back(return_info.type_id.has_value()
+                              ? get_debug_type(return_info.type_id)
+                              : nullptr);
+
+  for (auto param_pattern_id : llvm::concat<const SemIR::InstId>(
+           implicit_param_patterns, param_patterns)) {
+    auto param_pattern_info = SemIR::Function::GetParamPatternInfoFromPatternId(
+        sem_ir(), param_pattern_id);
+    if (!param_pattern_info) {
+      continue;
+    }
+    if (param_pattern_info->inst.kind == SemIR::RefParamPattern::Kind) {
+      // TODO: Maybe make the parameter type a reference type.
+    }
+    auto param_type_id = ExtractScrutineeType(
+        sem_ir(), SemIR::GetTypeOfInstInSpecific(sem_ir(), specific_id,
+                                                 param_pattern_info->inst_id));
+    switch (auto value_rep = SemIR::ValueRepr::ForType(sem_ir(), param_type_id);
+            value_rep.kind) {
+      case SemIR::ValueRepr::Unknown:
+        CARBON_FATAL("Lowering function with incomplete parameter type");
+      case SemIR::ValueRepr::Dependent:
+        CARBON_FATAL("Lowering function with dependent parameter type");
+      case SemIR::ValueRepr::None:
+        break;
+      case SemIR::ValueRepr::Copy:
+      case SemIR::ValueRepr::Custom:
+      case SemIR::ValueRepr::Pointer:
+        auto* param_type = get_debug_type(value_rep.type_id);
+        element_types.push_back(param_type);
+        break;
+    }
+  }
+
+  return context().di_builder().createSubroutineType(
+      context().di_builder().getOrCreateTypeArray(element_types),
+      llvm::DINode::FlagZero);
 }
 
 auto FileContext::BuildDISubprogram(const SemIR::Function& function,
+                                    SemIR::SpecificId specific_id,
                                     const llvm::Function* llvm_function)
     -> llvm::DISubprogram* {
   if (!context().di_compile_unit()) {
@@ -778,16 +850,23 @@ auto FileContext::BuildDISubprogram(const SemIR::Function& function,
   CARBON_CHECK(name, "Unexpected special name for function: {0}",
                function.name_id);
   auto loc = GetLocForDI(function.definition_id);
-  // TODO: Add more details here, including real subroutine type (once type
-  // information is built), etc.
-  return context().di_builder().createFunction(
+  llvm::DISubroutineType* subroutine_type =
+      BuildDISubroutineType(function, specific_id);
+  auto* subprogram = context().di_builder().createFunction(
       context().di_compile_unit(), *name, llvm_function->getName(),
       /*File=*/context().di_builder().createFile(loc.filename, ""),
-      /*LineNo=*/loc.line_number,
-      context().di_builder().createSubroutineType(
-          context().di_builder().getOrCreateTypeArray({})),
+      /*LineNo=*/loc.line_number, subroutine_type,
       /*ScopeLine=*/0, llvm::DINode::FlagZero,
       llvm::DISubprogram::SPFlagDefinition);
+  // Add a variable for each parameter, as that is where DWARF debug information
+  // comes from.
+  for (auto [argument_number, type] :
+       llvm::enumerate(llvm::drop_begin(subroutine_type->getTypeArray()))) {
+    context().di_builder().createParameterVariable(
+        subprogram, "", argument_number + 1, nullptr, 0, type,
+        /*AlwaysPreserve=*/true);
+  }
+  return subprogram;
 }
 
 // BuildTypeForInst is used to construct types for FileContext::BuildType below.
@@ -796,96 +875,107 @@ auto FileContext::BuildDISubprogram(const SemIR::Function& function,
 template <typename InstT>
   requires(InstT::Kind.is_type() == SemIR::InstIsType::Never)
 static auto BuildTypeForInst(FileContext& /*context*/, InstT inst)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   CARBON_FATAL("Cannot use inst as type: {0}", inst);
 }
 
 template <typename InstT>
   requires(InstT::Kind.is_symbolic_when_type())
 static auto BuildTypeForInst(FileContext& context, InstT /*inst*/)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   // Treat non-monomorphized symbolic types as opaque.
-  return llvm::StructType::get(context.llvm_context());
+  return {llvm::StructType::get(context.llvm_context()), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::ArrayType inst)
-    -> llvm::Type* {
-  return llvm::ArrayType::get(
-      context.GetType(context.sem_ir().types().GetTypeIdForTypeInstId(
-          inst.element_type_inst_id)),
-      *context.sem_ir().GetArrayBoundValue(inst.bound_id));
+    -> FileContext::LoweredTypes {
+  return {llvm::ArrayType::get(
+              context.GetType(context.sem_ir().types().GetTypeIdForTypeInstId(
+                  inst.element_type_inst_id)),
+              *context.sem_ir().GetArrayBoundValue(inst.bound_id)),
+          nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::BoolType /*inst*/)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   // TODO: We may want to have different representations for `bool` storage
   // (`i8`) versus for `bool` values (`i1`).
-  return llvm::Type::getInt1Ty(context.llvm_context());
+  return {llvm::Type::getInt1Ty(context.llvm_context()), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::ClassType inst)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   auto object_repr_id = context.sem_ir()
                             .classes()
                             .Get(inst.class_id)
                             .GetObjectRepr(context.sem_ir(), inst.specific_id);
-  return context.GetType(object_repr_id);
+  return context.GetTypeAndDIType(object_repr_id);
 }
 
 template <typename InstT>
   requires(SemIR::Internal::HasInstCategory<SemIR::AnyQualifiedType, InstT>)
-static auto BuildTypeForInst(FileContext& context, InstT inst) -> llvm::Type* {
-  return context.GetType(
-      context.sem_ir().types().GetTypeIdForTypeInstId(inst.inner_id));
+static auto BuildTypeForInst(FileContext& context, InstT inst)
+    -> FileContext::LoweredTypes {
+  return {context.GetType(
+              context.sem_ir().types().GetTypeIdForTypeInstId(inst.inner_id)),
+          nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::CustomLayoutType inst)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   auto layout = context.sem_ir().custom_layouts().Get(inst.layout_id);
-  return llvm::ArrayType::get(llvm::Type::getInt8Ty(context.llvm_context()),
-                              layout[SemIR::CustomLayoutId::SizeIndex]);
+  return {llvm::ArrayType::get(llvm::Type::getInt8Ty(context.llvm_context()),
+                               layout[SemIR::CustomLayoutId::SizeIndex]),
+          nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context,
                              SemIR::ImplWitnessAssociatedConstant inst)
-    -> llvm::Type* {
-  return context.GetType(inst.type_id);
+    -> FileContext::LoweredTypes {
+  return {context.GetType(inst.type_id), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& /*context*/,
-                             SemIR::ErrorInst /*inst*/) -> llvm::Type* {
+                             SemIR::ErrorInst /*inst*/)
+    -> FileContext::LoweredTypes {
   // This is a complete type but uses of it should never be lowered.
-  return nullptr;
+  return {nullptr, nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::FloatType inst)
-    -> llvm::Type* {
-  return llvm::Type::getFloatingPointTy(context.llvm_context(),
-                                        inst.float_kind.Semantics());
+    -> FileContext::LoweredTypes {
+  return {llvm::Type::getFloatingPointTy(context.llvm_context(),
+                                         inst.float_kind.Semantics()),
+          nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::IntType inst)
-    -> llvm::Type* {
-  auto width =
+    -> FileContext::LoweredTypes {
+  auto width_inst =
       context.sem_ir().insts().TryGetAs<SemIR::IntValue>(inst.bit_width_id);
-  CARBON_CHECK(width, "Can't lower int type with symbolic width");
-  return llvm::IntegerType::get(
-      context.llvm_context(),
-      context.sem_ir().ints().Get(width->int_id).getZExtValue());
+  CARBON_CHECK(width_inst, "Can't lower int type with symbolic width");
+  auto width = context.sem_ir().ints().Get(width_inst->int_id).getZExtValue();
+  return {llvm::IntegerType::get(context.llvm_context(), width),
+          context.context().di_builder().createBasicType(
+              "int", width,
+              inst.int_kind.is_signed() ? llvm::dwarf::DW_ATE_signed
+                                        : llvm::dwarf::DW_ATE_unsigned)};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::PointerType /*inst*/)
-    -> llvm::Type* {
-  return llvm::PointerType::get(context.llvm_context(), /*AddressSpace=*/0);
+    -> FileContext::LoweredTypes {
+  return {llvm::PointerType::get(context.llvm_context(), /*AddressSpace=*/0),
+          nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& /*context*/,
-                             SemIR::PatternType /*inst*/) -> llvm::Type* {
+                             SemIR::PatternType /*inst*/)
+    -> FileContext::LoweredTypes {
   CARBON_FATAL("Unexpected pattern type in lowering");
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::StructType inst)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   auto fields = context.sem_ir().struct_type_fields().Get(inst.fields_id);
   llvm::SmallVector<llvm::Type*> subtypes;
   subtypes.reserve(fields.size());
@@ -893,11 +983,11 @@ static auto BuildTypeForInst(FileContext& context, SemIR::StructType inst)
     subtypes.push_back(context.GetType(
         context.sem_ir().types().GetTypeIdForTypeInstId(field.type_inst_id)));
   }
-  return llvm::StructType::get(context.llvm_context(), subtypes);
+  return {llvm::StructType::get(context.llvm_context(), subtypes), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::TupleType inst)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   // TODO: Investigate special-casing handling of empty tuples so that they
   // can be collectively replaced with LLVM's void, particularly around
   // function returns. LLVM doesn't allow declaring variables with a void
@@ -908,23 +998,23 @@ static auto BuildTypeForInst(FileContext& context, SemIR::TupleType inst)
   for (auto type_id : context.sem_ir().types().GetBlockAsTypeIds(elements)) {
     subtypes.push_back(context.GetType(type_id));
   }
-  return llvm::StructType::get(context.llvm_context(), subtypes);
+  return {llvm::StructType::get(context.llvm_context(), subtypes), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::TypeType /*inst*/)
-    -> llvm::Type* {
-  return context.GetTypeType();
+    -> FileContext::LoweredTypes {
+  return {context.GetTypeType(), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context, SemIR::VtableType /*inst*/)
-    -> llvm::Type* {
-  return llvm::Type::getVoidTy(context.llvm_context());
+    -> FileContext::LoweredTypes {
+  return {llvm::Type::getVoidTy(context.llvm_context()), nullptr};
 }
 
 static auto BuildTypeForInst(FileContext& context,
                              SemIR::SpecificFunctionType /*inst*/)
-    -> llvm::Type* {
-  return llvm::PointerType::get(context.llvm_context(), 0);
+    -> FileContext::LoweredTypes {
+  return {llvm::PointerType::get(context.llvm_context(), 0), nullptr};
 }
 
 template <typename InstT>
@@ -938,14 +1028,14 @@ template <typename InstT>
            SemIR::RequireSpecificDefinitionType, SemIR::UnboundElementType,
            SemIR::WhereExpr, SemIR::WitnessType>())
 static auto BuildTypeForInst(FileContext& context, InstT /*inst*/)
-    -> llvm::Type* {
+    -> FileContext::LoweredTypes {
   // Return an empty struct as a placeholder.
   // TODO: Should we model an interface as a witness table, or an associated
   // entity as an index?
-  return llvm::StructType::get(context.llvm_context());
+  return {llvm::StructType::get(context.llvm_context()), nullptr};
 }
 
-auto FileContext::BuildType(SemIR::InstId inst_id) -> llvm::Type* {
+auto FileContext::BuildType(SemIR::InstId inst_id) -> LoweredTypes {
   // Use overload resolution to select the implementation, producing compile
   // errors when BuildTypeForInst isn't defined for a given instruction.
   CARBON_KIND_SWITCH(sem_ir_->insts().Get(inst_id)) {

+ 25 - 6
toolchain/lower/file_context.h

@@ -56,12 +56,24 @@ class FileContext {
 
   // Returns a lowered type for the given type_id.
   auto GetType(SemIR::TypeId type_id) -> llvm::Type* {
+    return GetTypeAndDIType(type_id).llvm_ir_type;
+  }
+
+  struct LoweredTypes {
+    llvm::Type* llvm_ir_type;
+    llvm::DIType* llvm_di_type;
+  };
+
+  // Returns both the lowered llvm IR type and the lowered llvm IR debug info
+  // type for the given type_id.
+  auto GetTypeAndDIType(SemIR::TypeId type_id) const -> LoweredTypes {
     CARBON_CHECK(type_id.has_value(), "Should not be called with `None`");
     CARBON_CHECK(type_id.is_concrete(), "Lowering symbolic type {0}: {1}",
                  type_id, sem_ir().types().GetAsInst(type_id));
-    CARBON_CHECK(types_.Get(type_id), "Missing type {0}: {1}", type_id,
+    auto result = types_.Get(type_id);
+    CARBON_CHECK(result.llvm_ir_type, "Missing type {0}: {1}", type_id,
                  sem_ir().types().GetAsInst(type_id));
-    return types_.Get(type_id);
+    return result;
   }
 
   // Returns location information for use with DebugInfo.
@@ -188,12 +200,19 @@ class FileContext {
 
   // Build the DISubprogram metadata for the given function.
   auto BuildDISubprogram(const SemIR::Function& function,
+                         SemIR::SpecificId specific_id,
                          const llvm::Function* llvm_function)
       -> llvm::DISubprogram*;
 
-  // Builds the type for the given instruction, which should then be cached by
-  // the caller.
-  auto BuildType(SemIR::InstId inst_id) -> llvm::Type*;
+  // Build a `DISubroutineType` for the given function, including the return and
+  // parameter types.
+  auto BuildDISubroutineType(const SemIR::Function&,
+                             SemIR::SpecificId specific_id)
+      -> llvm::DISubroutineType*;
+
+  // Builds the `llvm::Type` and `llvm::DIType` for the given instruction, which
+  // should then be cached by the caller.
+  auto BuildType(SemIR::InstId inst_id) -> LoweredTypes;
 
   auto BuildVtable(const SemIR::Vtable& vtable, SemIR::SpecificId specific_id)
       -> llvm::GlobalVariable*;
@@ -237,7 +256,7 @@ class FileContext {
   FixedSizeValueStore<SemIR::SpecificId, llvm::Function*> specific_functions_;
 
   // Provides lowered versions of types. Entries are non-symbolic types.
-  using LoweredTypeStore = FixedSizeValueStore<SemIR::TypeId, llvm::Type*>;
+  using LoweredTypeStore = FixedSizeValueStore<SemIR::TypeId, LoweredTypes>;
   LoweredTypeStore types_;
 
   // Maps constants to their lowered values. Indexes are the `InstId` for

+ 10 - 9
toolchain/lower/testdata/alias/local.carbon

@@ -22,11 +22,11 @@ fn F() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CF.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %a.var = alloca i32, align 4, !dbg !7
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !7
-// CHECK:STDOUT:   store i32 0, ptr %a.var, align 4, !dbg !7
-// CHECK:STDOUT:   %.loc16 = load i32, ptr %a.var, align 4, !dbg !8
-// CHECK:STDOUT:   ret i32 %.loc16, !dbg !9
+// CHECK:STDOUT:   %a.var = alloca i32, align 4, !dbg !8
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !8
+// CHECK:STDOUT:   store i32 0, ptr %a.var, align 4, !dbg !8
+// CHECK:STDOUT:   %.loc16 = load i32, ptr %a.var, align 4, !dbg !9
+// CHECK:STDOUT:   ret i32 %.loc16, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -44,7 +44,8 @@ fn F() -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "local.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 10, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !4)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 10, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 16, column: 3, scope: !4)

+ 1 - 1
toolchain/lower/testdata/array/array_in_place.carbon

@@ -48,7 +48,7 @@ fn G() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "array_in_place.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 16, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 16, column: 38, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 16, column: 39, scope: !4)

+ 29 - 26
toolchain/lower/testdata/array/assign_return_value.carbon

@@ -24,29 +24,29 @@ fn Run() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main(ptr sret({ i32, i32 }) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @tuple.014.loc13_39, i64 8, i1 false), !dbg !8
-// CHECK:STDOUT:   ret void, !dbg !8
+// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !8
+// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !8
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @tuple.014.loc13_39, i64 8, i1 false), !dbg !9
+// CHECK:STDOUT:   ret void, !dbg !9
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @main() #0 !dbg !9 {
+// CHECK:STDOUT: define void @main() #0 !dbg !10 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %t.var = alloca [2 x i32], align 4, !dbg !10
-// CHECK:STDOUT:   %.loc16_28.1.temp = alloca { i32, i32 }, align 8, !dbg !11
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %t.var), !dbg !10
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc16_28.1.temp), !dbg !11
-// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc16_28.1.temp), !dbg !11
-// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %.loc16_28.1.temp, i32 0, i32 0, !dbg !11
-// CHECK:STDOUT:   %.loc16_28.3 = load i32, ptr %tuple.elem0.tuple.elem, align 4, !dbg !11
-// CHECK:STDOUT:   %.loc16_28.4.array.index = getelementptr inbounds [2 x i32], ptr %t.var, i32 0, i64 0, !dbg !11
-// CHECK:STDOUT:   store i32 %.loc16_28.3, ptr %.loc16_28.4.array.index, align 4, !dbg !11
-// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %.loc16_28.1.temp, i32 0, i32 1, !dbg !11
-// CHECK:STDOUT:   %.loc16_28.6 = load i32, ptr %tuple.elem1.tuple.elem, align 4, !dbg !11
-// CHECK:STDOUT:   %.loc16_28.7.array.index = getelementptr inbounds [2 x i32], ptr %t.var, i32 0, i64 1, !dbg !11
-// CHECK:STDOUT:   store i32 %.loc16_28.6, ptr %.loc16_28.7.array.index, align 4, !dbg !11
-// CHECK:STDOUT:   ret void, !dbg !12
+// CHECK:STDOUT:   %t.var = alloca [2 x i32], align 4, !dbg !13
+// CHECK:STDOUT:   %.loc16_28.1.temp = alloca { i32, i32 }, align 8, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %t.var), !dbg !13
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc16_28.1.temp), !dbg !14
+// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc16_28.1.temp), !dbg !14
+// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %.loc16_28.1.temp, i32 0, i32 0, !dbg !14
+// CHECK:STDOUT:   %.loc16_28.3 = load i32, ptr %tuple.elem0.tuple.elem, align 4, !dbg !14
+// CHECK:STDOUT:   %.loc16_28.4.array.index = getelementptr inbounds [2 x i32], ptr %t.var, i32 0, i64 0, !dbg !14
+// CHECK:STDOUT:   store i32 %.loc16_28.3, ptr %.loc16_28.4.array.index, align 4, !dbg !14
+// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %.loc16_28.1.temp, i32 0, i32 1, !dbg !14
+// CHECK:STDOUT:   %.loc16_28.6 = load i32, ptr %tuple.elem1.tuple.elem, align 4, !dbg !14
+// CHECK:STDOUT:   %.loc16_28.7.array.index = getelementptr inbounds [2 x i32], ptr %t.var, i32 0, i64 1, !dbg !14
+// CHECK:STDOUT:   store i32 %.loc16_28.6, ptr %.loc16_28.7.array.index, align 4, !dbg !14
+// CHECK:STDOUT:   ret void, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -71,10 +71,13 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "assign_return_value.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 31, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 13, column: 24, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 16, column: 3, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 16, column: 26, scope: !9)
-// CHECK:STDOUT: !12 = !DILocation(line: 15, column: 1, scope: !9)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 13, column: 31, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 13, column: 24, scope: !4)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 15, type: !11, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !11 = !DISubroutineType(types: !12)
+// CHECK:STDOUT: !12 = !{null}
+// CHECK:STDOUT: !13 = !DILocation(line: 16, column: 3, scope: !10)
+// CHECK:STDOUT: !14 = !DILocation(line: 16, column: 26, scope: !10)
+// CHECK:STDOUT: !15 = !DILocation(line: 15, column: 1, scope: !10)

+ 1 - 1
toolchain/lower/testdata/array/base.carbon

@@ -92,7 +92,7 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "base.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 15, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !4)

+ 37 - 29
toolchain/lower/testdata/array/field.carbon

@@ -33,32 +33,32 @@ class A {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CInit.A.Main(ptr sret({ [2 x i32] }) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc16_39.2.v = getelementptr inbounds nuw { [2 x i32] }, ptr %return, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc16_38.3.array.index = getelementptr inbounds [2 x i32], ptr %.loc16_39.2.v, i32 0, i64 0, !dbg !8
-// CHECK:STDOUT:   %.loc16_38.6.array.index = getelementptr inbounds [2 x i32], ptr %.loc16_39.2.v, i32 0, i64 1, !dbg !8
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @A.val.loc16_40, i64 8, i1 false), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   %.loc16_39.2.v = getelementptr inbounds nuw { [2 x i32] }, ptr %return, i32 0, i32 0, !dbg !8
+// CHECK:STDOUT:   %.loc16_38.3.array.index = getelementptr inbounds [2 x i32], ptr %.loc16_39.2.v, i32 0, i64 0, !dbg !9
+// CHECK:STDOUT:   %.loc16_38.6.array.index = getelementptr inbounds [2 x i32], ptr %.loc16_39.2.v, i32 0, i64 1, !dbg !9
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @A.val.loc16_40, i64 8, i1 false), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CAccess.A.Main(ptr %self) #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CAccess.A.Main(ptr %self) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc19_16.1.v = getelementptr inbounds nuw { [2 x i32] }, ptr %self, i32 0, i32 0, !dbg !11
-// CHECK:STDOUT:   %.loc19_20.2.array.index = getelementptr inbounds [2 x i32], ptr %.loc19_16.1.v, i32 0, i32 0, !dbg !11
-// CHECK:STDOUT:   %.loc19_20.3 = load i32, ptr %.loc19_20.2.array.index, align 4, !dbg !11
-// CHECK:STDOUT:   ret i32 %.loc19_20.3, !dbg !12
+// CHECK:STDOUT:   %.loc19_16.1.v = getelementptr inbounds nuw { [2 x i32] }, ptr %self, i32 0, i32 0, !dbg !17
+// CHECK:STDOUT:   %.loc19_20.2.array.index = getelementptr inbounds [2 x i32], ptr %.loc19_16.1.v, i32 0, i32 0, !dbg !17
+// CHECK:STDOUT:   %.loc19_20.3 = load i32, ptr %.loc19_20.2.array.index, align 4, !dbg !17
+// CHECK:STDOUT:   ret i32 %.loc19_20.3, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CUse.A.Main(ptr %self) #0 !dbg !13 {
+// CHECK:STDOUT: define i32 @_CUse.A.Main(ptr %self) #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc23_9.v = getelementptr inbounds nuw { [2 x i32] }, ptr %self, i32 0, i32 0, !dbg !14
-// CHECK:STDOUT:   %.loc23_13.array.index = getelementptr inbounds [2 x i32], ptr %.loc23_9.v, i32 0, i32 0, !dbg !14
-// CHECK:STDOUT:   store i32 1, ptr %.loc23_13.array.index, align 4, !dbg !14
-// CHECK:STDOUT:   %.loc24_16.v = getelementptr inbounds nuw { [2 x i32] }, ptr %self, i32 0, i32 0, !dbg !15
-// CHECK:STDOUT:   %.loc24_20.1.array.index = getelementptr inbounds [2 x i32], ptr %.loc24_16.v, i32 0, i32 1, !dbg !15
-// CHECK:STDOUT:   %.loc24_20.2 = load i32, ptr %.loc24_20.1.array.index, align 4, !dbg !15
-// CHECK:STDOUT:   ret i32 %.loc24_20.2, !dbg !16
+// CHECK:STDOUT:   %.loc23_9.v = getelementptr inbounds nuw { [2 x i32] }, ptr %self, i32 0, i32 0, !dbg !22
+// CHECK:STDOUT:   %.loc23_13.array.index = getelementptr inbounds [2 x i32], ptr %.loc23_9.v, i32 0, i32 0, !dbg !22
+// CHECK:STDOUT:   store i32 1, ptr %.loc23_13.array.index, align 4, !dbg !22
+// CHECK:STDOUT:   %.loc24_16.v = getelementptr inbounds nuw { [2 x i32] }, ptr %self, i32 0, i32 0, !dbg !23
+// CHECK:STDOUT:   %.loc24_20.1.array.index = getelementptr inbounds [2 x i32], ptr %.loc24_16.v, i32 0, i32 1, !dbg !23
+// CHECK:STDOUT:   %.loc24_20.2 = load i32, ptr %.loc24_20.1.array.index, align 4, !dbg !23
+// CHECK:STDOUT:   ret i32 %.loc24_20.2, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -76,14 +76,22 @@ class A {
 // CHECK:STDOUT: !3 = !DIFile(filename: "field.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Init", linkageName: "_CInit.A.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 16, column: 27, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 33, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 20, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Access", linkageName: "_CAccess.A.Main", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 19, column: 12, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 19, column: 5, scope: !10)
-// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.A.Main", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !14 = !DILocation(line: 23, column: 5, scope: !13)
-// CHECK:STDOUT: !15 = !DILocation(line: 24, column: 12, scope: !13)
-// CHECK:STDOUT: !16 = !DILocation(line: 24, column: 5, scope: !13)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 27, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 33, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 16, column: 20, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Access", linkageName: "_CAccess.A.Main", scope: null, file: !3, line: 18, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{!14, !7}
+// CHECK:STDOUT: !14 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !15 = !{!16}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !11, type: !7)
+// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 12, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 19, column: 5, scope: !11)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.A.Main", scope: null, file: !3, line: 22, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !19, type: !7)
+// CHECK:STDOUT: !22 = !DILocation(line: 23, column: 5, scope: !19)
+// CHECK:STDOUT: !23 = !DILocation(line: 24, column: 12, scope: !19)
+// CHECK:STDOUT: !24 = !DILocation(line: 24, column: 5, scope: !19)

+ 27 - 20
toolchain/lower/testdata/array/function_param.carbon

@@ -26,22 +26,22 @@ fn G() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CF.Main(ptr %arr, i32 %i) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc14_15.2.array.index = getelementptr inbounds [3 x i32], ptr %arr, i32 0, i32 %i, !dbg !7
-// CHECK:STDOUT:   %.loc14_15.3 = load i32, ptr %.loc14_15.2.array.index, align 4, !dbg !7
-// CHECK:STDOUT:   ret i32 %.loc14_15.3, !dbg !8
+// CHECK:STDOUT:   %.loc14_15.2.array.index = getelementptr inbounds [3 x i32], ptr %arr, i32 0, i32 %i, !dbg !12
+// CHECK:STDOUT:   %.loc14_15.3 = load i32, ptr %.loc14_15.2.array.index, align 4, !dbg !12
+// CHECK:STDOUT:   ret i32 %.loc14_15.3, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CG.Main() #0 !dbg !9 {
+// CHECK:STDOUT: define i32 @_CG.Main() #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc18_20.3.temp = alloca [3 x i32], align 4, !dbg !10
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_20.3.temp), !dbg !10
-// CHECK:STDOUT:   %.loc18_20.4.array.index = getelementptr inbounds [3 x i32], ptr %.loc18_20.3.temp, i32 0, i64 0, !dbg !10
-// CHECK:STDOUT:   %.loc18_20.7.array.index = getelementptr inbounds [3 x i32], ptr %.loc18_20.3.temp, i32 0, i64 1, !dbg !10
-// CHECK:STDOUT:   %.loc18_20.10.array.index = getelementptr inbounds [3 x i32], ptr %.loc18_20.3.temp, i32 0, i64 2, !dbg !10
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %.loc18_20.3.temp, ptr align 4 @array.loc18_20.13, i64 12, i1 false), !dbg !10
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main(ptr %.loc18_20.3.temp, i32 1), !dbg !11
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !12
+// CHECK:STDOUT:   %.loc18_20.3.temp = alloca [3 x i32], align 4, !dbg !17
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_20.3.temp), !dbg !17
+// CHECK:STDOUT:   %.loc18_20.4.array.index = getelementptr inbounds [3 x i32], ptr %.loc18_20.3.temp, i32 0, i64 0, !dbg !17
+// CHECK:STDOUT:   %.loc18_20.7.array.index = getelementptr inbounds [3 x i32], ptr %.loc18_20.3.temp, i32 0, i64 1, !dbg !17
+// CHECK:STDOUT:   %.loc18_20.10.array.index = getelementptr inbounds [3 x i32], ptr %.loc18_20.3.temp, i32 0, i64 2, !dbg !17
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %.loc18_20.3.temp, ptr align 4 @array.loc18_20.13, i64 12, i1 false), !dbg !17
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main(ptr %.loc18_20.3.temp, i32 1), !dbg !18
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -61,12 +61,19 @@ fn G() -> i32 {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "function_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 18, column: 12, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 18, column: 10, scope: !9)
-// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 3, scope: !9)
+// CHECK:STDOUT: !6 = !{!7, !8, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10, !11}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !12 = !DILocation(line: 14, column: 10, scope: !4)
+// CHECK:STDOUT: !13 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 17, type: !15, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{!7}
+// CHECK:STDOUT: !17 = !DILocation(line: 18, column: 12, scope: !14)
+// CHECK:STDOUT: !18 = !DILocation(line: 18, column: 10, scope: !14)
+// CHECK:STDOUT: !19 = !DILocation(line: 18, column: 3, scope: !14)

+ 147 - 105
toolchain/lower/testdata/array/iterate.carbon

@@ -68,102 +68,102 @@ fn F() {
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @"_CNewCursor.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c"(ptr %self) #0 !dbg !12 {
-// CHECK:STDOUT:   ret i32 0, !dbg !14
+// CHECK:STDOUT:   ret i32 0, !dbg !20
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNext.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c"(ptr sret({ i32, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !15 {
-// CHECK:STDOUT:   %1 = load i32, ptr %cursor, align 4, !dbg !16
-// CHECK:STDOUT:   %2 = icmp slt i32 %1, 6, !dbg !16
-// CHECK:STDOUT:   br i1 %2, label %3, label %7, !dbg !17
+// CHECK:STDOUT: define linkonce_odr void @"_CNext.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c"(ptr sret({ i32, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !21 {
+// CHECK:STDOUT:   %1 = load i32, ptr %cursor, align 4, !dbg !27
+// CHECK:STDOUT:   %2 = icmp slt i32 %1, 6, !dbg !27
+// CHECK:STDOUT:   br i1 %2, label %3, label %7, !dbg !28
 // CHECK:STDOUT:
 // CHECK:STDOUT: 3:                                                ; preds = %0
-// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %cursor), !dbg !18
-// CHECK:STDOUT:   %4 = load i32, ptr %cursor, align 4, !dbg !19
-// CHECK:STDOUT:   %5 = sub i32 %4, 1, !dbg !19
-// CHECK:STDOUT:   %array.index = getelementptr inbounds [6 x i32], ptr %self, i32 0, i32 %5, !dbg !20
-// CHECK:STDOUT:   %6 = load i32, ptr %array.index, align 4, !dbg !20
-// CHECK:STDOUT:   call void @_CSome.Optional.Core.9a253b43086de47c(ptr %return, i32 %6), !dbg !21
-// CHECK:STDOUT:   ret void, !dbg !22
+// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %cursor), !dbg !29
+// CHECK:STDOUT:   %4 = load i32, ptr %cursor, align 4, !dbg !30
+// CHECK:STDOUT:   %5 = sub i32 %4, 1, !dbg !30
+// CHECK:STDOUT:   %array.index = getelementptr inbounds [6 x i32], ptr %self, i32 0, i32 %5, !dbg !31
+// CHECK:STDOUT:   %6 = load i32, ptr %array.index, align 4, !dbg !31
+// CHECK:STDOUT:   call void @_CSome.Optional.Core.9a253b43086de47c(ptr %return, i32 %6), !dbg !32
+// CHECK:STDOUT:   ret void, !dbg !33
 // CHECK:STDOUT:
 // CHECK:STDOUT: 7:                                                ; preds = %0
-// CHECK:STDOUT:   call void @_CNone.Optional.Core.9a253b43086de47c(ptr %return), !dbg !23
-// CHECK:STDOUT:   ret void, !dbg !24
+// CHECK:STDOUT:   call void @_CNone.Optional.Core.9a253b43086de47c(ptr %return), !dbg !34
+// CHECK:STDOUT:   ret void, !dbg !35
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.9a253b43086de47c(ptr %self) #0 !dbg !25 {
-// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %self), !dbg !27
-// CHECK:STDOUT:   ret i1 %1, !dbg !28
+// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.9a253b43086de47c(ptr %self) #0 !dbg !36 {
+// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %self), !dbg !42
+// CHECK:STDOUT:   ret i1 %1, !dbg !43
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CGet.Optional.Core.9a253b43086de47c(ptr %self) #0 !dbg !29 {
-// CHECK:STDOUT:   %1 = call i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %self), !dbg !30
-// CHECK:STDOUT:   ret i32 %1, !dbg !31
+// CHECK:STDOUT: define linkonce_odr i32 @_CGet.Optional.Core.9a253b43086de47c(ptr %self) #0 !dbg !44 {
+// CHECK:STDOUT:   %1 = call i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %self), !dbg !47
+// CHECK:STDOUT:   ret i32 %1, !dbg !48
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !32 {
-// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.dbc952efa35fc763"(ptr %self, i32 1), !dbg !34
-// CHECK:STDOUT:   ret void, !dbg !35
+// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !49 {
+// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.dbc952efa35fc763"(ptr %self, i32 1), !dbg !55
+// CHECK:STDOUT:   ret void, !dbg !56
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CSome.Optional.Core.9a253b43086de47c(ptr sret({ i32, i1 }) %return, i32 %value) #0 !dbg !36 {
-// CHECK:STDOUT:   call void @"_CSome.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %return, i32 %value), !dbg !37
-// CHECK:STDOUT:   ret void, !dbg !38
+// CHECK:STDOUT: define linkonce_odr void @_CSome.Optional.Core.9a253b43086de47c(ptr sret({ i32, i1 }) %return, i32 %value) #0 !dbg !57 {
+// CHECK:STDOUT:   call void @"_CSome.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %return, i32 %value), !dbg !62
+// CHECK:STDOUT:   ret void, !dbg !63
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.9a253b43086de47c(ptr sret({ i32, i1 }) %return) #0 !dbg !39 {
-// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %return), !dbg !40
-// CHECK:STDOUT:   ret void, !dbg !41
+// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.9a253b43086de47c(ptr sret({ i32, i1 }) %return) #0 !dbg !64 {
+// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %return), !dbg !67
+// CHECK:STDOUT:   ret void, !dbg !68
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %value) #0 !dbg !42 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 1, !dbg !43
-// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !43
-// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !43
-// CHECK:STDOUT:   ret i1 %2, !dbg !44
+// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %value) #0 !dbg !69 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 1, !dbg !72
+// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !72
+// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !72
+// CHECK:STDOUT:   ret i1 %2, !dbg !73
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %value) #0 !dbg !45 {
-// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 0, !dbg !46
-// CHECK:STDOUT:   %1 = load i32, ptr %value1, align 4, !dbg !46
-// CHECK:STDOUT:   ret i32 %1, !dbg !47
+// CHECK:STDOUT: define linkonce_odr i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr %value) #0 !dbg !74 {
+// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 0, !dbg !77
+// CHECK:STDOUT:   %1 = load i32, ptr %value1, align 4, !dbg !77
+// CHECK:STDOUT:   ret i32 %1, !dbg !78
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: alwaysinline nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.dbc952efa35fc763"(ptr %self, i32 %other) #3 !dbg !48 {
-// CHECK:STDOUT:   %1 = call i32 @"_CConvert.02bbc8f98b95ea6d:ImplicitAs.Core.5854fed63e66a74b"(i32 %other), !dbg !49
-// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !50
-// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !50
-// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !50
-// CHECK:STDOUT:   ret void, !dbg !50
+// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.dbc952efa35fc763"(ptr %self, i32 %other) #3 !dbg !79 {
+// CHECK:STDOUT:   %1 = call i32 @"_CConvert.02bbc8f98b95ea6d:ImplicitAs.Core.5854fed63e66a74b"(i32 %other), !dbg !85
+// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !86
+// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !86
+// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !86
+// CHECK:STDOUT:   ret void, !dbg !86
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CSome.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr sret({ i32, i1 }) %return, i32 %self) #0 !dbg !51 {
-// CHECK:STDOUT:   %value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 0, !dbg !52
-// CHECK:STDOUT:   store i32 %self, ptr %value, align 4, !dbg !52
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !53
-// CHECK:STDOUT:   store i8 1, ptr %has_value, align 1, !dbg !53
-// CHECK:STDOUT:   ret void, !dbg !54
+// CHECK:STDOUT: define linkonce_odr void @"_CSome.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr sret({ i32, i1 }) %return, i32 %self) #0 !dbg !87 {
+// CHECK:STDOUT:   %value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 0, !dbg !90
+// CHECK:STDOUT:   store i32 %self, ptr %value, align 4, !dbg !90
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !91
+// CHECK:STDOUT:   store i8 1, ptr %has_value, align 1, !dbg !91
+// CHECK:STDOUT:   ret void, !dbg !92
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr sret({ i32, i1 }) %return) #0 !dbg !55 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !56
-// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !56
-// CHECK:STDOUT:   ret void, !dbg !57
+// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899"(ptr sret({ i32, i1 }) %return) #0 !dbg !93 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !94
+// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !94
+// CHECK:STDOUT:   ret void, !dbg !95
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.02bbc8f98b95ea6d:ImplicitAs.Core.5854fed63e66a74b"(i32 %self) #0 !dbg !58 {
-// CHECK:STDOUT:   ret i32 %self, !dbg !60
+// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.02bbc8f98b95ea6d:ImplicitAs.Core.5854fed63e66a74b"(i32 %self) #0 !dbg !96 {
+// CHECK:STDOUT:   ret i32 %self, !dbg !102
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -183,58 +183,100 @@ fn F() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "iterate.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 16, column: 26, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 17, column: 7, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 18, column: 5, scope: !4)
 // CHECK:STDOUT: !10 = !DILocation(line: 17, column: 3, scope: !4)
 // CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !4)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c", scope: null, file: !13, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c", scope: null, file: !13, line: 23, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
 // CHECK:STDOUT: !13 = !DIFile(filename: "{{.*}}/prelude/iterate.carbon", directory: "")
-// CHECK:STDOUT: !14 = !DILocation(line: 23, column: 39, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c", scope: null, file: !13, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 25, column: 9, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 25, column: 8, scope: !15)
-// CHECK:STDOUT: !18 = !DILocation(line: 26, column: 7, scope: !15)
-// CHECK:STDOUT: !19 = !DILocation(line: 27, column: 36, scope: !15)
-// CHECK:STDOUT: !20 = !DILocation(line: 27, column: 31, scope: !15)
-// CHECK:STDOUT: !21 = !DILocation(line: 27, column: 14, scope: !15)
-// CHECK:STDOUT: !22 = !DILocation(line: 27, column: 7, scope: !15)
-// CHECK:STDOUT: !23 = !DILocation(line: 29, column: 14, scope: !15)
-// CHECK:STDOUT: !24 = !DILocation(line: 29, column: 7, scope: !15)
-// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.9a253b43086de47c", scope: null, file: !26, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !26 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
-// CHECK:STDOUT: !27 = !DILocation(line: 33, column: 12, scope: !25)
-// CHECK:STDOUT: !28 = !DILocation(line: 33, column: 5, scope: !25)
-// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.9a253b43086de47c", scope: null, file: !26, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !30 = !DILocation(line: 36, column: 12, scope: !29)
-// CHECK:STDOUT: !31 = !DILocation(line: 36, column: 5, scope: !29)
-// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !33, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !33 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !34 = !DILocation(line: 341, column: 5, scope: !32)
-// CHECK:STDOUT: !35 = !DILocation(line: 339, column: 3, scope: !32)
-// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.Optional.Core.9a253b43086de47c", scope: null, file: !26, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !37 = !DILocation(line: 30, column: 12, scope: !36)
-// CHECK:STDOUT: !38 = !DILocation(line: 30, column: 5, scope: !36)
-// CHECK:STDOUT: !39 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.9a253b43086de47c", scope: null, file: !26, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !40 = !DILocation(line: 27, column: 12, scope: !39)
-// CHECK:STDOUT: !41 = !DILocation(line: 27, column: 5, scope: !39)
-// CHECK:STDOUT: !42 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !26, line: 112, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !43 = !DILocation(line: 113, column: 12, scope: !42)
-// CHECK:STDOUT: !44 = !DILocation(line: 113, column: 5, scope: !42)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !26, line: 115, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 116, column: 12, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 116, column: 5, scope: !45)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.dbc952efa35fc763", scope: null, file: !33, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 4294967295, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 275, column: 3, scope: !48)
-// CHECK:STDOUT: !51 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !26, line: 104, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !52 = !DILocation(line: 108, column: 5, scope: !51)
-// CHECK:STDOUT: !53 = !DILocation(line: 109, column: 5, scope: !51)
-// CHECK:STDOUT: !54 = !DILocation(line: 110, column: 5, scope: !51)
-// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !26, line: 99, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !56 = !DILocation(line: 101, column: 5, scope: !55)
-// CHECK:STDOUT: !57 = !DILocation(line: 102, column: 5, scope: !55)
-// CHECK:STDOUT: !58 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.02bbc8f98b95ea6d:ImplicitAs.Core.5854fed63e66a74b", scope: null, file: !59, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !59 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
-// CHECK:STDOUT: !60 = !DILocation(line: 24, column: 38, scope: !58)
+// CHECK:STDOUT: !14 = !DISubroutineType(types: !15)
+// CHECK:STDOUT: !15 = !{!16, !17}
+// CHECK:STDOUT: !16 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !17 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !18 = !{!19}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !12, type: !17)
+// CHECK:STDOUT: !20 = !DILocation(line: 23, column: 39, scope: !12)
+// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.f06e388f4a5bd5ec:Iterate.Core.a21f6adcc8abe06c", scope: null, file: !13, line: 24, type: !22, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
+// CHECK:STDOUT: !22 = !DISubroutineType(types: !23)
+// CHECK:STDOUT: !23 = !{!17, !17, !17}
+// CHECK:STDOUT: !24 = !{!25, !26}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !21, type: !17)
+// CHECK:STDOUT: !26 = !DILocalVariable(arg: 2, scope: !21, type: !17)
+// CHECK:STDOUT: !27 = !DILocation(line: 25, column: 9, scope: !21)
+// CHECK:STDOUT: !28 = !DILocation(line: 25, column: 8, scope: !21)
+// CHECK:STDOUT: !29 = !DILocation(line: 26, column: 7, scope: !21)
+// CHECK:STDOUT: !30 = !DILocation(line: 27, column: 36, scope: !21)
+// CHECK:STDOUT: !31 = !DILocation(line: 27, column: 31, scope: !21)
+// CHECK:STDOUT: !32 = !DILocation(line: 27, column: 14, scope: !21)
+// CHECK:STDOUT: !33 = !DILocation(line: 27, column: 7, scope: !21)
+// CHECK:STDOUT: !34 = !DILocation(line: 29, column: 14, scope: !21)
+// CHECK:STDOUT: !35 = !DILocation(line: 29, column: 7, scope: !21)
+// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.9a253b43086de47c", scope: null, file: !37, line: 32, type: !38, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !40)
+// CHECK:STDOUT: !37 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
+// CHECK:STDOUT: !38 = !DISubroutineType(types: !39)
+// CHECK:STDOUT: !39 = !{!17, !17}
+// CHECK:STDOUT: !40 = !{!41}
+// CHECK:STDOUT: !41 = !DILocalVariable(arg: 1, scope: !36, type: !17)
+// CHECK:STDOUT: !42 = !DILocation(line: 33, column: 12, scope: !36)
+// CHECK:STDOUT: !43 = !DILocation(line: 33, column: 5, scope: !36)
+// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.9a253b43086de47c", scope: null, file: !37, line: 35, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !45)
+// CHECK:STDOUT: !45 = !{!46}
+// CHECK:STDOUT: !46 = !DILocalVariable(arg: 1, scope: !44, type: !17)
+// CHECK:STDOUT: !47 = !DILocation(line: 36, column: 12, scope: !44)
+// CHECK:STDOUT: !48 = !DILocation(line: 36, column: 5, scope: !44)
+// CHECK:STDOUT: !49 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !50, line: 339, type: !51, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !53)
+// CHECK:STDOUT: !50 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !51 = !DISubroutineType(types: !52)
+// CHECK:STDOUT: !52 = !{null, !16}
+// CHECK:STDOUT: !53 = !{!54}
+// CHECK:STDOUT: !54 = !DILocalVariable(arg: 1, scope: !49, type: !16)
+// CHECK:STDOUT: !55 = !DILocation(line: 341, column: 5, scope: !49)
+// CHECK:STDOUT: !56 = !DILocation(line: 339, column: 3, scope: !49)
+// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.Optional.Core.9a253b43086de47c", scope: null, file: !37, line: 29, type: !58, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !60)
+// CHECK:STDOUT: !58 = !DISubroutineType(types: !59)
+// CHECK:STDOUT: !59 = !{!17, !16}
+// CHECK:STDOUT: !60 = !{!61}
+// CHECK:STDOUT: !61 = !DILocalVariable(arg: 1, scope: !57, type: !16)
+// CHECK:STDOUT: !62 = !DILocation(line: 30, column: 12, scope: !57)
+// CHECK:STDOUT: !63 = !DILocation(line: 30, column: 5, scope: !57)
+// CHECK:STDOUT: !64 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.9a253b43086de47c", scope: null, file: !37, line: 26, type: !65, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !65 = !DISubroutineType(types: !66)
+// CHECK:STDOUT: !66 = !{!17}
+// CHECK:STDOUT: !67 = !DILocation(line: 27, column: 12, scope: !64)
+// CHECK:STDOUT: !68 = !DILocation(line: 27, column: 5, scope: !64)
+// CHECK:STDOUT: !69 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !37, line: 112, type: !38, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !70)
+// CHECK:STDOUT: !70 = !{!71}
+// CHECK:STDOUT: !71 = !DILocalVariable(arg: 1, scope: !69, type: !17)
+// CHECK:STDOUT: !72 = !DILocation(line: 113, column: 12, scope: !69)
+// CHECK:STDOUT: !73 = !DILocation(line: 113, column: 5, scope: !69)
+// CHECK:STDOUT: !74 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !37, line: 115, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !75)
+// CHECK:STDOUT: !75 = !{!76}
+// CHECK:STDOUT: !76 = !DILocalVariable(arg: 1, scope: !74, type: !17)
+// CHECK:STDOUT: !77 = !DILocation(line: 116, column: 12, scope: !74)
+// CHECK:STDOUT: !78 = !DILocation(line: 116, column: 5, scope: !74)
+// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.dbc952efa35fc763", scope: null, file: !50, line: 275, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !82)
+// CHECK:STDOUT: !80 = !DISubroutineType(types: !81)
+// CHECK:STDOUT: !81 = !{null, !16, !16}
+// CHECK:STDOUT: !82 = !{!83, !84}
+// CHECK:STDOUT: !83 = !DILocalVariable(arg: 1, scope: !79, type: !16)
+// CHECK:STDOUT: !84 = !DILocalVariable(arg: 2, scope: !79, type: !16)
+// CHECK:STDOUT: !85 = !DILocation(line: 4294967295, scope: !79)
+// CHECK:STDOUT: !86 = !DILocation(line: 275, column: 3, scope: !79)
+// CHECK:STDOUT: !87 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !37, line: 104, type: !58, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !88)
+// CHECK:STDOUT: !88 = !{!89}
+// CHECK:STDOUT: !89 = !DILocalVariable(arg: 1, scope: !87, type: !16)
+// CHECK:STDOUT: !90 = !DILocation(line: 108, column: 5, scope: !87)
+// CHECK:STDOUT: !91 = !DILocation(line: 109, column: 5, scope: !87)
+// CHECK:STDOUT: !92 = !DILocation(line: 110, column: 5, scope: !87)
+// CHECK:STDOUT: !93 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.5450dc8e8b8e0899", scope: null, file: !37, line: 99, type: !65, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !94 = !DILocation(line: 101, column: 5, scope: !93)
+// CHECK:STDOUT: !95 = !DILocation(line: 102, column: 5, scope: !93)
+// CHECK:STDOUT: !96 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.02bbc8f98b95ea6d:ImplicitAs.Core.5854fed63e66a74b", scope: null, file: !97, line: 24, type: !98, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !100)
+// CHECK:STDOUT: !97 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
+// CHECK:STDOUT: !98 = !DISubroutineType(types: !99)
+// CHECK:STDOUT: !99 = !{!16, !16}
+// CHECK:STDOUT: !100 = !{!101}
+// CHECK:STDOUT: !101 = !DILocalVariable(arg: 1, scope: !96, type: !16)
+// CHECK:STDOUT: !102 = !DILocation(line: 24, column: 38, scope: !96)

+ 32 - 22
toolchain/lower/testdata/builtins/bool.carbon

@@ -29,28 +29,28 @@ fn IfEq(a: Bool(), b: Bool()) -> Bool() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i1 @_CTestEq.Main(i1 %a, i1 %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Eq.call = icmp eq i1 %a, %b, !dbg !7
-// CHECK:STDOUT:   ret i1 %Eq.call, !dbg !8
+// CHECK:STDOUT:   %Eq.call = icmp eq i1 %a, %b, !dbg !11
+// CHECK:STDOUT:   ret i1 %Eq.call, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestNeq.Main(i1 %a, i1 %b) #0 !dbg !9 {
+// CHECK:STDOUT: define i1 @_CTestNeq.Main(i1 %a, i1 %b) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Neq.call = icmp ne i1 %a, %b, !dbg !10
-// CHECK:STDOUT:   ret i1 %Neq.call, !dbg !11
+// CHECK:STDOUT:   %Neq.call = icmp ne i1 %a, %b, !dbg !17
+// CHECK:STDOUT:   ret i1 %Neq.call, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CIfEq.Main(i1 %a, i1 %b) #0 !dbg !12 {
+// CHECK:STDOUT: define i1 @_CIfEq.Main(i1 %a, i1 %b) #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Eq.call = icmp eq i1 %a, %b, !dbg !13
-// CHECK:STDOUT:   br i1 %Eq.call, label %if.then, label %if.else, !dbg !14
+// CHECK:STDOUT:   %Eq.call = icmp eq i1 %a, %b, !dbg !23
+// CHECK:STDOUT:   br i1 %Eq.call, label %if.then, label %if.else, !dbg !24
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i1 true, !dbg !15
+// CHECK:STDOUT:   ret i1 true, !dbg !25
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i1 false, !dbg !16
+// CHECK:STDOUT:   ret i1 false, !dbg !26
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -62,16 +62,26 @@ fn IfEq(a: Bool(), b: Bool()) -> Bool() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "bool.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestEq", linkageName: "_CTestEq.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestEq", linkageName: "_CTestEq.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 16, column: 52, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 45, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "TestNeq", linkageName: "_CTestNeq.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 19, column: 53, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 19, column: 46, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "IfEq", linkageName: "_CIfEq.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 22, column: 7, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 22, column: 6, scope: !12)
-// CHECK:STDOUT: !15 = !DILocation(line: 22, column: 19, scope: !12)
-// CHECK:STDOUT: !16 = !DILocation(line: 23, column: 3, scope: !12)
+// CHECK:STDOUT: !6 = !{!7, !7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 16, column: 52, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 16, column: 45, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "TestNeq", linkageName: "_CTestNeq.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !14 = !{!15, !16}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !13, type: !7)
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 2, scope: !13, type: !7)
+// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 53, scope: !13)
+// CHECK:STDOUT: !18 = !DILocation(line: 19, column: 46, scope: !13)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "IfEq", linkageName: "_CIfEq.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !20 = !{!21, !22}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !19, type: !7)
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 2, scope: !19, type: !7)
+// CHECK:STDOUT: !23 = !DILocation(line: 22, column: 7, scope: !19)
+// CHECK:STDOUT: !24 = !DILocation(line: 22, column: 6, scope: !19)
+// CHECK:STDOUT: !25 = !DILocation(line: 22, column: 19, scope: !19)
+// CHECK:STDOUT: !26 = !DILocation(line: 23, column: 3, scope: !19)

+ 10 - 9
toolchain/lower/testdata/builtins/char.carbon

@@ -25,11 +25,11 @@ fn Example() -> char {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i8 @_CExample.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca i8, align 1, !dbg !7
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !7
-// CHECK:STDOUT:   store i8 97, ptr %c.var, align 1, !dbg !7
-// CHECK:STDOUT:   %.loc6 = load i8, ptr %c.var, align 1, !dbg !8
-// CHECK:STDOUT:   ret i8 %.loc6, !dbg !9
+// CHECK:STDOUT:   %c.var = alloca i8, align 1, !dbg !8
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !8
+// CHECK:STDOUT:   store i8 97, ptr %c.var, align 1, !dbg !8
+// CHECK:STDOUT:   %.loc6 = load i8, ptr %c.var, align 1, !dbg !9
+// CHECK:STDOUT:   ret i8 %.loc6, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -47,7 +47,8 @@ fn Example() -> char {
 // CHECK:STDOUT: !3 = !DIFile(filename: "basic.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Example", linkageName: "_CExample.Main", scope: null, file: !3, line: 4, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 5, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 6, column: 10, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 6, column: 3, scope: !4)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 8, encoding: DW_ATE_unsigned)
+// CHECK:STDOUT: !8 = !DILocation(line: 5, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 6, column: 10, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 6, column: 3, scope: !4)

+ 183 - 122
toolchain/lower/testdata/builtins/float.carbon

@@ -85,78 +85,78 @@ fn TestF128(a: f128, b: f128) -> f128 { return F128(a, b); }
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define double @_CTestNegate.Main(double %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Negate.call = fneg double %a, !dbg !7
-// CHECK:STDOUT:   ret double %Negate.call, !dbg !8
+// CHECK:STDOUT:   %Negate.call = fneg double %a, !dbg !10
+// CHECK:STDOUT:   ret double %Negate.call, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define double @_CTestAdd.Main(double %a, double %b) #0 !dbg !9 {
+// CHECK:STDOUT: define double @_CTestAdd.Main(double %a, double %b) #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Add.call = fadd double %a, %b, !dbg !10
-// CHECK:STDOUT:   ret double %Add.call, !dbg !11
+// CHECK:STDOUT:   %Add.call = fadd double %a, %b, !dbg !18
+// CHECK:STDOUT:   ret double %Add.call, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define double @_CTestSub.Main(double %a, double %b) #0 !dbg !12 {
+// CHECK:STDOUT: define double @_CTestSub.Main(double %a, double %b) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Sub.call = fsub double %a, %b, !dbg !13
-// CHECK:STDOUT:   ret double %Sub.call, !dbg !14
+// CHECK:STDOUT:   %Sub.call = fsub double %a, %b, !dbg !24
+// CHECK:STDOUT:   ret double %Sub.call, !dbg !25
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define double @_CTestMul.Main(double %a, double %b) #0 !dbg !15 {
+// CHECK:STDOUT: define double @_CTestMul.Main(double %a, double %b) #0 !dbg !26 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Mul.call = fmul double %a, %b, !dbg !16
-// CHECK:STDOUT:   ret double %Mul.call, !dbg !17
+// CHECK:STDOUT:   %Mul.call = fmul double %a, %b, !dbg !30
+// CHECK:STDOUT:   ret double %Mul.call, !dbg !31
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define double @_CTestDiv.Main(double %a, double %b) #0 !dbg !18 {
+// CHECK:STDOUT: define double @_CTestDiv.Main(double %a, double %b) #0 !dbg !32 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Div.call = fdiv double %a, %b, !dbg !19
-// CHECK:STDOUT:   ret double %Div.call, !dbg !20
+// CHECK:STDOUT:   %Div.call = fdiv double %a, %b, !dbg !36
+// CHECK:STDOUT:   ret double %Div.call, !dbg !37
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestEq.Main(double %a, double %b) #0 !dbg !21 {
+// CHECK:STDOUT: define i1 @_CTestEq.Main(double %a, double %b) #0 !dbg !38 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Eq.call = fcmp oeq double %a, %b, !dbg !22
-// CHECK:STDOUT:   ret i1 %Eq.call, !dbg !23
+// CHECK:STDOUT:   %Eq.call = fcmp oeq double %a, %b, !dbg !42
+// CHECK:STDOUT:   ret i1 %Eq.call, !dbg !43
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestNeq.Main(double %a, double %b) #0 !dbg !24 {
+// CHECK:STDOUT: define i1 @_CTestNeq.Main(double %a, double %b) #0 !dbg !44 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Neq.call = fcmp one double %a, %b, !dbg !25
-// CHECK:STDOUT:   ret i1 %Neq.call, !dbg !26
+// CHECK:STDOUT:   %Neq.call = fcmp one double %a, %b, !dbg !48
+// CHECK:STDOUT:   ret i1 %Neq.call, !dbg !49
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestLess.Main(double %a, double %b) #0 !dbg !27 {
+// CHECK:STDOUT: define i1 @_CTestLess.Main(double %a, double %b) #0 !dbg !50 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Less.call = fcmp olt double %a, %b, !dbg !28
-// CHECK:STDOUT:   ret i1 %Less.call, !dbg !29
+// CHECK:STDOUT:   %Less.call = fcmp olt double %a, %b, !dbg !54
+// CHECK:STDOUT:   ret i1 %Less.call, !dbg !55
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestLessEq.Main(double %a, double %b) #0 !dbg !30 {
+// CHECK:STDOUT: define i1 @_CTestLessEq.Main(double %a, double %b) #0 !dbg !56 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %LessEq.call = fcmp ole double %a, %b, !dbg !31
-// CHECK:STDOUT:   ret i1 %LessEq.call, !dbg !32
+// CHECK:STDOUT:   %LessEq.call = fcmp ole double %a, %b, !dbg !60
+// CHECK:STDOUT:   ret i1 %LessEq.call, !dbg !61
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestGreater.Main(double %a, double %b) #0 !dbg !33 {
+// CHECK:STDOUT: define i1 @_CTestGreater.Main(double %a, double %b) #0 !dbg !62 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Greater.call = fcmp ogt double %a, %b, !dbg !34
-// CHECK:STDOUT:   ret i1 %Greater.call, !dbg !35
+// CHECK:STDOUT:   %Greater.call = fcmp ogt double %a, %b, !dbg !66
+// CHECK:STDOUT:   ret i1 %Greater.call, !dbg !67
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestGreaterEq.Main(double %a, double %b) #0 !dbg !36 {
+// CHECK:STDOUT: define i1 @_CTestGreaterEq.Main(double %a, double %b) #0 !dbg !68 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %GreaterEq.call = fcmp oge double %a, %b, !dbg !37
-// CHECK:STDOUT:   ret i1 %GreaterEq.call, !dbg !38
+// CHECK:STDOUT:   %GreaterEq.call = fcmp oge double %a, %b, !dbg !72
+// CHECK:STDOUT:   ret i1 %GreaterEq.call, !dbg !73
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -168,78 +168,113 @@ fn TestF128(a: f128, b: f128) -> f128 { return F128(a, b); }
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "basic.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestNegate", linkageName: "_CTestNegate.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestNegate", linkageName: "_CTestNegate.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 5, column: 39, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 5, column: 32, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "TestAdd", linkageName: "_CTestAdd.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 8, column: 44, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 8, column: 37, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "TestSub", linkageName: "_CTestSub.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 11, column: 44, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 11, column: 37, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "TestMul", linkageName: "_CTestMul.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 14, column: 44, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 14, column: 37, scope: !15)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "TestDiv", linkageName: "_CTestDiv.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 17, column: 44, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 37, scope: !18)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "TestEq", linkageName: "_CTestEq.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 20, column: 44, scope: !21)
-// CHECK:STDOUT: !23 = !DILocation(line: 20, column: 37, scope: !21)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "TestNeq", linkageName: "_CTestNeq.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 23, column: 45, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 23, column: 38, scope: !24)
-// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "TestLess", linkageName: "_CTestLess.Main", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !28 = !DILocation(line: 26, column: 46, scope: !27)
-// CHECK:STDOUT: !29 = !DILocation(line: 26, column: 39, scope: !27)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "TestLessEq", linkageName: "_CTestLessEq.Main", scope: null, file: !3, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DILocation(line: 29, column: 48, scope: !30)
-// CHECK:STDOUT: !32 = !DILocation(line: 29, column: 41, scope: !30)
-// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "TestGreater", linkageName: "_CTestGreater.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !34 = !DILocation(line: 32, column: 49, scope: !33)
-// CHECK:STDOUT: !35 = !DILocation(line: 32, column: 42, scope: !33)
-// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "TestGreaterEq", linkageName: "_CTestGreaterEq.Main", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !37 = !DILocation(line: 35, column: 51, scope: !36)
-// CHECK:STDOUT: !38 = !DILocation(line: 35, column: 44, scope: !36)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 5, column: 39, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 5, column: 32, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "TestAdd", linkageName: "_CTestAdd.Main", scope: null, file: !3, line: 8, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{!7, !7, !7}
+// CHECK:STDOUT: !15 = !{!16, !17}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !12, type: !7)
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 2, scope: !12, type: !7)
+// CHECK:STDOUT: !18 = !DILocation(line: 8, column: 44, scope: !12)
+// CHECK:STDOUT: !19 = !DILocation(line: 8, column: 37, scope: !12)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "TestSub", linkageName: "_CTestSub.Main", scope: null, file: !3, line: 11, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !21)
+// CHECK:STDOUT: !21 = !{!22, !23}
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 1, scope: !20, type: !7)
+// CHECK:STDOUT: !23 = !DILocalVariable(arg: 2, scope: !20, type: !7)
+// CHECK:STDOUT: !24 = !DILocation(line: 11, column: 44, scope: !20)
+// CHECK:STDOUT: !25 = !DILocation(line: 11, column: 37, scope: !20)
+// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "TestMul", linkageName: "_CTestMul.Main", scope: null, file: !3, line: 14, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !27)
+// CHECK:STDOUT: !27 = !{!28, !29}
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 1, scope: !26, type: !7)
+// CHECK:STDOUT: !29 = !DILocalVariable(arg: 2, scope: !26, type: !7)
+// CHECK:STDOUT: !30 = !DILocation(line: 14, column: 44, scope: !26)
+// CHECK:STDOUT: !31 = !DILocation(line: 14, column: 37, scope: !26)
+// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "TestDiv", linkageName: "_CTestDiv.Main", scope: null, file: !3, line: 17, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !33)
+// CHECK:STDOUT: !33 = !{!34, !35}
+// CHECK:STDOUT: !34 = !DILocalVariable(arg: 1, scope: !32, type: !7)
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 2, scope: !32, type: !7)
+// CHECK:STDOUT: !36 = !DILocation(line: 17, column: 44, scope: !32)
+// CHECK:STDOUT: !37 = !DILocation(line: 17, column: 37, scope: !32)
+// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "TestEq", linkageName: "_CTestEq.Main", scope: null, file: !3, line: 20, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !39)
+// CHECK:STDOUT: !39 = !{!40, !41}
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 1, scope: !38, type: !7)
+// CHECK:STDOUT: !41 = !DILocalVariable(arg: 2, scope: !38, type: !7)
+// CHECK:STDOUT: !42 = !DILocation(line: 20, column: 44, scope: !38)
+// CHECK:STDOUT: !43 = !DILocation(line: 20, column: 37, scope: !38)
+// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "TestNeq", linkageName: "_CTestNeq.Main", scope: null, file: !3, line: 23, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !45)
+// CHECK:STDOUT: !45 = !{!46, !47}
+// CHECK:STDOUT: !46 = !DILocalVariable(arg: 1, scope: !44, type: !7)
+// CHECK:STDOUT: !47 = !DILocalVariable(arg: 2, scope: !44, type: !7)
+// CHECK:STDOUT: !48 = !DILocation(line: 23, column: 45, scope: !44)
+// CHECK:STDOUT: !49 = !DILocation(line: 23, column: 38, scope: !44)
+// CHECK:STDOUT: !50 = distinct !DISubprogram(name: "TestLess", linkageName: "_CTestLess.Main", scope: null, file: !3, line: 26, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !51)
+// CHECK:STDOUT: !51 = !{!52, !53}
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 1, scope: !50, type: !7)
+// CHECK:STDOUT: !53 = !DILocalVariable(arg: 2, scope: !50, type: !7)
+// CHECK:STDOUT: !54 = !DILocation(line: 26, column: 46, scope: !50)
+// CHECK:STDOUT: !55 = !DILocation(line: 26, column: 39, scope: !50)
+// CHECK:STDOUT: !56 = distinct !DISubprogram(name: "TestLessEq", linkageName: "_CTestLessEq.Main", scope: null, file: !3, line: 29, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !57)
+// CHECK:STDOUT: !57 = !{!58, !59}
+// CHECK:STDOUT: !58 = !DILocalVariable(arg: 1, scope: !56, type: !7)
+// CHECK:STDOUT: !59 = !DILocalVariable(arg: 2, scope: !56, type: !7)
+// CHECK:STDOUT: !60 = !DILocation(line: 29, column: 48, scope: !56)
+// CHECK:STDOUT: !61 = !DILocation(line: 29, column: 41, scope: !56)
+// CHECK:STDOUT: !62 = distinct !DISubprogram(name: "TestGreater", linkageName: "_CTestGreater.Main", scope: null, file: !3, line: 32, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !63)
+// CHECK:STDOUT: !63 = !{!64, !65}
+// CHECK:STDOUT: !64 = !DILocalVariable(arg: 1, scope: !62, type: !7)
+// CHECK:STDOUT: !65 = !DILocalVariable(arg: 2, scope: !62, type: !7)
+// CHECK:STDOUT: !66 = !DILocation(line: 32, column: 49, scope: !62)
+// CHECK:STDOUT: !67 = !DILocation(line: 32, column: 42, scope: !62)
+// CHECK:STDOUT: !68 = distinct !DISubprogram(name: "TestGreaterEq", linkageName: "_CTestGreaterEq.Main", scope: null, file: !3, line: 35, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !69)
+// CHECK:STDOUT: !69 = !{!70, !71}
+// CHECK:STDOUT: !70 = !DILocalVariable(arg: 1, scope: !68, type: !7)
+// CHECK:STDOUT: !71 = !DILocalVariable(arg: 2, scope: !68, type: !7)
+// CHECK:STDOUT: !72 = !DILocation(line: 35, column: 51, scope: !68)
+// CHECK:STDOUT: !73 = !DILocation(line: 35, column: 44, scope: !68)
 // CHECK:STDOUT: ; ModuleID = 'compound_assign.carbon'
 // CHECK:STDOUT: source_filename = "compound_assign.carbon"
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CTestAdd.Main(ptr %a, double %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Add.call = load double, ptr %a, align 8, !dbg !7
-// CHECK:STDOUT:   %Add.call1 = fadd double %Add.call, %b, !dbg !7
-// CHECK:STDOUT:   store double %Add.call1, ptr %a, align 8, !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !8
+// CHECK:STDOUT:   %Add.call = load double, ptr %a, align 8, !dbg !11
+// CHECK:STDOUT:   %Add.call1 = fadd double %Add.call, %b, !dbg !11
+// CHECK:STDOUT:   store double %Add.call1, ptr %a, align 8, !dbg !11
+// CHECK:STDOUT:   ret void, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTestSub.Main(ptr %a, double %b) #0 !dbg !9 {
+// CHECK:STDOUT: define void @_CTestSub.Main(ptr %a, double %b) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Sub.call = load double, ptr %a, align 8, !dbg !10
-// CHECK:STDOUT:   %Sub.call1 = fsub double %Sub.call, %b, !dbg !10
-// CHECK:STDOUT:   store double %Sub.call1, ptr %a, align 8, !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %Sub.call = load double, ptr %a, align 8, !dbg !17
+// CHECK:STDOUT:   %Sub.call1 = fsub double %Sub.call, %b, !dbg !17
+// CHECK:STDOUT:   store double %Sub.call1, ptr %a, align 8, !dbg !17
+// CHECK:STDOUT:   ret void, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTestMul.Main(ptr %a, double %b) #0 !dbg !12 {
+// CHECK:STDOUT: define void @_CTestMul.Main(ptr %a, double %b) #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Mul.call = load double, ptr %a, align 8, !dbg !13
-// CHECK:STDOUT:   %Mul.call1 = fmul double %Mul.call, %b, !dbg !13
-// CHECK:STDOUT:   store double %Mul.call1, ptr %a, align 8, !dbg !13
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   %Mul.call = load double, ptr %a, align 8, !dbg !23
+// CHECK:STDOUT:   %Mul.call1 = fmul double %Mul.call, %b, !dbg !23
+// CHECK:STDOUT:   store double %Mul.call1, ptr %a, align 8, !dbg !23
+// CHECK:STDOUT:   ret void, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTestDiv.Main(ptr %a, double %b) #0 !dbg !15 {
+// CHECK:STDOUT: define void @_CTestDiv.Main(ptr %a, double %b) #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Div.call = load double, ptr %a, align 8, !dbg !16
-// CHECK:STDOUT:   %Div.call1 = fdiv double %Div.call, %b, !dbg !16
-// CHECK:STDOUT:   store double %Div.call1, ptr %a, align 8, !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %Div.call = load double, ptr %a, align 8, !dbg !29
+// CHECK:STDOUT:   %Div.call1 = fdiv double %Div.call, %b, !dbg !29
+// CHECK:STDOUT:   store double %Div.call1, ptr %a, align 8, !dbg !29
+// CHECK:STDOUT:   ret void, !dbg !30
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -251,49 +286,62 @@ fn TestF128(a: f128, b: f128) -> f128 { return F128(a, b); }
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "compound_assign.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestAdd", linkageName: "_CTestAdd.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestAdd", linkageName: "_CTestAdd.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 5, column: 34, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 5, column: 1, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "TestSub", linkageName: "_CTestSub.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 8, column: 34, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 8, column: 1, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "TestMul", linkageName: "_CTestMul.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 11, column: 34, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 11, column: 1, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "TestDiv", linkageName: "_CTestDiv.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 14, column: 34, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 14, column: 1, scope: !15)
+// CHECK:STDOUT: !6 = !{null, !7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 5, column: 34, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 5, column: 1, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "TestSub", linkageName: "_CTestSub.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !14 = !{!15, !16}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !13, type: !7)
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 2, scope: !13, type: !7)
+// CHECK:STDOUT: !17 = !DILocation(line: 8, column: 34, scope: !13)
+// CHECK:STDOUT: !18 = !DILocation(line: 8, column: 1, scope: !13)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "TestMul", linkageName: "_CTestMul.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !20 = !{!21, !22}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !19, type: !7)
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 2, scope: !19, type: !7)
+// CHECK:STDOUT: !23 = !DILocation(line: 11, column: 34, scope: !19)
+// CHECK:STDOUT: !24 = !DILocation(line: 11, column: 1, scope: !19)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "TestDiv", linkageName: "_CTestDiv.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !26)
+// CHECK:STDOUT: !26 = !{!27, !28}
+// CHECK:STDOUT: !27 = !DILocalVariable(arg: 1, scope: !25, type: !7)
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 2, scope: !25, type: !7)
+// CHECK:STDOUT: !29 = !DILocation(line: 14, column: 34, scope: !25)
+// CHECK:STDOUT: !30 = !DILocation(line: 14, column: 1, scope: !25)
 // CHECK:STDOUT: ; ModuleID = 'types.carbon'
 // CHECK:STDOUT: source_filename = "types.carbon"
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define half @_CTestF16.Main(half %a, half %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %F16.call = fadd half %a, %b, !dbg !7
-// CHECK:STDOUT:   ret half %F16.call, !dbg !8
+// CHECK:STDOUT:   %F16.call = fadd half %a, %b, !dbg !11
+// CHECK:STDOUT:   ret half %F16.call, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define float @_CTestF32.Main(float %a, float %b) #0 !dbg !9 {
+// CHECK:STDOUT: define float @_CTestF32.Main(float %a, float %b) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %F32.call = fadd float %a, %b, !dbg !10
-// CHECK:STDOUT:   ret float %F32.call, !dbg !11
+// CHECK:STDOUT:   %F32.call = fadd float %a, %b, !dbg !17
+// CHECK:STDOUT:   ret float %F32.call, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define double @_CTestF64.Main(double %a, double %b) #0 !dbg !12 {
+// CHECK:STDOUT: define double @_CTestF64.Main(double %a, double %b) #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %F64.call = fadd double %a, %b, !dbg !13
-// CHECK:STDOUT:   ret double %F64.call, !dbg !14
+// CHECK:STDOUT:   %F64.call = fadd double %a, %b, !dbg !23
+// CHECK:STDOUT:   ret double %F64.call, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define fp128 @_CTestF128.Main(fp128 %a, fp128 %b) #0 !dbg !15 {
+// CHECK:STDOUT: define fp128 @_CTestF128.Main(fp128 %a, fp128 %b) #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %F128.call = fadd fp128 %a, %b, !dbg !16
-// CHECK:STDOUT:   ret fp128 %F128.call, !dbg !17
+// CHECK:STDOUT:   %F128.call = fadd fp128 %a, %b, !dbg !29
+// CHECK:STDOUT:   ret fp128 %F128.call, !dbg !30
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -305,17 +353,30 @@ fn TestF128(a: f128, b: f128) -> f128 { return F128(a, b); }
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "types.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestF16", linkageName: "_CTestF16.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestF16", linkageName: "_CTestF16.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 5, column: 44, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 5, column: 37, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "TestF32", linkageName: "_CTestF32.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 8, column: 44, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 8, column: 37, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "TestF64", linkageName: "_CTestF64.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 11, column: 44, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 11, column: 37, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "TestF128", linkageName: "_CTestF128.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 14, column: 48, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 14, column: 41, scope: !15)
+// CHECK:STDOUT: !6 = !{!7, !7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 5, column: 44, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 5, column: 37, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "TestF32", linkageName: "_CTestF32.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !14 = !{!15, !16}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !13, type: !7)
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 2, scope: !13, type: !7)
+// CHECK:STDOUT: !17 = !DILocation(line: 8, column: 44, scope: !13)
+// CHECK:STDOUT: !18 = !DILocation(line: 8, column: 37, scope: !13)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "TestF64", linkageName: "_CTestF64.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !20 = !{!21, !22}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !19, type: !7)
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 2, scope: !19, type: !7)
+// CHECK:STDOUT: !23 = !DILocation(line: 11, column: 44, scope: !19)
+// CHECK:STDOUT: !24 = !DILocation(line: 11, column: 37, scope: !19)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "TestF128", linkageName: "_CTestF128.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !26)
+// CHECK:STDOUT: !26 = !{!27, !28}
+// CHECK:STDOUT: !27 = !DILocalVariable(arg: 1, scope: !25, type: !7)
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 2, scope: !25, type: !7)
+// CHECK:STDOUT: !29 = !DILocation(line: 14, column: 48, scope: !25)
+// CHECK:STDOUT: !30 = !DILocation(line: 14, column: 41, scope: !25)

Разлика између датотеке није приказан због своје велике величине
+ 515 - 355
toolchain/lower/testdata/builtins/int.carbon


+ 22 - 16
toolchain/lower/testdata/builtins/int_literal.carbon

@@ -34,25 +34,25 @@ fn IntMin() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define {} @_CCopy.Main({} %x) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret {} %x, !dbg !7
+// CHECK:STDOUT:   ret {} %x, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CMinusOne.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define i32 @_CMinusOne.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 -1, !dbg !9
+// CHECK:STDOUT:   ret i32 -1, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CIntMax.Main() #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CIntMax.Main() #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 2147483647, !dbg !11
+// CHECK:STDOUT:   ret i32 2147483647, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CIntMin.Main() #0 !dbg !12 {
+// CHECK:STDOUT: define i32 @_CIntMin.Main() #0 !dbg !18 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 -2147483648, !dbg !13
+// CHECK:STDOUT:   ret i32 -2147483648, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -64,13 +64,19 @@ fn IntMin() -> i32 {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "int_literal.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Copy", linkageName: "_CCopy.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Copy", linkageName: "_CCopy.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 16, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "MinusOne", linkageName: "_CMinusOne.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 20, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "IntMax", linkageName: "_CIntMax.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 24, column: 3, scope: !10)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "IntMin", linkageName: "_CIntMin.Main", scope: null, file: !3, line: 27, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 28, column: 3, scope: !12)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 16, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "MinusOne", linkageName: "_CMinusOne.Main", scope: null, file: !3, line: 19, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{!14}
+// CHECK:STDOUT: !14 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !15 = !DILocation(line: 20, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "IntMax", linkageName: "_CIntMax.Main", scope: null, file: !3, line: 23, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !17 = !DILocation(line: 24, column: 3, scope: !16)
+// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "IntMin", linkageName: "_CIntMin.Main", scope: null, file: !3, line: 27, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !19 = !DILocation(line: 28, column: 3, scope: !18)

+ 78 - 62
toolchain/lower/testdata/builtins/maybe_unformed.carbon

@@ -61,80 +61,80 @@ fn PassAdapterBool() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CTakeI32.Main(i32 %x) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare i32 @_CMakeI32.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTakeBool.Main(ptr %x) #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CTakeBool.Main(ptr %x) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CMakeBool.Main(ptr sret(i1))
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CPassI32.Main() #0 !dbg !10 {
+// CHECK:STDOUT: define void @_CPassI32.Main() #0 !dbg !18 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %MakeI32.call = call i32 @_CMakeI32.Main(), !dbg !11
-// CHECK:STDOUT:   call void @_CTakeI32.Main(i32 %MakeI32.call), !dbg !12
-// CHECK:STDOUT:   ret void, !dbg !13
+// CHECK:STDOUT:   %MakeI32.call = call i32 @_CMakeI32.Main(), !dbg !21
+// CHECK:STDOUT:   call void @_CTakeI32.Main(i32 %MakeI32.call), !dbg !22
+// CHECK:STDOUT:   ret void, !dbg !23
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CPassBool.Main() #0 !dbg !14 {
+// CHECK:STDOUT: define void @_CPassBool.Main() #0 !dbg !24 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc28_21.1.temp = alloca i1, align 1, !dbg !15
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc28_21.1.temp), !dbg !15
-// CHECK:STDOUT:   call void @_CMakeBool.Main(ptr %.loc28_21.1.temp), !dbg !15
-// CHECK:STDOUT:   call void @_CTakeBool.Main(ptr %.loc28_21.1.temp), !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %.loc28_21.1.temp = alloca i1, align 1, !dbg !25
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc28_21.1.temp), !dbg !25
+// CHECK:STDOUT:   call void @_CMakeBool.Main(ptr %.loc28_21.1.temp), !dbg !25
+// CHECK:STDOUT:   call void @_CTakeBool.Main(ptr %.loc28_21.1.temp), !dbg !26
+// CHECK:STDOUT:   ret void, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CConvertBoolToUnformedBool.Main(ptr %b) #0 !dbg !18 {
+// CHECK:STDOUT: define void @_CConvertBoolToUnformedBool.Main(ptr %b) #0 !dbg !28 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CTakeBool.Main(ptr %b), !dbg !19
-// CHECK:STDOUT:   ret void, !dbg !20
+// CHECK:STDOUT:   call void @_CTakeBool.Main(ptr %b), !dbg !31
+// CHECK:STDOUT:   ret void, !dbg !32
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTakeAdapterI32.Main(i32 %x) #0 !dbg !21 {
+// CHECK:STDOUT: define void @_CTakeAdapterI32.Main(i32 %x) #0 !dbg !33 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !22
+// CHECK:STDOUT:   ret void, !dbg !36
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare i32 @_CMakeAdapterI32.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CPassAdapterI32.Main() #0 !dbg !23 {
+// CHECK:STDOUT: define void @_CPassAdapterI32.Main() #0 !dbg !37 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc48_33.1.temp = alloca i32, align 4, !dbg !24
-// CHECK:STDOUT:   %MakeAdapterI32.call = call i32 @_CMakeAdapterI32.Main(), !dbg !24
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc48_33.1.temp), !dbg !24
-// CHECK:STDOUT:   store i32 %MakeAdapterI32.call, ptr %.loc48_33.1.temp, align 4, !dbg !24
-// CHECK:STDOUT:   %.loc48_33.3 = load i32, ptr %.loc48_33.1.temp, align 4, !dbg !24
-// CHECK:STDOUT:   call void @_CTakeAdapterI32.Main(i32 %.loc48_33.3), !dbg !25
-// CHECK:STDOUT:   ret void, !dbg !26
+// CHECK:STDOUT:   %.loc48_33.1.temp = alloca i32, align 4, !dbg !38
+// CHECK:STDOUT:   %MakeAdapterI32.call = call i32 @_CMakeAdapterI32.Main(), !dbg !38
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc48_33.1.temp), !dbg !38
+// CHECK:STDOUT:   store i32 %MakeAdapterI32.call, ptr %.loc48_33.1.temp, align 4, !dbg !38
+// CHECK:STDOUT:   %.loc48_33.3 = load i32, ptr %.loc48_33.1.temp, align 4, !dbg !38
+// CHECK:STDOUT:   call void @_CTakeAdapterI32.Main(i32 %.loc48_33.3), !dbg !39
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTakeAdapterBool.Main(ptr %x) #0 !dbg !27 {
+// CHECK:STDOUT: define void @_CTakeAdapterBool.Main(ptr %x) #0 !dbg !41 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !28
+// CHECK:STDOUT:   ret void, !dbg !44
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CMakeAdapterBool.Main(ptr sret(i1))
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CPassAdapterBool.Main() #0 !dbg !29 {
+// CHECK:STDOUT: define void @_CPassAdapterBool.Main() #0 !dbg !45 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc55_35.1.temp = alloca i1, align 1, !dbg !30
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc55_35.1.temp), !dbg !30
-// CHECK:STDOUT:   call void @_CMakeAdapterBool.Main(ptr %.loc55_35.1.temp), !dbg !30
-// CHECK:STDOUT:   call void @_CTakeAdapterBool.Main(ptr %.loc55_35.1.temp), !dbg !31
-// CHECK:STDOUT:   ret void, !dbg !32
+// CHECK:STDOUT:   %.loc55_35.1.temp = alloca i1, align 1, !dbg !46
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc55_35.1.temp), !dbg !46
+// CHECK:STDOUT:   call void @_CMakeAdapterBool.Main(ptr %.loc55_35.1.temp), !dbg !46
+// CHECK:STDOUT:   call void @_CTakeAdapterBool.Main(ptr %.loc55_35.1.temp), !dbg !47
+// CHECK:STDOUT:   ret void, !dbg !48
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -153,32 +153,48 @@ fn PassAdapterBool() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "maybe_unformed.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TakeI32", linkageName: "_CTakeI32.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TakeI32", linkageName: "_CTakeI32.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 15, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "TakeBool", linkageName: "_CTakeBool.Main", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 18, column: 1, scope: !8)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "PassI32", linkageName: "_CPassI32.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 23, column: 11, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 23, column: 3, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 21, column: 1, scope: !10)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "PassBool", linkageName: "_CPassBool.Main", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !15 = !DILocation(line: 28, column: 12, scope: !14)
-// CHECK:STDOUT: !16 = !DILocation(line: 28, column: 3, scope: !14)
-// CHECK:STDOUT: !17 = !DILocation(line: 26, column: 1, scope: !14)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "ConvertBoolToUnformedBool", linkageName: "_CConvertBoolToUnformedBool.Main", scope: null, file: !3, line: 31, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 32, column: 3, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 31, column: 1, scope: !18)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "TakeAdapterI32", linkageName: "_CTakeAdapterI32.Main", scope: null, file: !3, line: 42, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 42, column: 1, scope: !21)
-// CHECK:STDOUT: !23 = distinct !DISubprogram(name: "PassAdapterI32", linkageName: "_CPassAdapterI32.Main", scope: null, file: !3, line: 45, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !24 = !DILocation(line: 48, column: 18, scope: !23)
-// CHECK:STDOUT: !25 = !DILocation(line: 48, column: 3, scope: !23)
-// CHECK:STDOUT: !26 = !DILocation(line: 45, column: 1, scope: !23)
-// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "TakeAdapterBool", linkageName: "_CTakeAdapterBool.Main", scope: null, file: !3, line: 51, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !28 = !DILocation(line: 51, column: 1, scope: !27)
-// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "PassAdapterBool", linkageName: "_CPassAdapterBool.Main", scope: null, file: !3, line: 54, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !30 = !DILocation(line: 55, column: 19, scope: !29)
-// CHECK:STDOUT: !31 = !DILocation(line: 55, column: 3, scope: !29)
-// CHECK:STDOUT: !32 = !DILocation(line: 54, column: 1, scope: !29)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "TakeBool", linkageName: "_CTakeBool.Main", scope: null, file: !3, line: 18, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null, !14}
+// CHECK:STDOUT: !14 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !15 = !{!16}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !11, type: !14)
+// CHECK:STDOUT: !17 = !DILocation(line: 18, column: 1, scope: !11)
+// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "PassI32", linkageName: "_CPassI32.Main", scope: null, file: !3, line: 21, type: !19, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !19 = !DISubroutineType(types: !20)
+// CHECK:STDOUT: !20 = !{null}
+// CHECK:STDOUT: !21 = !DILocation(line: 23, column: 11, scope: !18)
+// CHECK:STDOUT: !22 = !DILocation(line: 23, column: 3, scope: !18)
+// CHECK:STDOUT: !23 = !DILocation(line: 21, column: 1, scope: !18)
+// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "PassBool", linkageName: "_CPassBool.Main", scope: null, file: !3, line: 26, type: !19, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !25 = !DILocation(line: 28, column: 12, scope: !24)
+// CHECK:STDOUT: !26 = !DILocation(line: 28, column: 3, scope: !24)
+// CHECK:STDOUT: !27 = !DILocation(line: 26, column: 1, scope: !24)
+// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "ConvertBoolToUnformedBool", linkageName: "_CConvertBoolToUnformedBool.Main", scope: null, file: !3, line: 31, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !29)
+// CHECK:STDOUT: !29 = !{!30}
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 1, scope: !28, type: !14)
+// CHECK:STDOUT: !31 = !DILocation(line: 32, column: 3, scope: !28)
+// CHECK:STDOUT: !32 = !DILocation(line: 31, column: 1, scope: !28)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "TakeAdapterI32", linkageName: "_CTakeAdapterI32.Main", scope: null, file: !3, line: 42, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !34)
+// CHECK:STDOUT: !34 = !{!35}
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 1, scope: !33, type: !7)
+// CHECK:STDOUT: !36 = !DILocation(line: 42, column: 1, scope: !33)
+// CHECK:STDOUT: !37 = distinct !DISubprogram(name: "PassAdapterI32", linkageName: "_CPassAdapterI32.Main", scope: null, file: !3, line: 45, type: !19, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !38 = !DILocation(line: 48, column: 18, scope: !37)
+// CHECK:STDOUT: !39 = !DILocation(line: 48, column: 3, scope: !37)
+// CHECK:STDOUT: !40 = !DILocation(line: 45, column: 1, scope: !37)
+// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "TakeAdapterBool", linkageName: "_CTakeAdapterBool.Main", scope: null, file: !3, line: 51, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !42)
+// CHECK:STDOUT: !42 = !{!43}
+// CHECK:STDOUT: !43 = !DILocalVariable(arg: 1, scope: !41, type: !14)
+// CHECK:STDOUT: !44 = !DILocation(line: 51, column: 1, scope: !41)
+// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "PassAdapterBool", linkageName: "_CPassAdapterBool.Main", scope: null, file: !3, line: 54, type: !19, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !46 = !DILocation(line: 55, column: 19, scope: !45)
+// CHECK:STDOUT: !47 = !DILocation(line: 55, column: 3, scope: !45)
+// CHECK:STDOUT: !48 = !DILocation(line: 54, column: 1, scope: !45)

+ 19 - 12
toolchain/lower/testdata/builtins/method_vs_nonmethod.carbon

@@ -22,15 +22,15 @@ fn TestAddMethod(a: i32, b: i32) -> i32 { return a.(AddMethod)(b); }
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CTestAddNonmethod.Main(i32 %a, i32 %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %AddNonmethod.call = add i32 %a, %b, !dbg !7
-// CHECK:STDOUT:   ret i32 %AddNonmethod.call, !dbg !8
+// CHECK:STDOUT:   %AddNonmethod.call = add i32 %a, %b, !dbg !11
+// CHECK:STDOUT:   ret i32 %AddNonmethod.call, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CTestAddMethod.Main(i32 %a, i32 %b) #0 !dbg !9 {
+// CHECK:STDOUT: define i32 @_CTestAddMethod.Main(i32 %a, i32 %b) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %AddMethod.call = add i32 %a, %b, !dbg !10
-// CHECK:STDOUT:   ret i32 %AddMethod.call, !dbg !11
+// CHECK:STDOUT:   %AddMethod.call = add i32 %a, %b, !dbg !17
+// CHECK:STDOUT:   ret i32 %AddMethod.call, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -42,11 +42,18 @@ fn TestAddMethod(a: i32, b: i32) -> i32 { return a.(AddMethod)(b); }
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "method_vs_nonmethod.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestAddNonmethod", linkageName: "_CTestAddNonmethod.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestAddNonmethod", linkageName: "_CTestAddNonmethod.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 16, column: 53, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 46, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "TestAddMethod", linkageName: "_CTestAddMethod.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 50, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 43, scope: !9)
+// CHECK:STDOUT: !6 = !{!7, !7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 16, column: 53, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 16, column: 46, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "TestAddMethod", linkageName: "_CTestAddMethod.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !14 = !{!15, !16}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !13, type: !7)
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 2, scope: !13, type: !7)
+// CHECK:STDOUT: !17 = !DILocation(line: 17, column: 50, scope: !13)
+// CHECK:STDOUT: !18 = !DILocation(line: 17, column: 43, scope: !13)

+ 22 - 19
toolchain/lower/testdata/builtins/no_op.carbon

@@ -45,26 +45,26 @@ fn J() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CG.Main() #0 !dbg !8 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %a.var = alloca {}, align 8, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   %a.var = alloca {}, align 8, !dbg !12
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !12
+// CHECK:STDOUT:   ret void, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CH.Main() #0 !dbg !11 {
+// CHECK:STDOUT: define void @_CH.Main() #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !12
+// CHECK:STDOUT:   ret void, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CI.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CJ.Main() #0 !dbg !13 {
+// CHECK:STDOUT: define void @_CJ.Main() #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc33_11.1.temp = alloca {}, align 8, !dbg !14
-// CHECK:STDOUT:   call void @_CI.Main(), !dbg !14
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc33_11.1.temp), !dbg !14
-// CHECK:STDOUT:   ret void, !dbg !15
+// CHECK:STDOUT:   %.loc33_11.1.temp = alloca {}, align 8, !dbg !17
+// CHECK:STDOUT:   call void @_CI.Main(), !dbg !17
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc33_11.1.temp), !dbg !17
+// CHECK:STDOUT:   ret void, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -85,13 +85,16 @@ fn J() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "no_op.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 17, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 22, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 23, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !12 = !DILocation(line: 27, column: 3, scope: !11)
-// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "J", linkageName: "_CJ.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !14 = !DILocation(line: 33, column: 9, scope: !13)
-// CHECK:STDOUT: !15 = !DILocation(line: 32, column: 1, scope: !13)
+// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 21, type: !9, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !9 = !DISubroutineType(types: !10)
+// CHECK:STDOUT: !10 = !{!11}
+// CHECK:STDOUT: !11 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !12 = !DILocation(line: 22, column: 3, scope: !8)
+// CHECK:STDOUT: !13 = !DILocation(line: 23, column: 3, scope: !8)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main", scope: null, file: !3, line: 26, type: !9, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !15 = !DILocation(line: 27, column: 3, scope: !14)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "J", linkageName: "_CJ.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !17 = !DILocation(line: 33, column: 9, scope: !16)
+// CHECK:STDOUT: !18 = !DILocation(line: 32, column: 1, scope: !16)

+ 12 - 7
toolchain/lower/testdata/builtins/overloaded_operator.carbon

@@ -20,9 +20,9 @@ fn AddThreeIntegers(a: i32, b: i32, c: i32) -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CAddThreeIntegers.Main(i32 %a, i32 %b, i32 %c) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.loc14_12 = add i32 %a, %b, !dbg !7
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.loc14_16 = add i32 %Int.as.AddWith.impl.Op.call.loc14_12, %c, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.loc14_16, !dbg !8
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.loc14_12 = add i32 %a, %b, !dbg !12
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call.loc14_16 = add i32 %Int.as.AddWith.impl.Op.call.loc14_12, %c, !dbg !12
+// CHECK:STDOUT:   ret i32 %Int.as.AddWith.impl.Op.call.loc14_16, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -34,8 +34,13 @@ fn AddThreeIntegers(a: i32, b: i32, c: i32) -> i32 {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "overloaded_operator.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "AddThreeIntegers", linkageName: "_CAddThreeIntegers.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "AddThreeIntegers", linkageName: "_CAddThreeIntegers.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !6 = !{!7, !7, !7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9, !10, !11}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocalVariable(arg: 3, scope: !4, type: !7)
+// CHECK:STDOUT: !12 = !DILocation(line: 14, column: 10, scope: !4)
+// CHECK:STDOUT: !13 = !DILocation(line: 14, column: 3, scope: !4)

+ 14 - 9
toolchain/lower/testdata/builtins/pointer.carbon

@@ -30,14 +30,14 @@ fn Check(p: MakeUnformed(C*)) -> bool {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define ptr @_CNull.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret ptr null, !dbg !7
+// CHECK:STDOUT:   ret ptr null, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CCheck.Main(ptr %p) #0 !dbg !8 {
+// CHECK:STDOUT: define i1 @_CCheck.Main(ptr %p) #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %IsNull.call = icmp eq ptr %p, null, !dbg !9
-// CHECK:STDOUT:   ret i1 %IsNull.call, !dbg !10
+// CHECK:STDOUT:   %IsNull.call = icmp eq ptr %p, null, !dbg !14
+// CHECK:STDOUT:   ret i1 %IsNull.call, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -51,8 +51,13 @@ fn Check(p: MakeUnformed(C*)) -> bool {
 // CHECK:STDOUT: !3 = !DIFile(filename: "pointer.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Null", linkageName: "_CNull.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 20, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Check", linkageName: "_CCheck.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 24, column: 10, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 24, column: 3, scope: !8)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 20, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Check", linkageName: "_CCheck.Main", scope: null, file: !3, line: 23, type: !10, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !12)
+// CHECK:STDOUT: !10 = !DISubroutineType(types: !11)
+// CHECK:STDOUT: !11 = !{!7, !7}
+// CHECK:STDOUT: !12 = !{!13}
+// CHECK:STDOUT: !13 = !DILocalVariable(arg: 1, scope: !9, type: !7)
+// CHECK:STDOUT: !14 = !DILocation(line: 24, column: 10, scope: !9)
+// CHECK:STDOUT: !15 = !DILocation(line: 24, column: 3, scope: !9)

+ 1 - 1
toolchain/lower/testdata/builtins/print_read.carbon

@@ -79,7 +79,7 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "print_read.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 19, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 22, column: 9, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 22, column: 10, scope: !4)

+ 2 - 2
toolchain/lower/testdata/builtins/type.carbon

@@ -58,7 +58,7 @@ fn F() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "can_destroy.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 5, column: 1, scope: !4)
 // CHECK:STDOUT: ; ModuleID = 'destroy.carbon'
 // CHECK:STDOUT: source_filename = "destroy.carbon"
@@ -83,5 +83,5 @@ fn F() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "destroy.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 1, scope: !4)

+ 1 - 1
toolchain/lower/testdata/builtins/types.carbon

@@ -60,7 +60,7 @@ fn Uses() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "types.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Uses", linkageName: "_CUses.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 29, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 30, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 31, column: 3, scope: !4)

+ 166 - 108
toolchain/lower/testdata/builtins/uint.carbon

@@ -70,127 +70,127 @@ fn TestGreaterEq(a: u64, b: u64) -> bool { return GreaterEq(a, b); }
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i64 @_CTestNegate.Main(i64 %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Negate.call = sub i64 0, %a, !dbg !7
-// CHECK:STDOUT:   ret i64 %Negate.call, !dbg !8
+// CHECK:STDOUT:   %Negate.call = sub i64 0, %a, !dbg !10
+// CHECK:STDOUT:   ret i64 %Negate.call, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestAdd.Main(i64 %a, i64 %b) #0 !dbg !9 {
+// CHECK:STDOUT: define i64 @_CTestAdd.Main(i64 %a, i64 %b) #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Add.call = add i64 %a, %b, !dbg !10
-// CHECK:STDOUT:   ret i64 %Add.call, !dbg !11
+// CHECK:STDOUT:   %Add.call = add i64 %a, %b, !dbg !18
+// CHECK:STDOUT:   ret i64 %Add.call, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestSub.Main(i64 %a, i64 %b) #0 !dbg !12 {
+// CHECK:STDOUT: define i64 @_CTestSub.Main(i64 %a, i64 %b) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Sub.call = sub i64 %a, %b, !dbg !13
-// CHECK:STDOUT:   ret i64 %Sub.call, !dbg !14
+// CHECK:STDOUT:   %Sub.call = sub i64 %a, %b, !dbg !24
+// CHECK:STDOUT:   ret i64 %Sub.call, !dbg !25
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestMul.Main(i64 %a, i64 %b) #0 !dbg !15 {
+// CHECK:STDOUT: define i64 @_CTestMul.Main(i64 %a, i64 %b) #0 !dbg !26 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Mul.call = mul i64 %a, %b, !dbg !16
-// CHECK:STDOUT:   ret i64 %Mul.call, !dbg !17
+// CHECK:STDOUT:   %Mul.call = mul i64 %a, %b, !dbg !30
+// CHECK:STDOUT:   ret i64 %Mul.call, !dbg !31
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestDiv.Main(i64 %a, i64 %b) #0 !dbg !18 {
+// CHECK:STDOUT: define i64 @_CTestDiv.Main(i64 %a, i64 %b) #0 !dbg !32 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Div.call = udiv i64 %a, %b, !dbg !19
-// CHECK:STDOUT:   ret i64 %Div.call, !dbg !20
+// CHECK:STDOUT:   %Div.call = udiv i64 %a, %b, !dbg !36
+// CHECK:STDOUT:   ret i64 %Div.call, !dbg !37
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestMod.Main(i64 %a, i64 %b) #0 !dbg !21 {
+// CHECK:STDOUT: define i64 @_CTestMod.Main(i64 %a, i64 %b) #0 !dbg !38 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Mod.call = urem i64 %a, %b, !dbg !22
-// CHECK:STDOUT:   ret i64 %Mod.call, !dbg !23
+// CHECK:STDOUT:   %Mod.call = urem i64 %a, %b, !dbg !42
+// CHECK:STDOUT:   ret i64 %Mod.call, !dbg !43
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestComplement.Main(i64 %a) #0 !dbg !24 {
+// CHECK:STDOUT: define i64 @_CTestComplement.Main(i64 %a) #0 !dbg !44 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Complement.call = xor i64 -1, %a, !dbg !25
-// CHECK:STDOUT:   ret i64 %Complement.call, !dbg !26
+// CHECK:STDOUT:   %Complement.call = xor i64 -1, %a, !dbg !47
+// CHECK:STDOUT:   ret i64 %Complement.call, !dbg !48
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestAnd.Main(i64 %a, i64 %b) #0 !dbg !27 {
+// CHECK:STDOUT: define i64 @_CTestAnd.Main(i64 %a, i64 %b) #0 !dbg !49 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %And.call = and i64 %a, %b, !dbg !28
-// CHECK:STDOUT:   ret i64 %And.call, !dbg !29
+// CHECK:STDOUT:   %And.call = and i64 %a, %b, !dbg !53
+// CHECK:STDOUT:   ret i64 %And.call, !dbg !54
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestOr.Main(i64 %a, i64 %b) #0 !dbg !30 {
+// CHECK:STDOUT: define i64 @_CTestOr.Main(i64 %a, i64 %b) #0 !dbg !55 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Or.call = or i64 %a, %b, !dbg !31
-// CHECK:STDOUT:   ret i64 %Or.call, !dbg !32
+// CHECK:STDOUT:   %Or.call = or i64 %a, %b, !dbg !59
+// CHECK:STDOUT:   ret i64 %Or.call, !dbg !60
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestXor.Main(i64 %a, i64 %b) #0 !dbg !33 {
+// CHECK:STDOUT: define i64 @_CTestXor.Main(i64 %a, i64 %b) #0 !dbg !61 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Xor.call = xor i64 %a, %b, !dbg !34
-// CHECK:STDOUT:   ret i64 %Xor.call, !dbg !35
+// CHECK:STDOUT:   %Xor.call = xor i64 %a, %b, !dbg !65
+// CHECK:STDOUT:   ret i64 %Xor.call, !dbg !66
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestLeftShift.Main(i64 %a, i64 %b) #0 !dbg !36 {
+// CHECK:STDOUT: define i64 @_CTestLeftShift.Main(i64 %a, i64 %b) #0 !dbg !67 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %LeftShift.call = shl i64 %a, %b, !dbg !37
-// CHECK:STDOUT:   ret i64 %LeftShift.call, !dbg !38
+// CHECK:STDOUT:   %LeftShift.call = shl i64 %a, %b, !dbg !71
+// CHECK:STDOUT:   ret i64 %LeftShift.call, !dbg !72
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i64 @_CTestRightShift.Main(i64 %a, i64 %b) #0 !dbg !39 {
+// CHECK:STDOUT: define i64 @_CTestRightShift.Main(i64 %a, i64 %b) #0 !dbg !73 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %RightShift.call = lshr i64 %a, %b, !dbg !40
-// CHECK:STDOUT:   ret i64 %RightShift.call, !dbg !41
+// CHECK:STDOUT:   %RightShift.call = lshr i64 %a, %b, !dbg !77
+// CHECK:STDOUT:   ret i64 %RightShift.call, !dbg !78
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestEq.Main(i64 %a, i64 %b) #0 !dbg !42 {
+// CHECK:STDOUT: define i1 @_CTestEq.Main(i64 %a, i64 %b) #0 !dbg !79 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Eq.call = icmp eq i64 %a, %b, !dbg !43
-// CHECK:STDOUT:   ret i1 %Eq.call, !dbg !44
+// CHECK:STDOUT:   %Eq.call = icmp eq i64 %a, %b, !dbg !86
+// CHECK:STDOUT:   ret i1 %Eq.call, !dbg !87
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestNeq.Main(i64 %a, i64 %b) #0 !dbg !45 {
+// CHECK:STDOUT: define i1 @_CTestNeq.Main(i64 %a, i64 %b) #0 !dbg !88 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Neq.call = icmp ne i64 %a, %b, !dbg !46
-// CHECK:STDOUT:   ret i1 %Neq.call, !dbg !47
+// CHECK:STDOUT:   %Neq.call = icmp ne i64 %a, %b, !dbg !92
+// CHECK:STDOUT:   ret i1 %Neq.call, !dbg !93
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestLess.Main(i64 %a, i64 %b) #0 !dbg !48 {
+// CHECK:STDOUT: define i1 @_CTestLess.Main(i64 %a, i64 %b) #0 !dbg !94 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Less.call = icmp ult i64 %a, %b, !dbg !49
-// CHECK:STDOUT:   ret i1 %Less.call, !dbg !50
+// CHECK:STDOUT:   %Less.call = icmp ult i64 %a, %b, !dbg !98
+// CHECK:STDOUT:   ret i1 %Less.call, !dbg !99
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestLessEq.Main(i64 %a, i64 %b) #0 !dbg !51 {
+// CHECK:STDOUT: define i1 @_CTestLessEq.Main(i64 %a, i64 %b) #0 !dbg !100 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %LessEq.call = icmp ule i64 %a, %b, !dbg !52
-// CHECK:STDOUT:   ret i1 %LessEq.call, !dbg !53
+// CHECK:STDOUT:   %LessEq.call = icmp ule i64 %a, %b, !dbg !104
+// CHECK:STDOUT:   ret i1 %LessEq.call, !dbg !105
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestGreater.Main(i64 %a, i64 %b) #0 !dbg !54 {
+// CHECK:STDOUT: define i1 @_CTestGreater.Main(i64 %a, i64 %b) #0 !dbg !106 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Greater.call = icmp ugt i64 %a, %b, !dbg !55
-// CHECK:STDOUT:   ret i1 %Greater.call, !dbg !56
+// CHECK:STDOUT:   %Greater.call = icmp ugt i64 %a, %b, !dbg !110
+// CHECK:STDOUT:   ret i1 %Greater.call, !dbg !111
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i1 @_CTestGreaterEq.Main(i64 %a, i64 %b) #0 !dbg !57 {
+// CHECK:STDOUT: define i1 @_CTestGreaterEq.Main(i64 %a, i64 %b) #0 !dbg !112 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %GreaterEq.call = icmp uge i64 %a, %b, !dbg !58
-// CHECK:STDOUT:   ret i1 %GreaterEq.call, !dbg !59
+// CHECK:STDOUT:   %GreaterEq.call = icmp uge i64 %a, %b, !dbg !116
+// CHECK:STDOUT:   ret i1 %GreaterEq.call, !dbg !117
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -202,59 +202,117 @@ fn TestGreaterEq(a: u64, b: u64) -> bool { return GreaterEq(a, b); }
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "uint.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestNegate", linkageName: "_CTestNegate.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "TestNegate", linkageName: "_CTestNegate.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 39, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 32, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "TestAdd", linkageName: "_CTestAdd.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 44, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 37, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "TestSub", linkageName: "_CTestSub.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 20, column: 44, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 20, column: 37, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "TestMul", linkageName: "_CTestMul.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 23, column: 44, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 23, column: 37, scope: !15)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "TestDiv", linkageName: "_CTestDiv.Main", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 26, column: 44, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 26, column: 37, scope: !18)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "TestMod", linkageName: "_CTestMod.Main", scope: null, file: !3, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 29, column: 44, scope: !21)
-// CHECK:STDOUT: !23 = !DILocation(line: 29, column: 37, scope: !21)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "TestComplement", linkageName: "_CTestComplement.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 32, column: 43, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 32, column: 36, scope: !24)
-// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "TestAnd", linkageName: "_CTestAnd.Main", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !28 = !DILocation(line: 35, column: 44, scope: !27)
-// CHECK:STDOUT: !29 = !DILocation(line: 35, column: 37, scope: !27)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "TestOr", linkageName: "_CTestOr.Main", scope: null, file: !3, line: 38, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DILocation(line: 38, column: 43, scope: !30)
-// CHECK:STDOUT: !32 = !DILocation(line: 38, column: 36, scope: !30)
-// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "TestXor", linkageName: "_CTestXor.Main", scope: null, file: !3, line: 41, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !34 = !DILocation(line: 41, column: 44, scope: !33)
-// CHECK:STDOUT: !35 = !DILocation(line: 41, column: 37, scope: !33)
-// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "TestLeftShift", linkageName: "_CTestLeftShift.Main", scope: null, file: !3, line: 44, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !37 = !DILocation(line: 44, column: 50, scope: !36)
-// CHECK:STDOUT: !38 = !DILocation(line: 44, column: 43, scope: !36)
-// CHECK:STDOUT: !39 = distinct !DISubprogram(name: "TestRightShift", linkageName: "_CTestRightShift.Main", scope: null, file: !3, line: 47, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !40 = !DILocation(line: 47, column: 51, scope: !39)
-// CHECK:STDOUT: !41 = !DILocation(line: 47, column: 44, scope: !39)
-// CHECK:STDOUT: !42 = distinct !DISubprogram(name: "TestEq", linkageName: "_CTestEq.Main", scope: null, file: !3, line: 50, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !43 = !DILocation(line: 50, column: 44, scope: !42)
-// CHECK:STDOUT: !44 = !DILocation(line: 50, column: 37, scope: !42)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "TestNeq", linkageName: "_CTestNeq.Main", scope: null, file: !3, line: 53, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 53, column: 45, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 53, column: 38, scope: !45)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "TestLess", linkageName: "_CTestLess.Main", scope: null, file: !3, line: 56, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 56, column: 46, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 56, column: 39, scope: !48)
-// CHECK:STDOUT: !51 = distinct !DISubprogram(name: "TestLessEq", linkageName: "_CTestLessEq.Main", scope: null, file: !3, line: 59, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !52 = !DILocation(line: 59, column: 48, scope: !51)
-// CHECK:STDOUT: !53 = !DILocation(line: 59, column: 41, scope: !51)
-// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "TestGreater", linkageName: "_CTestGreater.Main", scope: null, file: !3, line: 62, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !55 = !DILocation(line: 62, column: 49, scope: !54)
-// CHECK:STDOUT: !56 = !DILocation(line: 62, column: 42, scope: !54)
-// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "TestGreaterEq", linkageName: "_CTestGreaterEq.Main", scope: null, file: !3, line: 65, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !58 = !DILocation(line: 65, column: 51, scope: !57)
-// CHECK:STDOUT: !59 = !DILocation(line: 65, column: 44, scope: !57)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 64, encoding: DW_ATE_unsigned)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 14, column: 39, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 14, column: 32, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "TestAdd", linkageName: "_CTestAdd.Main", scope: null, file: !3, line: 17, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{!7, !7, !7}
+// CHECK:STDOUT: !15 = !{!16, !17}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !12, type: !7)
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 2, scope: !12, type: !7)
+// CHECK:STDOUT: !18 = !DILocation(line: 17, column: 44, scope: !12)
+// CHECK:STDOUT: !19 = !DILocation(line: 17, column: 37, scope: !12)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "TestSub", linkageName: "_CTestSub.Main", scope: null, file: !3, line: 20, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !21)
+// CHECK:STDOUT: !21 = !{!22, !23}
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 1, scope: !20, type: !7)
+// CHECK:STDOUT: !23 = !DILocalVariable(arg: 2, scope: !20, type: !7)
+// CHECK:STDOUT: !24 = !DILocation(line: 20, column: 44, scope: !20)
+// CHECK:STDOUT: !25 = !DILocation(line: 20, column: 37, scope: !20)
+// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "TestMul", linkageName: "_CTestMul.Main", scope: null, file: !3, line: 23, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !27)
+// CHECK:STDOUT: !27 = !{!28, !29}
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 1, scope: !26, type: !7)
+// CHECK:STDOUT: !29 = !DILocalVariable(arg: 2, scope: !26, type: !7)
+// CHECK:STDOUT: !30 = !DILocation(line: 23, column: 44, scope: !26)
+// CHECK:STDOUT: !31 = !DILocation(line: 23, column: 37, scope: !26)
+// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "TestDiv", linkageName: "_CTestDiv.Main", scope: null, file: !3, line: 26, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !33)
+// CHECK:STDOUT: !33 = !{!34, !35}
+// CHECK:STDOUT: !34 = !DILocalVariable(arg: 1, scope: !32, type: !7)
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 2, scope: !32, type: !7)
+// CHECK:STDOUT: !36 = !DILocation(line: 26, column: 44, scope: !32)
+// CHECK:STDOUT: !37 = !DILocation(line: 26, column: 37, scope: !32)
+// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "TestMod", linkageName: "_CTestMod.Main", scope: null, file: !3, line: 29, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !39)
+// CHECK:STDOUT: !39 = !{!40, !41}
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 1, scope: !38, type: !7)
+// CHECK:STDOUT: !41 = !DILocalVariable(arg: 2, scope: !38, type: !7)
+// CHECK:STDOUT: !42 = !DILocation(line: 29, column: 44, scope: !38)
+// CHECK:STDOUT: !43 = !DILocation(line: 29, column: 37, scope: !38)
+// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "TestComplement", linkageName: "_CTestComplement.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !45)
+// CHECK:STDOUT: !45 = !{!46}
+// CHECK:STDOUT: !46 = !DILocalVariable(arg: 1, scope: !44, type: !7)
+// CHECK:STDOUT: !47 = !DILocation(line: 32, column: 43, scope: !44)
+// CHECK:STDOUT: !48 = !DILocation(line: 32, column: 36, scope: !44)
+// CHECK:STDOUT: !49 = distinct !DISubprogram(name: "TestAnd", linkageName: "_CTestAnd.Main", scope: null, file: !3, line: 35, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !50)
+// CHECK:STDOUT: !50 = !{!51, !52}
+// CHECK:STDOUT: !51 = !DILocalVariable(arg: 1, scope: !49, type: !7)
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 2, scope: !49, type: !7)
+// CHECK:STDOUT: !53 = !DILocation(line: 35, column: 44, scope: !49)
+// CHECK:STDOUT: !54 = !DILocation(line: 35, column: 37, scope: !49)
+// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "TestOr", linkageName: "_CTestOr.Main", scope: null, file: !3, line: 38, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !56)
+// CHECK:STDOUT: !56 = !{!57, !58}
+// CHECK:STDOUT: !57 = !DILocalVariable(arg: 1, scope: !55, type: !7)
+// CHECK:STDOUT: !58 = !DILocalVariable(arg: 2, scope: !55, type: !7)
+// CHECK:STDOUT: !59 = !DILocation(line: 38, column: 43, scope: !55)
+// CHECK:STDOUT: !60 = !DILocation(line: 38, column: 36, scope: !55)
+// CHECK:STDOUT: !61 = distinct !DISubprogram(name: "TestXor", linkageName: "_CTestXor.Main", scope: null, file: !3, line: 41, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !62)
+// CHECK:STDOUT: !62 = !{!63, !64}
+// CHECK:STDOUT: !63 = !DILocalVariable(arg: 1, scope: !61, type: !7)
+// CHECK:STDOUT: !64 = !DILocalVariable(arg: 2, scope: !61, type: !7)
+// CHECK:STDOUT: !65 = !DILocation(line: 41, column: 44, scope: !61)
+// CHECK:STDOUT: !66 = !DILocation(line: 41, column: 37, scope: !61)
+// CHECK:STDOUT: !67 = distinct !DISubprogram(name: "TestLeftShift", linkageName: "_CTestLeftShift.Main", scope: null, file: !3, line: 44, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !68)
+// CHECK:STDOUT: !68 = !{!69, !70}
+// CHECK:STDOUT: !69 = !DILocalVariable(arg: 1, scope: !67, type: !7)
+// CHECK:STDOUT: !70 = !DILocalVariable(arg: 2, scope: !67, type: !7)
+// CHECK:STDOUT: !71 = !DILocation(line: 44, column: 50, scope: !67)
+// CHECK:STDOUT: !72 = !DILocation(line: 44, column: 43, scope: !67)
+// CHECK:STDOUT: !73 = distinct !DISubprogram(name: "TestRightShift", linkageName: "_CTestRightShift.Main", scope: null, file: !3, line: 47, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !74)
+// CHECK:STDOUT: !74 = !{!75, !76}
+// CHECK:STDOUT: !75 = !DILocalVariable(arg: 1, scope: !73, type: !7)
+// CHECK:STDOUT: !76 = !DILocalVariable(arg: 2, scope: !73, type: !7)
+// CHECK:STDOUT: !77 = !DILocation(line: 47, column: 51, scope: !73)
+// CHECK:STDOUT: !78 = !DILocation(line: 47, column: 44, scope: !73)
+// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "TestEq", linkageName: "_CTestEq.Main", scope: null, file: !3, line: 50, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !83)
+// CHECK:STDOUT: !80 = !DISubroutineType(types: !81)
+// CHECK:STDOUT: !81 = !{!82, !7, !7}
+// CHECK:STDOUT: !82 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !83 = !{!84, !85}
+// CHECK:STDOUT: !84 = !DILocalVariable(arg: 1, scope: !79, type: !7)
+// CHECK:STDOUT: !85 = !DILocalVariable(arg: 2, scope: !79, type: !7)
+// CHECK:STDOUT: !86 = !DILocation(line: 50, column: 44, scope: !79)
+// CHECK:STDOUT: !87 = !DILocation(line: 50, column: 37, scope: !79)
+// CHECK:STDOUT: !88 = distinct !DISubprogram(name: "TestNeq", linkageName: "_CTestNeq.Main", scope: null, file: !3, line: 53, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !89)
+// CHECK:STDOUT: !89 = !{!90, !91}
+// CHECK:STDOUT: !90 = !DILocalVariable(arg: 1, scope: !88, type: !7)
+// CHECK:STDOUT: !91 = !DILocalVariable(arg: 2, scope: !88, type: !7)
+// CHECK:STDOUT: !92 = !DILocation(line: 53, column: 45, scope: !88)
+// CHECK:STDOUT: !93 = !DILocation(line: 53, column: 38, scope: !88)
+// CHECK:STDOUT: !94 = distinct !DISubprogram(name: "TestLess", linkageName: "_CTestLess.Main", scope: null, file: !3, line: 56, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !95)
+// CHECK:STDOUT: !95 = !{!96, !97}
+// CHECK:STDOUT: !96 = !DILocalVariable(arg: 1, scope: !94, type: !7)
+// CHECK:STDOUT: !97 = !DILocalVariable(arg: 2, scope: !94, type: !7)
+// CHECK:STDOUT: !98 = !DILocation(line: 56, column: 46, scope: !94)
+// CHECK:STDOUT: !99 = !DILocation(line: 56, column: 39, scope: !94)
+// CHECK:STDOUT: !100 = distinct !DISubprogram(name: "TestLessEq", linkageName: "_CTestLessEq.Main", scope: null, file: !3, line: 59, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !101)
+// CHECK:STDOUT: !101 = !{!102, !103}
+// CHECK:STDOUT: !102 = !DILocalVariable(arg: 1, scope: !100, type: !7)
+// CHECK:STDOUT: !103 = !DILocalVariable(arg: 2, scope: !100, type: !7)
+// CHECK:STDOUT: !104 = !DILocation(line: 59, column: 48, scope: !100)
+// CHECK:STDOUT: !105 = !DILocation(line: 59, column: 41, scope: !100)
+// CHECK:STDOUT: !106 = distinct !DISubprogram(name: "TestGreater", linkageName: "_CTestGreater.Main", scope: null, file: !3, line: 62, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !107)
+// CHECK:STDOUT: !107 = !{!108, !109}
+// CHECK:STDOUT: !108 = !DILocalVariable(arg: 1, scope: !106, type: !7)
+// CHECK:STDOUT: !109 = !DILocalVariable(arg: 2, scope: !106, type: !7)
+// CHECK:STDOUT: !110 = !DILocation(line: 62, column: 49, scope: !106)
+// CHECK:STDOUT: !111 = !DILocation(line: 62, column: 42, scope: !106)
+// CHECK:STDOUT: !112 = distinct !DISubprogram(name: "TestGreaterEq", linkageName: "_CTestGreaterEq.Main", scope: null, file: !3, line: 65, type: !80, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !113)
+// CHECK:STDOUT: !113 = !{!114, !115}
+// CHECK:STDOUT: !114 = !DILocalVariable(arg: 1, scope: !112, type: !7)
+// CHECK:STDOUT: !115 = !DILocalVariable(arg: 2, scope: !112, type: !7)
+// CHECK:STDOUT: !116 = !DILocation(line: 65, column: 51, scope: !112)
+// CHECK:STDOUT: !117 = !DILocation(line: 65, column: 44, scope: !112)

+ 54 - 41
toolchain/lower/testdata/class/adapt.carbon

@@ -65,35 +65,35 @@ fn DoStuff(a: Int) -> Int {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CMake.PairOfInts.Main(ptr sret({ i32, i32 }) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc9_27.3.a = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc9_27.6.b = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @PairOfInts.val.loc9_28, i64 8, i1 false), !dbg !8
-// CHECK:STDOUT:   ret void, !dbg !8
+// CHECK:STDOUT:   %.loc9_27.3.a = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !8
+// CHECK:STDOUT:   %.loc9_27.6.b = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !8
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @PairOfInts.val.loc9_28, i64 8, i1 false), !dbg !9
+// CHECK:STDOUT:   ret void, !dbg !9
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMake.PairAdapter.Main(ptr sret({ i32, i32 }) %return) #0 !dbg !9 {
+// CHECK:STDOUT: define void @_CMake.PairAdapter.Main(ptr sret({ i32, i32 }) %return) #0 !dbg !10 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CMake.PairOfInts.Main(ptr %return), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   call void @_CMake.PairOfInts.Main(ptr %return), !dbg !11
+// CHECK:STDOUT:   ret void, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CGetB.PairAdapter.Main(ptr %self) #0 !dbg !12 {
+// CHECK:STDOUT: define i32 @_CGetB.PairAdapter.Main(ptr %self) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc22_14.1.b = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !13
-// CHECK:STDOUT:   %.loc22_14.2 = load i32, ptr %.loc22_14.1.b, align 4, !dbg !13
-// CHECK:STDOUT:   ret i32 %.loc22_14.2, !dbg !14
+// CHECK:STDOUT:   %.loc22_14.1.b = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !19
+// CHECK:STDOUT:   %.loc22_14.2 = load i32, ptr %.loc22_14.1.b, align 4, !dbg !19
+// CHECK:STDOUT:   ret i32 %.loc22_14.2, !dbg !20
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CUse.Main() #0 !dbg !15 {
+// CHECK:STDOUT: define i32 @_CUse.Main() #0 !dbg !21 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %pa.var = alloca { i32, i32 }, align 8, !dbg !16
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %pa.var), !dbg !16
-// CHECK:STDOUT:   call void @_CMake.PairAdapter.Main(ptr %pa.var), !dbg !17
-// CHECK:STDOUT:   %PairAdapter.GetB.call = call i32 @_CGetB.PairAdapter.Main(ptr %pa.var), !dbg !18
-// CHECK:STDOUT:   ret i32 %PairAdapter.GetB.call, !dbg !19
+// CHECK:STDOUT:   %pa.var = alloca { i32, i32 }, align 8, !dbg !24
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %pa.var), !dbg !24
+// CHECK:STDOUT:   call void @_CMake.PairAdapter.Main(ptr %pa.var), !dbg !25
+// CHECK:STDOUT:   %PairAdapter.GetB.call = call i32 @_CGetB.PairAdapter.Main(ptr %pa.var), !dbg !26
+// CHECK:STDOUT:   ret i32 %PairAdapter.GetB.call, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -115,34 +115,42 @@ fn DoStuff(a: Int) -> Int {
 // CHECK:STDOUT: !3 = !DIFile(filename: "adapt_class.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.PairOfInts.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 9, column: 12, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 9, column: 5, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.PairAdapter.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 12, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 5, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "GetB", linkageName: "_CGetB.PairAdapter.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 22, column: 12, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 22, column: 5, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Main", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 27, column: 3, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 27, column: 25, scope: !15)
-// CHECK:STDOUT: !18 = !DILocation(line: 28, column: 10, scope: !15)
-// CHECK:STDOUT: !19 = !DILocation(line: 28, column: 3, scope: !15)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 9, column: 12, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 9, column: 5, scope: !4)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.PairAdapter.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 12, scope: !10)
+// CHECK:STDOUT: !12 = !DILocation(line: 17, column: 5, scope: !10)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "GetB", linkageName: "_CGetB.PairAdapter.Main", scope: null, file: !3, line: 20, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !17)
+// CHECK:STDOUT: !14 = !DISubroutineType(types: !15)
+// CHECK:STDOUT: !15 = !{!16, !7}
+// CHECK:STDOUT: !16 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !17 = !{!18}
+// CHECK:STDOUT: !18 = !DILocalVariable(arg: 1, scope: !13, type: !7)
+// CHECK:STDOUT: !19 = !DILocation(line: 22, column: 12, scope: !13)
+// CHECK:STDOUT: !20 = !DILocation(line: 22, column: 5, scope: !13)
+// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Main", scope: null, file: !3, line: 26, type: !22, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !22 = !DISubroutineType(types: !23)
+// CHECK:STDOUT: !23 = !{!16}
+// CHECK:STDOUT: !24 = !DILocation(line: 27, column: 3, scope: !21)
+// CHECK:STDOUT: !25 = !DILocation(line: 27, column: 25, scope: !21)
+// CHECK:STDOUT: !26 = !DILocation(line: 28, column: 10, scope: !21)
+// CHECK:STDOUT: !27 = !DILocation(line: 28, column: 3, scope: !21)
 // CHECK:STDOUT: ; ModuleID = 'adapt_int.carbon'
 // CHECK:STDOUT: source_filename = "adapt_int.carbon"
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @"_COp.Int.Main:Copy.Core"(i32 %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %self, !dbg !7
+// CHECK:STDOUT:   ret i32 %self, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CDoStuff.Main(i32 %a) #0 !dbg !8 {
+// CHECK:STDOUT: define i32 @_CDoStuff.Main(i32 %a) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.Copy.impl.Op.call = call i32 @"_COp.Int.Main:Copy.Core"(i32 %a), !dbg !9
-// CHECK:STDOUT:   ret i32 %Int.as.Copy.impl.Op.call, !dbg !10
+// CHECK:STDOUT:   %Int.as.Copy.impl.Op.call = call i32 @"_COp.Int.Main:Copy.Core"(i32 %a), !dbg !14
+// CHECK:STDOUT:   ret i32 %Int.as.Copy.impl.Op.call, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -154,10 +162,15 @@ fn DoStuff(a: Int) -> Int {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "adapt_int.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Main:Copy.Core", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Main:Copy.Core", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 8, column: 35, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "DoStuff", linkageName: "_CDoStuff.Main", scope: null, file: !3, line: 12, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 13, column: 10, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 3, scope: !8)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 8, column: 35, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "DoStuff", linkageName: "_CDoStuff.Main", scope: null, file: !3, line: 12, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !12)
+// CHECK:STDOUT: !12 = !{!13}
+// CHECK:STDOUT: !13 = !DILocalVariable(arg: 1, scope: !11, type: !7)
+// CHECK:STDOUT: !14 = !DILocation(line: 13, column: 10, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 13, column: 3, scope: !11)

+ 37 - 30
toolchain/lower/testdata/class/base.carbon

@@ -40,33 +40,33 @@ fn Convert(p: Derived*) -> Base* {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CMake.Main(ptr sret({ { i32 }, i32 }) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc24_35.2.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc24_26.3.b = getelementptr inbounds nuw { i32 }, ptr %.loc24_35.2.base, i32 0, i32 0, !dbg !8
-// CHECK:STDOUT:   %.loc24_35.5.d = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @Derived.val.loc24_36, i64 8, i1 false), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   %.loc24_35.2.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 0, !dbg !8
+// CHECK:STDOUT:   %.loc24_26.3.b = getelementptr inbounds nuw { i32 }, ptr %.loc24_35.2.base, i32 0, i32 0, !dbg !9
+// CHECK:STDOUT:   %.loc24_35.5.d = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 1, !dbg !8
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @Derived.val.loc24_36, i64 8, i1 false), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CAccess.Main(ptr sret({ i32, i32 }) %return, ptr %d) #0 !dbg !10 {
+// CHECK:STDOUT: define void @_CAccess.Main(ptr sret({ i32, i32 }) %return, ptr %d) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc28_12.1.d = getelementptr inbounds nuw { { i32 }, i32 }, ptr %d, i32 0, i32 1, !dbg !11
-// CHECK:STDOUT:   %.loc28_12.2 = load i32, ptr %.loc28_12.1.d, align 4, !dbg !11
-// CHECK:STDOUT:   %.loc28_17.1.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %d, i32 0, i32 0, !dbg !12
-// CHECK:STDOUT:   %.loc28_22.1.b = getelementptr inbounds nuw { i32 }, ptr %.loc28_17.1.base, i32 0, i32 0, !dbg !12
-// CHECK:STDOUT:   %.loc28_22.2 = load i32, ptr %.loc28_22.1.b, align 4, !dbg !12
-// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !13
-// CHECK:STDOUT:   store i32 %.loc28_12.2, ptr %tuple.elem0.tuple.elem, align 4, !dbg !13
-// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !13
-// CHECK:STDOUT:   store i32 %.loc28_22.2, ptr %tuple.elem1.tuple.elem, align 4, !dbg !13
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   %.loc28_12.1.d = getelementptr inbounds nuw { { i32 }, i32 }, ptr %d, i32 0, i32 1, !dbg !16
+// CHECK:STDOUT:   %.loc28_12.2 = load i32, ptr %.loc28_12.1.d, align 4, !dbg !16
+// CHECK:STDOUT:   %.loc28_17.1.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %d, i32 0, i32 0, !dbg !17
+// CHECK:STDOUT:   %.loc28_22.1.b = getelementptr inbounds nuw { i32 }, ptr %.loc28_17.1.base, i32 0, i32 0, !dbg !17
+// CHECK:STDOUT:   %.loc28_22.2 = load i32, ptr %.loc28_22.1.b, align 4, !dbg !17
+// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !18
+// CHECK:STDOUT:   store i32 %.loc28_12.2, ptr %tuple.elem0.tuple.elem, align 4, !dbg !18
+// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !18
+// CHECK:STDOUT:   store i32 %.loc28_22.2, ptr %tuple.elem1.tuple.elem, align 4, !dbg !18
+// CHECK:STDOUT:   ret void, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define ptr @_CConvert.Main(ptr %p) #0 !dbg !15 {
+// CHECK:STDOUT: define ptr @_CConvert.Main(ptr %p) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc32_11.2.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %p, i32 0, i32 0, !dbg !16
-// CHECK:STDOUT:   ret ptr %.loc32_11.2.base, !dbg !16
+// CHECK:STDOUT:   %.loc32_11.2.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %p, i32 0, i32 0, !dbg !23
+// CHECK:STDOUT:   ret ptr %.loc32_11.2.base, !dbg !23
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -84,14 +84,21 @@ fn Convert(p: Derived*) -> Base* {
 // CHECK:STDOUT: !3 = !DIFile(filename: "base.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 24, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 24, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 24, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Access", linkageName: "_CAccess.Main", scope: null, file: !3, line: 27, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 28, column: 11, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 28, column: 16, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 28, column: 10, scope: !10)
-// CHECK:STDOUT: !14 = !DILocation(line: 28, column: 3, scope: !10)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.Main", scope: null, file: !3, line: 31, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 32, column: 3, scope: !15)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 24, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 24, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 24, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Access", linkageName: "_CAccess.Main", scope: null, file: !3, line: 27, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{!7, !7}
+// CHECK:STDOUT: !14 = !{!15}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !11, type: !7)
+// CHECK:STDOUT: !16 = !DILocation(line: 28, column: 11, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 28, column: 16, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 28, column: 10, scope: !11)
+// CHECK:STDOUT: !19 = !DILocation(line: 28, column: 3, scope: !11)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.Main", scope: null, file: !3, line: 31, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !21)
+// CHECK:STDOUT: !21 = !{!22}
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 1, scope: !20, type: !7)
+// CHECK:STDOUT: !23 = !DILocation(line: 32, column: 3, scope: !20)

+ 1 - 1
toolchain/lower/testdata/class/basic.carbon

@@ -56,7 +56,7 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "basic.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 21, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 22, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 22, column: 14, scope: !4)

+ 35 - 25
toolchain/lower/testdata/class/convert.carbon

@@ -33,27 +33,27 @@ fn DoIt() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @"_CConvert.IntWrapper.Main:ImplicitAs.Core"(ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc18_48.1.n = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc18_48.2 = load i32, ptr %.loc18_48.1.n, align 4, !dbg !7
-// CHECK:STDOUT:   ret i32 %.loc18_48.2, !dbg !8
+// CHECK:STDOUT:   %.loc18_48.1.n = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !11
+// CHECK:STDOUT:   %.loc18_48.2 = load i32, ptr %.loc18_48.1.n, align 4, !dbg !11
+// CHECK:STDOUT:   ret i32 %.loc18_48.2, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CConsume.Main(i32 %n) #0 !dbg !9 {
+// CHECK:STDOUT: define void @_CConsume.Main(i32 %n) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CDoIt.Main() #0 !dbg !11 {
+// CHECK:STDOUT: define void @_CDoIt.Main() #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %w.var = alloca { i32 }, align 8, !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %w.var), !dbg !12
-// CHECK:STDOUT:   %.loc24_31.3.n = getelementptr inbounds nuw { i32 }, ptr %w.var, i32 0, i32 0, !dbg !13
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %w.var, ptr align 4 @IntWrapper.val.loc24_3, i64 4, i1 false), !dbg !12
-// CHECK:STDOUT:   %IntWrapper.as.ImplicitAs.impl.Convert.call = call i32 @"_CConvert.IntWrapper.Main:ImplicitAs.Core"(ptr %w.var), !dbg !14
-// CHECK:STDOUT:   call void @_CConsume.Main(i32 %IntWrapper.as.ImplicitAs.impl.Convert.call), !dbg !15
-// CHECK:STDOUT:   ret void, !dbg !16
+// CHECK:STDOUT:   %w.var = alloca { i32 }, align 8, !dbg !22
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %w.var), !dbg !22
+// CHECK:STDOUT:   %.loc24_31.3.n = getelementptr inbounds nuw { i32 }, ptr %w.var, i32 0, i32 0, !dbg !23
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %w.var, ptr align 4 @IntWrapper.val.loc24_3, i64 4, i1 false), !dbg !22
+// CHECK:STDOUT:   %IntWrapper.as.ImplicitAs.impl.Convert.call = call i32 @"_CConvert.IntWrapper.Main:ImplicitAs.Core"(ptr %w.var), !dbg !24
+// CHECK:STDOUT:   call void @_CConsume.Main(i32 %IntWrapper.as.ImplicitAs.impl.Convert.call), !dbg !25
+// CHECK:STDOUT:   ret void, !dbg !26
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -73,16 +73,26 @@ fn DoIt() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "convert.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.IntWrapper.Main:ImplicitAs.Core", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.IntWrapper.Main:ImplicitAs.Core", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 18, column: 44, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 18, column: 37, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Consume", linkageName: "_CConsume.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 21, column: 1, scope: !9)
-// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "DoIt", linkageName: "_CDoIt.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !12 = !DILocation(line: 24, column: 3, scope: !11)
-// CHECK:STDOUT: !13 = !DILocation(line: 24, column: 23, scope: !11)
-// CHECK:STDOUT: !14 = !DILocation(line: 25, column: 11, scope: !11)
-// CHECK:STDOUT: !15 = !DILocation(line: 25, column: 3, scope: !11)
-// CHECK:STDOUT: !16 = !DILocation(line: 23, column: 1, scope: !11)
+// CHECK:STDOUT: !6 = !{!7, !8}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocation(line: 18, column: 44, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 37, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "Consume", linkageName: "_CConsume.Main", scope: null, file: !3, line: 21, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !16)
+// CHECK:STDOUT: !14 = !DISubroutineType(types: !15)
+// CHECK:STDOUT: !15 = !{null, !7}
+// CHECK:STDOUT: !16 = !{!17}
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 1, scope: !13, type: !7)
+// CHECK:STDOUT: !18 = !DILocation(line: 21, column: 1, scope: !13)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "DoIt", linkageName: "_CDoIt.Main", scope: null, file: !3, line: 23, type: !20, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !20 = !DISubroutineType(types: !21)
+// CHECK:STDOUT: !21 = !{null}
+// CHECK:STDOUT: !22 = !DILocation(line: 24, column: 3, scope: !19)
+// CHECK:STDOUT: !23 = !DILocation(line: 24, column: 23, scope: !19)
+// CHECK:STDOUT: !24 = !DILocation(line: 25, column: 11, scope: !19)
+// CHECK:STDOUT: !25 = !DILocation(line: 25, column: 3, scope: !19)
+// CHECK:STDOUT: !26 = !DILocation(line: 23, column: 1, scope: !19)

+ 33 - 27
toolchain/lower/testdata/class/field.carbon

@@ -74,24 +74,24 @@ fn Run() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CF.Main(ptr %c) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc10_13.1.b = getelementptr inbounds nuw { i32, ptr }, ptr %c, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   %.loc10_13.2 = load ptr, ptr %.loc10_13.1.b, align 8, !dbg !7
-// CHECK:STDOUT:   %.loc10_16.1.a = getelementptr inbounds nuw { i32, ptr }, ptr %.loc10_13.2, i32 0, i32 0, !dbg !8
-// CHECK:STDOUT:   %.loc10_16.2 = load i32, ptr %.loc10_16.1.a, align 4, !dbg !8
-// CHECK:STDOUT:   ret i32 %.loc10_16.2, !dbg !9
+// CHECK:STDOUT:   %.loc10_13.1.b = getelementptr inbounds nuw { i32, ptr }, ptr %c, i32 0, i32 1, !dbg !11
+// CHECK:STDOUT:   %.loc10_13.2 = load ptr, ptr %.loc10_13.1.b, align 8, !dbg !11
+// CHECK:STDOUT:   %.loc10_16.1.a = getelementptr inbounds nuw { i32, ptr }, ptr %.loc10_13.2, i32 0, i32 0, !dbg !12
+// CHECK:STDOUT:   %.loc10_16.2 = load i32, ptr %.loc10_16.1.a, align 4, !dbg !12
+// CHECK:STDOUT:   ret i32 %.loc10_16.2, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @main() #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @main() #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca { i32, ptr }, align 8, !dbg !11
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !11
-// CHECK:STDOUT:   %.loc15_4.a = getelementptr inbounds nuw { i32, ptr }, ptr %c.var, i32 0, i32 0, !dbg !12
-// CHECK:STDOUT:   store i32 1, ptr %.loc15_4.a, align 4, !dbg !12
-// CHECK:STDOUT:   %.loc16.b = getelementptr inbounds nuw { i32, ptr }, ptr %c.var, i32 0, i32 1, !dbg !13
-// CHECK:STDOUT:   store ptr %c.var, ptr %.loc16.b, align 8, !dbg !13
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main(ptr %c.var), !dbg !14
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !15
+// CHECK:STDOUT:   %c.var = alloca { i32, ptr }, align 8, !dbg !17
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !17
+// CHECK:STDOUT:   %.loc15_4.a = getelementptr inbounds nuw { i32, ptr }, ptr %c.var, i32 0, i32 0, !dbg !18
+// CHECK:STDOUT:   store i32 1, ptr %.loc15_4.a, align 4, !dbg !18
+// CHECK:STDOUT:   %.loc16.b = getelementptr inbounds nuw { i32, ptr }, ptr %c.var, i32 0, i32 1, !dbg !19
+// CHECK:STDOUT:   store ptr %c.var, ptr %.loc16.b, align 8, !dbg !19
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main(ptr %c.var), !dbg !20
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !21
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -107,18 +107,24 @@ fn Run() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "basic.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 10, column: 12, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 10, column: 10, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 10, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 14, column: 3, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 15, column: 3, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 16, column: 3, scope: !10)
-// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 10, scope: !10)
-// CHECK:STDOUT: !15 = !DILocation(line: 17, column: 3, scope: !10)
+// CHECK:STDOUT: !6 = !{!7, !8}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocation(line: 10, column: 12, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 10, column: 10, scope: !4)
+// CHECK:STDOUT: !13 = !DILocation(line: 10, column: 3, scope: !4)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 13, type: !15, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{!7}
+// CHECK:STDOUT: !17 = !DILocation(line: 14, column: 3, scope: !14)
+// CHECK:STDOUT: !18 = !DILocation(line: 15, column: 3, scope: !14)
+// CHECK:STDOUT: !19 = !DILocation(line: 16, column: 3, scope: !14)
+// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 10, scope: !14)
+// CHECK:STDOUT: !21 = !DILocation(line: 17, column: 3, scope: !14)
 // CHECK:STDOUT: ; ModuleID = 'inplace_init_with_nonconst.carbon'
 // CHECK:STDOUT: source_filename = "inplace_init_with_nonconst.carbon"
 // CHECK:STDOUT:
@@ -160,7 +166,7 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "inplace_init_with_nonconst.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 12, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 15, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 15, column: 16, scope: !4)
@@ -207,7 +213,7 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "implicit_init_with_nonempty_nonconst.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 17, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 17, column: 16, scope: !4)

+ 214 - 179
toolchain/lower/testdata/class/generic.carbon

@@ -120,18 +120,18 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CCreateDerived.Create(ptr sret({ { i32 }, i32 }) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc7_35.2.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc7_26.3.b = getelementptr inbounds nuw { i32 }, ptr %.loc7_35.2.base, i32 0, i32 0, !dbg !8
-// CHECK:STDOUT:   %.loc7_35.5.d = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @Derived.val.loc7_36, i64 8, i1 false), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   %.loc7_35.2.base = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 0, !dbg !8
+// CHECK:STDOUT:   %.loc7_26.3.b = getelementptr inbounds nuw { i32 }, ptr %.loc7_35.2.base, i32 0, i32 0, !dbg !9
+// CHECK:STDOUT:   %.loc7_35.5.d = getelementptr inbounds nuw { { i32 }, i32 }, ptr %return, i32 0, i32 1, !dbg !8
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %return, ptr align 4 @Derived.val.loc7_36, i64 8, i1 false), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CCreateAdapter.Create(ptr sret({ { i32 }, i32 }) %return) #0 !dbg !10 {
+// CHECK:STDOUT: define void @_CCreateAdapter.Create(ptr sret({ { i32 }, i32 }) %return) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CCreateDerived.Create(ptr %return), !dbg !11
-// CHECK:STDOUT:   ret void, !dbg !12
+// CHECK:STDOUT:   call void @_CCreateDerived.Create(ptr %return), !dbg !12
+// CHECK:STDOUT:   ret void, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -149,13 +149,14 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "create.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "CreateDerived", linkageName: "_CCreateDerived.Create", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "CreateAdapter", linkageName: "_CCreateAdapter.Create", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 11, column: 10, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 11, column: 3, scope: !10)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 7, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CreateAdapter", linkageName: "_CCreateAdapter.Create", scope: null, file: !3, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DILocation(line: 11, column: 10, scope: !11)
+// CHECK:STDOUT: !13 = !DILocation(line: 11, column: 3, scope: !11)
 // CHECK:STDOUT: ; ModuleID = 'create_generic.carbon'
 // CHECK:STDOUT: source_filename = "create_generic.carbon"
 // CHECK:STDOUT:
@@ -164,63 +165,63 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CInts.Main(ptr sret({ i32, i32 }) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CMake.Main.5450dc8e8b8e0899(ptr %return, i32 1, i32 2), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !8
+// CHECK:STDOUT:   call void @_CMake.Main.5450dc8e8b8e0899(ptr %return, i32 1, i32 2), !dbg !8
+// CHECK:STDOUT:   ret void, !dbg !9
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CEmpty.Main(ptr sret({ {}, {} }) %return) #0 !dbg !9 {
+// CHECK:STDOUT: define void @_CEmpty.Main(ptr sret({ {}, {} }) %return) #0 !dbg !10 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CMake.Main.cf13cead63317d44(ptr %return), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   call void @_CMake.Main.cf13cead63317d44(ptr %return), !dbg !11
+// CHECK:STDOUT:   ret void, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTuples.Main(ptr sret({ { i32, i32 }, { i32, i32 } }) %return) #0 !dbg !12 {
+// CHECK:STDOUT: define void @_CTuples.Main(ptr sret({ { i32, i32 }, { i32, i32 } }) %return) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CMake.Main.a862d5c8b748242e(ptr %return, ptr @tuple.21c.loc22_28.6, ptr @tuple.21c.loc22_28.6), !dbg !13
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   call void @_CMake.Main.a862d5c8b748242e(ptr %return, ptr @tuple.21c.loc22_28.6, ptr @tuple.21c.loc22_28.6), !dbg !14
+// CHECK:STDOUT:   ret void, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CMake.Main.5450dc8e8b8e0899(ptr sret({ i32, i32 }) %return, i32 %x, i32 %y) #0 !dbg !15 {
+// CHECK:STDOUT: define linkonce_odr void @_CMake.Main.5450dc8e8b8e0899(ptr sret({ i32, i32 }) %return, i32 %x, i32 %y) #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc10_25.2.x = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !16
-// CHECK:STDOUT:   store i32 %x, ptr %.loc10_25.2.x, align 4, !dbg !16
-// CHECK:STDOUT:   %.loc10_25.4.y = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !16
-// CHECK:STDOUT:   store i32 %y, ptr %.loc10_25.4.y, align 4, !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %.loc10_25.2.x = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !23
+// CHECK:STDOUT:   store i32 %x, ptr %.loc10_25.2.x, align 4, !dbg !23
+// CHECK:STDOUT:   %.loc10_25.4.y = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !23
+// CHECK:STDOUT:   store i32 %y, ptr %.loc10_25.4.y, align 4, !dbg !23
+// CHECK:STDOUT:   ret void, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CMake.Main.cf13cead63317d44(ptr sret({ {}, {} }) %return) #0 !dbg !18 {
+// CHECK:STDOUT: define linkonce_odr void @_CMake.Main.cf13cead63317d44(ptr sret({ {}, {} }) %return) #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc10_25.2.x = getelementptr inbounds nuw { {}, {} }, ptr %return, i32 0, i32 0, !dbg !19
-// CHECK:STDOUT:   %.loc10_25.4.y = getelementptr inbounds nuw { {}, {} }, ptr %return, i32 0, i32 1, !dbg !19
-// CHECK:STDOUT:   ret void, !dbg !20
+// CHECK:STDOUT:   %.loc10_25.2.x = getelementptr inbounds nuw { {}, {} }, ptr %return, i32 0, i32 0, !dbg !26
+// CHECK:STDOUT:   %.loc10_25.4.y = getelementptr inbounds nuw { {}, {} }, ptr %return, i32 0, i32 1, !dbg !26
+// CHECK:STDOUT:   ret void, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CMake.Main.a862d5c8b748242e(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %x, ptr %y) #0 !dbg !21 {
+// CHECK:STDOUT: define linkonce_odr void @_CMake.Main.a862d5c8b748242e(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %x, ptr %y) #0 !dbg !28 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc10_25.2.x = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 0, !dbg !22
-// CHECK:STDOUT:   call void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr %.loc10_25.2.x, ptr %x), !dbg !23
-// CHECK:STDOUT:   %.loc10_25.4.y = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 1, !dbg !22
-// CHECK:STDOUT:   call void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr %.loc10_25.4.y, ptr %y), !dbg !24
-// CHECK:STDOUT:   ret void, !dbg !25
+// CHECK:STDOUT:   %.loc10_25.2.x = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 0, !dbg !34
+// CHECK:STDOUT:   call void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr %.loc10_25.2.x, ptr %x), !dbg !35
+// CHECK:STDOUT:   %.loc10_25.4.y = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 1, !dbg !34
+// CHECK:STDOUT:   call void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr %.loc10_25.4.y, ptr %y), !dbg !36
+// CHECK:STDOUT:   ret void, !dbg !37
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !26 {
-// CHECK:STDOUT:   %tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !28
-// CHECK:STDOUT:   %tuple.elem.load = load i32, ptr %tuple.elem, align 4, !dbg !28
-// CHECK:STDOUT:   %tuple.elem1 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !29
-// CHECK:STDOUT:   %tuple.elem2 = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !30
-// CHECK:STDOUT:   %tuple.elem.load3 = load i32, ptr %tuple.elem2, align 4, !dbg !30
-// CHECK:STDOUT:   %tuple.elem4 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !29
-// CHECK:STDOUT:   store i32 %tuple.elem.load, ptr %tuple.elem1, align 4, !dbg !29
-// CHECK:STDOUT:   store i32 %tuple.elem.load3, ptr %tuple.elem4, align 4, !dbg !29
-// CHECK:STDOUT:   ret void, !dbg !31
+// CHECK:STDOUT: define linkonce_odr void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !38 {
+// CHECK:STDOUT:   %tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !44
+// CHECK:STDOUT:   %tuple.elem.load = load i32, ptr %tuple.elem, align 4, !dbg !44
+// CHECK:STDOUT:   %tuple.elem1 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !45
+// CHECK:STDOUT:   %tuple.elem2 = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !46
+// CHECK:STDOUT:   %tuple.elem.load3 = load i32, ptr %tuple.elem2, align 4, !dbg !46
+// CHECK:STDOUT:   %tuple.elem4 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !45
+// CHECK:STDOUT:   store i32 %tuple.elem.load, ptr %tuple.elem1, align 4, !dbg !45
+// CHECK:STDOUT:   store i32 %tuple.elem.load3, ptr %tuple.elem4, align 4, !dbg !45
+// CHECK:STDOUT:   ret void, !dbg !47
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -237,32 +238,48 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "create_generic.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Ints", linkageName: "_CInts.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Empty", linkageName: "_CEmpty.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 18, column: 10, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 18, column: 3, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Tuples", linkageName: "_CTuples.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 23, column: 10, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 23, column: 3, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 10, column: 10, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 10, column: 3, scope: !15)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main.cf13cead63317d44", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 10, column: 10, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 10, column: 3, scope: !18)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main.a862d5c8b748242e", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 10, column: 10, scope: !21)
-// CHECK:STDOUT: !23 = !DILocation(line: 10, column: 16, scope: !21)
-// CHECK:STDOUT: !24 = !DILocation(line: 10, column: 24, scope: !21)
-// CHECK:STDOUT: !25 = !DILocation(line: 10, column: 3, scope: !21)
-// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "Op", linkageName: "_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1", scope: null, file: !27, line: 48, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !27 = !DIFile(filename: "min_prelude/parts/copy.carbon", directory: "")
-// CHECK:STDOUT: !28 = !DILocation(line: 49, column: 13, scope: !26)
-// CHECK:STDOUT: !29 = !DILocation(line: 49, column: 12, scope: !26)
-// CHECK:STDOUT: !30 = !DILocation(line: 49, column: 26, scope: !26)
-// CHECK:STDOUT: !31 = !DILocation(line: 49, column: 5, scope: !26)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Empty", linkageName: "_CEmpty.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !11 = !DILocation(line: 18, column: 10, scope: !10)
+// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 3, scope: !10)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "Tuples", linkageName: "_CTuples.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !14 = !DILocation(line: 23, column: 10, scope: !13)
+// CHECK:STDOUT: !15 = !DILocation(line: 23, column: 3, scope: !13)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 9, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{!7, !19, !19}
+// CHECK:STDOUT: !19 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !20 = !{!21, !22}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !16, type: !19)
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 2, scope: !16, type: !19)
+// CHECK:STDOUT: !23 = !DILocation(line: 10, column: 10, scope: !16)
+// CHECK:STDOUT: !24 = !DILocation(line: 10, column: 3, scope: !16)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main.cf13cead63317d44", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !26 = !DILocation(line: 10, column: 10, scope: !25)
+// CHECK:STDOUT: !27 = !DILocation(line: 10, column: 3, scope: !25)
+// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main.a862d5c8b748242e", scope: null, file: !3, line: 9, type: !29, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !31)
+// CHECK:STDOUT: !29 = !DISubroutineType(types: !30)
+// CHECK:STDOUT: !30 = !{!7, !7, !7}
+// CHECK:STDOUT: !31 = !{!32, !33}
+// CHECK:STDOUT: !32 = !DILocalVariable(arg: 1, scope: !28, type: !7)
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 2, scope: !28, type: !7)
+// CHECK:STDOUT: !34 = !DILocation(line: 10, column: 10, scope: !28)
+// CHECK:STDOUT: !35 = !DILocation(line: 10, column: 16, scope: !28)
+// CHECK:STDOUT: !36 = !DILocation(line: 10, column: 24, scope: !28)
+// CHECK:STDOUT: !37 = !DILocation(line: 10, column: 3, scope: !28)
+// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "Op", linkageName: "_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1", scope: null, file: !39, line: 48, type: !40, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !42)
+// CHECK:STDOUT: !39 = !DIFile(filename: "min_prelude/parts/copy.carbon", directory: "")
+// CHECK:STDOUT: !40 = !DISubroutineType(types: !41)
+// CHECK:STDOUT: !41 = !{!7, !7}
+// CHECK:STDOUT: !42 = !{!43}
+// CHECK:STDOUT: !43 = !DILocalVariable(arg: 1, scope: !38, type: !7)
+// CHECK:STDOUT: !44 = !DILocation(line: 49, column: 13, scope: !38)
+// CHECK:STDOUT: !45 = !DILocation(line: 49, column: 12, scope: !38)
+// CHECK:STDOUT: !46 = !DILocation(line: 49, column: 26, scope: !38)
+// CHECK:STDOUT: !47 = !DILocation(line: 49, column: 5, scope: !38)
 // CHECK:STDOUT: ; ModuleID = 'access.carbon'
 // CHECK:STDOUT: source_filename = "access.carbon"
 // CHECK:STDOUT:
@@ -273,52 +290,52 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i1 @_CAccessBool.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca { i1, i32 }, align 8, !dbg !7
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !7
-// CHECK:STDOUT:   %.loc16_37.2.v = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 0, !dbg !8
-// CHECK:STDOUT:   %.loc16_37.5.w = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 1, !dbg !8
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %c.var, ptr align 4 @C.val.9ee.loc16_3, i64 8, i1 false), !dbg !7
-// CHECK:STDOUT:   %C.GetBool.call = call i1 @_CGetBool.C.Main.5450dc8e8b8e0899(ptr %c.var), !dbg !9
-// CHECK:STDOUT:   ret i1 %C.GetBool.call, !dbg !10
+// CHECK:STDOUT:   %c.var = alloca { i1, i32 }, align 8, !dbg !8
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !8
+// CHECK:STDOUT:   %.loc16_37.2.v = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 0, !dbg !9
+// CHECK:STDOUT:   %.loc16_37.5.w = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 1, !dbg !9
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %c.var, ptr align 4 @C.val.9ee.loc16_3, i64 8, i1 false), !dbg !8
+// CHECK:STDOUT:   %C.GetBool.call = call i1 @_CGetBool.C.Main.5450dc8e8b8e0899(ptr %c.var), !dbg !10
+// CHECK:STDOUT:   ret i1 %C.GetBool.call, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CAccessInt.Main() #0 !dbg !11 {
+// CHECK:STDOUT: define i32 @_CAccessInt.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca { i1, i32 }, align 8, !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !12
-// CHECK:STDOUT:   %.loc21_37.2.v = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 0, !dbg !13
-// CHECK:STDOUT:   %.loc21_37.5.w = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 1, !dbg !13
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %c.var, ptr align 4 @C.val.9ee.loc16_3, i64 8, i1 false), !dbg !12
-// CHECK:STDOUT:   %C.GetT.call = call i32 @_CGetT.C.Main.5450dc8e8b8e0899(ptr %c.var), !dbg !14
-// CHECK:STDOUT:   ret i32 %C.GetT.call, !dbg !15
+// CHECK:STDOUT:   %c.var = alloca { i1, i32 }, align 8, !dbg !16
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !16
+// CHECK:STDOUT:   %.loc21_37.2.v = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 0, !dbg !17
+// CHECK:STDOUT:   %.loc21_37.5.w = getelementptr inbounds nuw { i1, i32 }, ptr %c.var, i32 0, i32 1, !dbg !17
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %c.var, ptr align 4 @C.val.9ee.loc16_3, i64 8, i1 false), !dbg !16
+// CHECK:STDOUT:   %C.GetT.call = call i32 @_CGetT.C.Main.5450dc8e8b8e0899(ptr %c.var), !dbg !18
+// CHECK:STDOUT:   ret i32 %C.GetT.call, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CAccessEmpty.Main() #0 !dbg !16 {
+// CHECK:STDOUT: define void @_CAccessEmpty.Main() #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca { i1, {} }, align 8, !dbg !17
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !17
-// CHECK:STDOUT:   %.loc26_37.2.v = getelementptr inbounds nuw { i1, {} }, ptr %c.var, i32 0, i32 0, !dbg !18
-// CHECK:STDOUT:   %.loc26_37.4.w = getelementptr inbounds nuw { i1, {} }, ptr %c.var, i32 0, i32 1, !dbg !18
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %c.var, ptr align 1 @C.val.f52.loc26_3, i64 1, i1 false), !dbg !17
-// CHECK:STDOUT:   call void @_CGetT.C.Main.cf13cead63317d44(ptr %c.var), !dbg !19
-// CHECK:STDOUT:   ret void, !dbg !20
+// CHECK:STDOUT:   %c.var = alloca { i1, {} }, align 8, !dbg !21
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !21
+// CHECK:STDOUT:   %.loc26_37.2.v = getelementptr inbounds nuw { i1, {} }, ptr %c.var, i32 0, i32 0, !dbg !22
+// CHECK:STDOUT:   %.loc26_37.4.w = getelementptr inbounds nuw { i1, {} }, ptr %c.var, i32 0, i32 1, !dbg !22
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %c.var, ptr align 1 @C.val.f52.loc26_3, i64 1, i1 false), !dbg !21
+// CHECK:STDOUT:   call void @_CGetT.C.Main.cf13cead63317d44(ptr %c.var), !dbg !23
+// CHECK:STDOUT:   ret void, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CAccessTuple.Main(ptr sret({ i32, i32, i32 }) %return) #0 !dbg !21 {
+// CHECK:STDOUT: define void @_CAccessTuple.Main(ptr sret({ i32, i32, i32 }) %return) #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca { i1, { i32, i32, i32 } }, align 8, !dbg !22
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !22
-// CHECK:STDOUT:   %.loc31_57.2.v = getelementptr inbounds nuw { i1, { i32, i32, i32 } }, ptr %c.var, i32 0, i32 0, !dbg !23
-// CHECK:STDOUT:   %.loc31_57.4.w = getelementptr inbounds nuw { i1, { i32, i32, i32 } }, ptr %c.var, i32 0, i32 1, !dbg !23
-// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc31_57.4.w, i32 0, i32 0, !dbg !24
-// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc31_57.4.w, i32 0, i32 1, !dbg !24
-// CHECK:STDOUT:   %tuple.elem2.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc31_57.4.w, i32 0, i32 2, !dbg !24
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %c.var, ptr align 4 @C.val.029.loc31_3, i64 16, i1 false), !dbg !22
-// CHECK:STDOUT:   call void @_CGetT.C.Main.623a49e5eda7ec3b(ptr %return, ptr %c.var), !dbg !25
-// CHECK:STDOUT:   ret void, !dbg !26
+// CHECK:STDOUT:   %c.var = alloca { i1, { i32, i32, i32 } }, align 8, !dbg !26
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !26
+// CHECK:STDOUT:   %.loc31_57.2.v = getelementptr inbounds nuw { i1, { i32, i32, i32 } }, ptr %c.var, i32 0, i32 0, !dbg !27
+// CHECK:STDOUT:   %.loc31_57.4.w = getelementptr inbounds nuw { i1, { i32, i32, i32 } }, ptr %c.var, i32 0, i32 1, !dbg !27
+// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc31_57.4.w, i32 0, i32 0, !dbg !28
+// CHECK:STDOUT:   %tuple.elem1.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc31_57.4.w, i32 0, i32 1, !dbg !28
+// CHECK:STDOUT:   %tuple.elem2.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc31_57.4.w, i32 0, i32 2, !dbg !28
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 4 %c.var, ptr align 4 @C.val.029.loc31_3, i64 16, i1 false), !dbg !26
+// CHECK:STDOUT:   call void @_CGetT.C.Main.623a49e5eda7ec3b(ptr %return, ptr %c.var), !dbg !29
+// CHECK:STDOUT:   ret void, !dbg !30
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -328,52 +345,52 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: declare void @llvm.memcpy.p0.p0.i64(ptr noalias writeonly captures(none), ptr noalias readonly captures(none), i64, i1 immarg) #2
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @_CGetBool.C.Main.5450dc8e8b8e0899(ptr %self) #0 !dbg !27 {
+// CHECK:STDOUT: define linkonce_odr i1 @_CGetBool.C.Main.5450dc8e8b8e0899(ptr %self) #0 !dbg !31 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc6_16.1.v = getelementptr inbounds nuw { i1, i32 }, ptr %self, i32 0, i32 0, !dbg !28
-// CHECK:STDOUT:   %.loc6_16.2 = load i8, ptr %.loc6_16.1.v, align 1, !dbg !28
-// CHECK:STDOUT:   %.loc6_16.21 = trunc i8 %.loc6_16.2 to i1, !dbg !28
-// CHECK:STDOUT:   ret i1 %.loc6_16.21, !dbg !29
+// CHECK:STDOUT:   %.loc6_16.1.v = getelementptr inbounds nuw { i1, i32 }, ptr %self, i32 0, i32 0, !dbg !36
+// CHECK:STDOUT:   %.loc6_16.2 = load i8, ptr %.loc6_16.1.v, align 1, !dbg !36
+// CHECK:STDOUT:   %.loc6_16.21 = trunc i8 %.loc6_16.2 to i1, !dbg !36
+// CHECK:STDOUT:   ret i1 %.loc6_16.21, !dbg !37
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CGetT.C.Main.5450dc8e8b8e0899(ptr %self) #0 !dbg !30 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CGetT.C.Main.5450dc8e8b8e0899(ptr %self) #0 !dbg !38 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc9_16.1.w = getelementptr inbounds nuw { i1, i32 }, ptr %self, i32 0, i32 1, !dbg !31
-// CHECK:STDOUT:   %.loc9_16.2 = load i32, ptr %.loc9_16.1.w, align 4, !dbg !31
-// CHECK:STDOUT:   ret i32 %.loc9_16.2, !dbg !32
+// CHECK:STDOUT:   %.loc9_16.1.w = getelementptr inbounds nuw { i1, i32 }, ptr %self, i32 0, i32 1, !dbg !43
+// CHECK:STDOUT:   %.loc9_16.2 = load i32, ptr %.loc9_16.1.w, align 4, !dbg !43
+// CHECK:STDOUT:   ret i32 %.loc9_16.2, !dbg !44
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CGetT.C.Main.cf13cead63317d44(ptr %self) #0 !dbg !33 {
+// CHECK:STDOUT: define linkonce_odr void @_CGetT.C.Main.cf13cead63317d44(ptr %self) #0 !dbg !45 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc9_16.1.w = getelementptr inbounds nuw { i1, {} }, ptr %self, i32 0, i32 1, !dbg !34
-// CHECK:STDOUT:   ret void, !dbg !35
+// CHECK:STDOUT:   %.loc9_16.1.w = getelementptr inbounds nuw { i1, {} }, ptr %self, i32 0, i32 1, !dbg !48
+// CHECK:STDOUT:   ret void, !dbg !49
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CGetT.C.Main.623a49e5eda7ec3b(ptr sret({ i32, i32, i32 }) %return, ptr %self) #0 !dbg !36 {
+// CHECK:STDOUT: define linkonce_odr void @_CGetT.C.Main.623a49e5eda7ec3b(ptr sret({ i32, i32, i32 }) %return, ptr %self) #0 !dbg !50 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc9_16.1.w = getelementptr inbounds nuw { i1, { i32, i32, i32 } }, ptr %self, i32 0, i32 1, !dbg !37
-// CHECK:STDOUT:   call void @"_COp.6d582b60b7397ec5:Copy.Core.8e95c89adba3b450"(ptr %return, ptr %.loc9_16.1.w), !dbg !37
-// CHECK:STDOUT:   ret void, !dbg !38
+// CHECK:STDOUT:   %.loc9_16.1.w = getelementptr inbounds nuw { i1, { i32, i32, i32 } }, ptr %self, i32 0, i32 1, !dbg !53
+// CHECK:STDOUT:   call void @"_COp.6d582b60b7397ec5:Copy.Core.8e95c89adba3b450"(ptr %return, ptr %.loc9_16.1.w), !dbg !53
+// CHECK:STDOUT:   ret void, !dbg !54
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp.6d582b60b7397ec5:Copy.Core.8e95c89adba3b450"(ptr sret({ i32, i32, i32 }) %return, ptr %self) #0 !dbg !39 {
-// CHECK:STDOUT:   %tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %self, i32 0, i32 0, !dbg !41
-// CHECK:STDOUT:   %tuple.elem.load = load i32, ptr %tuple.elem, align 4, !dbg !41
-// CHECK:STDOUT:   %tuple.elem1 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 0, !dbg !42
-// CHECK:STDOUT:   %tuple.elem2 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %self, i32 0, i32 1, !dbg !43
-// CHECK:STDOUT:   %tuple.elem.load3 = load i32, ptr %tuple.elem2, align 4, !dbg !43
-// CHECK:STDOUT:   %tuple.elem4 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 1, !dbg !42
-// CHECK:STDOUT:   %tuple.elem5 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %self, i32 0, i32 2, !dbg !44
-// CHECK:STDOUT:   %tuple.elem.load6 = load i32, ptr %tuple.elem5, align 4, !dbg !44
-// CHECK:STDOUT:   %tuple.elem7 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 2, !dbg !42
-// CHECK:STDOUT:   store i32 %tuple.elem.load, ptr %tuple.elem1, align 4, !dbg !42
-// CHECK:STDOUT:   store i32 %tuple.elem.load3, ptr %tuple.elem4, align 4, !dbg !42
-// CHECK:STDOUT:   store i32 %tuple.elem.load6, ptr %tuple.elem7, align 4, !dbg !42
-// CHECK:STDOUT:   ret void, !dbg !45
+// CHECK:STDOUT: define linkonce_odr void @"_COp.6d582b60b7397ec5:Copy.Core.8e95c89adba3b450"(ptr sret({ i32, i32, i32 }) %return, ptr %self) #0 !dbg !55 {
+// CHECK:STDOUT:   %tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %self, i32 0, i32 0, !dbg !59
+// CHECK:STDOUT:   %tuple.elem.load = load i32, ptr %tuple.elem, align 4, !dbg !59
+// CHECK:STDOUT:   %tuple.elem1 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 0, !dbg !60
+// CHECK:STDOUT:   %tuple.elem2 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %self, i32 0, i32 1, !dbg !61
+// CHECK:STDOUT:   %tuple.elem.load3 = load i32, ptr %tuple.elem2, align 4, !dbg !61
+// CHECK:STDOUT:   %tuple.elem4 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 1, !dbg !60
+// CHECK:STDOUT:   %tuple.elem5 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %self, i32 0, i32 2, !dbg !62
+// CHECK:STDOUT:   %tuple.elem.load6 = load i32, ptr %tuple.elem5, align 4, !dbg !62
+// CHECK:STDOUT:   %tuple.elem7 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 2, !dbg !60
+// CHECK:STDOUT:   store i32 %tuple.elem.load, ptr %tuple.elem1, align 4, !dbg !60
+// CHECK:STDOUT:   store i32 %tuple.elem.load3, ptr %tuple.elem4, align 4, !dbg !60
+// CHECK:STDOUT:   store i32 %tuple.elem.load6, ptr %tuple.elem7, align 4, !dbg !60
+// CHECK:STDOUT:   ret void, !dbg !63
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -393,43 +410,61 @@ fn AccessTuple() -> (i32, i32, i32) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "access.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "AccessBool", linkageName: "_CAccessBool.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 16, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 19, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 17, column: 10, scope: !4)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 3, scope: !4)
-// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "AccessInt", linkageName: "_CAccessInt.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !12 = !DILocation(line: 21, column: 3, scope: !11)
-// CHECK:STDOUT: !13 = !DILocation(line: 21, column: 19, scope: !11)
-// CHECK:STDOUT: !14 = !DILocation(line: 22, column: 10, scope: !11)
-// CHECK:STDOUT: !15 = !DILocation(line: 22, column: 3, scope: !11)
-// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "AccessEmpty", linkageName: "_CAccessEmpty.Main", scope: null, file: !3, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !17 = !DILocation(line: 26, column: 3, scope: !16)
-// CHECK:STDOUT: !18 = !DILocation(line: 26, column: 18, scope: !16)
-// CHECK:STDOUT: !19 = !DILocation(line: 27, column: 10, scope: !16)
-// CHECK:STDOUT: !20 = !DILocation(line: 27, column: 3, scope: !16)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "AccessTuple", linkageName: "_CAccessTuple.Main", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 31, column: 3, scope: !21)
-// CHECK:STDOUT: !23 = !DILocation(line: 31, column: 31, scope: !21)
-// CHECK:STDOUT: !24 = !DILocation(line: 31, column: 48, scope: !21)
-// CHECK:STDOUT: !25 = !DILocation(line: 32, column: 10, scope: !21)
-// CHECK:STDOUT: !26 = !DILocation(line: 32, column: 3, scope: !21)
-// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "GetBool", linkageName: "_CGetBool.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !28 = !DILocation(line: 6, column: 12, scope: !27)
-// CHECK:STDOUT: !29 = !DILocation(line: 6, column: 5, scope: !27)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "GetT", linkageName: "_CGetT.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DILocation(line: 9, column: 12, scope: !30)
-// CHECK:STDOUT: !32 = !DILocation(line: 9, column: 5, scope: !30)
-// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "GetT", linkageName: "_CGetT.C.Main.cf13cead63317d44", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !34 = !DILocation(line: 9, column: 12, scope: !33)
-// CHECK:STDOUT: !35 = !DILocation(line: 9, column: 5, scope: !33)
-// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "GetT", linkageName: "_CGetT.C.Main.623a49e5eda7ec3b", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !37 = !DILocation(line: 9, column: 12, scope: !36)
-// CHECK:STDOUT: !38 = !DILocation(line: 9, column: 5, scope: !36)
-// CHECK:STDOUT: !39 = distinct !DISubprogram(name: "Op", linkageName: "_COp.6d582b60b7397ec5:Copy.Core.8e95c89adba3b450", scope: null, file: !40, line: 54, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !40 = !DIFile(filename: "min_prelude/parts/copy.carbon", directory: "")
-// CHECK:STDOUT: !41 = !DILocation(line: 55, column: 13, scope: !39)
-// CHECK:STDOUT: !42 = !DILocation(line: 55, column: 12, scope: !39)
-// CHECK:STDOUT: !43 = !DILocation(line: 55, column: 26, scope: !39)
-// CHECK:STDOUT: !44 = !DILocation(line: 55, column: 39, scope: !39)
-// CHECK:STDOUT: !45 = !DILocation(line: 55, column: 5, scope: !39)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 16, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 19, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 10, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 3, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "AccessInt", linkageName: "_CAccessInt.Main", scope: null, file: !3, line: 20, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{!15}
+// CHECK:STDOUT: !15 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !16 = !DILocation(line: 21, column: 3, scope: !12)
+// CHECK:STDOUT: !17 = !DILocation(line: 21, column: 19, scope: !12)
+// CHECK:STDOUT: !18 = !DILocation(line: 22, column: 10, scope: !12)
+// CHECK:STDOUT: !19 = !DILocation(line: 22, column: 3, scope: !12)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "AccessEmpty", linkageName: "_CAccessEmpty.Main", scope: null, file: !3, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !21 = !DILocation(line: 26, column: 3, scope: !20)
+// CHECK:STDOUT: !22 = !DILocation(line: 26, column: 18, scope: !20)
+// CHECK:STDOUT: !23 = !DILocation(line: 27, column: 10, scope: !20)
+// CHECK:STDOUT: !24 = !DILocation(line: 27, column: 3, scope: !20)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "AccessTuple", linkageName: "_CAccessTuple.Main", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !26 = !DILocation(line: 31, column: 3, scope: !25)
+// CHECK:STDOUT: !27 = !DILocation(line: 31, column: 31, scope: !25)
+// CHECK:STDOUT: !28 = !DILocation(line: 31, column: 48, scope: !25)
+// CHECK:STDOUT: !29 = !DILocation(line: 32, column: 10, scope: !25)
+// CHECK:STDOUT: !30 = !DILocation(line: 32, column: 3, scope: !25)
+// CHECK:STDOUT: !31 = distinct !DISubprogram(name: "GetBool", linkageName: "_CGetBool.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 5, type: !32, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !34)
+// CHECK:STDOUT: !32 = !DISubroutineType(types: !33)
+// CHECK:STDOUT: !33 = !{!7, !7}
+// CHECK:STDOUT: !34 = !{!35}
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 1, scope: !31, type: !7)
+// CHECK:STDOUT: !36 = !DILocation(line: 6, column: 12, scope: !31)
+// CHECK:STDOUT: !37 = !DILocation(line: 6, column: 5, scope: !31)
+// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "GetT", linkageName: "_CGetT.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 8, type: !39, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !41)
+// CHECK:STDOUT: !39 = !DISubroutineType(types: !40)
+// CHECK:STDOUT: !40 = !{!15, !7}
+// CHECK:STDOUT: !41 = !{!42}
+// CHECK:STDOUT: !42 = !DILocalVariable(arg: 1, scope: !38, type: !7)
+// CHECK:STDOUT: !43 = !DILocation(line: 9, column: 12, scope: !38)
+// CHECK:STDOUT: !44 = !DILocation(line: 9, column: 5, scope: !38)
+// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "GetT", linkageName: "_CGetT.C.Main.cf13cead63317d44", scope: null, file: !3, line: 8, type: !32, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !46)
+// CHECK:STDOUT: !46 = !{!47}
+// CHECK:STDOUT: !47 = !DILocalVariable(arg: 1, scope: !45, type: !7)
+// CHECK:STDOUT: !48 = !DILocation(line: 9, column: 12, scope: !45)
+// CHECK:STDOUT: !49 = !DILocation(line: 9, column: 5, scope: !45)
+// CHECK:STDOUT: !50 = distinct !DISubprogram(name: "GetT", linkageName: "_CGetT.C.Main.623a49e5eda7ec3b", scope: null, file: !3, line: 8, type: !32, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !51)
+// CHECK:STDOUT: !51 = !{!52}
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 1, scope: !50, type: !7)
+// CHECK:STDOUT: !53 = !DILocation(line: 9, column: 12, scope: !50)
+// CHECK:STDOUT: !54 = !DILocation(line: 9, column: 5, scope: !50)
+// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "Op", linkageName: "_COp.6d582b60b7397ec5:Copy.Core.8e95c89adba3b450", scope: null, file: !56, line: 54, type: !32, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !57)
+// CHECK:STDOUT: !56 = !DIFile(filename: "min_prelude/parts/copy.carbon", directory: "")
+// CHECK:STDOUT: !57 = !{!58}
+// CHECK:STDOUT: !58 = !DILocalVariable(arg: 1, scope: !55, type: !7)
+// CHECK:STDOUT: !59 = !DILocation(line: 55, column: 13, scope: !55)
+// CHECK:STDOUT: !60 = !DILocation(line: 55, column: 12, scope: !55)
+// CHECK:STDOUT: !61 = !DILocation(line: 55, column: 26, scope: !55)
+// CHECK:STDOUT: !62 = !DILocation(line: 55, column: 39, scope: !55)
+// CHECK:STDOUT: !63 = !DILocation(line: 55, column: 5, scope: !55)

+ 1 - 1
toolchain/lower/testdata/class/import.carbon

@@ -62,6 +62,6 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "b.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 3, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 4, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 3, column: 1, scope: !4)

+ 11 - 8
toolchain/lower/testdata/class/method.carbon

@@ -32,9 +32,9 @@ fn F(p: C*) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main(ptr %p) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %C.Get.call = call i32 @_CGet.C.Main(ptr %p), !dbg !7
-// CHECK:STDOUT:   call void @_CSet.C.Main(ptr %p, i32 %C.Get.call), !dbg !8
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   %C.Get.call = call i32 @_CGet.C.Main(ptr %p), !dbg !10
+// CHECK:STDOUT:   call void @_CSet.C.Main(ptr %p, i32 %C.Get.call), !dbg !11
+// CHECK:STDOUT:   ret void, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -46,9 +46,12 @@ fn F(p: C*) {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "method.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 21, column: 16, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 22, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 20, column: 1, scope: !4)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 21, column: 16, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 22, column: 3, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 20, column: 1, scope: !4)

+ 22 - 14
toolchain/lower/testdata/class/self.carbon

@@ -31,17 +31,17 @@ fn C.Set[ref self: C]() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CGet.C.Main(ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc21_14.1.a = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc21_14.2 = load i32, ptr %.loc21_14.1.a, align 4, !dbg !7
-// CHECK:STDOUT:   ret i32 %.loc21_14.2, !dbg !8
+// CHECK:STDOUT:   %.loc21_14.1.a = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !11
+// CHECK:STDOUT:   %.loc21_14.2 = load i32, ptr %.loc21_14.1.a, align 4, !dbg !11
+// CHECK:STDOUT:   ret i32 %.loc21_14.2, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CSet.C.Main(ptr %self) #0 !dbg !9 {
+// CHECK:STDOUT: define void @_CSet.C.Main(ptr %self) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc25_7.a = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !10
-// CHECK:STDOUT:   store i32 1, ptr %.loc25_7.a, align 4, !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %.loc25_7.a = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !18
+// CHECK:STDOUT:   store i32 1, ptr %.loc25_7.a, align 4, !dbg !18
+// CHECK:STDOUT:   ret void, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -53,11 +53,19 @@ fn C.Set[ref self: C]() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "self.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.C.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.C.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 21, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 21, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Set", linkageName: "_CSet.C.Main", scope: null, file: !3, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 25, column: 3, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 24, column: 1, scope: !9)
+// CHECK:STDOUT: !6 = !{!7, !8}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocation(line: 21, column: 10, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 21, column: 3, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "Set", linkageName: "_CSet.C.Main", scope: null, file: !3, line: 24, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !16)
+// CHECK:STDOUT: !14 = !DISubroutineType(types: !15)
+// CHECK:STDOUT: !15 = !{null, !8}
+// CHECK:STDOUT: !16 = !{!17}
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 1, scope: !13, type: !8)
+// CHECK:STDOUT: !18 = !DILocation(line: 25, column: 3, scope: !13)
+// CHECK:STDOUT: !19 = !DILocation(line: 24, column: 1, scope: !13)

+ 25 - 21
toolchain/lower/testdata/class/value_access.carbon

@@ -27,23 +27,23 @@ fn F(c: C) -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CF.Main(ptr %c) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc21_11.1.a = getelementptr inbounds nuw { { i32, i32, i32 } }, ptr %c, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc21_11.1.a, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc21_11.2 = load i32, ptr %tuple.elem0.tuple.elem, align 4, !dbg !7
-// CHECK:STDOUT:   %tuple.elem1.loc21_11.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc21_11.1.a, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   %.loc21_11.3 = load i32, ptr %tuple.elem1.loc21_11.tuple.elem, align 4, !dbg !7
-// CHECK:STDOUT:   %tuple.elem2.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc21_11.1.a, i32 0, i32 2, !dbg !7
-// CHECK:STDOUT:   %.loc21_11.4 = load i32, ptr %tuple.elem2.tuple.elem, align 4, !dbg !7
-// CHECK:STDOUT:   %tuple = alloca { i32, i32, i32 }, align 8, !dbg !7
-// CHECK:STDOUT:   %tuple1 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   store i32 %.loc21_11.2, ptr %tuple1, align 4, !dbg !7
-// CHECK:STDOUT:   %tuple2 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   store i32 %.loc21_11.3, ptr %tuple2, align 4, !dbg !7
-// CHECK:STDOUT:   %tuple3 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 2, !dbg !7
-// CHECK:STDOUT:   store i32 %.loc21_11.4, ptr %tuple3, align 4, !dbg !7
-// CHECK:STDOUT:   %tuple.elem1.loc21_13.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 1, !dbg !7
-// CHECK:STDOUT:   %tuple.elem1.loc21_13.tuple.elem.load = load i32, ptr %tuple.elem1.loc21_13.tuple.elem, align 4, !dbg !7
-// CHECK:STDOUT:   ret i32 %tuple.elem1.loc21_13.tuple.elem.load, !dbg !8
+// CHECK:STDOUT:   %.loc21_11.1.a = getelementptr inbounds nuw { { i32, i32, i32 } }, ptr %c, i32 0, i32 0, !dbg !11
+// CHECK:STDOUT:   %tuple.elem0.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc21_11.1.a, i32 0, i32 0, !dbg !11
+// CHECK:STDOUT:   %.loc21_11.2 = load i32, ptr %tuple.elem0.tuple.elem, align 4, !dbg !11
+// CHECK:STDOUT:   %tuple.elem1.loc21_11.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc21_11.1.a, i32 0, i32 1, !dbg !11
+// CHECK:STDOUT:   %.loc21_11.3 = load i32, ptr %tuple.elem1.loc21_11.tuple.elem, align 4, !dbg !11
+// CHECK:STDOUT:   %tuple.elem2.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %.loc21_11.1.a, i32 0, i32 2, !dbg !11
+// CHECK:STDOUT:   %.loc21_11.4 = load i32, ptr %tuple.elem2.tuple.elem, align 4, !dbg !11
+// CHECK:STDOUT:   %tuple = alloca { i32, i32, i32 }, align 8, !dbg !11
+// CHECK:STDOUT:   %tuple1 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 0, !dbg !11
+// CHECK:STDOUT:   store i32 %.loc21_11.2, ptr %tuple1, align 4, !dbg !11
+// CHECK:STDOUT:   %tuple2 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 1, !dbg !11
+// CHECK:STDOUT:   store i32 %.loc21_11.3, ptr %tuple2, align 4, !dbg !11
+// CHECK:STDOUT:   %tuple3 = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 2, !dbg !11
+// CHECK:STDOUT:   store i32 %.loc21_11.4, ptr %tuple3, align 4, !dbg !11
+// CHECK:STDOUT:   %tuple.elem1.loc21_13.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %tuple, i32 0, i32 1, !dbg !11
+// CHECK:STDOUT:   %tuple.elem1.loc21_13.tuple.elem.load = load i32, ptr %tuple.elem1.loc21_13.tuple.elem, align 4, !dbg !11
+// CHECK:STDOUT:   ret i32 %tuple.elem1.loc21_13.tuple.elem.load, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -55,8 +55,12 @@ fn F(c: C) -> i32 {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "value_access.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 21, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 21, column: 3, scope: !4)
+// CHECK:STDOUT: !6 = !{!7, !8}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocation(line: 21, column: 10, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 21, column: 3, scope: !4)

+ 106 - 76
toolchain/lower/testdata/class/virtual.carbon

@@ -163,13 +163,13 @@ fn Make() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFn.Intermediate.Classes(ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CFn.Derived.Classes(ptr %self) #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CFn.Derived.Classes(ptr %self) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   ret void, !dbg !14
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -181,12 +181,17 @@ fn Make() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "classes.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.Intermediate.Classes", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.Intermediate.Classes", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 9, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.Derived.Classes", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 14, column: 3, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 9, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.Derived.Classes", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !12)
+// CHECK:STDOUT: !12 = !{!13}
+// CHECK:STDOUT: !13 = !DILocalVariable(arg: 1, scope: !11, type: !7)
+// CHECK:STDOUT: !14 = !DILocation(line: 14, column: 3, scope: !11)
 // CHECK:STDOUT: ; ModuleID = 'create.carbon'
 // CHECK:STDOUT: source_filename = "create.carbon"
 // CHECK:STDOUT:
@@ -225,10 +230,10 @@ fn Make() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CUse.Create(ptr %v) #0 !dbg !15 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Intermediate.Fn.call.vtable = load ptr, ptr %v, align 8, !dbg !16
-// CHECK:STDOUT:   %Intermediate.Fn.call = call ptr @llvm.load.relative.i32(ptr %Intermediate.Fn.call.vtable, i32 0), !dbg !16
-// CHECK:STDOUT:   call void %Intermediate.Fn.call(ptr %v), !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %Intermediate.Fn.call.vtable = load ptr, ptr %v, align 8, !dbg !21
+// CHECK:STDOUT:   %Intermediate.Fn.call = call ptr @llvm.load.relative.i32(ptr %Intermediate.Fn.call.vtable, i32 0), !dbg !21
+// CHECK:STDOUT:   call void %Intermediate.Fn.call(ptr %v), !dbg !21
+// CHECK:STDOUT:   ret void, !dbg !22
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -258,7 +263,7 @@ fn Make() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "create.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Create", linkageName: "_CCreate.Create", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 7, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 8, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 9, column: 3, scope: !4)
@@ -267,9 +272,14 @@ fn Make() {
 // CHECK:STDOUT: !12 = !DILocation(line: 9, column: 28, scope: !4)
 // CHECK:STDOUT: !13 = !DILocation(line: 9, column: 37, scope: !4)
 // CHECK:STDOUT: !14 = !DILocation(line: 6, column: 1, scope: !4)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Create", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 16, column: 3, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 15, column: 1, scope: !15)
+// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Create", scope: null, file: !3, line: 15, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !19)
+// CHECK:STDOUT: !16 = !DISubroutineType(types: !17)
+// CHECK:STDOUT: !17 = !{null, !18}
+// CHECK:STDOUT: !18 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !19 = !{!20}
+// CHECK:STDOUT: !20 = !DILocalVariable(arg: 1, scope: !15, type: !18)
+// CHECK:STDOUT: !21 = !DILocation(line: 16, column: 3, scope: !15)
+// CHECK:STDOUT: !22 = !DILocation(line: 15, column: 1, scope: !15)
 // CHECK:STDOUT: ; ModuleID = 'member_init.carbon'
 // CHECK:STDOUT: source_filename = "member_init.carbon"
 // CHECK:STDOUT:
@@ -279,30 +289,30 @@ fn Make() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFn.Base.MemberInit(ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CFn.MemberInit() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CFn.MemberInit() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %i.var = alloca i32, align 4, !dbg !9
-// CHECK:STDOUT:   %v.var = alloca { ptr, i32 }, align 8, !dbg !10
-// CHECK:STDOUT:   %u.var = alloca { ptr, i32 }, align 8, !dbg !11
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %i.var), !dbg !9
-// CHECK:STDOUT:   store i32 3, ptr %i.var, align 4, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !10
-// CHECK:STDOUT:   %.loc11_24.2.vptr = getelementptr inbounds nuw { ptr, i32 }, ptr %v.var, i32 0, i32 0, !dbg !12
-// CHECK:STDOUT:   %.loc11_23 = load i32, ptr %i.var, align 4, !dbg !13
-// CHECK:STDOUT:   %.loc11_24.4.m = getelementptr inbounds nuw { ptr, i32 }, ptr %v.var, i32 0, i32 1, !dbg !12
-// CHECK:STDOUT:   store i32 %.loc11_23, ptr %.loc11_24.4.m, align 4, !dbg !12
-// CHECK:STDOUT:   store ptr @"_CBase.MemberInit.$vtable", ptr %.loc11_24.2.vptr, align 8, !dbg !12
-// CHECK:STDOUT:   %.loc12_4.m = getelementptr inbounds nuw { ptr, i32 }, ptr %v.var, i32 0, i32 1, !dbg !14
-// CHECK:STDOUT:   store i32 5, ptr %.loc12_4.m, align 4, !dbg !14
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %u.var), !dbg !11
-// CHECK:STDOUT:   %.loc13_24.2.vptr = getelementptr inbounds nuw { ptr, i32 }, ptr %u.var, i32 0, i32 0, !dbg !15
-// CHECK:STDOUT:   %.loc13_24.5.m = getelementptr inbounds nuw { ptr, i32 }, ptr %u.var, i32 0, i32 1, !dbg !15
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 8 %u.var, ptr align 8 @Base.val.loc13_3, i64 16, i1 false), !dbg !11
-// CHECK:STDOUT:   ret void, !dbg !16
+// CHECK:STDOUT:   %i.var = alloca i32, align 4, !dbg !14
+// CHECK:STDOUT:   %v.var = alloca { ptr, i32 }, align 8, !dbg !15
+// CHECK:STDOUT:   %u.var = alloca { ptr, i32 }, align 8, !dbg !16
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %i.var), !dbg !14
+// CHECK:STDOUT:   store i32 3, ptr %i.var, align 4, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !15
+// CHECK:STDOUT:   %.loc11_24.2.vptr = getelementptr inbounds nuw { ptr, i32 }, ptr %v.var, i32 0, i32 0, !dbg !17
+// CHECK:STDOUT:   %.loc11_23 = load i32, ptr %i.var, align 4, !dbg !18
+// CHECK:STDOUT:   %.loc11_24.4.m = getelementptr inbounds nuw { ptr, i32 }, ptr %v.var, i32 0, i32 1, !dbg !17
+// CHECK:STDOUT:   store i32 %.loc11_23, ptr %.loc11_24.4.m, align 4, !dbg !17
+// CHECK:STDOUT:   store ptr @"_CBase.MemberInit.$vtable", ptr %.loc11_24.2.vptr, align 8, !dbg !17
+// CHECK:STDOUT:   %.loc12_4.m = getelementptr inbounds nuw { ptr, i32 }, ptr %v.var, i32 0, i32 1, !dbg !19
+// CHECK:STDOUT:   store i32 5, ptr %.loc12_4.m, align 4, !dbg !19
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %u.var), !dbg !16
+// CHECK:STDOUT:   %.loc13_24.2.vptr = getelementptr inbounds nuw { ptr, i32 }, ptr %u.var, i32 0, i32 0, !dbg !20
+// CHECK:STDOUT:   %.loc13_24.5.m = getelementptr inbounds nuw { ptr, i32 }, ptr %u.var, i32 0, i32 1, !dbg !20
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 8 %u.var, ptr align 8 @Base.val.loc13_3, i64 16, i1 false), !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !21
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -325,19 +335,24 @@ fn Make() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "member_init.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.Base.MemberInit", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.Base.MemberInit", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 6, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.MemberInit", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 10, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 11, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 3, scope: !8)
-// CHECK:STDOUT: !12 = !DILocation(line: 11, column: 17, scope: !8)
-// CHECK:STDOUT: !13 = !DILocation(line: 11, column: 23, scope: !8)
-// CHECK:STDOUT: !14 = !DILocation(line: 12, column: 3, scope: !8)
-// CHECK:STDOUT: !15 = !DILocation(line: 13, column: 17, scope: !8)
-// CHECK:STDOUT: !16 = !DILocation(line: 9, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 6, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Fn", linkageName: "_CFn.MemberInit", scope: null, file: !3, line: 9, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 10, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 11, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 13, column: 3, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 11, column: 17, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 11, column: 23, scope: !11)
+// CHECK:STDOUT: !19 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !20 = !DILocation(line: 13, column: 17, scope: !11)
+// CHECK:STDOUT: !21 = !DILocation(line: 9, column: 1, scope: !11)
 // CHECK:STDOUT: ; ModuleID = 'member_brace_init.carbon'
 // CHECK:STDOUT: source_filename = "member_brace_init.carbon"
 // CHECK:STDOUT:
@@ -377,7 +392,7 @@ fn Make() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "member_brace_init.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Main", scope: null, file: !3, line: 12, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 13, column: 21, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 13, column: 30, scope: !4)
@@ -392,10 +407,10 @@ fn Make() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CUse.Main(ptr %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Base.F.call.vtable = load ptr, ptr %b, align 8, !dbg !7
-// CHECK:STDOUT:   %Base.F.call = call ptr @llvm.load.relative.i32(ptr %Base.F.call.vtable, i32 0), !dbg !7
-// CHECK:STDOUT:   call void %Base.F.call(ptr %b), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !8
+// CHECK:STDOUT:   %Base.F.call.vtable = load ptr, ptr %b, align 8, !dbg !10
+// CHECK:STDOUT:   %Base.F.call = call ptr @llvm.load.relative.i32(ptr %Base.F.call.vtable, i32 0), !dbg !10
+// CHECK:STDOUT:   call void %Base.F.call(ptr %b), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: read)
@@ -411,11 +426,14 @@ fn Make() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "call.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 9, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 8, column: 1, scope: !4)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 9, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 8, column: 1, scope: !4)
 // CHECK:STDOUT: ; ModuleID = 'call_impl.carbon'
 // CHECK:STDOUT: source_filename = "call_impl.carbon"
 // CHECK:STDOUT:
@@ -464,7 +482,7 @@ fn Make() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_impl.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Use", linkageName: "_CUse.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 14, column: 21, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 14, column: 30, scope: !4)
@@ -505,17 +523,17 @@ fn Make() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_CF.Base.Main.b29a32b2b49cc0f3(ptr %self) #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca {}, align 8, !dbg !13
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !13
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   %v.var = alloca {}, align 8, !dbg !18
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !18
+// CHECK:STDOUT:   ret void, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Base.Main.aa6c84e7fdd60e03(ptr %self) #0 !dbg !15 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Base.Main.aa6c84e7fdd60e03(ptr %self) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca { {} }, align 8, !dbg !16
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %v.var = alloca { {} }, align 8, !dbg !23
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !23
+// CHECK:STDOUT:   ret void, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -541,18 +559,25 @@ fn Make() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "generic_use.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 16, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 17, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 16, column: 22, scope: !4)
 // CHECK:STDOUT: !10 = !DILocation(line: 17, column: 22, scope: !4)
 // CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !4)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "F", linkageName: "_CF.Base.Main.b29a32b2b49cc0f3", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 6, column: 5, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 5, column: 3, scope: !12)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "F", linkageName: "_CF.Base.Main.aa6c84e7fdd60e03", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 6, column: 5, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 5, column: 3, scope: !15)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "F", linkageName: "_CF.Base.Main.b29a32b2b49cc0f3", scope: null, file: !3, line: 5, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !16)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null, !15}
+// CHECK:STDOUT: !15 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !16 = !{!17}
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 1, scope: !12, type: !15)
+// CHECK:STDOUT: !18 = !DILocation(line: 6, column: 5, scope: !12)
+// CHECK:STDOUT: !19 = !DILocation(line: 5, column: 3, scope: !12)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "F", linkageName: "_CF.Base.Main.aa6c84e7fdd60e03", scope: null, file: !3, line: 5, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !21)
+// CHECK:STDOUT: !21 = !{!22}
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 1, scope: !20, type: !15)
+// CHECK:STDOUT: !23 = !DILocation(line: 6, column: 5, scope: !20)
+// CHECK:STDOUT: !24 = !DILocation(line: 5, column: 3, scope: !20)
 // CHECK:STDOUT: ; ModuleID = 'generic_base.carbon'
 // CHECK:STDOUT: source_filename = "generic_base.carbon"
 // CHECK:STDOUT:
@@ -569,7 +594,7 @@ fn Make() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_CF.Base.Main.4d2ffa01ebfb7a1d(ptr %self) #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -587,8 +612,13 @@ fn Make() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "generic_base.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Make", linkageName: "_CMake.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 15, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 14, column: 1, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "F", linkageName: "_CF.Base.Main.4d2ffa01ebfb7a1d", scope: null, file: !3, line: 5, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 5, column: 3, scope: !9)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "F", linkageName: "_CF.Base.Main.4d2ffa01ebfb7a1d", scope: null, file: !3, line: 5, type: !10, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !13)
+// CHECK:STDOUT: !10 = !DISubroutineType(types: !11)
+// CHECK:STDOUT: !11 = !{null, !12}
+// CHECK:STDOUT: !12 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !13 = !{!14}
+// CHECK:STDOUT: !14 = !DILocalVariable(arg: 1, scope: !9, type: !12)
+// CHECK:STDOUT: !15 = !DILocation(line: 5, column: 3, scope: !9)

+ 89 - 67
toolchain/lower/testdata/for/bindings.carbon

@@ -83,67 +83,67 @@ fn For() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @"_CNewCursor.EmptyRange.Main:Iterate.Core.a862d5c8b748242e"(ptr %self) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   ret void, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNext.EmptyRange.Main:Iterate.Core.a862d5c8b748242e"(ptr sret({ { i32, i32 }, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !15 {
+// CHECK:STDOUT: define linkonce_odr void @"_CNext.EmptyRange.Main:Iterate.Core.a862d5c8b748242e"(ptr sret({ { i32, i32 }, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CNone.Optional.Core.5497e08686bb6191(ptr %return), !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   call void @_CNone.Optional.Core.5497e08686bb6191(ptr %return), !dbg !26
+// CHECK:STDOUT:   ret void, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.5497e08686bb6191(ptr %self) #0 !dbg !18 {
-// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %self), !dbg !20
-// CHECK:STDOUT:   ret i1 %1, !dbg !21
+// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.5497e08686bb6191(ptr %self) #0 !dbg !28 {
+// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %self), !dbg !32
+// CHECK:STDOUT:   ret i1 %1, !dbg !33
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CGet.Optional.Core.5497e08686bb6191(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !22 {
-// CHECK:STDOUT:   call void @"_CGet.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %return, ptr %self), !dbg !23
-// CHECK:STDOUT:   ret void, !dbg !24
+// CHECK:STDOUT: define linkonce_odr void @_CGet.Optional.Core.5497e08686bb6191(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !34 {
+// CHECK:STDOUT:   call void @"_CGet.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %return, ptr %self), !dbg !37
+// CHECK:STDOUT:   ret void, !dbg !38
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.5497e08686bb6191(ptr sret({ { i32, i32 }, i1 }) %return) #0 !dbg !25 {
-// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %return), !dbg !26
-// CHECK:STDOUT:   ret void, !dbg !27
+// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.5497e08686bb6191(ptr sret({ { i32, i32 }, i1 }) %return) #0 !dbg !39 {
+// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %return), !dbg !42
+// CHECK:STDOUT:   ret void, !dbg !43
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %value) #0 !dbg !28 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { { i32, i32 }, i1 }, ptr %value, i32 0, i32 1, !dbg !29
-// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !29
-// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !29
-// CHECK:STDOUT:   ret i1 %2, !dbg !30
+// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr %value) #0 !dbg !44 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { { i32, i32 }, i1 }, ptr %value, i32 0, i32 1, !dbg !47
+// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !47
+// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !47
+// CHECK:STDOUT:   ret i1 %2, !dbg !48
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CGet.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr sret({ i32, i32 }) %return, ptr %value) #0 !dbg !31 {
-// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { { i32, i32 }, i1 }, ptr %value, i32 0, i32 0, !dbg !32
-// CHECK:STDOUT:   call void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr %return, ptr %value1), !dbg !32
-// CHECK:STDOUT:   ret void, !dbg !33
+// CHECK:STDOUT: define linkonce_odr void @"_CGet.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr sret({ i32, i32 }) %return, ptr %value) #0 !dbg !49 {
+// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { { i32, i32 }, i1 }, ptr %value, i32 0, i32 0, !dbg !52
+// CHECK:STDOUT:   call void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr %return, ptr %value1), !dbg !52
+// CHECK:STDOUT:   ret void, !dbg !53
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr sret({ { i32, i32 }, i1 }) %return) #0 !dbg !34 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { { i32, i32 }, i1 }, ptr %return, i32 0, i32 1, !dbg !35
-// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !35
-// CHECK:STDOUT:   ret void, !dbg !36
+// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e"(ptr sret({ { i32, i32 }, i1 }) %return) #0 !dbg !54 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { { i32, i32 }, i1 }, ptr %return, i32 0, i32 1, !dbg !55
+// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !55
+// CHECK:STDOUT:   ret void, !dbg !56
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !37 {
-// CHECK:STDOUT:   %tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !39
-// CHECK:STDOUT:   %tuple.elem.load = load i32, ptr %tuple.elem, align 4, !dbg !39
-// CHECK:STDOUT:   %tuple.elem1 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !40
-// CHECK:STDOUT:   %tuple.elem2 = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !41
-// CHECK:STDOUT:   %tuple.elem.load3 = load i32, ptr %tuple.elem2, align 4, !dbg !41
-// CHECK:STDOUT:   %tuple.elem4 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !40
-// CHECK:STDOUT:   store i32 %tuple.elem.load, ptr %tuple.elem1, align 4, !dbg !40
-// CHECK:STDOUT:   store i32 %tuple.elem.load3, ptr %tuple.elem4, align 4, !dbg !40
-// CHECK:STDOUT:   ret void, !dbg !42
+// CHECK:STDOUT: define linkonce_odr void @"_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !57 {
+// CHECK:STDOUT:   %tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !61
+// CHECK:STDOUT:   %tuple.elem.load = load i32, ptr %tuple.elem, align 4, !dbg !61
+// CHECK:STDOUT:   %tuple.elem1 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !62
+// CHECK:STDOUT:   %tuple.elem2 = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !63
+// CHECK:STDOUT:   %tuple.elem.load3 = load i32, ptr %tuple.elem2, align 4, !dbg !63
+// CHECK:STDOUT:   %tuple.elem4 = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !62
+// CHECK:STDOUT:   store i32 %tuple.elem.load, ptr %tuple.elem1, align 4, !dbg !62
+// CHECK:STDOUT:   store i32 %tuple.elem.load3, ptr %tuple.elem4, align 4, !dbg !62
+// CHECK:STDOUT:   ret void, !dbg !64
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -162,40 +162,62 @@ fn For() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "bindings.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "For", linkageName: "_CFor.Main", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 27, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 29, column: 7, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 29, column: 17, scope: !4)
 // CHECK:STDOUT: !10 = !DILocation(line: 30, column: 5, scope: !4)
 // CHECK:STDOUT: !11 = !DILocation(line: 29, column: 3, scope: !4)
 // CHECK:STDOUT: !12 = !DILocation(line: 26, column: 1, scope: !4)
-// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.EmptyRange.Main:Iterate.Core.a862d5c8b748242e", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !14 = !DILocation(line: 16, column: 7, scope: !13)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.EmptyRange.Main:Iterate.Core.a862d5c8b748242e", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 19, column: 14, scope: !15)
-// CHECK:STDOUT: !17 = !DILocation(line: 19, column: 7, scope: !15)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.5497e08686bb6191", scope: null, file: !19, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
-// CHECK:STDOUT: !20 = !DILocation(line: 33, column: 12, scope: !18)
-// CHECK:STDOUT: !21 = !DILocation(line: 33, column: 5, scope: !18)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.5497e08686bb6191", scope: null, file: !19, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = !DILocation(line: 36, column: 12, scope: !22)
-// CHECK:STDOUT: !24 = !DILocation(line: 36, column: 5, scope: !22)
-// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.5497e08686bb6191", scope: null, file: !19, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !26 = !DILocation(line: 27, column: 12, scope: !25)
-// CHECK:STDOUT: !27 = !DILocation(line: 27, column: 5, scope: !25)
-// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e", scope: null, file: !19, line: 112, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !29 = !DILocation(line: 113, column: 12, scope: !28)
-// CHECK:STDOUT: !30 = !DILocation(line: 113, column: 5, scope: !28)
-// CHECK:STDOUT: !31 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e", scope: null, file: !19, line: 115, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !32 = !DILocation(line: 116, column: 12, scope: !31)
-// CHECK:STDOUT: !33 = !DILocation(line: 116, column: 5, scope: !31)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e", scope: null, file: !19, line: 99, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DILocation(line: 101, column: 5, scope: !34)
-// CHECK:STDOUT: !36 = !DILocation(line: 102, column: 5, scope: !34)
-// CHECK:STDOUT: !37 = distinct !DISubprogram(name: "Op", linkageName: "_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1", scope: null, file: !38, line: 58, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !38 = !DIFile(filename: "{{.*}}/prelude/copy.carbon", directory: "")
-// CHECK:STDOUT: !39 = !DILocation(line: 59, column: 13, scope: !37)
-// CHECK:STDOUT: !40 = !DILocation(line: 59, column: 12, scope: !37)
-// CHECK:STDOUT: !41 = !DILocation(line: 59, column: 26, scope: !37)
-// CHECK:STDOUT: !42 = !DILocation(line: 59, column: 5, scope: !37)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.EmptyRange.Main:Iterate.Core.a862d5c8b748242e", scope: null, file: !3, line: 15, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !17)
+// CHECK:STDOUT: !14 = !DISubroutineType(types: !15)
+// CHECK:STDOUT: !15 = !{!16, !16}
+// CHECK:STDOUT: !16 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !17 = !{!18}
+// CHECK:STDOUT: !18 = !DILocalVariable(arg: 1, scope: !13, type: !16)
+// CHECK:STDOUT: !19 = !DILocation(line: 16, column: 7, scope: !13)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.EmptyRange.Main:Iterate.Core.a862d5c8b748242e", scope: null, file: !3, line: 18, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !23)
+// CHECK:STDOUT: !21 = !DISubroutineType(types: !22)
+// CHECK:STDOUT: !22 = !{!16, !16, !16}
+// CHECK:STDOUT: !23 = !{!24, !25}
+// CHECK:STDOUT: !24 = !DILocalVariable(arg: 1, scope: !20, type: !16)
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 2, scope: !20, type: !16)
+// CHECK:STDOUT: !26 = !DILocation(line: 19, column: 14, scope: !20)
+// CHECK:STDOUT: !27 = !DILocation(line: 19, column: 7, scope: !20)
+// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.5497e08686bb6191", scope: null, file: !29, line: 32, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !30)
+// CHECK:STDOUT: !29 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
+// CHECK:STDOUT: !30 = !{!31}
+// CHECK:STDOUT: !31 = !DILocalVariable(arg: 1, scope: !28, type: !16)
+// CHECK:STDOUT: !32 = !DILocation(line: 33, column: 12, scope: !28)
+// CHECK:STDOUT: !33 = !DILocation(line: 33, column: 5, scope: !28)
+// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.5497e08686bb6191", scope: null, file: !29, line: 35, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !35)
+// CHECK:STDOUT: !35 = !{!36}
+// CHECK:STDOUT: !36 = !DILocalVariable(arg: 1, scope: !34, type: !16)
+// CHECK:STDOUT: !37 = !DILocation(line: 36, column: 12, scope: !34)
+// CHECK:STDOUT: !38 = !DILocation(line: 36, column: 5, scope: !34)
+// CHECK:STDOUT: !39 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.5497e08686bb6191", scope: null, file: !29, line: 26, type: !40, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !40 = !DISubroutineType(types: !41)
+// CHECK:STDOUT: !41 = !{!16}
+// CHECK:STDOUT: !42 = !DILocation(line: 27, column: 12, scope: !39)
+// CHECK:STDOUT: !43 = !DILocation(line: 27, column: 5, scope: !39)
+// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e", scope: null, file: !29, line: 112, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !45)
+// CHECK:STDOUT: !45 = !{!46}
+// CHECK:STDOUT: !46 = !DILocalVariable(arg: 1, scope: !44, type: !16)
+// CHECK:STDOUT: !47 = !DILocation(line: 113, column: 12, scope: !44)
+// CHECK:STDOUT: !48 = !DILocation(line: 113, column: 5, scope: !44)
+// CHECK:STDOUT: !49 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e", scope: null, file: !29, line: 115, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !50)
+// CHECK:STDOUT: !50 = !{!51}
+// CHECK:STDOUT: !51 = !DILocalVariable(arg: 1, scope: !49, type: !16)
+// CHECK:STDOUT: !52 = !DILocation(line: 116, column: 12, scope: !49)
+// CHECK:STDOUT: !53 = !DILocation(line: 116, column: 5, scope: !49)
+// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.a862d5c8b748242e", scope: null, file: !29, line: 99, type: !40, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !55 = !DILocation(line: 101, column: 5, scope: !54)
+// CHECK:STDOUT: !56 = !DILocation(line: 102, column: 5, scope: !54)
+// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "Op", linkageName: "_COp.2b3ba83e01542f11:Copy.Core.4193728889277ad1", scope: null, file: !58, line: 58, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !59)
+// CHECK:STDOUT: !58 = !DIFile(filename: "{{.*}}/prelude/copy.carbon", directory: "")
+// CHECK:STDOUT: !59 = !{!60}
+// CHECK:STDOUT: !60 = !DILocalVariable(arg: 1, scope: !57, type: !16)
+// CHECK:STDOUT: !61 = !DILocation(line: 59, column: 13, scope: !57)
+// CHECK:STDOUT: !62 = !DILocation(line: 59, column: 12, scope: !57)
+// CHECK:STDOUT: !63 = !DILocation(line: 59, column: 26, scope: !57)
+// CHECK:STDOUT: !64 = !DILocation(line: 59, column: 5, scope: !57)

+ 155 - 113
toolchain/lower/testdata/for/break_continue.carbon

@@ -82,109 +82,109 @@ fn For() {
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @"_CNewCursor.IntRange.Core:Iterate.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !18 {
-// CHECK:STDOUT:   %start = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !20
-// CHECK:STDOUT:   %1 = load i32, ptr %start, align 4, !dbg !20
-// CHECK:STDOUT:   ret i32 %1, !dbg !21
+// CHECK:STDOUT:   %start = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !26
+// CHECK:STDOUT:   %1 = load i32, ptr %start, align 4, !dbg !26
+// CHECK:STDOUT:   ret i32 %1, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8"(ptr sret({ i32, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !22 {
-// CHECK:STDOUT:   %1 = alloca i32, align 4, !dbg !23
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %1), !dbg !23
-// CHECK:STDOUT:   %2 = load i32, ptr %cursor, align 4, !dbg !24
-// CHECK:STDOUT:   store i32 %2, ptr %1, align 4, !dbg !23
-// CHECK:STDOUT:   %end = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !25
-// CHECK:STDOUT:   %3 = load i32, ptr %end, align 4, !dbg !25
-// CHECK:STDOUT:   %4 = load i32, ptr %1, align 4, !dbg !26
-// CHECK:STDOUT:   %5 = icmp slt i32 %4, %3, !dbg !26
-// CHECK:STDOUT:   br i1 %5, label %6, label %8, !dbg !27
+// CHECK:STDOUT: define linkonce_odr void @"_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8"(ptr sret({ i32, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !28 {
+// CHECK:STDOUT:   %1 = alloca i32, align 4, !dbg !34
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %1), !dbg !34
+// CHECK:STDOUT:   %2 = load i32, ptr %cursor, align 4, !dbg !35
+// CHECK:STDOUT:   store i32 %2, ptr %1, align 4, !dbg !34
+// CHECK:STDOUT:   %end = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !36
+// CHECK:STDOUT:   %3 = load i32, ptr %end, align 4, !dbg !36
+// CHECK:STDOUT:   %4 = load i32, ptr %1, align 4, !dbg !37
+// CHECK:STDOUT:   %5 = icmp slt i32 %4, %3, !dbg !37
+// CHECK:STDOUT:   br i1 %5, label %6, label %8, !dbg !38
 // CHECK:STDOUT:
 // CHECK:STDOUT: 6:                                                ; preds = %0
-// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %cursor), !dbg !28
-// CHECK:STDOUT:   %7 = load i32, ptr %1, align 4, !dbg !29
-// CHECK:STDOUT:   call void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr %return, i32 %7), !dbg !30
-// CHECK:STDOUT:   ret void, !dbg !31
+// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %cursor), !dbg !39
+// CHECK:STDOUT:   %7 = load i32, ptr %1, align 4, !dbg !40
+// CHECK:STDOUT:   call void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr %return, i32 %7), !dbg !41
+// CHECK:STDOUT:   ret void, !dbg !42
 // CHECK:STDOUT:
 // CHECK:STDOUT: 8:                                                ; preds = %0
-// CHECK:STDOUT:   call void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr %return), !dbg !32
-// CHECK:STDOUT:   ret void, !dbg !33
+// CHECK:STDOUT:   call void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr %return), !dbg !43
+// CHECK:STDOUT:   ret void, !dbg !44
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !34 {
-// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !36
-// CHECK:STDOUT:   ret i1 %1, !dbg !37
+// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !45 {
+// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !51
+// CHECK:STDOUT:   ret i1 %1, !dbg !52
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CGet.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !38 {
-// CHECK:STDOUT:   %1 = call i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !39
-// CHECK:STDOUT:   ret i32 %1, !dbg !40
+// CHECK:STDOUT: define linkonce_odr i32 @_CGet.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !53 {
+// CHECK:STDOUT:   %1 = call i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !56
+// CHECK:STDOUT:   ret i32 %1, !dbg !57
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CInclusiveRange.Core(ptr sret({ i32, i32 }), i32, i32)
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !41 {
-// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 1), !dbg !43
-// CHECK:STDOUT:   ret void, !dbg !44
+// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !58 {
+// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 1), !dbg !64
+// CHECK:STDOUT:   ret void, !dbg !65
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return, i32 %value) #0 !dbg !45 {
-// CHECK:STDOUT:   call void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return, i32 %value), !dbg !46
-// CHECK:STDOUT:   ret void, !dbg !47
+// CHECK:STDOUT: define linkonce_odr void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return, i32 %value) #0 !dbg !66 {
+// CHECK:STDOUT:   call void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return, i32 %value), !dbg !71
+// CHECK:STDOUT:   ret void, !dbg !72
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return) #0 !dbg !48 {
-// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return), !dbg !49
-// CHECK:STDOUT:   ret void, !dbg !50
+// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return) #0 !dbg !73 {
+// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return), !dbg !76
+// CHECK:STDOUT:   ret void, !dbg !77
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !51 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 1, !dbg !52
-// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !52
-// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !52
-// CHECK:STDOUT:   ret i1 %2, !dbg !53
+// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !78 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 1, !dbg !81
+// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !81
+// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !81
+// CHECK:STDOUT:   ret i1 %2, !dbg !82
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !54 {
-// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 0, !dbg !55
-// CHECK:STDOUT:   %1 = load i32, ptr %value1, align 4, !dbg !55
-// CHECK:STDOUT:   ret i32 %1, !dbg !56
+// CHECK:STDOUT: define linkonce_odr i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !83 {
+// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 0, !dbg !86
+// CHECK:STDOUT:   %1 = load i32, ptr %value1, align 4, !dbg !86
+// CHECK:STDOUT:   ret i32 %1, !dbg !87
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: alwaysinline nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 %other) #2 !dbg !57 {
-// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %other), !dbg !58
-// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !59
-// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !59
-// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !59
-// CHECK:STDOUT:   ret void, !dbg !59
+// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 %other) #2 !dbg !88 {
+// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %other), !dbg !94
+// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !95
+// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !95
+// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !95
+// CHECK:STDOUT:   ret void, !dbg !95
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return, i32 %self) #0 !dbg !60 {
-// CHECK:STDOUT:   %value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 0, !dbg !61
-// CHECK:STDOUT:   store i32 %self, ptr %value, align 4, !dbg !61
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !62
-// CHECK:STDOUT:   store i8 1, ptr %has_value, align 1, !dbg !62
-// CHECK:STDOUT:   ret void, !dbg !63
+// CHECK:STDOUT: define linkonce_odr void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return, i32 %self) #0 !dbg !96 {
+// CHECK:STDOUT:   %value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 0, !dbg !99
+// CHECK:STDOUT:   store i32 %self, ptr %value, align 4, !dbg !99
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !100
+// CHECK:STDOUT:   store i8 1, ptr %has_value, align 1, !dbg !100
+// CHECK:STDOUT:   ret void, !dbg !101
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return) #0 !dbg !64 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !65
-// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !65
-// CHECK:STDOUT:   ret void, !dbg !66
+// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return) #0 !dbg !102 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !103
+// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !103
+// CHECK:STDOUT:   ret void, !dbg !104
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %self) #0 !dbg !67 {
-// CHECK:STDOUT:   ret i32 %self, !dbg !69
+// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %self) #0 !dbg !105 {
+// CHECK:STDOUT:   ret i32 %self, !dbg !111
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -203,7 +203,7 @@ fn For() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "break_continue.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "For", linkageName: "_CFor.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 20, column: 18, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 20, column: 7, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 21, column: 9, scope: !4)
@@ -215,55 +215,97 @@ fn For() {
 // CHECK:STDOUT: !15 = !DILocation(line: 23, column: 5, scope: !4)
 // CHECK:STDOUT: !16 = !DILocation(line: 20, column: 3, scope: !4)
 // CHECK:STDOUT: !17 = !DILocation(line: 19, column: 1, scope: !4)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !19, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !19, line: 25, type: !20, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
 // CHECK:STDOUT: !19 = !DIFile(filename: "{{.*}}/range.carbon", directory: "")
-// CHECK:STDOUT: !20 = !DILocation(line: 25, column: 51, scope: !18)
-// CHECK:STDOUT: !21 = !DILocation(line: 25, column: 44, scope: !18)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !19, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = !DILocation(line: 27, column: 7, scope: !22)
-// CHECK:STDOUT: !24 = !DILocation(line: 27, column: 27, scope: !22)
-// CHECK:STDOUT: !25 = !DILocation(line: 28, column: 19, scope: !22)
-// CHECK:STDOUT: !26 = !DILocation(line: 28, column: 11, scope: !22)
-// CHECK:STDOUT: !27 = !DILocation(line: 28, column: 10, scope: !22)
-// CHECK:STDOUT: !28 = !DILocation(line: 29, column: 9, scope: !22)
-// CHECK:STDOUT: !29 = !DILocation(line: 30, column: 38, scope: !22)
-// CHECK:STDOUT: !30 = !DILocation(line: 30, column: 16, scope: !22)
-// CHECK:STDOUT: !31 = !DILocation(line: 30, column: 9, scope: !22)
-// CHECK:STDOUT: !32 = !DILocation(line: 32, column: 16, scope: !22)
-// CHECK:STDOUT: !33 = !DILocation(line: 32, column: 9, scope: !22)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !35, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
-// CHECK:STDOUT: !36 = !DILocation(line: 33, column: 12, scope: !34)
-// CHECK:STDOUT: !37 = !DILocation(line: 33, column: 5, scope: !34)
-// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !35, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !39 = !DILocation(line: 36, column: 12, scope: !38)
-// CHECK:STDOUT: !40 = !DILocation(line: 36, column: 5, scope: !38)
-// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !42, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !42 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !43 = !DILocation(line: 341, column: 5, scope: !41)
-// CHECK:STDOUT: !44 = !DILocation(line: 339, column: 3, scope: !41)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !35, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 30, column: 12, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 30, column: 5, scope: !45)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !35, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 27, column: 12, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 27, column: 5, scope: !48)
-// CHECK:STDOUT: !51 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !35, line: 112, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !52 = !DILocation(line: 113, column: 12, scope: !51)
-// CHECK:STDOUT: !53 = !DILocation(line: 113, column: 5, scope: !51)
-// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !35, line: 115, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !55 = !DILocation(line: 116, column: 12, scope: !54)
-// CHECK:STDOUT: !56 = !DILocation(line: 116, column: 5, scope: !54)
-// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a", scope: null, file: !42, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !58 = !DILocation(line: 4294967295, scope: !57)
-// CHECK:STDOUT: !59 = !DILocation(line: 275, column: 3, scope: !57)
-// CHECK:STDOUT: !60 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !35, line: 104, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !61 = !DILocation(line: 108, column: 5, scope: !60)
-// CHECK:STDOUT: !62 = !DILocation(line: 109, column: 5, scope: !60)
-// CHECK:STDOUT: !63 = !DILocation(line: 110, column: 5, scope: !60)
-// CHECK:STDOUT: !64 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !35, line: 99, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !65 = !DILocation(line: 101, column: 5, scope: !64)
-// CHECK:STDOUT: !66 = !DILocation(line: 102, column: 5, scope: !64)
-// CHECK:STDOUT: !67 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9", scope: null, file: !68, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !68 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
-// CHECK:STDOUT: !69 = !DILocation(line: 24, column: 38, scope: !67)
+// CHECK:STDOUT: !20 = !DISubroutineType(types: !21)
+// CHECK:STDOUT: !21 = !{!22, !23}
+// CHECK:STDOUT: !22 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !23 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !24 = !{!25}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !18, type: !23)
+// CHECK:STDOUT: !26 = !DILocation(line: 25, column: 51, scope: !18)
+// CHECK:STDOUT: !27 = !DILocation(line: 25, column: 44, scope: !18)
+// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !19, line: 26, type: !29, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !31)
+// CHECK:STDOUT: !29 = !DISubroutineType(types: !30)
+// CHECK:STDOUT: !30 = !{!23, !23, !23}
+// CHECK:STDOUT: !31 = !{!32, !33}
+// CHECK:STDOUT: !32 = !DILocalVariable(arg: 1, scope: !28, type: !23)
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 2, scope: !28, type: !23)
+// CHECK:STDOUT: !34 = !DILocation(line: 27, column: 7, scope: !28)
+// CHECK:STDOUT: !35 = !DILocation(line: 27, column: 27, scope: !28)
+// CHECK:STDOUT: !36 = !DILocation(line: 28, column: 19, scope: !28)
+// CHECK:STDOUT: !37 = !DILocation(line: 28, column: 11, scope: !28)
+// CHECK:STDOUT: !38 = !DILocation(line: 28, column: 10, scope: !28)
+// CHECK:STDOUT: !39 = !DILocation(line: 29, column: 9, scope: !28)
+// CHECK:STDOUT: !40 = !DILocation(line: 30, column: 38, scope: !28)
+// CHECK:STDOUT: !41 = !DILocation(line: 30, column: 16, scope: !28)
+// CHECK:STDOUT: !42 = !DILocation(line: 30, column: 9, scope: !28)
+// CHECK:STDOUT: !43 = !DILocation(line: 32, column: 16, scope: !28)
+// CHECK:STDOUT: !44 = !DILocation(line: 32, column: 9, scope: !28)
+// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !46, line: 32, type: !47, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !49)
+// CHECK:STDOUT: !46 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
+// CHECK:STDOUT: !47 = !DISubroutineType(types: !48)
+// CHECK:STDOUT: !48 = !{!23, !23}
+// CHECK:STDOUT: !49 = !{!50}
+// CHECK:STDOUT: !50 = !DILocalVariable(arg: 1, scope: !45, type: !23)
+// CHECK:STDOUT: !51 = !DILocation(line: 33, column: 12, scope: !45)
+// CHECK:STDOUT: !52 = !DILocation(line: 33, column: 5, scope: !45)
+// CHECK:STDOUT: !53 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !46, line: 35, type: !20, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !54)
+// CHECK:STDOUT: !54 = !{!55}
+// CHECK:STDOUT: !55 = !DILocalVariable(arg: 1, scope: !53, type: !23)
+// CHECK:STDOUT: !56 = !DILocation(line: 36, column: 12, scope: !53)
+// CHECK:STDOUT: !57 = !DILocation(line: 36, column: 5, scope: !53)
+// CHECK:STDOUT: !58 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !59, line: 339, type: !60, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !62)
+// CHECK:STDOUT: !59 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !60 = !DISubroutineType(types: !61)
+// CHECK:STDOUT: !61 = !{null, !22}
+// CHECK:STDOUT: !62 = !{!63}
+// CHECK:STDOUT: !63 = !DILocalVariable(arg: 1, scope: !58, type: !22)
+// CHECK:STDOUT: !64 = !DILocation(line: 341, column: 5, scope: !58)
+// CHECK:STDOUT: !65 = !DILocation(line: 339, column: 3, scope: !58)
+// CHECK:STDOUT: !66 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !46, line: 29, type: !67, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !69)
+// CHECK:STDOUT: !67 = !DISubroutineType(types: !68)
+// CHECK:STDOUT: !68 = !{!23, !22}
+// CHECK:STDOUT: !69 = !{!70}
+// CHECK:STDOUT: !70 = !DILocalVariable(arg: 1, scope: !66, type: !22)
+// CHECK:STDOUT: !71 = !DILocation(line: 30, column: 12, scope: !66)
+// CHECK:STDOUT: !72 = !DILocation(line: 30, column: 5, scope: !66)
+// CHECK:STDOUT: !73 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !46, line: 26, type: !74, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !74 = !DISubroutineType(types: !75)
+// CHECK:STDOUT: !75 = !{!23}
+// CHECK:STDOUT: !76 = !DILocation(line: 27, column: 12, scope: !73)
+// CHECK:STDOUT: !77 = !DILocation(line: 27, column: 5, scope: !73)
+// CHECK:STDOUT: !78 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !46, line: 112, type: !47, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !79)
+// CHECK:STDOUT: !79 = !{!80}
+// CHECK:STDOUT: !80 = !DILocalVariable(arg: 1, scope: !78, type: !23)
+// CHECK:STDOUT: !81 = !DILocation(line: 113, column: 12, scope: !78)
+// CHECK:STDOUT: !82 = !DILocation(line: 113, column: 5, scope: !78)
+// CHECK:STDOUT: !83 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !46, line: 115, type: !20, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !84)
+// CHECK:STDOUT: !84 = !{!85}
+// CHECK:STDOUT: !85 = !DILocalVariable(arg: 1, scope: !83, type: !23)
+// CHECK:STDOUT: !86 = !DILocation(line: 116, column: 12, scope: !83)
+// CHECK:STDOUT: !87 = !DILocation(line: 116, column: 5, scope: !83)
+// CHECK:STDOUT: !88 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a", scope: null, file: !59, line: 275, type: !89, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !91)
+// CHECK:STDOUT: !89 = !DISubroutineType(types: !90)
+// CHECK:STDOUT: !90 = !{null, !22, !22}
+// CHECK:STDOUT: !91 = !{!92, !93}
+// CHECK:STDOUT: !92 = !DILocalVariable(arg: 1, scope: !88, type: !22)
+// CHECK:STDOUT: !93 = !DILocalVariable(arg: 2, scope: !88, type: !22)
+// CHECK:STDOUT: !94 = !DILocation(line: 4294967295, scope: !88)
+// CHECK:STDOUT: !95 = !DILocation(line: 275, column: 3, scope: !88)
+// CHECK:STDOUT: !96 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !46, line: 104, type: !67, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !97)
+// CHECK:STDOUT: !97 = !{!98}
+// CHECK:STDOUT: !98 = !DILocalVariable(arg: 1, scope: !96, type: !22)
+// CHECK:STDOUT: !99 = !DILocation(line: 108, column: 5, scope: !96)
+// CHECK:STDOUT: !100 = !DILocation(line: 109, column: 5, scope: !96)
+// CHECK:STDOUT: !101 = !DILocation(line: 110, column: 5, scope: !96)
+// CHECK:STDOUT: !102 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !46, line: 99, type: !74, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !103 = !DILocation(line: 101, column: 5, scope: !102)
+// CHECK:STDOUT: !104 = !DILocation(line: 102, column: 5, scope: !102)
+// CHECK:STDOUT: !105 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9", scope: null, file: !106, line: 24, type: !107, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !109)
+// CHECK:STDOUT: !106 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
+// CHECK:STDOUT: !107 = !DISubroutineType(types: !108)
+// CHECK:STDOUT: !108 = !{!22, !22}
+// CHECK:STDOUT: !109 = !{!110}
+// CHECK:STDOUT: !110 = !DILocalVariable(arg: 1, scope: !105, type: !22)
+// CHECK:STDOUT: !111 = !DILocation(line: 24, column: 38, scope: !105)

+ 155 - 113
toolchain/lower/testdata/for/for.carbon

@@ -70,109 +70,109 @@ fn For() {
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @"_CNewCursor.IntRange.Core:Iterate.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !14 {
-// CHECK:STDOUT:   %start = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !16
-// CHECK:STDOUT:   %1 = load i32, ptr %start, align 4, !dbg !16
-// CHECK:STDOUT:   ret i32 %1, !dbg !17
+// CHECK:STDOUT:   %start = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !22
+// CHECK:STDOUT:   %1 = load i32, ptr %start, align 4, !dbg !22
+// CHECK:STDOUT:   ret i32 %1, !dbg !23
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8"(ptr sret({ i32, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !18 {
-// CHECK:STDOUT:   %1 = alloca i32, align 4, !dbg !19
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %1), !dbg !19
-// CHECK:STDOUT:   %2 = load i32, ptr %cursor, align 4, !dbg !20
-// CHECK:STDOUT:   store i32 %2, ptr %1, align 4, !dbg !19
-// CHECK:STDOUT:   %end = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !21
-// CHECK:STDOUT:   %3 = load i32, ptr %end, align 4, !dbg !21
-// CHECK:STDOUT:   %4 = load i32, ptr %1, align 4, !dbg !22
-// CHECK:STDOUT:   %5 = icmp slt i32 %4, %3, !dbg !22
-// CHECK:STDOUT:   br i1 %5, label %6, label %8, !dbg !23
+// CHECK:STDOUT: define linkonce_odr void @"_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8"(ptr sret({ i32, i1 }) %return, ptr %self, ptr %cursor) #0 !dbg !24 {
+// CHECK:STDOUT:   %1 = alloca i32, align 4, !dbg !30
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %1), !dbg !30
+// CHECK:STDOUT:   %2 = load i32, ptr %cursor, align 4, !dbg !31
+// CHECK:STDOUT:   store i32 %2, ptr %1, align 4, !dbg !30
+// CHECK:STDOUT:   %end = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !32
+// CHECK:STDOUT:   %3 = load i32, ptr %end, align 4, !dbg !32
+// CHECK:STDOUT:   %4 = load i32, ptr %1, align 4, !dbg !33
+// CHECK:STDOUT:   %5 = icmp slt i32 %4, %3, !dbg !33
+// CHECK:STDOUT:   br i1 %5, label %6, label %8, !dbg !34
 // CHECK:STDOUT:
 // CHECK:STDOUT: 6:                                                ; preds = %0
-// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %cursor), !dbg !24
-// CHECK:STDOUT:   %7 = load i32, ptr %1, align 4, !dbg !25
-// CHECK:STDOUT:   call void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr %return, i32 %7), !dbg !26
-// CHECK:STDOUT:   ret void, !dbg !27
+// CHECK:STDOUT:   call void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %cursor), !dbg !35
+// CHECK:STDOUT:   %7 = load i32, ptr %1, align 4, !dbg !36
+// CHECK:STDOUT:   call void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr %return, i32 %7), !dbg !37
+// CHECK:STDOUT:   ret void, !dbg !38
 // CHECK:STDOUT:
 // CHECK:STDOUT: 8:                                                ; preds = %0
-// CHECK:STDOUT:   call void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr %return), !dbg !28
-// CHECK:STDOUT:   ret void, !dbg !29
+// CHECK:STDOUT:   call void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr %return), !dbg !39
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !30 {
-// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !32
-// CHECK:STDOUT:   ret i1 %1, !dbg !33
+// CHECK:STDOUT: define linkonce_odr i1 @_CHasValue.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !41 {
+// CHECK:STDOUT:   %1 = call i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !47
+// CHECK:STDOUT:   ret i1 %1, !dbg !48
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CGet.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !34 {
-// CHECK:STDOUT:   %1 = call i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !35
-// CHECK:STDOUT:   ret i32 %1, !dbg !36
+// CHECK:STDOUT: define linkonce_odr i32 @_CGet.Optional.Core.8d367a24b9d8bb7c(ptr %self) #0 !dbg !49 {
+// CHECK:STDOUT:   %1 = call i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %self), !dbg !52
+// CHECK:STDOUT:   ret i32 %1, !dbg !53
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CInclusiveRange.Core(ptr sret({ i32, i32 }), i32, i32)
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !37 {
-// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 1), !dbg !39
-// CHECK:STDOUT:   ret void, !dbg !40
+// CHECK:STDOUT: define linkonce_odr void @"_COp.Int.Core:Inc.Core.be1e879c1ad406d8"(ptr %self) #0 !dbg !54 {
+// CHECK:STDOUT:   call void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 1), !dbg !60
+// CHECK:STDOUT:   ret void, !dbg !61
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return, i32 %value) #0 !dbg !41 {
-// CHECK:STDOUT:   call void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return, i32 %value), !dbg !42
-// CHECK:STDOUT:   ret void, !dbg !43
+// CHECK:STDOUT: define linkonce_odr void @_CSome.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return, i32 %value) #0 !dbg !62 {
+// CHECK:STDOUT:   call void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return, i32 %value), !dbg !67
+// CHECK:STDOUT:   ret void, !dbg !68
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return) #0 !dbg !44 {
-// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return), !dbg !45
-// CHECK:STDOUT:   ret void, !dbg !46
+// CHECK:STDOUT: define linkonce_odr void @_CNone.Optional.Core.8d367a24b9d8bb7c(ptr sret({ i32, i1 }) %return) #0 !dbg !69 {
+// CHECK:STDOUT:   call void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %return), !dbg !72
+// CHECK:STDOUT:   ret void, !dbg !73
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !47 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 1, !dbg !48
-// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !48
-// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !48
-// CHECK:STDOUT:   ret i1 %2, !dbg !49
+// CHECK:STDOUT: define linkonce_odr i1 @"_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !74 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 1, !dbg !77
+// CHECK:STDOUT:   %1 = load i8, ptr %has_value, align 1, !dbg !77
+// CHECK:STDOUT:   %2 = trunc i8 %1 to i1, !dbg !77
+// CHECK:STDOUT:   ret i1 %2, !dbg !78
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !50 {
-// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 0, !dbg !51
-// CHECK:STDOUT:   %1 = load i32, ptr %value1, align 4, !dbg !51
-// CHECK:STDOUT:   ret i32 %1, !dbg !52
+// CHECK:STDOUT: define linkonce_odr i32 @"_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr %value) #0 !dbg !79 {
+// CHECK:STDOUT:   %value1 = getelementptr inbounds nuw { i32, i1 }, ptr %value, i32 0, i32 0, !dbg !82
+// CHECK:STDOUT:   %1 = load i32, ptr %value1, align 4, !dbg !82
+// CHECK:STDOUT:   ret i32 %1, !dbg !83
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: alwaysinline nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 %other) #2 !dbg !53 {
-// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %other), !dbg !54
-// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !55
-// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !55
-// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !55
-// CHECK:STDOUT:   ret void, !dbg !55
+// CHECK:STDOUT: define linkonce_odr void @"_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a"(ptr %self, i32 %other) #2 !dbg !84 {
+// CHECK:STDOUT:   %1 = call i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %other), !dbg !90
+// CHECK:STDOUT:   %2 = load i32, ptr %self, align 4, !dbg !91
+// CHECK:STDOUT:   %3 = add i32 %2, %1, !dbg !91
+// CHECK:STDOUT:   store i32 %3, ptr %self, align 4, !dbg !91
+// CHECK:STDOUT:   ret void, !dbg !91
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return, i32 %self) #0 !dbg !56 {
-// CHECK:STDOUT:   %value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 0, !dbg !57
-// CHECK:STDOUT:   store i32 %self, ptr %value, align 4, !dbg !57
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !58
-// CHECK:STDOUT:   store i8 1, ptr %has_value, align 1, !dbg !58
-// CHECK:STDOUT:   ret void, !dbg !59
+// CHECK:STDOUT: define linkonce_odr void @"_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return, i32 %self) #0 !dbg !92 {
+// CHECK:STDOUT:   %value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 0, !dbg !95
+// CHECK:STDOUT:   store i32 %self, ptr %value, align 4, !dbg !95
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !96
+// CHECK:STDOUT:   store i8 1, ptr %has_value, align 1, !dbg !96
+// CHECK:STDOUT:   ret void, !dbg !97
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return) #0 !dbg !60 {
-// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !61
-// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !61
-// CHECK:STDOUT:   ret void, !dbg !62
+// CHECK:STDOUT: define linkonce_odr void @"_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9"(ptr sret({ i32, i1 }) %return) #0 !dbg !98 {
+// CHECK:STDOUT:   %has_value = getelementptr inbounds nuw { i32, i1 }, ptr %return, i32 0, i32 1, !dbg !99
+// CHECK:STDOUT:   store i8 0, ptr %has_value, align 1, !dbg !99
+// CHECK:STDOUT:   ret void, !dbg !100
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %self) #0 !dbg !63 {
-// CHECK:STDOUT:   ret i32 %self, !dbg !65
+// CHECK:STDOUT: define linkonce_odr i32 @"_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9"(i32 %self) #0 !dbg !101 {
+// CHECK:STDOUT:   ret i32 %self, !dbg !107
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -191,7 +191,7 @@ fn For() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "for.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "For", linkageName: "_CFor.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 21, column: 18, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 21, column: 7, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 20, column: 3, scope: !4)
@@ -199,55 +199,97 @@ fn For() {
 // CHECK:STDOUT: !11 = !DILocation(line: 21, column: 3, scope: !4)
 // CHECK:STDOUT: !12 = !DILocation(line: 24, column: 3, scope: !4)
 // CHECK:STDOUT: !13 = !DILocation(line: 19, column: 1, scope: !4)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !15, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "NewCursor", linkageName: "_CNewCursor.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !15, line: 25, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
 // CHECK:STDOUT: !15 = !DIFile(filename: "{{.*}}/range.carbon", directory: "")
-// CHECK:STDOUT: !16 = !DILocation(line: 25, column: 51, scope: !14)
-// CHECK:STDOUT: !17 = !DILocation(line: 25, column: 44, scope: !14)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !15, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 27, column: 7, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 27, column: 27, scope: !18)
-// CHECK:STDOUT: !21 = !DILocation(line: 28, column: 19, scope: !18)
-// CHECK:STDOUT: !22 = !DILocation(line: 28, column: 11, scope: !18)
-// CHECK:STDOUT: !23 = !DILocation(line: 28, column: 10, scope: !18)
-// CHECK:STDOUT: !24 = !DILocation(line: 29, column: 9, scope: !18)
-// CHECK:STDOUT: !25 = !DILocation(line: 30, column: 38, scope: !18)
-// CHECK:STDOUT: !26 = !DILocation(line: 30, column: 16, scope: !18)
-// CHECK:STDOUT: !27 = !DILocation(line: 30, column: 9, scope: !18)
-// CHECK:STDOUT: !28 = !DILocation(line: 32, column: 16, scope: !18)
-// CHECK:STDOUT: !29 = !DILocation(line: 32, column: 9, scope: !18)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !31, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
-// CHECK:STDOUT: !32 = !DILocation(line: 33, column: 12, scope: !30)
-// CHECK:STDOUT: !33 = !DILocation(line: 33, column: 5, scope: !30)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !31, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DILocation(line: 36, column: 12, scope: !34)
-// CHECK:STDOUT: !36 = !DILocation(line: 36, column: 5, scope: !34)
-// CHECK:STDOUT: !37 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !38, line: 339, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !38 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
-// CHECK:STDOUT: !39 = !DILocation(line: 341, column: 5, scope: !37)
-// CHECK:STDOUT: !40 = !DILocation(line: 339, column: 3, scope: !37)
-// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !31, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !42 = !DILocation(line: 30, column: 12, scope: !41)
-// CHECK:STDOUT: !43 = !DILocation(line: 30, column: 5, scope: !41)
-// CHECK:STDOUT: !44 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !31, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !45 = !DILocation(line: 27, column: 12, scope: !44)
-// CHECK:STDOUT: !46 = !DILocation(line: 27, column: 5, scope: !44)
-// CHECK:STDOUT: !47 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !31, line: 112, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !48 = !DILocation(line: 113, column: 12, scope: !47)
-// CHECK:STDOUT: !49 = !DILocation(line: 113, column: 5, scope: !47)
-// CHECK:STDOUT: !50 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !31, line: 115, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !51 = !DILocation(line: 116, column: 12, scope: !50)
-// CHECK:STDOUT: !52 = !DILocation(line: 116, column: 5, scope: !50)
-// CHECK:STDOUT: !53 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a", scope: null, file: !38, line: 275, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !54 = !DILocation(line: 4294967295, scope: !53)
-// CHECK:STDOUT: !55 = !DILocation(line: 275, column: 3, scope: !53)
-// CHECK:STDOUT: !56 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !31, line: 104, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !57 = !DILocation(line: 108, column: 5, scope: !56)
-// CHECK:STDOUT: !58 = !DILocation(line: 109, column: 5, scope: !56)
-// CHECK:STDOUT: !59 = !DILocation(line: 110, column: 5, scope: !56)
-// CHECK:STDOUT: !60 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !31, line: 99, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !61 = !DILocation(line: 101, column: 5, scope: !60)
-// CHECK:STDOUT: !62 = !DILocation(line: 102, column: 5, scope: !60)
-// CHECK:STDOUT: !63 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9", scope: null, file: !64, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !64 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
-// CHECK:STDOUT: !65 = !DILocation(line: 24, column: 38, scope: !63)
+// CHECK:STDOUT: !16 = !DISubroutineType(types: !17)
+// CHECK:STDOUT: !17 = !{!18, !19}
+// CHECK:STDOUT: !18 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !19 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !14, type: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 25, column: 51, scope: !14)
+// CHECK:STDOUT: !23 = !DILocation(line: 25, column: 44, scope: !14)
+// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "Next", linkageName: "_CNext.IntRange.Core:Iterate.Core.be1e879c1ad406d8", scope: null, file: !15, line: 26, type: !25, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !27)
+// CHECK:STDOUT: !25 = !DISubroutineType(types: !26)
+// CHECK:STDOUT: !26 = !{!19, !19, !19}
+// CHECK:STDOUT: !27 = !{!28, !29}
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 1, scope: !24, type: !19)
+// CHECK:STDOUT: !29 = !DILocalVariable(arg: 2, scope: !24, type: !19)
+// CHECK:STDOUT: !30 = !DILocation(line: 27, column: 7, scope: !24)
+// CHECK:STDOUT: !31 = !DILocation(line: 27, column: 27, scope: !24)
+// CHECK:STDOUT: !32 = !DILocation(line: 28, column: 19, scope: !24)
+// CHECK:STDOUT: !33 = !DILocation(line: 28, column: 11, scope: !24)
+// CHECK:STDOUT: !34 = !DILocation(line: 28, column: 10, scope: !24)
+// CHECK:STDOUT: !35 = !DILocation(line: 29, column: 9, scope: !24)
+// CHECK:STDOUT: !36 = !DILocation(line: 30, column: 38, scope: !24)
+// CHECK:STDOUT: !37 = !DILocation(line: 30, column: 16, scope: !24)
+// CHECK:STDOUT: !38 = !DILocation(line: 30, column: 9, scope: !24)
+// CHECK:STDOUT: !39 = !DILocation(line: 32, column: 16, scope: !24)
+// CHECK:STDOUT: !40 = !DILocation(line: 32, column: 9, scope: !24)
+// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "HasValue", linkageName: "_CHasValue.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !42, line: 32, type: !43, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !45)
+// CHECK:STDOUT: !42 = !DIFile(filename: "{{.*}}/prelude/types/optional.carbon", directory: "")
+// CHECK:STDOUT: !43 = !DISubroutineType(types: !44)
+// CHECK:STDOUT: !44 = !{!19, !19}
+// CHECK:STDOUT: !45 = !{!46}
+// CHECK:STDOUT: !46 = !DILocalVariable(arg: 1, scope: !41, type: !19)
+// CHECK:STDOUT: !47 = !DILocation(line: 33, column: 12, scope: !41)
+// CHECK:STDOUT: !48 = !DILocation(line: 33, column: 5, scope: !41)
+// CHECK:STDOUT: !49 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !42, line: 35, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !50)
+// CHECK:STDOUT: !50 = !{!51}
+// CHECK:STDOUT: !51 = !DILocalVariable(arg: 1, scope: !49, type: !19)
+// CHECK:STDOUT: !52 = !DILocation(line: 36, column: 12, scope: !49)
+// CHECK:STDOUT: !53 = !DILocation(line: 36, column: 5, scope: !49)
+// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Inc.Core.be1e879c1ad406d8", scope: null, file: !55, line: 339, type: !56, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !58)
+// CHECK:STDOUT: !55 = !DIFile(filename: "{{.*}}/prelude/types/int.carbon", directory: "")
+// CHECK:STDOUT: !56 = !DISubroutineType(types: !57)
+// CHECK:STDOUT: !57 = !{null, !18}
+// CHECK:STDOUT: !58 = !{!59}
+// CHECK:STDOUT: !59 = !DILocalVariable(arg: 1, scope: !54, type: !18)
+// CHECK:STDOUT: !60 = !DILocation(line: 341, column: 5, scope: !54)
+// CHECK:STDOUT: !61 = !DILocation(line: 339, column: 3, scope: !54)
+// CHECK:STDOUT: !62 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !42, line: 29, type: !63, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !65)
+// CHECK:STDOUT: !63 = !DISubroutineType(types: !64)
+// CHECK:STDOUT: !64 = !{!19, !18}
+// CHECK:STDOUT: !65 = !{!66}
+// CHECK:STDOUT: !66 = !DILocalVariable(arg: 1, scope: !62, type: !18)
+// CHECK:STDOUT: !67 = !DILocation(line: 30, column: 12, scope: !62)
+// CHECK:STDOUT: !68 = !DILocation(line: 30, column: 5, scope: !62)
+// CHECK:STDOUT: !69 = distinct !DISubprogram(name: "None", linkageName: "_CNone.Optional.Core.8d367a24b9d8bb7c", scope: null, file: !42, line: 26, type: !70, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !70 = !DISubroutineType(types: !71)
+// CHECK:STDOUT: !71 = !{!19}
+// CHECK:STDOUT: !72 = !DILocation(line: 27, column: 12, scope: !69)
+// CHECK:STDOUT: !73 = !DILocation(line: 27, column: 5, scope: !69)
+// CHECK:STDOUT: !74 = distinct !DISubprogram(name: "Has", linkageName: "_CHas.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !42, line: 112, type: !43, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !75)
+// CHECK:STDOUT: !75 = !{!76}
+// CHECK:STDOUT: !76 = !DILocalVariable(arg: 1, scope: !74, type: !19)
+// CHECK:STDOUT: !77 = !DILocation(line: 113, column: 12, scope: !74)
+// CHECK:STDOUT: !78 = !DILocation(line: 113, column: 5, scope: !74)
+// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "Get", linkageName: "_CGet.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !42, line: 115, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !80)
+// CHECK:STDOUT: !80 = !{!81}
+// CHECK:STDOUT: !81 = !DILocalVariable(arg: 1, scope: !79, type: !19)
+// CHECK:STDOUT: !82 = !DILocation(line: 116, column: 12, scope: !79)
+// CHECK:STDOUT: !83 = !DILocation(line: 116, column: 5, scope: !79)
+// CHECK:STDOUT: !84 = distinct !DISubprogram(name: "Op", linkageName: "_COp:thunk.Int.Core:AddAssignWith.Core.ff11a2fb54eea08a", scope: null, file: !55, line: 275, type: !85, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !87)
+// CHECK:STDOUT: !85 = !DISubroutineType(types: !86)
+// CHECK:STDOUT: !86 = !{null, !18, !18}
+// CHECK:STDOUT: !87 = !{!88, !89}
+// CHECK:STDOUT: !88 = !DILocalVariable(arg: 1, scope: !84, type: !18)
+// CHECK:STDOUT: !89 = !DILocalVariable(arg: 2, scope: !84, type: !18)
+// CHECK:STDOUT: !90 = !DILocation(line: 4294967295, scope: !84)
+// CHECK:STDOUT: !91 = !DILocation(line: 275, column: 3, scope: !84)
+// CHECK:STDOUT: !92 = distinct !DISubprogram(name: "Some", linkageName: "_CSome.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !42, line: 104, type: !63, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !93)
+// CHECK:STDOUT: !93 = !{!94}
+// CHECK:STDOUT: !94 = !DILocalVariable(arg: 1, scope: !92, type: !18)
+// CHECK:STDOUT: !95 = !DILocation(line: 108, column: 5, scope: !92)
+// CHECK:STDOUT: !96 = !DILocation(line: 109, column: 5, scope: !92)
+// CHECK:STDOUT: !97 = !DILocation(line: 110, column: 5, scope: !92)
+// CHECK:STDOUT: !98 = distinct !DISubprogram(name: "None", linkageName: "_CNone.225258f1a45e9386:OptionalStorage.Core.c798a30c8da4d6f9", scope: null, file: !42, line: 99, type: !70, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !99 = !DILocation(line: 101, column: 5, scope: !98)
+// CHECK:STDOUT: !100 = !DILocation(line: 102, column: 5, scope: !98)
+// CHECK:STDOUT: !101 = distinct !DISubprogram(name: "Convert", linkageName: "_CConvert.225258f1a45e9386:ImplicitAs.Core.c798a30c8da4d6f9", scope: null, file: !102, line: 24, type: !103, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !105)
+// CHECK:STDOUT: !102 = !DIFile(filename: "{{.*}}/prelude/operators/as.carbon", directory: "")
+// CHECK:STDOUT: !103 = !DISubroutineType(types: !104)
+// CHECK:STDOUT: !104 = !{!18, !18}
+// CHECK:STDOUT: !105 = !{!106}
+// CHECK:STDOUT: !106 = !DILocalVariable(arg: 1, scope: !101, type: !18)
+// CHECK:STDOUT: !107 = !DILocation(line: 24, column: 38, scope: !101)

+ 15 - 12
toolchain/lower/testdata/function/call/empty_struct.carbon

@@ -24,16 +24,16 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CEcho.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %b.var = alloca {}, align 8, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %b.var), !dbg !9
-// CHECK:STDOUT:   call void @_CEcho.Main(), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %b.var = alloca {}, align 8, !dbg !12
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %b.var), !dbg !12
+// CHECK:STDOUT:   call void @_CEcho.Main(), !dbg !13
+// CHECK:STDOUT:   ret void, !dbg !14
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -51,9 +51,12 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "empty_struct.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Echo", linkageName: "_CEcho.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 18, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 18, column: 15, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !10, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = !DISubroutineType(types: !11)
+// CHECK:STDOUT: !11 = !{null}
+// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 3, scope: !9)
+// CHECK:STDOUT: !13 = !DILocation(line: 18, column: 15, scope: !9)
+// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 1, scope: !9)

+ 15 - 12
toolchain/lower/testdata/function/call/empty_tuple.carbon

@@ -24,16 +24,16 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CEcho.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %b.var = alloca {}, align 8, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %b.var), !dbg !9
-// CHECK:STDOUT:   call void @_CEcho.Main(), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %b.var = alloca {}, align 8, !dbg !12
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %b.var), !dbg !12
+// CHECK:STDOUT:   call void @_CEcho.Main(), !dbg !13
+// CHECK:STDOUT:   ret void, !dbg !14
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -51,9 +51,12 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "empty_tuple.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Echo", linkageName: "_CEcho.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 18, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 18, column: 15, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !10, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = !DISubroutineType(types: !11)
+// CHECK:STDOUT: !11 = !{null}
+// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 3, scope: !9)
+// CHECK:STDOUT: !13 = !DILocation(line: 18, column: 15, scope: !9)
+// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 1, scope: !9)

+ 19 - 14
toolchain/lower/testdata/function/call/i32.carbon

@@ -24,17 +24,17 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CEcho.Main(i32 %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %a, !dbg !7
+// CHECK:STDOUT:   ret i32 %a, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %b.var = alloca i32, align 4, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %b.var), !dbg !9
-// CHECK:STDOUT:   %Echo.call = call i32 @_CEcho.Main(i32 1), !dbg !10
-// CHECK:STDOUT:   store i32 %Echo.call, ptr %b.var, align 4, !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %b.var = alloca i32, align 4, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %b.var), !dbg !14
+// CHECK:STDOUT:   %Echo.call = call i32 @_CEcho.Main(i32 1), !dbg !15
+// CHECK:STDOUT:   store i32 %Echo.call, ptr %b.var, align 4, !dbg !14
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -50,11 +50,16 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "i32.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Echo", linkageName: "_CEcho.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Echo", linkageName: "_CEcho.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 18, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 18, column: 16, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 18, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 18, column: 16, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 17, column: 1, scope: !11)

+ 20 - 17
toolchain/lower/testdata/function/call/implicit_empty_tuple_as_arg.carbon

@@ -31,19 +31,19 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CBar.Main() #0 !dbg !8 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   ret void, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !10 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %x.var = alloca {}, align 8, !dbg !11
-// CHECK:STDOUT:   %.loc19_23.1.temp = alloca {}, align 8, !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %x.var), !dbg !11
-// CHECK:STDOUT:   call void @_CFoo.Main(), !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc19_23.1.temp), !dbg !12
-// CHECK:STDOUT:   call void @_CBar.Main(), !dbg !13
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   %x.var = alloca {}, align 8, !dbg !14
+// CHECK:STDOUT:   %.loc19_23.1.temp = alloca {}, align 8, !dbg !15
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %x.var), !dbg !14
+// CHECK:STDOUT:   call void @_CFoo.Main(), !dbg !15
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc19_23.1.temp), !dbg !15
+// CHECK:STDOUT:   call void @_CBar.Main(), !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -64,12 +64,15 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "implicit_empty_tuple_as_arg.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Bar", linkageName: "_CBar.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 23, scope: !8)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 19, column: 3, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 19, column: 19, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 19, column: 15, scope: !10)
-// CHECK:STDOUT: !14 = !DILocation(line: 18, column: 1, scope: !10)
+// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Bar", linkageName: "_CBar.Main", scope: null, file: !3, line: 16, type: !9, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !9 = !DISubroutineType(types: !10)
+// CHECK:STDOUT: !10 = !{!11}
+// CHECK:STDOUT: !11 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !12 = !DILocation(line: 16, column: 23, scope: !8)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !14 = !DILocation(line: 19, column: 3, scope: !13)
+// CHECK:STDOUT: !15 = !DILocation(line: 19, column: 19, scope: !13)
+// CHECK:STDOUT: !16 = !DILocation(line: 19, column: 15, scope: !13)
+// CHECK:STDOUT: !17 = !DILocation(line: 18, column: 1, scope: !13)

+ 15 - 10
toolchain/lower/testdata/function/call/params_one.carbon

@@ -22,14 +22,14 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFoo.Main(i32 %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CFoo.Main(i32 1), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   call void @_CFoo.Main(i32 1), !dbg !14
+// CHECK:STDOUT:   ret void, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -41,10 +41,15 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_one.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 16, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 15, column: 1, scope: !11)

+ 17 - 12
toolchain/lower/testdata/function/call/params_one_comma.carbon

@@ -23,15 +23,15 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFoo.Main(i32 %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CFoo.Main(i32 1), !dbg !9
-// CHECK:STDOUT:   call void @_CFoo.Main(i32 1), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   call void @_CFoo.Main(i32 1), !dbg !14
+// CHECK:STDOUT:   call void @_CFoo.Main(i32 1), !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -43,11 +43,16 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_one_comma.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 16, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 17, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 1, scope: !11)

+ 16 - 10
toolchain/lower/testdata/function/call/params_two.carbon

@@ -22,14 +22,14 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFoo.Main(i32 %a, i32 %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CFoo.Main(i32 1, i32 2), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   call void @_CFoo.Main(i32 1, i32 2), !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -41,10 +41,16 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_two.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null}
+// CHECK:STDOUT: !15 = !DILocation(line: 16, column: 3, scope: !12)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 1, scope: !12)

+ 18 - 12
toolchain/lower/testdata/function/call/params_two_comma.carbon

@@ -23,15 +23,15 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFoo.Main(i32 %a, i32 %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CFoo.Main(i32 1, i32 2), !dbg !9
-// CHECK:STDOUT:   call void @_CFoo.Main(i32 1, i32 2), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   call void @_CFoo.Main(i32 1, i32 2), !dbg !15
+// CHECK:STDOUT:   call void @_CFoo.Main(i32 1, i32 2), !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -43,11 +43,17 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_two_comma.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null}
+// CHECK:STDOUT: !15 = !DILocation(line: 16, column: 3, scope: !12)
+// CHECK:STDOUT: !16 = !DILocation(line: 17, column: 3, scope: !12)
+// CHECK:STDOUT: !17 = !DILocation(line: 15, column: 1, scope: !12)

+ 1 - 1
toolchain/lower/testdata/function/call/params_zero.carbon

@@ -43,7 +43,7 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_zero.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
 // CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)

+ 19 - 14
toolchain/lower/testdata/function/call/ref_param.carbon

@@ -23,17 +23,17 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CDoNothing.Main(ptr %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %a.var = alloca i32, align 4, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !9
-// CHECK:STDOUT:   store i32 0, ptr %a.var, align 4, !dbg !9
-// CHECK:STDOUT:   call void @_CDoNothing.Main(ptr %a.var), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %a.var = alloca i32, align 4, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !14
+// CHECK:STDOUT:   store i32 0, ptr %a.var, align 4, !dbg !14
+// CHECK:STDOUT:   call void @_CDoNothing.Main(ptr %a.var), !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -49,11 +49,16 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "ref_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "DoNothing", linkageName: "_CDoNothing.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "DoNothing", linkageName: "_CDoNothing.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 16, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 17, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 1, scope: !11)

+ 1 - 1
toolchain/lower/testdata/function/call/return_implicit.carbon

@@ -51,7 +51,7 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "return_implicit.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "MakeImplicitEmptyTuple", linkageName: "_CMakeImplicitEmptyTuple.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 1, scope: !4)
 // CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !9 = !DILocation(line: 18, column: 3, scope: !8)

+ 16 - 10
toolchain/lower/testdata/function/call/struct_param.carbon

@@ -24,14 +24,14 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main({ i32 } %b, ptr %c) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main({ i32 } { i32 1 }, ptr @struct.9ae.loc16_34.6), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   call void @_CF.Main({ i32 } { i32 1 }, ptr @struct.9ae.loc16_34.6), !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -43,10 +43,16 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "struct_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null}
+// CHECK:STDOUT: !15 = !DILocation(line: 16, column: 3, scope: !12)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 1, scope: !12)

+ 16 - 10
toolchain/lower/testdata/function/call/tuple_param.carbon

@@ -24,14 +24,14 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main({ i32 } %b, ptr %c) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main({ i32 } { i32 1 }, ptr @tuple.11a.loc16_20.6), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   call void @_CF.Main({ i32 } { i32 1 }, ptr @tuple.11a.loc16_20.6), !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -43,10 +43,16 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "tuple_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null}
+// CHECK:STDOUT: !15 = !DILocation(line: 16, column: 3, scope: !12)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 1, scope: !12)

+ 33 - 27
toolchain/lower/testdata/function/call/tuple_param_with_return_slot.carbon

@@ -26,27 +26,27 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main(ptr sret({ i32, i32, i32 }) %return, { i32 } %b, ptr %c) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %tuple.elem0.loc14_12.tuple.elem = extractvalue { i32 } %b, 0, !dbg !7
-// CHECK:STDOUT:   %tuple.elem0.loc14_17.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %c, i32 0, i32 0, !dbg !8
-// CHECK:STDOUT:   %tuple.elem0.loc14_17.tuple.elem.load = load i32, ptr %tuple.elem0.loc14_17.tuple.elem, align 4, !dbg !8
-// CHECK:STDOUT:   %tuple.elem1.loc14_22.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %c, i32 0, i32 1, !dbg !9
-// CHECK:STDOUT:   %tuple.elem1.loc14_22.tuple.elem.load = load i32, ptr %tuple.elem1.loc14_22.tuple.elem, align 4, !dbg !9
-// CHECK:STDOUT:   %tuple.elem0.loc14_24.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 0, !dbg !10
-// CHECK:STDOUT:   store i32 %tuple.elem0.loc14_12.tuple.elem, ptr %tuple.elem0.loc14_24.tuple.elem, align 4, !dbg !10
-// CHECK:STDOUT:   %tuple.elem1.loc14_24.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 1, !dbg !10
-// CHECK:STDOUT:   store i32 %tuple.elem0.loc14_17.tuple.elem.load, ptr %tuple.elem1.loc14_24.tuple.elem, align 4, !dbg !10
-// CHECK:STDOUT:   %tuple.elem2.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 2, !dbg !10
-// CHECK:STDOUT:   store i32 %tuple.elem1.loc14_22.tuple.elem.load, ptr %tuple.elem2.tuple.elem, align 4, !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %tuple.elem0.loc14_12.tuple.elem = extractvalue { i32 } %b, 0, !dbg !11
+// CHECK:STDOUT:   %tuple.elem0.loc14_17.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %c, i32 0, i32 0, !dbg !12
+// CHECK:STDOUT:   %tuple.elem0.loc14_17.tuple.elem.load = load i32, ptr %tuple.elem0.loc14_17.tuple.elem, align 4, !dbg !12
+// CHECK:STDOUT:   %tuple.elem1.loc14_22.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %c, i32 0, i32 1, !dbg !13
+// CHECK:STDOUT:   %tuple.elem1.loc14_22.tuple.elem.load = load i32, ptr %tuple.elem1.loc14_22.tuple.elem, align 4, !dbg !13
+// CHECK:STDOUT:   %tuple.elem0.loc14_24.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 0, !dbg !14
+// CHECK:STDOUT:   store i32 %tuple.elem0.loc14_12.tuple.elem, ptr %tuple.elem0.loc14_24.tuple.elem, align 4, !dbg !14
+// CHECK:STDOUT:   %tuple.elem1.loc14_24.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 1, !dbg !14
+// CHECK:STDOUT:   store i32 %tuple.elem0.loc14_17.tuple.elem.load, ptr %tuple.elem1.loc14_24.tuple.elem, align 4, !dbg !14
+// CHECK:STDOUT:   %tuple.elem2.tuple.elem = getelementptr inbounds nuw { i32, i32, i32 }, ptr %return, i32 0, i32 2, !dbg !14
+// CHECK:STDOUT:   store i32 %tuple.elem1.loc14_22.tuple.elem.load, ptr %tuple.elem2.tuple.elem, align 4, !dbg !14
+// CHECK:STDOUT:   ret void, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !12 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc18_21.1.temp = alloca { i32, i32, i32 }, align 8, !dbg !13
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_21.1.temp), !dbg !13
-// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc18_21.1.temp, { i32 } { i32 1 }, ptr @tuple.11a.loc18_20.6), !dbg !13
-// CHECK:STDOUT:   ret void, !dbg !14
+// CHECK:STDOUT:   %.loc18_21.1.temp = alloca { i32, i32, i32 }, align 8, !dbg !19
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_21.1.temp), !dbg !19
+// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc18_21.1.temp, { i32 } { i32 1 }, ptr @tuple.11a.loc18_20.6), !dbg !19
+// CHECK:STDOUT:   ret void, !dbg !20
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -62,14 +62,20 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "tuple_param_with_return_slot.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 11, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 16, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 14, column: 21, scope: !4)
-// CHECK:STDOUT: !10 = !DILocation(line: 14, column: 10, scope: !4)
-// CHECK:STDOUT: !11 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 18, column: 3, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 1, scope: !12)
+// CHECK:STDOUT: !6 = !{!7, !7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 14, column: 11, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 14, column: 16, scope: !4)
+// CHECK:STDOUT: !13 = !DILocation(line: 14, column: 21, scope: !4)
+// CHECK:STDOUT: !14 = !DILocation(line: 14, column: 10, scope: !4)
+// CHECK:STDOUT: !15 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 17, type: !17, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{null}
+// CHECK:STDOUT: !19 = !DILocation(line: 18, column: 3, scope: !16)
+// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 1, scope: !16)

+ 21 - 16
toolchain/lower/testdata/function/call/var_param.carbon

@@ -23,18 +23,18 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CDoNothing.Main(i32 %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CMain.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %a.var = alloca i32, align 4, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !9
-// CHECK:STDOUT:   store i32 0, ptr %a.var, align 4, !dbg !9
-// CHECK:STDOUT:   %.loc17 = load i32, ptr %a.var, align 4, !dbg !10
-// CHECK:STDOUT:   call void @_CDoNothing.Main(i32 %.loc17), !dbg !11
-// CHECK:STDOUT:   ret void, !dbg !12
+// CHECK:STDOUT:   %a.var = alloca i32, align 4, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %a.var), !dbg !14
+// CHECK:STDOUT:   store i32 0, ptr %a.var, align 4, !dbg !14
+// CHECK:STDOUT:   %.loc17 = load i32, ptr %a.var, align 4, !dbg !15
+// CHECK:STDOUT:   call void @_CDoNothing.Main(i32 %.loc17), !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -50,12 +50,17 @@ fn Main() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "var_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "DoNothing", linkageName: "_CDoNothing.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "DoNothing", linkageName: "_CDoNothing.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 13, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 3, scope: !8)
-// CHECK:STDOUT: !12 = !DILocation(line: 15, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 15, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 16, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 17, column: 13, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 17, column: 3, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 15, column: 1, scope: !11)

+ 9 - 6
toolchain/lower/testdata/function/declaration/simple.carbon

@@ -26,8 +26,8 @@ fn I() -> A;
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CG.Main(i32 %n) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main(i32 %n), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !8
+// CHECK:STDOUT:   call void @_CF.Main(i32 %n), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CH.Main()
@@ -43,8 +43,11 @@ fn I() -> A;
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "simple.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 15, column: 16, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 15, column: 1, scope: !4)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 16, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !4)

+ 76 - 63
toolchain/lower/testdata/function/definition/destroy.carbon

@@ -80,20 +80,20 @@ fn InitLet() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main(ptr %x) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CG.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CCallF.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CCallF.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc12_6.2.temp = alloca {}, align 8, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc12_6.2.temp), !dbg !9
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc12_6.2.temp, ptr align 1 @C.val.loc12_6.3, i64 0, i1 false), !dbg !9
-// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc12_6.2.temp), !dbg !10
-// CHECK:STDOUT:   call void @_CG.Main(), !dbg !11
-// CHECK:STDOUT:   ret void, !dbg !12
+// CHECK:STDOUT:   %.loc12_6.2.temp = alloca {}, align 8, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc12_6.2.temp), !dbg !14
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc12_6.2.temp, ptr align 1 @C.val.loc12_6.3, i64 0, i1 false), !dbg !14
+// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc12_6.2.temp), !dbg !15
+// CHECK:STDOUT:   call void @_CG.Main(), !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -113,15 +113,20 @@ fn InitLet() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "let_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 6, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "CallF", linkageName: "_CCallF.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 12, column: 5, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 12, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 15, column: 3, scope: !8)
-// CHECK:STDOUT: !12 = !DILocation(line: 11, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 6, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallF", linkageName: "_CCallF.Main", scope: null, file: !3, line: 11, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 12, column: 5, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 3, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 11, column: 1, scope: !11)
 // CHECK:STDOUT: ; ModuleID = 'var_param.carbon'
 // CHECK:STDOUT: source_filename = "var_param.carbon"
 // CHECK:STDOUT:
@@ -130,20 +135,20 @@ fn InitLet() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main(ptr %x) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CG.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CCallF.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CCallF.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc6_6.1.temp = alloca {}, align 8, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc6_6.1.temp), !dbg !9
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc6_6.1.temp, ptr align 1 @C.val.loc6_6.2, i64 0, i1 false), !dbg !9
-// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc6_6.1.temp), !dbg !10
-// CHECK:STDOUT:   call void @_CG.Main(), !dbg !11
-// CHECK:STDOUT:   ret void, !dbg !12
+// CHECK:STDOUT:   %.loc6_6.1.temp = alloca {}, align 8, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc6_6.1.temp), !dbg !14
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc6_6.1.temp, ptr align 1 @C.val.loc6_6.2, i64 0, i1 false), !dbg !14
+// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc6_6.1.temp), !dbg !15
+// CHECK:STDOUT:   call void @_CG.Main(), !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -163,15 +168,20 @@ fn InitLet() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "var_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 6, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "CallF", linkageName: "_CCallF.Main", scope: null, file: !3, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 6, column: 6, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 12, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 15, column: 3, scope: !8)
-// CHECK:STDOUT: !12 = !DILocation(line: 11, column: 1, scope: !8)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 6, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "CallF", linkageName: "_CCallF.Main", scope: null, file: !3, line: 11, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 6, column: 6, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 12, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 15, column: 3, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 11, column: 1, scope: !11)
 // CHECK:STDOUT: ; ModuleID = 'return_slot.carbon'
 // CHECK:STDOUT: source_filename = "return_slot.carbon"
 // CHECK:STDOUT:
@@ -180,37 +190,37 @@ fn InitLet() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CF.Main(ptr sret({}) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @C.val.loc7_12, i64 0, i1 false), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @C.val.loc7_12, i64 0, i1 false), !dbg !8
+// CHECK:STDOUT:   ret void, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CG.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CForward.Main(ptr sret({}) %return) #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CForward.Main(ptr sret({}) %return) #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main(ptr %return), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   call void @_CF.Main(ptr %return), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CInitVar.Main() #0 !dbg !11 {
+// CHECK:STDOUT: define void @_CInitVar.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local.var = alloca {}, align 8, !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local.var), !dbg !12
-// CHECK:STDOUT:   call void @_CF.Main(ptr %local.var), !dbg !13
-// CHECK:STDOUT:   call void @_CG.Main(), !dbg !14
-// CHECK:STDOUT:   ret void, !dbg !15
+// CHECK:STDOUT:   %local.var = alloca {}, align 8, !dbg !15
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local.var), !dbg !15
+// CHECK:STDOUT:   call void @_CF.Main(ptr %local.var), !dbg !16
+// CHECK:STDOUT:   call void @_CG.Main(), !dbg !17
+// CHECK:STDOUT:   ret void, !dbg !18
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CInitLet.Main() #0 !dbg !16 {
+// CHECK:STDOUT: define void @_CInitLet.Main() #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc22_20.1.temp = alloca {}, align 8, !dbg !17
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc22_20.1.temp), !dbg !17
-// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc22_20.1.temp), !dbg !17
-// CHECK:STDOUT:   call void @_CG.Main(), !dbg !18
-// CHECK:STDOUT:   ret void, !dbg !19
+// CHECK:STDOUT:   %.loc22_20.1.temp = alloca {}, align 8, !dbg !20
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc22_20.1.temp), !dbg !20
+// CHECK:STDOUT:   call void @_CF.Main(ptr %.loc22_20.1.temp), !dbg !20
+// CHECK:STDOUT:   call void @_CG.Main(), !dbg !21
+// CHECK:STDOUT:   ret void, !dbg !22
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -235,17 +245,20 @@ fn InitLet() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "return_slot.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "Forward", linkageName: "_CForward.Main", scope: null, file: !3, line: 12, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 13, column: 10, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "InitVar", linkageName: "_CInitVar.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !12 = !DILocation(line: 17, column: 3, scope: !11)
-// CHECK:STDOUT: !13 = !DILocation(line: 17, column: 18, scope: !11)
-// CHECK:STDOUT: !14 = !DILocation(line: 18, column: 3, scope: !11)
-// CHECK:STDOUT: !15 = !DILocation(line: 16, column: 1, scope: !11)
-// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "InitLet", linkageName: "_CInitLet.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !17 = !DILocation(line: 22, column: 18, scope: !16)
-// CHECK:STDOUT: !18 = !DILocation(line: 23, column: 3, scope: !16)
-// CHECK:STDOUT: !19 = !DILocation(line: 21, column: 1, scope: !16)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Forward", linkageName: "_CForward.Main", scope: null, file: !3, line: 12, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 10, scope: !9)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 3, scope: !9)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "InitVar", linkageName: "_CInitVar.Main", scope: null, file: !3, line: 16, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null}
+// CHECK:STDOUT: !15 = !DILocation(line: 17, column: 3, scope: !12)
+// CHECK:STDOUT: !16 = !DILocation(line: 17, column: 18, scope: !12)
+// CHECK:STDOUT: !17 = !DILocation(line: 18, column: 3, scope: !12)
+// CHECK:STDOUT: !18 = !DILocation(line: 16, column: 1, scope: !12)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "InitLet", linkageName: "_CInitLet.Main", scope: null, file: !3, line: 21, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !20 = !DILocation(line: 22, column: 18, scope: !19)
+// CHECK:STDOUT: !21 = !DILocation(line: 23, column: 3, scope: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 21, column: 1, scope: !19)

+ 1 - 1
toolchain/lower/testdata/function/definition/empty_struct.carbon

@@ -33,5 +33,5 @@ fn Echo(a: {}) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "empty_struct.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Echo", linkageName: "_CEcho.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)

+ 7 - 4
toolchain/lower/testdata/function/definition/params_one.carbon

@@ -18,7 +18,7 @@ fn Foo(a: i32) {}
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFoo.Main(i32 %a) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -30,7 +30,10 @@ fn Foo(a: i32) {}
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_one.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 13, column: 1, scope: !4)

+ 8 - 4
toolchain/lower/testdata/function/definition/params_two.carbon

@@ -18,7 +18,7 @@ fn Foo(a: i32, b: i32) {}
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CFoo.Main(i32 %a, i32 %b) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -30,7 +30,11 @@ fn Foo(a: i32, b: i32) {}
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_two.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
+// CHECK:STDOUT: !6 = !{null, !7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9, !10}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 2, scope: !4, type: !7)
+// CHECK:STDOUT: !11 = !DILocation(line: 13, column: 1, scope: !4)

+ 1 - 1
toolchain/lower/testdata/function/definition/params_zero.carbon

@@ -32,5 +32,5 @@ fn Foo() {}
 // CHECK:STDOUT: !3 = !DIFile(filename: "params_zero.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Foo", linkageName: "_CFoo.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)

+ 1 - 1
toolchain/lower/testdata/function/definition/raw_name.carbon

@@ -33,5 +33,5 @@ fn r#self() {}
 // CHECK:STDOUT: !3 = !DIFile(filename: "raw_name.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "self", linkageName: "_Cself.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)

+ 83 - 62
toolchain/lower/testdata/function/definition/var_param.carbon

@@ -36,63 +36,63 @@ fn Call() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_COneVar_i32.Main(ptr %n) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_COneVar_X.Main(ptr %x) #0 !dbg !8 {
+// CHECK:STDOUT: define void @_COneVar_X.Main(ptr %x) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !9
+// CHECK:STDOUT:   ret void, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CTwoVars.Main(ptr %a, ptr %b) #0 !dbg !10 {
+// CHECK:STDOUT: define void @_CTwoVars.Main(ptr %a, ptr %b) #0 !dbg !18 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   ret void, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CVarThenLet.Main(ptr %a, ptr %b) #0 !dbg !12 {
+// CHECK:STDOUT: define void @_CVarThenLet.Main(ptr %a, ptr %b) #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !13
+// CHECK:STDOUT:   ret void, !dbg !29
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CLetThenVar.Main(i32 %a, ptr %b) #0 !dbg !14 {
+// CHECK:STDOUT: define void @_CLetThenVar.Main(i32 %a, ptr %b) #0 !dbg !30 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !34
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CCall.Main() #0 !dbg !16 {
+// CHECK:STDOUT: define void @_CCall.Main() #0 !dbg !35 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc15_15.1.temp = alloca i32, align 4, !dbg !17
-// CHECK:STDOUT:   %.loc16_13.1.temp = alloca {}, align 8, !dbg !18
-// CHECK:STDOUT:   %.loc18_12.1.temp = alloca i32, align 4, !dbg !19
-// CHECK:STDOUT:   %.loc18_24.1.temp = alloca {}, align 8, !dbg !20
-// CHECK:STDOUT:   %.loc20_15.1.temp = alloca i32, align 4, !dbg !21
-// CHECK:STDOUT:   %.loc27_18.2.temp = alloca {}, align 8, !dbg !22
-// CHECK:STDOUT:   %.loc21_23.1.temp = alloca {}, align 8, !dbg !23
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc15_15.1.temp), !dbg !17
-// CHECK:STDOUT:   store i32 1, ptr %.loc15_15.1.temp, align 4, !dbg !17
-// CHECK:STDOUT:   call void @_COneVar_i32.Main(ptr %.loc15_15.1.temp), !dbg !24
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc16_13.1.temp), !dbg !18
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc16_13.1.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !18
-// CHECK:STDOUT:   call void @_COneVar_X.Main(ptr %.loc16_13.1.temp), !dbg !25
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_12.1.temp), !dbg !19
-// CHECK:STDOUT:   store i32 1, ptr %.loc18_12.1.temp, align 4, !dbg !19
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_24.1.temp), !dbg !20
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc18_24.1.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !20
-// CHECK:STDOUT:   call void @_CTwoVars.Main(ptr %.loc18_12.1.temp, ptr %.loc18_24.1.temp), !dbg !26
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc20_15.1.temp), !dbg !21
-// CHECK:STDOUT:   store i32 1, ptr %.loc20_15.1.temp, align 4, !dbg !21
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc27_18.2.temp), !dbg !22
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc27_18.2.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !22
-// CHECK:STDOUT:   call void @_CVarThenLet.Main(ptr %.loc20_15.1.temp, ptr %.loc27_18.2.temp), !dbg !27
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc21_23.1.temp), !dbg !23
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc21_23.1.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !23
-// CHECK:STDOUT:   call void @_CLetThenVar.Main(i32 1, ptr %.loc21_23.1.temp), !dbg !28
-// CHECK:STDOUT:   ret void, !dbg !29
+// CHECK:STDOUT:   %.loc15_15.1.temp = alloca i32, align 4, !dbg !38
+// CHECK:STDOUT:   %.loc16_13.1.temp = alloca {}, align 8, !dbg !39
+// CHECK:STDOUT:   %.loc18_12.1.temp = alloca i32, align 4, !dbg !40
+// CHECK:STDOUT:   %.loc18_24.1.temp = alloca {}, align 8, !dbg !41
+// CHECK:STDOUT:   %.loc20_15.1.temp = alloca i32, align 4, !dbg !42
+// CHECK:STDOUT:   %.loc27_18.2.temp = alloca {}, align 8, !dbg !43
+// CHECK:STDOUT:   %.loc21_23.1.temp = alloca {}, align 8, !dbg !44
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc15_15.1.temp), !dbg !38
+// CHECK:STDOUT:   store i32 1, ptr %.loc15_15.1.temp, align 4, !dbg !38
+// CHECK:STDOUT:   call void @_COneVar_i32.Main(ptr %.loc15_15.1.temp), !dbg !45
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc16_13.1.temp), !dbg !39
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc16_13.1.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !39
+// CHECK:STDOUT:   call void @_COneVar_X.Main(ptr %.loc16_13.1.temp), !dbg !46
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_12.1.temp), !dbg !40
+// CHECK:STDOUT:   store i32 1, ptr %.loc18_12.1.temp, align 4, !dbg !40
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc18_24.1.temp), !dbg !41
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc18_24.1.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !41
+// CHECK:STDOUT:   call void @_CTwoVars.Main(ptr %.loc18_12.1.temp, ptr %.loc18_24.1.temp), !dbg !47
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc20_15.1.temp), !dbg !42
+// CHECK:STDOUT:   store i32 1, ptr %.loc20_15.1.temp, align 4, !dbg !42
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc27_18.2.temp), !dbg !43
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc27_18.2.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !43
+// CHECK:STDOUT:   call void @_CVarThenLet.Main(ptr %.loc20_15.1.temp, ptr %.loc27_18.2.temp), !dbg !48
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc21_23.1.temp), !dbg !44
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %.loc21_23.1.temp, ptr align 1 @X.val.loc16_13.2, i64 0, i1 false), !dbg !44
+// CHECK:STDOUT:   call void @_CLetThenVar.Main(i32 1, ptr %.loc21_23.1.temp), !dbg !49
+// CHECK:STDOUT:   ret void, !dbg !50
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -116,29 +116,50 @@ fn Call() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "var_param.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "OneVar_i32", linkageName: "_COneVar_i32.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "OneVar_i32", linkageName: "_COneVar_i32.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 15, column: 1, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "OneVar_X", linkageName: "_COneVar_X.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 16, column: 1, scope: !8)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "TwoVars", linkageName: "_CTwoVars.Main", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 18, column: 1, scope: !10)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "VarThenLet", linkageName: "_CVarThenLet.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 20, column: 1, scope: !12)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "LetThenVar", linkageName: "_CLetThenVar.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !15 = !DILocation(line: 21, column: 1, scope: !14)
-// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "Call", linkageName: "_CCall.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !17 = !DILocation(line: 15, column: 15, scope: !16)
-// CHECK:STDOUT: !18 = !DILocation(line: 16, column: 13, scope: !16)
-// CHECK:STDOUT: !19 = !DILocation(line: 18, column: 12, scope: !16)
-// CHECK:STDOUT: !20 = !DILocation(line: 18, column: 24, scope: !16)
-// CHECK:STDOUT: !21 = !DILocation(line: 20, column: 15, scope: !16)
-// CHECK:STDOUT: !22 = !DILocation(line: 27, column: 17, scope: !16)
-// CHECK:STDOUT: !23 = !DILocation(line: 21, column: 23, scope: !16)
-// CHECK:STDOUT: !24 = !DILocation(line: 24, column: 3, scope: !16)
-// CHECK:STDOUT: !25 = !DILocation(line: 25, column: 3, scope: !16)
-// CHECK:STDOUT: !26 = !DILocation(line: 26, column: 3, scope: !16)
-// CHECK:STDOUT: !27 = !DILocation(line: 27, column: 3, scope: !16)
-// CHECK:STDOUT: !28 = !DILocation(line: 28, column: 3, scope: !16)
-// CHECK:STDOUT: !29 = !DILocation(line: 23, column: 1, scope: !16)
+// CHECK:STDOUT: !6 = !{null, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 1, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "OneVar_X", linkageName: "_COneVar_X.Main", scope: null, file: !3, line: 16, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null, !14}
+// CHECK:STDOUT: !14 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !15 = !{!16}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !11, type: !14)
+// CHECK:STDOUT: !17 = !DILocation(line: 16, column: 1, scope: !11)
+// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "TwoVars", linkageName: "_CTwoVars.Main", scope: null, file: !3, line: 18, type: !19, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !21)
+// CHECK:STDOUT: !19 = !DISubroutineType(types: !20)
+// CHECK:STDOUT: !20 = !{null, !7, !14}
+// CHECK:STDOUT: !21 = !{!22, !23}
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 1, scope: !18, type: !7)
+// CHECK:STDOUT: !23 = !DILocalVariable(arg: 2, scope: !18, type: !14)
+// CHECK:STDOUT: !24 = !DILocation(line: 18, column: 1, scope: !18)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "VarThenLet", linkageName: "_CVarThenLet.Main", scope: null, file: !3, line: 20, type: !19, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !26)
+// CHECK:STDOUT: !26 = !{!27, !28}
+// CHECK:STDOUT: !27 = !DILocalVariable(arg: 1, scope: !25, type: !7)
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 2, scope: !25, type: !14)
+// CHECK:STDOUT: !29 = !DILocation(line: 20, column: 1, scope: !25)
+// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "LetThenVar", linkageName: "_CLetThenVar.Main", scope: null, file: !3, line: 21, type: !19, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !31)
+// CHECK:STDOUT: !31 = !{!32, !33}
+// CHECK:STDOUT: !32 = !DILocalVariable(arg: 1, scope: !30, type: !7)
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 2, scope: !30, type: !14)
+// CHECK:STDOUT: !34 = !DILocation(line: 21, column: 1, scope: !30)
+// CHECK:STDOUT: !35 = distinct !DISubprogram(name: "Call", linkageName: "_CCall.Main", scope: null, file: !3, line: 23, type: !36, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !36 = !DISubroutineType(types: !37)
+// CHECK:STDOUT: !37 = !{null}
+// CHECK:STDOUT: !38 = !DILocation(line: 15, column: 15, scope: !35)
+// CHECK:STDOUT: !39 = !DILocation(line: 16, column: 13, scope: !35)
+// CHECK:STDOUT: !40 = !DILocation(line: 18, column: 12, scope: !35)
+// CHECK:STDOUT: !41 = !DILocation(line: 18, column: 24, scope: !35)
+// CHECK:STDOUT: !42 = !DILocation(line: 20, column: 15, scope: !35)
+// CHECK:STDOUT: !43 = !DILocation(line: 27, column: 17, scope: !35)
+// CHECK:STDOUT: !44 = !DILocation(line: 21, column: 23, scope: !35)
+// CHECK:STDOUT: !45 = !DILocation(line: 24, column: 3, scope: !35)
+// CHECK:STDOUT: !46 = !DILocation(line: 25, column: 3, scope: !35)
+// CHECK:STDOUT: !47 = !DILocation(line: 26, column: 3, scope: !35)
+// CHECK:STDOUT: !48 = !DILocation(line: 27, column: 3, scope: !35)
+// CHECK:STDOUT: !49 = !DILocation(line: 28, column: 3, scope: !35)
+// CHECK:STDOUT: !50 = !DILocation(line: 23, column: 1, scope: !35)

+ 30 - 16
toolchain/lower/testdata/function/generic/call.carbon

@@ -71,25 +71,25 @@ fn G() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_CF.Main.15b1f98bd9cc0c5b(ptr %x) #0 !dbg !19 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !20
+// CHECK:STDOUT:   ret void, !dbg !25
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.b88d1103f417c6d4(i32 %x) #0 !dbg !21 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.b88d1103f417c6d4(i32 %x) #0 !dbg !26 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !22
+// CHECK:STDOUT:   ret void, !dbg !32
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.d4b5665541d5d7a8(double %x) #0 !dbg !23 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.d4b5665541d5d7a8(double %x) #0 !dbg !33 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !24
+// CHECK:STDOUT:   ret void, !dbg !36
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.5754c7a55c7cbe4a(%type %x) #0 !dbg !25 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.5754c7a55c7cbe4a(%type %x) #0 !dbg !37 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !26
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -110,7 +110,7 @@ fn G() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 20, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 21, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 22, column: 3, scope: !4)
@@ -123,11 +123,25 @@ fn G() {
 // CHECK:STDOUT: !16 = !DILocation(line: 28, column: 3, scope: !4)
 // CHECK:STDOUT: !17 = !DILocation(line: 29, column: 3, scope: !4)
 // CHECK:STDOUT: !18 = !DILocation(line: 19, column: 1, scope: !4)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.15b1f98bd9cc0c5b", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DILocation(line: 13, column: 1, scope: !19)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.b88d1103f417c6d4", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 13, column: 1, scope: !21)
-// CHECK:STDOUT: !23 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d4b5665541d5d7a8", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !24 = !DILocation(line: 13, column: 1, scope: !23)
-// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5754c7a55c7cbe4a", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !26 = !DILocation(line: 13, column: 1, scope: !25)
+// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.15b1f98bd9cc0c5b", scope: null, file: !3, line: 13, type: !20, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !23)
+// CHECK:STDOUT: !20 = !DISubroutineType(types: !21)
+// CHECK:STDOUT: !21 = !{null, !22}
+// CHECK:STDOUT: !22 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !23 = !{!24}
+// CHECK:STDOUT: !24 = !DILocalVariable(arg: 1, scope: !19, type: !22)
+// CHECK:STDOUT: !25 = !DILocation(line: 13, column: 1, scope: !19)
+// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.b88d1103f417c6d4", scope: null, file: !3, line: 13, type: !27, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !30)
+// CHECK:STDOUT: !27 = !DISubroutineType(types: !28)
+// CHECK:STDOUT: !28 = !{null, !29}
+// CHECK:STDOUT: !29 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !30 = !{!31}
+// CHECK:STDOUT: !31 = !DILocalVariable(arg: 1, scope: !26, type: !29)
+// CHECK:STDOUT: !32 = !DILocation(line: 13, column: 1, scope: !26)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d4b5665541d5d7a8", scope: null, file: !3, line: 13, type: !20, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !34)
+// CHECK:STDOUT: !34 = !{!35}
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 1, scope: !33, type: !22)
+// CHECK:STDOUT: !36 = !DILocation(line: 13, column: 1, scope: !33)
+// CHECK:STDOUT: !37 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5754c7a55c7cbe4a", scope: null, file: !3, line: 13, type: !20, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !38)
+// CHECK:STDOUT: !38 = !{!39}
+// CHECK:STDOUT: !39 = !DILocalVariable(arg: 1, scope: !37, type: !22)
+// CHECK:STDOUT: !40 = !DILocation(line: 13, column: 1, scope: !37)

+ 217 - 187
toolchain/lower/testdata/function/generic/call_basic.carbon

@@ -67,34 +67,34 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @"_COp.C.Main:Copy.Core"(ptr sret({}) %return, ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @C.val.loc15_44, i64 0, i1 false), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @C.val.loc15_44, i64 0, i1 false), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CM.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CM.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !9
-// CHECK:STDOUT:   %m.var = alloca i32, align 4, !dbg !10
-// CHECK:STDOUT:   %p.var = alloca double, align 8, !dbg !11
-// CHECK:STDOUT:   %q.var = alloca double, align 8, !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !9
-// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %m.var), !dbg !10
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %p.var), !dbg !11
-// CHECK:STDOUT:   store double 1.000000e+00, ptr %p.var, align 8, !dbg !11
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %q.var), !dbg !12
-// CHECK:STDOUT:   %.loc54 = load i32, ptr %n.var, align 4, !dbg !13
-// CHECK:STDOUT:   call void @_CF.Main.b88d1103f417c6d4(i32 %.loc54), !dbg !14
-// CHECK:STDOUT:   %.loc55_9 = load i32, ptr %n.var, align 4, !dbg !15
-// CHECK:STDOUT:   %G.call.loc55 = call i32 @_CG.Main.d756e33fa3337243(i32 %.loc55_9), !dbg !16
-// CHECK:STDOUT:   store i32 %G.call.loc55, ptr %m.var, align 4, !dbg !17
-// CHECK:STDOUT:   %.loc56 = load double, ptr %p.var, align 8, !dbg !18
-// CHECK:STDOUT:   call void @_CF.Main.d4b5665541d5d7a8(double %.loc56), !dbg !19
-// CHECK:STDOUT:   %.loc57_9 = load double, ptr %p.var, align 8, !dbg !20
-// CHECK:STDOUT:   %G.call.loc57 = call double @_CG.Main.6765264419ed942e(double %.loc57_9), !dbg !21
-// CHECK:STDOUT:   store double %G.call.loc57, ptr %q.var, align 8, !dbg !22
-// CHECK:STDOUT:   ret void, !dbg !23
+// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !14
+// CHECK:STDOUT:   %m.var = alloca i32, align 4, !dbg !15
+// CHECK:STDOUT:   %p.var = alloca double, align 8, !dbg !16
+// CHECK:STDOUT:   %q.var = alloca double, align 8, !dbg !17
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !14
+// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %m.var), !dbg !15
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %p.var), !dbg !16
+// CHECK:STDOUT:   store double 1.000000e+00, ptr %p.var, align 8, !dbg !16
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %q.var), !dbg !17
+// CHECK:STDOUT:   %.loc54 = load i32, ptr %n.var, align 4, !dbg !18
+// CHECK:STDOUT:   call void @_CF.Main.b88d1103f417c6d4(i32 %.loc54), !dbg !19
+// CHECK:STDOUT:   %.loc55_9 = load i32, ptr %n.var, align 4, !dbg !20
+// CHECK:STDOUT:   %G.call.loc55 = call i32 @_CG.Main.d756e33fa3337243(i32 %.loc55_9), !dbg !21
+// CHECK:STDOUT:   store i32 %G.call.loc55, ptr %m.var, align 4, !dbg !22
+// CHECK:STDOUT:   %.loc56 = load double, ptr %p.var, align 8, !dbg !23
+// CHECK:STDOUT:   call void @_CF.Main.d4b5665541d5d7a8(double %.loc56), !dbg !24
+// CHECK:STDOUT:   %.loc57_9 = load double, ptr %p.var, align 8, !dbg !25
+// CHECK:STDOUT:   %G.call.loc57 = call double @_CG.Main.6765264419ed942e(double %.loc57_9), !dbg !26
+// CHECK:STDOUT:   store double %G.call.loc57, ptr %q.var, align 8, !dbg !27
+// CHECK:STDOUT:   ret void, !dbg !28
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -104,128 +104,128 @@ fn M() {
 // CHECK:STDOUT: declare void @llvm.lifetime.start.p0(ptr captures(none)) #2
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.b88d1103f417c6d4(i32 %x) #0 !dbg !24 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.b88d1103f417c6d4(i32 %x) #0 !dbg !29 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !25
+// CHECK:STDOUT:   ret void, !dbg !35
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.d756e33fa3337243(i32 %x) #0 !dbg !26 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.d756e33fa3337243(i32 %x) #0 !dbg !36 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc29_6.3.temp = alloca i32, align 4, !dbg !27
-// CHECK:STDOUT:   %.loc31_8.3.temp = alloca i32, align 4, !dbg !28
-// CHECK:STDOUT:   %.loc31_9.3.temp = alloca i32, align 4, !dbg !29
-// CHECK:STDOUT:   %var_f64.var = alloca double, align 8, !dbg !30
-// CHECK:STDOUT:   %ptr_i32.var = alloca ptr, align 8, !dbg !31
-// CHECK:STDOUT:   %ptr_f64.var = alloca ptr, align 8, !dbg !32
-// CHECK:STDOUT:   %ptr_i8.var = alloca ptr, align 8, !dbg !33
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !34
-// CHECK:STDOUT:   %.loc43_6.3.temp = alloca {}, align 8, !dbg !35
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc29_6.3.temp), !dbg !27
-// CHECK:STDOUT:   %H.call.loc29 = call i32 @_CH.Main.5450dc8e8b8e0899(i32 %x), !dbg !27
-// CHECK:STDOUT:   store i32 %H.call.loc29, ptr %.loc29_6.3.temp, align 4, !dbg !27
-// CHECK:STDOUT:   %H.call.loc30 = call %type @_CH.Main.402deed6b8733082(%type zeroinitializer), !dbg !36
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_8.3.temp), !dbg !28
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.d756e33fa3337243(i32 %x), !dbg !28
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_9.3.temp), !dbg !29
-// CHECK:STDOUT:   store i32 %G.call, ptr %.loc31_8.3.temp, align 4, !dbg !28
-// CHECK:STDOUT:   %.loc31_8.5 = load i32, ptr %.loc31_8.3.temp, align 4, !dbg !28
-// CHECK:STDOUT:   %H.call.loc31 = call i32 @_CH.Main.5450dc8e8b8e0899(i32 %.loc31_8.5), !dbg !29
-// CHECK:STDOUT:   store i32 %H.call.loc31, ptr %.loc31_9.3.temp, align 4, !dbg !29
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %var_f64.var), !dbg !30
-// CHECK:STDOUT:   %.loc35_5 = load double, ptr %var_f64.var, align 8, !dbg !37
-// CHECK:STDOUT:   %H.call.loc35 = call double @_CH.Main.83aece103b0a8681(double %.loc35_5), !dbg !38
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i32.var), !dbg !31
-// CHECK:STDOUT:   %.loc37_5 = load ptr, ptr %ptr_i32.var, align 8, !dbg !39
-// CHECK:STDOUT:   %H.call.loc37 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc37_5), !dbg !40
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_f64.var), !dbg !32
-// CHECK:STDOUT:   %.loc39_5 = load ptr, ptr %ptr_f64.var, align 8, !dbg !41
-// CHECK:STDOUT:   %H.call.loc39 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc39_5), !dbg !42
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i8.var), !dbg !33
-// CHECK:STDOUT:   %.loc41_5 = load ptr, ptr %ptr_i8.var, align 8, !dbg !43
-// CHECK:STDOUT:   %H.call.loc41 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc41_5), !dbg !44
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !34
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc43_6.3.temp), !dbg !35
-// CHECK:STDOUT:   call void @_CH.Main.936d996ea935415c(ptr %.loc43_6.3.temp, ptr %c.var), !dbg !35
-// CHECK:STDOUT:   ret i32 %x, !dbg !45
+// CHECK:STDOUT:   %.loc29_6.3.temp = alloca i32, align 4, !dbg !41
+// CHECK:STDOUT:   %.loc31_8.3.temp = alloca i32, align 4, !dbg !42
+// CHECK:STDOUT:   %.loc31_9.3.temp = alloca i32, align 4, !dbg !43
+// CHECK:STDOUT:   %var_f64.var = alloca double, align 8, !dbg !44
+// CHECK:STDOUT:   %ptr_i32.var = alloca ptr, align 8, !dbg !45
+// CHECK:STDOUT:   %ptr_f64.var = alloca ptr, align 8, !dbg !46
+// CHECK:STDOUT:   %ptr_i8.var = alloca ptr, align 8, !dbg !47
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !48
+// CHECK:STDOUT:   %.loc43_6.3.temp = alloca {}, align 8, !dbg !49
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc29_6.3.temp), !dbg !41
+// CHECK:STDOUT:   %H.call.loc29 = call i32 @_CH.Main.5450dc8e8b8e0899(i32 %x), !dbg !41
+// CHECK:STDOUT:   store i32 %H.call.loc29, ptr %.loc29_6.3.temp, align 4, !dbg !41
+// CHECK:STDOUT:   %H.call.loc30 = call %type @_CH.Main.402deed6b8733082(%type zeroinitializer), !dbg !50
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_8.3.temp), !dbg !42
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.d756e33fa3337243(i32 %x), !dbg !42
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_9.3.temp), !dbg !43
+// CHECK:STDOUT:   store i32 %G.call, ptr %.loc31_8.3.temp, align 4, !dbg !42
+// CHECK:STDOUT:   %.loc31_8.5 = load i32, ptr %.loc31_8.3.temp, align 4, !dbg !42
+// CHECK:STDOUT:   %H.call.loc31 = call i32 @_CH.Main.5450dc8e8b8e0899(i32 %.loc31_8.5), !dbg !43
+// CHECK:STDOUT:   store i32 %H.call.loc31, ptr %.loc31_9.3.temp, align 4, !dbg !43
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %var_f64.var), !dbg !44
+// CHECK:STDOUT:   %.loc35_5 = load double, ptr %var_f64.var, align 8, !dbg !51
+// CHECK:STDOUT:   %H.call.loc35 = call double @_CH.Main.83aece103b0a8681(double %.loc35_5), !dbg !52
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i32.var), !dbg !45
+// CHECK:STDOUT:   %.loc37_5 = load ptr, ptr %ptr_i32.var, align 8, !dbg !53
+// CHECK:STDOUT:   %H.call.loc37 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc37_5), !dbg !54
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_f64.var), !dbg !46
+// CHECK:STDOUT:   %.loc39_5 = load ptr, ptr %ptr_f64.var, align 8, !dbg !55
+// CHECK:STDOUT:   %H.call.loc39 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc39_5), !dbg !56
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i8.var), !dbg !47
+// CHECK:STDOUT:   %.loc41_5 = load ptr, ptr %ptr_i8.var, align 8, !dbg !57
+// CHECK:STDOUT:   %H.call.loc41 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc41_5), !dbg !58
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !48
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc43_6.3.temp), !dbg !49
+// CHECK:STDOUT:   call void @_CH.Main.936d996ea935415c(ptr %.loc43_6.3.temp, ptr %c.var), !dbg !49
+// CHECK:STDOUT:   ret i32 %x, !dbg !59
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.d4b5665541d5d7a8(double %x) #0 !dbg !46 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.d4b5665541d5d7a8(double %x) #0 !dbg !60 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !47
+// CHECK:STDOUT:   ret void, !dbg !65
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CG.Main.6765264419ed942e(double %x) #0 !dbg !48 {
+// CHECK:STDOUT: define linkonce_odr double @_CG.Main.6765264419ed942e(double %x) #0 !dbg !66 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc29_6.3.temp = alloca double, align 8, !dbg !49
-// CHECK:STDOUT:   %.loc31_8.3.temp = alloca double, align 8, !dbg !50
-// CHECK:STDOUT:   %.loc31_9.3.temp = alloca double, align 8, !dbg !51
-// CHECK:STDOUT:   %var_f64.var = alloca double, align 8, !dbg !52
-// CHECK:STDOUT:   %ptr_i32.var = alloca ptr, align 8, !dbg !53
-// CHECK:STDOUT:   %ptr_f64.var = alloca ptr, align 8, !dbg !54
-// CHECK:STDOUT:   %ptr_i8.var = alloca ptr, align 8, !dbg !55
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !56
-// CHECK:STDOUT:   %.loc43_6.3.temp = alloca {}, align 8, !dbg !57
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc29_6.3.temp), !dbg !49
-// CHECK:STDOUT:   %H.call.loc29 = call double @_CH.Main.83aece103b0a8681(double %x), !dbg !49
-// CHECK:STDOUT:   store double %H.call.loc29, ptr %.loc29_6.3.temp, align 8, !dbg !49
-// CHECK:STDOUT:   %H.call.loc30 = call %type @_CH.Main.402deed6b8733082(%type zeroinitializer), !dbg !58
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_8.3.temp), !dbg !50
-// CHECK:STDOUT:   %G.call = call double @_CG.Main.6765264419ed942e(double %x), !dbg !50
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_9.3.temp), !dbg !51
-// CHECK:STDOUT:   store double %G.call, ptr %.loc31_8.3.temp, align 8, !dbg !50
-// CHECK:STDOUT:   %.loc31_8.5 = load double, ptr %.loc31_8.3.temp, align 8, !dbg !50
-// CHECK:STDOUT:   %H.call.loc31 = call double @_CH.Main.83aece103b0a8681(double %.loc31_8.5), !dbg !51
-// CHECK:STDOUT:   store double %H.call.loc31, ptr %.loc31_9.3.temp, align 8, !dbg !51
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %var_f64.var), !dbg !52
-// CHECK:STDOUT:   %.loc35_5 = load double, ptr %var_f64.var, align 8, !dbg !59
-// CHECK:STDOUT:   %H.call.loc35 = call double @_CH.Main.83aece103b0a8681(double %.loc35_5), !dbg !60
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i32.var), !dbg !53
-// CHECK:STDOUT:   %.loc37_5 = load ptr, ptr %ptr_i32.var, align 8, !dbg !61
-// CHECK:STDOUT:   %H.call.loc37 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc37_5), !dbg !62
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_f64.var), !dbg !54
-// CHECK:STDOUT:   %.loc39_5 = load ptr, ptr %ptr_f64.var, align 8, !dbg !63
-// CHECK:STDOUT:   %H.call.loc39 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc39_5), !dbg !64
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i8.var), !dbg !55
-// CHECK:STDOUT:   %.loc41_5 = load ptr, ptr %ptr_i8.var, align 8, !dbg !65
-// CHECK:STDOUT:   %H.call.loc41 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc41_5), !dbg !66
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !56
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc43_6.3.temp), !dbg !57
-// CHECK:STDOUT:   call void @_CH.Main.936d996ea935415c(ptr %.loc43_6.3.temp, ptr %c.var), !dbg !57
-// CHECK:STDOUT:   ret double %x, !dbg !67
+// CHECK:STDOUT:   %.loc29_6.3.temp = alloca double, align 8, !dbg !69
+// CHECK:STDOUT:   %.loc31_8.3.temp = alloca double, align 8, !dbg !70
+// CHECK:STDOUT:   %.loc31_9.3.temp = alloca double, align 8, !dbg !71
+// CHECK:STDOUT:   %var_f64.var = alloca double, align 8, !dbg !72
+// CHECK:STDOUT:   %ptr_i32.var = alloca ptr, align 8, !dbg !73
+// CHECK:STDOUT:   %ptr_f64.var = alloca ptr, align 8, !dbg !74
+// CHECK:STDOUT:   %ptr_i8.var = alloca ptr, align 8, !dbg !75
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !76
+// CHECK:STDOUT:   %.loc43_6.3.temp = alloca {}, align 8, !dbg !77
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc29_6.3.temp), !dbg !69
+// CHECK:STDOUT:   %H.call.loc29 = call double @_CH.Main.83aece103b0a8681(double %x), !dbg !69
+// CHECK:STDOUT:   store double %H.call.loc29, ptr %.loc29_6.3.temp, align 8, !dbg !69
+// CHECK:STDOUT:   %H.call.loc30 = call %type @_CH.Main.402deed6b8733082(%type zeroinitializer), !dbg !78
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_8.3.temp), !dbg !70
+// CHECK:STDOUT:   %G.call = call double @_CG.Main.6765264419ed942e(double %x), !dbg !70
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc31_9.3.temp), !dbg !71
+// CHECK:STDOUT:   store double %G.call, ptr %.loc31_8.3.temp, align 8, !dbg !70
+// CHECK:STDOUT:   %.loc31_8.5 = load double, ptr %.loc31_8.3.temp, align 8, !dbg !70
+// CHECK:STDOUT:   %H.call.loc31 = call double @_CH.Main.83aece103b0a8681(double %.loc31_8.5), !dbg !71
+// CHECK:STDOUT:   store double %H.call.loc31, ptr %.loc31_9.3.temp, align 8, !dbg !71
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %var_f64.var), !dbg !72
+// CHECK:STDOUT:   %.loc35_5 = load double, ptr %var_f64.var, align 8, !dbg !79
+// CHECK:STDOUT:   %H.call.loc35 = call double @_CH.Main.83aece103b0a8681(double %.loc35_5), !dbg !80
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i32.var), !dbg !73
+// CHECK:STDOUT:   %.loc37_5 = load ptr, ptr %ptr_i32.var, align 8, !dbg !81
+// CHECK:STDOUT:   %H.call.loc37 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc37_5), !dbg !82
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_f64.var), !dbg !74
+// CHECK:STDOUT:   %.loc39_5 = load ptr, ptr %ptr_f64.var, align 8, !dbg !83
+// CHECK:STDOUT:   %H.call.loc39 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc39_5), !dbg !84
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i8.var), !dbg !75
+// CHECK:STDOUT:   %.loc41_5 = load ptr, ptr %ptr_i8.var, align 8, !dbg !85
+// CHECK:STDOUT:   %H.call.loc41 = call ptr @_CH.Main.0a952f8bcc623ce6(ptr %.loc41_5), !dbg !86
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !76
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc43_6.3.temp), !dbg !77
+// CHECK:STDOUT:   call void @_CH.Main.936d996ea935415c(ptr %.loc43_6.3.temp, ptr %c.var), !dbg !77
+// CHECK:STDOUT:   ret double %x, !dbg !87
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CH.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !68 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CH.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !88 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %x, !dbg !69
+// CHECK:STDOUT:   ret i32 %x, !dbg !91
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr %type @_CH.Main.402deed6b8733082(%type %x) #0 !dbg !70 {
+// CHECK:STDOUT: define linkonce_odr %type @_CH.Main.402deed6b8733082(%type %x) #0 !dbg !92 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret %type %x, !dbg !71
+// CHECK:STDOUT:   ret %type %x, !dbg !95
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CH.Main.83aece103b0a8681(double %x) #0 !dbg !72 {
+// CHECK:STDOUT: define linkonce_odr double @_CH.Main.83aece103b0a8681(double %x) #0 !dbg !96 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret double %x, !dbg !73
+// CHECK:STDOUT:   ret double %x, !dbg !99
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CH.Main.0a952f8bcc623ce6(ptr %x) #0 !dbg !74 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CH.Main.0a952f8bcc623ce6(ptr %x) #0 !dbg !100 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret ptr %x, !dbg !75
+// CHECK:STDOUT:   ret ptr %x, !dbg !103
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CH.Main.936d996ea935415c(ptr sret({}) %return, ptr %x) #0 !dbg !76 {
+// CHECK:STDOUT: define linkonce_odr void @_CH.Main.936d996ea935415c(ptr sret({}) %return, ptr %x) #0 !dbg !104 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @"_COp.C.Main:Copy.Core"(ptr %return, ptr %x), !dbg !77
-// CHECK:STDOUT:   ret void, !dbg !78
+// CHECK:STDOUT:   call void @"_COp.C.Main:Copy.Core"(ptr %return, ptr %x), !dbg !107
+// CHECK:STDOUT:   ret void, !dbg !108
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -247,78 +247,108 @@ fn M() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_basic.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.C.Main:Copy.Core", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.C.Main:Copy.Core", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 15, column: 35, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 48, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 49, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 50, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 51, column: 3, scope: !8)
-// CHECK:STDOUT: !12 = !DILocation(line: 52, column: 3, scope: !8)
-// CHECK:STDOUT: !13 = !DILocation(line: 54, column: 5, scope: !8)
-// CHECK:STDOUT: !14 = !DILocation(line: 54, column: 3, scope: !8)
-// CHECK:STDOUT: !15 = !DILocation(line: 55, column: 9, scope: !8)
-// CHECK:STDOUT: !16 = !DILocation(line: 55, column: 7, scope: !8)
-// CHECK:STDOUT: !17 = !DILocation(line: 55, column: 3, scope: !8)
-// CHECK:STDOUT: !18 = !DILocation(line: 56, column: 5, scope: !8)
-// CHECK:STDOUT: !19 = !DILocation(line: 56, column: 3, scope: !8)
-// CHECK:STDOUT: !20 = !DILocation(line: 57, column: 9, scope: !8)
-// CHECK:STDOUT: !21 = !DILocation(line: 57, column: 7, scope: !8)
-// CHECK:STDOUT: !22 = !DILocation(line: 57, column: 3, scope: !8)
-// CHECK:STDOUT: !23 = !DILocation(line: 48, column: 1, scope: !8)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.b88d1103f417c6d4", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 19, column: 1, scope: !24)
-// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.d756e33fa3337243", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !27 = !DILocation(line: 29, column: 3, scope: !26)
-// CHECK:STDOUT: !28 = !DILocation(line: 31, column: 5, scope: !26)
-// CHECK:STDOUT: !29 = !DILocation(line: 31, column: 3, scope: !26)
-// CHECK:STDOUT: !30 = !DILocation(line: 34, column: 3, scope: !26)
-// CHECK:STDOUT: !31 = !DILocation(line: 36, column: 3, scope: !26)
-// CHECK:STDOUT: !32 = !DILocation(line: 38, column: 3, scope: !26)
-// CHECK:STDOUT: !33 = !DILocation(line: 40, column: 3, scope: !26)
-// CHECK:STDOUT: !34 = !DILocation(line: 42, column: 3, scope: !26)
-// CHECK:STDOUT: !35 = !DILocation(line: 43, column: 3, scope: !26)
-// CHECK:STDOUT: !36 = !DILocation(line: 30, column: 3, scope: !26)
-// CHECK:STDOUT: !37 = !DILocation(line: 35, column: 5, scope: !26)
-// CHECK:STDOUT: !38 = !DILocation(line: 35, column: 3, scope: !26)
-// CHECK:STDOUT: !39 = !DILocation(line: 37, column: 5, scope: !26)
-// CHECK:STDOUT: !40 = !DILocation(line: 37, column: 3, scope: !26)
-// CHECK:STDOUT: !41 = !DILocation(line: 39, column: 5, scope: !26)
-// CHECK:STDOUT: !42 = !DILocation(line: 39, column: 3, scope: !26)
-// CHECK:STDOUT: !43 = !DILocation(line: 41, column: 5, scope: !26)
-// CHECK:STDOUT: !44 = !DILocation(line: 41, column: 3, scope: !26)
-// CHECK:STDOUT: !45 = !DILocation(line: 45, column: 3, scope: !26)
-// CHECK:STDOUT: !46 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d4b5665541d5d7a8", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !47 = !DILocation(line: 19, column: 1, scope: !46)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.6765264419ed942e", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 29, column: 3, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 31, column: 5, scope: !48)
-// CHECK:STDOUT: !51 = !DILocation(line: 31, column: 3, scope: !48)
-// CHECK:STDOUT: !52 = !DILocation(line: 34, column: 3, scope: !48)
-// CHECK:STDOUT: !53 = !DILocation(line: 36, column: 3, scope: !48)
-// CHECK:STDOUT: !54 = !DILocation(line: 38, column: 3, scope: !48)
-// CHECK:STDOUT: !55 = !DILocation(line: 40, column: 3, scope: !48)
-// CHECK:STDOUT: !56 = !DILocation(line: 42, column: 3, scope: !48)
-// CHECK:STDOUT: !57 = !DILocation(line: 43, column: 3, scope: !48)
-// CHECK:STDOUT: !58 = !DILocation(line: 30, column: 3, scope: !48)
-// CHECK:STDOUT: !59 = !DILocation(line: 35, column: 5, scope: !48)
-// CHECK:STDOUT: !60 = !DILocation(line: 35, column: 3, scope: !48)
-// CHECK:STDOUT: !61 = !DILocation(line: 37, column: 5, scope: !48)
-// CHECK:STDOUT: !62 = !DILocation(line: 37, column: 3, scope: !48)
-// CHECK:STDOUT: !63 = !DILocation(line: 39, column: 5, scope: !48)
-// CHECK:STDOUT: !64 = !DILocation(line: 39, column: 3, scope: !48)
-// CHECK:STDOUT: !65 = !DILocation(line: 41, column: 5, scope: !48)
-// CHECK:STDOUT: !66 = !DILocation(line: 41, column: 3, scope: !48)
-// CHECK:STDOUT: !67 = !DILocation(line: 45, column: 3, scope: !48)
-// CHECK:STDOUT: !68 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !69 = !DILocation(line: 23, column: 3, scope: !68)
-// CHECK:STDOUT: !70 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.402deed6b8733082", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !71 = !DILocation(line: 23, column: 3, scope: !70)
-// CHECK:STDOUT: !72 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.83aece103b0a8681", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !73 = !DILocation(line: 23, column: 3, scope: !72)
-// CHECK:STDOUT: !74 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !75 = !DILocation(line: 23, column: 3, scope: !74)
-// CHECK:STDOUT: !76 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.936d996ea935415c", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !77 = !DILocation(line: 23, column: 10, scope: !76)
-// CHECK:STDOUT: !78 = !DILocation(line: 23, column: 3, scope: !76)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 35, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 48, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 49, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 50, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 51, column: 3, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 52, column: 3, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 54, column: 5, scope: !11)
+// CHECK:STDOUT: !19 = !DILocation(line: 54, column: 3, scope: !11)
+// CHECK:STDOUT: !20 = !DILocation(line: 55, column: 9, scope: !11)
+// CHECK:STDOUT: !21 = !DILocation(line: 55, column: 7, scope: !11)
+// CHECK:STDOUT: !22 = !DILocation(line: 55, column: 3, scope: !11)
+// CHECK:STDOUT: !23 = !DILocation(line: 56, column: 5, scope: !11)
+// CHECK:STDOUT: !24 = !DILocation(line: 56, column: 3, scope: !11)
+// CHECK:STDOUT: !25 = !DILocation(line: 57, column: 9, scope: !11)
+// CHECK:STDOUT: !26 = !DILocation(line: 57, column: 7, scope: !11)
+// CHECK:STDOUT: !27 = !DILocation(line: 57, column: 3, scope: !11)
+// CHECK:STDOUT: !28 = !DILocation(line: 48, column: 1, scope: !11)
+// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.b88d1103f417c6d4", scope: null, file: !3, line: 19, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !33)
+// CHECK:STDOUT: !30 = !DISubroutineType(types: !31)
+// CHECK:STDOUT: !31 = !{null, !32}
+// CHECK:STDOUT: !32 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !33 = !{!34}
+// CHECK:STDOUT: !34 = !DILocalVariable(arg: 1, scope: !29, type: !32)
+// CHECK:STDOUT: !35 = !DILocation(line: 19, column: 1, scope: !29)
+// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.d756e33fa3337243", scope: null, file: !3, line: 28, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !39)
+// CHECK:STDOUT: !37 = !DISubroutineType(types: !38)
+// CHECK:STDOUT: !38 = !{!32, !32}
+// CHECK:STDOUT: !39 = !{!40}
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 1, scope: !36, type: !32)
+// CHECK:STDOUT: !41 = !DILocation(line: 29, column: 3, scope: !36)
+// CHECK:STDOUT: !42 = !DILocation(line: 31, column: 5, scope: !36)
+// CHECK:STDOUT: !43 = !DILocation(line: 31, column: 3, scope: !36)
+// CHECK:STDOUT: !44 = !DILocation(line: 34, column: 3, scope: !36)
+// CHECK:STDOUT: !45 = !DILocation(line: 36, column: 3, scope: !36)
+// CHECK:STDOUT: !46 = !DILocation(line: 38, column: 3, scope: !36)
+// CHECK:STDOUT: !47 = !DILocation(line: 40, column: 3, scope: !36)
+// CHECK:STDOUT: !48 = !DILocation(line: 42, column: 3, scope: !36)
+// CHECK:STDOUT: !49 = !DILocation(line: 43, column: 3, scope: !36)
+// CHECK:STDOUT: !50 = !DILocation(line: 30, column: 3, scope: !36)
+// CHECK:STDOUT: !51 = !DILocation(line: 35, column: 5, scope: !36)
+// CHECK:STDOUT: !52 = !DILocation(line: 35, column: 3, scope: !36)
+// CHECK:STDOUT: !53 = !DILocation(line: 37, column: 5, scope: !36)
+// CHECK:STDOUT: !54 = !DILocation(line: 37, column: 3, scope: !36)
+// CHECK:STDOUT: !55 = !DILocation(line: 39, column: 5, scope: !36)
+// CHECK:STDOUT: !56 = !DILocation(line: 39, column: 3, scope: !36)
+// CHECK:STDOUT: !57 = !DILocation(line: 41, column: 5, scope: !36)
+// CHECK:STDOUT: !58 = !DILocation(line: 41, column: 3, scope: !36)
+// CHECK:STDOUT: !59 = !DILocation(line: 45, column: 3, scope: !36)
+// CHECK:STDOUT: !60 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d4b5665541d5d7a8", scope: null, file: !3, line: 19, type: !61, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !63)
+// CHECK:STDOUT: !61 = !DISubroutineType(types: !62)
+// CHECK:STDOUT: !62 = !{null, !7}
+// CHECK:STDOUT: !63 = !{!64}
+// CHECK:STDOUT: !64 = !DILocalVariable(arg: 1, scope: !60, type: !7)
+// CHECK:STDOUT: !65 = !DILocation(line: 19, column: 1, scope: !60)
+// CHECK:STDOUT: !66 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.6765264419ed942e", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !67)
+// CHECK:STDOUT: !67 = !{!68}
+// CHECK:STDOUT: !68 = !DILocalVariable(arg: 1, scope: !66, type: !7)
+// CHECK:STDOUT: !69 = !DILocation(line: 29, column: 3, scope: !66)
+// CHECK:STDOUT: !70 = !DILocation(line: 31, column: 5, scope: !66)
+// CHECK:STDOUT: !71 = !DILocation(line: 31, column: 3, scope: !66)
+// CHECK:STDOUT: !72 = !DILocation(line: 34, column: 3, scope: !66)
+// CHECK:STDOUT: !73 = !DILocation(line: 36, column: 3, scope: !66)
+// CHECK:STDOUT: !74 = !DILocation(line: 38, column: 3, scope: !66)
+// CHECK:STDOUT: !75 = !DILocation(line: 40, column: 3, scope: !66)
+// CHECK:STDOUT: !76 = !DILocation(line: 42, column: 3, scope: !66)
+// CHECK:STDOUT: !77 = !DILocation(line: 43, column: 3, scope: !66)
+// CHECK:STDOUT: !78 = !DILocation(line: 30, column: 3, scope: !66)
+// CHECK:STDOUT: !79 = !DILocation(line: 35, column: 5, scope: !66)
+// CHECK:STDOUT: !80 = !DILocation(line: 35, column: 3, scope: !66)
+// CHECK:STDOUT: !81 = !DILocation(line: 37, column: 5, scope: !66)
+// CHECK:STDOUT: !82 = !DILocation(line: 37, column: 3, scope: !66)
+// CHECK:STDOUT: !83 = !DILocation(line: 39, column: 5, scope: !66)
+// CHECK:STDOUT: !84 = !DILocation(line: 39, column: 3, scope: !66)
+// CHECK:STDOUT: !85 = !DILocation(line: 41, column: 5, scope: !66)
+// CHECK:STDOUT: !86 = !DILocation(line: 41, column: 3, scope: !66)
+// CHECK:STDOUT: !87 = !DILocation(line: 45, column: 3, scope: !66)
+// CHECK:STDOUT: !88 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 22, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !89)
+// CHECK:STDOUT: !89 = !{!90}
+// CHECK:STDOUT: !90 = !DILocalVariable(arg: 1, scope: !88, type: !32)
+// CHECK:STDOUT: !91 = !DILocation(line: 23, column: 3, scope: !88)
+// CHECK:STDOUT: !92 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.402deed6b8733082", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !93)
+// CHECK:STDOUT: !93 = !{!94}
+// CHECK:STDOUT: !94 = !DILocalVariable(arg: 1, scope: !92, type: !7)
+// CHECK:STDOUT: !95 = !DILocation(line: 23, column: 3, scope: !92)
+// CHECK:STDOUT: !96 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.83aece103b0a8681", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !97)
+// CHECK:STDOUT: !97 = !{!98}
+// CHECK:STDOUT: !98 = !DILocalVariable(arg: 1, scope: !96, type: !7)
+// CHECK:STDOUT: !99 = !DILocation(line: 23, column: 3, scope: !96)
+// CHECK:STDOUT: !100 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !101)
+// CHECK:STDOUT: !101 = !{!102}
+// CHECK:STDOUT: !102 = !DILocalVariable(arg: 1, scope: !100, type: !7)
+// CHECK:STDOUT: !103 = !DILocation(line: 23, column: 3, scope: !100)
+// CHECK:STDOUT: !104 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.936d996ea935415c", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !105)
+// CHECK:STDOUT: !105 = !{!106}
+// CHECK:STDOUT: !106 = !DILocalVariable(arg: 1, scope: !104, type: !7)
+// CHECK:STDOUT: !107 = !DILocation(line: 23, column: 10, scope: !104)
+// CHECK:STDOUT: !108 = !DILocation(line: 23, column: 3, scope: !104)

+ 32 - 21
toolchain/lower/testdata/function/generic/call_basic_depth.carbon

@@ -60,25 +60,25 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_CF.Main.b88d1103f417c6d4(i32 %x) #0 !dbg !15 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !16
+// CHECK:STDOUT:   ret void, !dbg !21
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.d756e33fa3337243(i32 %x) #0 !dbg !17 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.d756e33fa3337243(i32 %x) #0 !dbg !22 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc25_6.3.temp = alloca i32, align 4, !dbg !18
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc25_6.3.temp), !dbg !18
-// CHECK:STDOUT:   %H.call = call i32 @_CH.Main.5450dc8e8b8e0899(i32 %x), !dbg !18
-// CHECK:STDOUT:   store i32 %H.call, ptr %.loc25_6.3.temp, align 4, !dbg !18
-// CHECK:STDOUT:   call void @_CF.Main.b88d1103f417c6d4(i32 %x), !dbg !19
-// CHECK:STDOUT:   ret i32 %x, !dbg !20
+// CHECK:STDOUT:   %.loc25_6.3.temp = alloca i32, align 4, !dbg !27
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc25_6.3.temp), !dbg !27
+// CHECK:STDOUT:   %H.call = call i32 @_CH.Main.5450dc8e8b8e0899(i32 %x), !dbg !27
+// CHECK:STDOUT:   store i32 %H.call, ptr %.loc25_6.3.temp, align 4, !dbg !27
+// CHECK:STDOUT:   call void @_CF.Main.b88d1103f417c6d4(i32 %x), !dbg !28
+// CHECK:STDOUT:   ret i32 %x, !dbg !29
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CH.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !21 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CH.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !30 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main.b88d1103f417c6d4(i32 %x), !dbg !22
-// CHECK:STDOUT:   ret i32 %x, !dbg !23
+// CHECK:STDOUT:   call void @_CF.Main.b88d1103f417c6d4(i32 %x), !dbg !33
+// CHECK:STDOUT:   ret i32 %x, !dbg !34
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -96,7 +96,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_basic_depth.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 31, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 32, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 34, column: 5, scope: !4)
@@ -105,12 +105,23 @@ fn M() {
 // CHECK:STDOUT: !12 = !DILocation(line: 35, column: 7, scope: !4)
 // CHECK:STDOUT: !13 = !DILocation(line: 35, column: 3, scope: !4)
 // CHECK:STDOUT: !14 = !DILocation(line: 30, column: 1, scope: !4)
-// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.b88d1103f417c6d4", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !16 = !DILocation(line: 16, column: 1, scope: !15)
-// CHECK:STDOUT: !17 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.d756e33fa3337243", scope: null, file: !3, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !18 = !DILocation(line: 25, column: 3, scope: !17)
-// CHECK:STDOUT: !19 = !DILocation(line: 26, column: 3, scope: !17)
-// CHECK:STDOUT: !20 = !DILocation(line: 27, column: 3, scope: !17)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 20, column: 3, scope: !21)
-// CHECK:STDOUT: !23 = !DILocation(line: 21, column: 3, scope: !21)
+// CHECK:STDOUT: !15 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.b88d1103f417c6d4", scope: null, file: !3, line: 16, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !19)
+// CHECK:STDOUT: !16 = !DISubroutineType(types: !17)
+// CHECK:STDOUT: !17 = !{null, !18}
+// CHECK:STDOUT: !18 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !19 = !{!20}
+// CHECK:STDOUT: !20 = !DILocalVariable(arg: 1, scope: !15, type: !18)
+// CHECK:STDOUT: !21 = !DILocation(line: 16, column: 1, scope: !15)
+// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.d756e33fa3337243", scope: null, file: !3, line: 24, type: !23, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !25)
+// CHECK:STDOUT: !23 = !DISubroutineType(types: !24)
+// CHECK:STDOUT: !24 = !{!18, !18}
+// CHECK:STDOUT: !25 = !{!26}
+// CHECK:STDOUT: !26 = !DILocalVariable(arg: 1, scope: !22, type: !18)
+// CHECK:STDOUT: !27 = !DILocation(line: 25, column: 3, scope: !22)
+// CHECK:STDOUT: !28 = !DILocation(line: 26, column: 3, scope: !22)
+// CHECK:STDOUT: !29 = !DILocation(line: 27, column: 3, scope: !22)
+// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 19, type: !23, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !31)
+// CHECK:STDOUT: !31 = !{!32}
+// CHECK:STDOUT: !32 = !DILocalVariable(arg: 1, scope: !30, type: !18)
+// CHECK:STDOUT: !33 = !DILocation(line: 20, column: 3, scope: !30)
+// CHECK:STDOUT: !34 = !DILocation(line: 21, column: 3, scope: !30)

+ 9 - 4
toolchain/lower/testdata/function/generic/call_dedup_ptr.carbon

@@ -50,7 +50,7 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x) #0 !dbg !17 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret ptr %x, !dbg !18
+// CHECK:STDOUT:   ret ptr %x, !dbg !23
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -69,7 +69,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_dedup_ptr.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 18, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 20, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 22, column: 3, scope: !4)
@@ -80,5 +80,10 @@ fn M() {
 // CHECK:STDOUT: !14 = !DILocation(line: 23, column: 5, scope: !4)
 // CHECK:STDOUT: !15 = !DILocation(line: 23, column: 3, scope: !4)
 // CHECK:STDOUT: !16 = !DILocation(line: 17, column: 1, scope: !4)
-// CHECK:STDOUT: !17 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !18 = !DILocation(line: 14, column: 3, scope: !17)
+// CHECK:STDOUT: !17 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 13, type: !18, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !21)
+// CHECK:STDOUT: !18 = !DISubroutineType(types: !19)
+// CHECK:STDOUT: !19 = !{!20, !20}
+// CHECK:STDOUT: !20 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !21 = !{!22}
+// CHECK:STDOUT: !22 = !DILocalVariable(arg: 1, scope: !17, type: !20)
+// CHECK:STDOUT: !23 = !DILocation(line: 14, column: 3, scope: !17)

+ 72 - 50
toolchain/lower/testdata/function/generic/call_deref_ptr.carbon

@@ -65,57 +65,57 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_CF.Main.d756e33fa3337243(ptr %x) #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !15
-// CHECK:STDOUT:   call void @_CB.Main.d756e33fa3337243(ptr %x), !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !20
+// CHECK:STDOUT:   call void @_CB.Main.d756e33fa3337243(ptr %x), !dbg !21
+// CHECK:STDOUT:   ret void, !dbg !22
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.6765264419ed942e(ptr %x) #0 !dbg !18 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.6765264419ed942e(ptr %x) #0 !dbg !23 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !19
-// CHECK:STDOUT:   call void @_CB.Main.6765264419ed942e(ptr %x), !dbg !20
-// CHECK:STDOUT:   ret void, !dbg !21
+// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !26
+// CHECK:STDOUT:   call void @_CB.Main.6765264419ed942e(ptr %x), !dbg !27
+// CHECK:STDOUT:   ret void, !dbg !28
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr %type @_CA.Main.402deed6b8733082(%type %x) #0 !dbg !22 {
+// CHECK:STDOUT: define linkonce_odr %type @_CA.Main.402deed6b8733082(%type %x) #0 !dbg !29 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret %type %x, !dbg !23
+// CHECK:STDOUT:   ret %type %x, !dbg !34
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.d756e33fa3337243(ptr %x) #0 !dbg !24 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.d756e33fa3337243(ptr %x) #0 !dbg !35 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc27_7.3.temp = alloca i32, align 4, !dbg !25
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc27_7.3.temp), !dbg !25
-// CHECK:STDOUT:   %.loc27_5.2 = load i32, ptr %x, align 4, !dbg !26
-// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %.loc27_5.2), !dbg !25
-// CHECK:STDOUT:   store i32 %D.call, ptr %.loc27_7.3.temp, align 4, !dbg !25
-// CHECK:STDOUT:   ret void, !dbg !27
+// CHECK:STDOUT:   %.loc27_7.3.temp = alloca i32, align 4, !dbg !38
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc27_7.3.temp), !dbg !38
+// CHECK:STDOUT:   %.loc27_5.2 = load i32, ptr %x, align 4, !dbg !39
+// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %.loc27_5.2), !dbg !38
+// CHECK:STDOUT:   store i32 %D.call, ptr %.loc27_7.3.temp, align 4, !dbg !38
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.6765264419ed942e(ptr %x) #0 !dbg !28 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.6765264419ed942e(ptr %x) #0 !dbg !41 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc27_7.3.temp = alloca double, align 8, !dbg !29
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc27_7.3.temp), !dbg !29
-// CHECK:STDOUT:   %.loc27_5.2 = load double, ptr %x, align 8, !dbg !30
-// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %.loc27_5.2), !dbg !29
-// CHECK:STDOUT:   store double %D.call, ptr %.loc27_7.3.temp, align 8, !dbg !29
-// CHECK:STDOUT:   ret void, !dbg !31
+// CHECK:STDOUT:   %.loc27_7.3.temp = alloca double, align 8, !dbg !44
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc27_7.3.temp), !dbg !44
+// CHECK:STDOUT:   %.loc27_5.2 = load double, ptr %x, align 8, !dbg !45
+// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %.loc27_5.2), !dbg !44
+// CHECK:STDOUT:   store double %D.call, ptr %.loc27_7.3.temp, align 8, !dbg !44
+// CHECK:STDOUT:   ret void, !dbg !46
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !32 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !47 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %x, !dbg !33
+// CHECK:STDOUT:   ret i32 %x, !dbg !53
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x) #0 !dbg !34 {
+// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x) #0 !dbg !54 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret double %x, !dbg !35
+// CHECK:STDOUT:   ret double %x, !dbg !57
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -134,7 +134,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_deref_ptr.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 36, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 37, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 39, column: 5, scope: !4)
@@ -142,25 +142,47 @@ fn M() {
 // CHECK:STDOUT: !11 = !DILocation(line: 40, column: 5, scope: !4)
 // CHECK:STDOUT: !12 = !DILocation(line: 40, column: 3, scope: !4)
 // CHECK:STDOUT: !13 = !DILocation(line: 35, column: 1, scope: !4)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d756e33fa3337243", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !15 = !DILocation(line: 31, column: 3, scope: !14)
-// CHECK:STDOUT: !16 = !DILocation(line: 32, column: 3, scope: !14)
-// CHECK:STDOUT: !17 = !DILocation(line: 30, column: 1, scope: !14)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.6765264419ed942e", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 31, column: 3, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 32, column: 3, scope: !18)
-// CHECK:STDOUT: !21 = !DILocation(line: 30, column: 1, scope: !18)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.402deed6b8733082", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 3, scope: !22)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.d756e33fa3337243", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 27, column: 3, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 27, column: 5, scope: !24)
-// CHECK:STDOUT: !27 = !DILocation(line: 26, column: 1, scope: !24)
-// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.6765264419ed942e", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !29 = !DILocation(line: 27, column: 3, scope: !28)
-// CHECK:STDOUT: !30 = !DILocation(line: 27, column: 5, scope: !28)
-// CHECK:STDOUT: !31 = !DILocation(line: 26, column: 1, scope: !28)
-// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !33 = !DILocation(line: 23, column: 3, scope: !32)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DILocation(line: 23, column: 3, scope: !34)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d756e33fa3337243", scope: null, file: !3, line: 30, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{null, !17}
+// CHECK:STDOUT: !17 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !18 = !{!19}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !14, type: !17)
+// CHECK:STDOUT: !20 = !DILocation(line: 31, column: 3, scope: !14)
+// CHECK:STDOUT: !21 = !DILocation(line: 32, column: 3, scope: !14)
+// CHECK:STDOUT: !22 = !DILocation(line: 30, column: 1, scope: !14)
+// CHECK:STDOUT: !23 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.6765264419ed942e", scope: null, file: !3, line: 30, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
+// CHECK:STDOUT: !24 = !{!25}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !23, type: !17)
+// CHECK:STDOUT: !26 = !DILocation(line: 31, column: 3, scope: !23)
+// CHECK:STDOUT: !27 = !DILocation(line: 32, column: 3, scope: !23)
+// CHECK:STDOUT: !28 = !DILocation(line: 30, column: 1, scope: !23)
+// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.402deed6b8733082", scope: null, file: !3, line: 18, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !32)
+// CHECK:STDOUT: !30 = !DISubroutineType(types: !31)
+// CHECK:STDOUT: !31 = !{!17, !17}
+// CHECK:STDOUT: !32 = !{!33}
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 1, scope: !29, type: !17)
+// CHECK:STDOUT: !34 = !DILocation(line: 19, column: 3, scope: !29)
+// CHECK:STDOUT: !35 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.d756e33fa3337243", scope: null, file: !3, line: 26, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !36)
+// CHECK:STDOUT: !36 = !{!37}
+// CHECK:STDOUT: !37 = !DILocalVariable(arg: 1, scope: !35, type: !17)
+// CHECK:STDOUT: !38 = !DILocation(line: 27, column: 3, scope: !35)
+// CHECK:STDOUT: !39 = !DILocation(line: 27, column: 5, scope: !35)
+// CHECK:STDOUT: !40 = !DILocation(line: 26, column: 1, scope: !35)
+// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.6765264419ed942e", scope: null, file: !3, line: 26, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !42)
+// CHECK:STDOUT: !42 = !{!43}
+// CHECK:STDOUT: !43 = !DILocalVariable(arg: 1, scope: !41, type: !17)
+// CHECK:STDOUT: !44 = !DILocation(line: 27, column: 3, scope: !41)
+// CHECK:STDOUT: !45 = !DILocation(line: 27, column: 5, scope: !41)
+// CHECK:STDOUT: !46 = !DILocation(line: 26, column: 1, scope: !41)
+// CHECK:STDOUT: !47 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 22, type: !48, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !51)
+// CHECK:STDOUT: !48 = !DISubroutineType(types: !49)
+// CHECK:STDOUT: !49 = !{!50, !50}
+// CHECK:STDOUT: !50 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !51 = !{!52}
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 1, scope: !47, type: !50)
+// CHECK:STDOUT: !53 = !DILocation(line: 23, column: 3, scope: !47)
+// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 22, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !55)
+// CHECK:STDOUT: !55 = !{!56}
+// CHECK:STDOUT: !56 = !DILocalVariable(arg: 1, scope: !54, type: !17)
+// CHECK:STDOUT: !57 = !DILocation(line: 23, column: 3, scope: !54)

+ 1 - 1
toolchain/lower/testdata/function/generic/call_different_associated_const.carbon

@@ -74,7 +74,7 @@ fn H() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_different_associated_const.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 36, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 37, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 35, column: 1, scope: !4)

+ 1 - 1
toolchain/lower/testdata/function/generic/call_different_impls.carbon

@@ -90,7 +90,7 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_different_impls.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.X.Main:I.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 20, column: 12, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 20, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = distinct !DISubprogram(name: "F", linkageName: "_CF.Y.Main:I.Main", scope: null, file: !3, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)

+ 47 - 41
toolchain/lower/testdata/function/generic/call_different_impls_with_const.carbon

@@ -50,49 +50,49 @@ fn Run() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i1 @"_CF.X.Main:I.Main"() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !7
-// CHECK:STDOUT:   ret i1 false, !dbg !8
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !8
+// CHECK:STDOUT:   ret i1 false, !dbg !9
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @"_CF.Y.Main:I.Main"() #0 !dbg !9 {
+// CHECK:STDOUT: define i32 @"_CF.Y.Main:I.Main"() #0 !dbg !10 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !10
-// CHECK:STDOUT:   ret i32 2, !dbg !11
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !14
+// CHECK:STDOUT:   ret i32 2, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @main() #0 !dbg !12 {
+// CHECK:STDOUT: define void @main() #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CG.Main.903f115cc96ac8da(), !dbg !13
-// CHECK:STDOUT:   call void @_CG.Main.34c09acedc4a7473(), !dbg !14
-// CHECK:STDOUT:   ret void, !dbg !15
+// CHECK:STDOUT:   call void @_CG.Main.903f115cc96ac8da(), !dbg !19
+// CHECK:STDOUT:   call void @_CG.Main.34c09acedc4a7473(), !dbg !20
+// CHECK:STDOUT:   ret void, !dbg !21
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare i32 @printf(ptr, ...)
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CG.Main.903f115cc96ac8da() #0 !dbg !16 {
+// CHECK:STDOUT: define linkonce_odr void @_CG.Main.903f115cc96ac8da() #0 !dbg !22 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc37_20.1.temp = alloca i1, align 1, !dbg !17
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc37_20.1.temp), !dbg !17
-// CHECK:STDOUT:   %.loc37_20.2 = call i1 @"_CF.X.Main:I.Main"(), !dbg !17
-// CHECK:STDOUT:   %.loc37_20.3 = zext i1 %.loc37_20.2 to i8, !dbg !17
-// CHECK:STDOUT:   store i8 %.loc37_20.3, ptr %.loc37_20.1.temp, align 1, !dbg !17
-// CHECK:STDOUT:   %.loc37_20.4 = load i8, ptr %.loc37_20.1.temp, align 1, !dbg !17
-// CHECK:STDOUT:   %.loc37_20.41 = trunc i8 %.loc37_20.4 to i1, !dbg !17
-// CHECK:STDOUT:   ret void, !dbg !18
+// CHECK:STDOUT:   %.loc37_20.1.temp = alloca i1, align 1, !dbg !23
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc37_20.1.temp), !dbg !23
+// CHECK:STDOUT:   %.loc37_20.2 = call i1 @"_CF.X.Main:I.Main"(), !dbg !23
+// CHECK:STDOUT:   %.loc37_20.3 = zext i1 %.loc37_20.2 to i8, !dbg !23
+// CHECK:STDOUT:   store i8 %.loc37_20.3, ptr %.loc37_20.1.temp, align 1, !dbg !23
+// CHECK:STDOUT:   %.loc37_20.4 = load i8, ptr %.loc37_20.1.temp, align 1, !dbg !23
+// CHECK:STDOUT:   %.loc37_20.41 = trunc i8 %.loc37_20.4 to i1, !dbg !23
+// CHECK:STDOUT:   ret void, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CG.Main.34c09acedc4a7473() #0 !dbg !19 {
+// CHECK:STDOUT: define linkonce_odr void @_CG.Main.34c09acedc4a7473() #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc37_20.1.temp = alloca i32, align 4, !dbg !20
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc37_20.1.temp), !dbg !20
-// CHECK:STDOUT:   %.loc37_20.2 = call i32 @"_CF.Y.Main:I.Main"(), !dbg !20
-// CHECK:STDOUT:   store i32 %.loc37_20.2, ptr %.loc37_20.1.temp, align 4, !dbg !20
-// CHECK:STDOUT:   %.loc37_20.4 = load i32, ptr %.loc37_20.1.temp, align 4, !dbg !20
-// CHECK:STDOUT:   ret void, !dbg !21
+// CHECK:STDOUT:   %.loc37_20.1.temp = alloca i32, align 4, !dbg !26
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc37_20.1.temp), !dbg !26
+// CHECK:STDOUT:   %.loc37_20.2 = call i32 @"_CF.Y.Main:I.Main"(), !dbg !26
+// CHECK:STDOUT:   store i32 %.loc37_20.2, ptr %.loc37_20.1.temp, align 4, !dbg !26
+// CHECK:STDOUT:   %.loc37_20.4 = load i32, ptr %.loc37_20.1.temp, align 4, !dbg !26
+// CHECK:STDOUT:   ret void, !dbg !27
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -114,19 +114,25 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_different_impls_with_const.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.X.Main:I.Main", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 22, column: 5, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 23, column: 5, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "F", linkageName: "_CF.Y.Main:I.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 29, column: 5, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 30, column: 5, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 40, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 41, column: 3, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 42, column: 3, scope: !12)
-// CHECK:STDOUT: !15 = !DILocation(line: 40, column: 1, scope: !12)
-// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.903f115cc96ac8da", scope: null, file: !3, line: 36, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !17 = !DILocation(line: 37, column: 16, scope: !16)
-// CHECK:STDOUT: !18 = !DILocation(line: 36, column: 1, scope: !16)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.34c09acedc4a7473", scope: null, file: !3, line: 36, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DILocation(line: 37, column: 16, scope: !19)
-// CHECK:STDOUT: !21 = !DILocation(line: 36, column: 1, scope: !19)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 22, column: 5, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 23, column: 5, scope: !4)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "F", linkageName: "_CF.Y.Main:I.Main", scope: null, file: !3, line: 28, type: !11, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !11 = !DISubroutineType(types: !12)
+// CHECK:STDOUT: !12 = !{!13}
+// CHECK:STDOUT: !13 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !14 = !DILocation(line: 29, column: 5, scope: !10)
+// CHECK:STDOUT: !15 = !DILocation(line: 30, column: 5, scope: !10)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 40, type: !17, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{null}
+// CHECK:STDOUT: !19 = !DILocation(line: 41, column: 3, scope: !16)
+// CHECK:STDOUT: !20 = !DILocation(line: 42, column: 3, scope: !16)
+// CHECK:STDOUT: !21 = !DILocation(line: 40, column: 1, scope: !16)
+// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.903f115cc96ac8da", scope: null, file: !3, line: 36, type: !17, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !23 = !DILocation(line: 37, column: 16, scope: !22)
+// CHECK:STDOUT: !24 = !DILocation(line: 36, column: 1, scope: !22)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.34c09acedc4a7473", scope: null, file: !3, line: 36, type: !17, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !26 = !DILocation(line: 37, column: 16, scope: !25)
+// CHECK:STDOUT: !27 = !DILocation(line: 36, column: 1, scope: !25)

+ 72 - 50
toolchain/lower/testdata/function/generic/call_different_specific.carbon

@@ -72,57 +72,57 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_CF.Main.d756e33fa3337243(ptr %x) #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !15
-// CHECK:STDOUT:   call void @_CB.Main.d756e33fa3337243(ptr %x), !dbg !16
-// CHECK:STDOUT:   ret void, !dbg !17
+// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !20
+// CHECK:STDOUT:   call void @_CB.Main.d756e33fa3337243(ptr %x), !dbg !21
+// CHECK:STDOUT:   ret void, !dbg !22
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.6765264419ed942e(ptr %x) #0 !dbg !18 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.6765264419ed942e(ptr %x) #0 !dbg !23 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !19
-// CHECK:STDOUT:   call void @_CB.Main.6765264419ed942e(ptr %x), !dbg !20
-// CHECK:STDOUT:   ret void, !dbg !21
+// CHECK:STDOUT:   %A.call = call %type @_CA.Main.402deed6b8733082(%type zeroinitializer), !dbg !26
+// CHECK:STDOUT:   call void @_CB.Main.6765264419ed942e(ptr %x), !dbg !27
+// CHECK:STDOUT:   ret void, !dbg !28
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr %type @_CA.Main.402deed6b8733082(%type %x) #0 !dbg !22 {
+// CHECK:STDOUT: define linkonce_odr %type @_CA.Main.402deed6b8733082(%type %x) #0 !dbg !29 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret %type %x, !dbg !23
+// CHECK:STDOUT:   ret %type %x, !dbg !34
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.d756e33fa3337243(ptr %x) #0 !dbg !24 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.d756e33fa3337243(ptr %x) #0 !dbg !35 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc34_7.3.temp = alloca i32, align 4, !dbg !25
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc34_7.3.temp), !dbg !25
-// CHECK:STDOUT:   %.loc34_5.2 = load i32, ptr %x, align 4, !dbg !26
-// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %.loc34_5.2), !dbg !25
-// CHECK:STDOUT:   store i32 %D.call, ptr %.loc34_7.3.temp, align 4, !dbg !25
-// CHECK:STDOUT:   ret void, !dbg !27
+// CHECK:STDOUT:   %.loc34_7.3.temp = alloca i32, align 4, !dbg !38
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc34_7.3.temp), !dbg !38
+// CHECK:STDOUT:   %.loc34_5.2 = load i32, ptr %x, align 4, !dbg !39
+// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %.loc34_5.2), !dbg !38
+// CHECK:STDOUT:   store i32 %D.call, ptr %.loc34_7.3.temp, align 4, !dbg !38
+// CHECK:STDOUT:   ret void, !dbg !40
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.6765264419ed942e(ptr %x) #0 !dbg !28 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.6765264419ed942e(ptr %x) #0 !dbg !41 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc34_7.3.temp = alloca double, align 8, !dbg !29
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc34_7.3.temp), !dbg !29
-// CHECK:STDOUT:   %.loc34_5.2 = load double, ptr %x, align 8, !dbg !30
-// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %.loc34_5.2), !dbg !29
-// CHECK:STDOUT:   store double %D.call, ptr %.loc34_7.3.temp, align 8, !dbg !29
-// CHECK:STDOUT:   ret void, !dbg !31
+// CHECK:STDOUT:   %.loc34_7.3.temp = alloca double, align 8, !dbg !44
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc34_7.3.temp), !dbg !44
+// CHECK:STDOUT:   %.loc34_5.2 = load double, ptr %x, align 8, !dbg !45
+// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %.loc34_5.2), !dbg !44
+// CHECK:STDOUT:   store double %D.call, ptr %.loc34_7.3.temp, align 8, !dbg !44
+// CHECK:STDOUT:   ret void, !dbg !46
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !32 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !47 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %x, !dbg !33
+// CHECK:STDOUT:   ret i32 %x, !dbg !53
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x) #0 !dbg !34 {
+// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x) #0 !dbg !54 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret double %x, !dbg !35
+// CHECK:STDOUT:   ret double %x, !dbg !57
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -141,7 +141,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_different_specific.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 42, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 43, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 44, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 46, column: 5, scope: !4)
@@ -149,25 +149,47 @@ fn M() {
 // CHECK:STDOUT: !11 = !DILocation(line: 47, column: 5, scope: !4)
 // CHECK:STDOUT: !12 = !DILocation(line: 47, column: 3, scope: !4)
 // CHECK:STDOUT: !13 = !DILocation(line: 42, column: 1, scope: !4)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d756e33fa3337243", scope: null, file: !3, line: 37, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !15 = !DILocation(line: 38, column: 3, scope: !14)
-// CHECK:STDOUT: !16 = !DILocation(line: 39, column: 3, scope: !14)
-// CHECK:STDOUT: !17 = !DILocation(line: 37, column: 1, scope: !14)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.6765264419ed942e", scope: null, file: !3, line: 37, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 38, column: 3, scope: !18)
-// CHECK:STDOUT: !20 = !DILocation(line: 39, column: 3, scope: !18)
-// CHECK:STDOUT: !21 = !DILocation(line: 37, column: 1, scope: !18)
-// CHECK:STDOUT: !22 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.402deed6b8733082", scope: null, file: !3, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !23 = !DILocation(line: 26, column: 3, scope: !22)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.d756e33fa3337243", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 34, column: 3, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 34, column: 5, scope: !24)
-// CHECK:STDOUT: !27 = !DILocation(line: 33, column: 1, scope: !24)
-// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.6765264419ed942e", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !29 = !DILocation(line: 34, column: 3, scope: !28)
-// CHECK:STDOUT: !30 = !DILocation(line: 34, column: 5, scope: !28)
-// CHECK:STDOUT: !31 = !DILocation(line: 33, column: 1, scope: !28)
-// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !33 = !DILocation(line: 30, column: 3, scope: !32)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 29, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DILocation(line: 30, column: 3, scope: !34)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.d756e33fa3337243", scope: null, file: !3, line: 37, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{null, !17}
+// CHECK:STDOUT: !17 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !18 = !{!19}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !14, type: !17)
+// CHECK:STDOUT: !20 = !DILocation(line: 38, column: 3, scope: !14)
+// CHECK:STDOUT: !21 = !DILocation(line: 39, column: 3, scope: !14)
+// CHECK:STDOUT: !22 = !DILocation(line: 37, column: 1, scope: !14)
+// CHECK:STDOUT: !23 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.6765264419ed942e", scope: null, file: !3, line: 37, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
+// CHECK:STDOUT: !24 = !{!25}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !23, type: !17)
+// CHECK:STDOUT: !26 = !DILocation(line: 38, column: 3, scope: !23)
+// CHECK:STDOUT: !27 = !DILocation(line: 39, column: 3, scope: !23)
+// CHECK:STDOUT: !28 = !DILocation(line: 37, column: 1, scope: !23)
+// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.402deed6b8733082", scope: null, file: !3, line: 25, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !32)
+// CHECK:STDOUT: !30 = !DISubroutineType(types: !31)
+// CHECK:STDOUT: !31 = !{!17, !17}
+// CHECK:STDOUT: !32 = !{!33}
+// CHECK:STDOUT: !33 = !DILocalVariable(arg: 1, scope: !29, type: !17)
+// CHECK:STDOUT: !34 = !DILocation(line: 26, column: 3, scope: !29)
+// CHECK:STDOUT: !35 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.d756e33fa3337243", scope: null, file: !3, line: 33, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !36)
+// CHECK:STDOUT: !36 = !{!37}
+// CHECK:STDOUT: !37 = !DILocalVariable(arg: 1, scope: !35, type: !17)
+// CHECK:STDOUT: !38 = !DILocation(line: 34, column: 3, scope: !35)
+// CHECK:STDOUT: !39 = !DILocation(line: 34, column: 5, scope: !35)
+// CHECK:STDOUT: !40 = !DILocation(line: 33, column: 1, scope: !35)
+// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.6765264419ed942e", scope: null, file: !3, line: 33, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !42)
+// CHECK:STDOUT: !42 = !{!43}
+// CHECK:STDOUT: !43 = !DILocalVariable(arg: 1, scope: !41, type: !17)
+// CHECK:STDOUT: !44 = !DILocation(line: 34, column: 3, scope: !41)
+// CHECK:STDOUT: !45 = !DILocation(line: 34, column: 5, scope: !41)
+// CHECK:STDOUT: !46 = !DILocation(line: 33, column: 1, scope: !41)
+// CHECK:STDOUT: !47 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 29, type: !48, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !51)
+// CHECK:STDOUT: !48 = !DISubroutineType(types: !49)
+// CHECK:STDOUT: !49 = !{!50, !50}
+// CHECK:STDOUT: !50 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !51 = !{!52}
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 1, scope: !47, type: !50)
+// CHECK:STDOUT: !53 = !DILocation(line: 30, column: 3, scope: !47)
+// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 29, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !55)
+// CHECK:STDOUT: !55 = !{!56}
+// CHECK:STDOUT: !56 = !DILocalVariable(arg: 1, scope: !54, type: !17)
+// CHECK:STDOUT: !57 = !DILocation(line: 30, column: 3, scope: !54)

+ 25 - 18
toolchain/lower/testdata/function/generic/call_impl_function.carbon

@@ -49,22 +49,22 @@ fn G() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @"_CF.ImplsSomeInterface.Main:SomeInterface.Main"(i32 %x) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.Negate.impl.Op.call = sub i32 0, %x, !dbg !7
-// CHECK:STDOUT:   ret i32 %Int.as.Negate.impl.Op.call, !dbg !8
+// CHECK:STDOUT:   %Int.as.Negate.impl.Op.call = sub i32 0, %x, !dbg !10
+// CHECK:STDOUT:   ret i32 %Int.as.Negate.impl.Op.call, !dbg !11
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CG.Main() #0 !dbg !9 {
+// CHECK:STDOUT: define void @_CG.Main() #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %CallGenericMethod.call = call i32 @_CCallGenericMethod.Main.dc54e41cb8a9bf68(i32 10), !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %CallGenericMethod.call = call i32 @_CCallGenericMethod.Main.dc54e41cb8a9bf68(i32 10), !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CCallGenericMethod.Main.dc54e41cb8a9bf68(i32 %x) #0 !dbg !12 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CCallGenericMethod.Main.dc54e41cb8a9bf68(i32 %x) #0 !dbg !17 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc36_15 = call i32 @"_CF.ImplsSomeInterface.Main:SomeInterface.Main"(i32 %x), !dbg !13
-// CHECK:STDOUT:   ret i32 %.loc36_15, !dbg !14
+// CHECK:STDOUT:   %.loc36_15 = call i32 @"_CF.ImplsSomeInterface.Main:SomeInterface.Main"(i32 %x), !dbg !20
+// CHECK:STDOUT:   ret i32 %.loc36_15, !dbg !21
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -76,14 +76,21 @@ fn G() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_impl_function.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.ImplsSomeInterface.Main:SomeInterface.Main", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.ImplsSomeInterface.Main:SomeInterface.Main", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 23, column: 12, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 23, column: 5, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 39, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 40, column: 3, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 39, column: 1, scope: !9)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "CallGenericMethod", linkageName: "_CCallGenericMethod.Main.dc54e41cb8a9bf68", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 36, column: 10, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 36, column: 3, scope: !12)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 23, column: 12, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 23, column: 5, scope: !4)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 39, type: !13, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null}
+// CHECK:STDOUT: !15 = !DILocation(line: 40, column: 3, scope: !12)
+// CHECK:STDOUT: !16 = !DILocation(line: 39, column: 1, scope: !12)
+// CHECK:STDOUT: !17 = distinct !DISubprogram(name: "CallGenericMethod", linkageName: "_CCallGenericMethod.Main.dc54e41cb8a9bf68", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
+// CHECK:STDOUT: !18 = !{!19}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !17, type: !7)
+// CHECK:STDOUT: !20 = !DILocation(line: 36, column: 10, scope: !17)
+// CHECK:STDOUT: !21 = !DILocation(line: 36, column: 3, scope: !17)

+ 26 - 19
toolchain/lower/testdata/function/generic/call_method.carbon

@@ -30,15 +30,15 @@ fn CallF() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CCallF.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !7
-// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !8
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !7
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %c.var, ptr align 1 @C.val.loc20_3, i64 0, i1 false), !dbg !7
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !8
-// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !8
-// CHECK:STDOUT:   %.loc22_14 = load i32, ptr %n.var, align 4, !dbg !9
-// CHECK:STDOUT:   %C.F.call = call i32 @_CF.C.Main.5450dc8e8b8e0899(ptr %c.var, i32 %.loc22_14), !dbg !10
-// CHECK:STDOUT:   ret i32 %C.F.call, !dbg !11
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !8
+// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !9
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !8
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %c.var, ptr align 1 @C.val.loc20_3, i64 0, i1 false), !dbg !8
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !9
+// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !9
+// CHECK:STDOUT:   %.loc22_14 = load i32, ptr %n.var, align 4, !dbg !10
+// CHECK:STDOUT:   %C.F.call = call i32 @_CF.C.Main.5450dc8e8b8e0899(ptr %c.var, i32 %.loc22_14), !dbg !11
+// CHECK:STDOUT:   ret i32 %C.F.call, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -48,9 +48,9 @@ fn CallF() -> i32 {
 // CHECK:STDOUT: declare void @llvm.memcpy.p0.p0.i64(ptr noalias writeonly captures(none), ptr noalias readonly captures(none), i64, i1 immarg) #2
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.C.Main.5450dc8e8b8e0899(ptr %self, i32 %x) #0 !dbg !12 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.C.Main.5450dc8e8b8e0899(ptr %self, i32 %x) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %x, !dbg !13
+// CHECK:STDOUT:   ret i32 %x, !dbg !20
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -69,11 +69,18 @@ fn CallF() -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_method.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "CallF", linkageName: "_CCallF.Main", scope: null, file: !3, line: 19, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 20, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 21, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 22, column: 14, scope: !4)
-// CHECK:STDOUT: !10 = !DILocation(line: 22, column: 10, scope: !4)
-// CHECK:STDOUT: !11 = !DILocation(line: 22, column: 3, scope: !4)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "F", linkageName: "_CF.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 15, column: 5, scope: !12)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 20, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 21, column: 3, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 22, column: 14, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 22, column: 10, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 22, column: 3, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "F", linkageName: "_CF.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 14, type: !14, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !17)
+// CHECK:STDOUT: !14 = !DISubroutineType(types: !15)
+// CHECK:STDOUT: !15 = !{!7, !16, !7}
+// CHECK:STDOUT: !16 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !17 = !{!18, !19}
+// CHECK:STDOUT: !18 = !DILocalVariable(arg: 1, scope: !13, type: !16)
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 2, scope: !13, type: !7)
+// CHECK:STDOUT: !20 = !DILocation(line: 15, column: 5, scope: !13)

+ 126 - 104
toolchain/lower/testdata/function/generic/call_recursive_basic.carbon

@@ -48,37 +48,37 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @"_COp.C.Main:Copy.Core"(ptr sret({}) %return, ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @C.val.loc15_44, i64 0, i1 false), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @C.val.loc15_44, i64 0, i1 false), !dbg !10
+// CHECK:STDOUT:   ret void, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CM.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_CM.Main() #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !9
-// CHECK:STDOUT:   %m.var = alloca double, align 8, !dbg !10
-// CHECK:STDOUT:   %ptr_i32.var = alloca ptr, align 8, !dbg !11
-// CHECK:STDOUT:   %ptr_f64.var = alloca ptr, align 8, !dbg !12
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !13
-// CHECK:STDOUT:   %.loc40_9.5.temp = alloca {}, align 8, !dbg !14
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !9
-// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !9
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %m.var), !dbg !10
-// CHECK:STDOUT:   store double 1.000000e+00, ptr %m.var, align 8, !dbg !10
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i32.var), !dbg !11
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_f64.var), !dbg !12
-// CHECK:STDOUT:   %.loc34_5 = load i32, ptr %n.var, align 4, !dbg !15
-// CHECK:STDOUT:   %F.call.loc34 = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %.loc34_5, i32 0), !dbg !16
-// CHECK:STDOUT:   %.loc35_5 = load double, ptr %m.var, align 8, !dbg !17
-// CHECK:STDOUT:   %F.call.loc35 = call double @_CF.Main.83aece103b0a8681(double %.loc35_5, i32 0), !dbg !18
-// CHECK:STDOUT:   %.loc36_5 = load ptr, ptr %ptr_i32.var, align 8, !dbg !19
-// CHECK:STDOUT:   %F.call.loc36 = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %.loc36_5, i32 0), !dbg !20
-// CHECK:STDOUT:   %.loc37_5 = load ptr, ptr %ptr_f64.var, align 8, !dbg !21
-// CHECK:STDOUT:   %F.call.loc37 = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %.loc37_5, i32 0), !dbg !22
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !13
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc40_9.5.temp), !dbg !14
-// CHECK:STDOUT:   call void @_CF.Main.936d996ea935415c(ptr %.loc40_9.5.temp, ptr %c.var, i32 0), !dbg !14
-// CHECK:STDOUT:   ret void, !dbg !23
+// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !14
+// CHECK:STDOUT:   %m.var = alloca double, align 8, !dbg !15
+// CHECK:STDOUT:   %ptr_i32.var = alloca ptr, align 8, !dbg !16
+// CHECK:STDOUT:   %ptr_f64.var = alloca ptr, align 8, !dbg !17
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !18
+// CHECK:STDOUT:   %.loc40_9.5.temp = alloca {}, align 8, !dbg !19
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !14
+// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !14
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %m.var), !dbg !15
+// CHECK:STDOUT:   store double 1.000000e+00, ptr %m.var, align 8, !dbg !15
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_i32.var), !dbg !16
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %ptr_f64.var), !dbg !17
+// CHECK:STDOUT:   %.loc34_5 = load i32, ptr %n.var, align 4, !dbg !20
+// CHECK:STDOUT:   %F.call.loc34 = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %.loc34_5, i32 0), !dbg !21
+// CHECK:STDOUT:   %.loc35_5 = load double, ptr %m.var, align 8, !dbg !22
+// CHECK:STDOUT:   %F.call.loc35 = call double @_CF.Main.83aece103b0a8681(double %.loc35_5, i32 0), !dbg !23
+// CHECK:STDOUT:   %.loc36_5 = load ptr, ptr %ptr_i32.var, align 8, !dbg !24
+// CHECK:STDOUT:   %F.call.loc36 = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %.loc36_5, i32 0), !dbg !25
+// CHECK:STDOUT:   %.loc37_5 = load ptr, ptr %ptr_f64.var, align 8, !dbg !26
+// CHECK:STDOUT:   %F.call.loc37 = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %.loc37_5, i32 0), !dbg !27
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !18
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %.loc40_9.5.temp), !dbg !19
+// CHECK:STDOUT:   call void @_CF.Main.936d996ea935415c(ptr %.loc40_9.5.temp, ptr %c.var, i32 0), !dbg !19
+// CHECK:STDOUT:   ret void, !dbg !28
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -88,64 +88,64 @@ fn M() {
 // CHECK:STDOUT: declare void @llvm.lifetime.start.p0(ptr captures(none)) #2
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !24 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !29 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !25
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !26
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !36
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !37
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %x, !dbg !27
+// CHECK:STDOUT:   ret i32 %x, !dbg !38
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !28
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !29
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !30
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !39
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !40
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !41
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !31 {
+// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !42 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !32
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !33
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !48
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !49
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret double %x, !dbg !34
+// CHECK:STDOUT:   ret double %x, !dbg !50
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !35
-// CHECK:STDOUT:   %F.call = call double @_CF.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !36
-// CHECK:STDOUT:   ret double %F.call, !dbg !37
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !51
+// CHECK:STDOUT:   %F.call = call double @_CF.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !52
+// CHECK:STDOUT:   ret double %F.call, !dbg !53
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !38 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !54 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !39
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !40
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !58
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !59
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret ptr %x, !dbg !41
+// CHECK:STDOUT:   ret ptr %x, !dbg !60
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !42
-// CHECK:STDOUT:   %F.call = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !43
-// CHECK:STDOUT:   ret ptr %F.call, !dbg !44
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !61
+// CHECK:STDOUT:   %F.call = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !62
+// CHECK:STDOUT:   ret ptr %F.call, !dbg !63
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.936d996ea935415c(ptr sret({}) %return, ptr %x, i32 %count) #0 !dbg !45 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.936d996ea935415c(ptr sret({}) %return, ptr %x, i32 %count) #0 !dbg !64 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !46
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !47
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !68
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !69
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   call void @"_COp.C.Main:Copy.Core"(ptr %return, ptr %x), !dbg !48
-// CHECK:STDOUT:   ret void, !dbg !49
+// CHECK:STDOUT:   call void @"_COp.C.Main:Copy.Core"(ptr %return, ptr %x), !dbg !70
+// CHECK:STDOUT:   ret void, !dbg !71
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !50
-// CHECK:STDOUT:   call void @_CF.Main.936d996ea935415c(ptr %return, ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !51
-// CHECK:STDOUT:   ret void, !dbg !52
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !72
+// CHECK:STDOUT:   call void @_CF.Main.936d996ea935415c(ptr %return, ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !73
+// CHECK:STDOUT:   ret void, !dbg !74
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -163,52 +163,74 @@ fn M() {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_basic.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.C.Main:Copy.Core", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.C.Main:Copy.Core", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 15, column: 35, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 29, column: 3, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 30, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 31, column: 3, scope: !8)
-// CHECK:STDOUT: !12 = !DILocation(line: 32, column: 3, scope: !8)
-// CHECK:STDOUT: !13 = !DILocation(line: 39, column: 3, scope: !8)
-// CHECK:STDOUT: !14 = !DILocation(line: 40, column: 3, scope: !8)
-// CHECK:STDOUT: !15 = !DILocation(line: 34, column: 5, scope: !8)
-// CHECK:STDOUT: !16 = !DILocation(line: 34, column: 3, scope: !8)
-// CHECK:STDOUT: !17 = !DILocation(line: 35, column: 5, scope: !8)
-// CHECK:STDOUT: !18 = !DILocation(line: 35, column: 3, scope: !8)
-// CHECK:STDOUT: !19 = !DILocation(line: 36, column: 5, scope: !8)
-// CHECK:STDOUT: !20 = !DILocation(line: 36, column: 3, scope: !8)
-// CHECK:STDOUT: !21 = !DILocation(line: 37, column: 5, scope: !8)
-// CHECK:STDOUT: !22 = !DILocation(line: 37, column: 3, scope: !8)
-// CHECK:STDOUT: !23 = !DILocation(line: 28, column: 1, scope: !8)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 22, column: 7, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 22, column: 6, scope: !24)
-// CHECK:STDOUT: !27 = !DILocation(line: 23, column: 5, scope: !24)
-// CHECK:STDOUT: !28 = !DILocation(line: 25, column: 15, scope: !24)
-// CHECK:STDOUT: !29 = !DILocation(line: 25, column: 10, scope: !24)
-// CHECK:STDOUT: !30 = !DILocation(line: 25, column: 3, scope: !24)
-// CHECK:STDOUT: !31 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !32 = !DILocation(line: 22, column: 7, scope: !31)
-// CHECK:STDOUT: !33 = !DILocation(line: 22, column: 6, scope: !31)
-// CHECK:STDOUT: !34 = !DILocation(line: 23, column: 5, scope: !31)
-// CHECK:STDOUT: !35 = !DILocation(line: 25, column: 15, scope: !31)
-// CHECK:STDOUT: !36 = !DILocation(line: 25, column: 10, scope: !31)
-// CHECK:STDOUT: !37 = !DILocation(line: 25, column: 3, scope: !31)
-// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !39 = !DILocation(line: 22, column: 7, scope: !38)
-// CHECK:STDOUT: !40 = !DILocation(line: 22, column: 6, scope: !38)
-// CHECK:STDOUT: !41 = !DILocation(line: 23, column: 5, scope: !38)
-// CHECK:STDOUT: !42 = !DILocation(line: 25, column: 15, scope: !38)
-// CHECK:STDOUT: !43 = !DILocation(line: 25, column: 10, scope: !38)
-// CHECK:STDOUT: !44 = !DILocation(line: 25, column: 3, scope: !38)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.936d996ea935415c", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 22, column: 7, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 22, column: 6, scope: !45)
-// CHECK:STDOUT: !48 = !DILocation(line: 23, column: 12, scope: !45)
-// CHECK:STDOUT: !49 = !DILocation(line: 23, column: 5, scope: !45)
-// CHECK:STDOUT: !50 = !DILocation(line: 25, column: 15, scope: !45)
-// CHECK:STDOUT: !51 = !DILocation(line: 25, column: 10, scope: !45)
-// CHECK:STDOUT: !52 = !DILocation(line: 25, column: 3, scope: !45)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 15, column: 35, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 28, type: !12, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null}
+// CHECK:STDOUT: !14 = !DILocation(line: 29, column: 3, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 30, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = !DILocation(line: 31, column: 3, scope: !11)
+// CHECK:STDOUT: !17 = !DILocation(line: 32, column: 3, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 39, column: 3, scope: !11)
+// CHECK:STDOUT: !19 = !DILocation(line: 40, column: 3, scope: !11)
+// CHECK:STDOUT: !20 = !DILocation(line: 34, column: 5, scope: !11)
+// CHECK:STDOUT: !21 = !DILocation(line: 34, column: 3, scope: !11)
+// CHECK:STDOUT: !22 = !DILocation(line: 35, column: 5, scope: !11)
+// CHECK:STDOUT: !23 = !DILocation(line: 35, column: 3, scope: !11)
+// CHECK:STDOUT: !24 = !DILocation(line: 36, column: 5, scope: !11)
+// CHECK:STDOUT: !25 = !DILocation(line: 36, column: 3, scope: !11)
+// CHECK:STDOUT: !26 = !DILocation(line: 37, column: 5, scope: !11)
+// CHECK:STDOUT: !27 = !DILocation(line: 37, column: 3, scope: !11)
+// CHECK:STDOUT: !28 = !DILocation(line: 28, column: 1, scope: !11)
+// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 21, type: !30, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !33)
+// CHECK:STDOUT: !30 = !DISubroutineType(types: !31)
+// CHECK:STDOUT: !31 = !{!32, !32, !32}
+// CHECK:STDOUT: !32 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !33 = !{!34, !35}
+// CHECK:STDOUT: !34 = !DILocalVariable(arg: 1, scope: !29, type: !32)
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 2, scope: !29, type: !32)
+// CHECK:STDOUT: !36 = !DILocation(line: 22, column: 7, scope: !29)
+// CHECK:STDOUT: !37 = !DILocation(line: 22, column: 6, scope: !29)
+// CHECK:STDOUT: !38 = !DILocation(line: 23, column: 5, scope: !29)
+// CHECK:STDOUT: !39 = !DILocation(line: 25, column: 15, scope: !29)
+// CHECK:STDOUT: !40 = !DILocation(line: 25, column: 10, scope: !29)
+// CHECK:STDOUT: !41 = !DILocation(line: 25, column: 3, scope: !29)
+// CHECK:STDOUT: !42 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 21, type: !43, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !45)
+// CHECK:STDOUT: !43 = !DISubroutineType(types: !44)
+// CHECK:STDOUT: !44 = !{!7, !7, !32}
+// CHECK:STDOUT: !45 = !{!46, !47}
+// CHECK:STDOUT: !46 = !DILocalVariable(arg: 1, scope: !42, type: !7)
+// CHECK:STDOUT: !47 = !DILocalVariable(arg: 2, scope: !42, type: !32)
+// CHECK:STDOUT: !48 = !DILocation(line: 22, column: 7, scope: !42)
+// CHECK:STDOUT: !49 = !DILocation(line: 22, column: 6, scope: !42)
+// CHECK:STDOUT: !50 = !DILocation(line: 23, column: 5, scope: !42)
+// CHECK:STDOUT: !51 = !DILocation(line: 25, column: 15, scope: !42)
+// CHECK:STDOUT: !52 = !DILocation(line: 25, column: 10, scope: !42)
+// CHECK:STDOUT: !53 = !DILocation(line: 25, column: 3, scope: !42)
+// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 21, type: !43, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !55)
+// CHECK:STDOUT: !55 = !{!56, !57}
+// CHECK:STDOUT: !56 = !DILocalVariable(arg: 1, scope: !54, type: !7)
+// CHECK:STDOUT: !57 = !DILocalVariable(arg: 2, scope: !54, type: !32)
+// CHECK:STDOUT: !58 = !DILocation(line: 22, column: 7, scope: !54)
+// CHECK:STDOUT: !59 = !DILocation(line: 22, column: 6, scope: !54)
+// CHECK:STDOUT: !60 = !DILocation(line: 23, column: 5, scope: !54)
+// CHECK:STDOUT: !61 = !DILocation(line: 25, column: 15, scope: !54)
+// CHECK:STDOUT: !62 = !DILocation(line: 25, column: 10, scope: !54)
+// CHECK:STDOUT: !63 = !DILocation(line: 25, column: 3, scope: !54)
+// CHECK:STDOUT: !64 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.936d996ea935415c", scope: null, file: !3, line: 21, type: !43, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !65)
+// CHECK:STDOUT: !65 = !{!66, !67}
+// CHECK:STDOUT: !66 = !DILocalVariable(arg: 1, scope: !64, type: !7)
+// CHECK:STDOUT: !67 = !DILocalVariable(arg: 2, scope: !64, type: !32)
+// CHECK:STDOUT: !68 = !DILocation(line: 22, column: 7, scope: !64)
+// CHECK:STDOUT: !69 = !DILocation(line: 22, column: 6, scope: !64)
+// CHECK:STDOUT: !70 = !DILocation(line: 23, column: 12, scope: !64)
+// CHECK:STDOUT: !71 = !DILocation(line: 23, column: 5, scope: !64)
+// CHECK:STDOUT: !72 = !DILocation(line: 25, column: 15, scope: !64)
+// CHECK:STDOUT: !73 = !DILocation(line: 25, column: 10, scope: !64)
+// CHECK:STDOUT: !74 = !DILocation(line: 25, column: 3, scope: !64)

+ 177 - 135
toolchain/lower/testdata/function/generic/call_recursive_diamond.carbon

@@ -91,144 +91,144 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CA.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !21
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc22, label %if.else.loc22, !dbg !22
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !27
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc22, label %if.else.loc22, !dbg !28
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc22:                                    ; preds = %entry
-// CHECK:STDOUT:   ret i32 %x, !dbg !23
+// CHECK:STDOUT:   ret i32 %x, !dbg !29
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc22:                                    ; preds = %entry
-// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !24
-// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !24
-// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc25, label %if.else.loc25, !dbg !25
+// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !30
+// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !30
+// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc25, label %if.else.loc25, !dbg !31
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc25:                                    ; preds = %if.else.loc22
-// CHECK:STDOUT:   %B.call = call i32 @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !26
-// CHECK:STDOUT:   ret i32 %B.call, !dbg !27
+// CHECK:STDOUT:   %B.call = call i32 @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !32
+// CHECK:STDOUT:   ret i32 %B.call, !dbg !33
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc25:                                    ; preds = %if.else.loc22
-// CHECK:STDOUT:   %C.call = call i32 @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !28
-// CHECK:STDOUT:   ret i32 %C.call, !dbg !29
+// CHECK:STDOUT:   %C.call = call i32 @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !34
+// CHECK:STDOUT:   ret i32 %C.call, !dbg !35
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CA.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !30 {
+// CHECK:STDOUT: define linkonce_odr double @_CA.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !36 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !31
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc22, label %if.else.loc22, !dbg !32
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !43
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc22, label %if.else.loc22, !dbg !44
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc22:                                    ; preds = %entry
-// CHECK:STDOUT:   ret double %x, !dbg !33
+// CHECK:STDOUT:   ret double %x, !dbg !45
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc22:                                    ; preds = %entry
-// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !34
-// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !34
-// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc25, label %if.else.loc25, !dbg !35
+// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !46
+// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !46
+// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc25, label %if.else.loc25, !dbg !47
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc25:                                    ; preds = %if.else.loc22
-// CHECK:STDOUT:   %B.call = call double @_CB.Main.83aece103b0a8681(double %x, i32 %count), !dbg !36
-// CHECK:STDOUT:   ret double %B.call, !dbg !37
+// CHECK:STDOUT:   %B.call = call double @_CB.Main.83aece103b0a8681(double %x, i32 %count), !dbg !48
+// CHECK:STDOUT:   ret double %B.call, !dbg !49
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc25:                                    ; preds = %if.else.loc22
-// CHECK:STDOUT:   %C.call = call double @_CC.Main.83aece103b0a8681(double %x, i32 %count), !dbg !38
-// CHECK:STDOUT:   ret double %C.call, !dbg !39
+// CHECK:STDOUT:   %C.call = call double @_CC.Main.83aece103b0a8681(double %x, i32 %count), !dbg !50
+// CHECK:STDOUT:   ret double %C.call, !dbg !51
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CA.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !40 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CA.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !52 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !41
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc22, label %if.else.loc22, !dbg !42
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !56
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc22, label %if.else.loc22, !dbg !57
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc22:                                    ; preds = %entry
-// CHECK:STDOUT:   ret ptr %x, !dbg !43
+// CHECK:STDOUT:   ret ptr %x, !dbg !58
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc22:                                    ; preds = %entry
-// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !44
-// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !44
-// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc25, label %if.else.loc25, !dbg !45
+// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !59
+// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !59
+// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc25, label %if.else.loc25, !dbg !60
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc25:                                    ; preds = %if.else.loc22
-// CHECK:STDOUT:   %B.call = call ptr @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !46
-// CHECK:STDOUT:   ret ptr %B.call, !dbg !47
+// CHECK:STDOUT:   %B.call = call ptr @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !61
+// CHECK:STDOUT:   ret ptr %B.call, !dbg !62
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc25:                                    ; preds = %if.else.loc22
-// CHECK:STDOUT:   %C.call = call ptr @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !48
-// CHECK:STDOUT:   ret ptr %C.call, !dbg !49
+// CHECK:STDOUT:   %C.call = call ptr @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !63
+// CHECK:STDOUT:   ret ptr %C.call, !dbg !64
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !50 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !65 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !51
-// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !52
-// CHECK:STDOUT:   ret i32 %D.call, !dbg !53
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !69
+// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !70
+// CHECK:STDOUT:   ret i32 %D.call, !dbg !71
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !54 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !72 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !55
-// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !56
-// CHECK:STDOUT:   ret i32 %D.call, !dbg !57
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !76
+// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !77
+// CHECK:STDOUT:   ret i32 %D.call, !dbg !78
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CB.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !58 {
+// CHECK:STDOUT: define linkonce_odr double @_CB.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !79 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !59
-// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %count), !dbg !60
-// CHECK:STDOUT:   ret double %D.call, !dbg !61
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !83
+// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %count), !dbg !84
+// CHECK:STDOUT:   ret double %D.call, !dbg !85
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CC.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !62 {
+// CHECK:STDOUT: define linkonce_odr double @_CC.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !86 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !63
-// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %count), !dbg !64
-// CHECK:STDOUT:   ret double %D.call, !dbg !65
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !90
+// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %count), !dbg !91
+// CHECK:STDOUT:   ret double %D.call, !dbg !92
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !66 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !93 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !67
-// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !68
-// CHECK:STDOUT:   ret ptr %D.call, !dbg !69
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 1), !dbg !97
+// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !98
+// CHECK:STDOUT:   ret ptr %D.call, !dbg !99
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !70 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !100 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !71
-// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !72
-// CHECK:STDOUT:   ret ptr %D.call, !dbg !73
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 2), !dbg !104
+// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !105
+// CHECK:STDOUT:   ret ptr %D.call, !dbg !106
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare i32 @printf(ptr, ...)
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !74 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !107 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !75
-// CHECK:STDOUT:   %A.call = call i32 @_CA.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !76
-// CHECK:STDOUT:   ret i32 %A.call, !dbg !77
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !111
+// CHECK:STDOUT:   %A.call = call i32 @_CA.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !112
+// CHECK:STDOUT:   ret i32 %A.call, !dbg !113
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !78 {
+// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !114 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !79
-// CHECK:STDOUT:   %A.call = call double @_CA.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !80
-// CHECK:STDOUT:   ret double %A.call, !dbg !81
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !118
+// CHECK:STDOUT:   %A.call = call double @_CA.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !119
+// CHECK:STDOUT:   ret double %A.call, !dbg !120
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !82 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !121 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !83
-// CHECK:STDOUT:   %A.call = call ptr @_CA.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !84
-// CHECK:STDOUT:   ret ptr %A.call, !dbg !85
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !125
+// CHECK:STDOUT:   %A.call = call ptr @_CA.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !126
+// CHECK:STDOUT:   ret ptr %A.call, !dbg !127
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -251,7 +251,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_diamond.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 47, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 48, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 49, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 50, column: 3, scope: !4)
@@ -265,69 +265,111 @@ fn M() {
 // CHECK:STDOUT: !17 = !DILocation(line: 56, column: 5, scope: !4)
 // CHECK:STDOUT: !18 = !DILocation(line: 56, column: 3, scope: !4)
 // CHECK:STDOUT: !19 = !DILocation(line: 47, column: 1, scope: !4)
-// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !21 = !DILocation(line: 22, column: 7, scope: !20)
-// CHECK:STDOUT: !22 = !DILocation(line: 22, column: 6, scope: !20)
-// CHECK:STDOUT: !23 = !DILocation(line: 23, column: 5, scope: !20)
-// CHECK:STDOUT: !24 = !DILocation(line: 25, column: 7, scope: !20)
-// CHECK:STDOUT: !25 = !DILocation(line: 25, column: 6, scope: !20)
-// CHECK:STDOUT: !26 = !DILocation(line: 26, column: 12, scope: !20)
-// CHECK:STDOUT: !27 = !DILocation(line: 26, column: 5, scope: !20)
-// CHECK:STDOUT: !28 = !DILocation(line: 28, column: 12, scope: !20)
-// CHECK:STDOUT: !29 = !DILocation(line: 28, column: 5, scope: !20)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.83aece103b0a8681", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DILocation(line: 22, column: 7, scope: !30)
-// CHECK:STDOUT: !32 = !DILocation(line: 22, column: 6, scope: !30)
-// CHECK:STDOUT: !33 = !DILocation(line: 23, column: 5, scope: !30)
-// CHECK:STDOUT: !34 = !DILocation(line: 25, column: 7, scope: !30)
-// CHECK:STDOUT: !35 = !DILocation(line: 25, column: 6, scope: !30)
-// CHECK:STDOUT: !36 = !DILocation(line: 26, column: 12, scope: !30)
-// CHECK:STDOUT: !37 = !DILocation(line: 26, column: 5, scope: !30)
-// CHECK:STDOUT: !38 = !DILocation(line: 28, column: 12, scope: !30)
-// CHECK:STDOUT: !39 = !DILocation(line: 28, column: 5, scope: !30)
-// CHECK:STDOUT: !40 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 21, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !41 = !DILocation(line: 22, column: 7, scope: !40)
-// CHECK:STDOUT: !42 = !DILocation(line: 22, column: 6, scope: !40)
-// CHECK:STDOUT: !43 = !DILocation(line: 23, column: 5, scope: !40)
-// CHECK:STDOUT: !44 = !DILocation(line: 25, column: 7, scope: !40)
-// CHECK:STDOUT: !45 = !DILocation(line: 25, column: 6, scope: !40)
-// CHECK:STDOUT: !46 = !DILocation(line: 26, column: 12, scope: !40)
-// CHECK:STDOUT: !47 = !DILocation(line: 26, column: 5, scope: !40)
-// CHECK:STDOUT: !48 = !DILocation(line: 28, column: 12, scope: !40)
-// CHECK:STDOUT: !49 = !DILocation(line: 28, column: 5, scope: !40)
-// CHECK:STDOUT: !50 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !51 = !DILocation(line: 34, column: 3, scope: !50)
-// CHECK:STDOUT: !52 = !DILocation(line: 35, column: 10, scope: !50)
-// CHECK:STDOUT: !53 = !DILocation(line: 35, column: 3, scope: !50)
-// CHECK:STDOUT: !54 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 38, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !55 = !DILocation(line: 39, column: 3, scope: !54)
-// CHECK:STDOUT: !56 = !DILocation(line: 40, column: 10, scope: !54)
-// CHECK:STDOUT: !57 = !DILocation(line: 40, column: 3, scope: !54)
-// CHECK:STDOUT: !58 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.83aece103b0a8681", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !59 = !DILocation(line: 34, column: 3, scope: !58)
-// CHECK:STDOUT: !60 = !DILocation(line: 35, column: 10, scope: !58)
-// CHECK:STDOUT: !61 = !DILocation(line: 35, column: 3, scope: !58)
-// CHECK:STDOUT: !62 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.83aece103b0a8681", scope: null, file: !3, line: 38, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !63 = !DILocation(line: 39, column: 3, scope: !62)
-// CHECK:STDOUT: !64 = !DILocation(line: 40, column: 10, scope: !62)
-// CHECK:STDOUT: !65 = !DILocation(line: 40, column: 3, scope: !62)
-// CHECK:STDOUT: !66 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !67 = !DILocation(line: 34, column: 3, scope: !66)
-// CHECK:STDOUT: !68 = !DILocation(line: 35, column: 10, scope: !66)
-// CHECK:STDOUT: !69 = !DILocation(line: 35, column: 3, scope: !66)
-// CHECK:STDOUT: !70 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 38, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !71 = !DILocation(line: 39, column: 3, scope: !70)
-// CHECK:STDOUT: !72 = !DILocation(line: 40, column: 10, scope: !70)
-// CHECK:STDOUT: !73 = !DILocation(line: 40, column: 3, scope: !70)
-// CHECK:STDOUT: !74 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 43, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !75 = !DILocation(line: 44, column: 15, scope: !74)
-// CHECK:STDOUT: !76 = !DILocation(line: 44, column: 10, scope: !74)
-// CHECK:STDOUT: !77 = !DILocation(line: 44, column: 3, scope: !74)
-// CHECK:STDOUT: !78 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 43, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !79 = !DILocation(line: 44, column: 15, scope: !78)
-// CHECK:STDOUT: !80 = !DILocation(line: 44, column: 10, scope: !78)
-// CHECK:STDOUT: !81 = !DILocation(line: 44, column: 3, scope: !78)
-// CHECK:STDOUT: !82 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 43, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !83 = !DILocation(line: 44, column: 15, scope: !82)
-// CHECK:STDOUT: !84 = !DILocation(line: 44, column: 10, scope: !82)
-// CHECK:STDOUT: !85 = !DILocation(line: 44, column: 3, scope: !82)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 21, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
+// CHECK:STDOUT: !21 = !DISubroutineType(types: !22)
+// CHECK:STDOUT: !22 = !{!23, !23, !23}
+// CHECK:STDOUT: !23 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !24 = !{!25, !26}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !20, type: !23)
+// CHECK:STDOUT: !26 = !DILocalVariable(arg: 2, scope: !20, type: !23)
+// CHECK:STDOUT: !27 = !DILocation(line: 22, column: 7, scope: !20)
+// CHECK:STDOUT: !28 = !DILocation(line: 22, column: 6, scope: !20)
+// CHECK:STDOUT: !29 = !DILocation(line: 23, column: 5, scope: !20)
+// CHECK:STDOUT: !30 = !DILocation(line: 25, column: 7, scope: !20)
+// CHECK:STDOUT: !31 = !DILocation(line: 25, column: 6, scope: !20)
+// CHECK:STDOUT: !32 = !DILocation(line: 26, column: 12, scope: !20)
+// CHECK:STDOUT: !33 = !DILocation(line: 26, column: 5, scope: !20)
+// CHECK:STDOUT: !34 = !DILocation(line: 28, column: 12, scope: !20)
+// CHECK:STDOUT: !35 = !DILocation(line: 28, column: 5, scope: !20)
+// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.83aece103b0a8681", scope: null, file: !3, line: 21, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !40)
+// CHECK:STDOUT: !37 = !DISubroutineType(types: !38)
+// CHECK:STDOUT: !38 = !{!39, !39, !23}
+// CHECK:STDOUT: !39 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !40 = !{!41, !42}
+// CHECK:STDOUT: !41 = !DILocalVariable(arg: 1, scope: !36, type: !39)
+// CHECK:STDOUT: !42 = !DILocalVariable(arg: 2, scope: !36, type: !23)
+// CHECK:STDOUT: !43 = !DILocation(line: 22, column: 7, scope: !36)
+// CHECK:STDOUT: !44 = !DILocation(line: 22, column: 6, scope: !36)
+// CHECK:STDOUT: !45 = !DILocation(line: 23, column: 5, scope: !36)
+// CHECK:STDOUT: !46 = !DILocation(line: 25, column: 7, scope: !36)
+// CHECK:STDOUT: !47 = !DILocation(line: 25, column: 6, scope: !36)
+// CHECK:STDOUT: !48 = !DILocation(line: 26, column: 12, scope: !36)
+// CHECK:STDOUT: !49 = !DILocation(line: 26, column: 5, scope: !36)
+// CHECK:STDOUT: !50 = !DILocation(line: 28, column: 12, scope: !36)
+// CHECK:STDOUT: !51 = !DILocation(line: 28, column: 5, scope: !36)
+// CHECK:STDOUT: !52 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 21, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !53)
+// CHECK:STDOUT: !53 = !{!54, !55}
+// CHECK:STDOUT: !54 = !DILocalVariable(arg: 1, scope: !52, type: !39)
+// CHECK:STDOUT: !55 = !DILocalVariable(arg: 2, scope: !52, type: !23)
+// CHECK:STDOUT: !56 = !DILocation(line: 22, column: 7, scope: !52)
+// CHECK:STDOUT: !57 = !DILocation(line: 22, column: 6, scope: !52)
+// CHECK:STDOUT: !58 = !DILocation(line: 23, column: 5, scope: !52)
+// CHECK:STDOUT: !59 = !DILocation(line: 25, column: 7, scope: !52)
+// CHECK:STDOUT: !60 = !DILocation(line: 25, column: 6, scope: !52)
+// CHECK:STDOUT: !61 = !DILocation(line: 26, column: 12, scope: !52)
+// CHECK:STDOUT: !62 = !DILocation(line: 26, column: 5, scope: !52)
+// CHECK:STDOUT: !63 = !DILocation(line: 28, column: 12, scope: !52)
+// CHECK:STDOUT: !64 = !DILocation(line: 28, column: 5, scope: !52)
+// CHECK:STDOUT: !65 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 33, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !66)
+// CHECK:STDOUT: !66 = !{!67, !68}
+// CHECK:STDOUT: !67 = !DILocalVariable(arg: 1, scope: !65, type: !23)
+// CHECK:STDOUT: !68 = !DILocalVariable(arg: 2, scope: !65, type: !23)
+// CHECK:STDOUT: !69 = !DILocation(line: 34, column: 3, scope: !65)
+// CHECK:STDOUT: !70 = !DILocation(line: 35, column: 10, scope: !65)
+// CHECK:STDOUT: !71 = !DILocation(line: 35, column: 3, scope: !65)
+// CHECK:STDOUT: !72 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 38, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !73)
+// CHECK:STDOUT: !73 = !{!74, !75}
+// CHECK:STDOUT: !74 = !DILocalVariable(arg: 1, scope: !72, type: !23)
+// CHECK:STDOUT: !75 = !DILocalVariable(arg: 2, scope: !72, type: !23)
+// CHECK:STDOUT: !76 = !DILocation(line: 39, column: 3, scope: !72)
+// CHECK:STDOUT: !77 = !DILocation(line: 40, column: 10, scope: !72)
+// CHECK:STDOUT: !78 = !DILocation(line: 40, column: 3, scope: !72)
+// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.83aece103b0a8681", scope: null, file: !3, line: 33, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !80)
+// CHECK:STDOUT: !80 = !{!81, !82}
+// CHECK:STDOUT: !81 = !DILocalVariable(arg: 1, scope: !79, type: !39)
+// CHECK:STDOUT: !82 = !DILocalVariable(arg: 2, scope: !79, type: !23)
+// CHECK:STDOUT: !83 = !DILocation(line: 34, column: 3, scope: !79)
+// CHECK:STDOUT: !84 = !DILocation(line: 35, column: 10, scope: !79)
+// CHECK:STDOUT: !85 = !DILocation(line: 35, column: 3, scope: !79)
+// CHECK:STDOUT: !86 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.83aece103b0a8681", scope: null, file: !3, line: 38, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !87)
+// CHECK:STDOUT: !87 = !{!88, !89}
+// CHECK:STDOUT: !88 = !DILocalVariable(arg: 1, scope: !86, type: !39)
+// CHECK:STDOUT: !89 = !DILocalVariable(arg: 2, scope: !86, type: !23)
+// CHECK:STDOUT: !90 = !DILocation(line: 39, column: 3, scope: !86)
+// CHECK:STDOUT: !91 = !DILocation(line: 40, column: 10, scope: !86)
+// CHECK:STDOUT: !92 = !DILocation(line: 40, column: 3, scope: !86)
+// CHECK:STDOUT: !93 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 33, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !94)
+// CHECK:STDOUT: !94 = !{!95, !96}
+// CHECK:STDOUT: !95 = !DILocalVariable(arg: 1, scope: !93, type: !39)
+// CHECK:STDOUT: !96 = !DILocalVariable(arg: 2, scope: !93, type: !23)
+// CHECK:STDOUT: !97 = !DILocation(line: 34, column: 3, scope: !93)
+// CHECK:STDOUT: !98 = !DILocation(line: 35, column: 10, scope: !93)
+// CHECK:STDOUT: !99 = !DILocation(line: 35, column: 3, scope: !93)
+// CHECK:STDOUT: !100 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 38, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !101)
+// CHECK:STDOUT: !101 = !{!102, !103}
+// CHECK:STDOUT: !102 = !DILocalVariable(arg: 1, scope: !100, type: !39)
+// CHECK:STDOUT: !103 = !DILocalVariable(arg: 2, scope: !100, type: !23)
+// CHECK:STDOUT: !104 = !DILocation(line: 39, column: 3, scope: !100)
+// CHECK:STDOUT: !105 = !DILocation(line: 40, column: 10, scope: !100)
+// CHECK:STDOUT: !106 = !DILocation(line: 40, column: 3, scope: !100)
+// CHECK:STDOUT: !107 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 43, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !108)
+// CHECK:STDOUT: !108 = !{!109, !110}
+// CHECK:STDOUT: !109 = !DILocalVariable(arg: 1, scope: !107, type: !23)
+// CHECK:STDOUT: !110 = !DILocalVariable(arg: 2, scope: !107, type: !23)
+// CHECK:STDOUT: !111 = !DILocation(line: 44, column: 15, scope: !107)
+// CHECK:STDOUT: !112 = !DILocation(line: 44, column: 10, scope: !107)
+// CHECK:STDOUT: !113 = !DILocation(line: 44, column: 3, scope: !107)
+// CHECK:STDOUT: !114 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 43, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !115)
+// CHECK:STDOUT: !115 = !{!116, !117}
+// CHECK:STDOUT: !116 = !DILocalVariable(arg: 1, scope: !114, type: !39)
+// CHECK:STDOUT: !117 = !DILocalVariable(arg: 2, scope: !114, type: !23)
+// CHECK:STDOUT: !118 = !DILocation(line: 44, column: 15, scope: !114)
+// CHECK:STDOUT: !119 = !DILocation(line: 44, column: 10, scope: !114)
+// CHECK:STDOUT: !120 = !DILocation(line: 44, column: 3, scope: !114)
+// CHECK:STDOUT: !121 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 43, type: !37, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !122)
+// CHECK:STDOUT: !122 = !{!123, !124}
+// CHECK:STDOUT: !123 = !DILocalVariable(arg: 1, scope: !121, type: !39)
+// CHECK:STDOUT: !124 = !DILocalVariable(arg: 2, scope: !121, type: !23)
+// CHECK:STDOUT: !125 = !DILocation(line: 44, column: 15, scope: !121)
+// CHECK:STDOUT: !126 = !DILocation(line: 44, column: 10, scope: !121)
+// CHECK:STDOUT: !127 = !DILocation(line: 44, column: 3, scope: !121)

+ 39 - 32
toolchain/lower/testdata/function/generic/call_recursive_impl.carbon

@@ -73,33 +73,33 @@ fn Run() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.4d3c36eeac175c1f(i32 %count) #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @"_CF.X.Main:I.Main"(), !dbg !17
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !18
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !19
+// CHECK:STDOUT:   call void @"_CF.X.Main:I.Main"(), !dbg !22
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !23
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !24
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !20
+// CHECK:STDOUT:   ret i32 %count, !dbg !25
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !21
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.4d3c36eeac175c1f(i32 %Int.as.AddWith.impl.Op.call), !dbg !22
-// CHECK:STDOUT:   ret i32 %G.call, !dbg !23
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !26
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.4d3c36eeac175c1f(i32 %Int.as.AddWith.impl.Op.call), !dbg !27
+// CHECK:STDOUT:   ret i32 %G.call, !dbg !28
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.7abe23e63361d139(i32 %count) #0 !dbg !24 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.7abe23e63361d139(i32 %count) #0 !dbg !29 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @"_CF.Y.Main:I.Main"(), !dbg !25
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !26
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !27
+// CHECK:STDOUT:   call void @"_CF.Y.Main:I.Main"(), !dbg !32
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 0, !dbg !33
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !34
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !28
+// CHECK:STDOUT:   ret i32 %count, !dbg !35
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !29
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.7abe23e63361d139(i32 %Int.as.AddWith.impl.Op.call), !dbg !30
-// CHECK:STDOUT:   ret i32 %G.call, !dbg !31
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !36
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.7abe23e63361d139(i32 %Int.as.AddWith.impl.Op.call), !dbg !37
+// CHECK:STDOUT:   ret i32 %G.call, !dbg !38
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -116,7 +116,7 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_impl.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.X.Main:I.Main", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 20, column: 12, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 20, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = distinct !DISubprogram(name: "F", linkageName: "_CF.Y.Main:I.Main", scope: null, file: !3, line: 24, type: !5, spFlags: DISPFlagDefinition, unit: !2)
@@ -126,19 +126,26 @@ fn Run() {
 // CHECK:STDOUT: !13 = !DILocation(line: 40, column: 3, scope: !12)
 // CHECK:STDOUT: !14 = !DILocation(line: 41, column: 3, scope: !12)
 // CHECK:STDOUT: !15 = !DILocation(line: 39, column: 1, scope: !12)
-// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.4d3c36eeac175c1f", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !17 = !DILocation(line: 31, column: 3, scope: !16)
-// CHECK:STDOUT: !18 = !DILocation(line: 33, column: 7, scope: !16)
-// CHECK:STDOUT: !19 = !DILocation(line: 33, column: 6, scope: !16)
-// CHECK:STDOUT: !20 = !DILocation(line: 34, column: 5, scope: !16)
-// CHECK:STDOUT: !21 = !DILocation(line: 36, column: 15, scope: !16)
-// CHECK:STDOUT: !22 = !DILocation(line: 36, column: 10, scope: !16)
-// CHECK:STDOUT: !23 = !DILocation(line: 36, column: 3, scope: !16)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.7abe23e63361d139", scope: null, file: !3, line: 30, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 31, column: 3, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 33, column: 7, scope: !24)
-// CHECK:STDOUT: !27 = !DILocation(line: 33, column: 6, scope: !24)
-// CHECK:STDOUT: !28 = !DILocation(line: 34, column: 5, scope: !24)
-// CHECK:STDOUT: !29 = !DILocation(line: 36, column: 15, scope: !24)
-// CHECK:STDOUT: !30 = !DILocation(line: 36, column: 10, scope: !24)
-// CHECK:STDOUT: !31 = !DILocation(line: 36, column: 3, scope: !24)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.4d3c36eeac175c1f", scope: null, file: !3, line: 30, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{!19, !19}
+// CHECK:STDOUT: !19 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !16, type: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 31, column: 3, scope: !16)
+// CHECK:STDOUT: !23 = !DILocation(line: 33, column: 7, scope: !16)
+// CHECK:STDOUT: !24 = !DILocation(line: 33, column: 6, scope: !16)
+// CHECK:STDOUT: !25 = !DILocation(line: 34, column: 5, scope: !16)
+// CHECK:STDOUT: !26 = !DILocation(line: 36, column: 15, scope: !16)
+// CHECK:STDOUT: !27 = !DILocation(line: 36, column: 10, scope: !16)
+// CHECK:STDOUT: !28 = !DILocation(line: 36, column: 3, scope: !16)
+// CHECK:STDOUT: !29 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.7abe23e63361d139", scope: null, file: !3, line: 30, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !30)
+// CHECK:STDOUT: !30 = !{!31}
+// CHECK:STDOUT: !31 = !DILocalVariable(arg: 1, scope: !29, type: !19)
+// CHECK:STDOUT: !32 = !DILocation(line: 31, column: 3, scope: !29)
+// CHECK:STDOUT: !33 = !DILocation(line: 33, column: 7, scope: !29)
+// CHECK:STDOUT: !34 = !DILocation(line: 33, column: 6, scope: !29)
+// CHECK:STDOUT: !35 = !DILocation(line: 34, column: 5, scope: !29)
+// CHECK:STDOUT: !36 = !DILocation(line: 36, column: 15, scope: !29)
+// CHECK:STDOUT: !37 = !DILocation(line: 36, column: 10, scope: !29)
+// CHECK:STDOUT: !38 = !DILocation(line: 36, column: 3, scope: !29)

+ 108 - 84
toolchain/lower/testdata/function/generic/call_recursive_mutual.carbon

@@ -74,91 +74,91 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 3, !dbg !21
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !22
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 3, !dbg !27
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !28
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %x, !dbg !23
+// CHECK:STDOUT:   ret i32 %x, !dbg !29
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !24
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !25
-// CHECK:STDOUT:   ret i32 %G.call, !dbg !26
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !30
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !31
+// CHECK:STDOUT:   ret i32 %G.call, !dbg !32
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !27 {
+// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !33 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 3, !dbg !28
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !29
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 3, !dbg !40
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !41
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret double %x, !dbg !30
+// CHECK:STDOUT:   ret double %x, !dbg !42
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !31
-// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !32
-// CHECK:STDOUT:   ret double %G.call, !dbg !33
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !43
+// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !44
+// CHECK:STDOUT:   ret double %G.call, !dbg !45
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !34 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !46 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 3, !dbg !35
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !36
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 3, !dbg !50
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !51
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret ptr %x, !dbg !37
+// CHECK:STDOUT:   ret ptr %x, !dbg !52
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !38
-// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !39
-// CHECK:STDOUT:   ret ptr %G.call, !dbg !40
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !53
+// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !54
+// CHECK:STDOUT:   ret ptr %G.call, !dbg !55
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !41 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !56 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !42
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !43
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !60
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !61
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %x, !dbg !44
+// CHECK:STDOUT:   ret i32 %x, !dbg !62
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !45
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !46
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !47
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !63
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !64
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !65
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CG.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !48 {
+// CHECK:STDOUT: define linkonce_odr double @_CG.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !66 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !49
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !50
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !70
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !71
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret double %x, !dbg !51
+// CHECK:STDOUT:   ret double %x, !dbg !72
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !52
-// CHECK:STDOUT:   %F.call = call double @_CF.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !53
-// CHECK:STDOUT:   ret double %F.call, !dbg !54
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !73
+// CHECK:STDOUT:   %F.call = call double @_CF.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !74
+// CHECK:STDOUT:   ret double %F.call, !dbg !75
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !55 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !76 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !56
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !57
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !80
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !81
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret ptr %x, !dbg !58
+// CHECK:STDOUT:   ret ptr %x, !dbg !82
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !59
-// CHECK:STDOUT:   %F.call = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !60
-// CHECK:STDOUT:   ret ptr %F.call, !dbg !61
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !83
+// CHECK:STDOUT:   %F.call = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !84
+// CHECK:STDOUT:   ret ptr %F.call, !dbg !85
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -177,7 +177,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_mutual.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 33, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 34, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 35, column: 3, scope: !4)
@@ -191,45 +191,69 @@ fn M() {
 // CHECK:STDOUT: !17 = !DILocation(line: 41, column: 5, scope: !4)
 // CHECK:STDOUT: !18 = !DILocation(line: 41, column: 3, scope: !4)
 // CHECK:STDOUT: !19 = !DILocation(line: 32, column: 1, scope: !4)
-// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !21 = !DILocation(line: 19, column: 7, scope: !20)
-// CHECK:STDOUT: !22 = !DILocation(line: 19, column: 6, scope: !20)
-// CHECK:STDOUT: !23 = !DILocation(line: 20, column: 5, scope: !20)
-// CHECK:STDOUT: !24 = !DILocation(line: 22, column: 15, scope: !20)
-// CHECK:STDOUT: !25 = !DILocation(line: 22, column: 10, scope: !20)
-// CHECK:STDOUT: !26 = !DILocation(line: 22, column: 3, scope: !20)
-// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !28 = !DILocation(line: 19, column: 7, scope: !27)
-// CHECK:STDOUT: !29 = !DILocation(line: 19, column: 6, scope: !27)
-// CHECK:STDOUT: !30 = !DILocation(line: 20, column: 5, scope: !27)
-// CHECK:STDOUT: !31 = !DILocation(line: 22, column: 15, scope: !27)
-// CHECK:STDOUT: !32 = !DILocation(line: 22, column: 10, scope: !27)
-// CHECK:STDOUT: !33 = !DILocation(line: 22, column: 3, scope: !27)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DILocation(line: 19, column: 7, scope: !34)
-// CHECK:STDOUT: !36 = !DILocation(line: 19, column: 6, scope: !34)
-// CHECK:STDOUT: !37 = !DILocation(line: 20, column: 5, scope: !34)
-// CHECK:STDOUT: !38 = !DILocation(line: 22, column: 15, scope: !34)
-// CHECK:STDOUT: !39 = !DILocation(line: 22, column: 10, scope: !34)
-// CHECK:STDOUT: !40 = !DILocation(line: 22, column: 3, scope: !34)
-// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !42 = !DILocation(line: 26, column: 7, scope: !41)
-// CHECK:STDOUT: !43 = !DILocation(line: 26, column: 6, scope: !41)
-// CHECK:STDOUT: !44 = !DILocation(line: 27, column: 5, scope: !41)
-// CHECK:STDOUT: !45 = !DILocation(line: 29, column: 15, scope: !41)
-// CHECK:STDOUT: !46 = !DILocation(line: 29, column: 10, scope: !41)
-// CHECK:STDOUT: !47 = !DILocation(line: 29, column: 3, scope: !41)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.83aece103b0a8681", scope: null, file: !3, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 26, column: 7, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 26, column: 6, scope: !48)
-// CHECK:STDOUT: !51 = !DILocation(line: 27, column: 5, scope: !48)
-// CHECK:STDOUT: !52 = !DILocation(line: 29, column: 15, scope: !48)
-// CHECK:STDOUT: !53 = !DILocation(line: 29, column: 10, scope: !48)
-// CHECK:STDOUT: !54 = !DILocation(line: 29, column: 3, scope: !48)
-// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 25, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !56 = !DILocation(line: 26, column: 7, scope: !55)
-// CHECK:STDOUT: !57 = !DILocation(line: 26, column: 6, scope: !55)
-// CHECK:STDOUT: !58 = !DILocation(line: 27, column: 5, scope: !55)
-// CHECK:STDOUT: !59 = !DILocation(line: 29, column: 15, scope: !55)
-// CHECK:STDOUT: !60 = !DILocation(line: 29, column: 10, scope: !55)
-// CHECK:STDOUT: !61 = !DILocation(line: 29, column: 3, scope: !55)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 18, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
+// CHECK:STDOUT: !21 = !DISubroutineType(types: !22)
+// CHECK:STDOUT: !22 = !{!23, !23, !23}
+// CHECK:STDOUT: !23 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !24 = !{!25, !26}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !20, type: !23)
+// CHECK:STDOUT: !26 = !DILocalVariable(arg: 2, scope: !20, type: !23)
+// CHECK:STDOUT: !27 = !DILocation(line: 19, column: 7, scope: !20)
+// CHECK:STDOUT: !28 = !DILocation(line: 19, column: 6, scope: !20)
+// CHECK:STDOUT: !29 = !DILocation(line: 20, column: 5, scope: !20)
+// CHECK:STDOUT: !30 = !DILocation(line: 22, column: 15, scope: !20)
+// CHECK:STDOUT: !31 = !DILocation(line: 22, column: 10, scope: !20)
+// CHECK:STDOUT: !32 = !DILocation(line: 22, column: 3, scope: !20)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 18, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !37)
+// CHECK:STDOUT: !34 = !DISubroutineType(types: !35)
+// CHECK:STDOUT: !35 = !{!36, !36, !23}
+// CHECK:STDOUT: !36 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !37 = !{!38, !39}
+// CHECK:STDOUT: !38 = !DILocalVariable(arg: 1, scope: !33, type: !36)
+// CHECK:STDOUT: !39 = !DILocalVariable(arg: 2, scope: !33, type: !23)
+// CHECK:STDOUT: !40 = !DILocation(line: 19, column: 7, scope: !33)
+// CHECK:STDOUT: !41 = !DILocation(line: 19, column: 6, scope: !33)
+// CHECK:STDOUT: !42 = !DILocation(line: 20, column: 5, scope: !33)
+// CHECK:STDOUT: !43 = !DILocation(line: 22, column: 15, scope: !33)
+// CHECK:STDOUT: !44 = !DILocation(line: 22, column: 10, scope: !33)
+// CHECK:STDOUT: !45 = !DILocation(line: 22, column: 3, scope: !33)
+// CHECK:STDOUT: !46 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 18, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !47)
+// CHECK:STDOUT: !47 = !{!48, !49}
+// CHECK:STDOUT: !48 = !DILocalVariable(arg: 1, scope: !46, type: !36)
+// CHECK:STDOUT: !49 = !DILocalVariable(arg: 2, scope: !46, type: !23)
+// CHECK:STDOUT: !50 = !DILocation(line: 19, column: 7, scope: !46)
+// CHECK:STDOUT: !51 = !DILocation(line: 19, column: 6, scope: !46)
+// CHECK:STDOUT: !52 = !DILocation(line: 20, column: 5, scope: !46)
+// CHECK:STDOUT: !53 = !DILocation(line: 22, column: 15, scope: !46)
+// CHECK:STDOUT: !54 = !DILocation(line: 22, column: 10, scope: !46)
+// CHECK:STDOUT: !55 = !DILocation(line: 22, column: 3, scope: !46)
+// CHECK:STDOUT: !56 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 25, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !57)
+// CHECK:STDOUT: !57 = !{!58, !59}
+// CHECK:STDOUT: !58 = !DILocalVariable(arg: 1, scope: !56, type: !23)
+// CHECK:STDOUT: !59 = !DILocalVariable(arg: 2, scope: !56, type: !23)
+// CHECK:STDOUT: !60 = !DILocation(line: 26, column: 7, scope: !56)
+// CHECK:STDOUT: !61 = !DILocation(line: 26, column: 6, scope: !56)
+// CHECK:STDOUT: !62 = !DILocation(line: 27, column: 5, scope: !56)
+// CHECK:STDOUT: !63 = !DILocation(line: 29, column: 15, scope: !56)
+// CHECK:STDOUT: !64 = !DILocation(line: 29, column: 10, scope: !56)
+// CHECK:STDOUT: !65 = !DILocation(line: 29, column: 3, scope: !56)
+// CHECK:STDOUT: !66 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.83aece103b0a8681", scope: null, file: !3, line: 25, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !67)
+// CHECK:STDOUT: !67 = !{!68, !69}
+// CHECK:STDOUT: !68 = !DILocalVariable(arg: 1, scope: !66, type: !36)
+// CHECK:STDOUT: !69 = !DILocalVariable(arg: 2, scope: !66, type: !23)
+// CHECK:STDOUT: !70 = !DILocation(line: 26, column: 7, scope: !66)
+// CHECK:STDOUT: !71 = !DILocation(line: 26, column: 6, scope: !66)
+// CHECK:STDOUT: !72 = !DILocation(line: 27, column: 5, scope: !66)
+// CHECK:STDOUT: !73 = !DILocation(line: 29, column: 15, scope: !66)
+// CHECK:STDOUT: !74 = !DILocation(line: 29, column: 10, scope: !66)
+// CHECK:STDOUT: !75 = !DILocation(line: 29, column: 3, scope: !66)
+// CHECK:STDOUT: !76 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 25, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !77)
+// CHECK:STDOUT: !77 = !{!78, !79}
+// CHECK:STDOUT: !78 = !DILocalVariable(arg: 1, scope: !76, type: !36)
+// CHECK:STDOUT: !79 = !DILocalVariable(arg: 2, scope: !76, type: !23)
+// CHECK:STDOUT: !80 = !DILocation(line: 26, column: 7, scope: !76)
+// CHECK:STDOUT: !81 = !DILocation(line: 26, column: 6, scope: !76)
+// CHECK:STDOUT: !82 = !DILocation(line: 27, column: 5, scope: !76)
+// CHECK:STDOUT: !83 = !DILocation(line: 29, column: 15, scope: !76)
+// CHECK:STDOUT: !84 = !DILocation(line: 29, column: 10, scope: !76)
+// CHECK:STDOUT: !85 = !DILocation(line: 29, column: 3, scope: !76)

+ 22 - 14
toolchain/lower/testdata/function/generic/call_recursive_reorder.carbon

@@ -55,16 +55,16 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.2fe87eb83f5a4614(ptr %x, ptr %y, i32 %count) #0 !dbg !17 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !18
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !19
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !26
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !27
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !20
+// CHECK:STDOUT:   ret i32 %count, !dbg !28
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !21
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.2fe87eb83f5a4614(ptr %y, ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !22
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !23
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !29
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.2fe87eb83f5a4614(ptr %y, ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !30
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !31
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -83,7 +83,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_reorder.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 23, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 24, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 25, column: 3, scope: !4)
@@ -94,10 +94,18 @@ fn M() {
 // CHECK:STDOUT: !14 = !DILocation(line: 28, column: 14, scope: !4)
 // CHECK:STDOUT: !15 = !DILocation(line: 28, column: 3, scope: !4)
 // CHECK:STDOUT: !16 = !DILocation(line: 22, column: 1, scope: !4)
-// CHECK:STDOUT: !17 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.2fe87eb83f5a4614", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !18 = !DILocation(line: 16, column: 7, scope: !17)
-// CHECK:STDOUT: !19 = !DILocation(line: 16, column: 6, scope: !17)
-// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 5, scope: !17)
-// CHECK:STDOUT: !21 = !DILocation(line: 19, column: 18, scope: !17)
-// CHECK:STDOUT: !22 = !DILocation(line: 19, column: 10, scope: !17)
-// CHECK:STDOUT: !23 = !DILocation(line: 19, column: 3, scope: !17)
+// CHECK:STDOUT: !17 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.2fe87eb83f5a4614", scope: null, file: !3, line: 15, type: !18, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !22)
+// CHECK:STDOUT: !18 = !DISubroutineType(types: !19)
+// CHECK:STDOUT: !19 = !{!20, !21, !21, !20}
+// CHECK:STDOUT: !20 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !21 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !22 = !{!23, !24, !25}
+// CHECK:STDOUT: !23 = !DILocalVariable(arg: 1, scope: !17, type: !21)
+// CHECK:STDOUT: !24 = !DILocalVariable(arg: 2, scope: !17, type: !21)
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 3, scope: !17, type: !20)
+// CHECK:STDOUT: !26 = !DILocation(line: 16, column: 7, scope: !17)
+// CHECK:STDOUT: !27 = !DILocation(line: 16, column: 6, scope: !17)
+// CHECK:STDOUT: !28 = !DILocation(line: 17, column: 5, scope: !17)
+// CHECK:STDOUT: !29 = !DILocation(line: 19, column: 18, scope: !17)
+// CHECK:STDOUT: !30 = !DILocation(line: 19, column: 10, scope: !17)
+// CHECK:STDOUT: !31 = !DILocation(line: 19, column: 3, scope: !17)

+ 145 - 98
toolchain/lower/testdata/function/generic/call_recursive_reorder_more.carbon

@@ -135,106 +135,106 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.077d2bb2ab5eee86(i16 %x, ptr %y, ptr %z, i32 %count) #0 !dbg !65 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !66
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !67
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !76
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !77
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !68
+// CHECK:STDOUT:   ret i32 %count, !dbg !78
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !69
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.077d2bb2ab5eee86(i16 %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !70
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !71
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !79
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.077d2bb2ab5eee86(i16 %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !80
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !81
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.9a89ac9e10448feb(i32 %x, ptr %y, ptr %z, i32 %count) #0 !dbg !72 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.9a89ac9e10448feb(i32 %x, ptr %y, ptr %z, i32 %count) #0 !dbg !82 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !73
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !74
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !90
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !91
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !75
+// CHECK:STDOUT:   ret i32 %count, !dbg !92
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !76
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.9a89ac9e10448feb(i32 %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !77
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !78
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !93
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.9a89ac9e10448feb(i32 %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !94
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !95
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.76a945443862cc1f(i1 %x, ptr %y, ptr %z, i32 %count) #0 !dbg !79 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.76a945443862cc1f(i1 %x, ptr %y, ptr %z, i32 %count) #0 !dbg !96 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !80
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !81
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !104
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !105
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !82
+// CHECK:STDOUT:   ret i32 %count, !dbg !106
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !83
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.76a945443862cc1f(i1 %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !84
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !85
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !107
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.76a945443862cc1f(i1 %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !108
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !109
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.02da1a7614ea56b6(i64 %x, i1 %y, ptr %z, i32 %count) #0 !dbg !86 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.02da1a7614ea56b6(i64 %x, i1 %y, ptr %z, i32 %count) #0 !dbg !110 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !87
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !88
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !119
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !120
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !89
+// CHECK:STDOUT:   ret i32 %count, !dbg !121
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !90
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.bea8bae6e14e4034(i64 %x, ptr %z, i1 %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !91
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !92
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !122
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.bea8bae6e14e4034(i64 %x, ptr %z, i1 %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !123
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !124
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.4dcab66ec095dfec(double %x, ptr %y, ptr %z, i32 %count) #0 !dbg !93 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.4dcab66ec095dfec(double %x, ptr %y, ptr %z, i32 %count) #0 !dbg !125 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !94
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !95
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !131
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !132
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !96
+// CHECK:STDOUT:   ret i32 %count, !dbg !133
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !97
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.4dcab66ec095dfec(double %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !98
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !99
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !134
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.4dcab66ec095dfec(double %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !135
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !136
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.7776e910959584d9(ptr %x, ptr %y, ptr %z, i32 %count) #0 !dbg !100 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.7776e910959584d9(ptr %x, ptr %y, ptr %z, i32 %count) #0 !dbg !137 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !101
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !102
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !143
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !144
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !103
+// CHECK:STDOUT:   ret i32 %count, !dbg !145
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !104
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.7776e910959584d9(ptr %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !105
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !106
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !146
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.7776e910959584d9(ptr %x, ptr %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !147
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !148
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.bea8bae6e14e4034(i64 %x, ptr %y, i1 %z, i32 %count) #0 !dbg !107 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.bea8bae6e14e4034(i64 %x, ptr %y, i1 %z, i32 %count) #0 !dbg !149 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !108
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !109
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 2, !dbg !155
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then, label %if.else, !dbg !156
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   ret i32 %count, !dbg !110
+// CHECK:STDOUT:   ret i32 %count, !dbg !157
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !111
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.02da1a7614ea56b6(i64 %x, i1 %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !112
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !113
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !158
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.02da1a7614ea56b6(i64 %x, i1 %z, ptr %y, i32 %Int.as.AddWith.impl.Op.call), !dbg !159
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !160
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -253,7 +253,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_reorder_more.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 22, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 23, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 24, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 25, column: 3, scope: !4)
@@ -312,52 +312,99 @@ fn M() {
 // CHECK:STDOUT: !62 = !DILocation(line: 52, column: 25, scope: !4)
 // CHECK:STDOUT: !63 = !DILocation(line: 52, column: 3, scope: !4)
 // CHECK:STDOUT: !64 = !DILocation(line: 22, column: 1, scope: !4)
-// CHECK:STDOUT: !65 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.077d2bb2ab5eee86", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !66 = !DILocation(line: 16, column: 7, scope: !65)
-// CHECK:STDOUT: !67 = !DILocation(line: 16, column: 6, scope: !65)
-// CHECK:STDOUT: !68 = !DILocation(line: 17, column: 5, scope: !65)
-// CHECK:STDOUT: !69 = !DILocation(line: 19, column: 21, scope: !65)
-// CHECK:STDOUT: !70 = !DILocation(line: 19, column: 10, scope: !65)
-// CHECK:STDOUT: !71 = !DILocation(line: 19, column: 3, scope: !65)
-// CHECK:STDOUT: !72 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.9a89ac9e10448feb", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !73 = !DILocation(line: 16, column: 7, scope: !72)
-// CHECK:STDOUT: !74 = !DILocation(line: 16, column: 6, scope: !72)
-// CHECK:STDOUT: !75 = !DILocation(line: 17, column: 5, scope: !72)
-// CHECK:STDOUT: !76 = !DILocation(line: 19, column: 21, scope: !72)
-// CHECK:STDOUT: !77 = !DILocation(line: 19, column: 10, scope: !72)
-// CHECK:STDOUT: !78 = !DILocation(line: 19, column: 3, scope: !72)
-// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.76a945443862cc1f", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !80 = !DILocation(line: 16, column: 7, scope: !79)
-// CHECK:STDOUT: !81 = !DILocation(line: 16, column: 6, scope: !79)
-// CHECK:STDOUT: !82 = !DILocation(line: 17, column: 5, scope: !79)
-// CHECK:STDOUT: !83 = !DILocation(line: 19, column: 21, scope: !79)
-// CHECK:STDOUT: !84 = !DILocation(line: 19, column: 10, scope: !79)
-// CHECK:STDOUT: !85 = !DILocation(line: 19, column: 3, scope: !79)
-// CHECK:STDOUT: !86 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.02da1a7614ea56b6", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !87 = !DILocation(line: 16, column: 7, scope: !86)
-// CHECK:STDOUT: !88 = !DILocation(line: 16, column: 6, scope: !86)
-// CHECK:STDOUT: !89 = !DILocation(line: 17, column: 5, scope: !86)
-// CHECK:STDOUT: !90 = !DILocation(line: 19, column: 21, scope: !86)
-// CHECK:STDOUT: !91 = !DILocation(line: 19, column: 10, scope: !86)
-// CHECK:STDOUT: !92 = !DILocation(line: 19, column: 3, scope: !86)
-// CHECK:STDOUT: !93 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.4dcab66ec095dfec", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !94 = !DILocation(line: 16, column: 7, scope: !93)
-// CHECK:STDOUT: !95 = !DILocation(line: 16, column: 6, scope: !93)
-// CHECK:STDOUT: !96 = !DILocation(line: 17, column: 5, scope: !93)
-// CHECK:STDOUT: !97 = !DILocation(line: 19, column: 21, scope: !93)
-// CHECK:STDOUT: !98 = !DILocation(line: 19, column: 10, scope: !93)
-// CHECK:STDOUT: !99 = !DILocation(line: 19, column: 3, scope: !93)
-// CHECK:STDOUT: !100 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.7776e910959584d9", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !101 = !DILocation(line: 16, column: 7, scope: !100)
-// CHECK:STDOUT: !102 = !DILocation(line: 16, column: 6, scope: !100)
-// CHECK:STDOUT: !103 = !DILocation(line: 17, column: 5, scope: !100)
-// CHECK:STDOUT: !104 = !DILocation(line: 19, column: 21, scope: !100)
-// CHECK:STDOUT: !105 = !DILocation(line: 19, column: 10, scope: !100)
-// CHECK:STDOUT: !106 = !DILocation(line: 19, column: 3, scope: !100)
-// CHECK:STDOUT: !107 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.bea8bae6e14e4034", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !108 = !DILocation(line: 16, column: 7, scope: !107)
-// CHECK:STDOUT: !109 = !DILocation(line: 16, column: 6, scope: !107)
-// CHECK:STDOUT: !110 = !DILocation(line: 17, column: 5, scope: !107)
-// CHECK:STDOUT: !111 = !DILocation(line: 19, column: 21, scope: !107)
-// CHECK:STDOUT: !112 = !DILocation(line: 19, column: 10, scope: !107)
-// CHECK:STDOUT: !113 = !DILocation(line: 19, column: 3, scope: !107)
+// CHECK:STDOUT: !65 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.077d2bb2ab5eee86", scope: null, file: !3, line: 15, type: !66, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !71)
+// CHECK:STDOUT: !66 = !DISubroutineType(types: !67)
+// CHECK:STDOUT: !67 = !{!68, !69, !70, !70, !68}
+// CHECK:STDOUT: !68 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !69 = !DIBasicType(name: "int", size: 16, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !70 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !71 = !{!72, !73, !74, !75}
+// CHECK:STDOUT: !72 = !DILocalVariable(arg: 1, scope: !65, type: !69)
+// CHECK:STDOUT: !73 = !DILocalVariable(arg: 2, scope: !65, type: !70)
+// CHECK:STDOUT: !74 = !DILocalVariable(arg: 3, scope: !65, type: !70)
+// CHECK:STDOUT: !75 = !DILocalVariable(arg: 4, scope: !65, type: !68)
+// CHECK:STDOUT: !76 = !DILocation(line: 16, column: 7, scope: !65)
+// CHECK:STDOUT: !77 = !DILocation(line: 16, column: 6, scope: !65)
+// CHECK:STDOUT: !78 = !DILocation(line: 17, column: 5, scope: !65)
+// CHECK:STDOUT: !79 = !DILocation(line: 19, column: 21, scope: !65)
+// CHECK:STDOUT: !80 = !DILocation(line: 19, column: 10, scope: !65)
+// CHECK:STDOUT: !81 = !DILocation(line: 19, column: 3, scope: !65)
+// CHECK:STDOUT: !82 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.9a89ac9e10448feb", scope: null, file: !3, line: 15, type: !83, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !85)
+// CHECK:STDOUT: !83 = !DISubroutineType(types: !84)
+// CHECK:STDOUT: !84 = !{!68, !68, !70, !70, !68}
+// CHECK:STDOUT: !85 = !{!86, !87, !88, !89}
+// CHECK:STDOUT: !86 = !DILocalVariable(arg: 1, scope: !82, type: !68)
+// CHECK:STDOUT: !87 = !DILocalVariable(arg: 2, scope: !82, type: !70)
+// CHECK:STDOUT: !88 = !DILocalVariable(arg: 3, scope: !82, type: !70)
+// CHECK:STDOUT: !89 = !DILocalVariable(arg: 4, scope: !82, type: !68)
+// CHECK:STDOUT: !90 = !DILocation(line: 16, column: 7, scope: !82)
+// CHECK:STDOUT: !91 = !DILocation(line: 16, column: 6, scope: !82)
+// CHECK:STDOUT: !92 = !DILocation(line: 17, column: 5, scope: !82)
+// CHECK:STDOUT: !93 = !DILocation(line: 19, column: 21, scope: !82)
+// CHECK:STDOUT: !94 = !DILocation(line: 19, column: 10, scope: !82)
+// CHECK:STDOUT: !95 = !DILocation(line: 19, column: 3, scope: !82)
+// CHECK:STDOUT: !96 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.76a945443862cc1f", scope: null, file: !3, line: 15, type: !97, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !99)
+// CHECK:STDOUT: !97 = !DISubroutineType(types: !98)
+// CHECK:STDOUT: !98 = !{!68, !70, !70, !70, !68}
+// CHECK:STDOUT: !99 = !{!100, !101, !102, !103}
+// CHECK:STDOUT: !100 = !DILocalVariable(arg: 1, scope: !96, type: !70)
+// CHECK:STDOUT: !101 = !DILocalVariable(arg: 2, scope: !96, type: !70)
+// CHECK:STDOUT: !102 = !DILocalVariable(arg: 3, scope: !96, type: !70)
+// CHECK:STDOUT: !103 = !DILocalVariable(arg: 4, scope: !96, type: !68)
+// CHECK:STDOUT: !104 = !DILocation(line: 16, column: 7, scope: !96)
+// CHECK:STDOUT: !105 = !DILocation(line: 16, column: 6, scope: !96)
+// CHECK:STDOUT: !106 = !DILocation(line: 17, column: 5, scope: !96)
+// CHECK:STDOUT: !107 = !DILocation(line: 19, column: 21, scope: !96)
+// CHECK:STDOUT: !108 = !DILocation(line: 19, column: 10, scope: !96)
+// CHECK:STDOUT: !109 = !DILocation(line: 19, column: 3, scope: !96)
+// CHECK:STDOUT: !110 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.02da1a7614ea56b6", scope: null, file: !3, line: 15, type: !111, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !114)
+// CHECK:STDOUT: !111 = !DISubroutineType(types: !112)
+// CHECK:STDOUT: !112 = !{!68, !113, !70, !70, !68}
+// CHECK:STDOUT: !113 = !DIBasicType(name: "int", size: 64, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !114 = !{!115, !116, !117, !118}
+// CHECK:STDOUT: !115 = !DILocalVariable(arg: 1, scope: !110, type: !113)
+// CHECK:STDOUT: !116 = !DILocalVariable(arg: 2, scope: !110, type: !70)
+// CHECK:STDOUT: !117 = !DILocalVariable(arg: 3, scope: !110, type: !70)
+// CHECK:STDOUT: !118 = !DILocalVariable(arg: 4, scope: !110, type: !68)
+// CHECK:STDOUT: !119 = !DILocation(line: 16, column: 7, scope: !110)
+// CHECK:STDOUT: !120 = !DILocation(line: 16, column: 6, scope: !110)
+// CHECK:STDOUT: !121 = !DILocation(line: 17, column: 5, scope: !110)
+// CHECK:STDOUT: !122 = !DILocation(line: 19, column: 21, scope: !110)
+// CHECK:STDOUT: !123 = !DILocation(line: 19, column: 10, scope: !110)
+// CHECK:STDOUT: !124 = !DILocation(line: 19, column: 3, scope: !110)
+// CHECK:STDOUT: !125 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.4dcab66ec095dfec", scope: null, file: !3, line: 15, type: !97, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !126)
+// CHECK:STDOUT: !126 = !{!127, !128, !129, !130}
+// CHECK:STDOUT: !127 = !DILocalVariable(arg: 1, scope: !125, type: !70)
+// CHECK:STDOUT: !128 = !DILocalVariable(arg: 2, scope: !125, type: !70)
+// CHECK:STDOUT: !129 = !DILocalVariable(arg: 3, scope: !125, type: !70)
+// CHECK:STDOUT: !130 = !DILocalVariable(arg: 4, scope: !125, type: !68)
+// CHECK:STDOUT: !131 = !DILocation(line: 16, column: 7, scope: !125)
+// CHECK:STDOUT: !132 = !DILocation(line: 16, column: 6, scope: !125)
+// CHECK:STDOUT: !133 = !DILocation(line: 17, column: 5, scope: !125)
+// CHECK:STDOUT: !134 = !DILocation(line: 19, column: 21, scope: !125)
+// CHECK:STDOUT: !135 = !DILocation(line: 19, column: 10, scope: !125)
+// CHECK:STDOUT: !136 = !DILocation(line: 19, column: 3, scope: !125)
+// CHECK:STDOUT: !137 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.7776e910959584d9", scope: null, file: !3, line: 15, type: !97, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !138)
+// CHECK:STDOUT: !138 = !{!139, !140, !141, !142}
+// CHECK:STDOUT: !139 = !DILocalVariable(arg: 1, scope: !137, type: !70)
+// CHECK:STDOUT: !140 = !DILocalVariable(arg: 2, scope: !137, type: !70)
+// CHECK:STDOUT: !141 = !DILocalVariable(arg: 3, scope: !137, type: !70)
+// CHECK:STDOUT: !142 = !DILocalVariable(arg: 4, scope: !137, type: !68)
+// CHECK:STDOUT: !143 = !DILocation(line: 16, column: 7, scope: !137)
+// CHECK:STDOUT: !144 = !DILocation(line: 16, column: 6, scope: !137)
+// CHECK:STDOUT: !145 = !DILocation(line: 17, column: 5, scope: !137)
+// CHECK:STDOUT: !146 = !DILocation(line: 19, column: 21, scope: !137)
+// CHECK:STDOUT: !147 = !DILocation(line: 19, column: 10, scope: !137)
+// CHECK:STDOUT: !148 = !DILocation(line: 19, column: 3, scope: !137)
+// CHECK:STDOUT: !149 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.bea8bae6e14e4034", scope: null, file: !3, line: 15, type: !111, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !150)
+// CHECK:STDOUT: !150 = !{!151, !152, !153, !154}
+// CHECK:STDOUT: !151 = !DILocalVariable(arg: 1, scope: !149, type: !113)
+// CHECK:STDOUT: !152 = !DILocalVariable(arg: 2, scope: !149, type: !70)
+// CHECK:STDOUT: !153 = !DILocalVariable(arg: 3, scope: !149, type: !70)
+// CHECK:STDOUT: !154 = !DILocalVariable(arg: 4, scope: !149, type: !68)
+// CHECK:STDOUT: !155 = !DILocation(line: 16, column: 7, scope: !149)
+// CHECK:STDOUT: !156 = !DILocation(line: 16, column: 6, scope: !149)
+// CHECK:STDOUT: !157 = !DILocation(line: 17, column: 5, scope: !149)
+// CHECK:STDOUT: !158 = !DILocation(line: 19, column: 21, scope: !149)
+// CHECK:STDOUT: !159 = !DILocation(line: 19, column: 10, scope: !149)
+// CHECK:STDOUT: !160 = !DILocation(line: 19, column: 3, scope: !149)

+ 286 - 213
toolchain/lower/testdata/function/generic/call_recursive_sccs_deep.carbon

@@ -117,231 +117,231 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CA.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !20 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !21
-// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !22
-// CHECK:STDOUT:   ret i32 %D.call, !dbg !23
+// CHECK:STDOUT:   call void @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !27
+// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !28
+// CHECK:STDOUT:   ret i32 %D.call, !dbg !29
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CA.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !24 {
+// CHECK:STDOUT: define linkonce_odr double @_CA.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !30 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CB.Main.83aece103b0a8681(double %x, i32 %count), !dbg !25
-// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %count), !dbg !26
-// CHECK:STDOUT:   ret double %D.call, !dbg !27
+// CHECK:STDOUT:   call void @_CB.Main.83aece103b0a8681(double %x, i32 %count), !dbg !37
+// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %count), !dbg !38
+// CHECK:STDOUT:   ret double %D.call, !dbg !39
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CA.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !28 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CA.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !40 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !29
-// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !30
-// CHECK:STDOUT:   ret ptr %D.call, !dbg !31
+// CHECK:STDOUT:   call void @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !44
+// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !45
+// CHECK:STDOUT:   ret ptr %D.call, !dbg !46
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !32 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !47 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !33
-// CHECK:STDOUT:   ret void, !dbg !34
+// CHECK:STDOUT:   call void @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !53
+// CHECK:STDOUT:   ret void, !dbg !54
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !35 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !55 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !36
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc48, label %if.else.loc48, !dbg !37
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !59
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc48, label %if.else.loc48, !dbg !60
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc48:                                    ; preds = %entry
-// CHECK:STDOUT:   ret i32 %x, !dbg !38
+// CHECK:STDOUT:   ret i32 %x, !dbg !61
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc48:                                    ; preds = %entry
-// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !39
-// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !39
-// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc51, label %if.else.loc51, !dbg !40
+// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !62
+// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !62
+// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc51, label %if.else.loc51, !dbg !63
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc51:                                    ; preds = %if.else.loc48
-// CHECK:STDOUT:   %E.call = call i32 @_CE.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !41
-// CHECK:STDOUT:   ret i32 %E.call, !dbg !42
+// CHECK:STDOUT:   %E.call = call i32 @_CE.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !64
+// CHECK:STDOUT:   ret i32 %E.call, !dbg !65
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc51:                                    ; preds = %if.else.loc48
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !43
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !44
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !66
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !67
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !45 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !68 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CC.Main.83aece103b0a8681(double %x, i32 %count), !dbg !46
-// CHECK:STDOUT:   ret void, !dbg !47
+// CHECK:STDOUT:   call void @_CC.Main.83aece103b0a8681(double %x, i32 %count), !dbg !74
+// CHECK:STDOUT:   ret void, !dbg !75
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !48 {
+// CHECK:STDOUT: define linkonce_odr double @_CD.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !76 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !49
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc48, label %if.else.loc48, !dbg !50
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !80
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc48, label %if.else.loc48, !dbg !81
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc48:                                    ; preds = %entry
-// CHECK:STDOUT:   ret double %x, !dbg !51
+// CHECK:STDOUT:   ret double %x, !dbg !82
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc48:                                    ; preds = %entry
-// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !52
-// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !52
-// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc51, label %if.else.loc51, !dbg !53
+// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !83
+// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !83
+// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc51, label %if.else.loc51, !dbg !84
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc51:                                    ; preds = %if.else.loc48
-// CHECK:STDOUT:   %E.call = call double @_CE.Main.83aece103b0a8681(double %x, i32 %count), !dbg !54
-// CHECK:STDOUT:   ret double %E.call, !dbg !55
+// CHECK:STDOUT:   %E.call = call double @_CE.Main.83aece103b0a8681(double %x, i32 %count), !dbg !85
+// CHECK:STDOUT:   ret double %E.call, !dbg !86
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc51:                                    ; preds = %if.else.loc48
-// CHECK:STDOUT:   %F.call = call double @_CF.Main.83aece103b0a8681(double %x, i32 %count), !dbg !56
-// CHECK:STDOUT:   ret double %F.call, !dbg !57
+// CHECK:STDOUT:   %F.call = call double @_CF.Main.83aece103b0a8681(double %x, i32 %count), !dbg !87
+// CHECK:STDOUT:   ret double %F.call, !dbg !88
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !58 {
+// CHECK:STDOUT: define linkonce_odr void @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !89 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !59
-// CHECK:STDOUT:   ret void, !dbg !60
+// CHECK:STDOUT:   call void @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !93
+// CHECK:STDOUT:   ret void, !dbg !94
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !61 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !95 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !62
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc48, label %if.else.loc48, !dbg !63
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.Greater.call = icmp sgt i32 %count, 4, !dbg !99
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.Greater.call, label %if.then.loc48, label %if.else.loc48, !dbg !100
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc48:                                    ; preds = %entry
-// CHECK:STDOUT:   ret ptr %x, !dbg !64
+// CHECK:STDOUT:   ret ptr %x, !dbg !101
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc48:                                    ; preds = %entry
-// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !65
-// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !65
-// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc51, label %if.else.loc51, !dbg !66
+// CHECK:STDOUT:   %Int.as.ModWith.impl.Op.call = srem i32 %count, 2, !dbg !102
+// CHECK:STDOUT:   %Int.as.EqWith.impl.Equal.call = icmp eq i32 %Int.as.ModWith.impl.Op.call, 0, !dbg !102
+// CHECK:STDOUT:   br i1 %Int.as.EqWith.impl.Equal.call, label %if.then.loc51, label %if.else.loc51, !dbg !103
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then.loc51:                                    ; preds = %if.else.loc48
-// CHECK:STDOUT:   %E.call = call ptr @_CE.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !67
-// CHECK:STDOUT:   ret ptr %E.call, !dbg !68
+// CHECK:STDOUT:   %E.call = call ptr @_CE.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !104
+// CHECK:STDOUT:   ret ptr %E.call, !dbg !105
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else.loc51:                                    ; preds = %if.else.loc48
-// CHECK:STDOUT:   %F.call = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !69
-// CHECK:STDOUT:   ret ptr %F.call, !dbg !70
+// CHECK:STDOUT:   %F.call = call ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !106
+// CHECK:STDOUT:   ret ptr %F.call, !dbg !107
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !71 {
+// CHECK:STDOUT: define linkonce_odr void @_CC.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !108 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.LessOrEquivalent.call = icmp sle i32 %count, 2, !dbg !72
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.LessOrEquivalent.call, label %if.then, label %if.else, !dbg !73
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.LessOrEquivalent.call = icmp sle i32 %count, 2, !dbg !112
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.LessOrEquivalent.call, label %if.then, label %if.else, !dbg !113
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 %count), !dbg !74
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !75
-// CHECK:STDOUT:   call void @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !76
-// CHECK:STDOUT:   br label %if.else, !dbg !77
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 %count), !dbg !114
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !115
+// CHECK:STDOUT:   call void @_CB.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !116
+// CHECK:STDOUT:   br label %if.else, !dbg !117
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %if.then, %entry
-// CHECK:STDOUT:   ret void, !dbg !78
+// CHECK:STDOUT:   ret void, !dbg !118
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CE.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !79 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CE.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !119 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !80
-// CHECK:STDOUT:   ret i32 %G.call, !dbg !81
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !123
+// CHECK:STDOUT:   ret i32 %G.call, !dbg !124
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !82 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !125 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !83
-// CHECK:STDOUT:   ret i32 %G.call, !dbg !84
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count), !dbg !129
+// CHECK:STDOUT:   ret i32 %G.call, !dbg !130
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CC.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !85 {
+// CHECK:STDOUT: define linkonce_odr void @_CC.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !131 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.LessOrEquivalent.call = icmp sle i32 %count, 2, !dbg !86
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.LessOrEquivalent.call, label %if.then, label %if.else, !dbg !87
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.LessOrEquivalent.call = icmp sle i32 %count, 2, !dbg !135
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.LessOrEquivalent.call, label %if.then, label %if.else, !dbg !136
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 %count), !dbg !88
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !89
-// CHECK:STDOUT:   call void @_CB.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !90
-// CHECK:STDOUT:   br label %if.else, !dbg !91
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 %count), !dbg !137
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !138
+// CHECK:STDOUT:   call void @_CB.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !139
+// CHECK:STDOUT:   br label %if.else, !dbg !140
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %if.then, %entry
-// CHECK:STDOUT:   ret void, !dbg !92
+// CHECK:STDOUT:   ret void, !dbg !141
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CE.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !93 {
+// CHECK:STDOUT: define linkonce_odr double @_CE.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !142 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x, i32 %count), !dbg !94
-// CHECK:STDOUT:   ret double %G.call, !dbg !95
+// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x, i32 %count), !dbg !146
+// CHECK:STDOUT:   ret double %G.call, !dbg !147
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !96 {
+// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !148 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x, i32 %count), !dbg !97
-// CHECK:STDOUT:   ret double %G.call, !dbg !98
+// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x, i32 %count), !dbg !152
+// CHECK:STDOUT:   ret double %G.call, !dbg !153
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !99 {
+// CHECK:STDOUT: define linkonce_odr void @_CC.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !154 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.OrderedWith.impl.LessOrEquivalent.call = icmp sle i32 %count, 2, !dbg !100
-// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.LessOrEquivalent.call, label %if.then, label %if.else, !dbg !101
+// CHECK:STDOUT:   %Int.as.OrderedWith.impl.LessOrEquivalent.call = icmp sle i32 %count, 2, !dbg !158
+// CHECK:STDOUT:   br i1 %Int.as.OrderedWith.impl.LessOrEquivalent.call, label %if.then, label %if.else, !dbg !159
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 %count), !dbg !102
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !103
-// CHECK:STDOUT:   call void @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !104
-// CHECK:STDOUT:   br label %if.else, !dbg !105
+// CHECK:STDOUT:   %Print.call = call i32 (ptr, ...) @printf(ptr @printf.int.format, i32 %count), !dbg !160
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !161
+// CHECK:STDOUT:   call void @_CB.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !162
+// CHECK:STDOUT:   br label %if.else, !dbg !163
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %if.then, %entry
-// CHECK:STDOUT:   ret void, !dbg !106
+// CHECK:STDOUT:   ret void, !dbg !164
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CE.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !107 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CE.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !165 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !108
-// CHECK:STDOUT:   ret ptr %G.call, !dbg !109
+// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !169
+// CHECK:STDOUT:   ret ptr %G.call, !dbg !170
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !110 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !171 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !111
-// CHECK:STDOUT:   ret ptr %G.call, !dbg !112
+// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count), !dbg !175
+// CHECK:STDOUT:   ret ptr %G.call, !dbg !176
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare i32 @printf(ptr, ...)
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !113 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.5450dc8e8b8e0899(i32 %x, i32 %count) #0 !dbg !177 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !114
-// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !115
-// CHECK:STDOUT:   ret i32 %D.call, !dbg !116
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !181
+// CHECK:STDOUT:   %D.call = call i32 @_CD.Main.5450dc8e8b8e0899(i32 %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !182
+// CHECK:STDOUT:   ret i32 %D.call, !dbg !183
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CG.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !117 {
+// CHECK:STDOUT: define linkonce_odr double @_CG.Main.83aece103b0a8681(double %x, i32 %count) #0 !dbg !184 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !118
-// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !119
-// CHECK:STDOUT:   ret double %D.call, !dbg !120
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !188
+// CHECK:STDOUT:   %D.call = call double @_CD.Main.83aece103b0a8681(double %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !189
+// CHECK:STDOUT:   ret double %D.call, !dbg !190
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !121 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CG.Main.0a952f8bcc623ce6(ptr %x, i32 %count) #0 !dbg !191 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !122
-// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !123
-// CHECK:STDOUT:   ret ptr %D.call, !dbg !124
+// CHECK:STDOUT:   %Int.as.AddWith.impl.Op.call = add i32 %count, 1, !dbg !195
+// CHECK:STDOUT:   %D.call = call ptr @_CD.Main.0a952f8bcc623ce6(ptr %x, i32 %Int.as.AddWith.impl.Op.call), !dbg !196
+// CHECK:STDOUT:   ret ptr %D.call, !dbg !197
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -364,7 +364,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_recursive_sccs_deep.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 73, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 74, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 75, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 76, column: 3, scope: !4)
@@ -378,108 +378,181 @@ fn M() {
 // CHECK:STDOUT: !17 = !DILocation(line: 82, column: 5, scope: !4)
 // CHECK:STDOUT: !18 = !DILocation(line: 82, column: 3, scope: !4)
 // CHECK:STDOUT: !19 = !DILocation(line: 73, column: 1, scope: !4)
-// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 31, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !21 = !DILocation(line: 32, column: 3, scope: !20)
-// CHECK:STDOUT: !22 = !DILocation(line: 33, column: 10, scope: !20)
-// CHECK:STDOUT: !23 = !DILocation(line: 33, column: 3, scope: !20)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.83aece103b0a8681", scope: null, file: !3, line: 31, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 32, column: 3, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 33, column: 10, scope: !24)
-// CHECK:STDOUT: !27 = !DILocation(line: 33, column: 3, scope: !24)
-// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 31, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !29 = !DILocation(line: 32, column: 3, scope: !28)
-// CHECK:STDOUT: !30 = !DILocation(line: 33, column: 10, scope: !28)
-// CHECK:STDOUT: !31 = !DILocation(line: 33, column: 3, scope: !28)
-// CHECK:STDOUT: !32 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 36, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !33 = !DILocation(line: 37, column: 3, scope: !32)
-// CHECK:STDOUT: !34 = !DILocation(line: 36, column: 1, scope: !32)
-// CHECK:STDOUT: !35 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 47, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !36 = !DILocation(line: 48, column: 7, scope: !35)
-// CHECK:STDOUT: !37 = !DILocation(line: 48, column: 6, scope: !35)
-// CHECK:STDOUT: !38 = !DILocation(line: 49, column: 5, scope: !35)
-// CHECK:STDOUT: !39 = !DILocation(line: 51, column: 7, scope: !35)
-// CHECK:STDOUT: !40 = !DILocation(line: 51, column: 6, scope: !35)
-// CHECK:STDOUT: !41 = !DILocation(line: 52, column: 12, scope: !35)
-// CHECK:STDOUT: !42 = !DILocation(line: 52, column: 5, scope: !35)
-// CHECK:STDOUT: !43 = !DILocation(line: 54, column: 12, scope: !35)
-// CHECK:STDOUT: !44 = !DILocation(line: 54, column: 5, scope: !35)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.83aece103b0a8681", scope: null, file: !3, line: 36, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 37, column: 3, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 36, column: 1, scope: !45)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 47, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 48, column: 7, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 48, column: 6, scope: !48)
-// CHECK:STDOUT: !51 = !DILocation(line: 49, column: 5, scope: !48)
-// CHECK:STDOUT: !52 = !DILocation(line: 51, column: 7, scope: !48)
-// CHECK:STDOUT: !53 = !DILocation(line: 51, column: 6, scope: !48)
-// CHECK:STDOUT: !54 = !DILocation(line: 52, column: 12, scope: !48)
-// CHECK:STDOUT: !55 = !DILocation(line: 52, column: 5, scope: !48)
-// CHECK:STDOUT: !56 = !DILocation(line: 54, column: 12, scope: !48)
-// CHECK:STDOUT: !57 = !DILocation(line: 54, column: 5, scope: !48)
-// CHECK:STDOUT: !58 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 36, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !59 = !DILocation(line: 37, column: 3, scope: !58)
-// CHECK:STDOUT: !60 = !DILocation(line: 36, column: 1, scope: !58)
-// CHECK:STDOUT: !61 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 47, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !62 = !DILocation(line: 48, column: 7, scope: !61)
-// CHECK:STDOUT: !63 = !DILocation(line: 48, column: 6, scope: !61)
-// CHECK:STDOUT: !64 = !DILocation(line: 49, column: 5, scope: !61)
-// CHECK:STDOUT: !65 = !DILocation(line: 51, column: 7, scope: !61)
-// CHECK:STDOUT: !66 = !DILocation(line: 51, column: 6, scope: !61)
-// CHECK:STDOUT: !67 = !DILocation(line: 52, column: 12, scope: !61)
-// CHECK:STDOUT: !68 = !DILocation(line: 52, column: 5, scope: !61)
-// CHECK:STDOUT: !69 = !DILocation(line: 54, column: 12, scope: !61)
-// CHECK:STDOUT: !70 = !DILocation(line: 54, column: 5, scope: !61)
-// CHECK:STDOUT: !71 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 40, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !72 = !DILocation(line: 41, column: 7, scope: !71)
-// CHECK:STDOUT: !73 = !DILocation(line: 41, column: 6, scope: !71)
-// CHECK:STDOUT: !74 = !DILocation(line: 42, column: 5, scope: !71)
-// CHECK:STDOUT: !75 = !DILocation(line: 43, column: 10, scope: !71)
-// CHECK:STDOUT: !76 = !DILocation(line: 43, column: 5, scope: !71)
-// CHECK:STDOUT: !77 = !DILocation(line: 41, column: 3, scope: !71)
-// CHECK:STDOUT: !78 = !DILocation(line: 40, column: 1, scope: !71)
-// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "E", linkageName: "_CE.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 60, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !80 = !DILocation(line: 61, column: 10, scope: !79)
-// CHECK:STDOUT: !81 = !DILocation(line: 61, column: 3, scope: !79)
-// CHECK:STDOUT: !82 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 64, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !83 = !DILocation(line: 65, column: 10, scope: !82)
-// CHECK:STDOUT: !84 = !DILocation(line: 65, column: 3, scope: !82)
-// CHECK:STDOUT: !85 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.83aece103b0a8681", scope: null, file: !3, line: 40, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !86 = !DILocation(line: 41, column: 7, scope: !85)
-// CHECK:STDOUT: !87 = !DILocation(line: 41, column: 6, scope: !85)
-// CHECK:STDOUT: !88 = !DILocation(line: 42, column: 5, scope: !85)
-// CHECK:STDOUT: !89 = !DILocation(line: 43, column: 10, scope: !85)
-// CHECK:STDOUT: !90 = !DILocation(line: 43, column: 5, scope: !85)
-// CHECK:STDOUT: !91 = !DILocation(line: 41, column: 3, scope: !85)
-// CHECK:STDOUT: !92 = !DILocation(line: 40, column: 1, scope: !85)
-// CHECK:STDOUT: !93 = distinct !DISubprogram(name: "E", linkageName: "_CE.Main.83aece103b0a8681", scope: null, file: !3, line: 60, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !94 = !DILocation(line: 61, column: 10, scope: !93)
-// CHECK:STDOUT: !95 = !DILocation(line: 61, column: 3, scope: !93)
-// CHECK:STDOUT: !96 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 64, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !97 = !DILocation(line: 65, column: 10, scope: !96)
-// CHECK:STDOUT: !98 = !DILocation(line: 65, column: 3, scope: !96)
-// CHECK:STDOUT: !99 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 40, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !100 = !DILocation(line: 41, column: 7, scope: !99)
-// CHECK:STDOUT: !101 = !DILocation(line: 41, column: 6, scope: !99)
-// CHECK:STDOUT: !102 = !DILocation(line: 42, column: 5, scope: !99)
-// CHECK:STDOUT: !103 = !DILocation(line: 43, column: 10, scope: !99)
-// CHECK:STDOUT: !104 = !DILocation(line: 43, column: 5, scope: !99)
-// CHECK:STDOUT: !105 = !DILocation(line: 41, column: 3, scope: !99)
-// CHECK:STDOUT: !106 = !DILocation(line: 40, column: 1, scope: !99)
-// CHECK:STDOUT: !107 = distinct !DISubprogram(name: "E", linkageName: "_CE.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 60, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !108 = !DILocation(line: 61, column: 10, scope: !107)
-// CHECK:STDOUT: !109 = !DILocation(line: 61, column: 3, scope: !107)
-// CHECK:STDOUT: !110 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 64, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !111 = !DILocation(line: 65, column: 10, scope: !110)
-// CHECK:STDOUT: !112 = !DILocation(line: 65, column: 3, scope: !110)
-// CHECK:STDOUT: !113 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 68, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !114 = !DILocation(line: 69, column: 15, scope: !113)
-// CHECK:STDOUT: !115 = !DILocation(line: 69, column: 10, scope: !113)
-// CHECK:STDOUT: !116 = !DILocation(line: 69, column: 3, scope: !113)
-// CHECK:STDOUT: !117 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.83aece103b0a8681", scope: null, file: !3, line: 68, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !118 = !DILocation(line: 69, column: 15, scope: !117)
-// CHECK:STDOUT: !119 = !DILocation(line: 69, column: 10, scope: !117)
-// CHECK:STDOUT: !120 = !DILocation(line: 69, column: 3, scope: !117)
-// CHECK:STDOUT: !121 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 68, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !122 = !DILocation(line: 69, column: 15, scope: !121)
-// CHECK:STDOUT: !123 = !DILocation(line: 69, column: 10, scope: !121)
-// CHECK:STDOUT: !124 = !DILocation(line: 69, column: 3, scope: !121)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 31, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !24)
+// CHECK:STDOUT: !21 = !DISubroutineType(types: !22)
+// CHECK:STDOUT: !22 = !{!23, !23, !23}
+// CHECK:STDOUT: !23 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !24 = !{!25, !26}
+// CHECK:STDOUT: !25 = !DILocalVariable(arg: 1, scope: !20, type: !23)
+// CHECK:STDOUT: !26 = !DILocalVariable(arg: 2, scope: !20, type: !23)
+// CHECK:STDOUT: !27 = !DILocation(line: 32, column: 3, scope: !20)
+// CHECK:STDOUT: !28 = !DILocation(line: 33, column: 10, scope: !20)
+// CHECK:STDOUT: !29 = !DILocation(line: 33, column: 3, scope: !20)
+// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.83aece103b0a8681", scope: null, file: !3, line: 31, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !34)
+// CHECK:STDOUT: !31 = !DISubroutineType(types: !32)
+// CHECK:STDOUT: !32 = !{!33, !33, !23}
+// CHECK:STDOUT: !33 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !34 = !{!35, !36}
+// CHECK:STDOUT: !35 = !DILocalVariable(arg: 1, scope: !30, type: !33)
+// CHECK:STDOUT: !36 = !DILocalVariable(arg: 2, scope: !30, type: !23)
+// CHECK:STDOUT: !37 = !DILocation(line: 32, column: 3, scope: !30)
+// CHECK:STDOUT: !38 = !DILocation(line: 33, column: 10, scope: !30)
+// CHECK:STDOUT: !39 = !DILocation(line: 33, column: 3, scope: !30)
+// CHECK:STDOUT: !40 = distinct !DISubprogram(name: "A", linkageName: "_CA.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 31, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !41)
+// CHECK:STDOUT: !41 = !{!42, !43}
+// CHECK:STDOUT: !42 = !DILocalVariable(arg: 1, scope: !40, type: !33)
+// CHECK:STDOUT: !43 = !DILocalVariable(arg: 2, scope: !40, type: !23)
+// CHECK:STDOUT: !44 = !DILocation(line: 32, column: 3, scope: !40)
+// CHECK:STDOUT: !45 = !DILocation(line: 33, column: 10, scope: !40)
+// CHECK:STDOUT: !46 = !DILocation(line: 33, column: 3, scope: !40)
+// CHECK:STDOUT: !47 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 36, type: !48, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !50)
+// CHECK:STDOUT: !48 = !DISubroutineType(types: !49)
+// CHECK:STDOUT: !49 = !{null, !23, !23}
+// CHECK:STDOUT: !50 = !{!51, !52}
+// CHECK:STDOUT: !51 = !DILocalVariable(arg: 1, scope: !47, type: !23)
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 2, scope: !47, type: !23)
+// CHECK:STDOUT: !53 = !DILocation(line: 37, column: 3, scope: !47)
+// CHECK:STDOUT: !54 = !DILocation(line: 36, column: 1, scope: !47)
+// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 47, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !56)
+// CHECK:STDOUT: !56 = !{!57, !58}
+// CHECK:STDOUT: !57 = !DILocalVariable(arg: 1, scope: !55, type: !23)
+// CHECK:STDOUT: !58 = !DILocalVariable(arg: 2, scope: !55, type: !23)
+// CHECK:STDOUT: !59 = !DILocation(line: 48, column: 7, scope: !55)
+// CHECK:STDOUT: !60 = !DILocation(line: 48, column: 6, scope: !55)
+// CHECK:STDOUT: !61 = !DILocation(line: 49, column: 5, scope: !55)
+// CHECK:STDOUT: !62 = !DILocation(line: 51, column: 7, scope: !55)
+// CHECK:STDOUT: !63 = !DILocation(line: 51, column: 6, scope: !55)
+// CHECK:STDOUT: !64 = !DILocation(line: 52, column: 12, scope: !55)
+// CHECK:STDOUT: !65 = !DILocation(line: 52, column: 5, scope: !55)
+// CHECK:STDOUT: !66 = !DILocation(line: 54, column: 12, scope: !55)
+// CHECK:STDOUT: !67 = !DILocation(line: 54, column: 5, scope: !55)
+// CHECK:STDOUT: !68 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.83aece103b0a8681", scope: null, file: !3, line: 36, type: !69, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !71)
+// CHECK:STDOUT: !69 = !DISubroutineType(types: !70)
+// CHECK:STDOUT: !70 = !{null, !33, !23}
+// CHECK:STDOUT: !71 = !{!72, !73}
+// CHECK:STDOUT: !72 = !DILocalVariable(arg: 1, scope: !68, type: !33)
+// CHECK:STDOUT: !73 = !DILocalVariable(arg: 2, scope: !68, type: !23)
+// CHECK:STDOUT: !74 = !DILocation(line: 37, column: 3, scope: !68)
+// CHECK:STDOUT: !75 = !DILocation(line: 36, column: 1, scope: !68)
+// CHECK:STDOUT: !76 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.83aece103b0a8681", scope: null, file: !3, line: 47, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !77)
+// CHECK:STDOUT: !77 = !{!78, !79}
+// CHECK:STDOUT: !78 = !DILocalVariable(arg: 1, scope: !76, type: !33)
+// CHECK:STDOUT: !79 = !DILocalVariable(arg: 2, scope: !76, type: !23)
+// CHECK:STDOUT: !80 = !DILocation(line: 48, column: 7, scope: !76)
+// CHECK:STDOUT: !81 = !DILocation(line: 48, column: 6, scope: !76)
+// CHECK:STDOUT: !82 = !DILocation(line: 49, column: 5, scope: !76)
+// CHECK:STDOUT: !83 = !DILocation(line: 51, column: 7, scope: !76)
+// CHECK:STDOUT: !84 = !DILocation(line: 51, column: 6, scope: !76)
+// CHECK:STDOUT: !85 = !DILocation(line: 52, column: 12, scope: !76)
+// CHECK:STDOUT: !86 = !DILocation(line: 52, column: 5, scope: !76)
+// CHECK:STDOUT: !87 = !DILocation(line: 54, column: 12, scope: !76)
+// CHECK:STDOUT: !88 = !DILocation(line: 54, column: 5, scope: !76)
+// CHECK:STDOUT: !89 = distinct !DISubprogram(name: "B", linkageName: "_CB.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 36, type: !69, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !90)
+// CHECK:STDOUT: !90 = !{!91, !92}
+// CHECK:STDOUT: !91 = !DILocalVariable(arg: 1, scope: !89, type: !33)
+// CHECK:STDOUT: !92 = !DILocalVariable(arg: 2, scope: !89, type: !23)
+// CHECK:STDOUT: !93 = !DILocation(line: 37, column: 3, scope: !89)
+// CHECK:STDOUT: !94 = !DILocation(line: 36, column: 1, scope: !89)
+// CHECK:STDOUT: !95 = distinct !DISubprogram(name: "D", linkageName: "_CD.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 47, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !96)
+// CHECK:STDOUT: !96 = !{!97, !98}
+// CHECK:STDOUT: !97 = !DILocalVariable(arg: 1, scope: !95, type: !33)
+// CHECK:STDOUT: !98 = !DILocalVariable(arg: 2, scope: !95, type: !23)
+// CHECK:STDOUT: !99 = !DILocation(line: 48, column: 7, scope: !95)
+// CHECK:STDOUT: !100 = !DILocation(line: 48, column: 6, scope: !95)
+// CHECK:STDOUT: !101 = !DILocation(line: 49, column: 5, scope: !95)
+// CHECK:STDOUT: !102 = !DILocation(line: 51, column: 7, scope: !95)
+// CHECK:STDOUT: !103 = !DILocation(line: 51, column: 6, scope: !95)
+// CHECK:STDOUT: !104 = !DILocation(line: 52, column: 12, scope: !95)
+// CHECK:STDOUT: !105 = !DILocation(line: 52, column: 5, scope: !95)
+// CHECK:STDOUT: !106 = !DILocation(line: 54, column: 12, scope: !95)
+// CHECK:STDOUT: !107 = !DILocation(line: 54, column: 5, scope: !95)
+// CHECK:STDOUT: !108 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 40, type: !48, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !109)
+// CHECK:STDOUT: !109 = !{!110, !111}
+// CHECK:STDOUT: !110 = !DILocalVariable(arg: 1, scope: !108, type: !23)
+// CHECK:STDOUT: !111 = !DILocalVariable(arg: 2, scope: !108, type: !23)
+// CHECK:STDOUT: !112 = !DILocation(line: 41, column: 7, scope: !108)
+// CHECK:STDOUT: !113 = !DILocation(line: 41, column: 6, scope: !108)
+// CHECK:STDOUT: !114 = !DILocation(line: 42, column: 5, scope: !108)
+// CHECK:STDOUT: !115 = !DILocation(line: 43, column: 10, scope: !108)
+// CHECK:STDOUT: !116 = !DILocation(line: 43, column: 5, scope: !108)
+// CHECK:STDOUT: !117 = !DILocation(line: 41, column: 3, scope: !108)
+// CHECK:STDOUT: !118 = !DILocation(line: 40, column: 1, scope: !108)
+// CHECK:STDOUT: !119 = distinct !DISubprogram(name: "E", linkageName: "_CE.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 60, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !120)
+// CHECK:STDOUT: !120 = !{!121, !122}
+// CHECK:STDOUT: !121 = !DILocalVariable(arg: 1, scope: !119, type: !23)
+// CHECK:STDOUT: !122 = !DILocalVariable(arg: 2, scope: !119, type: !23)
+// CHECK:STDOUT: !123 = !DILocation(line: 61, column: 10, scope: !119)
+// CHECK:STDOUT: !124 = !DILocation(line: 61, column: 3, scope: !119)
+// CHECK:STDOUT: !125 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 64, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !126)
+// CHECK:STDOUT: !126 = !{!127, !128}
+// CHECK:STDOUT: !127 = !DILocalVariable(arg: 1, scope: !125, type: !23)
+// CHECK:STDOUT: !128 = !DILocalVariable(arg: 2, scope: !125, type: !23)
+// CHECK:STDOUT: !129 = !DILocation(line: 65, column: 10, scope: !125)
+// CHECK:STDOUT: !130 = !DILocation(line: 65, column: 3, scope: !125)
+// CHECK:STDOUT: !131 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.83aece103b0a8681", scope: null, file: !3, line: 40, type: !69, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !132)
+// CHECK:STDOUT: !132 = !{!133, !134}
+// CHECK:STDOUT: !133 = !DILocalVariable(arg: 1, scope: !131, type: !33)
+// CHECK:STDOUT: !134 = !DILocalVariable(arg: 2, scope: !131, type: !23)
+// CHECK:STDOUT: !135 = !DILocation(line: 41, column: 7, scope: !131)
+// CHECK:STDOUT: !136 = !DILocation(line: 41, column: 6, scope: !131)
+// CHECK:STDOUT: !137 = !DILocation(line: 42, column: 5, scope: !131)
+// CHECK:STDOUT: !138 = !DILocation(line: 43, column: 10, scope: !131)
+// CHECK:STDOUT: !139 = !DILocation(line: 43, column: 5, scope: !131)
+// CHECK:STDOUT: !140 = !DILocation(line: 41, column: 3, scope: !131)
+// CHECK:STDOUT: !141 = !DILocation(line: 40, column: 1, scope: !131)
+// CHECK:STDOUT: !142 = distinct !DISubprogram(name: "E", linkageName: "_CE.Main.83aece103b0a8681", scope: null, file: !3, line: 60, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !143)
+// CHECK:STDOUT: !143 = !{!144, !145}
+// CHECK:STDOUT: !144 = !DILocalVariable(arg: 1, scope: !142, type: !33)
+// CHECK:STDOUT: !145 = !DILocalVariable(arg: 2, scope: !142, type: !23)
+// CHECK:STDOUT: !146 = !DILocation(line: 61, column: 10, scope: !142)
+// CHECK:STDOUT: !147 = !DILocation(line: 61, column: 3, scope: !142)
+// CHECK:STDOUT: !148 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 64, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !149)
+// CHECK:STDOUT: !149 = !{!150, !151}
+// CHECK:STDOUT: !150 = !DILocalVariable(arg: 1, scope: !148, type: !33)
+// CHECK:STDOUT: !151 = !DILocalVariable(arg: 2, scope: !148, type: !23)
+// CHECK:STDOUT: !152 = !DILocation(line: 65, column: 10, scope: !148)
+// CHECK:STDOUT: !153 = !DILocation(line: 65, column: 3, scope: !148)
+// CHECK:STDOUT: !154 = distinct !DISubprogram(name: "C", linkageName: "_CC.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 40, type: !69, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !155)
+// CHECK:STDOUT: !155 = !{!156, !157}
+// CHECK:STDOUT: !156 = !DILocalVariable(arg: 1, scope: !154, type: !33)
+// CHECK:STDOUT: !157 = !DILocalVariable(arg: 2, scope: !154, type: !23)
+// CHECK:STDOUT: !158 = !DILocation(line: 41, column: 7, scope: !154)
+// CHECK:STDOUT: !159 = !DILocation(line: 41, column: 6, scope: !154)
+// CHECK:STDOUT: !160 = !DILocation(line: 42, column: 5, scope: !154)
+// CHECK:STDOUT: !161 = !DILocation(line: 43, column: 10, scope: !154)
+// CHECK:STDOUT: !162 = !DILocation(line: 43, column: 5, scope: !154)
+// CHECK:STDOUT: !163 = !DILocation(line: 41, column: 3, scope: !154)
+// CHECK:STDOUT: !164 = !DILocation(line: 40, column: 1, scope: !154)
+// CHECK:STDOUT: !165 = distinct !DISubprogram(name: "E", linkageName: "_CE.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 60, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !166)
+// CHECK:STDOUT: !166 = !{!167, !168}
+// CHECK:STDOUT: !167 = !DILocalVariable(arg: 1, scope: !165, type: !33)
+// CHECK:STDOUT: !168 = !DILocalVariable(arg: 2, scope: !165, type: !23)
+// CHECK:STDOUT: !169 = !DILocation(line: 61, column: 10, scope: !165)
+// CHECK:STDOUT: !170 = !DILocation(line: 61, column: 3, scope: !165)
+// CHECK:STDOUT: !171 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 64, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !172)
+// CHECK:STDOUT: !172 = !{!173, !174}
+// CHECK:STDOUT: !173 = !DILocalVariable(arg: 1, scope: !171, type: !33)
+// CHECK:STDOUT: !174 = !DILocalVariable(arg: 2, scope: !171, type: !23)
+// CHECK:STDOUT: !175 = !DILocation(line: 65, column: 10, scope: !171)
+// CHECK:STDOUT: !176 = !DILocation(line: 65, column: 3, scope: !171)
+// CHECK:STDOUT: !177 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 68, type: !21, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !178)
+// CHECK:STDOUT: !178 = !{!179, !180}
+// CHECK:STDOUT: !179 = !DILocalVariable(arg: 1, scope: !177, type: !23)
+// CHECK:STDOUT: !180 = !DILocalVariable(arg: 2, scope: !177, type: !23)
+// CHECK:STDOUT: !181 = !DILocation(line: 69, column: 15, scope: !177)
+// CHECK:STDOUT: !182 = !DILocation(line: 69, column: 10, scope: !177)
+// CHECK:STDOUT: !183 = !DILocation(line: 69, column: 3, scope: !177)
+// CHECK:STDOUT: !184 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.83aece103b0a8681", scope: null, file: !3, line: 68, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !185)
+// CHECK:STDOUT: !185 = !{!186, !187}
+// CHECK:STDOUT: !186 = !DILocalVariable(arg: 1, scope: !184, type: !33)
+// CHECK:STDOUT: !187 = !DILocalVariable(arg: 2, scope: !184, type: !23)
+// CHECK:STDOUT: !188 = !DILocation(line: 69, column: 15, scope: !184)
+// CHECK:STDOUT: !189 = !DILocation(line: 69, column: 10, scope: !184)
+// CHECK:STDOUT: !190 = !DILocation(line: 69, column: 3, scope: !184)
+// CHECK:STDOUT: !191 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 68, type: !31, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !192)
+// CHECK:STDOUT: !192 = !{!193, !194}
+// CHECK:STDOUT: !193 = !DILocalVariable(arg: 1, scope: !191, type: !33)
+// CHECK:STDOUT: !194 = !DILocalVariable(arg: 2, scope: !191, type: !23)
+// CHECK:STDOUT: !195 = !DILocation(line: 69, column: 15, scope: !191)
+// CHECK:STDOUT: !196 = !DILocation(line: 69, column: 10, scope: !191)
+// CHECK:STDOUT: !197 = !DILocation(line: 69, column: 3, scope: !191)

+ 114 - 76
toolchain/lower/testdata/function/generic/call_specific_in_class.carbon

@@ -86,89 +86,89 @@ fn M() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr ptr @_CF.Main.0a952f8bcc623ce6(ptr %x) #0 !dbg !25 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x), !dbg !26
-// CHECK:STDOUT:   ret ptr %G.call, !dbg !27
+// CHECK:STDOUT:   %G.call = call ptr @_CG.Main.0a952f8bcc623ce6(ptr %x), !dbg !31
+// CHECK:STDOUT:   ret ptr %G.call, !dbg !32
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !28 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !33 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x), !dbg !29
-// CHECK:STDOUT:   ret i32 %G.call, !dbg !30
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main.5450dc8e8b8e0899(i32 %x), !dbg !39
+// CHECK:STDOUT:   ret i32 %G.call, !dbg !40
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x) #0 !dbg !31 {
+// CHECK:STDOUT: define linkonce_odr double @_CF.Main.83aece103b0a8681(double %x) #0 !dbg !41 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x), !dbg !32
-// CHECK:STDOUT:   ret double %G.call, !dbg !33
+// CHECK:STDOUT:   %G.call = call double @_CG.Main.83aece103b0a8681(double %x), !dbg !44
+// CHECK:STDOUT:   ret double %G.call, !dbg !45
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr %type @_CF.Main.402deed6b8733082(%type %x) #0 !dbg !34 {
+// CHECK:STDOUT: define linkonce_odr %type @_CF.Main.402deed6b8733082(%type %x) #0 !dbg !46 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %G.call = call %type @_CG.Main.402deed6b8733082(%type %x), !dbg !35
-// CHECK:STDOUT:   ret %type %G.call, !dbg !36
+// CHECK:STDOUT:   %G.call = call %type @_CG.Main.402deed6b8733082(%type %x), !dbg !49
+// CHECK:STDOUT:   ret %type %G.call, !dbg !50
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CG.Main.0a952f8bcc623ce6(ptr %x) #0 !dbg !37 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CG.Main.0a952f8bcc623ce6(ptr %x) #0 !dbg !51 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !38
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !38
-// CHECK:STDOUT:   %C.Cfn.call = call ptr @_CCfn.C.Main.0a952f8bcc623ce6(ptr %c.var, ptr %x), !dbg !39
-// CHECK:STDOUT:   ret ptr %C.Cfn.call, !dbg !40
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !54
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !54
+// CHECK:STDOUT:   %C.Cfn.call = call ptr @_CCfn.C.Main.0a952f8bcc623ce6(ptr %c.var, ptr %x), !dbg !55
+// CHECK:STDOUT:   ret ptr %C.Cfn.call, !dbg !56
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !41 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CG.Main.5450dc8e8b8e0899(i32 %x) #0 !dbg !57 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !42
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !42
-// CHECK:STDOUT:   %C.Cfn.call = call i32 @_CCfn.C.Main.5450dc8e8b8e0899(ptr %c.var, i32 %x), !dbg !43
-// CHECK:STDOUT:   ret i32 %C.Cfn.call, !dbg !44
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !60
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !60
+// CHECK:STDOUT:   %C.Cfn.call = call i32 @_CCfn.C.Main.5450dc8e8b8e0899(ptr %c.var, i32 %x), !dbg !61
+// CHECK:STDOUT:   ret i32 %C.Cfn.call, !dbg !62
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CG.Main.83aece103b0a8681(double %x) #0 !dbg !45 {
+// CHECK:STDOUT: define linkonce_odr double @_CG.Main.83aece103b0a8681(double %x) #0 !dbg !63 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !46
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !46
-// CHECK:STDOUT:   %C.Cfn.call = call double @_CCfn.C.Main.83aece103b0a8681(ptr %c.var, double %x), !dbg !47
-// CHECK:STDOUT:   ret double %C.Cfn.call, !dbg !48
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !66
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !66
+// CHECK:STDOUT:   %C.Cfn.call = call double @_CCfn.C.Main.83aece103b0a8681(ptr %c.var, double %x), !dbg !67
+// CHECK:STDOUT:   ret double %C.Cfn.call, !dbg !68
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr %type @_CG.Main.402deed6b8733082(%type %x) #0 !dbg !49 {
+// CHECK:STDOUT: define linkonce_odr %type @_CG.Main.402deed6b8733082(%type %x) #0 !dbg !69 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !50
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !50
-// CHECK:STDOUT:   %C.Cfn.call = call %type @_CCfn.C.Main.402deed6b8733082(ptr %c.var, %type %x), !dbg !51
-// CHECK:STDOUT:   ret %type %C.Cfn.call, !dbg !52
+// CHECK:STDOUT:   %c.var = alloca {}, align 8, !dbg !72
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %c.var), !dbg !72
+// CHECK:STDOUT:   %C.Cfn.call = call %type @_CCfn.C.Main.402deed6b8733082(ptr %c.var, %type %x), !dbg !73
+// CHECK:STDOUT:   ret %type %C.Cfn.call, !dbg !74
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CCfn.C.Main.0a952f8bcc623ce6(ptr %self, ptr %x) #0 !dbg !53 {
+// CHECK:STDOUT: define linkonce_odr ptr @_CCfn.C.Main.0a952f8bcc623ce6(ptr %self, ptr %x) #0 !dbg !75 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret ptr %x, !dbg !54
+// CHECK:STDOUT:   ret ptr %x, !dbg !81
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CCfn.C.Main.5450dc8e8b8e0899(ptr %self, i32 %x) #0 !dbg !55 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CCfn.C.Main.5450dc8e8b8e0899(ptr %self, i32 %x) #0 !dbg !82 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %x, !dbg !56
+// CHECK:STDOUT:   ret i32 %x, !dbg !88
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr double @_CCfn.C.Main.83aece103b0a8681(ptr %self, double %x) #0 !dbg !57 {
+// CHECK:STDOUT: define linkonce_odr double @_CCfn.C.Main.83aece103b0a8681(ptr %self, double %x) #0 !dbg !89 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret double %x, !dbg !58
+// CHECK:STDOUT:   ret double %x, !dbg !93
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr %type @_CCfn.C.Main.402deed6b8733082(ptr %self, %type %x) #0 !dbg !59 {
+// CHECK:STDOUT: define linkonce_odr %type @_CCfn.C.Main.402deed6b8733082(ptr %self, %type %x) #0 !dbg !94 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret %type %x, !dbg !60
+// CHECK:STDOUT:   ret %type %x, !dbg !98
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -187,7 +187,7 @@ fn M() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "call_specific_in_class.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "M", linkageName: "_CM.Main", scope: null, file: !3, line: 32, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 33, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 35, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 37, column: 3, scope: !4)
@@ -206,39 +206,77 @@ fn M() {
 // CHECK:STDOUT: !22 = !DILocation(line: 42, column: 3, scope: !4)
 // CHECK:STDOUT: !23 = !DILocation(line: 44, column: 3, scope: !4)
 // CHECK:STDOUT: !24 = !DILocation(line: 32, column: 1, scope: !4)
-// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !26 = !DILocation(line: 29, column: 10, scope: !25)
-// CHECK:STDOUT: !27 = !DILocation(line: 29, column: 3, scope: !25)
-// CHECK:STDOUT: !28 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !29 = !DILocation(line: 29, column: 10, scope: !28)
-// CHECK:STDOUT: !30 = !DILocation(line: 29, column: 3, scope: !28)
-// CHECK:STDOUT: !31 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !32 = !DILocation(line: 29, column: 10, scope: !31)
-// CHECK:STDOUT: !33 = !DILocation(line: 29, column: 3, scope: !31)
-// CHECK:STDOUT: !34 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.402deed6b8733082", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !35 = !DILocation(line: 29, column: 10, scope: !34)
-// CHECK:STDOUT: !36 = !DILocation(line: 29, column: 3, scope: !34)
-// CHECK:STDOUT: !37 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !38 = !DILocation(line: 24, column: 3, scope: !37)
-// CHECK:STDOUT: !39 = !DILocation(line: 25, column: 10, scope: !37)
-// CHECK:STDOUT: !40 = !DILocation(line: 25, column: 3, scope: !37)
-// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !42 = !DILocation(line: 24, column: 3, scope: !41)
-// CHECK:STDOUT: !43 = !DILocation(line: 25, column: 10, scope: !41)
-// CHECK:STDOUT: !44 = !DILocation(line: 25, column: 3, scope: !41)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.83aece103b0a8681", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 24, column: 3, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 25, column: 10, scope: !45)
-// CHECK:STDOUT: !48 = !DILocation(line: 25, column: 3, scope: !45)
-// CHECK:STDOUT: !49 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.402deed6b8733082", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !50 = !DILocation(line: 24, column: 3, scope: !49)
-// CHECK:STDOUT: !51 = !DILocation(line: 25, column: 10, scope: !49)
-// CHECK:STDOUT: !52 = !DILocation(line: 25, column: 3, scope: !49)
-// CHECK:STDOUT: !53 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !54 = !DILocation(line: 19, column: 5, scope: !53)
-// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !56 = !DILocation(line: 19, column: 5, scope: !55)
-// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.83aece103b0a8681", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !58 = !DILocation(line: 19, column: 5, scope: !57)
-// CHECK:STDOUT: !59 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.402deed6b8733082", scope: null, file: !3, line: 18, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !60 = !DILocation(line: 19, column: 5, scope: !59)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 28, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !29)
+// CHECK:STDOUT: !26 = !DISubroutineType(types: !27)
+// CHECK:STDOUT: !27 = !{!28, !28}
+// CHECK:STDOUT: !28 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !29 = !{!30}
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 1, scope: !25, type: !28)
+// CHECK:STDOUT: !31 = !DILocation(line: 29, column: 10, scope: !25)
+// CHECK:STDOUT: !32 = !DILocation(line: 29, column: 3, scope: !25)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 28, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !37)
+// CHECK:STDOUT: !34 = !DISubroutineType(types: !35)
+// CHECK:STDOUT: !35 = !{!36, !36}
+// CHECK:STDOUT: !36 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !37 = !{!38}
+// CHECK:STDOUT: !38 = !DILocalVariable(arg: 1, scope: !33, type: !36)
+// CHECK:STDOUT: !39 = !DILocation(line: 29, column: 10, scope: !33)
+// CHECK:STDOUT: !40 = !DILocation(line: 29, column: 3, scope: !33)
+// CHECK:STDOUT: !41 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.83aece103b0a8681", scope: null, file: !3, line: 28, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !42)
+// CHECK:STDOUT: !42 = !{!43}
+// CHECK:STDOUT: !43 = !DILocalVariable(arg: 1, scope: !41, type: !28)
+// CHECK:STDOUT: !44 = !DILocation(line: 29, column: 10, scope: !41)
+// CHECK:STDOUT: !45 = !DILocation(line: 29, column: 3, scope: !41)
+// CHECK:STDOUT: !46 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.402deed6b8733082", scope: null, file: !3, line: 28, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !47)
+// CHECK:STDOUT: !47 = !{!48}
+// CHECK:STDOUT: !48 = !DILocalVariable(arg: 1, scope: !46, type: !28)
+// CHECK:STDOUT: !49 = !DILocation(line: 29, column: 10, scope: !46)
+// CHECK:STDOUT: !50 = !DILocation(line: 29, column: 3, scope: !46)
+// CHECK:STDOUT: !51 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 23, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !52)
+// CHECK:STDOUT: !52 = !{!53}
+// CHECK:STDOUT: !53 = !DILocalVariable(arg: 1, scope: !51, type: !28)
+// CHECK:STDOUT: !54 = !DILocation(line: 24, column: 3, scope: !51)
+// CHECK:STDOUT: !55 = !DILocation(line: 25, column: 10, scope: !51)
+// CHECK:STDOUT: !56 = !DILocation(line: 25, column: 3, scope: !51)
+// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 23, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !58)
+// CHECK:STDOUT: !58 = !{!59}
+// CHECK:STDOUT: !59 = !DILocalVariable(arg: 1, scope: !57, type: !36)
+// CHECK:STDOUT: !60 = !DILocation(line: 24, column: 3, scope: !57)
+// CHECK:STDOUT: !61 = !DILocation(line: 25, column: 10, scope: !57)
+// CHECK:STDOUT: !62 = !DILocation(line: 25, column: 3, scope: !57)
+// CHECK:STDOUT: !63 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.83aece103b0a8681", scope: null, file: !3, line: 23, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !64)
+// CHECK:STDOUT: !64 = !{!65}
+// CHECK:STDOUT: !65 = !DILocalVariable(arg: 1, scope: !63, type: !28)
+// CHECK:STDOUT: !66 = !DILocation(line: 24, column: 3, scope: !63)
+// CHECK:STDOUT: !67 = !DILocation(line: 25, column: 10, scope: !63)
+// CHECK:STDOUT: !68 = !DILocation(line: 25, column: 3, scope: !63)
+// CHECK:STDOUT: !69 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main.402deed6b8733082", scope: null, file: !3, line: 23, type: !26, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !70)
+// CHECK:STDOUT: !70 = !{!71}
+// CHECK:STDOUT: !71 = !DILocalVariable(arg: 1, scope: !69, type: !28)
+// CHECK:STDOUT: !72 = !DILocation(line: 24, column: 3, scope: !69)
+// CHECK:STDOUT: !73 = !DILocation(line: 25, column: 10, scope: !69)
+// CHECK:STDOUT: !74 = !DILocation(line: 25, column: 3, scope: !69)
+// CHECK:STDOUT: !75 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.0a952f8bcc623ce6", scope: null, file: !3, line: 18, type: !76, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !78)
+// CHECK:STDOUT: !76 = !DISubroutineType(types: !77)
+// CHECK:STDOUT: !77 = !{!28, !28, !28}
+// CHECK:STDOUT: !78 = !{!79, !80}
+// CHECK:STDOUT: !79 = !DILocalVariable(arg: 1, scope: !75, type: !28)
+// CHECK:STDOUT: !80 = !DILocalVariable(arg: 2, scope: !75, type: !28)
+// CHECK:STDOUT: !81 = !DILocation(line: 19, column: 5, scope: !75)
+// CHECK:STDOUT: !82 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.5450dc8e8b8e0899", scope: null, file: !3, line: 18, type: !83, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !85)
+// CHECK:STDOUT: !83 = !DISubroutineType(types: !84)
+// CHECK:STDOUT: !84 = !{!36, !28, !36}
+// CHECK:STDOUT: !85 = !{!86, !87}
+// CHECK:STDOUT: !86 = !DILocalVariable(arg: 1, scope: !82, type: !28)
+// CHECK:STDOUT: !87 = !DILocalVariable(arg: 2, scope: !82, type: !36)
+// CHECK:STDOUT: !88 = !DILocation(line: 19, column: 5, scope: !82)
+// CHECK:STDOUT: !89 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.83aece103b0a8681", scope: null, file: !3, line: 18, type: !76, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !90)
+// CHECK:STDOUT: !90 = !{!91, !92}
+// CHECK:STDOUT: !91 = !DILocalVariable(arg: 1, scope: !89, type: !28)
+// CHECK:STDOUT: !92 = !DILocalVariable(arg: 2, scope: !89, type: !28)
+// CHECK:STDOUT: !93 = !DILocation(line: 19, column: 5, scope: !89)
+// CHECK:STDOUT: !94 = distinct !DISubprogram(name: "Cfn", linkageName: "_CCfn.C.Main.402deed6b8733082", scope: null, file: !3, line: 18, type: !76, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !95)
+// CHECK:STDOUT: !95 = !{!96, !97}
+// CHECK:STDOUT: !96 = !DILocalVariable(arg: 1, scope: !94, type: !28)
+// CHECK:STDOUT: !97 = !DILocalVariable(arg: 2, scope: !94, type: !28)
+// CHECK:STDOUT: !98 = !DILocation(line: 19, column: 5, scope: !94)

+ 29 - 17
toolchain/lower/testdata/function/generic/cross_library_name_collision_private.carbon

@@ -84,19 +84,19 @@ fn Run() {
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr i32 @_CLib1CallF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b) #0 !dbg !10 {
-// CHECK:STDOUT:   %1 = call i32 @_CF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b), !dbg !12
-// CHECK:STDOUT:   ret i32 %1, !dbg !13
+// CHECK:STDOUT:   %1 = call i32 @_CF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b), !dbg !18
+// CHECK:STDOUT:   ret i32 %1, !dbg !19
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CLib2CallF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b) #0 !dbg !14 {
-// CHECK:STDOUT:   %1 = call i32 @_CF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b), !dbg !16
-// CHECK:STDOUT:   ret i32 %1, !dbg !17
+// CHECK:STDOUT: define linkonce_odr i32 @_CLib2CallF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b) #0 !dbg !20 {
+// CHECK:STDOUT:   %1 = call i32 @_CF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b), !dbg !25
+// CHECK:STDOUT:   ret i32 %1, !dbg !26
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b) #0 !dbg !18 {
-// CHECK:STDOUT:   ret i32 %a, !dbg !19
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.99cfc57c95d4cf0a(i32 %a, i32 %b) #0 !dbg !27 {
+// CHECK:STDOUT:   ret i32 %a, !dbg !31
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -113,17 +113,29 @@ fn Run() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "todo_use.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Run", linkageName: "main", scope: null, file: !3, line: 9, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 10, column: 16, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 11, column: 16, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 9, column: 1, scope: !4)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Lib1CallF", linkageName: "_CLib1CallF.Main.99cfc57c95d4cf0a", scope: null, file: !11, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Lib1CallF", linkageName: "_CLib1CallF.Main.99cfc57c95d4cf0a", scope: null, file: !11, line: 8, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
 // CHECK:STDOUT: !11 = !DIFile(filename: "lib1.carbon", directory: "")
-// CHECK:STDOUT: !12 = !DILocation(line: 9, column: 10, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 9, column: 3, scope: !10)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "Lib2CallF", linkageName: "_CLib2CallF.Main.99cfc57c95d4cf0a", scope: null, file: !15, line: 11, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !15 = !DIFile(filename: "lib2.carbon", directory: "")
-// CHECK:STDOUT: !16 = !DILocation(line: 12, column: 10, scope: !14)
-// CHECK:STDOUT: !17 = !DILocation(line: 12, column: 3, scope: !14)
-// CHECK:STDOUT: !18 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.99cfc57c95d4cf0a", scope: null, file: !11, line: 4, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !19 = !DILocation(line: 5, column: 3, scope: !18)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{!14, !14, !14}
+// CHECK:STDOUT: !14 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !15 = !{!16, !17}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !10, type: !14)
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 2, scope: !10, type: !14)
+// CHECK:STDOUT: !18 = !DILocation(line: 9, column: 10, scope: !10)
+// CHECK:STDOUT: !19 = !DILocation(line: 9, column: 3, scope: !10)
+// CHECK:STDOUT: !20 = distinct !DISubprogram(name: "Lib2CallF", linkageName: "_CLib2CallF.Main.99cfc57c95d4cf0a", scope: null, file: !21, line: 11, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !22)
+// CHECK:STDOUT: !21 = !DIFile(filename: "lib2.carbon", directory: "")
+// CHECK:STDOUT: !22 = !{!23, !24}
+// CHECK:STDOUT: !23 = !DILocalVariable(arg: 1, scope: !20, type: !14)
+// CHECK:STDOUT: !24 = !DILocalVariable(arg: 2, scope: !20, type: !14)
+// CHECK:STDOUT: !25 = !DILocation(line: 12, column: 10, scope: !20)
+// CHECK:STDOUT: !26 = !DILocation(line: 12, column: 3, scope: !20)
+// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.99cfc57c95d4cf0a", scope: null, file: !11, line: 4, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !28)
+// CHECK:STDOUT: !28 = !{!29, !30}
+// CHECK:STDOUT: !29 = !DILocalVariable(arg: 1, scope: !27, type: !14)
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 2, scope: !27, type: !14)
+// CHECK:STDOUT: !31 = !DILocation(line: 5, column: 3, scope: !27)

+ 47 - 39
toolchain/lower/testdata/function/generic/import.carbon

@@ -78,7 +78,7 @@ fn Call() -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "indirectly_imported.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "IndirectDefined", linkageName: "_CIndirectDefined.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 6, column: 1, scope: !4)
 // CHECK:STDOUT: ; ModuleID = 'directly_imported.carbon'
 // CHECK:STDOUT: source_filename = "directly_imported.carbon"
@@ -102,7 +102,7 @@ fn Call() -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "directly_imported.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "DirectDefined", linkageName: "_CDirectDefined.Main", scope: null, file: !3, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 8, column: 1, scope: !4)
 // CHECK:STDOUT: ; ModuleID = 'use.carbon'
 // CHECK:STDOUT: source_filename = "use.carbon"
@@ -110,27 +110,27 @@ fn Call() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CCall.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !7
-// CHECK:STDOUT:   %p.var = alloca ptr, align 8, !dbg !8
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !7
-// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !7
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %p.var), !dbg !8
-// CHECK:STDOUT:   %DirectGeneric.call = call ptr @_CDirectGeneric.Main.b88d1103f417c6d4(ptr %n.var), !dbg !9
-// CHECK:STDOUT:   store ptr %DirectGeneric.call, ptr %p.var, align 8, !dbg !8
-// CHECK:STDOUT:   %.loc9_11 = load ptr, ptr %p.var, align 8, !dbg !10
-// CHECK:STDOUT:   %.loc9_10.2 = load i32, ptr %.loc9_11, align 4, !dbg !11
-// CHECK:STDOUT:   ret i32 %.loc9_10.2, !dbg !12
+// CHECK:STDOUT:   %n.var = alloca i32, align 4, !dbg !8
+// CHECK:STDOUT:   %p.var = alloca ptr, align 8, !dbg !9
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %n.var), !dbg !8
+// CHECK:STDOUT:   store i32 0, ptr %n.var, align 4, !dbg !8
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %p.var), !dbg !9
+// CHECK:STDOUT:   %DirectGeneric.call = call ptr @_CDirectGeneric.Main.b88d1103f417c6d4(ptr %n.var), !dbg !10
+// CHECK:STDOUT:   store ptr %DirectGeneric.call, ptr %p.var, align 8, !dbg !9
+// CHECK:STDOUT:   %.loc9_11 = load ptr, ptr %p.var, align 8, !dbg !11
+// CHECK:STDOUT:   %.loc9_10.2 = load i32, ptr %.loc9_11, align 4, !dbg !12
+// CHECK:STDOUT:   ret i32 %.loc9_10.2, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
 // CHECK:STDOUT: declare void @llvm.lifetime.start.p0(ptr captures(none)) #1
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CDirectGeneric.Main.b88d1103f417c6d4(ptr %y) #0 !dbg !13 {
-// CHECK:STDOUT:   call void @_CDirectDeclared.Main(), !dbg !15
-// CHECK:STDOUT:   call void @_CDirectDefined.Main(), !dbg !16
-// CHECK:STDOUT:   %1 = call ptr @_CIndirectGeneric.Main.b88d1103f417c6d4(ptr %y), !dbg !17
-// CHECK:STDOUT:   ret ptr %1, !dbg !18
+// CHECK:STDOUT: define linkonce_odr ptr @_CDirectGeneric.Main.b88d1103f417c6d4(ptr %y) #0 !dbg !14 {
+// CHECK:STDOUT:   call void @_CDirectDeclared.Main(), !dbg !21
+// CHECK:STDOUT:   call void @_CDirectDefined.Main(), !dbg !22
+// CHECK:STDOUT:   %1 = call ptr @_CIndirectGeneric.Main.b88d1103f417c6d4(ptr %y), !dbg !23
+// CHECK:STDOUT:   ret ptr %1, !dbg !24
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CDirectDeclared.Main()
@@ -138,10 +138,10 @@ fn Call() -> i32 {
 // CHECK:STDOUT: declare void @_CDirectDefined.Main()
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr ptr @_CIndirectGeneric.Main.b88d1103f417c6d4(ptr %x) #0 !dbg !19 {
-// CHECK:STDOUT:   call void @_CIndirectDeclared.Main(), !dbg !21
-// CHECK:STDOUT:   call void @_CIndirectDefined.Main(), !dbg !22
-// CHECK:STDOUT:   ret ptr %x, !dbg !23
+// CHECK:STDOUT: define linkonce_odr ptr @_CIndirectGeneric.Main.b88d1103f417c6d4(ptr %x) #0 !dbg !25 {
+// CHECK:STDOUT:   call void @_CIndirectDeclared.Main(), !dbg !29
+// CHECK:STDOUT:   call void @_CIndirectDefined.Main(), !dbg !30
+// CHECK:STDOUT:   ret ptr %x, !dbg !31
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: declare void @_CIndirectDeclared.Main()
@@ -163,21 +163,29 @@ fn Call() -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "use.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Call", linkageName: "_CCall.Main", scope: null, file: !3, line: 6, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 7, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 8, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 8, column: 17, scope: !4)
-// CHECK:STDOUT: !10 = !DILocation(line: 9, column: 11, scope: !4)
-// CHECK:STDOUT: !11 = !DILocation(line: 9, column: 10, scope: !4)
-// CHECK:STDOUT: !12 = !DILocation(line: 9, column: 3, scope: !4)
-// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "DirectGeneric", linkageName: "_CDirectGeneric.Main.b88d1103f417c6d4", scope: null, file: !14, line: 10, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !14 = !DIFile(filename: "directly_imported.carbon", directory: "")
-// CHECK:STDOUT: !15 = !DILocation(line: 11, column: 3, scope: !13)
-// CHECK:STDOUT: !16 = !DILocation(line: 12, column: 3, scope: !13)
-// CHECK:STDOUT: !17 = !DILocation(line: 13, column: 10, scope: !13)
-// CHECK:STDOUT: !18 = !DILocation(line: 13, column: 3, scope: !13)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "IndirectGeneric", linkageName: "_CIndirectGeneric.Main.b88d1103f417c6d4", scope: null, file: !20, line: 8, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DIFile(filename: "indirectly_imported.carbon", directory: "")
-// CHECK:STDOUT: !21 = !DILocation(line: 9, column: 3, scope: !19)
-// CHECK:STDOUT: !22 = !DILocation(line: 10, column: 3, scope: !19)
-// CHECK:STDOUT: !23 = !DILocation(line: 11, column: 3, scope: !19)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 7, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 8, column: 3, scope: !4)
+// CHECK:STDOUT: !10 = !DILocation(line: 8, column: 17, scope: !4)
+// CHECK:STDOUT: !11 = !DILocation(line: 9, column: 11, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 9, column: 10, scope: !4)
+// CHECK:STDOUT: !13 = !DILocation(line: 9, column: 3, scope: !4)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "DirectGeneric", linkageName: "_CDirectGeneric.Main.b88d1103f417c6d4", scope: null, file: !15, line: 10, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !19)
+// CHECK:STDOUT: !15 = !DIFile(filename: "directly_imported.carbon", directory: "")
+// CHECK:STDOUT: !16 = !DISubroutineType(types: !17)
+// CHECK:STDOUT: !17 = !{!18, !18}
+// CHECK:STDOUT: !18 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !19 = !{!20}
+// CHECK:STDOUT: !20 = !DILocalVariable(arg: 1, scope: !14, type: !18)
+// CHECK:STDOUT: !21 = !DILocation(line: 11, column: 3, scope: !14)
+// CHECK:STDOUT: !22 = !DILocation(line: 12, column: 3, scope: !14)
+// CHECK:STDOUT: !23 = !DILocation(line: 13, column: 10, scope: !14)
+// CHECK:STDOUT: !24 = !DILocation(line: 13, column: 3, scope: !14)
+// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "IndirectGeneric", linkageName: "_CIndirectGeneric.Main.b88d1103f417c6d4", scope: null, file: !26, line: 8, type: !16, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !27)
+// CHECK:STDOUT: !26 = !DIFile(filename: "indirectly_imported.carbon", directory: "")
+// CHECK:STDOUT: !27 = !{!28}
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 1, scope: !25, type: !18)
+// CHECK:STDOUT: !29 = !DILocation(line: 9, column: 3, scope: !25)
+// CHECK:STDOUT: !30 = !DILocation(line: 10, column: 3, scope: !25)
+// CHECK:STDOUT: !31 = !DILocation(line: 11, column: 3, scope: !25)

+ 136 - 97
toolchain/lower/testdata/function/generic/reverse_canonical.carbon

@@ -72,89 +72,89 @@ fn Main() {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_Cfirst.Main.36f5e0b0ce09cb9a(i1 %arg1, i1 %arg2, ptr %arg3) #0 !dbg !14 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !15
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !15
-// CHECK:STDOUT:   %.loc23 = load ptr, ptr %local_name.var, align 8, !dbg !16
-// CHECK:STDOUT:   call void @_Csecond.Main.e20e3db21e34eb80(i1 %arg2, i1 %arg2, ptr %.loc23), !dbg !17
-// CHECK:STDOUT:   ret void, !dbg !18
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !22
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !22
+// CHECK:STDOUT:   %.loc23 = load ptr, ptr %local_name.var, align 8, !dbg !23
+// CHECK:STDOUT:   call void @_Csecond.Main.e20e3db21e34eb80(i1 %arg2, i1 %arg2, ptr %.loc23), !dbg !24
+// CHECK:STDOUT:   ret void, !dbg !25
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Csecond.Main.e20e3db21e34eb80(i1 %arg1, i1 %arg2, ptr %arg3) #0 !dbg !19 {
+// CHECK:STDOUT: define linkonce_odr void @_Csecond.Main.e20e3db21e34eb80(i1 %arg1, i1 %arg2, ptr %arg3) #0 !dbg !26 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !20
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !20
-// CHECK:STDOUT:   call void @_Cfirst.Main.140560e2430fc2f7(ptr %arg3, ptr %arg3, i1 %arg1), !dbg !21
-// CHECK:STDOUT:   %.loc30 = load ptr, ptr %local_name.var, align 8, !dbg !22
-// CHECK:STDOUT:   call void @_Cthird.Main.e20e3db21e34eb80(i1 %arg2, i1 %arg2, ptr %.loc30), !dbg !23
-// CHECK:STDOUT:   ret void, !dbg !24
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !31
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !31
+// CHECK:STDOUT:   call void @_Cfirst.Main.140560e2430fc2f7(ptr %arg3, ptr %arg3, i1 %arg1), !dbg !32
+// CHECK:STDOUT:   %.loc30 = load ptr, ptr %local_name.var, align 8, !dbg !33
+// CHECK:STDOUT:   call void @_Cthird.Main.e20e3db21e34eb80(i1 %arg2, i1 %arg2, ptr %.loc30), !dbg !34
+// CHECK:STDOUT:   ret void, !dbg !35
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cfirst.Main.140560e2430fc2f7(ptr %arg1, ptr %arg2, i1 %arg3) #0 !dbg !25 {
+// CHECK:STDOUT: define linkonce_odr void @_Cfirst.Main.140560e2430fc2f7(ptr %arg1, ptr %arg2, i1 %arg3) #0 !dbg !36 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !26
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !26
-// CHECK:STDOUT:   %.loc23 = load ptr, ptr %local_name.var, align 8, !dbg !27
-// CHECK:STDOUT:   call void @_Csecond.Main.f9ad2587bfb58bac(ptr %arg2, ptr %arg2, ptr %.loc23), !dbg !28
-// CHECK:STDOUT:   ret void, !dbg !29
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !41
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !41
+// CHECK:STDOUT:   %.loc23 = load ptr, ptr %local_name.var, align 8, !dbg !42
+// CHECK:STDOUT:   call void @_Csecond.Main.f9ad2587bfb58bac(ptr %arg2, ptr %arg2, ptr %.loc23), !dbg !43
+// CHECK:STDOUT:   ret void, !dbg !44
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cthird.Main.e20e3db21e34eb80(i1 %arg1, i1 %arg2, ptr %arg3) #0 !dbg !30 {
+// CHECK:STDOUT: define linkonce_odr void @_Cthird.Main.e20e3db21e34eb80(i1 %arg1, i1 %arg2, ptr %arg3) #0 !dbg !45 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !31
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !31
-// CHECK:STDOUT:   %.loc36_10 = load ptr, ptr %local_name.var, align 8, !dbg !32
-// CHECK:STDOUT:   %.loc36_22 = load ptr, ptr %local_name.var, align 8, !dbg !33
-// CHECK:STDOUT:   call void @_Cfourth.Main.9260a3b095cb39ed(ptr %.loc36_10, ptr %.loc36_22, i1 %arg1), !dbg !34
-// CHECK:STDOUT:   call void @_Cfourth.Main.9260a3b095cb39ed(ptr %arg3, ptr %arg3, i1 %arg2), !dbg !35
-// CHECK:STDOUT:   ret void, !dbg !36
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !50
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !50
+// CHECK:STDOUT:   %.loc36_10 = load ptr, ptr %local_name.var, align 8, !dbg !51
+// CHECK:STDOUT:   %.loc36_22 = load ptr, ptr %local_name.var, align 8, !dbg !52
+// CHECK:STDOUT:   call void @_Cfourth.Main.9260a3b095cb39ed(ptr %.loc36_10, ptr %.loc36_22, i1 %arg1), !dbg !53
+// CHECK:STDOUT:   call void @_Cfourth.Main.9260a3b095cb39ed(ptr %arg3, ptr %arg3, i1 %arg2), !dbg !54
+// CHECK:STDOUT:   ret void, !dbg !55
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Csecond.Main.f9ad2587bfb58bac(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !37 {
+// CHECK:STDOUT: define linkonce_odr void @_Csecond.Main.f9ad2587bfb58bac(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !56 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !38
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !38
-// CHECK:STDOUT:   call void @_Cfirst.Main.f9ad2587bfb58bac(ptr %arg3, ptr %arg3, ptr %arg1), !dbg !39
-// CHECK:STDOUT:   %.loc30 = load ptr, ptr %local_name.var, align 8, !dbg !40
-// CHECK:STDOUT:   call void @_Cthird.Main.f9ad2587bfb58bac(ptr %arg2, ptr %arg2, ptr %.loc30), !dbg !41
-// CHECK:STDOUT:   ret void, !dbg !42
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !61
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !61
+// CHECK:STDOUT:   call void @_Cfirst.Main.f9ad2587bfb58bac(ptr %arg3, ptr %arg3, ptr %arg1), !dbg !62
+// CHECK:STDOUT:   %.loc30 = load ptr, ptr %local_name.var, align 8, !dbg !63
+// CHECK:STDOUT:   call void @_Cthird.Main.f9ad2587bfb58bac(ptr %arg2, ptr %arg2, ptr %.loc30), !dbg !64
+// CHECK:STDOUT:   ret void, !dbg !65
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cfourth.Main.9260a3b095cb39ed(ptr %arg1, ptr %arg2, i1 %arg3) #0 !dbg !43 {
+// CHECK:STDOUT: define linkonce_odr void @_Cfourth.Main.9260a3b095cb39ed(ptr %arg1, ptr %arg2, i1 %arg3) #0 !dbg !66 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !44
+// CHECK:STDOUT:   ret void, !dbg !71
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cfirst.Main.f9ad2587bfb58bac(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !45 {
+// CHECK:STDOUT: define linkonce_odr void @_Cfirst.Main.f9ad2587bfb58bac(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !72 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !46
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !46
-// CHECK:STDOUT:   %.loc23 = load ptr, ptr %local_name.var, align 8, !dbg !47
-// CHECK:STDOUT:   call void @_Csecond.Main.f9ad2587bfb58bac(ptr %arg2, ptr %arg2, ptr %.loc23), !dbg !48
-// CHECK:STDOUT:   ret void, !dbg !49
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !77
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !77
+// CHECK:STDOUT:   %.loc23 = load ptr, ptr %local_name.var, align 8, !dbg !78
+// CHECK:STDOUT:   call void @_Csecond.Main.f9ad2587bfb58bac(ptr %arg2, ptr %arg2, ptr %.loc23), !dbg !79
+// CHECK:STDOUT:   ret void, !dbg !80
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cthird.Main.f9ad2587bfb58bac(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !50 {
+// CHECK:STDOUT: define linkonce_odr void @_Cthird.Main.f9ad2587bfb58bac(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !81 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !51
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !51
-// CHECK:STDOUT:   %.loc36_10 = load ptr, ptr %local_name.var, align 8, !dbg !52
-// CHECK:STDOUT:   %.loc36_22 = load ptr, ptr %local_name.var, align 8, !dbg !53
-// CHECK:STDOUT:   call void @_Cfourth.Main.880241312efeb323(ptr %.loc36_10, ptr %.loc36_22, ptr %arg1), !dbg !54
-// CHECK:STDOUT:   call void @_Cfourth.Main.880241312efeb323(ptr %arg3, ptr %arg3, ptr %arg2), !dbg !55
-// CHECK:STDOUT:   ret void, !dbg !56
+// CHECK:STDOUT:   %local_name.var = alloca ptr, align 8, !dbg !86
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local_name.var), !dbg !86
+// CHECK:STDOUT:   %.loc36_10 = load ptr, ptr %local_name.var, align 8, !dbg !87
+// CHECK:STDOUT:   %.loc36_22 = load ptr, ptr %local_name.var, align 8, !dbg !88
+// CHECK:STDOUT:   call void @_Cfourth.Main.880241312efeb323(ptr %.loc36_10, ptr %.loc36_22, ptr %arg1), !dbg !89
+// CHECK:STDOUT:   call void @_Cfourth.Main.880241312efeb323(ptr %arg3, ptr %arg3, ptr %arg2), !dbg !90
+// CHECK:STDOUT:   ret void, !dbg !91
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cfourth.Main.880241312efeb323(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !57 {
+// CHECK:STDOUT: define linkonce_odr void @_Cfourth.Main.880241312efeb323(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !92 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !58
+// CHECK:STDOUT:   ret void, !dbg !97
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -174,7 +174,7 @@ fn Main() {
 // CHECK:STDOUT: !3 = !DIFile(filename: "reverse_canonical.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Main", linkageName: "_CMain.Main", scope: null, file: !3, line: 43, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 44, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 45, column: 3, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 47, column: 9, scope: !4)
@@ -182,48 +182,87 @@ fn Main() {
 // CHECK:STDOUT: !11 = !DILocation(line: 47, column: 15, scope: !4)
 // CHECK:STDOUT: !12 = !DILocation(line: 47, column: 3, scope: !4)
 // CHECK:STDOUT: !13 = !DILocation(line: 43, column: 1, scope: !4)
-// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "first", linkageName: "_Cfirst.Main.36f5e0b0ce09cb9a", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !15 = !DILocation(line: 21, column: 3, scope: !14)
-// CHECK:STDOUT: !16 = !DILocation(line: 23, column: 22, scope: !14)
-// CHECK:STDOUT: !17 = !DILocation(line: 23, column: 3, scope: !14)
-// CHECK:STDOUT: !18 = !DILocation(line: 20, column: 1, scope: !14)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "second", linkageName: "_Csecond.Main.e20e3db21e34eb80", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DILocation(line: 27, column: 3, scope: !19)
-// CHECK:STDOUT: !21 = !DILocation(line: 29, column: 3, scope: !19)
-// CHECK:STDOUT: !22 = !DILocation(line: 30, column: 21, scope: !19)
-// CHECK:STDOUT: !23 = !DILocation(line: 30, column: 3, scope: !19)
-// CHECK:STDOUT: !24 = !DILocation(line: 26, column: 1, scope: !19)
-// CHECK:STDOUT: !25 = distinct !DISubprogram(name: "first", linkageName: "_Cfirst.Main.140560e2430fc2f7", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !26 = !DILocation(line: 21, column: 3, scope: !25)
-// CHECK:STDOUT: !27 = !DILocation(line: 23, column: 22, scope: !25)
-// CHECK:STDOUT: !28 = !DILocation(line: 23, column: 3, scope: !25)
-// CHECK:STDOUT: !29 = !DILocation(line: 20, column: 1, scope: !25)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "third", linkageName: "_Cthird.Main.e20e3db21e34eb80", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DILocation(line: 34, column: 3, scope: !30)
-// CHECK:STDOUT: !32 = !DILocation(line: 36, column: 10, scope: !30)
-// CHECK:STDOUT: !33 = !DILocation(line: 36, column: 22, scope: !30)
-// CHECK:STDOUT: !34 = !DILocation(line: 36, column: 3, scope: !30)
-// CHECK:STDOUT: !35 = !DILocation(line: 37, column: 3, scope: !30)
-// CHECK:STDOUT: !36 = !DILocation(line: 33, column: 1, scope: !30)
-// CHECK:STDOUT: !37 = distinct !DISubprogram(name: "second", linkageName: "_Csecond.Main.f9ad2587bfb58bac", scope: null, file: !3, line: 26, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !38 = !DILocation(line: 27, column: 3, scope: !37)
-// CHECK:STDOUT: !39 = !DILocation(line: 29, column: 3, scope: !37)
-// CHECK:STDOUT: !40 = !DILocation(line: 30, column: 21, scope: !37)
-// CHECK:STDOUT: !41 = !DILocation(line: 30, column: 3, scope: !37)
-// CHECK:STDOUT: !42 = !DILocation(line: 26, column: 1, scope: !37)
-// CHECK:STDOUT: !43 = distinct !DISubprogram(name: "fourth", linkageName: "_Cfourth.Main.9260a3b095cb39ed", scope: null, file: !3, line: 40, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !44 = !DILocation(line: 40, column: 1, scope: !43)
-// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "first", linkageName: "_Cfirst.Main.f9ad2587bfb58bac", scope: null, file: !3, line: 20, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !46 = !DILocation(line: 21, column: 3, scope: !45)
-// CHECK:STDOUT: !47 = !DILocation(line: 23, column: 22, scope: !45)
-// CHECK:STDOUT: !48 = !DILocation(line: 23, column: 3, scope: !45)
-// CHECK:STDOUT: !49 = !DILocation(line: 20, column: 1, scope: !45)
-// CHECK:STDOUT: !50 = distinct !DISubprogram(name: "third", linkageName: "_Cthird.Main.f9ad2587bfb58bac", scope: null, file: !3, line: 33, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !51 = !DILocation(line: 34, column: 3, scope: !50)
-// CHECK:STDOUT: !52 = !DILocation(line: 36, column: 10, scope: !50)
-// CHECK:STDOUT: !53 = !DILocation(line: 36, column: 22, scope: !50)
-// CHECK:STDOUT: !54 = !DILocation(line: 36, column: 3, scope: !50)
-// CHECK:STDOUT: !55 = !DILocation(line: 37, column: 3, scope: !50)
-// CHECK:STDOUT: !56 = !DILocation(line: 33, column: 1, scope: !50)
-// CHECK:STDOUT: !57 = distinct !DISubprogram(name: "fourth", linkageName: "_Cfourth.Main.880241312efeb323", scope: null, file: !3, line: 40, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !58 = !DILocation(line: 40, column: 1, scope: !57)
+// CHECK:STDOUT: !14 = distinct !DISubprogram(name: "first", linkageName: "_Cfirst.Main.36f5e0b0ce09cb9a", scope: null, file: !3, line: 20, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !18)
+// CHECK:STDOUT: !15 = !DISubroutineType(types: !16)
+// CHECK:STDOUT: !16 = !{null, !17, !17, !17}
+// CHECK:STDOUT: !17 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !18 = !{!19, !20, !21}
+// CHECK:STDOUT: !19 = !DILocalVariable(arg: 1, scope: !14, type: !17)
+// CHECK:STDOUT: !20 = !DILocalVariable(arg: 2, scope: !14, type: !17)
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 3, scope: !14, type: !17)
+// CHECK:STDOUT: !22 = !DILocation(line: 21, column: 3, scope: !14)
+// CHECK:STDOUT: !23 = !DILocation(line: 23, column: 22, scope: !14)
+// CHECK:STDOUT: !24 = !DILocation(line: 23, column: 3, scope: !14)
+// CHECK:STDOUT: !25 = !DILocation(line: 20, column: 1, scope: !14)
+// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "second", linkageName: "_Csecond.Main.e20e3db21e34eb80", scope: null, file: !3, line: 26, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !27)
+// CHECK:STDOUT: !27 = !{!28, !29, !30}
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 1, scope: !26, type: !17)
+// CHECK:STDOUT: !29 = !DILocalVariable(arg: 2, scope: !26, type: !17)
+// CHECK:STDOUT: !30 = !DILocalVariable(arg: 3, scope: !26, type: !17)
+// CHECK:STDOUT: !31 = !DILocation(line: 27, column: 3, scope: !26)
+// CHECK:STDOUT: !32 = !DILocation(line: 29, column: 3, scope: !26)
+// CHECK:STDOUT: !33 = !DILocation(line: 30, column: 21, scope: !26)
+// CHECK:STDOUT: !34 = !DILocation(line: 30, column: 3, scope: !26)
+// CHECK:STDOUT: !35 = !DILocation(line: 26, column: 1, scope: !26)
+// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "first", linkageName: "_Cfirst.Main.140560e2430fc2f7", scope: null, file: !3, line: 20, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !37)
+// CHECK:STDOUT: !37 = !{!38, !39, !40}
+// CHECK:STDOUT: !38 = !DILocalVariable(arg: 1, scope: !36, type: !17)
+// CHECK:STDOUT: !39 = !DILocalVariable(arg: 2, scope: !36, type: !17)
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 3, scope: !36, type: !17)
+// CHECK:STDOUT: !41 = !DILocation(line: 21, column: 3, scope: !36)
+// CHECK:STDOUT: !42 = !DILocation(line: 23, column: 22, scope: !36)
+// CHECK:STDOUT: !43 = !DILocation(line: 23, column: 3, scope: !36)
+// CHECK:STDOUT: !44 = !DILocation(line: 20, column: 1, scope: !36)
+// CHECK:STDOUT: !45 = distinct !DISubprogram(name: "third", linkageName: "_Cthird.Main.e20e3db21e34eb80", scope: null, file: !3, line: 33, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !46)
+// CHECK:STDOUT: !46 = !{!47, !48, !49}
+// CHECK:STDOUT: !47 = !DILocalVariable(arg: 1, scope: !45, type: !17)
+// CHECK:STDOUT: !48 = !DILocalVariable(arg: 2, scope: !45, type: !17)
+// CHECK:STDOUT: !49 = !DILocalVariable(arg: 3, scope: !45, type: !17)
+// CHECK:STDOUT: !50 = !DILocation(line: 34, column: 3, scope: !45)
+// CHECK:STDOUT: !51 = !DILocation(line: 36, column: 10, scope: !45)
+// CHECK:STDOUT: !52 = !DILocation(line: 36, column: 22, scope: !45)
+// CHECK:STDOUT: !53 = !DILocation(line: 36, column: 3, scope: !45)
+// CHECK:STDOUT: !54 = !DILocation(line: 37, column: 3, scope: !45)
+// CHECK:STDOUT: !55 = !DILocation(line: 33, column: 1, scope: !45)
+// CHECK:STDOUT: !56 = distinct !DISubprogram(name: "second", linkageName: "_Csecond.Main.f9ad2587bfb58bac", scope: null, file: !3, line: 26, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !57)
+// CHECK:STDOUT: !57 = !{!58, !59, !60}
+// CHECK:STDOUT: !58 = !DILocalVariable(arg: 1, scope: !56, type: !17)
+// CHECK:STDOUT: !59 = !DILocalVariable(arg: 2, scope: !56, type: !17)
+// CHECK:STDOUT: !60 = !DILocalVariable(arg: 3, scope: !56, type: !17)
+// CHECK:STDOUT: !61 = !DILocation(line: 27, column: 3, scope: !56)
+// CHECK:STDOUT: !62 = !DILocation(line: 29, column: 3, scope: !56)
+// CHECK:STDOUT: !63 = !DILocation(line: 30, column: 21, scope: !56)
+// CHECK:STDOUT: !64 = !DILocation(line: 30, column: 3, scope: !56)
+// CHECK:STDOUT: !65 = !DILocation(line: 26, column: 1, scope: !56)
+// CHECK:STDOUT: !66 = distinct !DISubprogram(name: "fourth", linkageName: "_Cfourth.Main.9260a3b095cb39ed", scope: null, file: !3, line: 40, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !67)
+// CHECK:STDOUT: !67 = !{!68, !69, !70}
+// CHECK:STDOUT: !68 = !DILocalVariable(arg: 1, scope: !66, type: !17)
+// CHECK:STDOUT: !69 = !DILocalVariable(arg: 2, scope: !66, type: !17)
+// CHECK:STDOUT: !70 = !DILocalVariable(arg: 3, scope: !66, type: !17)
+// CHECK:STDOUT: !71 = !DILocation(line: 40, column: 1, scope: !66)
+// CHECK:STDOUT: !72 = distinct !DISubprogram(name: "first", linkageName: "_Cfirst.Main.f9ad2587bfb58bac", scope: null, file: !3, line: 20, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !73)
+// CHECK:STDOUT: !73 = !{!74, !75, !76}
+// CHECK:STDOUT: !74 = !DILocalVariable(arg: 1, scope: !72, type: !17)
+// CHECK:STDOUT: !75 = !DILocalVariable(arg: 2, scope: !72, type: !17)
+// CHECK:STDOUT: !76 = !DILocalVariable(arg: 3, scope: !72, type: !17)
+// CHECK:STDOUT: !77 = !DILocation(line: 21, column: 3, scope: !72)
+// CHECK:STDOUT: !78 = !DILocation(line: 23, column: 22, scope: !72)
+// CHECK:STDOUT: !79 = !DILocation(line: 23, column: 3, scope: !72)
+// CHECK:STDOUT: !80 = !DILocation(line: 20, column: 1, scope: !72)
+// CHECK:STDOUT: !81 = distinct !DISubprogram(name: "third", linkageName: "_Cthird.Main.f9ad2587bfb58bac", scope: null, file: !3, line: 33, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !82)
+// CHECK:STDOUT: !82 = !{!83, !84, !85}
+// CHECK:STDOUT: !83 = !DILocalVariable(arg: 1, scope: !81, type: !17)
+// CHECK:STDOUT: !84 = !DILocalVariable(arg: 2, scope: !81, type: !17)
+// CHECK:STDOUT: !85 = !DILocalVariable(arg: 3, scope: !81, type: !17)
+// CHECK:STDOUT: !86 = !DILocation(line: 34, column: 3, scope: !81)
+// CHECK:STDOUT: !87 = !DILocation(line: 36, column: 10, scope: !81)
+// CHECK:STDOUT: !88 = !DILocation(line: 36, column: 22, scope: !81)
+// CHECK:STDOUT: !89 = !DILocation(line: 36, column: 3, scope: !81)
+// CHECK:STDOUT: !90 = !DILocation(line: 37, column: 3, scope: !81)
+// CHECK:STDOUT: !91 = !DILocation(line: 33, column: 1, scope: !81)
+// CHECK:STDOUT: !92 = distinct !DISubprogram(name: "fourth", linkageName: "_Cfourth.Main.880241312efeb323", scope: null, file: !3, line: 40, type: !15, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !93)
+// CHECK:STDOUT: !93 = !{!94, !95, !96}
+// CHECK:STDOUT: !94 = !DILocalVariable(arg: 1, scope: !92, type: !17)
+// CHECK:STDOUT: !95 = !DILocalVariable(arg: 2, scope: !92, type: !17)
+// CHECK:STDOUT: !96 = !DILocalVariable(arg: 3, scope: !92, type: !17)
+// CHECK:STDOUT: !97 = !DILocation(line: 40, column: 1, scope: !92)

+ 92 - 75
toolchain/lower/testdata/function/generic/self_canonical.carbon

@@ -101,59 +101,59 @@ fn Main_method_no_template () {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define linkonce_odr void @_Cfourth_function.Main.a95d5636f2d020e8(ptr %arg) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !12
-// CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !13
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !12
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !13
-// CHECK:STDOUT:   %.loc53 = load ptr, ptr %local1.var, align 8, !dbg !14
-// CHECK:STDOUT:   call void @_Cfirst_function.Main.308f7be7cd8574f7(ptr %.loc53), !dbg !15
-// CHECK:STDOUT:   %.loc54 = load ptr, ptr %local2.var, align 8, !dbg !16
-// CHECK:STDOUT:   call void @_Cfirst_function.Main.308f7be7cd8574f7(ptr %.loc54), !dbg !17
-// CHECK:STDOUT:   ret void, !dbg !18
+// CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !17
+// CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !18
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !17
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !18
+// CHECK:STDOUT:   %.loc53 = load ptr, ptr %local1.var, align 8, !dbg !19
+// CHECK:STDOUT:   call void @_Cfirst_function.Main.308f7be7cd8574f7(ptr %.loc53), !dbg !20
+// CHECK:STDOUT:   %.loc54 = load ptr, ptr %local2.var, align 8, !dbg !21
+// CHECK:STDOUT:   call void @_Cfirst_function.Main.308f7be7cd8574f7(ptr %.loc54), !dbg !22
+// CHECK:STDOUT:   ret void, !dbg !23
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cfirst_function.Main.308f7be7cd8574f7(ptr %arg) #0 !dbg !19 {
-// CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !20
-// CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !21
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !20
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !21
-// CHECK:STDOUT:   %.loc61_19 = load ptr, ptr %local2.var, align 8, !dbg !22
-// CHECK:STDOUT:   %.loc61_27 = load ptr, ptr %local1.var, align 8, !dbg !23
-// CHECK:STDOUT:   call void @_Csecond_function.Main.6e67709fb5f3d893(ptr %.loc61_19, ptr %.loc61_27, ptr %arg), !dbg !24
-// CHECK:STDOUT:   ret void, !dbg !25
-// CHECK:STDOUT: }
-// CHECK:STDOUT:
-// CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Csecond_function.Main.6e67709fb5f3d893(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !26 {
+// CHECK:STDOUT: define linkonce_odr void @_Cfirst_function.Main.308f7be7cd8574f7(ptr %arg) #0 !dbg !24 {
 // CHECK:STDOUT: entry:
 // CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !27
 // CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !28
-// CHECK:STDOUT:   %local3.var = alloca ptr, align 8, !dbg !29
 // CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !27
 // CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !28
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local3.var), !dbg !29
-// CHECK:STDOUT:   %.loc75_25 = load ptr, ptr %local3.var, align 8, !dbg !30
-// CHECK:STDOUT:   %.loc75_33 = load ptr, ptr %local2.var, align 8, !dbg !31
-// CHECK:STDOUT:   call void @_Csecond_function.Main.6e67709fb5f3d893(ptr %arg3, ptr %.loc75_25, ptr %.loc75_33), !dbg !32
-// CHECK:STDOUT:   %.loc76 = load ptr, ptr %local1.var, align 8, !dbg !33
-// CHECK:STDOUT:   call void @_Cthird_function.Main.bd8cd068af0bdf76(ptr %.loc76, ptr %arg3, ptr %arg1), !dbg !34
-// CHECK:STDOUT:   ret void, !dbg !35
+// CHECK:STDOUT:   %.loc61_19 = load ptr, ptr %local2.var, align 8, !dbg !29
+// CHECK:STDOUT:   %.loc61_27 = load ptr, ptr %local1.var, align 8, !dbg !30
+// CHECK:STDOUT:   call void @_Csecond_function.Main.6e67709fb5f3d893(ptr %.loc61_19, ptr %.loc61_27, ptr %arg), !dbg !31
+// CHECK:STDOUT:   ret void, !dbg !32
+// CHECK:STDOUT: }
+// CHECK:STDOUT:
+// CHECK:STDOUT: ; Function Attrs: nounwind
+// CHECK:STDOUT: define linkonce_odr void @_Csecond_function.Main.6e67709fb5f3d893(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !33 {
+// CHECK:STDOUT: entry:
+// CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !40
+// CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !41
+// CHECK:STDOUT:   %local3.var = alloca ptr, align 8, !dbg !42
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !40
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !41
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local3.var), !dbg !42
+// CHECK:STDOUT:   %.loc75_25 = load ptr, ptr %local3.var, align 8, !dbg !43
+// CHECK:STDOUT:   %.loc75_33 = load ptr, ptr %local2.var, align 8, !dbg !44
+// CHECK:STDOUT:   call void @_Csecond_function.Main.6e67709fb5f3d893(ptr %arg3, ptr %.loc75_25, ptr %.loc75_33), !dbg !45
+// CHECK:STDOUT:   %.loc76 = load ptr, ptr %local1.var, align 8, !dbg !46
+// CHECK:STDOUT:   call void @_Cthird_function.Main.bd8cd068af0bdf76(ptr %.loc76, ptr %arg3, ptr %arg1), !dbg !47
+// CHECK:STDOUT:   ret void, !dbg !48
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_Cthird_function.Main.bd8cd068af0bdf76(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !36 {
+// CHECK:STDOUT: define linkonce_odr void @_Cthird_function.Main.bd8cd068af0bdf76(ptr %arg1, ptr %arg2, ptr %arg3) #0 !dbg !49 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !37
-// CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !38
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !37
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !38
-// CHECK:STDOUT:   %.loc39 = load ptr, ptr %local2.var, align 8, !dbg !39
-// CHECK:STDOUT:   call void @_Cthird_function.Main.bd8cd068af0bdf76(ptr %arg1, ptr %arg2, ptr %.loc39), !dbg !40
-// CHECK:STDOUT:   %.loc40 = load ptr, ptr %local1.var, align 8, !dbg !41
-// CHECK:STDOUT:   call void @_Cfourth_function.Main.a95d5636f2d020e8(ptr %.loc40), !dbg !42
-// CHECK:STDOUT:   ret void, !dbg !43
+// CHECK:STDOUT:   %local1.var = alloca ptr, align 8, !dbg !54
+// CHECK:STDOUT:   %local2.var = alloca ptr, align 8, !dbg !55
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local1.var), !dbg !54
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %local2.var), !dbg !55
+// CHECK:STDOUT:   %.loc39 = load ptr, ptr %local2.var, align 8, !dbg !56
+// CHECK:STDOUT:   call void @_Cthird_function.Main.bd8cd068af0bdf76(ptr %arg1, ptr %arg2, ptr %.loc39), !dbg !57
+// CHECK:STDOUT:   %.loc40 = load ptr, ptr %local1.var, align 8, !dbg !58
+// CHECK:STDOUT:   call void @_Cfourth_function.Main.a95d5636f2d020e8(ptr %.loc40), !dbg !59
+// CHECK:STDOUT:   ret void, !dbg !60
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; uselistorder directives
@@ -171,41 +171,58 @@ fn Main_method_no_template () {
 // CHECK:STDOUT: !3 = !DIFile(filename: "self_canonical.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Main_method_no_template", linkageName: "_CMain_method_no_template.Main", scope: null, file: !3, line: 79, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 80, column: 3, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 82, column: 18, scope: !4)
 // CHECK:STDOUT: !9 = !DILocation(line: 82, column: 3, scope: !4)
 // CHECK:STDOUT: !10 = !DILocation(line: 79, column: 1, scope: !4)
-// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "fourth_function", linkageName: "_Cfourth_function.Main.a95d5636f2d020e8", scope: null, file: !3, line: 49, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !12 = !DILocation(line: 50, column: 3, scope: !11)
-// CHECK:STDOUT: !13 = !DILocation(line: 51, column: 3, scope: !11)
-// CHECK:STDOUT: !14 = !DILocation(line: 53, column: 18, scope: !11)
-// CHECK:STDOUT: !15 = !DILocation(line: 53, column: 3, scope: !11)
-// CHECK:STDOUT: !16 = !DILocation(line: 54, column: 18, scope: !11)
-// CHECK:STDOUT: !17 = !DILocation(line: 54, column: 3, scope: !11)
-// CHECK:STDOUT: !18 = !DILocation(line: 49, column: 1, scope: !11)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "first_function", linkageName: "_Cfirst_function.Main.308f7be7cd8574f7", scope: null, file: !3, line: 57, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DILocation(line: 58, column: 3, scope: !19)
-// CHECK:STDOUT: !21 = !DILocation(line: 59, column: 3, scope: !19)
-// CHECK:STDOUT: !22 = !DILocation(line: 61, column: 19, scope: !19)
-// CHECK:STDOUT: !23 = !DILocation(line: 61, column: 27, scope: !19)
-// CHECK:STDOUT: !24 = !DILocation(line: 61, column: 3, scope: !19)
-// CHECK:STDOUT: !25 = !DILocation(line: 57, column: 1, scope: !19)
-// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "second_function", linkageName: "_Csecond_function.Main.6e67709fb5f3d893", scope: null, file: !3, line: 70, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !27 = !DILocation(line: 71, column: 3, scope: !26)
-// CHECK:STDOUT: !28 = !DILocation(line: 72, column: 3, scope: !26)
-// CHECK:STDOUT: !29 = !DILocation(line: 73, column: 3, scope: !26)
-// CHECK:STDOUT: !30 = !DILocation(line: 75, column: 25, scope: !26)
-// CHECK:STDOUT: !31 = !DILocation(line: 75, column: 33, scope: !26)
-// CHECK:STDOUT: !32 = !DILocation(line: 75, column: 3, scope: !26)
-// CHECK:STDOUT: !33 = !DILocation(line: 76, column: 18, scope: !26)
-// CHECK:STDOUT: !34 = !DILocation(line: 76, column: 3, scope: !26)
-// CHECK:STDOUT: !35 = !DILocation(line: 70, column: 1, scope: !26)
-// CHECK:STDOUT: !36 = distinct !DISubprogram(name: "third_function", linkageName: "_Cthird_function.Main.bd8cd068af0bdf76", scope: null, file: !3, line: 35, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !37 = !DILocation(line: 36, column: 3, scope: !36)
-// CHECK:STDOUT: !38 = !DILocation(line: 37, column: 3, scope: !36)
-// CHECK:STDOUT: !39 = !DILocation(line: 39, column: 30, scope: !36)
-// CHECK:STDOUT: !40 = !DILocation(line: 39, column: 3, scope: !36)
-// CHECK:STDOUT: !41 = !DILocation(line: 40, column: 19, scope: !36)
-// CHECK:STDOUT: !42 = !DILocation(line: 40, column: 3, scope: !36)
-// CHECK:STDOUT: !43 = !DILocation(line: 35, column: 1, scope: !36)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "fourth_function", linkageName: "_Cfourth_function.Main.a95d5636f2d020e8", scope: null, file: !3, line: 49, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{null, !14}
+// CHECK:STDOUT: !14 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !15 = !{!16}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !11, type: !14)
+// CHECK:STDOUT: !17 = !DILocation(line: 50, column: 3, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 51, column: 3, scope: !11)
+// CHECK:STDOUT: !19 = !DILocation(line: 53, column: 18, scope: !11)
+// CHECK:STDOUT: !20 = !DILocation(line: 53, column: 3, scope: !11)
+// CHECK:STDOUT: !21 = !DILocation(line: 54, column: 18, scope: !11)
+// CHECK:STDOUT: !22 = !DILocation(line: 54, column: 3, scope: !11)
+// CHECK:STDOUT: !23 = !DILocation(line: 49, column: 1, scope: !11)
+// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "first_function", linkageName: "_Cfirst_function.Main.308f7be7cd8574f7", scope: null, file: !3, line: 57, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !25)
+// CHECK:STDOUT: !25 = !{!26}
+// CHECK:STDOUT: !26 = !DILocalVariable(arg: 1, scope: !24, type: !14)
+// CHECK:STDOUT: !27 = !DILocation(line: 58, column: 3, scope: !24)
+// CHECK:STDOUT: !28 = !DILocation(line: 59, column: 3, scope: !24)
+// CHECK:STDOUT: !29 = !DILocation(line: 61, column: 19, scope: !24)
+// CHECK:STDOUT: !30 = !DILocation(line: 61, column: 27, scope: !24)
+// CHECK:STDOUT: !31 = !DILocation(line: 61, column: 3, scope: !24)
+// CHECK:STDOUT: !32 = !DILocation(line: 57, column: 1, scope: !24)
+// CHECK:STDOUT: !33 = distinct !DISubprogram(name: "second_function", linkageName: "_Csecond_function.Main.6e67709fb5f3d893", scope: null, file: !3, line: 70, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !36)
+// CHECK:STDOUT: !34 = !DISubroutineType(types: !35)
+// CHECK:STDOUT: !35 = !{null, !14, !14, !14}
+// CHECK:STDOUT: !36 = !{!37, !38, !39}
+// CHECK:STDOUT: !37 = !DILocalVariable(arg: 1, scope: !33, type: !14)
+// CHECK:STDOUT: !38 = !DILocalVariable(arg: 2, scope: !33, type: !14)
+// CHECK:STDOUT: !39 = !DILocalVariable(arg: 3, scope: !33, type: !14)
+// CHECK:STDOUT: !40 = !DILocation(line: 71, column: 3, scope: !33)
+// CHECK:STDOUT: !41 = !DILocation(line: 72, column: 3, scope: !33)
+// CHECK:STDOUT: !42 = !DILocation(line: 73, column: 3, scope: !33)
+// CHECK:STDOUT: !43 = !DILocation(line: 75, column: 25, scope: !33)
+// CHECK:STDOUT: !44 = !DILocation(line: 75, column: 33, scope: !33)
+// CHECK:STDOUT: !45 = !DILocation(line: 75, column: 3, scope: !33)
+// CHECK:STDOUT: !46 = !DILocation(line: 76, column: 18, scope: !33)
+// CHECK:STDOUT: !47 = !DILocation(line: 76, column: 3, scope: !33)
+// CHECK:STDOUT: !48 = !DILocation(line: 70, column: 1, scope: !33)
+// CHECK:STDOUT: !49 = distinct !DISubprogram(name: "third_function", linkageName: "_Cthird_function.Main.bd8cd068af0bdf76", scope: null, file: !3, line: 35, type: !34, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !50)
+// CHECK:STDOUT: !50 = !{!51, !52, !53}
+// CHECK:STDOUT: !51 = !DILocalVariable(arg: 1, scope: !49, type: !14)
+// CHECK:STDOUT: !52 = !DILocalVariable(arg: 2, scope: !49, type: !14)
+// CHECK:STDOUT: !53 = !DILocalVariable(arg: 3, scope: !49, type: !14)
+// CHECK:STDOUT: !54 = !DILocation(line: 36, column: 3, scope: !49)
+// CHECK:STDOUT: !55 = !DILocation(line: 37, column: 3, scope: !49)
+// CHECK:STDOUT: !56 = !DILocation(line: 39, column: 30, scope: !49)
+// CHECK:STDOUT: !57 = !DILocation(line: 39, column: 3, scope: !49)
+// CHECK:STDOUT: !58 = !DILocation(line: 40, column: 19, scope: !49)
+// CHECK:STDOUT: !59 = !DILocation(line: 40, column: 3, scope: !49)
+// CHECK:STDOUT: !60 = !DILocation(line: 35, column: 1, scope: !49)

+ 167 - 137
toolchain/lower/testdata/function/generic/type_representation.carbon

@@ -80,141 +80,141 @@ fn F_nested_tuple(a: ((i32, i32), X)) -> ((i32, i32), X) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @"_COp.Int.Core:Copy.Main"(i32 %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 %self, !dbg !7
+// CHECK:STDOUT:   ret i32 %self, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CF_i32.Main(i32 %a) #0 !dbg !8 {
+// CHECK:STDOUT: define i32 @_CF_i32.Main(i32 %a) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.cf9485df26e40963(i32 %a), !dbg !9
-// CHECK:STDOUT:   ret i32 %F.call, !dbg !10
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main.cf9485df26e40963(i32 %a), !dbg !14
+// CHECK:STDOUT:   ret i32 %F.call, !dbg !15
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @"_COp.X.Main:Copy.Main"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !11 {
+// CHECK:STDOUT: define void @"_COp.X.Main:Copy.Main"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !16 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc38_24.1.a = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !12
-// CHECK:STDOUT:   %.loc38_24.2 = load i32, ptr %.loc38_24.1.a, align 4, !dbg !12
-// CHECK:STDOUT:   %.loc38_37.1.b = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !13
-// CHECK:STDOUT:   %.loc38_37.2 = load i32, ptr %.loc38_37.1.b, align 4, !dbg !13
-// CHECK:STDOUT:   %.loc38_39.2.a = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !14
-// CHECK:STDOUT:   store i32 %.loc38_24.2, ptr %.loc38_39.2.a, align 4, !dbg !14
-// CHECK:STDOUT:   %.loc38_39.4.b = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !14
-// CHECK:STDOUT:   store i32 %.loc38_37.2, ptr %.loc38_39.4.b, align 4, !dbg !14
-// CHECK:STDOUT:   ret void, !dbg !15
+// CHECK:STDOUT:   %.loc38_24.1.a = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !22
+// CHECK:STDOUT:   %.loc38_24.2 = load i32, ptr %.loc38_24.1.a, align 4, !dbg !22
+// CHECK:STDOUT:   %.loc38_37.1.b = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !23
+// CHECK:STDOUT:   %.loc38_37.2 = load i32, ptr %.loc38_37.1.b, align 4, !dbg !23
+// CHECK:STDOUT:   %.loc38_39.2.a = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !24
+// CHECK:STDOUT:   store i32 %.loc38_24.2, ptr %.loc38_39.2.a, align 4, !dbg !24
+// CHECK:STDOUT:   %.loc38_39.4.b = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !24
+// CHECK:STDOUT:   store i32 %.loc38_37.2, ptr %.loc38_39.4.b, align 4, !dbg !24
+// CHECK:STDOUT:   ret void, !dbg !25
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CF_X.Main(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !16 {
+// CHECK:STDOUT: define void @_CF_X.Main(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !26 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main.731881fd665c07ab(ptr %return, ptr %a), !dbg !17
-// CHECK:STDOUT:   ret void, !dbg !18
+// CHECK:STDOUT:   call void @_CF.Main.731881fd665c07ab(ptr %return, ptr %a), !dbg !29
+// CHECK:STDOUT:   ret void, !dbg !30
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @"_COp.61ea2aba74ab3bf1:Copy.Main"() #0 !dbg !19 {
+// CHECK:STDOUT: define void @"_COp.61ea2aba74ab3bf1:Copy.Main"() #0 !dbg !31 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret void, !dbg !20
+// CHECK:STDOUT:   ret void, !dbg !34
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CF_empty_tuple.Main() #0 !dbg !21 {
+// CHECK:STDOUT: define void @_CF_empty_tuple.Main() #0 !dbg !35 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main.ac6bb6b581e07691(), !dbg !22
-// CHECK:STDOUT:   ret void, !dbg !23
+// CHECK:STDOUT:   call void @_CF.Main.ac6bb6b581e07691(), !dbg !36
+// CHECK:STDOUT:   ret void, !dbg !37
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @"_COp.d07e2731f1087d49:Copy.Main"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !24 {
+// CHECK:STDOUT: define void @"_COp.d07e2731f1087d49:Copy.Main"(ptr sret({ i32, i32 }) %return, ptr %self) #0 !dbg !38 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %tuple.elem0.loc59_12.1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !25
-// CHECK:STDOUT:   %tuple.elem0.loc59_12.1.tuple.elem.load = load i32, ptr %tuple.elem0.loc59_12.1.tuple.elem, align 4, !dbg !25
-// CHECK:STDOUT:   %tuple.elem0.loc59_12.2.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !25
-// CHECK:STDOUT:   store i32 %tuple.elem0.loc59_12.1.tuple.elem.load, ptr %tuple.elem0.loc59_12.2.tuple.elem, align 4, !dbg !25
-// CHECK:STDOUT:   %tuple.elem1.loc59_12.1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !25
-// CHECK:STDOUT:   %tuple.elem1.loc59_12.1.tuple.elem.load = load i32, ptr %tuple.elem1.loc59_12.1.tuple.elem, align 4, !dbg !25
-// CHECK:STDOUT:   %tuple.elem1.loc59_12.2.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !25
-// CHECK:STDOUT:   store i32 %tuple.elem1.loc59_12.1.tuple.elem.load, ptr %tuple.elem1.loc59_12.2.tuple.elem, align 4, !dbg !25
-// CHECK:STDOUT:   ret void, !dbg !26
+// CHECK:STDOUT:   %tuple.elem0.loc59_12.1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 0, !dbg !41
+// CHECK:STDOUT:   %tuple.elem0.loc59_12.1.tuple.elem.load = load i32, ptr %tuple.elem0.loc59_12.1.tuple.elem, align 4, !dbg !41
+// CHECK:STDOUT:   %tuple.elem0.loc59_12.2.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 0, !dbg !41
+// CHECK:STDOUT:   store i32 %tuple.elem0.loc59_12.1.tuple.elem.load, ptr %tuple.elem0.loc59_12.2.tuple.elem, align 4, !dbg !41
+// CHECK:STDOUT:   %tuple.elem1.loc59_12.1.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %self, i32 0, i32 1, !dbg !41
+// CHECK:STDOUT:   %tuple.elem1.loc59_12.1.tuple.elem.load = load i32, ptr %tuple.elem1.loc59_12.1.tuple.elem, align 4, !dbg !41
+// CHECK:STDOUT:   %tuple.elem1.loc59_12.2.tuple.elem = getelementptr inbounds nuw { i32, i32 }, ptr %return, i32 0, i32 1, !dbg !41
+// CHECK:STDOUT:   store i32 %tuple.elem1.loc59_12.1.tuple.elem.load, ptr %tuple.elem1.loc59_12.2.tuple.elem, align 4, !dbg !41
+// CHECK:STDOUT:   ret void, !dbg !42
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CF_two_tuple.Main(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !27 {
+// CHECK:STDOUT: define void @_CF_two_tuple.Main(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !43 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main.86a4a70fb2978f72(ptr %return, ptr %a), !dbg !28
-// CHECK:STDOUT:   ret void, !dbg !29
+// CHECK:STDOUT:   call void @_CF.Main.86a4a70fb2978f72(ptr %return, ptr %a), !dbg !46
+// CHECK:STDOUT:   ret void, !dbg !47
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @"_COp.4af564822fd0c29a:Copy.Main"(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %self) #0 !dbg !30 {
+// CHECK:STDOUT: define void @"_COp.4af564822fd0c29a:Copy.Main"(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %self) #0 !dbg !48 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %tuple.elem0.loc69_17.tuple.elem = getelementptr inbounds nuw { ptr, ptr }, ptr %self, i32 0, i32 0, !dbg !31
-// CHECK:STDOUT:   %tuple.elem0.loc69_17.tuple.elem.load = load ptr, ptr %tuple.elem0.loc69_17.tuple.elem, align 8, !dbg !31
-// CHECK:STDOUT:   %tuple.elem0.loc69_51.tuple.elem = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 0, !dbg !32
-// CHECK:STDOUT:   call void @"_COp.d07e2731f1087d49:Copy.Main"(ptr %tuple.elem0.loc69_51.tuple.elem, ptr %tuple.elem0.loc69_17.tuple.elem.load), !dbg !31
-// CHECK:STDOUT:   %tuple.elem1.loc69_37.tuple.elem = getelementptr inbounds nuw { ptr, ptr }, ptr %self, i32 0, i32 1, !dbg !33
-// CHECK:STDOUT:   %tuple.elem1.loc69_37.tuple.elem.load = load ptr, ptr %tuple.elem1.loc69_37.tuple.elem, align 8, !dbg !33
-// CHECK:STDOUT:   %tuple.elem1.loc69_51.tuple.elem = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 1, !dbg !32
-// CHECK:STDOUT:   call void @"_COp.X.Main:Copy.Main"(ptr %tuple.elem1.loc69_51.tuple.elem, ptr %tuple.elem1.loc69_37.tuple.elem.load), !dbg !33
-// CHECK:STDOUT:   ret void, !dbg !34
+// CHECK:STDOUT:   %tuple.elem0.loc69_17.tuple.elem = getelementptr inbounds nuw { ptr, ptr }, ptr %self, i32 0, i32 0, !dbg !51
+// CHECK:STDOUT:   %tuple.elem0.loc69_17.tuple.elem.load = load ptr, ptr %tuple.elem0.loc69_17.tuple.elem, align 8, !dbg !51
+// CHECK:STDOUT:   %tuple.elem0.loc69_51.tuple.elem = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 0, !dbg !52
+// CHECK:STDOUT:   call void @"_COp.d07e2731f1087d49:Copy.Main"(ptr %tuple.elem0.loc69_51.tuple.elem, ptr %tuple.elem0.loc69_17.tuple.elem.load), !dbg !51
+// CHECK:STDOUT:   %tuple.elem1.loc69_37.tuple.elem = getelementptr inbounds nuw { ptr, ptr }, ptr %self, i32 0, i32 1, !dbg !53
+// CHECK:STDOUT:   %tuple.elem1.loc69_37.tuple.elem.load = load ptr, ptr %tuple.elem1.loc69_37.tuple.elem, align 8, !dbg !53
+// CHECK:STDOUT:   %tuple.elem1.loc69_51.tuple.elem = getelementptr inbounds nuw { { i32, i32 }, { i32, i32 } }, ptr %return, i32 0, i32 1, !dbg !52
+// CHECK:STDOUT:   call void @"_COp.X.Main:Copy.Main"(ptr %tuple.elem1.loc69_51.tuple.elem, ptr %tuple.elem1.loc69_37.tuple.elem.load), !dbg !53
+// CHECK:STDOUT:   ret void, !dbg !54
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_CF_nested_tuple.Main(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %a) #0 !dbg !35 {
+// CHECK:STDOUT: define void @_CF_nested_tuple.Main(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %a) #0 !dbg !55 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @_CF.Main.bfaac0eb7445cea4(ptr %return, ptr %a), !dbg !36
-// CHECK:STDOUT:   ret void, !dbg !37
+// CHECK:STDOUT:   call void @_CF.Main.bfaac0eb7445cea4(ptr %return, ptr %a), !dbg !58
+// CHECK:STDOUT:   ret void, !dbg !59
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.cf9485df26e40963(i32 %a) #0 !dbg !38 {
+// CHECK:STDOUT: define linkonce_odr i32 @_CF.Main.cf9485df26e40963(i32 %a) #0 !dbg !60 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca i32, align 4, !dbg !39
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !39
-// CHECK:STDOUT:   %.loc18_26 = call i32 @"_COp.Int.Core:Copy.Main"(i32 %a), !dbg !40
-// CHECK:STDOUT:   store i32 %.loc18_26, ptr %v.var, align 4, !dbg !39
-// CHECK:STDOUT:   %.loc19 = call i32 @"_COp.Int.Core:Copy.Main"(i32 %a), !dbg !41
-// CHECK:STDOUT:   ret i32 %.loc19, !dbg !42
+// CHECK:STDOUT:   %v.var = alloca i32, align 4, !dbg !63
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !63
+// CHECK:STDOUT:   %.loc18_26 = call i32 @"_COp.Int.Core:Copy.Main"(i32 %a), !dbg !64
+// CHECK:STDOUT:   store i32 %.loc18_26, ptr %v.var, align 4, !dbg !63
+// CHECK:STDOUT:   %.loc19 = call i32 @"_COp.Int.Core:Copy.Main"(i32 %a), !dbg !65
+// CHECK:STDOUT:   ret i32 %.loc19, !dbg !66
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.731881fd665c07ab(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !43 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.731881fd665c07ab(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !67 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca { i32, i32 }, align 8, !dbg !44
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !44
-// CHECK:STDOUT:   call void @"_COp.X.Main:Copy.Main"(ptr %v.var, ptr %a), !dbg !45
-// CHECK:STDOUT:   call void @"_COp.X.Main:Copy.Main"(ptr %return, ptr %a), !dbg !46
-// CHECK:STDOUT:   ret void, !dbg !47
+// CHECK:STDOUT:   %v.var = alloca { i32, i32 }, align 8, !dbg !70
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !70
+// CHECK:STDOUT:   call void @"_COp.X.Main:Copy.Main"(ptr %v.var, ptr %a), !dbg !71
+// CHECK:STDOUT:   call void @"_COp.X.Main:Copy.Main"(ptr %return, ptr %a), !dbg !72
+// CHECK:STDOUT:   ret void, !dbg !73
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.ac6bb6b581e07691() #0 !dbg !48 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.ac6bb6b581e07691() #0 !dbg !74 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca {}, align 8, !dbg !49
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !49
-// CHECK:STDOUT:   call void @"_COp.61ea2aba74ab3bf1:Copy.Main"(), !dbg !50
-// CHECK:STDOUT:   call void @"_COp.61ea2aba74ab3bf1:Copy.Main"(), !dbg !51
-// CHECK:STDOUT:   ret void, !dbg !52
+// CHECK:STDOUT:   %v.var = alloca {}, align 8, !dbg !75
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !75
+// CHECK:STDOUT:   call void @"_COp.61ea2aba74ab3bf1:Copy.Main"(), !dbg !76
+// CHECK:STDOUT:   call void @"_COp.61ea2aba74ab3bf1:Copy.Main"(), !dbg !77
+// CHECK:STDOUT:   ret void, !dbg !78
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.86a4a70fb2978f72(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !53 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.86a4a70fb2978f72(ptr sret({ i32, i32 }) %return, ptr %a) #0 !dbg !79 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca { i32, i32 }, align 8, !dbg !54
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !54
-// CHECK:STDOUT:   call void @"_COp.d07e2731f1087d49:Copy.Main"(ptr %v.var, ptr %a), !dbg !55
-// CHECK:STDOUT:   call void @"_COp.d07e2731f1087d49:Copy.Main"(ptr %return, ptr %a), !dbg !56
-// CHECK:STDOUT:   ret void, !dbg !57
+// CHECK:STDOUT:   %v.var = alloca { i32, i32 }, align 8, !dbg !82
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !82
+// CHECK:STDOUT:   call void @"_COp.d07e2731f1087d49:Copy.Main"(ptr %v.var, ptr %a), !dbg !83
+// CHECK:STDOUT:   call void @"_COp.d07e2731f1087d49:Copy.Main"(ptr %return, ptr %a), !dbg !84
+// CHECK:STDOUT:   ret void, !dbg !85
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define linkonce_odr void @_CF.Main.bfaac0eb7445cea4(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %a) #0 !dbg !58 {
+// CHECK:STDOUT: define linkonce_odr void @_CF.Main.bfaac0eb7445cea4(ptr sret({ { i32, i32 }, { i32, i32 } }) %return, ptr %a) #0 !dbg !86 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %v.var = alloca { { i32, i32 }, { i32, i32 } }, align 8, !dbg !59
-// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !59
-// CHECK:STDOUT:   call void @"_COp.4af564822fd0c29a:Copy.Main"(ptr %v.var, ptr %a), !dbg !60
-// CHECK:STDOUT:   call void @"_COp.4af564822fd0c29a:Copy.Main"(ptr %return, ptr %a), !dbg !61
-// CHECK:STDOUT:   ret void, !dbg !62
+// CHECK:STDOUT:   %v.var = alloca { { i32, i32 }, { i32, i32 } }, align 8, !dbg !89
+// CHECK:STDOUT:   call void @llvm.lifetime.start.p0(ptr %v.var), !dbg !89
+// CHECK:STDOUT:   call void @"_COp.4af564822fd0c29a:Copy.Main"(ptr %v.var, ptr %a), !dbg !90
+// CHECK:STDOUT:   call void @"_COp.4af564822fd0c29a:Copy.Main"(ptr %return, ptr %a), !dbg !91
+// CHECK:STDOUT:   ret void, !dbg !92
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nosync nounwind willreturn memory(argmem: readwrite)
@@ -233,62 +233,92 @@ fn F_nested_tuple(a: ((i32, i32), X)) -> ((i32, i32), X) {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "type_representation.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Copy.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Op", linkageName: "_COp.Int.Core:Copy.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !8)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 24, column: 5, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "F_i32", linkageName: "_CF_i32.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 29, column: 10, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 29, column: 3, scope: !8)
-// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Op", linkageName: "_COp.X.Main:Copy.Main", scope: null, file: !3, line: 37, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !12 = !DILocation(line: 38, column: 20, scope: !11)
-// CHECK:STDOUT: !13 = !DILocation(line: 38, column: 33, scope: !11)
-// CHECK:STDOUT: !14 = !DILocation(line: 38, column: 14, scope: !11)
-// CHECK:STDOUT: !15 = !DILocation(line: 38, column: 7, scope: !11)
-// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "F_X", linkageName: "_CF_X.Main", scope: null, file: !3, line: 43, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !17 = !DILocation(line: 44, column: 10, scope: !16)
-// CHECK:STDOUT: !18 = !DILocation(line: 44, column: 3, scope: !16)
-// CHECK:STDOUT: !19 = distinct !DISubprogram(name: "Op", linkageName: "_COp.61ea2aba74ab3bf1:Copy.Main", scope: null, file: !3, line: 48, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !20 = !DILocation(line: 49, column: 5, scope: !19)
-// CHECK:STDOUT: !21 = distinct !DISubprogram(name: "F_empty_tuple", linkageName: "_CF_empty_tuple.Main", scope: null, file: !3, line: 53, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !22 = !DILocation(line: 54, column: 10, scope: !21)
-// CHECK:STDOUT: !23 = !DILocation(line: 54, column: 3, scope: !21)
-// CHECK:STDOUT: !24 = distinct !DISubprogram(name: "Op", linkageName: "_COp.d07e2731f1087d49:Copy.Main", scope: null, file: !3, line: 58, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !25 = !DILocation(line: 59, column: 12, scope: !24)
-// CHECK:STDOUT: !26 = !DILocation(line: 59, column: 5, scope: !24)
-// CHECK:STDOUT: !27 = distinct !DISubprogram(name: "F_two_tuple", linkageName: "_CF_two_tuple.Main", scope: null, file: !3, line: 63, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !28 = !DILocation(line: 64, column: 10, scope: !27)
-// CHECK:STDOUT: !29 = !DILocation(line: 64, column: 3, scope: !27)
-// CHECK:STDOUT: !30 = distinct !DISubprogram(name: "Op", linkageName: "_COp.4af564822fd0c29a:Copy.Main", scope: null, file: !3, line: 68, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !31 = !DILocation(line: 69, column: 13, scope: !30)
-// CHECK:STDOUT: !32 = !DILocation(line: 69, column: 12, scope: !30)
-// CHECK:STDOUT: !33 = !DILocation(line: 69, column: 33, scope: !30)
-// CHECK:STDOUT: !34 = !DILocation(line: 69, column: 5, scope: !30)
-// CHECK:STDOUT: !35 = distinct !DISubprogram(name: "F_nested_tuple", linkageName: "_CF_nested_tuple.Main", scope: null, file: !3, line: 73, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !36 = !DILocation(line: 74, column: 10, scope: !35)
-// CHECK:STDOUT: !37 = !DILocation(line: 74, column: 3, scope: !35)
-// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.cf9485df26e40963", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !39 = !DILocation(line: 18, column: 3, scope: !38)
-// CHECK:STDOUT: !40 = !DILocation(line: 18, column: 14, scope: !38)
-// CHECK:STDOUT: !41 = !DILocation(line: 19, column: 10, scope: !38)
-// CHECK:STDOUT: !42 = !DILocation(line: 19, column: 3, scope: !38)
-// CHECK:STDOUT: !43 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.731881fd665c07ab", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !44 = !DILocation(line: 18, column: 3, scope: !43)
-// CHECK:STDOUT: !45 = !DILocation(line: 18, column: 14, scope: !43)
-// CHECK:STDOUT: !46 = !DILocation(line: 19, column: 10, scope: !43)
-// CHECK:STDOUT: !47 = !DILocation(line: 19, column: 3, scope: !43)
-// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.ac6bb6b581e07691", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !49 = !DILocation(line: 18, column: 3, scope: !48)
-// CHECK:STDOUT: !50 = !DILocation(line: 18, column: 14, scope: !48)
-// CHECK:STDOUT: !51 = !DILocation(line: 19, column: 10, scope: !48)
-// CHECK:STDOUT: !52 = !DILocation(line: 19, column: 3, scope: !48)
-// CHECK:STDOUT: !53 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.86a4a70fb2978f72", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !54 = !DILocation(line: 18, column: 3, scope: !53)
-// CHECK:STDOUT: !55 = !DILocation(line: 18, column: 14, scope: !53)
-// CHECK:STDOUT: !56 = !DILocation(line: 19, column: 10, scope: !53)
-// CHECK:STDOUT: !57 = !DILocation(line: 19, column: 3, scope: !53)
-// CHECK:STDOUT: !58 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.bfaac0eb7445cea4", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !59 = !DILocation(line: 18, column: 3, scope: !58)
-// CHECK:STDOUT: !60 = !DILocation(line: 18, column: 14, scope: !58)
-// CHECK:STDOUT: !61 = !DILocation(line: 19, column: 10, scope: !58)
-// CHECK:STDOUT: !62 = !DILocation(line: 19, column: 3, scope: !58)
+// CHECK:STDOUT: !6 = !{!7, !7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !{!9}
+// CHECK:STDOUT: !9 = !DILocalVariable(arg: 1, scope: !4, type: !7)
+// CHECK:STDOUT: !10 = !DILocation(line: 24, column: 5, scope: !4)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "F_i32", linkageName: "_CF_i32.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !12)
+// CHECK:STDOUT: !12 = !{!13}
+// CHECK:STDOUT: !13 = !DILocalVariable(arg: 1, scope: !11, type: !7)
+// CHECK:STDOUT: !14 = !DILocation(line: 29, column: 10, scope: !11)
+// CHECK:STDOUT: !15 = !DILocation(line: 29, column: 3, scope: !11)
+// CHECK:STDOUT: !16 = distinct !DISubprogram(name: "Op", linkageName: "_COp.X.Main:Copy.Main", scope: null, file: !3, line: 37, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !20)
+// CHECK:STDOUT: !17 = !DISubroutineType(types: !18)
+// CHECK:STDOUT: !18 = !{!19, !19}
+// CHECK:STDOUT: !19 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !20 = !{!21}
+// CHECK:STDOUT: !21 = !DILocalVariable(arg: 1, scope: !16, type: !19)
+// CHECK:STDOUT: !22 = !DILocation(line: 38, column: 20, scope: !16)
+// CHECK:STDOUT: !23 = !DILocation(line: 38, column: 33, scope: !16)
+// CHECK:STDOUT: !24 = !DILocation(line: 38, column: 14, scope: !16)
+// CHECK:STDOUT: !25 = !DILocation(line: 38, column: 7, scope: !16)
+// CHECK:STDOUT: !26 = distinct !DISubprogram(name: "F_X", linkageName: "_CF_X.Main", scope: null, file: !3, line: 43, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !27)
+// CHECK:STDOUT: !27 = !{!28}
+// CHECK:STDOUT: !28 = !DILocalVariable(arg: 1, scope: !26, type: !19)
+// CHECK:STDOUT: !29 = !DILocation(line: 44, column: 10, scope: !26)
+// CHECK:STDOUT: !30 = !DILocation(line: 44, column: 3, scope: !26)
+// CHECK:STDOUT: !31 = distinct !DISubprogram(name: "Op", linkageName: "_COp.61ea2aba74ab3bf1:Copy.Main", scope: null, file: !3, line: 48, type: !32, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !32 = !DISubroutineType(types: !33)
+// CHECK:STDOUT: !33 = !{!19}
+// CHECK:STDOUT: !34 = !DILocation(line: 49, column: 5, scope: !31)
+// CHECK:STDOUT: !35 = distinct !DISubprogram(name: "F_empty_tuple", linkageName: "_CF_empty_tuple.Main", scope: null, file: !3, line: 53, type: !32, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !36 = !DILocation(line: 54, column: 10, scope: !35)
+// CHECK:STDOUT: !37 = !DILocation(line: 54, column: 3, scope: !35)
+// CHECK:STDOUT: !38 = distinct !DISubprogram(name: "Op", linkageName: "_COp.d07e2731f1087d49:Copy.Main", scope: null, file: !3, line: 58, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !39)
+// CHECK:STDOUT: !39 = !{!40}
+// CHECK:STDOUT: !40 = !DILocalVariable(arg: 1, scope: !38, type: !19)
+// CHECK:STDOUT: !41 = !DILocation(line: 59, column: 12, scope: !38)
+// CHECK:STDOUT: !42 = !DILocation(line: 59, column: 5, scope: !38)
+// CHECK:STDOUT: !43 = distinct !DISubprogram(name: "F_two_tuple", linkageName: "_CF_two_tuple.Main", scope: null, file: !3, line: 63, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !44)
+// CHECK:STDOUT: !44 = !{!45}
+// CHECK:STDOUT: !45 = !DILocalVariable(arg: 1, scope: !43, type: !19)
+// CHECK:STDOUT: !46 = !DILocation(line: 64, column: 10, scope: !43)
+// CHECK:STDOUT: !47 = !DILocation(line: 64, column: 3, scope: !43)
+// CHECK:STDOUT: !48 = distinct !DISubprogram(name: "Op", linkageName: "_COp.4af564822fd0c29a:Copy.Main", scope: null, file: !3, line: 68, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !49)
+// CHECK:STDOUT: !49 = !{!50}
+// CHECK:STDOUT: !50 = !DILocalVariable(arg: 1, scope: !48, type: !19)
+// CHECK:STDOUT: !51 = !DILocation(line: 69, column: 13, scope: !48)
+// CHECK:STDOUT: !52 = !DILocation(line: 69, column: 12, scope: !48)
+// CHECK:STDOUT: !53 = !DILocation(line: 69, column: 33, scope: !48)
+// CHECK:STDOUT: !54 = !DILocation(line: 69, column: 5, scope: !48)
+// CHECK:STDOUT: !55 = distinct !DISubprogram(name: "F_nested_tuple", linkageName: "_CF_nested_tuple.Main", scope: null, file: !3, line: 73, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !56)
+// CHECK:STDOUT: !56 = !{!57}
+// CHECK:STDOUT: !57 = !DILocalVariable(arg: 1, scope: !55, type: !19)
+// CHECK:STDOUT: !58 = !DILocation(line: 74, column: 10, scope: !55)
+// CHECK:STDOUT: !59 = !DILocation(line: 74, column: 3, scope: !55)
+// CHECK:STDOUT: !60 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.cf9485df26e40963", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !61)
+// CHECK:STDOUT: !61 = !{!62}
+// CHECK:STDOUT: !62 = !DILocalVariable(arg: 1, scope: !60, type: !7)
+// CHECK:STDOUT: !63 = !DILocation(line: 18, column: 3, scope: !60)
+// CHECK:STDOUT: !64 = !DILocation(line: 18, column: 14, scope: !60)
+// CHECK:STDOUT: !65 = !DILocation(line: 19, column: 10, scope: !60)
+// CHECK:STDOUT: !66 = !DILocation(line: 19, column: 3, scope: !60)
+// CHECK:STDOUT: !67 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.731881fd665c07ab", scope: null, file: !3, line: 17, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !68)
+// CHECK:STDOUT: !68 = !{!69}
+// CHECK:STDOUT: !69 = !DILocalVariable(arg: 1, scope: !67, type: !19)
+// CHECK:STDOUT: !70 = !DILocation(line: 18, column: 3, scope: !67)
+// CHECK:STDOUT: !71 = !DILocation(line: 18, column: 14, scope: !67)
+// CHECK:STDOUT: !72 = !DILocation(line: 19, column: 10, scope: !67)
+// CHECK:STDOUT: !73 = !DILocation(line: 19, column: 3, scope: !67)
+// CHECK:STDOUT: !74 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.ac6bb6b581e07691", scope: null, file: !3, line: 17, type: !32, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !75 = !DILocation(line: 18, column: 3, scope: !74)
+// CHECK:STDOUT: !76 = !DILocation(line: 18, column: 14, scope: !74)
+// CHECK:STDOUT: !77 = !DILocation(line: 19, column: 10, scope: !74)
+// CHECK:STDOUT: !78 = !DILocation(line: 19, column: 3, scope: !74)
+// CHECK:STDOUT: !79 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.86a4a70fb2978f72", scope: null, file: !3, line: 17, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !80)
+// CHECK:STDOUT: !80 = !{!81}
+// CHECK:STDOUT: !81 = !DILocalVariable(arg: 1, scope: !79, type: !19)
+// CHECK:STDOUT: !82 = !DILocation(line: 18, column: 3, scope: !79)
+// CHECK:STDOUT: !83 = !DILocation(line: 18, column: 14, scope: !79)
+// CHECK:STDOUT: !84 = !DILocation(line: 19, column: 10, scope: !79)
+// CHECK:STDOUT: !85 = !DILocation(line: 19, column: 3, scope: !79)
+// CHECK:STDOUT: !86 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main.bfaac0eb7445cea4", scope: null, file: !3, line: 17, type: !17, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !87)
+// CHECK:STDOUT: !87 = !{!88}
+// CHECK:STDOUT: !88 = !DILocalVariable(arg: 1, scope: !86, type: !19)
+// CHECK:STDOUT: !89 = !DILocation(line: 18, column: 3, scope: !86)
+// CHECK:STDOUT: !90 = !DILocation(line: 18, column: 14, scope: !86)
+// CHECK:STDOUT: !91 = !DILocation(line: 19, column: 10, scope: !86)
+// CHECK:STDOUT: !92 = !DILocation(line: 19, column: 3, scope: !86)

+ 1 - 1
toolchain/lower/testdata/global/class_obj.carbon

@@ -42,6 +42,6 @@ var a: A = {};
 // CHECK:STDOUT: !3 = !DIFile(filename: "class_obj.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 14, column: 1, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 0, scope: !4)

+ 13 - 10
toolchain/lower/testdata/global/class_with_fun.carbon

@@ -27,15 +27,15 @@ var a: A = {};
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_Cret_a.Main(ptr sret({}) %return) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @A.val.loc15_12, i64 0, i1 false), !dbg !7
-// CHECK:STDOUT:   ret void, !dbg !7
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 %return, ptr align 1 @A.val.loc15_12, i64 0, i1 false), !dbg !8
+// CHECK:STDOUT:   ret void, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_C__global_init.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_C__global_init.Main() #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 @_Ca.Main, ptr align 1 @A.val.loc15_12, i64 0, i1 false), !dbg !9
-// CHECK:STDOUT:   ret void, !dbg !10
+// CHECK:STDOUT:   call void @llvm.memcpy.p0.p0.i64(ptr align 1 @_Ca.Main, ptr align 1 @A.val.loc15_12, i64 0, i1 false), !dbg !12
+// CHECK:STDOUT:   ret void, !dbg !13
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nocallback nofree nounwind willreturn memory(argmem: readwrite)
@@ -56,8 +56,11 @@ var a: A = {};
 // CHECK:STDOUT: !3 = !DIFile(filename: "class_with_fun.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "ret_a", linkageName: "_Cret_a.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 15, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 18, column: 1, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 0, scope: !8)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !8 = !DILocation(line: 15, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !10, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = !DISubroutineType(types: !11)
+// CHECK:STDOUT: !11 = !{null}
+// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 1, scope: !9)
+// CHECK:STDOUT: !13 = !DILocation(line: 0, scope: !9)

+ 1 - 1
toolchain/lower/testdata/global/simple_init.carbon

@@ -35,6 +35,6 @@ var a: i32 = 0;
 // CHECK:STDOUT: !3 = !DIFile(filename: "simple_init.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 12, column: 1, scope: !4)
 // CHECK:STDOUT: !8 = !DILocation(line: 0, scope: !4)

+ 14 - 11
toolchain/lower/testdata/global/simple_with_fun.carbon

@@ -25,15 +25,15 @@ var a: i32 = test_a();
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_Ctest_a.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 0, !dbg !7
+// CHECK:STDOUT:   ret i32 0, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_C__global_init.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define void @_C__global_init.Main() #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %test_a.call = call i32 @_Ctest_a.Main(), !dbg !9
-// CHECK:STDOUT:   store i32 %test_a.call, ptr @_Ca.Main, align 4, !dbg !10
-// CHECK:STDOUT:   ret void, !dbg !11
+// CHECK:STDOUT:   %test_a.call = call i32 @_Ctest_a.Main(), !dbg !12
+// CHECK:STDOUT:   store i32 %test_a.call, ptr @_Ca.Main, align 4, !dbg !13
+// CHECK:STDOUT:   ret void, !dbg !14
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -47,9 +47,12 @@ var a: i32 = test_a();
 // CHECK:STDOUT: !3 = !DIFile(filename: "simple_with_fun.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "test_a", linkageName: "_Ctest_a.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 3, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 17, column: 14, scope: !8)
-// CHECK:STDOUT: !10 = !DILocation(line: 17, column: 1, scope: !8)
-// CHECK:STDOUT: !11 = !DILocation(line: 0, scope: !8)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !10, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = !DISubroutineType(types: !11)
+// CHECK:STDOUT: !11 = !{null}
+// CHECK:STDOUT: !12 = !DILocation(line: 17, column: 14, scope: !9)
+// CHECK:STDOUT: !13 = !DILocation(line: 17, column: 1, scope: !9)
+// CHECK:STDOUT: !14 = !DILocation(line: 0, scope: !9)

+ 18 - 15
toolchain/lower/testdata/global/use.carbon

@@ -27,17 +27,17 @@ fn F() -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CF.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc17 = load i32, ptr @_Ca.Main, align 4, !dbg !7
-// CHECK:STDOUT:   ret i32 %.loc17, !dbg !8
+// CHECK:STDOUT:   %.loc17 = load i32, ptr @_Ca.Main, align 4, !dbg !8
+// CHECK:STDOUT:   ret i32 %.loc17, !dbg !9
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define void @_C__global_init.Main() #0 !dbg !9 {
+// CHECK:STDOUT: define void @_C__global_init.Main() #0 !dbg !10 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   store i32 5, ptr @_Ca.Main, align 4, !dbg !10
-// CHECK:STDOUT:   %.loc14 = load i32, ptr @_Ca.Main, align 4, !dbg !11
-// CHECK:STDOUT:   store i32 %.loc14, ptr @_Cb.Main, align 4, !dbg !12
-// CHECK:STDOUT:   ret void, !dbg !13
+// CHECK:STDOUT:   store i32 5, ptr @_Ca.Main, align 4, !dbg !13
+// CHECK:STDOUT:   %.loc14 = load i32, ptr @_Ca.Main, align 4, !dbg !14
+// CHECK:STDOUT:   store i32 %.loc14, ptr @_Cb.Main, align 4, !dbg !15
+// CHECK:STDOUT:   ret void, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -51,11 +51,14 @@ fn F() -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "use.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 17, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 17, column: 3, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 12, column: 1, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 14, column: 14, scope: !9)
-// CHECK:STDOUT: !12 = !DILocation(line: 14, column: 1, scope: !9)
-// CHECK:STDOUT: !13 = !DILocation(line: 0, scope: !9)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 17, column: 10, scope: !4)
+// CHECK:STDOUT: !9 = !DILocation(line: 17, column: 3, scope: !4)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "__global_init", linkageName: "_C__global_init.Main", scope: null, file: !3, type: !11, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !11 = !DISubroutineType(types: !12)
+// CHECK:STDOUT: !12 = !{null}
+// CHECK:STDOUT: !13 = !DILocation(line: 12, column: 1, scope: !10)
+// CHECK:STDOUT: !14 = !DILocation(line: 14, column: 14, scope: !10)
+// CHECK:STDOUT: !15 = !DILocation(line: 14, column: 1, scope: !10)
+// CHECK:STDOUT: !16 = !DILocation(line: 0, scope: !10)

+ 20 - 15
toolchain/lower/testdata/if/else.carbon

@@ -47,19 +47,19 @@ fn If(b: bool) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CIf.Main(i1 %b) #0 !dbg !12 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br i1 %b, label %if.then, label %if.else, !dbg !13
+// CHECK:STDOUT:   br i1 %b, label %if.then, label %if.else, !dbg !18
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   call void @_CF.Main(), !dbg !14
-// CHECK:STDOUT:   br label %if.done, !dbg !15
+// CHECK:STDOUT:   call void @_CF.Main(), !dbg !19
+// CHECK:STDOUT:   br label %if.done, !dbg !20
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %entry
-// CHECK:STDOUT:   call void @_CG.Main(), !dbg !16
-// CHECK:STDOUT:   br label %if.done, !dbg !15
+// CHECK:STDOUT:   call void @_CG.Main(), !dbg !21
+// CHECK:STDOUT:   br label %if.done, !dbg !20
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.done:                                          ; preds = %if.else, %if.then
-// CHECK:STDOUT:   call void @_CH.Main(), !dbg !17
-// CHECK:STDOUT:   ret void, !dbg !18
+// CHECK:STDOUT:   call void @_CH.Main(), !dbg !22
+// CHECK:STDOUT:   ret void, !dbg !23
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -73,16 +73,21 @@ fn If(b: bool) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "else.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
 // CHECK:STDOUT: !8 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !9 = !DILocation(line: 14, column: 1, scope: !8)
 // CHECK:STDOUT: !10 = distinct !DISubprogram(name: "H", linkageName: "_CH.Main", scope: null, file: !3, line: 15, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !11 = !DILocation(line: 15, column: 1, scope: !10)
-// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "If", linkageName: "_CIf.Main", scope: null, file: !3, line: 17, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !13 = !DILocation(line: 18, column: 6, scope: !12)
-// CHECK:STDOUT: !14 = !DILocation(line: 19, column: 5, scope: !12)
-// CHECK:STDOUT: !15 = !DILocation(line: 18, column: 3, scope: !12)
-// CHECK:STDOUT: !16 = !DILocation(line: 21, column: 5, scope: !12)
-// CHECK:STDOUT: !17 = !DILocation(line: 23, column: 3, scope: !12)
-// CHECK:STDOUT: !18 = !DILocation(line: 17, column: 1, scope: !12)
+// CHECK:STDOUT: !12 = distinct !DISubprogram(name: "If", linkageName: "_CIf.Main", scope: null, file: !3, line: 17, type: !13, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !16)
+// CHECK:STDOUT: !13 = !DISubroutineType(types: !14)
+// CHECK:STDOUT: !14 = !{null, !15}
+// CHECK:STDOUT: !15 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !16 = !{!17}
+// CHECK:STDOUT: !17 = !DILocalVariable(arg: 1, scope: !12, type: !15)
+// CHECK:STDOUT: !18 = !DILocation(line: 18, column: 6, scope: !12)
+// CHECK:STDOUT: !19 = !DILocation(line: 19, column: 5, scope: !12)
+// CHECK:STDOUT: !20 = !DILocation(line: 18, column: 3, scope: !12)
+// CHECK:STDOUT: !21 = !DILocation(line: 21, column: 5, scope: !12)
+// CHECK:STDOUT: !22 = !DILocation(line: 23, column: 3, scope: !12)
+// CHECK:STDOUT: !23 = !DILocation(line: 17, column: 1, scope: !12)

+ 17 - 12
toolchain/lower/testdata/if/no_else.carbon

@@ -38,15 +38,15 @@ fn If(b: bool) {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define void @_CIf.Main(i1 %b) #0 !dbg !10 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br i1 %b, label %if.then, label %if.else, !dbg !11
+// CHECK:STDOUT:   br i1 %b, label %if.then, label %if.else, !dbg !16
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.then:                                          ; preds = %entry
-// CHECK:STDOUT:   call void @_CF.Main(), !dbg !12
-// CHECK:STDOUT:   br label %if.else, !dbg !13
+// CHECK:STDOUT:   call void @_CF.Main(), !dbg !17
+// CHECK:STDOUT:   br label %if.else, !dbg !18
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.else:                                          ; preds = %if.then, %entry
-// CHECK:STDOUT:   call void @_CG.Main(), !dbg !14
-// CHECK:STDOUT:   ret void, !dbg !15
+// CHECK:STDOUT:   call void @_CG.Main(), !dbg !19
+// CHECK:STDOUT:   ret void, !dbg !20
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -60,13 +60,18 @@ fn If(b: bool) {
 // CHECK:STDOUT: !3 = !DIFile(filename: "no_else.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
+// CHECK:STDOUT: !6 = !{null}
 // CHECK:STDOUT: !7 = !DILocation(line: 13, column: 1, scope: !4)
 // CHECK:STDOUT: !8 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !9 = !DILocation(line: 14, column: 1, scope: !8)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "If", linkageName: "_CIf.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 6, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 18, column: 5, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 17, column: 3, scope: !10)
-// CHECK:STDOUT: !14 = !DILocation(line: 20, column: 3, scope: !10)
-// CHECK:STDOUT: !15 = !DILocation(line: 16, column: 1, scope: !10)
+// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "If", linkageName: "_CIf.Main", scope: null, file: !3, line: 16, type: !11, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !11 = !DISubroutineType(types: !12)
+// CHECK:STDOUT: !12 = !{null, !13}
+// CHECK:STDOUT: !13 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !14 = !{!15}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !10, type: !13)
+// CHECK:STDOUT: !16 = !DILocation(line: 17, column: 6, scope: !10)
+// CHECK:STDOUT: !17 = !DILocation(line: 18, column: 5, scope: !10)
+// CHECK:STDOUT: !18 = !DILocation(line: 17, column: 3, scope: !10)
+// CHECK:STDOUT: !19 = !DILocation(line: 20, column: 3, scope: !10)
+// CHECK:STDOUT: !20 = !DILocation(line: 16, column: 1, scope: !10)

+ 25 - 19
toolchain/lower/testdata/if_expr/basic.carbon

@@ -23,31 +23,31 @@ fn Select(b: bool) -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CF.Main() #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 1, !dbg !7
+// CHECK:STDOUT:   ret i32 1, !dbg !8
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CG.Main() #0 !dbg !8 {
+// CHECK:STDOUT: define i32 @_CG.Main() #0 !dbg !9 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   ret i32 2, !dbg !9
+// CHECK:STDOUT:   ret i32 2, !dbg !10
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CSelect.Main(i1 %b) #0 !dbg !10 {
+// CHECK:STDOUT: define i32 @_CSelect.Main(i1 %b) #0 !dbg !11 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br i1 %b, label %if.expr.then, label %if.expr.else, !dbg !11
+// CHECK:STDOUT:   br i1 %b, label %if.expr.then, label %if.expr.else, !dbg !17
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.then:                                     ; preds = %entry
-// CHECK:STDOUT:   %F.call = call i32 @_CF.Main(), !dbg !12
-// CHECK:STDOUT:   br label %if.expr.result, !dbg !11
+// CHECK:STDOUT:   %F.call = call i32 @_CF.Main(), !dbg !18
+// CHECK:STDOUT:   br label %if.expr.result, !dbg !17
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.else:                                     ; preds = %entry
-// CHECK:STDOUT:   %G.call = call i32 @_CG.Main(), !dbg !13
-// CHECK:STDOUT:   br label %if.expr.result, !dbg !11
+// CHECK:STDOUT:   %G.call = call i32 @_CG.Main(), !dbg !19
+// CHECK:STDOUT:   br label %if.expr.result, !dbg !17
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.result:                                   ; preds = %if.expr.else, %if.expr.then
 // CHECK:STDOUT:   %0 = phi i32 [ %F.call, %if.expr.then ], [ %G.call, %if.expr.else ]
-// CHECK:STDOUT:   ret i32 %0, !dbg !14
+// CHECK:STDOUT:   ret i32 %0, !dbg !20
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -61,12 +61,18 @@ fn Select(b: bool) -> i32 {
 // CHECK:STDOUT: !3 = !DIFile(filename: "basic.carbon", directory: "")
 // CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 13, column: 17, scope: !4)
-// CHECK:STDOUT: !8 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !9 = !DILocation(line: 14, column: 17, scope: !8)
-// CHECK:STDOUT: !10 = distinct !DISubprogram(name: "Select", linkageName: "_CSelect.Main", scope: null, file: !3, line: 16, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !11 = !DILocation(line: 17, column: 10, scope: !10)
-// CHECK:STDOUT: !12 = !DILocation(line: 17, column: 20, scope: !10)
-// CHECK:STDOUT: !13 = !DILocation(line: 17, column: 29, scope: !10)
-// CHECK:STDOUT: !14 = !DILocation(line: 17, column: 3, scope: !10)
+// CHECK:STDOUT: !6 = !{!7}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DILocation(line: 13, column: 17, scope: !4)
+// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "G", linkageName: "_CG.Main", scope: null, file: !3, line: 14, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !10 = !DILocation(line: 14, column: 17, scope: !9)
+// CHECK:STDOUT: !11 = distinct !DISubprogram(name: "Select", linkageName: "_CSelect.Main", scope: null, file: !3, line: 16, type: !12, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !15)
+// CHECK:STDOUT: !12 = !DISubroutineType(types: !13)
+// CHECK:STDOUT: !13 = !{!7, !14}
+// CHECK:STDOUT: !14 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !15 = !{!16}
+// CHECK:STDOUT: !16 = !DILocalVariable(arg: 1, scope: !11, type: !14)
+// CHECK:STDOUT: !17 = !DILocation(line: 17, column: 10, scope: !11)
+// CHECK:STDOUT: !18 = !DILocation(line: 17, column: 20, scope: !11)
+// CHECK:STDOUT: !19 = !DILocation(line: 17, column: 29, scope: !11)
+// CHECK:STDOUT: !20 = !DILocation(line: 17, column: 3, scope: !11)

+ 22 - 16
toolchain/lower/testdata/if_expr/empty_block.carbon

@@ -20,37 +20,37 @@ fn Select(b: bool, c: bool, d: bool) -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @_CSelect.Main(i1 %b, i1 %c, i1 %d) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   br i1 %b, label %if.expr.then.loc14_10, label %if.expr.else.loc14_10, !dbg !7
+// CHECK:STDOUT:   br i1 %b, label %if.expr.then.loc14_10, label %if.expr.else.loc14_10, !dbg !13
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.then.loc14_10:                            ; preds = %entry
-// CHECK:STDOUT:   br i1 %c, label %if.expr.then.loc14_20, label %if.expr.else.loc14_20, !dbg !8
+// CHECK:STDOUT:   br i1 %c, label %if.expr.then.loc14_20, label %if.expr.else.loc14_20, !dbg !14
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.then.loc14_20:                            ; preds = %if.expr.then.loc14_10
-// CHECK:STDOUT:   br label %if.expr.result.loc14_20, !dbg !8
+// CHECK:STDOUT:   br label %if.expr.result.loc14_20, !dbg !14
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.else.loc14_20:                            ; preds = %if.expr.then.loc14_10
-// CHECK:STDOUT:   br label %if.expr.result.loc14_20, !dbg !8
+// CHECK:STDOUT:   br label %if.expr.result.loc14_20, !dbg !14
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.result.loc14_20:                          ; preds = %if.expr.else.loc14_20, %if.expr.then.loc14_20
 // CHECK:STDOUT:   %0 = phi i32 [ 1, %if.expr.then.loc14_20 ], [ 2, %if.expr.else.loc14_20 ]
-// CHECK:STDOUT:   br label %if.expr.result.loc14_10, !dbg !7
+// CHECK:STDOUT:   br label %if.expr.result.loc14_10, !dbg !13
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.else.loc14_10:                            ; preds = %entry
-// CHECK:STDOUT:   br i1 %d, label %if.expr.then.loc14_51, label %if.expr.else.loc14_51, !dbg !9
+// CHECK:STDOUT:   br i1 %d, label %if.expr.then.loc14_51, label %if.expr.else.loc14_51, !dbg !15
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.then.loc14_51:                            ; preds = %if.expr.else.loc14_10
-// CHECK:STDOUT:   br label %if.expr.result.loc14_51, !dbg !9
+// CHECK:STDOUT:   br label %if.expr.result.loc14_51, !dbg !15
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.else.loc14_51:                            ; preds = %if.expr.else.loc14_10
-// CHECK:STDOUT:   br label %if.expr.result.loc14_51, !dbg !9
+// CHECK:STDOUT:   br label %if.expr.result.loc14_51, !dbg !15
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.result.loc14_51:                          ; preds = %if.expr.else.loc14_51, %if.expr.then.loc14_51
 // CHECK:STDOUT:   %1 = phi i32 [ 3, %if.expr.then.loc14_51 ], [ 4, %if.expr.else.loc14_51 ]
-// CHECK:STDOUT:   br label %if.expr.result.loc14_10, !dbg !7
+// CHECK:STDOUT:   br label %if.expr.result.loc14_10, !dbg !13
 // CHECK:STDOUT:
 // CHECK:STDOUT: if.expr.result.loc14_10:                          ; preds = %if.expr.result.loc14_51, %if.expr.result.loc14_20
 // CHECK:STDOUT:   %2 = phi i32 [ %0, %if.expr.result.loc14_20 ], [ %1, %if.expr.result.loc14_51 ]
-// CHECK:STDOUT:   ret i32 %2, !dbg !10
+// CHECK:STDOUT:   ret i32 %2, !dbg !16
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -62,10 +62,16 @@ fn Select(b: bool, c: bool, d: bool) -> i32 {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "empty_block.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Select", linkageName: "_CSelect.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "Select", linkageName: "_CSelect.Main", scope: null, file: !3, line: 13, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 14, column: 10, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 14, column: 20, scope: !4)
-// CHECK:STDOUT: !9 = !DILocation(line: 14, column: 51, scope: !4)
-// CHECK:STDOUT: !10 = !DILocation(line: 14, column: 3, scope: !4)
+// CHECK:STDOUT: !6 = !{!7, !8, !8, !8}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10, !11, !12}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocalVariable(arg: 2, scope: !4, type: !8)
+// CHECK:STDOUT: !12 = !DILocalVariable(arg: 3, scope: !4, type: !8)
+// CHECK:STDOUT: !13 = !DILocation(line: 14, column: 10, scope: !4)
+// CHECK:STDOUT: !14 = !DILocation(line: 14, column: 20, scope: !4)
+// CHECK:STDOUT: !15 = !DILocation(line: 14, column: 51, scope: !4)
+// CHECK:STDOUT: !16 = !DILocation(line: 14, column: 3, scope: !4)

+ 19 - 13
toolchain/lower/testdata/impl/assoc_fn_alias.carbon

@@ -35,16 +35,16 @@ fn Call(a: A) -> i32 {
 // CHECK:STDOUT: ; Function Attrs: nounwind
 // CHECK:STDOUT: define i32 @"_CF.A.Main:I.Main"(ptr %self) #0 !dbg !4 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %.loc24_16.1.n = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !7
-// CHECK:STDOUT:   %.loc24_16.2 = load i32, ptr %.loc24_16.1.n, align 4, !dbg !7
-// CHECK:STDOUT:   ret i32 %.loc24_16.2, !dbg !8
+// CHECK:STDOUT:   %.loc24_16.1.n = getelementptr inbounds nuw { i32 }, ptr %self, i32 0, i32 0, !dbg !11
+// CHECK:STDOUT:   %.loc24_16.2 = load i32, ptr %.loc24_16.1.n, align 4, !dbg !11
+// CHECK:STDOUT:   ret i32 %.loc24_16.2, !dbg !12
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: ; Function Attrs: nounwind
-// CHECK:STDOUT: define i32 @_CCall.Main(ptr %a) #0 !dbg !9 {
+// CHECK:STDOUT: define i32 @_CCall.Main(ptr %a) #0 !dbg !13 {
 // CHECK:STDOUT: entry:
-// CHECK:STDOUT:   %A.as.I.impl.F.call = call i32 @"_CF.A.Main:I.Main"(ptr %a), !dbg !10
-// CHECK:STDOUT:   ret i32 %A.as.I.impl.F.call, !dbg !11
+// CHECK:STDOUT:   %A.as.I.impl.F.call = call i32 @"_CF.A.Main:I.Main"(ptr %a), !dbg !16
+// CHECK:STDOUT:   ret i32 %A.as.I.impl.F.call, !dbg !17
 // CHECK:STDOUT: }
 // CHECK:STDOUT:
 // CHECK:STDOUT: attributes #0 = { nounwind }
@@ -56,11 +56,17 @@ fn Call(a: A) -> i32 {
 // CHECK:STDOUT: !1 = !{i32 2, !"Debug Info Version", i32 3}
 // CHECK:STDOUT: !2 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !3, producer: "carbon", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug)
 // CHECK:STDOUT: !3 = !DIFile(filename: "assoc_fn_alias.carbon", directory: "")
-// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.A.Main:I.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2)
+// CHECK:STDOUT: !4 = distinct !DISubprogram(name: "F", linkageName: "_CF.A.Main:I.Main", scope: null, file: !3, line: 23, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !9)
 // CHECK:STDOUT: !5 = !DISubroutineType(types: !6)
-// CHECK:STDOUT: !6 = !{}
-// CHECK:STDOUT: !7 = !DILocation(line: 24, column: 12, scope: !4)
-// CHECK:STDOUT: !8 = !DILocation(line: 24, column: 5, scope: !4)
-// CHECK:STDOUT: !9 = distinct !DISubprogram(name: "Call", linkageName: "_CCall.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2)
-// CHECK:STDOUT: !10 = !DILocation(line: 29, column: 10, scope: !9)
-// CHECK:STDOUT: !11 = !DILocation(line: 29, column: 3, scope: !9)
+// CHECK:STDOUT: !6 = !{!7, !8}
+// CHECK:STDOUT: !7 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
+// CHECK:STDOUT: !8 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: null, size: 8)
+// CHECK:STDOUT: !9 = !{!10}
+// CHECK:STDOUT: !10 = !DILocalVariable(arg: 1, scope: !4, type: !8)
+// CHECK:STDOUT: !11 = !DILocation(line: 24, column: 12, scope: !4)
+// CHECK:STDOUT: !12 = !DILocation(line: 24, column: 5, scope: !4)
+// CHECK:STDOUT: !13 = distinct !DISubprogram(name: "Call", linkageName: "_CCall.Main", scope: null, file: !3, line: 28, type: !5, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !14)
+// CHECK:STDOUT: !14 = !{!15}
+// CHECK:STDOUT: !15 = !DILocalVariable(arg: 1, scope: !13, type: !8)
+// CHECK:STDOUT: !16 = !DILocation(line: 29, column: 10, scope: !13)
+// CHECK:STDOUT: !17 = !DILocation(line: 29, column: 3, scope: !13)

Неке датотеке нису приказане због велике количине промена