aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorRichard Kenner <kenner@gcc.gnu.org>1993-11-16 07:15:18 -0500
committerRichard Kenner <kenner@gcc.gnu.org>1993-11-16 07:15:18 -0500
commite560f22692e361d8618cb35958535b98480b58c0 (patch)
treeeaf2d3a487d7480988666b36050d08655010f548 /gcc
parente63a24c8a1ba7f92d1b1512d372575605e07daca (diff)
downloadgcc-e560f22692e361d8618cb35958535b98480b58c0.zip
gcc-e560f22692e361d8618cb35958535b98480b58c0.tar.gz
gcc-e560f22692e361d8618cb35958535b98480b58c0.tar.bz2
(EXTRA_CONSTRAINT): New macro.
(SECONDARY_{INPUT,OUTPUT}_RELOAD_CLASS): Disallow unaligned into float regs. From-SVN: r6108
Diffstat (limited to 'gcc')
-rw-r--r--gcc/config/alpha/alpha.h22
1 files changed, 19 insertions, 3 deletions
diff --git a/gcc/config/alpha/alpha.h b/gcc/config/alpha/alpha.h
index 4fc9e2d..54c41f1 100644
--- a/gcc/config/alpha/alpha.h
+++ b/gcc/config/alpha/alpha.h
@@ -501,6 +501,15 @@ enum reg_class { NO_REGS, GENERAL_REGS, FLOAT_REGS, ALL_REGS,
&& zap_mask (CONST_DOUBLE_HIGH (VALUE))) \
: 0)
+/* Optional extra constraints for this machine.
+
+ For the Alpha, `Q' means that this is a memory operand but not a
+ reference to an unaligned location. */
+
+#define EXTRA_CONSTRAINT(OP, C) \
+ ((C) == 'Q' ? GET_CODE (OP) == MEM && GET_CODE (XEXP (OP, 0)) != AND \
+ : 0)
+
/* Given an rtx X being reloaded into a reg required to be
in class CLASS, return the class of reg to actually use.
In general this is just CLASS; but on some machines
@@ -516,7 +525,8 @@ enum reg_class { NO_REGS, GENERAL_REGS, FLOAT_REGS, ALL_REGS,
/* Loading and storing HImode or QImode values to and from memory
usually requires a scratch register. The exceptions are loading
- QImode and HImode from an aligned address to a general register. */
+ QImode and HImode from an aligned address to a general register.
+ We also cannot load an unaligned address into an FP register. */
#define SECONDARY_INPUT_RELOAD_CLASS(CLASS,MODE,IN) \
(((GET_CODE (IN) == MEM \
@@ -529,7 +539,10 @@ enum reg_class { NO_REGS, GENERAL_REGS, FLOAT_REGS, ALL_REGS,
&& ((MODE) == SImode || (MODE) == HImode || (MODE) == QImode)) \
|| (((MODE) == QImode || (MODE) == HImode) \
&& unaligned_memory_operand (IN, MODE)))) \
- ? GENERAL_REGS : NO_REGS)
+ ? GENERAL_REGS \
+ : ((CLASS) == FLOAT_REGS && GET_CODE (IN) == MEM \
+ && GET_CODE (XEXP (IN, 0)) == AND) ? GENERAL_REGS \
+ : NO_REGS)
#define SECONDARY_OUTPUT_RELOAD_CLASS(CLASS,MODE,OUT) \
(((GET_CODE (OUT) == MEM \
@@ -540,7 +553,10 @@ enum reg_class { NO_REGS, GENERAL_REGS, FLOAT_REGS, ALL_REGS,
&& REGNO (SUBREG_REG (OUT)) >= FIRST_PSEUDO_REGISTER)))) \
&& (((MODE) == HImode || (MODE) == QImode \
|| ((MODE) == SImode && (CLASS) == FLOAT_REGS)))) \
- ? GENERAL_REGS : NO_REGS)
+ ? GENERAL_REGS \
+ : ((CLASS) == FLOAT_REGS && GET_CODE (OUT) == MEM \
+ && GET_CODE (XEXP (OUT, 0)) == AND) ? GENERAL_REGS \
+ : NO_REGS)
/* If we are copying between general and FP registers, we need a memory
location. */