From: Jakub Jelinek <jakub@redhat.com>
To: Jason Merrill <jason@redhat.com>,
Bernd Schmidt <bschmidt@redhat.com>,
Eric Botcazou <ebotcazou@adacore.com>
Cc: gcc-patches@gcc.gnu.org
Subject: [PATCH] Fix expansion of TREE_ADDRESSABLE bitwise copies (PR c++/69851)
Date: Fri, 19 Feb 2016 14:03:00 -0000 [thread overview]
Message-ID: <20160219140330.GJ3017@tucnak.redhat.com> (raw)
Hi!
As described in the PR, in C++ we can have assignments
where both the lhs and rhs are COMPONENT_REFs with TREE_ADDRESSABLE types,
including padding, but the FIELD_DECLs are artificial fields that have
narrower bit sizes.
store_field in this case takes the path of bit-field handling (even when
it has bitpos and bitsize multiples of BITS_PER_UNIT (I think that is
necessarily true for the TREE_ADDRESSABLE types), which is incorrect,
because the rhs is expanded in that case through expand_normal, which
for a result type wider than the FIELD_DECL with forces it into a temporary.
In older GCCs that just generated inefficient code (copy the rhs into a
stack temporary, then copy that to lhs), but GCC trunk ICEs on that.
Fixed by not taking the bit-field path in that case after verifying
we'll be able to expand it properly using the normal store_expr.
Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?
2016-02-19 Jakub Jelinek <jakub@redhat.com>
PR c++/69851
* expr.c (store_field): Don't use bit-field path if exp is
COMPONENT_REF with TREE_ADDRESSABLE type, where TYPE_SIZE is
different from bitsize, but DECL_SIZE of FIELD_DECL is bitsize
and the assignment can be performed by bitwise copy. Formatting
fix.
* g++.dg/torture/pr69851.C: New test.
--- gcc/expr.c.jj 2016-02-12 00:50:55.000000000 +0100
+++ gcc/expr.c 2016-02-19 10:43:59.639162531 +0100
@@ -6643,14 +6643,24 @@ store_field (rtx target, HOST_WIDE_INT b
/* Except for initialization of full bytes from a CONSTRUCTOR, which
we will handle specially below. */
&& !(TREE_CODE (exp) == CONSTRUCTOR
- && bitsize % BITS_PER_UNIT == 0))
+ && bitsize % BITS_PER_UNIT == 0)
+ /* And except for bitwise copying of TREE_ADDRESSABLE types,
+ where the FIELD_DECL has the right bitsize, but TREE_TYPE (exp)
+ includes some extra padding. */
+ && (!TREE_ADDRESSABLE (TREE_TYPE (exp))
+ || TREE_CODE (exp) != COMPONENT_REF
+ || TREE_CODE (DECL_SIZE (TREE_OPERAND (exp, 1))) != INTEGER_CST
+ || (bitsize % BITS_PER_UNIT != 0)
+ || (bitpos % BITS_PER_UNIT != 0)
+ || (compare_tree_int (DECL_SIZE (TREE_OPERAND (exp, 1)), bitsize)
+ != 0)))
/* If we are expanding a MEM_REF of a non-BLKmode non-addressable
decl we must use bitfield operations. */
|| (bitsize >= 0
&& TREE_CODE (exp) == MEM_REF
&& TREE_CODE (TREE_OPERAND (exp, 0)) == ADDR_EXPR
&& DECL_P (TREE_OPERAND (TREE_OPERAND (exp, 0), 0))
- && !TREE_ADDRESSABLE (TREE_OPERAND (TREE_OPERAND (exp, 0),0 ))
+ && !TREE_ADDRESSABLE (TREE_OPERAND (TREE_OPERAND (exp, 0), 0))
&& DECL_MODE (TREE_OPERAND (TREE_OPERAND (exp, 0), 0)) != BLKmode))
{
rtx temp;
--- gcc/testsuite/g++.dg/torture/pr69851.C.jj 2016-02-19 10:59:22.224438830 +0100
+++ gcc/testsuite/g++.dg/torture/pr69851.C 2016-02-19 10:59:12.000000000 +0100
@@ -0,0 +1,24 @@
+// PR c++/69851
+// { dg-do compile }
+// { dg-options "-std=c++11" }
+
+template <typename T>
+struct A { T a; };
+template <unsigned long, typename...>
+struct B;
+template <unsigned long N, typename T, typename... U>
+struct B<N, T, U...> : B<1, U...>, A<T>
+{
+ B (B &) = default;
+ B (B &&x) : B(x) {}
+};
+template <unsigned long N, typename T>
+struct B<N, T> {};
+struct C { C (C &); };
+struct D {};
+
+void
+foo (B<0, C, D, int, int> a)
+{
+ B<0, C, D, int, int> b (a);
+}
Jakub
next reply other threads:[~2016-02-19 14:03 UTC|newest]
Thread overview: 14+ messages / expand[flat|nested] mbox.gz Atom feed top
2016-02-19 14:03 Jakub Jelinek [this message]
2016-02-19 18:30 ` Jason Merrill
2016-02-19 18:41 ` Jakub Jelinek
2016-02-19 19:00 ` Jason Merrill
2016-02-19 19:07 ` Jakub Jelinek
2016-02-19 19:11 ` Jason Merrill
2016-02-19 18:42 Bernd Edlinger
2016-02-19 19:04 ` Jakub Jelinek
2016-02-19 20:04 ` Bernd Edlinger
2016-02-19 20:08 ` Jakub Jelinek
2016-02-19 20:18 ` Bernd Edlinger
2016-02-19 20:45 ` Bernd Edlinger
2016-02-19 20:57 ` Jakub Jelinek
2016-02-19 20:46 ` Bernd Edlinger
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20160219140330.GJ3017@tucnak.redhat.com \
--to=jakub@redhat.com \
--cc=bschmidt@redhat.com \
--cc=ebotcazou@adacore.com \
--cc=gcc-patches@gcc.gnu.org \
--cc=jason@redhat.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).