[clang] [C++20][Modules] Allow using stdarg.h with header units (PR #100739)

Dmitry Polukhin via cfe-commits cfe-commits at lists.llvm.org
Fri Jul 26 07:40:40 PDT 2024


https://github.com/dmpolukhin updated https://github.com/llvm/llvm-project/pull/100739

>From edc7f5c84caefeae197a5884c91ec2194fd3148b Mon Sep 17 00:00:00 2001
From: Dmitry Polukhin <dmitry.polukhin at gmail.com>
Date: Fri, 26 Jul 2024 05:02:52 -0700
Subject: [PATCH 1/4] [C++20][Modules] Allow using stdarg.h with header units

Summary:
Macro like `va_start`/`va_end` marked as builtin functions that makes
these identifiers special and it results in false redifinition for the
identifiers and hides macro definitions.

Test Plan: check-clang
---
 clang/lib/Serialization/ASTReader.cpp     |  9 ++++----
 clang/test/Headers/stdarg-cxx-modules.cpp | 27 +++++++++++++++++++++++
 2 files changed, 31 insertions(+), 5 deletions(-)
 create mode 100644 clang/test/Headers/stdarg-cxx-modules.cpp

diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp
index 3cb96df12e4da..f3e8027526f6a 100644
--- a/clang/lib/Serialization/ASTReader.cpp
+++ b/clang/lib/Serialization/ASTReader.cpp
@@ -1051,10 +1051,9 @@ IdentifierID ASTIdentifierLookupTrait::ReadIdentifierID(const unsigned char *d)
   return Reader.getGlobalIdentifierID(F, RawID >> 1);
 }
 
