srcdest.c revision 1.10 1 1.1 christos /* srcdest.c --- decoding M32C addressing modes.
2 1.1 christos
3 1.10 christos Copyright (C) 2005-2023 Free Software Foundation, Inc.
4 1.1 christos Contributed by Red Hat, Inc.
5 1.1 christos
6 1.1 christos This file is part of the GNU simulators.
7 1.1 christos
8 1.1 christos This program is free software; you can redistribute it and/or modify
9 1.1 christos it under the terms of the GNU General Public License as published by
10 1.1 christos the Free Software Foundation; either version 3 of the License, or
11 1.1 christos (at your option) any later version.
12 1.1 christos
13 1.1 christos This program is distributed in the hope that it will be useful,
14 1.1 christos but WITHOUT ANY WARRANTY; without even the implied warranty of
15 1.1 christos MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 1.1 christos GNU General Public License for more details.
17 1.1 christos
18 1.1 christos You should have received a copy of the GNU General Public License
19 1.1 christos along with this program. If not, see <http://www.gnu.org/licenses/>. */
20 1.1 christos
21 1.10 christos /* This must come before any other includes. */
22 1.10 christos #include "defs.h"
23 1.1 christos
24 1.1 christos #include <stdio.h>
25 1.1 christos #include <stdlib.h>
26 1.1 christos
27 1.7 christos #include "libiberty.h"
28 1.1 christos #include "cpu.h"
29 1.1 christos #include "mem.h"
30 1.1 christos
31 1.1 christos static int src_indirect = 0;
32 1.1 christos static int dest_indirect = 0;
33 1.1 christos static int src_addend = 0;
34 1.1 christos static int dest_addend = 0;
35 1.1 christos
36 1.1 christos static int
37 1.5 christos disp8 (void)
38 1.1 christos {
39 1.1 christos int rv;
40 1.1 christos int tsave = trace;
41 1.1 christos
42 1.1 christos if (trace == 1)
43 1.1 christos trace = 0;
44 1.1 christos rv = mem_get_qi (get_reg (pc));
45 1.1 christos regs.r_pc++;
46 1.1 christos trace = tsave;
47 1.1 christos return rv;
48 1.1 christos }
49 1.1 christos
50 1.1 christos static int
51 1.5 christos disp16 (void)
52 1.1 christos {
53 1.1 christos int rv;
54 1.1 christos int tsave = trace;
55 1.1 christos
56 1.1 christos if (trace == 1)
57 1.1 christos trace = 0;
58 1.1 christos rv = mem_get_hi (get_reg (pc));
59 1.1 christos regs.r_pc += 2;
60 1.1 christos trace = tsave;
61 1.1 christos return rv;
62 1.1 christos }
63 1.1 christos
64 1.1 christos static int
65 1.5 christos disp24 (void)
66 1.1 christos {
67 1.1 christos int rv;
68 1.1 christos int tsave = trace;
69 1.1 christos
70 1.1 christos if (trace == 1)
71 1.1 christos trace = 0;
72 1.1 christos rv = mem_get_psi (get_reg (pc));
73 1.1 christos regs.r_pc += 3;
74 1.1 christos trace = tsave;
75 1.1 christos return rv;
76 1.1 christos }
77 1.1 christos
78 1.1 christos static int
79 1.5 christos disp20 (void)
80 1.1 christos {
81 1.1 christos return disp24 () & 0x000fffff;
82 1.1 christos }
83 1.1 christos
84 1.1 christos const char *
85 1.1 christos bits (int v, int b)
86 1.1 christos {
87 1.1 christos static char buf[17];
88 1.1 christos char *bp = buf + 16;
89 1.1 christos *bp = 0;
90 1.1 christos while (b)
91 1.1 christos {
92 1.1 christos *--bp = (v & 1) ? '1' : '0';
93 1.1 christos v >>= 1;
94 1.1 christos b--;
95 1.1 christos }
96 1.1 christos return bp;
97 1.1 christos }
98 1.1 christos
99 1.1 christos static const char *the_bits = 0;
100 1.1 christos
101 1.1 christos void
102 1.1 christos decode_indirect (int si, int di)
103 1.1 christos {
104 1.1 christos src_indirect = si;
105 1.1 christos dest_indirect = di;
106 1.1 christos if (trace && (si || di))
107 1.1 christos printf ("indirect: s:%d d:%d\n", si, di);
108 1.1 christos }
109 1.1 christos
110 1.1 christos void
111 1.1 christos decode_index (int sa, int da)
112 1.1 christos {
113 1.1 christos src_addend = sa;
114 1.1 christos dest_addend = da;
115 1.1 christos if (trace && (sa || da))
116 1.1 christos printf ("index: s:%d d:%d\n", sa, da);
117 1.1 christos }
118 1.1 christos
119 1.1 christos srcdest
120 1.1 christos decode_srcdest4 (int destcode, int bw)
121 1.1 christos {
122 1.1 christos srcdest sd;
123 1.1 christos static const char *dc_wnames[16] = { "r0", "r1", "r2", "r3",
124 1.1 christos "a0", "a1", "[a0]", "[a1]",
125 1.1 christos "disp8[a0]", "disp8[a1]", "disp8[sb]", "disp8[fb]",
126 1.1 christos "disp16[a0]", "disp16[a1]", "disp16[sb]", "disp16"
127 1.1 christos };
128 1.1 christos static const char *dc_bnames[4] = { "r0l", "r0h", "r1l", "r1h" };;
129 1.1 christos
130 1.5 christos sd.bytes = bw ? 2 : 1;
131 1.5 christos sd.mem = (destcode >= 6) ? 1 : 0;
132 1.5 christos
133 1.1 christos if (trace)
134 1.1 christos {
135 1.1 christos const char *n = dc_wnames[destcode];
136 1.1 christos if (bw == 0 && destcode <= 3)
137 1.1 christos n = dc_bnames[destcode];
138 1.1 christos if (!the_bits)
139 1.1 christos the_bits = bits (destcode, 4);
140 1.1 christos printf ("decode: %s (%d) : %s\n", the_bits, destcode, n);
141 1.1 christos the_bits = 0;
142 1.1 christos }
143 1.1 christos
144 1.1 christos switch (destcode)
145 1.1 christos {
146 1.1 christos case 0x0:
147 1.1 christos sd.u.reg = bw ? r0 : r0l;
148 1.1 christos break;
149 1.1 christos case 0x1:
150 1.1 christos sd.u.reg = bw ? r1 : r0h;
151 1.1 christos break;
152 1.1 christos case 0x2:
153 1.1 christos sd.u.reg = bw ? r2 : r1l;
154 1.1 christos break;
155 1.1 christos case 0x3:
156 1.1 christos sd.u.reg = bw ? r3 : r1h;
157 1.1 christos break;
158 1.1 christos case 0x4:
159 1.1 christos sd.u.reg = a0;
160 1.1 christos break;
161 1.1 christos case 0x5:
162 1.1 christos sd.u.reg = a1;
163 1.1 christos break;
164 1.1 christos case 0x6:
165 1.1 christos sd.u.addr = get_reg (a0);
166 1.1 christos break;
167 1.1 christos case 0x7:
168 1.1 christos sd.u.addr = get_reg (a1);
169 1.1 christos break;
170 1.1 christos case 0x8:
171 1.1 christos sd.u.addr = get_reg (a0) + disp8 ();
172 1.1 christos break;
173 1.1 christos case 0x9:
174 1.1 christos sd.u.addr = get_reg (a1) + disp8 ();
175 1.1 christos break;
176 1.1 christos case 0xa:
177 1.1 christos sd.u.addr = get_reg (sb) + disp8 ();
178 1.1 christos break;
179 1.1 christos case 0xb:
180 1.1 christos sd.u.addr = get_reg (fb) + sign_ext (disp8 (), 8);
181 1.1 christos break;
182 1.1 christos case 0xc:
183 1.1 christos sd.u.addr = get_reg (a0) + disp16 ();
184 1.1 christos break;
185 1.1 christos case 0xd:
186 1.1 christos sd.u.addr = get_reg (a1) + disp16 ();
187 1.1 christos break;
188 1.1 christos case 0xe:
189 1.1 christos sd.u.addr = get_reg (sb) + disp16 ();
190 1.1 christos break;
191 1.1 christos case 0xf:
192 1.1 christos sd.u.addr = disp16 ();
193 1.1 christos break;
194 1.1 christos default:
195 1.1 christos abort ();
196 1.1 christos }
197 1.1 christos if (sd.mem)
198 1.1 christos sd.u.addr &= addr_mask;
199 1.1 christos return sd;
200 1.1 christos }
201 1.1 christos
202 1.1 christos srcdest
203 1.1 christos decode_jumpdest (int destcode, int w)
204 1.1 christos {
205 1.1 christos srcdest sd;
206 1.1 christos static const char *dc_wnames[16] = { "r0", "r1", "r2", "r3",
207 1.1 christos "a0", "a1", "[a0]", "[a1]",
208 1.1 christos "disp8[a0]", "disp8[a1]", "disp8[sb]", "disp8[fb]",
209 1.1 christos "disp20[a0]", "disp20[a1]", "disp16[sb]", "abs16"
210 1.1 christos };
211 1.1 christos static const char *dc_anames[4] = { "r0l", "r0h", "r1l", "r1h" };
212 1.1 christos
213 1.5 christos sd.bytes = w ? 2 : 3;
214 1.5 christos sd.mem = (destcode >= 6) ? 1 : 0;
215 1.5 christos
216 1.1 christos if (trace)
217 1.1 christos {
218 1.1 christos const char *n = dc_wnames[destcode];
219 1.1 christos if (w == 0 && destcode <= 3)
220 1.1 christos n = dc_anames[destcode];
221 1.1 christos if (!the_bits)
222 1.1 christos the_bits = bits (destcode, 4);
223 1.1 christos printf ("decode: %s : %s\n", the_bits, n);
224 1.1 christos the_bits = 0;
225 1.1 christos }
226 1.1 christos
227 1.1 christos switch (destcode)
228 1.1 christos {
229 1.1 christos case 0x0:
230 1.1 christos sd.u.reg = w ? r0 : r2r0;
231 1.1 christos break;
232 1.1 christos case 0x1:
233 1.1 christos sd.u.reg = w ? r1 : r2r0;
234 1.1 christos break;
235 1.1 christos case 0x2:
236 1.1 christos sd.u.reg = w ? r2 : r3r1;
237 1.1 christos break;
238 1.1 christos case 0x3:
239 1.1 christos sd.u.reg = w ? r3 : r3r1;
240 1.1 christos break;
241 1.1 christos case 0x4:
242 1.1 christos sd.u.reg = w ? a0 : a1a0;
243 1.1 christos break;
244 1.1 christos case 0x5:
245 1.1 christos sd.u.reg = w ? a1 : a1a0;
246 1.1 christos break;
247 1.1 christos case 0x6:
248 1.1 christos sd.u.addr = get_reg (a0);
249 1.1 christos break;
250 1.1 christos case 0x7:
251 1.1 christos sd.u.addr = get_reg (a1);
252 1.1 christos break;
253 1.1 christos case 0x8:
254 1.1 christos sd.u.addr = get_reg (a0) + disp8 ();
255 1.1 christos break;
256 1.1 christos case 0x9:
257 1.1 christos sd.u.addr = get_reg (a1) + disp8 ();
258 1.1 christos break;
259 1.1 christos case 0xa:
260 1.1 christos sd.u.addr = get_reg (sb) + disp8 ();
261 1.1 christos break;
262 1.1 christos case 0xb:
263 1.1 christos sd.u.addr = get_reg (fb) + sign_ext (disp8 (), 8);
264 1.1 christos break;
265 1.1 christos case 0xc:
266 1.1 christos sd.u.addr = get_reg (a0) + disp20 ();
267 1.1 christos break;
268 1.1 christos case 0xd:
269 1.1 christos sd.u.addr = get_reg (a1) + disp20 ();
270 1.1 christos break;
271 1.1 christos case 0xe:
272 1.1 christos sd.u.addr = get_reg (sb) + disp16 ();
273 1.1 christos break;
274 1.1 christos case 0xf:
275 1.1 christos sd.u.addr = disp16 ();
276 1.1 christos break;
277 1.1 christos default:
278 1.1 christos abort ();
279 1.1 christos }
280 1.1 christos if (sd.mem)
281 1.1 christos sd.u.addr &= addr_mask;
282 1.1 christos return sd;
283 1.1 christos }
284 1.1 christos
285 1.1 christos srcdest
286 1.1 christos decode_dest3 (int destcode, int bw)
287 1.1 christos {
288 1.1 christos static char map[8] = { -1, -1, -1, 1, 0, 10, 11, 15 };
289 1.1 christos
290 1.1 christos the_bits = bits (destcode, 3);
291 1.1 christos return decode_srcdest4 (map[destcode], bw);
292 1.1 christos }
293 1.1 christos
294 1.1 christos srcdest
295 1.1 christos decode_src2 (int srccode, int bw, int d)
296 1.1 christos {
297 1.1 christos static char map[4] = { 0, 10, 11, 15 };
298 1.1 christos
299 1.1 christos the_bits = bits (srccode, 2);
300 1.1 christos return decode_srcdest4 (srccode ? map[srccode] : 1 - d, bw);
301 1.1 christos }
302 1.1 christos
303 1.1 christos static struct
304 1.1 christos {
305 1.1 christos reg_id b_regno;
306 1.1 christos reg_id w_regno;
307 1.1 christos int is_memory;
308 1.1 christos int disp_bytes;
309 1.1 christos char *name;
310 1.1 christos } modes23[] =
311 1.1 christos {
312 1.1 christos {
313 1.1 christos a0, a0, 1, 0, "[A0]"}, /* 0 0 0 0 0 */
314 1.1 christos {
315 1.1 christos a1, a1, 1, 0, "[A1]"}, /* 0 0 0 0 1 */
316 1.1 christos {
317 1.1 christos a0, a0, 0, 0, "A0"}, /* 0 0 0 1 0 */
318 1.1 christos {
319 1.1 christos a1, a1, 0, 0, "A1"}, /* 0 0 0 1 1 */
320 1.1 christos {
321 1.1 christos a0, a0, 1, 1, "dsp:8[A0]"}, /* 0 0 1 0 0 */
322 1.1 christos {
323 1.1 christos a1, a1, 1, 1, "dsp:8[A1]"}, /* 0 0 1 0 1 */
324 1.1 christos {
325 1.1 christos sb, sb, 1, 1, "dsp:8[SB]"}, /* 0 0 1 1 0 */
326 1.1 christos {
327 1.1 christos fb, fb, 1, -1, "dsp:8[FB]"}, /* 0 0 1 1 1 */
328 1.1 christos {
329 1.1 christos a0, a0, 1, 2, "dsp:16[A0]"}, /* 0 1 0 0 0 */
330 1.1 christos {
331 1.1 christos a1, a1, 1, 2, "dsp:16[A1]"}, /* 0 1 0 0 1 */
332 1.1 christos {
333 1.1 christos sb, sb, 1, 2, "dsp:16[SB]"}, /* 0 1 0 1 0 */
334 1.1 christos {
335 1.1 christos fb, fb, 1, -2, "dsp:16[FB]"}, /* 0 1 0 1 1 */
336 1.1 christos {
337 1.1 christos a0, a0, 1, 3, "dsp:24[A0]"}, /* 0 1 1 0 0 */
338 1.1 christos {
339 1.1 christos a1, a1, 1, 3, "dsp:24[A1]"}, /* 0 1 1 0 1 */
340 1.1 christos {
341 1.1 christos mem, mem, 1, 3, "abs24"}, /* 0 1 1 1 0 */
342 1.1 christos {
343 1.1 christos mem, mem, 1, 2, "abs16"}, /* 0 1 1 1 1 */
344 1.1 christos {
345 1.1 christos r0h, r2, 0, 0, "R0H/R2"}, /* 1 0 0 0 0 */
346 1.1 christos {
347 1.1 christos r1h, r3, 0, 0, "R1H/R3"}, /* 1 0 0 0 1 */
348 1.1 christos {
349 1.1 christos r0l, r0, 0, 0, "R0L/R0"}, /* 1 0 0 1 0 */
350 1.1 christos {
351 1.1 christos r1l, r1, 0, 0, "R1L/R1"}, /* 1 0 0 1 1 */
352 1.1 christos };
353 1.1 christos
354 1.1 christos static srcdest
355 1.1 christos decode_sd23 (int bbb, int bb, int bytes, int ind, int add)
356 1.1 christos {
357 1.1 christos srcdest sd;
358 1.1 christos int code = (bbb << 2) | bb;
359 1.1 christos
360 1.7 christos if (code >= ARRAY_SIZE (modes23))
361 1.1 christos abort ();
362 1.1 christos
363 1.1 christos if (trace)
364 1.1 christos {
365 1.1 christos char *b1 = "";
366 1.1 christos char *b2 = "";
367 1.1 christos char ad[30];
368 1.1 christos if (ind)
369 1.1 christos {
370 1.1 christos b1 = "[";
371 1.1 christos b2 = "]";
372 1.1 christos }
373 1.1 christos if (add)
374 1.1 christos sprintf (ad, "%+d", add);
375 1.1 christos else
376 1.1 christos ad[0] = 0;
377 1.1 christos if (!the_bits)
378 1.1 christos the_bits = bits (code, 4);
379 1.1 christos printf ("decode: %s (%d) : %s%s%s%s\n", the_bits, code, b1,
380 1.1 christos modes23[code].name, ad, b2);
381 1.1 christos the_bits = 0;
382 1.1 christos }
383 1.1 christos
384 1.1 christos sd.bytes = bytes;
385 1.1 christos sd.mem = modes23[code].is_memory;
386 1.1 christos if (sd.mem)
387 1.1 christos {
388 1.1 christos if (modes23[code].w_regno == mem)
389 1.1 christos sd.u.addr = 0;
390 1.1 christos else
391 1.1 christos sd.u.addr = get_reg (modes23[code].w_regno);
392 1.1 christos switch (modes23[code].disp_bytes)
393 1.1 christos {
394 1.1 christos case 1:
395 1.1 christos sd.u.addr += disp8 ();
396 1.1 christos break;
397 1.1 christos case 2:
398 1.1 christos sd.u.addr += disp16 ();
399 1.1 christos break;
400 1.1 christos case -1:
401 1.1 christos sd.u.addr += sign_ext (disp8 (), 8);
402 1.1 christos break;
403 1.1 christos case -2:
404 1.1 christos sd.u.addr += sign_ext (disp16 (), 16);
405 1.1 christos break;
406 1.1 christos case 3:
407 1.1 christos sd.u.addr += disp24 ();
408 1.1 christos break;
409 1.1 christos default:
410 1.1 christos break;
411 1.1 christos }
412 1.1 christos if (add)
413 1.1 christos sd.u.addr += add;
414 1.1 christos if (ind)
415 1.1 christos sd.u.addr = mem_get_si (sd.u.addr & membus_mask);
416 1.1 christos sd.u.addr &= membus_mask;
417 1.1 christos }
418 1.1 christos else
419 1.1 christos {
420 1.1 christos sd.u.reg = (bytes > 1) ? modes23[code].w_regno : modes23[code].b_regno;
421 1.1 christos if (bytes == 3 || bytes == 4)
422 1.1 christos {
423 1.1 christos switch (sd.u.reg)
424 1.1 christos {
425 1.1 christos case r0:
426 1.1 christos sd.u.reg = r2r0;
427 1.1 christos break;
428 1.1 christos case r1:
429 1.1 christos sd.u.reg = r3r1;
430 1.1 christos break;
431 1.1 christos case r2:
432 1.1 christos abort ();
433 1.1 christos case r3:
434 1.1 christos abort ();
435 1.1 christos default:;
436 1.1 christos }
437 1.1 christos }
438 1.1 christos
439 1.1 christos }
440 1.1 christos return sd;
441 1.1 christos }
442 1.1 christos
443 1.1 christos srcdest
444 1.1 christos decode_dest23 (int ddd, int dd, int bytes)
445 1.1 christos {
446 1.1 christos return decode_sd23 (ddd, dd, bytes, dest_indirect, dest_addend);
447 1.1 christos }
448 1.1 christos
449 1.1 christos srcdest
450 1.1 christos decode_src23 (int sss, int ss, int bytes)
451 1.1 christos {
452 1.1 christos return decode_sd23 (sss, ss, bytes, src_indirect, src_addend);
453 1.1 christos }
454 1.1 christos
455 1.1 christos srcdest
456 1.1 christos decode_dest2 (int dd, int bytes)
457 1.1 christos {
458 1.1 christos /* r0l/r0, abs16, dsp:8[SB], dsp:8[FB] */
459 1.1 christos static char map[4] = { 0x12, 0x0f, 0x06, 0x07 };
460 1.1 christos
461 1.1 christos the_bits = bits (dd, 2);
462 1.1 christos return decode_sd23 (map[dd] >> 2, map[dd] & 3, bytes, dest_indirect,
463 1.1 christos dest_addend);
464 1.1 christos }
465 1.1 christos
466 1.1 christos srcdest
467 1.1 christos decode_src3 (int sss, int bytes)
468 1.1 christos {
469 1.1 christos /* r0, r1, a0, a1, r2, r3, N/A, N/A */
470 1.1 christos static char map[8] = { 0x12, 0x13, 0x02, 0x03, 0x10, 0x11, 0, 0 };
471 1.1 christos
472 1.1 christos the_bits = bits (sss, 3);
473 1.1 christos return decode_sd23 (map[sss] >> 2, map[sss] & 3, bytes, src_indirect,
474 1.1 christos src_addend);
475 1.1 christos }
476 1.1 christos
477 1.1 christos srcdest
478 1.1 christos decode_dest1 (int destcode, int bw)
479 1.1 christos {
480 1.1 christos the_bits = bits (destcode, 1);
481 1.1 christos return decode_srcdest4 (destcode, bw);
482 1.1 christos }
483 1.1 christos
484 1.1 christos srcdest
485 1.1 christos decode_cr (int crcode)
486 1.1 christos {
487 1.1 christos static int regcode[] = { 0, intbl, intbh, flags, isp, sp, sb, fb };
488 1.1 christos srcdest sd;
489 1.1 christos sd.mem = 0;
490 1.1 christos sd.bytes = 2;
491 1.1 christos sd.u.reg = regcode[crcode & 7];
492 1.1 christos return sd;
493 1.1 christos }
494 1.1 christos
495 1.1 christos srcdest
496 1.1 christos decode_cr_b (int crcode, int bank)
497 1.1 christos {
498 1.1 christos /* FIXME: intbl, intbh, isp */
499 1.1 christos static int regcode[3][8] = {
500 1.1 christos {0, 0, flags, 0, 0, 0, 0, 0},
501 1.1 christos {intb, sp, sb, fb, 0, 0, 0, isp},
502 1.1 christos {0, 0, 0, 0, 0, 0, 0, 0}
503 1.1 christos };
504 1.1 christos srcdest sd;
505 1.1 christos sd.mem = 0;
506 1.1 christos sd.bytes = bank ? 3 : 2;
507 1.1 christos sd.u.reg = regcode[bank][crcode & 7];
508 1.1 christos return sd;
509 1.1 christos }
510 1.1 christos
511 1.1 christos srcdest
512 1.1 christos widen_sd (srcdest sd)
513 1.1 christos {
514 1.1 christos sd.bytes *= 2;
515 1.1 christos if (!sd.mem)
516 1.1 christos switch (sd.u.reg)
517 1.1 christos {
518 1.1 christos case r0l:
519 1.1 christos sd.u.reg = r0;
520 1.1 christos break;
521 1.1 christos case r0:
522 1.1 christos sd.u.reg = r2r0;
523 1.1 christos break;
524 1.1 christos case r1l:
525 1.1 christos sd.u.reg = r1;
526 1.1 christos break;
527 1.1 christos case r1:
528 1.1 christos sd.u.reg = r3r1;
529 1.1 christos break;
530 1.1 christos case a0:
531 1.1 christos if (A16)
532 1.1 christos sd.u.reg = a1a0;
533 1.1 christos break;
534 1.1 christos default:
535 1.1 christos break;
536 1.1 christos }
537 1.1 christos return sd;
538 1.1 christos }
539 1.1 christos
540 1.1 christos srcdest
541 1.1 christos reg_sd (reg_id reg)
542 1.1 christos {
543 1.1 christos srcdest rv;
544 1.1 christos rv.bytes = reg_bytes[reg];
545 1.1 christos rv.mem = 0;
546 1.1 christos rv.u.reg = reg;
547 1.1 christos return rv;
548 1.1 christos }
549 1.1 christos
550 1.1 christos int
551 1.1 christos get_src (srcdest sd)
552 1.1 christos {
553 1.1 christos int v;
554 1.1 christos if (sd.mem)
555 1.1 christos {
556 1.1 christos switch (sd.bytes)
557 1.1 christos {
558 1.1 christos case 1:
559 1.1 christos v = mem_get_qi (sd.u.addr);
560 1.1 christos break;
561 1.1 christos case 2:
562 1.1 christos v = mem_get_hi (sd.u.addr);
563 1.1 christos break;
564 1.1 christos case 3:
565 1.1 christos v = mem_get_psi (sd.u.addr);
566 1.1 christos break;
567 1.1 christos case 4:
568 1.1 christos v = mem_get_si (sd.u.addr);
569 1.1 christos break;
570 1.1 christos default:
571 1.1 christos abort ();
572 1.1 christos }
573 1.1 christos }
574 1.1 christos else
575 1.1 christos {
576 1.1 christos v = get_reg (sd.u.reg);
577 1.1 christos switch (sd.bytes)
578 1.1 christos {
579 1.1 christos case 1:
580 1.1 christos v &= 0xff;
581 1.1 christos break;
582 1.1 christos case 2:
583 1.1 christos v &= 0xffff;
584 1.1 christos break;
585 1.1 christos case 3:
586 1.1 christos v &= 0xffffff;
587 1.1 christos break;
588 1.1 christos }
589 1.1 christos }
590 1.1 christos return v;
591 1.1 christos }
592 1.1 christos
593 1.1 christos void
594 1.1 christos put_dest (srcdest sd, int v)
595 1.1 christos {
596 1.1 christos if (sd.mem)
597 1.1 christos {
598 1.1 christos switch (sd.bytes)
599 1.1 christos {
600 1.1 christos case 1:
601 1.1 christos mem_put_qi (sd.u.addr, v);
602 1.1 christos break;
603 1.1 christos case 2:
604 1.1 christos mem_put_hi (sd.u.addr, v);
605 1.1 christos break;
606 1.1 christos case 3:
607 1.1 christos mem_put_psi (sd.u.addr, v);
608 1.1 christos break;
609 1.1 christos case 4:
610 1.1 christos mem_put_si (sd.u.addr, v);
611 1.1 christos break;
612 1.1 christos }
613 1.1 christos }
614 1.1 christos else
615 1.1 christos {
616 1.1 christos switch (sd.bytes)
617 1.1 christos {
618 1.1 christos case 1:
619 1.1 christos v &= 0xff;
620 1.1 christos break;
621 1.1 christos case 2:
622 1.1 christos v &= 0xffff;
623 1.1 christos break;
624 1.1 christos case 3:
625 1.1 christos v &= 0xffffff;
626 1.1 christos break;
627 1.1 christos }
628 1.1 christos put_reg (sd.u.reg, v);
629 1.1 christos }
630 1.1 christos }
631 1.1 christos
632 1.1 christos srcdest
633 1.1 christos decode_bit (int destcode)
634 1.1 christos {
635 1.1 christos srcdest sd;
636 1.1 christos int addr = 0;
637 1.1 christos static const char *dc_names[] = { "r0", "r1", "r2", "r3",
638 1.1 christos "a0", "a1", "[a0]", "[a1]",
639 1.1 christos "disp8[a0]", "disp8[a1]", "disp8[sb]", "disp8[fb]",
640 1.1 christos "disp16[a0]", "disp16[a1]", "disp16[sb]", "abs16"
641 1.1 christos };
642 1.1 christos
643 1.1 christos if (trace)
644 1.1 christos {
645 1.1 christos const char *the_bits = bits (destcode, 4);
646 1.1 christos printf ("decode: %s : %s\n", the_bits, dc_names[destcode]);
647 1.1 christos }
648 1.1 christos
649 1.1 christos switch (destcode)
650 1.1 christos {
651 1.1 christos case 0:
652 1.1 christos sd.u.reg = r0;
653 1.1 christos break;
654 1.1 christos case 1:
655 1.1 christos sd.u.reg = r1;
656 1.1 christos break;
657 1.1 christos case 2:
658 1.1 christos sd.u.reg = r2;
659 1.1 christos break;
660 1.1 christos case 3:
661 1.1 christos sd.u.reg = r3;
662 1.1 christos break;
663 1.1 christos case 4:
664 1.1 christos sd.u.reg = a0;
665 1.1 christos break;
666 1.1 christos case 5:
667 1.1 christos sd.u.reg = a1;
668 1.1 christos break;
669 1.1 christos case 6:
670 1.1 christos addr = get_reg (a0);
671 1.1 christos break;
672 1.1 christos case 7:
673 1.1 christos addr = get_reg (a1);
674 1.1 christos break;
675 1.1 christos case 8:
676 1.1 christos addr = get_reg (a0) + disp8 ();
677 1.1 christos break;
678 1.1 christos case 9:
679 1.1 christos addr = get_reg (a1) + disp8 ();
680 1.1 christos break;
681 1.1 christos case 10:
682 1.1 christos addr = get_reg (sb) * 8 + disp8 ();
683 1.1 christos break;
684 1.1 christos case 11:
685 1.1 christos addr = get_reg (fb) * 8 + sign_ext (disp8 (), 8);
686 1.1 christos break;
687 1.1 christos case 12:
688 1.1 christos addr = get_reg (a0) + disp16 ();
689 1.1 christos break;
690 1.1 christos case 13:
691 1.1 christos addr = get_reg (a1) + disp16 ();
692 1.1 christos break;
693 1.1 christos case 14:
694 1.1 christos addr = get_reg (sb) + disp16 ();
695 1.1 christos break;
696 1.1 christos case 15:
697 1.1 christos addr = disp16 ();
698 1.1 christos break;
699 1.1 christos }
700 1.1 christos
701 1.1 christos if (destcode < 6)
702 1.1 christos {
703 1.1 christos int d = disp8 ();
704 1.1 christos sd.mem = 0;
705 1.1 christos sd.mask = 1 << (d & 0x0f);
706 1.1 christos }
707 1.1 christos else
708 1.1 christos {
709 1.1 christos addr &= addr_mask;
710 1.1 christos sd.mem = 1;
711 1.1 christos sd.mask = 1 << (addr & 7);
712 1.1 christos sd.u.addr = addr >> 3;
713 1.1 christos }
714 1.1 christos return sd;
715 1.1 christos }
716 1.1 christos
717 1.1 christos srcdest
718 1.1 christos decode_bit11 (int op0)
719 1.1 christos {
720 1.1 christos srcdest sd;
721 1.1 christos sd.mask = 1 << (op0 & 7);
722 1.1 christos sd.mem = 1;
723 1.1 christos sd.u.addr = get_reg (sb) + disp8 ();
724 1.1 christos return sd;
725 1.1 christos }
726 1.1 christos
727 1.1 christos int
728 1.1 christos get_bit (srcdest sd)
729 1.1 christos {
730 1.1 christos int b;
731 1.1 christos if (sd.mem)
732 1.1 christos b = mem_get_qi (sd.u.addr) & sd.mask;
733 1.1 christos else
734 1.1 christos b = get_reg (sd.u.reg) & sd.mask;
735 1.1 christos return b ? 1 : 0;
736 1.1 christos }
737 1.1 christos
738 1.1 christos void
739 1.1 christos put_bit (srcdest sd, int val)
740 1.1 christos {
741 1.1 christos int b;
742 1.1 christos if (sd.mem)
743 1.1 christos b = mem_get_qi (sd.u.addr);
744 1.1 christos else
745 1.1 christos b = get_reg (sd.u.reg);
746 1.1 christos if (val)
747 1.1 christos b |= sd.mask;
748 1.1 christos else
749 1.1 christos b &= ~sd.mask;
750 1.1 christos if (sd.mem)
751 1.1 christos mem_put_qi (sd.u.addr, b);
752 1.1 christos else
753 1.1 christos put_reg (sd.u.reg, b);
754 1.1 christos }
755 1.1 christos
756 1.1 christos int
757 1.1 christos get_bit2 (srcdest sd, int bit)
758 1.1 christos {
759 1.1 christos int b;
760 1.1 christos if (sd.mem)
761 1.1 christos b = mem_get_qi (sd.u.addr + (bit >> 3)) & (1 << (bit & 7));
762 1.1 christos else
763 1.1 christos b = get_reg (sd.u.reg) & (1 << bit);
764 1.1 christos return b ? 1 : 0;
765 1.1 christos }
766 1.1 christos
767 1.1 christos void
768 1.1 christos put_bit2 (srcdest sd, int bit, int val)
769 1.1 christos {
770 1.1 christos int b;
771 1.1 christos if (sd.mem)
772 1.1 christos b = mem_get_qi (sd.u.addr + (bit >> 3));
773 1.1 christos else
774 1.1 christos b = get_reg (sd.u.reg);
775 1.1 christos if (val)
776 1.1 christos b |= (1 << (bit & 7));
777 1.1 christos else
778 1.1 christos b &= ~(1 << (bit & 7));
779 1.1 christos if (sd.mem)
780 1.1 christos mem_put_qi (sd.u.addr + (bit >> 3), b);
781 1.1 christos else
782 1.1 christos put_reg (sd.u.reg, b);
783 1.1 christos }
784