@@ -864,6 +864,48 @@ static bool hasUserDefinedDesignatedInit(Evaluator &eval,
864
864
false );
865
865
}
866
866
867
+ static bool canInheritDesignatedInits (Evaluator &eval, ClassDecl *decl) {
868
+ // We can only inherit designated initializers if the user hasn't defined
869
+ // a designated init of their own, and all the stored properties have initial
870
+ // values.
871
+ return !hasUserDefinedDesignatedInit (eval, decl) &&
872
+ areAllStoredPropertiesDefaultInitializable (eval, decl);
873
+ }
874
+
875
+ static void collectNonOveriddenSuperclassInits (
876
+ ClassDecl *subclass, SmallVectorImpl<ConstructorDecl *> &results) {
877
+ auto superclassTy = subclass->getSuperclass ();
878
+ assert (superclassTy);
879
+
880
+ // Record all of the initializers the subclass has overriden, excluding stub
881
+ // overrides, which we don't want to consider as viable delegates for
882
+ // convenience inits.
883
+ llvm::SmallPtrSet<ConstructorDecl *, 4 > overriddenInits;
884
+ for (auto member : subclass->getMembers ())
885
+ if (auto ctor = dyn_cast<ConstructorDecl>(member))
886
+ if (!ctor->hasStubImplementation ())
887
+ if (auto overridden = ctor->getOverriddenDecl ())
888
+ overriddenInits.insert (overridden);
889
+
890
+ auto superclassCtors = TypeChecker::lookupConstructors (
891
+ subclass, superclassTy, NameLookupFlags::IgnoreAccessControl);
892
+
893
+ for (auto memberResult : superclassCtors) {
894
+ auto superclassCtor = cast<ConstructorDecl>(memberResult.getValueDecl ());
895
+
896
+ // Skip invalid superclass initializers.
897
+ if (superclassCtor->isInvalid ())
898
+ continue ;
899
+
900
+ // Skip unavailable superclass initializers.
901
+ if (AvailableAttr::isUnavailable (superclassCtor))
902
+ continue ;
903
+
904
+ if (!overriddenInits.count (superclassCtor))
905
+ results.push_back (superclassCtor);
906
+ }
907
+ }
908
+
867
909
// / For a class with a superclass, automatically define overrides
868
910
// / for all of the superclass's designated initializers.
869
911
static void addImplicitInheritedConstructorsToClass (ClassDecl *decl) {
@@ -944,25 +986,11 @@ static void addImplicitInheritedConstructorsToClass(ClassDecl *decl) {
944
986
945
987
bool canInheritInitializers = defaultInitable && !foundDesignatedInit;
946
988
947
- bool canInheritConvenienceInitalizers =
948
- !superclassDecl->hasMissingDesignatedInitializers ();
949
989
SmallVector<ConstructorDecl *, 4 > requiredConvenienceInitializers;
950
- for (auto memberResult : ctors) {
951
- auto member = memberResult.getValueDecl ();
952
-
953
- // Skip unavailable superclass initializers.
954
- if (AvailableAttr::isUnavailable (member))
955
- continue ;
956
-
957
- // Skip invalid superclass initializers.
958
- auto superclassCtor = dyn_cast<ConstructorDecl>(member);
959
- if (superclassCtor->isInvalid ())
960
- continue ;
961
-
962
- // If we have an override for this constructor, it's okay.
963
- if (overriddenInits.count (superclassCtor) > 0 )
964
- continue ;
990
+ SmallVector<ConstructorDecl *, 4 > nonOverridenSuperclassCtors;
991
+ collectNonOveriddenSuperclassInits (decl, nonOverridenSuperclassCtors);
965
992
993
+ for (auto *superclassCtor : nonOverridenSuperclassCtors) {
966
994
// We only care about required or designated initializers.
967
995
if (!superclassCtor->isDesignatedInit ()) {
968
996
if (superclassCtor->isRequired ()) {
@@ -973,10 +1001,6 @@ static void addImplicitInheritedConstructorsToClass(ClassDecl *decl) {
973
1001
continue ;
974
1002
}
975
1003
976
- // Otherwise, it may no longer be safe to inherit convenience
977
- // initializers.
978
- canInheritConvenienceInitalizers &= canInheritInitializers;
979
-
980
1004
// Everything after this is only relevant for Swift classes being defined.
981
1005
if (decl->hasClangNode ())
982
1006
continue ;
@@ -1028,12 +1052,38 @@ static void addImplicitInheritedConstructorsToClass(ClassDecl *decl) {
1028
1052
}
1029
1053
}
1030
1054
1031
- if (canInheritConvenienceInitalizers) {
1032
- decl->setInheritsSuperclassInitializers ();
1033
- } else {
1055
+ if (!decl->inheritsSuperclassInitializers ())
1034
1056
for (ConstructorDecl *requiredCtor : requiredConvenienceInitializers)
1035
1057
diagnoseMissingRequiredInitializer (decl, requiredCtor, ctx);
1036
- }
1058
+ }
1059
+
1060
+ llvm::Expected<bool >
1061
+ InheritsSuperclassInitializersRequest::evaluate (Evaluator &eval,
1062
+ ClassDecl *decl) const {
1063
+ auto superclass = decl->getSuperclass ();
1064
+ assert (superclass);
1065
+
1066
+ // If the superclass has known-missing designated initializers, inheriting
1067
+ // is unsafe.
1068
+ auto *superclassDecl = superclass->getClassOrBoundGenericClass ();
1069
+ if (superclassDecl->hasMissingDesignatedInitializers ())
1070
+ return false ;
1071
+
1072
+ // If we're allowed to inherit designated initializers, then we can inherit
1073
+ // convenience inits too.
1074
+ if (canInheritDesignatedInits (eval, decl))
1075
+ return true ;
1076
+
1077
+ // Otherwise we need to check whether the user has overriden all of the
1078
+ // superclass' designed inits.
1079
+ SmallVector<ConstructorDecl *, 4 > nonOverridenSuperclassCtors;
1080
+ collectNonOveriddenSuperclassInits (decl, nonOverridenSuperclassCtors);
1081
+
1082
+ auto allDesignatedInitsOverriden =
1083
+ llvm::none_of (nonOverridenSuperclassCtors, [](ConstructorDecl *ctor) {
1084
+ return ctor->isDesignatedInit ();
1085
+ });
1086
+ return allDesignatedInitsOverriden;
1037
1087
}
1038
1088
1039
1089
static bool shouldAttemptInitializerSynthesis (const NominalTypeDecl *decl) {
0 commit comments