2018-02-25 06:35:58 +00:00
|
|
|
#include "dict.h"
|
2018-02-22 19:38:27 +00:00
|
|
|
#include "io.h"
|
2018-02-23 17:07:12 +00:00
|
|
|
#include "parser.h"
|
2018-02-25 06:35:58 +00:00
|
|
|
#include "system.h"
|
2018-02-22 19:38:27 +00:00
|
|
|
|
2018-02-23 22:01:52 +00:00
|
|
|
#include <stdlib.h>
|
2018-02-24 03:19:29 +00:00
|
|
|
#include <string.h>
|
2018-02-23 22:01:52 +00:00
|
|
|
|
2018-02-22 19:38:27 +00:00
|
|
|
#ifdef __linux__
|
|
|
|
#include "linux.h"
|
|
|
|
#endif // __linux__
|
|
|
|
|
|
|
|
static char ok[] = "ok.\n";
|
2018-02-25 06:35:58 +00:00
|
|
|
static System sys;
|
2018-02-24 03:19:29 +00:00
|
|
|
|
|
|
|
|
|
|
|
static void
|
2018-02-25 06:35:58 +00:00
|
|
|
write_dstack()
|
2018-02-24 03:19:29 +00:00
|
|
|
{
|
|
|
|
KF_INT tmp;
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrch('<');
|
|
|
|
for (size_t i = 0; i < sys.dstack.size(); i++) {
|
2018-02-24 03:19:29 +00:00
|
|
|
if (i > 0) {
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrch(' ');
|
2018-02-24 03:19:29 +00:00
|
|
|
}
|
|
|
|
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.dstack.get(i, tmp);
|
|
|
|
write_num(sys.interface, tmp);
|
2018-02-24 03:19:29 +00:00
|
|
|
}
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrch('>');
|
2018-02-24 03:19:29 +00:00
|
|
|
}
|
|
|
|
|
2018-02-23 22:01:52 +00:00
|
|
|
static bool
|
2018-02-25 06:35:58 +00:00
|
|
|
parser(const char *buf, const size_t buflen)
|
2018-02-23 22:01:52 +00:00
|
|
|
{
|
|
|
|
static size_t offset = 0;
|
|
|
|
static struct Token token;
|
|
|
|
static PARSE_RESULT result = PARSE_FAIL;
|
2018-02-25 06:35:58 +00:00
|
|
|
static LOOKUP lresult = LOOKUP_FAILED;
|
|
|
|
static bool stop = false;
|
2018-02-23 22:01:52 +00:00
|
|
|
|
|
|
|
offset = 0;
|
|
|
|
|
|
|
|
// reset token
|
|
|
|
token.token = nullptr;
|
|
|
|
token.length = 0;
|
|
|
|
|
|
|
|
while ((result = parse_next(buf, buflen, &offset, &token)) == PARSE_OK) {
|
2018-02-25 06:35:58 +00:00
|
|
|
lresult = lookup(&token, &sys);
|
|
|
|
switch (lresult) {
|
|
|
|
case LOOKUP_OK:
|
|
|
|
continue;
|
|
|
|
case LOOKUP_NOTFOUND:
|
|
|
|
sys.interface->wrln((char *)"word not found", 15);
|
|
|
|
stop = true;
|
|
|
|
break;
|
|
|
|
case LOOKUP_FAILED:
|
|
|
|
sys.interface->wrln((char *)"execution failed", 17);
|
|
|
|
stop = true;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
sys.interface->wrln((char *)"*** the world is broken ***", 27);
|
|
|
|
exit(1);
|
2018-02-24 03:19:29 +00:00
|
|
|
}
|
2018-02-25 06:35:58 +00:00
|
|
|
|
|
|
|
if (stop) {
|
|
|
|
stop = false;
|
|
|
|
break;
|
|
|
|
}
|
2018-02-23 22:01:52 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
switch (result) {
|
2018-02-25 06:35:58 +00:00
|
|
|
case PARSE_OK:
|
|
|
|
return false;
|
2018-02-23 22:01:52 +00:00
|
|
|
case PARSE_EOB:
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrbuf(ok, 4);
|
2018-02-23 22:01:52 +00:00
|
|
|
return true;
|
|
|
|
case PARSE_LEN:
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrln((char *)"parse error: token too long", 27);
|
2018-02-23 22:01:52 +00:00
|
|
|
return false;
|
|
|
|
case PARSE_FAIL:
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrln((char *)"parser failure", 14);
|
2018-02-23 22:01:52 +00:00
|
|
|
return false;
|
|
|
|
default:
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrln((char *)"*** the world is broken ***", 27);
|
2018-02-23 22:01:52 +00:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
}
|
2018-02-22 19:38:27 +00:00
|
|
|
|
|
|
|
static void
|
2018-02-25 06:35:58 +00:00
|
|
|
interpreter()
|
2018-02-22 19:38:27 +00:00
|
|
|
{
|
|
|
|
static size_t buflen = 0;
|
|
|
|
static char linebuf[81];
|
|
|
|
|
|
|
|
while (true) {
|
2018-02-25 06:35:58 +00:00
|
|
|
write_dstack();
|
|
|
|
sys.interface->wrch('\n');
|
|
|
|
sys.interface->wrch('?');
|
|
|
|
sys.interface->wrch(' ');
|
|
|
|
buflen = sys.interface->rdbuf(linebuf, 80, true, '\n');
|
|
|
|
parser(linebuf, buflen);
|
2018-02-22 19:38:27 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
static char banner[] = "kforth interpreter\n";
|
|
|
|
const size_t bannerlen = 19;
|
|
|
|
|
|
|
|
int
|
|
|
|
main(void)
|
|
|
|
{
|
2018-02-27 16:04:17 +00:00
|
|
|
init_dict(&sys);
|
2018-02-22 19:38:27 +00:00
|
|
|
#ifdef __linux__
|
|
|
|
Console interface;
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface = &interface;
|
2018-02-22 19:38:27 +00:00
|
|
|
#endif
|
2018-02-25 06:35:58 +00:00
|
|
|
sys.interface->wrbuf(banner, bannerlen);
|
|
|
|
interpreter();
|
2018-02-22 19:38:27 +00:00
|
|
|
return 0;
|
|
|
|
}
|