Skip to content

Commit 96122b5

Browse files
committed
[C++20] [Modules] Introduce ForceCheckCXX20ModulesInputFiles options for
C++20 modules Previously, we banned the check for input files from C++20 modules since we thought the BMI from C++20 modules should be a standalone artifact. However, during the recent experiment with clangd for modules, I find it is necessary to tell whether or not a BMI is out-of-date by checking the input files especially for language servers. So this patch brings a header search option ForceCheckCXX20ModulesInputFiles to allow the tools (concretly, clangd) to check the input files from BMI.
1 parent 6ffea74 commit 96122b5

File tree

5 files changed

+58
-2
lines changed

5 files changed

+58
-2
lines changed

clang/include/clang/Driver/Options.td

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2906,6 +2906,11 @@ def fvalidate_ast_input_files_content:
29062906
" Files with mismatching mtime's are considered valid"
29072907
" if both contents is identical">,
29082908
MarshallingInfoFlag<HeaderSearchOpts<"ValidateASTInputFilesContent">>;
2909+
def fforce_check_cxx20_modules_input_files:
2910+
Flag <["-"], "fforce-check-cxx20-modules-input-files">,
2911+
Group<f_Group>, Visibility<[ClangOption, CC1Option]>,
2912+
HelpText<"Check the input source files from C++20 modules explicitly">,
2913+
MarshallingInfoFlag<HeaderSearchOpts<"ForceCheckCXX20ModulesInputFiles">>;
29092914
def fmodules_validate_input_files_content:
29102915
Flag <["-"], "fmodules-validate-input-files-content">,
29112916
Group<f_Group>, Flags<[NoXarchOption]>,

clang/include/clang/Lex/HeaderSearchOptions.h

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -211,6 +211,9 @@ class HeaderSearchOptions {
211211
// validate consistency.
212212
unsigned ValidateASTInputFilesContent : 1;
213213

214+
// Whether the input files from C++20 Modules should be checked.
215+
unsigned ForceCheckCXX20ModulesInputFiles : 1;
216+
214217
/// Whether the module includes debug information (-gmodules).
215218
unsigned UseDebugInfo : 1;
216219

@@ -233,7 +236,8 @@ class HeaderSearchOptions {
233236
UseStandardCXXIncludes(true), UseLibcxx(false), Verbose(false),
234237
ModulesValidateOncePerBuildSession(false),
235238
ModulesValidateSystemHeaders(false),
236-
ValidateASTInputFilesContent(false), UseDebugInfo(false),
239+
ValidateASTInputFilesContent(false),
240+
ForceCheckCXX20ModulesInputFiles(false), UseDebugInfo(false),
237241
ModulesValidateDiagnosticOptions(true), ModulesHashContent(false),
238242
ModulesStrictContextHash(false) {}
239243

clang/lib/Frontend/ASTUnit.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -550,12 +550,16 @@ class ASTInfoCollector : public ASTReaderListener {
550550
bool ReadHeaderSearchOptions(const HeaderSearchOptions &HSOpts,
551551
StringRef SpecificModuleCachePath,
552552
bool Complain) override {
553-
// Preserve previously set header search paths.
553+
// llvm::SaveAndRestore doesn't support bit field.
554+
auto ForceCheckCXX20ModulesInputFiles =
555+
this->HSOpts.ForceCheckCXX20ModulesInputFiles;
554556
llvm::SaveAndRestore X(this->HSOpts.UserEntries);
555557
llvm::SaveAndRestore Y(this->HSOpts.SystemHeaderPrefixes);
556558
llvm::SaveAndRestore Z(this->HSOpts.VFSOverlayFiles);
557559

558560
this->HSOpts = HSOpts;
561+
this->HSOpts.ForceCheckCXX20ModulesInputFiles =
562+
ForceCheckCXX20ModulesInputFiles;
559563

560564
return false;
561565
}

clang/lib/Serialization/ASTReader.cpp

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2428,6 +2428,16 @@ InputFile ASTReader::getInputFile(ModuleFile &F, unsigned ID, bool Complain) {
24282428
// For standard C++ modules, we don't need to check the inputs.
24292429
bool SkipChecks = F.StandardCXXModule;
24302430

2431+
const HeaderSearchOptions &HSOpts =
2432+
PP.getHeaderSearchInfo().getHeaderSearchOpts();
2433+
2434+
// The option ForceCheckCXX20ModulesInputFiles is only meaningful for C++20
2435+
// modules.
2436+
if (F.StandardCXXModule && HSOpts.ForceCheckCXX20ModulesInputFiles) {
2437+
SkipChecks = false;
2438+
Overridden = false;
2439+
}
2440+
24312441
OptionalFileEntryRefDegradesToFileEntryPtr File = OptionalFileEntryRef(
24322442
expectedToOptional(FileMgr.getFileRef(Filename, /*OpenFile=*/false)));
24332443

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
// RUN: rm -rf %t
2+
// RUN: split-file %s %t
3+
//
4+
// RUN: %clang_cc1 -std=c++20 -triple %itanium_abi_triple \
5+
// RUN: %t/a.cppm -emit-module-interface -o %t/a.pcm
6+
//
7+
// RUN: echo "inline int bar = 46;" >> %t/foo.h
8+
// RUNX: %clang_cc1 -std=c++20 -triple %itanium_abi_triple \
9+
// RUNX: %t/use.cpp -fmodule-file=a=%t/a.pcm -verify -fsyntax-only
10+
// RUNX: %clang_cc1 -std=c++20 -triple %itanium_abi_triple \
11+
// RUNX: %t/a.pcm -emit-llvm -o - | FileCheck %t/a.ll
12+
//
13+
// RUN: echo "export int var = 43;" >> %t/a.cppm
14+
// RUNX: %clang_cc1 -std=c++20 -triple %itanium_abi_triple \
15+
// RUNX: %t/use.cpp -fmodule-file=a=%t/a.pcm -verify -fsyntax-only
16+
// RUNX: %clang_cc1 -std=c++20 -triple %itanium_abi_triple \
17+
// RUNX: %t/a.pcm -emit-llvm -o - | FileCheck %t/a.ll
18+
//
19+
// RUN: not %clang_cc1 -std=c++20 -triple %itanium_abi_triple \
20+
// RUN: -fforce-check-cxx20-modules-input-files %t/a.pcm \
21+
// RUN: -emit-llvm -o - 2>&1 | FileCheck %t/a.cppm -check-prefix=CHECK-FAILURE
22+
23+
//--- foo.h
24+
inline int foo = 43;
25+
26+
//--- a.cppm
27+
// expected-no-diagnostics
28+
module;
29+
#include "foo.h"
30+
export module a;
31+
export using ::foo;
32+
33+
// CHECK-FAILURE: fatal error:{{.*}}a.cppm' has been modified since the AST file {{.*}}was built

0 commit comments

Comments
 (0)