@@ -1409,7 +1409,15 @@ class SyntacticElementSolutionApplication
1409
1409
}
1410
1410
1411
1411
auto caseStmt = cast<CaseStmt>(rawCase.get <Stmt *>());
1412
- visitCaseStmt (caseStmt);
1412
+ // Body of the `case` statement can contain a `fallthrough`
1413
+ // statement that requires both source and destination
1414
+ // `case` preambles to be type-checked, so bodies of `case`
1415
+ // statements should be visited after preambles.
1416
+ visitCaseStmtPreamble (caseStmt);
1417
+ }
1418
+
1419
+ for (auto *caseStmt : switchStmt->getCases ()) {
1420
+ visitCaseStmtBody (caseStmt);
1413
1421
1414
1422
// Check restrictions on '@unknown'.
1415
1423
if (caseStmt->hasUnknownAttr ()) {
@@ -1436,7 +1444,7 @@ class SyntacticElementSolutionApplication
1436
1444
return doStmt;
1437
1445
}
1438
1446
1439
- ASTNode visitCaseStmt (CaseStmt *caseStmt) {
1447
+ void visitCaseStmtPreamble (CaseStmt *caseStmt) {
1440
1448
// Translate the patterns and guard expressions for each case label item.
1441
1449
for (auto &caseItem : caseStmt->getMutableCaseLabelItems ()) {
1442
1450
SolutionApplicationTarget caseTarget (&caseItem,
@@ -1453,11 +1461,16 @@ class SyntacticElementSolutionApplication
1453
1461
solution.getType (prev)->mapTypeOutOfContext ());
1454
1462
expected->setInterfaceType (type);
1455
1463
}
1464
+ }
1456
1465
1457
- // Translate the body.
1466
+ void visitCaseStmtBody (CaseStmt *caseStmt) {
1458
1467
auto *newBody = visit (caseStmt->getBody ()).get <Stmt *>();
1459
1468
caseStmt->setBody (cast<BraceStmt>(newBody));
1469
+ }
1460
1470
1471
+ ASTNode visitCaseStmt (CaseStmt *caseStmt) {
1472
+ visitCaseStmtPreamble (caseStmt);
1473
+ visitCaseStmtBody (caseStmt);
1461
1474
return caseStmt;
1462
1475
}
1463
1476
0 commit comments