+ /* Special handling is required if part of the parameter lies in the
+ register parameter area. The argument may be copied into the stack
+ slot using memcpy(), but the original contents of the register
+ parameter area will be restored after the memcpy() call.
+
+ To ensure that the part that lies in the register parameter area
+ is copied correctly, we emit a separate push for that part. This
+ push should be small enough to avoid a call to memcpy(). */
+#ifndef STACK_PARMS_IN_REG_PARM_AREA
+ if (arg->reg && arg->pass_on_stack)
+#else
+ if (1)
+#endif
+ {
+ if (arg->offset.constant < reg_parm_stack_space && arg->offset.var)
+ error ("variable offset is passed partially in stack and in reg");
+ else if (arg->offset.constant < reg_parm_stack_space && arg->size.var)
+ error ("variable size is passed partially in stack and in reg");
+ else if (arg->offset.constant < reg_parm_stack_space
+ && ((arg->offset.constant + arg->size.constant)
+ > 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,
+ TYPE_ALIGN (TREE_TYPE (pval)), partial, reg,
+ excess, argblock, ARGS_SIZE_RTX (arg->offset),
+ reg_parm_stack_space,
+ ARGS_SIZE_RTX (arg->alignment_pad));
+ }
+ }
+
+