@@ -1857,7 +1857,7 @@ static void fixItAvailableAttrRename(InFlightDiagnostic &diag,
18571857 SourceRange referenceRange,
18581858 const ValueDecl *renamedDecl,
18591859 const AvailableAttr *attr,
1860- const ApplyExpr *call) {
1860+ const Expr *call) {
18611861 if (isa<AccessorDecl>(renamedDecl))
18621862 return ;
18631863
@@ -1877,21 +1877,21 @@ static void fixItAvailableAttrRename(InFlightDiagnostic &diag,
18771877
18781878 auto &ctx = renamedDecl->getASTContext ();
18791879 SourceManager &sourceMgr = ctx.SourceMgr ;
1880-
18811880 if (parsed.isInstanceMember ()) {
1881+ auto *CE = dyn_cast_or_null<CallExpr>(call);
1882+ if (!CE)
1883+ return ;
1884+
18821885 // Replace the base of the call with the "self argument".
18831886 // We can only do a good job with the fix-it if we have the whole call
18841887 // expression.
18851888 // FIXME: Should we be validating the ContextName in some way?
1886- if (!call || !isa<CallExpr>(call))
1887- return ;
1888-
18891889 unsigned selfIndex = parsed.SelfIndex .getValue ();
18901890 const Expr *selfExpr = nullptr ;
18911891 SourceLoc removeRangeStart;
18921892 SourceLoc removeRangeEnd;
18931893
1894- auto *argExpr = call ->getArg ();
1894+ auto *argExpr = CE ->getArg ();
18951895 auto argList = getOriginalArgumentList (argExpr);
18961896
18971897 size_t numElementsWithinParens = argList.args .size ();
@@ -1988,54 +1988,83 @@ static void fixItAvailableAttrRename(InFlightDiagnostic &diag,
19881988 selfReplace += base;
19891989 if (needsParens)
19901990 selfReplace.push_back (' )' );
1991+
19911992 selfReplace.push_back (' .' );
19921993 selfReplace += parsed.BaseName ;
1993- diag.fixItReplace (call->getFn ()->getSourceRange (), selfReplace);
1994+
1995+ diag.fixItReplace (CE->getFn ()->getSourceRange (), selfReplace);
19941996
19951997 if (!parsed.isPropertyAccessor ())
19961998 diag.fixItRemoveChars (removeRangeStart, removeRangeEnd);
19971999
19982000 // Continue on to diagnose any argument label renames.
19992001
20002002 } else if (parsed.BaseName == " init" && isa_and_nonnull<CallExpr>(call)) {
2003+ auto *CE = dyn_cast<CallExpr>(call);
2004+
20012005 // For initializers, replace with a "call" of the context type...but only
20022006 // if we know we're doing a call (rather than a first-class reference).
20032007 if (parsed.isMember ()) {
2004- diag.fixItReplace (call->getFn ()->getSourceRange (), parsed.ContextName );
2005-
2006- } else if (auto *dotCall = dyn_cast<DotSyntaxCallExpr>(call->getFn ())) {
2008+ diag.fixItReplace (CE->getFn ()->getSourceRange (), parsed.ContextName );
2009+ } else if (auto *dotCall = dyn_cast<DotSyntaxCallExpr>(CE->getFn ())) {
20072010 SourceLoc removeLoc = dotCall->getDotLoc ();
20082011 if (removeLoc.isInvalid ())
20092012 return ;
20102013
20112014 diag.fixItRemove (SourceRange (removeLoc, dotCall->getFn ()->getEndLoc ()));
2012- } else if (!isa<ConstructorRefCallExpr>(call ->getFn ())) {
2015+ } else if (!isa<ConstructorRefCallExpr>(CE ->getFn ())) {
20132016 return ;
20142017 }
20152018
20162019 // Continue on to diagnose any constructor argument label renames.
2017-
2020+
2021+ } else if (parsed.IsSubscript ) {
2022+ if (auto *CE = dyn_cast_or_null<CallExpr>(call)) {
2023+ // Renaming from CallExpr to SubscriptExpr. Remove function name and
2024+ // replace parens with square brackets.
2025+ diag.fixItReplace (CE->getFn ()->getEndLoc (), " [" );
2026+ diag.fixItReplace (CE->getEndLoc (), " ]" );
2027+ }
20182028 } else {
20192029 // Just replace the base name.
20202030 SmallString<64 > baseReplace;
2031+
20212032 if (!parsed.ContextName .empty ()) {
20222033 baseReplace += parsed.ContextName ;
20232034 baseReplace += ' .' ;
20242035 }
20252036 baseReplace += parsed.BaseName ;
2026- if (parsed.IsFunctionName && parsed.ArgumentLabels .empty () &&
2027- isa<VarDecl>(renamedDecl)) {
2028- // If we're going from a var to a function with no arguments, emit an
2029- // empty parameter list.
2030- baseReplace += " ()" ;
2037+
2038+ if (parsed.IsFunctionName && isa_and_nonnull<SubscriptExpr>(call)) {
2039+ auto *SE = dyn_cast<SubscriptExpr>(call);
2040+ // Renaming from SubscriptExpr to CallExpr. Insert function name and
2041+ // replace square brackets with parens.
2042+
2043+ diag.fixItReplace (SE->getIndex ()->getStartLoc (),
2044+ (" ." + baseReplace.str ()).str ());
2045+ diag.fixItReplace (SE->getEndLoc (), " )" );
2046+ } else {
2047+ if (parsed.IsFunctionName && parsed.ArgumentLabels .empty () &&
2048+ isa<VarDecl>(renamedDecl)) {
2049+ // If we're going from a var to a function with no arguments, emit an
2050+ // empty parameter list.
2051+ baseReplace += " ()" ;
2052+ }
2053+ diag.fixItReplace (referenceRange, baseReplace);
20312054 }
2032- diag.fixItReplace (referenceRange, baseReplace);
20332055 }
20342056
2035- if (!call || !isa<CallExpr>(call))
2057+ if (!call)
2058+ return ;
2059+
2060+ Expr *argExpr;
2061+ if (auto *CE = dyn_cast<CallExpr>(call))
2062+ argExpr = CE->getArg ();
2063+ else if (auto *SE = dyn_cast<SubscriptExpr>(call))
2064+ argExpr = SE->getIndex ();
2065+ else
20362066 return ;
20372067
2038- auto *argExpr = call->getArg ();
20392068 auto argList = getOriginalArgumentList (argExpr);
20402069
20412070 if (parsed.IsGetter ) {
@@ -2148,7 +2177,8 @@ static void fixItAvailableAttrRename(InFlightDiagnostic &diag,
21482177 if (argList.isUnlabeledTrailingClosureIdx (i))
21492178 continue ;
21502179 if (argumentLabelIDs[i] != argList.labels [i]) {
2151- diagnoseArgumentLabelError (ctx, argExpr, argumentLabelIDs, false , &diag);
2180+ diagnoseArgumentLabelError (ctx, argExpr, argumentLabelIDs,
2181+ parsed.IsSubscript , &diag);
21522182 return ;
21532183 }
21542184 }
@@ -2191,7 +2221,7 @@ describeRename(ASTContext &ctx, const AvailableAttr *attr, const ValueDecl *D,
21912221 name << parsed.ContextName << ' .' ;
21922222
21932223 if (parsed.IsFunctionName ) {
2194- name << parsed.formDeclName (ctx);
2224+ name << parsed.formDeclName (ctx, (D && isa<SubscriptDecl>(D)) );
21952225 } else {
21962226 name << parsed.BaseName ;
21972227 }
@@ -2208,7 +2238,7 @@ describeRename(ASTContext &ctx, const AvailableAttr *attr, const ValueDecl *D,
22082238void TypeChecker::diagnoseIfDeprecated (SourceRange ReferenceRange,
22092239 const ExportContext &Where,
22102240 const ValueDecl *DeprecatedDecl,
2211- const ApplyExpr *Call) {
2241+ const Expr *Call) {
22122242 const AvailableAttr *Attr = TypeChecker::getDeprecated (DeprecatedDecl);
22132243 if (!Attr)
22142244 return ;
@@ -2392,10 +2422,9 @@ void swift::diagnoseUnavailableOverride(ValueDecl *override,
23922422
23932423// / Emit a diagnostic for references to declarations that have been
23942424// / marked as unavailable, either through "unavailable" or "obsoleted:".
2395- bool swift::diagnoseExplicitUnavailability (const ValueDecl *D,
2396- SourceRange R,
2425+ bool swift::diagnoseExplicitUnavailability (const ValueDecl *D, SourceRange R,
23972426 const ExportContext &Where,
2398- const ApplyExpr *call,
2427+ const Expr *call,
23992428 DeclAvailabilityFlags Flags) {
24002429 return diagnoseExplicitUnavailability (D, R, Where, Flags,
24012430 [=](InFlightDiagnostic &diag) {
@@ -2762,7 +2791,7 @@ class ExprAvailabilityWalker : public ASTWalker {
27622791 diagnoseDeclRefAvailability (DS->getMember (), DS->getSourceRange ());
27632792 if (auto S = dyn_cast<SubscriptExpr>(E)) {
27642793 if (S->hasDecl ()) {
2765- diagnoseDeclRefAvailability (S->getDecl (), S->getSourceRange ());
2794+ diagnoseDeclRefAvailability (S->getDecl (), S->getSourceRange (), S );
27662795 maybeDiagStorageAccess (S->getDecl ().getDecl (), S->getSourceRange (), DC);
27672796 }
27682797 }
@@ -2820,7 +2849,7 @@ class ExprAvailabilityWalker : public ASTWalker {
28202849 }
28212850
28222851 bool diagnoseDeclRefAvailability (ConcreteDeclRef declRef, SourceRange R,
2823- const ApplyExpr *call = nullptr ,
2852+ const Expr *call = nullptr ,
28242853 DeclAvailabilityFlags flags = None) const ;
28252854
28262855private:
@@ -3003,9 +3032,8 @@ class ExprAvailabilityWalker : public ASTWalker {
30033032
30043033// / Diagnose uses of unavailable declarations. Returns true if a diagnostic
30053034// / was emitted.
3006- bool
3007- ExprAvailabilityWalker::diagnoseDeclRefAvailability (
3008- ConcreteDeclRef declRef, SourceRange R, const ApplyExpr *call,
3035+ bool ExprAvailabilityWalker::diagnoseDeclRefAvailability (
3036+ ConcreteDeclRef declRef, SourceRange R, const Expr *call,
30093037 DeclAvailabilityFlags Flags) const {
30103038 if (!declRef)
30113039 return false ;
@@ -3014,7 +3042,8 @@ ExprAvailabilityWalker::diagnoseDeclRefAvailability(
30143042 if (auto *attr = AvailableAttr::isUnavailable (D)) {
30153043 if (diagnoseIncDecRemoval (D, R, attr))
30163044 return true ;
3017- if (call && diagnoseMemoryLayoutMigration (D, R, attr, call))
3045+ if (isa_and_nonnull<ApplyExpr>(call) &&
3046+ diagnoseMemoryLayoutMigration (D, R, attr, dyn_cast<ApplyExpr>(call)))
30183047 return true ;
30193048 }
30203049
@@ -3032,12 +3061,10 @@ ExprAvailabilityWalker::diagnoseDeclRefAvailability(
30323061
30333062// / Diagnose uses of unavailable declarations. Returns true if a diagnostic
30343063// / was emitted.
3035- bool
3036- swift::diagnoseDeclAvailability (const ValueDecl *D,
3037- SourceRange R,
3038- const ApplyExpr *call,
3039- const ExportContext &Where,
3040- DeclAvailabilityFlags Flags) {
3064+ bool swift::diagnoseDeclAvailability (const ValueDecl *D, SourceRange R,
3065+ const Expr *call,
3066+ const ExportContext &Where,
3067+ DeclAvailabilityFlags Flags) {
30413068 assert (!Where.isImplicit ());
30423069
30433070 // Generic parameters are always available.
@@ -3097,7 +3124,6 @@ swift::diagnoseDeclAvailability(const ValueDecl *D,
30973124 return false ;
30983125}
30993126
3100-
31013127// / Return true if the specified type looks like an integer of floating point
31023128// / type.
31033129static bool isIntegerOrFloatingPointType (Type ty, ModuleDecl *M) {
0 commit comments