@@ -809,12 +809,12 @@ static SILInstruction *tryDevirtualizeApplyHelper(FullApplySite InnerAI,
809
809
// /
810
810
// / \returns true if successful, false if failed due to circular inlining.
811
811
static bool
812
- runOnFunctionRecursively (SILOptFunctionBuilder &FuncBuilder,
813
- SILFunction *F, FullApplySite AI,
814
- DenseFunctionSet &FullyInlinedSet,
812
+ runOnFunctionRecursively (SILOptFunctionBuilder &FuncBuilder, SILFunction *F,
813
+ FullApplySite AI, DenseFunctionSet &FullyInlinedSet,
815
814
ImmutableFunctionSet::Factory &SetFactory,
816
815
ImmutableFunctionSet CurrentInliningSet,
817
- ClassHierarchyAnalysis *CHA) {
816
+ ClassHierarchyAnalysis *CHA,
817
+ DenseFunctionSet &changedFunctions) {
818
818
// Avoid reprocessing functions needlessly.
819
819
if (FullyInlinedSet.count (F))
820
820
return true ;
@@ -861,6 +861,10 @@ runOnFunctionRecursively(SILOptFunctionBuilder &FuncBuilder,
861
861
// but a casted result of InnerAI or even a block argument due to
862
862
// abstraction changes when calling the witness or class method.
863
863
auto *devirtInst = tryDevirtualizeApplyHelper (InnerAI, CHA);
864
+ // If devirtualization succeeds, make sure we record that this function
865
+ // changed.
866
+ if (devirtInst != InnerAI.getInstruction ())
867
+ changedFunctions.insert (F);
864
868
// Restore II to the current apply site.
865
869
II = devirtInst->getReverseIterator ();
866
870
// If the devirtualized call result is no longer a invalid FullApplySite,
@@ -879,9 +883,9 @@ runOnFunctionRecursively(SILOptFunctionBuilder &FuncBuilder,
879
883
continue ;
880
884
881
885
// Then recursively process it first before trying to inline it.
882
- if (!runOnFunctionRecursively (FuncBuilder, CalleeFunction, InnerAI,
883
- FullyInlinedSet, SetFactory,
884
- CurrentInliningSet, CHA)) {
886
+ if (!runOnFunctionRecursively (
887
+ FuncBuilder, CalleeFunction, InnerAI, FullyInlinedSet, SetFactory,
888
+ CurrentInliningSet, CHA, changedFunctions )) {
885
889
// If we failed due to circular inlining, then emit some notes to
886
890
// trace back the failure if we have more information.
887
891
// FIXME: possibly it could be worth recovering and attempting other
@@ -971,6 +975,10 @@ runOnFunctionRecursively(SILOptFunctionBuilder &FuncBuilder,
971
975
closureCleanup.cleanupDeadClosures (F);
972
976
invalidatedStackNesting |= closureCleanup.invalidatedStackNesting ;
973
977
978
+ // Record that we inlined into this function so that we can invalidate it
979
+ // later.
980
+ changedFunctions.insert (F);
981
+
974
982
// Resume inlining within nextBB, which contains only the inlined
975
983
// instructions and possibly instructions in the original call block that
976
984
// have not yet been visited.
@@ -980,6 +988,7 @@ runOnFunctionRecursively(SILOptFunctionBuilder &FuncBuilder,
980
988
981
989
if (invalidatedStackNesting) {
982
990
StackNesting ().correctStackNesting (F);
991
+ changedFunctions.insert (F);
983
992
}
984
993
985
994
// Keep track of full inlined functions so we don't waste time recursively
@@ -999,10 +1008,10 @@ class MandatoryInlining : public SILModuleTransform {
999
1008
void run () override {
1000
1009
ClassHierarchyAnalysis *CHA = getAnalysis<ClassHierarchyAnalysis>();
1001
1010
SILModule *M = getModule ();
1002
- bool ShouldCleanup = !getOptions ().DebugSerialization ;
1003
1011
bool SILVerifyAll = getOptions ().VerifyAll ;
1004
1012
DenseFunctionSet FullyInlinedSet;
1005
1013
ImmutableFunctionSet::Factory SetFactory;
1014
+ DenseFunctionSet changedFunctions;
1006
1015
1007
1016
SILOptFunctionBuilder FuncBuilder (*this );
1008
1017
for (auto &F : *M) {
@@ -1014,13 +1023,15 @@ class MandatoryInlining : public SILModuleTransform {
1014
1023
if (F.wasDeserializedCanonical ())
1015
1024
continue ;
1016
1025
1017
- runOnFunctionRecursively (FuncBuilder, &F,
1018
- FullApplySite (), FullyInlinedSet, SetFactory,
1019
- SetFactory.getEmptySet (), CHA);
1026
+ runOnFunctionRecursively (FuncBuilder, &F, FullApplySite (),
1027
+ FullyInlinedSet, SetFactory,
1028
+ SetFactory.getEmptySet (), CHA, changedFunctions );
1020
1029
1021
1030
// The inliner splits blocks at call sites. Re-merge trivial branches
1022
1031
// to reestablish a canonical CFG.
1023
- mergeBasicBlocks (&F);
1032
+ if (mergeBasicBlocks (&F)) {
1033
+ changedFunctions.insert (&F);
1034
+ }
1024
1035
1025
1036
// If we are asked to perform SIL verify all, perform that now so that we
1026
1037
// can discover the immediate inlining trigger of the problematic
@@ -1030,38 +1041,10 @@ class MandatoryInlining : public SILModuleTransform {
1030
1041
}
1031
1042
}
1032
1043
1033
- if (!ShouldCleanup )
1044
+ if (getOptions (). DebugSerialization )
1034
1045
return ;
1035
-
1036
- // Now that we've inlined some functions, clean up. If there are any
1037
- // transparent functions that are deserialized from another module that are
1038
- // now unused, just remove them from the module.
1039
- //
1040
- // We do this with a simple linear scan, because transparent functions that
1041
- // reference each other have already been flattened.
1042
- for (auto FI = M->begin (), E = M->end (); FI != E; ) {
1043
- SILFunction &F = *FI++;
1044
-
1045
- invalidateAnalysis (&F, SILAnalysis::InvalidationKind::Everything);
1046
-
1047
- if (F.getRefCount () != 0 ) continue ;
1048
-
1049
- // Leave non-transparent functions alone.
1050
- if (!F.isTransparent ())
1051
- continue ;
1052
-
1053
- // We discard functions that don't have external linkage,
1054
- // e.g. deserialized functions, internal functions, and thunks.
1055
- // Being marked transparent controls this.
1056
- if (F.isPossiblyUsedExternally ()) continue ;
1057
-
1058
- // ObjC functions are called through the runtime and are therefore alive
1059
- // even if not referenced inside SIL.
1060
- if (F.getRepresentation () == SILFunctionTypeRepresentation::ObjCMethod)
1061
- continue ;
1062
-
1063
- // Okay, just erase the function from the module.
1064
- FuncBuilder.eraseFunction (&F);
1046
+ for (auto *F : changedFunctions) {
1047
+ invalidateAnalysis (F, SILAnalysis::InvalidationKind::Everything);
1065
1048
}
1066
1049
}
1067
1050
0 commit comments