@@ -4162,7 +4162,7 @@ namespace {
41624162
41634163 // SIL-generation magically turns this into a Bool; make sure it can.
41644164 if (!ctx.getBoolBuiltinInitDecl ()) {
4165- ctx.Diags .diagnose (expr->getLoc (), diag::broken_bool );
4165+ ctx.Diags .diagnose (expr->getLoc (), diag::broken_stdlib_type, " Bool " );
41664166 // Continue anyway.
41674167 }
41684168
@@ -4200,7 +4200,7 @@ namespace {
42004200 auto boolDecl = ctx.getBoolDecl ();
42014201
42024202 if (!boolDecl) {
4203- ctx.Diags .diagnose (SourceLoc (), diag::broken_bool );
4203+ ctx.Diags .diagnose (SourceLoc (), diag::broken_stdlib_type, " Bool " );
42044204 }
42054205
42064206 cs.setType (isSomeExpr, boolDecl ? ctx.getBoolType () : Type ());
@@ -7262,77 +7262,46 @@ Expr *ExprRewriter::coerceToType(Expr *expr, Type toType,
72627262
72637263 case ConversionRestrictionKind::CGFloatToDouble:
72647264 case ConversionRestrictionKind::DoubleToCGFloat: {
7265- auto conversionKind = knownRestriction->second ;
7266-
7267- auto shouldUseCoercedExpr = [&]() {
7268- // If conversion wraps the whole body of a single-expression closure,
7269- // let's use the passed-in expression since the closure itself doesn't
7270- // get updated until coercion is done.
7271- if (locator.endsWith <LocatorPathElt::ClosureBody>())
7272- return true ;
7273-
7274- // Contextual type locator always uses the original version of
7275- // expression (before any coercions have been applied) because
7276- // otherwise it wouldn't be possible to find the overload choice.
7277- if (locator.endsWith <LocatorPathElt::ContextualType>())
7278- return true ;
7279-
7280- // In all other cases use the expression associated with locator.
7281- return false ;
7282- };
7283-
7284- auto *argExpr =
7285- shouldUseCoercedExpr () ? expr : locator.trySimplifyToExpr ();
7286- assert (argExpr);
7287-
7288- // Source requires implicit conversion to match destination
7289- // type but the conversion itself is recorded on assignment.
7290- if (auto *assignment = dyn_cast<AssignExpr>(argExpr))
7291- argExpr = assignment->getSrc ();
7292-
7293- // Load the value for conversion.
7294- argExpr = cs.coerceToRValue (argExpr);
7295-
7296- auto *argList = ArgumentList::forImplicitUnlabeled (ctx, {argExpr});
7297- auto *implicitInit = CallExpr::createImplicit (
7298- ctx, TypeExpr::createImplicit (toType, ctx), argList);
7299-
7300- cs.cacheExprTypes (implicitInit->getFn ());
7301- cs.setType (argExpr, fromType);
7302-
7303- auto *callLocator = cs.getConstraintLocator (
7304- implicitInit, LocatorPathElt::ImplicitConversion (conversionKind));
7305-
7306- // HACK: Temporarily push the call expr onto the expr stack to make sure
7307- // we don't try to prematurely close an existential when applying the
7308- // curried member ref. This can be removed once existential opening is
7309- // refactored not to rely on the shape of the AST prior to rewriting.
7310- ExprStack.push_back (implicitInit);
7311- SWIFT_DEFER { ExprStack.pop_back (); };
7312-
7313- // We need to take information recorded for all conversions of this
7314- // kind and move it to a specific location where restriction is applied.
7315- {
7316- auto *memberLoc = solution.getConstraintLocator (
7317- callLocator, {ConstraintLocator::ApplyFunction,
7318- ConstraintLocator::ConstructorMember});
7319-
7320- ConstraintLocator *baseLoc =
7321- cs.getImplicitValueConversionLocator (locator, conversionKind);
7265+ DeclName name (ctx, DeclBaseName::createConstructor (), Identifier ());
7266+
7267+ ConstructorDecl *decl = nullptr ;
7268+ SmallVector<ValueDecl *, 2 > candidates;
7269+ dc->lookupQualified (toType->getAnyNominal (),
7270+ DeclNameRef (name), SourceLoc (),
7271+ NL_QualifiedDefault, candidates);
7272+ for (auto *candidate : candidates) {
7273+ auto *ctor = cast<ConstructorDecl>(candidate);
7274+ auto fnType = ctor->getMethodInterfaceType ()->castTo <FunctionType>();
7275+ if (fnType->getNumParams () == 1 &&
7276+ fnType->getParams ()[0 ].getPlainType ()->isEqual (fromType) &&
7277+ fnType->getResult ()->isEqual (toType)) {
7278+ decl = ctor;
7279+ break ;
7280+ }
7281+ }
73227282
7323- auto overload =
7324- solution.getOverloadChoice (solution.getConstraintLocator (
7325- baseLoc, {ConstraintLocator::ApplyFunction,
7326- ConstraintLocator::ConstructorMember}));
7283+ if (decl == nullptr ) {
7284+ ctx.Diags .diagnose (expr->getLoc (), diag::broken_stdlib_type,
7285+ toType->getAnyNominal ()->getName ().str ());
7286+ auto *errorExpr = new (ctx) ErrorExpr (SourceRange (), toType);
7287+ cs.setType (errorExpr, toType);
73277288
7328- solution. overloadChoices . insert ({memberLoc, overload}) ;
7289+ return errorExpr ;
73297290 }
73307291
7331- // Record the implicit call's parameter bindings and match direction.
7332- solution.recordSingleArgMatchingChoice (callLocator);
7292+ auto *ctorRefExpr = new (ctx) DeclRefExpr (decl, DeclNameLoc (), /* Implicit=*/ true );
7293+ ctorRefExpr->setType (decl->getInterfaceType ());
7294+ auto *typeExpr = TypeExpr::createImplicit (toType, ctx);
7295+ auto *innerCall = ConstructorRefCallExpr::create (ctx, ctorRefExpr, typeExpr,
7296+ decl->getMethodInterfaceType ());
7297+ cs.cacheExprTypes (innerCall);
7298+
7299+ auto *argList = ArgumentList::forImplicitUnlabeled (ctx, {cs.coerceToRValue (expr)});
7300+ auto *outerCall = CallExpr::createImplicit (ctx, innerCall, argList);
7301+ outerCall->setType (toType);
7302+ cs.setType (outerCall, toType);
73337303
7334- finishApply (implicitInit, toType, callLocator, callLocator);
7335- return implicitInit;
7304+ return outerCall;
73367305 }
73377306 }
73387307 }
0 commit comments