X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=gdb%2Fcompleter.c;h=07facfb012c1e0a196c784cb65108d028640338b;hb=0670413d0eb264302e10a1baa163bc9c8c279a21;hp=5d1decca1d1b0b9ad5fb5a2c6c2c86a36b63c797;hpb=eedc3f4f0a02c9774277bd1a34aab6ebdc32f797;p=external%2Fbinutils.git diff --git a/gdb/completer.c b/gdb/completer.c index 5d1decc..07facfb 100644 --- a/gdb/completer.c +++ b/gdb/completer.c @@ -22,7 +22,7 @@ #include "expression.h" #include "filenames.h" /* For DOSish file names. */ #include "language.h" -#include "common/gdb_signals.h" +#include "gdbsupport/gdb_signals.h" #include "target.h" #include "reggroups.h" #include "user-regs.h" @@ -352,29 +352,58 @@ gdb_rl_find_completion_word (struct gdb_rl_completion_word_info *info, return line_buffer + point; } -/* See completer.h. */ +/* Find the completion word point for TEXT, emulating the algorithm + readline uses to find the word point, using WORD_BREAK_CHARACTERS + as word break characters. */ -const char * -advance_to_expression_complete_word_point (completion_tracker &tracker, - const char *text) +static const char * +advance_to_completion_word (completion_tracker &tracker, + const char *word_break_characters, + const char *text) { gdb_rl_completion_word_info info; - info.word_break_characters - = current_language->la_word_break_characters (); + info.word_break_characters = word_break_characters; info.quote_characters = gdb_completer_quote_characters; info.basic_quote_characters = rl_basic_quote_characters; + int delimiter; const char *start - = gdb_rl_find_completion_word (&info, NULL, NULL, text); + = gdb_rl_find_completion_word (&info, NULL, &delimiter, text); tracker.advance_custom_word_point_by (start - text); + if (delimiter) + { + tracker.set_quote_char (delimiter); + tracker.set_suppress_append_ws (true); + } + return start; } /* See completer.h. */ +const char * +advance_to_expression_complete_word_point (completion_tracker &tracker, + const char *text) +{ + const char *brk_chars = current_language->la_word_break_characters (); + return advance_to_completion_word (tracker, brk_chars, text); +} + +/* See completer.h. */ + +const char * +advance_to_filename_complete_word_point (completion_tracker &tracker, + const char *text) +{ + const char *brk_chars = gdb_completer_file_name_break_characters; + return advance_to_completion_word (tracker, brk_chars, text); +} + +/* See completer.h. */ + bool completion_tracker::completes_to_completion_word (const char *word) { @@ -394,6 +423,39 @@ completion_tracker::completes_to_completion_word (const char *word) return false; } +/* See completer.h. */ + +void +complete_nested_command_line (completion_tracker &tracker, const char *text) +{ + /* Must be called from a custom-word-point completer. */ + gdb_assert (tracker.use_custom_word_point ()); + + /* Disable the custom word point temporarily, because we want to + probe whether the command we're completing itself uses a custom + word point. */ + tracker.set_use_custom_word_point (false); + size_t save_custom_word_point = tracker.custom_word_point (); + + int quote_char = '\0'; + const char *word = completion_find_completion_word (tracker, text, + "e_char); + + if (tracker.use_custom_word_point ()) + { + /* The command we're completing uses a custom word point, so the + tracker already contains the matches. We're done. */ + return; + } + + /* Restore the custom word point settings. */ + tracker.set_custom_word_point (save_custom_word_point); + tracker.set_use_custom_word_point (true); + + /* Run the handle_completions completer phase. */ + complete_line (tracker, word, text, strlen (text)); +} + /* Complete on linespecs, which might be of two possible forms: file:line @@ -798,9 +860,7 @@ complete_explicit_location (completion_tracker &tracker, before: "b -function 'not_loaded_function_yet()'" after: "b -function 'not_loaded_function_yet()' " */ - gdb::unique_xmalloc_ptr text_copy - (xstrdup (text)); - tracker.add_completion (std::move (text_copy)); + tracker.add_completion (make_unique_xstrdup (text)); } else if (quoted_arg_end[1] == ' ') { @@ -1398,6 +1458,9 @@ complete_line_internal_1 (completion_tracker &tracker, break; } + /* Move the custom word point back too. */ + tracker.advance_custom_word_point_by (q - p); + if (reason != handle_brkchars) complete_on_cmdlist (result_list, tracker, q, word, ignore_help_classes); @@ -1613,6 +1676,48 @@ make_completion_match_str (gdb::unique_xmalloc_ptr &&match_name, return gdb::unique_xmalloc_ptr (newobj); } +/* See complete.h. */ + +completion_result +complete (const char *line, char const **word, int *quote_char) +{ + completion_tracker tracker_handle_brkchars; + completion_tracker tracker_handle_completions; + completion_tracker *tracker; + + /* The WORD should be set to the end of word to complete. We initialize + to the completion point which is assumed to be at the end of LINE. + This leaves WORD to be initialized to a sensible value in cases + completion_find_completion_word() fails i.e., throws an exception. + See bug 24587. */ + *word = line + strlen (line); + + try + { + *word = completion_find_completion_word (tracker_handle_brkchars, + line, quote_char); + + /* Completers that provide a custom word point in the + handle_brkchars phase also compute their completions then. + Completers that leave the completion word handling to readline + must be called twice. */ + if (tracker_handle_brkchars.use_custom_word_point ()) + tracker = &tracker_handle_brkchars; + else + { + complete_line (tracker_handle_completions, *word, line, strlen (line)); + tracker = &tracker_handle_completions; + } + } + catch (const gdb_exception &ex) + { + return {}; + } + + return tracker->build_completion_result (*word, *word - line, strlen (line)); +} + + /* Generate completions all at once. Does nothing if max_completions is 0. If max_completions is non-negative, this will collect at most max_completions strings. @@ -1681,10 +1786,7 @@ signal_completer (struct cmd_list_element *ignore, continue; if (strncasecmp (signame, word, len) == 0) - { - gdb::unique_xmalloc_ptr copy (xstrdup (signame)); - tracker.add_completion (std::move (copy)); - } + tracker.add_completion (make_unique_xstrdup (signame)); } } @@ -1723,10 +1825,7 @@ reg_or_group_completer_1 (completion_tracker &tracker, i++) { if (*name != '\0' && strncmp (word, name, len) == 0) - { - gdb::unique_xmalloc_ptr copy (xstrdup (name)); - tracker.add_completion (std::move (copy)); - } + tracker.add_completion (make_unique_xstrdup (name)); } } @@ -1740,10 +1839,7 @@ reg_or_group_completer_1 (completion_tracker &tracker, { name = reggroup_name (group); if (strncmp (word, name, len) == 0) - { - gdb::unique_xmalloc_ptr copy (xstrdup (name)); - tracker.add_completion (std::move (copy)); - } + tracker.add_completion (make_unique_xstrdup (name)); } } } @@ -1831,6 +1927,9 @@ gdb_completion_word_break_characters_throw () { gdb_assert (tracker.custom_word_point () > 0); rl_point = tracker.custom_word_point () - 1; + + gdb_assert (rl_point >= 0 && rl_point < strlen (rl_line_buffer)); + gdb_custom_word_point_brkchars[0] = rl_line_buffer[rl_point]; rl_completer_word_break_characters = gdb_custom_word_point_brkchars; rl_completer_quote_characters = NULL; @@ -1934,7 +2033,7 @@ completion_tracker::recompute_lowest_common_denominator /* See completer.h. */ void -completion_tracker::advance_custom_word_point_by (size_t len) +completion_tracker::advance_custom_word_point_by (int len) { m_custom_word_point += len; }