1// REQUIRES: asserts
2// RUN: %clang_cc1 -x objective-c -emit-llvm -triple x86_64-apple-macosx10.10.0 -fblocks -fobjc-arc -fsanitize=nullability-arg,nullability-assign,nullability-return -w %s -o - | FileCheck %s
3// RUN: %clang_cc1 -x objective-c++ -emit-llvm -triple x86_64-apple-macosx10.10.0 -fblocks -fobjc-arc -fsanitize=nullability-arg,nullability-assign,nullability-return -w %s -o - | FileCheck %s
4
5// CHECK: [[NONNULL_RV_LOC1:@.*]] = private unnamed_addr global {{.*}} i32 100, i32 6
6// CHECK: [[NONNULL_ARG_LOC:@.*]] = private unnamed_addr global {{.*}} i32 204, i32 15 {{.*}} i32 190, i32 23
7// CHECK: [[NONNULL_ASSIGN1_LOC:@.*]] = private unnamed_addr global {{.*}} i32 305, i32 9
8// CHECK: [[NONNULL_ASSIGN2_LOC:@.*]] = private unnamed_addr global {{.*}} i32 405, i32 10
9// CHECK: [[NONNULL_ASSIGN3_LOC:@.*]] = private unnamed_addr global {{.*}} i32 506, i32 10
10// CHECK: [[NONNULL_INIT1_LOC:@.*]] = private unnamed_addr global {{.*}} i32 604, i32 25
11// CHECK: [[NONNULL_INIT2_LOC1:@.*]] = private unnamed_addr global {{.*}} i32 707, i32 26
12// CHECK: [[NONNULL_INIT2_LOC2:@.*]] = private unnamed_addr global {{.*}} i32 707, i32 29
13// CHECK: [[NONNULL_RV_LOC2:@.*]] = private unnamed_addr global {{.*}} i32 800, i32 6
14
15#define NULL ((void *)0)
16#define INULL ((int *)NULL)
17#define INNULL ((int *_Nonnull)NULL)
18
19// CHECK-LABEL: define{{.*}} i32* @{{.*}}nonnull_retval1
20#line 100
21int *_Nonnull nonnull_retval1(int *p) {
22  // CHECK: [[ICMP:%.*]] = icmp ne i32* {{.*}}, null, !nosanitize
23  // CHECK: br i1 [[ICMP]], {{.*}}, !nosanitize
24  // CHECK: call void @__ubsan_handle_nullability_return{{.*}}[[NONNULL_RV_LOC1]]
25  return p;
26  // CHECK: ret i32*
27}
28
29#line 190
30void nonnull_arg(int *_Nonnull p) {}
31
32// CHECK-LABEL: define{{.*}} void @{{.*}}call_func_with_nonnull_arg
33#line 200
34void call_func_with_nonnull_arg(int *_Nonnull p) {
35  // CHECK: [[ICMP:%.*]] = icmp ne i32* {{.*}}, null, !nosanitize
36  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
37  // CHECK: call void @__ubsan_handle_nullability_arg{{.*}}[[NONNULL_ARG_LOC]]
38  nonnull_arg(p);
39}
40
41// CHECK-LABEL: define{{.*}} void @{{.*}}nonnull_assign1
42#line 300
43void nonnull_assign1(int *p) {
44  // CHECK: [[ICMP:%.*]] = icmp ne i32* {{.*}}, null, !nosanitize
45  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
46  // CHECK: call void @__ubsan_handle_type_mismatch{{.*}}[[NONNULL_ASSIGN1_LOC]]
47  int *_Nonnull local;
48  local = p;
49}
50
51// CHECK-LABEL: define{{.*}} void @{{.*}}nonnull_assign2
52#line 400
53void nonnull_assign2(int *p) {
54  // CHECK: [[ICMP:%.*]] = icmp ne i32* %{{.*}}, null, !nosanitize
55  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
56  // CHECK: call void @__ubsan_handle_type_mismatch{{.*}}[[NONNULL_ASSIGN2_LOC]]
57  int *_Nonnull arr[1];
58  arr[0] = p;
59}
60
61struct S1 {
62  int *_Nonnull mptr;
63};
64
65// CHECK-LABEL: define{{.*}} void @{{.*}}nonnull_assign3
66#line 500
67void nonnull_assign3(int *p) {
68  // CHECK: [[ICMP:%.*]] = icmp ne i32* %{{.*}}, null, !nosanitize
69  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
70  // CHECK: call void @__ubsan_handle_type_mismatch{{.*}}[[NONNULL_ASSIGN3_LOC]]
71  // CHECK-NOT: call void @__ubsan_handle_type_mismatch
72  struct S1 s;
73  s.mptr = p;
74}
75
76// CHECK-LABEL: define{{.*}} void @{{.*}}nonnull_init1
77#line 600
78void nonnull_init1(int *p) {
79  // CHECK: [[ICMP:%.*]] = icmp ne i32* %{{.*}}, null, !nosanitize
80  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
81  // CHECK: call void @__ubsan_handle_type_mismatch{{.*}}[[NONNULL_INIT1_LOC]]
82  int *_Nonnull local = p;
83}
84
85// CHECK-LABEL: define{{.*}} void @{{.*}}nonnull_init2
86#line 700
87void nonnull_init2(int *p) {
88  // CHECK: [[ICMP:%.*]] = icmp ne i32* %{{.*}}, null, !nosanitize
89  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
90  // CHECK: call void @__ubsan_handle_type_mismatch{{.*}}[[NONNULL_INIT2_LOC1]]
91  // CHECK: [[ICMP:%.*]] = icmp ne i32* %{{.*}}, null, !nosanitize
92  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
93  // CHECK: call void @__ubsan_handle_type_mismatch{{.*}}[[NONNULL_INIT2_LOC2]]
94  int *_Nonnull arr[] = {p, p};
95}
96
97// CHECK-LABEL: define{{.*}} i32* @{{.*}}nonnull_retval2
98#line 800
99int *_Nonnull nonnull_retval2(int *_Nonnull arg1,  //< Test this.
100                              int *_Nonnull arg2,  //< Test this.
101                              int *_Nullable arg3, //< Don't test the rest.
102                              int *arg4,
103                              int arg5, ...) {
104  // CHECK: [[ARG1CMP:%.*]] = icmp ne i32* %arg1, null, !nosanitize
105  // CHECK-NEXT: [[DO_RV_CHECK_1:%.*]] = and i1 true, [[ARG1CMP]], !nosanitize
106  // CHECK: [[ARG2CMP:%.*]] = icmp ne i32* %arg2, null, !nosanitize
107  // CHECK-NEXT: [[DO_RV_CHECK_2:%.*]] = and i1 [[DO_RV_CHECK_1]], [[ARG2CMP]]
108  // CHECK: [[SLOC_PTR:%.*]] = load i8*, i8** %return.sloc.ptr
109  // CHECK-NEXT: [[SLOC_NONNULL:%.*]] = icmp ne i8* [[SLOC_PTR]], null
110  // CHECK-NEXT: [[DO_RV_CHECK_3:%.*]] = and i1 [[SLOC_NONNULL]], [[DO_RV_CHECK_2]]
111  // CHECK: br i1 [[DO_RV_CHECK_3]], label %[[NULL:.*]], label %[[NONULL:.*]], !nosanitize
112  // CHECK: [[NULL]]:
113  // CHECK-NEXT: [[ICMP:%.*]] = icmp ne i32* {{.*}}, null, !nosanitize
114  // CHECK: br i1 [[ICMP]], {{.*}}, !nosanitize
115  // CHECK: call void @__ubsan_handle_nullability_return{{.*}}[[NONNULL_RV_LOC2]]
116  return arg1;
117  // CHECK: [[NONULL]]:
118  // CHECK-NEXT: ret i32*
119}
120
121@interface A
122+(int *_Nonnull) objc_clsmethod: (int *_Nonnull) arg1;
123-(int *_Nonnull) objc_method: (int *_Nonnull) arg1;
124@end
125
126@implementation A
127
128// CHECK-LABEL: define internal i32* @"\01+[A objc_clsmethod:]"
129+(int *_Nonnull) objc_clsmethod: (int *_Nonnull) arg1 {
130  // CHECK: [[ARG1CMP:%.*]] = icmp ne i32* %arg1, null, !nosanitize
131  // CHECK-NEXT: [[DO_RV_CHECK:%.*]] = and i1 true, [[ARG1CMP]]
132  // CHECK: [[SLOC_PTR:%.*]] = load i8*, i8** %return.sloc.ptr
133  // CHECK-NEXT: [[SLOC_NONNULL:%.*]] = icmp ne i8* [[SLOC_PTR]], null
134  // CHECK-NEXT: [[DO_RV_CHECK_2:%.*]] = and i1 [[SLOC_NONNULL]], [[DO_RV_CHECK]]
135  // CHECK: br i1 [[DO_RV_CHECK_2]], label %[[NULL:.*]], label %[[NONULL:.*]], !nosanitize
136  // CHECK: [[NULL]]:
137  // CHECK-NEXT: [[ICMP:%.*]] = icmp ne i32* {{.*}}, null, !nosanitize
138  // CHECK: br i1 [[ICMP]], {{.*}}, !nosanitize
139  // CHECK: call void @__ubsan_handle_nullability_return{{.*}}
140  return arg1;
141  // CHECK: [[NONULL]]:
142  // CHECK-NEXT: ret i32*
143}
144
145// CHECK-LABEL: define internal i32* @"\01-[A objc_method:]"
146-(int *_Nonnull) objc_method: (int *_Nonnull) arg1 {
147  // CHECK: [[ARG1CMP:%.*]] = icmp ne i32* %arg1, null, !nosanitize
148  // CHECK-NEXT: [[DO_RV_CHECK:%.*]] = and i1 true, [[ARG1CMP]]
149  // CHECK: [[SLOC_PTR:%.*]] = load i8*, i8** %return.sloc.ptr
150  // CHECK-NEXT: [[SLOC_NONNULL:%.*]] = icmp ne i8* [[SLOC_PTR]], null
151  // CHECK-NEXT: [[DO_RV_CHECK_2:%.*]] = and i1 [[SLOC_NONNULL]], [[DO_RV_CHECK]]
152  // CHECK: br i1 [[DO_RV_CHECK_2]], label %[[NULL:.*]], label %[[NONULL:.*]], !nosanitize
153  // CHECK: [[NULL]]:
154  // CHECK-NEXT: [[ICMP:%.*]] = icmp ne i32* {{.*}}, null, !nosanitize
155  // CHECK: br i1 [[ICMP]], {{.*}}, !nosanitize
156  // CHECK: call void @__ubsan_handle_nullability_return{{.*}}
157  return arg1;
158  // CHECK: [[NONULL]]:
159  // CHECK-NEXT: ret i32*
160}
161@end
162
163// CHECK-LABEL: define{{.*}} void @{{.*}}call_A
164void call_A(A *a, int *p) {
165  // CHECK: [[ICMP:%.*]] = icmp ne i32* [[P1:%.*]], null, !nosanitize
166  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
167  // CHECK: call void @__ubsan_handle_nullability_arg{{.*}} !nosanitize
168  // CHECK: call i32* {{.*}} @objc_msgSend to i32* {{.*}}({{.*}}, i32* [[P1]])
169  [a objc_method: p];
170
171  // CHECK: [[ICMP:%.*]] = icmp ne i32* [[P2:%.*]], null, !nosanitize
172  // CHECK-NEXT: br i1 [[ICMP]], {{.*}}, !nosanitize
173  // CHECK: call void @__ubsan_handle_nullability_arg{{.*}} !nosanitize
174  // CHECK: call i32* {{.*}} @objc_msgSend to i32* {{.*}}({{.*}}, i32* [[P2]])
175  [A objc_clsmethod: p];
176}
177
178void dont_crash(int *_Nonnull p, ...) {}
179
180@protocol NSObject
181- (id)init;
182@end
183@interface NSObject <NSObject> {}
184@end
185
186#pragma clang assume_nonnull begin
187
188/// Create a "NSObject * _Nonnull" instance.
189NSObject *get_nonnull_error() {
190  // Use nil for convenience. The actual object doesn't matter.
191  return (NSObject *)NULL;
192}
193
194NSObject *_Nullable no_null_return_value_diagnostic(int flag) {
195// CHECK-LABEL: define internal {{.*}}no_null_return_value_diagnostic{{i?}}_block_invoke
196// CHECK-NOT: @__ubsan_handle_nullability_return
197  NSObject *_Nullable (^foo)() = ^() {
198    if (flag) {
199      // Clang should not infer a nonnull return value for this block when this
200      // call is present.
201      return get_nonnull_error();
202    } else {
203      return (NSObject *)NULL;
204    }
205  };
206  return foo();
207}
208
209#pragma clang assume_nonnull end
210
211int main() {
212  nonnull_retval1(INULL);
213  nonnull_retval2(INNULL, INNULL, INULL, (int *_Nullable)NULL, 0, 0, 0, 0);
214  call_func_with_nonnull_arg(INNULL);
215  nonnull_assign1(INULL);
216  nonnull_assign2(INULL);
217  nonnull_assign3(INULL);
218  nonnull_init1(INULL);
219  nonnull_init2(INULL);
220  call_A((A *)NULL, INULL);
221  dont_crash(INNULL, NULL);
222  no_null_return_value_diagnostic(0);
223  no_null_return_value_diagnostic(1);
224  return 0;
225}
226