summaryrefslogtreecommitdiff
path: root/gcc/ipa-polymorphic-call.c
diff options
context:
space:
mode:
authorJan Hubicka <hubicka@ucw.cz>2015-11-06 17:04:38 +0100
committerJan Hubicka <hubicka@gcc.gnu.org>2015-11-06 16:04:38 +0000
commit567700fddd2cbc1d90bb8f2acae81b3210dba2fb (patch)
tree3f1b62e0829f2a22ffd60ffa7837118243d314e2 /gcc/ipa-polymorphic-call.c
parent563407398727d5943aa1b16320483d9e275cc11d (diff)
re PR ipa/68057 (450.soplex in SPEC CPU 2006 failed to build)
PR ipa/68057 PR ipa/68220 * ipa-polymorphic-call.c (ipa_polymorphic_call_context::restrict_to_inner_type): Fix ordering issue when offset is out of range. (contains_type_p): Fix out of range check, clear dynamic flag. * g++.dg/lto/pr68057_0.C: New testcase. * g++.dg/lto/pr68057_1.C: New testcase. * g++.dg/torture/pr68220.C: New testcase. From-SVN: r229859
Diffstat (limited to 'gcc/ipa-polymorphic-call.c')
-rw-r--r--gcc/ipa-polymorphic-call.c21
1 files changed, 14 insertions, 7 deletions
diff --git a/gcc/ipa-polymorphic-call.c b/gcc/ipa-polymorphic-call.c
index 2f284950d8d..5730e46069f 100644
--- a/gcc/ipa-polymorphic-call.c
+++ b/gcc/ipa-polymorphic-call.c
@@ -154,6 +154,8 @@ ipa_polymorphic_call_context::restrict_to_inner_class (tree otr_type,
&& tree_to_shwi (TYPE_SIZE (outer_type)) >= 0
&& tree_to_shwi (TYPE_SIZE (outer_type)) <= offset)
{
+ bool der = maybe_derived_type; /* clear_outer_type will reset it. */
+ bool dyn = dynamic;
clear_outer_type (otr_type);
type = otr_type;
cur_offset = 0;
@@ -162,7 +164,7 @@ ipa_polymorphic_call_context::restrict_to_inner_class (tree otr_type,
For dynamic types, we really do not have information about
size of the memory location. It is possible that completely
different type is stored after outer_type. */
- if (!maybe_derived_type && !dynamic)
+ if (!der && !dyn)
{
clear_speculation ();
invalid = true;
@@ -425,8 +427,10 @@ no_useful_type_info:
return true;
}
else
- clear_speculation ();
- return true;
+ {
+ clear_speculation ();
+ return true;
+ }
}
else
{
@@ -459,15 +463,18 @@ contains_type_p (tree outer_type, HOST_WIDE_INT offset,
if (offset < 0)
return false;
if (TYPE_SIZE (outer_type) && TYPE_SIZE (otr_type)
- && TREE_CODE (outer_type) == INTEGER_CST
- && TREE_CODE (otr_type) == INTEGER_CST
- && wi::ltu_p (wi::to_offset (outer_type), (wi::to_offset (otr_type) + offset)))
+ && TREE_CODE (TYPE_SIZE (outer_type)) == INTEGER_CST
+ && TREE_CODE (TYPE_SIZE (otr_type)) == INTEGER_CST
+ && wi::ltu_p (wi::to_offset (TYPE_SIZE (outer_type)),
+ (wi::to_offset (TYPE_SIZE (otr_type)) + offset)))
return false;
context.offset = offset;
context.outer_type = TYPE_MAIN_VARIANT (outer_type);
context.maybe_derived_type = false;
- return context.restrict_to_inner_class (otr_type, consider_placement_new, consider_bases);
+ context.dynamic = false;
+ return context.restrict_to_inner_class (otr_type, consider_placement_new,
+ consider_bases);
}