xref: /llvm-project/llvm/test/Transforms/InstCombine/strcall-bad-sig.ll (revision 10f315dc9c96ec2413881ab55a285e35d80def88)
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2; Verify that calls to known string library functions declared with
3; incompatible signatures are handled gracefully and without aborting.
4;
5; RUN: opt < %s -passes=instcombine -S | FileCheck %s
6
7@a = constant [2 x i8] c"1\00"
8
9declare ptr @atoi(ptr)
10declare ptr @atol(ptr)
11declare ptr @atoll(ptr)
12
13define void @call_bad_ato(ptr %ps) {
14; CHECK-LABEL: @call_bad_ato(
15; CHECK-NEXT:    [[IR:%.*]] = call ptr @atoi(ptr nonnull @a)
16; CHECK-NEXT:    store ptr [[IR]], ptr [[PS:%.*]], align 8
17; CHECK-NEXT:    [[LR:%.*]] = call ptr @atol(ptr nonnull @a)
18; CHECK-NEXT:    [[PS1:%.*]] = getelementptr i8, ptr [[PS]], i64 8
19; CHECK-NEXT:    store ptr [[LR]], ptr [[PS1]], align 8
20; CHECK-NEXT:    [[LLR:%.*]] = call ptr @atol(ptr nonnull @a)
21; CHECK-NEXT:    [[PS2:%.*]] = getelementptr i8, ptr [[PS]], i64 16
22; CHECK-NEXT:    store ptr [[LLR]], ptr [[PS2]], align 8
23; CHECK-NEXT:    ret void
24;
25
26  %ir = call ptr @atoi(ptr @a)
27  store ptr %ir, ptr %ps
28
29  %lr = call ptr @atol(ptr @a)
30  %ps1 = getelementptr ptr, ptr %ps, i32 1
31  store ptr %lr, ptr %ps1
32
33  %llr = call ptr @atol(ptr @a)
34  %ps2 = getelementptr ptr, ptr %ps, i32 2
35  store ptr %llr, ptr %ps2
36
37  ret void
38}
39
40
41declare ptr @strncasecmp(ptr, ptr)
42
43define ptr @call_bad_strncasecmp() {
44; CHECK-LABEL: @call_bad_strncasecmp(
45; CHECK-NEXT:    [[CMP:%.*]] = call ptr @strncasecmp(ptr nonnull @a, ptr nonnull getelementptr inbounds nuw (i8, ptr @a, i64 1))
46; CHECK-NEXT:    ret ptr [[CMP]]
47;
48  %p1 = getelementptr [2 x i8], ptr @a, i32 0, i32 1
49  %cmp = call ptr @strncasecmp(ptr @a, ptr %p1)
50  ret ptr %cmp
51}
52
53
54declare i1 @strcoll(ptr, ptr, ptr)
55
56define i1 @call_bad_strcoll() {
57; CHECK-LABEL: @call_bad_strcoll(
58; CHECK-NEXT:    [[I:%.*]] = call i1 @strcoll(ptr nonnull @a, ptr nonnull getelementptr inbounds nuw (i8, ptr @a, i64 1), ptr nonnull @a)
59; CHECK-NEXT:    ret i1 [[I]]
60;
61  %p1 = getelementptr [2 x i8], ptr @a, i32 0, i32 1
62  %i = call i1 @strcoll(ptr @a, ptr %p1, ptr @a)
63  ret i1 %i
64}
65
66
67declare ptr @strndup(ptr)
68
69define ptr @call_bad_strndup() {
70; CHECK-LABEL: @call_bad_strndup(
71; CHECK-NEXT:    [[D:%.*]] = call ptr @strndup(ptr nonnull @a)
72; CHECK-NEXT:    ret ptr [[D]]
73;
74  %d = call ptr @strndup(ptr @a)
75  ret ptr %d
76}
77
78
79declare i1 @strtok(ptr, ptr, i1)
80
81define i1 @call_bad_strtok() {
82; CHECK-LABEL: @call_bad_strtok(
83; CHECK-NEXT:    [[RET:%.*]] = call i1 @strtok(ptr nonnull @a, ptr nonnull getelementptr inbounds nuw (i8, ptr @a, i64 1), i1 false)
84; CHECK-NEXT:    ret i1 [[RET]]
85;
86  %p1 = getelementptr [2 x i8], ptr @a, i32 0, i32 1
87  %ret = call i1 @strtok(ptr @a, ptr %p1, i1 0)
88  ret i1 %ret
89}
90
91
92
93declare i1 @strtok_r(ptr, ptr)
94
95define i1 @call_bad_strtok_r() {
96; CHECK-LABEL: @call_bad_strtok_r(
97; CHECK-NEXT:    [[RET:%.*]] = call i1 @strtok_r(ptr nonnull @a, ptr nonnull getelementptr inbounds nuw (i8, ptr @a, i64 1))
98; CHECK-NEXT:    ret i1 [[RET]]
99;
100  %p1 = getelementptr [2 x i8], ptr @a, i32 0, i32 1
101  %ret = call i1 @strtok_r(ptr @a, ptr %p1)
102  ret i1 %ret
103}
104
105
106declare i32 @strtol(ptr, ptr)
107declare i32 @strtoul(ptr, ptr)
108
109declare i64 @strtoll(ptr, ptr)
110declare i64 @strtoull(ptr, ptr)
111
112define void @call_bad_strto(ptr %psi32, ptr %psi64) {
113; CHECK-LABEL: @call_bad_strto(
114; CHECK-NEXT:    [[LR:%.*]] = call i32 @strtol(ptr nonnull @a, ptr null)
115; CHECK-NEXT:    store i32 [[LR]], ptr [[PSI32:%.*]], align 4
116; CHECK-NEXT:    [[ULR:%.*]] = call i32 @strtoul(ptr nonnull @a, ptr null)
117; CHECK-NEXT:    [[PS1:%.*]] = getelementptr i8, ptr [[PSI32]], i64 4
118; CHECK-NEXT:    store i32 [[ULR]], ptr [[PS1]], align 4
119; CHECK-NEXT:    [[LLR:%.*]] = call i64 @strtoll(ptr nonnull @a, ptr null)
120; CHECK-NEXT:    store i64 [[LLR]], ptr [[PSI64:%.*]], align 4
121; CHECK-NEXT:    [[ULLR:%.*]] = call i64 @strtoull(ptr nonnull @a, ptr null)
122; CHECK-NEXT:    [[PS3:%.*]] = getelementptr i8, ptr [[PSI64]], i64 24
123; CHECK-NEXT:    store i64 [[ULLR]], ptr [[PS3]], align 4
124; CHECK-NEXT:    ret void
125;
126
127  %lr = call i32 @strtol(ptr @a, ptr null)
128  store i32 %lr, ptr %psi32
129
130  %ulr = call i32 @strtoul(ptr @a, ptr null)
131  %ps1 = getelementptr i32, ptr %psi32, i32 1
132  store i32 %ulr, ptr %ps1
133
134  %llr = call i64 @strtoll(ptr @a, ptr null)
135  store i64 %llr, ptr %psi64
136
137  %ullr = call i64 @strtoull(ptr @a, ptr null)
138  %ps3 = getelementptr i64, ptr %psi64, i32 3
139  store i64 %ullr, ptr %ps3
140
141  ret void
142}
143
144
145declare ptr @strxfrm(ptr, ptr)
146
147define ptr @call_bad_strxfrm() {
148; CHECK-LABEL: @call_bad_strxfrm(
149; CHECK-NEXT:    [[RET:%.*]] = call ptr @strxfrm(ptr nonnull @a, ptr nonnull getelementptr inbounds nuw (i8, ptr @a, i64 1))
150; CHECK-NEXT:    ret ptr [[RET]]
151;
152  %p1 = getelementptr [2 x i8], ptr @a, i32 0, i32 1
153  %ret = call ptr @strxfrm(ptr @a, ptr %p1)
154  ret ptr %ret
155}
156