calls.c (alloca_call_p): New global function.

* calls.c (alloca_call_p): New global function.
	* tree.h (alloca_call_p): New.
	* tree-inline.c (inlinable_function_p):  Do not inline when
	function calls alloca.
	(find_alloca_call, find_alloca_call_1): New functions.

From-SVN: r59228
This commit is contained in:
Jan Hubicka 2002-11-18 20:30:34 +01:00 committed by Jan Hubicka
parent 5602b49d69
commit c986baf631
4 changed files with 54 additions and 0 deletions

View File

@ -1,3 +1,11 @@
Sun Nov 17 00:01:28 CET 2002 Jan Hubicka <jh@suse.cz>
* calls.c (alloca_call_p): New global function.
* tree.h (alloca_call_p): New.
* tree-inline.c (inlinable_function_p): Do not inline when
function calls alloca.
(find_alloca_call, find_alloca_call_1): New functions.
2002-11-18 Kazu Hirata <kazu@cs.umass.edu>
* config/h8300/h8300.md (*andorqi3): Use bor between bld and

View File

@ -801,6 +801,21 @@ setjmp_call_p (fndecl)
return special_function_p (fndecl, 0) & ECF_RETURNS_TWICE;
}
/* Return true when exp contains alloca call. */
bool
alloca_call_p (exp)
tree exp;
{
if (TREE_CODE (exp) == CALL_EXPR
&& TREE_CODE (TREE_OPERAND (exp, 0)) == ADDR_EXPR
&& (TREE_CODE (TREE_OPERAND (TREE_OPERAND (exp, 0), 0))
== FUNCTION_DECL)
&& (special_function_p (TREE_OPERAND (TREE_OPERAND (exp, 0), 0),
0) & ECF_MAY_BE_ALLOCA))
return true;
return false;
}
/* Detect flags (function attributes) from the function decl or type node. */
static int

View File

@ -122,6 +122,8 @@ static void copy_scope_stmt PARAMS ((tree *, int *, inline_data *));
static tree initialize_inlined_parameters PARAMS ((inline_data *, tree, tree, tree));
static void remap_block PARAMS ((tree *, tree, inline_data *));
static tree add_stmt_to_compound PARAMS ((tree, tree, tree));
static tree find_alloca_call_1 PARAMS ((tree *, int *, void *));
static tree find_alloca_call PARAMS ((tree));
#endif /* INLINER_FOR_JAVA */
/* The approximate number of instructions per statement. This number
@ -857,6 +859,27 @@ tree_inlinable_function_p (fn)
return inlinable_function_p (fn, NULL);
}
/* if *TP is possibly call to alloca, return nonzero. */
static tree
find_alloca_call_1 (tp, walk_subtrees, data)
tree *tp;
int *walk_subtrees ATTRIBUTE_UNUSED;
void *data ATTRIBUTE_UNUSED;
{
if (alloca_call_p (*tp))
return *tp;
return NULL;
}
/* Return subexpression representing possible alloca call,
if any. */
static tree
find_alloca_call (exp)
tree exp;
{
return walk_tree (&exp, find_alloca_call_1, NULL, NULL);
}
/* Returns nonzero if FN is a function that can be inlined into the
inlining context ID_. If ID_ is NULL, check whether the function
can be inlined at all. */
@ -897,6 +920,13 @@ inlinable_function_p (fn, id)
else if (! (*lang_hooks.tree_inlining.disregard_inline_limits) (fn)
&& currfn_insns > MAX_INLINE_INSNS_SINGLE)
;
/* Refuse to inline alloca call unless user explicitly forced so as this may
change program's memory overhead drastically when the function using alloca
is called in loop. In GCC present in SPEC2000 inlining into schedule_block
cause it to require 2GB of ram instead of 256MB. */
else if (lookup_attribute ("always_inline", DECL_ATTRIBUTES (fn)) == NULL
&& find_alloca_call (DECL_SAVED_TREE (fn)))
;
/* All is well. We can inline this function. Traditionally, GCC
has refused to inline functions using alloca, or functions whose
values are returned in a PARALLEL, and a few other such obscure

View File

@ -3018,6 +3018,7 @@ extern rtx emit_line_note PARAMS ((const char *, int));
/* In calls.c */
extern int setjmp_call_p PARAMS ((tree));
extern bool alloca_call_p PARAMS ((tree));
/* In attribs.c. */