19
19
20
20
#include " swift/AST/AccessScope.h"
21
21
#include " swift/AST/Attr.h"
22
+ #include " swift/AST/Availability.h"
22
23
#include " swift/AST/CaptureInfo.h"
23
24
#include " swift/AST/ClangNode.h"
24
25
#include " swift/AST/ConcreteDeclRef.h"
@@ -2786,6 +2787,40 @@ class OpaqueTypeDecl final :
2786
2787
private llvm::TrailingObjects<OpaqueTypeDecl, OpaqueReturnTypeRepr *> {
2787
2788
friend TrailingObjects;
2788
2789
2790
+ public:
2791
+ // / A set of substitutions that represents a possible underlying type iff
2792
+ // / associated set of availability conditions is met.
2793
+ class ConditionallyAvailableSubstitutions ;
2794
+
2795
+ private:
2796
+ // / A container to keep a set of conditional available underlying type
2797
+ // / substitutions with their availability conditions.
2798
+ class ConditionalAlternatives final
2799
+ : private llvm::TrailingObjects<ConditionalAlternatives,
2800
+ ConditionallyAvailableSubstitutions *> {
2801
+ friend TrailingObjects;
2802
+
2803
+ unsigned NumAlternatives;
2804
+
2805
+ ConditionalAlternatives (
2806
+ ArrayRef<ConditionallyAvailableSubstitutions *> underlyingTypes)
2807
+ : NumAlternatives(underlyingTypes.size()) {
2808
+ std::uninitialized_copy (
2809
+ underlyingTypes.begin (), underlyingTypes.end (),
2810
+ getTrailingObjects<ConditionallyAvailableSubstitutions *>());
2811
+ }
2812
+
2813
+ public:
2814
+ ArrayRef<ConditionallyAvailableSubstitutions *> getAlternatives () const {
2815
+ return {getTrailingObjects<ConditionallyAvailableSubstitutions *>(),
2816
+ NumAlternatives};
2817
+ }
2818
+
2819
+ static ConditionalAlternatives *
2820
+ get (ASTContext &ctx,
2821
+ ArrayRef<ConditionallyAvailableSubstitutions *> underlyingTypes);
2822
+ };
2823
+
2789
2824
// / The original declaration that "names" the opaque type. Although a specific
2790
2825
// / opaque type cannot be explicitly named, oapque types can propagate
2791
2826
// / arbitrarily through expressions, so we need to know *which* opaque type is
@@ -2806,7 +2841,12 @@ class OpaqueTypeDecl final :
2806
2841
// / This maps types in the interface generic signature to the outer generic
2807
2842
// / signature of the original declaration.
2808
2843
Optional<SubstitutionMap> UnderlyingTypeSubstitutions;
2809
-
2844
+
2845
+ // / A set of substitutions which are used based on the availability
2846
+ // / checks performed at runtime. This set of only populated if there
2847
+ // / is no single unique underlying type for this opaque type declaration.
2848
+ ConditionalAlternatives *ConditionallyAvailableTypes = nullptr ;
2849
+
2810
2850
mutable Identifier OpaqueReturnTypeIdentifier;
2811
2851
2812
2852
OpaqueTypeDecl (ValueDecl *NamingDecl, GenericParamList *GenericParams,
@@ -2891,7 +2931,15 @@ class OpaqueTypeDecl final :
2891
2931
assert (!UnderlyingTypeSubstitutions.hasValue () && " resetting underlying type?!" );
2892
2932
UnderlyingTypeSubstitutions = subs;
2893
2933
}
2894
-
2934
+ t
2935
+ void setConditionallyAvailableSubstitutions (
2936
+ ArrayRef<ConditionallyAvailableSubstitutions *> substitutions) {
2937
+ assert (!ConditionallyAvailableTypes &&
2938
+ " resetting conditional substitutions?!" );
2939
+ ConditionallyAvailableTypes =
2940
+ ConditionalAlternatives::get (getASTContext (), substitutions);
2941
+ }
2942
+
2895
2943
// Opaque type decls are currently always implicit
2896
2944
SourceRange getSourceRange () const { return SourceRange (); }
2897
2945
@@ -2910,6 +2958,40 @@ class OpaqueTypeDecl final :
2910
2958
return classof (D);
2911
2959
return false ;
2912
2960
}
2961
+
2962
+ class ConditionallyAvailableSubstitutions final
2963
+ : private llvm::TrailingObjects<ConditionallyAvailableSubstitutions,
2964
+ VersionRange> {
2965
+ friend TrailingObjects;
2966
+
2967
+ unsigned NumAvailabilityConditions;
2968
+
2969
+ SubstitutionMap Substitutions;
2970
+
2971
+ // / A type with limited availability described by the provided set
2972
+ // / of availability conditions (with `and` relationship).
2973
+ ConditionallyAvailableSubstitutions (
2974
+ ArrayRef<VersionRange> availabilityContext,
2975
+ SubstitutionMap substitutions)
2976
+ : NumAvailabilityConditions(availabilityContext.size()),
2977
+ Substitutions (substitutions) {
2978
+ assert (!availabilityContext.empty ());
2979
+ std::uninitialized_copy (availabilityContext.begin (),
2980
+ availabilityContext.end (),
2981
+ getTrailingObjects<VersionRange>());
2982
+ }
2983
+
2984
+ public:
2985
+ ArrayRef<VersionRange> getAvailability () const {
2986
+ return {getTrailingObjects<VersionRange>(), NumAvailabilityConditions};
2987
+ }
2988
+
2989
+ SubstitutionMap getSubstitutions () const { return Substitutions; }
2990
+
2991
+ static ConditionallyAvailableSubstitutions *
2992
+ get (ASTContext &ctx, ArrayRef<VersionRange> availabilityContext,
2993
+ SubstitutionMap substitutions);
2994
+ };
2913
2995
};
2914
2996
2915
2997
// / TypeAliasDecl - This is a declaration of a typealias, for example:
0 commit comments