diff options
| Commit | 9a7a8a31e75d1b85274ef46ca29714270062809e (patch) | |
|---|---|---|
| Author | 2018-11-14 19:47:37 +0200 | |
| Committer | 2018-11-14 19:47:37 +0200 | |
| Files | 587a120e78e7c0d50c381d8f38bf0665ed8733a7 /spasm/src/spasm_impl.hpp | |
| IPL-9a7a8a31e75d1b85274ef46ca29714270062809e.tar IPL-9a7a8a31e75d1b85274ef46ca29714270062809e.tar.gz IPL-9a7a8a31e75d1b85274ef46ca29714270062809e.zip | ||
| Parent | 990a8f5e2c2d6e246acfd8b7a99ac1cbf4fb1675 (diff) | |
| Parent | e7c2a14f3e424f1ef1109d7634ece820a058e862 (diff) | |
Merge pull request #45 from SofiaCPP/feature/spasm_improvements
Feature/spasm improvements
1 files changed, 78 insertions, 43 deletions
| -rw-r--r-- | spasm/src/spasm_impl.hpp | 121 |
diff --git a/spasm/src/spasm_impl.hpp b/spasm/src/spasm_impl.hpp index 78c5d08..75fb4c4 100644 --- a/spasm/src/spasm_impl.hpp +++ b/spasm/src/spasm_impl.hpp @@ -3,12 +3,37 @@ #include <iostream> -#include "dstack.hpp" -#include "frames.hpp" #include "types.hpp" namespace SpasmImpl { +enum OpCodes : char +{ + Halt, + Dup, + Pop, + PopTo, + Push, + Alloc, + Print, + Read, + Call, + Ret, + Jump, + JumpT, + JumpF, + Const, + Add, + Sub, + Mul, + Div, + Mod, + Less, + LessEq, + LastIndex = LessEq, +}; +static_assert(LastIndex < 0x3f, "Too many opcodes"); + //! The Abstract Stack Machine /*! ** The machine contains a data stack for operations and control flow and @@ -19,42 +44,48 @@ class Spasm { public: Spasm(); - Spasm(PC_t, + void Initialize(PC_t, const byte*, std::istream& = std::cin, std::ostream& = std::cout); - Spasm(const Spasm&); ~Spasm(); - Spasm& operator=(const Spasm&); + Spasm(const Spasm&) = delete; + Spasm& operator=(const Spasm&) = delete; - void run(); - - const Dstack& get_dstack() const; + enum RunResult { + Success, + Exception, + NotImplemented, + }; + RunResult run(); private: - //! Operations (opcodes) of the machine - static Operation operations[]; - - //! number of operations - static PC_t op_size; - //! Program counter - points the current opcode - PC_t pc; - - //! size of the program bytecode - PC_t bc_size; + PC_t m_PC = 0; + typedef SPVector<byte> ByteCode; //! bytecode of the program - byte* bytecode; + ByteCode m_ByteCode; + + typedef SPVector<data_t> DataStack; + //! stack for storing arguments and local variables + DataStack data_stack; + + //! Stack pointer - always the top of the stack + data_t* m_SP = nullptr; - //! Data stack for arithmetic operations and control flow - Dstack data_stack; + //! Frame pointer - the start of the stack for the current function + data_t* m_FP = nullptr; - //! Return stack for the addresses of the returns - Rstack_t return_stack; + struct Frame { + PC_t ReturnAddress; + PC_t FramePointer; + PC_t StackPointer; + }; - //! Stack for the frame of the functions - FrameStack frame; + typedef std::stack<Frame> FrameStack; + //! Stack for function frames + FrameStack m_Frames; //! Input stream for read () operation std::istream* istr; @@ -62,35 +93,39 @@ class Spasm //! Output stream for print () opertion std::ostream* ostr; - void push(); + void push(reg_t reg); + void pop(reg_t reg); void pop(); void dup(); - void print(); - void read(); + void print(reg_t reg); + void read(reg_t reg); - void plus(); - void minus(); - void multiply(); - void divide(); - void modulus(); + void plus(reg_t a0, reg_t a1, reg_t a2); + void minus(reg_t a0, reg_t a1, reg_t a2); + void multiply(reg_t a0, reg_t a1, reg_t a2); + void divide(reg_t a0, reg_t a1, reg_t a2); + void modulus(reg_t a0, reg_t a1, reg_t a2); - void gotrue(); - void gofalse(); - void go(); + void gotrue(reg_t a0, reg_t a1); + void gofalse(reg_t a0, reg_t a1); + void go(reg_t a0); - void call(); - void ret(); + void call(reg_t a0); + void ret(reg_t a0); void load(); void store(); - void less(); - void lesseq(); + void less(reg_t a0, reg_t a1, reg_t a2); + void lesseq(reg_t a0, reg_t a1, reg_t a2); - // private method for copying and deleting an object - void copybc(const Spasm&); - void deleteobj(); + data_t get_local(reg_t reg); + void set_local(reg_t reg, data_t data); + data_t pop_data(); + void push_data(data_t); + reg_t read_reg(size_t size); + data_t read_number(size_t size); }; } // namespace SpasmImpl |
