@@ -750,6 +750,103 @@ swift::castValueToABICompatibleType(SILBuilder *builder, SILPassManager *pm,
750
750
llvm_unreachable (" Unknown combination of types for casting" );
751
751
}
752
752
753
+ namespace {
754
+ class TypeDependentVisitor : public CanTypeVisitor <TypeDependentVisitor, bool > {
755
+ public:
756
+ // If the type isn't actually dependent, we're okay.
757
+ bool visit (CanType type) {
758
+ if (!type->hasArchetype () && !type->hasTypeParameter ())
759
+ return false ;
760
+ return CanTypeVisitor::visit (type);
761
+ }
762
+
763
+ bool visitStructType (CanStructType type) {
764
+ return visitStructDecl (type->getDecl ());
765
+ }
766
+ bool visitBoundGenericStructType (CanBoundGenericStructType type) {
767
+ return visitStructDecl (type->getDecl ());
768
+ }
769
+ bool visitStructDecl (StructDecl *decl) {
770
+ auto rawLayout = decl->getAttrs ().getAttribute <RawLayoutAttr>();
771
+ if (rawLayout) {
772
+ if (auto likeType = rawLayout->getResolvedScalarLikeType (decl)) {
773
+ return visit ((*likeType)->getCanonicalType ());
774
+ } else if (auto likeArray = rawLayout->getResolvedArrayLikeTypeAndCount (decl)) {
775
+ return visit (likeArray->first ->getCanonicalType ());
776
+ }
777
+ }
778
+
779
+ for (auto field : decl->getStoredProperties ()) {
780
+ if (visit (field->getInterfaceType ()->getCanonicalType ()))
781
+ return true ;
782
+ }
783
+ return false ;
784
+ }
785
+
786
+ bool visitEnumType (CanEnumType type) {
787
+ return visitEnumDecl (type->getDecl ());
788
+ }
789
+ bool visitBoundGenericEnumType (CanBoundGenericEnumType type) {
790
+ return visitEnumDecl (type->getDecl ());
791
+ }
792
+ bool visitEnumDecl (EnumDecl *decl) {
793
+ if (decl->isIndirect ())
794
+ return false ;
795
+
796
+ for (auto elt : decl->getAllElements ()) {
797
+ if (!elt->hasAssociatedValues () || elt->isIndirect ())
798
+ continue ;
799
+
800
+ if (visit (elt->getArgumentInterfaceType ()->getCanonicalType ()))
801
+ return true ;
802
+ }
803
+ return false ;
804
+ }
805
+
806
+ bool visitTupleType (CanTupleType type) {
807
+ for (auto eltTy : type.getElementTypes ()) {
808
+ if (visit (eltTy->getCanonicalType ()))
809
+ return true ;
810
+ }
811
+ return false ;
812
+ }
813
+
814
+ // A class reference does not depend on the layout of the class.
815
+ bool visitClassType (CanClassType type) {
816
+ return false ;
817
+ }
818
+ bool visitBoundGenericClassType (CanBoundGenericClassType type) {
819
+ return false ;
820
+ }
821
+
822
+ // The same for non-strong references.
823
+ bool visitReferenceStorageType (CanReferenceStorageType type) {
824
+ return false ;
825
+ }
826
+
827
+ // All function types have the same layout.
828
+ bool visitAnyFunctionType (CanAnyFunctionType type) {
829
+ return false ;
830
+ }
831
+
832
+ // The safe default for types we didn't handle above.
833
+ bool visitType (CanType type) {
834
+ return true ;
835
+ }
836
+ };
837
+ } // end anonymous namespace
838
+
839
+ bool swift::layoutIsTypeDependent (NominalTypeDecl *decl) {
840
+ if (auto *classDecl = dyn_cast<ClassDecl>(decl)) {
841
+ return false ;
842
+ } else if (auto *structDecl = dyn_cast<StructDecl>(decl)) {
843
+ return TypeDependentVisitor ().visitStructDecl (structDecl);
844
+ } else {
845
+ auto *enumDecl = cast<EnumDecl>(decl);
846
+ return TypeDependentVisitor ().visitEnumDecl (enumDecl);
847
+ }
848
+ }
849
+
753
850
ProjectBoxInst *swift::getOrCreateProjectBox (AllocBoxInst *abi,
754
851
unsigned index) {
755
852
SILBasicBlock::iterator iter (abi);
0 commit comments