aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorNick Clifton <nickc@redhat.com>2014-04-03 13:02:27 +0000
committerNick Clifton <nickc@gcc.gnu.org>2014-04-03 13:02:27 +0000
commit0886676007c494d1a74efb0512d31f36171f3b0c (patch)
tree700a658b58e7c59384e9c221d8a9bc7ce1964b64 /gcc
parent5bed50e827ee7d43a3bd52fd7480fa1b33e25fdc (diff)
downloadgcc-0886676007c494d1a74efb0512d31f36171f3b0c.zip
gcc-0886676007c494d1a74efb0512d31f36171f3b0c.tar.gz
gcc-0886676007c494d1a74efb0512d31f36171f3b0c.tar.bz2
rl78-expand.md (movqi): Handle (SUBREG (SYMBOL_REF)) properly.
* config/rl78/rl78-expand.md (movqi): Handle (SUBREG (SYMBOL_REF)) properly. From-SVN: r209055
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog5
-rw-r--r--gcc/config/rl78/rl78-expand.md17
2 files changed, 16 insertions, 6 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 20447da..5d7eef5 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,8 @@
+2014-04-03 Nick Clifton <nickc@redhat.com>
+
+ * config/rl78/rl78-expand.md (movqi): Handle (SUBREG (SYMBOL_REF))
+ properly.
+
2014-04-03 Martin Jambor <mjambor@suse.cz>
* ipa-cp.c (ipcp_verify_propagated_values): Also dump symtab and
diff --git a/gcc/config/rl78/rl78-expand.md b/gcc/config/rl78/rl78-expand.md
index f794d7c..f61e444 100644
--- a/gcc/config/rl78/rl78-expand.md
+++ b/gcc/config/rl78/rl78-expand.md
@@ -30,18 +30,23 @@
if (rl78_far_p (operands[0]) && rl78_far_p (operands[1]))
operands[1] = copy_to_mode_reg (QImode, operands[1]);
- /* FIXME: Not sure how GCC can generate (SUBREG (SYMBOL_REF)),
- but it does. Since this makes no sense, reject it here. */
+ /* GCC can generate (SUBREG (SYMBOL_REF)) when it has to store a symbol
+ into a bitfield, or a packed ordinary field. We can handle this
+ provided that the destination is a register. If not, then load the
+ source into a register first. */
if (GET_CODE (operands[1]) == SUBREG
- && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF)
- FAIL;
+ && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
+ && ! REG_P (operands[0]))
+ operands[1] = copy_to_mode_reg (QImode, operands[1]);
+
/* Similarly for (SUBREG (CONST (PLUS (SYMBOL_REF)))).
cf. g++.dg/abi/packed.C. */
if (GET_CODE (operands[1]) == SUBREG
&& GET_CODE (XEXP (operands[1], 0)) == CONST
&& GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == PLUS
- && GET_CODE (XEXP (XEXP (XEXP (operands[1], 0), 0), 0)) == SYMBOL_REF)
- FAIL;
+ && GET_CODE (XEXP (XEXP (XEXP (operands[1], 0), 0), 0)) == SYMBOL_REF
+ && ! REG_P (operands[0]))
+ operands[1] = copy_to_mode_reg (QImode, operands[1]);
if (CONST_INT_P (operands[1]) && ! IN_RANGE (INTVAL (operands[1]), (-1 << 8) + 1, (1 << 8) - 1))
FAIL;