https://gcc.gnu.org/g:86717c5808dacd36b85e5d4cd3499c6fe96d2733
commit r16-9259-g86717c5808dacd36b85e5d4cd3499c6fe96d2733 Author: Jerry DeLisle <[email protected]> Date: Thu Jul 9 19:24:49 2026 -0700 fortran: [PR126170] Fix LTO ICE in copy_function_or_variable A redundant USE of a module already visible via host association, written inside a contained procedure, caused gfortran's module reader to create a second copy of that module's derived type. PR fortran/126170 gcc/fortran/ChangeLog: PR fortran/126170 * class.cc (gfc_find_derived_vtab): Fix up a stale non-use-associated duplicate vtab symbol. (gfc_is_finalizable): Same fix-up, for the finalizer wrapper symbol. * module.cc (read_module): Skip re-importing a symbol already visible via host association from the same module. gcc/testsuite/ChangeLog: PR fortran/126170 * gfortran.dg/lto/pr126170_0.f90: New test. * gfortran.dg/lto/pr126170_1.f90: New test. (cherry picked from commit f935a7a9013d0748ba1f42dc532df3d278707bf6) Diff: --- gcc/fortran/class.cc | 22 ++++++++++++++++++++ gcc/fortran/module.cc | 13 ++++++++++++ gcc/testsuite/gfortran.dg/lto/pr126170_0.f90 | 31 ++++++++++++++++++++++++++++ gcc/testsuite/gfortran.dg/lto/pr126170_1.f90 | 14 +++++++++++++ 4 files changed, 80 insertions(+) diff --git a/gcc/fortran/class.cc b/gcc/fortran/class.cc index 956572f7de1a..d14f34ac4266 100644 --- a/gcc/fortran/class.cc +++ b/gcc/fortran/class.cc @@ -2523,6 +2523,15 @@ gfc_find_derived_vtab (gfc_symbol *derived) if (vtab == NULL && module_ns != ns) gfc_find_symbol (name, module_ns, 0, &vtab); + /* Fix up a stale non-use-associated duplicate vtab. */ + if (vtab + && (derived->attr.use_assoc || derived->attr.used_in_submodule) + && !vtab->attr.use_assoc && !vtab->module) + { + vtab->attr.use_assoc = 1; + vtab->module = derived->module; + } + if (vtab == NULL) { gfc_get_symbol (name, ns, &vtab); @@ -2860,6 +2869,19 @@ yes: gcc_assert (final->initializer && final->initializer->expr_type != EXPR_NULL); *final_expr = final->initializer; + + /* Fix up a stale non-use-associated duplicate vtab. */ + if ((derived->attr.use_assoc || derived->attr.used_in_submodule) + && (*final_expr)->expr_type == EXPR_VARIABLE + && (*final_expr)->symtree) + { + gfc_symbol *final_sym = (*final_expr)->symtree->n.sym; + if (final_sym && !final_sym->attr.use_assoc && !final_sym->module) + { + final_sym->attr.use_assoc = 1; + final_sym->module = derived->module; + } + } } return true; } diff --git a/gcc/fortran/module.cc b/gcc/fortran/module.cc index 04ddf6b4476b..4600845f5f6d 100644 --- a/gcc/fortran/module.cc +++ b/gcc/fortran/module.cc @@ -5881,6 +5881,19 @@ read_module (void) module_name, 0)) continue; + /* Skip re-importing a symbol already visible via host association + from the same module. */ + if (!only_flag && !info->u.rsym.renamed + && strcmp (name, module_name) != 0 + && gfc_current_ns->parent) + { + gfc_symbol *host_sym; + gfc_find_symbol (name, gfc_current_ns, 1, &host_sym); + if (host_sym && host_sym->module + && strcmp (host_sym->module, module_name) == 0) + continue; + } + st = gfc_find_symtree (gfc_current_ns->sym_root, p); if (st != NULL diff --git a/gcc/testsuite/gfortran.dg/lto/pr126170_0.f90 b/gcc/testsuite/gfortran.dg/lto/pr126170_0.f90 new file mode 100644 index 000000000000..c862da5d5442 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/lto/pr126170_0.f90 @@ -0,0 +1,31 @@ +! { dg-lto-do link } +! +! PR fortran/126170 +! A redundant, already host-associated USE inside a contained function +! caused gfortran to create duplicate of a derived type with +! a FINAL binding. + +module vsm + type :: vs + integer :: c + contains + final :: vdst + end type vs +contains + subroutine vdst(v) + type(vs), intent(inout) :: v + end subroutine vdst +end module vsm + +module m_ds + use vsm + type :: mdcc + end type mdcc +contains + function mdot(self) + use vsm + class(mdcc), intent(inout) :: self + type(vs) :: mdot + mdot%c = 1 + end function mdot +end module m_ds diff --git a/gcc/testsuite/gfortran.dg/lto/pr126170_1.f90 b/gcc/testsuite/gfortran.dg/lto/pr126170_1.f90 new file mode 100644 index 000000000000..b13fd6c8edd9 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/lto/pr126170_1.f90 @@ -0,0 +1,14 @@ +module caller + use m_ds +contains + subroutine s() + type(mdcc) :: self + type(vs) :: vs_ + vs_ = mdot(self) + end subroutine s +end module caller + +program main + use caller + call s() +end program main
