-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathFACT_opcodes.h
189 lines (178 loc) · 7.69 KB
/
FACT_opcodes.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
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
/* This file is part of FACT.
*
* FACT is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
n * the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* FACT is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with FACT. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef FACT_OPCODES_H_
#define FACT_OPCODES_H_
/* Furlow VM bytecode instructions. */
typedef enum Furlow_opcode {
ADD = 0, /* Addition. */
AND, /* Bitwise AND. */
APPEND, /* Append a variable to another. */
CALL, /* Push to the call stack and jump to a function. */
CEQ, /* Equal. */
CLE, /* Less than, equal. */
CLT, /* Less than. */
CME, /* More than, equal. */
CMT, /* More than. */
CNE, /* Not equal. */
CONSTS, /* Convert a string to a real and push it. */
CONSTI, /* Push a signed 32 bit integer to the stack. */
CONSTU, /* Push an unsigned 32 bit integer to the stack. */
DEC, /* Decrement a register by 1. */
DEF_N, /* Define a new number in the this scope. */
DEF_S, /* Define a new scope in the this scope. */
DIE, /* Kills a thread. */
DIV, /* Division. */
DROP, /* Drop the first item on the var stack. */
DUP, /* Duplicate the first element on the var stack. */
ELEM, /* Get the element of an array. */
EXIT, /* Like ret, except the ip is left unchanged. */
GLOBAL, /* Make a variable global. */
GOTO, /* Jump to a function but do not push. */
GROUP, /* Group elements on the var stack into an array. */
HALT, /* Halt execution. */
INC, /* Increment a register by 1. */
IOR, /* Bitwise inclusive OR. */
IS_AUTO, /* Checks if a variable is defined locally. */
IS_DEF, /* Checks if a variable is defined globablly. */
JMP, /* Unconditional jump. */
JMP_PNT, /* Push a scope with an address to the var stack. */
JIF, /* Jump on false. */
JIN, /* Jump on type `number'. */
JIS, /* Jump on type `scope'. */
JIT, /* Jump on true. */
LAMBDA, /* Push a lambda scope to the stack. */
LOCK, /* Make a variable immutable. */
MOD, /* Modulo. */
MUL, /* Multiplication. */
NAME, /* Set the name of a scope. */
NEG, /* Negative. */
NEW_N, /* Allocate a num and push it to the var stack. */
NEW_S, /* Allocate a scope and push it to the var stack. */
NOP, /* No operator. */
PURGE, /* Remove all items from the var stack. */
REF, /* Create a reference. */
RET, /* Pop the call stack. */
SET_C, /* Set the jump address of a function. */
SET_F, /* Set the function data of a scope. */
SPRT, /* Create a new thread and unconditionally jump. */
STO, /* Copy one var to the other. */
SUB, /* Subraction. */
SWAP, /* Swap the first two elements on the var stack. */
THIS, /* Push the this scope to the variable stack. */
TRAP_B, /* Push to the trap stack. */
TRAP_E, /* Pop the trap stack. */
USE, /* Push to the call stack. */
VAR, /* Retrieve and push a variable to the stack. */
VA_ADD, /* Add a variable to a scope's var arg list. */
XOR, /* Bitwise exclusive OR. */
} Furlow_opc_t;
static struct {
const char *token; /* String identifier of the instruction. */
enum Furlow_opcode opcode; /* Integer opcode. */
const char *args; /* Type and number of arguments taken.
* r = register (1 byte)
* a = segment address (4 bytes)
* s = string (n bytes null terminated)
*/
} Furlow_instructions[] = {
{ "add" , ADD , "rrr" },
{ "and" , AND , "rrr" },
{ "append" , APPEND , "rr" },
{ "call" , CALL , "r" },
{ "ceq" , CEQ , "rrr" },
{ "cle" , CLE , "rrr" },
{ "clt" , CLT , "rrr" },
{ "cme" , CME , "rrr" },
{ "cmt" , CMT , "rrr" },
{ "cne" , CNE , "rrr" },
{ "consts" , CONSTS , "s" },
{ "consti" , CONSTI , "a" },
{ "constu" , CONSTU , "a" },
{ "dec" , DEC , "r" },
{ "def_n" , DEF_N , "rs" },
{ "def_s" , DEF_S , "rs" },
{ "die" , DIE , "" },
{ "div" , DIV , "rrr" },
{ "drop" , DROP , "" },
{ "dup" , DUP , "" },
{ "elem" , ELEM , "rr" },
{ "exit" , EXIT , "" },
{ "global" , GLOBAL , "rs" },
{ "goto" , GOTO , "r" },
{ "group" , GROUP , "r" },
{ "halt" , HALT , "" },
{ "inc" , INC , "r" },
{ "ior" , IOR , "rrr" },
{ "is_auto" , IS_AUTO , "s" },
{ "is_def" , IS_DEF , "s" },
{ "jmp" , JMP , "a" },
{ "jmp_pnt" , JMP_PNT , "a" },
{ "jif" , JIF , "ra" },
{ "jin" , JIN , "ra" },
{ "jis" , JIS , "ra" },
{ "jit" , JIT , "ra" },
{ "lambda" , LAMBDA , "" },
{ "lock" , LOCK , "r" },
{ "mod" , MOD , "rrr" },
{ "mul" , MUL , "rrr" },
{ "name" , NAME , "rr" },
{ "neg" , NEG , "r" },
{ "new_n" , NEW_N , "r" },
{ "new_s" , NEW_S , "r" },
{ "nop" , NOP , "" },
{ "purge" , PURGE , "" },
{ "ref" , REF , "rr" },
{ "ret" , RET , "" },
{ "set_c" , SET_C , "ra" },
{ "set_f" , SET_F , "rr" },
{ "sprt" , SPRT , "a" },
{ "sto" , STO , "rr" },
{ "sub" , SUB , "rrr" },
{ "swap" , SWAP , "" },
{ "this" , THIS , "" },
{ "trap_b" , TRAP_B , "a" },
{ "trap_e" , TRAP_E , "" },
{ "use" , USE , "r" },
{ "var" , VAR , "s" },
{ "va_add" , VA_ADD , "rr" },
{ "xor" , XOR , "rrr" },
};
#define MAX_INSTRUCTION_LEN 10
#define NUM_FURLOW_INSTRUCTIONS (sizeof (Furlow_instructions) \
/ sizeof (Furlow_instructions[0]))
static int Furlow_get_instruction (char *id)
{
int res;
int low, high, mid;
low = 0;
high = NUM_FURLOW_INSTRUCTIONS - 1;
while (high >= low) {
mid = low + (high - low) / 2;
res = strcmp (id, Furlow_instructions[mid].token);
if (res < 0)
high = mid - 1;
else if (res > 0)
low = mid + 1;
else
goto found;
}
/* No result found. */
return -1;
found:
/* The instruction was found. */
return mid;
}
#endif /* FACT_OPCODES_H_ */