[Heikki Kultala] This patch contains the ABI changes for the TCE target.
[clang.git] / test / Analysis / array-struct.c
blobdf9e9786fff3b64c61fd36e65489934b2220f962
1 // RUN: %clang_cc1 -analyze -analyzer-checker=core.experimental.CastToStruct -analyzer-check-objc-mem -analyzer-store=basic -analyzer-constraints=basic -verify %s
2 // RUN: %clang_cc1 -analyze -analyzer-checker=core.experimental.CastToStruct -analyzer-check-objc-mem -analyzer-store=basic -analyzer-constraints=range -verify %s
3 // RUN: %clang_cc1 -analyze -analyzer-checker=core.experimental.CastToStruct -analyzer-check-objc-mem -analyzer-store=region -analyzer-constraints=basic -verify %s
4 // RUN: %clang_cc1 -analyze -analyzer-checker=core.experimental.CastToStruct -analyzer-check-objc-mem -analyzer-store=region -analyzer-constraints=range -verify %s
6 struct s {
7 int data;
8 int data_array[10];
9 };
11 typedef struct {
12 int data;
13 } STYPE;
15 void g(char *p);
16 void g1(struct s* p);
18 // Array to pointer conversion. Array in the struct field.
19 void f(void) {
20 int a[10];
21 int (*p)[10];
22 p = &a;
23 (*p)[3] = 1;
25 struct s d;
26 struct s *q;
27 q = &d;
28 q->data = 3;
29 d.data_array[9] = 17;
32 // StringLiteral in lvalue context and pointer to array type.
33 // p: ElementRegion, q: StringRegion
34 void f2() {
35 char *p = "/usr/local";
36 char (*q)[4];
37 q = &"abc";
40 // Typedef'ed struct definition.
41 void f3() {
42 STYPE s;
45 // Initialize array with InitExprList.
46 void f4() {
47 int a[] = { 1, 2, 3};
48 int b[3] = { 1, 2 };
49 struct s c[] = {{1,{1}}};
52 // Struct variable in lvalue context.
53 // Assign UnknownVal to the whole struct.
54 void f5() {
55 struct s data;
56 g1(&data);
59 // AllocaRegion test.
60 void f6() {
61 char *p;
62 p = __builtin_alloca(10);
63 g(p);
64 char c = *p;
65 p[1] = 'a';
66 // Test if RegionStore::EvalBinOp converts the alloca region to element
67 // region.
68 p += 2;
71 struct s2;
73 void g2(struct s2 *p);
75 // Incomplete struct pointer used as function argument.
76 void f7() {
77 struct s2 *p = __builtin_alloca(10);
78 g2(p);
81 // sizeof() is unsigned while -1 is signed in array index.
82 void f8() {
83 int a[10];
84 a[sizeof(a)/sizeof(int) - 1] = 1; // no-warning
87 // Initialization of struct array elements.
88 void f9() {
89 struct s a[10];
92 // Initializing array with string literal.
93 void f10() {
94 char a1[4] = "abc";
95 char a3[6] = "abc";
98 // Retrieve the default value of element/field region.
99 void f11() {
100 struct s a;
101 g1(&a);
102 if (a.data == 0) // no-warning
103 a.data = 1;
106 // Convert unsigned offset to signed when creating ElementRegion from
107 // SymbolicRegion.
108 void f12(int *list) {
109 unsigned i = 0;
110 list[i] = 1;
113 struct s1 {
114 struct s2 {
115 int d;
116 } e;
119 // The binding of a.e.d should not be removed. Test recursive subregion map
120 // building: a->e, e->d. Only then 'a' could be added to live region roots.
121 void f13(double timeout) {
122 struct s1 a;
123 a.e.d = (int) timeout;
124 if (a.e.d == 10)
125 a.e.d = 4;
128 struct s3 {
129 int a[2];
132 static struct s3 opt;
134 // Test if the embedded array is retrieved correctly.
135 void f14() {
136 struct s3 my_opt = opt;
139 void bar(int*);
141 // Test if the array is correctly invalidated.
142 void f15() {
143 int a[10];
144 bar(a);
145 if (a[1]) // no-warning
146 (void)1;
149 struct s3 p[1];
151 // Code from postgresql.
152 // Current cast logic of region store mistakenly leaves the final result region
153 // an ElementRegion of type 'char'. Then load a nonloc::SymbolVal from it and
154 // assigns to 'a'.
155 void f16(struct s3 *p) {
156 struct s3 a = *((struct s3*) ((char*) &p[0])); // expected-warning{{Casting a non-structure type to a structure type and accessing a field can lead to memory access errors or data corruption.}}
159 void inv(struct s1 *);
161 // Invalidate the struct field.
162 void f17() {
163 struct s1 t;
164 int x;
165 inv(&t);
166 if (t.e.d)
167 x = 1;
170 void read(char*);
172 void f18() {
173 char *q;
174 char *p = (char *) __builtin_alloca(10);
175 read(p);
176 q = p;
177 q++;
178 if (*q) { // no-warning