diff options
author | Richard Henderson <rth@redhat.com> | 2002-09-18 17:37:24 -0700 |
---|---|---|
committer | Richard Henderson <rth@gcc.gnu.org> | 2002-09-18 17:37:24 -0700 |
commit | 1b1f20cab9ba8fea71e43cecfe985eb60e2f59e7 (patch) | |
tree | 1c0bdbce207c01a6f967dd988580a82b62456ac3 /gcc/calls.c | |
parent | 724838b9aa794141c9230c5d72316173752a9875 (diff) | |
download | gcc-1b1f20cab9ba8fea71e43cecfe985eb60e2f59e7.zip gcc-1b1f20cab9ba8fea71e43cecfe985eb60e2f59e7.tar.gz gcc-1b1f20cab9ba8fea71e43cecfe985eb60e2f59e7.tar.bz2 |
calls.c (store_one_arg): Rename default_align to parm_align; always adjust parm_align for downward padding.
* calls.c (store_one_arg): Rename default_align to parm_align;
always adjust parm_align for downward padding.
From-SVN: r57292
Diffstat (limited to 'gcc/calls.c')
-rw-r--r-- | gcc/calls.c | 32 |
1 files changed, 20 insertions, 12 deletions
diff --git a/gcc/calls.c b/gcc/calls.c index 578bd98..97e7e04 100644 --- a/gcc/calls.c +++ b/gcc/calls.c @@ -4491,7 +4491,7 @@ store_one_arg (arg, argblock, flags, variable_size, reg_parm_stack_space) { /* BLKmode, at least partly to be pushed. */ - unsigned int default_align = PARM_BOUNDARY; + unsigned int parm_align; int excess; rtx size_rtx; @@ -4499,13 +4499,6 @@ store_one_arg (arg, argblock, flags, variable_size, reg_parm_stack_space) If part is passed in registers, PARTIAL says how much and emit_push_insn will take care of putting it there. */ -#ifdef ARGS_GROW_DOWNWARD - /* When an argument is padded down, the block is not aligned to - PARM_BOUNDARY. */ - if (FUNCTION_ARG_PADDING (arg->mode, TREE_TYPE (pval)) == downward) - default_align = BITS_PER_UNIT; -#endif - /* Round its size up to a multiple of the allocation unit for arguments. */ @@ -4524,6 +4517,23 @@ store_one_arg (arg, argblock, flags, variable_size, reg_parm_stack_space) NULL_RTX, TYPE_MODE (sizetype), 0); } + /* Some types will require stricter alignment, which will be + provided for elsewhere in argument layout. */ + parm_align = MAX (PARM_BOUNDARY, TYPE_ALIGN (TREE_TYPE (pval))); + + /* When an argument is padded down, the block is aligned to + PARM_BOUNDARY, but the actual argument isn't. */ + if (FUNCTION_ARG_PADDING (arg->mode, TREE_TYPE (pval)) == downward) + { + if (arg->size.var) + parm_align = BITS_PER_UNIT; + else if (excess) + { + int excess_align = (excess & -excess) * BITS_PER_UNIT; + parm_align = MIN (parm_align, excess_align); + } + } + if ((flags & ECF_SIBCALL) && GET_CODE (arg->value) == MEM) { /* emit_push_insn might not work properly if arg->value and @@ -4581,8 +4591,7 @@ store_one_arg (arg, argblock, flags, variable_size, reg_parm_stack_space) { rtx size_rtx1 = GEN_INT (reg_parm_stack_space - arg->offset.constant); emit_push_insn (arg->value, arg->mode, TREE_TYPE (pval), size_rtx1, - MAX (default_align, TYPE_ALIGN (TREE_TYPE (pval))), - partial, reg, excess, argblock, + parm_align, partial, reg, excess, argblock, ARGS_SIZE_RTX (arg->offset), reg_parm_stack_space, ARGS_SIZE_RTX (arg->alignment_pad)); } @@ -4590,8 +4599,7 @@ store_one_arg (arg, argblock, flags, variable_size, reg_parm_stack_space) emit_push_insn (arg->value, arg->mode, TREE_TYPE (pval), size_rtx, - MAX (default_align, TYPE_ALIGN (TREE_TYPE (pval))), - partial, reg, excess, argblock, + parm_align, partial, reg, excess, argblock, ARGS_SIZE_RTX (arg->offset), reg_parm_stack_space, ARGS_SIZE_RTX (arg->alignment_pad)); |