1 /* PR middle-end/78786 - GCC hangs/out of memory calling sprintf with large
2 precision
3 { dg-do compile }
4 { dg-require-effective-target int32plus }
5 { dg-options "-Wformat-overflow -ftrack-macro-expansion=0" } */
6
7 #define INT_MAX __INT_MAX__
8 #define INT_MIN (-INT_MAX - 1)
9
10 typedef __SIZE_TYPE__ size_t;
11
12 void sink (int, void*);
13
14 char buf [1];
15
16 #define T(n, fmt, ...) \
17 sink (__builtin_sprintf (buf + sizeof buf - n, fmt, __VA_ARGS__), buf)
18
test_integer_cst(void)19 void test_integer_cst (void)
20 {
21 T (0, "%*d", INT_MIN, 0); /* { dg-warning "writing 2147483648 bytes" } */
22 T (0, "%*d", INT_MAX, 0); /* { dg-warning "writing 2147483647 bytes" } */
23
24 T (0, "%.*d", INT_MIN, 0); /* { dg-warning "writing 1 byte" } */
25 T (0, "%.*d", INT_MAX, 0); /* { dg-warning "writing 2147483647 bytes" } */
26
27 T (0, "%*.*d", INT_MIN, INT_MIN, 0); /* { dg-warning "writing 2147483648 bytes" } */
28
29 T (0, "%*.*d", INT_MAX, INT_MAX, 0); /* { dg-warning "writing 2147483647 bytes" } */
30 }
31
test_integer_var(int i)32 void test_integer_var (int i)
33 {
34 T (0, "%*d", INT_MIN, i); /* { dg-warning "writing 2147483648 bytes" } */
35
36 /* The following writes INT_MAX digits and, when i is negative, a minus
37 sign. */
38 T (0, "%.*d", INT_MAX, i); /* { dg-warning "writing between 2147483647 and 2147483648 bytes" } */
39
40 T (0, "%.*d", INT_MIN, i); /* { dg-warning "writing between 1 and 11 bytes" } */
41
42 /* The following writes a range because of the possible minus sign. */
43 T (0, "%.*d", INT_MAX, i); /* { dg-warning "writing between 2147483647 and 2147483648 bytes" } */
44
45 T (0, "%*.*d", INT_MIN, INT_MIN, i); /* { dg-warning "writing 2147483648 bytes" } */
46
47 /* The following writes INT_MAX digits and, when i is negative, a minus
48 sign. */
49 T (0, "%*.*d", INT_MAX, INT_MAX, i); /* { dg-warning "writing between 2147483647 and 2147483648 bytes" } */
50 }
51
test_floating_a_cst(void)52 void test_floating_a_cst (void)
53 {
54 T (0, "%*a", INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
55 T (0, "%*a", INT_MAX, 0.); /* { dg-warning "writing 2147483647 bytes" } */
56
57 /* %a is poorly specified and as a result some implementations trim
58 redundant trailing zeros (e.g., Glibc) and others don't (e.g.,
59 Solaris). */
60 T (0, "%.*a", INT_MIN, 0.); /* { dg-warning "writing between 6 and 20 bytes" } */
61
62 T (0, "%.*a", INT_MAX, 0.); /* { dg-warning "writing 2147483654 bytes" } */
63
64 T (0, "%*.*a", INT_MIN, INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
65
66 T (0, "%*.*a", INT_MAX, INT_MAX, 0.); /* { dg-warning "writing 2147483654 bytes" } */
67 }
68
test_floating_a_var(double x)69 void test_floating_a_var (double x)
70 {
71 T (0, "%*a", INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
72 T (0, "%*a", INT_MAX, x); /* { dg-warning "writing 2147483647 bytes" } */
73
74 T (0, "%.*a", INT_MIN, x); /* { dg-warning "writing between 3 and 24 bytes" } */
75
76 /* Expected output is "0x0." followed by INT_MAX digits followed by
77 "p+" followed by 1 to four digits, with a byte count in the range
78 [3 + INT_MAX + 2 + 1, 3 + INT_MAX + 2 + 4]. */
79 T (0, "%.*a", INT_MAX, x); /* { dg-warning "writing between 3 and 2147483658 bytes" } */
80
81 T (0, "%*.*a", INT_MIN, INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
82
83 T (0, "%*.*a", INT_MAX, INT_MAX, x); /* { dg-warning "writing between 2147483647 and 2147483658 bytes" } */
84 }
85
test_floating_e_cst(void)86 void test_floating_e_cst (void)
87 {
88 T (0, "%*e", INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
89 T (0, "%*e", INT_MAX, 0.); /* { dg-warning "writing 2147483647 bytes" } */
90
91 T (0, "%.*e", INT_MIN, 0.); /* { dg-warning "writing 12 bytes" } */
92
93 T (0, "%.*e", INT_MAX, 0.); /* { dg-warning "writing 2147483653 bytes" } */
94
95 T (0, "%*.*e", INT_MIN, INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
96
97 T (0, "%*.*e", INT_MAX, INT_MAX, 0.); /* { dg-warning "writing 2147483653 bytes" } */
98 }
99
test_floating_e_var(double x)100 void test_floating_e_var (double x)
101 {
102 T (0, "%*e", INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
103 T (0, "%*e", INT_MAX, x); /* { dg-warning "writing 2147483647 bytes" } */
104
105 T (0, "%.*e", INT_MIN, x); /* { dg-warning "writing between 3 and 14 bytes" } */
106
107 T (0, "%.*e", INT_MAX, x); /* { dg-warning "writing between 3 and 2147483655 bytes" } */
108
109 T (0, "%*.*e", INT_MIN, INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
110
111 T (0, "%*.*e", INT_MAX, INT_MAX, x); /* { dg-warning "writing between 2147483647 and 2147483655 bytes" } */
112 }
113
test_floating_f_cst(void)114 void test_floating_f_cst (void)
115 {
116 T (0, "%*f", INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
117 T (0, "%*f", INT_MAX, 0.); /* { dg-warning "writing 2147483647 bytes" } */
118
119 T (0, "%.*f", INT_MIN, 0.); /* { dg-warning "writing 8 bytes" } */
120
121 T (0, "%.*f", INT_MAX, 0.); /* { dg-warning "writing 2147483649 bytes" } */
122
123 T (0, "%*.*f", INT_MIN, INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
124
125 T (0, "%*.*f", INT_MAX, INT_MAX, 0.); /* { dg-warning "writing 2147483649 bytes" } */
126 }
127
test_floating_f_var(double x)128 void test_floating_f_var (double x)
129 {
130 T (0, "%*f", INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
131 T (0, "%*f", INT_MAX, x); /* { dg-warning "writing 2147483647 bytes" } */
132
133 T (0, "%.*f", INT_MIN, x); /* { dg-warning "writing between 3 and 317 bytes" } */
134
135 T (0, "%.*f", INT_MAX, x); /* { dg-warning "writing between 3 and 2147483958 bytes" } */
136
137 T (0, "%*.*f", INT_MIN, INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
138
139 T (0, "%*.*f", INT_MAX, INT_MAX, x); /* { dg-warning "writing between 2147483647 and 2147483958 bytes" } */
140 }
141
test_floating_g_cst(void)142 void test_floating_g_cst (void)
143 {
144 T (0, "%*g", INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
145 T (0, "%*g", INT_MAX, 0.); /* { dg-warning "writing 2147483647 bytes" } */
146
147 T (0, "%.*g", INT_MIN, 0.); /* { dg-warning "writing 1 byte" } */
148
149 T (0, "%.*g", INT_MAX, 0.); /* { dg-warning "writing 1 byte" } */
150
151 T (0, "%*.*g", INT_MIN, INT_MIN, 0.); /* { dg-warning "writing 2147483648 bytes" } */
152
153 T (0, "%*.*g", INT_MAX, INT_MAX, 0.); /* { dg-warning "writing 2147483647 bytes" } */
154 }
155
test_floating_g(double x)156 void test_floating_g (double x)
157 {
158 T (0, "%*g", INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
159 T (0, "%*g", INT_MAX, x); /* { dg-warning "writing 2147483647 bytes" } */
160
161 T (0, "%.*g", INT_MIN, x); /* { dg-warning "writing between 1 and 13 bytes" } */
162
163 T (0, "%.*g", INT_MAX, x); /* { dg-warning "writing between 1 and 310 bytes" } */
164
165 T (0, "%*.*g", INT_MIN, INT_MIN, x); /* { dg-warning "writing 2147483648 bytes" } */
166
167 T (0, "%*.*g", INT_MAX, INT_MAX, x); /* { dg-warning "writing 2147483647 bytes" } */
168 }
169
test_string_cst(void)170 void test_string_cst (void)
171 {
172 T (0, "%*s", INT_MIN, ""); /* { dg-warning "writing 2147483648 bytes" } */
173 T (0, "%*s", INT_MAX, ""); /* { dg-warning "writing 2147483647 bytes" } */
174
175 T (0, "%.*s", INT_MIN, ""); /* { dg-warning "writing a terminating nul" } */
176
177 T (0, "%.*s", INT_MAX, ""); /* { dg-warning "writing a terminating nul" } */
178
179 T (0, "%*.*s", INT_MIN, INT_MIN, ""); /* { dg-warning "writing 2147483648 bytes" } */
180
181 T (0, "%*.*s", INT_MAX, INT_MAX, ""); /* { dg-warning "writing 2147483647 bytes" } */
182 }
183
test_string_var(const char * s)184 void test_string_var (const char *s)
185 {
186 T (0, "%*s", INT_MIN, s); /* { dg-warning "writing 2147483648 or more bytes" } */
187 T (0, "%*s", INT_MAX, s); /* { dg-warning "writing 2147483647 or more bytes" } */
188
189 T (0, "%.*s", INT_MIN, s); /* { dg-warning "writing a terminating nul" } */
190
191 T (0, "%.*s", INT_MAX, s); /* { dg-warning "writing up to 2147483647 bytes" } */
192
193 T (0, "%*.*s", INT_MIN, INT_MIN, s); /* { dg-warning "writing 2147483648 or more bytes" } */
194
195 T (0, "%*.*s", INT_MAX, INT_MAX, s); /* { dg-warning "writing 2147483647 bytes" } */
196 }
197