-static void markIdentifierFromAST(ASTReader &Reader, IdentifierInfo &II) {
+static void markIdentifierFromAST(ASTReader &Reader, IdentifierInfo &II, bool IsModule) {
   if (!II.isFromAST()) {
     II.setIsFromAST();
-    bool IsModule = Reader.getPreprocessor().getCurrentModule() != nullptr;
     if (isInterestingIdentifier(Reader, II, IsModule))
       II.setChangedSinceDeserialization();
   }
@@ -1080,7 +1079,7 @@ IdentifierInfo *ASTIdentifierLookupTrait::ReadData(const internal_key_type& k,
     II = &Reader.getIdentifierTable().getOwn(k);
     KnownII = II;
   }
-  markIdentifierFromAST(Reader, *II);
+  markIdentifierFromAST(Reader, *II, Reader.getPreprocessor().getCurrentModule() != nullptr);
   Reader.markIdentifierUpToDate(II);
 
   IdentifierID ID = Reader.getGlobalIdentifierID(F, RawID);
@@ -4543,7 +4542,7 @@ ASTReader::ASTReadResult ASTReader::ReadAST(StringRef FileName, ModuleKind Type,
 
       // Mark this identifier as being from an AST file so that we can track
       // whether we need to serialize it.
-      markIdentifierFromAST(*this, *II);
+      markIdentifierFromAST(*this, *II, true);
 
       // Associate the ID with the identifier so that the writer can reuse it.
       auto ID = Trait.ReadIdentifierID(Data + KeyDataLen.first);
@@ -8961,7 +8960,7 @@ IdentifierInfo *ASTReader::DecodeIdentifierInfo(IdentifierID ID) {
     auto Key = Trait.ReadKey(Data, KeyDataLen.first);
     auto &II = PP.getIdentifierTable().get(Key);
     IdentifiersLoaded[Index] = &II;
-    markIdentifierFromAST(*this,  II);
+    markIdentifierFromAST(*this,  II, getPreprocessor().getCurrentModule() != nullptr);
     if (DeserializationListener)
       DeserializationListener->IdentifierRead(ID, &II);
   }
diff --git a/clang/test/Headers/stdarg-cxx-modules.cpp b/clang/test/Headers/stdarg-cxx-modules.cpp
new file mode 100644
index 0000000000000..b7c4486c89374
--- /dev/null
+++ b/clang/test/Headers/stdarg-cxx-modules.cpp
@@ -0,0 +1,27 @@
+// RUN: rm -fR %t
+// RUN: split-file %s %t
+// RUN: cd %t
+// RUN: %clang_cc1 -std=c++20 -emit-header-unit -xc++-user-header h1.h
+// RUN: %clang_cc1 -std=c++20 -emit-header-unit -xc++-user-header h2.h -fmodule-file=h1.pcm
+// RUN: %clang_cc1 -std=c++20 -fsyntax-only main.cpp -fmodule-file=h1.pcm -fmodule-file=h2.pcm
+
+//--- h1.h
+#pragma once
+#include <stdarg.h>
+// expected-no-diagnostics
+
+//--- h2.h
+#pragma once
+import "h1.h";
+// expected-no-diagnostics
+
+//--- main.cpp
+import "h1.h";
+import "h2.h";
+
+void foo(int x, ...) {
+  va_list v;
+  va_start(v, x);
+  va_end(v);
+}
+// expected-no-diagnostics

>From 21f11739412975f5ef7a801e16ceb052e7adaeda Mon Sep 17 00:00:00 2001
From: Dmitry Polukhin <dmitry.polukhin at gmail.com>
Date: Fri, 26 Jul 2024 05:02:52 -0700
Subject: [PATCH 2/4] Fix formatting, simplify test

---
 clang/lib/Serialization/ASTReader.cpp     | 6 ++++--
 clang/test/Headers/stdarg-cxx-modules.cpp | 2 --
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp
index f3e8027526f6a..714be9edc3f62 100644
--- a/clang/lib/Serialization/ASTReader.cpp
+++ b/clang/lib/Serialization/ASTReader.cpp
@@ -1079,7 +1079,8 @@ IdentifierInfo *ASTIdentifierLookupTrait::ReadData(const internal_key_type& k,
     II = &Reader.getIdentifierTable().getOwn(k);
     KnownII = II;
   }
-  markIdentifierFromAST(Reader, *II, Reader.getPreprocessor().getCurrentModule() != nullptr);
+  bool IsModule = Reader.getPreprocessor().getCurrentModule() != nullptr;
+  markIdentifierFromAST(Reader, *II, IsModule);
   Reader.markIdentifierUpToDate(II);
 
   IdentifierID ID = Reader.getGlobalIdentifierID(F, RawID);
@@ -8960,7 +8961,8 @@ IdentifierInfo *ASTReader::DecodeIdentifierInfo(IdentifierID ID) {
     auto Key = Trait.ReadKey(Data, KeyDataLen.first);
     auto &II = PP.getIdentifierTable().get(Key);
     IdentifiersLoaded[Index] = &II;
-    markIdentifierFromAST(*this,  II, getPreprocessor().getCurrentModule() != nullptr);
+    bool IsModule = getPreprocessor().getCurrentModule() != nullptr;
+    markIdentifierFromAST(*this,  II, IsModule);
     if (DeserializationListener)
       DeserializationListener->IdentifierRead(ID, &II);
   }
diff --git a/clang/test/Headers/stdarg-cxx-modules.cpp b/clang/test/Headers/stdarg-cxx-modules.cpp
index b7c4486c89374..113ece4fb64b3 100644
--- a/clang/test/Headers/stdarg-cxx-modules.cpp
+++ b/clang/test/Headers/stdarg-cxx-modules.cpp
@@ -6,12 +6,10 @@
 // RUN: %clang_cc1 -std=c++20 -fsyntax-only main.cpp -fmodule-file=h1.pcm -fmodule-file=h2.pcm
 
 //--- h1.h
-#pragma once
 #include <stdarg.h>
 // expected-no-diagnostics
 
 //--- h2.h
-#pragma once
 import "h1.h";
 // expected-no-diagnostics
 

>From 75f862a78d863e61a0120c40a69c996b450d4267 Mon Sep 17 00:00:00 2001
From: Dmitry Polukhin <dmitry.polukhin at gmail.com>
Date: Fri, 26 Jul 2024 07:31:38 -0700
Subject: [PATCH 3/4] And one more formatting issue

---
 clang/lib/Serialization/ASTReader.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp
index 714be9edc3f62..74265fec3a1c2 100644
--- a/clang/lib/Serialization/ASTReader.cpp
+++ b/clang/lib/Serialization/ASTReader.cpp
@@ -8962,7 +8962,7 @@ IdentifierInfo *ASTReader::DecodeIdentifierInfo(IdentifierID ID) {
     auto &II = PP.getIdentifierTable().get(Key);
     IdentifiersLoaded[Index] = &II;
     bool IsModule = getPreprocessor().getCurrentModule() != nullptr;
-    markIdentifierFromAST(*this,  II, IsModule);
+    markIdentifierFromAST(*this, II, IsModule);
     if (DeserializationListener)
       DeserializationListener->IdentifierRead(ID, &II);
   }

>From 74578b6b2771a4d51007d5cc3d9946633281c09a Mon Sep 17 00:00:00 2001
From: Dmitry Polukhin <dmitry.polukhin at gmail.com>
Date: Fri, 26 Jul 2024 07:39:37 -0700
Subject: [PATCH 4/4] one more formatting issue

---
 clang/lib/Serialization/ASTReader.cpp | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp
index 74265fec3a1c2..25e6e0d4c78bb 100644
--- a/clang/lib/Serialization/ASTReader.cpp
+++ b/clang/lib/Serialization/ASTReader.cpp
@@ -1051,7 +1051,8 @@ IdentifierID ASTIdentifierLookupTrait::ReadIdentifierID(const unsigned char *d)
   return Reader.getGlobalIdentifierID(F, RawID >> 1);
 }
 
-static void markIdentifierFromAST(ASTReader &Reader, IdentifierInfo &II, bool IsModule) {
+static void markIdentifierFromAST(ASTReader &Reader, IdentifierInfo &II,
+                                  bool IsModule) {
   if (!II.isFromAST()) {
     II.setIsFromAST();
     if (isInterestingIdentifier(Reader, II, IsModule))



More information about the cfe-commits mailing list