| |
| #ifndef Forth_DEFINED |
| #define Forth_DEFINED |
| |
| #include "SkTypes.h" |
| |
| class ForthOutput { |
| public: |
| virtual void show(const char output[]) = 0; |
| }; |
| |
| union FloatIntDual { |
| int32_t fInt; |
| float fFloat; |
| }; |
| |
| static inline int32_t f2i_bits(float x) { |
| FloatIntDual d; |
| d.fFloat = x; |
| return d.fInt; |
| } |
| |
| static inline float i2f_bits(int32_t x) { |
| FloatIntDual d; |
| d.fInt = x; |
| return d.fFloat; |
| } |
| |
| class ForthEngine { |
| public: |
| ForthEngine(ForthOutput*); |
| ~ForthEngine(); |
| |
| int depth() const { return fStackStop - fStackCurr; } |
| void clearStack() { fStackCurr = fStackStop; } |
| |
| void push(intptr_t value); |
| intptr_t top() const { return this->peek(0); } |
| intptr_t peek(size_t index) const; |
| void setTop(intptr_t value); |
| intptr_t pop(); |
| |
| void fpush(float value) { this->push(f2i_bits(value)); } |
| float fpeek(size_t i) const { return i2f_bits(this->fpeek(i)); } |
| float ftop() const { return i2f_bits(this->top()); } |
| void fsetTop(float value) { this->setTop(f2i_bits(value)); } |
| float fpop() { return i2f_bits(this->pop()); } |
| |
| void sendOutput(const char text[]); |
| |
| private: |
| ForthOutput* fOutput; |
| intptr_t* fStackBase; |
| intptr_t* fStackCurr; |
| intptr_t* fStackStop; |
| |
| void signal_error(const char msg[]) const { |
| SkDebugf("ForthEngine error: %s\n", msg); |
| } |
| }; |
| |
| struct ForthCallBlock { |
| const intptr_t* in_data; |
| size_t in_count; |
| intptr_t* out_data; |
| size_t out_count; |
| size_t out_depth; |
| }; |
| |
| class ForthWord { |
| public: |
| virtual ~ForthWord() {} |
| virtual void exec(ForthEngine*) = 0; |
| |
| // todo: return error state of the engine |
| void call(ForthCallBlock*); |
| }; |
| |
| class ForthEnv { |
| public: |
| ForthEnv(); |
| ~ForthEnv(); |
| |
| |
| void addWord(const char name[], ForthWord*); |
| |
| void parse(const char code[]); |
| |
| ForthWord* findWord(const char name[]); |
| |
| void run(ForthOutput* = NULL); |
| |
| private: |
| class Impl; |
| Impl* fImpl; |
| }; |
| |
| #endif |
| |