Fix behavior of backspace in multiline cmdline editing

This commit is contained in:
Robbie Harwood 2021-10-21 19:32:49 +00:00
parent 1b3247c3a2
commit a3a4d8c3e5
2 changed files with 142 additions and 1 deletions

View File

@ -0,0 +1,137 @@
From 7ebe10128eef978e99667d741ed4588d80b38441 Mon Sep 17 00:00:00 2001
From: Robbie Harwood <rharwood@redhat.com>
Date: Thu, 21 Oct 2021 15:15:33 -0400
Subject: [PATCH] Fix backspace when editing a multiline cmdline
Once the cmdline had passed the width of the screen, adding additional
characters introduced a spurious newline, and another newline at the
width of input. Furthermore, hitting backspace would not start
redrawing at the end of input, but rather at the beginning of the
current line - resulting in extra duplicate lines scrolling the console.
First, fix the assumption that the length of cmdline is the width - it
needs to include the length of the prompt (i.e., length of input and
space).
Second, fix the behavior of single-line redraw (i.e., redraw == 1) to
move the cursor to the row the line begins at.
Third, don't scroll the cursor down when a line wrap would occur - it's
not necessary since line wrap is enabled, and results in the extra blank
line.
Finally, comment all used escape sequences so that I don't need to look
them up again.
Signed-off-by: Robbie Harwood <rharwood@redhat.com>
---
com32/elflink/ldlinux/cli.c | 33 ++++++++++++++++++---------------
1 file changed, 18 insertions(+), 15 deletions(-)
diff --git a/com32/elflink/ldlinux/cli.c b/com32/elflink/ldlinux/cli.c
index 3119b11f..4913f038 100644
--- a/com32/elflink/ldlinux/cli.c
+++ b/com32/elflink/ldlinux/cli.c
@@ -135,6 +135,7 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
struct cli_command *comm_counter = NULL;
clock_t kbd_to = kbdtimeout;
clock_t tto = totaltimeout;
+ int prompt_len = 1 + strlen(input);
if (!width) {
int height;
@@ -144,7 +145,7 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
len = cursor = 0;
prev_len = 0;
- x = y = 0;
+ y = 0;
/*
* Before we start messing with the x,y coordinates print 'input'
@@ -152,6 +153,7 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
* previously.
*/
printf("%s ", input);
+ x = prompt_len;
while (!done) {
if (redraw > 1) {
@@ -162,8 +164,7 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
if (pDraw_Menu)
(*pDraw_Menu) (-1, top, 1);
prev_len = 0;
- printf("\033[2J\033[H");
- // printf("\033[0m\033[2J\033[H");
+ printf("\033[2J\033[H"); /* Clear entire screen; move to 0, 0. */
}
if (redraw > 0) {
@@ -172,10 +173,14 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
prev_len = max(len, prev_len);
/* Redraw the command line */
- printf("\033[?25l");
- printf("\033[1G%s ", input);
+ printf("\033[?25l"); /* Hide cursor. */
+ printf("\033[1G"); /* Column 1. */
+ if (y > 0)
+ printf("\033[%dA", y); /* Directly up. */
- x = strlen(input);
+ printf("%s ", input);
+
+ x = prompt_len;
y = 0;
at = 0;
while (at < prev_len) {
@@ -183,23 +188,22 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
at++;
x++;
if (x >= width) {
- printf("\r\n");
x = 0;
y++;
}
}
- printf("\033[K\r");
+ printf("\033[K\r"); /* Clear to end of line; go to beginning. */
- dy = y - (cursor + strlen(input) + 1) / width;
- x = (cursor + strlen(input) + 1) % width;
+ dy = y - (cursor + prompt_len) / width;
+ x = (cursor + prompt_len) % width;
if (dy) {
- printf("\033[%dA", dy);
+ printf("\033[%dA", dy); /* Cursor directly up. */
y -= dy;
}
if (x)
- printf("\033[%dC", x);
- printf("\033[?25h");
+ printf("\033[%dC", x); /* Cursor forward. */
+ printf("\033[?25h"); /* Show cursor. */
prev_len = len;
redraw = 0;
}
@@ -439,7 +443,6 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
cursor++;
x++;
if (x >= width) {
- printf("\r\n\033[K");
y++;
x = 0;
}
@@ -459,7 +462,7 @@ const char *edit_cmdline(const char *input, int top /*, int width */ ,
}
}
- printf("\033[?7h");
+ printf("\033[?7h"); /* Enable line wrap. */
/* Add the command to the history if its length is larger than 0 */
len = strlen(ret);
--
2.33.0

View File

@ -7,7 +7,7 @@ Summary: Simple kernel loader which boots from a FAT filesystem
Name: syslinux
Version: 6.04
%define tarball_version 6.04-pre1
Release: 0.19%{?dist}
Release: 0.20%{?dist}
License: GPLv2+
URL: http://syslinux.zytor.com/wiki/index.php/The_Syslinux_Project
Source0: http://www.kernel.org/pub/linux/utils/boot/syslinux/%{name}-%{tarball_version}.tar.xz
@ -17,6 +17,7 @@ Patch0003: 0003-include-sysmacros-h.patch
Patch0004: 0004-Add-RPMOPTFLAGS-to-CFLAGS-for-some-stuff.patch
Patch0005: 0005-Workaround-multiple-definition-of-symbol-errors.patch
Patch0006: 0006-Replace-builtin-strlen-that-appears-to-get-optimized.patch
Patch0007: 0007-Fix-backspace-when-editing-a-multiline-cmdline.patch
# this is to keep rpmbuild from thinking the .c32 / .com / .0 / memdisk files
# in noarch packages are a reason to stop the build.
@ -256,6 +257,9 @@ fi
%endif
%changelog
* Thu Oct 21 2021 Robbie Harwood <rharwood@redhat.com> - 6.04-0.20
- Fix behavior of backspace in multiline cmdline editing
* Wed Sep 01 2021 Robbie Harwood <rharwood@redhat.com> - 6.04-0.19
- Place extlinux(1) in the extlinux subpackage
- Resolves: #977004