58e0de7ae1
Co-authored-by: aider (openrouter/moonshotai/kimi-k2.6) <aider@aider.chat>
175 lines
3.8 KiB
C
175 lines
3.8 KiB
C
#ifndef FORTH_H
|
|
#define FORTH_H
|
|
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
#include <ctype.h>
|
|
#include <stdint.h>
|
|
#include <inttypes.h>
|
|
|
|
// Configuration
|
|
#define DATA_STACK_SIZE 256
|
|
#define RET_STACK_SIZE 256
|
|
#define DICT_SIZE 256
|
|
#define BODY_SIZE 1024
|
|
#define COMPILE_BUF_SIZE 1024
|
|
#define INPUT_BUF_SIZE 256
|
|
#define MAX_NAME_LEN 31
|
|
#define COMPILE_STACK_SIZE 256
|
|
#define USER_MEMORY_SIZE 1024
|
|
|
|
// Core types
|
|
typedef struct Word Word;
|
|
typedef union Cell {
|
|
Word* word;
|
|
int32_t num;
|
|
union Cell* cell_ptr; // Use union tag here, as typedef Cell is not available yet
|
|
} Cell;
|
|
|
|
struct Word {
|
|
Word* prev;
|
|
uint8_t flags; // Bit7=immediate, Bit6=hidden, Bits0-5=name length
|
|
char name[MAX_NAME_LEN + 1];
|
|
void (*code)(Word*);
|
|
Cell* body;
|
|
};
|
|
|
|
// Globals
|
|
extern int32_t data_stack[DATA_STACK_SIZE];
|
|
extern int sp;
|
|
extern Cell ret_stack[RET_STACK_SIZE];
|
|
extern int rp;
|
|
extern Cell* ip;
|
|
|
|
extern Word dict[DICT_SIZE];
|
|
extern int dict_idx;
|
|
extern Word* dict_head;
|
|
extern Cell dict_bodies[BODY_SIZE];
|
|
extern int body_idx;
|
|
|
|
extern int state; // 0=interpret, 1=compile
|
|
extern Cell compile_buf[COMPILE_BUF_SIZE];
|
|
extern int compile_idx;
|
|
extern char compiling_name[MAX_NAME_LEN + 1];
|
|
|
|
extern char input_buf[INPUT_BUF_SIZE];
|
|
extern char* input_ptr;
|
|
|
|
extern Cell* compile_stack[COMPILE_STACK_SIZE];
|
|
extern int compile_sp;
|
|
|
|
extern int32_t user_mem[USER_MEMORY_SIZE];
|
|
extern int32_t* here;
|
|
|
|
// Core function prototypes
|
|
void data_push(int32_t val);
|
|
int32_t data_pop(void);
|
|
void ret_push_ip(Cell* val);
|
|
Cell* ret_pop_ip(void);
|
|
void ret_push_num(int32_t val);
|
|
int32_t ret_pop_num(void);
|
|
void compile_push(Cell* addr);
|
|
Cell* compile_pop(void);
|
|
|
|
Word* add_primitive(const char* name, void (*code)(Word*), uint8_t flags);
|
|
Word* lookup_word(const char* name);
|
|
Word* lookup_word_internal(const char* name);
|
|
|
|
char* next_token(void);
|
|
|
|
void inner_interpreter(void);
|
|
void process_token(const char* token);
|
|
void outer_interpreter(void);
|
|
|
|
// Primitive word prototypes
|
|
// Stack ops
|
|
void do_dup(Word* w);
|
|
void do_drop(Word* w);
|
|
void do_swap(Word* w);
|
|
void do_over(Word* w);
|
|
void do_rot(Word* w);
|
|
void do_minus_rot(Word* w);
|
|
void do_nip(Word* w);
|
|
void do_tuck(Word* w);
|
|
|
|
// Arithmetic
|
|
void do_add(Word* w);
|
|
void do_sub(Word* w);
|
|
void do_mul(Word* w);
|
|
void do_div(Word* w);
|
|
void do_mod(Word* w);
|
|
void do_slash_mod(Word* w);
|
|
void do_one_plus(Word* w);
|
|
void do_one_minus(Word* w);
|
|
void do_two_plus(Word* w);
|
|
void do_two_minus(Word* w);
|
|
void do_negate(Word* w);
|
|
void do_abs(Word* w);
|
|
void do_min(Word* w);
|
|
void do_max(Word* w);
|
|
|
|
// Logic
|
|
void do_and(Word* w);
|
|
void do_or(Word* w);
|
|
void do_xor(Word* w);
|
|
void do_invert(Word* w);
|
|
void do_lshift(Word* w);
|
|
void do_rshift(Word* w);
|
|
|
|
// Comparison
|
|
void do_eq(Word* w);
|
|
void do_neq(Word* w);
|
|
void do_lt(Word* w);
|
|
void do_gt(Word* w);
|
|
void do_lte(Word* w);
|
|
void do_gte(Word* w);
|
|
void do_zero_eq(Word* w);
|
|
void do_zero_lt(Word* w);
|
|
void do_zero_gt(Word* w);
|
|
|
|
// I/O
|
|
void do_dot(Word* w);
|
|
void do_cr(Word* w);
|
|
void do_emit(Word* w);
|
|
void do_key(Word* w);
|
|
void do_dot_quote(Word* w);
|
|
void do_dot_quote_inner(Word* w);
|
|
void do_words(Word* w);
|
|
|
|
// Memory
|
|
void do_fetch(Word* w);
|
|
void do_store(Word* w);
|
|
void do_plus_store(Word* w);
|
|
void do_cfetch(Word* w);
|
|
void do_cstore(Word* w);
|
|
void do_variable(Word* w);
|
|
void do_constant(Word* w);
|
|
void do_do_var(Word* w);
|
|
void do_do_const(Word* w);
|
|
void do_here(Word* w);
|
|
void do_allot(Word* w);
|
|
|
|
// Return stack
|
|
void do_to_r(Word* w);
|
|
void do_r_from(Word* w);
|
|
void do_r_fetch(Word* w);
|
|
|
|
// Control flow
|
|
void do_exit(Word* w);
|
|
void do_docolon(Word* w);
|
|
void do_lit(Word* w);
|
|
void do_colon(Word* w);
|
|
void do_semicolon(Word* w);
|
|
void do_branch(Word* w);
|
|
void do_zero_branch(Word* w);
|
|
void do_if(Word* w);
|
|
void do_else(Word* w);
|
|
void do_then(Word* w);
|
|
void do_begin(Word* w);
|
|
void do_until(Word* w);
|
|
void do_while(Word* w);
|
|
void do_repeat(Word* w);
|
|
|
|
#endif // FORTH_H
|