@@ -23,6 +23,17 @@ static llvm::cl::opt<bool> clDisableStructuredFir(
23
23
" no-structured-fir" , llvm::cl::desc(" disable generation of structured FIR" ),
24
24
llvm::cl::init(false ), llvm::cl::Hidden);
25
25
26
+ // FIXME: should be set with switch such as `--std=2018`.
27
+ static llvm::cl::opt<bool > nonRecursiveProcedures (
28
+ " non-recursive-procedures" ,
29
+ llvm::cl::desc (" Make procedures non-recursive by default. This was the "
30
+ " default for all Fortran standards prior to 2018." ),
31
+ llvm::cl::init(/* 2018 standard=*/ false ));
32
+
33
+ static bool defaultRecursiveFunctionSetting () {
34
+ return !nonRecursiveProcedures;
35
+ }
36
+
26
37
using namespace Fortran ;
27
38
28
39
namespace {
@@ -1275,6 +1286,17 @@ Fortran::lower::pft::FunctionLikeUnit::FunctionLikeUnit(
1275
1286
}
1276
1287
}
1277
1288
1289
+ template <typename A>
1290
+ static bool procedureIsRecursive (const A &stmt) {
1291
+ for (const auto &p : std::get<std::list<parser::PrefixSpec>>(stmt.t )) {
1292
+ if (std::holds_alternative<parser::PrefixSpec::Recursive>(p.u ))
1293
+ return true ;
1294
+ if (std::holds_alternative<parser::PrefixSpec::Non_Recursive>(p.u ))
1295
+ return false ;
1296
+ }
1297
+ return defaultRecursiveFunctionSetting ();
1298
+ }
1299
+
1278
1300
Fortran::lower::pft::FunctionLikeUnit::FunctionLikeUnit (
1279
1301
const parser::FunctionSubprogram &func,
1280
1302
const lower::pft::ParentVariant &parent,
@@ -1283,6 +1305,8 @@ Fortran::lower::pft::FunctionLikeUnit::FunctionLikeUnit(
1283
1305
beginStmt{getFunctionStmt<parser::FunctionStmt>(func)},
1284
1306
endStmt{getFunctionStmt<parser::EndFunctionStmt>(func)} {
1285
1307
auto symbol = getSymbol (*beginStmt);
1308
+ recursiveFunction =
1309
+ procedureIsRecursive (beginStmt->getStatement <parser::FunctionStmt>());
1286
1310
entryPointList[0 ].first = symbol;
1287
1311
processSymbolTable (*symbol->scope (), varList);
1288
1312
}
@@ -1295,6 +1319,8 @@ Fortran::lower::pft::FunctionLikeUnit::FunctionLikeUnit(
1295
1319
beginStmt{getFunctionStmt<parser::SubroutineStmt>(func)},
1296
1320
endStmt{getFunctionStmt<parser::EndSubroutineStmt>(func)} {
1297
1321
auto symbol = getSymbol (*beginStmt);
1322
+ recursiveFunction =
1323
+ procedureIsRecursive (beginStmt->getStatement <parser::SubroutineStmt>());
1298
1324
entryPointList[0 ].first = symbol;
1299
1325
processSymbolTable (*symbol->scope (), varList);
1300
1326
}
@@ -1305,7 +1331,8 @@ Fortran::lower::pft::FunctionLikeUnit::FunctionLikeUnit(
1305
1331
const semantics::SemanticsContext &)
1306
1332
: ProgramUnit{func, parent},
1307
1333
beginStmt{getFunctionStmt<parser::MpSubprogramStmt>(func)},
1308
- endStmt{getFunctionStmt<parser::EndMpSubprogramStmt>(func)} {
1334
+ endStmt{getFunctionStmt<parser::EndMpSubprogramStmt>(func)},
1335
+ recursiveFunction{defaultRecursiveFunctionSetting ()} {
1309
1336
auto symbol = getSymbol (*beginStmt);
1310
1337
entryPointList[0 ].first = symbol;
1311
1338
processSymbolTable (*symbol->scope (), varList);
0 commit comments