mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
[SourceKit] Add a dedicated request to retrieve the diagnostics of a file
Currently, SourceKit always implicitly sends diagnostics to the client after every edit. This doesn’t match our new cancellation story because diagnostics retrieval is no request and thus can’t be cancelled. Instead, diagnostics retrieval should be a standalone request, which returns a cancellation token like every other request and which can thus also be cancelled as such. The indented transition path here is to change all open and edit requests to be syntactic only. When diagnostics are needed, the new diagnostics request should be used. rdar://83391522
This commit is contained in:
@@ -10,12 +10,13 @@
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "SwiftASTManager.h"
|
||||
#include "SwiftLangSupport.h"
|
||||
#include "SourceKit/Support/FileSystemProvider.h"
|
||||
#include "SourceKit/Support/ImmutableTextBuffer.h"
|
||||
#include "SourceKit/Support/Logging.h"
|
||||
#include "SourceKit/Support/UIdent.h"
|
||||
#include "SwiftASTManager.h"
|
||||
#include "SwiftEditorDiagConsumer.h"
|
||||
#include "SwiftLangSupport.h"
|
||||
|
||||
#include "swift/AST/ASTDemangler.h"
|
||||
#include "swift/AST/ASTPrinter.h"
|
||||
@@ -1588,6 +1589,36 @@ static void resolveCursor(
|
||||
CancellationToken, fileSystem);
|
||||
}
|
||||
|
||||
static void computeDiagnostics(
|
||||
SwiftLangSupport &Lang, StringRef InputFile, SwiftInvocationRef Invok,
|
||||
llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FileSystem,
|
||||
SourceKitCancellationToken CancellationToken,
|
||||
std::function<void(const RequestResult<DiagnosticsResult> &)> Receiver) {
|
||||
|
||||
class DiagnosticsConsumer : public SwiftASTConsumer {
|
||||
std::function<void(const RequestResult<DiagnosticsResult> &)> Receiver;
|
||||
|
||||
public:
|
||||
DiagnosticsConsumer(
|
||||
std::function<void(const RequestResult<DiagnosticsResult> &)> Receiver)
|
||||
: Receiver(Receiver) {}
|
||||
|
||||
void handlePrimaryAST(ASTUnitRef AstUnit) override {
|
||||
unsigned BufferID =
|
||||
AstUnit->getPrimarySourceFile().getBufferID().getValue();
|
||||
auto &DiagConsumer = AstUnit->getEditorDiagConsumer();
|
||||
auto Diagnostics = DiagConsumer.getDiagnosticsForBuffer(BufferID);
|
||||
Receiver(RequestResult<DiagnosticsResult>::fromResult(Diagnostics));
|
||||
}
|
||||
};
|
||||
|
||||
auto Consumer = std::make_shared<DiagnosticsConsumer>(std::move(Receiver));
|
||||
|
||||
Lang.getASTManager()->processASTAsync(Invok, std::move(Consumer),
|
||||
/*OncePerASTToken=*/nullptr,
|
||||
CancellationToken, FileSystem);
|
||||
}
|
||||
|
||||
static void resolveName(
|
||||
SwiftLangSupport &Lang, StringRef InputFile, unsigned Offset,
|
||||
SwiftInvocationRef Invok, bool TryExistingAST, NameTranslatingInfo &Input,
|
||||
@@ -1846,6 +1877,33 @@ void SwiftLangSupport::getCursorInfo(
|
||||
fileSystem, CancellationToken, Receiver);
|
||||
}
|
||||
|
||||
void SwiftLangSupport::getDiagnostics(
|
||||
StringRef InputFile, ArrayRef<const char *> Args,
|
||||
Optional<VFSOptions> VfsOptions,
|
||||
SourceKitCancellationToken CancellationToken,
|
||||
std::function<void(const RequestResult<DiagnosticsResult> &)> Receiver) {
|
||||
std::string FileSystemError;
|
||||
auto FileSystem = getFileSystem(VfsOptions, InputFile, FileSystemError);
|
||||
if (!FileSystem) {
|
||||
Receiver(RequestResult<DiagnosticsResult>::fromError(FileSystemError));
|
||||
return;
|
||||
}
|
||||
|
||||
std::string InvocationError;
|
||||
SwiftInvocationRef Invok =
|
||||
ASTMgr->getInvocation(Args, InputFile, FileSystem, InvocationError);
|
||||
if (!InvocationError.empty()) {
|
||||
LOG_WARN_FUNC("error creating ASTInvocation: " << InvocationError);
|
||||
}
|
||||
if (!Invok) {
|
||||
Receiver(RequestResult<DiagnosticsResult>::fromError(InvocationError));
|
||||
return;
|
||||
}
|
||||
|
||||
computeDiagnostics(*this, InputFile, Invok, FileSystem, CancellationToken,
|
||||
Receiver);
|
||||
}
|
||||
|
||||
void SwiftLangSupport::getRangeInfo(
|
||||
StringRef InputFile, unsigned Offset, unsigned Length,
|
||||
bool CancelOnSubsequentRequest, ArrayRef<const char *> Args,
|
||||
|
||||
Reference in New Issue
Block a user