|
16 | 16 |
|
17 | 17 | #define DEBUG_TYPE "sil-existential-transform"
|
18 | 18 | #include "ExistentialTransform.h"
|
| 19 | +#include "swift/AST/ExistentialLayout.h" |
19 | 20 | #include "swift/AST/GenericEnvironment.h"
|
20 | 21 | #include "swift/AST/TypeCheckRequests.h"
|
21 | 22 | #include "swift/SIL/OptimizationRemark.h"
|
@@ -114,11 +115,29 @@ void ExistentialSpecializerCloner::cloneAndPopulateFunction() {
|
114 | 115 | }
|
115 | 116 | }
|
116 | 117 |
|
| 118 | +// Gather the conformances needed for an existential value based on an opened |
| 119 | +// archetype. This adds any conformances inherited from superclass constraints. |
| 120 | +static ArrayRef<ProtocolConformanceRef> |
| 121 | +collectExistentialConformances(ModuleDecl *M, CanType openedType, |
| 122 | + CanType existentialType) { |
| 123 | + assert(!openedType.isAnyExistentialType()); |
| 124 | + |
| 125 | + auto layout = existentialType.getExistentialLayout(); |
| 126 | + auto protocols = layout.getProtocols(); |
| 127 | + |
| 128 | + SmallVector<ProtocolConformanceRef, 4> conformances; |
| 129 | + for (auto proto : protocols) { |
| 130 | + auto conformance = M->lookupConformance(openedType, proto->getDecl()); |
| 131 | + assert(conformance); |
| 132 | + conformances.push_back(conformance); |
| 133 | + } |
| 134 | + return M->getASTContext().AllocateCopy(conformances); |
| 135 | +} |
| 136 | + |
117 | 137 | // Create the entry basic block with the function arguments.
|
118 | 138 | void ExistentialSpecializerCloner::cloneArguments(
|
119 | 139 | SmallVectorImpl<SILValue> &entryArgs) {
|
120 | 140 | auto &M = OrigF->getModule();
|
121 |
| - auto &Ctx = M.getASTContext(); |
122 | 141 |
|
123 | 142 | // Create the new entry block.
|
124 | 143 | SILFunction &NewF = getBuilder().getFunction();
|
@@ -164,14 +183,10 @@ void ExistentialSpecializerCloner::cloneArguments(
|
164 | 183 | NewArg->setOwnershipKind(ValueOwnershipKind(
|
165 | 184 | NewF, GenericSILType, ArgDesc.Arg->getArgumentConvention()));
|
166 | 185 | // Determine the Conformances.
|
167 |
| - SmallVector<ProtocolConformanceRef, 1> NewConformances; |
168 |
| - auto ContextTy = NewF.mapTypeIntoContext(GenericParam); |
169 |
| - auto OpenedArchetype = ContextTy->castTo<ArchetypeType>(); |
170 |
| - for (auto proto : OpenedArchetype->getConformsTo()) { |
171 |
| - NewConformances.push_back(ProtocolConformanceRef(proto)); |
172 |
| - } |
173 |
| - ArrayRef<ProtocolConformanceRef> Conformances = |
174 |
| - Ctx.AllocateCopy(NewConformances); |
| 186 | + SILType ExistentialType = ArgDesc.Arg->getType().getObjectType(); |
| 187 | + CanType OpenedType = NewArg->getType().getASTType(); |
| 188 | + auto Conformances = collectExistentialConformances( |
| 189 | + M.getSwiftModule(), OpenedType, ExistentialType.getASTType()); |
175 | 190 | auto ExistentialRepr =
|
176 | 191 | ArgDesc.Arg->getType().getPreferredExistentialRepresentation();
|
177 | 192 | auto &EAD = ExistentialArgDescriptor[ArgDesc.Index];
|
|
0 commit comments