[cfe-commits] r66387 - in /cfe/trunk: include/clang/Basic/DiagnosticSemaKinds.def lib/Sema/SemaExpr.cpp test/Sema/exprs.c
Chris Lattner
sabre at nondot.org
Sun Mar 8 12:39:53 PDT 2009
Author: lattner
Date: Sun Mar 8 14:39:53 2009
New Revision: 66387
URL: http://llvm.org/viewvc/llvm-project?rev=66387&view=rev
Log:
implement PR3753, warning about comparisons with a string literal.
Modified:
cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.def
cfe/trunk/lib/Sema/SemaExpr.cpp
cfe/trunk/test/Sema/exprs.c
Modified: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.def
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.def?rev=66387&r1=66386&r2=66387&view=diff
==============================================================================
--- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.def (original)
+++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.def Sun Mar 8 14:39:53 2009
@@ -1344,10 +1344,12 @@
"reference to stack memory associated with local variable %0 returned")
-// CHECK: for non-floating point, expressions of the form x == x or x != x
+// for non-floating point, expressions of the form x == x or x != x
// should result in a warning, since these always evaluate to a constant.
-DIAG(warn_selfcomparison,WARNING,
- "self-comparison always results in a constant value.")
+DIAG(warn_selfcomparison, WARNING,
+ "self-comparison always results in a constant value")
+DIAG(warn_stringcompare, WARNING,
+ "comparison against a string literal is undefined (use strcmp?)")
// Blocks
Modified: cfe/trunk/lib/Sema/SemaExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=66387&r1=66386&r2=66387&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Sun Mar 8 14:39:53 2009
@@ -3155,18 +3155,35 @@
QualType lType = lex->getType();
QualType rType = rex->getType();
- // For non-floating point types, check for self-comparisons of the form
- // x == x, x != x, x < x, etc. These always evaluate to a constant, and
- // often indicate logic errors in the program.
if (!lType->isFloatingType()) {
- if (DeclRefExpr* DRL = dyn_cast<DeclRefExpr>(lex->IgnoreParens()))
- if (DeclRefExpr* DRR = dyn_cast<DeclRefExpr>(rex->IgnoreParens()))
+ // For non-floating point types, check for self-comparisons of the form
+ // x == x, x != x, x < x, etc. These always evaluate to a constant, and
+ // often indicate logic errors in the program.
+ Expr *LHSStripped = lex->IgnoreParens();
+ Expr *RHSStripped = rex->IgnoreParens();
+ if (DeclRefExpr* DRL = dyn_cast<DeclRefExpr>(LHSStripped))
+ if (DeclRefExpr* DRR = dyn_cast<DeclRefExpr>(RHSStripped))
if (DRL->getDecl() == DRR->getDecl())
Diag(Loc, diag::warn_selfcomparison);
+
+ if (isa<CastExpr>(LHSStripped))
+ LHSStripped = LHSStripped->IgnoreParenCasts();
+ if (isa<CastExpr>(RHSStripped))
+ RHSStripped = RHSStripped->IgnoreParenCasts();
+
+ // Warn about comparisons against a string constant (unless the other
+ // operand is null), the user probably wants strcmp.
+ if ((isa<StringLiteral>(LHSStripped) || isa<ObjCEncodeExpr>(LHSStripped)) &&
+ !RHSStripped->isNullPointerConstant(Context))
+ Diag(Loc, diag::warn_stringcompare) << lex->getSourceRange();
+ else if ((isa<StringLiteral>(RHSStripped) ||
+ isa<ObjCEncodeExpr>(RHSStripped)) &&
+ !LHSStripped->isNullPointerConstant(Context))
+ Diag(Loc, diag::warn_stringcompare) << rex->getSourceRange();
}
// The result of comparisons is 'bool' in C++, 'int' in C.
- QualType ResultTy = getLangOptions().CPlusPlus? Context.BoolTy : Context.IntTy;
+ QualType ResultTy = getLangOptions().CPlusPlus? Context.BoolTy :Context.IntTy;
if (isRelational) {
if (lType->isRealType() && rType->isRealType())
@@ -3174,7 +3191,7 @@
} else {
// Check for comparisons of floating point operands using != and ==.
if (lType->isFloatingType()) {
- assert (rType->isFloatingType());
+ assert(rType->isFloatingType());
CheckFloatComparison(Loc,lex,rex);
}
Modified: cfe/trunk/test/Sema/exprs.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/exprs.c?rev=66387&r1=66386&r2=66387&view=diff
==============================================================================
--- cfe/trunk/test/Sema/exprs.c (original)
+++ cfe/trunk/test/Sema/exprs.c Sun Mar 8 14:39:53 2009
@@ -72,7 +72,12 @@
#define MYMAX(A,B) __extension__ ({ __typeof__(A) __a = (A); __typeof__(B) __b = (B); __a < __b ? __b : __a; })
struct mystruct {int A; };
-void foo(struct mystruct P, float F) {
+void test11(struct mystruct P, float F) {
MYMAX(P, F); // expected-error {{invalid operands to binary expression ('typeof(P)' (aka 'struct mystruct') and 'typeof(F)' (aka 'float'))}}
}
+// PR3753
+int test12(const char *X) {
+ return X == "foo"; // expected-warning {{comparison against a string literal is undefined}}
+}
+
More information about the cfe-commits
mailing list