LLDB mainline
CompletionRequest.h
Go to the documentation of this file.
1//===-- CompletionRequest.h -------------------------------------*- C++ -*-===//
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#ifndef LLDB_UTILITY_COMPLETIONREQUEST_H
10#define LLDB_UTILITY_COMPLETIONREQUEST_H
11
12#include "lldb/Utility/Args.h"
15#include "llvm/ADT/StringRef.h"
16#include "llvm/ADT/StringSet.h"
17
18namespace lldb_private {
19enum class CompletionMode {
20 /// The current token has been completed. The client should indicate this
21 /// to the user (usually this is done by adding a trailing space behind the
22 /// token).
23 /// Example: "command sub" -> "command subcommand " (note the trailing space).
25 /// The current token has been partially completed. This means that we found
26 /// a completion, but that the token is still incomplete. Examples
27 /// for this are file paths, where we want to complete "/bi" to "/bin/", but
28 /// the file path token is still incomplete after the completion. Clients
29 /// should not indicate to the user that this is a full completion (e.g. by
30 /// not inserting the usual trailing space after a successful completion).
31 /// Example: "file /us" -> "file /usr/" (note the missing trailing space).
33 /// The full line has been rewritten by the completion.
34 /// Example: "alias name" -> "other_command full_name".
36};
37
39public:
40 /// A single completion and all associated data.
41 class Completion {
42
43 /// The actual text that should be completed. The meaning of this text
44 /// is defined by the CompletionMode.
45 /// \see m_mode
46 std::string m_completion;
47 /// The description that should be displayed to the user alongside the
48 /// completion text.
49 std::string m_descripton;
51
52 public:
53 Completion(llvm::StringRef completion, llvm::StringRef description,
54 CompletionMode mode)
55 : m_completion(completion.rtrim().str()),
56 m_descripton(description.rtrim().str()), m_mode(mode) {}
57 const std::string &GetCompletion() const { return m_completion; }
58 const std::string &GetDescription() const { return m_descripton; }
59 CompletionMode GetMode() const { return m_mode; }
60
61 /// Generates a string that uniquely identifies this completion result.
62 std::string GetUniqueKey() const;
63 };
64
65private:
66 /// List of found completions.
67 std::vector<Completion> m_results;
68
69 /// A set of the unique keys of all found completions so far. Used to filter
70 /// out duplicates.
71 /// \see CompletionResult::Completion::GetUniqueKey
72 llvm::StringSet<> m_added_values;
73
74public:
75 void AddResult(llvm::StringRef completion, llvm::StringRef description,
76 CompletionMode mode);
77
78 llvm::ArrayRef<Completion> GetResults() const { return m_results; }
79
80 /// Adds all collected completion matches to the given list.
81 /// The list will be cleared before the results are added. The number of
82 /// results here is guaranteed to be equal to GetNumberOfResults().
83 void GetMatches(StringList &matches) const;
84
85 /// Adds all collected completion descriptions to the given list.
86 /// The list will be cleared before the results are added. The number of
87 /// results here is guaranteed to be equal to GetNumberOfResults().
88 void GetDescriptions(StringList &descriptions) const;
89
90 std::size_t GetNumberOfResults() const { return m_results.size(); }
91};
92
93/// \class CompletionRequest CompletionRequest.h
94/// "lldb/Utility/ArgCompletionRequest.h"
95///
96/// Contains all information necessary to complete an incomplete command
97/// for the user. Will be filled with the generated completions by the different
98/// completions functions.
99///
101public:
102 /// Constructs a completion request.
103 ///
104 /// \param [in] command_line
105 /// The command line the user has typed at this point.
106 ///
107 /// \param [in] raw_cursor_pos
108 /// The position of the cursor in the command line string. Index 0 means
109 /// the cursor is at the start of the line. The completion starts from
110 /// this cursor position.
111 ///
112 /// \param [out] result
113 /// The CompletionResult that will be filled with the results after this
114 /// request has been handled.
115 CompletionRequest(llvm::StringRef command_line, unsigned raw_cursor_pos,
116 CompletionResult &result);
117
118 /// Sets the maximum number of completions that should be returned.
119 void SetMaxReturnElements(size_t max_return_elements) {
120 m_max_return_elements = max_return_elements;
121 }
122
123 /// Returns the raw user input used to create this CompletionRequest cut off
124 /// at the cursor position. The cursor will be at the end of the raw line.
125 llvm::StringRef GetRawLine() const {
126 return m_command.substr(0, GetRawCursorPos());
127 }
128
129 /// Returns the full raw user input used to create this CompletionRequest.
130 /// This string is not cut off at the cursor position and will include
131 /// characters behind the cursor position.
132 ///
133 /// You should most likely *not* use this function unless the characters
134 /// behind the cursor position influence the completion.
135 llvm::StringRef GetRawLineWithUnusedSuffix() const { return m_command; }
136
137 unsigned GetRawCursorPos() const { return m_raw_cursor_pos; }
138
139 const Args &GetParsedLine() const { return m_parsed_line; }
140
142
144 return GetParsedLine()[GetCursorIndex()];
145 }
146
147 size_t GetCursorCharPos() const { return m_cursor_char_position; }
148
149 /// Drops the first argument from the argument list.
152 m_parsed_line.Shift();
153 }
154
155 /// Adds an empty argument at the end of the argument list and moves
156 /// the cursor to this new argument.
158 m_parsed_line.AppendArgument(llvm::StringRef());
161 }
162
163 size_t GetCursorIndex() const { return m_cursor_index; }
164
166
167 /// Returns true if the maximum number of completions has not been reached
168 /// yet, hence we should keep adding completions.
169 bool ShouldAddCompletions() const {
171 }
172
173 /// Returns the maximum number of completions that need to be added
174 /// until reaching the maximum
176 const size_t number_of_results = m_result.GetNumberOfResults();
177 if (number_of_results >= m_max_return_elements)
178 return 0;
179 return m_max_return_elements - number_of_results;
180 }
181
182 /// Adds a possible completion string. If the completion was already
183 /// suggested before, it will not be added to the list of results. A copy of
184 /// the suggested completion is stored, so the given string can be free'd
185 /// afterwards.
186 ///
187 /// \param completion The suggested completion.
188 /// \param description An optional description of the completion string. The
189 /// description will be displayed to the user alongside the completion.
190 /// \param mode The CompletionMode for this completion.
191 void AddCompletion(llvm::StringRef completion,
192 llvm::StringRef description = "",
194 m_result.AddResult(completion, description, mode);
195 }
196
197 /// Adds a possible completion string if the completion would complete the
198 /// current argument.
199 ///
200 /// \param completion The suggested completion.
201 /// \param description An optional description of the completion string. The
202 /// description will be displayed to the user alongside the completion.
203 template <CompletionMode M = CompletionMode::Normal>
204 void TryCompleteCurrentArg(llvm::StringRef completion,
205 llvm::StringRef description = "") {
206 // Trying to rewrite the whole line while checking for the current
207 // argument never makes sense. Completion modes are always hardcoded, so
208 // this can be a static_assert.
209 static_assert(M != CompletionMode::RewriteLine,
210 "Shouldn't rewrite line with this function");
211 if (completion.starts_with(GetCursorArgumentPrefix()))
212 AddCompletion(completion, description, M);
213 }
214
215 /// Adds multiple possible completion strings.
216 ///
217 /// \param completions The list of completions.
218 ///
219 /// \see AddCompletion
220 void AddCompletions(const StringList &completions) {
221 for (const std::string &completion : completions)
222 AddCompletion(completion);
223 }
224
225 /// Adds multiple possible completion strings alongside their descriptions.
226 ///
227 /// The number of completions and descriptions must be identical.
228 ///
229 /// \param completions The list of completions.
230 /// \param descriptions The list of descriptions.
231 ///
232 /// \see AddCompletion
233 void AddCompletions(const StringList &completions,
234 const StringList &descriptions) {
235 lldbassert(completions.GetSize() == descriptions.GetSize());
236 for (std::size_t i = 0; i < completions.GetSize(); ++i)
237 AddCompletion(completions.GetStringAtIndex(i),
238 descriptions.GetStringAtIndex(i));
239 }
240
241 llvm::StringRef GetCursorArgumentPrefix() const {
243 }
244
245private:
246 /// The raw command line we are supposed to complete.
247 llvm::StringRef m_command;
248 /// The cursor position in m_command.
250 /// The command line parsed as arguments.
252 /// The index of the argument in which the completion cursor is.
254 /// The cursor position in the argument indexed by m_cursor_index.
256 /// The maximum number of completions that should be returned.
257 size_t m_max_return_elements = std::numeric_limits<size_t>::max();
258
259 /// The result this request is supposed to fill out.
260 /// We keep this object private to ensure that no backend can in any way
261 /// depend on already calculated completions (which would make debugging and
262 /// testing them much more complicated).
264};
265
266} // namespace lldb_private
267
268#endif // LLDB_UTILITY_COMPLETIONREQUEST_H
#define lldbassert(x)
Definition LLDBAssert.h:16
A command line argument class.
Definition Args.h:33
const char * GetArgumentAtIndex(size_t idx) const
Gets the NULL terminated C string argument pointer for the argument at index idx.
Definition Args.cpp:273
size_t m_cursor_char_position
The cursor position in the argument indexed by m_cursor_index.
CompletionResult & m_result
The result this request is supposed to fill out.
CompletionRequest(llvm::StringRef command_line, unsigned raw_cursor_pos, CompletionResult &result)
Constructs a completion request.
void SetMaxReturnElements(size_t max_return_elements)
Sets the maximum number of completions that should be returned.
void AddCompletion(llvm::StringRef completion, llvm::StringRef description="", CompletionMode mode=CompletionMode::Normal)
Adds a possible completion string.
void AddCompletions(const StringList &completions)
Adds multiple possible completion strings.
llvm::StringRef GetRawLine() const
Returns the raw user input used to create this CompletionRequest cut off at the cursor position.
void AddCompletions(const StringList &completions, const StringList &descriptions)
Adds multiple possible completion strings alongside their descriptions.
llvm::StringRef GetCursorArgumentPrefix() const
size_t m_max_return_elements
The maximum number of completions that should be returned.
void ShiftArguments()
Drops the first argument from the argument list.
llvm::StringRef GetRawLineWithUnusedSuffix() const
Returns the full raw user input used to create this CompletionRequest.
bool ShouldAddCompletions() const
Returns true if the maximum number of completions has not been reached yet, hence we should keep addi...
size_t m_cursor_index
The index of the argument in which the completion cursor is.
Args m_parsed_line
The command line parsed as arguments.
void AppendEmptyArgument()
Adds an empty argument at the end of the argument list and moves the cursor to this new argument.
llvm::StringRef m_command
The raw command line we are supposed to complete.
void TryCompleteCurrentArg(llvm::StringRef completion, llvm::StringRef description="")
Adds a possible completion string if the completion would complete the current argument.
size_t GetMaxNumberOfCompletionsToAdd() const
Returns the maximum number of completions that need to be added until reaching the maximum.
const Args::ArgEntry & GetParsedArg()
unsigned m_raw_cursor_pos
The cursor position in m_command.
std::string m_descripton
The description that should be displayed to the user alongside the completion text.
std::string m_completion
The actual text that should be completed.
Completion(llvm::StringRef completion, llvm::StringRef description, CompletionMode mode)
std::string GetUniqueKey() const
Generates a string that uniquely identifies this completion result.
llvm::ArrayRef< Completion > GetResults() const
std::vector< Completion > m_results
List of found completions.
void AddResult(llvm::StringRef completion, llvm::StringRef description, CompletionMode mode)
void GetDescriptions(StringList &descriptions) const
Adds all collected completion descriptions to the given list.
std::size_t GetNumberOfResults() const
void GetMatches(StringList &matches) const
Adds all collected completion matches to the given list.
llvm::StringSet m_added_values
A set of the unique keys of all found completions so far.
const char * GetStringAtIndex(size_t idx) const
A class that represents a running process on the host machine.
@ Partial
The current token has been partially completed.
@ Normal
The current token has been completed.
@ RewriteLine
The full line has been rewritten by the completion.