merge emitters, add uxn emitter, update c emitter, update simple to use raw ascii for example
This commit is contained in:
parent
b4512f2434
commit
8e430a9d46
|
|
@ -40,14 +40,37 @@ static char* readFile(const char* path) {
|
||||||
return buffer;
|
return buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void print_help() {
|
||||||
|
printf("Usage: undar [options] file...\nOptions:\n\t-emit={c|u}\tEmitter output, currently C source and Uxn binary.\n\n");
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
main(int argc, char **argv)
|
main(int argc, char **argv)
|
||||||
{
|
{
|
||||||
if(argc != 2) return EXIT_FAILURE;
|
if (argc > 1 && (seq(argv[1], "--help") || seq(argv[1], "-h"))) {
|
||||||
|
print_help();
|
||||||
|
return EXIT_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
char* source = readFile(argv[1]);
|
if(argc != 3) {
|
||||||
compile(source);
|
print_help();
|
||||||
|
return EXIT_FAILURE;
|
||||||
|
}
|
||||||
|
|
||||||
|
Emitter e;
|
||||||
|
if (seq(argv[1], "-emit=c")) {
|
||||||
|
e = c_emitter();
|
||||||
|
} else if (seq(argv[1], "-emit=u")) {
|
||||||
|
e = uxn_emitter();
|
||||||
|
} else {
|
||||||
|
printf("unknown emitter type\n");
|
||||||
|
return EXIT_FAILURE;
|
||||||
|
}
|
||||||
|
|
||||||
|
char* source = readFile(argv[2]);
|
||||||
|
compile(e, source);
|
||||||
free(source);
|
free(source);
|
||||||
|
printf("\n");
|
||||||
|
|
||||||
return EXIT_SUCCESS;
|
return EXIT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
10
build
10
build
|
|
@ -10,10 +10,6 @@ if [ -z $MODE ]; then
|
||||||
MODE='debug'
|
MODE='debug'
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if [ -z $EMIT ]; then
|
|
||||||
EMIT='c'
|
|
||||||
fi
|
|
||||||
|
|
||||||
case $ARCH in
|
case $ARCH in
|
||||||
"linux")
|
"linux")
|
||||||
if [ -z $CC ]; then
|
if [ -z $CC ]; then
|
||||||
|
|
@ -27,7 +23,7 @@ esac
|
||||||
|
|
||||||
# setup dirs
|
# setup dirs
|
||||||
SRC_DIR=./arch/$ARCH
|
SRC_DIR=./arch/$ARCH
|
||||||
BUILD_DIR=./out/$EMIT/$ARCH
|
BUILD_DIR=./out/$ARCH
|
||||||
GEN_DIR=$BUILD_DIR/gen
|
GEN_DIR=$BUILD_DIR/gen
|
||||||
TOOL_SRC=tools/file2header.c
|
TOOL_SRC=tools/file2header.c
|
||||||
TOOL_EXE=$BUILD_DIR/file2header
|
TOOL_EXE=$BUILD_DIR/file2header
|
||||||
|
|
@ -85,10 +81,10 @@ ${CC} -c parser.c -o $BUILD_DIR/parser.o $VM_BUILD_FLAGS
|
||||||
# Set up the final build command
|
# Set up the final build command
|
||||||
case $ARCH in
|
case $ARCH in
|
||||||
"linux")
|
"linux")
|
||||||
BUILD_CMD="$CC -o $BUILD_DIR/undar $SRC_DIR/main.c emit/$EMIT/emit.c $LINK_FLAGS $BUILD_DIR/libc.o $BUILD_DIR/list.o $BUILD_DIR/lexer.o $BUILD_DIR/parser.o $BUILD_FLAGS $LINK_FLAGS"
|
BUILD_CMD="$CC -o $BUILD_DIR/undar $SRC_DIR/main.c emit/c/emit.c emit/uxn/emit.c $LINK_FLAGS $BUILD_DIR/libc.o $BUILD_DIR/list.o $BUILD_DIR/lexer.o $BUILD_DIR/parser.o $BUILD_FLAGS $LINK_FLAGS"
|
||||||
;;
|
;;
|
||||||
"web")
|
"web")
|
||||||
BUILD_CMD="$CC $SRC_DIR/main.c emit/$EMIT/emit.c $BUILD_DIR/libc.o $BUILD_DIR/list.o $BUILD_DIR/lexer.o $BUILD_DIR/parser.o -o $BUILD_DIR/undar.html $BUILD_FLAGS $LINK_FLAGS"
|
BUILD_CMD="$CC $SRC_DIR/main.c emit/c/emit.c emit/uxn/emit.c $BUILD_DIR/libc.o $BUILD_DIR/list.o $BUILD_DIR/lexer.o $BUILD_DIR/parser.o -o $BUILD_DIR/undar.html $BUILD_FLAGS $LINK_FLAGS"
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
|
|
||||||
|
|
|
||||||
118
emit.h
118
emit.h
|
|
@ -3,74 +3,72 @@
|
||||||
|
|
||||||
#include "libc.h"
|
#include "libc.h"
|
||||||
|
|
||||||
typedef enum expression_config_e {
|
typedef enum notation_type_e {
|
||||||
PREFIX,
|
PREFIX,
|
||||||
INFIX,
|
INFIX,
|
||||||
POSTFIX
|
POSTFIX
|
||||||
} ExpressionConfig;
|
} NotationType;
|
||||||
|
|
||||||
typedef enum output_config_e {
|
typedef enum output_type_e {
|
||||||
BINARY,
|
BINARY,
|
||||||
TEXT
|
TEXT
|
||||||
} OutputConfig;
|
} OutputType;
|
||||||
|
|
||||||
ExpressionConfig expression_config();
|
typedef void (*VoidArgEmit)();
|
||||||
OutputConfig output_config();
|
typedef void (*StrArgEmit)(const char *str, i32 length);
|
||||||
|
|
||||||
/**
|
typedef struct emitter_s Emitter;
|
||||||
* Prolog is for all of the "setup" boilerplate
|
struct emitter_s {
|
||||||
*/
|
NotationType notation;
|
||||||
void prolog();
|
OutputType output;
|
||||||
|
VoidArgEmit prolog;
|
||||||
|
VoidArgEmit epilogue;
|
||||||
|
VoidArgEmit emit_add;
|
||||||
|
VoidArgEmit emit_sub;
|
||||||
|
VoidArgEmit emit_mul;
|
||||||
|
VoidArgEmit emit_div;
|
||||||
|
VoidArgEmit emit_lt;
|
||||||
|
VoidArgEmit emit_le;
|
||||||
|
VoidArgEmit emit_gt;
|
||||||
|
VoidArgEmit emit_ge;
|
||||||
|
VoidArgEmit emit_ne;
|
||||||
|
VoidArgEmit emit_eq;
|
||||||
|
VoidArgEmit emit_false;
|
||||||
|
VoidArgEmit emit_true;
|
||||||
|
VoidArgEmit emit_nil;
|
||||||
|
VoidArgEmit emit_void;
|
||||||
|
StrArgEmit emit_int;
|
||||||
|
StrArgEmit emit_nat;
|
||||||
|
StrArgEmit emit_real;
|
||||||
|
StrArgEmit emit_byte;
|
||||||
|
StrArgEmit emit_str;
|
||||||
|
VoidArgEmit emit_bool_type;
|
||||||
|
VoidArgEmit emit_byte_type;
|
||||||
|
VoidArgEmit emit_int_type;
|
||||||
|
VoidArgEmit emit_nat_type;
|
||||||
|
VoidArgEmit emit_real_type;
|
||||||
|
VoidArgEmit emit_str_type;
|
||||||
|
VoidArgEmit emit_u8_type;
|
||||||
|
VoidArgEmit emit_i8_type;
|
||||||
|
VoidArgEmit emit_i16_type;
|
||||||
|
VoidArgEmit emit_u16_type;
|
||||||
|
VoidArgEmit emit_i32_type;
|
||||||
|
VoidArgEmit emit_u32_type;
|
||||||
|
VoidArgEmit emit_f32_type;
|
||||||
|
VoidArgEmit emit_array;
|
||||||
|
VoidArgEmit emit_function;
|
||||||
|
VoidArgEmit emit_plex;
|
||||||
|
VoidArgEmit emit_method;
|
||||||
|
VoidArgEmit emit_trait;
|
||||||
|
VoidArgEmit emit_const;
|
||||||
|
VoidArgEmit emit_print;
|
||||||
|
VoidArgEmit emit_neg;
|
||||||
|
VoidArgEmit emit_not;
|
||||||
|
VoidArgEmit emit_open_paren;
|
||||||
|
VoidArgEmit emit_close_paren;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
Emitter c_emitter();
|
||||||
* Prolog is for all of the "cleanup" boilerplate
|
Emitter uxn_emitter();
|
||||||
*/
|
|
||||||
void epilogue();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Emitters
|
|
||||||
*/
|
|
||||||
void emit_add();
|
|
||||||
void emit_sub();
|
|
||||||
void emit_mul();
|
|
||||||
void emit_div();
|
|
||||||
void emit_lt();
|
|
||||||
void emit_le();
|
|
||||||
void emit_gt();
|
|
||||||
void emit_ge();
|
|
||||||
void emit_ne();
|
|
||||||
void emit_eq();
|
|
||||||
void emit_false();
|
|
||||||
void emit_true();
|
|
||||||
void emit_nil();
|
|
||||||
void emit_void();
|
|
||||||
void emit_int(const char *str, i32 length);
|
|
||||||
void emit_nat(const char *str, i32 length);
|
|
||||||
void emit_real(const char *str, i32 length);
|
|
||||||
void emit_str(const char *str, i32 length);
|
|
||||||
void emit_bool_type();
|
|
||||||
void emit_byte_type();
|
|
||||||
void emit_int_type();
|
|
||||||
void emit_nat_type();
|
|
||||||
void emit_real_type();
|
|
||||||
void emit_str_type();
|
|
||||||
void emit_u8_type();
|
|
||||||
void emit_i8_type();
|
|
||||||
void emit_i16_type();
|
|
||||||
void emit_u16_type();
|
|
||||||
void emit_i32_type();
|
|
||||||
void emit_u32_type();
|
|
||||||
void emit_f32_type();
|
|
||||||
void emit_array();
|
|
||||||
void emit_function();
|
|
||||||
void emit_plex();
|
|
||||||
void emit_method();
|
|
||||||
void emit_trait();
|
|
||||||
void emit_const();
|
|
||||||
void emit_print();
|
|
||||||
void emit_neg();
|
|
||||||
void emit_not();
|
|
||||||
void emit_open_paren();
|
|
||||||
void emit_close_paren();
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
164
emit/c/emit.c
164
emit/c/emit.c
|
|
@ -1,258 +1,304 @@
|
||||||
#include "../../emit.h"
|
#include "../../emit.h"
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
ExpressionConfig
|
void
|
||||||
expression_config()
|
c_prolog()
|
||||||
{
|
{
|
||||||
return INFIX;
|
|
||||||
}
|
|
||||||
|
|
||||||
OutputConfig
|
|
||||||
output_config()
|
|
||||||
{
|
|
||||||
return TEXT;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
prolog()
|
c_epilogue()
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
epilogue()
|
c_emit_add()
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_add()
|
|
||||||
{
|
{
|
||||||
printf("+ ");
|
printf("+ ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_sub()
|
c_emit_sub()
|
||||||
{
|
{
|
||||||
printf("- ");
|
printf("- ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_mul()
|
c_emit_mul()
|
||||||
{
|
{
|
||||||
printf("* ");
|
printf("* ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_div()
|
c_emit_div()
|
||||||
{
|
{
|
||||||
printf("/ ");
|
printf("/ ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_lt()
|
c_emit_lt()
|
||||||
{
|
{
|
||||||
printf("< ");
|
printf("< ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_le()
|
c_emit_le()
|
||||||
{
|
{
|
||||||
printf("<= ");
|
printf("<= ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_gt()
|
c_emit_gt()
|
||||||
{
|
{
|
||||||
printf("> ");
|
printf("> ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_ge()
|
c_emit_ge()
|
||||||
{
|
{
|
||||||
printf(">= ");
|
printf(">= ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_ne()
|
c_emit_ne()
|
||||||
{
|
{
|
||||||
printf("!= ");
|
printf("!= ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_eq()
|
c_emit_eq()
|
||||||
{
|
{
|
||||||
printf("== ");
|
printf("== ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_false()
|
c_emit_false()
|
||||||
{
|
{
|
||||||
printf("false ");
|
printf("false ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_true()
|
c_emit_true()
|
||||||
{
|
{
|
||||||
printf("true ");
|
printf("true ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_nil()
|
c_emit_nil()
|
||||||
{
|
{
|
||||||
printf("NULL ");
|
printf("NULL ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_neg()
|
c_emit_neg()
|
||||||
{
|
{
|
||||||
printf("-");
|
printf("-");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_not()
|
c_emit_not()
|
||||||
{
|
{
|
||||||
printf("!");
|
printf("!");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_void()
|
c_emit_void()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_bool_type()
|
c_emit_bool_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_byte_type()
|
c_emit_byte_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_int_type()
|
c_emit_int_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_nat_type()
|
c_emit_nat_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_real_type()
|
c_emit_real_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_str_type()
|
c_emit_str_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_u8_type()
|
c_emit_u8_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_i8_type()
|
c_emit_i8_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_i16_type()
|
c_emit_i16_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_u16_type()
|
c_emit_u16_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_i32_type()
|
c_emit_i32_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_u32_type()
|
c_emit_u32_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_f32_type()
|
c_emit_f32_type()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_int(const char *str, i32 length)
|
c_emit_int(const char *str, i32 length)
|
||||||
{
|
{
|
||||||
printf("%.*s ", length, str);
|
printf("%.*s ", length, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_nat(const char *str, i32 length)
|
c_emit_nat(const char *str, i32 length)
|
||||||
{
|
{
|
||||||
printf("%.*s ", length, str);
|
printf("%.*s ", length, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_real(const char *str, i32 length)
|
c_emit_real(const char *str, i32 length)
|
||||||
{
|
{
|
||||||
printf("%.*s ", length, str);
|
printf("%.*s ", length, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_str(const char *str, i32 length)
|
c_emit_byte(const char *str, i32 length)
|
||||||
{
|
{
|
||||||
printf("%.*s ", length, str);
|
printf("%.*s ", length, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_array()
|
c_emit_str(const char *str, i32 length)
|
||||||
|
{
|
||||||
|
printf("%.*s ", length, str);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
c_emit_array()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_function()
|
c_emit_function()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_plex()
|
c_emit_plex()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_method()
|
c_emit_method()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_trait()
|
c_emit_trait()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_const()
|
c_emit_const()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_print()
|
c_emit_print()
|
||||||
{
|
{
|
||||||
printf("printf(\"%%s\", ");
|
printf("printf(\"%%s\", ");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_open_paren()
|
c_emit_open_paren()
|
||||||
{
|
{
|
||||||
printf("(");
|
printf("(");
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
emit_close_paren()
|
c_emit_close_paren()
|
||||||
{
|
{
|
||||||
printf(")");
|
printf(")");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Emitter
|
||||||
|
c_emitter()
|
||||||
|
{
|
||||||
|
return (Emitter){
|
||||||
|
INFIX,
|
||||||
|
TEXT,
|
||||||
|
c_prolog,
|
||||||
|
c_epilogue,
|
||||||
|
c_emit_add,
|
||||||
|
c_emit_sub,
|
||||||
|
c_emit_mul,
|
||||||
|
c_emit_div,
|
||||||
|
c_emit_lt,
|
||||||
|
c_emit_le,
|
||||||
|
c_emit_gt,
|
||||||
|
c_emit_ge,
|
||||||
|
c_emit_ne,
|
||||||
|
c_emit_eq,
|
||||||
|
c_emit_false,
|
||||||
|
c_emit_true,
|
||||||
|
c_emit_nil,
|
||||||
|
c_emit_void,
|
||||||
|
c_emit_int,
|
||||||
|
c_emit_nat,
|
||||||
|
c_emit_real,
|
||||||
|
c_emit_byte,
|
||||||
|
c_emit_str,
|
||||||
|
c_emit_bool_type,
|
||||||
|
c_emit_byte_type,
|
||||||
|
c_emit_int_type,
|
||||||
|
c_emit_nat_type,
|
||||||
|
c_emit_real_type,
|
||||||
|
c_emit_str_type,
|
||||||
|
c_emit_u8_type,
|
||||||
|
c_emit_i8_type,
|
||||||
|
c_emit_i16_type,
|
||||||
|
c_emit_u16_type,
|
||||||
|
c_emit_i32_type,
|
||||||
|
c_emit_u32_type,
|
||||||
|
c_emit_f32_type,
|
||||||
|
c_emit_array,
|
||||||
|
c_emit_function,
|
||||||
|
c_emit_plex,
|
||||||
|
c_emit_method,
|
||||||
|
c_emit_trait,
|
||||||
|
c_emit_const,
|
||||||
|
c_emit_print,
|
||||||
|
c_emit_neg,
|
||||||
|
c_emit_not,
|
||||||
|
c_emit_open_paren,
|
||||||
|
c_emit_close_paren,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,346 @@
|
||||||
|
#include "../../emit.h"
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
#define UXN_OP_2 (1 << 5)
|
||||||
|
#define UXN_OP_R (1 << 6)
|
||||||
|
#define UXN_OP_K (1 << 7)
|
||||||
|
|
||||||
|
enum uxn_opcode {
|
||||||
|
/* Stack I */ /* Logic */ /* Memory I */ /* Arithmetic*/
|
||||||
|
BRK = 0x00, EQU = 0x08, LDZ = 0x10, ADD = 0x18,
|
||||||
|
INC = 0x01, NEQ = 0x09, STZ = 0x11, SUB = 0x19,
|
||||||
|
POP = 0x02, GTH = 0x0A, LDR = 0x12, MUL = 0x1A,
|
||||||
|
NIP = 0x03, LTH = 0x0B, STR = 0x13, DIV = 0x1B,
|
||||||
|
/* Stack II */ /* Stash */ /* Memory II */ /* Bitwise */
|
||||||
|
SWP = 0x04, JMP = 0x0C, LDA = 0x14, AND = 0x1C,
|
||||||
|
ROT = 0x05, JCN = 0x0D, STA = 0x15, ORA = 0x1D,
|
||||||
|
DUP = 0x06, JSR = 0x0E, DEI = 0x16, EOR = 0x1E,
|
||||||
|
OVR = 0x07, STH = 0x0F, DEO = 0x17, SFT = 0x1F,
|
||||||
|
|
||||||
|
LIT = 0x80, JCI = 0x20, JMI = 0x40, JSI = 0x60,
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
https://rosettacode.org/wiki/Bitwise_operations#Uxntal
|
||||||
|
|
||||||
|
%not { #ff EOR }
|
||||||
|
%and { AND }
|
||||||
|
%or { ORA }
|
||||||
|
%xor { EOR }
|
||||||
|
%shl { #40 SFT SFT }
|
||||||
|
%shr { SFT }
|
||||||
|
%rol { #40 SFT #00 ROT ROT SFT2 ORA }
|
||||||
|
%ror { SWP #00 ROT SFT2 ORA }
|
||||||
|
*/
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_prolog()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_epilogue()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_add()
|
||||||
|
{
|
||||||
|
printf("ADD2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_sub()
|
||||||
|
{
|
||||||
|
printf("SUB2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_mul()
|
||||||
|
{
|
||||||
|
printf("MUL2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_div()
|
||||||
|
{
|
||||||
|
printf("DIV2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_lt()
|
||||||
|
{
|
||||||
|
printf("LTH2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_le()
|
||||||
|
{
|
||||||
|
printf("ROT SWP LTH ?{ LTH #00 EQU JMPr } GTH JMPr ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_gt()
|
||||||
|
{
|
||||||
|
printf("GTH2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_ge()
|
||||||
|
{
|
||||||
|
printf("ROT SWP GTH ?{ GTH #00 EQU JMPr } LTH JMPr ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_ne()
|
||||||
|
{
|
||||||
|
printf("NEQ2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_eq()
|
||||||
|
{
|
||||||
|
printf("EQU2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_false()
|
||||||
|
{
|
||||||
|
printf("#0000 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_true()
|
||||||
|
{
|
||||||
|
printf("#0001 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_nil()
|
||||||
|
{
|
||||||
|
printf("#0000 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_neg()
|
||||||
|
{
|
||||||
|
printf("#0000 SUB2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_not()
|
||||||
|
{
|
||||||
|
printf("#FFFF EOR2 ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_void()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_bool_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_byte_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_int_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_nat_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_real_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_str_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_u8_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_i8_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_i16_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_u16_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_i32_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_u32_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_f32_type()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_int(const char *str, i32 length)
|
||||||
|
{
|
||||||
|
i32 i = (i32)strtol(str, nil, 10);
|
||||||
|
printf("#%04x ", i);
|
||||||
|
USED(length);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_nat(const char *str, i32 length)
|
||||||
|
{
|
||||||
|
u32 i = (u32)strtol(str, nil, 10);
|
||||||
|
printf("#%04x ", i);
|
||||||
|
USED(length);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_real(const char *str, i32 length)
|
||||||
|
{
|
||||||
|
USED(str);
|
||||||
|
USED(length);
|
||||||
|
/// TODO: implement this
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_byte(const char *str, i32 length)
|
||||||
|
{
|
||||||
|
u8 i = (u8)strtol(str, nil, 10);
|
||||||
|
printf("#%04x ", i);
|
||||||
|
USED(length);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_str(const char *str, i32 length)
|
||||||
|
{
|
||||||
|
printf("\"%.*s ", length, str);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_array()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_function()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_plex()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_method()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_trait()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_const()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_print()
|
||||||
|
{
|
||||||
|
printf("#18 DEO ");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
uxn_emit_open_paren()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
void
|
||||||
|
uxn_emit_close_paren()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
Emitter
|
||||||
|
uxn_emitter()
|
||||||
|
{
|
||||||
|
return (Emitter){
|
||||||
|
POSTFIX,
|
||||||
|
BINARY,
|
||||||
|
uxn_prolog,
|
||||||
|
uxn_epilogue,
|
||||||
|
uxn_emit_add,
|
||||||
|
uxn_emit_sub,
|
||||||
|
uxn_emit_mul,
|
||||||
|
uxn_emit_div,
|
||||||
|
uxn_emit_lt,
|
||||||
|
uxn_emit_le,
|
||||||
|
uxn_emit_gt,
|
||||||
|
uxn_emit_ge,
|
||||||
|
uxn_emit_ne,
|
||||||
|
uxn_emit_eq,
|
||||||
|
uxn_emit_false,
|
||||||
|
uxn_emit_true,
|
||||||
|
uxn_emit_nil,
|
||||||
|
uxn_emit_void,
|
||||||
|
uxn_emit_int,
|
||||||
|
uxn_emit_nat,
|
||||||
|
uxn_emit_real,
|
||||||
|
uxn_emit_byte,
|
||||||
|
uxn_emit_str,
|
||||||
|
uxn_emit_bool_type,
|
||||||
|
uxn_emit_byte_type,
|
||||||
|
uxn_emit_int_type,
|
||||||
|
uxn_emit_nat_type,
|
||||||
|
uxn_emit_real_type,
|
||||||
|
uxn_emit_str_type,
|
||||||
|
uxn_emit_u8_type,
|
||||||
|
uxn_emit_i8_type,
|
||||||
|
uxn_emit_i16_type,
|
||||||
|
uxn_emit_u16_type,
|
||||||
|
uxn_emit_i32_type,
|
||||||
|
uxn_emit_u32_type,
|
||||||
|
uxn_emit_f32_type,
|
||||||
|
uxn_emit_array,
|
||||||
|
uxn_emit_function,
|
||||||
|
uxn_emit_plex,
|
||||||
|
uxn_emit_method,
|
||||||
|
uxn_emit_trait,
|
||||||
|
uxn_emit_const,
|
||||||
|
uxn_emit_print,
|
||||||
|
uxn_emit_neg,
|
||||||
|
uxn_emit_not,
|
||||||
|
uxn_emit_open_paren,
|
||||||
|
uxn_emit_close_paren,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
@ -1,257 +0,0 @@
|
||||||
#include "../../emit.h"
|
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
ExpressionConfig
|
|
||||||
expression_config()
|
|
||||||
{
|
|
||||||
return POSTFIX;
|
|
||||||
}
|
|
||||||
|
|
||||||
OutputConfig
|
|
||||||
output_config()
|
|
||||||
{
|
|
||||||
return TEXT;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
prolog()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
epilogue()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_add()
|
|
||||||
{
|
|
||||||
printf("+ ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_sub()
|
|
||||||
{
|
|
||||||
printf("- ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_mul()
|
|
||||||
{
|
|
||||||
printf("* ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_div()
|
|
||||||
{
|
|
||||||
printf("/ ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_lt()
|
|
||||||
{
|
|
||||||
printf("< ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_le()
|
|
||||||
{
|
|
||||||
printf("<= ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_gt()
|
|
||||||
{
|
|
||||||
printf("> ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_ge()
|
|
||||||
{
|
|
||||||
printf(">= ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_ne()
|
|
||||||
{
|
|
||||||
printf("!= ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_eq()
|
|
||||||
{
|
|
||||||
printf("== ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_false()
|
|
||||||
{
|
|
||||||
printf("false ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_true()
|
|
||||||
{
|
|
||||||
printf("true ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_nil()
|
|
||||||
{
|
|
||||||
printf("NULL ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_neg()
|
|
||||||
{
|
|
||||||
printf("-");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_not()
|
|
||||||
{
|
|
||||||
printf("!");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_void()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_bool_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_byte_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_int_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_nat_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_real_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_str_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_u8_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_i8_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_i16_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_u16_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_i32_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_u32_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_f32_type()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_int(const char *str, i32 length)
|
|
||||||
{
|
|
||||||
printf("%.*s ", length, str);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_nat(const char *str, i32 length)
|
|
||||||
{
|
|
||||||
printf("%.*s ", length, str);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_real(const char *str, i32 length)
|
|
||||||
{
|
|
||||||
printf("%.*s ", length, str);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_str(const char *str, i32 length)
|
|
||||||
{
|
|
||||||
printf("%.*s ", length, str);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_array()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_function()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_plex()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_method()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_trait()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_const()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_print()
|
|
||||||
{
|
|
||||||
printf("printf(\"%%s\", ");
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
emit_open_paren()
|
|
||||||
{
|
|
||||||
printf("(");
|
|
||||||
}
|
|
||||||
void
|
|
||||||
emit_close_paren()
|
|
||||||
{
|
|
||||||
printf(")");
|
|
||||||
}
|
|
||||||
5
lexer.c
5
lexer.c
|
|
@ -132,8 +132,9 @@ skip_whitespace()
|
||||||
static TokenType
|
static TokenType
|
||||||
check_keyword(i32 start, i32 length, const char *rest, TokenType type)
|
check_keyword(i32 start, i32 length, const char *rest, TokenType type)
|
||||||
{
|
{
|
||||||
if(lexer.current - lexer.start == start + length &&
|
i32 s1 = lexer.current - lexer.start;
|
||||||
sleq(lexer.start + start, rest, length) == 0) {
|
i32 s2 = start + length;
|
||||||
|
if(s1 == s2 && sleq(lexer.start + start, rest, length)) {
|
||||||
return type;
|
return type;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
96
parser.c
96
parser.c
|
|
@ -1,6 +1,7 @@
|
||||||
#include "parser.h"
|
#include "parser.h"
|
||||||
#include "emit.h"
|
#include "emit.h"
|
||||||
|
|
||||||
|
Emitter emitter;
|
||||||
Parser parser;
|
Parser parser;
|
||||||
|
|
||||||
/****************************************************
|
/****************************************************
|
||||||
|
|
@ -116,43 +117,48 @@ binary()
|
||||||
TokenType operatorType = parser.previous.type;
|
TokenType operatorType = parser.previous.type;
|
||||||
ParseRule *rule = get_rule(operatorType);
|
ParseRule *rule = get_rule(operatorType);
|
||||||
|
|
||||||
|
if (emitter.notation == POSTFIX) {
|
||||||
|
parse_precedence((Precedence)(rule->precedence + 1));
|
||||||
|
}
|
||||||
|
|
||||||
switch(operatorType) {
|
switch(operatorType) {
|
||||||
case TOKEN_BANG_EQ:
|
case TOKEN_BANG_EQ:
|
||||||
emit_ne();
|
emitter.emit_ne();
|
||||||
break;
|
break;
|
||||||
case TOKEN_EQ_EQ:
|
case TOKEN_EQ_EQ:
|
||||||
emit_eq();
|
emitter.emit_eq();
|
||||||
break;
|
break;
|
||||||
case TOKEN_GT:
|
case TOKEN_GT:
|
||||||
emit_ge();
|
emitter.emit_ge();
|
||||||
break;
|
break;
|
||||||
case TOKEN_GTE:
|
case TOKEN_GTE:
|
||||||
emit_ge();
|
emitter.emit_ge();
|
||||||
break;
|
break;
|
||||||
case TOKEN_LT:
|
case TOKEN_LT:
|
||||||
emit_lt();
|
emitter.emit_lt();
|
||||||
break;
|
break;
|
||||||
case TOKEN_LTE:
|
case TOKEN_LTE:
|
||||||
emit_le();
|
emitter.emit_le();
|
||||||
break;
|
break;
|
||||||
case TOKEN_PLUS:
|
case TOKEN_PLUS:
|
||||||
emit_add();
|
emitter.emit_add();
|
||||||
break;
|
break;
|
||||||
case TOKEN_MINUS:
|
case TOKEN_MINUS:
|
||||||
emit_sub();
|
emitter.emit_sub();
|
||||||
break;
|
break;
|
||||||
case TOKEN_STAR:
|
case TOKEN_STAR:
|
||||||
emit_mul();
|
emitter.emit_mul();
|
||||||
break;
|
break;
|
||||||
case TOKEN_SLASH:
|
case TOKEN_SLASH:
|
||||||
emit_div();
|
emitter.emit_div();
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Move to above switch statement for postfix */
|
if (emitter.notation == INFIX) {
|
||||||
parse_precedence((Precedence)(rule->precedence + 1));
|
parse_precedence((Precedence)(rule->precedence + 1));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
|
@ -160,13 +166,13 @@ literal()
|
||||||
{
|
{
|
||||||
switch(parser.previous.type) {
|
switch(parser.previous.type) {
|
||||||
case TOKEN_KEYWORD_FALSE:
|
case TOKEN_KEYWORD_FALSE:
|
||||||
emit_false();
|
emitter.emit_false();
|
||||||
break;
|
break;
|
||||||
case TOKEN_KEYWORD_TRUE:
|
case TOKEN_KEYWORD_TRUE:
|
||||||
emit_true();
|
emitter.emit_true();
|
||||||
break;
|
break;
|
||||||
case TOKEN_KEYWORD_NIL:
|
case TOKEN_KEYWORD_NIL:
|
||||||
emit_nil();
|
emitter.emit_nil();
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return;
|
return;
|
||||||
|
|
@ -183,25 +189,25 @@ static void
|
||||||
declaration()
|
declaration()
|
||||||
{
|
{
|
||||||
if(match(TOKEN_TYPE_INT)) {
|
if(match(TOKEN_TYPE_INT)) {
|
||||||
emit_int_type();
|
emitter.emit_int_type();
|
||||||
} else if(match(TOKEN_TYPE_NAT)) {
|
} else if(match(TOKEN_TYPE_NAT)) {
|
||||||
emit_nat_type();
|
emitter.emit_nat_type();
|
||||||
} else if(match(TOKEN_TYPE_REAL)) {
|
} else if(match(TOKEN_TYPE_REAL)) {
|
||||||
emit_real_type();
|
emitter.emit_real_type();
|
||||||
} else if(match(TOKEN_TYPE_STR)) {
|
} else if(match(TOKEN_TYPE_STR)) {
|
||||||
emit_str_type();
|
emitter.emit_str_type();
|
||||||
} else if(match(TOKEN_TYPE_BOOL)) {
|
} else if(match(TOKEN_TYPE_BOOL)) {
|
||||||
emit_bool_type();
|
emitter.emit_bool_type();
|
||||||
} else if(match(TOKEN_TYPE_BYTE)) {
|
} else if(match(TOKEN_TYPE_BYTE)) {
|
||||||
emit_byte_type();
|
emitter.emit_byte_type();
|
||||||
} else if(match(TOKEN_TYPE_U8)) {
|
} else if(match(TOKEN_TYPE_U8)) {
|
||||||
emit_u8_type();
|
emitter.emit_u8_type();
|
||||||
} else if(match(TOKEN_TYPE_I8)) {
|
} else if(match(TOKEN_TYPE_I8)) {
|
||||||
emit_i8_type();
|
emitter.emit_i8_type();
|
||||||
} else if(match(TOKEN_TYPE_U16)) {
|
} else if(match(TOKEN_TYPE_U16)) {
|
||||||
emit_u16_type();
|
emitter.emit_u16_type();
|
||||||
} else if(match(TOKEN_TYPE_I16)) {
|
} else if(match(TOKEN_TYPE_I16)) {
|
||||||
emit_i16_type();
|
emitter.emit_i16_type();
|
||||||
} else if(match(TOKEN_IDENTIFIER)) {
|
} else if(match(TOKEN_IDENTIFIER)) {
|
||||||
/**
|
/**
|
||||||
* maybe a Plex?
|
* maybe a Plex?
|
||||||
|
|
@ -213,56 +219,67 @@ declaration()
|
||||||
statement();
|
statement();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void print_statement() {
|
||||||
|
expression();
|
||||||
|
consume(TOKEN_SEMICOLON);
|
||||||
|
emitter.emit_print();
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
statement()
|
statement()
|
||||||
{
|
{
|
||||||
if(match(TOKEN_KEYWORD_PRINT))
|
if(match(TOKEN_KEYWORD_PRINT)) {
|
||||||
emit_print();
|
print_statement();
|
||||||
else
|
} else {
|
||||||
expression();
|
expression();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
grouping()
|
grouping()
|
||||||
{
|
{
|
||||||
emit_open_paren();
|
emitter.emit_open_paren();
|
||||||
|
|
||||||
expression();
|
expression();
|
||||||
|
|
||||||
emit_close_paren();
|
emitter.emit_close_paren();
|
||||||
consume(TOKEN_RPAREN);
|
consume(TOKEN_RPAREN);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
number()
|
number()
|
||||||
{
|
{
|
||||||
emit_int(parser.previous.start, parser.previous.length);
|
emitter.emit_int(parser.previous.start, parser.previous.length);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
string()
|
string()
|
||||||
{
|
{
|
||||||
emit_str(parser.previous.start, parser.previous.length);
|
emitter.emit_str(parser.previous.start, parser.previous.length);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
unary()
|
unary()
|
||||||
{
|
{
|
||||||
TokenType operatorType = parser.previous.type;
|
TokenType operatorType = parser.previous.type;
|
||||||
|
if (emitter.notation == POSTFIX) {
|
||||||
|
parse_precedence(PREC_UNARY);
|
||||||
|
}
|
||||||
|
|
||||||
switch(operatorType) {
|
switch(operatorType) {
|
||||||
case TOKEN_MINUS:
|
case TOKEN_MINUS:
|
||||||
emit_neg();
|
emitter.emit_neg();
|
||||||
break;
|
break;
|
||||||
case TOKEN_BANG:
|
case TOKEN_BANG:
|
||||||
emit_not();
|
emitter.emit_not();
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Move to above switch statement for postfix */
|
if (emitter.notation == INFIX) {
|
||||||
parse_precedence(PREC_UNARY);
|
parse_precedence(PREC_UNARY);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ParseRule rules[] = {
|
ParseRule rules[] = {
|
||||||
|
|
@ -375,16 +392,17 @@ get_rule(TokenType type)
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
compile(char *source)
|
compile(Emitter e, char *source)
|
||||||
{
|
{
|
||||||
|
emitter = e;
|
||||||
init_lexer(source);
|
init_lexer(source);
|
||||||
advance();
|
advance();
|
||||||
|
|
||||||
prolog();
|
emitter.prolog();
|
||||||
|
|
||||||
while(!match(TOKEN_EOF)) declaration();
|
while(!match(TOKEN_EOF)) declaration();
|
||||||
|
|
||||||
epilogue();
|
emitter.epilogue();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
5
parser.h
5
parser.h
|
|
@ -79,9 +79,6 @@ struct parser_s {
|
||||||
Token previous;
|
Token previous;
|
||||||
};
|
};
|
||||||
|
|
||||||
bool compile(char *source);
|
bool compile(Emitter e, char *source);
|
||||||
|
|
||||||
extern void emit_return();
|
|
||||||
extern void emit_constant();
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
||||||
|
|
@ -1 +1 @@
|
||||||
print((1.0 + 1.0) as str);
|
print((122 - 32)); // prints ascii `Z`
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue