16#include <llvm/ADT/StringExtras.h>
17#include <llvm/ADT/StringRef.h>
18#include <llvm/ADT/StringSwitch.h>
19#include <llvm/Support/ErrorHandling.h>
20#include <llvm/Support/JSON.h>
21#include <llvm/Support/Path.h>
22#include <llvm/Support/raw_ostream.h>
29bool mapOptOrNull(
const llvm::json::Value &Params, llvm::StringLiteral Prop,
30 T &Out, llvm::json::Path P) {
31 auto *O = Params.getAsObject();
33 auto *V = O->get(Prop);
35 if (!V || V->getAsNull())
37 return fromJSON(*V, Out, P.field(Prop));
44 llvm::StringRef TUPath) {
45 assert(llvm::sys::path::is_absolute(AbsPath) &&
"the path is relative");
48 elog(
"URIForFile: failed to resolve path {0} with TU path {1}: "
49 "{2}.\nUsing unresolved path.",
50 AbsPath, TUPath, Resolved.takeError());
57 llvm::StringRef HintPath) {
60 return Resolved.takeError();
65 if (
auto S = E.getAsString()) {
68 consumeError(Parsed.takeError());
69 P.report(
"failed to parse URI");
72 if (Parsed->scheme() !=
"file" && Parsed->scheme() !=
"test") {
73 P.report(
"clangd only supports 'file' URI scheme for workspace files");
79 P.report(
"unresolvable URI");
80 consumeError(U.takeError());
96 return llvm::json::Object{{
"uri", R.
uri}};
100 llvm::json::Path P) {
101 llvm::json::ObjectMapper O(Params, P);
102 return O && O.map(
"uri", R.
uri);
107 Result.getAsObject()->try_emplace(
"version", R.
version);
113 llvm::json::ObjectMapper O(Params, P);
119 llvm::json::Path P) {
120 llvm::json::ObjectMapper O(Params, P);
121 return O && O.map(
"line", R.
line) && O.map(
"character", R.
character);
125 return llvm::json::Object{
135bool fromJSON(
const llvm::json::Value &Params,
Range &R, llvm::json::Path P) {
136 llvm::json::ObjectMapper O(Params, P);
137 return O && O.map(
"start", R.
start) && O.map(
"end", R.
end);
141 return llvm::json::Object{
148 return OS << R.
start <<
'-' << R.
end;
152 return llvm::json::Object{
159 llvm::json::Path P) {
160 llvm::json::ObjectMapper O(Params, P);
161 return O && O.map(
"uri", R.
uri) && O.map(
"range", R.
range);
165 return OS << L.
range <<
'@' << L.
uri;
169 llvm::json::Object Result{
185 llvm::json::Path P) {
186 llvm::json::ObjectMapper O(Params, P);
187 return O && O.map(
"uri", R.
uri) && O.map(
"languageId", R.
languageId) &&
188 O.map(
"version", R.
version) && O.map(
"text", R.
text);
192 llvm::json::Path P) {
193 llvm::json::ObjectMapper O(Params, P);
194 return O && O.map(
"range", R.
range) && O.map(
"newText", R.
newText) &&
199 llvm::json::Object Result{
209 llvm::json::Path P) {
210 llvm::json::ObjectMapper O(Params, P);
211 return O && O.map(
"label", R.
label) &&
216 llvm::json::Object Result{{
"label", CA.
label}};
225 llvm::json::Path P) {
226 llvm::json::ObjectMapper O(Params, P);
230 llvm::json::Object Result{{
"textDocument", P.
textDocument},
236 OS << TE.
range <<
" => \"";
237 llvm::printEscapedString(TE.
newText, OS);
242 if (
auto S = E.getAsString()) {
247 if (*S ==
"messages") {
251 if (*S ==
"verbose") {
260 if (
auto T = E.getAsInteger()) {
271 llvm::json::Path P) {
272 if (
auto *A = E.getAsArray()) {
273 for (
size_t I = 0; I < A->size(); ++I) {
275 if (
fromJSON((*A)[I], KindOut, P.index(I)))
276 Out.set(
size_t(KindOut));
285 auto KindVal =
static_cast<size_t>(Kind);
286 if (KindVal >=
SymbolKindMin && KindVal <= SupportedSymbolKinds.size() &&
287 SupportedSymbolKinds[KindVal])
302 llvm::json::Path P) {
303 const llvm::json::Object *O = Params.getAsObject();
305 P.report(
"expected object");
308 if (
auto *TextDocument = O->getObject(
"textDocument")) {
309 if (
auto *SemanticHighlighting =
310 TextDocument->getObject(
"semanticHighlightingCapabilities")) {
311 if (
auto SemanticHighlightingSupport =
312 SemanticHighlighting->getBoolean(
"semanticHighlighting"))
315 if (
auto *InactiveRegions =
316 TextDocument->getObject(
"inactiveRegionsCapabilities")) {
317 if (
auto InactiveRegionsSupport =
318 InactiveRegions->getBoolean(
"inactiveRegions")) {
322 if (TextDocument->getObject(
"semanticTokens"))
324 if (
auto *Diagnostics = TextDocument->getObject(
"publishDiagnostics")) {
325 if (
auto CategorySupport = Diagnostics->getBoolean(
"categorySupport"))
327 if (
auto CodeActions = Diagnostics->getBoolean(
"codeActionsInline"))
329 if (
auto RelatedInfo = Diagnostics->getBoolean(
"relatedInformation"))
332 if (
auto *References = TextDocument->getObject(
"references"))
333 if (
auto ContainerSupport = References->getBoolean(
"container"))
335 if (
auto *Completion = TextDocument->getObject(
"completion")) {
336 if (
auto *Item = Completion->getObject(
"completionItem")) {
337 if (
auto SnippetSupport = Item->getBoolean(
"snippetSupport"))
339 if (
const auto *DocumentationFormat =
340 Item->getArray(
"documentationFormat")) {
341 for (
const auto &Format : *DocumentationFormat) {
347 if (
auto *ItemKind = Completion->getObject(
"completionItemKind")) {
348 if (
auto *ValueSet = ItemKind->get(
"valueSet")) {
351 P.field(
"textDocument")
353 .field(
"completionItemKind")
358 if (
auto EditsNearCursor = Completion->getBoolean(
"editsNearCursor"))
361 if (
auto *
CodeAction = TextDocument->getObject(
"codeAction")) {
362 if (
CodeAction->getObject(
"codeActionLiteralSupport"))
365 if (
auto *
DocumentSymbol = TextDocument->getObject(
"documentSymbol")) {
366 if (
auto HierarchicalSupport =
370 if (
auto *
Hover = TextDocument->getObject(
"hover")) {
371 if (
auto *ContentFormat =
Hover->getArray(
"contentFormat")) {
372 for (
const auto &Format : *ContentFormat) {
378 if (
auto *Help = TextDocument->getObject(
"signatureHelp")) {
380 if (
auto *
Info = Help->getObject(
"signatureInformation")) {
381 if (
auto *
Parameter =
Info->getObject(
"parameterInformation")) {
382 if (
auto OffsetSupport =
Parameter->getBoolean(
"labelOffsetSupport"))
385 if (
const auto *DocumentationFormat =
386 Info->getArray(
"documentationFormat")) {
387 for (
const auto &Format : *DocumentationFormat) {
394 if (
auto *Folding = TextDocument->getObject(
"foldingRange")) {
395 if (
auto LineFolding = Folding->getBoolean(
"lineFoldingOnly"))
398 if (
auto *Rename = TextDocument->getObject(
"rename")) {
399 if (
auto RenameSupport = Rename->getBoolean(
"prepareSupport"))
403 if (
auto *Workspace = O->getObject(
"workspace")) {
404 if (
auto *Symbol = Workspace->getObject(
"symbol")) {
405 if (
auto *
SymbolKind = Symbol->getObject(
"symbolKind")) {
406 if (
auto *ValueSet =
SymbolKind->get(
"valueSet")) {
418 if (
auto WorkspaceConfiguration = Workspace->getBoolean(
"configuration")) {
422 if (
auto *
SemanticTokens = Workspace->getObject(
"semanticTokens")) {
423 if (
auto RefreshSupport =
SemanticTokens->getBoolean(
"refreshSupport"))
426 if (
auto *
WorkspaceEdit = Workspace->getObject(
"workspaceEdit")) {
427 if (
auto DocumentChanges =
WorkspaceEdit->getBoolean(
"documentChanges"))
434 if (
auto *Window = O->getObject(
"window")) {
435 if (
auto WorkDoneProgress = Window->getBoolean(
"workDoneProgress"))
437 if (
auto Implicit = Window->getBoolean(
"implicitWorkDoneProgressCreate"))
440 if (
auto *General = O->getObject(
"general")) {
441 if (
auto *StaleRequestSupport = General->getObject(
"staleRequestSupport")) {
442 if (
auto Cancel = StaleRequestSupport->getBoolean(
"cancel"))
449 P.field(
"offsetEncoding")))
456 llvm::json::Path P) {
457 llvm::json::ObjectMapper O(Params, P);
466 if (
auto *RawCaps = Params.getAsObject()->getObject(
"capabilities"))
468 O.map(
"trace", R.
trace);
474 return llvm::json::Object{{
"token", P.
token}};
478 llvm::json::Object Result{
483 Result[
"cancellable"] =
true;
485 Result[
"percentage"] = 0;
492 llvm::json::Object Result{{
"kind",
"report"}};
496 Result[
"message"] = *P.
message;
504 llvm::json::Object Result{{
"kind",
"end"}};
506 Result[
"message"] = *P.
message;
512 return static_cast<int64_t
>(R);
516 return llvm::json::Object{{
"type", R.
type}, {
"message", R.
message}};
520 llvm::json::Path P) {
521 llvm::json::ObjectMapper O(Params, P);
526 llvm::json::Path P) {
527 llvm::json::ObjectMapper O(Params, P);
532 llvm::json::Path P) {
533 llvm::json::ObjectMapper O(Params, P);
538 llvm::json::Path P) {
539 llvm::json::ObjectMapper O(Params, P);
543 mapOptOrNull(Params,
"forceRebuild", R.
forceRebuild, P);
547 llvm::json::Path P) {
548 if (
auto T = E.getAsInteger()) {
559 llvm::json::Path P) {
560 llvm::json::ObjectMapper O(Params, P);
561 return O && O.map(
"uri", R.
uri) && O.map(
"type", R.
type);
565 llvm::json::Path P) {
566 llvm::json::ObjectMapper O(Params, P);
567 return O && O.map(
"changes", R.
changes);
572 llvm::json::ObjectMapper O(Params, P);
573 return O && O.map(
"range", R.
range) && O.map(
"rangeLength", R.
rangeLength) &&
574 O.map(
"text", R.
text);
578 llvm::json::Path P) {
579 llvm::json::ObjectMapper O(Params, P);
585 llvm::json::ObjectMapper O(Params, P);
587 O.map(
"position", R.
position) && O.map(
"ch", R.
ch);
591 llvm::json::Path P) {
592 llvm::json::ObjectMapper O(Params, P);
597 llvm::json::Path P) {
598 llvm::json::ObjectMapper O(Params, P);
603 return llvm::json::Object{
612 return llvm::json::Object{{
"href", D.
href}};
616 llvm::json::Object Diag{
626 Diag[
"code"] = D.
code;
630 Diag[
"source"] = D.
source;
634 Diag[
"data"] = llvm::json::Object(D.
data);
636 Diag[
"tags"] = llvm::json::Array{D.
tags};
642 llvm::json::Path P) {
643 llvm::json::ObjectMapper O(Params, P);
646 if (
auto *Data = Params.getAsObject()->getObject(
"data"))
648 return O.map(
"range", R.
range) && O.map(
"message", R.
message) &&
649 mapOptOrNull(Params,
"severity", R.
severity, P) &&
650 mapOptOrNull(Params,
"category", R.
category, P) &&
651 mapOptOrNull(Params,
"code", R.
code, P) &&
652 mapOptOrNull(Params,
"source", R.
source, P);
656 llvm::json::Object Result{
661 Result[
"version"] = PDP.
version;
666 llvm::json::Path P) {
667 llvm::json::ObjectMapper O(Params, P);
670 O.map(
"only", R.
only);
675 OS << D.
range <<
" [";
697 llvm::json::Path P) {
698 llvm::json::ObjectMapper O(Params, P);
704 llvm::json::Path P) {
705 llvm::json::ObjectMapper O(Params, P);
706 return O && O.map(
"changes", R.
changes) &&
712 llvm::json::Path P) {
713 llvm::json::ObjectMapper O(Params, P);
714 if (!O || !O.map(
"command", R.
command))
717 const auto *Args = Params.getAsObject()->get(
"arguments");
720 const auto *ArgsArray = Args->getAsArray();
722 P.field(
"arguments").report(
"expected array");
725 if (ArgsArray->size() > 1) {
726 P.field(
"arguments").report(
"Command should have 0 or 1 argument");
729 if (ArgsArray->size() == 1) {
736 llvm::json::Object O{
738 {
"kind",
static_cast<int>(P.
kind)},
743 O[
"score"] = *P.
score;
754 llvm::json::Path P) {
755 llvm::json::ObjectMapper O(Params, P);
756 return O && O.map(
"query", R.
query) &&
757 mapOptOrNull(Params,
"limit", R.
limit, P);
761 auto Cmd = llvm::json::Object{{
"title", C.
title}, {
"command", C.
command}};
763 Cmd[
"arguments"] = llvm::json::Array{C.
argument};
791 llvm::json::Object Result{{
"name", S.
name},
792 {
"kind",
static_cast<int>(S.
kind)},
797 Result[
"detail"] = S.
detail;
801 Result[
"deprecated"] =
true;
807 llvm::json::Object Result;
809 llvm::json::Object FileChanges;
810 for (
auto &Change : *WE.
changes)
811 FileChanges[Change.first] = llvm::json::Array(Change.second);
812 Result[
"changes"] = std::move(FileChanges);
817 llvm::json::Object ChangeAnnotations;
819 ChangeAnnotations[Annotation.first] = Annotation.second;
820 Result[
"changeAnnotations"] = std::move(ChangeAnnotations);
826 llvm::json::Path P) {
827 llvm::json::ObjectMapper O(Params, P);
828 return O && O.map(
"file", A.
file) && O.map(
"selection", A.
selection) &&
833 return llvm::json::Object{
838 return llvm::json::Object{{
"edit", Params.
edit}};
842 llvm::json::Path P) {
843 llvm::json::ObjectMapper O(Response, P);
844 return O && O.map(
"applied", R.
applied) &&
849 llvm::json::Path P) {
850 llvm::json::ObjectMapper O(Params, P);
856 llvm::json::Path P) {
857 llvm::json::ObjectMapper O(Params, P);
859 if (!O || !O.map(
"triggerKind", TriggerKind) ||
867 llvm::json::Path P) {
869 !mapOptOrNull(Params,
"limit", R.
limit, P))
871 if (
auto *Context = Params.getAsObject()->get(
"context"))
876static llvm::StringRef toTextKind(
MarkupKind Kind) {
883 llvm_unreachable(
"Invalid MarkupKind");
886static MarkupKind fromTextKind(llvm::StringRef Kind) {
887 if (Kind ==
"plaintext")
889 if (Kind ==
"markdown")
891 llvm_unreachable(
"Invalid MarkupKind");
895 auto Str = V.getAsString();
897 P.report(
"expected string");
900 if (*Str ==
"plaintext")
902 else if (*Str ==
"markdown")
905 P.report(
"unknown markup kind");
912 return OS << toTextKind(K);
916 if (MC.
value.empty())
919 return llvm::json::Object{
920 {
"kind", toTextKind(MC.
kind)},
926 llvm::json::Path P) {
927 llvm::json::ObjectMapper O(Params, P);
931 return O.mapOptional(
"value", R.
value);
944 llvm::json::Path P) {
945 if (
auto T = E.getAsInteger()) {
958 auto KindVal =
static_cast<size_t>(Kind);
960 KindVal <= SupportedCompletionItemKinds.size() &&
961 SupportedCompletionItemKinds[KindVal])
978 llvm::json::Path P) {
979 if (
auto *A = E.getAsArray()) {
980 for (
size_t I = 0; I < A->size(); ++I) {
982 if (
fromJSON((*A)[I], KindOut, P.index(I)))
983 Out.set(
size_t(KindOut));
991 assert(!CI.
label.empty() &&
"completion item label is required");
992 llvm::json::Object Result{{
"label", CI.
label}};
994 Result[
"kind"] =
static_cast<int>(CI.
kind);
996 Result[
"detail"] = CI.
detail;
1013 Result[
"score"] = CI.
score;
1014 Result[
"data"] = CI.
data;
1019 llvm::json::Path P) {
1020 llvm::json::ObjectMapper O(Params, P);
1022 if (!O.mapOptional(
"kind", Kind))
1026 if (!O.mapOptional(
"insertTextFormat", Kind))
1030 && O.map(
"label", R.
label)
1031 && O.mapOptional(
"detail", R.
detail)
1033 && O.mapOptional(
"sortText", R.
sortText)
1036 && O.mapOptional(
"textEdit", R.
textEdit)
1038 && O.mapOptional(
"data", R.
data)
1053 return llvm::json::Object{
1055 {
"items", llvm::json::Array(L.
items)},
1061 "parameter information label is required");
1062 llvm::json::Object Result;
1074 assert(!SI.
label.empty() &&
"signature information label is required");
1075 llvm::json::Object Result{
1076 {
"label", SI.
label},
1077 {
"parameters", llvm::json::Array(SI.
parameters)},
1092 "Unexpected negative value for number of active signatures.");
1094 "Unexpected negative value for active parameter index");
1095 return llvm::json::Object{
1098 {
"signatures", llvm::json::Array(SH.
signatures)},
1103 llvm::json::Path P) {
1104 llvm::json::ObjectMapper O(Params, P);
1110 return llvm::json::Object{
1112 {
"kind",
static_cast<int>(DH.
kind)},
1117 return llvm::json::Object{
1118 {
"uri", FStatus.
uri},
1119 {
"state", FStatus.
state},
1124static llvm::json::Value encodeTokens(llvm::ArrayRef<SemanticToken> Toks) {
1125 llvm::json::Array Result;
1127 for (
const auto &Tok : Toks) {
1128 Result.push_back(Tok.deltaLine);
1129 Result.push_back(Tok.deltaStart);
1130 Result.push_back(Tok.length);
1131 Result.push_back(Tok.tokenType);
1132 Result.push_back(Tok.tokenModifiers);
1146 return llvm::json::Object{{
"resultId", Tokens.
resultId},
1147 {
"data", encodeTokens(Tokens.
tokens)}};
1151 return llvm::json::Object{
1154 {
"data", encodeTokens(Edit.
tokens)}};
1158 llvm::json::Object Result{{
"resultId", TE.
resultId}};
1160 Result[
"edits"] = *TE.
edits;
1162 Result[
"data"] = encodeTokens(*TE.
tokens);
1167 llvm::json::Path P) {
1168 llvm::json::ObjectMapper O(Params, P);
1173 llvm::json::Path P) {
1174 llvm::json::ObjectMapper O(Params, P);
1180 return llvm::json::Object{
1197 llvm::json::ObjectMapper O(Params, P);
1198 return O && O.map(
"settings", CCP.
settings);
1202 llvm::json::Path P) {
1203 llvm::json::ObjectMapper O(Params, P);
1209 llvm::json::Path P) {
1210 llvm::json::ObjectMapper O(Params, P);
1213 return mapOptOrNull(Params,
"compilationDatabaseChanges",
1218 llvm::json::Path P) {
1219 llvm::json::ObjectMapper O(Params, P);
1225 mapOptOrNull(Params,
"fallbackFlags", Opts.
fallbackFlags, P) &&
1226 mapOptOrNull(Params,
"clangdFileStatus", Opts.
FileStatus, P);
1230 llvm::json::Path P) {
1231 auto T = E.getAsInteger();
1242 llvm::json::Path P) {
1243 llvm::json::ObjectMapper O(Params, P);
1246 mapOptOrNull(Params,
"resolve", R.
resolve, P) &&
1247 mapOptOrNull(Params,
"direction", R.
direction, P);
1256 llvm::json::Object Result{};
1258 Result[
"parents"] = RP.
parents;
1263 llvm::json::ObjectMapper O(Params, P);
1264 return O && mapOptOrNull(Params,
"parents", RP.
parents, P);
1268 llvm::json::Object Result{
1269 {
"name", I.
name}, {
"kind",
static_cast<int>(I.
kind)},
1271 {
"uri", I.
uri}, {
"data", I.
data},
1275 Result[
"detail"] = I.
detail;
1280 llvm::json::Path P) {
1281 llvm::json::ObjectMapper O(Params, P);
1284 return O && O.map(
"name", I.
name) && O.map(
"kind", I.
kind) &&
1285 O.map(
"uri", I.
uri) && O.map(
"range", I.
range) &&
1287 mapOptOrNull(Params,
"detail", I.
detail, P) &&
1288 mapOptOrNull(Params,
"deprecated", I.
deprecated, P) &&
1289 mapOptOrNull(Params,
"parents", I.
parents, P) &&
1290 mapOptOrNull(Params,
"children", I.
children, P) &&
1291 mapOptOrNull(Params,
"data", I.
data, P);
1296 llvm::json::ObjectMapper O(Params, P);
1297 return O && O.map(
"item", R.
item) &&
1298 mapOptOrNull(Params,
"resolve", R.
resolve, P) &&
1299 mapOptOrNull(Params,
"direction", R.
direction, P);
1303 llvm::json::Path P) {
1304 llvm::json::ObjectMapper O(Params, P);
1309 llvm::json::Path P) {
1311 llvm::json::ObjectMapper O(Params, P);
1312 return fromJSON(Params, Base, P) && O && O.mapOptional(
"context", R.
context);
1316 return llvm::json::Value{
static_cast<int>(Tag)};
1320 llvm::json::Object Result{{
"name", I.
name},
1321 {
"kind",
static_cast<int>(I.
kind)},
1325 if (!I.
tags.empty())
1326 Result[
"tags"] = I.
tags;
1328 Result[
"detail"] = I.
detail;
1329 if (!I.
data.empty())
1330 Result[
"data"] = I.
data;
1335 llvm::json::Path P) {
1336 llvm::json::ObjectMapper O(Params, P);
1341 return O && O.map(
"name", I.
name) && O.map(
"kind", I.
kind) &&
1342 O.map(
"uri", I.
uri) && O.map(
"range", I.
range) &&
1344 mapOptOrNull(Params,
"data", I.
data, P);
1349 llvm::json::ObjectMapper O(Params, P);
1350 return O.map(
"item", C.
item);
1354 return llvm::json::Object{{
"from", C.
from}, {
"fromRanges", C.
fromRanges}};
1359 llvm::json::ObjectMapper O(Params, P);
1360 return O.map(
"item", C.
item);
1364 return llvm::json::Object{{
"to", C.
to}, {
"fromRanges", C.
fromRanges}};
1368 llvm::json::Path P) {
1369 llvm::json::ObjectMapper O(Params, P);
1382 llvm_unreachable(
"Unknown clang.clangd.InlayHintKind");
1386 llvm::json::Object Result{{
"position", H.
position},
1392 Result[
"kind"] = std::move(K);
1412 return "designator";
1414 llvm_unreachable(
"Unknown clang.clangd.InlayHintKind");
1416 return OS << ToString(Kind);
1430 llvm_unreachable(
"Unknown clang.clangd.OffsetEncoding");
1434 llvm::json::Path P) {
1435 auto Str = V.getAsString();
1438 OE = llvm::StringSwitch<OffsetEncoding>(*Str)
1446 return OS << toString(Enc);
1450 llvm::json::Path P) {
1451 llvm::json::ObjectMapper O(Params, P);
1458 return llvm::json::Object{{
"range", Out.
range},
1461 return llvm::json::Object{{
"range", Out.
range}};
1465 llvm::json::Path P) {
1466 llvm::json::ObjectMapper O(Params, P);
1471 return llvm::json::Object{
1478 llvm::json::Path P) {
1479 llvm::json::ObjectMapper O(Params, P);
1488 llvm::json::Object Result{
1489 {
"startLine",
Range.startLine},
1490 {
"endLine",
Range.endLine},
1492 if (
Range.startCharacter)
1493 Result[
"startCharacter"] =
Range.startCharacter;
1494 if (
Range.endCharacter)
1495 Result[
"endCharacter"] =
Range.endCharacter;
1496 if (!
Range.kind.empty())
1497 Result[
"kind"] =
Range.kind;
1502 llvm::json::Path P) {
1503 llvm::json::ObjectMapper O(Params, P);
1508 llvm::json::Object Result{
1515 Result[
"detail"] = N.
detail;
1517 Result[
"arcana"] = N.
arcana;
1519 Result[
"range"] = *N.
range;
1524 std::function<void(
const ASTNode &,
unsigned)> Print = [&](
const ASTNode &N,
1526 OS.indent(2 * Level) << N.
role <<
": " << N.
kind;
1531 Print(C, Level + 1);
1538 llvm::json::Object R;
1547 return llvm::json::Object{{
"items", N.
items}};
static llvm::Expected< std::string > resolve(const URI &U, llvm::StringRef HintPath="")
static llvm::Expected< URI > parse(llvm::StringRef Uri)
static llvm::Expected< std::string > resolvePath(llvm::StringRef AbsPath, llvm::StringRef HintPath="")
Whether current platform treats paths case insensitively.
std::bitset< SymbolKindMax+1 > SymbolKindBitset
@ Created
The file got created.
@ Deleted
The file got deleted.
@ Info
An information message.
bool fromJSON(const llvm::json::Value &, URIForFile &, llvm::json::Path)
constexpr auto CompletionItemKindMin
std::bitset< CompletionItemKindMax+1 > CompletionItemKindBitset
void elog(const char *Fmt, Ts &&...Vals)
llvm::json::Value toJSON(const URIForFile &U)
Serialize/deserialize URIForFile to/from a string URI.
llvm::raw_ostream & operator<<(llvm::raw_ostream &, const Position &)
CompletionItemKind
The kind of a completion entry.
CompletionItemKind adjustKindToCapability(CompletionItemKind Kind, CompletionItemKindBitset &SupportedCompletionItemKinds)
bool operator==(const TextEdit &L, const TextEdit &R)
InlayHintKind
Inlay hint kinds.
constexpr auto SymbolKindMin
constexpr unsigned SemanticTokenEncodingSize
bool operator<(const CompletionItem &, const CompletionItem &)
std::vector< ASTNode > children
Nodes nested within this one, such as the operands of a BinaryOperator.
std::optional< Range > range
TextDocumentIdentifier textDocument
The text document.
std::optional< Range > range
std::optional< std::string > failureReason
Represents an incoming call, e.g. a caller of a method or constructor.
CallHierarchyItem from
The item that makes the call.
std::vector< Range > fromRanges
The parameter of a callHierarchy/incomingCalls request.
URIForFile uri
The resource identifier of this item.
std::vector< SymbolTag > tags
Tags for this item.
std::string detail
More detaill for this item, e.g. the signature of a function.
SymbolKind kind
The kind of this item.
std::string name
The name of this item.
CallHierarchyItem to
The item that is called.
std::vector< Range > fromRanges
The parameter of a callHierarchy/outgoingCalls request.
std::optional< bool > needsConfirmation
std::string workingDirectory
std::vector< std::string > compilationCommand
MarkupKind SignatureHelpDocumentationFormat
bool ChangeAnnotation
The client supports change annotations on text edits,.
bool WorkspaceConfiguration
bool RenamePrepareSupport
bool DocumentChanges
The client supports versioned document changes for WorkspaceEdit.
std::optional< SymbolKindBitset > WorkspaceSymbolKinds
bool TheiaSemanticHighlighting
std::optional< CompletionItemKindBitset > CompletionItemKinds
bool HierarchicalDocumentSymbol
MarkupKind CompletionDocumentationFormat
bool CancelsStaleRequests
bool OffsetsInSignatureHelp
std::optional< std::vector< OffsetEncoding > > offsetEncoding
Supported encodings for LSP character offsets. (clangd extension).
bool ImplicitProgressCreation
bool SemanticTokenRefreshSupport
bool DiagnosticRelatedInformation
MarkupKind HoverContentFormat
std::vector< Diagnostic > diagnostics
std::vector< std::string > only
Range range
The range for which the command was invoked.
TextDocumentIdentifier textDocument
The document in which the command was invoked.
CodeActionContext context
Context carrying additional information.
std::string title
A short, human-readable, title for this code action.
std::optional< std::string > kind
static const llvm::StringLiteral REFACTOR_KIND
std::optional< Command > command
static const llvm::StringLiteral INFO_KIND
std::optional< WorkspaceEdit > edit
The workspace edit this code action performs.
static const llvm::StringLiteral QUICKFIX_KIND
std::optional< std::vector< Diagnostic > > diagnostics
The diagnostics that this code action resolves.
Structure to capture a description for an error code.
std::string href
An URI to open with more information about the diagnostic error.
std::string triggerCharacter
CompletionTriggerKind triggerKind
How the completion was triggered.
bool deprecated
Indicates if this item is deprecated.
std::optional< TextEdit > textEdit
InsertTextFormat insertTextFormat
std::optional< MarkupContent > documentation
A human-readable string that represents a doc-comment.
std::vector< TextEdit > additionalTextEdits
Represents a collection of completion items to be presented in the editor.
std::vector< CompletionItem > items
The completion items.
CompletionContext context
std::optional< int > limit
std::optional< std::string > section
std::optional< URIForFile > scopeUri
std::vector< ConfigurationItem > items
std::map< std::string, ClangdCompileCommand > compilationDatabaseChanges
std::optional< std::string > category
std::optional< std::vector< CodeAction > > codeActions
llvm::SmallVector< DiagnosticTag, 1 > tags
Additional metadata about the diagnostic.
Range range
The range at which the message applies.
std::string message
The diagnostic's message.
std::optional< std::vector< DiagnosticRelatedInformation > > relatedInformation
std::optional< CodeDescription > codeDescription
An optional property to describe the error code.
std::string code
The diagnostic's code. Can be omitted.
ConfigurationSettings settings
std::optional< bool > wantDiagnostics
std::vector< TextDocumentContentChangeEvent > contentChanges
The actual content changes.
VersionedTextDocumentIdentifier textDocument
std::vector< FileEvent > changes
The actual file events.
TextDocumentIdentifier textDocument
The document that was closed.
TextDocumentItem textDocument
The document that was opened.
TextDocumentIdentifier textDocument
The document that was saved.
Range range
The range this highlight applies to.
DocumentHighlightKind kind
The highlight kind, default is DocumentHighlightKind.Text.
Parameters for the document link request.
TextDocumentIdentifier textDocument
The document to provide document links for.
Range range
The range this link applies to.
URIForFile target
The uri this link points to. If missing a resolve request is sent later.
TextDocumentIdentifier textDocument
SymbolKind kind
The kind of this symbol.
std::vector< DocumentSymbol > children
Children of this symbol, e.g. properties of a class.
std::string name
The name of this symbol.
bool deprecated
Indicates if this symbol is deprecated.
std::string detail
More detail for this symbol, e.g the signature of a function.
llvm::json::Value argument
std::string command
The identifier of the actual command handler.
URIForFile uri
The file's URI.
FileChangeType type
The change type.
URIForFile uri
The text document's URI.
TextDocumentIdentifier textDocument
Stores information about a region of code that can be folded.
static const llvm::StringLiteral IMPORT_KIND
static const llvm::StringLiteral COMMENT_KIND
static const llvm::StringLiteral REGION_KIND
std::optional< Range > range
MarkupContent contents
The hover's content.
TextDocumentIdentifier TextDocument
The textdocument these inactive regions belong to.
std::vector< Range > InactiveRegions
The inactive regions that should be sent.
bool FileStatus
Clients supports show file status for textDocument/clangd.fileStatus.
std::vector< std::string > fallbackFlags
ConfigurationSettings ConfigSettings
std::optional< std::string > compilationDatabasePath
std::optional< std::string > rootPath
llvm::json::Object rawCapabilities
The same data as capabilities, but not parsed (to expose to modules).
InitializationOptions initializationOptions
User-provided initialization options.
std::optional< TraceLevel > trace
The initial trace setting. If omitted trace is disabled ('off').
ClientCapabilities capabilities
The capabilities provided by the client (editor or tool)
std::optional< URIForFile > rootUri
std::optional< int > processId
Position position
The position of this hint.
A parameter literal used in inlay hint requests.
TextDocumentIdentifier textDocument
The text document.
std::optional< Range > range
URIForFile uri
The text document's URI.
int64_t line
Line position in a document (zero-based).
URIForFile uri
The URI for which diagnostic information is reported.
std::optional< int64_t > version
The version number of the document the diagnostics are published for.
std::vector< Diagnostic > diagnostics
An array of diagnostic information items.
Position start
The range's start position.
Position end
The range's end position.
bool includeDeclaration
Include the declaration of the current symbol.
std::optional< std::string > containerName
std::string newName
The new name of the symbol.
Position position
The position at which this request was sent.
TextDocumentIdentifier textDocument
The document that was opened.
Parameters for the typeHierarchy/resolve request.
TypeHierarchyDirection direction
The direction of the hierarchy levels to resolve.
TypeHierarchyItem item
The item to resolve.
int resolve
The hierarchy levels to resolve. 0 indicates no level.
TextDocumentIdentifier textDocument
The text document.
std::vector< Position > positions
The positions inside the text document.
std::unique_ptr< SelectionRange > parent
unsigned length
the length of the token. A token cannot be multiline
unsigned tokenType
will be looked up in SemanticTokensLegend.tokenTypes
unsigned deltaLine
token line number, relative to the previous token
unsigned tokenModifiers
each set bit will be looked up in SemanticTokensLegend.tokenModifiers
std::string previousResultId
The previous result id.
TextDocumentIdentifier textDocument
The text document.
Describes a replacement of a contiguous range of semanticTokens.
std::vector< SemanticToken > tokens
std::optional< std::vector< SemanticTokensEdit > > edits
Set if we computed edits relative to a previous set of tokens.
std::optional< std::vector< SemanticToken > > tokens
Set if we computed a fresh set of tokens.
Body of textDocument/semanticTokens/full request.
TextDocumentIdentifier textDocument
The text document.
A versioned set of tokens.
std::vector< SemanticToken > tokens
The actual tokens.
MessageType type
The message type.
std::string message
The actual message.
Represents the signature of a callable.
int activeSignature
The active signature.
int activeParameter
The active parameter of the active signature.
std::vector< SignatureInformation > signatures
The resulting signatures.
std::string text
The new text of the range/document.
std::optional< Range > range
The range of the document that changed.
std::optional< int > rangeLength
The length of the range that got replaced.
std::vector< TextEdit > edits
VersionedTextDocumentIdentifier textDocument
The text document to change.
URIForFile uri
The text document's URI.
std::string languageId
The text document's language identifier.
std::optional< int64_t > version
std::string text
The content of the opened text document.
URIForFile uri
The text document's URI.
Position position
The position inside the text document.
TextDocumentIdentifier textDocument
The text document.
ChangeAnnotationIdentifier annotationId
std::string tweakID
ID of the tweak that should be executed. Corresponds to Tweak::id().
URIForFile file
A file provided by the client on a textDocument/codeAction request.
Range selection
A selection provided by the client on a textDocument/codeAction request.
Used to resolve a client provided item back.
std::optional< std::vector< ResolveParams > > parents
std::nullopt means parents aren't resolved and empty is no parents.
std::optional< std::vector< TypeHierarchyItem > > children
std::optional< std::string > detail
More detail for this item, e.g. the signature of a function.
SymbolKind kind
The kind of this item.
std::optional< std::vector< TypeHierarchyItem > > parents
This is a clangd exntesion.
URIForFile uri
The resource identifier of this item.
std::string name
The name of this item.
TypeHierarchyDirection direction
static URIForFile canonicalize(llvm::StringRef AbsPath, llvm::StringRef TUPath)
static llvm::Expected< URIForFile > fromURI(const URI &U, llvm::StringRef HintPath)
std::optional< std::int64_t > version
llvm::json::Value token
The token to be used to report progress.
Signals the end of progress reporting.
std::optional< std::string > message
Reporting progress is done using the following payload.
std::optional< bool > cancellable
std::optional< std::string > message
std::optional< unsigned > percentage
std::optional< std::map< std::string, std::vector< TextEdit > > > changes
Holds changes to existing resources.
std::map< std::string, ChangeAnnotation > changeAnnotations
std::optional< std::vector< TextDocumentEdit > > documentChanges
The parameters of a Workspace Symbol Request.
std::optional< int > limit