clang-tools  9.0.0
Protocol.cpp
Go to the documentation of this file.
1 //===--- Protocol.cpp - Language Server Protocol Implementation -----------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file contains the serialization code for the LSP structs.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "Protocol.h"
14 #include "Logger.h"
15 #include "URI.h"
16 #include "clang/Basic/LLVM.h"
17 #include "llvm/ADT/Hashing.h"
18 #include "llvm/ADT/SmallString.h"
19 #include "llvm/ADT/StringSwitch.h"
20 #include "llvm/Support/ErrorHandling.h"
21 #include "llvm/Support/Format.h"
22 #include "llvm/Support/FormatVariadic.h"
23 #include "llvm/Support/JSON.h"
24 #include "llvm/Support/Path.h"
25 #include "llvm/Support/raw_ostream.h"
26 
27 namespace clang {
28 namespace clangd {
29 
30 char LSPError::ID;
31 
32 URIForFile URIForFile::canonicalize(llvm::StringRef AbsPath,
33  llvm::StringRef TUPath) {
34  assert(llvm::sys::path::is_absolute(AbsPath) && "the path is relative");
35  auto Resolved = URI::resolvePath(AbsPath, TUPath);
36  if (!Resolved) {
37  elog("URIForFile: failed to resolve path {0} with TU path {1}: "
38  "{2}.\nUsing unresolved path.",
39  AbsPath, TUPath, Resolved.takeError());
40  return URIForFile(AbsPath);
41  }
42  return URIForFile(std::move(*Resolved));
43 }
44 
45 llvm::Expected<URIForFile> URIForFile::fromURI(const URI &U,
46  llvm::StringRef HintPath) {
47  auto Resolved = URI::resolve(U, HintPath);
48  if (!Resolved)
49  return Resolved.takeError();
50  return URIForFile(std::move(*Resolved));
51 }
52 
53 bool fromJSON(const llvm::json::Value &E, URIForFile &R) {
54  if (auto S = E.getAsString()) {
55  auto Parsed = URI::parse(*S);
56  if (!Parsed) {
57  elog("Failed to parse URI {0}: {1}", *S, Parsed.takeError());
58  return false;
59  }
60  if (Parsed->scheme() != "file" && Parsed->scheme() != "test") {
61  elog("Clangd only supports 'file' URI scheme for workspace files: {0}",
62  *S);
63  return false;
64  }
65  // "file" and "test" schemes do not require hint path.
66  auto U = URIForFile::fromURI(*Parsed, /*HintPath=*/"");
67  if (!U) {
68  elog("{0}", U.takeError());
69  return false;
70  }
71  R = std::move(*U);
72  return true;
73  }
74  return false;
75 }
76 
77 llvm::json::Value toJSON(const URIForFile &U) { return U.uri(); }
78 
79 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const URIForFile &U) {
80  return OS << U.uri();
81 }
82 
83 llvm::json::Value toJSON(const TextDocumentIdentifier &R) {
84  return llvm::json::Object{{"uri", R.uri}};
85 }
86 
87 bool fromJSON(const llvm::json::Value &Params, TextDocumentIdentifier &R) {
88  llvm::json::ObjectMapper O(Params);
89  return O && O.map("uri", R.uri);
90 }
91 
92 bool fromJSON(const llvm::json::Value &Params, Position &R) {
93  llvm::json::ObjectMapper O(Params);
94  return O && O.map("line", R.line) && O.map("character", R.character);
95 }
96 
97 llvm::json::Value toJSON(const Position &P) {
98  return llvm::json::Object{
99  {"line", P.line},
100  {"character", P.character},
101  };
102 }
103 
104 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const Position &P) {
105  return OS << P.line << ':' << P.character;
106 }
107 
108 bool fromJSON(const llvm::json::Value &Params, Range &R) {
109  llvm::json::ObjectMapper O(Params);
110  return O && O.map("start", R.start) && O.map("end", R.end);
111 }
112 
113 llvm::json::Value toJSON(const Range &P) {
114  return llvm::json::Object{
115  {"start", P.start},
116  {"end", P.end},
117  };
118 }
119 
120 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const Range &R) {
121  return OS << R.start << '-' << R.end;
122 }
123 
124 llvm::json::Value toJSON(const Location &P) {
125  return llvm::json::Object{
126  {"uri", P.uri},
127  {"range", P.range},
128  };
129 }
130 
131 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const Location &L) {
132  return OS << L.range << '@' << L.uri;
133 }
134 
135 bool fromJSON(const llvm::json::Value &Params, TextDocumentItem &R) {
136  llvm::json::ObjectMapper O(Params);
137  return O && O.map("uri", R.uri) && O.map("languageId", R.languageId) &&
138  O.map("version", R.version) && O.map("text", R.text);
139 }
140 
141 bool fromJSON(const llvm::json::Value &Params, TextEdit &R) {
142  llvm::json::ObjectMapper O(Params);
143  return O && O.map("range", R.range) && O.map("newText", R.newText);
144 }
145 
146 llvm::json::Value toJSON(const TextEdit &P) {
147  return llvm::json::Object{
148  {"range", P.range},
149  {"newText", P.newText},
150  };
151 }
152 
153 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const TextEdit &TE) {
154  OS << TE.range << " => \"";
155  llvm::printEscapedString(TE.newText, OS);
156  return OS << '"';
157 }
158 
159 bool fromJSON(const llvm::json::Value &E, TraceLevel &Out) {
160  if (auto S = E.getAsString()) {
161  if (*S == "off") {
162  Out = TraceLevel::Off;
163  return true;
164  } else if (*S == "messages") {
165  Out = TraceLevel::Messages;
166  return true;
167  } else if (*S == "verbose") {
168  Out = TraceLevel::Verbose;
169  return true;
170  }
171  }
172  return false;
173 }
174 
175 bool fromJSON(const llvm::json::Value &E, SymbolKind &Out) {
176  if (auto T = E.getAsInteger()) {
177  if (*T < static_cast<int>(SymbolKind::File) ||
178  *T > static_cast<int>(SymbolKind::TypeParameter))
179  return false;
180  Out = static_cast<SymbolKind>(*T);
181  return true;
182  }
183  return false;
184 }
185 
186 bool fromJSON(const llvm::json::Value &E, SymbolKindBitset &Out) {
187  if (auto *A = E.getAsArray()) {
188  for (size_t I = 0; I < A->size(); ++I) {
189  SymbolKind KindOut;
190  if (fromJSON((*A)[I], KindOut))
191  Out.set(size_t(KindOut));
192  }
193  return true;
194  }
195  return false;
196 }
197 
199  SymbolKindBitset &SupportedSymbolKinds) {
200  auto KindVal = static_cast<size_t>(Kind);
201  if (KindVal >= SymbolKindMin && KindVal <= SupportedSymbolKinds.size() &&
202  SupportedSymbolKinds[KindVal])
203  return Kind;
204 
205  switch (Kind) {
206  // Provide some fall backs for common kinds that are close enough.
207  case SymbolKind::Struct:
208  return SymbolKind::Class;
210  return SymbolKind::Enum;
211  default:
212  return SymbolKind::String;
213  }
214 }
215 
217  switch (Kind) {
219  return SymbolKind::Variable;
220  case index::SymbolKind::Module:
221  return SymbolKind::Module;
222  case index::SymbolKind::Namespace:
223  return SymbolKind::Namespace;
224  case index::SymbolKind::NamespaceAlias:
225  return SymbolKind::Namespace;
226  case index::SymbolKind::Macro:
227  return SymbolKind::String;
228  case index::SymbolKind::Enum:
229  return SymbolKind::Enum;
230  case index::SymbolKind::Struct:
231  return SymbolKind::Struct;
232  case index::SymbolKind::Class:
233  return SymbolKind::Class;
234  case index::SymbolKind::Protocol:
235  return SymbolKind::Interface;
236  case index::SymbolKind::Extension:
237  return SymbolKind::Interface;
238  case index::SymbolKind::Union:
239  return SymbolKind::Class;
240  case index::SymbolKind::TypeAlias:
241  return SymbolKind::Class;
242  case index::SymbolKind::Function:
243  return SymbolKind::Function;
244  case index::SymbolKind::Variable:
245  return SymbolKind::Variable;
246  case index::SymbolKind::Field:
247  return SymbolKind::Field;
248  case index::SymbolKind::EnumConstant:
249  return SymbolKind::EnumMember;
250  case index::SymbolKind::InstanceMethod:
251  case index::SymbolKind::ClassMethod:
252  case index::SymbolKind::StaticMethod:
253  return SymbolKind::Method;
254  case index::SymbolKind::InstanceProperty:
255  case index::SymbolKind::ClassProperty:
256  case index::SymbolKind::StaticProperty:
257  return SymbolKind::Property;
258  case index::SymbolKind::Constructor:
259  case index::SymbolKind::Destructor:
260  return SymbolKind::Method;
261  case index::SymbolKind::ConversionFunction:
262  return SymbolKind::Function;
263  case index::SymbolKind::Parameter:
264  return SymbolKind::Variable;
265  case index::SymbolKind::Using:
266  return SymbolKind::Namespace;
267  }
268  llvm_unreachable("invalid symbol kind");
269 }
270 
271 bool fromJSON(const llvm::json::Value &Params, ClientCapabilities &R) {
272  const llvm::json::Object *O = Params.getAsObject();
273  if (!O)
274  return false;
275  if (auto *TextDocument = O->getObject("textDocument")) {
276  if (auto *SemanticHighlighting =
277  TextDocument->getObject("semanticHighlightingCapabilities")) {
278  if (auto SemanticHighlightingSupport =
279  SemanticHighlighting->getBoolean("semanticHighlighting"))
280  R.SemanticHighlighting = *SemanticHighlightingSupport;
281  }
282  if (auto *Diagnostics = TextDocument->getObject("publishDiagnostics")) {
283  if (auto CategorySupport = Diagnostics->getBoolean("categorySupport"))
284  R.DiagnosticCategory = *CategorySupport;
285  if (auto CodeActions = Diagnostics->getBoolean("codeActionsInline"))
286  R.DiagnosticFixes = *CodeActions;
287  if (auto RelatedInfo = Diagnostics->getBoolean("relatedInformation"))
288  R.DiagnosticRelatedInformation = *RelatedInfo;
289  }
290  if (auto *Completion = TextDocument->getObject("completion")) {
291  if (auto *Item = Completion->getObject("completionItem")) {
292  if (auto SnippetSupport = Item->getBoolean("snippetSupport"))
293  R.CompletionSnippets = *SnippetSupport;
294  }
295  if (auto *ItemKind = Completion->getObject("completionItemKind")) {
296  if (auto *ValueSet = ItemKind->get("valueSet")) {
297  R.CompletionItemKinds.emplace();
298  if (!fromJSON(*ValueSet, *R.CompletionItemKinds))
299  return false;
300  }
301  }
302  if (auto EditsNearCursor = Completion->getBoolean("editsNearCursor"))
303  R.CompletionFixes = *EditsNearCursor;
304  }
305  if (auto *CodeAction = TextDocument->getObject("codeAction")) {
306  if (CodeAction->getObject("codeActionLiteralSupport"))
307  R.CodeActionStructure = true;
308  }
309  if (auto *DocumentSymbol = TextDocument->getObject("documentSymbol")) {
310  if (auto HierarchicalSupport =
311  DocumentSymbol->getBoolean("hierarchicalDocumentSymbolSupport"))
312  R.HierarchicalDocumentSymbol = *HierarchicalSupport;
313  }
314  if (auto *Hover = TextDocument->getObject("hover")) {
315  if (auto *ContentFormat = Hover->getArray("contentFormat")) {
316  for (const auto &Format : *ContentFormat) {
318  if (fromJSON(Format, K)) {
319  R.HoverContentFormat = K;
320  break;
321  }
322  }
323  }
324  }
325  if (auto *Help = TextDocument->getObject("signatureHelp")) {
326  R.HasSignatureHelp = true;
327  if (auto *Info = Help->getObject("signatureInformation")) {
328  if (auto *Parameter = Info->getObject("parameterInformation")) {
329  if (auto OffsetSupport = Parameter->getBoolean("labelOffsetSupport"))
330  R.OffsetsInSignatureHelp = *OffsetSupport;
331  }
332  }
333  }
334  }
335  if (auto *Workspace = O->getObject("workspace")) {
336  if (auto *Symbol = Workspace->getObject("symbol")) {
337  if (auto *SymbolKind = Symbol->getObject("symbolKind")) {
338  if (auto *ValueSet = SymbolKind->get("valueSet")) {
339  R.WorkspaceSymbolKinds.emplace();
340  if (!fromJSON(*ValueSet, *R.WorkspaceSymbolKinds))
341  return false;
342  }
343  }
344  }
345  }
346  if (auto *OffsetEncoding = O->get("offsetEncoding")) {
347  R.offsetEncoding.emplace();
349  return false;
350  }
351  return true;
352 }
353 
354 bool fromJSON(const llvm::json::Value &Params, InitializeParams &R) {
355  llvm::json::ObjectMapper O(Params);
356  if (!O)
357  return false;
358  // We deliberately don't fail if we can't parse individual fields.
359  // Failing to handle a slightly malformed initialize would be a disaster.
360  O.map("processId", R.processId);
361  O.map("rootUri", R.rootUri);
362  O.map("rootPath", R.rootPath);
363  O.map("capabilities", R.capabilities);
364  O.map("trace", R.trace);
365  O.map("initializationOptions", R.initializationOptions);
366  return true;
367 }
368 
369 llvm::json::Value toJSON(const MessageType &R) {
370  return static_cast<int64_t>(R);
371 }
372 
373 llvm::json::Value toJSON(const ShowMessageParams &R) {
374  return llvm::json::Object{{"type", R.type}, {"message", R.message}};
375 }
376 
377 bool fromJSON(const llvm::json::Value &Params, DidOpenTextDocumentParams &R) {
378  llvm::json::ObjectMapper O(Params);
379  return O && O.map("textDocument", R.textDocument);
380 }
381 
382 bool fromJSON(const llvm::json::Value &Params, DidCloseTextDocumentParams &R) {
383  llvm::json::ObjectMapper O(Params);
384  return O && O.map("textDocument", R.textDocument);
385 }
386 
387 bool fromJSON(const llvm::json::Value &Params, DidChangeTextDocumentParams &R) {
388  llvm::json::ObjectMapper O(Params);
389  return O && O.map("textDocument", R.textDocument) &&
390  O.map("contentChanges", R.contentChanges) &&
391  O.map("wantDiagnostics", R.wantDiagnostics);
392 }
393 
394 bool fromJSON(const llvm::json::Value &E, FileChangeType &Out) {
395  if (auto T = E.getAsInteger()) {
396  if (*T < static_cast<int>(FileChangeType::Created) ||
397  *T > static_cast<int>(FileChangeType::Deleted))
398  return false;
399  Out = static_cast<FileChangeType>(*T);
400  return true;
401  }
402  return false;
403 }
404 
405 bool fromJSON(const llvm::json::Value &Params, FileEvent &R) {
406  llvm::json::ObjectMapper O(Params);
407  return O && O.map("uri", R.uri) && O.map("type", R.type);
408 }
409 
410 bool fromJSON(const llvm::json::Value &Params, DidChangeWatchedFilesParams &R) {
411  llvm::json::ObjectMapper O(Params);
412  return O && O.map("changes", R.changes);
413 }
414 
415 bool fromJSON(const llvm::json::Value &Params,
417  llvm::json::ObjectMapper O(Params);
418  return O && O.map("range", R.range) && O.map("rangeLength", R.rangeLength) &&
419  O.map("text", R.text);
420 }
421 
422 bool fromJSON(const llvm::json::Value &Params,
424  llvm::json::ObjectMapper O(Params);
425  return O && O.map("textDocument", R.textDocument) && O.map("range", R.range);
426 }
427 
428 bool fromJSON(const llvm::json::Value &Params,
430  llvm::json::ObjectMapper O(Params);
431  return O && O.map("textDocument", R.textDocument) &&
432  O.map("position", R.position) && O.map("ch", R.ch);
433 }
434 
435 bool fromJSON(const llvm::json::Value &Params, DocumentFormattingParams &R) {
436  llvm::json::ObjectMapper O(Params);
437  return O && O.map("textDocument", R.textDocument);
438 }
439 
440 bool fromJSON(const llvm::json::Value &Params, DocumentSymbolParams &R) {
441  llvm::json::ObjectMapper O(Params);
442  return O && O.map("textDocument", R.textDocument);
443 }
444 
445 llvm::json::Value toJSON(const DiagnosticRelatedInformation &DRI) {
446  return llvm::json::Object{
447  {"location", DRI.location},
448  {"message", DRI.message},
449  };
450 }
451 
452 llvm::json::Value toJSON(const Diagnostic &D) {
453  llvm::json::Object Diag{
454  {"range", D.range},
455  {"severity", D.severity},
456  {"message", D.message},
457  };
458  if (D.category)
459  Diag["category"] = *D.category;
460  if (D.codeActions)
461  Diag["codeActions"] = D.codeActions;
462  if (!D.code.empty())
463  Diag["code"] = D.code;
464  if (!D.source.empty())
465  Diag["source"] = D.source;
466  if (D.relatedInformation)
467  Diag["relatedInformation"] = *D.relatedInformation;
468  return std::move(Diag);
469 }
470 
471 bool fromJSON(const llvm::json::Value &Params, Diagnostic &R) {
472  llvm::json::ObjectMapper O(Params);
473  if (!O || !O.map("range", R.range) || !O.map("message", R.message))
474  return false;
475  O.map("severity", R.severity);
476  O.map("category", R.category);
477  O.map("code", R.code);
478  O.map("source", R.source);
479  return true;
480 }
481 
482 bool fromJSON(const llvm::json::Value &Params, CodeActionContext &R) {
483  llvm::json::ObjectMapper O(Params);
484  return O && O.map("diagnostics", R.diagnostics);
485 }
486 
487 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, const Diagnostic &D) {
488  OS << D.range << " [";
489  switch (D.severity) {
490  case 1:
491  OS << "error";
492  break;
493  case 2:
494  OS << "warning";
495  break;
496  case 3:
497  OS << "note";
498  break;
499  case 4:
500  OS << "remark";
501  break;
502  default:
503  OS << "diagnostic";
504  break;
505  }
506  return OS << '(' << D.severity << "): " << D.message << "]";
507 }
508 
509 bool fromJSON(const llvm::json::Value &Params, CodeActionParams &R) {
510  llvm::json::ObjectMapper O(Params);
511  return O && O.map("textDocument", R.textDocument) &&
512  O.map("range", R.range) && O.map("context", R.context);
513 }
514 
515 bool fromJSON(const llvm::json::Value &Params, WorkspaceEdit &R) {
516  llvm::json::ObjectMapper O(Params);
517  return O && O.map("changes", R.changes);
518 }
519 
520 const llvm::StringLiteral ExecuteCommandParams::CLANGD_APPLY_FIX_COMMAND =
521  "clangd.applyFix";
522 const llvm::StringLiteral ExecuteCommandParams::CLANGD_APPLY_TWEAK =
523  "clangd.applyTweak";
524 
525 bool fromJSON(const llvm::json::Value &Params, ExecuteCommandParams &R) {
526  llvm::json::ObjectMapper O(Params);
527  if (!O || !O.map("command", R.command))
528  return false;
529 
530  auto Args = Params.getAsObject()->getArray("arguments");
531  if (R.command == ExecuteCommandParams::CLANGD_APPLY_FIX_COMMAND) {
532  return Args && Args->size() == 1 &&
533  fromJSON(Args->front(), R.workspaceEdit);
534  }
535  if (R.command == ExecuteCommandParams::CLANGD_APPLY_TWEAK)
536  return Args && Args->size() == 1 && fromJSON(Args->front(), R.tweakArgs);
537  return false; // Unrecognized command.
538 }
539 
540 llvm::json::Value toJSON(const SymbolInformation &P) {
541  return llvm::json::Object{
542  {"name", P.name},
543  {"kind", static_cast<int>(P.kind)},
544  {"location", P.location},
545  {"containerName", P.containerName},
546  };
547 }
548 
549 llvm::raw_ostream &operator<<(llvm::raw_ostream &O,
550  const SymbolInformation &SI) {
551  O << SI.containerName << "::" << SI.name << " - " << toJSON(SI);
552  return O;
553 }
554 
555 bool operator==(const SymbolDetails &LHS, const SymbolDetails &RHS) {
556  return LHS.name == RHS.name && LHS.containerName == RHS.containerName &&
557  LHS.USR == RHS.USR && LHS.ID == RHS.ID;
558 }
559 
560 llvm::json::Value toJSON(const SymbolDetails &P) {
561  llvm::json::Object Result{{"name", llvm::json::Value(nullptr)},
562  {"containerName", llvm::json::Value(nullptr)},
563  {"usr", llvm::json::Value(nullptr)},
564  {"id", llvm::json::Value(nullptr)}};
565 
566  if (!P.name.empty())
567  Result["name"] = P.name;
568 
569  if (!P.containerName.empty())
570  Result["containerName"] = P.containerName;
571 
572  if (!P.USR.empty())
573  Result["usr"] = P.USR;
574 
575  if (P.ID.hasValue())
576  Result["id"] = P.ID.getValue().str();
577 
578  // Older clang cannot compile 'return Result', even though it is legal.
579  return llvm::json::Value(std::move(Result));
580 }
581 
582 llvm::raw_ostream &operator<<(llvm::raw_ostream &O, const SymbolDetails &S) {
583  if (!S.containerName.empty()) {
584  O << S.containerName;
585  llvm::StringRef ContNameRef;
586  if (!ContNameRef.endswith("::")) {
587  O << " ";
588  }
589  }
590  O << S.name << " - " << toJSON(S);
591  return O;
592 }
593 
594 bool fromJSON(const llvm::json::Value &Params, WorkspaceSymbolParams &R) {
595  llvm::json::ObjectMapper O(Params);
596  return O && O.map("query", R.query);
597 }
598 
599 llvm::json::Value toJSON(const Command &C) {
600  auto Cmd = llvm::json::Object{{"title", C.title}, {"command", C.command}};
601  if (C.workspaceEdit)
602  Cmd["arguments"] = {*C.workspaceEdit};
603  if (C.tweakArgs)
604  Cmd["arguments"] = {*C.tweakArgs};
605  return std::move(Cmd);
606 }
607 
608 const llvm::StringLiteral CodeAction::QUICKFIX_KIND = "quickfix";
609 const llvm::StringLiteral CodeAction::REFACTOR_KIND = "refactor";
610 const llvm::StringLiteral CodeAction::INFO_KIND = "info";
611 
612 llvm::json::Value toJSON(const CodeAction &CA) {
613  auto CodeAction = llvm::json::Object{{"title", CA.title}};
614  if (CA.kind)
615  CodeAction["kind"] = *CA.kind;
616  if (CA.diagnostics)
617  CodeAction["diagnostics"] = llvm::json::Array(*CA.diagnostics);
618  if (CA.edit)
619  CodeAction["edit"] = *CA.edit;
620  if (CA.command)
621  CodeAction["command"] = *CA.command;
622  return std::move(CodeAction);
623 }
624 
625 llvm::raw_ostream &operator<<(llvm::raw_ostream &O, const DocumentSymbol &S) {
626  return O << S.name << " - " << toJSON(S);
627 }
628 
629 llvm::json::Value toJSON(const DocumentSymbol &S) {
630  llvm::json::Object Result{{"name", S.name},
631  {"kind", static_cast<int>(S.kind)},
632  {"range", S.range},
633  {"selectionRange", S.selectionRange}};
634 
635  if (!S.detail.empty())
636  Result["detail"] = S.detail;
637  if (!S.children.empty())
638  Result["children"] = S.children;
639  if (S.deprecated)
640  Result["deprecated"] = true;
641  // Older gcc cannot compile 'return Result', even though it is legal.
642  return llvm::json::Value(std::move(Result));
643 }
644 
645 llvm::json::Value toJSON(const WorkspaceEdit &WE) {
646  if (!WE.changes)
647  return llvm::json::Object{};
648  llvm::json::Object FileChanges;
649  for (auto &Change : *WE.changes)
650  FileChanges[Change.first] = llvm::json::Array(Change.second);
651  return llvm::json::Object{{"changes", std::move(FileChanges)}};
652 }
653 
654 bool fromJSON(const llvm::json::Value &Params, TweakArgs &A) {
655  llvm::json::ObjectMapper O(Params);
656  return O && O.map("file", A.file) && O.map("selection", A.selection) &&
657  O.map("tweakID", A.tweakID);
658 }
659 
660 llvm::json::Value toJSON(const TweakArgs &A) {
661  return llvm::json::Object{
662  {"tweakID", A.tweakID}, {"selection", A.selection}, {"file", A.file}};
663 }
664 
665 llvm::json::Value toJSON(const ApplyWorkspaceEditParams &Params) {
666  return llvm::json::Object{{"edit", Params.edit}};
667 }
668 
669 bool fromJSON(const llvm::json::Value &Params, TextDocumentPositionParams &R) {
670  llvm::json::ObjectMapper O(Params);
671  return O && O.map("textDocument", R.textDocument) &&
672  O.map("position", R.position);
673 }
674 
675 bool fromJSON(const llvm::json::Value &Params, CompletionContext &R) {
676  llvm::json::ObjectMapper O(Params);
677  if (!O)
678  return false;
679 
680  int TriggerKind;
681  if (!O.map("triggerKind", TriggerKind))
682  return false;
683  R.triggerKind = static_cast<CompletionTriggerKind>(TriggerKind);
684 
685  if (auto *TC = Params.getAsObject()->get("triggerCharacter"))
686  return fromJSON(*TC, R.triggerCharacter);
687  return true;
688 }
689 
690 bool fromJSON(const llvm::json::Value &Params, CompletionParams &R) {
691  if (!fromJSON(Params, static_cast<TextDocumentPositionParams &>(R)))
692  return false;
693  if (auto *Context = Params.getAsObject()->get("context"))
694  return fromJSON(*Context, R.context);
695  return true;
696 }
697 
698 static llvm::StringRef toTextKind(MarkupKind Kind) {
699  switch (Kind) {
701  return "plaintext";
703  return "markdown";
704  }
705  llvm_unreachable("Invalid MarkupKind");
706 }
707 
708 bool fromJSON(const llvm::json::Value &V, MarkupKind &K) {
709  auto Str = V.getAsString();
710  if (!Str) {
711  elog("Failed to parse markup kind: expected a string");
712  return false;
713  }
714  if (*Str == "plaintext")
716  else if (*Str == "markdown")
718  else {
719  elog("Unknown markup kind: {0}", *Str);
720  return false;
721  }
722  return true;
723 }
724 
725 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, MarkupKind K) {
726  return OS << toTextKind(K);
727 }
728 
729 llvm::json::Value toJSON(const MarkupContent &MC) {
730  if (MC.value.empty())
731  return nullptr;
732 
733  return llvm::json::Object{
734  {"kind", toTextKind(MC.kind)},
735  {"value", MC.value},
736  };
737 }
738 
739 llvm::json::Value toJSON(const Hover &H) {
740  llvm::json::Object Result{{"contents", toJSON(H.contents)}};
741 
742  if (H.range.hasValue())
743  Result["range"] = toJSON(*H.range);
744 
745  return std::move(Result);
746 }
747 
748 bool fromJSON(const llvm::json::Value &E, CompletionItemKind &Out) {
749  if (auto T = E.getAsInteger()) {
750  if (*T < static_cast<int>(CompletionItemKind::Text) ||
751  *T > static_cast<int>(CompletionItemKind::TypeParameter))
752  return false;
753  Out = static_cast<CompletionItemKind>(*T);
754  return true;
755  }
756  return false;
757 }
758 
761  CompletionItemKindBitset &SupportedCompletionItemKinds) {
762  auto KindVal = static_cast<size_t>(Kind);
763  if (KindVal >= CompletionItemKindMin &&
764  KindVal <= SupportedCompletionItemKinds.size() &&
765  SupportedCompletionItemKinds[KindVal])
766  return Kind;
767 
768  switch (Kind) {
769  // Provide some fall backs for common kinds that are close enough.
776  default:
778  }
779 }
780 
781 bool fromJSON(const llvm::json::Value &E, CompletionItemKindBitset &Out) {
782  if (auto *A = E.getAsArray()) {
783  for (size_t I = 0; I < A->size(); ++I) {
784  CompletionItemKind KindOut;
785  if (fromJSON((*A)[I], KindOut))
786  Out.set(size_t(KindOut));
787  }
788  return true;
789  }
790  return false;
791 }
792 
793 llvm::json::Value toJSON(const CompletionItem &CI) {
794  assert(!CI.label.empty() && "completion item label is required");
795  llvm::json::Object Result{{"label", CI.label}};
797  Result["kind"] = static_cast<int>(CI.kind);
798  if (!CI.detail.empty())
799  Result["detail"] = CI.detail;
800  if (!CI.documentation.empty())
801  Result["documentation"] = CI.documentation;
802  if (!CI.sortText.empty())
803  Result["sortText"] = CI.sortText;
804  if (!CI.filterText.empty())
805  Result["filterText"] = CI.filterText;
806  if (!CI.insertText.empty())
807  Result["insertText"] = CI.insertText;
809  Result["insertTextFormat"] = static_cast<int>(CI.insertTextFormat);
810  if (CI.textEdit)
811  Result["textEdit"] = *CI.textEdit;
812  if (!CI.additionalTextEdits.empty())
813  Result["additionalTextEdits"] = llvm::json::Array(CI.additionalTextEdits);
814  if (CI.deprecated)
815  Result["deprecated"] = CI.deprecated;
816  return std::move(Result);
817 }
818 
819 llvm::raw_ostream &operator<<(llvm::raw_ostream &O, const CompletionItem &I) {
820  O << I.label << " - " << toJSON(I);
821  return O;
822 }
823 
824 bool operator<(const CompletionItem &L, const CompletionItem &R) {
825  return (L.sortText.empty() ? L.label : L.sortText) <
826  (R.sortText.empty() ? R.label : R.sortText);
827 }
828 
829 llvm::json::Value toJSON(const CompletionList &L) {
830  return llvm::json::Object{
831  {"isIncomplete", L.isIncomplete},
832  {"items", llvm::json::Array(L.items)},
833  };
834 }
835 
836 llvm::json::Value toJSON(const ParameterInformation &PI) {
837  assert((PI.labelOffsets.hasValue() || !PI.labelString.empty()) &&
838  "parameter information label is required");
839  llvm::json::Object Result;
840  if (PI.labelOffsets)
841  Result["label"] =
842  llvm::json::Array({PI.labelOffsets->first, PI.labelOffsets->second});
843  else
844  Result["label"] = PI.labelString;
845  if (!PI.documentation.empty())
846  Result["documentation"] = PI.documentation;
847  return std::move(Result);
848 }
849 
850 llvm::json::Value toJSON(const SignatureInformation &SI) {
851  assert(!SI.label.empty() && "signature information label is required");
852  llvm::json::Object Result{
853  {"label", SI.label},
854  {"parameters", llvm::json::Array(SI.parameters)},
855  };
856  if (!SI.documentation.empty())
857  Result["documentation"] = SI.documentation;
858  return std::move(Result);
859 }
860 
861 llvm::raw_ostream &operator<<(llvm::raw_ostream &O,
862  const SignatureInformation &I) {
863  O << I.label << " - " << toJSON(I);
864  return O;
865 }
866 
867 llvm::json::Value toJSON(const SignatureHelp &SH) {
868  assert(SH.activeSignature >= 0 &&
869  "Unexpected negative value for number of active signatures.");
870  assert(SH.activeParameter >= 0 &&
871  "Unexpected negative value for active parameter index");
872  return llvm::json::Object{
873  {"activeSignature", SH.activeSignature},
874  {"activeParameter", SH.activeParameter},
875  {"signatures", llvm::json::Array(SH.signatures)},
876  };
877 }
878 
879 bool fromJSON(const llvm::json::Value &Params, RenameParams &R) {
880  llvm::json::ObjectMapper O(Params);
881  return O && O.map("textDocument", R.textDocument) &&
882  O.map("position", R.position) && O.map("newName", R.newName);
883 }
884 
885 llvm::json::Value toJSON(const DocumentHighlight &DH) {
886  return llvm::json::Object{
887  {"range", toJSON(DH.range)},
888  {"kind", static_cast<int>(DH.kind)},
889  };
890 }
891 
892 llvm::json::Value toJSON(const FileStatus &FStatus) {
893  return llvm::json::Object{
894  {"uri", FStatus.uri},
895  {"state", FStatus.state},
896  };
897 }
898 
899 llvm::raw_ostream &operator<<(llvm::raw_ostream &O,
900  const DocumentHighlight &V) {
901  O << V.range;
903  O << "(r)";
905  O << "(w)";
906  return O;
907 }
908 
909 bool fromJSON(const llvm::json::Value &Params,
911  llvm::json::ObjectMapper O(Params);
912  return O && O.map("settings", CCP.settings);
913 }
914 
915 bool fromJSON(const llvm::json::Value &Params,
916  ClangdCompileCommand &CDbUpdate) {
917  llvm::json::ObjectMapper O(Params);
918  return O && O.map("workingDirectory", CDbUpdate.workingDirectory) &&
919  O.map("compilationCommand", CDbUpdate.compilationCommand);
920 }
921 
922 bool fromJSON(const llvm::json::Value &Params, ConfigurationSettings &S) {
923  llvm::json::ObjectMapper O(Params);
924  if (!O)
925  return true; // 'any' type in LSP.
926  O.map("compilationDatabaseChanges", S.compilationDatabaseChanges);
927  return true;
928 }
929 
930 bool fromJSON(const llvm::json::Value &Params, InitializationOptions &Opts) {
931  llvm::json::ObjectMapper O(Params);
932  if (!O)
933  return true; // 'any' type in LSP.
934 
935  fromJSON(Params, Opts.ConfigSettings);
936  O.map("compilationDatabasePath", Opts.compilationDatabasePath);
937  O.map("fallbackFlags", Opts.fallbackFlags);
938  O.map("clangdFileStatus", Opts.FileStatus);
939  return true;
940 }
941 
942 bool fromJSON(const llvm::json::Value &E, TypeHierarchyDirection &Out) {
943  auto T = E.getAsInteger();
944  if (!T)
945  return false;
946  if (*T < static_cast<int>(TypeHierarchyDirection::Children) ||
947  *T > static_cast<int>(TypeHierarchyDirection::Both))
948  return false;
949  Out = static_cast<TypeHierarchyDirection>(*T);
950  return true;
951 }
952 
953 bool fromJSON(const llvm::json::Value &Params, TypeHierarchyParams &R) {
954  llvm::json::ObjectMapper O(Params);
955  return O && O.map("textDocument", R.textDocument) &&
956  O.map("position", R.position) && O.map("resolve", R.resolve) &&
957  O.map("direction", R.direction);
958 }
959 
960 llvm::raw_ostream &operator<<(llvm::raw_ostream &O,
961  const TypeHierarchyItem &I) {
962  return O << I.name << " - " << toJSON(I);
963 }
964 
965 llvm::json::Value toJSON(const TypeHierarchyItem &I) {
966  llvm::json::Object Result{{"name", I.name},
967  {"kind", static_cast<int>(I.kind)},
968  {"range", I.range},
969  {"selectionRange", I.selectionRange},
970  {"uri", I.uri}};
971 
972  if (I.detail)
973  Result["detail"] = I.detail;
974  if (I.deprecated)
975  Result["deprecated"] = I.deprecated;
976  if (I.parents)
977  Result["parents"] = I.parents;
978  if (I.children)
979  Result["children"] = I.children;
980  if (I.data)
981  Result["data"] = I.data;
982  return std::move(Result);
983 }
984 
985 bool fromJSON(const llvm::json::Value &Params, TypeHierarchyItem &I) {
986  llvm::json::ObjectMapper O(Params);
987 
988  // Required fields.
989  if (!(O && O.map("name", I.name) && O.map("kind", I.kind) &&
990  O.map("uri", I.uri) && O.map("range", I.range) &&
991  O.map("selectionRange", I.selectionRange))) {
992  return false;
993  }
994 
995  // Optional fields.
996  O.map("detail", I.detail);
997  O.map("deprecated", I.deprecated);
998  O.map("parents", I.parents);
999  O.map("children", I.children);
1000  O.map("data", I.data);
1001 
1002  return true;
1003 }
1004 
1005 bool fromJSON(const llvm::json::Value &Params,
1007  llvm::json::ObjectMapper O(Params);
1008  return O && O.map("item", P.item) && O.map("resolve", P.resolve) &&
1009  O.map("direction", P.direction);
1010 }
1011 
1012 bool fromJSON(const llvm::json::Value &Params, ReferenceParams &R) {
1014  return fromJSON(Params, Base);
1015 }
1016 
1017 static const char *toString(OffsetEncoding OE) {
1018  switch (OE) {
1019  case OffsetEncoding::UTF8:
1020  return "utf-8";
1021  case OffsetEncoding::UTF16:
1022  return "utf-16";
1023  case OffsetEncoding::UTF32:
1024  return "utf-32";
1026  return "unknown";
1027  }
1028  llvm_unreachable("Unknown clang.clangd.OffsetEncoding");
1029 }
1030 llvm::json::Value toJSON(const OffsetEncoding &OE) { return toString(OE); }
1031 bool fromJSON(const llvm::json::Value &V, OffsetEncoding &OE) {
1032  auto Str = V.getAsString();
1033  if (!Str)
1034  return false;
1035  OE = llvm::StringSwitch<OffsetEncoding>(*Str)
1036  .Case("utf-8", OffsetEncoding::UTF8)
1037  .Case("utf-16", OffsetEncoding::UTF16)
1038  .Case("utf-32", OffsetEncoding::UTF32)
1040  return true;
1041 }
1042 llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, OffsetEncoding Enc) {
1043  return OS << toString(Enc);
1044 }
1045 
1047  const SemanticHighlightingInformation &Rhs) {
1048  return Lhs.Line == Rhs.Line && Lhs.Tokens == Rhs.Tokens;
1049 }
1050 
1051 llvm::json::Value toJSON(const SemanticHighlightingInformation &Highlighting) {
1052  return llvm::json::Object{{"line", Highlighting.Line},
1053  {"tokens", Highlighting.Tokens}};
1054 }
1055 
1056 llvm::json::Value toJSON(const SemanticHighlightingParams &Highlighting) {
1057  return llvm::json::Object{
1058  {"textDocument", Highlighting.TextDocument},
1059  {"lines", std::move(Highlighting.Lines)},
1060  };
1061 }
1062 
1063 } // namespace clangd
1064 } // namespace clang
std::string insertText
A string that should be inserted to a document when selecting this completion.
Definition: Protocol.h:966
Range range
The range to format.
Definition: Protocol.h:602
std::string USR
Unified Symbol Resolution identifier This is an opaque string uniquely identifying a symbol...
Definition: Protocol.h:852
const tooling::CompileCommand & Command
llvm::Optional< std::vector< TypeHierarchyItem > > children
If this type hierarchy item is resolved, it contains the direct children of the current item...
Definition: Protocol.h:1154
TextDocumentIdentifier textDocument
The document to format.
Definition: Protocol.h:620
URIForFile uri
The file&#39;s URI.
Definition: Protocol.h:572
std::string code
The diagnostic&#39;s code. Can be omitted.
Definition: Protocol.h:651
llvm::json::Value toJSON(const FuzzyFindRequest &Request)
Definition: Index.cpp:48
Location location
The location of this symbol.
Definition: Protocol.h:832
TypeHierarchyDirection direction
The direction of the hierarchy levels to resolve.
Definition: Protocol.h:1114
llvm::Optional< TextEdit > textEdit
An edit which is applied to a document when selecting this completion.
Definition: Protocol.h:977
Exact commands are not specified in the protocol so we define the ones supported by Clangd here...
Definition: Protocol.h:741
TextDocumentIdentifier textDocument
The document to format.
Definition: Protocol.h:608
llvm::Optional< SymbolKindBitset > WorkspaceSymbolKinds
The supported set of SymbolKinds for workspace/symbol.
Definition: Protocol.h:371
llvm::Optional< URIForFile > rootUri
The rootUri of the workspace.
Definition: Protocol.h:481
Position start
The range&#39;s start position.
Definition: Protocol.h:157
friend bool operator==(const URIForFile &LHS, const URIForFile &RHS)
Definition: Protocol.h:97
Represents a collection of completion items to be presented in the editor.
Definition: Protocol.h:999
Range range
The range this highlight applies to.
Definition: Protocol.h:1083
llvm::Optional< bool > wantDiagnostics
Forces diagnostics to be generated, or to not be generated, for this version of the file...
Definition: Protocol.h:556
std::vector< std::string > compilationCommand
Definition: Protocol.h:433
Range range
The range for which the command was invoked.
Definition: Protocol.h:701
CodeActionContext context
Context carrying additional information.
Definition: Protocol.h:704
static const llvm::StringLiteral CLANGD_APPLY_FIX_COMMAND
Definition: Protocol.h:743
CompletionItemKind kind
The kind of this completion item.
Definition: Protocol.h:947
Clangd extension: parameters configurable at initialize time.
Definition: Protocol.h:449
std::string labelString
The label of this parameter. Ignored when labelOffsets is set.
Definition: Protocol.h:1013
bool CompletionSnippets
Client supports snippets as insert text.
Definition: Protocol.h:388
std::string ch
The character that has been typed.
Definition: Protocol.h:614
std::vector< CompletionItem > items
The completion items.
Definition: Protocol.h:1005
llvm::Optional< std::vector< CodeAction > > codeActions
Clangd extension: code actions related to this diagnostic.
Definition: Protocol.h:673
clang::find_all_symbols::SymbolInfo::SymbolKind SymbolKind
Definition: SymbolInfo.cpp:21
llvm::Optional< std::map< std::string, std::vector< TextEdit > > > changes
Holds changes to existing resources.
Definition: Protocol.h:710
llvm::Optional< std::string > kind
The kind of the code action.
Definition: Protocol.h:772
std::string title
A short, human-readable, title for this code action.
Definition: Protocol.h:768
Location location
The location of this related diagnostic information.
Definition: Protocol.h:635
llvm::Optional< Range > range
An optional range is a range inside a text document that is used to visualize a hover, e.g.
Definition: Protocol.h:918
TextDocumentIdentifier textDocument
The document that was closed.
Definition: Protocol.h:527
SymbolKind indexSymbolKindToSymbolKind(index::SymbolKind Kind)
Definition: Protocol.cpp:216
Represents a related message and source code location for a diagnostic.
Definition: Protocol.h:633
static llvm::StringRef toTextKind(MarkupKind Kind)
Definition: Protocol.cpp:698
std::string tweakID
ID of the tweak that should be executed. Corresponds to Tweak::id().
Definition: Protocol.h:728
std::string label
The label of this signature. Mandatory.
Definition: Protocol.h:1030
std::string state
The human-readable string presents the current state of the file, can be shown in the UI (e...
Definition: Protocol.h:1189
llvm::Optional< std::string > data
An optional &#39;data&#39; filed, which can be used to identify a type hierarchy item in a resolve request...
Definition: Protocol.h:1158
A code action represents a change that can be performed in code, e.g.
Definition: Protocol.h:766
URIForFile uri
The text document&#39;s URI.
Definition: Protocol.h:183
std::string text
The new text of the range/document.
Definition: Protocol.h:539
llvm::Optional< WorkspaceEdit > edit
The workspace edit this code action performs.
Definition: Protocol.h:781
Range selectionRange
The range that should be selected and revealed when this symbol is being picked, e.g the name of a function.
Definition: Protocol.h:814
constexpr auto SymbolKindMin
Definition: Protocol.h:328
The show message notification is sent from a server to a client to ask the client to display a partic...
Definition: Protocol.h:511
llvm::Optional< std::string > compilationDatabasePath
Definition: Protocol.h:454
std::string sortText
A string that should be used when comparing this item with other items.
Definition: Protocol.h:958
constexpr auto CompletionItemKindMin
Definition: Protocol.h:288
std::string name
The human readable name of the hierarchy item.
Definition: Protocol.h:1120
std::vector< ParameterInformation > parameters
The parameters of this signature.
Definition: Protocol.h:1036
std::bitset< CompletionItemKindMax+1 > CompletionItemKindBitset
Definition: Protocol.h:292
bool isIncomplete
The list is not complete.
Definition: Protocol.h:1002
Range selectionRange
The range that should be selected and revealed when this type hierarchy item is being picked...
Definition: Protocol.h:1144
std::string documentation
A human-readable string that represents a doc-comment.
Definition: Protocol.h:954
Range range
The range enclosing this symbol not including leading/trailing whitespace but everything else like co...
Definition: Protocol.h:810
URIForFile uri
The text document&#39;s URI.
Definition: Protocol.h:1186
std::vector< TextEdit > additionalTextEdits
An optional array of additional text edits that are applied when selecting this completion.
Definition: Protocol.h:982
void elog(const char *Fmt, Ts &&... Vals)
Definition: Logger.h:56
Represents programming constructs like variables, classes, interfaces etc.
Definition: Protocol.h:793
static const llvm::StringLiteral CLANGD_APPLY_TWEAK
Definition: Protocol.h:745
MarkupKind HoverContentFormat
The content format that should be used for Hover requests.
Definition: Protocol.h:424
std::string Tokens
The base64 encoded string of highlighting tokens.
Definition: Protocol.h:1200
llvm::Optional< int > processId
The process Id of the parent process that started the server.
Definition: Protocol.h:470
Range range
The range enclosing this type hierarchy item not including leading/trailing whitespace but everything...
Definition: Protocol.h:1139
CompletionItemKind
The kind of a completion entry.
Definition: Protocol.h:259
ConfigurationSettings ConfigSettings
Definition: Protocol.h:452
TextDocumentIdentifier TextDocument
The textdocument these highlightings belong to.
Definition: Protocol.h:1209
A top-level diagnostic that may have Notes and Fixes.
Definition: Diagnostics.h:84
std::string uri() const
Definition: Protocol.h:95
BindArgumentKind Kind
bool OffsetsInSignatureHelp
Client supports processing label offsets instead of a simple label string.
Definition: Protocol.h:405
MarkupContent contents
The hover&#39;s content.
Definition: Protocol.h:914
A document highlight is a range inside a text document which deserves special attention.
Definition: Protocol.h:1081
URIForFile uri
The text document&#39;s URI.
Definition: Protocol.h:219
bool CompletionFixes
Client supports completions with additionalTextEdit near the cursor.
Definition: Protocol.h:393
std::string detail
A human-readable string with additional information about this item, like type or symbol information...
Definition: Protocol.h:951
const Type * get(const Key< Type > &Key) const
Get data stored for a typed Key.
Definition: Context.h:100
llvm::Optional< SymbolID > ID
Definition: Protocol.h:854
std::string source
A human-readable string describing the source of this diagnostic, e.g.
Definition: Protocol.h:655
llvm::Optional< TweakArgs > tweakArgs
Definition: Protocol.h:752
TextDocumentIdentifier textDocument
The document that was opened.
Definition: Protocol.h:1065
std::string newText
The string to be inserted.
Definition: Protocol.h:208
Parameters for the semantic highlighting (server-side) push notification.
Definition: Protocol.h:1207
bool DiagnosticCategory
Whether the client accepts diagnostics with category attached to it using the "category" extension...
Definition: Protocol.h:384
std::string newName
The new name of the symbol.
Definition: Protocol.h:1071
Represents the signature of something callable.
Definition: Protocol.h:1027
Clangd extension: parameters configurable at any time, via the workspace/didChangeConfiguration notif...
Definition: Protocol.h:440
std::string command
The command identifier, e.g. CLANGD_APPLY_FIX_COMMAND.
Definition: Protocol.h:748
static llvm::Expected< URIForFile > fromURI(const URI &U, llvm::StringRef HintPath)
Definition: Protocol.cpp:45
InitializationOptions initializationOptions
User-provided initialization options.
Definition: Protocol.h:493
TextDocumentIdentifier textDocument
Definition: Protocol.h:626
std::string filterText
A string that should be used when filtering a set of completion items.
Definition: Protocol.h:962
TextDocumentIdentifier textDocument
The document in which the command was invoked.
Definition: Protocol.h:698
Range range
The range of the text document to be manipulated.
Definition: Protocol.h:204
static llvm::Expected< std::string > resolvePath(llvm::StringRef AbsPath, llvm::StringRef HintPath="")
Resolves AbsPath into a canonical path of its URI, by converting AbsPath to URI and resolving the URI...
Definition: URI.cpp:230
bool deprecated
Indicates if this item is deprecated.
Definition: Protocol.h:985
int activeSignature
The active signature.
Definition: Protocol.h:1049
std::vector< std::string > fallbackFlags
Definition: Protocol.h:458
MessageType type
The message type.
Definition: Protocol.h:513
int activeParameter
The active parameter of the active signature.
Definition: Protocol.h:1052
static const char * toString(OffsetEncoding OE)
Definition: Protocol.cpp:1017
llvm::Optional< Range > range
The range of the document that changed.
Definition: Protocol.h:533
llvm::Optional< std::string > category
The diagnostic&#39;s category.
Definition: Protocol.h:668
CompletionTriggerKind triggerKind
How the completion was triggered.
Definition: Protocol.h:894
static URIForFile canonicalize(llvm::StringRef AbsPath, llvm::StringRef TUPath)
Canonicalizes AbsPath via URI.
Definition: Protocol.cpp:32
Position position
The position inside the text document.
Definition: Protocol.h:877
URIForFile file
A file provided by the client on a textDocument/codeAction request.
Definition: Protocol.h:724
bool SemanticHighlighting
Client supports semantic highlighting.
Definition: Protocol.h:417
int Line
The line these highlightings belong to.
Definition: Protocol.h:1198
std::vector< DocumentSymbol > children
Children of this symbol, e.g. properties of a class.
Definition: Protocol.h:817
const Decl * D
Definition: XRefs.cpp:868
std::string message
The message of this related diagnostic information.
Definition: Protocol.h:637
std::string documentation
The documentation of this parameter. Optional.
Definition: Protocol.h:1022
SymbolKind kind
The kind of this symbol.
Definition: Protocol.h:829
static const llvm::StringLiteral REFACTOR_KIND
Definition: Protocol.h:774
std::vector< SignatureInformation > signatures
The resulting signatures.
Definition: Protocol.h:1046
llvm::Optional< int > rangeLength
The length of the range that got replaced.
Definition: Protocol.h:536
bool FileStatus
Clients supports show file status for textDocument/clangd.fileStatus.
Definition: Protocol.h:461
std::string name
The name of this symbol.
Definition: Protocol.h:795
bool DiagnosticFixes
Whether the client accepts diagnostics with codeActions attached inline.
Definition: Protocol.h:375
ClientCapabilities capabilities
The capabilities provided by the client (editor or tool)
Definition: Protocol.h:487
TextDocumentItem textDocument
The document that was opened.
Definition: Protocol.h:521
llvm::Optional< std::string > detail
Optional detail for the hierarchy item.
Definition: Protocol.h:1124
A context is an immutable container for per-request data that must be propagated through layers that ...
Definition: Context.h:69
TextDocumentIdentifier textDocument
The document that did change.
Definition: Protocol.h:547
std::map< std::string, ClangdCompileCommand > compilationDatabaseChanges
Definition: Protocol.h:443
std::string detail
More detail for this symbol, e.g the signature of a function.
Definition: Protocol.h:798
std::vector< FileEvent > changes
The actual file events.
Definition: Protocol.h:580
std::vector< SemanticHighlightingInformation > Lines
The lines of highlightings that should be sent.
Definition: Protocol.h:1211
An information message.
llvm::Optional< CompletionItemKindBitset > CompletionItemKinds
The supported set of CompletionItemKinds for textDocument/completion.
Definition: Protocol.h:409
std::string languageId
The text document&#39;s language identifier.
Definition: Protocol.h:222
llvm::Optional< std::string > rootPath
The rootPath of the workspace.
Definition: Protocol.h:476
Position position
The position at which this request was sent.
Definition: Protocol.h:611
bool CodeActionStructure
Client supports CodeAction return value for textDocument/codeAction.
Definition: Protocol.h:413
bool fromJSON(const llvm::json::Value &Parameters, FuzzyFindRequest &Request)
Definition: Index.cpp:34
A single parameter of a particular signature.
Definition: Protocol.h:1010
int line
Line position in a document (zero-based).
Definition: Protocol.h:128
std::vector< TextDocumentContentChangeEvent > contentChanges
The actual content changes.
Definition: Protocol.h:550
int character
Character offset on a line in a document (zero-based).
Definition: Protocol.h:133
TypeHierarchyDirection direction
The direction of the hierarchy levels to resolve.
Definition: Protocol.h:1173
CompletionContext context
Definition: Protocol.h:902
Represents the signature of a callable.
Definition: Protocol.h:1043
std::string query
A non-empty query string.
Definition: Protocol.h:863
The class presents a C++ symbol, e.g.
Definition: Symbol.h:36
SymbolKind kind
The kind of this symbol.
Definition: Protocol.h:801
===– Representation.cpp - ClangDoc Representation --------—*- C++ -*-===//
std::bitset< SymbolKindMax+1 > SymbolKindBitset
Definition: Protocol.h:330
SymbolKind
A symbol kind.
Definition: Protocol.h:299
std::string message
The diagnostic&#39;s message.
Definition: Protocol.h:658
std::string triggerCharacter
The trigger character (a single character) that has trigger code complete.
Definition: Protocol.h:897
TextDocumentIdentifier textDocument
The text document.
Definition: Protocol.h:874
static const llvm::StringLiteral INFO_KIND
Definition: Protocol.h:775
std::string label
The label of this completion item.
Definition: Protocol.h:943
The type hierarchy params is an extension of the TextDocumentPositionsParams with optional properties...
Definition: Protocol.h:1109
llvm::Optional< std::pair< unsigned, unsigned > > labelOffsets
Inclusive start and exclusive end offsets withing the containing signature label. ...
Definition: Protocol.h:1019
DocumentHighlightKind kind
The highlight kind, default is DocumentHighlightKind.Text.
Definition: Protocol.h:1086
SymbolKind adjustKindToCapability(SymbolKind Kind, SymbolKindBitset &SupportedSymbolKinds)
Definition: Protocol.cpp:198
static const llvm::StringLiteral QUICKFIX_KIND
Definition: Protocol.h:773
A URI describes the location of a source file.
Definition: URI.h:28
Range selection
A selection provided by the client on a textDocument/codeAction request.
Definition: Protocol.h:726
std::vector< Diagnostic > diagnostics
An array of diagnostics.
Definition: Protocol.h:692
int severity
The diagnostic&#39;s severity.
Definition: Protocol.h:648
bool deprecated
Indicates if this symbol is deprecated.
Definition: Protocol.h:804
llvm::Optional< Command > command
A command this code action executes.
Definition: Protocol.h:785
llvm::Optional< llvm::Expected< tooling::AtomicChanges > > Result
Definition: Rename.cpp:36
The parameters of a Workspace Symbol Request.
Definition: Protocol.h:861
FileChangeType type
The change type.
Definition: Protocol.h:574
llvm::Optional< std::vector< TypeHierarchyItem > > parents
If this type hierarchy item is resolved, it contains the direct parents.
Definition: Protocol.h:1149
int resolve
The hierarchy levels to resolve. 0 indicates no level.
Definition: Protocol.h:1111
Parameters for the typeHierarchy/resolve request.
Definition: Protocol.h:1165
std::string text
The content of the opened text document.
Definition: Protocol.h:228
Clangd extension: indicates the current state of the file in clangd, sent from server via the textDoc...
Definition: Protocol.h:1184
static llvm::Expected< std::string > resolve(const URI &U, llvm::StringRef HintPath="")
Resolves the absolute path of U.
Definition: URI.cpp:222
std::string containerName
The name of the symbol containing this symbol.
Definition: Protocol.h:835
llvm::Optional< std::vector< Diagnostic > > diagnostics
The diagnostics that this code action resolves.
Definition: Protocol.h:778
SymbolKind kind
The kind of the hierarchy item. For instance, class or interface.
Definition: Protocol.h:1127
Position position
The position at which this request was sent.
Definition: Protocol.h:1068
URIForFile uri
The text document&#39;s URI.
Definition: Protocol.h:121
std::string message
The actual message.
Definition: Protocol.h:515
TypeHierarchyItem item
The item to resolve.
Definition: Protocol.h:1167
static llvm::Expected< URI > parse(llvm::StringRef Uri)
Parse a URI string "<scheme>:[//<authority>/]<path>".
Definition: URI.cpp:164
Range range
The range at which the message applies.
Definition: Protocol.h:644
Represents a semantic highlighting information that has to be applied on a specific line of the text ...
Definition: Protocol.h:1196
friend bool operator<(const URIForFile &LHS, const URIForFile &RHS)
Definition: Protocol.h:105
int version
The version number of this document (it will strictly increase after each.
Definition: Protocol.h:225
bool HasSignatureHelp
Client supports signature help.
Definition: Protocol.h:401
bool DiagnosticRelatedInformation
Whether the client accepts diagnostics with related locations.
Definition: Protocol.h:379
TextDocumentIdentifier textDocument
The document to format.
Definition: Protocol.h:599
std::unique_ptr< GlobalCompilationDatabase > Base
Position end
The range&#39;s end position.
Definition: Protocol.h:160
llvm::Optional< WorkspaceEdit > workspaceEdit
Definition: Protocol.h:751
int resolve
The hierarchy levels to resolve. 0 indicates no level.
Definition: Protocol.h:1170
llvm::raw_ostream & operator<<(llvm::raw_ostream &OS, const CodeCompletion &C)
URIForFile uri
The URI of the text document where this type hierarchy item belongs to.
Definition: Protocol.h:1133
std::string name
The name of this symbol.
Definition: Protocol.h:826
InsertTextFormat insertTextFormat
The format of the insert text.
Definition: Protocol.h:970
Clangd extension that&#39;s used in the &#39;compilationDatabaseChanges&#39; in workspace/didChangeConfiguration ...
Definition: Protocol.h:431
Arguments for the &#39;applyTweak&#39; command.
Definition: Protocol.h:722
llvm::Optional< std::vector< DiagnosticRelatedInformation > > relatedInformation
An array of related diagnostic information, e.g.
Definition: Protocol.h:662
bool deprecated
true if the hierarchy item is deprecated. Otherwise, false.
Definition: Protocol.h:1130
Represents information about identifier.
Definition: Protocol.h:842
llvm::Optional< std::vector< OffsetEncoding > > offsetEncoding
Supported encodings for LSP character offsets. (clangd extension).
Definition: Protocol.h:420
llvm::Optional< TraceLevel > trace
The initial trace setting. If omitted trace is disabled (&#39;off&#39;).
Definition: Protocol.h:490
std::string documentation
The documentation of this signature. Optional.
Definition: Protocol.h:1033
bool HierarchicalDocumentSymbol
Client supports hierarchical document symbols.
Definition: Protocol.h:397
Represents information about programming constructs like variables, classes, interfaces etc...
Definition: Protocol.h:824