Skip to content

Commit a6651a9

Browse files
committed
Generalize and fix compiler resource freeing before LLVM
Centralize part of the routine that selects which resources to free. Then, add an additional condition for -dump-api-path. Before, if this option were specified along with -emit-llvm or -c, the compiler would try to rebuild the torn-down ModuleDecl and crash trying to access the torn-down ASTContext.
1 parent 7dd000b commit a6651a9

File tree

2 files changed

+52
-15
lines changed

2 files changed

+52
-15
lines changed

include/swift/Frontend/Frontend.h

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -625,8 +625,7 @@ class CompilerInstance {
625625
/// \param silModule The SIL module that was generated during SILGen.
626626
/// \param stats A stats reporter that will report optimization statistics.
627627
/// \returns true if any errors occurred.
628-
bool performSILProcessing(SILModule *silModule,
629-
UnifiedStatsReporter *stats = nullptr);
628+
bool performSILProcessing(SILModule *silModule);
630629

631630
private:
632631
SourceFile *

lib/FrontendTool/FrontendTool.cpp

Lines changed: 51 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1460,6 +1460,55 @@ static bool validateTBDIfNeeded(const CompilerInvocation &Invocation,
14601460
Opts, allSymbols);
14611461
}
14621462

1463+
enum class DeallocatableResources {
1464+
None,
1465+
SILModule,
1466+
SILModuleAndASTContext,
1467+
};
1468+
static DeallocatableResources
1469+
computeDeallocatableResources(const CompilerInvocation &Invocation,
1470+
const CompilerInstance &Instance) {
1471+
// If the stats reporter is installed, we need the ASTContext and SILModule
1472+
// to live through the entire compilation process.
1473+
if (Instance.getASTContext().Stats) {
1474+
return DeallocatableResources::None;
1475+
}
1476+
1477+
// If we're going to dump the API of the module, we cannot tear down
1478+
// the ASTContext, as that would cause the module to be freed prematurely.
1479+
if (!Invocation.getFrontendOptions().DumpAPIPath.empty()) {
1480+
return DeallocatableResources::SILModule;
1481+
}
1482+
1483+
// If there are multiple primary inputs it is too soon to free
1484+
// the ASTContext, etc.. OTOH, if this compilation generates code for > 1
1485+
// primary input, then freeing it after processing the last primary is
1486+
// unlikely to reduce the peak heap size. So, only optimize the
1487+
// single-primary-case (or WMO).
1488+
if (Invocation.getFrontendOptions()
1489+
.InputsAndOutputs.hasMultiplePrimaryInputs()) {
1490+
return DeallocatableResources::SILModule;
1491+
}
1492+
1493+
return DeallocatableResources::SILModuleAndASTContext;
1494+
}
1495+
1496+
static void
1497+
freeDeallocatableResourcesIfPossible(const CompilerInvocation &Invocation,
1498+
CompilerInstance &Instance) {
1499+
switch (computeDeallocatableResources(Invocation, Instance)) {
1500+
case DeallocatableResources::None:
1501+
break;
1502+
case DeallocatableResources::SILModule:
1503+
Instance.freeSILModule();
1504+
break;
1505+
case DeallocatableResources::SILModuleAndASTContext:
1506+
Instance.freeSILModule();
1507+
Instance.freeASTContext();
1508+
break;
1509+
}
1510+
}
1511+
14631512
static bool generateCode(const CompilerInvocation &Invocation,
14641513
CompilerInstance &Instance, StringRef OutputFilename,
14651514
llvm::Module *IRModule,
@@ -1469,19 +1518,8 @@ static bool generateCode(const CompilerInvocation &Invocation,
14691518
version::Version EffectiveLanguageVersion =
14701519
Instance.getASTContext().LangOpts.EffectiveLanguageVersion;
14711520

1472-
if (!Stats) {
1473-
// Free up some compiler resources now that we have an IRModule.
1474-
Instance.freeSILModule();
1475-
1476-
// If there are multiple primary inputs it is too soon to free
1477-
// the ASTContext, etc.. OTOH, if this compilation generates code for > 1
1478-
// primary input, then freeing it after processing the last primary is
1479-
// unlikely to reduce the peak heap size. So, only optimize the
1480-
// single-primary-case (or WMO).
1481-
if (!Invocation.getFrontendOptions()
1482-
.InputsAndOutputs.hasMultiplePrimaryInputs())
1483-
Instance.freeASTContext();
1484-
}
1521+
// Free up some compiler resources now that we have an IRModule.
1522+
freeDeallocatableResourcesIfPossible(Invocation, Instance);
14851523

14861524
// Now that we have a single IR Module, hand it over to performLLVM.
14871525
return performLLVM(Invocation.getIRGenOptions(), Instance.getDiags(),

0 commit comments

Comments
 (0)