Commit b6128b8c by Stuart Hastings Committed by Stan Shebs

function.h (struct function): Add flag all_throwers_are_sibcalls.

2002-08-24  Stuart Hastings  <stuart@apple.com>

        * function.h (struct function): Add flag
        all_throwers_are_sibcalls.
        * except.c (set_nothrow_function_flags): Replaces
        nothrow_function_p. Set new flag.
        * except.h (set_nothrow_function_flags): Replaces
        nothrow_function_p.
        * dwarf2out.c (struct dw_fde_struct): Add flag
        all_throwers_are_sibcalls.
        (output_call_frame_info): Test it.
        (dwarf2out_begin_prologue) Propagate it from cfun to
        dw_fde_struct.
        * toplev.c (rest_of_compilation): Update calls to
        nothrow_function_p.

From-SVN: r56561
parent 13d3f0b6
2002-08-24 Stuart Hastings <stuart@apple.com>
* function.h (struct function): Add flag
all_throwers_are_sibcalls.
* except.c (set_nothrow_function_flags): Replaces
nothrow_function_p. Set new flag.
* except.h (set_nothrow_function_flags): Replaces
nothrow_function_p.
* dwarf2out.c (struct dw_fde_struct): Add flag
all_throwers_are_sibcalls.
(output_call_frame_info): Test it.
(dwarf2out_begin_prologue) Propagate it from cfun to
dw_fde_struct.
* toplev.c (rest_of_compilation): Update calls to
nothrow_function_p.
2002-08-23 Zack Weinberg <zack@codesourcery.com>
* ggc-page.c (compute_inverse): Short circuit calculation for
......
......@@ -203,6 +203,7 @@ typedef struct dw_fde_struct
const char *dw_fde_end;
dw_cfi_ref dw_fde_cfi;
unsigned funcdef_number;
unsigned all_throwers_are_sibcalls : 1;
unsigned nothrow : 1;
unsigned uses_eh_lsda : 1;
}
......@@ -1952,8 +1953,9 @@ output_call_frame_info (for_eh)
fde = &fde_table[i];
/* Don't emit EH unwind info for leaf functions that don't need it. */
if (!flag_asynchronous_unwind_tables && for_eh && fde->nothrow
&& ! fde->uses_eh_lsda)
if (!flag_asynchronous_unwind_tables && for_eh
&& (fde->nothrow || fde->all_throwers_are_sibcalls)
&& !fde->uses_eh_lsda)
continue;
ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, FDE_LABEL, for_eh + i * 2);
......@@ -2115,6 +2117,7 @@ dwarf2out_begin_prologue (line, file)
fde->funcdef_number = current_function_funcdef_no;
fde->nothrow = current_function_nothrow;
fde->uses_eh_lsda = cfun->uses_eh_lsda;
fde->all_throwers_are_sibcalls = cfun->all_throwers_are_sibcalls;
args_size = old_args_size = 0;
......
......@@ -2893,25 +2893,50 @@ can_throw_external (insn)
return true;
}
/* True if nothing in this function can throw outside this function. */
/* Set current_function_nothrow and cfun->all_throwers_are_sibcalls. */
bool
nothrow_function_p ()
void
set_nothrow_function_flags ()
{
rtx insn;
current_function_nothrow = 1;
if (! flag_exceptions)
return true;
/* Assume cfun->all_throwers_are_sibcalls until we encounter
something that can throw an exception. We specifically exempt
CALL_INSNs that are SIBLING_CALL_P, as these are really jumps,
and can't throw. Most CALL_INSNs are not SIBLING_CALL_P, so this
is optimistic. */
cfun->all_throwers_are_sibcalls = 1;
if (! flag_exceptions)
return;
for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
if (can_throw_external (insn))
return false;
{
current_function_nothrow = 0;
if (GET_CODE (insn) != CALL_INSN || !SIBLING_CALL_P (insn))
{
cfun->all_throwers_are_sibcalls = 0;
return;
}
}
for (insn = current_function_epilogue_delay_list; insn;
insn = XEXP (insn, 1))
if (can_throw_external (XEXP (insn, 0)))
return false;
if (can_throw_external (insn))
{
current_function_nothrow = 0;
return true;
if (GET_CODE (insn) != CALL_INSN || !SIBLING_CALL_P (insn))
{
cfun->all_throwers_are_sibcalls = 0;
return;
}
}
}
......
......@@ -91,8 +91,8 @@ extern void for_each_eh_label PARAMS ((void (*) (rtx)));
extern bool can_throw_internal PARAMS ((rtx));
extern bool can_throw_external PARAMS ((rtx));
/* Return nonzero if nothing in this function can throw. */
extern bool nothrow_function_p PARAMS ((void));
/* Set current_function_nothrow and cfun->all_throwers_are_sibcalls. */
extern void set_nothrow_function_flags PARAMS ((void));
/* After initial rtl generation, call back to finish generating
exception support code. */
......
......@@ -437,6 +437,13 @@ struct function GTY(())
we should try to cut corners where we can. */
unsigned int is_thunk : 1;
/* This bit is used by the exception handling logic. It is set if all
calls (if any) are sibling calls. Such functions do not have to
have EH tables generated, as they cannot throw. A call to such a
function, however, should be treated as throwing if any of its callees
can throw. */
unsigned int all_throwers_are_sibcalls : 1;
/* Nonzero if instrumentation calls for function entry and exit should be
generated. */
unsigned int instrument_entry_exit : 1;
......
......@@ -2506,7 +2506,7 @@ rest_of_compilation (decl)
free_bb_for_insn ();
}
current_function_nothrow = nothrow_function_p ();
set_nothrow_function_flags ();
if (current_function_nothrow)
/* Now we know that this can't throw; set the flag for the benefit
of other functions later in this translation unit. */
......@@ -3528,7 +3528,7 @@ rest_of_compilation (decl)
shorten_branches (get_insns ());
timevar_pop (TV_SHORTEN_BRANCH);
current_function_nothrow = nothrow_function_p ();
set_nothrow_function_flags ();
if (current_function_nothrow)
/* Now we know that this can't throw; set the flag for the benefit
of other functions later in this translation unit. */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment