diff --git a/alee.cpp b/alee.cpp index b2d8fd0..633b8d7 100644 --- a/alee.cpp +++ b/alee.cpp @@ -30,11 +30,12 @@ static void readchar(State& state); static void parseLine(Parser&, State&, const std::string&); static void parseFile(Parser&, State&, std::istream&); +static Parser parser; + int main(int argc, char *argv[]) { MemDict dict; State state (dict, readchar); - Parser parser; dict.initialize(); @@ -80,6 +81,7 @@ static void load(State& state) state.dict.writebyte(i++, file.get()); } +#include void user_sys(State& state) { char buf[32] = {0}; @@ -107,6 +109,17 @@ void user_sys(State& state) std::cout << buf << ' '; } break; + case 5: // eval + { + auto oldip = state.ip; + std::jmp_buf oldjb; + memcpy(oldjb, state.jmpbuf, sizeof(std::jmp_buf)); + state.ip = 0; + parser.parseSource(state); + memcpy(state.jmpbuf, oldjb, sizeof(std::jmp_buf)); + state.ip = oldip; + } + break; } } diff --git a/core.fth b/core.fth index 1d9a10a..2d769c2 100644 --- a/core.fth +++ b/core.fth @@ -25,7 +25,8 @@ : imm _latest @ dup @ 1 5 << | swap ! ; : immediate imm ; : state 3 cells ; -: >in 4 cells ; +: _source 4 cells ; +: >in 5 cells ; : , here ! 1 cells allot ; @@ -138,10 +139,11 @@ : min 2dup <= if drop else nip then ; : max 2dup <= if nip else drop then ; -: key >in @ 5 cells + +: source _source @ 0 begin 2dup + c@ while char+ repeat ; +: key _source @ >in @ + begin dup c@ 0 = while _in repeat c@ 1 >in +! ; -: key? >in @ 5 cells + c@ 0 <> ; +: key? _source @ >in @ + c@ 0 <> ; : word here dup >r char+ >r begin key? if key 2dup <> else 0 0 then while r> tuck c! char+ >r repeat @@ -151,7 +153,7 @@ : [char] char postpone literal ; imm : ( begin [char] ) key <> while repeat ; imm -: \ >in @ 5 cells + +: \ _source @ >in @ + begin dup c@ while 0 over c! char+ repeat drop ; imm : type begin dup 0 > while swap dup c@ emit char+ swap 1- repeat 2drop ; @@ -199,8 +201,6 @@ -1 constant true 0 constant false -: source >in cell+ 0 begin 2dup + c@ while char+ repeat ; - : quit begin _rdepth 1 > while r> drop repeat postpone [ ; : abort begin depth 0 > while drop repeat quit ; : abort" postpone s" ['] rot , @@ -231,3 +231,7 @@ : marker create _latest @ , here , does> dup @ _latest ! cell+ @ here swap - allot ; : :noname 0 , here ] ; + +: evaluate _source @ >r >in @ >r + 0 >in ! _source ! 5 sys + r> >in ! r> _source ! ; diff --git a/dictionary.cpp b/dictionary.cpp index ff80957..6432607 100644 --- a/dictionary.cpp +++ b/dictionary.cpp @@ -27,6 +27,7 @@ void Dictionary::initialize() write(Here, Begin); write(Latest, Begin); write(Compiling, 0); + write(Source, Input + sizeof(Cell)); } Addr Dictionary::allot(Cell amount) noexcept @@ -95,10 +96,11 @@ Addr Dictionary::getexec(Addr addr) noexcept Word Dictionary::input() noexcept { auto idx = read(Dictionary::Input); - auto ch = readbyte(Dictionary::Input + sizeof(Cell) + idx); + auto src = read(Dictionary::Source); + auto ch = readbyte(src + idx); if (ch) { - Addr wordstart = Dictionary::Input + sizeof(Cell) + idx; + Addr wordstart = src + idx; Addr wordend = wordstart; do { diff --git a/dictionary.hpp b/dictionary.hpp index dbf1dcc..20ac7e4 100644 --- a/dictionary.hpp +++ b/dictionary.hpp @@ -31,9 +31,10 @@ public: constexpr static Addr Here = sizeof(Cell); constexpr static Addr Latest = sizeof(Cell) * 2; constexpr static Addr Compiling = sizeof(Cell) * 3; - constexpr static Addr Input = sizeof(Cell) * 4; // len data... + constexpr static Addr Source = sizeof(Cell) * 4; + constexpr static Addr Input = sizeof(Cell) * 5; // len data... constexpr static Addr InputCells = 82; // bytes! - constexpr static Addr Begin = sizeof(Cell) * 5 + InputCells; + constexpr static Addr Begin = sizeof(Cell) * 6 + InputCells; void initialize(); diff --git a/parser.hpp b/parser.hpp index 5bcf3f9..4b14d64 100644 --- a/parser.hpp +++ b/parser.hpp @@ -29,9 +29,9 @@ public: constexpr static int UnknownWord = -1; int parse(State&, const char *); + int parseSource(State&); private: - int parseSource(State&); int parseWord(State&, Word); int parseNumber(State&, Word); };