Index: arm.c =================================================================== RCS file: /cvsroot/gcc/gcc/gcc/config/arm/arm.c,v retrieving revision 1.456 diff -c -3 -p -r1.456 arm.c *** arm.c 9 May 2005 22:09:47 -0000 1.456 --- arm.c 13 May 2005 17:56:11 -0000 *************** static int thumb_far_jump_used_p (void); *** 73,78 **** --- 73,79 ---- static bool thumb_force_lr_save (void); static int const_ok_for_op (HOST_WIDE_INT, enum rtx_code); static rtx emit_sfm (int, int); + static int arm_size_return_regs (void); #ifndef AOF_ASSEMBLER static bool arm_assemble_integer (rtx, unsigned int, int); #endif *************** use_return_insn (int iscond, rtx sibling *** 1465,1473 **** if (!call_used_regs[3]) return 0; ! /* ... that it isn't being used for a return value (always true ! until we implement return-in-regs), or for a tail-call ! argument ... */ if (sibling) { gcc_assert (GET_CODE (sibling) == CALL_INSN); --- 1466,1476 ---- if (!call_used_regs[3]) return 0; ! /* ... that it isn't being used for a return value ... */ ! if (arm_size_return_regs () >= (4 * UNITS_PER_WORD)) ! return 0; ! ! /* ... or for a tail-call argument ... */ if (sibling) { gcc_assert (GET_CODE (sibling) == CALL_INSN); *************** emit_multi_reg_push (unsigned long mask) *** 9845,9850 **** --- 9848,9867 ---- return par; } + /* Calculate the size of the return value that is passed in registers. */ + static int + arm_size_return_regs (void) + { + enum machine_mode mode; + + if (current_function_return_rtx != 0) + mode = GET_MODE (current_function_return_rtx); + else + mode = DECL_MODE (DECL_RESULT (current_function_decl)); + + return GET_MODE_SIZE (mode); + } + static rtx emit_sfm (int base_reg, int count) { *************** thumb_unexpanded_epilogue (void) *** 12914,12926 **** This is more reliable that examining regs_ever_live[] because that will be set if the register is ever used in the function, not just if the register is used to hold a return value. */ ! ! if (current_function_return_rtx != 0) ! mode = GET_MODE (current_function_return_rtx); ! else ! mode = DECL_MODE (DECL_RESULT (current_function_decl)); ! ! size = GET_MODE_SIZE (mode); /* The prolog may have pushed some high registers to use as work registers. e.g. the testsuite file: --- 12931,12937 ---- This is more reliable that examining regs_ever_live[] because that will be set if the register is ever used in the function, not just if the register is used to hold a return value. */ ! size = arm_size_return_regs (); /* The prolog may have pushed some high registers to use as work registers. e.g. the testsuite file: