https://github.com/ChuanqiXu9 created 
https://github.com/llvm/llvm-project/pull/214389

Reverts llvm/llvm-project#208348 as it introduces a regression in 
https://github.com/llvm/llvm-project/issues/214091

>From 63465d3eb6e406612367629183b84817aa425ab0 Mon Sep 17 00:00:00 2001
From: Chuanqi Xu <[email protected]>
Date: Thu, 6 Aug 2026 10:55:51 +0800
Subject: [PATCH] =?UTF-8?q?Revert=20"[Modules]=20Handle=20decl=20attribute?=
 =?UTF-8?q?s=20on=20deserialization=20the=20same=20as=20durin=E2=80=A6"?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

This reverts commit 3ce0df7ca8027229618de9802eeffe1f0023bf74.
---
 clang/docs/ReleaseNotes.md                    |  1 -
 clang/include/clang/Parse/Parser.h            | 10 +--
 clang/lib/Interpreter/IncrementalParser.cpp   |  2 +-
 clang/lib/Parse/ParseAST.cpp                  |  2 +-
 clang/lib/Parse/ParseHLSLRootSignature.cpp    |  2 +-
 clang/lib/Parse/Parser.cpp                    |  5 +-
 clang/lib/Sema/Sema.cpp                       |  4 -
 clang/lib/Serialization/ASTReaderDecl.cpp     | 55 ++++++++-----
 .../decl-attr-merge-explicit-modules.c        | 79 -------------------
 clang/test/Modules/decl-attr-merge2.c         | 38 ---------
 .../declare_variant_construct_codegen_1.c     |  2 +-
 .../Clang/ClangModulesDeclVendor.cpp          |  2 +-
 12 files changed, 49 insertions(+), 153 deletions(-)
 delete mode 100644 clang/test/Modules/decl-attr-merge-explicit-modules.c
 delete mode 100644 clang/test/Modules/decl-attr-merge2.c

diff --git a/clang/docs/ReleaseNotes.md b/clang/docs/ReleaseNotes.md
index d4b1cf9e44945..2f13ec59483ee 100644
--- a/clang/docs/ReleaseNotes.md
+++ b/clang/docs/ReleaseNotes.md
@@ -398,7 +398,6 @@ features cannot lower the translation-unit ABI level;
   the `sized_by`/`sized_by_or_null` attributes. Because `sized_by` and
   `sized_by_or_null` describe the size in bytes rather than a count of 
elements,
   they are now correctly accepted on such pointers.
-- Propagate attributes on redeclarations across modules.
 
 #### Bug Fixes to C++ Support
 
diff --git a/clang/include/clang/Parse/Parser.h 
b/clang/include/clang/Parse/Parser.h
index 08b67cb08cdd5..163aa483a84e3 100644
--- a/clang/include/clang/Parse/Parser.h
+++ b/clang/include/clang/Parse/Parser.h
@@ -277,12 +277,6 @@ class Parser : public CodeCompletionHandler {
   /// Implementations are in Parser.cpp
   ///@{
 
-private:
-  /// Prepare the parser and its components.
-  ///
-  /// The lack of initialization can lead to missing functionality.
-  void Initialize();
-
 public:
   friend class ColonProtectionRAIIObject;
   friend class PoisonSEHIdentifiersRAIIObject;
@@ -310,6 +304,10 @@ class Parser : public CodeCompletionHandler {
   typedef OpaquePtr<DeclGroupRef> DeclGroupPtrTy;
   typedef OpaquePtr<TemplateName> TemplateTy;
 
+  /// Initialize - Warm up the parser.
+  ///
+  void Initialize();
+
   /// Parse the first top-level declaration in a translation unit.
   ///
   /// \verbatim
diff --git a/clang/lib/Interpreter/IncrementalParser.cpp 
b/clang/lib/Interpreter/IncrementalParser.cpp
index b13d318a1df76..f6d2779d64b2b 100644
--- a/clang/lib/Interpreter/IncrementalParser.cpp
+++ b/clang/lib/Interpreter/IncrementalParser.cpp
@@ -43,7 +43,7 @@ IncrementalParser::IncrementalParser(CompilerInstance 
&Instance,
   if (ExternalASTSource *External = S.getASTContext().getExternalSource())
     External->StartTranslationUnit(Consumer);
 
-  P->ConsumeToken();
+  P->Initialize();
 }
 
 IncrementalParser::~IncrementalParser() { P.reset(); }
diff --git a/clang/lib/Parse/ParseAST.cpp b/clang/lib/Parse/ParseAST.cpp
index b1a798144bf6b..b2eec498a5457 100644
--- a/clang/lib/Parse/ParseAST.cpp
+++ b/clang/lib/Parse/ParseAST.cpp
@@ -155,7 +155,7 @@ void clang::ParseAST(Sema &S, bool PrintStats, bool 
SkipFunctionBodies) {
       }
       return M;
     });
