summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--clang/Sema/SemaDecl.cpp10
-rw-r--r--clang/Sema/SemaExpr.cpp33
-rw-r--r--clang/Sema/SemaStmt.cpp9
-rw-r--r--clang/test/Sema/assign-null.c10
4 files changed, 31 insertions, 31 deletions
diff --git a/clang/Sema/SemaDecl.cpp b/clang/Sema/SemaDecl.cpp
index e50fe1101af..8ecbd7cb525 100644
--- a/clang/Sema/SemaDecl.cpp
+++ b/clang/Sema/SemaDecl.cpp
@@ -391,13 +391,9 @@ bool Sema::CheckSingleInitializer(Expr *&Init, bool isStatic,
Init->getSourceRange());
return true;
case PointerFromInt:
- // check for null pointer constant (C99 6.3.2.3p3)
- if (!Init->isNullPointerConstant(Context)) {
- Diag(loc, diag::ext_typecheck_assign_pointer_int,
- DeclType.getAsString(), rhsType.getAsString(),
- Init->getSourceRange());
- return true;
- }
+ Diag(loc, diag::ext_typecheck_assign_pointer_int,
+ DeclType.getAsString(), rhsType.getAsString(),
+ Init->getSourceRange());
break;
case IntFromPointer:
Diag(loc, diag::ext_typecheck_assign_pointer_int,
diff --git a/clang/Sema/SemaExpr.cpp b/clang/Sema/SemaExpr.cpp
index 2cea607343e..14302aab082 100644
--- a/clang/Sema/SemaExpr.cpp
+++ b/clang/Sema/SemaExpr.cpp
@@ -613,12 +613,9 @@ ActOnCallExpr(ExprTy *fn, SourceLocation LParenLoc,
case Compatible:
break;
case PointerFromInt:
- // check for null pointer constant (C99 6.3.2.3p3)
- if (!argExpr->isNullPointerConstant(Context)) {
- Diag(l, diag::ext_typecheck_passing_pointer_int,
- lhsType.getAsString(), rhsType.getAsString(),
- Fn->getSourceRange(), argExpr->getSourceRange());
- }
+ Diag(l, diag::ext_typecheck_passing_pointer_int,
+ lhsType.getAsString(), rhsType.getAsString(),
+ Fn->getSourceRange(), argExpr->getSourceRange());
break;
case IntFromPointer:
Diag(l, diag::ext_typecheck_passing_pointer_int,
@@ -1125,6 +1122,12 @@ Sema::CheckAssignmentConstraints(QualType lhsType, QualType rhsType) {
Sema::AssignmentCheckResult
Sema::CheckSingleAssignmentConstraints(QualType lhsType, Expr *&rExpr) {
+ // C99 6.5.16.1p1: the left operand is a pointer and the right is
+ // a null pointer constant.
+ if (lhsType->isPointerType() && rExpr->isNullPointerConstant(Context)) {
+ promoteExprToType(rExpr, lhsType);
+ return Compatible;
+ }
// This check seems unnatural, however it is necessary to ensure the proper
// conversion of functions/arrays. If the conversion were done for all
// DeclExpr's (created by ActOnIdentifierExpr), it would mess up the unary
@@ -1412,12 +1415,9 @@ inline QualType Sema::CheckAssignmentOperands( // C99 6.5.16.1
hadError = true;
break;
case PointerFromInt:
- // check for null pointer constant (C99 6.3.2.3p3)
- if (compoundType.isNull() && !rex->isNullPointerConstant(Context)) {
- Diag(loc, diag::ext_typecheck_assign_pointer_int,
- lhsType.getAsString(), rhsType.getAsString(),
- lex->getSourceRange(), rex->getSourceRange());
- }
+ Diag(loc, diag::ext_typecheck_assign_pointer_int,
+ lhsType.getAsString(), rhsType.getAsString(),
+ lex->getSourceRange(), rex->getSourceRange());
break;
case IntFromPointer:
Diag(loc, diag::ext_typecheck_assign_pointer_int,
@@ -2067,12 +2067,9 @@ bool Sema::CheckMessageArgumentTypes(Expr **Args, unsigned NumArgs,
case Compatible:
break;
case PointerFromInt:
- // check for null pointer constant (C99 6.3.2.3p3)
- if (!argExpr->isNullPointerConstant(Context)) {
- Diag(l, diag::ext_typecheck_sending_pointer_int,
- lhsType.getAsString(), rhsType.getAsString(),
- argExpr->getSourceRange());
- }
+ Diag(l, diag::ext_typecheck_sending_pointer_int,
+ lhsType.getAsString(), rhsType.getAsString(),
+ argExpr->getSourceRange());
break;
case IntFromPointer:
Diag(l, diag::ext_typecheck_sending_pointer_int,
diff --git a/clang/Sema/SemaStmt.cpp b/clang/Sema/SemaStmt.cpp
index d051f6b333e..d00501ae0a2 100644
--- a/clang/Sema/SemaStmt.cpp
+++ b/clang/Sema/SemaStmt.cpp
@@ -617,12 +617,9 @@ Sema::ActOnReturnStmt(SourceLocation ReturnLoc, ExprTy *rex) {
RetValExp->getSourceRange());
break;
case PointerFromInt:
- // check for null pointer constant (C99 6.3.2.3p3)
- if (!RetValExp->isNullPointerConstant(Context)) {
- Diag(ReturnLoc, diag::ext_typecheck_return_pointer_int,
- lhsType.getAsString(), rhsType.getAsString(),
- RetValExp->getSourceRange());
- }
+ Diag(ReturnLoc, diag::ext_typecheck_return_pointer_int,
+ lhsType.getAsString(), rhsType.getAsString(),
+ RetValExp->getSourceRange());
break;
case IntFromPointer:
Diag(ReturnLoc, diag::ext_typecheck_return_pointer_int,
diff --git a/clang/test/Sema/assign-null.c b/clang/test/Sema/assign-null.c
new file mode 100644
index 00000000000..6972d902236
--- /dev/null
+++ b/clang/test/Sema/assign-null.c
@@ -0,0 +1,10 @@
+// RUN: clang -fsyntax-only -verify %s
+
+#include <stddef.h>
+
+typedef void (*hookfunc)(void *arg);
+hookfunc hook;
+
+void clear_hook() {
+ hook = NULL;
+}
OpenPOWER on IntegriCloud