From a46ccd3ebd191c1b685b3c4e0f4c8802631303e1 Mon Sep 17 00:00:00 2001 From: Jakob Kaivo Date: Sat, 1 Apr 2023 20:41:59 -0400 Subject: integrate interactive command editing --- shed.c | 65 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 65 insertions(+) create mode 100644 shed.c (limited to 'shed.c') diff --git a/shed.c b/shed.c new file mode 100644 index 0000000..a0cc554 --- /dev/null +++ b/shed.c @@ -0,0 +1,65 @@ +#define _POSIX_C_SOURCE 200809L +#include +#include +#include +#include +#include "shed.h" + +/* + * BIG FAT TODO: DEAL WITH MULTIBYTE CHARACTERS CORRECTLY + */ + +struct shed *shed(struct shed *e) +{ + if (e == NULL) { + e = calloc(1, sizeof(*e)); + if (e == NULL) { + return NULL; + } + } + + /* TODO: head/tail/history */ + if (e->cur == NULL) { + e->cur = calloc(1, sizeof(*e->cur)); + if (e->cur == NULL) { + return e; + } + e->handle = shed_handle_non_vi; + } + + memset(e->cur, '\0', sizeof(*e->cur)); + + struct termios original_tio; + if (tcgetattr(STDIN_FILENO, &original_tio) != 0) { + e->cur = NULL; + return e; + } + + struct termios tio = original_tio; + tio.c_iflag &= ~BRKINT; + tio.c_lflag &= ~ECHO; + tio.c_lflag &= ~IEXTEN; + tio.c_lflag &= ~ICANON; + tio.c_lflag &= ~ISIG; + tcsetattr(STDIN_FILENO, TCSADRAIN, &tio); + + if (e->prompt == NULL) { + e->prompt = getenv("PS1"); + if (e->prompt == NULL) { + e->prompt = "$ "; + } + } + write(STDOUT_FILENO, e->prompt, strlen(e->prompt)); + + char c; + do { + if (read(STDIN_FILENO, &c, 1) == -1) { + //b.nread = -1; + /* TODO: signal failure */ + break; + } + } while (e->handle(e, &tio, c)); + + tcsetattr(STDIN_FILENO, TCSADRAIN, &original_tio); + return e; +} -- cgit v1.2.1