1// RUN: %clang_analyze_cc1 -analyzer-config eagerly-assume=false %s -analyzer-checker=osx.cocoa.RetainCount,deadcode.DeadStores,core -analyzer-output=plist -analyzer-config deadcode.DeadStores:ShowFixIts=true -o %t.plist
2// RUN: %normalize_plist <%t.plist | diff -ub %S/Inputs/expected-plists/plist-output.m.plist -
3
4void test_null_init(void) {
5  int *p = 0;
6  *p = 0xDEADBEEF;
7}
8
9void test_null_assign(void) {
10  int *p;
11  p = 0;
12  *p = 0xDEADBEEF;
13}
14
15void test_null_assign_transitive(void) {
16  int *p;
17  p = 0;
18  int *q = p;
19  *q = 0xDEADBEEF;
20}
21
22void test_null_cond(int *p) {
23  if (!p) {
24    *p = 0xDEADBEEF;
25  }
26}
27
28void test_null_cond_transitive(int *q) {
29  if (!q) {
30    int *p = q;
31    *p = 0xDEADBEEF;
32  }
33}
34
35void test_null_field(void) {
36  struct s { int *p; } x;
37  x.p = 0;
38  *(x.p) = 0xDEADBEEF;
39}
40
41void test_assumptions(int a, int b)
42{
43  if (a == 0) {
44    return;
45  }
46  if (b != 0) {
47    return;
48  }
49  int *p = 0;
50  *p = 0xDEADBEEF;
51}
52
53int *bar_cond_assign();
54int test_cond_assign() {
55  int *p;
56  if (p = bar_cond_assign())
57    return 1;
58  return *p;
59}
60
61// The following previously crashed when generating extensive diagnostics.
62// <rdar://problem/10797980>
63@interface RDar10797980_help
64@property (readonly) int x;
65@end
66
67@interface RDar10797980 {
68  RDar10797980_help *y;
69}
70- (void) test;
71@end
72
73@implementation RDar10797980
74- (void) test {
75  if (y.x == 1) {
76    int *p = 0;
77    *p = 0xDEADBEEF; // expected-warning {{deference}}
78  }
79}
80
81// The original source for the above Radar contains another problem:
82// if the end-of-path node is an implicit statement, it may not have a valid
83// source location. <rdar://problem/12446776>
84- (void)test2 {
85  if (bar_cond_assign()) {
86    id foo = [[RDar10797980 alloc] init]; // leak
87  }
88  (void)y; // first statement after the 'if' is an implicit 'self' DeclRefExpr
89}
90
91@end
92
93// Test that loops are documented in the path.
94void rdar12280665() {
95  for (unsigned i = 0; i < 2; ++i) {
96	  if (i == 1) {
97		  int *p = 0;
98		  *p = 0xDEADBEEF; // expected-warning {{dereference}}
99	  }
100  }
101}
102
103// Test for a "loop executed 0 times" diagnostic.
104int *radar12322528_bar();
105
106void radar12322528_for(int x) {
107  int *p = 0;
108  for (unsigned i = 0; i < x; ++i) {
109    p = radar12322528_bar();
110  }
111  *p = 0xDEADBEEF;
112}
113
114void radar12322528_while(int x) {
115  int *p = 0;
116  unsigned i = 0;
117  for ( ; i < x ; ) {
118    ++i;
119    p = radar12322528_bar();
120  }
121  *p = 0xDEADBEEF;
122}
123
124void radar12322528_foo_2() {
125  int *p = 0;
126  for (unsigned i = 0; i < 2; ++i) {
127    if (i == 1)
128      break;
129  }
130  *p = 0xDEADBEEF;
131}
132
133void test_loop_diagnostics() {
134  int *p = 0;
135  for (int i = 0; i < 2; ++i) { p = 0; }
136  *p = 1;
137}
138
139void test_loop_diagnostics_2() {
140  int *p = 0;
141  for (int i = 0; i < 2; ) {
142    ++i;
143    p = 0;
144  }
145  *p = 1;
146}
147
148void test_loop_diagnostics_3() {
149  int *p = 0;
150  int i = 0;
151  while (i < 2) {
152    ++i;
153    p = 0;
154  }
155  *p = 1;
156}
157
158void test_loop_fast_enumeration(id arr) {
159  int x;
160  for (id obj in arr) {
161    x = 1;
162  }
163  x += 1;
164}
165
166@interface RDar12114812 { char *p; }
167@end
168
169@implementation RDar12114812
170- (void)test {
171  p = 0;
172  *p = 1;
173}
174@end
175
176// Test diagnostics for initialization of structs.
177void RDar13295437_f(void *i) __attribute__((__nonnull__));
178
179struct  RDar13295437_S { int *i; };
180
181int  RDar13295437() {
182  struct RDar13295437_S s = {0};
183  struct RDar13295437_S *sp = &s;
184  RDar13295437_f(sp->i);
185}
186
187@interface Foo
188- (int *) returnsPointer;
189@end
190
191int testFoo(Foo *x) {
192  if (x)
193    return 1;
194  return *[x returnsPointer];
195}
196
197