From 4b02997f471d575f8367d32ee9c494aecfbc0d29 Mon Sep 17 00:00:00 2001 From: Nick Clifton Date: Tue, 22 Jan 2002 17:35:27 +0000 Subject: [PATCH] Move body of HARD_REGNO_MODE_OK into a function: arm_hard_regno_mode_ok From-SVN: r49080 --- gcc/ChangeLog | 16 ++++++++++- gcc/config/arm/arm-protos.h | 1 + gcc/config/arm/arm.c | 56 ++++++++++++++++++++++++++----------- gcc/config/arm/arm.h | 25 ++++------------- 4 files changed, 62 insertions(+), 36 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index a304260b04a..4659749eddf 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,4 +1,18 @@ -2002-01-22 Nick Clifton +2002-01-22 Nick Clifton + + * config/arm/arm.h (CONDITIONAL_REGISTER_USAGE): Move 'regno' + variable declaration to outer scope in order to simplify + future extensions. + (HARD_REGNO_MODE_OK): Replace macro body with a with a call to + arm_hard_regno_mode_ok. + * config/arm/arm-protos.h: Add a prototype for + arm_hard_regno_mode_ok. + * config/arm/arm.c (soft_df_operand): Remove now redundant + check for DImode values using IP_REGNUM. + (nonimmediate_soft_df_operand): Remove now redundant check for + DImode values using IP_REGNUM. + (arm_hard_regno_mode_ok): New function. New check: make sure + that DImode values are not stored in IP_REGNUM. * config/arm/arm.c (arm_expand_prologue): Replace REG_MAYBE_DEAD note with a USE. diff --git a/gcc/config/arm/arm-protos.h b/gcc/config/arm/arm-protos.h index 11accd34b32..b42da823869 100644 --- a/gcc/config/arm/arm-protos.h +++ b/gcc/config/arm/arm-protos.h @@ -43,6 +43,7 @@ extern void arm_encode_call_attribute PARAMS ((tree, int)); extern int arm_function_ok_for_sibcall PARAMS ((tree)); #endif #ifdef RTX_CODE +extern int arm_hard_regno_mode_ok PARAMS ((unsigned int, enum machine_mode)); extern int const_ok_for_arm PARAMS ((HOST_WIDE_INT)); extern int arm_split_constant PARAMS ((RTX_CODE, enum machine_mode, HOST_WIDE_INT, rtx, rtx, int)); diff --git a/gcc/config/arm/arm.c b/gcc/config/arm/arm.c index 1490134efde..04f06ae997d 100644 --- a/gcc/config/arm/arm.c +++ b/gcc/config/arm/arm.c @@ -3358,14 +3358,7 @@ soft_df_operand (op, mode) enum machine_mode mode; { if (s_register_operand (op, mode)) - { - if (GET_CODE (op) == SUBREG) - op = SUBREG_REG (op); - - /* The IP register must not be used, since its higher - numbered counterpart is 13 - the stack pointer. */ - return REGNO (op) != IP_REGNUM; - } + return TRUE; if (mode != VOIDmode && GET_MODE (op) != mode) return FALSE; @@ -3397,14 +3390,7 @@ nonimmediate_soft_df_operand (op, mode) enum machine_mode mode; { if (s_register_operand (op, mode)) - { - if (GET_CODE (op) == SUBREG) - op = SUBREG_REG (op); - - /* The IP register must not be used, since its higher - numbered counterpart is 13 - the stack pointer. */ - return REGNO (op) != IP_REGNUM; - } + return TRUE; if (mode != VOIDmode && GET_MODE (op) != mode) return FALSE; @@ -9133,6 +9119,44 @@ arm_final_prescan_insn (insn) } } +/* Returns true if REGNO is a valid register + for holding a quantity of tyoe MODE. */ + +int +arm_hard_regno_mode_ok (regno, mode) + unsigned int regno; + enum machine_mode mode; +{ + if (GET_MODE_CLASS (mode) == MODE_CC) + return regno == CC_REGNUM; + + if (TARGET_THUMB) + /* For the Thumb we only allow values bigger than SImode in + registers 0 - 6, so that there is always a second low + register available to hold the upper part of the value. + We probably we ought to ensure that the register is the + start of an even numbered register pair. */ + return (NUM_REGS (mode) < 2) || (regno < LAST_LO_REGNUM); + + if (regno <= LAST_ARM_REGNUM) + /* If the register is a general purpose ARM register we allow + it only if it not a special register (SP, LR, PC) and only + if there will be enough (non-special) registers to hold the + entire value. */ + return regno < (SP_REGNUM - (unsigned) NUM_REGS (mode)); + + if ( regno == FRAME_POINTER_REGNUM + || regno == ARG_POINTER_REGNUM) + /* We only allow integers in the fake hard registers. */ + return GET_MODE_CLASS (mode) == MODE_INT; + + /* The only registers left are the FPU registers + which we only allow to hold FP values. */ + return GET_MODE_CLASS (mode) == MODE_FLOAT + && regno >= FIRST_ARM_FP_REGNUM + && regno <= LAST_ARM_FP_REGNUM; +} + int arm_regno_class (regno) int regno; diff --git a/gcc/config/arm/arm.h b/gcc/config/arm/arm.h index 5a7b9b543d3..6f055699f01 100644 --- a/gcc/config/arm/arm.h +++ b/gcc/config/arm/arm.h @@ -847,9 +847,10 @@ extern const char * structure_size_string; #define CONDITIONAL_REGISTER_USAGE \ { \ + int regno; \ + \ if (TARGET_SOFT_FLOAT || TARGET_THUMB) \ { \ - int regno; \ for (regno = FIRST_ARM_FP_REGNUM; \ regno <= LAST_ARM_FP_REGNUM; ++regno) \ fixed_regs[regno] = call_used_regs[regno] = 1; \ @@ -1004,23 +1005,9 @@ extern const char * structure_size_string; && REGNO != ARG_POINTER_REGNUM) \ ? 1 : NUM_REGS (MODE)) -/* Value is 1 if hard register REGNO can hold a value of machine-mode MODE. - This is TRUE for ARM regs since they can hold anything, and TRUE for FPU - regs holding FP. - For the Thumb we only allow values bigger than SImode in registers 0 - 6, - so that there is always a second lo register available to hold the upper - part of the value. Probably we ought to ensure that the register is the - start of an even numbered register pair. */ +/* Return true if REGNO is suitable for holding a quantity of type MODE. */ #define HARD_REGNO_MODE_OK(REGNO, MODE) \ - (TARGET_ARM ? \ - ((GET_MODE_CLASS (MODE) == MODE_CC) ? (REGNO == CC_REGNUM) : \ - ( REGNO <= LAST_ARM_REGNUM \ - || REGNO == FRAME_POINTER_REGNUM \ - || REGNO == ARG_POINTER_REGNUM \ - || GET_MODE_CLASS (MODE) == MODE_FLOAT)) \ - : \ - ((GET_MODE_CLASS (MODE) == MODE_CC) ? (REGNO == CC_REGNUM) : \ - (NUM_REGS (MODE) < 2 || REGNO < LAST_LO_REGNUM))) + arm_hard_regno_mode_ok ((REGNO), (MODE)) /* Value is 1 if it is a good idea to tie two pseudo registers when one has mode MODE1 and one has mode MODE2. @@ -1092,7 +1079,7 @@ enum reg_class { 0x200FFFF }, /* GENERAL_REGS */ \ { 0x2FFFFFF } /* ALL_REGS */ \ } - + /* The same information, inverted: Return the class number of the smallest class containing reg number REGNO. This could be a conditional expression @@ -1909,7 +1896,7 @@ typedef struct arm_encode_call_attribute (decl, LONG_CALL_FLAG_CHAR); \ else if (! TREE_PUBLIC (decl)) \ arm_encode_call_attribute (decl, SHORT_CALL_FLAG_CHAR); \ - } \ + } /* Symbols in the text segment can be accessed without indirecting via the constant pool; it may take an extra binary operation, but this is still -- 2.30.2