1
/* Nitfol - z-machine interpreter using Glk for output.
2
Copyright (C) 1999 Evin Robertson
4
This program is free software; you can redistribute it and/or modify
5
it under the terms of the GNU General Public License as published by
6
the Free Software Foundation; either version 2 of the License, or
7
(at your option) any later version.
9
This program is distributed in the hope that it will be useful,
10
but WITHOUT ANY WARRANTY; without even the implied warranty of
11
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
GNU General Public License for more details.
14
You should have received a copy of the GNU General Public License
15
along with this program; if not, write to the Free Software
16
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA.
18
The author can be reached at nitfol@deja.com
22
static void op_nop(void) { ; }
24
static void op_XXX(void)
26
zbyte ins = HIBYTE(oldPC);
27
n_show_error(E_INSTR, "illegal instruction", ins);
32
/* offsets in opcodetable for various types */
33
#define OFFSET_0OP 0x00
34
#define OFFSET_1OP 0x10
35
#define OFFSET_2OP 0x20
36
#define OFFSET_VAR 0x40
37
#define OFFSET_EXT 0x60
38
#define OFFSET_END 0x80
40
typedef void (*op_func)(void);
44
op_func opcodetable[] = {
46
op_rtrue, op_rfalse, op_print, op_print_ret,
47
op_nop, op_save4, op_restore4, op_restart,
48
op_ret_popped, op_catch, op_quit, op_new_line,
49
op_show_status, op_verify, op_XXX, op_piracy,
51
op_jz, op_get_sibling, op_get_child, op_get_parent,
52
op_get_prop_len, op_inc, op_dec, op_print_addr,
53
op_call_s, op_remove_obj, op_print_obj, op_ret,
54
op_jump, op_print_paddr, op_load, op_call_n,
56
op_XXX, op_je, op_jl, op_jg,
57
op_dec_chk, op_inc_chk, op_jin, op_test,
58
op_or, op_and, op_test_attr, op_set_attr,
59
op_clear_attr, op_store, op_insert_obj, op_loadw,
60
op_loadb, op_get_prop, op_get_prop_addr, op_get_next_prop,
61
op_add, op_sub, op_mul, op_div,
62
op_mod, op_call_s, op_call_n, op_set_colour,
63
op_throw, op_XXX, op_XXX, op_XXX,
65
op_call_s, op_storew, op_storeb, op_put_prop,
66
op_aread, op_print_char, op_print_num, op_random,
67
op_push, op_pull, op_split_window, op_set_window,
68
op_call_s, op_erase_window, op_erase_line, op_set_cursor,
69
op_get_cursor, op_set_text_style,op_buffer_mode, op_output_stream,
70
op_input_stream, op_sound_effect, op_read_char, op_scan_table,
71
op_not, op_call_n, op_call_n, op_tokenise,
72
op_encode_text, op_copy_table, op_print_table, op_check_arg_count,
74
op_save5, op_restore5, op_log_shift, op_art_shift,
75
op_set_font, op_draw_picture, op_picture_data, op_erase_picture,
76
op_set_margins, op_save_undo, op_restore_undo, op_print_unicode,
77
op_check_unicode, op_XXX, op_XXX, op_XXX,
78
op_move_window, op_window_size, op_window_style, op_get_wind_prop,
79
op_scroll_window, op_pop_stack, op_read_mouse, op_mouse_window,
80
op_push_stack, op_put_wind_prop, op_print_form, op_make_menu,
81
op_picture_table, op_XXX, op_XXX, op_XXX
86
opcodeinfo opcodelist[] = {
88
{ "rtrue", v1, vM, 0, 0, opNONE, 0 },
89
{ "rfalse", v1, vM, 0, 0, opNONE, 0 },
90
{ "print", v1, vM, 0, 0, opTEXTINLINE, 0 },
91
{ "print_ret", v1, vM, 0, 0, opTEXTINLINE, 0 },
92
{ "nop", v1, vM, 0, 0, opNONE, 0 },
93
{ "save", v4, v4, 0, 0, opSTORES, 0 },
94
{ "restore", v4, v4, 0, 0, opSTORES, 0 },
95
{ "restart", v1, vM, 0, 0, opNONE, 0 },
96
{ "ret_popped", v1, vM, 0, 0, opNONE, 0 },
97
{ "catch", v5, vM, 0, 0, opSTORES, 0 },
98
{ "quit", v1, vM, 0, 0, opNONE, 0 },
99
{ "new_line", v1, vM, 0, 0, opNONE, 0 },
100
{ "show_status", v3, v3, 0, 0, opNONE, 0 },
101
{ "verify", v3, vM, 0, 0, opBRANCHES, 0 },
102
{ "extended", v5, vM, 0, 0, opNONE, 0 },
103
{ "piracy", v5, vM, 0, 0, opBRANCHES, 0 },
105
{ "jz", v1, vM, 1, 1, opBRANCHES, 0 },
106
{ "get_sibling", v1, vM, 1, 1, opSTORES | opBRANCHES, 0 },
107
{ "get_child", v1, vM, 1, 1, opSTORES | opBRANCHES, 0 },
108
{ "get_parent", v1, vM, 1, 1, opSTORES, 0 },
109
{ "get_prop_len", v1, vM, 1, 1, opSTORES, 0 },
110
{ "inc", v1, vM, 1, 1, opNONE, 0 },
111
{ "dec", v1, vM, 1, 1, opNONE, 0 },
112
{ "print_addr", v1, vM, 1, 1, opNONE, 0 },
113
{ "call_1s", v4, vM, 1, 1, opSTORES, 0 },
114
{ "remove_obj", v1, vM, 1, 1, opNONE, 0 },
115
{ "print_obj", v1, vM, 1, 1, opNONE, 0 },
116
{ "ret", v1, vM, 1, 1, opNONE, 0 },
117
{ "jump", v1, vM, 1, 1, opJUMPS, 0 },
118
{ "print_paddr", v1, vM, 1, 1, opNONE, 0 },
119
{ "load", v1, vM, 1, 1, opSTORES, 0 },
120
{ "call_1n", v5, vM, 1, 1, opNONE, 0 },
122
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
123
{ "je", v1, vM, 1, 4, opBRANCHES, 0 },
124
{ "jl", v1, vM, 2, 2, opBRANCHES, 0 },
125
{ "jg", v1, vM, 2, 2, opBRANCHES, 0 },
126
{ "dec_chk", v1, vM, 2, 2, opBRANCHES, 0 },
127
{ "inc_chk", v1, vM, 2, 2, opBRANCHES, 0 },
128
{ "jin", v1, vM, 2, 2, opBRANCHES, 0 },
129
{ "test", v1, vM, 2, 2, opBRANCHES, 0 },
130
{ "or", v1, vM, 2, 2, opNONE, 0 },
131
{ "and", v1, vM, 2, 2, opNONE, 0 },
132
{ "test_attr", v1, vM, 2, 2, opBRANCHES, 0 },
133
{ "set_attr", v1, vM, 2, 2, opNONE, 0 },
134
{ "clear_attr", v1, vM, 2, 2, opNONE, 0 },
135
{ "store", v1, vM, 2, 2, opNONE, 0 },
136
{ "insert_obj", v1, vM, 2, 2, opNONE, 0 },
137
{ "loadw", v1, vM, 2, 2, opSTORES, 0 },
138
{ "loadb", v1, vM, 2, 2, opSTORES, 0 },
139
{ "get_prop", v1, vM, 2, 2, opSTORES, 0 },
140
{ "get_prop_addr", v1, vM, 2, 2, opSTORES, 0 },
141
{ "get_next_prop", v1, vM, 2, 2, opSTORES, 0 },
142
{ "add", v1, vM, 2, 2, opSTORES, 0 },
143
{ "sub", v1, vM, 2, 2, opSTORES, 0 },
144
{ "mul", v1, vM, 2, 2, opSTORES, 0 },
145
{ "div", v1, vM, 2, 2, opSTORES, 0 },
146
{ "mod", v1, vM, 2, 2, opSTORES, 0 },
147
{ "call_2s", v4, vM, 2, 2, opSTORES, 0 },
148
{ "call_2n", v5, vM, 2, 2, opNONE, 0 },
149
{ "set_colour", v5, vM, 2, 2, opNONE, 0 },
150
{ "throw", v5, vM, 2, 2, opNONE, 0 },
151
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
152
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
153
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
155
{ "call_vs", v1, vM, 1, 4, opSTORES, 0 },
156
{ "storew", v1, vM, 3, 3, opNONE, 0 },
157
{ "storeb", v1, vM, 3, 3, opNONE, 0 },
158
{ "put_prop", v1, vM, 3, 3, opNONE, 0 },
159
{ "aread", v5, vM, 0, 4, opSTORES, 0 },
160
{ "print_char", v1, vM, 1, 1, opNONE, 0 },
161
{ "print_num", v1, vM, 1, 1, opNONE, 0 },
162
{ "random", v1, vM, 1, 1, opSTORES, 0 },
163
{ "push", v1, vM, 1, 1, opNONE, 0 },
164
{ "pull", v1, vM, 1, 1, opNONE, 0 },
165
{ "split_window", v3, vM, 1, 1, opNONE, 0 },
166
{ "set_window", v3, vM, 1, 1, opNONE, 0 },
167
{ "call_vs2", v4, vM, 1, 8, opSTORES, 0 },
168
{ "erase_window", v4, vM, 1, 1, opNONE, 0 },
169
{ "erase_line", v4, vM, 1, 1, opNONE, 0 },
170
{ "set_cursor", v4, vM, 2, 2, opNONE, 0 },
171
{ "get_cursor", v4, vM, 1, 1, opNONE, 0 },
172
{ "set_text_style", v4, vM, 1, 1, opNONE, 0 },
173
{ "buffer_mode", v4, vM, 1, 1, opNONE, 0 },
174
{ "output_stream", v5, vM, 1, 2, opNONE, 0 },
175
{ "input_stream", v3, vM, 1, 1, opNONE, 0 },
176
{ "sound_effect", v3, vM, 4, 4, opNONE, 0 },
177
{ "read_char", v4, vM, 1, 3, opSTORES, 0 },
178
{ "scan_table", v4, vM, 4, 4, opSTORES | opBRANCHES, 0 },
179
{ "not", v5, vM, 1, 1, opSTORES, 0 },
180
{ "call_vn", v5, vM, 1, 4, opNONE, 0 },
181
{ "call_vn2", v5, vM, 1, 8, opNONE, 0 },
182
{ "tokenise", v5, vM, 4, 4, opNONE, 0 },
183
{ "encode_text", v5, vM, 4, 4, opNONE, 0 },
184
{ "copy_table", v5, vM, 3, 3, opNONE, 0 },
185
{ "print_table", v5, vM, 4, 4, opNONE, 0 },
186
{ "check_arg_count", v5, vM, 1, 1, opBRANCHES, 0 },
188
{ "save", v5, vM, 0, 3, opSTORES, 0 },
189
{ "restore", v5, vM, 0, 3, opSTORES, 0 },
190
{ "log_shift", v5, vM, 2, 2, opSTORES, 0 },
191
{ "art_shift", v5, vM, 2, 2, opSTORES, 0 },
192
{ "set_font", v5, vM, 1, 1, opSTORES, 0 },
193
{ "draw_picture", v6, vM, 3, 3, opNONE, 0 },
194
{ "picture_data", v6, vM, 2, 2, opBRANCHES, 0 },
195
{ "erase_picture", v6, vM, 3, 3, opNONE, 0 },
196
{ "set_margins", v6, vM, 3, 3, opNONE, 0 },
197
{ "save_undo", v5, vM, 0, 0, opSTORES, 0 },
198
{ "restore_undo", v5, vM, 0, 0, opSTORES, 0 },
199
{ "print_unicode", v5, vM, 1, 1, opNONE, 0 },
200
{ "check_unicode", v5, vM, 1, 1, opSTORES, 0 },
201
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
202
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
203
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
204
{ "move_window", v6, vM, 3, 3, opNONE, 0 },
205
{ "window_size", v6, vM, 3, 3, opNONE, 0 },
206
{ "window_style", v6, vM, 2, 3, opNONE, 0 },
207
{ "get_wind_prop", v6, vM, 2, 2, opSTORES, 0 },
208
{ "scroll_window", v6, vM, 2, 2, opNONE, 0 },
209
{ "pop_stack", v6, vM, 1, 2, opNONE, 0 },
210
{ "read_mouse", v6, vM, 1, 1, opNONE, 0 },
211
{ "mouse_window", v6, vM, 1, 1, opNONE, 0 },
212
{ "push_stack", v6, vM, 1, 2, opBRANCHES, 0 },
213
{ "put_wind_prop", v6, vM, 3, 3, opNONE, 0 },
214
{ "print_form", v6, vM, 1, 1, opNONE, 0 },
215
{ "make_menu", v6, vM, 2, 2, opBRANCHES, 0 },
216
{ "picture_table", v6, vM, 1, 1, opNONE, 0 },
217
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
218
{ "XXX", v1, vM, 0, 8, opNONE, 0 },
219
{ "XXX", v1, vM, 0, 8, opNONE, 0 },