mirror of https://github.com/MidnightCommander/mc
Ticket #4258: wron subshell prompt parsing with fish 3.3.0.
Fish 3.3.0 sends \r while printing prompt and mc erases prompt buffer. This change was introduced by https://github.com/fish-shell/fish-shell/pull/8011. (parse_subshell_prompt_string): modify subshell promt parsing. First, skip trailing EOL (\n and \r). Then find previous EOL (if it exists). Get a part of subshell prompt between those EOLs and use it as MC prompt. Signed-off-by: Andrew Borodin <aborodin@vmail.ru>
This commit is contained in:
parent
0e6721c32b
commit
e819ed7421
|
@ -722,6 +722,7 @@ tests/src/Makefile
|
|||
tests/src/filemanager/Makefile
|
||||
tests/src/editor/Makefile
|
||||
tests/src/editor/test-data.txt
|
||||
tests/src/subshell/Makefile
|
||||
tests/src/vfs/Makefile
|
||||
tests/src/vfs/extfs/Makefile
|
||||
tests/src/vfs/extfs/helpers-list/Makefile
|
||||
|
|
|
@ -717,11 +717,33 @@ parse_subshell_prompt_string (const char *buffer, int bytes)
|
|||
subshell_prompt_temp_buffer = g_string_sized_new (INITIAL_PROMPT_SIZE);
|
||||
|
||||
/* Extract the prompt from the shell output */
|
||||
for (i = 0; i < bytes; i++)
|
||||
if (buffer[i] == '\n' || buffer[i] == '\r')
|
||||
g_string_set_size (subshell_prompt_temp_buffer, 0);
|
||||
else if (buffer[i] != '\0')
|
||||
g_string_append_c (subshell_prompt_temp_buffer, buffer[i]);
|
||||
|
||||
/* Remove trailing '\n' and '\r' */
|
||||
for (i = bytes - 1; (buffer[i] == '\n' || buffer[i] == '\r') && i >= 0; i--)
|
||||
;
|
||||
if (i < 0)
|
||||
{
|
||||
g_string_set_size (subshell_prompt_temp_buffer, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
/* New length */
|
||||
bytes = i + 1;
|
||||
|
||||
/* Get a part of buffer between last '\n' and/or '\r' and penultimate ones */
|
||||
for (; buffer[i] != '\n' && buffer[i] != '\r' && i >= 0; i--)
|
||||
;
|
||||
if (i >= 0)
|
||||
{
|
||||
i++;
|
||||
buffer += i;
|
||||
bytes -= i;
|
||||
}
|
||||
g_string_overwrite_len (subshell_prompt_temp_buffer, 0, buffer, bytes);
|
||||
/* Make string nul-terminated */
|
||||
g_string_set_size (subshell_prompt_temp_buffer, bytes);
|
||||
|
||||
/* FIXME: can buffer contain '\0'? */
|
||||
}
|
||||
|
||||
/* --------------------------------------------------------------------------------------------- */
|
||||
|
|
|
@ -6,6 +6,10 @@ if USE_INTERNAL_EDIT
|
|||
SUBDIRS += editor
|
||||
endif
|
||||
|
||||
if ENABLE_SUBSHELL
|
||||
SUBDIRS += subshell
|
||||
endif
|
||||
|
||||
AM_CPPFLAGS = \
|
||||
$(GLIB_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
|
|
|
@ -0,0 +1,26 @@
|
|||
PACKAGE_STRING = "/src/subshell"
|
||||
|
||||
AM_CPPFLAGS = \
|
||||
$(GLIB_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
@CHECK_CFLAGS@ \
|
||||
@PCRE_CPPFLAGS@
|
||||
|
||||
AM_LDFLAGS = @TESTS_LDFLAGS@
|
||||
|
||||
LIBS = @CHECK_LIBS@ \
|
||||
$(top_builddir)/src/libinternal.la \
|
||||
$(top_builddir)/lib/libmc.la \
|
||||
@PCRE_LIBS@
|
||||
|
||||
if ENABLE_MCLIB
|
||||
LIBS += $(GLIB_LIBS)
|
||||
endif
|
||||
|
||||
TESTS = \
|
||||
parse_subshell_prompt_string
|
||||
|
||||
check_PROGRAMS = $(TESTS)
|
||||
|
||||
parse_subshell_prompt_string_SOURCES = \
|
||||
parse_subshell_prompt_string.c
|
|
@ -0,0 +1,135 @@
|
|||
/*
|
||||
src/subshell - tests for parse_subshell_prompt_string() function
|
||||
|
||||
Copyright (C) 2021
|
||||
Free Software Foundation, Inc.
|
||||
|
||||
Written by:
|
||||
Andrew Borodin <aborodin@vmail.ru>, 2021
|
||||
|
||||
This file is part of the Midnight Commander.
|
||||
|
||||
The Midnight Commander is free software: you can redistribute it
|
||||
and/or modify it under the terms of the GNU General Public License as
|
||||
published by the Free Software Foundation, either version 3 of the License,
|
||||
or (at your option) any later version.
|
||||
|
||||
The Midnight Commander is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define TEST_SUITE_NAME "/src/subshell"
|
||||
|
||||
#include "tests/mctest.h"
|
||||
|
||||
#include "src/subshell/common.c"
|
||||
|
||||
/* --------------------------------------------------------------------------------------------- */
|
||||
|
||||
/* @Before */
|
||||
static void
|
||||
setup (void)
|
||||
{
|
||||
mc_global.mc_run_mode = MC_RUN_FULL;
|
||||
}
|
||||
|
||||
/* --------------------------------------------------------------------------------------------- */
|
||||
|
||||
/* @After */
|
||||
static void
|
||||
teardown (void)
|
||||
{
|
||||
g_string_free (subshell_prompt, TRUE);
|
||||
subshell_prompt = NULL;
|
||||
g_string_free (subshell_prompt_temp_buffer, TRUE);
|
||||
subshell_prompt_temp_buffer = NULL;
|
||||
}
|
||||
|
||||
/* --------------------------------------------------------------------------------------------- */
|
||||
|
||||
/* @DataSource("test_parse_subshell_prompt_string_ds") */
|
||||
/* *INDENT-OFF* */
|
||||
static const struct test_parse_subshell_prompt_string_ds
|
||||
{
|
||||
const char *input_value;
|
||||
const char *expected_result;
|
||||
} test_parse_subshell_prompt_string_ds[] =
|
||||
{
|
||||
{ /* 0 */
|
||||
"blabla",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 1 */
|
||||
"blabla\r",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 2 */
|
||||
"blabla\n",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 3 */
|
||||
"blabla\r\n",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 4 */
|
||||
"\r\n",
|
||||
""
|
||||
},
|
||||
{ /* 5 */
|
||||
"\rblabla",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 6 */
|
||||
"\r\nblabla",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 7 */
|
||||
"\r\nblabla\r\n",
|
||||
"blabla"
|
||||
},
|
||||
{ /* 8 */
|
||||
"bla1\r\nbla2\r\n",
|
||||
"bla2"
|
||||
}
|
||||
};
|
||||
/* *INDENT-ON* */
|
||||
|
||||
/* @Test(dataSource = "test_parse_subshell_prompt_string_ds") */
|
||||
/* *INDENT-OFF* */
|
||||
START_PARAMETRIZED_TEST (test_parse_subshell_prompt_string, test_parse_subshell_prompt_string_ds)
|
||||
/* *INDENT-ON* */
|
||||
{
|
||||
/* when */
|
||||
parse_subshell_prompt_string (data->input_value, strlen (data->input_value));
|
||||
/* then */
|
||||
mctest_assert_str_eq (subshell_prompt_temp_buffer->str, data->expected_result);
|
||||
}
|
||||
/* *INDENT-OFF* */
|
||||
END_PARAMETRIZED_TEST
|
||||
/* *INDENT-ON* */
|
||||
|
||||
/* --------------------------------------------------------------------------------------------- */
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TCase *tc_core;
|
||||
|
||||
tc_core = tcase_create ("Core");
|
||||
|
||||
tcase_add_checked_fixture (tc_core, setup, teardown);
|
||||
|
||||
/* Add new tests here: *************** */
|
||||
mctest_add_parameterized_test (tc_core, test_parse_subshell_prompt_string,
|
||||
test_parse_subshell_prompt_string_ds);
|
||||
/* *********************************** */
|
||||
|
||||
return mctest_run_all (tc_core);
|
||||
}
|
||||
|
||||
/* --------------------------------------------------------------------------------------------- */
|
Loading…
Reference in New Issue