Kernel: Shell now somewhat functions again

I will not be fixing the shell implementation until I get to
userspace
This commit is contained in:
Bananymous 2023-04-05 11:37:41 +03:00
parent 5db4e5b4d5
commit e84f613c4d
2 changed files with 73 additions and 12 deletions

View File

@ -59,6 +59,7 @@ namespace Kernel
{ {
MUST(set_prompt(s_default_prompt)); MUST(set_prompt(s_default_prompt));
MUST(m_buffer.push_back(""sv)); MUST(m_buffer.push_back(""sv));
MUST(Process::current()->set_termios(termios { .canonical = false, .echo = false }));
} }
BAN::ErrorOr<void> Shell::set_prompt(BAN::StringView prompt) BAN::ErrorOr<void> Shell::set_prompt(BAN::StringView prompt)
@ -111,21 +112,83 @@ namespace Kernel
void Shell::run() void Shell::run()
{ {
auto getch = [this] { uint8_t ch; MUST(Process::current()->read(STDIN_FILENO, &ch, 1)); return ch; };
MUST(m_buffer.push_back(""sv));
TTY_PRINT("{}", m_prompt); TTY_PRINT("{}", m_prompt);
BAN::String input;
for (;;) for (;;)
{ {
char buffer[128]; BAN::String& current = m_buffer[m_cursor_pos.line];
size_t n_read = MUST(Process::current()->read(STDIN_FILENO, buffer, sizeof(buffer)));
MUST(input.append(BAN::StringView(buffer, n_read))); uint8_t ch = getch();
if (input.back() == '\n')
if (ch == '\b')
{ {
input.pop_back(); if (!current.empty())
if (auto res = process_command(parse_arguments(input)); res.is_error()) {
TTY_PRINTLN("{}", res.error()); while ((current.back() & 0xC0) == 0x80)
TTY_PRINT("{}", m_prompt); current.pop_back();
input.clear(); current.pop_back();
MUST(Process::current()->write(STDOUT_FILENO, "\b \b", 3));
}
continue;
}
if (ch == '\e')
{
bool handled = false;
if (getch() == '[')
{
handled = true;
switch (getch())
{
case 'A': // Up
if (m_cursor_pos.line > 0)
{
m_cursor_pos.line--;
TTY_PRINT("\e[G{}{}\e[K", m_prompt, m_buffer[m_cursor_pos.line]);
}
break;
case 'B': // Down
if (m_cursor_pos.line < m_buffer.size() - 1)
{
m_cursor_pos.line++;
TTY_PRINT("\e[G{}{}\e[K", m_prompt, m_buffer[m_cursor_pos.line]);
}
break;
case 'C': // Right
break;
case 'D': // Left
break;
default:
handled = false;
}
}
if (!handled)
while (!isalpha(ch))
ch = getch();
continue;
}
MUST(Process::current()->write(STDOUT_FILENO, &ch, 1));
if (ch != '\n')
{
MUST(current.push_back(ch));
continue;
}
if (auto res = process_command(parse_arguments(current)); res.is_error())
TTY_PRINTLN("{}", res.error());
TTY_PRINT("{}", m_prompt);
if (!current.empty())
{
MUST(m_old_buffer.push_back(current));
m_buffer = m_old_buffer;
MUST(m_buffer.push_back(""sv));
m_cursor_pos.line = m_buffer.size() - 1;
} }
} }
} }

View File

@ -22,8 +22,6 @@
#include <kernel/Terminal/TTY.h> #include <kernel/Terminal/TTY.h>
#include <kernel/Terminal/VesaTerminalDriver.h> #include <kernel/Terminal/VesaTerminalDriver.h>
#include <unistd.h>
extern "C" const char g_kernel_cmdline[]; extern "C" const char g_kernel_cmdline[];
struct ParsedCommandLine struct ParsedCommandLine