diff --git a/flang/docs/Extensions.md b/flang/docs/Extensions.md --- a/flang/docs/Extensions.md +++ b/flang/docs/Extensions.md @@ -84,6 +84,10 @@ scope" -- i.e., not scoped by `BLOCK` constructs. As most (but not all) compilers implement `BLOCK` scoping of construct names, so does f18, with a portability warning. +* 15.6.4 paragraph 2 prohibits an implicitly typed statement function + from sharing the same name as a symbol in its scope's host, if it + has one. + We accept this usage with a portability warning. ## Extensions, deletions, and legacy features supported by default diff --git a/flang/lib/Semantics/check-declarations.cpp b/flang/lib/Semantics/check-declarations.cpp --- a/flang/lib/Semantics/check-declarations.cpp +++ b/flang/lib/Semantics/check-declarations.cpp @@ -1044,6 +1044,15 @@ if (auto msg{evaluate::CheckStatementFunction( symbol, *stmtFunction, context_.foldingContext())}) { SayWithDeclaration(symbol, std::move(*msg)); + } else if (details.result().flags().test(Symbol::Flag::Implicit)) { + // 15.6.4 p2 weird requirement + if (const Symbol * + host{symbol.owner().parent().FindSymbol(symbol.name())}) { + evaluate::AttachDeclaration( + messages_.Say(symbol.name(), + "An implicitly typed statement function should not appear when the same symbol is available in its host scope"_port_en_US), + *host); + } } } if (IsElementalProcedure(symbol)) { diff --git a/flang/test/Semantics/stmt-func01.f90 b/flang/test/Semantics/stmt-func01.f90 --- a/flang/test/Semantics/stmt-func01.f90 +++ b/flang/test/Semantics/stmt-func01.f90 @@ -34,6 +34,7 @@ integer :: sf9 !ERROR: Defining expression of statement function 'sf9' cannot be converted to its result type INTEGER(4) sf9(n) = "bad" + sf10 = 1. contains real function explicit(x,y) integer, intent(in) :: x @@ -44,4 +45,8 @@ real :: arr(2) arr = [1., 2.] end function + subroutine foo + !PORTABILITY: An implicitly typed statement function should not appear when the same symbol is available in its host scope + sf10(x) = 2.*x + end subroutine end