From 51381aea436df9c01472242e9e8229a3a94c14af Mon Sep 17 00:00:00 2001 From: ProgramSnail Date: Mon, 17 Feb 2025 19:36:11 +0300 Subject: [PATCH] sm_parser impl beginning --- byterun/include/sm_parser.hpp | 234 +++++++++++++++++++++++++++++++++ byterun/src/compiler.cpp | 226 +------------------------------ byterun/src/module_manager.cpp | 2 - byterun/src/sm_parser.cpp | 36 +++++ 4 files changed, 272 insertions(+), 226 deletions(-) create mode 100644 byterun/include/sm_parser.hpp create mode 100644 byterun/src/sm_parser.cpp diff --git a/byterun/include/sm_parser.hpp b/byterun/include/sm_parser.hpp new file mode 100644 index 000000000..cac4cf9de --- /dev/null +++ b/byterun/include/sm_parser.hpp @@ -0,0 +1,234 @@ +#pragma once + +#include +#include +#include +#include + +enum class Patt { + BOXED, + UNBOXED, + ARRAY, + STRING, + SEXP, + CLOSURE, + STRCMP, +}; + +enum class Opr { + ADD = 0, // + + SUB, // - + MULT, // * + DIV, // / + MOD, // % + LEQ, // <= + LT, // < + GT, // > + GEQ, // >= + EQ, // == + NEQ, // != + AND, // && + OR, // !! + XOR, // ^ (compiler only) + CMP, // cmp (compiler only) + TEST, // test (compiler only) +}; + +struct ValT { + struct Global { + std::string s; + }; + struct Local { + size_t n; + }; + struct Arg { + size_t n; + }; + struct Access { + size_t n; + }; + struct Fun { + std::string s; + }; + + using T = std::variant; + + T val; + + template + requires(not std::is_same_v>) + ValT(U &&x) : val(std::forward(x)) {} + + template bool is() const { + return std::holds_alternative(val); + } + + const T &operator*() const { return val; } + const T &operator->() const { return val; } + + bool operator==(const ValT &other) const = default; +}; + +/* The type for local scopes tree */ +struct Scope { + std::string blab; + std::string elab; + std::vector> names; + std::vector subs; +}; + +// TODO: use bytecode in interpreter represientation instead +/* The type for the stack machine instructions */ +struct SMInstr { + + /* binary operator */ + struct BINOP { + Opr opr; + }; + /* put a constant on the stack */ + struct CONST { + int n; + }; + /* put a string on the stack */ + struct STRING { + std::string str; + }; + /* create an S-expression */ + struct SEXP { + std::string tag; + int n; + }; + /* load a variable to the stack */ + struct LD { + ValT v; + }; + /* load a variable address to the stack */ + struct LDA { + ValT v; + }; + /* store a value into a variable */ + struct ST { + ValT v; + }; + /* store a value into a reference */ + struct STI {}; + /* store a value into array/sexp/string */ + struct STA {}; + /* takes an element of array/string/sexp */ + struct ELEM {}; + /* a label */ + struct LABEL { + std::string s; + }; + /* a forwarded label */ + struct FLABEL { + std::string s; + }; + /* a scope label */ + struct SLABEL { + std::string s; + }; + /* unconditional jump */ + struct JMP { + std::string l; + }; + /* conditional jump */ + struct CJMP { + std::string s; + std::string l; + }; + /* begins procedure definition */ + struct BEGIN { + std::string f; + int nargs; + int nlocals; + std::vector closure; + std::vector args; + std::vector scopes; + }; + /* end procedure definition */ + struct END {}; + /* create a closure */ + struct CLOSURE { + std::string name; + std::vector closure; + }; + /* calls a closure */ + struct CALLC { + int n; + bool tail; + }; + /* calls a function/procedure */ + struct CALL { + std::string fname; + int n; + bool tail; + }; + /* returns from a function */ + struct RET {}; + /* drops the top element off */ + struct DROP {}; + /* duplicates the top element */ + struct DUP {}; + /* swaps two top elements */ + struct SWAP {}; + /* checks the tag and arity of S-expression */ + struct TAG { + std::string tag; + int n; + }; + /* checks the tag and size of array */ + struct ARRAY { + int n; + }; + /* checks various patterns */ + struct PATT { + Patt patt; + }; + /* match failure (location, leave a value */ + struct FAIL { + size_t line; + size_t col; + bool val; + }; + /* external definition */ + struct EXTERN { + std::string name; + }; + /* public definition */ + struct PUBLIC { + std::string name; + }; + /* import clause */ + struct IMPORT { + std::string name; + }; + /* line info */ + struct LINE { + int n; + }; + + using T = std::variant; + + T val; + + template + requires(not std::is_same_v>) + SMInstr(U &&x) : val(std::forward(x)) {} + + template bool is() const { + return std::holds_alternative(val); + } + + const T &operator*() const { return val; } + const T &operator->() const { return val; } + + bool operator==(const SMInstr &other) const = default; +}; + +std::vector parse_sm(std::istream &in); + +std::optional parse_sm(std::string &line); diff --git a/byterun/src/compiler.cpp b/byterun/src/compiler.cpp index 7c7130862..35ae073e9 100644 --- a/byterun/src/compiler.cpp +++ b/byterun/src/compiler.cpp @@ -2,6 +2,8 @@ #include "../../runtime/runtime.h" +#include "sm_parser.hpp" + #include #include #include @@ -137,25 +139,6 @@ struct CompilationMode { OS os; }; -enum class Opr { - ADD = 0, // + - SUB, // - - MULT, // * - DIV, // / - MOD, // % - LEQ, // <= - LT, // < - GT, // > - GEQ, // >= - EQ, // == - NEQ, // != - AND, // && - OR, // !! - XOR, // ^ (compiler only) - CMP, // cmp (compiler only) - TEST, // test (compiler only) -}; - namespace Register { struct Desc { std::string name8; @@ -514,41 +497,6 @@ using Sal1 = Instr::Sal1; using Sar1 = Instr::Sar1; using Repmovsl = Instr::Repmovsl; -struct ValT { - struct Global { - std::string s; - }; - struct Local { - size_t n; - }; - struct Arg { - size_t n; - }; - struct Access { - size_t n; - }; - struct Fun { - std::string s; - }; - - using T = std::variant; - - T val; - - template - requires(not std::is_same_v>) - ValT(U &&x) : val(std::forward(x)) {} - - template bool is() const { - return std::holds_alternative(val); - } - - const T &operator*() const { return val; } - const T &operator->() const { return val; } - - bool operator==(const ValT &other) const = default; -}; - template struct AbstractSymbolicStack { // type 'a t // type 'a symbolic_location = Stack of int | Register of 'a @@ -1710,176 +1658,6 @@ std::vector compile_call(Env &env, return compile_common_call(env, fname, nargs); } -enum class Patt { - BOXED, - UNBOXED, - ARRAY, - STRING, - SEXP, - CLOSURE, - STRCMP, -}; - -/* The type for local scopes tree */ -struct Scope { - std::string blab; - std::string elab; - std::vector> names; - std::vector subs; -}; - -// TODO: use bytecode in interpreter represientation instead -/* The type for the stack machine instructions */ -struct SMInstr { - - /* binary operator */ - struct BINOP { - Opr opr; - }; - /* put a constant on the stack */ - struct CONST { - int n; - }; - /* put a string on the stack */ - struct STRING { - std::string str; - }; - /* create an S-expression */ - struct SEXP { - std::string tag; - int n; - }; - /* load a variable to the stack */ - struct LD { - ValT v; - }; - /* load a variable address to the stack */ - struct LDA { - ValT v; - }; - /* store a value into a variable */ - struct ST { - ValT v; - }; - /* store a value into a reference */ - struct STI {}; - /* store a value into array/sexp/string */ - struct STA {}; - /* takes an element of array/string/sexp */ - struct ELEM {}; - /* a label */ - struct LABEL { - std::string s; - }; - /* a forwarded label */ - struct FLABEL { - std::string s; - }; - /* a scope label */ - struct SLABEL { - std::string s; - }; - /* unconditional jump */ - struct JMP { - std::string l; - }; - /* conditional jump */ - struct CJMP { - std::string s; - std::string l; - }; - /* begins procedure definition */ - struct BEGIN { - std::string f; - int nargs; - int nlocals; - std::vector closure; - std::vector args; - std::vector scopes; - }; - /* end procedure definition */ - struct END {}; - /* create a closure */ - struct CLOSURE { - std::string name; - std::vector closure; - }; - /* calls a closure */ - struct CALLC { - int n; - bool tail; - }; - /* calls a function/procedure */ - struct CALL { - std::string fname; - int n; - bool tail; - }; - /* returns from a function */ - struct RET {}; - /* drops the top element off */ - struct DROP {}; - /* duplicates the top element */ - struct DUP {}; - /* swaps two top elements */ - struct SWAP {}; - /* checks the tag and arity of S-expression */ - struct TAG { - std::string tag; - int n; - }; - /* checks the tag and size of array */ - struct ARRAY { - int n; - }; - /* checks various patterns */ - struct PATT { - Patt patt; - }; - /* match failure (location, leave a value */ - struct FAIL { - size_t line; - size_t col; - bool val; - }; - /* external definition */ - struct EXTERN { - std::string name; - }; - /* public definition */ - struct PUBLIC { - std::string name; - }; - /* import clause */ - struct IMPORT { - std::string name; - }; - /* line info */ - struct LINE { - int n; - }; - - using T = std::variant; - - T val; - - template - requires(not std::is_same_v>) - SMInstr(U &&x) : val(std::forward(x)) {} - - template bool is() const { - return std::holds_alternative(val); - } - - const T &operator*() const { return val; } - const T &operator->() const { return val; } - - bool operator==(const SMInstr &other) const = default; -}; - namespace utils::compile { std::vector stabs_scope(Env &env, const SMInstr::BEGIN &x, diff --git a/byterun/src/module_manager.cpp b/byterun/src/module_manager.cpp index 58010dc2d..188392728 100644 --- a/byterun/src/module_manager.cpp +++ b/byterun/src/module_manager.cpp @@ -1,5 +1,3 @@ -#include -#include extern "C" { #include "module_manager.h" #include "runtime_externs.h" diff --git a/byterun/src/sm_parser.cpp b/byterun/src/sm_parser.cpp new file mode 100644 index 000000000..f173398cb --- /dev/null +++ b/byterun/src/sm_parser.cpp @@ -0,0 +1,36 @@ +#include "sm_parser.hpp" + +#include +#include + +std::vector parse_sm(std::istream &in) { + std::vector result; + + for (size_t i = 1; !in.eof(); ++i) { + if (in.fail()) { + std::cerr << "line " << i << ": input failure"; + break; + } + std::string instr_str; + std::getline(in, instr_str); + auto instr = parse_sm(instr_str); + + if (!instr) { + std::cerr << "line " << i << ": instr parsing failure"; + break; + } + + result.push_back(std::move(instr.value())); + } + + return result; +} + +std::optional> +parse(std::string::iterator begin, std::string::iterator end) { + size_t result = 0; + std::from_chars(&*begin, &*end, result); + // TODO +} + +std::optional parse_sm(const std::string &line) {}