@@ -180,6 +180,27 @@ static ValueDecl *rewriteIntegerTypes(SubstitutionMap subst, ValueDecl *oldDecl,
180180 return newDecl;
181181}
182182
183+ static Expr *createSelfExpr (FuncDecl *fnDecl) {
184+ ASTContext &ctx = fnDecl->getASTContext ();
185+
186+ auto selfDecl = fnDecl->getImplicitSelfDecl ();
187+ auto selfRefExpr = new (ctx) DeclRefExpr (selfDecl, DeclNameLoc (),
188+ /* implicit*/ true );
189+
190+ if (!fnDecl->isMutating ()) {
191+ selfRefExpr->setType (selfDecl->getInterfaceType ());
192+ return selfRefExpr;
193+ }
194+ selfRefExpr->setType (LValueType::get (selfDecl->getInterfaceType ()));
195+
196+ auto inoutSelfExpr = new (ctx) InOutExpr (
197+ SourceLoc (), selfRefExpr,
198+ fnDecl->mapTypeIntoContext (selfDecl->getValueInterfaceType ()),
199+ /* isImplicit*/ true );
200+ inoutSelfExpr->setType (InOutType::get (selfDecl->getInterfaceType ()));
201+ return inoutSelfExpr;
202+ }
203+
183204// Synthesize a thunk body for the function created in
184205// "addThunkForDependentTypes". This will just cast all params and forward them
185206// along to the specialized function. It will also cast the result before
@@ -211,10 +232,27 @@ synthesizeDependentTypeThunkParamForwarding(AbstractFunctionDecl *afd, void *con
211232 paramIndex++;
212233 }
213234
214- auto *specializedFuncDeclRef = new (ctx) DeclRefExpr (ConcreteDeclRef (specializedFuncDecl),
235+ Expr *specializedFuncDeclRef = new (ctx) DeclRefExpr (ConcreteDeclRef (specializedFuncDecl),
215236 DeclNameLoc (), true );
216237 specializedFuncDeclRef->setType (specializedFuncDecl->getInterfaceType ());
217238
239+ if (specializedFuncDecl->isInstanceMember ()) {
240+ auto selfExpr = createSelfExpr (thunkDecl);
241+ auto *memberCall = DotSyntaxCallExpr::create (ctx, specializedFuncDeclRef, SourceLoc (), selfExpr);
242+ memberCall->setThrows (false );
243+ auto resultType = specializedFuncDecl->getInterfaceType ()->getAs <FunctionType>()->getResult ();
244+ specializedFuncDeclRef = memberCall;
245+ specializedFuncDeclRef->setType (resultType);
246+ } else if (specializedFuncDecl->isStatic ()) {
247+ auto resultType = specializedFuncDecl->getInterfaceType ()->getAs <FunctionType>()->getResult ();
248+ auto selfType = cast<NominalTypeDecl>(thunkDecl->getDeclContext ()->getAsDecl ())->getDeclaredInterfaceType ();
249+ auto selfTypeExpr = TypeExpr::createImplicit (selfType, ctx);
250+ auto *memberCall = DotSyntaxCallExpr::create (ctx, specializedFuncDeclRef, SourceLoc (), selfTypeExpr);
251+ memberCall->setThrows (false );
252+ specializedFuncDeclRef = memberCall;
253+ specializedFuncDeclRef->setType (resultType);
254+ }
255+
218256 auto argList = ArgumentList::createImplicit (ctx, forwardingParams);
219257 auto *specializedFuncCallExpr = CallExpr::createImplicit (ctx, specializedFuncDeclRef, argList);
220258 specializedFuncCallExpr->setType (specializedFuncDecl->getResultInterfaceType ());
@@ -279,6 +317,7 @@ static ValueDecl *addThunkForDependentTypes(FuncDecl *oldDecl,
279317 newFnDecl->copyFormalAccessFrom (newDecl);
280318 newFnDecl->setBodySynthesizer (synthesizeDependentTypeThunkParamForwarding, newDecl);
281319 newFnDecl->setSelfAccessKind (newDecl->getSelfAccessKind ());
320+ if (newDecl->isStatic ()) newFnDecl->setStatic ();
282321 newFnDecl->getAttrs ().add (
283322 new (newDecl->getASTContext ()) TransparentAttr (/* IsImplicit=*/ true ));
284323 return newFnDecl;
@@ -308,10 +347,27 @@ synthesizeForwardingThunkBody(AbstractFunctionDecl *afd, void *context) {
308347 forwardingParams.push_back (Argument (SourceLoc (), Identifier (), paramRefExpr));
309348 }
310349
311- auto *specializedFuncDeclRef = new (ctx) DeclRefExpr (ConcreteDeclRef (specializedFuncDecl),
350+ Expr *specializedFuncDeclRef = new (ctx) DeclRefExpr (ConcreteDeclRef (specializedFuncDecl),
312351 DeclNameLoc (), true );
313352 specializedFuncDeclRef->setType (specializedFuncDecl->getInterfaceType ());
314353
354+ if (specializedFuncDecl->isInstanceMember ()) {
355+ auto selfExpr = createSelfExpr (thunkDecl);
356+ auto *memberCall = DotSyntaxCallExpr::create (ctx, specializedFuncDeclRef, SourceLoc (), selfExpr);
357+ memberCall->setThrows (false );
358+ auto resultType = specializedFuncDecl->getInterfaceType ()->getAs <FunctionType>()->getResult ();
359+ specializedFuncDeclRef = memberCall;
360+ specializedFuncDeclRef->setType (resultType);
361+ } else if (specializedFuncDecl->isStatic ()) {
362+ auto resultType = specializedFuncDecl->getInterfaceType ()->getAs <FunctionType>()->getResult ();
363+ auto selfType = cast<NominalTypeDecl>(thunkDecl->getDeclContext ()->getAsDecl ())->getDeclaredInterfaceType ();
364+ auto selfTypeExpr = TypeExpr::createImplicit (selfType, ctx);
365+ auto *memberCall = DotSyntaxCallExpr::create (ctx, specializedFuncDeclRef, SourceLoc (), selfTypeExpr);
366+ memberCall->setThrows (false );
367+ specializedFuncDeclRef = memberCall;
368+ specializedFuncDeclRef->setType (resultType);
369+ }
370+
315371 auto argList = ArgumentList::createImplicit (ctx, forwardingParams);
316372 auto *specializedFuncCallExpr = CallExpr::createImplicit (ctx, specializedFuncDeclRef, argList);
317373 specializedFuncCallExpr->setType (thunkDecl->getResultInterfaceType ());
@@ -379,6 +435,7 @@ static ValueDecl *generateThunkForExtraMetatypes(SubstitutionMap subst,
379435 thunk->copyFormalAccessFrom (newDecl);
380436 thunk->setBodySynthesizer (synthesizeForwardingThunkBody, newDecl);
381437 thunk->setSelfAccessKind (newDecl->getSelfAccessKind ());
438+ if (newDecl->isStatic ()) thunk->setStatic ();
382439 thunk->getAttrs ().add (
383440 new (newDecl->getASTContext ()) TransparentAttr (/* IsImplicit=*/ true ));
384441
0 commit comments