55
55
#include " clang/Basic/DiagnosticOptions.h"
56
56
#include " clang/Basic/FileEntry.h"
57
57
#include " clang/Basic/IdentifierTable.h"
58
+ #include " clang/Basic/LangStandard.h"
58
59
#include " clang/Basic/Module.h"
59
60
#include " clang/Basic/TargetInfo.h"
60
61
#include " clang/Basic/Version.h"
61
62
#include " clang/CAS/CASOptions.h"
63
+ #include " clang/CAS/IncludeTree.h"
62
64
#include " clang/CodeGen/ObjectFilePCHContainerOperations.h"
63
65
#include " clang/Frontend/CompilerInvocation.h"
64
66
#include " clang/Frontend/FrontendActions.h"
67
+ #include " clang/Frontend/IncludeTreePPActions.h"
65
68
#include " clang/Frontend/TextDiagnosticPrinter.h"
66
69
#include " clang/Frontend/Utils.h"
67
70
#include " clang/Index/IndexingAction.h"
80
83
#include " llvm/ADT/STLExtras.h"
81
84
#include " llvm/ADT/SmallVector.h"
82
85
#include " llvm/ADT/StringExtras.h"
86
+ #include " llvm/CAS/CASReference.h"
87
+ #include " llvm/CAS/ObjectStore.h"
83
88
#include " llvm/Support/CrashRecoveryContext.h"
89
+ #include " llvm/Support/Error.h"
90
+ #include " llvm/Support/ErrorHandling.h"
84
91
#include " llvm/Support/FileCollector.h"
85
92
#include " llvm/Support/FileSystem.h"
86
93
#include " llvm/Support/Memory.h"
@@ -1766,16 +1773,46 @@ bool ClangImporter::importBridgingHeader(StringRef header, ModuleDecl *adapter,
1766
1773
std::move (sourceBuffer), implicitImport);
1767
1774
}
1768
1775
1769
- std::string ClangImporter::getBridgingHeaderContents (StringRef headerPath,
1770
- off_t &fileSize,
1771
- time_t &fileModTime) {
1776
+ static llvm::Expected<llvm::cas::ObjectRef>
1777
+ setupIncludeTreeInput (clang::CompilerInvocation &invocation,
1778
+ StringRef headerPath, StringRef pchIncludeTree) {
1779
+ auto DB = invocation.getCASOpts ().getOrCreateDatabases ();
1780
+ if (!DB)
1781
+ return DB.takeError ();
1782
+ auto CAS = DB->first ;
1783
+ auto ID = CAS->parseID (pchIncludeTree);
1784
+ if (!ID)
1785
+ return ID.takeError ();
1786
+ auto includeTreeRef = CAS->getReference (*ID);
1787
+ if (!includeTreeRef)
1788
+ return llvm::cas::ObjectStore::createUnknownObjectError (*ID);
1789
+
1790
+ invocation.getFrontendOpts ().Inputs .push_back (clang::FrontendInputFile (
1791
+ *includeTreeRef, headerPath, clang::Language::ObjC));
1792
+
1793
+ return *includeTreeRef;
1794
+ }
1795
+
1796
+ std::string ClangImporter::getBridgingHeaderContents (
1797
+ StringRef headerPath, off_t &fileSize, time_t &fileModTime,
1798
+ StringRef pchIncludeTree) {
1772
1799
auto invocation =
1773
1800
std::make_shared<clang::CompilerInvocation>(*Impl.Invocation );
1774
1801
1775
1802
invocation->getFrontendOpts ().DisableFree = false ;
1776
1803
invocation->getFrontendOpts ().Inputs .clear ();
1777
- invocation->getFrontendOpts ().Inputs .push_back (
1778
- clang::FrontendInputFile (headerPath, clang::Language::ObjC));
1804
+
1805
+ std::optional<llvm::cas::ObjectRef> includeTreeRef;
1806
+ if (pchIncludeTree.empty ())
1807
+ invocation->getFrontendOpts ().Inputs .push_back (
1808
+ clang::FrontendInputFile (headerPath, clang::Language::ObjC));
1809
+ else if (auto err =
1810
+ setupIncludeTreeInput (*invocation, headerPath, pchIncludeTree)
1811
+ .moveInto (includeTreeRef)) {
1812
+ Impl.diagnose ({}, diag::err_rewrite_bridging_header,
1813
+ toString (std::move (err)));
1814
+ return " " ;
1815
+ }
1779
1816
1780
1817
invocation->getPreprocessorOpts ().resetNonModularOptions ();
1781
1818
@@ -1796,18 +1833,36 @@ std::string ClangImporter::getBridgingHeaderContents(StringRef headerPath,
1796
1833
// write to an in-memory buffer.
1797
1834
class RewriteIncludesAction : public clang ::PreprocessorFrontendAction {
1798
1835
raw_ostream &OS;
1836
+ std::optional<llvm::cas::ObjectRef> includeTreeRef;
1799
1837
1800
1838
void ExecuteAction () override {
1801
1839
clang::CompilerInstance &compiler = getCompilerInstance ();
1840
+ // If the input is include tree, setup the IncludeTreePPAction.
1841
+ if (includeTreeRef) {
1842
+ auto IncludeTreeRoot = clang::cas::IncludeTreeRoot::get (
1843
+ compiler.getOrCreateObjectStore (), *includeTreeRef);
1844
+ if (!IncludeTreeRoot)
1845
+ llvm::report_fatal_error (IncludeTreeRoot.takeError ());
1846
+ auto PPCachedAct =
1847
+ clang::createPPActionsFromIncludeTree (*IncludeTreeRoot);
1848
+ if (!PPCachedAct)
1849
+ llvm::report_fatal_error (PPCachedAct.takeError ());
1850
+ compiler.getPreprocessor ().setPPCachedActions (
1851
+ std::move (*PPCachedAct));
1852
+ }
1853
+
1802
1854
clang::RewriteIncludesInInput (compiler.getPreprocessor (), &OS,
1803
1855
compiler.getPreprocessorOutputOpts ());
1804
1856
}
1857
+
1805
1858
public:
1806
- explicit RewriteIncludesAction (raw_ostream &os) : OS(os) {}
1859
+ explicit RewriteIncludesAction (
1860
+ raw_ostream &os, std::optional<llvm::cas::ObjectRef> includeTree)
1861
+ : OS(os), includeTreeRef(includeTree) {}
1807
1862
};
1808
1863
1809
1864
llvm::raw_string_ostream os (result);
1810
- RewriteIncludesAction action (os);
1865
+ RewriteIncludesAction action (os, includeTreeRef );
1811
1866
rewriteInstance.ExecuteAction (action);
1812
1867
});
1813
1868
@@ -2528,6 +2583,7 @@ ClangImporter::Implementation::Implementation(
2528
2583
!ctx.ClangImporterOpts.BridgingHeader.empty()),
2529
2584
DisableOverlayModules(ctx.ClangImporterOpts.DisableOverlayModules),
2530
2585
EnableClangSPI(ctx.ClangImporterOpts.EnableClangSPI),
2586
+ UseClangIncludeTree(ctx.ClangImporterOpts.UseClangIncludeTree),
2531
2587
importSymbolicCXXDecls(
2532
2588
ctx.LangOpts.hasFeature(Feature::ImportSymbolicCXXDecls)),
2533
2589
IsReadingBridgingPCH(false ),
0 commit comments