From fb639962a5b5e14157e558d737e97185c6b0bad7 Mon Sep 17 00:00:00 2001 From: Lephenixnoir Date: Thu, 8 Dec 2022 22:51:34 +0100 Subject: [PATCH] shell: provide parser with expr_or_range() function --- shell/d.cpp | 13 +++++++++++-- shell/parser.cpp | 40 +++++++++++++++++++++------------------- shell/parser.h | 5 ++++- 3 files changed, 36 insertions(+), 22 deletions(-) diff --git a/shell/d.cpp b/shell/d.cpp index 79aacb6..d293b51 100644 --- a/shell/d.cpp +++ b/shell/d.cpp @@ -75,8 +75,17 @@ static uint32_t parse_d(Session &session, Parser &parser) return 0; uint32_t address = session.current_space->cursor; - if(!parser.at_end()) - address = parser.expr(session.current_space); + if(!parser.at_end()) { + auto v = parser.expr_or_range(session.current_space); + + if(std::holds_alternative(v)) { + address = std::get(v); + } + else { + // TODO: Use an args struct etc. This is placeholder. + address = std::get(v).start; + } + } parser.end(); return address; diff --git a/shell/parser.cpp b/shell/parser.cpp index 1fa09a2..c826ca2 100644 --- a/shell/parser.cpp +++ b/shell/parser.cpp @@ -142,24 +142,7 @@ void Parser::dump_command() { while(!at_end()) { Token t = m_la; - - if(t.type == T::NUM) - fmt::print("NUM {:#x}\n", t.value.NUM); - else if(t.type == T::SYSCALL) - fmt::print("SYSCALL %{:04x}\n", t.value.NUM); - else if(t.type == T::SYMBOL) - fmt::print("SYMBOL '{}'\n", t.value.STRING); - else if(t.type == T::OPTION) - fmt::print("OPTION '{}'\n", t.value.STRING); - else if(t.type == T::STRING) - fmt::print("STRING '{}'\n", t.value.STRING); - else if(t.type == '>') - fmt::print(">>\n"); - else if(t.type == '<') - fmt::print("<<\n"); - else - fmt::print("{}\n", (char)t.type); - + fmt::print("{}\n", t.str()); feed(); } } @@ -246,7 +229,7 @@ Range Parser::range(VirtualSpace *space, long before, long after) { long start = expr(space); - /* Accept non-rangs if (before) and (after) are provided */ + /* Accept non-ranges if (before) and (after) are provided */ if(m_la.type != ':' && m_la.type != '.' && before >= 0 && after >= 0) return {start - before, start + after}; @@ -259,6 +242,25 @@ Range Parser::range(VirtualSpace *space, long before, long after) return r; } +std::variant Parser::expr_or_range(VirtualSpace *space) +{ + long start = expr(space); + + if(m_la.type == ':') { + expect(':'); + long length = expr(space); + return (Range){start, start + length}; + } + else if(m_la.type == '.') { + expect('.'); + long end = expr(space); + return (Range){start, end}; + } + else { + return (long)start; + } +} + FxOS::MemoryRegion Parser::region(VirtualSpace *space, long before, long after) { if(m_la.type == '$' || m_la.type == '(' || m_la.type == '-' diff --git a/shell/parser.h b/shell/parser.h index 9de9771..693df9f 100644 --- a/shell/parser.h +++ b/shell/parser.h @@ -12,6 +12,7 @@ #include #include #include +#include #include #include @@ -144,8 +145,10 @@ public: long expr(VirtualSpace *space); /* Read a range; again $ and symbols are interpreted. If (before) and (after) are both specified, a single value will also be accepted, and - the range [value+before, value.after) will be returned. */ + the range [value-before, value+after) will be returned. */ Range range(VirtualSpace *space, long before=-1, long after=-1); + /* Read an expression or a range */ + std::variant expr_or_range(VirtualSpace *space); /* Read a memory region (allows both ranges and symbolic names) */ FxOS::MemoryRegion region(VirtualSpace *space, long before=-1, long after=-1);