Commit 8e926cb1 by Jan Hubicka Committed by Jan Hubicka

ipa-inline.c (check_maybe_up, [...]): New macros.


	* ipa-inline.c (check_maybe_up, check_maybe_down, check_match):
	New macros.
	(can_inline_edge_p): Relax option matching for always inline functions.

From-SVN: r221714
parent 06d75031
2015-03-26 Jan Hubicka <hubicka@ucw.cz>
* ipa-inline.c (check_maybe_up, check_maybe_down, check_match):
New macros.
(can_inline_edge_p): Relax option matching for always inline functions.
2015-03-26 Uros Bizjak <ubizjak@gmail.com> 2015-03-26 Uros Bizjak <ubizjak@gmail.com>
PR target/65561 PR target/65561
......
...@@ -298,6 +298,27 @@ sanitize_attrs_match_for_inline_p (const_tree caller, const_tree callee) ...@@ -298,6 +298,27 @@ sanitize_attrs_match_for_inline_p (const_tree caller, const_tree callee)
DECL_ATTRIBUTES (callee)); DECL_ATTRIBUTES (callee));
} }
/* Used for flags where it is safe to inline when caller's value is
grater than callee's. */
#define check_maybe_up(flag) \
(opts_for_fn (caller->decl)->x_##flag \
!= opts_for_fn (callee->decl)->x_##flag \
&& (!always_inline \
|| opts_for_fn (caller->decl)->x_##flag \
< opts_for_fn (callee->decl)->x_##flag))
/* Used for flags where it is safe to inline when caller's value is
smaller than callee's. */
#define check_maybe_down(flag) \
(opts_for_fn (caller->decl)->x_##flag \
!= opts_for_fn (callee->decl)->x_##flag \
&& (!always_inline \
|| opts_for_fn (caller->decl)->x_##flag \
> opts_for_fn (callee->decl)->x_##flag))
/* Used for flags where exact match is needed for correctness. */
#define check_match(flag) \
(opts_for_fn (caller->decl)->x_##flag \
!= opts_for_fn (callee->decl)->x_##flag)
/* Decide if we can inline the edge and possibly update /* Decide if we can inline the edge and possibly update
inline_failed reason. inline_failed reason.
We check whether inlining is possible at all and whether We check whether inlining is possible at all and whether
...@@ -401,74 +422,60 @@ can_inline_edge_p (struct cgraph_edge *e, bool report, ...@@ -401,74 +422,60 @@ can_inline_edge_p (struct cgraph_edge *e, bool report,
optimization attribute. */ optimization attribute. */
else if (caller_tree != callee_tree) else if (caller_tree != callee_tree)
{ {
bool always_inline =
(DECL_DISREGARD_INLINE_LIMITS (callee->decl)
&& lookup_attribute ("always_inline",
DECL_ATTRIBUTES (callee->decl)));
/* There are some options that change IL semantics which means /* There are some options that change IL semantics which means
we cannot inline in these cases for correctness reason. we cannot inline in these cases for correctness reason.
Not even for always_inline declared functions. */ Not even for always_inline declared functions. */
/* Strictly speaking only when the callee contains signed integer /* Strictly speaking only when the callee contains signed integer
math where overflow is undefined. */ math where overflow is undefined. */
if ((opt_for_fn (caller->decl, flag_strict_overflow) if ((check_maybe_up (flag_strict_overflow)
!= opt_for_fn (callee->decl, flag_strict_overflow)) /* this flag is set by optimize. Allow inlining across
|| (opt_for_fn (caller->decl, flag_wrapv) optimize boundary. */
!= opt_for_fn (callee->decl, flag_wrapv)) && (!opt_for_fn (caller->decl, optimize)
|| (opt_for_fn (caller->decl, flag_trapv) == !opt_for_fn (callee->decl, optimize) || !always_inline))
!= opt_for_fn (callee->decl, flag_trapv)) || check_match (flag_wrapv)
|| check_match (flag_trapv)
/* Strictly speaking only when the callee contains memory /* Strictly speaking only when the callee contains memory
accesses that are not using alias-set zero anyway. */ accesses that are not using alias-set zero anyway. */
|| (opt_for_fn (caller->decl, flag_strict_aliasing) || check_maybe_down (flag_strict_aliasing)
!= opt_for_fn (callee->decl, flag_strict_aliasing))
/* Strictly speaking only when the callee uses FP math. */ /* Strictly speaking only when the callee uses FP math. */
|| (opt_for_fn (caller->decl, flag_rounding_math) || check_maybe_up (flag_rounding_math)
!= opt_for_fn (callee->decl, flag_rounding_math)) || check_maybe_up (flag_trapping_math)
|| (opt_for_fn (caller->decl, flag_trapping_math) || check_maybe_down (flag_unsafe_math_optimizations)
!= opt_for_fn (callee->decl, flag_trapping_math)) || check_maybe_down (flag_finite_math_only)
|| (opt_for_fn (caller->decl, flag_unsafe_math_optimizations) || check_maybe_up (flag_signaling_nans)
!= opt_for_fn (callee->decl, flag_unsafe_math_optimizations)) || check_maybe_down (flag_cx_limited_range)
|| (opt_for_fn (caller->decl, flag_finite_math_only) || check_maybe_up (flag_signed_zeros)
!= opt_for_fn (callee->decl, flag_finite_math_only)) || check_maybe_down (flag_associative_math)
|| (opt_for_fn (caller->decl, flag_signaling_nans) || check_maybe_down (flag_reciprocal_math)
!= opt_for_fn (callee->decl, flag_signaling_nans))
|| (opt_for_fn (caller->decl, flag_cx_limited_range)
!= opt_for_fn (callee->decl, flag_cx_limited_range))
|| (opt_for_fn (caller->decl, flag_signed_zeros)
!= opt_for_fn (callee->decl, flag_signed_zeros))
|| (opt_for_fn (caller->decl, flag_associative_math)
!= opt_for_fn (callee->decl, flag_associative_math))
|| (opt_for_fn (caller->decl, flag_reciprocal_math)
!= opt_for_fn (callee->decl, flag_reciprocal_math))
/* We do not want to make code compiled with exceptions to be brought /* We do not want to make code compiled with exceptions to be brought
into a non-EH function unless we know that the callee does not into a non-EH function unless we know that the callee does not
throw. This is tracked by DECL_FUNCTION_PERSONALITY. */ throw. This is tracked by DECL_FUNCTION_PERSONALITY. */
|| (opt_for_fn (caller->decl, flag_non_call_exceptions) || (check_match (flag_non_call_exceptions)
!= opt_for_fn (callee->decl, flag_non_call_exceptions)
/* TODO: We also may allow bringing !flag_non_call_exceptions /* TODO: We also may allow bringing !flag_non_call_exceptions
to flag_non_call_exceptions function, but that may need to flag_non_call_exceptions function, but that may need
extra work in tree-inline to add the extra EH edges. */ extra work in tree-inline to add the extra EH edges. */
&& (!opt_for_fn (callee->decl, flag_non_call_exceptions) && (!opt_for_fn (callee->decl, flag_non_call_exceptions)
|| DECL_FUNCTION_PERSONALITY (callee->decl))) || DECL_FUNCTION_PERSONALITY (callee->decl)))
|| (!opt_for_fn (caller->decl, flag_exceptions) || (check_maybe_up (flag_exceptions)
&& opt_for_fn (callee->decl, flag_exceptions)
&& DECL_FUNCTION_PERSONALITY (callee->decl)) && DECL_FUNCTION_PERSONALITY (callee->decl))
/* Strictly speaking only when the callee contains function /* Strictly speaking only when the callee contains function
calls that may end up setting errno. */ calls that may end up setting errno. */
|| (opt_for_fn (caller->decl, flag_errno_math) || check_maybe_up (flag_errno_math)
!= opt_for_fn (callee->decl, flag_errno_math))
/* When devirtualization is diabled for callee, it is not safe /* When devirtualization is diabled for callee, it is not safe
to inline it as we possibly mangled the type info. to inline it as we possibly mangled the type info.
Allow early inlining of always inlines. */ Allow early inlining of always inlines. */
|| (opt_for_fn (caller->decl, flag_devirtualize) || (!early && check_maybe_down (flag_devirtualize)))
&& !opt_for_fn (callee->decl, flag_devirtualize)
&& (!early
|| (!DECL_DISREGARD_INLINE_LIMITS (callee->decl)
|| !lookup_attribute ("always_inline",
DECL_ATTRIBUTES (callee->decl))))))
{ {
e->inline_failed = CIF_OPTIMIZATION_MISMATCH; e->inline_failed = CIF_OPTIMIZATION_MISMATCH;
inlinable = false; inlinable = false;
} }
/* gcc.dg/pr43564.c. Apply user-forced inline even at -O0. */ /* gcc.dg/pr43564.c. Apply user-forced inline even at -O0. */
else if (DECL_DISREGARD_INLINE_LIMITS (callee->decl) else if (always_inline)
&& lookup_attribute ("always_inline",
DECL_ATTRIBUTES (callee->decl)))
; ;
/* When user added an attribute to the callee honor it. */ /* When user added an attribute to the callee honor it. */
else if (lookup_attribute ("optimize", DECL_ATTRIBUTES (callee->decl)) else if (lookup_attribute ("optimize", DECL_ATTRIBUTES (callee->decl))
......
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