From: James E. Wilson Date: Thu, 8 Jun 2000 17:15:32 +0000 (+0000) Subject: Add unwind support for epilogues, because the kernel unwinder needs them. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=0186257f7898165091cde0d6e6f307862966fa2a;p=gcc.git Add unwind support for epilogues, because the kernel unwinder needs them. * config/ia64/ia64-protos.h (ia64_output_end_prologue): Add. (output_function_prologue): Fix mispelling. (output_function_prologue, output_function_epilogue): Reorder to match ia64.c definition order. * config/ia64/ia64.c (ia64_expand_prologue): Add comment. (ia64_expand_epilogue): Set RTX_FRAME_RELATED_P on stack restore insns. Use r3 instead of r2 for large stack restores. (ia64_output_end_prologue): New function. (process_set): Emit ".restore sp" for epilogue stack restores. * config/ia64/ia64.h (FUNCTION_END_PROLOGUE): Define. From-SVN: r34456 --- diff --git a/gcc/ChangeLog b/gcc/ChangeLog index b47a92af027..18956ddb437 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,16 @@ +2000-06-08 James E. Wilson + + * config/ia64/ia64-protos.h (ia64_output_end_prologue): Add. + (output_function_prologue): Fix mispelling. + (output_function_prologue, output_function_epilogue): Reorder to + match ia64.c definition order. + * config/ia64/ia64.c (ia64_expand_prologue): Add comment. + (ia64_expand_epilogue): Set RTX_FRAME_RELATED_P on stack restore insns. + Use r3 instead of r2 for large stack restores. + (ia64_output_end_prologue): New function. + (process_set): Emit ".restore sp" for epilogue stack restores. + * config/ia64/ia64.h (FUNCTION_END_PROLOGUE): Define. + 2000-06-08 Jakub Jelinek * dbxout.c (dbxout_type_fields): Don't segfault on fields with diff --git a/gcc/config/ia64/ia64-protos.h b/gcc/config/ia64/ia64-protos.h index ec820b1aaa6..7c4c5faadda 100644 --- a/gcc/config/ia64/ia64-protos.h +++ b/gcc/config/ia64/ia64-protos.h @@ -92,11 +92,12 @@ extern void ia64_encode_section_info PARAMS((tree)); extern int ia64_epilogue_uses PARAMS((int)); extern void ia64_expand_prologue PARAMS((void)); extern void ia64_expand_epilogue PARAMS((void)); +extern void ia64_function_prologue PARAMS((FILE *, int)); +extern void ia64_output_end_prologue PARAMS((FILE *)); +extern void ia64_function_epilogue PARAMS((FILE *, int)); extern int ia64_direct_return PARAMS((void)); extern int ia64_rap_fp_offset PARAMS((void)); extern void ia64_init_builtins PARAMS((void)); extern void ia64_override_options PARAMS((void)); extern unsigned int ia64_compute_frame_size PARAMS((int)); extern void save_restore_insns PARAMS((int)); -extern void ia64_function_prologue PARAMS((FILE *, int)); -extern void ia64_funtion_epilogue PARAMS((FILE *, int)); diff --git a/gcc/config/ia64/ia64.c b/gcc/config/ia64/ia64.c index e9eade30b93..43ffdcbed61 100644 --- a/gcc/config/ia64/ia64.c +++ b/gcc/config/ia64/ia64.c @@ -1001,6 +1001,8 @@ ia64_expand_prologue () offset = GEN_INT (-frame_size); else { + /* ??? We use r2 to tell process_set that this is a stack pointer + decrement. See also ia64_expand_epilogue. */ offset = gen_rtx_REG (DImode, GR_REG (2)); insn = emit_insn (gen_movdi (offset, GEN_INT (-frame_size))); RTX_FRAME_RELATED_P (insn) = 1; @@ -1033,6 +1035,8 @@ ia64_expand_prologue () void ia64_expand_epilogue () { + rtx insn; + /* Restore registers from frame. */ save_restore_insns (0); @@ -1053,8 +1057,10 @@ ia64_expand_epilogue () /* If there is a frame pointer, then we need to make the stack pointer restore depend on the frame pointer, so that the stack pointer restore won't be moved up past fp-relative loads from the frame. */ - emit_insn (gen_epilogue_deallocate_stack (stack_pointer_rtx, - hard_frame_pointer_rtx)); + insn + = emit_insn (gen_epilogue_deallocate_stack (stack_pointer_rtx, + hard_frame_pointer_rtx)); + RTX_FRAME_RELATED_P (insn) = 1; } else { @@ -1067,11 +1073,14 @@ ia64_expand_epilogue () offset = GEN_INT (frame_size); else { - offset = gen_rtx_REG (DImode, GR_REG (2)); + /* ??? We use r3 to tell process_set that this is a stack + pointer increment. See also ia64_expand_prologue. */ + offset = gen_rtx_REG (DImode, GR_REG (3)); emit_insn (gen_movdi (offset, GEN_INT (frame_size))); } - emit_insn (gen_adddi3 (stack_pointer_rtx, stack_pointer_rtx, - offset)); + insn = emit_insn (gen_adddi3 (stack_pointer_rtx, stack_pointer_rtx, + offset)); + RTX_FRAME_RELATED_P (insn) = 1; } } } @@ -1136,6 +1145,18 @@ ia64_function_prologue (file, size) fprintf (file, "\t.prologue\n"); } +/* Emit the .body directive at the scheduled end of the prologue. */ + +void +ia64_output_end_prologue (file) + FILE *file; +{ + if (!flag_unwind_tables && (!flag_exceptions || exceptions_via_longjmp)) + return; + + fputs ("\t.body\n", file); +} + /* Emit the function epilogue. */ void @@ -3021,19 +3042,40 @@ process_set (asm_out_file, pat) rtx op1 = XEXP (src, 1); if (op0 == dest && GET_CODE (op1) == CONST_INT) { - fputs ("\t.fframe ", asm_out_file); - fprintf (asm_out_file, HOST_WIDE_INT_PRINT_DEC, -INTVAL (op1)); - fputc ('\n', asm_out_file); - frame_size = INTVAL (op1); - return 1; + if (INTVAL (op1) < 0) + { + fputs ("\t.fframe ", asm_out_file); + fprintf (asm_out_file, HOST_WIDE_INT_PRINT_DEC, + -INTVAL (op1)); + fputc ('\n', asm_out_file); + frame_size = INTVAL (op1); + } + else + fprintf (asm_out_file, "\t.restore sp\n"); } else if (op0 == dest && GET_CODE (op1) == REG) { - fprintf (asm_out_file, "\t.vframe r%d\n", REGNO (op1)); - frame_size = 0; - return 1; + /* ia64_expand_prologue uses r2 for stack pointer decrements, + ia64_expand_epilogue uses r3 for stack pointer increments. */ + if (REGNO (op1) == GR_REG (2)) + { + fprintf (asm_out_file, "\t.vframe r%d\n", REGNO (op1)); + frame_size = 0; + } + else if (REGNO (op1) == GR_REG (3)) + fprintf (asm_out_file, "\t.restore sp\n"); + else + abort (); } + else + abort (); } + else if (GET_CODE (src) == REG && REGNO (src) == FRAME_POINTER_REGNUM) + fprintf (asm_out_file, "\t.restore sp\n"); + else + abort (); + + return 1; } /* Look for a frame offset. */ if (GET_CODE (dest) == REG) diff --git a/gcc/config/ia64/ia64.h b/gcc/config/ia64/ia64.h index 6ea12dcc9ee..cc5ba5b214d 100644 --- a/gcc/config/ia64/ia64.h +++ b/gcc/config/ia64/ia64.h @@ -1464,6 +1464,10 @@ do { \ #define FUNCTION_PROLOGUE(FILE, SIZE) \ ia64_function_prologue (FILE, SIZE) +/* This macro notes the end of the prologue. */ + +#define FUNCTION_END_PROLOGUE(FILE) ia64_output_end_prologue (FILE) + /* Define this macro as a C expression that is nonzero if the return instruction or the function epilogue ignores the value of the stack pointer; in other words, if it is safe to delete an instruction to adjust the stack