diff options
author | Luboš Luňák <l.lunak@centrum.cz> | 2019-11-03 21:15:03 +0100 |
---|---|---|
committer | Luboš Luňák <l.lunak@centrum.cz> | 2020-01-15 00:01:08 +0100 |
commit | cbc9d22e49b434b6ceb2eb94b67079d02e0a7b74 (patch) | |
tree | 4ca09fdd49b20ff9b144dc1a4229cb54396de63f | |
parent | b5b2cf7af47f1ca04635dae7b787c8a81d5af4c9 (diff) | |
download | bcm5719-llvm-cbc9d22e49b434b6ceb2eb94b67079d02e0a7b74.tar.gz bcm5719-llvm-cbc9d22e49b434b6ceb2eb94b67079d02e0a7b74.zip |
make -fmodules-codegen and -fmodules-debuginfo work also with PCHs
Allow to build PCH's (with -building-pch-with-obj and the extra .o file)
with -fmodules-codegen -fmodules-debuginfo to allow emitting shared code
into the extra .o file, similarly to how it works with modules. A bit of
a misnomer, but the underlying functionality is the same. This saves up
to 20% of build time here.
Differential Revision: https://reviews.llvm.org/D69778
-rw-r--r-- | clang/lib/Serialization/ASTReader.cpp | 3 | ||||
-rw-r--r-- | clang/lib/Serialization/ASTReaderDecl.cpp | 18 | ||||
-rw-r--r-- | clang/lib/Serialization/ASTWriter.cpp | 4 | ||||
-rw-r--r-- | clang/lib/Serialization/ASTWriterDecl.cpp | 13 | ||||
-rw-r--r-- | clang/test/Modules/Inputs/codegen-flags/foo.h | 3 | ||||
-rw-r--r-- | clang/test/PCH/codegen.cpp | 30 |
6 files changed, 60 insertions, 11 deletions
diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp index a9f433b5007..6c8bc7dc33a 100644 --- a/clang/lib/Serialization/ASTReader.cpp +++ b/clang/lib/Serialization/ASTReader.cpp @@ -3224,7 +3224,8 @@ ASTReader::ReadASTBlock(ModuleFile &F, unsigned ClientLoadCapabilities) { case MODULAR_CODEGEN_DECLS: // FIXME: Skip reading this record if our ASTConsumer doesn't care about // them (ie: if we're not codegenerating this module). - if (F.Kind == MK_MainFile) + if (F.Kind == MK_MainFile || + getContext().getLangOpts().BuildingPCHWithObjectFile) for (unsigned I = 0, N = Record.size(); I != N; ++I) EagerlyDeserializedDecls.push_back(getGlobalDeclID(F, Record[I])); break; diff --git a/clang/lib/Serialization/ASTReaderDecl.cpp b/clang/lib/Serialization/ASTReaderDecl.cpp index a132164d30e..3bcc9ad5805 100644 --- a/clang/lib/Serialization/ASTReaderDecl.cpp +++ b/clang/lib/Serialization/ASTReaderDecl.cpp @@ -501,8 +501,12 @@ uint64_t ASTDeclReader::GetCurrentCursorOffset() { } void ASTDeclReader::ReadFunctionDefinition(FunctionDecl *FD) { - if (Record.readInt()) + if (Record.readInt()) { Reader.DefinitionSource[FD] = Loc.F->Kind == ModuleKind::MK_MainFile; + if (Reader.getContext().getLangOpts().BuildingPCHWithObjectFile && + Reader.DeclIsFromPCHWithObjectFile(FD)) + Reader.DefinitionSource[FD] = true; + } if (auto *CD = dyn_cast<CXXConstructorDecl>(FD)) { CD->setNumCtorInitializers(Record.readInt()); if (CD->getNumCtorInitializers()) @@ -1417,8 +1421,12 @@ ASTDeclReader::RedeclarableResult ASTDeclReader::VisitVarDeclImpl(VarDecl *VD) { Reader.getContext().setBlockVarCopyInit(VD, CopyExpr, Record.readInt()); } - if (VD->getStorageDuration() == SD_Static && Record.readInt()) + if (VD->getStorageDuration() == SD_Static && Record.readInt()) { Reader.DefinitionSource[VD] = Loc.F->Kind == ModuleKind::MK_MainFile; + if (Reader.getContext().getLangOpts().BuildingPCHWithObjectFile && + Reader.DeclIsFromPCHWithObjectFile(VD)) + Reader.DefinitionSource[VD] = true; + } enum VarKind { VarNotTemplate = 0, VarTemplate, StaticDataMemberSpecialization @@ -1677,8 +1685,12 @@ void ASTDeclReader::ReadCXXDefinitionData( Data.ODRHash = Record.readInt(); Data.HasODRHash = true; - if (Record.readInt()) + if (Record.readInt()) { Reader.DefinitionSource[D] = Loc.F->Kind == ModuleKind::MK_MainFile; + if (Reader.getContext().getLangOpts().BuildingPCHWithObjectFile && + Reader.DeclIsFromPCHWithObjectFile(D)) + Reader.DefinitionSource[D] = true; + } Data.NumBases = Record.readInt(); if (Data.NumBases) diff --git a/clang/lib/Serialization/ASTWriter.cpp b/clang/lib/Serialization/ASTWriter.cpp index aebdfa90706..6eba48a1abe 100644 --- a/clang/lib/Serialization/ASTWriter.cpp +++ b/clang/lib/Serialization/ASTWriter.cpp @@ -5583,8 +5583,8 @@ void ASTRecordWriter::AddCXXDefinitionData(const CXXRecordDecl *D) { // getODRHash will compute the ODRHash if it has not been previously computed. Record->push_back(D->getODRHash()); - bool ModulesDebugInfo = Writer->Context->getLangOpts().ModulesDebugInfo && - Writer->WritingModule && !D->isDependentType(); + bool ModulesDebugInfo = + Writer->Context->getLangOpts().ModulesDebugInfo && !D->isDependentType(); Record->push_back(ModulesDebugInfo); if (ModulesDebugInfo) Writer->ModularCodegenDecls.push_back(Writer->GetDeclRef(D)); diff --git a/clang/lib/Serialization/ASTWriterDecl.cpp b/clang/lib/Serialization/ASTWriterDecl.cpp index 74a49fa813a..6b8a9d9719d 100644 --- a/clang/lib/Serialization/ASTWriterDecl.cpp +++ b/clang/lib/Serialization/ASTWriterDecl.cpp @@ -1010,15 +1010,16 @@ void ASTDeclWriter::VisitVarDecl(VarDecl *D) { if (D->getStorageDuration() == SD_Static) { bool ModulesCodegen = false; - if (Writer.WritingModule && - !D->getDescribedVarTemplate() && !D->getMemberSpecializationInfo() && + if (!D->getDescribedVarTemplate() && !D->getMemberSpecializationInfo() && !isa<VarTemplateSpecializationDecl>(D)) { // When building a C++ Modules TS module interface unit, a strong // definition in the module interface is provided by the compilation of // that module interface unit, not by its users. (Inline variables are // still emitted in module users.) ModulesCodegen = - (Writer.WritingModule->Kind == Module::ModuleInterfaceUnit && + (((Writer.WritingModule && + Writer.WritingModule->Kind == Module::ModuleInterfaceUnit) || + Writer.Context->getLangOpts().BuildingPCHWithObjectFile) && Writer.Context->GetGVALinkageForVariable(D) == GVA_StrongExternal); } Record.push_back(ModulesCodegen); @@ -2425,9 +2426,11 @@ void ASTRecordWriter::AddFunctionDefinition(const FunctionDecl *FD) { assert(FD->doesThisDeclarationHaveABody()); bool ModulesCodegen = false; - if (Writer->WritingModule && !FD->isDependentContext()) { + if (!FD->isDependentContext()) { Optional<GVALinkage> Linkage; - if (Writer->WritingModule->Kind == Module::ModuleInterfaceUnit) { + if ((Writer->WritingModule && + Writer->WritingModule->Kind == Module::ModuleInterfaceUnit) || + Writer->Context->getLangOpts().BuildingPCHWithObjectFile) { // When building a C++ Modules TS module interface unit, a strong // definition in the module interface is provided by the compilation of // that module interface unit, not by its users. (Inline functions are diff --git a/clang/test/Modules/Inputs/codegen-flags/foo.h b/clang/test/Modules/Inputs/codegen-flags/foo.h index 7b9c1cd8e08..74cfab1771f 100644 --- a/clang/test/Modules/Inputs/codegen-flags/foo.h +++ b/clang/test/Modules/Inputs/codegen-flags/foo.h @@ -1,4 +1,7 @@ +#ifndef FOO_H +#define FOO_H struct foo { }; inline void f1() { } +#endif diff --git a/clang/test/PCH/codegen.cpp b/clang/test/PCH/codegen.cpp new file mode 100644 index 00000000000..120db0e82b9 --- /dev/null +++ b/clang/test/PCH/codegen.cpp @@ -0,0 +1,30 @@ +// This test is the PCH version of Modules/codegen-flags.test . It uses its inputs. +// The purpose of this test is just verify that the codegen options work with PCH as well. +// All the codegen functionality should be tested in Modules/. + +// RUN: rm -rf %t +// RUN: mkdir -p %t +// REQUIRES: x86-registered-target + +// RUN: %clang_cc1 -triple=x86_64-linux-gnu -fmodules-codegen -x c++-header -building-pch-with-obj -emit-pch %S/../Modules/Inputs/codegen-flags/foo.h -o %t/foo-cg.pch +// RUN: %clang_cc1 -triple=x86_64-linux-gnu -fmodules-debuginfo -x c++-header -building-pch-with-obj -emit-pch %S/../Modules/Inputs/codegen-flags/foo.h -o %t/foo-di.pch + +// RUN: %clang_cc1 -triple x86_64-linux-gnu -emit-llvm -debug-info-kind=limited -o - %s -include-pch %t/foo-cg.pch -building-pch-with-obj -fmodules-codegen | FileCheck --check-prefix=CG %s +// RUN: %clang_cc1 -triple x86_64-linux-gnu -emit-llvm -debug-info-kind=limited -o - %s -include-pch %t/foo-di.pch -building-pch-with-obj -fmodules-debuginfo | FileCheck --check-prefix=DI %s + +// RUN: %clang_cc1 -triple x86_64-linux-gnu -emit-llvm -debug-info-kind=limited -o - -include-pch %t/foo-cg.pch %S/../Modules/Inputs/codegen-flags/use.cpp | FileCheck --check-prefix=CG-USE %s +// RUN: %clang_cc1 -triple x86_64-linux-gnu -emit-llvm -debug-info-kind=limited -o - -include-pch %t/foo-di.pch %S/../Modules/Inputs/codegen-flags/use.cpp | FileCheck --check-prefix=DI-USE %s + +// CG: define weak_odr void @_Z2f1v +// CG: DICompileUnit +// CG-NOT: DICompositeType + +// CG-USE: declare void @_Z2f1v +// CG-USE: DICompileUnit +// CG-USE: distinct !DICompositeType(tag: DW_TAG_structure_type, name: "foo" + +// DI-NOT: define +// DI: distinct !DICompositeType(tag: DW_TAG_structure_type, name: "foo" + +// DI-USE: define linkonce_odr void @_Z2f1v +// DI-USE: = !DICompositeType(tag: DW_TAG_structure_type, name: "foo", {{.*}}, flags: DIFlagFwdDecl |