openmp: Handle clauses with gimple sequences in convert_nonlocal_omp_clauses properly
If the walk_body on the various sequences of reduction, lastprivate and/or linear clauses needs to create a temporary variable, we should declare that variable in that sequence rather than outside, where it would need to be privatized inside of the construct. 2020-08-08 Jakub Jelinek <jakub@redhat.com> PR fortran/93553 * tree-nested.c (convert_nonlocal_omp_clauses): For OMP_CLAUSE_REDUCTION, OMP_CLAUSE_LASTPRIVATE and OMP_CLAUSE_LINEAR save info->new_local_var_chain around walks of the clause gimple sequences and declare_vars if needed into the sequence. 2020-08-08 Tobias Burnus <tobias@codesourcery.com> PR fortran/93553 * testsuite/libgomp.fortran/pr93553.f90: New test.
This commit is contained in:
parent
87d6dae308
commit
676b5525e8
@ -1419,12 +1419,22 @@ convert_nonlocal_omp_clauses (tree *pclauses, struct walk_stmt_info *wi)
|
||||
if (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (clause))
|
||||
DECL_CONTEXT (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (clause))
|
||||
= info->context;
|
||||
tree save_local_var_chain = info->new_local_var_chain;
|
||||
info->new_local_var_chain = NULL;
|
||||
gimple_seq *seq = &OMP_CLAUSE_REDUCTION_GIMPLE_INIT (clause);
|
||||
walk_body (convert_nonlocal_reference_stmt,
|
||||
convert_nonlocal_reference_op, info,
|
||||
&OMP_CLAUSE_REDUCTION_GIMPLE_INIT (clause));
|
||||
convert_nonlocal_reference_op, info, seq);
|
||||
if (info->new_local_var_chain)
|
||||
declare_vars (info->new_local_var_chain,
|
||||
gimple_seq_first_stmt (*seq), false);
|
||||
info->new_local_var_chain = NULL;
|
||||
seq = &OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (clause);
|
||||
walk_body (convert_nonlocal_reference_stmt,
|
||||
convert_nonlocal_reference_op, info,
|
||||
&OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (clause));
|
||||
convert_nonlocal_reference_op, info, seq);
|
||||
if (info->new_local_var_chain)
|
||||
declare_vars (info->new_local_var_chain,
|
||||
gimple_seq_first_stmt (*seq), false);
|
||||
info->new_local_var_chain = save_local_var_chain;
|
||||
DECL_CONTEXT (OMP_CLAUSE_REDUCTION_PLACEHOLDER (clause))
|
||||
= old_context;
|
||||
if (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (clause))
|
||||
@ -1434,15 +1444,31 @@ convert_nonlocal_omp_clauses (tree *pclauses, struct walk_stmt_info *wi)
|
||||
break;
|
||||
|
||||
case OMP_CLAUSE_LASTPRIVATE:
|
||||
walk_body (convert_nonlocal_reference_stmt,
|
||||
convert_nonlocal_reference_op, info,
|
||||
&OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (clause));
|
||||
{
|
||||
tree save_local_var_chain = info->new_local_var_chain;
|
||||
info->new_local_var_chain = NULL;
|
||||
gimple_seq *seq = &OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (clause);
|
||||
walk_body (convert_nonlocal_reference_stmt,
|
||||
convert_nonlocal_reference_op, info, seq);
|
||||
if (info->new_local_var_chain)
|
||||
declare_vars (info->new_local_var_chain,
|
||||
gimple_seq_first_stmt (*seq), false);
|
||||
info->new_local_var_chain = save_local_var_chain;
|
||||
}
|
||||
break;
|
||||
|
||||
case OMP_CLAUSE_LINEAR:
|
||||
walk_body (convert_nonlocal_reference_stmt,
|
||||
convert_nonlocal_reference_op, info,
|
||||
&OMP_CLAUSE_LINEAR_GIMPLE_SEQ (clause));
|
||||
{
|
||||
tree save_local_var_chain = info->new_local_var_chain;
|
||||
info->new_local_var_chain = NULL;
|
||||
gimple_seq *seq = &OMP_CLAUSE_LINEAR_GIMPLE_SEQ (clause);
|
||||
walk_body (convert_nonlocal_reference_stmt,
|
||||
convert_nonlocal_reference_op, info, seq);
|
||||
if (info->new_local_var_chain)
|
||||
declare_vars (info->new_local_var_chain,
|
||||
gimple_seq_first_stmt (*seq), false);
|
||||
info->new_local_var_chain = save_local_var_chain;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
|
21
libgomp/testsuite/libgomp.fortran/pr93553.f90
Normal file
21
libgomp/testsuite/libgomp.fortran/pr93553.f90
Normal file
@ -0,0 +1,21 @@
|
||||
program p
|
||||
implicit none
|
||||
integer :: x(8) = 0
|
||||
call sub(x)
|
||||
end
|
||||
subroutine sub(x)
|
||||
implicit none
|
||||
integer i
|
||||
integer :: x(8)
|
||||
integer :: c(8) = [(11*i, i=1,8)]
|
||||
call s
|
||||
if (any (x /= c)) stop 1
|
||||
contains
|
||||
subroutine s
|
||||
integer :: i
|
||||
!$omp parallel do reduction(+:x)
|
||||
do i = 1, 8
|
||||
x(i) = c(i)
|
||||
end do
|
||||
end
|
||||
end
|
Loading…
Reference in New Issue
Block a user