HP-PA 1.1 has 32 fullword registers and 32 floating point
registers. However, the floating point registers behave
differently: the left and right halves of registers are addressable
- as 32 bit registers. So, we will set things up like the 68k which
+ as 32-bit registers. So, we will set things up like the 68k which
has different fp units: define separate register sets for the 1.0
and 1.1 fp units. */
registers will generally not be allocated across a call).
Experimentation has shown slightly better results by allocating
- FP registers first.
+ FP registers first. We allocate the caller-saved registers more
+ or less in reverse order to their allocation as arguments.
FP registers are ordered so that all L registers are selected before
R registers. This works around a false dependency interlock on the
{ \
/* caller-saved fp regs. */ \
68, 70, 72, 74, 76, 78, 80, 82, \
- 84, 86, 40, 42, 44, 46, 32, 34, \
- 36, 38, \
+ 84, 86, 40, 42, 44, 46, 38, 36, \
+ 34, 32, \
69, 71, 73, 75, 77, 79, 81, 83, \
- 85, 87, 41, 43, 45, 47, 33, 35, \
- 37, 39, \
+ 85, 87, 41, 43, 45, 47, 39, 37, \
+ 35, 33, \
/* caller-saved general regs. */ \
- 19, 20, 21, 22, 23, 24, 25, 26, \
- 27, 28, 29, 31, 2, \
+ 28, 19, 20, 21, 22, 31, 27, 29, \
+ 23, 24, 25, 26, 2, \
/* callee-saved fp regs. */ \
48, 50, 52, 54, 56, 58, 60, 62, \
64, 66, \
This is ordinarily the length in words of a value of mode MODE
but can be less for certain modes in special long registers.
- On the HP-PA, ordinary registers hold 32 bits worth;
- The floating point registers are 64 bits wide. Snake fp regs are 32
- bits wide */
+ On the HP-PA, general registers are 32 bits wide. The floating
+ point registers are 64 bits wide. Snake fp regs are treated as
+ 32 bits wide since the left and right parts are independently
+ accessible. */
#define HARD_REGNO_NREGS(REGNO, MODE) \
(FP_REGNO_P (REGNO) \
- ? (!TARGET_PA_11 ? 1 : (GET_MODE_SIZE (MODE) + 4 - 1) / 4) \
- : ((GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD))
+ ? (!TARGET_PA_11 \
+ ? COMPLEX_MODE_P (MODE) ? 2 : 1 \
+ : (GET_MODE_SIZE (MODE) + 4 - 1) / 4) \
+ : (GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD)
+
+/* There are no instructions that use DImode in PA 1.0, so we only
+ allow it in PA 1.1 and later. */
+#define VALID_FP_MODE_P(MODE) \
+ ((MODE) == SFmode || (MODE) == DFmode \
+ || (MODE) == SCmode || (MODE) == DCmode \
+ || (MODE) == SImode || (TARGET_PA_11 && (MODE) == DImode))
/* Value is 1 if hard register REGNO can hold a value of machine-mode MODE.
- On the HP-PA, the cpu registers can hold any mode. We
- force this to be an even register is it cannot hold the full mode. */
+
+ On the HP-PA, the cpu registers can hold any mode that fits in 32 bits.
+ For the 64-bit modes, we choose a set of non-overlapping general registers
+ that includes the incoming arguments and the return value. We specify a
+ set with no overlaps so that we don't have to specify that the destination
+ register is an early clobber in patterns using this mode. Except for the
+ return value, the starting registers are odd. For 128 and 256 bit modes,
+ we similarly specify non-overlapping sets of cpu registers. However,
+ there aren't any patterns defined for modes larger than 64 bits at the
+ moment.
+
+ We limit the modes allowed in the floating point registers to the
+ set of modes used in the machine definition. In addition, we allow
+ the complex modes SCmode and DCmode. The real and imaginary parts
+ of complex modes are allocated to separate registers. This might
+ allow patterns to be defined in the future to operate on these values.
+
+ The PA 2.0 architecture specifies that quad-precision floating-point
+ values should start on an even floating point register. Thus, we
+ choose non-overlapping sets of registers starting on even register
+ boundaries for large modes. However, there is currently no support
+ in the machine definition for modes larger than 64 bits. TFmode is
+ supported under HP-UX using libcalls. Since TFmode values are passed
+ by reference, they never need to be loaded into the floating-point
+ registers. */
#define HARD_REGNO_MODE_OK(REGNO, MODE) \
((REGNO) == 0 ? (MODE) == CCmode || (MODE) == CCFPmode \
- /* On 1.0 machines, don't allow wide non-fp modes in fp regs. */ \
: !TARGET_PA_11 && FP_REGNO_P (REGNO) \
- ? GET_MODE_SIZE (MODE) <= 4 || GET_MODE_CLASS (MODE) == MODE_FLOAT \
+ ? (VALID_FP_MODE_P (MODE) \
+ && (GET_MODE_SIZE (MODE) <= 8 \
+ || (GET_MODE_SIZE (MODE) == 16 && ((REGNO) & 3) == 0))) \
: FP_REGNO_P (REGNO) \
- ? GET_MODE_SIZE (MODE) <= 4 || ((REGNO) & 1) == 0 \
- /* Make wide modes be in aligned registers. */ \
+ ? (VALID_FP_MODE_P (MODE) \
+ && (GET_MODE_SIZE (MODE) <= 4 \
+ || (GET_MODE_SIZE (MODE) == 8 && ((REGNO) & 1) == 0) \
+ || (GET_MODE_SIZE (MODE) == 16 && ((REGNO) & 3) == 0) \
+ || (GET_MODE_SIZE (MODE) == 32 && ((REGNO) & 7) == 0))) \
: (GET_MODE_SIZE (MODE) <= UNITS_PER_WORD \
- || (GET_MODE_SIZE (MODE) <= 4 * UNITS_PER_WORD && ((REGNO) & 1) == 0)))
+ || (GET_MODE_SIZE (MODE) == 2 * UNITS_PER_WORD \
+ && ((((REGNO) & 1) == 1 && (REGNO) <= 25) || (REGNO) == 28)) \
+ || (GET_MODE_SIZE (MODE) == 4 * UNITS_PER_WORD \
+ && ((REGNO) & 3) == 3 && (REGNO) <= 23) \
+ || (GET_MODE_SIZE (MODE) == 8 * UNITS_PER_WORD \
+ && ((REGNO) & 7) == 3 && (REGNO) <= 19)))
/* How to renumber registers for dbx and gdb.
#define N_REG_CLASSES (int) LIM_REG_CLASSES
-/* Give names of register classes as strings for dump file. */
+/* Give names of register classes as strings for dump file. */
#define REG_CLASS_NAMES \
{"NO_REGS", "R1_REGS", "GENERAL_REGS", "FPUPPER_REGS", "FP_REGS", \
{0x00000000, 0x00000000, 0x01000000}, /* SHIFT_REGS */ \
{0xfffffffe, 0xffffffff, 0x01ffffff}} /* ALL_REGS */
-/* This may not actually be necessary anymore. But until I can prove
- otherwise it will stay. */
-#define CLASS_CANNOT_CHANGE_MODE NO_REGS
+/* The following macro defines cover classes for Integrated Register
+ Allocator. Cover classes is a set of non-intersected register
+ classes covering all hard registers used for register allocation
+ purpose. Any move between two registers of a cover class should be
+ cheaper than load or store of the registers. The macro value is
+ array of register classes with LIM_REG_CLASSES used as the end
+ marker. */
+
+#define IRA_COVER_CLASSES \
+{ \
+ GENERAL_REGS, FP_REGS, SHIFT_REGS, LIM_REG_CLASSES \
+}
+
+/* Defines invalid mode changes. */
-/* Defines illegal mode changes for CLASS_CANNOT_CHANGE_MODE. */
-#define CLASS_CANNOT_CHANGE_MODE_P(FROM,TO) \
- (GET_MODE_SIZE (FROM) != GET_MODE_SIZE (TO))
+#define CANNOT_CHANGE_MODE_CLASS(FROM, TO, CLASS) \
+ pa_cannot_change_mode_class (FROM, TO, CLASS)
-/* The same information, inverted:
- Return the class number of the smallest class containing
+/* Return the class number of the smallest class containing
reg number REGNO. This could be a conditional expression
or could index an array. */
: (REGNO) < 32 ? GENERAL_REGS \
: (REGNO) < 56 ? FP_REGS \
: (REGNO) < 88 ? FPUPPER_REGS \
- : (REGNO) < 88 ? FPUPPER_REGS \
: SHIFT_REGS)
-/* Get reg_class from a letter such as appears in the machine description. */
-/* Keep 'x' for backward compatibility with user asm. */
-#define REG_CLASS_FROM_LETTER(C) \
- ((C) == 'f' ? FP_REGS : \
- (C) == 'y' ? FPUPPER_REGS : \
- (C) == 'y' ? FPUPPER_REGS : \
- (C) == 'x' ? FP_REGS : \
- (C) == 'q' ? SHIFT_REGS : \
- (C) == 'a' ? R1_REGS : \
- (C) == 'Z' ? ALL_REGS : NO_REGS)
-
/* Return the maximum number of consecutive registers
needed to represent mode MODE in a register of class CLASS. */
#define CLASS_MAX_NREGS(CLASS, MODE) \
((CLASS) == FP_REGS || (CLASS) == FPUPPER_REGS \
- ? (!TARGET_PA_11 ? 1 : (GET_MODE_SIZE (MODE) + 4 - 1) / 4) \
+ ? (!TARGET_PA_11 \
+ ? COMPLEX_MODE_P (MODE) ? 2 : 1 \
+ : (GET_MODE_SIZE (MODE) + 4 - 1) / 4) \
: ((GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD))
/* 1 if N is a possible register number for function argument passing. */