summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lldb/include/lldb/Utility/CompletionRequest.h8
-rw-r--r--lldb/packages/Python/lldbsuite/test/functionalities/completion/TestCompletion.py7
-rw-r--r--lldb/packages/Python/lldbsuite/test/iohandler/completion/TestIOHandlerCompletion.py14
-rw-r--r--lldb/source/Commands/CommandCompletions.cpp27
-rw-r--r--lldb/source/Host/common/Editline.cpp6
5 files changed, 53 insertions, 9 deletions
diff --git a/lldb/include/lldb/Utility/CompletionRequest.h b/lldb/include/lldb/Utility/CompletionRequest.h
index 88ee3344a3f..28ac78a8756 100644
--- a/lldb/include/lldb/Utility/CompletionRequest.h
+++ b/lldb/include/lldb/Utility/CompletionRequest.h
@@ -17,7 +17,15 @@
namespace lldb_private {
enum class CompletionMode {
+ // The current token has been completed.
Normal,
+ // The current token has been partially completed. This means that we found
+ // a completion, but that the completed token is still incomplete. Examples
+ // for this are file paths, where we want to complete "/bi" to "/bin/", but
+ // the file path token is still incomplete after the completion. Clients
+ // should not indicate to the user that this is a full completion (e.g. by
+ // not inserting the usual trailing space after a successful completion).
+ Partial,
// The full line has been rewritten by the completion.
RewriteLine,
};
diff --git a/lldb/packages/Python/lldbsuite/test/functionalities/completion/TestCompletion.py b/lldb/packages/Python/lldbsuite/test/functionalities/completion/TestCompletion.py
index b95d490c887..0b5b3a416a0 100644
--- a/lldb/packages/Python/lldbsuite/test/functionalities/completion/TestCompletion.py
+++ b/lldb/packages/Python/lldbsuite/test/functionalities/completion/TestCompletion.py
@@ -137,6 +137,13 @@ class CommandLineCompletionTestCase(TestBase):
self.complete_from_to('log enable lldb expr -f ' + src_dir,
['main.cpp'])
+ @skipIfFreeBSD # timing out on the FreeBSD buildbot
+ def test_log_file(self):
+ # Complete in our source directory which contains a 'main.cpp' file.
+ src_dir = os.path.dirname(os.path.realpath(__file__))
+ self.complete_from_to('log enable lldb expr -f ' + src_dir,
+ [src_dir + "/"])
+
# <rdar://problem/11052829>
@skipIfFreeBSD # timing out on the FreeBSD buildbot
def test_infinite_loop_while_completing(self):
diff --git a/lldb/packages/Python/lldbsuite/test/iohandler/completion/TestIOHandlerCompletion.py b/lldb/packages/Python/lldbsuite/test/iohandler/completion/TestIOHandlerCompletion.py
index 26805bfb07c..a6748c65619 100644
--- a/lldb/packages/Python/lldbsuite/test/iohandler/completion/TestIOHandlerCompletion.py
+++ b/lldb/packages/Python/lldbsuite/test/iohandler/completion/TestIOHandlerCompletion.py
@@ -2,6 +2,8 @@
Test completion in our IOHandlers.
"""
+import os
+
import lldb
from lldbsuite.test.decorators import *
from lldbsuite.test.lldbtest import *
@@ -48,6 +50,18 @@ class IOHandlerCompletionTest(TestBase):
self.expect_string(prompt + "register")
self.child.send("\n")
+ # Try tab completing directories and files. Also tests the partial
+ # completion where LLDB shouldn't print a space after the directory
+ # completion (as it didn't completed the full token).
+ dir_without_slashes = os.path.realpath(os.path.dirname(__file__)).rstrip("/")
+ self.child.send("file " + dir_without_slashes + "\t")
+ self.expect_string("iohandler/completion/")
+ # If we get a correct partial completion without a trailing space, then this
+ # should complete the current test file.
+ self.child.send("TestIOHandler\t")
+ self.expect_string("TestIOHandlerCompletion.py")
+ self.child.send("\n")
+
# Start tab completion and abort showing more commands with 'n'.
self.child.send("\t")
self.expect_string("More (Y/n/a)")
diff --git a/lldb/source/Commands/CommandCompletions.cpp b/lldb/source/Commands/CommandCompletions.cpp
index a06f9a4db53..f00a35d3d81 100644
--- a/lldb/source/Commands/CommandCompletions.cpp
+++ b/lldb/source/Commands/CommandCompletions.cpp
@@ -87,10 +87,9 @@ void CommandCompletions::SourceFiles(CommandInterpreter &interpreter,
}
static void DiskFilesOrDirectories(const llvm::Twine &partial_name,
- bool only_directories, StringList &matches,
+ bool only_directories,
+ CompletionRequest &request,
TildeExpressionResolver &Resolver) {
- matches.Clear();
-
llvm::SmallString<256> CompletionBuffer;
llvm::SmallString<256> Storage;
partial_name.toVector(CompletionBuffer);
@@ -124,7 +123,7 @@ static void DiskFilesOrDirectories(const llvm::Twine &partial_name,
for (const auto &S : MatchSet) {
Resolved = S.getKey();
path::append(Resolved, path::get_separator());
- matches.AppendString(Resolved);
+ request.AddCompletion(Resolved, "", CompletionMode::Partial);
}
}
return;
@@ -136,7 +135,7 @@ static void DiskFilesOrDirectories(const llvm::Twine &partial_name,
if (FirstSep == llvm::StringRef::npos) {
// Make sure it ends with a separator.
path::append(CompletionBuffer, path::get_separator());
- matches.AppendString(CompletionBuffer);
+ request.AddCompletion(CompletionBuffer, "", CompletionMode::Partial);
return;
}
@@ -217,17 +216,27 @@ static void DiskFilesOrDirectories(const llvm::Twine &partial_name,
path::append(CompletionBuffer, path::get_separator());
}
- matches.AppendString(CompletionBuffer);
+ CompletionMode mode =
+ is_dir ? CompletionMode::Partial : CompletionMode::Normal;
+ request.AddCompletion(CompletionBuffer, "", mode);
}
}
+static void DiskFilesOrDirectories(const llvm::Twine &partial_name,
+ bool only_directories, StringList &matches,
+ TildeExpressionResolver &Resolver) {
+ CompletionResult result;
+ std::string partial_name_str = partial_name.str();
+ CompletionRequest request(partial_name_str, partial_name_str.size(), result);
+ DiskFilesOrDirectories(partial_name, only_directories, request, Resolver);
+ result.GetMatches(matches);
+}
+
static void DiskFilesOrDirectories(CompletionRequest &request,
bool only_directories) {
StandardTildeExpressionResolver resolver;
- StringList matches;
DiskFilesOrDirectories(request.GetCursorArgumentPrefix(), only_directories,
- matches, resolver);
- request.AddCompletions(matches);
+ request, resolver);
}
void CommandCompletions::DiskFiles(CommandInterpreter &interpreter,
diff --git a/lldb/source/Host/common/Editline.cpp b/lldb/source/Host/common/Editline.cpp
index a2e8773f8f1..0a95dffa40e 100644
--- a/lldb/source/Host/common/Editline.cpp
+++ b/lldb/source/Host/common/Editline.cpp
@@ -954,6 +954,12 @@ unsigned char Editline::TabCommand(int ch) {
el_insertstr(m_editline, to_add.c_str());
break;
}
+ case CompletionMode::Partial: {
+ std::string to_add = completion.GetCompletion();
+ to_add = to_add.substr(request.GetCursorArgumentPrefix().size());
+ el_insertstr(m_editline, to_add.c_str());
+ break;
+ }
case CompletionMode::RewriteLine: {
el_deletestr(m_editline, line_info->cursor - line_info->buffer);
el_insertstr(m_editline, completion.GetCompletion().c_str());
OpenPOWER on IntegriCloud