Index: flang/lib/Semantics/expression.cpp =================================================================== --- flang/lib/Semantics/expression.cpp +++ flang/lib/Semantics/expression.cpp @@ -1921,7 +1921,10 @@ }}; auto pair{ResolveGeneric(*sym, arguments, adjustment)}; sym = pair.first; - if (!sym) { + if (sym) { + // re-resolve the name to the specific binding + sc.component.symbol = const_cast(sym); + } else { EmitGenericResolutionError(*sc.component.symbol, pair.second); return std::nullopt; } @@ -2184,6 +2187,10 @@ *symbol, arguments, noAdjustment, mightBeStructureConstructor)}; resolution = pair.first; dueToNullActual = pair.second; + if (resolution) { + // re-resolve name to the specific procedure + name.symbol = const_cast(resolution); + } } if (!resolution) { // Not generic, or no resolution; may be intrinsic Index: flang/test/Semantics/doconcurrent09.f90 =================================================================== --- /dev/null +++ flang/test/Semantics/doconcurrent09.f90 @@ -0,0 +1,47 @@ +! RUN: %python %S/test_errors.py %s %flang_fc1 +! Ensure that DO CONCURRENT purity checks apply to specific procedures +! in the case of calls to generic interfaces. +module m + interface purity + module procedure :: ps, ips + end interface + type t + contains + procedure :: pb, ipb + generic :: purity => pb, ipb + end type + contains + pure subroutine ps(n) + integer, intent(in) :: n + end subroutine + impure subroutine ips(a) + real, intent(in) :: a + end subroutine + pure subroutine pb(x,n) + class(t), intent(in) :: x + integer, intent(in) :: n + end subroutine + impure subroutine ipb(x,n) + class(t), intent(in) :: x + real, intent(in) :: n + end subroutine +end module + +program test + use m + type(t) :: x + do concurrent (j=1:1) + call ps(1) ! ok + call purity(1) ! ok + !ERROR: Call to an impure procedure is not allowed in DO CONCURRENT + call purity(1.) + !ERROR: Call to an impure procedure is not allowed in DO CONCURRENT + call ips(1.) + call x%pb(1) ! ok + call x%purity(1) ! ok + !ERROR: Call to an impure procedure component is not allowed in DO CONCURRENT + call x%purity(1.) + !ERROR: Call to an impure procedure component is not allowed in DO CONCURRENT + call x%ipb(1.) + end do +end program