[clangd] Support simpler JSON-RPC stream parsing for lit tests.

Summary:
Instead of content-length, we delimit messages with ---.
This also removes the need for (most) dos-formatted test files.

Reviewers: ioeric

Subscribers: klimek, ilya-biryukov, jkorous-apple, cfe-commits

Differential Revision: https://reviews.llvm.org/D42919

llvm-svn: 324333
This commit is contained in:
Sam McCall 2018-02-06 10:47:30 +00:00
parent bc08aa7d97
commit 5ed599eafa
23 changed files with 1146 additions and 1257 deletions

View File

@ -332,7 +332,7 @@ ClangdLSPServer::ClangdLSPServer(JSONOutput &Out, unsigned AsyncThreadsCount,
StorePreamblesInMemory, BuildDynamicSymbolIndex, StaticIdx,
ResourceDir) {}
bool ClangdLSPServer::run(std::istream &In) {
bool ClangdLSPServer::run(std::istream &In, JSONStreamStyle InputStyle) {
assert(!IsDone && "Run was called before");
// Set up JSONRPCDispatcher.
@ -342,7 +342,7 @@ bool ClangdLSPServer::run(std::istream &In) {
registerCallbackHandlers(Dispatcher, Out, /*Callbacks=*/*this);
// Run the Language Server loop.
runLanguageServerLoop(In, Out, Dispatcher, IsDone);
runLanguageServerLoop(In, Out, InputStyle, Dispatcher, IsDone);
// Make sure IsDone is set to true after this method exits to ensure assertion
// at the start of the method fires if it's ever executed again.

View File

@ -45,7 +45,8 @@ public:
/// each instance of ClangdLSPServer.
///
/// \return Wether we received a 'shutdown' request before an 'exit' request
bool run(std::istream &In);
bool run(std::istream &In,
JSONStreamStyle InputStyle = JSONStreamStyle::Standard);
private:
// Implement DiagnosticsConsumer.

View File

@ -180,89 +180,132 @@ bool JSONRPCDispatcher::call(const json::Expr &Message, JSONOutput &Out) const {
return true;
}
void clangd::runLanguageServerLoop(std::istream &In, JSONOutput &Out,
JSONRPCDispatcher &Dispatcher,
bool &IsDone) {
static llvm::Optional<std::string> readStandardMessage(std::istream &In,
JSONOutput &Out) {
// A Language Server Protocol message starts with a set of HTTP headers,
// delimited by \r\n, and terminated by an empty line (\r\n).
unsigned long long ContentLength = 0;
while (In.good()) {
// A Language Server Protocol message starts with a set of HTTP headers,
// delimited by \r\n, and terminated by an empty line (\r\n).
unsigned long long ContentLength = 0;
while (In.good()) {
std::string Line;
std::getline(In, Line);
if (!In.good() && errno == EINTR) {
In.clear();
continue;
}
Out.mirrorInput(Line);
// Mirror '\n' that gets consumed by std::getline, but is not included in
// the resulting Line.
// Note that '\r' is part of Line, so we don't need to mirror it
// separately.
if (!In.eof())
Out.mirrorInput("\n");
llvm::StringRef LineRef(Line);
// We allow comments in headers. Technically this isn't part
// of the LSP specification, but makes writing tests easier.
if (LineRef.startswith("#"))
continue;
// Content-Type is a specified header, but does nothing.
// Content-Length is a mandatory header. It specifies the length of the
// following JSON.
// It is unspecified what sequence headers must be supplied in, so we
// allow any sequence.
// The end of headers is signified by an empty line.
if (LineRef.consume_front("Content-Length: ")) {
if (ContentLength != 0) {
log("Warning: Duplicate Content-Length header received. "
"The previous value for this message (" +
llvm::Twine(ContentLength) + ") was ignored.\n");
}
llvm::getAsUnsignedInteger(LineRef.trim(), 0, ContentLength);
continue;
} else if (!LineRef.trim().empty()) {
// It's another header, ignore it.
continue;
} else {
// An empty line indicates the end of headers.
// Go ahead and read the JSON.
break;
}
}
// Guard against large messages. This is usually a bug in the client code
// and we don't want to crash downstream because of it.
if (ContentLength > 1 << 30) { // 1024M
In.ignore(ContentLength);
log("Skipped overly large message of " + Twine(ContentLength) +
" bytes.\n");
std::string Line;
std::getline(In, Line);
if (!In.good() && errno == EINTR) {
In.clear();
continue;
}
if (ContentLength > 0) {
std::vector<char> JSON(ContentLength);
llvm::StringRef JSONRef;
{
In.read(JSON.data(), ContentLength);
Out.mirrorInput(StringRef(JSON.data(), In.gcount()));
Out.mirrorInput(Line);
// Mirror '\n' that gets consumed by std::getline, but is not included in
// the resulting Line.
// Note that '\r' is part of Line, so we don't need to mirror it
// separately.
if (!In.eof())
Out.mirrorInput("\n");
// If the stream is aborted before we read ContentLength bytes, In
// will have eofbit and failbit set.
if (!In) {
log("Input was aborted. Read only " + llvm::Twine(In.gcount()) +
" bytes of expected " + llvm::Twine(ContentLength) + ".\n");
break;
}
llvm::StringRef LineRef(Line);
JSONRef = StringRef(JSON.data(), ContentLength);
// We allow comments in headers. Technically this isn't part
// of the LSP specification, but makes writing tests easier.
if (LineRef.startswith("#"))
continue;
// Content-Type is a specified header, but does nothing.
// Content-Length is a mandatory header. It specifies the length of the
// following JSON.
// It is unspecified what sequence headers must be supplied in, so we
// allow any sequence.
// The end of headers is signified by an empty line.
if (LineRef.consume_front("Content-Length: ")) {
if (ContentLength != 0) {
log("Warning: Duplicate Content-Length header received. "
"The previous value for this message (" +
llvm::Twine(ContentLength) + ") was ignored.\n");
}
if (auto Doc = json::parse(JSONRef)) {
llvm::getAsUnsignedInteger(LineRef.trim(), 0, ContentLength);
continue;
} else if (!LineRef.trim().empty()) {
// It's another header, ignore it.
continue;
} else {
// An empty line indicates the end of headers.
// Go ahead and read the JSON.
break;
}
}
// Guard against large messages. This is usually a bug in the client code
// and we don't want to crash downstream because of it.
if (ContentLength > 1 << 30) { // 1024M
In.ignore(ContentLength);
log("Skipped overly large message of " + Twine(ContentLength) +
" bytes.\n");
return llvm::None;
}
if (ContentLength > 0) {
std::string JSON(ContentLength, '\0');
llvm::StringRef JSONRef;
In.read(&JSON[0], ContentLength);
Out.mirrorInput(StringRef(JSON.data(), In.gcount()));
// If the stream is aborted before we read ContentLength bytes, In
// will have eofbit and failbit set.
if (!In) {
log("Input was aborted. Read only " + llvm::Twine(In.gcount()) +
" bytes of expected " + llvm::Twine(ContentLength) + ".\n");
return llvm::None;
}
return std::move(JSON);
} else {
log("Warning: Missing Content-Length header, or message has zero "
"length.\n");
return llvm::None;
}
}
// For lit tests we support a simplified syntax:
// - messages are delimited by '---' on a line by itself
// - lines starting with # are ignored.
// This is a testing path, so favor simplicity over performance here.
static llvm::Optional<std::string> readDelimitedMessage(std::istream &In,
JSONOutput &Out) {
std::string JSON;
std::string Line;
while (std::getline(In, Line)) {
if (!In.eof()) // getline() consumed the newline.
Line.push_back('\n');
auto LineRef = llvm::StringRef(Line).trim();
if (LineRef.startswith("#")) // comment
continue;
bool IsDelim = LineRef.find_first_not_of('-') == llvm::StringRef::npos;
if (!IsDelim) // Line is part of a JSON message.
JSON += Line;
if (IsDelim || In.eof()) {
Out.mirrorInput(
llvm::formatv("Content-Length: {0}\r\n\r\n{1}", JSON.size(), JSON));
return std::move(JSON);
}
}
if (In.bad()) {
log("Input error while reading message!");
return llvm::None;
} else {
log("Input message terminated by EOF");
return std::move(JSON);
}
}
void clangd::runLanguageServerLoop(std::istream &In, JSONOutput &Out,
JSONStreamStyle InputStyle,
JSONRPCDispatcher &Dispatcher,
bool &IsDone) {
auto &ReadMessage =
(InputStyle == Delimited) ? readDelimitedMessage : readStandardMessage;
while (In.good()) {
if (auto JSON = ReadMessage(In, Out)) {
if (auto Doc = json::parse(*JSON)) {
// Log the formatted message.
log(llvm::formatv(Out.Pretty ? "<-- {0:2}\n" : "<-- {0}\n", *Doc));
// Finally, execute the action for this JSON message.
@ -270,17 +313,13 @@ void clangd::runLanguageServerLoop(std::istream &In, JSONOutput &Out,
log("JSON dispatch failed!\n");
} else {
// Parse error. Log the raw message.
log("<-- " + JSONRef + "\n");
log(llvm::formatv("<-- {0}\n" , *JSON));
log(llvm::Twine("JSON parse error: ") +
llvm::toString(Doc.takeError()) + "\n");
}
// If we're done, exit the loop.
if (IsDone)
break;
} else {
log("Warning: Missing Content-Length header, or message has zero "
"length.\n");
}
// If we're done, exit the loop.
if (IsDone)
break;
}
}

View File

@ -88,6 +88,14 @@ private:
Handler UnknownHandler;
};
/// Controls the way JSON-RPC messages are encoded (both input and output).
enum JSONStreamStyle {
/// Encoding per the LSP specification, with mandatory Content-Length header.
Standard,
/// Messages are delimited by a '---' line. Comment lines start with #.
Delimited
};
/// Parses input queries from LSP client (coming from \p In) and runs call
/// method of \p Dispatcher for each query.
/// After handling each query checks if \p IsDone is set true and exits the loop
@ -95,6 +103,7 @@ private:
/// Input stream(\p In) must be opened in binary mode to avoid preliminary
/// replacements of \r\n with \n.
void runLanguageServerLoop(std::istream &In, JSONOutput &Out,
JSONStreamStyle InputStyle,
JSONRPCDispatcher &Dispatcher, bool &IsDone);
} // namespace clangd

View File

@ -73,10 +73,25 @@ static llvm::cl::opt<bool> IncludeIneligibleResults(
llvm::cl::init(clangd::CodeCompleteOptions().IncludeIneligibleResults),
llvm::cl::Hidden);
static llvm::cl::opt<JSONStreamStyle> InputStyle(
"input-style", llvm::cl::desc("Input JSON stream encoding"),
llvm::cl::values(
clEnumValN(JSONStreamStyle::Standard, "standard", "usual LSP protocol"),
clEnumValN(JSONStreamStyle::Delimited, "delimited",
"messages delimited by --- lines, with # comment support")),
llvm::cl::init(JSONStreamStyle::Standard));
static llvm::cl::opt<bool>
PrettyPrint("pretty", llvm::cl::desc("Pretty-print JSON output"),
llvm::cl::init(false));
static llvm::cl::opt<bool> Test(
"lit-test",
llvm::cl::desc(
"Abbreviation for -input-style=delimited -pretty -run-synchronously. "
"Intended to simplify lit tests."),
llvm::cl::init(false), llvm::cl::Hidden);
static llvm::cl::opt<PCHStorageFlag> PCHStorage(
"pch-storage",
llvm::cl::desc("Storing PCHs in memory increases memory usages, but may "
@ -132,6 +147,11 @@ static llvm::cl::opt<Path> YamlSymbolFile(
int main(int argc, char *argv[]) {
llvm::cl::ParseCommandLineOptions(argc, argv, "clangd");
if (Test) {
RunSynchronously = true;
InputStyle = JSONStreamStyle::Delimited;
PrettyPrint = true;
}
if (!RunSynchronously && WorkerThreadsCount == 0) {
llvm::errs() << "A number of worker threads cannot be 0. Did you mean to "
@ -228,5 +248,5 @@ int main(int argc, char *argv[]) {
EnableIndexBasedCompletion, StaticIdx.get());
constexpr int NoShutdownRequestErrorCode = 1;
llvm::set_thread_name("clangd.main");
return LSPServer.run(std::cin) ? 0 : NoShutdownRequestErrorCode;
return LSPServer.run(std::cin, InputStyle) ? 0 : NoShutdownRequestErrorCode;
}

View File

@ -1,57 +1,44 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# RUN: clangd -pretty -run-synchronously -pch-storage=memory < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
Content-Length: 186
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":"struct S { int a; };\nint main() {\nS().\n}"}}}
Content-Length: 148
{"jsonrpc":"2.0","id":1,"method":"textDocument/completion","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":2,"character":4}}}
# CHECK: "id": 1
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "isIncomplete": false,
# CHECK-NEXT: "items": [
# CHECK-NEXT: {
# CHECK-NEXT: "detail": "int",
# CHECK-NEXT: "filterText": "a",
# CHECK-NEXT: "insertText": "a",
# CHECK-NEXT: "insertTextFormat": 1,
# CHECK-NEXT: "kind": 5,
# CHECK-NEXT: "label": "a",
# CHECK-NEXT: "sortText": "{{.*}}a"
# CHECK-NEXT: },
# CHECK: ]
# Update the source file and check for completions again.
Content-Length: 190
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///main.cpp","version":2},"contentChanges":[{"text":"struct S { int b; };\nint main() {\nS().\n}"}]}}
Content-Length: 148
{"jsonrpc":"2.0","id":3,"method":"textDocument/completion","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":2,"character":4}}}
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "isIncomplete": false,
# CHECK-NEXT: "items": [
# CHECK-NEXT: {
# CHECK-NEXT: "detail": "int",
# CHECK-NEXT: "filterText": "b",
# CHECK-NEXT: "insertText": "b",
# CHECK-NEXT: "insertTextFormat": 1,
# CHECK-NEXT: "kind": 5,
# CHECK-NEXT: "label": "b",
# CHECK-NEXT: "sortText": "{{.*}}b"
# CHECK-NEXT: },
# CHECK: ]
Content-Length: 44
{"jsonrpc":"2.0","id":4,"method":"shutdown"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
# RUN: clangd -lit-test -pch-storage=memory < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":"struct S { int a; };\nint main() {\nS().\n}"}}}
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/completion","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":2,"character":4}}}
# CHECK: "id": 1
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "isIncomplete": false,
# CHECK-NEXT: "items": [
# CHECK-NEXT: {
# CHECK-NEXT: "detail": "int",
# CHECK-NEXT: "filterText": "a",
# CHECK-NEXT: "insertText": "a",
# CHECK-NEXT: "insertTextFormat": 1,
# CHECK-NEXT: "kind": 5,
# CHECK-NEXT: "label": "a",
# CHECK-NEXT: "sortText": "{{.*}}a"
# CHECK-NEXT: },
# CHECK: ]
---
# Update the source file and check for completions again.
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///main.cpp","version":2},"contentChanges":[{"text":"struct S { int b; };\nint main() {\nS().\n}"}]}}
---
{"jsonrpc":"2.0","id":3,"method":"textDocument/completion","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":2,"character":4}}}
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "isIncomplete": false,
# CHECK-NEXT: "items": [
# CHECK-NEXT: {
# CHECK-NEXT: "detail": "int",
# CHECK-NEXT: "filterText": "b",
# CHECK-NEXT: "insertText": "b",
# CHECK-NEXT: "insertTextFormat": 1,
# CHECK-NEXT: "kind": 5,
# CHECK-NEXT: "label": "b",
# CHECK-NEXT: "sortText": "{{.*}}b"
# CHECK-NEXT: },
# CHECK: ]
---
{"jsonrpc":"2.0","id":4,"method":"shutdown"}

View File

@ -1,45 +1,34 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 746
{"jsonrpc":"2.0","id":2,"method":"textDocument/codeAction","params":{"textDocument":{"uri":"file:///foo.c"},"range":{"start":{"line":104,"character":13},"end":{"line":0,"character":35}},"context":{"diagnostics":[{"range":{"start": {"line": 0, "character": 32}, "end": {"line": 0, "character": 37}},"severity":2,"message":"using the result of an assignment as a condition without parentheses"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"place parentheses around the assignment to silence this warning"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"use '==' to turn this assignment into an equality comparison"}]}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onCodeAction called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 2,
Content-Length: 233
{"jsonrpc":"2.0","id":3,"method":"textDocument/rangeFormatting","params":{"textDocument":{"uri":"file:///foo.c"},"range":{"start":{"line":1,"character":4},"end":{"line":1,"character":12}},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onDocumentRangeFormatting called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 3,
Content-Length: 153
{"jsonrpc":"2.0","id":4,"method":"textDocument/formatting","params":{"textDocument":{"uri":"file:///foo.c"},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onDocumentFormatting called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 4,
Content-Length: 204
{"jsonrpc":"2.0","id":5,"method":"textDocument/onTypeFormatting","params":{"textDocument":{"uri":"file:///foo.c"},"position":{"line":3,"character":1},"ch":"}","options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onDocumentOnTypeFormatting called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 5,
Content-Length: 44
{"jsonrpc":"2.0","id":6,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0","method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","id":2,"method":"textDocument/codeAction","params":{"textDocument":{"uri":"file:///foo.c"},"range":{"start":{"line":104,"character":13},"end":{"line":0,"character":35}},"context":{"diagnostics":[{"range":{"start": {"line": 0, "character": 32}, "end": {"line": 0, "character": 37}},"severity":2,"message":"using the result of an assignment as a condition without parentheses"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"place parentheses around the assignment to silence this warning"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"use '==' to turn this assignment into an equality comparison"}]}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onCodeAction called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 2,
---
{"jsonrpc":"2.0","id":3,"method":"textDocument/rangeFormatting","params":{"textDocument":{"uri":"file:///foo.c"},"range":{"start":{"line":1,"character":4},"end":{"line":1,"character":12}},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onDocumentRangeFormatting called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 3,
---
{"jsonrpc":"2.0","id":4,"method":"textDocument/formatting","params":{"textDocument":{"uri":"file:///foo.c"},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onDocumentFormatting called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 4,
---
{"jsonrpc":"2.0","id":5,"method":"textDocument/onTypeFormatting","params":{"textDocument":{"uri":"file:///foo.c"},"position":{"line":3,"character":1},"ch":"}","options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32602
# CHECK-NEXT: "message": "onDocumentOnTypeFormatting called for non-added file"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 5,
---
{"jsonrpc":"2.0","id":6,"method":"shutdown"}
---
{"jsonrpc":"2.0","method":"exit"}

View File

@ -1,50 +1,42 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 152
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "return type of 'main' is not 'int'",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 0,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "change return type to 'int'",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 0,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
Content-Length: 44
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0","method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "return type of 'main' is not 'int'",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 0,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "change return type to 'int'",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 0,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
---
{"jsonrpc":"2.0","method":"exit"}

View File

@ -1,112 +1,92 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 180
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int main(int i, char **a) { if (i = 2) {}}"}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "using the result of an assignment as a condition without parentheses",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "place parentheses around the assignment to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "use '==' to turn this assignment into an equality comparison",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
Content-Length: 72
{"jsonrpc":"2.0","id":3,"method":"workspace/executeCommand","params":{}}
# No command name
Content-Length: 85
{"jsonrpc":"2.0","id":4,"method":"workspace/executeCommand","params":{"command": {}}}
# Invalid, non-scalar command name
Content-Length: 345
{"jsonrpc":"2.0","id":5,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","custom":"foo", "arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}]}}
Content-Length: 117
{"jsonrpc":"2.0","id":6,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":"foo"}}
# Arguments not a sequence.
Content-Length: 93
{"jsonrpc":"2.0","id":7,"method":"workspace/executeCommand","params":{"command":"mycommand"}}
# Unknown command.
Content-Length: 132
{"jsonrpc":"2.0","id":8,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","custom":"foo", "arguments":[""]}}
# ApplyFix argument not a mapping node.
Content-Length: 345
{"jsonrpc":"2.0","id":9,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"custom":"foo", "changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}]}}
# Custom field in WorkspaceEdit
Content-Length: 132
{"jsonrpc":"2.0","id":10,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":"foo"}]}}
# changes in WorkspaceEdit with no mapping node
Content-Length: 346
{"jsonrpc":"2.0","id":11,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}], "custom":"foo"}}]}}
# Custom field in WorkspaceEditChange
Content-Length: 150
{"jsonrpc":"2.0","id":12,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":"bar"}}]}}
# No sequence node for TextEdits
Content-Length: 149
{"jsonrpc":"2.0","id":13,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[""]}}]}}
# No mapping node for TextEdit
Content-Length: 265
{"jsonrpc":"2.0","id":14,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":"","newText":")"}]}}]}}
# TextEdit not decoded
Content-Length: 345
{"jsonrpc":"2.0","id":9,"method":"workspace/executeCommand","params":{"arguments":[{"custom":"foo", "changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}],"command":"clangd.applyFix"}}
# Command name after arguments
Content-Length: 44
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int main(int i, char **a) { if (i = 2) {}}"}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "using the result of an assignment as a condition without parentheses",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "place parentheses around the assignment to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "use '==' to turn this assignment into an equality comparison",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
---
# No command name
{"jsonrpc":"2.0","id":3,"method":"workspace/executeCommand","params":{}}
---
# Invalid, non-scalar command name
{"jsonrpc":"2.0","id":4,"method":"workspace/executeCommand","params":{"command": {}}}
---
{"jsonrpc":"2.0","id":5,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","custom":"foo", "arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}]}}
---
# Arguments not a sequence.
{"jsonrpc":"2.0","id":6,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":"foo"}}
---
# Unknown command.
{"jsonrpc":"2.0","id":7,"method":"workspace/executeCommand","params":{"command":"mycommand"}}
---
# ApplyFix argument not a mapping node.
{"jsonrpc":"2.0","id":8,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","custom":"foo", "arguments":[""]}}
---
# Custom field in WorkspaceEdit
{"jsonrpc":"2.0","id":9,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"custom":"foo", "changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}]}}
---
# changes in WorkspaceEdit with no mapping node
{"jsonrpc":"2.0","id":10,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":"foo"}]}}
---
# Custom field in WorkspaceEditChange
{"jsonrpc":"2.0","id":11,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}], "custom":"foo"}}]}}
---
# No sequence node for TextEdits
{"jsonrpc":"2.0","id":12,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":"bar"}}]}}
---
# No mapping node for TextEdit
{"jsonrpc":"2.0","id":13,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[""]}}]}}
---
# TextEdit not decoded
{"jsonrpc":"2.0","id":14,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":"","newText":")"}]}}]}}
---
# Command name after arguments
{"jsonrpc":"2.0","id":9,"method":"workspace/executeCommand","params":{"arguments":[{"custom":"foo", "changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}],"command":"clangd.applyFix"}}
---
{"jsonrpc":"2.0","id":3,"method":"shutdown"}

View File

@ -1,89 +1,80 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 205
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int main() { int i; return i; }"},"metadata":{"extraFlags":["-Wall"]}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "variable 'i' is uninitialized when used here",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 28,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 27,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "initialize the variable 'i' to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 19,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 18,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
Content-Length: 175
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":2},"contentChanges":[{"text":"int main() { int i; return i; }"}]}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "variable 'i' is uninitialized when used here",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 28,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 27,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "initialize the variable 'i' to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 19,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 18,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
Content-Length: 44
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int main() { int i; return i; }"},"metadata":{"extraFlags":["-Wall"]}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "variable 'i' is uninitialized when used here",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 28,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 27,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "initialize the variable 'i' to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 19,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 18,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":2},"contentChanges":[{"text":"int main() { int i; return i; }"}]}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "variable 'i' is uninitialized when used here",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 28,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 27,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "initialize the variable 'i' to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 19,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 18,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
---
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,249 +1,238 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 180
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int main(int i, char **a) { if (i = 2) {}}"}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "using the result of an assignment as a condition without parentheses",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "place parentheses around the assignment to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "use '==' to turn this assignment into an equality comparison",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
Content-Length: 746
{"jsonrpc":"2.0","id":2,"method":"textDocument/codeAction","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":104,"character":13},"end":{"line":0,"character":35}},"context":{"diagnostics":[{"range":{"start": {"line": 0, "character": 32}, "end": {"line": 0, "character": 37}},"severity":2,"message":"using the result of an assignment as a condition without parentheses"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"place parentheses around the assignment to silence this warning"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"use '==' to turn this assignment into an equality comparison"}]}}}
# CHECK: "id": 2,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "(",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": ")",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt place parentheses around the assignment to silence this warning"
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "==",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt use '==' to turn this assignment into an equality comparison"
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 771
{"jsonrpc":"2.0","id":3,"method":"textDocument/codeAction","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":104,"character":13},"end":{"line":0,"character":35}},"context":{"diagnostics":[{"range":{"start": {"line": 0, "character": 32}, "end": {"line": 0, "character": 37}},"severity":2,"code":"1","source":"foo","message":"using the result of an assignment as a condition without parentheses"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"place parentheses around the assignment to silence this warning"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"use '==' to turn this assignment into an equality comparison"}]}}}
# Make sure unused "code" and "source" fields ignored gracefully
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "(",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": ")",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt place parentheses around the assignment to silence this warning"
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "==",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt use '==' to turn this assignment into an equality comparison"
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 329
{"jsonrpc":"2.0","id":4,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}]}}
# CHECK: "id": 4,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": "Fix applied."
#
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "method": "workspace/applyEdit",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "edit": {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "(",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": ")",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
Content-Length: 44
{"jsonrpc":"2.0","id":4,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0","method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int main(int i, char **a) { if (i = 2) {}}"}}}
# CHECK: "method": "textDocument/publishDiagnostics",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "diagnostics": [
# CHECK-NEXT: {
# CHECK-NEXT: "message": "using the result of an assignment as a condition without parentheses",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 2
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "place parentheses around the assignment to silence this warning",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "message": "use '==' to turn this assignment into an equality comparison",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "severity": 3
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "uri": "file://{{.*}}/foo.c"
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":2,"method":"textDocument/codeAction","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":104,"character":13},"end":{"line":0,"character":35}},"context":{"diagnostics":[{"range":{"start": {"line": 0, "character": 32}, "end": {"line": 0, "character": 37}},"severity":2,"message":"using the result of an assignment as a condition without parentheses"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"place parentheses around the assignment to silence this warning"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"use '==' to turn this assignment into an equality comparison"}]}}}
# CHECK: "id": 2,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "(",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": ")",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt place parentheses around the assignment to silence this warning"
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "==",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt use '==' to turn this assignment into an equality comparison"
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","id":3,"method":"textDocument/codeAction","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":104,"character":13},"end":{"line":0,"character":35}},"context":{"diagnostics":[{"range":{"start": {"line": 0, "character": 32}, "end": {"line": 0, "character": 37}},"severity":2,"code":"1","source":"foo","message":"using the result of an assignment as a condition without parentheses"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"place parentheses around the assignment to silence this warning"},{"range":{"start": {"line": 0, "character": 34}, "end": {"line": 0, "character": 35}},"severity":3,"message":"use '==' to turn this assignment into an equality comparison"}]}}}
# Make sure unused "code" and "source" fields ignored gracefully
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "(",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": ")",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt place parentheses around the assignment to silence this warning"
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "arguments": [
# CHECK-NEXT: {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "==",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 35,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 34,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ],
# CHECK-NEXT: "command": "clangd.applyFix",
# CHECK-NEXT: "title": "Apply FixIt use '==' to turn this assignment into an equality comparison"
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","id":4,"method":"workspace/executeCommand","params":{"command":"clangd.applyFix","arguments":[{"changes":{"test:///foo.c":[{"range":{"start":{"line":0,"character":32},"end":{"line":0,"character":32}},"newText":"("},{"range":{"start":{"line":0,"character":37},"end":{"line":0,"character":37}},"newText":")"}]}}]}}
# CHECK: "id": 4,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": "Fix applied."
#
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "method": "workspace/applyEdit",
# CHECK-NEXT: "params": {
# CHECK-NEXT: "edit": {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "{{.*}}/foo.c": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "(",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 32,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": ")",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 37,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":4,"method":"shutdown"}
---
{"jsonrpc":"2.0","method":"exit"}

View File

@ -1,207 +1,187 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
Content-Length: 193
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int foo ( int x ) {\n x = x+1;\n return x;\n }"}}}
Content-Length: 233
{"jsonrpc":"2.0","id":1,"method":"textDocument/rangeFormatting","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":1,"character":4},"end":{"line":1,"character":12}},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "\n ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 19,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": " ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": " ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "\n ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 2
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 12,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 197
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":5},"contentChanges":[{"text":"int foo ( int x ) {\n x = x + 1;\n return x;\n }"}]}}
#
#
Content-Length: 233
{"jsonrpc":"2.0","id":2,"method":"textDocument/rangeFormatting","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":1,"character":2},"end":{"line":1,"character":12}},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 2,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": []
Content-Length: 153
{"jsonrpc":"2.0","id":3,"method":"textDocument/formatting","params":{"textDocument":{"uri":"test:///foo.c"},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 8,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 7,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 16,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 15,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "\n",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 3
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 11,
# CHECK-NEXT: "line": 2
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 190
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":9},"contentChanges":[{"text":"int foo(int x) {\n x = x + 1;\n return x;\n}"}]}}
#
#
Content-Length: 153
{"jsonrpc":"2.0","id":4,"method":"textDocument/formatting","params":{"textDocument":{"uri":"test:///foo.c"},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 4,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": []
Content-Length: 193
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":5},"contentChanges":[{"text":"int foo ( int x ) {\n x = x + 1;\n return x;\n}"}]}}
#
#
Content-Length: 204
{"jsonrpc":"2.0","id":5,"method":"textDocument/onTypeFormatting","params":{"textDocument":{"uri":"test:///foo.c"},"position":{"line":3,"character":1},"ch":"}","options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 5,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 8,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 7,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 16,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 15,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 44
{"jsonrpc":"2.0","id":6,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"int foo ( int x ) {\n x = x+1;\n return x;\n }"}}}
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/rangeFormatting","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":1,"character":4},"end":{"line":1,"character":12}},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "\n ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 19,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": " ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": " ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "\n ",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 2
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 12,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":5},"contentChanges":[{"text":"int foo ( int x ) {\n x = x + 1;\n return x;\n }"}]}}
#
#
---
{"jsonrpc":"2.0","id":2,"method":"textDocument/rangeFormatting","params":{"textDocument":{"uri":"test:///foo.c"},"range":{"start":{"line":1,"character":2},"end":{"line":1,"character":12}},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 2,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": []
---
{"jsonrpc":"2.0","id":3,"method":"textDocument/formatting","params":{"textDocument":{"uri":"test:///foo.c"},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 8,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 7,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 16,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 15,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "\n",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 3
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 11,
# CHECK-NEXT: "line": 2
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":9},"contentChanges":[{"text":"int foo(int x) {\n x = x + 1;\n return x;\n}"}]}}
---
{"jsonrpc":"2.0","id":4,"method":"textDocument/formatting","params":{"textDocument":{"uri":"test:///foo.c"},"options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 4,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": []
---
{"jsonrpc":"2.0","method":"textDocument/didChange","params":{"textDocument":{"uri":"test:///foo.c","version":5},"contentChanges":[{"text":"int foo ( int x ) {\n x = x + 1;\n return x;\n}"}]}}
---
{"jsonrpc":"2.0","id":5,"method":"textDocument/onTypeFormatting","params":{"textDocument":{"uri":"test:///foo.c"},"position":{"line":3,"character":1},"ch":"}","options":{"tabSize":4,"insertSpaces":true}}}
# CHECK: "id": 5,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 8,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 7,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 10,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 16,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 15,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","id":6,"method":"shutdown"}
---
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,49 +1,43 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
# Test with invalid initialize request parameters
Content-Length: 142
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":"","rootUri":"file:///path/to/workspace","capabilities":{},"trace":"off"}}
# CHECK: "id": 0,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "capabilities": {
# CHECK-NEXT: "codeActionProvider": true,
# CHECK-NEXT: "completionProvider": {
# CHECK-NEXT: "resolveProvider": false,
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: ".",
# CHECK-NEXT: ">",
# CHECK-NEXT: ":"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "definitionProvider": true,
# CHECK-NEXT: "documentFormattingProvider": true,
# CHECK-NEXT: "documentHighlightProvider": true,
# CHECK-NEXT: "documentOnTypeFormattingProvider": {
# CHECK-NEXT: "firstTriggerCharacter": "}",
# CHECK-NEXT: "moreTriggerCharacter": []
# CHECK-NEXT: },
# CHECK-NEXT: "documentRangeFormattingProvider": true,
# CHECK-NEXT: "executeCommandProvider": {
# CHECK-NEXT: "commands": [
# CHECK-NEXT: "clangd.applyFix"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "renameProvider": true,
# CHECK-NEXT: "signatureHelpProvider": {
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: "(",
# CHECK-NEXT: ","
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "textDocumentSync": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
Content-Length: 44
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0","method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
# Test with invalid initialize request parameters
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":"","rootUri":"file:///path/to/workspace","capabilities":{},"trace":"off"}}
# CHECK: "id": 0,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "capabilities": {
# CHECK-NEXT: "codeActionProvider": true,
# CHECK-NEXT: "completionProvider": {
# CHECK-NEXT: "resolveProvider": false,
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: ".",
# CHECK-NEXT: ">",
# CHECK-NEXT: ":"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "definitionProvider": true,
# CHECK-NEXT: "documentFormattingProvider": true,
# CHECK-NEXT: "documentHighlightProvider": true,
# CHECK-NEXT: "documentOnTypeFormattingProvider": {
# CHECK-NEXT: "firstTriggerCharacter": "}",
# CHECK-NEXT: "moreTriggerCharacter": []
# CHECK-NEXT: },
# CHECK-NEXT: "documentRangeFormattingProvider": true,
# CHECK-NEXT: "executeCommandProvider": {
# CHECK-NEXT: "commands": [
# CHECK-NEXT: "clangd.applyFix"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "renameProvider": true,
# CHECK-NEXT: "signatureHelpProvider": {
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: "(",
# CHECK-NEXT: ","
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "textDocumentSync": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
---
{"jsonrpc":"2.0","method":"exit"}

View File

@ -1,52 +1,46 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
# Test initialize request parameters with rootUri
Content-Length: 143
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootUri":"file:///path/to/workspace","capabilities":{},"trace":"off"}}
# CHECK: "id": 0,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "capabilities": {
# CHECK-NEXT: "codeActionProvider": true,
# CHECK-NEXT: "completionProvider": {
# CHECK-NEXT: "resolveProvider": false,
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: ".",
# CHECK-NEXT: ">",
# CHECK-NEXT: ":"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "definitionProvider": true,
# CHECK-NEXT: "documentFormattingProvider": true,
# CHECK-NEXT: "documentHighlightProvider": true,
# CHECK-NEXT: "documentOnTypeFormattingProvider": {
# CHECK-NEXT: "firstTriggerCharacter": "}",
# CHECK-NEXT: "moreTriggerCharacter": []
# CHECK-NEXT: },
# CHECK-NEXT: "documentRangeFormattingProvider": true,
# CHECK-NEXT: "executeCommandProvider": {
# CHECK-NEXT: "commands": [
# CHECK-NEXT: "clangd.applyFix"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "renameProvider": true,
# CHECK-NEXT: "signatureHelpProvider": {
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: "(",
# CHECK-NEXT: ","
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "textDocumentSync": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
Content-Length: 44
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": null
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
# Test initialize request parameters with rootUri
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootUri":"file:///path/to/workspace","capabilities":{},"trace":"off"}}
# CHECK: "id": 0,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "capabilities": {
# CHECK-NEXT: "codeActionProvider": true,
# CHECK-NEXT: "completionProvider": {
# CHECK-NEXT: "resolveProvider": false,
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: ".",
# CHECK-NEXT: ">",
# CHECK-NEXT: ":"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "definitionProvider": true,
# CHECK-NEXT: "documentFormattingProvider": true,
# CHECK-NEXT: "documentHighlightProvider": true,
# CHECK-NEXT: "documentOnTypeFormattingProvider": {
# CHECK-NEXT: "firstTriggerCharacter": "}",
# CHECK-NEXT: "moreTriggerCharacter": []
# CHECK-NEXT: },
# CHECK-NEXT: "documentRangeFormattingProvider": true,
# CHECK-NEXT: "executeCommandProvider": {
# CHECK-NEXT: "commands": [
# CHECK-NEXT: "clangd.applyFix"
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "renameProvider": true,
# CHECK-NEXT: "signatureHelpProvider": {
# CHECK-NEXT: "triggerCharacters": [
# CHECK-NEXT: "(",
# CHECK-NEXT: ","
# CHECK-NEXT: ]
# CHECK-NEXT: },
# CHECK-NEXT: "textDocumentSync": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
# CHECK: "id": 3,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": null
---
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,50 +1,39 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
Content-Length: 150
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.cpp","languageId":"cpp","version":1,"text":"int foo;"}}}
Content-Length: 159
{"jsonrpc":"2.0","id":1,"method":"textDocument/rename","params":{"textDocument":{"uri":"test:///foo.cpp"},"position":{"line":0,"character":5},"newName":"bar"}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.cpp": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "bar",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 7
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 4
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
Content-Length: 159
{"jsonrpc":"2.0","id":2,"method":"textDocument/rename","params":{"textDocument":{"uri":"test:///foo.cpp"},"position":{"line":0,"character":2},"newName":"bar"}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32603,
# CHECK-NEXT: "message": "clang diagnostic"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 2,
# CHECK-NEXT: "jsonrpc": "2.0"
Content-Length: 44
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.cpp","languageId":"cpp","version":1,"text":"int foo;"}}}
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/rename","params":{"textDocument":{"uri":"test:///foo.cpp"},"position":{"line":0,"character":5},"newName":"bar"}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "changes": {
# CHECK-NEXT: "file://{{.*}}/foo.cpp": [
# CHECK-NEXT: {
# CHECK-NEXT: "newText": "bar",
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 7
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 4
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":2,"method":"textDocument/rename","params":{"textDocument":{"uri":"test:///foo.cpp"},"position":{"line":0,"character":2},"newName":"bar"}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32603,
# CHECK-NEXT: "message": "clang diagnostic"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 2,
# CHECK-NEXT: "jsonrpc": "2.0"
---
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
---
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,9 +1,4 @@
# RUN: clangd -run-synchronously < %s
# vim: fileformat=dos
# It is absolutely vital that this file has CRLF line endings.
Content-Length: 44
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: clangd -lit-test < %s
{"jsonrpc":"2.0","id":3,"method":"shutdown"}
---
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,6 +1,2 @@
# RUN: not clangd -run-synchronously < %s
# vim: fileformat=dos
# It is absolutely vital that this file has CRLF line endings.
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: not clangd -lit-test < %s
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,37 +1,25 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
# Start a session.
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
Content-Length: 172
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":"void x(int);\nint main(){\nx("}}}
Content-Length: 151
{"jsonrpc":"2.0","id":1,"method":"textDocument/signatureHelp","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":2,"character":2}}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "activeParameter": 0,
# CHECK-NEXT: "activeSignature": 0,
# CHECK-NEXT: "signatures": [
# CHECK-NEXT: {
# CHECK-NEXT: "label": "x(int) -> void",
# CHECK-NEXT: "parameters": [
# CHECK-NEXT: {
# CHECK-NEXT: "label": "int"
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# Shutdown.
Content-Length: 49
{"jsonrpc":"2.0","id":100000,"method":"shutdown"}
Content-Length: 33
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
# Start a session.
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":"void x(int);\nint main(){\nx("}}}
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/signatureHelp","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":2,"character":2}}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": {
# CHECK-NEXT: "activeParameter": 0,
# CHECK-NEXT: "activeSignature": 0,
# CHECK-NEXT: "signatures": [
# CHECK-NEXT: {
# CHECK-NEXT: "label": "x(int) -> void",
# CHECK-NEXT: "parameters": [
# CHECK-NEXT: {
# CHECK-NEXT: "label": "int"
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
# CHECK-NEXT: ]
# CHECK-NEXT: }
---
{"jsonrpc":"2.0","id":100000,"method":"shutdown"}

View File

@ -1,19 +1,11 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# UNSUPPORTED: mingw32,win32
# It is absolutely vital that this file has CRLF line endings.
#
# Test authority-less URI
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 152
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: "uri": "file:///clangd-test/foo.c"
Content-Length: 44
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0","method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
# UNSUPPORTED: mingw32,win32
# Test authority-less URI
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: "uri": "file:///clangd-test/foo.c"
---
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
---
{"jsonrpc":"2.0","method":"exit"}

View File

@ -1,19 +1,11 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# REQUIRES: mingw32 || win32
# It is absolutely vital that this file has CRLF line endings.
#
# Test authority-less URI
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 152
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: "uri": "file:///C:/clangd-test/foo.c"
Content-Length: 44
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0","method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
# REQUIRES: mingw32 || win32
# Test authority-less URI
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: "uri": "file:///C:/clangd-test/foo.c"
---
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
---
{"jsonrpc":"2.0","method":"exit"}

View File

@ -1,26 +1,19 @@
# RUN: clangd -pretty -run-synchronously -trace %t < %s && FileCheck %s < %t
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
#
Content-Length: 152
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: {"displayTimeUnit":"ns","traceEvents":[
# Start opening the doc.
# CHECK: "name": "textDocument/didOpen"
# CHECK: "ph": "B"
# Start building the preamble.
# CHECK: "name": "Preamble"
# CHECK: },
# Finish building the preamble, with filename.
# CHECK: "File": "{{.*}}/foo.c"
# CHECK-NEXT: },
# CHECK-NEXT: "ph": "E"
# Start building the file.
# CHECK: "name": "Build"
Content-Length: 44
{"jsonrpc":"2.0","id":5,"method":"shutdown"}
# RUN: clangd -lit-test -trace %t < %s && FileCheck %s < %t
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///foo.c","languageId":"c","version":1,"text":"void main() {}"}}}
# CHECK: {"displayTimeUnit":"ns","traceEvents":[
# Start opening the doc.
# CHECK: "name": "textDocument/didOpen"
# CHECK: "ph": "B"
# Start building the preamble.
# CHECK: "name": "Preamble"
# CHECK: },
# Finish building the preamble, with filename.
# CHECK: "File": "{{.*}}/foo.c"
# CHECK-NEXT: },
# CHECK-NEXT: "ph": "E"
# Start building the file.
# CHECK: "name": "Build"
---
{"jsonrpc":"2.0","id":5,"method":"shutdown"}

View File

@ -1,27 +1,16 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
Content-Length: 143
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":""}}}
Content-Length: 92
{"jsonrpc":"2.0","id":1,"method":"textDocument/jumpInTheAirLikeYouJustDontCare","params":{}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32601,
# CHECK-NEXT: "message": "method not found"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0"
Content-Length: 44
{"jsonrpc":"2.0","id":2,"method":"shutdown"}
Content-Length: 33
{"jsonrpc":"2.0":"method":"exit"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":""}}}
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/jumpInTheAirLikeYouJustDontCare","params":{}}
# CHECK: "error": {
# CHECK-NEXT: "code": -32601,
# CHECK-NEXT: "message": "method not found"
# CHECK-NEXT: },
# CHECK-NEXT: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0"
---
{"jsonrpc":"2.0","id":2,"method":"shutdown"}
---
{"jsonrpc":"2.0":"method":"exit"}

View File

@ -1,67 +1,57 @@
# RUN: clangd -pretty -run-synchronously < %s | FileCheck -strict-whitespace %s
# It is absolutely vital that this file has CRLF line endings.
#
Content-Length: 125
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
Content-Length: 165
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":"int x = 0;\nint y = x;"}}}
Content-Length: 148
{"jsonrpc":"2.0","id":1,"method":"textDocument/definition","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":1,"character":8}}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 0,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "uri": "file://{{.*}}/{{([A-Z]:/)?}}main.cpp"
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 155
{"jsonrpc":"2.0","id":1,"method":"textDocument/documentHighlight","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":1,"character":8}}}
# CHECK: "id": 1
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "kind": 1,
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 5,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "kind": 2,
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 8,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
Content-Length: 48
{"jsonrpc":"2.0","id":10000,"method":"shutdown"}
# RUN: clangd -lit-test < %s | FileCheck -strict-whitespace %s
{"jsonrpc":"2.0","id":0,"method":"initialize","params":{"processId":123,"rootPath":"clangd","capabilities":{},"trace":"off"}}
---
{"jsonrpc":"2.0","method":"textDocument/didOpen","params":{"textDocument":{"uri":"test:///main.cpp","languageId":"cpp","version":1,"text":"int x = 0;\nint y = x;"}}}
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/definition","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":1,"character":8}}}
# CHECK: "id": 1,
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 0,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: "uri": "file://{{.*}}/{{([A-Z]:/)?}}main.cpp"
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","id":1,"method":"textDocument/documentHighlight","params":{"textDocument":{"uri":"test:///main.cpp"},"position":{"line":1,"character":8}}}
# CHECK: "id": 1
# CHECK-NEXT: "jsonrpc": "2.0",
# CHECK-NEXT: "result": [
# CHECK-NEXT: {
# CHECK-NEXT: "kind": 1,
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 5,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 4,
# CHECK-NEXT: "line": 0
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: },
# CHECK-NEXT: {
# CHECK-NEXT: "kind": 2,
# CHECK-NEXT: "range": {
# CHECK-NEXT: "end": {
# CHECK-NEXT: "character": 9,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: },
# CHECK-NEXT: "start": {
# CHECK-NEXT: "character": 8,
# CHECK-NEXT: "line": 1
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: }
# CHECK-NEXT: ]
---
{"jsonrpc":"2.0","id":10000,"method":"shutdown"}