Skip to content

Commit

Permalink
[C++20] [Modules] Avoid crash if the inconsistency the size of lang o…
Browse files Browse the repository at this point in the history
…ptions exceeds 1

Close #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.
  • Loading branch information
ChuanqiXu9 committed Apr 27, 2023
1 parent f88f8fd commit aba32ab
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 9 deletions.
4 changes: 1 addition & 3 deletions clang/lib/Lex/Lexer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -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;
Expand Down
17 changes: 11 additions & 6 deletions clang/lib/Serialization/ASTReader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -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) \
Expand Down
43 changes: 43 additions & 0 deletions clang/test/Modules/pr62359.cppm
Original file line number Diff line number Diff line change
@@ -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{{.*}}differs 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{{.*}}differs in PCH file vs. current file
// CHECK: use of undeclared identifier 'pragma'

0 comments on commit aba32ab

Please sign in to comment.