aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJan Hubicka <jh@suse.cz>2008-02-19 18:09:42 +0100
committerJan Hubicka <hubicka@gcc.gnu.org>2008-02-19 17:09:42 +0000
commit8723e2fedf070eeea2d16e68f4baf2295d9a94e8 (patch)
tree1fe672986c3dc436f7d252f138457d6ff2315160
parent5ba5440f24b648e4d52d4e38b1e73084199c5325 (diff)
downloadgcc-8723e2fedf070eeea2d16e68f4baf2295d9a94e8.zip
gcc-8723e2fedf070eeea2d16e68f4baf2295d9a94e8.tar.gz
gcc-8723e2fedf070eeea2d16e68f4baf2295d9a94e8.tar.bz2
re PR middle-end/28779 (internal compiler error: in cgraph_estimate_size_after_inlining, at ipa-inline.c:106)
PR middle-end/28779 * tree-inline.c (estimate_num_insns_1): Fix counting of cost of call_expr. From-SVN: r132439
-rw-r--r--gcc/ChangeLog5
-rw-r--r--gcc/tree-inline.c34
2 files changed, 31 insertions, 8 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 2282f15..1589844 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,8 @@
+2008-02-19 Jan Hubicka <jh@suse.cz>
+
+ PR middle-end/28779
+ * tree-inline.c (estimate_num_insns_1): Fix counting of cost of call_expr.
+
2008-02-19 H.J. Lu <hongjiu.lu@intel.com>
PR Ada/35186
diff --git a/gcc/tree-inline.c b/gcc/tree-inline.c
index b683f20..201f2cf 100644
--- a/gcc/tree-inline.c
+++ b/gcc/tree-inline.c
@@ -2434,6 +2434,11 @@ estimate_num_insns_1 (tree *tp, int *walk_subtrees, void *data)
case CALL_EXPR:
{
tree decl = get_callee_fndecl (x);
+ tree addr = CALL_EXPR_FN (x);
+ tree funtype = TREE_TYPE (addr);
+
+ gcc_assert (POINTER_TYPE_P (funtype));
+ funtype = TREE_TYPE (funtype);
if (decl && DECL_BUILT_IN_CLASS (decl) == BUILT_IN_MD)
cost = d->weights->target_builtin_call_cost;
@@ -2456,21 +2461,34 @@ estimate_num_insns_1 (tree *tp, int *walk_subtrees, void *data)
break;
}
+ if (decl)
+ funtype = TREE_TYPE (decl);
+
/* Our cost must be kept in sync with cgraph_estimate_size_after_inlining
- that does use function declaration to figure out the arguments. */
- if (!decl)
+ that does use function declaration to figure out the arguments.
+
+ When we deal with function with no body nor prototype, base estimates on
+ actual parameters of the call expression. Otherwise use either the actual
+ arguments types or function declaration for more precise answer. */
+ if (decl && DECL_ARGUMENTS (decl))
+ {
+ tree arg;
+ for (arg = DECL_ARGUMENTS (decl); arg; arg = TREE_CHAIN (arg))
+ d->count += estimate_move_cost (TREE_TYPE (arg));
+ }
+ else if (funtype && prototype_p (funtype))
+ {
+ tree t;
+ for (t = TYPE_ARG_TYPES (funtype); t; t = TREE_CHAIN (t))
+ d->count += estimate_move_cost (TREE_VALUE (t));
+ }
+ else
{
tree a;
call_expr_arg_iterator iter;
FOR_EACH_CALL_EXPR_ARG (a, iter, x)
d->count += estimate_move_cost (TREE_TYPE (a));
}
- else
- {
- tree arg;
- for (arg = DECL_ARGUMENTS (decl); arg; arg = TREE_CHAIN (arg))
- d->count += estimate_move_cost (TREE_TYPE (arg));
- }
d->count += cost;
break;