This source file includes following definitions.
- hash_cmdtype
- create_cmdtable
- free_cmdtable
- getcmdcode
- hash_code
- getcmdptr
- getcmdtype
- getcmdname
- grstr
- memsize_str2word
- comet2_init
- cpu_reset
- memory_reset
- comet2_reset
- comet2_resetall
- comet2_shutdown
1 #include <errno.h>
2 #include "struct.h"
3 #include "exec.h"
4
5
6
7
8 SYSTEM *sys = NULL;
9
10
11
12
13 EXECPTR *execptr = NULL;
14
15
16
17
18 static const COMET2CMD comet2cmd[] = {
19 { "NOP", NONE, 0x0, nop },
20 { "LD", R_ADR_X, 0x1000, ld_r_adr_x },
21 { "ST", R_ADR_X, 0x1100, st },
22 { "LAD", R_ADR_X, 0x1200, lad },
23 { "LD", R1_R2, 0x1400, ld_r1_r2 },
24 { "ADDA", R_ADR_X, 0x2000, adda_r_adr_x },
25 { "SUBA", R_ADR_X, 0x2100, suba_r_adr_x },
26 { "ADDL", R_ADR_X, 0x2200, addl_r_adr_x },
27 { "SUBL", R_ADR_X, 0x2300, subl_r_adr_x },
28 { "ADDA", R1_R2, 0x2400, adda_r1_r2 },
29 { "SUBA", R1_R2, 0x2500, suba_r1_r2 },
30 { "ADDL", R1_R2, 0x2600, addl_r1_r2 },
31 { "SUBL", R1_R2, 0x2700, subl_r1_r2 },
32 { "AND", R_ADR_X, 0x3000, and_r_adr_x },
33 { "OR", R_ADR_X, 0x3100, or_r_adr_x },
34 { "XOR", R_ADR_X, 0x3200, xor_r_adr_x },
35 { "AND", R1_R2, 0x3400, and_r1_r2 },
36 { "OR", R1_R2, 0x3500, or_r1_r2 },
37 { "XOR", R1_R2, 0x3600, xor_r1_r2 },
38 { "CPA", R_ADR_X, 0x4000, cpa_r_adr_x },
39 { "CPL", R_ADR_X, 0x4100, cpl_r_adr_x },
40 { "CPA", R1_R2, 0x4400, cpa_r1_r2 },
41 { "CPL", R1_R2, 0x4500, cpl_r1_r2 },
42 { "SLA", R_ADR_X, 0x5000, sla },
43 { "SRA", R_ADR_X, 0x5100, sra },
44 { "SLL", R_ADR_X, 0x5200, sll },
45 { "SRL", R_ADR_X, 0x5300, srl },
46 { "JMI", ADR_X, 0x6100, jmi },
47 { "JNZ", ADR_X, 0x6200, jnz },
48 { "JZE", ADR_X, 0x6300, jze },
49 { "JUMP", ADR_X, 0x6400, jump },
50 { "JPL", ADR_X, 0x6500, jpl },
51 { "JOV", ADR_X, 0x6600, jov },
52 { "PUSH", ADR_X, 0x7000, push },
53 { "POP", R_, 0x7100, pop },
54 { "CALL", ADR_X, 0x8000, call },
55 { "SVC", ADR_X, 0xF000, svc },
56 { "RET", NONE, 0x8100, ret },
57 };
58
59
60
61
62 static int comet2cmdsize = ARRAYSIZE(comet2cmd);
63
64
65
66
67 enum {
68 CMDTABSIZE = 41,
69 };
70
71
72
73
74 static CMDTAB *cmdtab[HASH_MAX][CMDTABSIZE] = {{NULL}};
75
76
77
78
79 unsigned hash_cmdtype(const char *cmd, CMDTYPE type);
80
81
82
83
84 unsigned hash_code(WORD code);
85
86
87
88
89 void cpu_reset();
90
91
92
93
94 void memory_reset();
95
96
97
98
99 unsigned hash_cmdtype(const char *cmd, CMDTYPE type)
100 {
101 HKEY *keys[2] = {NULL};
102 unsigned hashval = 0;
103
104
105 keys[0] = malloc_chk(sizeof(HKEY), "hash_cmdtype.keys[0]");
106 keys[0]->type = CHARS;
107 keys[0]->val.s = strdup_chk(cmd, "keys[0].val.s");
108
109 keys[1] = malloc_chk(sizeof(HKEY), "hash_cmdtype.keys[1]");
110 keys[1]->type = INT;
111 keys[1]->val.i = (int)(type & 070);
112
113 hashval = hash(2, keys, CMDTABSIZE);
114 FREE(keys[0]->val.s);
115 FREE(keys[0]);
116 FREE(keys[1]);
117
118 return hashval;
119 }
120
121
122
123
124 bool create_cmdtable(CMDTAB_HASH hash)
125 {
126 CMDTAB *p = NULL;
127 unsigned hashval;
128
129 for(int i = 0; i < comet2cmdsize; i++) {
130 p = malloc_chk(sizeof(CMDTAB), "create_cmdtable.p");
131 p->cmd = &comet2cmd[i];
132 if(hash == HASH_CMDTYPE) {
133 hashval = hash_cmdtype(comet2cmd[i].name, comet2cmd[i].type);
134 } else if(hash == HASH_CODE) {
135 hashval = hash_code(comet2cmd[i].code);
136 }
137 p->next = cmdtab[hash][hashval];
138 cmdtab[hash][hashval] = p;
139 }
140 return true;
141 }
142
143
144
145
146 void free_cmdtable(CMDTAB_HASH hash)
147 {
148 CMDTAB *p = NULL;
149 CMDTAB *q = NULL;
150
151 for(int i = 0; i < CMDTABSIZE; i++) {
152 for(p = cmdtab[hash][i]; p != NULL; p = q) {
153 q = p->next;
154 FREE(p);
155 }
156 cmdtab[hash][i] = NULL;
157 }
158 }
159
160
161
162
163
164 WORD getcmdcode(const char *cmd, CMDTYPE type)
165 {
166 CMDTAB *p = NULL;
167 WORD w = 0xFFFF;
168
169 assert(cmd != NULL);
170 for(p = cmdtab[HASH_CMDTYPE][hash_cmdtype(cmd, type)]; p != NULL; p = p->next) {
171 if(strcmp(cmd, p->cmd->name) == 0 && type == p->cmd->type) {
172 w = p->cmd->code;
173 break;
174 }
175 }
176 return w;
177 }
178
179
180
181
182 unsigned hash_code(WORD code)
183 {
184 HKEY *keys[1] = {NULL};
185 unsigned h = 0;
186
187
188 keys[0] = malloc_chk(sizeof(HKEY), "hash_code.key");
189 keys[0]->type = INT;
190 keys[0]->val.i = (int)(code >> 8);
191 h = hash(1, keys, CMDTABSIZE);
192 FREE(keys[0]);
193 return h;
194 }
195
196
197
198
199 const void (*getcmdptr(WORD code))
200 {
201 CMDTAB *t = NULL;
202 const void *ptr = NULL;
203
204 for(t = cmdtab[HASH_CODE][hash_code(code)]; t != NULL; t = t->next) {
205 if(code == t->cmd->code) {
206 ptr = t->cmd->ptr;
207 break;
208 }
209 }
210 return ptr;
211 }
212
213
214
215
216 CMDTYPE getcmdtype(WORD code)
217 {
218 CMDTAB *t = NULL;
219 CMDTYPE type = NONE;
220
221 for(t = cmdtab[HASH_CODE][hash_code(code)]; t != NULL; t = t->next) {
222 if(code == t->cmd->code) {
223 type = t->cmd->type;
224 break;
225 }
226 }
227 return type;
228 }
229
230
231
232
233 char *getcmdname(WORD code)
234 {
235 CMDTAB *t = NULL;
236 char *cmd = NULL;
237
238 for(t = cmdtab[HASH_CODE][hash_code(code)]; t != NULL; t = t->next) {
239 if(code == t->cmd->code) {
240 cmd = t->cmd->name;
241 break;
242 }
243 }
244 return cmd;
245 }
246
247
248
249
250
251 char *grstr(WORD word)
252 {
253 assert(word <= 7);
254 char *str = NULL;
255
256 str = malloc_chk(3 + 1, "grstr.str");
257 sprintf(str, "GR%d", word);
258 return str;
259 }
260
261 WORD memsize_str2word(const char *str) {
262 return (WORD)str2l_range(str, 1, MAX_MEMSIZE, "Memory Size");
263 }
264
265
266
267
268 void comet2_init(WORD memsize, CLOCK clocks)
269 {
270 sys = malloc_chk(sizeof(SYSTEM), "sys");
271
272 assert(0 < memsize && memsize <= MAX_MEMSIZE-1);
273 sys->memsize = memsize;
274
275 assert(0 < clocks && clocks <= MAX_CLOCKS);
276 sys->clocks = clocks;
277
278 sys->cpu = malloc_chk(sizeof(CPU), "comet2_init.cpu");
279
280 cpu_reset();
281
282 sys->memory = calloc_chk(sys->memsize, sizeof(WORD), "comet2_init.memory");
283
284 memory_reset();
285
286 execptr = malloc_chk(sizeof(EXECPTR), "execptr");
287 execptr->stop = false;
288 }
289
290
291 void cpu_reset() {
292
293 for(int i = 0; i < GRSIZE; i++) {
294 sys->cpu->gr[i] = 0x0;
295 }
296 sys->cpu->sp = sys->memsize;
297 sys->cpu->pr = 0x0;
298 sys->cpu->fr = 0x0;
299 }
300
301
302
303
304 void memory_reset() {
305 memset(sys->memory, 0, sys->memsize * sizeof(WORD));
306 }
307
308
309
310
311 void comet2_reset()
312 {
313
314 cpu_reset();
315 }
316
317
318
319
320 void comet2_resetall()
321 {
322
323 cpu_reset();
324
325 memory_reset();
326 }
327
328
329
330
331 void comet2_shutdown()
332 {
333 FREE(execptr);
334 FREE(sys->memory);
335 FREE(sys->cpu);
336 FREE(sys);
337 }