Merge pull request #69986 from hamishknight/try-try-again

This commit is contained in:
Hamish Knight
2023-11-27 20:18:53 +00:00
committed by GitHub
3 changed files with 945 additions and 102 deletions

View File

@@ -11,8 +11,11 @@ struct S {
func throwingMethod() throws -> Int { 0 }
}
@discardableResult
func throwingFn() throws -> Int { 0 }
func throwingBool() throws -> Bool { true }
var throwingProp: Int {
get throws { 5 }
}
@@ -150,6 +153,53 @@ enum SomeErr : Error {
// CHECK: [[BB_ERR]]
// CHECK-NEXT: increment_profiler_counter 1
// func test28() throws -> Int {
// let x = try .random()
// ? throwingFn()
// : throwingFn()
// return x
// }
// CHECK-LABEL: sil hidden @$s15coverage_errors6test28SiyKF : $@convention(thin) () -> (Int, @error any Error)
// CHECK: bb0:
// CHECK: increment_profiler_counter 0
// CHECK: function_ref @$sSb6randomSbyFZ
// CHECK: cond_br {{%[0-9]+}}, [[BB_TRUE:bb[0-9]+]], [[BB_FALSE:bb[0-9]+]]
//
// CHECK: [[BB_FALSE]]
// CHECK: [[THROW_FN:%[0-9]+]] = function_ref @$s15coverage_errors10throwingFnSiyKF
// CHECK: try_apply [[THROW_FN]]() : $@convention(thin) () -> (Int, @error any Error), normal [[BB_NORMAL:bb[0-9]+]], error [[BB_ERR:bb[0-9]+]]
//
// CHECK: [[BB_ERR]]
// CHECK: increment_profiler_counter 3
//
// CHECK: [[BB_TRUE]]
// CHECK: increment_profiler_counter 1
// CHECK: [[THROW_FN:%[0-9]+]] = function_ref @$s15coverage_errors10throwingFnSiyKF
// CHECK: try_apply [[THROW_FN]]() : $@convention(thin) () -> (Int, @error any Error), normal [[BB_NORMAL:bb[0-9]+]], error [[BB_ERR:bb[0-9]+]]
//
// CHECK: [[BB_ERR]]
// CHECK: increment_profiler_counter 2
// func test43() -> Int? {
// let x = try? throwingS.throwingMethod()
// return x
// }
// CHECK-LABEL: sil hidden @$s15coverage_errors6test43SiSgyF : $@convention(thin) () -> Optional<Int>
// CHECK: bb0:
// CHECK: increment_profiler_counter 0
// CHECK: [[GETTER:%[0-9]+]] = function_ref @$s15coverage_errors9throwingSAA1SVvg : $@convention(thin) () -> (S, @error any Error)
// CHECK: try_apply [[GETTER]]() : $@convention(thin) () -> (S, @error any Error), normal [[BB_NORMAL:bb[0-9]+]], error [[BB_ERR:bb[0-9]+]]
//
// CHECK: [[BB_ERR]]
// CHECK: increment_profiler_counter 1
//
// CHECK: [[BB_NORMAL]]
// CHECK: [[METHOD:%[0-9]+]] = function_ref @$s15coverage_errors1SV14throwingMethodSiyKF : $@convention(method) (S) -> (Int, @error any Error) // user: %5
// CHECK: try_apply [[METHOD]]({{%[0-9]+}}) : $@convention(method) (S) -> (Int, @error any Error), normal [[BB_NORMAL:bb[0-9]+]], error [[BB_ERR:bb[0-9]+]]
//
// CHECK: [[BB_ERR]]
// CHECK: increment_profiler_counter 2
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors5test1SiyF"
func test1() -> Int { // CHECK-NEXT: [[@LINE]]:21 -> [[@LINE+7]]:2 : 0
do { // CHECK-NEXT: [[@LINE]]:6 -> [[@LINE+3]]:4 : 0
@@ -402,6 +452,371 @@ func test23() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+11]]:2 : 0
return 2
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test24SiyKF"
func test24() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+4]]:2 : 0
let x = .random() ? try throwingFn() : 0 // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE]]:39 : 1
return x // CHECK-NEXT: [[@LINE-1]]:39 -> [[@LINE]]:11 : (0 - 2)
// CHECK-NEXT: [[@LINE-2]]:42 -> [[@LINE-2]]:43 : (0 - 1)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test25SiyKF"
func test25() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+4]]:2 : 0
let x = .random() ? 0 : try throwingFn() // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE]]:24 : 1
return x // CHECK-NEXT: [[@LINE-1]]:27 -> [[@LINE-1]]:43 : (0 - 1)
// CHECK-NEXT: [[@LINE-2]]:43 -> [[@LINE-1]]:11 : (0 - 2)
} // CHECK-NEXT: }
// Note in this case the throws region of the first branch overlaps the
// second branch, which isn't ideal, but it matches what we already do
// for e.g if statements and returns, and doesn't impact the resulting
// coverage since we always take the counter for the smallest subrange,
// which in this case is the region for the second branch.
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test26SiyKF"
func test26() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+5]]:2 : 0
let x = .random() ? try throwingFn() : try throwingFn() // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE]]:39 : 1
return x // CHECK-NEXT: [[@LINE-1]]:39 -> [[@LINE]]:11 : (0 - 2)
// CHECK-NEXT: [[@LINE-2]]:42 -> [[@LINE-2]]:58 : (0 - 1)
// CHECK-NEXT: [[@LINE-3]]:58 -> [[@LINE-2]]:11 : ((0 - 2) - 3)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test27SiyKF"
func test27() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+5]]:2 : 0
let x = try .random() ? throwingFn() : throwingFn() // CHECK-NEXT: [[@LINE]]:27 -> [[@LINE]]:39 : 1
return x // CHECK-NEXT: [[@LINE-1]]:39 -> [[@LINE]]:11 : (0 - 2)
// CHECK-NEXT: [[@LINE-2]]:42 -> [[@LINE-2]]:54 : (0 - 1)
// CHECK-NEXT: [[@LINE-3]]:54 -> [[@LINE-2]]:11 : ((0 - 2) - 3)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test28SiyKF"
func test28() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+5]]:2 : 0
let x = try .random() // CHECK-NEXT: [[@LINE+1]]:7 -> [[@LINE+1]]:19 : 1
? throwingFn() // CHECK-NEXT: [[@LINE]]:19 -> [[@LINE+2]]:11 : (0 - 2)
: throwingFn() // CHECK-NEXT: [[@LINE]]:7 -> [[@LINE]]:19 : (0 - 1)
return x // CHECK-NEXT: [[@LINE-1]]:19 -> [[@LINE]]:11 : ((0 - 2) - 3)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test29Si_SityKF"
func test29() throws -> (Int, Int) { // CHECK-NEXT: [[@LINE]]:36 -> [[@LINE+7]]:2 : 0
let x = try .random() // CHECK-NEXT: [[@LINE+1]]:7 -> [[@LINE+1]]:24 : 1
? (throwingFn(), 0) // CHECK-NEXT: [[@LINE]]:20 -> [[@LINE]]:24 : (1 - 2)
: (0, throwingFn()) // CHECK-NEXT: [[@LINE-1]]:24 -> [[@LINE+1]]:11 : (0 - 2)
return x // CHECK-NEXT: [[@LINE-1]]:7 -> [[@LINE-1]]:24 : (0 - 1)
// CHECK-NEXT: [[@LINE-2]]:23 -> [[@LINE-2]]:24 : ((0 - 1) - 3)
// CHECK-NEXT: [[@LINE-3]]:24 -> [[@LINE-2]]:11 : ((0 - 2) - 3)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test30Si_SityKF"
func test30() throws -> (Int, Int) { // CHECK-NEXT: [[@LINE]]:36 -> [[@LINE+6]]:2 : 0
let x = try .random() // CHECK-NEXT: [[@LINE+1]]:7 -> [[@LINE+1]]:35 : 1
? (throwingFn(), throwingFn()) // CHECK-NEXT: [[@LINE]]:20 -> [[@LINE]]:35 : (1 - 2)
: (0, 0) // CHECK-NEXT: [[@LINE-1]]:34 -> [[@LINE-1]]:35 : ((1 - 2) - 3)
return x // CHECK-NEXT: [[@LINE-2]]:35 -> [[@LINE]]:11 : ((0 - 2) - 3)
// CHECK-NEXT: [[@LINE-2]]:7 -> [[@LINE-2]]:13 : (0 - 1)
} // CHECK-NEXT: }
@discardableResult
func takesOptInts(_ x: Int?, _ y: Int?) -> Int { 0 }
// `throwingFn` is within a `try?`, so the non-error branch is empty.
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test31yyF"
func test31() { // CHECK-NEXT: [[@LINE]]:15 -> [[@LINE+2]]:2 : 0
takesOptInts(try? throwingFn(), 0)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test32yyF"
func test32() { // CHECK-NEXT: [[@LINE]]:15 -> [[@LINE+5]]:2 : 0
takesOptInts(
try? throwingFn(),
try? throwingFn()
)
} // CHECK-NEXT: }
// Here the throws region extends into the second arg.
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test33SiSgyF"
func test33() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+2]]:2 : 0
try? takesOptInts(throwingFn(), 0) // CHECK-NEXT: [[@LINE]]:33 -> [[@LINE]]:37 : (0 - 1)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test34SiSgyF"
func test34() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+3]]:2 : 0
try? takesOptInts(throwingFn(), throwingFn()) // CHECK-NEXT: [[@LINE]]:33 -> [[@LINE]]:48 : (0 - 1)
// CHECK-NEXT: [[@LINE-1]]:47 -> [[@LINE-1]]:48 : ((0 - 1) - 2)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test35SiSgyF"
func test35() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+5]]:2 : 0
try? takesOptInts(
throwingFn(), // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+2]]:4 : (0 - 1)
throwingFn() // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+1]]:4 : ((0 - 1) - 2)
)
} // CHECK-NEXT: }
// The 'try's here are redundant.
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test36SiSgyF"
func test36() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+5]]:2 : 0
try? takesOptInts(
try throwingFn(), // CHECK-NEXT: [[@LINE]]:21 -> [[@LINE+2]]:4 : (0 - 1)
try throwingFn() // CHECK-NEXT: [[@LINE]]:21 -> [[@LINE+1]]:4 : ((0 - 1) - 2)
)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test37SiSgyF"
func test37() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+5]]:2 : 0
try? takesOptInts(
try throwingFn(), // CHECK-NEXT: [[@LINE]]:21 -> [[@LINE+2]]:4 : (0 - 1)
try? S[]
)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test38SiSgyF"
func test38() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+5]]:2 : 0
try? takesOptInts(
try? throwingFn(),
try S[] // CHECK-NEXT: [[@LINE]]:12 -> [[@LINE+1]]:4 : (0 - 2)
)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test39Si_SitSgyF"
func test39(
) -> (Int, Int)? { // CHECK-NEXT: [[@LINE]]:18 -> [[@LINE+5]]:2 : 0
try? (takesOptInts(
throwingFn(), // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+2]]:8 : (0 - 1)
try? throwingProp
), 0)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test40SiyKF"
func test40(
) throws -> Int { // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+5]]:2 : 0
try takesOptInts(
try? throwingFn(),
throwingProp // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+2]]:2 : (0 - 2)
)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test41SiyKF"
func test41(
) throws -> Int { // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+5]]:2 : 0
try takesOptInts(
throwingFn(), // CHECK-NEXT: [[@LINE]]:17 -> [[@LINE+3]]:2 : (0 - 1)
try? throwingFn()
)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test42SiSgyF"
func test42() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+5]]:2 : 0
guard let x = try? throwingFn() else { // CHECK-NEXT: [[@LINE]]:40 -> [[@LINE+2]]:4 : 1
return nil
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:11 : (0 - 1)
return x
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test43SiSgyF"
func test43() -> Int? { // CHECK-NEXT: [[@LINE]]:23 -> [[@LINE+3]]:2 : 0
let x = try? throwingS.throwingMethod() // CHECK-NEXT: [[@LINE]]:25 -> [[@LINE]]:42 : (0 - 1)
return x
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test44SiSgyKF"
func test44() throws -> Int? { // CHECK-NEXT: [[@LINE]]:30 -> [[@LINE+3]]:2 : 0
let x = try (try? throwingS)?.throwingMethod() // CHECK-NEXT: [[@LINE]]:49 -> [[@LINE+1]]:11 : (0 - 2)
return x
}
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test45yyF"
func test45() { // CHECK-NEXT: [[@LINE]]:15 -> [[@LINE+2]]:2 : 0
_ = try? { throw SomeErr.Err1 }()
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test45yyFyyKXEfU_"
// CHECK-NEXT: [[@LINE-4]]:12 -> [[@LINE-4]]:34 : 0
// CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test46Si_SitSgyF"
func test46() -> (Int, Int)? { // CHECK-NEXT: [[@LINE]]:30 -> [[@LINE+2]]:2 : 0
try? ({ throw SomeErr.Err1 }(), 0) // CHECK-NEXT: [[@LINE]]:33 -> [[@LINE]]:37 : (0 - 1)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test47yyKF"
func test47() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+2]]:2 : 0
try throwingFn() // CHECK-NEXT: [[@LINE]]:19 -> [[@LINE+1]]:2 : (0 - 1)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test48SiyKF"
func test48() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+5]]:2 : 0
try throwingBool() // CHECK-NEXT: [[@LINE]]:21 -> [[@LINE+4]]:2 : (0 - 2)
? try throwingFn() // CHECK-NEXT: [[@LINE]]:7 -> [[@LINE]]:23 : 1
: 1 // CHECK-NEXT: [[@LINE-1]]:23 -> [[@LINE+2]]:2 : ((0 - 2) - 3)
// CHECK-NEXT: [[@LINE-1]]:7 -> [[@LINE-1]]:8 : ((0 - 1) - 2)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test49SiyKF"
func test49() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+6]]:2 : 0
try throwingBool() // CHECK-NEXT: [[@LINE]]:21 -> [[@LINE+5]]:2 : (0 - 2)
? try throwingFn() // CHECK-NEXT: [[@LINE]]:7 -> [[@LINE]]:23 : 1
: try throwingFn() // CHECK-NEXT: [[@LINE-1]]:23 -> [[@LINE+3]]:2 : ((0 - 2) - 3)
// CHECK-NEXT: [[@LINE-1]]:7 -> [[@LINE-1]]:23 : ((0 - 1) - 2)
// CHECK-NEXT: [[@LINE-2]]:23 -> [[@LINE+1]]:2 : (((0 - 2) - 3) - 4)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test50SiyKF"
func test50() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+8]]:2 : 0
let x = if try throwingBool() { // CHECK-NEXT: [[@LINE]]:14 -> [[@LINE]]:32 : 0
try throwingFn() // CHECK-NEXT: [[@LINE-1]]:32 -> [[@LINE+4]]:11 : (0 - 2)
} else { // CHECK-NEXT: [[@LINE-2]]:33 -> [[@LINE]]:4 : 1
1 // CHECK-NEXT: [[@LINE-2]]:21 -> [[@LINE-1]]:4 : (1 - 3)
} // CHECK-NEXT: [[@LINE-2]]:4 -> [[@LINE+1]]:11 : ((0 - 2) - 3)
return x // CHECK-NEXT: [[@LINE-3]]:10 -> [[@LINE-1]]:4 : ((0 - 1) - 2)
// CHECK-NEXT: [[@LINE-2]]:4 -> [[@LINE-1]]:11 : ((0 - 2) - 3)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test51SiyKF"
func test51() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+9]]:2 : 0
let x = if try throwingBool() { // CHECK-NEXT: [[@LINE]]:14 -> [[@LINE]]:32 : 0
try throwingFn() // CHECK-NEXT: [[@LINE-1]]:32 -> [[@LINE+4]]:11 : (0 - 2)
} else { // CHECK-NEXT: [[@LINE-2]]:33 -> [[@LINE]]:4 : 1
try throwingFn() // CHECK-NEXT: [[@LINE-2]]:21 -> [[@LINE-1]]:4 : (1 - 3)
} // CHECK-NEXT: [[@LINE-2]]:4 -> [[@LINE+1]]:11 : ((0 - 2) - 3)
return x // CHECK-NEXT: [[@LINE-3]]:10 -> [[@LINE-1]]:4 : ((0 - 1) - 2)
// CHECK-NEXT: [[@LINE-3]]:21 -> [[@LINE-2]]:4 : (((0 - 1) - 2) - 4)
// CHECK-NEXT: [[@LINE-3]]:4 -> [[@LINE-2]]:11 : (((0 - 2) - 3) - 4)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test52SiyKF"
func test52() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+10]]:2 : 0
let x = if try throwingBool(), // CHECK-NEXT: [[@LINE]]:14 -> [[@LINE]]:32 : 0
try throwingBool() { // CHECK-NEXT: [[@LINE-1]]:32 -> [[@LINE+5]]:11 : (0 - 2)
try throwingFn() // CHECK-NEXT: [[@LINE-1]]:32 -> [[@LINE+4]]:11 : ((0 - 2) - 3)
} else { // CHECK-NEXT: [[@LINE-2]]:33 -> [[@LINE]]:4 : 1
try throwingFn() // CHECK-NEXT: [[@LINE-2]]:21 -> [[@LINE-1]]:4 : (1 - 4)
} // CHECK-NEXT: [[@LINE-2]]:4 -> [[@LINE+1]]:11 : (((0 - 2) - 3) - 4)
return x // CHECK-NEXT: [[@LINE-3]]:10 -> [[@LINE-1]]:4 : (((0 - 1) - 2) - 3)
// CHECK-NEXT: [[@LINE-3]]:21 -> [[@LINE-2]]:4 : ((((0 - 1) - 2) - 3) - 5)
// CHECK-NEXT: [[@LINE-3]]:4 -> [[@LINE-2]]:11 : ((((0 - 2) - 3) - 4) - 5)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test53yyKF"
func test53() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+10]]:2 : 0
if try throwingBool(), // CHECK-NEXT: [[@LINE]]:6 -> [[@LINE]]:24 : 0
try throwingBool() { // CHECK-NEXT: [[@LINE-1]]:24 -> [[@LINE+8]]:2 : (0 - 2)
try throwingFn() // CHECK-NEXT: [[@LINE-1]]:25 -> [[@LINE+7]]:2 : ((0 - 2) - 3)
} else { // CHECK-NEXT: [[@LINE-2]]:26 -> [[@LINE]]:4 : 1
try throwingFn() // CHECK-NEXT: [[@LINE-2]]:21 -> [[@LINE-1]]:4 : (1 - 4)
} // CHECK-NEXT: [[@LINE-2]]:4 -> [[@LINE+4]]:2 : (((0 - 2) - 3) - 4)
// CHECK-NEXT: [[@LINE-3]]:10 -> [[@LINE-1]]:4 : (((0 - 1) - 2) - 3)
// CHECK-NEXT: [[@LINE-3]]:21 -> [[@LINE-2]]:4 : ((((0 - 1) - 2) - 3) - 5)
// CHECK-NEXT: [[@LINE-3]]:4 -> [[@LINE+1]]:2 : ((((0 - 2) - 3) - 4) - 5)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test54SiSgyF"
func test54()-> Int? { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+7]]:2 : 0
if let x = try? throwingFn(),
let y = try? throwingFn() { // CHECK-NEXT: [[@LINE]]:33 -> [[@LINE+2]]:4 : 1
x + y // FIXME: This region is redundant, and not really accurate since we have implicit returns (rdar://118653218)
} else { // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+3]]:2 : 0
try? throwingFn() // CHECK-NEXT: [[@LINE-1]]:10 -> [[@LINE+1]]:4 : (0 - 1)
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : 0
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test55yyKF"
func test55() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+5]]:2 : 0
while try throwingBool() { // CHECK-NEXT: [[@LINE]]:9 -> [[@LINE]]:27 : (0 + 1)
// CHECK-NEXT: [[@LINE-1]]:27 -> [[@LINE+3]]:2 : (0 - 2)
// CHECK-NEXT: [[@LINE-2]]:28 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : (0 - 2)
} // CHECK-NEXT: }
// FIXME: The second condition ought to get a region too (rdar://118649481)
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test56yyKF"
func test56() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+6]]:2 : 0
while try throwingBool(), // CHECK-NEXT: [[@LINE]]:9 -> [[@LINE]]:27 : (0 + 1)
try throwingBool() { // CHECK-NEXT: [[@LINE-1]]:27 -> [[@LINE+4]]:2 : (0 - 2)
// CHECK-NEXT: [[@LINE-1]]:27 -> [[@LINE+3]]:2 : ((0 - 2) - 3)
// CHECK-NEXT: [[@LINE-2]]:28 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : ((0 - 2) - 3)
} // CHECK-NEXT: }
// FIXME: We ought to be giving both conditions a region here...
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test57yyF"
func test57() { // CHECK-NEXT: [[@LINE]]:15 -> [[@LINE+4]]:2 : 0
while let _ = try? throwingFn(),
let _ = try? throwingFn() { // CHECK-NEXT: [[@LINE]]:35 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : 0
} // CHECK-NEXT: }
// We generate the same regions for `try!` as `try`. We could handle it
// specially, but the error branches are effectively unreachable, so it
// doesn't make a difference.
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test58SiyF"
func test58() -> Int { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+3]]:2 : 0
let x = try! throwingFn() // CHECK-NEXT: [[@LINE]]:28 -> [[@LINE+1]]:11 : (0 - 1)
return x
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test59SiyKF"
func test59() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+5]]:2 : 0
guard try throwingBool() else { // CHECK-NEXT: [[@LINE]]:27 -> [[@LINE+3]]:11 : (0 - 2)
return 1 // CHECK-NEXT: [[@LINE-1]]:33 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:11 : ((0 - 1) - 2)
return 0
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test60SiyKF"
func test60() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+7]]:2 : 0
switch try throwingBool() { // CHECK-NEXT: [[@LINE]]:10 -> [[@LINE]]:28 : 0
case true: // CHECK-NEXT: [[@LINE-1]]:28 -> [[@LINE+5]]:2 : (0 - 1)
return 0 // CHECK-NEXT: [[@LINE-1]]:3 -> [[@LINE]]:13 : 2
case false: // CHECK-NEXT: [[@LINE]]:3 -> [[@LINE+1]]:13 : 3
return 1
}
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test61SiyKF"
func test61() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+7]]:2 : 0
switch try throwingBool() { // CHECK-NEXT: [[@LINE]]:10 -> [[@LINE]]:28 : 0
case true: // CHECK-NEXT: [[@LINE-1]]:28 -> [[@LINE+5]]:2 : (0 - 1)
0 // CHECK-NEXT: [[@LINE-1]]:3 -> [[@LINE]]:6 : 2
case false: // CHECK-NEXT: [[@LINE]]:3 -> [[@LINE+1]]:6 : 3
1 // FIXME: This next region shouldn't be needed, we should know it's unrechabale (rdar://118653218).
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : (2 + 3)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test62SiyKF"
func test62() throws -> Int { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+8]]:2 : 0
let x = switch try throwingBool() { // CHECK-NEXT: [[@LINE]]:18 -> [[@LINE]]:36 : 0
case true: // CHECK-NEXT: [[@LINE-1]]:36 -> [[@LINE+5]]:11 : (0 - 1)
0 // CHECK-NEXT: [[@LINE-1]]:3 -> [[@LINE]]:6 : 2
case false: // CHECK-NEXT: [[@LINE]]:3 -> [[@LINE+1]]:6 : 3
1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:11 : (2 + 3)
return x
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test63yyKF"
func test63() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+4]]:2 : 0
for _ in [try throwingFn()] { // CHECK-NEXT: [[@LINE]]:29 -> [[@LINE+3]]:2 : (0 - 2)
// CHECK-NEXT: [[@LINE-1]]:31 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : (0 - 2)
} // CHECK-NEXT: }
// FIXME: We don't currently assign a separate region for the where clause, but
// we ought to (rdar://118653191).
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test64yyKF"
func test64() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+5]]:2 : 0
for _ in [0]
where try throwingBool() { // CHECK-NEXT: [[@LINE]]:27 -> [[@LINE+3]]:2 : (0 - 2)
// CHECK-NEXT: [[@LINE-1]]:28 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: [[@LINE]]:4 -> [[@LINE+1]]:2 : (0 - 2)
} // CHECK-NEXT: }
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors6test65yyKF"
func test65() throws { // CHECK-NEXT: [[@LINE]]:22 -> [[@LINE+5]]:2 : 0
repeat { // CHECK-NEXT: [[@LINE]]:10 -> [[@LINE+2]]:4 : 1
// CHECK-NEXT: [[@LINE+1]]:4 -> [[@LINE+3]]:2 : 0
} while try throwingBool() // CHECK-NEXT: [[@LINE]]:11 -> [[@LINE]]:29 : 1
// CHECK-NEXT: [[@LINE-1]]:29 -> [[@LINE+1]]:2 : (0 - 2)
} // CHECK-NEXT: }
struct TestInit {
// CHECK-LABEL: sil_coverage_map {{.*}}// coverage_errors.TestInit.init() -> coverage_errors.TestInit
init() { // CHECK-NEXT: [[@LINE]]:10 -> [[@LINE+5]]:4 : 0
@@ -411,3 +826,32 @@ struct TestInit {
} // CHECK-NEXT: [[@LINE]]:6 -> [[@LINE+1]]:4 : 1
} // CHECK-NEXT: }
}
struct TestProp {
let a = try? throwingFn()
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors8TestPropV1aSiSgvpfi"
// CHECK-NEXT: [[@LINE-2]]:11 -> [[@LINE-2]]:28 : 0
// CHECK-NEXT: }
let b = try? (throwingFn(), 0)
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors8TestPropV1bSi_SitSgvpfi"
// CHECK-NEXT: [[@LINE-2]]:11 -> [[@LINE-2]]:33 : 0
// CHECK-NEXT: [[@LINE-3]]:29 -> [[@LINE-3]]:33 : (0 - 1)
// CHECK-NEXT: }
let c = try? (throwingFn(), .random() ? 0 : 1)
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors8TestPropV1cSi_SitSgvpfi"
// CHECK-NEXT: [[@LINE-2]]:11 -> [[@LINE-2]]:49 : 0
// CHECK-NEXT: [[@LINE-3]]:29 -> [[@LINE-3]]:49 : (0 - 1)
// CHECK-NEXT: [[@LINE-4]]:43 -> [[@LINE-4]]:44 : 2
// CHECK-NEXT: [[@LINE-5]]:47 -> [[@LINE-5]]:48 : ((0 - 1) - 2)
// CHECK-NEXT: }
let d = (try? (throwingFn(), .random() ? 0 : 1), 0)
// CHECK-LABEL: sil_coverage_map {{.*}} "$s15coverage_errors8TestPropV1dSi_SitSg_Sitvpfi"
// CHECK-NEXT: [[@LINE-2]]:11 -> [[@LINE-2]]:54 : 0
// CHECK-NEXT: [[@LINE-3]]:30 -> [[@LINE-3]]:50 : (0 - 1)
// CHECK-NEXT: [[@LINE-4]]:44 -> [[@LINE-4]]:45 : 2
// CHECK-NEXT: [[@LINE-5]]:48 -> [[@LINE-5]]:49 : ((0 - 1) - 2)
// CHECK-NEXT: }
}