aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMartin Sebor <msebor@redhat.com>2016-05-30 22:56:43 +0000
committerMartin Sebor <msebor@gcc.gnu.org>2016-05-30 16:56:43 -0600
commit265149a6ae5ca6548da1a6b0c9cc90a2174d36f3 (patch)
tree11899376f198d04d5907a2b09279954417a5e1f2
parent00631022d83c44777b37f168831eb64142737cbe (diff)
downloadgcc-265149a6ae5ca6548da1a6b0c9cc90a2174d36f3.zip
gcc-265149a6ae5ca6548da1a6b0c9cc90a2174d36f3.tar.gz
gcc-265149a6ae5ca6548da1a6b0c9cc90a2174d36f3.tar.bz2
PR c++/71306 - bogus -Wplacement-new with an array element
gcc/cp/ChangeLog: 2016-05-27 Martin Sebor <msebor@redhat.com> PR c++/71306 * init.c (warn_placement_new_too_small): Handle placement new arguments that are elements of arrays more carefully. Remove a pointless loop. gcc/testsuite/ChangeLog: 2016-05-27 Martin Sebor <msebor@redhat.com> PR c++/71306 * g++.dg/warn/Wplacement-new-size-3.C: New test. From-SVN: r236902
-rw-r--r--gcc/cp/ChangeLog6
-rw-r--r--gcc/cp/init.c7
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/g++.dg/warn/Wplacement-new-size-3.C40
4 files changed, 55 insertions, 3 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index 1e4ca0c..266ca0a 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,9 @@
+2016-05-27 Martin Sebor <msebor@redhat.com>
+
+ PR c++/71306
+ * init.c (warn_placement_new_too_small): Handle placement new arguments
+ that are elements of arrays more carefully. Remove a pointless loop.
+
2016-05-30 Jakub Jelinek <jakub@redhat.com>
PR c++/71349
diff --git a/gcc/cp/init.c b/gcc/cp/init.c
index 8e7541f..a71c21a 100644
--- a/gcc/cp/init.c
+++ b/gcc/cp/init.c
@@ -2376,7 +2376,8 @@ warn_placement_new_too_small (tree type, tree nelts, tree size, tree oper)
STRIP_NOPS (oper);
- if (TREE_CODE (oper) == ARRAY_REF)
+ if (TREE_CODE (oper) == ARRAY_REF
+ && (addr_expr || TREE_CODE (TREE_TYPE (oper)) == ARRAY_TYPE))
{
/* Similar to the offset computed above, see if the array index
is a compile-time constant. If so, and unless the offset was
@@ -2405,8 +2406,8 @@ warn_placement_new_too_small (tree type, tree nelts, tree size, tree oper)
bool compref = TREE_CODE (oper) == COMPONENT_REF;
/* Descend into a struct or union to find the member whose address
- is being used as the agument. */
- while (TREE_CODE (oper) == COMPONENT_REF)
+ is being used as the argument. */
+ if (TREE_CODE (oper) == COMPONENT_REF)
{
tree op0 = oper;
while (TREE_CODE (op0 = TREE_OPERAND (op0, 0)) == COMPONENT_REF);
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index d9ef789..dfcd446 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2016-05-27 Martin Sebor <msebor@redhat.com>
+
+ PR c++/71306
+ * g++.dg/warn/Wplacement-new-size-3.C: New test.
+
2016-05-30 Jakub Jelinek <jakub@redhat.com>
PR c++/71349
diff --git a/gcc/testsuite/g++.dg/warn/Wplacement-new-size-3.C b/gcc/testsuite/g++.dg/warn/Wplacement-new-size-3.C
new file mode 100644
index 0000000..c93e4e69
--- /dev/null
+++ b/gcc/testsuite/g++.dg/warn/Wplacement-new-size-3.C
@@ -0,0 +1,40 @@
+// PR c++/71306 - bogus -Wplacement-new with an array element
+// { dg-do compile }
+// { dg-options "-Wplacement-new" }
+
+void* operator new (__SIZE_TYPE__, void *p) { return p; }
+
+struct S64 { char c [64]; };
+
+S64 s2 [2];
+S64* ps2 [2];
+S64* ps2_2 [2][2];
+
+void* pv2 [2];
+
+void f ()
+{
+ char a [2][sizeof (S64)];
+
+ new (a) S64;
+ new (a [0]) S64;
+ new (a [1]) S64;
+
+ // Verify there is no warning with buffers of sufficient size.
+ new (&s2 [0]) S64;
+ new (&s2 [1]) S64;
+
+ // ..and no warning with pointers to buffers of unknown size.
+ new (ps2 [0]) S64;
+ new (ps2 [1]) S64;
+
+ // But a warning when using the ps2_2 array itself as opposed
+ // to the pointers it's elements might point to.
+ new (ps2_2 [0]) S64; // { dg-warning "placement new" }
+ new (ps2_2 [1]) S64; // { dg-warning "placement new" }
+
+ // ..and no warning again with pointers to buffers of unknown
+ // size.
+ new (pv2 [0]) S64;
+ new (pv2 [1]) S64;
+}