diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 50d3bbbc97e91..5ddc30eb09327 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -128,6 +128,8 @@ Improvements to Clang's diagnostics which are supposed to only exist once per program, but may get duplicated when built into a shared library. - Fixed a bug where Clang's Analysis did not correctly model the destructor behavior of ``union`` members (#GH119415). +- A statement attribute applied to a ``case`` label no longer suppresses + 'bypassing variable initialization' diagnostics (#84072). Improvements to Clang's time-trace ---------------------------------- diff --git a/clang/lib/Sema/JumpDiagnostics.cpp b/clang/lib/Sema/JumpDiagnostics.cpp index ffbb9bc0bfe7c..edcfffa2b3894 100644 --- a/clang/lib/Sema/JumpDiagnostics.cpp +++ b/clang/lib/Sema/JumpDiagnostics.cpp @@ -597,15 +597,6 @@ void JumpScopeChecker::BuildScopeInformation(Stmt *S, LabelAndGotoScopes[S] = ParentScope; break; - case Stmt::AttributedStmtClass: { - AttributedStmt *AS = cast(S); - if (GetMustTailAttr(AS)) { - LabelAndGotoScopes[AS] = ParentScope; - MustTailStmts.push_back(AS); - } - break; - } - case Stmt::OpenACCComputeConstructClass: { unsigned NewParentScope = Scopes.size(); OpenACCComputeConstruct *CC = cast(S); @@ -649,7 +640,7 @@ void JumpScopeChecker::BuildScopeInformation(Stmt *S, continue; } - // Cases, labels, and defaults aren't "scope parents". It's also + // Cases, labels, attributes, and defaults aren't "scope parents". It's also // important to handle these iteratively instead of recursively in // order to avoid blowing out the stack. while (true) { @@ -658,7 +649,13 @@ void JumpScopeChecker::BuildScopeInformation(Stmt *S, Next = SC->getSubStmt(); else if (LabelStmt *LS = dyn_cast(SubStmt)) Next = LS->getSubStmt(); - else + else if (AttributedStmt *AS = dyn_cast(SubStmt)) { + if (GetMustTailAttr(AS)) { + LabelAndGotoScopes[AS] = ParentScope; + MustTailStmts.push_back(AS); + } + Next = AS->getSubStmt(); + } else break; LabelAndGotoScopes[SubStmt] = ParentScope; diff --git a/clang/test/CXX/stmt.stmt/stmt.select/stmt.switch/p4.cpp b/clang/test/CXX/stmt.stmt/stmt.select/stmt.switch/p4.cpp new file mode 100644 index 0000000000000..e816da1803694 --- /dev/null +++ b/clang/test/CXX/stmt.stmt/stmt.select/stmt.switch/p4.cpp @@ -0,0 +1,11 @@ +// RUN: %clang -fsyntax-only -std=c++20 -Xclang -verify %s + +void Func(int x) { + switch (x) { + [[likely]] case 0: + case 1: + int i = 3; // expected-note {{jump bypasses variable initialization}} + case 2: // expected-error {{cannot jump from switch statement to this case label}} + break; + } +}