-    P.ConsumeToken();
+    P.Initialize();
     Parser::DeclGroupPtrTy ADecl;
     Sema::ModuleImportState ImportState;
     EnterExpressionEvaluationContext PotentiallyEvaluated(
diff --git a/clang/lib/Parse/ParseHLSLRootSignature.cpp 
b/clang/lib/Parse/ParseHLSLRootSignature.cpp
index 3f461cec5c417..80e81e5c403e1 100644
--- a/clang/lib/Parse/ParseHLSLRootSignature.cpp
+++ b/clang/lib/Parse/ParseHLSLRootSignature.cpp
@@ -1556,7 +1556,7 @@ void HandleRootSignatureTarget(Sema &S, StringRef 
EntryRootSig) {
 
   bool HaveLexer = S.getPreprocessor().getCurrentLexer();
   if (HaveLexer) {
-    P->ConsumeToken();
+    P->Initialize();
     S.ActOnStartOfTranslationUnit();
 
     // Skim through the file to parse to find the define
diff --git a/clang/lib/Parse/Parser.cpp b/clang/lib/Parse/Parser.cpp
index a261178fcad01..d83b75072f844 100644
--- a/clang/lib/Parse/Parser.cpp
+++ b/clang/lib/Parse/Parser.cpp
@@ -83,8 +83,6 @@ Parser::Parser(Preprocessor &pp, Sema &actions, bool 
skipFunctionBodies)
       [this](StringRef TypeStr, StringRef Context, SourceLocation IncludeLoc) {
         return this->ParseTypeFromString(TypeStr, Context, IncludeLoc);
       };
-
-  Initialize();
 }
 
 DiagnosticBuilder Parser::Diag(SourceLocation Loc, unsigned DiagID) {
@@ -580,6 +578,9 @@ void Parser::Initialize() {
   }
 
   Actions.Initialize();
+
+  // Prime the lexer look-ahead.
+  ConsumeToken();
 }
 
 void Parser::DestroyTemplateIds() {
diff --git a/clang/lib/Sema/Sema.cpp b/clang/lib/Sema/Sema.cpp
index 2c229bb12cfc1..d59d82fe5203e 100644
--- a/clang/lib/Sema/Sema.cpp
+++ b/clang/lib/Sema/Sema.cpp
@@ -616,10 +616,6 @@ Sema::~Sema() {
   if (ExternalSemaSource *ExternalSema
         = dyn_cast_or_null<ExternalSemaSource>(Context.getExternalSource()))
     ExternalSema->ForgetSema();
-  // FIXME: keep just a single ExternalSemaSource instead of 2 with a slightly
-  // different behavior.
-  if (ExternalSource)
-    ExternalSource->ForgetSema();
 
   // Delete cached satisfactions.
   std::vector<ConstraintSatisfaction *> Satisfactions;
diff --git a/clang/lib/Serialization/ASTReaderDecl.cpp 
b/clang/lib/Serialization/ASTReaderDecl.cpp
index 05ace69a4d999..4d5c8648fe611 100644
--- a/clang/lib/Serialization/ASTReaderDecl.cpp
+++ b/clang/lib/Serialization/ASTReaderDecl.cpp
@@ -286,7 +286,7 @@ class ASTDeclReader : public DeclVisitor<ASTDeclReader, 
void> {
                                      Decl *Previous, Decl *Canon);
   static void attachPreviousDeclImpl(ASTReader &Reader, ...);
   static void attachPreviousDecl(ASTReader &Reader, Decl *D, Decl *Previous,
-                                 Decl *PreviousNonLocal, Decl *Canon);
+                                 Decl *Canon);
 
   static void checkMultipleDefinitionInNamedModules(ASTReader &Reader, Decl *D,
                                                     Decl *Previous);
@@ -3667,6 +3667,28 @@ Decl *ASTReader::getMostRecentExistingDecl(Decl *D) {
   return ASTDeclReader::getMostRecentDecl(D->getCanonicalDecl());
 }
 
+namespace {
+void mergeInheritableAttributes(ASTReader &Reader, Decl *D, Decl *Previous) {
+  InheritableAttr *NewAttr = nullptr;
+  ASTContext &Context = Reader.getContext();
+  const auto *IA = Previous->getAttr<MSInheritanceAttr>();
+
+  if (IA && !D->hasAttr<MSInheritanceAttr>()) {
+    NewAttr = cast<InheritableAttr>(IA->clone(Context));
+    NewAttr->setInherited(true);
+    D->addAttr(NewAttr);
+  }
+
+  if (!D->hasAttr<AvailabilityAttr>()) {
+    for (const auto *AA : Previous->specific_attrs<AvailabilityAttr>()) {
+      NewAttr = AA->clone(Context);
+      NewAttr->setInherited(true);
+      D->addAttr(NewAttr);
+    }
+  }
+}
+} // namespace
+
 template<typename DeclT>
 void ASTDeclReader::attachPreviousDeclImpl(ASTReader &Reader,
                                            Redeclarable<DeclT> *D,
@@ -3878,8 +3900,7 @@ void 
ASTDeclReader::checkMultipleDefinitionInNamedModules(ASTReader &Reader,
 }
 
 void ASTDeclReader::attachPreviousDecl(ASTReader &Reader, Decl *D,
-                                       Decl *Previous, Decl *PreviousNonLocal,
-                                       Decl *Canon) {
+                                       Decl *Previous, Decl *Canon) {
   assert(D && Previous);
 
   switch (D->getKind()) {
@@ -3908,12 +3929,11 @@ void ASTDeclReader::attachPreviousDecl(ASTReader 
&Reader, Decl *D,
     inheritDefaultTemplateArguments(Reader.getContext(),
                                     cast<TemplateDecl>(Previous), TD);
 
-  if (PreviousNonLocal) {
-    if (Sema *S = Reader.getSema()) {
-      if (auto *ND = dyn_cast<NamedDecl>(D))
-        S->mergeDeclAttributes(ND, PreviousNonLocal);
-    }
-  }
+  // If any of the declaration in the chain contains an Inheritable attribute,
+  // it needs to be added to all the declarations in the redeclarable chain.
+  // FIXME: Only the logic of merging MSInheritableAttr is present, it should
+  // be extended for all inheritable attributes.
+  mergeInheritableAttributes(Reader, D, Previous);
 }
 
 template<typename DeclT>
@@ -4564,17 +4584,17 @@ void 
ASTReader::loadDeclUpdateRecords(PendingUpdateRecord &Record) {
 void ASTReader::loadPendingDeclChain(Decl *FirstLocal, uint64_t LocalOffset) {
   // Attach FirstLocal to the end of the decl chain.
   Decl *CanonDecl = FirstLocal->getCanonicalDecl();
-  Decl *NonLocalMostRecent = nullptr;
   if (FirstLocal != CanonDecl) {
     Decl *PrevMostRecent = ASTDeclReader::getMostRecentDecl(CanonDecl);
-    NonLocalMostRecent = PrevMostRecent ? PrevMostRecent : CanonDecl;
-    ASTDeclReader::attachPreviousDecl(*this, FirstLocal, NonLocalMostRecent,
-                                      NonLocalMostRecent, CanonDecl);
-    ASTDeclReader::attachLatestDecl(CanonDecl, FirstLocal);
+    ASTDeclReader::attachPreviousDecl(
+        *this, FirstLocal, PrevMostRecent ? PrevMostRecent : CanonDecl,
+        CanonDecl);
   }
 
-  if (!LocalOffset)
+  if (!LocalOffset) {
+    ASTDeclReader::attachLatestDecl(CanonDecl, FirstLocal);
     return;
+  }
 
   // Load the list of other redeclarations from this module file.
   ModuleFile *M = getOwningModuleFile(FirstLocal);
@@ -4608,11 +4628,10 @@ void ASTReader::loadPendingDeclChain(Decl *FirstLocal, 
uint64_t LocalOffset) {
   for (unsigned I = 0, N = Record.size(); I != N; ++I) {
     unsigned Idx = N - I - 1;
     auto *D = ReadDecl(*M, Record, Idx);
-    ASTDeclReader::attachPreviousDecl(*this, D, MostRecent, NonLocalMostRecent,
-                                      CanonDecl);
+    ASTDeclReader::attachPreviousDecl(*this, D, MostRecent, CanonDecl);
     MostRecent = D;
-    ASTDeclReader::attachLatestDecl(CanonDecl, MostRecent);
   }
+  ASTDeclReader::attachLatestDecl(CanonDecl, MostRecent);
 }
 
 namespace {
diff --git a/clang/test/Modules/decl-attr-merge-explicit-modules.c 
b/clang/test/Modules/decl-attr-merge-explicit-modules.c
deleted file mode 100644
index 5b31171a3404f..0000000000000
--- a/clang/test/Modules/decl-attr-merge-explicit-modules.c
+++ /dev/null
@@ -1,79 +0,0 @@
-// Check merging attributes when modules are built explicitly.
-//
-// RUN: rm -rf %t
-// RUN: split-file %s %t
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-name=first -xc %t/headers/first.modulemap -emit-module -o 
%t/first.pcm
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-name=second -xc %t/headers/second.modulemap -emit-module -o 
%t/second.pcm
-
-// Without module names.
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=%t/first.pcm -fmodule-file=%t/second.pcm -fsyntax-only 
%t/test.c -verify
-// With module names.
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=first=%t/first.pcm -fmodule-file=second=%t/second.pcm 
-fsyntax-only %t/test.c -verify
-
-// Reverse order.
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=%t/second.pcm -fmodule-file=%t/first.pcm -fsyntax-only 
%t/test-reverse.c -verify
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=second=%t/second.pcm -fmodule-file=first=%t/first.pcm 
-fsyntax-only %t/test-reverse.c -verify
-
-// With a transitive module dependency.
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=first=%t/first.pcm \
-// RUN:   -fmodule-name=second_transitive -xc 
%t/headers/second-transitive.modulemap -emit-module -o %t/second-transitive.pcm
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=%t/second-transitive.pcm -fsyntax-only 
%t/test-transitive.c -verify
-// RUN: %clang_cc1 -fmodules -fno-implicit-modules -triple 
arm64-apple-macosx10.7.0 -I%t/headers \
-// RUN:   -fmodule-file=second_transitive=%t/second-transitive.pcm 
-fsyntax-only %t/test-transitive.c -verify
-
-//--- headers/first.h
-// Added "used" attribute to add corresponding `FunctionDecl` to 
`EagerlyDeserializedDecls`.
-void availabilityAttr(void) __attribute__((used)) 
__attribute__((availability(macos,unavailable)));
-//--- headers/first.modulemap
-module first {
-  header "first.h" export *
-}
-
-//--- headers/second.h
-void availabilityAttr(void) __attribute__((used)) 
__attribute__((availability(ios,introduced=4.0)));
-//--- headers/second.modulemap
-module second {
-  header "second.h" export *
-}
-
-//--- headers/second-transitive.h
-#include <first.h>
-void availabilityAttr(void) __attribute__((availability(ios,introduced=4.0)));
-//--- headers/second-transitive.modulemap
-module second_transitive {
-  header "second-transitive.h" export *
-}
-
-//--- test.c
-#include <first.h>
-#include <second.h>
-void test(void) {
-  availabilityAttr();
-  // expected-error@-1 {{'availabilityAttr' is unavailable: not available on 
macOS}}
-  // [email protected]:* {{'availabilityAttr' has been explicitly marked 
unavailable here}}
-}
-
-//--- test-reverse.c
-#include <second.h>
-#include <first.h>
-void test(void) {
-  availabilityAttr();
-  // expected-error@-1 {{'availabilityAttr' is unavailable: not available on 
macOS}}
-  // [email protected]:* {{'availabilityAttr' has been explicitly marked 
unavailable here}}
-}
-
-//--- test-transitive.c
-#include <second-transitive.h>
-void test(void) {
-  availabilityAttr();
-  // expected-error@-1 {{'availabilityAttr' is unavailable: not available on 
macOS}}
-  // [email protected]:* {{'availabilityAttr' has been explicitly marked 
unavailable here}}
-}
diff --git a/clang/test/Modules/decl-attr-merge2.c 
b/clang/test/Modules/decl-attr-merge2.c
deleted file mode 100644
index fc84b9df70171..0000000000000
--- a/clang/test/Modules/decl-attr-merge2.c
+++ /dev/null
@@ -1,38 +0,0 @@
-// RUN: rm -rf %t
-// RUN: split-file %s %t
-// RUN: %clang_cc1 -fmodules -fimplicit-module-maps \
-// RUN:   -fmodules-cache-path=%t/mcache -triple arm64-apple-macosx10.7.0 \
-// RUN:   -I%t/headers -fsyntax-only %t/test.c -verify
-
-// Check more cases of attribute merging across multiple modules.
-
-//--- headers/module.modulemap
-module First {
-  header "first.h" export *
-}
-module Second {
-  header "second.h" export *
-}
-//--- headers/first.h
-void additiveAttr(void) __attribute__((availability(macos,unavailable)));
-void exclusiveAttr(void) __attribute__((hot));
-
-//--- headers/second.h
-void additiveAttr(void) __attribute__((availability(ios,introduced=4.0)));
-void exclusiveAttr(void) __attribute__((cold));
-
-//--- test.c
-#include <first.h>
-#include <second.h>
-
-void test(void) {
-  // Check the attribute from "second.h" doesn't hide the attribute from 
"first.h".
-  additiveAttr();
-  // expected-error@-1 {{'additiveAttr' is unavailable: not available on 
macOS}}
-  // [email protected]:* {{'additiveAttr' has been explicitly marked 
unavailable here}}
-
-  // Check calling a function with `MutualExclusions` attributes.
-  exclusiveAttr();
-  // [email protected]:* {{'cold' and 'hot' attributes are not 
compatible}}
-  // [email protected]:* {{conflicting attribute is here}}
-}
diff --git a/clang/test/OpenMP/declare_variant_construct_codegen_1.c 
b/clang/test/OpenMP/declare_variant_construct_codegen_1.c
index 7f3421d7191da..05db6fb74d683 100644
--- a/clang/test/OpenMP/declare_variant_construct_codegen_1.c
+++ b/clang/test/OpenMP/declare_variant_construct_codegen_1.c
@@ -28,8 +28,8 @@
 void p_vxv(int *v1, int *v2, int *v3, int n);
 void t_vxv(int *v1, int *v2, int *v3, int n);
 
-#pragma omp declare variant(p_vxv) match(construct={parallel})
 #pragma omp declare variant(t_vxv) match(construct={target})
+#pragma omp declare variant(p_vxv) match(construct={parallel})
 void vxv(int *v1, int *v2, int *v3, int n) {
     for (int i = 0; i < n; i++) v3[i] = v1[i] * v2[i];
 }
diff --git 
a/lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp 
b/lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp
index 9e6b04efbf1b8..3784acd511095 100644
--- a/lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp
+++ b/lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp
@@ -791,7 +791,7 @@ ClangModulesDeclVendor::Create(Target &target) {
       instance->getPreprocessor(), instance->getSema(), skipFunctionBodies));
 
   instance->getPreprocessor().EnterMainSourceFile();
-  parser->ConsumeToken();
+  parser->Initialize();
 
   clang::Parser::DeclGroupPtrTy parsed;
   auto ImportState = clang::Sema::ModuleImportState::NotACXX20Module;

_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to