From 40472ef14cd3bbed665789825b47d055e0a83402 Mon Sep 17 00:00:00 2001 From: Jan Svoboda Date: Fri, 2 Dec 2022 15:43:48 -0800 Subject: [clang][modules] Serialize VFS overlay paths into PCMs With implicitly built modules, the importing `CompilerInstance` assumes PCMs were built in a "compatible way" (i.e. with similarly set up instance). Either because their context hash matches, or because this instance has just built them. There are some use-cases, however, where this assumption doesn't hold, libclang/c-index-test being one of them. There, the importing instance (or `ASTUnit`) is being set up while the PCM file is being deserialized. Until now, we've assumed the serialized paths to input files are the actual on-disk files, meaning the default physical VFS was always able to resolve them. This won't be the case after D135636. Therefore, this patch makes sure `ASTUnit` is initialized with the same VFS as the PCM it's deserializing - by storing paths to the VFS overlay files into the PCM itself. For the VFS overlay files to be adopted at the very start of PCM deserialization, they are stored in a new section in the unhashed control block, together with header search paths and system header prefixes. The move to the unhashed control block should be safe: if two modules were built with different header search paths and they produced different results, the hashed part of the PCM file will reflect that. Reviewed By: akyrtzi, benlangmuir Differential Revision: https://reviews.llvm.org/D135634 --- clang/lib/Frontend/CompilerInvocation.cpp | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) (limited to 'clang/lib/Frontend/CompilerInvocation.cpp') diff --git a/clang/lib/Frontend/CompilerInvocation.cpp b/clang/lib/Frontend/CompilerInvocation.cpp index 9536319..a637b92 100644 --- a/clang/lib/Frontend/CompilerInvocation.cpp +++ b/clang/lib/Frontend/CompilerInvocation.cpp @@ -4737,12 +4737,19 @@ IntrusiveRefCntPtr clang::createVFSFromCompilerInvocation( const CompilerInvocation &CI, DiagnosticsEngine &Diags, IntrusiveRefCntPtr BaseFS) { - if (CI.getHeaderSearchOpts().VFSOverlayFiles.empty()) + return createVFSFromOverlayFiles(CI.getHeaderSearchOpts().VFSOverlayFiles, + Diags, std::move(BaseFS)); +} + +IntrusiveRefCntPtr clang::createVFSFromOverlayFiles( + ArrayRef VFSOverlayFiles, DiagnosticsEngine &Diags, + IntrusiveRefCntPtr BaseFS) { + if (VFSOverlayFiles.empty()) return BaseFS; IntrusiveRefCntPtr Result = BaseFS; // earlier vfs files are on the bottom - for (const auto &File : CI.getHeaderSearchOpts().VFSOverlayFiles) { + for (const auto &File : VFSOverlayFiles) { llvm::ErrorOr> Buffer = Result->getBufferForFile(File); if (!Buffer) { -- cgit v1.1