forked from qt-creator/qt-creator
Clang: Use PCHs for indexing
As generating the AST is quite expensive it would be very useful to cache the not changed include. So we generate PCHs for include outside of a project part. With this change this PCHs are used by the indexer. For that they are save to the symbol database by the PCH manager and when fetched by the symbol indexer. Change-Id: I7a5b07cfb32d72d50dc52d2b108cd41727a7bfc7 Reviewed-by: Ivan Donchevskii <ivan.donchevskii@qt.io>
This commit is contained in:
@@ -95,12 +95,12 @@ void RefactoringServer::requestSourceRangesForQueryMessage(RequestSourceRangesFo
|
||||
message.takeQuery());
|
||||
}
|
||||
|
||||
void RefactoringServer::updatePchProjectParts(UpdatePchProjectPartsMessage &&message)
|
||||
void RefactoringServer::updateProjectParts(UpdateProjectPartsMessage &&message)
|
||||
{
|
||||
m_symbolIndexing.updateProjectParts(message.takeProjectsParts(), message.takeGeneratedFiles());
|
||||
}
|
||||
|
||||
void RefactoringServer::removePchProjectParts(RemovePchProjectPartsMessage &&)
|
||||
void RefactoringServer::removeProjectParts(RemoveProjectPartsMessage &&)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
@@ -61,8 +61,8 @@ public:
|
||||
void requestSourceLocationsForRenamingMessage(RequestSourceLocationsForRenamingMessage &&message) override;
|
||||
void requestSourceRangesAndDiagnosticsForQueryMessage(RequestSourceRangesAndDiagnosticsForQueryMessage &&message) override;
|
||||
void requestSourceRangesForQueryMessage(RequestSourceRangesForQueryMessage &&message) override;
|
||||
void updatePchProjectParts(UpdatePchProjectPartsMessage &&message) override;
|
||||
void removePchProjectParts(RemovePchProjectPartsMessage &&message) override;
|
||||
void updateProjectParts(UpdateProjectPartsMessage &&message) override;
|
||||
void removeProjectParts(RemoveProjectPartsMessage &&message) override;
|
||||
void cancel() override;
|
||||
|
||||
bool isCancelingJobs() const;
|
||||
|
||||
@@ -30,15 +30,13 @@
|
||||
|
||||
namespace ClangBackEnd {
|
||||
|
||||
template<typename Database,
|
||||
typename ReadStatement,
|
||||
typename WriteStatement>
|
||||
template<typename DatabaseType>
|
||||
class StorageSqliteStatementFactory
|
||||
{
|
||||
public:
|
||||
using DatabaseType = Database;
|
||||
using ReadStatementType = ReadStatement;
|
||||
using WriteStatementType = WriteStatement;
|
||||
using Database = DatabaseType;
|
||||
using ReadStatement = typename Database::ReadStatement;
|
||||
using WriteStatement = typename Database::WriteStatement;
|
||||
|
||||
StorageSqliteStatementFactory(Database &database)
|
||||
: transaction(database),
|
||||
@@ -229,5 +227,9 @@ public:
|
||||
"WITH RECURSIVE sourceIds(sourceId) AS (VALUES(?) UNION SELECT dependencySourceId FROM sourceDependencies, sourceIds WHERE sourceDependencies.sourceId = sourceIds.sourceId) SELECT min(lastModified) FROM fileStatuses, sourceIds WHERE fileStatuses.sourceId = sourceIds.sourceId",
|
||||
database
|
||||
};
|
||||
ReadStatement getPrecompiledHeader{
|
||||
"SELECT pchPath, pchBuildTime FROM precompiledHeaders WHERE projectPartId = ?",
|
||||
database
|
||||
};
|
||||
};
|
||||
} // namespace ClangBackEnd
|
||||
|
||||
@@ -54,10 +54,14 @@ void SymbolIndexer::updateProjectPart(V2::ProjectPartContainer &&projectPart,
|
||||
{
|
||||
m_symbolsCollector.clear();
|
||||
|
||||
FilePathIds sourcePathIds = updatableFilePathIds(projectPart);
|
||||
const Utils::optional<ProjectPartArtefact> optionalArtefact = m_symbolStorage.fetchProjectPartArtefact(
|
||||
projectPart.projectPartId());
|
||||
|
||||
FilePathIds sourcePathIds = updatableFilePathIds(projectPart, optionalArtefact);
|
||||
|
||||
if (!sourcePathIds.empty()) {
|
||||
m_symbolsCollector.addFiles(projectPart.sourcePathIds(), projectPart.arguments());
|
||||
m_symbolsCollector.addFiles(projectPart.sourcePathIds(),
|
||||
compilerArguments(projectPart, optionalArtefact));
|
||||
|
||||
m_symbolsCollector.addUnsavedFiles(generatedFiles);
|
||||
|
||||
@@ -102,10 +106,11 @@ void SymbolIndexer::updateChangedPath(FilePathId filePathId)
|
||||
|
||||
const Utils::optional<ProjectPartArtefact> optionalArtefact = m_symbolStorage.fetchProjectPartArtefact(filePathId);
|
||||
|
||||
if (optionalArtefact) {
|
||||
if (optionalArtefact && !optionalArtefact.value().compilerArguments.empty()) {
|
||||
const ProjectPartArtefact &artefact = optionalArtefact.value();
|
||||
|
||||
m_symbolsCollector.addFiles({filePathId}, artefact.compilerArguments);
|
||||
m_symbolsCollector.addFiles({filePathId},
|
||||
compilerArguments(artefact.compilerArguments, artefact.projectPartId));
|
||||
|
||||
m_symbolsCollector.collectSymbols();
|
||||
|
||||
@@ -127,11 +132,10 @@ void SymbolIndexer::updateChangedPath(FilePathId filePathId)
|
||||
}
|
||||
}
|
||||
|
||||
bool SymbolIndexer::compilerMacrosOrIncludeSearchPathsAreDifferent(const V2::ProjectPartContainer &projectPart) const
|
||||
bool SymbolIndexer::compilerMacrosOrIncludeSearchPathsAreDifferent(
|
||||
const V2::ProjectPartContainer &projectPart,
|
||||
const Utils::optional<ProjectPartArtefact> &optionalArtefact) const
|
||||
{
|
||||
const Utils::optional<ProjectPartArtefact> optionalArtefact = m_symbolStorage.fetchProjectPartArtefact(
|
||||
projectPart.projectPartId());
|
||||
|
||||
if (optionalArtefact) {
|
||||
const ProjectPartArtefact &artefact = optionalArtefact.value();
|
||||
return projectPart.compilerMacros() != artefact.compilerMacros
|
||||
@@ -156,12 +160,40 @@ FilePathIds SymbolIndexer::filterChangedFiles(const V2::ProjectPartContainer &pr
|
||||
return ids;
|
||||
}
|
||||
|
||||
FilePathIds SymbolIndexer::updatableFilePathIds(const V2::ProjectPartContainer &projectPart) const
|
||||
FilePathIds SymbolIndexer::updatableFilePathIds(const V2::ProjectPartContainer &projectPart,
|
||||
const Utils::optional<ProjectPartArtefact> &optionalArtefact) const
|
||||
{
|
||||
if (compilerMacrosOrIncludeSearchPathsAreDifferent(projectPart))
|
||||
if (compilerMacrosOrIncludeSearchPathsAreDifferent(projectPart, optionalArtefact))
|
||||
return projectPart.sourcePathIds();
|
||||
|
||||
return filterChangedFiles(projectPart);
|
||||
}
|
||||
|
||||
Utils::SmallStringVector SymbolIndexer::compilerArguments(
|
||||
Utils::SmallStringVector arguments,
|
||||
int projectPartId) const
|
||||
{
|
||||
Utils::optional<ProjectPartPch> optionalProjectPartPch = m_symbolStorage.fetchPrecompiledHeader(projectPartId);
|
||||
|
||||
if (optionalProjectPartPch) {
|
||||
arguments.emplace_back("-Xclang");
|
||||
arguments.emplace_back("-include-pch");
|
||||
arguments.emplace_back("-Xclang");
|
||||
arguments.emplace_back(std::move(optionalProjectPartPch.value().pchPath));
|
||||
}
|
||||
|
||||
return arguments;
|
||||
}
|
||||
|
||||
Utils::SmallStringVector SymbolIndexer::compilerArguments(
|
||||
const V2::ProjectPartContainer &projectPart,
|
||||
const Utils::optional<ProjectPartArtefact> &optionalProjectPartArtefact) const
|
||||
{
|
||||
if (optionalProjectPartArtefact)
|
||||
return compilerArguments(projectPart.arguments(),
|
||||
optionalProjectPartArtefact.value().projectPartId);
|
||||
|
||||
return projectPart.arguments();
|
||||
}
|
||||
|
||||
} // namespace ClangBackEnd
|
||||
|
||||
@@ -55,12 +55,19 @@ public:
|
||||
void updateChangedPath(FilePathId filePath);
|
||||
|
||||
bool compilerMacrosOrIncludeSearchPathsAreDifferent(
|
||||
const V2::ProjectPartContainer &projectPart) const;
|
||||
const V2::ProjectPartContainer &projectPart,
|
||||
const Utils::optional<ProjectPartArtefact> &optionalArtefact) const;
|
||||
|
||||
FilePathIds filterChangedFiles(
|
||||
const V2::ProjectPartContainer &projectPart) const;
|
||||
|
||||
FilePathIds updatableFilePathIds(const V2::ProjectPartContainer &projectPart) const;
|
||||
FilePathIds updatableFilePathIds(const V2::ProjectPartContainer &projectPart,
|
||||
const Utils::optional<ProjectPartArtefact> &optionalArtefact) const;
|
||||
|
||||
Utils::SmallStringVector compilerArguments(const V2::ProjectPartContainer &projectPart,
|
||||
const Utils::optional<ProjectPartArtefact> &optionalArtefact) const;
|
||||
Utils::SmallStringVector compilerArguments(Utils::SmallStringVector arguments,
|
||||
int projectPartId) const;
|
||||
|
||||
private:
|
||||
SymbolsCollectorInterface &m_symbolsCollector;
|
||||
|
||||
@@ -46,9 +46,7 @@ namespace ClangBackEnd {
|
||||
class SymbolIndexing final : public SymbolIndexingInterface
|
||||
{
|
||||
public:
|
||||
using StatementFactory = ClangBackEnd::StorageSqliteStatementFactory<Sqlite::Database,
|
||||
Sqlite::ReadStatement,
|
||||
Sqlite::WriteStatement>;
|
||||
using StatementFactory = ClangBackEnd::StorageSqliteStatementFactory<Sqlite::Database>;
|
||||
using Storage = ClangBackEnd::SymbolStorage<StatementFactory>;
|
||||
|
||||
SymbolIndexing(Sqlite::Database &database,
|
||||
|
||||
@@ -40,9 +40,9 @@ namespace ClangBackEnd {
|
||||
template <typename StatementFactory>
|
||||
class SymbolStorage final : public SymbolStorageInterface
|
||||
{
|
||||
using ReadStatement = typename StatementFactory::ReadStatementType;
|
||||
using WriteStatement = typename StatementFactory::WriteStatementType;
|
||||
using Database = typename StatementFactory::DatabaseType;
|
||||
using ReadStatement = typename StatementFactory::ReadStatement;
|
||||
using WriteStatement = typename StatementFactory::WriteStatement;
|
||||
using Database = typename StatementFactory::Database;
|
||||
|
||||
public:
|
||||
SymbolStorage(StatementFactory &statementFactory,
|
||||
@@ -87,8 +87,8 @@ public:
|
||||
WriteStatement &updateStatement = m_statementFactory.updateProjectPartStatement;
|
||||
updateStatement.write(compilerArguementsAsJson,
|
||||
compilerMacrosAsJson,
|
||||
projectPartName,
|
||||
includeSearchPathsAsJason);
|
||||
includeSearchPathsAsJason,
|
||||
projectPartName);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -252,6 +252,11 @@ public:
|
||||
m_statementFactory.deleteNewLocationsTableStatement.execute();
|
||||
}
|
||||
|
||||
Utils::optional<ProjectPartPch> fetchPrecompiledHeader(int projectPartId) const
|
||||
{
|
||||
return m_statementFactory.getPrecompiledHeader.template value<ProjectPartPch, 2>(projectPartId);
|
||||
}
|
||||
|
||||
SourceLocationEntries sourceLocations() const
|
||||
{
|
||||
return SourceLocationEntries();
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
|
||||
#include "filestatus.h"
|
||||
#include "projectpartentry.h"
|
||||
#include "projectpartpch.h"
|
||||
#include "projectpartartefact.h"
|
||||
#include "sourcelocationentry.h"
|
||||
#include "sourcedependency.h"
|
||||
@@ -63,6 +64,7 @@ public:
|
||||
virtual Utils::optional<ProjectPartArtefact> fetchProjectPartArtefact(FilePathId sourceId) const = 0;
|
||||
virtual Utils::optional<ProjectPartArtefact> fetchProjectPartArtefact(Utils::SmallStringView projectPartName) const = 0;
|
||||
virtual long long fetchLowestLastModifiedTime(FilePathId sourceId) const = 0;
|
||||
virtual Utils::optional<ProjectPartPch> fetchPrecompiledHeader(int projectPartId) const = 0;
|
||||
};
|
||||
|
||||
} // namespace ClangBackEnd
|
||||
|
||||
Reference in New Issue
Block a user