+2011-02-20 Paul Thomas <pault@gcc.gnu.org>
+
+ PR fortran/45077
+ PR fortran/44945
+ * trans-types.c (gfc_get_derived_type): Remove code that looks
+ for decls in gsym and add call to gfc_get_module_backend_decl.
+ * trans.h : Add prototype for gfc_get_module_backend_decl.
+ * trans-decl.c (gfc_get_module_backend_decl): New function.
+ (gfc_get_symbol_decl): Call it.
+
2011-02-19 Paul Thomas <pault@gcc.gnu.org>
PR fortran/47348
}
+/* Used in gfc_get_symbol_decl and gfc_get_derived_type to obtain the
+ backend_decl for a module symbol, if it all ready exists. If the
+ module gsymbol does not exist, it is created. If the symbol does
+ not exist, it is added to the gsymbol namespace. Returns true if
+ an existing backend_decl is found. */
+
+bool
+gfc_get_module_backend_decl (gfc_symbol *sym)
+{
+ gfc_gsymbol *gsym;
+ gfc_symbol *s;
+ gfc_symtree *st;
+
+ gsym = gfc_find_gsymbol (gfc_gsym_root, sym->module);
+
+ if (!gsym || (gsym->ns && gsym->type == GSYM_MODULE))
+ {
+ st = NULL;
+ s = NULL;
+
+ if (gsym)
+ gfc_find_symbol (sym->name, gsym->ns, 0, &s);
+
+ if (!s)
+ {
+ if (!gsym)
+ {
+ gsym = gfc_get_gsymbol (sym->module);
+ gsym->type = GSYM_MODULE;
+ gsym->ns = gfc_get_namespace (NULL, 0);
+ }
+
+ st = gfc_new_symtree (&gsym->ns->sym_root, sym->name);
+ st->n.sym = sym;
+ sym->refs++;
+ }
+ else if (sym->attr.flavor == FL_DERIVED)
+ {
+ if (!s->backend_decl)
+ s->backend_decl = gfc_get_derived_type (s);
+ gfc_copy_dt_decls_ifequal (s, sym, true);
+ return true;
+ }
+ else if (s->backend_decl)
+ {
+ if (sym->ts.type == BT_DERIVED)
+ gfc_copy_dt_decls_ifequal (s->ts.u.derived, sym->ts.u.derived,
+ true);
+ else if (sym->ts.type == BT_CHARACTER)
+ sym->ts.u.cl->backend_decl = s->ts.u.cl->backend_decl;
+ sym->backend_decl = s->backend_decl;
+ return true;
+ }
+ }
+ return false;
+}
+
+
/* Create an array index type variable with function scope. */
static tree
if (gfc_option.flag_whole_file
&& (sym->attr.flavor == FL_VARIABLE
|| sym->attr.flavor == FL_PARAMETER)
- && sym->attr.use_assoc && !intrinsic_array_parameter
- && sym->module)
- {
- gfc_gsymbol *gsym;
-
- gsym = gfc_find_gsymbol (gfc_gsym_root, sym->module);
- if (gsym && gsym->ns && gsym->type == GSYM_MODULE)
- {
- gfc_symbol *s;
- s = NULL;
- gfc_find_symbol (sym->name, gsym->ns, 0, &s);
- if (s && s->backend_decl)
- {
- if (sym->ts.type == BT_DERIVED)
- gfc_copy_dt_decls_ifequal (s->ts.u.derived, sym->ts.u.derived,
- true);
- if (sym->ts.type == BT_CHARACTER)
- sym->ts.u.cl->backend_decl = s->ts.u.cl->backend_decl;
- sym->backend_decl = s->backend_decl;
- return sym->backend_decl;
- }
- }
- }
+ && sym->attr.use_assoc
+ && !intrinsic_array_parameter
+ && sym->module
+ && gfc_get_module_backend_decl (sym))
+ return sym->backend_decl;
if (sym->attr.flavor == FL_PROCEDURE)
{
int
gfc_copy_dt_decls_ifequal (gfc_symbol *from, gfc_symbol *to,
- bool from_gsym)
+ bool from_gsym)
{
gfc_component *to_cm;
gfc_component *from_cm;
gfc_component *c;
gfc_dt_list *dt;
gfc_namespace *ns;
- gfc_gsymbol *gsym;
gcc_assert (derived && derived->attr.flavor == FL_DERIVED);
return derived->backend_decl;
}
-/* If use associated, use the module type for this one. */
+ /* If use associated, use the module type for this one. */
if (gfc_option.flag_whole_file
&& derived->backend_decl == NULL
&& derived->attr.use_assoc
- && derived->module)
- {
- gsym = gfc_find_gsymbol (gfc_gsym_root, derived->module);
- if (gsym && gsym->ns && gsym->type == GSYM_MODULE)
- {
- gfc_symbol *s;
- s = NULL;
- gfc_find_symbol (derived->name, gsym->ns, 0, &s);
- if (s)
- {
- if (!s->backend_decl)
- s->backend_decl = gfc_get_derived_type (s);
- gfc_copy_dt_decls_ifequal (s, derived, true);
- goto copy_derived_types;
- }
- }
- }
+ && derived->module
+ && gfc_get_module_backend_decl (derived))
+ goto copy_derived_types;
/* If a whole file compilation, the derived types from an earlier
namespace can be used as the the canonical type. */
/* Set the backend source location of a decl. */
void gfc_set_decl_location (tree, locus *);
+/* Get a module symbol backend_decl if possible. */
+bool gfc_get_module_backend_decl (gfc_symbol *);
+
/* Return the variable decl for a symbol. */
tree gfc_get_symbol_decl (gfc_symbol *);
+2011-02-20 Paul Thomas <pault@gcc.gnu.org>
+
+ PR fortran/45077
+ PR fortran/44945
+ * gfortran.dg/whole_file_28.f90 : New test.
+ * gfortran.dg/whole_file_29.f90 : New test.
+
2011-02-20 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/44118
--- /dev/null
+! { dg-do compile }
+! Test the fix for the problem described in PR45077 comments #4 and #5.
+! Note that the module file is kept for whole_file_29.f90
+!
+! Contributed by Tobias Burnus <burnus@gcc.gnu.org>
+!
+module iso_red
+ type, public :: varying_string
+ character(LEN=1), dimension(:), allocatable :: chars
+ end type varying_string
+end module iso_red
+! DO NOT CLEAN UP THE MODULE FILE - whole_file_29.f90 does it.
--- /dev/null
+! { dg-do compile }
+! Test the fix for the problem described in PR45077 comments #4 and #5.
+! Note that the module file from whole_file_28.f90, 'iso_red', is
+! needed for this test.
+!
+! Contributed by Tobias Burnus <burnus@gcc.gnu.org>
+!
+module ifiles
+ use iso_red, string_t => varying_string
+contains
+ function line_get_string_advance (line) result (string)
+ type(string_t) :: string
+ character :: line
+ end function line_get_string_advance
+end module ifiles
+
+module syntax_rules
+ use iso_red, string_t => varying_string
+ use ifiles, only: line_get_string_advance
+contains
+ subroutine syntax_init_from_ifile ()
+ type(string_t) :: string
+ string = line_get_string_advance ("")
+ end subroutine syntax_init_from_ifile
+end module syntax_rules
+end
+! { dg-final { cleanup-modules "syntax_rules ifiles iso_red" } }