From: Tobias Burnus Date: Tue, 25 Jan 2011 17:01:06 +0000 (+0100) Subject: backport: re PR fortran/47331 (ICE in make_decl_rtl, at varasm.c:1133 (with -fopenmp)) X-Git-Tag: releases/gcc-4.5.3~272 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=a029b1b66ee140155745ff304ee632132039696c;p=thirdparty%2Fgcc.git backport: re PR fortran/47331 (ICE in make_decl_rtl, at varasm.c:1133 (with -fopenmp)) 2011-01-25 Tobias Burnus Backport from mainline 2011-01-17 Jakub Jelinek PR fortran/47331 * gfortran.h (struct gfc_omp_saved_state): New type. (gfc_omp_save_and_clear_state, gfc_omp_restore_state): New prototypes. * resolve.c (resolve_global_procedure): Call it around gfc_resolve call. 2011-01-25 Tobias Burnus Backport from mainline 2011-01-17 Jakub Jelinek PR fortran/47331 * gfortran.dg/gomp/pr47331.f90: New test. From-SVN: r169244 --- diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index d93841351bf3..9b78c07755c6 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,16 @@ +2011-01-25 Tobias Burnus + + Backport from mainline + 2011-01-17 Jakub Jelinek + + PR fortran/47331 + * gfortran.h (struct gfc_omp_saved_state): New type. + (gfc_omp_save_and_clear_state, gfc_omp_restore_state): New prototypes. + * resolve.c (resolve_global_procedure): Call it around gfc_resolve + call. + * openmp.c (gfc_omp_save_and_clear_state, gfc_omp_restore_state): New + functions. + 2011-01-25 Tobias Burnus PR fortran/47448 diff --git a/gcc/fortran/gfortran.h b/gcc/fortran/gfortran.h index 79bdfeb08b18..3fcc5ccba7c7 100644 --- a/gcc/fortran/gfortran.h +++ b/gcc/fortran/gfortran.h @@ -2575,11 +2575,14 @@ void gfc_free_case_list (gfc_case *); gfc_expr *gfc_get_parentheses (gfc_expr *); /* openmp.c */ +struct gfc_omp_saved_state { void *ptrs[2]; int ints[1]; }; void gfc_free_omp_clauses (gfc_omp_clauses *); void gfc_resolve_omp_directive (gfc_code *, gfc_namespace *); void gfc_resolve_do_iterator (gfc_code *, gfc_symbol *); void gfc_resolve_omp_parallel_blocks (gfc_code *, gfc_namespace *); void gfc_resolve_omp_do_blocks (gfc_code *, gfc_namespace *); +void gfc_omp_save_and_clear_state (struct gfc_omp_saved_state *); +void gfc_omp_restore_state (struct gfc_omp_saved_state *); /* expr.c */ void gfc_free_actual_arglist (gfc_actual_arglist *); diff --git a/gcc/fortran/openmp.c b/gcc/fortran/openmp.c index 851b9f228544..e26535eaeb03 100644 --- a/gcc/fortran/openmp.c +++ b/gcc/fortran/openmp.c @@ -1363,6 +1363,31 @@ gfc_resolve_omp_parallel_blocks (gfc_code *code, gfc_namespace *ns) } +/* Save and clear openmp.c private state. */ + +void +gfc_omp_save_and_clear_state (struct gfc_omp_saved_state *state) +{ + state->ptrs[0] = omp_current_ctx; + state->ptrs[1] = omp_current_do_code; + state->ints[0] = omp_current_do_collapse; + omp_current_ctx = NULL; + omp_current_do_code = NULL; + omp_current_do_collapse = 0; +} + + +/* Restore openmp.c private state from the saved state. */ + +void +gfc_omp_restore_state (struct gfc_omp_saved_state *state) +{ + omp_current_ctx = (struct omp_context *) state->ptrs[0]; + omp_current_do_code = (gfc_code *) state->ptrs[1]; + omp_current_do_collapse = state->ints[0]; +} + + /* Note a DO iterator variable. This is special in !$omp parallel construct, where they are predetermined private. */ diff --git a/gcc/fortran/resolve.c b/gcc/fortran/resolve.c index 83d48b6653db..d102357645f6 100644 --- a/gcc/fortran/resolve.c +++ b/gcc/fortran/resolve.c @@ -1810,11 +1810,14 @@ resolve_global_procedure (gfc_symbol *sym, locus *where, if (!gsym->ns->resolved) { gfc_dt_list *old_dt_list; + struct gfc_omp_saved_state old_omp_state; /* Stash away derived types so that the backend_decls do not get mixed up. */ old_dt_list = gfc_derived_types; gfc_derived_types = NULL; + /* And stash away openmp state. */ + gfc_omp_save_and_clear_state (&old_omp_state); gfc_resolve (gsym->ns); @@ -1824,6 +1827,8 @@ resolve_global_procedure (gfc_symbol *sym, locus *where, /* Restore the derived types of this namespace. */ gfc_derived_types = old_dt_list; + /* And openmp state. */ + gfc_omp_restore_state (&old_omp_state); } /* Make sure that translation for the gsymbol occurs before diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index adad4a629473..7eb83817dadb 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,11 @@ +2011-01-25 Tobias Burnus + + Backport from mainline + 2011-01-17 Jakub Jelinek + + PR fortran/47331 + * gfortran.dg/gomp/pr47331.f90: New test. + 2011-01-25 Tobias Burnus PR fortran/47448 diff --git a/gcc/testsuite/gfortran.dg/gomp/pr47331.f90 b/gcc/testsuite/gfortran.dg/gomp/pr47331.f90 new file mode 100644 index 000000000000..71713e02233f --- /dev/null +++ b/gcc/testsuite/gfortran.dg/gomp/pr47331.f90 @@ -0,0 +1,24 @@ +! PR fortran/47331 +! { dg-do compile } +! { dg-options "-fopenmp -fwhole-file" } + +subroutine foo + !$omp parallel + call bar () + !$omp end parallel +end subroutine foo + +subroutine bar + integer :: k + do k=1,5 + call baz (k) + end do +end subroutine bar + +subroutine baz (k) + integer :: k +end subroutine + +program pr47331 + call foo +end program pr47331