diff --git a/flang/lib/Semantics/mod-file.cpp b/flang/lib/Semantics/mod-file.cpp index 70b6bbf8b557a..5fc6188a1f028 100644 --- a/flang/lib/Semantics/mod-file.cpp +++ b/flang/lib/Semantics/mod-file.cpp @@ -1444,6 +1444,9 @@ void SubprogramSymbolCollector::DoSymbol( DoType(details.type()); } }, + [this](const ProcBindingDetails &details) { + DoSymbol(details.symbol()); + }, [](const auto &) {}, }, symbol.details()); @@ -1469,17 +1472,21 @@ void SubprogramSymbolCollector::DoType(const DeclTypeSpec *type) { default: if (const DerivedTypeSpec * derived{type->AsDerived()}) { const auto &typeSymbol{derived->typeSymbol()}; - if (const DerivedTypeSpec * extends{typeSymbol.GetParentTypeSpec()}) { - DoSymbol(extends->name(), extends->typeSymbol()); - } for (const auto &pair : derived->parameters()) { DoParamValue(pair.second); } - for (const auto &pair : *typeSymbol.scope()) { - const Symbol &comp{*pair.second}; - DoSymbol(comp); + // The components of the type (including its parent component, if + // any) matter to IMPORT symbol collection only for derived types + // defined in the subprogram. + if (typeSymbol.owner() == scope_) { + if (const DerivedTypeSpec * extends{typeSymbol.GetParentTypeSpec()}) { + DoSymbol(extends->name(), extends->typeSymbol()); + } + for (const auto &pair : *typeSymbol.scope()) { + DoSymbol(*pair.second); + } } - DoSymbol(derived->name(), derived->typeSymbol()); + DoSymbol(derived->name(), typeSymbol); } } } @@ -1511,8 +1518,8 @@ bool SubprogramSymbolCollector::NeedImport( // detect import from ancestor of use-associated symbol return found->has() && found->owner() != scope_; } else { - // "found" can be null in the case of a use-associated derived type's parent - // type + // "found" can be null in the case of a use-associated derived type's + // parent type CHECK(symbol.has()); return false; } diff --git a/flang/test/Semantics/modfile61.f90 b/flang/test/Semantics/modfile61.f90 new file mode 100644 index 0000000000000..b6bc9492d495e --- /dev/null +++ b/flang/test/Semantics/modfile61.f90 @@ -0,0 +1,130 @@ +! RUN: %python %S/test_modfile.py %s %flang_fc1 +module m + type t1 + procedure(p1), pointer, nopass :: p + end type + type t2 + procedure(p2), pointer, nopass :: p + end type + type t3 + procedure(p4), pointer, nopass :: p + end type + type t4 + procedure(p6), pointer, nopass :: p + end type + type t5 + procedure(p7), pointer, nopass :: p + end type + interface + subroutine p1 + end + subroutine p2 + end + subroutine p3 + end + subroutine p4 + end + subroutine p5(c) + import + type(t3), intent(in) :: c + end + subroutine p6(d) + import + type(t5), intent(in) :: d + end + subroutine p7 + end + subroutine p8 + end + function f(a,b,dp) + import + type(t1), intent(in) :: a + type, extends(t2) :: localt1 + procedure(p3), pointer, nopass :: p + end type + type, extends(localt1) :: localt2 + contains + procedure, nopass :: p8 + end type + type(localt2), intent(in) :: b + procedure(p5) dp + type(t4), pointer :: f + end + end interface +end + +!Expect: m.mod +!module m +!type::t1 +!procedure(p1),nopass,pointer::p +!end type +!type::t2 +!procedure(p2),nopass,pointer::p +!end type +!type::t3 +!procedure(p4),nopass,pointer::p +!end type +!type::t4 +!procedure(p6),nopass,pointer::p +!end type +!type::t5 +!procedure(p7),nopass,pointer::p +!end type +!interface +!subroutine p1() +!end +!end interface +!interface +!subroutine p2() +!end +!end interface +!interface +!subroutine p3() +!end +!end interface +!interface +!subroutine p4() +!end +!end interface +!interface +!subroutine p5(c) +!import::t3 +!type(t3),intent(in)::c +!end +!end interface +!interface +!subroutine p6(d) +!import::t5 +!type(t5),intent(in)::d +!end +!end interface +!interface +!subroutine p7() +!end +!end interface +!interface +!subroutine p8() +!end +!end interface +!interface +!function f(a,b,dp) +!import::p3 +!import::p5 +!import::p8 +!import::t1 +!import::t2 +!import::t4 +!type(t1),intent(in)::a +!type,extends(t2)::localt1 +!procedure(p3),nopass,pointer::p +!end type +!type,extends(localt1)::localt2 +!contains +!procedure,nopass::p8 +!end type +!type(localt2),intent(in)::b +!procedure(p5)::dp +!type(t4),pointer::f +!end +!end interface +!end