1; RUN: opt < %s -ipsccp -S | FileCheck %s
2; PR36485
3; musttail call result can\'t be replaced with a constant, unless the call
4; can be removed
5
6declare i32 @external()
7
8define i8* @start(i8 %v) {
9  %c1 = icmp eq i8 %v, 0
10  br i1 %c1, label %true, label %false
11true:
12  ; CHECK: %ca = musttail call i8* @side_effects(i8 %v)
13  ; CHECK: ret i8* %ca
14  %ca = musttail call i8* @side_effects(i8 %v)
15  ret i8* %ca
16false:
17  %c2 = icmp eq i8 %v, 1
18  br i1 %c2, label %c2_true, label %c2_false
19c2_true:
20  %ca1 = musttail call i8* @no_side_effects(i8 %v)
21  ; CHECK: ret i8* null
22  ret i8* %ca1
23c2_false:
24  ; CHECK: %ca2 = musttail call i8* @dont_zap_me(i8 %v)
25  ; CHECK: ret i8* %ca2
26  %ca2 = musttail call i8* @dont_zap_me(i8 %v)
27  ret i8* %ca2
28}
29
30define internal i8* @side_effects(i8 %v) {
31  %i1 = call i32 @external()
32
33  ; since this goes back to `start` the SCPP should be see that the return value
34  ; is always `null`.
35  ; The call can't be removed due to `external` call above, though.
36
37  ; CHECK: %ca = musttail call i8* @start(i8 %v)
38  %ca = musttail call i8* @start(i8 %v)
39
40  ; Thus the result must be returned anyway
41  ; CHECK: ret i8* %ca
42  ret i8* %ca
43}
44
45define internal i8* @no_side_effects(i8 %v) readonly nounwind {
46  ; The call to this function is removed, so the return value must be zapped
47  ; CHECK: ret i8* undef
48  ret i8* null
49}
50
51define internal i8* @dont_zap_me(i8 %v) {
52  %i1 = call i32 @external()
53
54  ; The call to this function cannot be removed due to side effects. Thus the
55  ; return value should stay as it is, and should not be zapped.
56  ; CHECK: ret i8* null
57  ret i8* null
58}
59