1 // RUN: %clang_cc1 -std=c++20 -Wunsafe-buffer-usage -fsafe-buffer-usage-suggestions -verify %s
7 void local_assign_both_span() {
9 int* p
= new int[10]; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' to 'std::span' to propagate bounds information between them}}
10 tmp
= p
[4]; // expected-note{{used in buffer access here}}
12 int* q
= new int[10]; // expected-warning{{'q' is an unsafe pointer used for buffer access}} expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'p' to 'std::span' to propagate bounds information between them}}
13 tmp
= q
[4]; // expected-note{{used in buffer access here}}
18 void local_assign_rhs_span() {
21 int* q
= new int[10]; // expected-warning{{'q' is an unsafe pointer used for buffer access}}
22 tmp
= q
[4]; // expected-note{{used in buffer access here}}
23 p
= q
; // FIXME: we do not fix `p = q` here as the `.data()` fix-it is not generally correct
26 void local_assign_no_span() {
33 void local_assign_lhs_span() {
35 int* p
= new int[10]; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' to 'std::span' to propagate bounds information between them}}
36 tmp
= p
[4]; // expected-note{{used in buffer access here}}
42 void lhs_span_multi_assign() {
46 int *d
= c
; // expected-warning{{'d' is an unsafe pointer used for buffer access}} expected-note{{change type of 'd' to 'std::span' to preserve bounds information, and change 'c', 'b', and 'a' to 'std::span' to propagate bounds information between them}}
47 int tmp
= d
[2]; // expected-note{{used in buffer access here}}
52 int *y
; // expected-warning{{'y' is an unsafe pointer used for buffer access}}
53 y
[5] = 10; // expected-note{{used in buffer access here}}
55 x
= y
; // FIXME: we do not fix `x = y` here as the `.data()` fix-it is not generally correct
60 int *p
= q
; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' and 'r' to 'std::span' to propagate bounds information between them}}
61 p
[5] = 10; // expected-note{{used in buffer access here}}
62 int *r
= q
; // expected-warning{{'r' is an unsafe pointer used for buffer access}} expected-note{{change type of 'r' to 'std::span' to preserve bounds information, and change 'p' and 'q' to 'std::span' to propagate bounds information between them}}
63 r
[10] = 5; // expected-note{{used in buffer access here}}
68 int *p
= q
; // expected-warning{{'p' is an unsafe pointer used for buffer access}}
69 p
[5] = 10; // expected-note{{used in buffer access here}}
70 int *r
= q
; // FIXME: we do not fix `int *r = q` here as the `.data()` fix-it is not generally correct
73 void test_grouping() {
76 int *y
= new int[10]; // expected-warning{{'y' is an unsafe pointer used for buffer access}}
77 tmp
= y
[5]; // expected-note{{used in buffer access here}}
80 x
= y
; // FIXME: we do not fix `x = y` here as the `.data()` fix-it is not generally correct
85 void test_grouping1() {
87 int *y
= new int[10]; // expected-warning{{'y' is an unsafe pointer used for buffer access}}
88 tmp
= y
[5]; // expected-note{{used in buffer access here}}
90 x
= y
; // FIXME: we do not fix `x = y` here as the `.data()` fix-it is not generally correct
92 int *w
= new int[10]; // expected-warning{{'w' is an unsafe pointer used for buffer access}}
93 tmp
= w
[5]; // expected-note{{used in buffer access here}}
95 z
= w
; // FIXME: we do not fix `z = w` here as the `.data()` fix-it is not generally correct
100 int *p
= new int[4]; // expected-warning{{'p' is an unsafe pointer used for buffer access}}
102 int tmp
= p
[9]; // expected-note{{used in buffer access here}}
104 q
= r
; // FIXME: we do not fix `q = r` here as the `.data()` fix-it is not generally correct
109 int *p
= new int[4]; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'r' and 'q' to 'std::span' to propagate bounds information between them}}
111 int tmp
= p
[9]; // expected-note{{used in buffer access here}}
112 int *q
; // expected-warning{{'q' is an unsafe pointer used for buffer access}} expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'p' and 'r' to 'std::span' to propagate bounds information between them}}
114 tmp
= q
[9]; // expected-note{{used in buffer access here}}
118 int *r
= new int[7]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
120 p
= r
; // FIXME: we do not fix `p = r` here as the `.data()` fix-it is not generally correct
121 int tmp
= r
[9]; // expected-note{{used in buffer access here}}
122 int *q
; // expected-warning{{'q' is an unsafe pointer used for buffer access}}
123 q
= r
; // FIXME: we do not fix `q = r` here as the `.data()` fix-it is not generally correct
124 tmp
= q
[9]; // expected-note{{used in buffer access here}}
129 int *p
= new int[5]; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' and 'r' to 'std::span' to propagate bounds information between them}}
132 int tmp
= p
[8]; // expected-note{{used in buffer access here}}
139 int *q
= new int[4]; // expected-warning{{'q' is an unsafe pointer used for buffer access}}
140 p
= q
; // FIXME: we do not fix `p = q` here as the `.data()` fix-it is not generally correct
141 int tmp
= q
[8]; // expected-note{{used in buffer access here}}
147 int *p
= new int[5]; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' and 'r' to 'std::span' to propagate bounds information between them}}
148 int *q
= new int[4]; // expected-warning{{'q' is an unsafe pointer used for buffer access}} expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'p' and 'r' to 'std::span' to propagate bounds information between them}}
150 int tmp
= p
[8]; // expected-note{{used in buffer access here}}
152 tmp
= q
[8]; // expected-note{{used in buffer access here}}
157 int *p
= new int[5]; // expected-warning{{'p' is an unsafe pointer used for buffer access}}
159 q
= p
; // FIXME: we do not fix `q = p` here as the `.data()` fix-it is not generally correct
160 int tmp
= p
[8]; // expected-note{{used in buffer access here}}
167 int *q
= new int[4]; // expected-warning{{'q' is an unsafe pointer used for buffer access}} //expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'r' and 'p' to 'std::span' to propagate bounds information between them}}
169 int tmp
= q
[8]; // expected-note{{used in buffer access here}}
176 int *p
; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' and 'r' to 'std::span' to propagate bounds information between them}}
178 int tmp
= p
[9]; // expected-note{{used in buffer access here}}
183 int *local
; // expected-warning{{'local' is an unsafe pointer used for buffer access}}
185 local
++; // expected-note{{used in pointer arithmetic here}}
187 (local
= ptr
) += 5; // expected-warning{{unsafe pointer arithmetic}}
190 void check_rhs_fix() {
191 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}} // expected-note{{change type of 'r' to 'std::span' to preserve bounds information, and change 'x' to 'std::span' to propagate bounds information between them}}
193 r
[7] = 9; // expected-note{{used in buffer access here}}
197 void check_rhs_nofix() {
198 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
199 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
200 r
[7] = 9; // expected-note{{used in buffer access here}}
202 x
++; // expected-note{{used in pointer arithmetic here}}
205 void check_rhs_nofix_order() {
206 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
207 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
208 x
++; // expected-note{{used in pointer arithmetic here}}
209 r
[7] = 9; // expected-note{{used in buffer access here}}
213 void check_rhs_nofix_order1() {
214 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
215 r
[7] = 9; // expected-note{{used in buffer access here}}
216 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
217 x
++; // expected-note{{used in pointer arithmetic here}}
221 void check_rhs_nofix_order2() {
222 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
223 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
224 r
[7] = 9; // expected-note{{used in buffer access here}}
225 x
++; // expected-note{{used in pointer arithmetic here}}
229 void check_rhs_nofix_order3() {
230 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
231 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
233 r
[7] = 9; // expected-note{{used in buffer access here}}
234 x
++; // expected-note{{used in pointer arithmetic here}}
237 void check_rhs_nofix_order4() {
238 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
239 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
240 r
[7] = 9; // expected-note{{used in buffer access here}}
242 x
++; // expected-note{{used in pointer arithmetic here}}
245 void no_unhandled_lhs() {
246 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}} // expected-note{{change type of 'r' to 'std::span' to preserve bounds information, and change 'x' to 'std::span' to propagate bounds information between them}}
247 r
[7] = 9; // expected-note{{used in buffer access here}}
252 const std::type_info
unhandled_lhs() {
253 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
254 r
[7] = 9; // expected-note{{used in buffer access here}}
260 const std::type_info
unhandled_rhs() {
261 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
262 r
[7] = 9; // expected-note{{used in buffer access here}}
268 void test_negative_index() {
269 int *x
= new int[4]; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
270 int *p
; // expected-warning{{'p' is an unsafe pointer used for buffer access}}
271 p
= &x
[1]; // expected-note{{used in buffer access here}}
272 p
[-1] = 9; // expected-note{{used in buffer access here}}
275 void test_unfixable() {
276 int *r
= new int[8]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
277 int *x
; // expected-warning{{'x' is an unsafe pointer used for buffer access}}
278 x
[7] = 9; // expected-note{{used in buffer access here}}
280 r
++; // expected-note{{used in pointer arithmetic here}}
283 void test_cyclic_deps() {
284 int *r
= new int[10]; // expected-warning{{'r' is an unsafe pointer used for buffer access}} expected-note{{change type of 'r' to 'std::span' to preserve bounds information, and change 'p' and 'q' to 'std::span' to propagate bounds information between them}}
289 r
[3] = 9; // expected-note{{used in buffer access here}}
293 void test_cyclic_deps_a() {
294 int *r
= new int[10]; // expected-warning{{'r' is an unsafe pointer used for buffer access}}
297 int *p
; // expected-warning{{'p' is an unsafe pointer used for buffer access}}
299 r
[3] = 9; // expected-note{{used in buffer access here}}
301 p
++; // expected-note{{used in pointer arithmetic here}}
304 void test_cyclic_deps1() {
305 int *r
= new int[10];
308 int *p
; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' and 'r' to 'std::span' to propagate bounds information between them}}
310 p
[3] = 9; // expected-note{{used in buffer access here}}
314 void test_cyclic_deps2() {
315 int *r
= new int[10];
316 int *q
; // expected-warning{{'q' is an unsafe pointer used for buffer access}} expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'r' and 'p' to 'std::span' to propagate bounds information between them}}
320 q
[3] = 9; // expected-note{{used in buffer access here}}
324 void test_cyclic_deps3() {
325 int *r
= new int[10];
326 int *q
; // expected-warning{{'q' is an unsafe pointer used for buffer access}} expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'r' and 'p' to 'std::span' to propagate bounds information between them}}
328 int *p
; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'q' and 'r' to 'std::span' to propagate bounds information between them}}
330 q
[3] = 9; // expected-note{{used in buffer access here}}
331 p
[4] = 7; // expected-note{{used in buffer access here}}
335 void test_cyclic_deps4() {
336 int *r
= new int[10]; // expected-warning{{'r' is an unsafe pointer used for buffer access}} expected-note{{change type of 'r' to 'std::span' to preserve bounds information, and change 'p' and 'q' to 'std::span' to propagate bounds information between them}}
337 int *q
; // expected-warning{{'q' is an unsafe pointer used for buffer access}} expected-note{{change type of 'q' to 'std::span' to preserve bounds information, and change 'r' and 'p' to 'std::span' to propagate bounds information between them}}
339 int *p
; // expected-warning{{'p' is an unsafe pointer used for buffer access}} expected-note{{change type of 'p' to 'std::span' to preserve bounds information, and change 'r' and 'q' to 'std::span' to propagate bounds information between them}}
341 q
[3] = 9; // expected-note{{used in buffer access here}}
342 p
[4] = 7; // expected-note{{used in buffer access here}}
343 r
[1] = 5; // expected-note{{used in buffer access here}}