From: David Kerkeslager Date: Tue, 1 Oct 2019 06:27:35 +0000 (-0400) Subject: Implement and/or, introducing jumps and labels X-Git-Url: https://code.kerkeslager.com/?p=fur;a=commitdiff_plain;h=4efcfd00920263da31dc2bb216050df4041299e7 Implement and/or, introducing jumps and labels --- diff --git a/c_generation.py b/c_generation.py index a1e4e59..821048f 100644 --- a/c_generation.py +++ b/c_generation.py @@ -22,6 +22,9 @@ def generate_integer_argument(argument): assert isinstance(argument, int) return '(int32_t){}'.format(argument) +def generate_label_argument(argument): + return 'LABEL_{}'.format(argument) + def generate_null_argument(argument): assert argument is None return 'NULL' @@ -55,6 +58,8 @@ def generate_argument(instruction): 'gt': generate_null_argument_from(2), 'gte': generate_null_argument_from(2), 'idiv': generate_null_argument_from(2), + 'jump': generate_label_argument, + 'jump_if_false': generate_label_argument, 'lt': generate_null_argument_from(2), 'lte': generate_null_argument_from(2), 'mod': generate_null_argument_from(2), diff --git a/templates/program2.c b/templates/program2.c index ffd014c..180a4c7 100644 --- a/templates/program2.c +++ b/templates/program2.c @@ -174,6 +174,20 @@ void end(struct Thread* thread, Argument argument) { {% include "arithmetic_instruction.c" %} {% endwith %} +void jump(Thread* thread, Argument argument) { + thread->program_counter = argument.label - 1; // We will increment before running +} + +void jump_if_false(Thread* thread, Argument argument) { + assert(!Stack_isEmpty(&(thread->stack))); + Object result = Stack_pop(&(thread->stack)); + assert(result.type == BOOLEAN); + + if(!(result.value.boolean)) { + jump(thread, argument); + } +} + {% with name='lt', operation='<' %} {% include "comparison_instruction.c" %} {% endwith %} @@ -194,7 +208,7 @@ void end(struct Thread* thread, Argument argument) { {% include "comparison_instruction.c" %} {% endwith %} -void neg(struct Thread* thread, Argument argument) { +void neg(Thread* thread, Argument argument) { assert(!Stack_isEmpty(&(thread->stack))); Object result = Stack_pop(&(thread->stack)); assert(result.type == INTEGER); @@ -286,7 +300,7 @@ const Instruction program[] = { int main() { Thread thread; - Thread_initialize(&thread, 0); + Thread_initialize(&thread, LABEL___main__); for(; program[thread.program_counter].instruction != end; thread.program_counter++) { program[thread.program_counter].instruction(