1 // RUN: %clang_analyze_cc1 -analyzer-checker=security.PointerSub -analyzer-output=text-minimal -verify %s
7 int d
= &y
- &x
; // expected-warning{{Subtraction of two pointers that do not point into the same array is undefined behavior}}
8 d
= z
- &y
; // expected-warning{{Subtraction of two pointers that do not point into the same array is undefined behavior}}
9 d
= &x
- &x
; // no-warning (subtraction of any two identical pointers is allowed)
10 d
= (long *)&x
- (long *)&x
;
11 d
= (&x
+ 1) - &x
; // no-warning ('&x' is like a single-element array)
12 d
= &x
- (&x
+ 1); // no-warning
13 d
= (&x
+ 0) - &x
; // no-warning
14 d
= (z
+ 10) - z
; // no-warning
15 d
= (long long)&y
- (long long)&x
; // no-warning
17 d
= l
- (long long)&y
; // no-warning
20 d
= p1
- p2
; // expected-warning{{Subtraction of two pointers that do not point into the same array is undefined behavior}}
24 int a
[10], b
[10], c
; // expected-note{{Array at the left-hand side of subtraction}} \
25 // expected-note2{{Array at the right-hand side of subtraction}}
28 int d
= q
- p
; // no-warning (pointers into the same array)
31 d
= q
- p
; // expected-warning{{Subtraction of two pointers that}}
33 d
= &a
[4] - a
; // no-warning
34 d
= &a
[2] - p
; // no-warning
35 d
= &c
- p
; // expected-warning{{Subtraction of two pointers that}}
37 d
= (int *)((char *)(&a
[4]) + sizeof(int)) - &a
[4]; // no-warning (pointers into the same array data)
38 d
= (int *)((char *)(&a
[4]) + 1) - &a
[4]; // expected-warning{{Subtraction of two pointers that}}
40 long long a1
= (long long)&a
[1];
41 long long b1
= (long long)&b
[1];
46 int a
[3][4]; // expected-note{{Array at the left-hand side of subtraction}} \
47 // expected-note2{{Array at the right-hand side of subtraction}}
50 d
= &(a
[2]) - &(a
[1]);
51 d
= a
[2] - a
[1]; // expected-warning{{Subtraction of two pointers that}}
53 d
= &(a
[1][2]) - &(a
[1][0]);
54 d
= &(a
[1][2]) - &(a
[0][0]); // expected-warning{{Subtraction of two pointers that}}
56 d
= (int *)((char *)(&a
[2][2]) + sizeof(int)) - &a
[2][2]; // expected-warning{{Subtraction of two pointers that}}
57 d
= (int *)((char *)(&a
[2][2]) + 1) - &a
[2][2]; // expected-warning{{Subtraction of two pointers that}}
58 d
= (int (*)[4])((char *)&a
[2] + sizeof(int (*)[4])) - &a
[2]; // expected-warning{{Subtraction of two pointers that}}
59 d
= (int (*)[4])((char *)&a
[2] + 1) - &a
[2]; // expected-warning{{Subtraction of two pointers that}}
65 int (*p
)[m
] = a
; // p == &a[0]
68 // FIXME: This is a known problem with -Wpointer-arith (https://github.com/llvm/llvm-project/issues/28328)
69 int d
= p
- a
; // d == 1 // expected-warning{{subtraction of pointers to type 'int[m]' of zero size has undefined behavior}}
71 // FIXME: This is a known problem with -Wpointer-arith (https://github.com/llvm/llvm-project/issues/28328)
72 d
= &(a
[2]) - &(a
[1]); // expected-warning{{subtraction of pointers to type 'int[m]' of zero size has undefined behavior}}
74 d
= a
[2] - a
[1]; // expected-warning{{Subtraction of two pointers that}}
80 int c
[10]; // expected-note2{{Array at the right-hand side of subtraction}}
81 int d
[10]; // expected-note2{{Array at the left-hand side of subtraction}}
89 d
= &s
.b
- &s
.a
; // expected-warning{{Subtraction of two pointers that}}
90 d
= &s
.c
[0] - &s
.a
; // expected-warning{{Subtraction of two pointers that}}
91 d
= &s
.b
- &y
; // expected-warning{{Subtraction of two pointers that}}
92 d
= &s
.c
[3] - &s
.c
[2];
93 d
= &s
.d
[3] - &s
.c
[2]; // expected-warning{{Subtraction of two pointers that}}
94 d
= s
.d
- s
.c
; // expected-warning{{Subtraction of two pointers that}}
98 d
= &sa
[2].a
- &sa
[1].b
; // expected-warning{{Subtraction of two pointers that}}
103 char *a1
= (char *)&l
;
106 long long la1
[3] = {1}; // expected-note{{Array at the right-hand side of subtraction}}
107 long long la2
[3] = {1}; // expected-note{{Array at the left-hand side of subtraction}}
108 char *pla1
= (char *)la1
;
109 char *pla2
= (char *)la2
;
110 d
= pla1
[1] - pla1
[0];
111 d
= (long long *)&pla1
[1] - &l
; // expected-warning{{Subtraction of two pointers that}}
112 d
= &pla2
[3] - &pla1
[3]; // expected-warning{{Subtraction of two pointers that}}
117 int d
= &a
[10] - p
; // no-warning ('p' is unknown, even if it cannot point into 'a')
122 int d
= a
[n
] - a
[0]; // no-warning
125 int f9(const char *p1
) {
129 return p1
- p2
; // no-warning
132 int f10(struct S
*p1
, struct S
*p2
) {
133 return &p1
->c
[5] - &p2
->c
[5]; // no-warning
138 int b
; // expected-note{{Object at the right-hand side of subtraction}}
142 struct S1 s
; // expected-note{{Object at the left-hand side of subtraction}}
143 return (char *)&s
- (char *)&s
.b
; // expected-warning{{Subtraction of two pointers that}}
151 void init_S2(struct S2
*);
156 return s
.p1
- s
.p2
; // no-warning (pointers are unknown)