mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-02-25 11:15:56 +08:00
alpha.c (alpha_sa_size): Force procedure type to PT_STACK when frame_pointer_needed on OpenVMS.
* config/alpha/alpha.c (alpha_sa_size): Force procedure type to PT_STACK when frame_pointer_needed on OpenVMS. (alpha_pv_save_size, alpha_using_fp): Remove. (alpha_vms_can_eliminate): New function. Support for CAN_ELIMINATE with proper processing for PT_NULL. (alpha_vms_initial_elimination_offset): New function. Support for INITIAL_ELIMINATION_OFFSET with proper processing for PT_NULL. (alpha_sa_size): Force procedure type to PT_STACK when frame_pointer_needed on OpenVMS. * config/alpha/alpha-protos.h (alpha_pv_save_size): Remove prototype. (alpha_using_fp): Likewise. (alpha_vms_can_eliminate): Add prototype. (alpha_vms_initial_elimination_offset): Likewise. * config/alpha/vms.h (CAN_ELIMINATE, INITIAL_ELIMINATION_OFFSET): Call alpha_vms_can_eliminate and alpha_vms_initial_elimination_offset. Co-Authored-By: Douglas B Rupp <rupp@gnat.com> From-SVN: r150646
This commit is contained in:
parent
18fd562170
commit
1d3499d85c
@ -1,3 +1,22 @@
|
||||
2009-08-10 Olivier Hainque <hainqueu@adacore.com>
|
||||
Douglas B Rupp <rupp@gnat.com>
|
||||
|
||||
* config/alpha/alpha.c (alpha_sa_size): Force procedure type to
|
||||
PT_STACK when frame_pointer_needed on OpenVMS.
|
||||
(alpha_pv_save_size, alpha_using_fp): Remove.
|
||||
(alpha_vms_can_eliminate): New function. Support for CAN_ELIMINATE
|
||||
with proper processing for PT_NULL.
|
||||
(alpha_vms_initial_elimination_offset): New function. Support for
|
||||
INITIAL_ELIMINATION_OFFSET with proper processing for PT_NULL.
|
||||
(alpha_sa_size): Force procedure type to PT_STACK when
|
||||
frame_pointer_needed on OpenVMS.
|
||||
* config/alpha/alpha-protos.h (alpha_pv_save_size): Remove prototype.
|
||||
(alpha_using_fp): Likewise.
|
||||
(alpha_vms_can_eliminate): Add prototype.
|
||||
(alpha_vms_initial_elimination_offset): Likewise.
|
||||
* config/alpha/vms.h (CAN_ELIMINATE, INITIAL_ELIMINATION_OFFSET):
|
||||
Call alpha_vms_can_eliminate and alpha_vms_initial_elimination_offset.
|
||||
|
||||
2009-08-10 Eric Botcazou <botcazou@adacore.com>
|
||||
Douglas B Rupp <rupp@gnat.com>
|
||||
|
||||
|
@ -28,8 +28,6 @@ extern int direct_return (void);
|
||||
extern int alpha_sa_size (void);
|
||||
extern HOST_WIDE_INT alpha_initial_elimination_offset (unsigned int,
|
||||
unsigned int);
|
||||
extern int alpha_pv_save_size (void);
|
||||
extern int alpha_using_fp (void);
|
||||
extern void alpha_expand_prologue (void);
|
||||
extern void alpha_expand_epilogue (void);
|
||||
extern void alpha_output_filename (FILE *, const char *);
|
||||
@ -116,7 +114,9 @@ extern void avms_asm_output_external (FILE *, tree, const char *);
|
||||
extern void vms_output_aligned_decl_common (FILE *, tree, const char *,
|
||||
unsigned HOST_WIDE_INT,
|
||||
unsigned int);
|
||||
|
||||
extern int alpha_vms_can_eliminate (unsigned int, unsigned int);
|
||||
extern HOST_WIDE_INT alpha_vms_initial_elimination_offset (unsigned int,
|
||||
unsigned int);
|
||||
#endif
|
||||
|
||||
extern rtx unicosmk_add_call_info_word (rtx);
|
||||
|
@ -7353,10 +7353,10 @@ alpha_sa_size (void)
|
||||
}
|
||||
else if (TARGET_ABI_OPEN_VMS)
|
||||
{
|
||||
/* Start by assuming we can use a register procedure if we don't
|
||||
make any calls (REG_RA not used) or need to save any
|
||||
registers and a stack procedure if we do. */
|
||||
if ((mask[0] >> REG_RA) & 1)
|
||||
/* Start with a stack procedure if we make any calls (REG_RA used), or
|
||||
need a frame pointer, with a register procedure if we otherwise need
|
||||
at least a slot, and with a null procedure in other cases. */
|
||||
if ((mask[0] >> REG_RA) & 1 || frame_pointer_needed)
|
||||
alpha_procedure_type = PT_STACK;
|
||||
else if (get_frame_size() != 0)
|
||||
alpha_procedure_type = PT_REGISTER;
|
||||
@ -7446,21 +7446,96 @@ alpha_initial_elimination_offset (unsigned int from,
|
||||
return ret;
|
||||
}
|
||||
|
||||
int
|
||||
alpha_pv_save_size (void)
|
||||
{
|
||||
alpha_sa_size ();
|
||||
return alpha_procedure_type == PT_STACK ? 8 : 0;
|
||||
}
|
||||
|
||||
int
|
||||
alpha_using_fp (void)
|
||||
{
|
||||
alpha_sa_size ();
|
||||
return vms_unwind_regno == HARD_FRAME_POINTER_REGNUM;
|
||||
}
|
||||
|
||||
#if TARGET_ABI_OPEN_VMS
|
||||
|
||||
int
|
||||
alpha_vms_can_eliminate (unsigned int from ATTRIBUTE_UNUSED, unsigned int to)
|
||||
{
|
||||
/* We need the alpha_procedure_type to decide. Evaluate it now. */
|
||||
alpha_sa_size ();
|
||||
|
||||
switch (alpha_procedure_type)
|
||||
{
|
||||
case PT_NULL:
|
||||
/* NULL procedures have no frame of their own and we only
|
||||
know how to resolve from the current stack pointer. */
|
||||
return to == STACK_POINTER_REGNUM;
|
||||
|
||||
case PT_REGISTER:
|
||||
case PT_STACK:
|
||||
/* We always eliminate except to the stack pointer if there is no
|
||||
usable frame pointer at hand. */
|
||||
return (to != STACK_POINTER_REGNUM
|
||||
|| vms_unwind_regno != HARD_FRAME_POINTER_REGNUM);
|
||||
}
|
||||
|
||||
gcc_unreachable ();
|
||||
}
|
||||
|
||||
/* FROM is to be eliminated for TO. Return the offset so that TO+offset
|
||||
designates the same location as FROM. */
|
||||
|
||||
HOST_WIDE_INT
|
||||
alpha_vms_initial_elimination_offset (unsigned int from, unsigned int to)
|
||||
{
|
||||
/* The only possible attempts we ever expect are ARG or FRAME_PTR to
|
||||
HARD_FRAME or STACK_PTR. We need the alpha_procedure_type to decide
|
||||
on the proper computations and will need the register save area size
|
||||
in most cases. */
|
||||
|
||||
HOST_WIDE_INT sa_size = alpha_sa_size ();
|
||||
|
||||
/* PT_NULL procedures have no frame of their own and we only allow
|
||||
elimination to the stack pointer. This is the argument pointer and we
|
||||
resolve the soft frame pointer to that as well. */
|
||||
|
||||
if (alpha_procedure_type == PT_NULL)
|
||||
return 0;
|
||||
|
||||
/* For a PT_STACK procedure the frame layout looks as follows
|
||||
|
||||
-----> decreasing addresses
|
||||
|
||||
< size rounded up to 16 | likewise >
|
||||
--------------#------------------------------+++--------------+++-------#
|
||||
incoming args # pretended args | "frame" | regs sa | PV | outgoing args #
|
||||
--------------#---------------------------------------------------------#
|
||||
^ ^ ^ ^
|
||||
ARG_PTR FRAME_PTR HARD_FRAME_PTR STACK_PTR
|
||||
|
||||
|
||||
PT_REGISTER procedures are similar in that they may have a frame of their
|
||||
own. They have no regs-sa/pv/outgoing-args area.
|
||||
|
||||
We first compute offset to HARD_FRAME_PTR, then add what we need to get
|
||||
to STACK_PTR if need be. */
|
||||
|
||||
{
|
||||
HOST_WIDE_INT offset;
|
||||
HOST_WIDE_INT pv_save_size = alpha_procedure_type == PT_STACK ? 8 : 0;
|
||||
|
||||
switch (from)
|
||||
{
|
||||
case FRAME_POINTER_REGNUM:
|
||||
offset = ALPHA_ROUND (sa_size + pv_save_size);
|
||||
break;
|
||||
case ARG_POINTER_REGNUM:
|
||||
offset = (ALPHA_ROUND (sa_size + pv_save_size
|
||||
+ get_frame_size ()
|
||||
+ crtl->args.pretend_args_size)
|
||||
- crtl->args.pretend_args_size);
|
||||
break;
|
||||
default:
|
||||
gcc_unreachable ();
|
||||
}
|
||||
|
||||
if (to == STACK_POINTER_REGNUM)
|
||||
offset += ALPHA_ROUND (crtl->outgoing_args_size);
|
||||
|
||||
return offset;
|
||||
}
|
||||
}
|
||||
|
||||
#define COMMON_OBJECT "common_object"
|
||||
|
||||
static tree
|
||||
|
@ -144,27 +144,12 @@ along with GCC; see the file COPYING3. If not see
|
||||
|
||||
#undef CAN_ELIMINATE
|
||||
#define CAN_ELIMINATE(FROM, TO) \
|
||||
((TO) != STACK_POINTER_REGNUM || ! alpha_using_fp ())
|
||||
(alpha_vms_can_eliminate ((FROM), (TO)))
|
||||
|
||||
#undef INITIAL_ELIMINATION_OFFSET
|
||||
#define INITIAL_ELIMINATION_OFFSET(FROM, TO, OFFSET) \
|
||||
{ switch (FROM) \
|
||||
{ \
|
||||
case FRAME_POINTER_REGNUM: \
|
||||
(OFFSET) = alpha_sa_size () + alpha_pv_save_size (); \
|
||||
break; \
|
||||
case ARG_POINTER_REGNUM: \
|
||||
(OFFSET) = (ALPHA_ROUND (alpha_sa_size () + alpha_pv_save_size () \
|
||||
+ get_frame_size () \
|
||||
+ crtl->args.pretend_args_size) \
|
||||
- crtl->args.pretend_args_size); \
|
||||
break; \
|
||||
default: \
|
||||
gcc_unreachable (); \
|
||||
} \
|
||||
if ((TO) == STACK_POINTER_REGNUM) \
|
||||
(OFFSET) += ALPHA_ROUND (crtl->outgoing_args_size); \
|
||||
}
|
||||
((OFFSET) = alpha_vms_initial_elimination_offset(FROM, TO))
|
||||
|
||||
|
||||
/* Define a data type for recording info about an argument list
|
||||
during the scan of that argument list. This data type should
|
||||
|
Loading…
Reference in New Issue
Block a user