@@ -38,12 +38,6 @@ bool ArgumentTypeCheckCompletionCallback::addPossibleParams(
38
38
39
39
ArrayRef<AnyFunctionType::Param> ParamsToPass = Res.FuncTy ->getParams ();
40
40
41
- ParameterList *PL = nullptr ;
42
- if (Res.FuncD ) {
43
- PL = swift::getParameterList (Res.FuncD );
44
- }
45
- assert (!PL || PL->size () == ParamsToPass.size ());
46
-
47
41
bool ShowGlobalCompletions = false ;
48
42
for (auto Idx : range (*Res.ParamIdx , ParamsToPass.size ())) {
49
43
bool IsCompletion = (Idx == Res.ParamIdx );
@@ -53,22 +47,35 @@ bool ArgumentTypeCheckCompletionCallback::addPossibleParams(
53
47
break ;
54
48
}
55
49
56
- const AnyFunctionType::Param *P = &ParamsToPass[Idx];
57
- bool Required =
58
- !(PL && PL->get (Idx)->isDefaultArgument ()) && !P->isVariadic ();
50
+ // We work with the parameter from the function type and the declaration
51
+ // because they contain different information that we need.
52
+ //
53
+ // Since not all function types are backed by declarations (e.g. closure
54
+ // paramters), `DeclParam` might be `nullptr`.
55
+ const AnyFunctionType::Param *TypeParam = &ParamsToPass[Idx];
56
+ const ParamDecl *DeclParam = getParameterAt (Res.FuncDeclRef , Idx);
57
+
58
+ bool Required = true ;
59
+ if (DeclParam && DeclParam->isDefaultArgument ()) {
60
+ Required = false ;
61
+ } else if (DeclParam && DeclParam->getType ()->is <PackExpansionType>()) {
62
+ Required = false ;
63
+ } else if (TypeParam->isVariadic ()) {
64
+ Required = false ;
65
+ }
59
66
60
- if (P ->hasLabel () && !(IsCompletion && Res.IsNoninitialVariadic )) {
67
+ if (TypeParam ->hasLabel () && !(IsCompletion && Res.IsNoninitialVariadic )) {
61
68
// Suggest parameter label if parameter has label, we are completing in it
62
69
// and it is not a variadic parameter that already has arguments
63
- PossibleParamInfo PP (P , Required);
70
+ PossibleParamInfo PP (TypeParam , Required);
64
71
if (!llvm::is_contained (Params, PP)) {
65
72
Params.push_back (std::move (PP));
66
73
}
67
74
} else {
68
75
// We have a parameter that doesn't require a label. Suggest global
69
76
// results for that type.
70
77
ShowGlobalCompletions = true ;
71
- Types.push_back (P ->getPlainType ());
78
+ Types.push_back (TypeParam ->getPlainType ());
72
79
}
73
80
if (Required) {
74
81
// The user should only be suggested the first required param. Stop.
@@ -157,7 +164,7 @@ void ArgumentTypeCheckCompletionCallback::sawSolutionImpl(const Solution &S) {
157
164
auto *CalleeLocator = S.getCalleeLocator (CallLocator);
158
165
159
166
auto Info = getSelectedOverloadInfo (S, CalleeLocator);
160
- if (Info.Value && Info.Value ->shouldHideFromEditor ()) {
167
+ if (Info.getValue () && Info.getValue () ->shouldHideFromEditor ()) {
161
168
return ;
162
169
}
163
170
// Disallow invalid initializer references
@@ -215,7 +222,7 @@ void ArgumentTypeCheckCompletionCallback::sawSolutionImpl(const Solution &S) {
215
222
216
223
// If this is a duplicate of any other result, ignore this solution.
217
224
if (llvm::any_of (Results, [&](const Result &R) {
218
- return R.FuncD == Info.Value &&
225
+ return R.FuncDeclRef == Info.ValueRef &&
219
226
nullableTypesEqual (R.FuncTy , Info.ValueTy ) &&
220
227
nullableTypesEqual (R.BaseType , Info.BaseTy ) &&
221
228
R.ParamIdx == ParamIdx &&
@@ -232,9 +239,10 @@ void ArgumentTypeCheckCompletionCallback::sawSolutionImpl(const Solution &S) {
232
239
FuncTy = Info.ValueTy ->lookThroughAllOptionalTypes ()->getAs <AnyFunctionType>();
233
240
}
234
241
Results.push_back ({ExpectedTy, ExpectedCallType,
235
- isa<SubscriptExpr>(ParentCall), Info.Value , FuncTy, ArgIdx,
236
- ParamIdx, std::move (ClaimedParams), IsNoninitialVariadic,
237
- Info.BaseTy , HasLabel, IsAsync, SolutionSpecificVarTypes});
242
+ isa<SubscriptExpr>(ParentCall), Info.ValueRef , FuncTy,
243
+ ArgIdx, ParamIdx, std::move (ClaimedParams),
244
+ IsNoninitialVariadic, Info.BaseTy , HasLabel, IsAsync,
245
+ SolutionSpecificVarTypes});
238
246
}
239
247
240
248
void ArgumentTypeCheckCompletionCallback::computeShadowedDecls (
@@ -243,24 +251,25 @@ void ArgumentTypeCheckCompletionCallback::computeShadowedDecls(
243
251
auto &ResultA = Results[i];
244
252
for (size_t j = i + 1 ; j < Results.size (); ++j) {
245
253
auto &ResultB = Results[j];
246
- if (!ResultA.FuncD || !ResultB.FuncD || !ResultA.FuncTy || !ResultB.FuncTy ) {
254
+ if (!ResultA.getFuncD () || !ResultB.getFuncD () || !ResultA.FuncTy ||
255
+ !ResultB.FuncTy ) {
247
256
continue ;
248
257
}
249
- if (ResultA.FuncD ->getName () != ResultB.FuncD ->getName ()) {
258
+ if (ResultA.getFuncD () ->getName () != ResultB.getFuncD () ->getName ()) {
250
259
continue ;
251
260
}
252
261
if (!ResultA.FuncTy ->isEqual (ResultB.FuncTy )) {
253
262
continue ;
254
263
}
255
264
ProtocolDecl *inProtocolExtensionA =
256
- ResultA.FuncD ->getDeclContext ()->getExtendedProtocolDecl ();
265
+ ResultA.getFuncD () ->getDeclContext ()->getExtendedProtocolDecl ();
257
266
ProtocolDecl *inProtocolExtensionB =
258
- ResultB.FuncD ->getDeclContext ()->getExtendedProtocolDecl ();
267
+ ResultB.getFuncD () ->getDeclContext ()->getExtendedProtocolDecl ();
259
268
260
269
if (inProtocolExtensionA && !inProtocolExtensionB) {
261
- ShadowedDecls.insert (ResultA.FuncD );
270
+ ShadowedDecls.insert (ResultA.getFuncD () );
262
271
} else if (!inProtocolExtensionA && inProtocolExtensionB) {
263
- ShadowedDecls.insert (ResultB.FuncD );
272
+ ShadowedDecls.insert (ResultB.getFuncD () );
264
273
}
265
274
}
266
275
}
@@ -301,35 +310,37 @@ void ArgumentTypeCheckCompletionCallback::deliverResults(
301
310
}
302
311
if ((BaseNominal = BaseTy->getAnyNominal ())) {
303
312
SemanticContext = SemanticContextKind::CurrentNominal;
304
- if (Result.FuncD &&
305
- Result.FuncD ->getDeclContext ()->getSelfNominalTypeDecl () !=
313
+ if (Result.getFuncD () &&
314
+ Result.getFuncD () ->getDeclContext ()->getSelfNominalTypeDecl () !=
306
315
BaseNominal) {
307
316
SemanticContext = SemanticContextKind::Super;
308
317
}
309
318
} else if (BaseTy->is <TupleType>() || BaseTy->is <SubstitutableType>()) {
310
319
SemanticContext = SemanticContextKind::CurrentNominal;
311
320
}
312
321
}
313
- if (SemanticContext == SemanticContextKind::None && Result.FuncD ) {
314
- if (Result.FuncD ->getDeclContext ()->isTypeContext ()) {
322
+ if (SemanticContext == SemanticContextKind::None && Result.getFuncD () ) {
323
+ if (Result.getFuncD () ->getDeclContext ()->isTypeContext ()) {
315
324
SemanticContext = SemanticContextKind::CurrentNominal;
316
- } else if (Result.FuncD ->getDeclContext ()->isLocalContext ()) {
325
+ } else if (Result.getFuncD () ->getDeclContext ()->isLocalContext ()) {
317
326
SemanticContext = SemanticContextKind::Local;
318
- } else if (Result.FuncD ->getModuleContext () == DC->getParentModule ()) {
327
+ } else if (Result.getFuncD ()->getModuleContext () ==
328
+ DC->getParentModule ()) {
319
329
SemanticContext = SemanticContextKind::CurrentModule;
320
330
}
321
331
}
322
332
if (Result.FuncTy ) {
323
333
if (auto FuncTy = Result.FuncTy ) {
324
- if (ShadowedDecls.count (Result.FuncD ) == 0 ) {
334
+ if (ShadowedDecls.count (Result.getFuncD () ) == 0 ) {
325
335
// Don't show call pattern completions if the function is
326
336
// overridden.
327
337
if (Result.IsSubscript ) {
328
338
assert (SemanticContext != SemanticContextKind::None);
329
- auto *SD = dyn_cast_or_null<SubscriptDecl>(Result.FuncD );
339
+ auto *SD = dyn_cast_or_null<SubscriptDecl>(Result.getFuncD () );
330
340
Lookup.addSubscriptCallPattern (FuncTy, SD, SemanticContext);
331
341
} else {
332
- auto *FD = dyn_cast_or_null<AbstractFunctionDecl>(Result.FuncD );
342
+ auto *FD =
343
+ dyn_cast_or_null<AbstractFunctionDecl>(Result.getFuncD ());
333
344
Lookup.addFunctionCallPattern (FuncTy, FD, SemanticContext);
334
345
}
335
346
}
0 commit comments