moka/lib/prog.c

82 lines
1.8 KiB
C

#include "prog.h"
MK_ENUM_C(OpcodeKind, OPCODE_KIND);
void prog_init(struct prog* self)
{
assert(self);
vec_init(&self->instructions);
vec_init(&self->values);
self->stack_addr = 0;
}
void prog_free(struct prog* self)
{
assert(self);
vec_free_elements(&self->instructions, NULL);
vec_free(&self->instructions);
vec_free_elements(&self->values, (void*) value_free);
vec_free(&self->values);
}
size_t prog_add_instruction(struct prog* self,
OpcodeKind opcode,
ssize_t param)
{
assert(self);
struct instruction* instr = malloc(sizeof(struct instruction));
instr->opcode = opcode;
instr->param = param;
vec_push(&self->instructions, instr);
switch (opcode)
{
case OP_CALL:
case OP_GLOBAL_LOAD:
case OP_LOCAL_LOAD:
case OP_PUSH: {
self->stack_addr++;
} break;
case OP_MAKE_ARRAY: {
self->stack_addr += param;
} break;
default: {
fprintf(stderr, "cannot find stack address of <%s>\n",
OpcodeKindStr[opcode]);
abort();
} break;
}
return self->instructions.size - 1;
}
size_t prog_add_new_value(struct prog* self,
struct value* value)
{
assert(self);
assert(value);
vec_push(&self->values, value);
return self->values.size - 1;
}
void prog_dump(struct prog* self)
{
assert(self);
printf("--- PROG ---\n");
for (size_t i=0; i<self->instructions.size; i++)
{
struct instruction const* instr = self->instructions.data[i];
printf("%zu\t%s %zd\n",
i,
OpcodeKindStr[instr->opcode],
instr->param);
}
}