[clang] aba32ab - [C++20] [Modules] Avoid crash if the inconsistency the size of lang options exceeds 1

Chuanqi Xu via cfe-commits cfe-commits at lists.llvm.org
Wed Apr 26 23:21:34 PDT 2023


Author: Chuanqi Xu
Date: 2023-04-27T14:20:59+08:00
New Revision: aba32abe2d93133a46f67764937a1c85d455dce8

URL: https://github.com/llvm/llvm-project/commit/aba32abe2d93133a46f67764937a1c85d455dce8
DIFF: https://github.com/llvm/llvm-project/commit/aba32abe2d93133a46f67764937a1c85d455dce8.diff

LOG: [C++20] [Modules] Avoid crash if the inconsistency the size of lang options exceeds 1

Close https://github.com/llvm/llvm-project/issues/62359

The root reason for the crash is that we didn't test the case that
the bits number of a language option exceeds 1.

Added: 
    clang/test/Modules/pr62359.cppm

Modified: 
    clang/lib/Lex/Lexer.cpp
    clang/lib/Serialization/ASTReader.cpp

Removed: 
    


################################################################################
diff  --git a/clang/lib/Lex/Lexer.cpp b/clang/lib/Lex/Lexer.cpp
index bc97ca18a2ebd..53cd43d63ea02 100644
--- a/clang/lib/Lex/Lexer.cpp
+++ b/clang/lib/Lex/Lexer.cpp
@@ -4361,11 +4361,9 @@ bool Lexer::LexTokenInternal(Token &Result, bool TokAtPhysicalStartOfLine) {
   FormTokenWithChars(Result, CurPtr, tok::hash);
   PP->HandleDirective(Result);
 
-  if (PP->hadModuleLoaderFatalFailure()) {
+  if (PP->hadModuleLoaderFatalFailure())
     // With a fatal failure in the module loader, we abort parsing.
-    assert(Result.is(tok::eof) && "Preprocessor did not set tok:eof");
     return true;
-  }
 
   // We parsed the directive; lex a token with the new state.
   return false;

diff  --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp
index 723dd99ffada2..6a7bc22d3b7b3 100644
--- a/clang/lib/Serialization/ASTReader.cpp
+++ b/clang/lib/Serialization/ASTReader.cpp
@@ -277,12 +277,17 @@ static bool checkLanguageOptions(const LangOptions &LangOpts,
                                  const LangOptions &ExistingLangOpts,
                                  DiagnosticsEngine *Diags,
                                  bool AllowCompatibleDifferences = true) {
-#define LANGOPT(Name, Bits, Default, Description)                 \
-  if (ExistingLangOpts.Name != LangOpts.Name) {                   \
-    if (Diags)                                                    \
-      Diags->Report(diag::err_pch_langopt_mismatch)               \
-        << Description << LangOpts.Name << ExistingLangOpts.Name; \
-    return true;                                                  \
+#define LANGOPT(Name, Bits, Default, Description)                   \
+  if (ExistingLangOpts.Name != LangOpts.Name) {                     \
+    if (Diags) {                                                    \
+      if (Bits == 1)                                                \
+        Diags->Report(diag::err_pch_langopt_mismatch)               \
+          << Description << LangOpts.Name << ExistingLangOpts.Name; \
+      else                                                          \
+        Diags->Report(diag::err_pch_langopt_value_mismatch)         \
+          << Description;                                           \
+    }                                                               \
+    return true;                                                    \
   }
 
 #define VALUE_LANGOPT(Name, Bits, Default, Description)   \

diff  --git a/clang/test/Modules/pr62359.cppm b/clang/test/Modules/pr62359.cppm
new file mode 100644
index 0000000000000..4632457e57f18
--- /dev/null
+++ b/clang/test/Modules/pr62359.cppm
@@ -0,0 +1,43 @@
+// RUN: rm -rf %t
+// RUN: mkdir -p %t
+// RUN: split-file %s %t
+//
+// RUN: %clang_cc1 -std=c++20 -emit-module-interface %t/Hello.cppm -o %t/Hello.pcm
+// RUN: not %clang_cc1 -std=c++20 -fopenmp %t/use.cpp -fmodule-file=hello=%t/Hello.pcm -fsyntax-only \
+// RUN:     2>&1 | FileCheck %t/use.cpp
+// RUN: not %clang_cc1 -std=c++20 -fopenmp %t/use2.cpp -fmodule-file=hello=%t/Hello.pcm -fsyntax-only \
+// RUN:     2>&1 | FileCheck %t/use2.cpp
+//
+// RUN: %clang_cc1 -std=c++20 -fopenmp -emit-module-interface %t/Hello.cppm -o %t/Hello.pcm
+// RUN: %clang_cc1 -std=c++20 -fopenmp %t/use.cpp -fmodule-file=hello=%t/Hello.pcm -fsyntax-only -verify
+// RUN: %clang_cc1 -std=c++20 -fopenmp %t/use2.cpp -fmodule-file=hello=%t/Hello.pcm -fsyntax-only -verify
+
+//--- Hello.cppm
+export module hello;
+export void hello() {
+  
+}
+
+//--- use.cpp
+// expected-no-diagnostics
+import hello;
+int use() {
+  for(int i=0;i<10;i++)
+    hello();
+  return 0;
+}
+
+// CHECK: OpenMP{{.*}}
diff ers in PCH file vs. current file
+
+//--- use2.cpp
+// expected-no-diagnostics
+import hello;
+int use2() {
+#pragma omp parallel for
+  for(int i=0;i<10;i++)
+    hello();
+  return 0;
+}
+
+// CHECK: OpenMP{{.*}}
diff ers in PCH file vs. current file
+// CHECK: use of undeclared identifier 'pragma'


        


More information about the cfe-commits mailing list