Hi,
when doing an ftree-parallelize-loops=2 build (PR68967), I ran into an
ICE building gcc/ada/g-debpoo.adb.
The problem occurs when handling a loop with header bb 109, latch bb 108
and exit bb 110:
...
;; basic block 109
# ivtmp_520 = PHI <0(129), ivtmp_151(108)>
# RANGE [0, 1022] NONZERO 1023
j_528 = (gnat__debug_pools__TheaderBD.4905) ivtmp_520;
ivtmp_479 = 1023 - ivtmp_520;
# RANGE [1, 1023] NONZERO 1023
j_529 = j_528 + 1;
ivtmp_19 = ivtmp_479 - 1;
if (ivtmp_520 < 1022)
goto <bb 108>;
else
goto <bb 110>;
;; basic block 108
ivtmp_151 = ivtmp_520 + 1;
goto <bb 109>;
;; basic block 110
# .MEM_28 = PHI <.MEM_743(109), .MEM_743(126)>
goto <bb 8>;
...
The phi defining .MEM_28 is a case of 'exit phi without corresponding
loop header phi'. [ A patch was committed at r225873 to detect and
handle this kind of situation, but it looks like it doesn't handle the
virtual phi case correctly. ]
After create_parallel_loop, we're left with missing arguments in the new
loop exit phi:
...
# .MEM_765 = PHI <(108), (135)>
#pragma omp return(nowait)
...
This causes an ssa verification failure at the start of
rewrite_virtuals_into_loop_closed_ssa when parallelizing another loop in
the same function.
This patch fixes the problem by setting the missing phi arguments in
create_parallel_loop.
Bootstrapped and reg-tested on x86_64.
Committed to trunk.
Thanks,
- Tom
Add missing phi args in create_parallel_loop
2016-01-07 Tom de Vries <t...@codesourcery.com>
PR tree-optimization/69069
* tree-parloops.c (create_parallel_loop): Add missing phi args.
---
gcc/tree-parloops.c | 7 ++++++-
1 file changed, 6 insertions(+), 1 deletion(-)
diff --git a/gcc/tree-parloops.c b/gcc/tree-parloops.c
index 5afaaf8..46d70ac 100644
--- a/gcc/tree-parloops.c
+++ b/gcc/tree-parloops.c
@@ -2086,7 +2086,12 @@ create_parallel_loop (struct loop *loop, tree loop_fn, tree data,
value is not modified in the loop, and we're done with this phi. */
if (!(gimple_code (def_stmt) == GIMPLE_PHI
&& gimple_bb (def_stmt) == loop->header))
- continue;
+ {
+ locus = gimple_phi_arg_location_from_edge (phi, exit);
+ add_phi_arg (phi, def, guard, locus);
+ add_phi_arg (phi, def, end, locus);
+ continue;
+ }
gphi *stmt = as_a <gphi *> (def_stmt);
def = PHI_ARG_DEF_FROM_EDGE (stmt, loop_preheader_edge (loop));