On Fri, Nov 21, 2014 at 10:59 AM, Martin Jambor <mjam...@suse.cz> wrote: > Hi, > > PR 63814 is caused by cgraph_edge_brings_value_p misidentifying an > edge to an expanded artificial thunk as an edge to the original node, > which then leads to crazy double-cloning and doubling the thunks along > the call. > > This patch fixes the bug by strengthening the predicate so that it > knows where the value is supposed to go and can check that it goes > there and not anywhere else. It also adds an extra availability check > that was probably missing in it. > > Bootstrapped and tested on x86_64-linux, and i686-linux. OK for > trunk? > > Thanks, > > Martin > > > 2014-11-20 Martin Jambor <mjam...@suse.cz> > > PR ipa/63814 > * ipa-cp.c (same_node_or_its_all_contexts_clone_p): New function. > (cgraph_edge_brings_value_p): New parameter dest, use > same_node_or_its_all_contexts_clone_p and check availability. > (cgraph_edge_brings_value_p): Likewise. > (get_info_about_necessary_edges): New parameter dest, pass it to > cgraph_edge_brings_value_p. Update caller. > (gather_edges_for_value): Likewise. > (perhaps_add_new_callers): Use cgraph_edge_brings_value_p to check > both the destination and availability. > >
I checked in this testcase: diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index a17cc6c..1410f10 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2014-12-02 H.J. Lu <hongjiu...@intel.com> + + PR ipa/63814 + * g++.dg/ipa/pr63814.C: New test. + 2014-12-02 Wilco Dijkstra <wilco.dijks...@arm.com> * gcc.target/aarch64/remat1.c: New testcase. diff --git a/gcc/testsuite/g++.dg/ipa/pr63814.C b/gcc/testsuite/g++.dg/ipa/pr63814.C new file mode 100644 index 0000000..15a7dda --- /dev/null +++ b/gcc/testsuite/g++.dg/ipa/pr63814.C @@ -0,0 +1,29 @@ +// { dg-do run { target fpic } } +// { dg-options "-O3 -fpic" } + +struct CBase { + virtual void BaseFunc () {} +}; + +struct MMixin { + virtual void * MixinFunc (int, int) = 0; +}; + +struct CExample: CBase, public MMixin +{ + void *MixinFunc (int arg, int arg2) + { + return this; + } +}; + +void *test (MMixin & anExample) +{ + return anExample.MixinFunc (0, 0); +} + +int main () +{ + CExample c; + return (test (c) != &c); +} H.J.