annotate gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf-warn-16.c @ 131:84e7813d76e9

gcc-8.2
author mir3636
date Thu, 25 Oct 2018 07:37:49 +0900
parents 04ced10e8804
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
111
kono
parents:
diff changeset
1 /* PR middle-end/80364 - sanitizer detects signed integer overflow
kono
parents:
diff changeset
2 in gimple-ssa-sprintf.c
kono
parents:
diff changeset
3 { dg-do compile }
kono
parents:
diff changeset
4 { dg-options "-O2 -Wall -Wformat-overflow=1 -ftrack-macro-expansion=0" }
kono
parents:
diff changeset
5 { dg-require-effective-target int32plus } */
kono
parents:
diff changeset
6
kono
parents:
diff changeset
7 typedef __SIZE_TYPE__ size_t;
kono
parents:
diff changeset
8 typedef __WCHAR_TYPE__ wchar_t;
kono
parents:
diff changeset
9
kono
parents:
diff changeset
10 void sink (void*);
kono
parents:
diff changeset
11 void* get_value (void);
kono
parents:
diff changeset
12
kono
parents:
diff changeset
13 /* Return a random width as type T. */
kono
parents:
diff changeset
14 #define W(T) *(T*)get_value ()
kono
parents:
diff changeset
15
kono
parents:
diff changeset
16 /* Return a random precision as type T. */
kono
parents:
diff changeset
17 #define P(T) *(T*)get_value ()
kono
parents:
diff changeset
18
kono
parents:
diff changeset
19 /* Return a random value as type T. */
kono
parents:
diff changeset
20 #define V(T) *(T*)get_value ()
kono
parents:
diff changeset
21
kono
parents:
diff changeset
22 extern char buf[1];
kono
parents:
diff changeset
23
kono
parents:
diff changeset
24 /* Test convenience macro. */
kono
parents:
diff changeset
25 #define T(fmt, ...) \
kono
parents:
diff changeset
26 __builtin_sprintf (buf + 1, fmt, __VA_ARGS__); \
kono
parents:
diff changeset
27 sink (buf)
kono
parents:
diff changeset
28
kono
parents:
diff changeset
29 typedef signed char schar_t;
kono
parents:
diff changeset
30 typedef unsigned char uchar_t;
kono
parents:
diff changeset
31 typedef signed short sshort_t;
kono
parents:
diff changeset
32 typedef unsigned short ushort_t;
kono
parents:
diff changeset
33 typedef signed int sint_t;
kono
parents:
diff changeset
34 typedef unsigned int uint_t;
kono
parents:
diff changeset
35 typedef signed long slong_t;
kono
parents:
diff changeset
36 typedef unsigned long ulong_t;
kono
parents:
diff changeset
37 typedef signed long long sllong_t;
kono
parents:
diff changeset
38 typedef unsigned long long ullong_t;
kono
parents:
diff changeset
39
kono
parents:
diff changeset
40 #if __SIZEOF_INT128__
kono
parents:
diff changeset
41 typedef __int128_t sint128_t;
kono
parents:
diff changeset
42 typedef __uint128_t uint128_t;
kono
parents:
diff changeset
43 #else
kono
parents:
diff changeset
44 /* When __int128_t is not available, repeat the same tests with long long.
kono
parents:
diff changeset
45 This is to avoid having to guard the tests below and to avoid making
kono
parents:
diff changeset
46 the dg-warning directives conditional. */
kono
parents:
diff changeset
47 typedef signed long long sint128_t;
kono
parents:
diff changeset
48 typedef unsigned long long uint128_t;
kono
parents:
diff changeset
49 #endif
kono
parents:
diff changeset
50
kono
parents:
diff changeset
51 const sint128_t sint128_max
kono
parents:
diff changeset
52 = (sint128_t)1 << (sizeof sint128_max * __CHAR_BIT__ - 2);
kono
parents:
diff changeset
53 const sint128_t uint128_max = (uint128_t)-1;
kono
parents:
diff changeset
54
kono
parents:
diff changeset
55 void test_width_cst (void)
kono
parents:
diff changeset
56 {
kono
parents:
diff changeset
57 T ("%*i", W (schar_t), 1); /* { dg-warning "between 1 and 128 " } */
kono
parents:
diff changeset
58 T ("%*i", W (uchar_t), 12); /* { dg-warning "between 2 and 255 " } */
kono
parents:
diff changeset
59
kono
parents:
diff changeset
60 T ("%*i", W (sshort_t), 123); /* { dg-warning "between 3 and 32768 " } */
kono
parents:
diff changeset
61 T ("%*i", W (ushort_t), 1234); /* { dg-warning "between 4 and 65535 " } */
kono
parents:
diff changeset
62
kono
parents:
diff changeset
63 T ("%*i", W (sint_t), 12345); /* { dg-warning "between 5 and 2147483648 " } */
kono
parents:
diff changeset
64 T ("%*i", W (uint_t), 123456); /* { dg-warning "between 6 and 2147483648 " } */
kono
parents:
diff changeset
65
kono
parents:
diff changeset
66 /* Exercise calls with invalid arguments (to verify there is no ICE). */
kono
parents:
diff changeset
67 T ("%*li", W (slong_t), 1234567L); /* { dg-warning "between 7 and 2147483648 " } */
kono
parents:
diff changeset
68 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
69 T ("%*li", W (ulong_t), 12345678L); /* { dg-warning "between 8 and 2147483648 " } */
kono
parents:
diff changeset
70 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
71
kono
parents:
diff changeset
72 T ("%*lli", W (sllong_t), 123456789LL); /* { dg-warning "between 9 and 2147483648 " } */
kono
parents:
diff changeset
73 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
74 T ("%*lli", W (ullong_t), 1234567890LL); /* { dg-warning "between 10 and 2147483648 " } */
kono
parents:
diff changeset
75 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
76
kono
parents:
diff changeset
77 T ("%*i", W (sint128_t), 0); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
78 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
79 T ("%*i", W (uint128_t), 1); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
80 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
81
kono
parents:
diff changeset
82 {
kono
parents:
diff changeset
83 extern sint128_t si128;
kono
parents:
diff changeset
84 if (si128 < sint128_max / 2 || sint128_max - 8 < si128)
kono
parents:
diff changeset
85 si128 = sint128_max / 2;
kono
parents:
diff changeset
86
kono
parents:
diff changeset
87 T ("%*i", si128, 0); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
88 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
89
kono
parents:
diff changeset
90 extern uint128_t ui128;
kono
parents:
diff changeset
91 if (ui128 < uint128_max / 2 || uint128_max - 8 < ui128)
kono
parents:
diff changeset
92 ui128 = uint128_max / 2;
kono
parents:
diff changeset
93
kono
parents:
diff changeset
94 T ("%*i", ui128, 0); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
95 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
96 }
kono
parents:
diff changeset
97
kono
parents:
diff changeset
98 T ("%*i", W (float), 2); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
99 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
100 T ("%*i", W (double), 3); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
101 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
102 }
kono
parents:
diff changeset
103
kono
parents:
diff changeset
104 void test_width_var (void)
kono
parents:
diff changeset
105 {
kono
parents:
diff changeset
106 T ("%*i", W (schar_t), V (schar_t)); /* { dg-warning "between 1 and 128 " } */
kono
parents:
diff changeset
107 T ("%*i", W (uchar_t), V (uchar_t)); /* { dg-warning "between 1 and 255 " } */
kono
parents:
diff changeset
108
kono
parents:
diff changeset
109 T ("%*i", W (sshort_t), V (sshort_t)); /* { dg-warning "between 1 and 32768 " } */
kono
parents:
diff changeset
110 T ("%*i", W (ushort_t), V (ushort_t)); /* { dg-warning "between 1 and 65535 " } */
kono
parents:
diff changeset
111
kono
parents:
diff changeset
112 T ("%*i", W (sint_t), V (sint_t)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
113 T ("%*i", W (uint_t), V (uint_t)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
114
kono
parents:
diff changeset
115 /* Exercise calls with invalid arguments (to verify there is no ICE). */
kono
parents:
diff changeset
116 T ("%*li", W (slong_t), V (slong_t)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
117 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
118 T ("%*li", W (ulong_t), V (ulong_t)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
119 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
120
kono
parents:
diff changeset
121 T ("%*lli", W (sllong_t), V (sllong_t)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
122 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
123 T ("%*lli", W (ullong_t), V (ullong_t)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
124 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
125
kono
parents:
diff changeset
126 T ("%*i", W (float), V (int)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
127 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
128 T ("%*i", W (double), V (int)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
129 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
130
kono
parents:
diff changeset
131 {
kono
parents:
diff changeset
132 /* Create an unsigned range with a lower bound greater than 1 and
kono
parents:
diff changeset
133 an upper bound in excess of INT_MAX and verify that the lower
kono
parents:
diff changeset
134 bound isn't used as the minimum output (since the excessive
kono
parents:
diff changeset
135 upper bound wraps around zero). It's possible to constrain
kono
parents:
diff changeset
136 the upper bound on the output more, based on the upper bound
kono
parents:
diff changeset
137 of the width here, but not worth the trouble. */
kono
parents:
diff changeset
138 extern unsigned w;
kono
parents:
diff changeset
139 if (w < 5 || (unsigned)-1 - 7 < w)
kono
parents:
diff changeset
140 w = 5;
kono
parents:
diff changeset
141
kono
parents:
diff changeset
142 T ("%*u", w, V (int)); /* { dg-warning "between 1 and 2147483648 " } */
kono
parents:
diff changeset
143 }
kono
parents:
diff changeset
144
kono
parents:
diff changeset
145 {
kono
parents:
diff changeset
146 /* Verify that enums are correctly handled (i.e., that the warning
kono
parents:
diff changeset
147 doesn't just test for TREE_CODE(type) == INTEGER_TYPE but instead
kono
parents:
diff changeset
148 uses INTEGRAL_TYPE_P() or some equivalent. */
kono
parents:
diff changeset
149 enum WidthEnum { e7 = 7, e9 = 9 };
kono
parents:
diff changeset
150 enum WidthEnum w = V (enum WidthEnum);
kono
parents:
diff changeset
151 if (w < e7 || e9 < w)
kono
parents:
diff changeset
152 w = e7;
kono
parents:
diff changeset
153
kono
parents:
diff changeset
154 T ("%*hu", w, V (int)); /* { dg-warning "between 7 and 9 " } */
kono
parents:
diff changeset
155 }
kono
parents:
diff changeset
156 }
kono
parents:
diff changeset
157
kono
parents:
diff changeset
158 void test_precision_cst (void)
kono
parents:
diff changeset
159 {
kono
parents:
diff changeset
160 T ("%.*i", P (schar_t), 1); /* { dg-warning "between 1 and 127 " } */
kono
parents:
diff changeset
161 T ("%.*i", P (uchar_t), 12); /* { dg-warning "between 2 and 255 " } */
kono
parents:
diff changeset
162
kono
parents:
diff changeset
163 T ("%.*i", P (sshort_t), 123); /* { dg-warning "between 3 and 32767 " } */
kono
parents:
diff changeset
164 T ("%.*i", P (ushort_t), 1234); /* { dg-warning "between 4 and 65535 " } */
kono
parents:
diff changeset
165
kono
parents:
diff changeset
166 T ("%.*i", P (sint_t), 12345); /* { dg-warning "between 5 and 2147483647 " } */
kono
parents:
diff changeset
167 T ("%.*i", P (uint_t), 123456); /* { dg-warning "between 6 and 2147483647 " } */
kono
parents:
diff changeset
168
kono
parents:
diff changeset
169 /* Exercise calls with invalid arguments (to verify there is no ICE). */
kono
parents:
diff changeset
170 T ("%.*li", P (slong_t), 1234567L); /* { dg-warning "between 7 and 2147483647 " } */
kono
parents:
diff changeset
171 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
172 T ("%.*li", P (ulong_t), 12345678L); /* { dg-warning "between 8 and 2147483647 " } */
kono
parents:
diff changeset
173 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
174
kono
parents:
diff changeset
175 T ("%.*lli", P (sllong_t), 123456789LL); /* { dg-warning "between 9 and 2147483647 " } */
kono
parents:
diff changeset
176 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
177 T ("%.*lli", P (ullong_t), 1234567890LL); /* { dg-warning "between 10 and 2147483647 " } */
kono
parents:
diff changeset
178 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
179
kono
parents:
diff changeset
180 T ("%.*i", P (sint128_t), 0); /* { dg-warning "up to 2147483647 " } */
kono
parents:
diff changeset
181 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
182 T ("%.*i", P (uint128_t), 1); /* { dg-warning "between 1 and 2147483647 " } */
kono
parents:
diff changeset
183 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
184
kono
parents:
diff changeset
185 {
kono
parents:
diff changeset
186 extern sint128_t si128;
kono
parents:
diff changeset
187 if (si128 < sint128_max / 2 || sint128_max - 8 < si128)
kono
parents:
diff changeset
188 si128 = sint128_max / 2;
kono
parents:
diff changeset
189
kono
parents:
diff changeset
190 T ("%.*i", si128, 0); /* { dg-warning "up to 2147483647 " } */
kono
parents:
diff changeset
191 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
192
kono
parents:
diff changeset
193 extern uint128_t ui128;
kono
parents:
diff changeset
194 if (ui128 < uint128_max / 2 || uint128_max - 8 < ui128)
kono
parents:
diff changeset
195 ui128 = uint128_max / 2;
kono
parents:
diff changeset
196
kono
parents:
diff changeset
197 T ("%.*i", ui128, 0); /* { dg-warning "up to 2147483647 " } */
kono
parents:
diff changeset
198 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
199 }
kono
parents:
diff changeset
200
kono
parents:
diff changeset
201 T ("%.*i", P (float), 0); /* { dg-warning "up to 2147483647 " } */
kono
parents:
diff changeset
202 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
203 T ("%.*i", P (double), 1); /* { dg-warning "between 1 and 2147483647 " } */
kono
parents:
diff changeset
204 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
205 }
kono
parents:
diff changeset
206
kono
parents:
diff changeset
207 void test_precision_var (void)
kono
parents:
diff changeset
208 {
kono
parents:
diff changeset
209 T ("%.*i", P (schar_t), V (schar_t)); /* { dg-warning "up to 128 " } */
kono
parents:
diff changeset
210 T ("%.*i", P (uchar_t), V (uchar_t)); /* { dg-warning "up to 255 " } */
kono
parents:
diff changeset
211
kono
parents:
diff changeset
212 T ("%.*i", P (sshort_t), V (sshort_t)); /* { dg-warning "up to 32768 " } */
kono
parents:
diff changeset
213 T ("%.*i", P (ushort_t), V (ushort_t)); /* { dg-warning "up to 65535 " } */
kono
parents:
diff changeset
214
kono
parents:
diff changeset
215 T ("%.*i", P (sint_t), V (sint_t)); /* { dg-warning "up to 2147483648 " } */
kono
parents:
diff changeset
216 T ("%.*i", P (uint_t), V (uint_t)); /* { dg-warning "up to 2147483648 " } */
kono
parents:
diff changeset
217
kono
parents:
diff changeset
218 /* Exercise calls with invalid arguments (to verify there is no ICE). */
kono
parents:
diff changeset
219 T ("%.*li", P (slong_t), V (slong_t)); /* { dg-warning "up to 2147483648 " } */
kono
parents:
diff changeset
220 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
221 T ("%.*li", P (ulong_t), V (ulong_t)); /* { dg-warning "up to 2147483648 " } */
kono
parents:
diff changeset
222 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
223
kono
parents:
diff changeset
224 T ("%.*lli", P (sllong_t), V (sllong_t)); /* { dg-warning "up to 2147483648" } */
kono
parents:
diff changeset
225 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
226 T ("%.*lli", P (ullong_t), V (ullong_t)); /* { dg-warning "up to 2147483648" } */
kono
parents:
diff changeset
227 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
228
kono
parents:
diff changeset
229 T ("%.*i", P (float), V (int)); /* { dg-warning "up to 2147483648 " } */
kono
parents:
diff changeset
230 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
231 T ("%.*i", P (double), V (int)); /* { dg-warning "up to 2147483648 " } */
kono
parents:
diff changeset
232 /* { dg-warning "expects argument of type .int." "" { target *-*-* } .-1 } */
kono
parents:
diff changeset
233
kono
parents:
diff changeset
234 {
kono
parents:
diff changeset
235 /* Similar to the corresponding width case, create an unsigned range
kono
parents:
diff changeset
236 with a lower bound greater than 1 and an upper bound in excess of
kono
parents:
diff changeset
237 INT_MAX and verify that the lower bound isn't used as the minimum
kono
parents:
diff changeset
238 output (since the excessive upper bound wraps around zero). */
kono
parents:
diff changeset
239 extern unsigned p;
kono
parents:
diff changeset
240 if (p < 7 || (unsigned)-1 - 9 < p)
kono
parents:
diff changeset
241 p = 7;
kono
parents:
diff changeset
242
kono
parents:
diff changeset
243 T ("%.*u", p, V (int)); /* { dg-warning "up to 2147483647 " } */
kono
parents:
diff changeset
244 }
kono
parents:
diff changeset
245
kono
parents:
diff changeset
246 {
kono
parents:
diff changeset
247 /* Verify that enums are correctly handled. */
kono
parents:
diff changeset
248 enum PrecEnum { e9 = 9, e17 = 17 };
kono
parents:
diff changeset
249 enum PrecEnum p = V (enum PrecEnum);
kono
parents:
diff changeset
250 if (p < e9 || e17 < p)
kono
parents:
diff changeset
251 p = e9;
kono
parents:
diff changeset
252
kono
parents:
diff changeset
253 T ("%.*u", p, V (int)); /* { dg-warning "between 9 and 17 " } */
kono
parents:
diff changeset
254 }
kono
parents:
diff changeset
255 }