171 lines · plain
1// RUN: %clang_analyze_cc1 -fobjc-arc -analyzer-checker=core,nullability.NullPassedToNonnull,nullability.NullReturnedFromNonnull -DNOSYSTEMHEADERS=0 -verify %s2// RUN: %clang_analyze_cc1 -fobjc-arc -analyzer-checker=core,nullability.NullPassedToNonnull,nullability.NullReturnedFromNonnull -analyzer-config nullability:NoDiagnoseCallsToSystemHeaders=true -DNOSYSTEMHEADERS=1 -verify %s3 4#include "Inputs/system-header-simulator-for-nullability.h"5 6int getRandom();7 8typedef struct Dummy { int val; } Dummy;9 10void takesNullable(Dummy *_Nullable);11void takesNonnull(Dummy *_Nonnull);12Dummy *_Nullable returnsNullable();13 14void testBasicRules() {15 // The tracking of nullable values is turned off.16 Dummy *p = returnsNullable();17 takesNonnull(p); // no warning18 Dummy *q = 0;19 if (getRandom()) {20 takesNullable(q);21 takesNonnull(q); // expected-warning {{Null passed to a callee that requires a non-null 1st parameter}}22 }23}24 25Dummy *_Nonnull testNullReturn() {26 Dummy *p = 0;27 return p; // expected-warning {{Null returned from a function that is expected to return a non-null value}}28}29 30void onlyReportFirstPreconditionViolationOnPath() {31 Dummy *p = 0;32 takesNonnull(p); // expected-warning {{Null passed to a callee that requires a non-null 1st parameter}}33 takesNonnull(p); // No warning.34 // Passing null to nonnull is a sink. Stop the analysis.35 int i = 0;36 i = 5 / i; // no warning37 (void)i;38}39 40Dummy *_Nonnull doNotWarnWhenPreconditionIsViolatedInTopFunc(41 Dummy *_Nonnull p) {42 if (!p) {43 Dummy *ret =44 0; // avoid compiler warning (which is not generated by the analyzer)45 if (getRandom())46 return ret; // no warning47 else48 return p; // no warning49 } else {50 return p;51 }52}53 54Dummy *_Nonnull doNotWarnWhenPreconditionIsViolated(Dummy *_Nonnull p) {55 if (!p) {56 Dummy *ret =57 0; // avoid compiler warning (which is not generated by the analyzer)58 if (getRandom())59 return ret; // no warning60 else61 return p; // no warning62 } else {63 return p;64 }65}66 67void testPreconditionViolationInInlinedFunction(Dummy *p) {68 doNotWarnWhenPreconditionIsViolated(p);69}70 71void inlinedNullable(Dummy *_Nullable p) {72 if (p) return;73}74void inlinedNonnull(Dummy *_Nonnull p) {75 if (p) return;76}77void inlinedUnspecified(Dummy *p) {78 if (p) return;79}80 81Dummy *_Nonnull testDefensiveInlineChecks(Dummy * p) {82 switch (getRandom()) {83 case 1: inlinedNullable(p); break;84 case 2: inlinedNonnull(p); break;85 case 3: inlinedUnspecified(p); break;86 }87 if (getRandom())88 takesNonnull(p);89 return p;90}91 92@interface TestObject : NSObject93@end94 95TestObject *_Nonnull getNonnullTestObject();96 97void testObjCARCImplicitZeroInitialization() {98 TestObject * _Nonnull implicitlyZeroInitialized; // no-warning99 implicitlyZeroInitialized = getNonnullTestObject();100}101 102void testObjCARCExplicitZeroInitialization() {103 TestObject * _Nonnull explicitlyZeroInitialized = nil; // expected-warning {{nil assigned to a pointer which is expected to have non-null value}}104}105 106// Under ARC, returned expressions of ObjC objects types are are implicitly107// cast to _Nonnull when the functions return type is _Nonnull, so make108// sure this doesn't implicit cast doesn't suppress a legitimate warning.109TestObject * _Nonnull returnsNilObjCInstanceIndirectly() {110 TestObject *local = nil;111 return local; // expected-warning {{nil returned from a function that is expected to return a non-null value}}112}113 114TestObject * _Nonnull returnsNilObjCInstanceIndirectlyWithSupressingCast() {115 TestObject *local = nil;116 return (TestObject * _Nonnull)local; // no-warning117}118 119TestObject * _Nonnull returnsNilObjCInstanceDirectly() {120 return nil; // expected-warning {{nil returned from a function that is expected to return a non-null value}}121}122 123TestObject * _Nonnull returnsNilObjCInstanceDirectlyWithSuppressingCast() {124 return (TestObject * _Nonnull)nil; // no-warning125}126 127@interface SomeClass : NSObject128@end129 130@implementation SomeClass (MethodReturn)131- (SomeClass * _Nonnull)testReturnsNilInNonnull {132 SomeClass *local = nil;133 return local; // expected-warning {{nil returned from a method that is expected to return a non-null value}}134}135 136- (SomeClass * _Nonnull)testReturnsCastSuppressedNilInNonnull {137 SomeClass *local = nil;138 return (SomeClass * _Nonnull)local; // no-warning139}140 141- (SomeClass * _Nonnull)testReturnsNilInNonnullWhenPreconditionViolated:(SomeClass * _Nonnull) p {142 SomeClass *local = nil;143 if (!p) // Pre-condition violated here.144 return local; // no-warning145 else146 return p; // no-warning147}148@end149 150 151void callFunctionInSystemHeader() {152 NSString *s;153 s = nil;154 155 NSSystemFunctionTakingNonnull(s);156 #if !NOSYSTEMHEADERS157 // expected-warning@-2{{nil passed to a callee that requires a non-null 1st parameter}}158 #endif159}160 161void callMethodInSystemHeader() {162 NSString *s;163 s = nil;164 165 NSSystemClass *sc = [[NSSystemClass alloc] init];166 [sc takesNonnull:s];167 #if !NOSYSTEMHEADERS168 // expected-warning@-2{{nil passed to a callee that requires a non-null 1st parameter}}169 #endif170}171