summaryrefslogtreecommitdiffstats
path: root/vtysh
diff options
context:
space:
mode:
authorDonatas Abraitis <donatas@opensourcerouting.org>2022-08-10 12:43:11 +0200
committerDonatas Abraitis <donatas@opensourcerouting.org>2022-08-10 15:18:49 +0200
commit149a3fffe0d713e4c78edd908f4ebf3fd99cb397 (patch)
tree71d89e83c89e261cb37efe43bf640d06b9a7025f /vtysh
parentMerge pull request #11668 from rampxxxx/bfd_rtt_in_echo_pkt (diff)
downloadfrr-149a3fffe0d713e4c78edd908f4ebf3fd99cb397.tar.xz
frr-149a3fffe0d713e4c78edd908f4ebf3fd99cb397.zip
vtysh: Handle SIGTSTP (C-z) without exiting the vty shell
After 4c92dd90d3d15cff640de063ff14eec950402d25 switching to poll-based I/O, vtysh prompt exits on C-z signal. Signed-off-by: Donatas Abraitis <donatas@opensourcerouting.org>
Diffstat (limited to 'vtysh')
-rw-r--r--vtysh/vtysh_main.c82
1 files changed, 35 insertions, 47 deletions
diff --git a/vtysh/vtysh_main.c b/vtysh/vtysh_main.c
index 04eb47fee..ca119eb90 100644
--- a/vtysh/vtysh_main.c
+++ b/vtysh/vtysh_main.c
@@ -78,36 +78,56 @@ int execute_flag = 0;
/* Flag to indicate if in user/unprivileged mode. */
int user_mode;
-/* For sigsetjmp() & siglongjmp(). */
-static sigjmp_buf jmpbuf;
-
-/* Flag for avoid recursive siglongjmp() call. */
-static int jmpflag = 0;
-
/* Master of threads. */
struct thread_master *master;
/* Command logging */
FILE *logfile;
+static void vtysh_rl_callback(char *line_read)
+{
+ HIST_ENTRY *last;
+
+ rl_callback_handler_remove();
+
+ if (!line_read) {
+ vtysh_loop_exited = true;
+ return;
+ }
+
+ /* If the line has any text in it, save it on the history. But only if
+ * last command in history isn't the same one.
+ */
+ if (*line_read) {
+ using_history();
+ last = previous_history();
+ if (!last || strcmp(last->line, line_read) != 0) {
+ add_history(line_read);
+ append_history(1, history_file);
+ }
+ }
+
+ vtysh_execute(line_read);
+
+ if (!vtysh_loop_exited)
+ rl_callback_handler_install(vtysh_prompt(), vtysh_rl_callback);
+}
+
/* SIGTSTP handler. This function care user's ^Z input. */
static void sigtstp(int sig)
{
+ rl_callback_handler_remove();
+
/* Execute "end" command. */
vtysh_execute("end");
+ if (!vtysh_loop_exited)
+ rl_callback_handler_install(vtysh_prompt(), vtysh_rl_callback);
+
/* Initialize readline. */
rl_initialize();
printf("\n");
-
- /* Check jmpflag for duplicate siglongjmp(). */
- if (!jmpflag)
- return;
-
- jmpflag = 0;
-
- /* Back to main command loop. */
- siglongjmp(jmpbuf, 1);
+ rl_forced_update_display();
}
/* SIGINT handler. This function care user's ^Z input. */
@@ -207,34 +227,6 @@ struct option longopts[] = {
bool vtysh_loop_exited;
-static void vtysh_rl_callback(char *line_read)
-{
- HIST_ENTRY *last;
-
- rl_callback_handler_remove();
-
- if (!line_read) {
- vtysh_loop_exited = true;
- return;
- }
-
- /* If the line has any text in it, save it on the history. But only if
- * last command in history isn't the same one. */
- if (*line_read) {
- using_history();
- last = previous_history();
- if (!last || strcmp(last->line, line_read) != 0) {
- add_history(line_read);
- append_history(1, history_file);
- }
- }
-
- vtysh_execute(line_read);
-
- if (!vtysh_loop_exited)
- rl_callback_handler_install(vtysh_prompt(), vtysh_rl_callback);
-}
-
static struct thread *vtysh_rl_read_thread;
static void vtysh_rl_read(struct thread *thread)
@@ -752,10 +744,6 @@ int main(int argc, char **argv, char **env)
vtysh_add_timestamp = ts_flag;
- /* Preparation for longjmp() in sigtstp(). */
- sigsetjmp(jmpbuf, 1);
- jmpflag = 1;
-
/* Main command loop. */
vtysh_rl_run();