diff options
author | Ron Yorston <rmy@pobox.com> | 2021-03-25 14:20:56 +0000 |
---|---|---|
committer | Denys Vlasenko <vda.linux@googlemail.com> | 2021-03-29 12:05:53 +0200 |
commit | 7b4c2276a89fca0dfedf73db07fbe20fff17a0de (patch) | |
tree | 4dcfd339390b32341bcb2dd5b6ee8db9204d47c4 /editors/vi.c | |
parent | 1195782d79d282639f54ef9620a9211c96c572f1 (diff) | |
download | busybox-w32-7b4c2276a89fca0dfedf73db07fbe20fff17a0de.tar.gz busybox-w32-7b4c2276a89fca0dfedf73db07fbe20fff17a0de.tar.bz2 busybox-w32-7b4c2276a89fca0dfedf73db07fbe20fff17a0de.zip |
vi: fix word operations across line boundaries
Commit 4b49422a0 (vi: fix changes to word at end of line. Closes
11796) fixed a problem where an operation on a word at the end of
a line followed by a line starting with whitespace incorrectly
joined the lines. However it also broke the case where operating
on multiple words across a line boundary *should* join the lines.
Fix this by detecting when trailing whitepace in a word operation
includes a newline. Whitespace beyond the newline is excluded
from consideration.
function old new delta
do_cmd 5083 5088 +5
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 1/0 up/down: 5/0) Total: 5 bytes
Signed-off-by: Ron Yorston <rmy@pobox.com>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
Diffstat (limited to 'editors/vi.c')
-rw-r--r-- | editors/vi.c | 16 |
1 files changed, 9 insertions, 7 deletions
diff --git a/editors/vi.c b/editors/vi.c index abc0aeae8..1bc2d08ad 100644 --- a/editors/vi.c +++ b/editors/vi.c | |||
@@ -3774,14 +3774,16 @@ static void do_cmd(int c) | |||
3774 | place_cursor(0, 0); | 3774 | place_cursor(0, 0); |
3775 | if (c1 == 27) { // ESC- user changed mind and wants out | 3775 | if (c1 == 27) { // ESC- user changed mind and wants out |
3776 | c = c1 = 27; // Escape- do nothing | 3776 | c = c1 = 27; // Escape- do nothing |
3777 | } else if (strchr("wW", c1)) { | 3777 | } else if (c1 == 'w' || c1 == 'W') { |
3778 | ml = 0; // multi-line ranges aren't allowed for words | 3778 | char *q0 = q; |
3779 | if (c == 'c') { | 3779 | // don't include trailing WS as part of word |
3780 | // don't include trailing WS as part of word | 3780 | while (q > p && isspace(*q)) { |
3781 | while (isspace(*q) && q > p) { | 3781 | if (*q-- == '\n') |
3782 | q--; | 3782 | q0 = q; |
3783 | } | ||
3784 | } | 3783 | } |
3784 | // for non-change operations WS after NL is not part of word | ||
3785 | if (c != 'c' && q != p && *q != '\n') | ||
3786 | q = q0; | ||
3785 | dot = yank_delete(p, q, ml, yf, ALLOW_UNDO); // delete word | 3787 | dot = yank_delete(p, q, ml, yf, ALLOW_UNDO); // delete word |
3786 | } else if (strchr("^0bBeEft%$ lh\b\177", c1)) { | 3788 | } else if (strchr("^0bBeEft%$ lh\b\177", c1)) { |
3787 | // partial line copy text into a register and delete | 3789 | // partial line copy text into a register and delete |