@@ -116,7 +116,7 @@ LifetimeDependenceInfo::fromTypeRepr(AbstractFunctionDecl *afd, Type resultType,
116
116
SmallBitVector scopeLifetimeParamIndices (capacity);
117
117
118
118
auto updateLifetimeDependenceInfo = [&](LifetimeDependenceSpecifier specifier,
119
- unsigned paramIndexToSet,
119
+ unsigned paramIndexToSet, Type type,
120
120
ValueOwnership ownership) {
121
121
auto loc = specifier.getLoc ();
122
122
auto kind = specifier.getLifetimeDependenceKind ();
@@ -148,6 +148,14 @@ LifetimeDependenceInfo::fromTypeRepr(AbstractFunctionDecl *afd, Type resultType,
148
148
getOwnershipSpelling (ownership));
149
149
return true ;
150
150
}
151
+ if (kind == LifetimeDependenceKind::Consume ||
152
+ kind == LifetimeDependenceKind::Copy) {
153
+ if (type->isEscapable ()) {
154
+ diags.diagnose (loc, diag::lifetime_dependence_cannot_use_infer,
155
+ specifier.getLifetimeDependenceKindString ());
156
+ return true ;
157
+ }
158
+ }
151
159
if (inheritLifetimeParamIndices.test (paramIndexToSet) ||
152
160
scopeLifetimeParamIndices.test (paramIndexToSet)) {
153
161
diags.diagnose (loc, diag::lifetime_dependence_duplicate_param_id);
@@ -168,17 +176,20 @@ LifetimeDependenceInfo::fromTypeRepr(AbstractFunctionDecl *afd, Type resultType,
168
176
switch (specifier.getSpecifierKind ()) {
169
177
case LifetimeDependenceSpecifier::SpecifierKind::Named: {
170
178
bool foundParamName = false ;
171
- unsigned paramIndexToSet = 1 ;
179
+ unsigned paramIndex = 0 ;
172
180
for (auto *param : *afd->getParameters ()) {
173
181
if (param->getParameterName () == specifier.getName ()) {
174
182
foundParamName = true ;
175
- if (updateLifetimeDependenceInfo (specifier, paramIndexToSet,
176
- param->getValueOwnership ())) {
183
+ if (updateLifetimeDependenceInfo (
184
+ specifier, paramIndex + 1 ,
185
+ afd->mapTypeIntoContext (
186
+ param->toFunctionParam ().getParameterType ()),
187
+ param->getValueOwnership ())) {
177
188
return llvm::None;
178
189
}
179
190
break ;
180
191
}
181
- paramIndexToSet ++;
192
+ paramIndex ++;
182
193
}
183
194
if (!foundParamName) {
184
195
diags.diagnose (specifier.getLoc (),
@@ -189,29 +200,23 @@ LifetimeDependenceInfo::fromTypeRepr(AbstractFunctionDecl *afd, Type resultType,
189
200
break ;
190
201
}
191
202
case LifetimeDependenceSpecifier::SpecifierKind::Ordered: {
192
- auto paramIndex = specifier.getIndex ();
193
- if (paramIndex > afd->getParameters ()->size ()) {
203
+ auto index = specifier.getIndex ();
204
+ if (index > afd->getParameters ()->size ()) {
194
205
diags.diagnose (specifier.getLoc (),
195
- diag::lifetime_dependence_invalid_param_index,
196
- paramIndex);
206
+ diag::lifetime_dependence_invalid_param_index, index);
197
207
return llvm::None;
198
208
}
199
- if (paramIndex == 0 ) {
200
- if (!afd->hasImplicitSelfDecl ()) {
201
- diags.diagnose (specifier.getLoc (),
202
- diag::lifetime_dependence_invalid_self);
209
+ if (index != 0 ) {
210
+ auto param = afd->getParameters ()->get (index - 1 );
211
+ auto ownership = param->getValueOwnership ();
212
+ auto type = afd->mapTypeIntoContext (
213
+ param->toFunctionParam ().getParameterType ());
214
+ if (updateLifetimeDependenceInfo (specifier, index, type, ownership)) {
203
215
return llvm::None;
204
216
}
217
+ break ;
205
218
}
206
- auto ownership =
207
- paramIndex == 0
208
- ? afd->getImplicitSelfDecl ()->getValueOwnership ()
209
- : afd->getParameters ()->get (paramIndex - 1 )->getValueOwnership ();
210
- if (updateLifetimeDependenceInfo (
211
- specifier, /* paramIndexToSet*/ specifier.getIndex (), ownership)) {
212
- return llvm::None;
213
- }
214
- break ;
219
+ LLVM_FALLTHROUGH;
215
220
}
216
221
case LifetimeDependenceSpecifier::SpecifierKind::Self: {
217
222
if (!afd->hasImplicitSelfDecl ()) {
@@ -221,6 +226,7 @@ LifetimeDependenceInfo::fromTypeRepr(AbstractFunctionDecl *afd, Type resultType,
221
226
}
222
227
if (updateLifetimeDependenceInfo (
223
228
specifier, /* selfIndex*/ 0 ,
229
+ afd->getImplicitSelfDecl ()->getTypeInContext (),
224
230
afd->getImplicitSelfDecl ()->getValueOwnership ())) {
225
231
return llvm::None;
226
232
}
0 commit comments