diff options
author | Bad Diode <bd@badd10de.dev> | 2021-10-23 19:47:50 +0200 |
---|---|---|
committer | Bad Diode <bd@badd10de.dev> | 2021-10-23 19:47:50 +0200 |
commit | b271ce1d9098c9057fccdca6eba6b0ee0a5245a2 (patch) | |
tree | e7b5a5f55e317f7ef6cd090eb12edc421f68504a | |
parent | b07ece568d8d62ca80a8ba3b43fb46a98e117d5a (diff) | |
download | bdl-b271ce1d9098c9057fccdca6eba6b0ee0a5245a2.tar.gz bdl-b271ce1d9098c9057fccdca6eba6b0ee0a5245a2.zip |
Change relevant OPs to use list operations
-rwxr-xr-x | src/bytecode/compiler.h | 14 | ||||
-rwxr-xr-x | src/bytecode/objects.h | 1 | ||||
-rwxr-xr-x | src/bytecode/vm.h | 99 |
3 files changed, 65 insertions, 49 deletions
diff --git a/src/bytecode/compiler.h b/src/bytecode/compiler.h index 6f43416..7a25678 100755 --- a/src/bytecode/compiler.h +++ b/src/bytecode/compiler.h | |||
@@ -80,21 +80,15 @@ compile_list_binary_op(Chunk *chunk, Visitor *vs, Token list_start, Ops op) { | |||
80 | .line = list_start.line, | 80 | .line = list_start.line, |
81 | .col = list_start.column, | 81 | .col = list_start.column, |
82 | }); | 82 | }); |
83 | return; | ||
83 | } | 84 | } |
84 | return; | 85 | break; |
85 | } | 86 | } |
86 | parse_tree(chunk, vs); | 87 | parse_tree(chunk, vs); |
87 | n++; | 88 | n++; |
88 | if (n > 1) { | ||
89 | add_code(chunk, op, list_start.line, list_start.column); | ||
90 | } | ||
91 | } | 89 | } |
92 | error_push((Error){ | 90 | emit_constant(chunk, list_start, FIXNUM_VAL(n)); |
93 | .type = ERR_TYPE_COMPILER, | 91 | add_code(chunk, op, list_start.line, list_start.column); |
94 | .value = ERR_NOT_ENOUGH_ARGS, | ||
95 | .line = list_start.line, | ||
96 | .col = list_start.column, | ||
97 | }); | ||
98 | } | 92 | } |
99 | 93 | ||
100 | void | 94 | void |
diff --git a/src/bytecode/objects.h b/src/bytecode/objects.h index a25b0b1..35a954f 100755 --- a/src/bytecode/objects.h +++ b/src/bytecode/objects.h | |||
@@ -50,6 +50,7 @@ void display(Object obj); | |||
50 | #define TRUE_VAL ((Object){.type = OBJ_TYPE_TRUE}) | 50 | #define TRUE_VAL ((Object){.type = OBJ_TYPE_TRUE}) |
51 | #define FALSE_VAL ((Object){.type = OBJ_TYPE_FALSE}) | 51 | #define FALSE_VAL ((Object){.type = OBJ_TYPE_FALSE}) |
52 | #define FIXNUM_VAL(VAL) ((Object){.type = OBJ_TYPE_FIXNUM, .fixnum = VAL}) | 52 | #define FIXNUM_VAL(VAL) ((Object){.type = OBJ_TYPE_FIXNUM, .fixnum = VAL}) |
53 | #define BOOL_VAL(VAL) ((VAL) ? TRUE_VAL : FALSE_VAL) | ||
53 | 54 | ||
54 | // Value extraction. | 55 | // Value extraction. |
55 | #define AS_FIXNUM(VAL) ((VAL).fixnum) | 56 | #define AS_FIXNUM(VAL) ((VAL).fixnum) |
diff --git a/src/bytecode/vm.h b/src/bytecode/vm.h index c94e22b..b3dd8c3 100755 --- a/src/bytecode/vm.h +++ b/src/bytecode/vm.h | |||
@@ -41,41 +41,62 @@ vm_reset(VM *vm) { | |||
41 | } | 41 | } |
42 | 42 | ||
43 | // Helper macros for a more clear VM switch. | 43 | // Helper macros for a more clear VM switch. |
44 | #define FIXNUM_BINARY_OP(OP) \ | 44 | #define WRONG_ARG_ERR() \ |
45 | error_push((Error){ \ | ||
46 | .type = ERR_TYPE_RUNTIME, \ | ||
47 | .value = ERR_WRONG_ARG_TYPE, \ | ||
48 | .line = vm->chunk->lines[vm->pc - vm->chunk->code - 1].line, \ | ||
49 | .col = vm->chunk->lines[vm->pc - vm->chunk->code - 1].col, \ | ||
50 | }) | ||
51 | |||
52 | #define FIXNUM_ARITHMETIC_OP(OP) \ | ||
45 | do { \ | 53 | do { \ |
46 | Object a = array_pop(vm->stack); \ | 54 | ssize_t n = AS_FIXNUM(array_pop(vm->stack)); \ |
47 | Object b = array_pop(vm->stack); \ | 55 | size_t stack_size = array_size(vm->stack) - n; \ |
48 | if (!IS_FIXNUM(a) || !IS_FIXNUM(b)) { \ | 56 | Object obj = array_peek(vm->stack, n - 1); \ |
49 | error_push((Error){ \ | 57 | if (!IS_FIXNUM(obj)) { \ |
50 | .type = ERR_TYPE_RUNTIME, \ | 58 | WRONG_ARG_ERR(); \ |
51 | .value = ERR_WRONG_ARG_TYPE, \ | ||
52 | .line = vm->chunk->lines[vm->pc - vm->chunk->code - 1].line, \ | ||
53 | .col = vm->chunk->lines[vm->pc - vm->chunk->code - 1].col, \ | ||
54 | }); \ | ||
55 | return; \ | 59 | return; \ |
56 | } \ | 60 | } \ |
57 | ssize_t x = AS_FIXNUM(a); \ | 61 | ssize_t acc = AS_FIXNUM(obj); \ |
58 | ssize_t y = AS_FIXNUM(b); \ | 62 | while (n > 1) { \ |
59 | array_push(vm->stack, FIXNUM_VAL(y OP x)); \ | 63 | obj = array_peek(vm->stack, n - 2); \ |
64 | if (!IS_FIXNUM(obj)) { \ | ||
65 | WRONG_ARG_ERR(); \ | ||
66 | return; \ | ||
67 | } \ | ||
68 | ssize_t current = AS_FIXNUM(obj); \ | ||
69 | acc = acc OP current; \ | ||
70 | n--; \ | ||
71 | } \ | ||
72 | array_head(vm->stack)->size = stack_size; \ | ||
73 | array_push(vm->stack, FIXNUM_VAL(acc)); \ | ||
60 | } while (false) | 74 | } while (false) |
61 | 75 | ||
62 | #define FIXNUM_CMP_OP(OP) \ | 76 | #define FIXNUM_COMPARE_OP(OP) \ |
63 | do { \ | 77 | do { \ |
64 | Object a = array_pop(vm->stack); \ | 78 | ssize_t n = AS_FIXNUM(array_pop(vm->stack)); \ |
65 | Object b = array_pop(vm->stack); \ | 79 | size_t stack_size = array_size(vm->stack) - n; \ |
66 | if (!IS_FIXNUM(a) || !IS_FIXNUM(b)) { \ | 80 | Object obj = array_peek(vm->stack, n - 1); \ |
67 | error_push((Error){ \ | 81 | if (!IS_FIXNUM(obj)) { \ |
68 | .type = ERR_TYPE_RUNTIME, \ | 82 | WRONG_ARG_ERR(); \ |
69 | .value = ERR_WRONG_ARG_TYPE, \ | ||
70 | .line = vm->chunk->lines[vm->pc - vm->chunk->code - 1].line, \ | ||
71 | .col = vm->chunk->lines[vm->pc - vm->chunk->code - 1].col, \ | ||
72 | }); \ | ||
73 | return; \ | 83 | return; \ |
74 | } \ | 84 | } \ |
75 | ssize_t x = AS_FIXNUM(a); \ | 85 | ssize_t prev = AS_FIXNUM(obj); \ |
76 | ssize_t y = AS_FIXNUM(b); \ | 86 | bool ret = true; \ |
77 | Object result = y OP x ? TRUE_VAL : FALSE_VAL; \ | 87 | while (n > 1) { \ |
78 | array_push(vm->stack, result); \ | 88 | obj = array_peek(vm->stack, n - 2); \ |
89 | if (!IS_FIXNUM(obj)) { \ | ||
90 | WRONG_ARG_ERR(); \ | ||
91 | return; \ | ||
92 | } \ | ||
93 | ssize_t current = AS_FIXNUM(obj); \ | ||
94 | ret = ret && (prev OP current); \ | ||
95 | prev = current; \ | ||
96 | n--; \ | ||
97 | } \ | ||
98 | array_head(vm->stack)->size = stack_size; \ | ||
99 | array_push(vm->stack, BOOL_VAL(ret)); \ | ||
79 | } while (false) | 100 | } while (false) |
80 | 101 | ||
81 | #define LOGIC_OP(OP) \ | 102 | #define LOGIC_OP(OP) \ |
@@ -121,11 +142,11 @@ vm_interpret(VM *vm, Chunk *chunk) { | |||
121 | Object obj = vm->chunk->constants[constant]; | 142 | Object obj = vm->chunk->constants[constant]; |
122 | array_push(vm->stack, obj); | 143 | array_push(vm->stack, obj); |
123 | } break; | 144 | } break; |
124 | case OP_SUM: { FIXNUM_BINARY_OP(+); } break; | 145 | case OP_SUM: { FIXNUM_ARITHMETIC_OP(+); } break; |
125 | case OP_SUB: { FIXNUM_BINARY_OP(-); } break; | 146 | case OP_SUB: { FIXNUM_ARITHMETIC_OP(-); } break; |
126 | case OP_MUL: { FIXNUM_BINARY_OP(*); } break; | 147 | case OP_MUL: { FIXNUM_ARITHMETIC_OP(*); } break; |
127 | case OP_DIV: { FIXNUM_BINARY_OP(/); } break; | 148 | case OP_DIV: { FIXNUM_ARITHMETIC_OP(/); } break; |
128 | case OP_MOD: { FIXNUM_BINARY_OP(%); } break; | 149 | case OP_MOD: { FIXNUM_ARITHMETIC_OP(%); } break; |
129 | case OP_NOT: { | 150 | case OP_NOT: { |
130 | Object prev = array_pop(vm->stack); | 151 | Object prev = array_pop(vm->stack); |
131 | Object new = IS_TRUE(prev) ? FALSE_VAL : TRUE_VAL; | 152 | Object new = IS_TRUE(prev) ? FALSE_VAL : TRUE_VAL; |
@@ -133,11 +154,11 @@ vm_interpret(VM *vm, Chunk *chunk) { | |||
133 | } break; | 154 | } break; |
134 | case OP_AND: { LOGIC_OP(&&); } break; | 155 | case OP_AND: { LOGIC_OP(&&); } break; |
135 | case OP_OR: { LOGIC_OP(||); } break; | 156 | case OP_OR: { LOGIC_OP(||); } break; |
136 | case OP_EQUAL: { FIXNUM_CMP_OP(==); } break; | 157 | case OP_EQUAL: { FIXNUM_COMPARE_OP(==); } break; |
137 | case OP_LESS: { FIXNUM_CMP_OP(<); } break; | 158 | case OP_LESS: { FIXNUM_COMPARE_OP(<); } break; |
138 | case OP_GREATER: { FIXNUM_CMP_OP(>); } break; | 159 | case OP_GREATER: { FIXNUM_COMPARE_OP(>); } break; |
139 | case OP_LESS_EQUAL: { FIXNUM_CMP_OP(<=); } break; | 160 | case OP_LESS_EQUAL: { FIXNUM_COMPARE_OP(<=); } break; |
140 | case OP_GREATER_EQUAL: { FIXNUM_CMP_OP(>=); } break; | 161 | case OP_GREATER_EQUAL: { FIXNUM_COMPARE_OP(>=); } break; |
141 | case OP_RETURN: { | 162 | case OP_RETURN: { |
142 | display(array_pop(vm->stack)); | 163 | display(array_pop(vm->stack)); |
143 | printf("\n"); | 164 | printf("\n"); |
@@ -163,8 +184,8 @@ vm_interpret(VM *vm, Chunk *chunk) { | |||
163 | }); | 184 | }); |
164 | } | 185 | } |
165 | 186 | ||
166 | #undef FIXNUM_BINARY_OP | 187 | #undef FIXNUM_ARITHMETIC_OP |
167 | #undef FIXNUM_CMP_OP | 188 | #undef FIXNUM_COMPARE_OP |
168 | #undef LOGIC_OP | 189 | #undef LOGIC_OP |
169 | 190 | ||
170 | #endif // BDL_VM_H | 191 | #endif // BDL_VM_H |