forked from qt-creator/qt-creator
Clang: Reparse only if files are changed
Includes are now watched by a file watcher. Unsaved file changes are watched too. If they are changed the translation units which depend on them are set to a state which require a reparse. Later the diagnostics of this units are collected and send back to creator. Change-Id: I2fb5c7dd6644687f22399edd8d18edd6215c9505 Reviewed-by: Nikolai Kosjar <nikolai.kosjar@theqtcompany.com>
This commit is contained in:
@@ -30,10 +30,14 @@
|
||||
|
||||
#include "translationunits.h"
|
||||
|
||||
#include <diagnosticschangedmessage.h>
|
||||
#include <diagnosticset.h>
|
||||
#include <projectpartsdonotexistexception.h>
|
||||
#include <projects.h>
|
||||
#include <translationunitdoesnotexistexception.h>
|
||||
|
||||
#include <QDebug>
|
||||
|
||||
namespace ClangBackEnd {
|
||||
|
||||
bool operator==(const FileContainer &fileContainer, const TranslationUnit &translationUnit)
|
||||
@@ -48,15 +52,20 @@ bool operator==(const TranslationUnit &translationUnit, const FileContainer &fil
|
||||
|
||||
|
||||
TranslationUnits::TranslationUnits(ProjectParts &projects, UnsavedFiles &unsavedFiles)
|
||||
: projects(projects),
|
||||
unsavedFiles(unsavedFiles)
|
||||
: fileSystemWatcher(*this),
|
||||
projectParts(projects),
|
||||
unsavedFiles_(unsavedFiles)
|
||||
{
|
||||
}
|
||||
|
||||
void TranslationUnits::createOrUpdate(const QVector<FileContainer> &fileContainers)
|
||||
{
|
||||
for (const FileContainer &fileContainer : fileContainers)
|
||||
for (const FileContainer &fileContainer : fileContainers) {
|
||||
createOrUpdateTranslationUnit(fileContainer);
|
||||
updateTranslationUnitsWithChangedDependencies(fileContainer.filePath());
|
||||
}
|
||||
|
||||
sendChangedDiagnostics();
|
||||
}
|
||||
|
||||
static bool removeFromFileContainer(QVector<FileContainer> &fileContainers, const TranslationUnit &translationUnit)
|
||||
@@ -100,20 +109,78 @@ const TranslationUnit &TranslationUnits::translationUnit(const Utf8String &fileP
|
||||
return *findIterator;
|
||||
}
|
||||
|
||||
const TranslationUnit &TranslationUnits::translationUnit(const FileContainer &fileContainer) const
|
||||
{
|
||||
return translationUnit(fileContainer.filePath(), fileContainer.projectPartId());
|
||||
}
|
||||
|
||||
const std::vector<TranslationUnit> &TranslationUnits::translationUnits() const
|
||||
{
|
||||
return translationUnits_;
|
||||
}
|
||||
|
||||
UnsavedFiles &TranslationUnits::unsavedFiles() const
|
||||
{
|
||||
return unsavedFiles_;
|
||||
}
|
||||
|
||||
void TranslationUnits::addWatchedFiles(QSet<Utf8String> &filePaths)
|
||||
{
|
||||
fileSystemWatcher.addFiles(filePaths);
|
||||
}
|
||||
|
||||
void TranslationUnits::updateTranslationUnitsWithChangedDependencies(const Utf8String &filePath)
|
||||
{
|
||||
for (auto &translationUnit : translationUnits_)
|
||||
translationUnit.updateIsNeedingReparseIfDependencyIsMet(filePath);
|
||||
}
|
||||
|
||||
void TranslationUnits::sendChangedDiagnostics()
|
||||
{
|
||||
for (const auto &translationUnit : translationUnits_) {
|
||||
if (translationUnit.isNeedingReparse())
|
||||
sendDiagnosticChangedMessage(translationUnit);
|
||||
}
|
||||
}
|
||||
|
||||
void TranslationUnits::setSendChangeDiagnosticsCallback(std::function<void(const DiagnosticsChangedMessage &)> &&callback)
|
||||
{
|
||||
sendDiagnosticsChangedCallback = std::move(callback);
|
||||
}
|
||||
|
||||
QVector<FileContainer> TranslationUnits::newerFileContainers(const QVector<FileContainer> &fileContainers) const
|
||||
{
|
||||
QVector<FileContainer> newerContainers;
|
||||
|
||||
auto translationUnitIsNewer = [this] (const FileContainer &fileContainer) {
|
||||
try {
|
||||
return translationUnit(fileContainer).documentRevision() != fileContainer.documentRevision();
|
||||
} catch (const TranslationUnitDoesNotExistException &) {
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
std::copy_if(fileContainers.cbegin(),
|
||||
fileContainers.cend(),
|
||||
std::back_inserter(newerContainers),
|
||||
translationUnitIsNewer);
|
||||
|
||||
return newerContainers;
|
||||
}
|
||||
|
||||
void TranslationUnits::createOrUpdateTranslationUnit(const FileContainer &fileContainer)
|
||||
{
|
||||
TranslationUnit::FileExistsCheck checkIfFileExists = fileContainer.hasUnsavedFileContent() ? TranslationUnit::DoNotCheckIfFileExists : TranslationUnit::CheckIfFileExists;
|
||||
auto findIterator = findTranslationUnit(fileContainer);
|
||||
if (findIterator == translationUnits_.end())
|
||||
if (findIterator == translationUnits_.end()) {
|
||||
translationUnits_.push_back(TranslationUnit(fileContainer.filePath(),
|
||||
unsavedFiles,
|
||||
projects.project(fileContainer.projectPartId()),
|
||||
projectParts.project(fileContainer.projectPartId()),
|
||||
*this,
|
||||
checkIfFileExists));
|
||||
translationUnits_.back().setDocumentRevision(fileContainer.documentRevision());
|
||||
} else {
|
||||
findIterator->setDocumentRevision(fileContainer.documentRevision());
|
||||
}
|
||||
}
|
||||
|
||||
std::vector<TranslationUnit>::iterator TranslationUnits::findTranslationUnit(const FileContainer &fileContainer)
|
||||
@@ -129,7 +196,7 @@ std::vector<TranslationUnit>::const_iterator TranslationUnits::findTranslationUn
|
||||
|
||||
void TranslationUnits::checkIfProjectPartExists(const Utf8String &projectFileName) const
|
||||
{
|
||||
projects.project(projectFileName);
|
||||
projectParts.project(projectFileName);
|
||||
}
|
||||
|
||||
void TranslationUnits::checkIfProjectPartsExists(const QVector<FileContainer> &fileContainers) const
|
||||
@@ -137,7 +204,7 @@ void TranslationUnits::checkIfProjectPartsExists(const QVector<FileContainer> &f
|
||||
Utf8StringVector notExistingProjectParts;
|
||||
|
||||
for (const FileContainer &fileContainer : fileContainers) {
|
||||
if (!projects.hasProjectPart(fileContainer.projectPartId()))
|
||||
if (!projectParts.hasProjectPart(fileContainer.projectPartId()))
|
||||
notExistingProjectParts.push_back(fileContainer.projectPartId());
|
||||
}
|
||||
|
||||
@@ -146,5 +213,15 @@ void TranslationUnits::checkIfProjectPartsExists(const QVector<FileContainer> &f
|
||||
|
||||
}
|
||||
|
||||
void TranslationUnits::sendDiagnosticChangedMessage(const TranslationUnit &translationUnit)
|
||||
{
|
||||
if (sendDiagnosticsChangedCallback) {
|
||||
DiagnosticsChangedMessage message(translationUnit.fileContainer(),
|
||||
translationUnit.diagnostics().toDiagnosticContainers());
|
||||
|
||||
sendDiagnosticsChangedCallback(std::move(message));
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace ClangBackEnd
|
||||
|
||||
|
||||
Reference in New Issue
Block a user