Committed. Thank you,
Claudiu

On Thu, Apr 11, 2019 at 12:54 AM Andrew Burgess
<andrew.burg...@embecosm.com> wrote:
>
> * Claudiu Zissulescu <claz...@gmail.com> [2019-03-25 12:03:12 +0100]:
>
> > Refurbish eliminable regs howto by introducing a fake
> > FRAME_POINTER_REGNUM with the purpose to release FP register to be
> > used freely by the register allocator.
> >
> > gcc/
> > xxxx-xx-xx  Claudiu Zissulescu  <claz...@synopsys.com>
> >
> >       * config/arc/arc.c (arc_hard_regno_modes): Add two missing modes
> >       for last two fake registers.
> >       (arc_conditional_register_usage): Make sure fake frame and arg
> >       pointer regs are in general regs class.
> >       (FRAME_POINTER_MASK): Remove.
> >       (RETURN_ADDR_MASK): Remove.
> >       (arc_must_save_register): Use hard frame regnum.
> >       (frame_restore_reg): Use hard_frame_pointer_rtx.
> >       (arc_save_callee_saves): Likewise.
> >       (arc_restore_callee_saves): Likewise.
> >       (arc_save_callee_enter): Likewise.
> >       (arc_restore_callee_leave): Likewise.
> >       (arc_save_callee_milli): Likewise.
> >       (arc_eh_return_address_location): Likewise.
> >       (arc_check_multi): Use hard frame regnum.
> >       (arc_can_eliminate): Likewise.
> >       * config/arc/arc.h (FIXED_REGISTERS): Make FP register available
> >       for register allocator.
> >       (REG_CLASS_CONTENTS): Update GENERAL_REGS.
> >       (REGNO_OK_FOR_BASE_P): Consider FRAME_POINTER_REGNUM.
> >       (FRAME_POINTER_REGNUM): Change it to a fake register.
> >       (HARD_FRAME_POINTER_REGNUM): Defined.
> >       (ARG_POINTER_REGNUM): Change it to a new fake register.
> >       (ELIMINABLE_REGS): Update.
> >       (REGISTER_NAMES): Update names.
> >       * config/arc/arc.md (LP_START): Remove.
> >       (LP_END): Likewise.
> >       (shift_si3_loop): Update pattern.
>
> This is fine, thanks.
>
> Andrew
>
>
> > ---
> >  gcc/config/arc/arc.c  | 173 +++++++++++++++++++++++-------------------
> >  gcc/config/arc/arc.h  |  31 ++++----
> >  gcc/config/arc/arc.md |  12 +--
> >  3 files changed, 115 insertions(+), 101 deletions(-)
> >
> > diff --git a/gcc/config/arc/arc.c b/gcc/config/arc/arc.c
> > index 62f435b0a1d..9938a774d91 100644
> > --- a/gcc/config/arc/arc.c
> > +++ b/gcc/config/arc/arc.c
> > @@ -1651,7 +1651,8 @@ static unsigned int arc_hard_regno_modes[] = {
> >    V_MODES, V_MODES, V_MODES, V_MODES, V_MODES, V_MODES, V_MODES, V_MODES,
> >
> >    S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES,
> > -  S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES
> > +  S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES, S_MODES,
> > +  S_MODES, S_MODES
> >  };
> >
> >  static unsigned int arc_mode_class [NUM_MACHINE_MODES];
> > @@ -1886,7 +1887,8 @@ arc_conditional_register_usage (void)
> >
> >    /* Handle Special Registers.  */
> >    arc_regno_reg_class[CC_REG] = NO_REGS;      /* CC_REG: must be NO_REGS.  
> > */
> > -  arc_regno_reg_class[62] = GENERAL_REGS;
> > +  arc_regno_reg_class[FRAME_POINTER_REGNUM] = GENERAL_REGS;
> > +  arc_regno_reg_class[ARG_POINTER_REGNUM] = GENERAL_REGS;
> >
> >    if (TARGET_DPFP)
> >      for (i = R40_REG; i < R44_REG; ++i)
> > @@ -2616,8 +2618,53 @@ arc_compute_function_type (struct function *fun)
> >    return fun->machine->fn_type = fn_type;
> >  }
> >
> > -#define FRAME_POINTER_MASK (1 << (FRAME_POINTER_REGNUM))
> > -#define RETURN_ADDR_MASK (1 << (RETURN_ADDR_REGNUM))
> > +/* Helper function to wrap FRAME_POINTER_NEEDED.  We do this as
> > +   FRAME_POINTER_NEEDED will not be true until the IRA (Integrated
> > +   Register Allocator) pass, while we want to get the frame size
> > +   correct earlier than the IRA pass.
> > +
> > +   When a function uses eh_return we must ensure that the fp register
> > +   is saved and then restored so that the unwinder can restore the
> > +   correct value for the frame we are going to jump to.
> > +
> > +   To do this we force all frames that call eh_return to require a
> > +   frame pointer (see arc_frame_pointer_required), this
> > +   will ensure that the previous frame pointer is stored on entry to
> > +   the function, and will then be reloaded at function exit.
> > +
> > +   As the frame pointer is handled as a special case in our prologue
> > +   and epilogue code it must not be saved and restored using the
> > +   MUST_SAVE_REGISTER mechanism otherwise we run into issues where GCC
> > +   believes that the function is not using a frame pointer and that
> > +   the value in the fp register is the frame pointer, while the
> > +   prologue and epilogue are busy saving and restoring the fp
> > +   register.
> > +
> > +   During compilation of a function the frame size is evaluated
> > +   multiple times, it is not until the reload pass is complete the the
> > +   frame size is considered fixed (it is at this point that space for
> > +   all spills has been allocated).  However the frame_pointer_needed
> > +   variable is not set true until the register allocation pass, as a
> > +   result in the early stages the frame size does not include space
> > +   for the frame pointer to be spilled.
> > +
> > +   The problem that this causes is that the rtl generated for
> > +   EH_RETURN_HANDLER_RTX uses the details of the frame size to compute
> > +   the offset from the frame pointer at which the return address
> > +   lives.  However, in early passes GCC has not yet realised we need a
> > +   frame pointer, and so has not included space for the frame pointer
> > +   in the frame size, and so gets the offset of the return address
> > +   wrong.  This should not be an issue as in later passes GCC has
> > +   realised that the frame pointer needs to be spilled, and has
> > +   increased the frame size.  However, the rtl for the
> > +   EH_RETURN_HANDLER_RTX is not regenerated to use the newer, larger
> > +   offset, and the wrong smaller offset is used.  */
> > +
> > +static bool
> > +arc_frame_pointer_needed (void)
> > +{
> > +  return (frame_pointer_needed || crtl->calls_eh_return);
> > +}
> >
> >  /* Tell prologue and epilogue if register REGNO should be saved / restored.
> >     The return address and frame pointer are treated separately.
> > @@ -2656,16 +2703,28 @@ arc_must_save_register (int regno, struct function 
> > *func)
> >        break;
> >      }
> >
> > -  if ((regno) != RETURN_ADDR_REGNUM
> > -      && (regno) != FRAME_POINTER_REGNUM
> > -      && (regno) != STACK_POINTER_REGNUM
> > -      && df_regs_ever_live_p (regno)
> > -      && (!call_used_regs[regno]
> > -       || ARC_INTERRUPT_P (fn_type))
> > -      /* Do not emit code for auto saved regs.  */
> > -      && !irq_auto_save_p
> > -      && !firq_auto_save_p)
> > -    return true;
> > +  switch (regno)
> > +    {
> > +    case RETURN_ADDR_REGNUM:
> > +    case STACK_POINTER_REGNUM:
> > +      return false;
> > +
> > +    case HARD_FRAME_POINTER_REGNUM:
> > +      /* If we need FP reg as a frame pointer then don't save it as a
> > +      regular reg.  */
> > +      if (arc_frame_pointer_needed ())
> > +     return false;
> > +
> > +      /* FALLTHRU */
> > +    default:
> > +      if (df_regs_ever_live_p (regno)
> > +       && (!call_used_regs[regno]
> > +           || ARC_INTERRUPT_P (fn_type))
> > +       /* Do not emit code for auto saved regs.  */
> > +       && !irq_auto_save_p
> > +       && !firq_auto_save_p)
> > +     return true;
> > +    }
> >
> >    return false;
> >  }
> > @@ -2682,54 +2741,6 @@ arc_must_save_return_addr (struct function *func)
> >    return false;
> >  }
> >
> > -/* Helper function to wrap FRAME_POINTER_NEEDED.  We do this as
> > -   FRAME_POINTER_NEEDED will not be true until the IRA (Integrated
> > -   Register Allocator) pass, while we want to get the frame size
> > -   correct earlier than the IRA pass.
> > -
> > -   When a function uses eh_return we must ensure that the fp register
> > -   is saved and then restored so that the unwinder can restore the
> > -   correct value for the frame we are going to jump to.
> > -
> > -   To do this we force all frames that call eh_return to require a
> > -   frame pointer (see arc_frame_pointer_required), this
> > -   will ensure that the previous frame pointer is stored on entry to
> > -   the function, and will then be reloaded at function exit.
> > -
> > -   As the frame pointer is handled as a special case in our prologue
> > -   and epilogue code it must not be saved and restored using the
> > -   MUST_SAVE_REGISTER mechanism otherwise we run into issues where GCC
> > -   believes that the function is not using a frame pointer and that
> > -   the value in the fp register is the frame pointer, while the
> > -   prologue and epilogue are busy saving and restoring the fp
> > -   register.
> > -
> > -   During compilation of a function the frame size is evaluated
> > -   multiple times, it is not until the reload pass is complete the the
> > -   frame size is considered fixed (it is at this point that space for
> > -   all spills has been allocated).  However the frame_pointer_needed
> > -   variable is not set true until the register allocation pass, as a
> > -   result in the early stages the frame size does not include space
> > -   for the frame pointer to be spilled.
> > -
> > -   The problem that this causes is that the rtl generated for
> > -   EH_RETURN_HANDLER_RTX uses the details of the frame size to compute
> > -   the offset from the frame pointer at which the return address
> > -   lives.  However, in early passes GCC has not yet realised we need a
> > -   frame pointer, and so has not included space for the frame pointer
> > -   in the frame size, and so gets the offset of the return address
> > -   wrong.  This should not be an issue as in later passes GCC has
> > -   realised that the frame pointer needs to be spilled, and has
> > -   increased the frame size.  However, the rtl for the
> > -   EH_RETURN_HANDLER_RTX is not regenerated to use the newer, larger
> > -   offset, and the wrong smaller offset is used.  */
> > -
> > -static bool
> > -arc_frame_pointer_needed (void)
> > -{
> > -  return (frame_pointer_needed || crtl->calls_eh_return);
> > -}
> > -
> >  /* Return non-zero if there are registers to be saved or loaded using
> >     millicode thunks.  We can only use consecutive sequences starting
> >     with r13, and not going beyond r25.
> > @@ -2991,7 +3002,7 @@ frame_restore_reg (rtx reg, HOST_WIDE_INT offset)
> >    insn = frame_move_inc (reg, addr, stack_pointer_rtx, 0);
> >    add_reg_note (insn, REG_CFA_RESTORE, reg);
> >
> > -  if (reg == frame_pointer_rtx)
> > +  if (reg == hard_frame_pointer_rtx)
> >      add_reg_note (insn, REG_CFA_DEF_CFA,
> >                 plus_constant (Pmode, stack_pointer_rtx,
> >                                GET_MODE_SIZE (GET_MODE (reg)) + offset));
> > @@ -3077,13 +3088,13 @@ arc_save_callee_saves (unsigned int gmask,
> >       registers are saved.  */
> >    if (save_fp)
> >      {
> > -      frame_allocated += frame_save_reg (frame_pointer_rtx, offset);
> > +      frame_allocated += frame_save_reg (hard_frame_pointer_rtx, offset);
> >        offset = 0;
> >      }
> >
> >    /* Emit mov fp,sp.  */
> >    if (arc_frame_pointer_needed ())
> > -    frame_move (frame_pointer_rtx, stack_pointer_rtx);
> > +    frame_move (hard_frame_pointer_rtx, stack_pointer_rtx);
> >
> >    return frame_allocated;
> >  }
> > @@ -3106,7 +3117,7 @@ arc_restore_callee_saves (unsigned int gmask,
> >    /* Emit mov fp,sp.  */
> >    if (arc_frame_pointer_needed () && offset)
> >      {
> > -      frame_move (stack_pointer_rtx, frame_pointer_rtx);
> > +      frame_move (stack_pointer_rtx, hard_frame_pointer_rtx);
> >        frame_deallocated += offset;
> >        offset = 0;
> >      }
> > @@ -3115,7 +3126,7 @@ arc_restore_callee_saves (unsigned int gmask,
> >      {
> >        /* Any offset is taken care by previous if-statement.  */
> >        gcc_assert (offset == 0);
> > -      frame_deallocated += frame_restore_reg (frame_pointer_rtx, 0);
> > +      frame_deallocated += frame_restore_reg (hard_frame_pointer_rtx, 0);
> >      }
> >
> >    if (offset)
> > @@ -3260,11 +3271,11 @@ arc_save_callee_enter (unsigned int gmask,
> >        mem = gen_frame_mem (Pmode, plus_constant (Pmode,
> >                                                stack_pointer_rtx,
> >                                                off));
> > -      XVECEXP (insn, 0, indx) = gen_rtx_SET (mem, frame_pointer_rtx);
> > +      XVECEXP (insn, 0, indx) = gen_rtx_SET (mem, hard_frame_pointer_rtx);
> >        RTX_FRAME_RELATED_P (XVECEXP (insn, 0, indx++)) = 1;
> >        off -= UNITS_PER_WORD;
> >
> > -      XVECEXP (insn, 0, indx) = gen_rtx_SET (frame_pointer_rtx,
> > +      XVECEXP (insn, 0, indx) = gen_rtx_SET (hard_frame_pointer_rtx,
> >                                            stack_pointer_rtx);
> >        RTX_FRAME_RELATED_P (XVECEXP (insn, 0, indx++)) = 1;
> >        save_fp = false;
> > @@ -3368,7 +3379,7 @@ arc_restore_callee_leave (unsigned int gmask,
> >        mem = gen_frame_mem (Pmode, plus_constant (Pmode,
> >                                                stack_pointer_rtx,
> >                                                off));
> > -      XVECEXP (insn, 0, indx) = gen_rtx_SET (frame_pointer_rtx, mem);
> > +      XVECEXP (insn, 0, indx) = gen_rtx_SET (hard_frame_pointer_rtx, mem);
> >        RTX_FRAME_RELATED_P (XVECEXP (insn, 0, indx++)) = 1;
> >        off -= UNITS_PER_WORD;
> >      }
> > @@ -3387,7 +3398,7 @@ arc_restore_callee_leave (unsigned int gmask,
> >    /* Dwarf related info.  */
> >    if (restore_fp)
> >      {
> > -      add_reg_note (insn, REG_CFA_RESTORE, frame_pointer_rtx);
> > +      add_reg_note (insn, REG_CFA_RESTORE, hard_frame_pointer_rtx);
> >        add_reg_note (insn, REG_CFA_DEF_CFA,
> >                   plus_constant (Pmode, stack_pointer_rtx,
> >                                  offset + nregs * UNITS_PER_WORD));
> > @@ -3525,11 +3536,11 @@ arc_save_callee_milli (unsigned int gmask,
> >       above loop to save fp because our ABI states fp goes aftert all
> >       registers are saved.  */
> >    if (save_fp)
> > -    frame_allocated += frame_save_reg (frame_pointer_rtx, offset);
> > +    frame_allocated += frame_save_reg (hard_frame_pointer_rtx, offset);
> >
> >    /* Emit mov fp,sp.  */
> >    if (arc_frame_pointer_needed ())
> > -    frame_move (frame_pointer_rtx, stack_pointer_rtx);
> > +    frame_move (hard_frame_pointer_rtx, stack_pointer_rtx);
> >
> >    return frame_allocated;
> >  }
> > @@ -3559,13 +3570,13 @@ arc_restore_callee_milli (unsigned int gmask,
> >    /* Emit mov fp,sp.  */
> >    if (arc_frame_pointer_needed () && offset)
> >      {
> > -      frame_move (stack_pointer_rtx, frame_pointer_rtx);
> > +      frame_move (stack_pointer_rtx, hard_frame_pointer_rtx);
> >        frame_allocated = offset;
> >        offset = 0;
> >      }
> >
> >    if (restore_fp)
> > -    frame_allocated += frame_restore_reg (frame_pointer_rtx, 0);
> > +    frame_allocated += frame_restore_reg (hard_frame_pointer_rtx, 0);
> >
> >    if (offset)
> >      {
> > @@ -3875,7 +3886,7 @@ arc_check_multi (rtx op, bool push_p)
> >        if (REGNO (reg) == RETURN_ADDR_REGNUM
> >         && i == start)
> >       regno = 12;
> > -      else if (REGNO (reg) == FRAME_POINTER_REGNUM)
> > +      else if (REGNO (reg) == HARD_FRAME_POINTER_REGNUM)
> >       ++i;
> >        else if (REGNO (reg) != regno)
> >       return false;
> > @@ -3922,7 +3933,7 @@ arc_eh_return_address_location (rtx source)
> >       included in the 'extra_size' field.  */
> >    offset = afi->reg_size + afi->extra_size - 4;
> >    mem = gen_frame_mem (Pmode,
> > -                    plus_constant (Pmode, frame_pointer_rtx, offset));
> > +                    plus_constant (Pmode, hard_frame_pointer_rtx, offset));
> >
> >    /* The following should not be needed, and is, really a hack.  The
> >       issue being worked around here is that the DSE (Dead Store
> > @@ -5396,7 +5407,7 @@ arc_final_prescan_insn (rtx_insn *insn, rtx *opvec 
> > ATTRIBUTE_UNUSED,
> >  static bool
> >  arc_can_eliminate (const int from ATTRIBUTE_UNUSED, const int to)
> >  {
> > -  return ((to == FRAME_POINTER_REGNUM) || !arc_frame_pointer_needed ());
> > +  return ((to == HARD_FRAME_POINTER_REGNUM) || (to == 
> > STACK_POINTER_REGNUM));
> >  }
> >
> >  /* Define the offset between two registers, one to be eliminated, and
> > @@ -5408,7 +5419,7 @@ arc_initial_elimination_offset (int from, int to)
> >    if (!cfun->machine->frame_info.initialized)
> >      arc_compute_frame_size ();
> >
> > -  if (from == ARG_POINTER_REGNUM && to == FRAME_POINTER_REGNUM)
> > +  if (from == ARG_POINTER_REGNUM && to == HARD_FRAME_POINTER_REGNUM)
> >      {
> >        return (cfun->machine->frame_info.extra_size
> >             + cfun->machine->frame_info.reg_size);
> > @@ -5427,6 +5438,8 @@ arc_initial_elimination_offset (int from, int to)
> >             + cfun->machine->frame_info.extra_size
> >             + cfun->machine->frame_info.reg_size));
> >      }
> > +  if ((from == FRAME_POINTER_REGNUM) && (to == HARD_FRAME_POINTER_REGNUM))
> > +    return 0;
> >
> >    gcc_unreachable ();
> >  }
> > @@ -11024,7 +11037,7 @@ arc_builtin_setjmp_frame_value (void)
> >       frame pointer value for this frame (if the use of the frame pointer
> >       had not been removed).  We really do want the raw frame pointer
> >       register value.  */
> > -  return gen_raw_REG (Pmode, FRAME_POINTER_REGNUM);
> > +  return gen_raw_REG (Pmode, HARD_FRAME_POINTER_REGNUM);
> >  }
> >
> >  /* Return nonzero if a jli call should be generated for a call from
> > diff --git a/gcc/config/arc/arc.h b/gcc/config/arc/arc.h
> > index 6a77869b58c..fbe71278346 100644
> > --- a/gcc/config/arc/arc.h
> > +++ b/gcc/config/arc/arc.h
> > @@ -325,7 +325,7 @@ if (GET_MODE_CLASS (MODE) == MODE_INT             \
> >     argument pointer.  */
> >
> >  /* r63 is pc, r64-r127 = simd vregs, r128-r143 = simd dma config regs
> > -   r144, r145 = lp_start, lp_end
> > +   r144, r145 = ARG_POINTER, FRAME_POINTER
> >     and therefore the pseudo registers start from r146. */
> >  #define FIRST_PSEUDO_REGISTER 146
> >
> > @@ -366,7 +366,7 @@ if (GET_MODE_CLASS (MODE) == MODE_INT             \
> >  { 0, 0, 0, 0, 0, 0, 0, 0,    \
> >    0, 0, 0, 0, 0, 0, 0, 0,    \
> >    0, 0, 0, 0, 0, 0, 0, 0,    \
> > -  0, 0, 1, 1, 1, 1, 1, 1,    \
> > +  0, 0, 1, 0, 1, 1, 1, 1,    \
> >                               \
> >    1, 1, 1, 1, 1, 1, 1, 1,    \
> >    0, 0, 0, 0, 1, 1, 1, 1,    \
> > @@ -398,7 +398,7 @@ if (GET_MODE_CLASS (MODE) == MODE_INT             \
> >    1, 1, 1, 1, 1, 1, 1, 1,    \
> >    1, 1, 1, 1, 1, 0, 0, 0,    \
> >    0, 0, 0, 0, 0, 0, 0, 0,    \
> > -  0, 0, 1, 1, 1, 1, 1, 1,    \
> > +  0, 0, 1, 0, 1, 1, 1, 1,    \
> >                               \
> >    1, 1, 1, 1, 1, 1, 1, 1,    \
> >    1, 1, 1, 1, 1, 1, 1, 1,    \
> > @@ -511,10 +511,10 @@ enum reg_class
> >    {0x00000003, 0x00000000, 0x00000000, 0x00000000, 0x00000000}, /* 'Rsd'.  
> > */ \
> >    {0x0000000f, 0x00000000, 0x00000000, 0x00000000, 0x00000000}, /* 'Rcd'.  
> > */ \
> >    {0x0000f00f, 0x00000000, 0x00000000, 0x00000000, 0x00000000}, /* 'q'.  
> > */ \
> > -  {0x1c001fff, 0x00000000, 0x00000000, 0x00000000, 0x00000000}, /* 'Rsc'.  
> > */ \
> > +  {0x00001fff, 0x00000000, 0x00000000, 0x00000000, 0x00000000}, /* 'Rsc'.  
> > */ \
> >    {0x9fffffff, 0x00000000, 0x00000000, 0x00000000, 0x00000000}, /* 'h'.  
> > */ \
> >    {0x00000000, 0x00000f00, 0x00000000, 0x00000000, 0x00000000}, /* 'D'.  
> > */ \
> > -  {0xffffffff, 0x8fffffff, 0x00000000, 0x00000000, 0x00000000}, /* 'r'.  
> > */ \
> > +  {0xffffffff, 0x8fffffff, 0x00000000, 0x00000000, 0x00030000}, /* 'r'.  
> > */ \
> >    {0x00000000, 0x00000000, 0xffffffff, 0xffffffff, 0x00000000}, /* 'v'.  
> > */ \
> >    {0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x0000ffff}, /* 'd'.  
> > */ \
> >    {0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0x0003ffff} /* 
> > ALL_REGS.  */\
> > @@ -562,11 +562,14 @@ extern enum reg_class arc_regno_reg_class[];
> >     Since they use reg_renumber, they are safe only once reg_renumber
> >     has been allocated, which happens in local-alloc.c.  */
> >  #define REGNO_OK_FOR_BASE_P(REGNO)                                   \
> > -  ((REGNO) < 29 || ((REGNO) == ARG_POINTER_REGNUM) || ((REGNO) == 63)      
> >   \
> > +  ((REGNO) < 29                                                            
> >   \
> > +   || ((REGNO) == ARG_POINTER_REGNUM)                                      
> >   \
> > +   || ((REGNO) == FRAME_POINTER_REGNUM)                                    
> >   \
> > +   || ((REGNO) == PCL_REG)                                           \
> >     || ((unsigned) reg_renumber[REGNO] < 29)                          \
> >     || ((unsigned) (REGNO) == (unsigned) arc_tp_regno)                      
> >   \
> >     || (fixed_regs[REGNO] == 0 && IN_RANGE (REGNO, 32, 59))           \
> > -   || ((REGNO) == 30 && fixed_regs[REGNO] == 0))
> > +   || (fixed_regs[REGNO] == 0 && (REGNO) == R30_REG))
> >
> >  #define REGNO_OK_FOR_INDEX_P(REGNO) REGNO_OK_FOR_BASE_P(REGNO)
> >
> > @@ -652,11 +655,12 @@ arc_return_addr_rtx(COUNT,FRAME)
> >  #define STACK_POINTER_REGNUM 28
> >
> >  /* Base register for access to local variables of the function.  */
> > -#define FRAME_POINTER_REGNUM 27
> > +#define FRAME_POINTER_REGNUM 145
> > +#define HARD_FRAME_POINTER_REGNUM 27
> >
> >  /* Base register for access to arguments of the function. This register
> >     will be eliminated into either fp or sp.  */
> > -#define ARG_POINTER_REGNUM 62
> > +#define ARG_POINTER_REGNUM 144
> >
> >  #define RETURN_ADDR_REGNUM 31
> >
> > @@ -766,8 +770,9 @@ arc_return_addr_rtx(COUNT,FRAME)
> >
> >  #define ELIMINABLE_REGS                                      \
> >  {{ARG_POINTER_REGNUM, STACK_POINTER_REGNUM},         \
> > - {ARG_POINTER_REGNUM, FRAME_POINTER_REGNUM},         \
> > - {FRAME_POINTER_REGNUM, STACK_POINTER_REGNUM}}
> > + {ARG_POINTER_REGNUM, HARD_FRAME_POINTER_REGNUM},    \
> > + {FRAME_POINTER_REGNUM, STACK_POINTER_REGNUM},       \
> > + {FRAME_POINTER_REGNUM, HARD_FRAME_POINTER_REGNUM}}
> >
> >  /* Define the offset between two registers, one to be eliminated, and the 
> > other
> >     its replacement, at the start of a routine.  */
> > @@ -1161,7 +1166,7 @@ extern char rname56[], rname57[], rname58[], 
> > rname59[];
> >    "r32",  "r33",  "r34",  "r35",      "r36",    "r37",    "r38",   "r39",  
> >   \
> >     "d1",   "d1",   "d2",   "d2",      "r44",    "r45",    "r46",   "r47",  
> >   \
> >    "r48",  "r49",  "r50",  "r51",      "r52",    "r53",    "r54",   "r55",  
> >   \
> > -  rname56,rname57,rname58,rname59,"lp_count",    "cc",     "ap",   "pcl",  
> >   \
> > +  rname56,rname57,rname58,rname59,"lp_count",    "cc",   "limm",   "pcl",  
> >   \
> >    "vr0",  "vr1",  "vr2",  "vr3",      "vr4",    "vr5",    "vr6",   "vr7",  
> >      \
> >    "vr8",  "vr9", "vr10", "vr11",     "vr12",   "vr13",   "vr14",  "vr15",  
> >   \
> >   "vr16", "vr17", "vr18", "vr19",     "vr20",   "vr21",   "vr22",  "vr23",  
> >   \
> > @@ -1172,7 +1177,7 @@ extern char rname56[], rname57[], rname58[], 
> > rname59[];
> >   "vr56", "vr57", "vr58", "vr59",     "vr60",   "vr61",   "vr62",  "vr63",  
> >   \
> >    "dr0",  "dr1",  "dr2",  "dr3",      "dr4",    "dr5",    "dr6",   "dr7",  
> >   \
> >    "dr0",  "dr1",  "dr2",  "dr3",      "dr4",    "dr5",    "dr6",   "dr7",  
> >   \
> > -  "lp_start", "lp_end" \
> > +  "arg", "frame" \
> >  }
> >
> >  #define ADDITIONAL_REGISTER_NAMES            \
> > diff --git a/gcc/config/arc/arc.md b/gcc/config/arc/arc.md
> > index 3a903d4224a..7ac5a1b5785 100644
> > --- a/gcc/config/arc/arc.md
> > +++ b/gcc/config/arc/arc.md
> > @@ -202,8 +202,6 @@
> >     (LP_COUNT 60)
> >     (CC_REG 61)
> >     (PCL_REG 63)
> > -   (LP_START 144)
> > -   (LP_END 145)
> >    ]
> >  )
> >
> > @@ -3467,8 +3465,6 @@ core_3, archs4x, archs4xd, archs4xd_slow"
> >                           (match_operand:SI 2 "nonmemory_operand" 
> > "rn,Cal")]))
> >     (clobber (match_scratch:SI 4 "=X,X"))
> >     (clobber (reg:SI LP_COUNT))
> > -   (clobber (reg:SI LP_START))
> > -   (clobber (reg:SI LP_END))
> >     (clobber (reg:CC CC_REG))
> >    ]
> >    "!TARGET_BARREL_SHIFTER"
> > @@ -6508,7 +6504,7 @@ core_3, archs4x, archs4xd, archs4xd_slow"
> >    {
> >     int len = XVECLEN (operands[0], 0);
> >     rtx tmp = XVECEXP (operands[0], 0, len - 1);
> > -   if (XEXP (tmp, 0) != frame_pointer_rtx)
> > +   if (XEXP (tmp, 0) != hard_frame_pointer_rtx)
> >       {
> >        operands[3] = XEXP (tmp, 0);
> >        gcc_assert (INTVAL (operands[1]) == INTVAL (operands[2]));
> > @@ -6538,7 +6534,7 @@ core_3, archs4x, archs4xd, archs4xd_slow"
> >    {
> >     int len = XVECLEN (operands[0], 0);
> >     rtx tmp = XVECEXP (operands[0], 0, len - 1);
> > -   if (XEXP (tmp, 0) != frame_pointer_rtx)
> > +   if (XEXP (tmp, 0) != hard_frame_pointer_rtx)
> >       {
> >        operands[3] = XEXP (tmp, 0);
> >        gcc_assert (INTVAL (operands[1]) == INTVAL (operands[2]));
> > @@ -6569,7 +6565,7 @@ core_3, archs4x, archs4xd, archs4xd_slow"
> >    {
> >     int len = XVECLEN (operands[0], 0);
> >     rtx tmp = XVECEXP (operands[0], 0, len - 1);
> > -   if (XEXP (tmp, 0) != frame_pointer_rtx)
> > +   if (XEXP (tmp, 0) != hard_frame_pointer_rtx)
> >       {
> >        operands[3] = XEXP (tmp, 0);
> >        gcc_assert (INTVAL (operands[1]) == INTVAL (operands[2]));
> > @@ -6600,7 +6596,7 @@ core_3, archs4x, archs4xd, archs4xd_slow"
> >    {
> >     int len = XVECLEN (operands[0], 0);
> >     rtx tmp = XVECEXP (operands[0], 0, len - 1);
> > -   if (XEXP (tmp, 0) != frame_pointer_rtx)
> > +   if (XEXP (tmp, 0) != hard_frame_pointer_rtx)
> >       {
> >        operands[3] = XEXP (tmp, 0);
> >        gcc_assert (INTVAL (operands[1]) == INTVAL (operands[2]));
> > --
> > 2.20.1
> >

Reply via email to