1818#include " swift/AST/ASTContext.h"
1919#include " swift/AST/GenericSignatureBuilder.h"
2020#include " swift/AST/ProtocolConformance.h"
21- #include " swift/Basic/Defer.h"
22- #include " GenericSignatureBuilderImpl.h"
2321
2422using namespace swift ;
2523
@@ -48,24 +46,15 @@ GenericEnvironment::getGenericParams() const {
4846 return Signature->getGenericParams ();
4947}
5048
51- GenericEnvironment::GenericEnvironment (GenericSignature signature)
52- : Signature(signature)
49+ GenericEnvironment::GenericEnvironment (GenericSignature signature,
50+ GenericSignatureBuilder *builder)
51+ : Signature(signature), Builder(builder)
5352{
5453 // Clear out the memory that holds the context types.
5554 std::uninitialized_fill (getContextTypes ().begin (), getContextTypes ().end (),
5655 Type ());
5756}
5857
59- GenericSignatureBuilder *GenericEnvironment::getGenericSignatureBuilder () const {
60- if (Builder)
61- return Builder;
62-
63- const_cast <GenericEnvironment *>(this )->Builder
64- = Signature->getGenericSignatureBuilder ();
65-
66- return Builder;
67- }
68-
6958void GenericEnvironment::addMapping (GenericParamKey key,
7059 Type contextType) {
7160 // Find the index into the parallel arrays of generic parameters and
@@ -75,9 +64,7 @@ void GenericEnvironment::addMapping(GenericParamKey key,
7564 assert (genericParams[index] == key && " Bad generic parameter" );
7665
7766 // Add the mapping from the generic parameter to the context type.
78- assert (getContextTypes ()[index].isNull () ||
79- getContextTypes ()[index]->is <ErrorType>() &&
80- " Already recoded this mapping" );
67+ assert (getContextTypes ()[index].isNull () && " Already recoded this mapping" );
8168 getContextTypes ()[index] = contextType;
8269}
8370
@@ -120,116 +107,6 @@ Type TypeBase::mapTypeOutOfContext() {
120107 SubstFlags::AllowLoweredTypes);
121108}
122109
123- Type
124- GenericEnvironment::getOrCreateArchetypeFromInterfaceType (Type depType) {
125- auto &builder = *getGenericSignatureBuilder ();
126- auto &ctx = builder.getASTContext ();
127-
128- auto resolved =
129- builder.maybeResolveEquivalenceClass (
130- depType,
131- ArchetypeResolutionKind::CompleteWellFormed,
132- /* wantExactPotentialArchetype=*/ false );
133- if (!resolved)
134- return ErrorType::get (depType);
135-
136- if (auto concrete = resolved.getAsConcreteType ()) {
137- return mapTypeIntoContext (concrete,
138- builder.getLookupConformanceFn ());
139- }
140-
141- auto *equivClass = resolved.getEquivalenceClass (builder);
142-
143- auto genericParams = getGenericParams ();
144- Type anchor = equivClass->getAnchor (builder, genericParams);
145-
146- // First, write an ErrorType to the location where this type is cached,
147- // to catch re-entrant lookups that might arise from an invalid generic
148- // signature (eg, <X where X == Array<X>>).
149- ArchetypeType *parentArchetype = nullptr ;
150- GenericTypeParamType *genericParam = nullptr ;
151- if (auto depMemTy = anchor->getAs <DependentMemberType>()) {
152- parentArchetype =
153- getOrCreateArchetypeFromInterfaceType (depMemTy->getBase ())
154- ->getAs <ArchetypeType>();
155- if (!parentArchetype)
156- return ErrorType::get (depMemTy);
157-
158- auto name = depMemTy->getName ();
159- if (auto type = parentArchetype->getNestedTypeIfKnown (name))
160- return *type;
161-
162- parentArchetype->registerNestedType (name, ErrorType::get (ctx));
163- } else {
164- genericParam = anchor->castTo <GenericTypeParamType>();
165- if (auto type = getMappingIfPresent (genericParam))
166- return *type;
167- addMapping (genericParam, ErrorType::get (ctx));
168- }
169-
170- Type result;
171-
172- // If this equivalence class is mapped to a concrete type, produce that
173- // type.
174- if (equivClass->concreteType ) {
175- result = mapTypeIntoContext (equivClass->concreteType ,
176- builder.getLookupConformanceFn ());
177- } else {
178- // Substitute into the superclass.
179- Type superclass = equivClass->superclass ;
180- if (superclass && superclass->hasTypeParameter ()) {
181- superclass = mapTypeIntoContext (superclass,
182- builder.getLookupConformanceFn ());
183- if (superclass->is <ErrorType>())
184- superclass = Type ();
185- }
186-
187- // Collect the protocol conformances for the archetype.
188- SmallVector<ProtocolDecl *, 4 > protos;
189- for (const auto &conforms : equivClass->conformsTo ) {
190- auto proto = conforms.first ;
191-
192- if (!equivClass->isConformanceSatisfiedBySuperclass (proto))
193- protos.push_back (proto);
194- }
195-
196- if (parentArchetype) {
197- auto *depMemTy = anchor->castTo <DependentMemberType>();
198- result = NestedArchetypeType::getNew (ctx, parentArchetype, depMemTy,
199- protos, superclass,
200- equivClass->layout );
201- } else {
202- result = PrimaryArchetypeType::getNew (ctx, this , genericParam,
203- protos, superclass,
204- equivClass->layout );
205- }
206- }
207-
208- // Cache the new archetype for future lookups.
209- if (auto depMemTy = anchor->getAs <DependentMemberType>()) {
210- parentArchetype->registerNestedType (depMemTy->getName (), result);
211- } else {
212- addMapping (genericParam, result);
213- }
214-
215- return result;
216- }
217-
218- void ArchetypeType::resolveNestedType (
219- std::pair<Identifier, Type> &nested) const {
220- Type interfaceType = getInterfaceType ();
221- Type memberInterfaceType =
222- DependentMemberType::get (interfaceType, nested.first );
223-
224- Type result = getGenericEnvironment ()->getOrCreateArchetypeFromInterfaceType (
225- memberInterfaceType);
226-
227- assert (!nested.second ||
228- nested.second ->isEqual (result) ||
229- nested.second ->is <ErrorType>());
230- nested.second = result;
231- }
232-
233110Type QueryInterfaceTypeSubstitutions::operator ()(SubstitutableType *type) const {
234111 if (auto gp = type->getAs <GenericTypeParamType>()) {
235112 // Find the index into the parallel arrays of generic parameters and
@@ -243,18 +120,24 @@ Type QueryInterfaceTypeSubstitutions::operator()(SubstitutableType *type) const{
243120 return Type ();
244121
245122 // If the context type isn't already known, lazily create it.
246- auto mutableSelf = const_cast <GenericEnvironment *>(self);
247- Type &contextType = mutableSelf->getContextTypes ()[index];
248- if (contextType)
249- return contextType;
250-
251- auto result = mutableSelf->getOrCreateArchetypeFromInterfaceType (type);
252-
253- assert (!contextType ||
254- contextType->isEqual (result) ||
255- contextType->is <ErrorType>());
256- contextType = result;
257- return result;
123+ Type contextType = self->getContextTypes ()[index];
124+ if (!contextType) {
125+ assert (self->Builder &&" Missing generic signature builder for lazy query" );
126+ auto equivClass =
127+ self->Builder ->resolveEquivalenceClass (
128+ type,
129+ ArchetypeResolutionKind::CompleteWellFormed);
130+
131+ auto mutableSelf = const_cast <GenericEnvironment *>(self);
132+ contextType = equivClass->getTypeInContext (*mutableSelf->Builder ,
133+ mutableSelf);
134+
135+ // FIXME: Redundant mapping from key -> index.
136+ if (self->getContextTypes ()[index].isNull ())
137+ mutableSelf->addMapping (key, contextType);
138+ }
139+
140+ return contextType;
258141 }
259142
260143 return Type ();
0 commit comments