From 076fecad0db4fb76524af6785b146491d4060dd4 Mon Sep 17 00:00:00 2001 From: Patrick Palka Date: Sat, 13 Jun 2015 16:11:15 +0000 Subject: [PATCH] Emit -Waddress warnings for comparing address of reference against NULL gcc/c-family/ChangeLog: PR c++/65168 * c-common.c (c_common_truthvalue_conversion): Warn when converting an address of a reference to a truth value. gcc/cp/ChangeLog: PR c++/65168 * typeck.c (cp_build_binary_op): Warn when comparing an address of a reference against NULL. gcc/testsuite/ChangeLog: PR c++/65168 g++.dg/warn/Walways-true-3.C: New test. From-SVN: r224455 --- gcc/c-family/ChangeLog | 6 +++ gcc/c-family/c-common.c | 14 +++++++ gcc/cp/ChangeLog | 6 +++ gcc/cp/typeck.c | 34 ++++++++++++++++ gcc/testsuite/ChangeLog | 5 +++ gcc/testsuite/g++.dg/warn/Walways-true-3.C | 46 ++++++++++++++++++++++ 6 files changed, 111 insertions(+) create mode 100644 gcc/testsuite/g++.dg/warn/Walways-true-3.C diff --git a/gcc/c-family/ChangeLog b/gcc/c-family/ChangeLog index a2324a49b54..80c3e48e13d 100644 --- a/gcc/c-family/ChangeLog +++ b/gcc/c-family/ChangeLog @@ -1,3 +1,9 @@ +2015-06-13 Patrick Palka + + PR c++/65168 + * c-common.c (c_common_truthvalue_conversion): Warn when + converting an address of a reference to a truth value. + 2015-06-08 Andrew MacLeod * array-notation-common.c : Adjust include files. diff --git a/gcc/c-family/c-common.c b/gcc/c-family/c-common.c index 5b76567735a..b1af682cf62 100644 --- a/gcc/c-family/c-common.c +++ b/gcc/c-family/c-common.c @@ -4973,6 +4973,20 @@ c_common_truthvalue_conversion (location_t location, tree expr) tree totype = TREE_TYPE (expr); tree fromtype = TREE_TYPE (TREE_OPERAND (expr, 0)); + if (POINTER_TYPE_P (totype) + && TREE_CODE (fromtype) == REFERENCE_TYPE) + { + tree inner = expr; + STRIP_NOPS (inner); + + if (DECL_P (inner)) + warning_at (location, + OPT_Waddress, + "the compiler can assume that the address of " + "%qD will always evaluate to %", + inner); + } + /* Don't cancel the effect of a CONVERT_EXPR from a REFERENCE_TYPE, since that affects how `default_conversion' will behave. */ if (TREE_CODE (totype) == REFERENCE_TYPE diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index b18a893a2ca..c091617f960 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,9 @@ +2015-06-13 Patrick Palka + + PR c++/65168 + * typeck.c (cp_build_binary_op): Warn when comparing an address + of a reference against NULL. + 2015-06-12 Jason Merrill PR c++/65719 diff --git a/gcc/cp/typeck.c b/gcc/cp/typeck.c index 5b09b73bafa..7716c215425 100644 --- a/gcc/cp/typeck.c +++ b/gcc/cp/typeck.c @@ -4430,6 +4430,23 @@ cp_build_binary_op (location_t location, warning (OPT_Waddress, "the address of %qD will never be NULL", TREE_OPERAND (op0, 0)); } + + if (CONVERT_EXPR_P (op0) + && TREE_CODE (TREE_TYPE (TREE_OPERAND (op0, 0))) + == REFERENCE_TYPE) + { + tree inner_op0 = op0; + STRIP_NOPS (inner_op0); + + if ((complain & tf_warning) + && c_inhibit_evaluation_warnings == 0 + && !TREE_NO_WARNING (op0) + && DECL_P (inner_op0)) + warning_at (location, OPT_Waddress, + "the compiler can assume that the address of " + "%qD will never be NULL", + inner_op0); + } } else if (((code1 == POINTER_TYPE || TYPE_PTRDATAMEM_P (type1)) && null_ptr_cst_p (op0)) @@ -4452,6 +4469,23 @@ cp_build_binary_op (location_t location, warning (OPT_Waddress, "the address of %qD will never be NULL", TREE_OPERAND (op1, 0)); } + + if (CONVERT_EXPR_P (op1) + && TREE_CODE (TREE_TYPE (TREE_OPERAND (op1, 0))) + == REFERENCE_TYPE) + { + tree inner_op1 = op1; + STRIP_NOPS (inner_op1); + + if ((complain & tf_warning) + && c_inhibit_evaluation_warnings == 0 + && !TREE_NO_WARNING (op1) + && DECL_P (inner_op1)) + warning_at (location, OPT_Waddress, + "the compiler can assume that the address of " + "%qD will never be NULL", + inner_op1); + } } else if ((code0 == POINTER_TYPE && code1 == POINTER_TYPE) || (TYPE_PTRDATAMEM_P (type0) && TYPE_PTRDATAMEM_P (type1))) diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 35822f36c76..b9b96e7e1b3 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2015-06-13 Patrick Palka + + PR c++/65168 + g++.dg/warn/Walways-true-3.C: New test. + 2015-06-13 Tom de Vries * gcc.dg/parloops-exit-first-loop-alt-4.c: New test. diff --git a/gcc/testsuite/g++.dg/warn/Walways-true-3.C b/gcc/testsuite/g++.dg/warn/Walways-true-3.C new file mode 100644 index 00000000000..d6e9df4a6b9 --- /dev/null +++ b/gcc/testsuite/g++.dg/warn/Walways-true-3.C @@ -0,0 +1,46 @@ +// PR c++/65168 +// { dg-options "-Waddress" } + +void foo (void); + +int d; +int &c = d; + +void +bar (int &a) +{ + int &b = a; + + if ((int *)&a) // { dg-warning "address of" } + foo (); + + if (&b) // { dg-warning "address of" } + foo (); + + if (!&c) // { dg-warning "address of" } + foo (); + + if (!&(int &)(int &)a) // { dg-warning "address of" } + foo (); + + if (&a == 0) // { dg-warning "never be NULL" } + foo (); + + if (&b != 0) // { dg-warning "never be NULL" } + foo (); + + if (0 == &(int &)(int &)c) // { dg-warning "never be NULL" } + foo (); + + if (&a != (int *)0) // { dg-warning "never be NULL" } + foo (); +} + +bool +bar_1 (int &a) +{ + if (d == 5) + return &a; // { dg-warning "address of" } + else + return !&(int &)(int &)a; // { dg-warning "address of" } +} -- 2.30.2