Skip to content

Commit e83c5b2

Browse files
authored
[flang] Warn about automatic data in main program, disallow in BLOCK … (llvm#102045)
…DATA We allow automatic data objects in the specification part of the main program; add an optional portability warning and documentation. Don't allow them in BLOCK DATA. They're already disallowed as module variables.
1 parent d46c639 commit e83c5b2

File tree

5 files changed

+43
-6
lines changed

5 files changed

+43
-6
lines changed

flang/docs/Extensions.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -384,6 +384,8 @@ end
384384
* `BIND(C, NAME="...", CDEFINED)` signifies that the storage for an
385385
interoperable variable will be allocated outside of Fortran,
386386
probably by a C or C++ external definition.
387+
* An automatic data object may be declared in the specification part
388+
of the main program.
387389

388390
### Extensions supported when enabled by options
389391

flang/include/flang/Common/Fortran-features.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ ENUM_CLASS(LanguageFeature, BackslashEscapes, OldDebugLines,
5151
BadBranchTarget, ConvertedArgument, HollerithPolymorphic, ListDirectedSize,
5252
NonBindCInteroperability, CudaManaged, CudaUnified,
5353
PolymorphicActualAllocatableOrPointerToMonomorphicDummy, RelaxedPureDummy,
54-
UndefinableAsynchronousOrVolatileActual)
54+
UndefinableAsynchronousOrVolatileActual, AutomaticInMainProgram)
5555

5656
// Portability and suspicious usage warnings
5757
ENUM_CLASS(UsageWarning, Portability, PointerToUndefinable,

flang/lib/Semantics/check-declarations.cpp

Lines changed: 25 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -247,6 +247,14 @@ void CheckHelper::Check(
247247
}
248248
}
249249

250+
static bool IsBlockData(const Scope &scope) {
251+
return scope.kind() == Scope::Kind::BlockData;
252+
}
253+
254+
static bool IsBlockData(const Symbol &symbol) {
255+
return symbol.scope() && IsBlockData(*symbol.scope());
256+
}
257+
250258
void CheckHelper::Check(const Symbol &symbol) {
251259
if (symbol.name().size() > common::maxNameLen &&
252260
&symbol == &symbol.GetUltimate()) {
@@ -463,6 +471,23 @@ void CheckHelper::Check(const Symbol &symbol) {
463471
messages_.Say(
464472
"Automatic data object '%s' may not appear in a module"_err_en_US,
465473
symbol.name());
474+
} else if (IsBlockData(symbol.owner())) {
475+
messages_.Say(
476+
"Automatic data object '%s' may not appear in a BLOCK DATA subprogram"_err_en_US,
477+
symbol.name());
478+
} else if (symbol.owner().kind() == Scope::Kind::MainProgram) {
479+
if (context_.IsEnabled(common::LanguageFeature::AutomaticInMainProgram)) {
480+
if (context_.ShouldWarn(
481+
common::LanguageFeature::AutomaticInMainProgram)) {
482+
messages_.Say(
483+
"Automatic data object '%s' should not appear in the specification part of a main program"_port_en_US,
484+
symbol.name());
485+
}
486+
} else {
487+
messages_.Say(
488+
"Automatic data object '%s' may not appear in the specification part of a main program"_err_en_US,
489+
symbol.name());
490+
}
466491
}
467492
}
468493
if (IsProcedure(symbol)) {
@@ -2799,10 +2824,6 @@ static bool IsSubprogramDefinition(const Symbol &symbol) {
27992824
symbol.scope()->kind() == Scope::Kind::Subprogram;
28002825
}
28012826

2802-
static bool IsBlockData(const Symbol &symbol) {
2803-
return symbol.scope() && symbol.scope()->kind() == Scope::Kind::BlockData;
2804-
}
2805-
28062827
static bool IsExternalProcedureDefinition(const Symbol &symbol) {
28072828
return IsBlockData(symbol) ||
28082829
(IsSubprogramDefinition(symbol) &&

flang/test/Semantics/resolve77.f90

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
! RUN: %python %S/test_errors.py %s %flang_fc1
1+
! RUN: %python %S/test_errors.py %s %flang_fc1 -pedantic
22
! Tests valid and invalid usage of forward references to procedures
33
! in specification expressions.
44
module m
@@ -56,3 +56,16 @@ pure integer function if2(n)
5656
if2 = n
5757
end function
5858
end subroutine
59+
60+
block data
61+
common /blk2/ n
62+
data n/100/
63+
!ERROR: Automatic data object 'a' may not appear in a BLOCK DATA subprogram
64+
real a(n)
65+
end
66+
67+
program main
68+
common /blk2/ n
69+
!PORTABILITY: Automatic data object 'a' should not appear in the specification part of a main program
70+
real a(n)
71+
end

flang/test/Semantics/stmt-func01.f90

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ program main
1010
pure integer function ifunc()
1111
end function
1212
end interface
13+
!PORTABILITY: Automatic data object 'x1' should not appear in the specification part of a main program
1314
type(t1(k=4,l=ifunc())) x1
1415
!PORTABILITY: Statement function 'sf1' should not contain an array constructor
1516
sf1(n) = sum([(j,j=1,n)])

0 commit comments

Comments
 (0)