diff options
| author | Denis Vlasenko <vda.linux@googlemail.com> | 2008-05-25 21:52:03 +0000 |
|---|---|---|
| committer | Denis Vlasenko <vda.linux@googlemail.com> | 2008-05-25 21:52:03 +0000 |
| commit | b267ed95bc8141dbf14b276d4aef0fb8e2f5dda7 (patch) | |
| tree | c1b92f55c181c430525713fa81efdf6bf3216f47 | |
| parent | 4830fc565acd064e4ae033a6573a432c8b3857b9 (diff) | |
| download | busybox-w32-b267ed95bc8141dbf14b276d4aef0fb8e2f5dda7.tar.gz busybox-w32-b267ed95bc8141dbf14b276d4aef0fb8e2f5dda7.tar.bz2 busybox-w32-b267ed95bc8141dbf14b276d4aef0fb8e2f5dda7.zip | |
lineedit: correctly handle prompt longer than screen width. closes bug 3414
| -rw-r--r-- | libbb/lineedit.c | 32 |
1 files changed, 18 insertions, 14 deletions
diff --git a/libbb/lineedit.c b/libbb/lineedit.c index c91efd40c..fb595c010 100644 --- a/libbb/lineedit.c +++ b/libbb/lineedit.c | |||
| @@ -80,10 +80,9 @@ struct lineedit_statics { | |||
| 80 | volatile unsigned cmdedit_termw; /* = 80; */ /* actual terminal width */ | 80 | volatile unsigned cmdedit_termw; /* = 80; */ /* actual terminal width */ |
| 81 | sighandler_t previous_SIGWINCH_handler; | 81 | sighandler_t previous_SIGWINCH_handler; |
| 82 | 82 | ||
| 83 | 83 | unsigned cmdedit_x; /* real x terminal position */ | |
| 84 | int cmdedit_x; /* real x terminal position */ | 84 | unsigned cmdedit_y; /* pseudoreal y terminal position */ |
| 85 | int cmdedit_y; /* pseudoreal y terminal position */ | 85 | unsigned cmdedit_prmt_len; /* length of prompt (without colors etc) */ |
| 86 | int cmdedit_prmt_len; /* length of prompt (without colors etc) */ | ||
| 87 | 86 | ||
| 88 | unsigned cursor; | 87 | unsigned cursor; |
| 89 | unsigned command_len; | 88 | unsigned command_len; |
| @@ -199,7 +198,7 @@ static void cmdedit_set_out_char(int next_char) | |||
| 199 | { | 198 | { |
| 200 | bb_putchar(c); | 199 | bb_putchar(c); |
| 201 | } | 200 | } |
| 202 | if (++cmdedit_x >= (int)cmdedit_termw) { | 201 | if (++cmdedit_x >= cmdedit_termw) { |
| 203 | /* terminal is scrolled down */ | 202 | /* terminal is scrolled down */ |
| 204 | cmdedit_y++; | 203 | cmdedit_y++; |
| 205 | cmdedit_x = 0; | 204 | cmdedit_x = 0; |
| @@ -262,12 +261,12 @@ static void input_backward(unsigned num) | |||
| 262 | return; | 261 | return; |
| 263 | cursor -= num; | 262 | cursor -= num; |
| 264 | 263 | ||
| 265 | if ((unsigned)cmdedit_x >= num) { | 264 | if (cmdedit_x >= num) { |
| 266 | cmdedit_x -= num; | 265 | cmdedit_x -= num; |
| 267 | if (num <= 4) { | 266 | if (num <= 4) { |
| 268 | /* This is longer by 5 bytes on x86. | 267 | /* This is longer by 5 bytes on x86. |
| 269 | * Also gets mysteriously | 268 | * Also gets miscompiled for ARM users |
| 270 | * miscompiled for some ARM users. | 269 | * (busybox.net/bugs/view.php?id=2274). |
| 271 | * printf(("\b\b\b\b" + 4) - num); | 270 | * printf(("\b\b\b\b" + 4) - num); |
| 272 | * return; | 271 | * return; |
| 273 | */ | 272 | */ |
| @@ -282,9 +281,12 @@ static void input_backward(unsigned num) | |||
| 282 | 281 | ||
| 283 | /* Need to go one or more lines up */ | 282 | /* Need to go one or more lines up */ |
| 284 | num -= cmdedit_x; | 283 | num -= cmdedit_x; |
| 285 | count_y = 1 + (num / cmdedit_termw); | 284 | { |
| 286 | cmdedit_y -= count_y; | 285 | unsigned w = cmdedit_termw; /* volatile var */ |
| 287 | cmdedit_x = cmdedit_termw * count_y - num; | 286 | count_y = 1 + (num / w); |
| 287 | cmdedit_y -= count_y; | ||
| 288 | cmdedit_x = w * count_y - num; | ||
| 289 | } | ||
| 288 | /* go to 1st column; go up; go to correct column */ | 290 | /* go to 1st column; go up; go to correct column */ |
| 289 | printf("\r" "\033[%dA" "\033[%dC", count_y, cmdedit_x); | 291 | printf("\r" "\033[%dA" "\033[%dC", count_y, cmdedit_x); |
| 290 | } | 292 | } |
| @@ -292,10 +294,12 @@ static void input_backward(unsigned num) | |||
| 292 | static void put_prompt(void) | 294 | static void put_prompt(void) |
| 293 | { | 295 | { |
| 294 | out1str(cmdedit_prompt); | 296 | out1str(cmdedit_prompt); |
| 295 | cmdedit_x = cmdedit_prmt_len; | ||
| 296 | cursor = 0; | 297 | cursor = 0; |
| 297 | // Huh? what if cmdedit_prmt_len >= width? | 298 | { |
| 298 | cmdedit_y = 0; /* new quasireal y */ | 299 | unsigned w = cmdedit_termw; /* volatile var */ |
| 300 | cmdedit_y = cmdedit_prmt_len / w; /* new quasireal y */ | ||
| 301 | cmdedit_x = cmdedit_prmt_len % w; | ||
| 302 | } | ||
| 299 | } | 303 | } |
| 300 | 304 | ||
| 301 | /* draw prompt, editor line, and clear tail */ | 305 | /* draw prompt, editor line, and clear tail */ |
