-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathvm.h
139 lines (106 loc) · 2.56 KB
/
vm.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
/*
* Implements the Derplang virtual machine
* This includes the mark phase of garbage collection
*/
#pragma once
#include <stdbool.h>
#include <string.h>
#include <stdlib.h>
#include "list.h"
#include "map.h"
#include "debug.h"
#include "object.h"
#include "bytecodes.h"
#include "err.h"
#define VM_STACK_HEIGHT 64
typedef enum {
FN_BYTECODE,
FN_ANON,
FN_NATIVE,
// FN_AST?
} fn_type_t;
typedef struct {
instr* blob;
size_t blob_len;
// is only updated for anonymous fns
size_t argc;
// size_t varc; // number of local variables
} FnBytecode;
typedef struct {
fn_type_t type;
char* name;
size_t argc; // number of parameters
union {
FnBytecode bytecode;
// struct native {
// };
};
} fn_blob_t;
typedef struct {
// NOTE: We might want to be storing some sort of type here in the future
union {
FnBytecode anon_fn;
// TODO:
char* string;
};
} literal_t;
typedef struct {
char* name;
fn_blob_t* fns[4];
size_t fn_c;
literal_t* literals[4];
size_t literal_c;
} file_blob_t;
void file_blob_init(file_blob_t* blob, char* name);
fn_blob_t* file_blob_add_fn(file_blob_t* blob, char* name, fn_type_t type);
literal_t* file_blob_add_literal(file_blob_t* blob);
void file_blob_print(file_blob_t* blob);
typedef enum {
OP_ADD,
OP_SUB,
OP_MUL,
OP_DIV,
OP_CMP_EQ,
OP_CMP_NEQ,
OP_CMP_LT,
OP_CMP_LT_EQ,
OP_CMP_GT,
OP_CMP_GT_EQ,
} Vm_arithmetic_optype;
typedef struct {
size_t return_addr;
fn_blob_t* return_fn;
Map* symbol_table;
} Stack_frame;
typedef struct {
Derp_obj** stack;
int stack_len;
List* call_stack; // list of Stack_frames
Map* func_map;
err_t* err;
int pointer;
// instr* bytecode;
file_blob_t* blob;
// size_t num_bytecodes;
List* std_lib;
} Derp_vm;
typedef err_t* (*Derp_native_fn)(Derp_vm* vm, int argc, Derp_obj** argv);
typedef struct {
char* name;
Derp_native_fn fn;
} Derp_native;
#include "stdlib.h"
void vm_push_int(Derp_vm *vm, int i);
/* allocates and initializes a vm, then returns a pointer to it */
Derp_vm* derp_vm_create();
/* deallocates a vm and all its associated data */
void derp_vm_destroy(Derp_vm *obj);
/* add a function to the Derplang standard library */
void derp_add_native(Derp_vm* vm, char* name, Derp_native_fn fn);
/* call the standard libary function with the given name, with arguments
* coming from the vm's stack */
bool derp_run_native(Derp_vm* vm, char* name, int argc);
/* stop the world, then mark all objects reachable from the current scope */
void vm_gc_mark(Derp_vm *vm);
/* run the vm */
void derp_vm_run(Derp_vm *vm);