@@ -327,20 +327,31 @@ void ParentConditionalConformance::diagnoseConformanceStack(
327327}
328328
329329namespace {
330- // / Produce any additional syntactic diagnostics for the body of a function
331- // / that had a result builder applied.
332- class FunctionSyntacticDiagnosticWalker : public ASTWalker {
330+ // / Produce any additional syntactic diagnostics for a SyntacticElementTarget.
331+ class SyntacticDiagnosticWalker final : public ASTWalker {
333332 SmallVector<DeclContext *, 4 > dcStack;
333+ const SyntacticElementTarget &Target;
334+ bool IsTopLevelExprStmt;
335+
336+ SyntacticDiagnosticWalker (const SyntacticElementTarget &target,
337+ bool isExprStmt)
338+ : Target(target), IsTopLevelExprStmt(isExprStmt) {
339+ dcStack.push_back (target.getDeclContext ());
340+ }
334341
335342public:
336- FunctionSyntacticDiagnosticWalker (DeclContext *dc) { dcStack.push_back (dc); }
343+ static void check (const SyntacticElementTarget &target, bool isExprStmt) {
344+ auto walker = SyntacticDiagnosticWalker (target, isExprStmt);
345+ target.walk (walker);
346+ }
337347
338348 MacroWalking getMacroWalkingBehavior () const override {
339349 return MacroWalking::Expansion;
340350 }
341351
342352 PreWalkResult<Expr *> walkToExprPre (Expr *expr) override {
343- performSyntacticExprDiagnostics (expr, dcStack.back (), /* isExprStmt=*/ false );
353+ auto isExprStmt = (expr == Target.getAsExpr ()) ? IsTopLevelExprStmt : false ;
354+ performSyntacticExprDiagnostics (expr, dcStack.back (), isExprStmt);
344355
345356 if (auto closure = dyn_cast<ClosureExpr>(expr)) {
346357 if (closure->isSeparatelyTypeChecked ()) {
@@ -368,9 +379,10 @@ class FunctionSyntacticDiagnosticWalker : public ASTWalker {
368379 return Action::Continue (stmt);
369380 }
370381
371- PreWalkResult<Pattern *> walkToPatternPre (Pattern *pattern ) override {
372- return Action::SkipNode (pattern );
382+ PreWalkAction walkToDeclPre (Decl *D ) override {
383+ return Action::VisitNodeIf (isa<PatternBindingDecl>(D) );
373384 }
385+
374386 PreWalkAction walkToTypeReprPre (TypeRepr *typeRepr) override {
375387 return Action::SkipNode ();
376388 }
@@ -382,41 +394,7 @@ class FunctionSyntacticDiagnosticWalker : public ASTWalker {
382394
383395void constraints::performSyntacticDiagnosticsForTarget (
384396 const SyntacticElementTarget &target, bool isExprStmt) {
385- auto *dc = target.getDeclContext ();
386- switch (target.kind ) {
387- case SyntacticElementTarget::Kind::expression: {
388- // First emit diagnostics for the main expression.
389- performSyntacticExprDiagnostics (target.getAsExpr (), dc, isExprStmt);
390- return ;
391- }
392-
393- case SyntacticElementTarget::Kind::forEachPreamble: {
394- auto *stmt = target.getAsForEachStmt ();
395-
396- // First emit diagnostics for the main expression.
397- performSyntacticExprDiagnostics (stmt->getTypeCheckedSequence (), dc,
398- isExprStmt);
399-
400- if (auto *whereExpr = stmt->getWhere ())
401- performSyntacticExprDiagnostics (whereExpr, dc, /* isExprStmt*/ false );
402- return ;
403- }
404-
405- case SyntacticElementTarget::Kind::function: {
406- auto *body = target.getFunctionBody ();
407- FunctionSyntacticDiagnosticWalker walker (dc);
408- body->walk (walker);
409- return ;
410- }
411- case SyntacticElementTarget::Kind::closure:
412- case SyntacticElementTarget::Kind::stmtCondition:
413- case SyntacticElementTarget::Kind::caseLabelItem:
414- case SyntacticElementTarget::Kind::patternBinding:
415- case SyntacticElementTarget::Kind::uninitializedVar:
416- // Nothing to do for these.
417- return ;
418- }
419- llvm_unreachable (" Unhandled case in switch!" );
397+ SyntacticDiagnosticWalker::check (target, isExprStmt);
420398}
421399
422400#pragma mark High-level entry points
0 commit comments