summaryrefslogtreecommitdiffstats
path: root/clang/lib/Sema/SemaChecking.cpp
diff options
context:
space:
mode:
authorErik Pilkington <erik.pilkington@gmail.com>2019-07-09 17:29:40 +0000
committerErik Pilkington <erik.pilkington@gmail.com>2019-07-09 17:29:40 +0000
commitabffae3a563d67d0a31a9687aecc4de33a4cc273 (patch)
tree42e62001dc2067d512719cc27b5f798f1fa901bf /clang/lib/Sema/SemaChecking.cpp
parent0efac296f140f9e6eac31a9f979dbd0dc0659c24 (diff)
downloadbcm5719-llvm-abffae3a563d67d0a31a9687aecc4de33a4cc273.tar.gz
bcm5719-llvm-abffae3a563d67d0a31a9687aecc4de33a4cc273.zip
[ObjC] Add a warning for implicit conversions of a constant non-boolean value to BOOL
rdar://51954400 Differential revision: https://reviews.llvm.org/D63912 llvm-svn: 365518
Diffstat (limited to 'clang/lib/Sema/SemaChecking.cpp')
-rw-r--r--clang/lib/Sema/SemaChecking.cpp28
1 files changed, 28 insertions, 0 deletions
diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp
index 7ab0f2d312a..64ee7c86ca5 100644
--- a/clang/lib/Sema/SemaChecking.cpp
+++ b/clang/lib/Sema/SemaChecking.cpp
@@ -11149,6 +11149,11 @@ static bool isSameWidthConstantConversion(Sema &S, Expr *E, QualType T,
return true;
}
+static bool isObjCSignedCharBool(Sema &S, QualType Ty) {
+ return Ty->isSpecificBuiltinType(BuiltinType::SChar) &&
+ S.getLangOpts().ObjC && S.NSAPIObj->isObjCBOOLType(Ty);
+}
+
static void
CheckImplicitConversion(Sema &S, Expr *E, QualType T, SourceLocation CC,
bool *ICContext = nullptr) {
@@ -11192,6 +11197,29 @@ CheckImplicitConversion(Sema &S, Expr *E, QualType T, SourceLocation CC,
}
}
+ // If the we're converting a constant to an ObjC BOOL on a platform where BOOL
+ // is a typedef for signed char (macOS), then that constant value has to be 1
+ // or 0.
+ if (isObjCSignedCharBool(S, T) && Source->isIntegralType(S.Context)) {
+ Expr::EvalResult Result;
+ if (E->EvaluateAsInt(Result, S.getASTContext(),
+ Expr::SE_AllowSideEffects) &&
+ Result.Val.getInt() != 1 && Result.Val.getInt() != 0) {
+ auto Builder = S.Diag(CC, diag::warn_impcast_constant_int_to_objc_bool)
+ << Result.Val.getInt().toString(10);
+ Expr *Ignored = E->IgnoreImplicit();
+ bool NeedsParens = isa<AbstractConditionalOperator>(Ignored) ||
+ isa<BinaryOperator>(Ignored) ||
+ isa<CXXOperatorCallExpr>(Ignored);
+ SourceLocation EndLoc = S.getLocForEndOfToken(E->getEndLoc());
+ if (NeedsParens)
+ Builder << FixItHint::CreateInsertion(E->getBeginLoc(), "(")
+ << FixItHint::CreateInsertion(EndLoc, ")");
+ Builder << FixItHint::CreateInsertion(EndLoc, " ? YES : NO");
+ return;
+ }
+ }
+
// Check implicit casts from Objective-C collection literals to specialized
// collection types, e.g., NSArray<NSString *> *.
if (auto *ArrayLiteral = dyn_cast<ObjCArrayLiteral>(E))
OpenPOWER on IntegriCloud