diff options
author | Martin Sebor <msebor@redhat.com> | 2016-05-30 22:56:43 +0000 |
---|---|---|
committer | Martin Sebor <msebor@gcc.gnu.org> | 2016-05-30 16:56:43 -0600 |
commit | 265149a6ae5ca6548da1a6b0c9cc90a2174d36f3 (patch) | |
tree | 11899376f198d04d5907a2b09279954417a5e1f2 | |
parent | 00631022d83c44777b37f168831eb64142737cbe (diff) | |
download | gcc-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/ChangeLog | 6 | ||||
-rw-r--r-- | gcc/cp/init.c | 7 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/warn/Wplacement-new-size-3.C | 40 |
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; +} |