@@ -2246,3 +2246,57 @@ bool OutOfOrderArgumentFailure::diagnoseAsError() {
22462246
22472247 return true ;
22482248}
2249+
2250+ bool InaccessibleMemberFailure::diagnoseAsError () {
2251+ auto *anchor = getRawAnchor ();
2252+ // Let's try to avoid over-diagnosing chains of inaccessible
2253+ // members e.g.:
2254+ //
2255+ // struct A {
2256+ // struct B {
2257+ // struct C {}
2258+ // }
2259+ // }
2260+ //
2261+ // _ = A.B.C()
2262+ //
2263+ // We'll have a fix for each `B', `C` and `C.init` but it makes
2264+ // sense to diagnose only `B` and consider the rest hidden.
2265+ Expr *baseExpr = nullptr ;
2266+ DeclNameLoc nameLoc;
2267+ if (auto *UDE = dyn_cast<UnresolvedDotExpr>(anchor)) {
2268+ baseExpr = UDE->getBase ();
2269+ nameLoc = UDE->getNameLoc ();
2270+ } else if (auto *UME = dyn_cast<UnresolvedMemberExpr>(anchor)) {
2271+ nameLoc = UME->getNameLoc ();
2272+ } else if (auto *SE = dyn_cast<SubscriptExpr>(anchor)) {
2273+ baseExpr = SE->getBase ();
2274+ } else if (auto *call = dyn_cast<CallExpr>(anchor)) {
2275+ baseExpr = call->getFn ();
2276+ }
2277+
2278+ if (baseExpr) {
2279+ auto &cs = getConstraintSystem ();
2280+ auto *locator =
2281+ cs.getConstraintLocator (baseExpr, ConstraintLocator::Member);
2282+ if (llvm::any_of (cs.getFixes (), [&](const ConstraintFix *fix) {
2283+ return fix->getLocator () == locator;
2284+ }))
2285+ return false ;
2286+ }
2287+
2288+ auto loc = nameLoc.isValid () ? nameLoc.getStartLoc () : anchor->getLoc ();
2289+ auto accessLevel = Member->getFormalAccessScope ().accessLevelForDiagnostics ();
2290+ if (auto *CD = dyn_cast<ConstructorDecl>(Member)) {
2291+ emitDiagnostic (loc, diag::init_candidate_inaccessible,
2292+ CD->getResultInterfaceType (), accessLevel)
2293+ .highlight (nameLoc.getSourceRange ());
2294+ } else {
2295+ emitDiagnostic (loc, diag::candidate_inaccessible, Member->getBaseName (),
2296+ accessLevel)
2297+ .highlight (nameLoc.getSourceRange ());
2298+ }
2299+
2300+ emitDiagnostic (Member, diag::decl_declared_here, Member->getFullName ());
2301+ return true ;
2302+ }
0 commit comments