ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/cebix/BasiliskII/src/uae_cpu/gencpu.c
Revision: 1.14
Committed: 2001-07-13T10:13:57Z (23 years, 4 months ago) by gbeauche
Content type: text/plain
Branch: MAIN
Changes since 1.13: +45 -356 lines
Log Message:
- merged some code from uae-0.8.16

File Contents

# Content
1 /*
2 * UAE - The Un*x Amiga Emulator
3 *
4 * MC68000 emulation generator
5 *
6 * This is a fairly stupid program that generates a lot of case labels that
7 * can be #included in a switch statement.
8 * As an alternative, it can generate functions that handle specific
9 * MC68000 instructions, plus a prototype header file and a function pointer
10 * array to look up the function for an opcode.
11 * Error checking is bad, an illegal table68k file will cause the program to
12 * call abort().
13 * The generated code is sometimes sub-optimal, an optimizing compiler should
14 * take care of this.
15 *
16 * Copyright 1995, 1996 Bernd Schmidt
17 */
18
19 #include <ctype.h>
20 #include <stdio.h>
21 #include <stdlib.h>
22 #include <string.h>
23
24 #include "sysdeps.h"
25 #include "readcpu.h"
26
27 #if defined(SPARC_V8_ASSEMBLY) || defined(SPARC_V9_ASSEMBLY)
28 #define SPARC_ASSEMBLY 0
29 #endif
30
31 #define BOOL_TYPE "int"
32
33 static FILE *headerfile;
34 static FILE *stblfile;
35
36 static int using_prefetch;
37 static int using_exception_3;
38 static int cpu_level;
39
40 /* For the current opcode, the next lower level that will have different code.
41 * Initialized to -1 for each opcode. If it remains unchanged, indicates we
42 * are done with that opcode. */
43 static int next_cpu_level;
44
45 static int *opcode_map;
46 static int *opcode_next_clev;
47 static int *opcode_last_postfix;
48 static unsigned long *counts;
49
50 static void read_counts (void)
51 {
52 FILE *file;
53 unsigned long opcode, count, total;
54 char name[20];
55 int nr = 0;
56 memset (counts, 0, 65536 * sizeof *counts);
57
58 file = fopen ("frequent.68k", "r");
59 if (file) {
60 fscanf (file, "Total: %lu\n", &total);
61 while (fscanf (file, "%lx: %lu %s\n", &opcode, &count, name) == 3) {
62 opcode_next_clev[nr] = 4;
63 opcode_last_postfix[nr] = -1;
64 opcode_map[nr++] = opcode;
65 counts[opcode] = count;
66 }
67 fclose (file);
68 }
69 if (nr == nr_cpuop_funcs)
70 return;
71 for (opcode = 0; opcode < 0x10000; opcode++) {
72 if (table68k[opcode].handler == -1 && table68k[opcode].mnemo != i_ILLG
73 && counts[opcode] == 0)
74 {
75 opcode_next_clev[nr] = 4;
76 opcode_last_postfix[nr] = -1;
77 opcode_map[nr++] = opcode;
78 counts[opcode] = count;
79 }
80 }
81 if (nr != nr_cpuop_funcs)
82 abort ();
83 }
84
85 static char endlabelstr[80];
86 static int endlabelno = 0;
87 static int need_endlabel;
88
89 static int n_braces = 0;
90 static int m68k_pc_offset = 0;
91 static int insn_n_cycles;
92
93 static void start_brace (void)
94 {
95 n_braces++;
96 printf ("{");
97 }
98
99 static void close_brace (void)
100 {
101 assert (n_braces > 0);
102 n_braces--;
103 printf ("}");
104 }
105
106 static void finish_braces (void)
107 {
108 while (n_braces > 0)
109 close_brace ();
110 }
111
112 static void pop_braces (int to)
113 {
114 while (n_braces > to)
115 close_brace ();
116 }
117
118 static int bit_size (int size)
119 {
120 switch (size) {
121 case sz_byte: return 8;
122 case sz_word: return 16;
123 case sz_long: return 32;
124 default: abort ();
125 }
126 return 0;
127 }
128
129 static const char *bit_mask (int size)
130 {
131 switch (size) {
132 case sz_byte: return "0xff";
133 case sz_word: return "0xffff";
134 case sz_long: return "0xffffffff";
135 default: abort ();
136 }
137 return 0;
138 }
139
140 static const char *gen_nextilong (void)
141 {
142 static char buffer[80];
143 int r = m68k_pc_offset;
144 m68k_pc_offset += 4;
145
146 insn_n_cycles += 4;
147
148 if (using_prefetch)
149 sprintf (buffer, "get_ilong_prefetch(%d)", r);
150 else
151 sprintf (buffer, "get_ilong(%d)", r);
152 return buffer;
153 }
154
155 static const char *gen_nextiword (void)
156 {
157 static char buffer[80];
158 int r = m68k_pc_offset;
159 m68k_pc_offset += 2;
160
161 insn_n_cycles += 2;
162
163 if (using_prefetch)
164 sprintf (buffer, "get_iword_prefetch(%d)", r);
165 else
166 sprintf (buffer, "get_iword(%d)", r);
167 return buffer;
168 }
169
170 static const char *gen_nextibyte (void)
171 {
172 static char buffer[80];
173 int r = m68k_pc_offset;
174 m68k_pc_offset += 2;
175
176 insn_n_cycles += 2;
177
178 if (using_prefetch)
179 sprintf (buffer, "get_ibyte_prefetch(%d)", r);
180 else
181 sprintf (buffer, "get_ibyte(%d)", r);
182 return buffer;
183 }
184
185 static void fill_prefetch_0 (void)
186 {
187 if (using_prefetch)
188 printf ("fill_prefetch_0 ();\n");
189 }
190
191 static void fill_prefetch_2 (void)
192 {
193 if (using_prefetch)
194 printf ("fill_prefetch_2 ();\n");
195 }
196
197 static void swap_opcode (void)
198 {
199 printf ("#ifdef HAVE_GET_WORD_UNSWAPPED\n");
200 printf ("\topcode = ((opcode << 8) & 0xFF00) | ((opcode >> 8) & 0xFF);\n");
201 printf ("#endif\n");
202 }
203
204 static void sync_m68k_pc (void)
205 {
206 if (m68k_pc_offset == 0)
207 return;
208 printf ("m68k_incpc(%d);\n", m68k_pc_offset);
209 switch (m68k_pc_offset) {
210 case 0:
211 /*fprintf (stderr, "refilling prefetch at 0\n"); */
212 break;
213 case 2:
214 fill_prefetch_2 ();
215 break;
216 default:
217 fill_prefetch_0 ();
218 break;
219 }
220 m68k_pc_offset = 0;
221 }
222
223 /* getv == 1: fetch data; getv != 0: check for odd address. If movem != 0,
224 * the calling routine handles Apdi and Aipi modes.
225 * gb-- movem == 2 means the same thing but for a MOVE16 instruction */
226 static void genamode (amodes mode, char *reg, wordsizes size, char *name, int getv, int movem)
227 {
228 start_brace ();
229 switch (mode) {
230 case Dreg:
231 if (movem)
232 abort ();
233 if (getv == 1)
234 switch (size) {
235 case sz_byte:
236 #if defined(AMIGA) && !defined(WARPUP)
237 /* sam: I don't know why gcc.2.7.2.1 produces a code worse */
238 /* if it is not done like that: */
239 printf ("\tuae_s8 %s = ((uae_u8*)&m68k_dreg(regs, %s))[3];\n", name, reg);
240 #else
241 printf ("\tuae_s8 %s = m68k_dreg(regs, %s);\n", name, reg);
242 #endif
243 break;
244 case sz_word:
245 #if defined(AMIGA) && !defined(WARPUP)
246 printf ("\tuae_s16 %s = ((uae_s16*)&m68k_dreg(regs, %s))[1];\n", name, reg);
247 #else
248 printf ("\tuae_s16 %s = m68k_dreg(regs, %s);\n", name, reg);
249 #endif
250 break;
251 case sz_long:
252 printf ("\tuae_s32 %s = m68k_dreg(regs, %s);\n", name, reg);
253 break;
254 default:
255 abort ();
256 }
257 return;
258 case Areg:
259 if (movem)
260 abort ();
261 if (getv == 1)
262 switch (size) {
263 case sz_word:
264 printf ("\tuae_s16 %s = m68k_areg(regs, %s);\n", name, reg);
265 break;
266 case sz_long:
267 printf ("\tuae_s32 %s = m68k_areg(regs, %s);\n", name, reg);
268 break;
269 default:
270 abort ();
271 }
272 return;
273 case Aind:
274 printf ("\tuaecptr %sa = m68k_areg(regs, %s);\n", name, reg);
275 break;
276 case Aipi:
277 printf ("\tuaecptr %sa = m68k_areg(regs, %s);\n", name, reg);
278 break;
279 case Apdi:
280 switch (size) {
281 case sz_byte:
282 if (movem)
283 printf ("\tuaecptr %sa = m68k_areg(regs, %s);\n", name, reg);
284 else
285 printf ("\tuaecptr %sa = m68k_areg(regs, %s) - areg_byteinc[%s];\n", name, reg, reg);
286 break;
287 case sz_word:
288 printf ("\tuaecptr %sa = m68k_areg(regs, %s) - %d;\n", name, reg, movem ? 0 : 2);
289 break;
290 case sz_long:
291 printf ("\tuaecptr %sa = m68k_areg(regs, %s) - %d;\n", name, reg, movem ? 0 : 4);
292 break;
293 default:
294 abort ();
295 }
296 break;
297 case Ad16:
298 printf ("\tuaecptr %sa = m68k_areg(regs, %s) + (uae_s32)(uae_s16)%s;\n", name, reg, gen_nextiword ());
299 break;
300 case Ad8r:
301 if (cpu_level > 1) {
302 if (next_cpu_level < 1)
303 next_cpu_level = 1;
304 sync_m68k_pc ();
305 start_brace ();
306 printf ("\tuaecptr %sa = get_disp_ea_020(m68k_areg(regs, %s), next_iword());\n", name, reg);
307 } else
308 printf ("\tuaecptr %sa = get_disp_ea_000(m68k_areg(regs, %s), %s);\n", name, reg, gen_nextiword ());
309
310 break;
311 case PC16:
312 printf ("\tuaecptr %sa = m68k_getpc () + %d;\n", name, m68k_pc_offset);
313 printf ("\t%sa += (uae_s32)(uae_s16)%s;\n", name, gen_nextiword ());
314 break;
315 case PC8r:
316 if (cpu_level > 1) {
317 if (next_cpu_level < 1)
318 next_cpu_level = 1;
319 sync_m68k_pc ();
320 start_brace ();
321 printf ("\tuaecptr tmppc = m68k_getpc();\n");
322 printf ("\tuaecptr %sa = get_disp_ea_020(tmppc, next_iword());\n", name);
323 } else {
324 printf ("\tuaecptr tmppc = m68k_getpc() + %d;\n", m68k_pc_offset);
325 printf ("\tuaecptr %sa = get_disp_ea_000(tmppc, %s);\n", name, gen_nextiword ());
326 }
327
328 break;
329 case absw:
330 printf ("\tuaecptr %sa = (uae_s32)(uae_s16)%s;\n", name, gen_nextiword ());
331 break;
332 case absl:
333 printf ("\tuaecptr %sa = %s;\n", name, gen_nextilong ());
334 break;
335 case imm:
336 if (getv != 1)
337 abort ();
338 switch (size) {
339 case sz_byte:
340 printf ("\tuae_s8 %s = %s;\n", name, gen_nextibyte ());
341 break;
342 case sz_word:
343 printf ("\tuae_s16 %s = %s;\n", name, gen_nextiword ());
344 break;
345 case sz_long:
346 printf ("\tuae_s32 %s = %s;\n", name, gen_nextilong ());
347 break;
348 default:
349 abort ();
350 }
351 return;
352 case imm0:
353 if (getv != 1)
354 abort ();
355 printf ("\tuae_s8 %s = %s;\n", name, gen_nextibyte ());
356 return;
357 case imm1:
358 if (getv != 1)
359 abort ();
360 printf ("\tuae_s16 %s = %s;\n", name, gen_nextiword ());
361 return;
362 case imm2:
363 if (getv != 1)
364 abort ();
365 printf ("\tuae_s32 %s = %s;\n", name, gen_nextilong ());
366 return;
367 case immi:
368 if (getv != 1)
369 abort ();
370 printf ("\tuae_u32 %s = %s;\n", name, reg);
371 return;
372 default:
373 abort ();
374 }
375
376 /* We get here for all non-reg non-immediate addressing modes to
377 * actually fetch the value. */
378
379 if (using_exception_3 && getv != 0 && size != sz_byte) {
380 printf ("\tif ((%sa & 1) != 0) {\n", name);
381 printf ("\t\tlast_fault_for_exception_3 = %sa;\n", name);
382 printf ("\t\tlast_op_for_exception_3 = opcode;\n");
383 printf ("\t\tlast_addr_for_exception_3 = m68k_getpc() + %d;\n", m68k_pc_offset);
384 printf ("\t\tException(3, 0);\n");
385 printf ("\t\tgoto %s;\n", endlabelstr);
386 printf ("\t}\n");
387 need_endlabel = 1;
388 start_brace ();
389 }
390
391 if (getv == 1) {
392 switch (size) {
393 case sz_byte: insn_n_cycles += 2; break;
394 case sz_word: insn_n_cycles += 2; break;
395 case sz_long: insn_n_cycles += 4; break;
396 default: abort ();
397 }
398 start_brace ();
399 switch (size) {
400 case sz_byte: printf ("\tuae_s8 %s = get_byte(%sa);\n", name, name); break;
401 case sz_word: printf ("\tuae_s16 %s = get_word(%sa);\n", name, name); break;
402 case sz_long: printf ("\tuae_s32 %s = get_long(%sa);\n", name, name); break;
403 default: abort ();
404 }
405 }
406
407 /* We now might have to fix up the register for pre-dec or post-inc
408 * addressing modes. */
409 if (!movem)
410 switch (mode) {
411 case Aipi:
412 switch (size) {
413 case sz_byte:
414 printf ("\tm68k_areg(regs, %s) += areg_byteinc[%s];\n", reg, reg);
415 break;
416 case sz_word:
417 printf ("\tm68k_areg(regs, %s) += 2;\n", reg);
418 break;
419 case sz_long:
420 printf ("\tm68k_areg(regs, %s) += 4;\n", reg);
421 break;
422 default:
423 abort ();
424 }
425 break;
426 case Apdi:
427 printf ("\tm68k_areg (regs, %s) = %sa;\n", reg, name);
428 break;
429 default:
430 break;
431 }
432 }
433
434 static void genastore (char *from, amodes mode, char *reg, wordsizes size, char *to)
435 {
436 switch (mode) {
437 case Dreg:
438 switch (size) {
439 case sz_byte:
440 printf ("\tm68k_dreg(regs, %s) = (m68k_dreg(regs, %s) & ~0xff) | ((%s) & 0xff);\n", reg, reg, from);
441 break;
442 case sz_word:
443 printf ("\tm68k_dreg(regs, %s) = (m68k_dreg(regs, %s) & ~0xffff) | ((%s) & 0xffff);\n", reg, reg, from);
444 break;
445 case sz_long:
446 printf ("\tm68k_dreg(regs, %s) = (%s);\n", reg, from);
447 break;
448 default:
449 abort ();
450 }
451 break;
452 case Areg:
453 switch (size) {
454 case sz_word:
455 fprintf (stderr, "Foo\n");
456 printf ("\tm68k_areg(regs, %s) = (uae_s32)(uae_s16)(%s);\n", reg, from);
457 break;
458 case sz_long:
459 printf ("\tm68k_areg(regs, %s) = (%s);\n", reg, from);
460 break;
461 default:
462 abort ();
463 }
464 break;
465 case Aind:
466 case Aipi:
467 case Apdi:
468 case Ad16:
469 case Ad8r:
470 case absw:
471 case absl:
472 case PC16:
473 case PC8r:
474 if (using_prefetch)
475 sync_m68k_pc ();
476 switch (size) {
477 case sz_byte:
478 insn_n_cycles += 2;
479 printf ("\tput_byte(%sa,%s);\n", to, from);
480 break;
481 case sz_word:
482 insn_n_cycles += 2;
483 if (cpu_level < 2 && (mode == PC16 || mode == PC8r))
484 abort ();
485 printf ("\tput_word(%sa,%s);\n", to, from);
486 break;
487 case sz_long:
488 insn_n_cycles += 4;
489 if (cpu_level < 2 && (mode == PC16 || mode == PC8r))
490 abort ();
491 printf ("\tput_long(%sa,%s);\n", to, from);
492 break;
493 default:
494 abort ();
495 }
496 break;
497 case imm:
498 case imm0:
499 case imm1:
500 case imm2:
501 case immi:
502 abort ();
503 break;
504 default:
505 abort ();
506 }
507 }
508
509 static void genmovemel (uae_u16 opcode)
510 {
511 char getcode[100];
512 int size = table68k[opcode].size == sz_long ? 4 : 2;
513
514 if (table68k[opcode].size == sz_long) {
515 strcpy (getcode, "get_long(srca)");
516 } else {
517 strcpy (getcode, "(uae_s32)(uae_s16)get_word(srca)");
518 }
519
520 printf ("\tuae_u16 mask = %s;\n", gen_nextiword ());
521 printf ("\tunsigned int dmask = mask & 0xff, amask = (mask >> 8) & 0xff;\n");
522 genamode (table68k[opcode].dmode, "dstreg", table68k[opcode].size, "src", 2, 1);
523 start_brace ();
524 printf ("\twhile (dmask) { m68k_dreg(regs, movem_index1[dmask]) = %s; srca += %d; dmask = movem_next[dmask]; }\n",
525 getcode, size);
526 printf ("\twhile (amask) { m68k_areg(regs, movem_index1[amask]) = %s; srca += %d; amask = movem_next[amask]; }\n",
527 getcode, size);
528
529 if (table68k[opcode].dmode == Aipi)
530 printf ("\tm68k_areg(regs, dstreg) = srca;\n");
531 }
532
533 static void genmovemle (uae_u16 opcode)
534 {
535 char putcode[100];
536 int size = table68k[opcode].size == sz_long ? 4 : 2;
537 if (table68k[opcode].size == sz_long) {
538 strcpy (putcode, "put_long(srca,");
539 } else {
540 strcpy (putcode, "put_word(srca,");
541 }
542
543 printf ("\tuae_u16 mask = %s;\n", gen_nextiword ());
544 genamode (table68k[opcode].dmode, "dstreg", table68k[opcode].size, "src", 2, 1);
545 if (using_prefetch)
546 sync_m68k_pc ();
547
548 start_brace ();
549 if (table68k[opcode].dmode == Apdi) {
550 printf ("\tuae_u16 amask = mask & 0xff, dmask = (mask >> 8) & 0xff;\n");
551 printf ("\twhile (amask) { srca -= %d; %s m68k_areg(regs, movem_index2[amask])); amask = movem_next[amask]; }\n",
552 size, putcode);
553 printf ("\twhile (dmask) { srca -= %d; %s m68k_dreg(regs, movem_index2[dmask])); dmask = movem_next[dmask]; }\n",
554 size, putcode);
555 printf ("\tm68k_areg(regs, dstreg) = srca;\n");
556 } else {
557 printf ("\tuae_u16 dmask = mask & 0xff, amask = (mask >> 8) & 0xff;\n");
558 printf ("\twhile (dmask) { %s m68k_dreg(regs, movem_index1[dmask])); srca += %d; dmask = movem_next[dmask]; }\n",
559 putcode, size);
560 printf ("\twhile (amask) { %s m68k_areg(regs, movem_index1[amask])); srca += %d; amask = movem_next[amask]; }\n",
561 putcode, size);
562 }
563 }
564
565 static void duplicate_carry (void)
566 {
567 printf ("\tCOPY_CARRY;\n");
568 }
569
570 typedef enum {
571 flag_logical_noclobber, flag_logical, flag_add, flag_sub, flag_cmp, flag_addx, flag_subx, flag_zn,
572 flag_av, flag_sv
573 } flagtypes;
574
575 static void genflags_normal (flagtypes type, wordsizes size, char *value, char *src, char *dst)
576 {
577 char vstr[100], sstr[100], dstr[100];
578 char usstr[100], udstr[100];
579 char unsstr[100], undstr[100];
580
581 switch (size) {
582 case sz_byte:
583 strcpy (vstr, "((uae_s8)(");
584 strcpy (usstr, "((uae_u8)(");
585 break;
586 case sz_word:
587 strcpy (vstr, "((uae_s16)(");
588 strcpy (usstr, "((uae_u16)(");
589 break;
590 case sz_long:
591 strcpy (vstr, "((uae_s32)(");
592 strcpy (usstr, "((uae_u32)(");
593 break;
594 default:
595 abort ();
596 }
597 strcpy (unsstr, usstr);
598
599 strcpy (sstr, vstr);
600 strcpy (dstr, vstr);
601 strcat (vstr, value);
602 strcat (vstr, "))");
603 strcat (dstr, dst);
604 strcat (dstr, "))");
605 strcat (sstr, src);
606 strcat (sstr, "))");
607
608 strcpy (udstr, usstr);
609 strcat (udstr, dst);
610 strcat (udstr, "))");
611 strcat (usstr, src);
612 strcat (usstr, "))");
613
614 strcpy (undstr, unsstr);
615 strcat (unsstr, "-");
616 strcat (undstr, "~");
617 strcat (undstr, dst);
618 strcat (undstr, "))");
619 strcat (unsstr, src);
620 strcat (unsstr, "))");
621
622 switch (type) {
623 case flag_logical_noclobber:
624 case flag_logical:
625 case flag_zn:
626 case flag_av:
627 case flag_sv:
628 case flag_addx:
629 case flag_subx:
630 break;
631
632 case flag_add:
633 start_brace ();
634 printf ("uae_u32 %s = %s + %s;\n", value, dstr, sstr);
635 break;
636 case flag_sub:
637 case flag_cmp:
638 start_brace ();
639 printf ("uae_u32 %s = %s - %s;\n", value, dstr, sstr);
640 break;
641 }
642
643 switch (type) {
644 case flag_logical_noclobber:
645 case flag_logical:
646 case flag_zn:
647 break;
648
649 case flag_add:
650 case flag_sub:
651 case flag_addx:
652 case flag_subx:
653 case flag_cmp:
654 case flag_av:
655 case flag_sv:
656 start_brace ();
657 printf ("\t" BOOL_TYPE " flgs = %s < 0;\n", sstr);
658 printf ("\t" BOOL_TYPE " flgo = %s < 0;\n", dstr);
659 printf ("\t" BOOL_TYPE " flgn = %s < 0;\n", vstr);
660 break;
661 }
662
663 switch (type) {
664 case flag_logical:
665 printf ("\tCLEAR_CZNV;\n");
666 printf ("\tSET_ZFLG (%s == 0);\n", vstr);
667 printf ("\tSET_NFLG (%s < 0);\n", vstr);
668 break;
669 case flag_logical_noclobber:
670 printf ("\tSET_ZFLG (%s == 0);\n", vstr);
671 printf ("\tSET_NFLG (%s < 0);\n", vstr);
672 break;
673 case flag_av:
674 printf ("\tSET_VFLG ((flgs ^ flgn) & (flgo ^ flgn));\n");
675 break;
676 case flag_sv:
677 printf ("\tSET_VFLG ((flgs ^ flgo) & (flgn ^ flgo));\n");
678 break;
679 case flag_zn:
680 printf ("\tSET_ZFLG (GET_ZFLG & (%s == 0));\n", vstr);
681 printf ("\tSET_NFLG (%s < 0);\n", vstr);
682 break;
683 case flag_add:
684 printf ("\tSET_ZFLG (%s == 0);\n", vstr);
685 printf ("\tSET_VFLG ((flgs ^ flgn) & (flgo ^ flgn));\n");
686 printf ("\tSET_CFLG (%s < %s);\n", undstr, usstr);
687 duplicate_carry ();
688 printf ("\tSET_NFLG (flgn != 0);\n");
689 break;
690 case flag_sub:
691 printf ("\tSET_ZFLG (%s == 0);\n", vstr);
692 printf ("\tSET_VFLG ((flgs ^ flgo) & (flgn ^ flgo));\n");
693 printf ("\tSET_CFLG (%s > %s);\n", usstr, udstr);
694 duplicate_carry ();
695 printf ("\tSET_NFLG (flgn != 0);\n");
696 break;
697 case flag_addx:
698 printf ("\tSET_VFLG ((flgs ^ flgn) & (flgo ^ flgn));\n"); /* minterm SON: 0x42 */
699 printf ("\tSET_CFLG (flgs ^ ((flgs ^ flgo) & (flgo ^ flgn)));\n"); /* minterm SON: 0xD4 */
700 duplicate_carry ();
701 break;
702 case flag_subx:
703 printf ("\tSET_VFLG ((flgs ^ flgo) & (flgo ^ flgn));\n"); /* minterm SON: 0x24 */
704 printf ("\tSET_CFLG (flgs ^ ((flgs ^ flgn) & (flgo ^ flgn)));\n"); /* minterm SON: 0xB2 */
705 duplicate_carry ();
706 break;
707 case flag_cmp:
708 printf ("\tSET_ZFLG (%s == 0);\n", vstr);
709 printf ("\tSET_VFLG ((flgs != flgo) && (flgn != flgo));\n");
710 printf ("\tSET_CFLG (%s > %s);\n", usstr, udstr);
711 printf ("\tSET_NFLG (flgn != 0);\n");
712 break;
713 }
714 }
715
716 static void genflags (flagtypes type, wordsizes size, char *value, char *src, char *dst)
717 {
718 /* Temporarily deleted 68k/ARM flag optimizations. I'd prefer to have
719 them in the appropriate m68k.h files and use just one copy of this
720 code here. The API can be changed if necessary. */
721 #ifdef OPTIMIZED_FLAGS
722 switch (type) {
723 case flag_add:
724 case flag_sub:
725 start_brace ();
726 printf ("\tuae_u32 %s;\n", value);
727 break;
728
729 default:
730 break;
731 }
732
733 /* At least some of those casts are fairly important! */
734 switch (type) {
735 case flag_logical_noclobber:
736 printf ("\t{uae_u32 oldcznv = GET_CZNV & ~(FLAGVAL_Z | FLAGVAL_N);\n");
737 if (strcmp (value, "0") == 0) {
738 printf ("\tSET_CZNV (olcznv | FLAGVAL_Z);\n");
739 } else {
740 switch (size) {
741 case sz_byte: printf ("\toptflag_testb ((uae_s8)(%s));\n", value); break;
742 case sz_word: printf ("\toptflag_testw ((uae_s16)(%s));\n", value); break;
743 case sz_long: printf ("\toptflag_testl ((uae_s32)(%s));\n", value); break;
744 }
745 printf ("\tIOR_CZNV (oldcznv);\n");
746 }
747 printf ("\t}\n");
748 return;
749 case flag_logical:
750 if (strcmp (value, "0") == 0) {
751 printf ("\tSET_CZNV (FLAGVAL_Z);\n");
752 } else {
753 switch (size) {
754 case sz_byte: printf ("\toptflag_testb ((uae_s8)(%s));\n", value); break;
755 case sz_word: printf ("\toptflag_testw ((uae_s16)(%s));\n", value); break;
756 case sz_long: printf ("\toptflag_testl ((uae_s32)(%s));\n", value); break;
757 }
758 }
759 return;
760
761 case flag_add:
762 switch (size) {
763 case sz_byte: printf ("\toptflag_addb (%s, (uae_s8)(%s), (uae_s8)(%s));\n", value, src, dst); break;
764 case sz_word: printf ("\toptflag_addw (%s, (uae_s16)(%s), (uae_s16)(%s));\n", value, src, dst); break;
765 case sz_long: printf ("\toptflag_addl (%s, (uae_s32)(%s), (uae_s32)(%s));\n", value, src, dst); break;
766 }
767 return;
768
769 case flag_sub:
770 switch (size) {
771 case sz_byte: printf ("\toptflag_subb (%s, (uae_s8)(%s), (uae_s8)(%s));\n", value, src, dst); break;
772 case sz_word: printf ("\toptflag_subw (%s, (uae_s16)(%s), (uae_s16)(%s));\n", value, src, dst); break;
773 case sz_long: printf ("\toptflag_subl (%s, (uae_s32)(%s), (uae_s32)(%s));\n", value, src, dst); break;
774 }
775 return;
776
777 case flag_cmp:
778 switch (size) {
779 case sz_byte: printf ("\toptflag_cmpb ((uae_s8)(%s), (uae_s8)(%s));\n", src, dst); break;
780 case sz_word: printf ("\toptflag_cmpw ((uae_s16)(%s), (uae_s16)(%s));\n", src, dst); break;
781 case sz_long: printf ("\toptflag_cmpl ((uae_s32)(%s), (uae_s32)(%s));\n", src, dst); break;
782 }
783 return;
784
785 default:
786 break;
787 }
788 #endif
789
790 genflags_normal (type, size, value, src, dst);
791 }
792
793 static void force_range_for_rox (const char *var, wordsizes size)
794 {
795 /* Could do a modulo operation here... which one is faster? */
796 switch (size) {
797 case sz_long:
798 printf ("\tif (%s >= 33) %s -= 33;\n", var, var);
799 break;
800 case sz_word:
801 printf ("\tif (%s >= 34) %s -= 34;\n", var, var);
802 printf ("\tif (%s >= 17) %s -= 17;\n", var, var);
803 break;
804 case sz_byte:
805 printf ("\tif (%s >= 36) %s -= 36;\n", var, var);
806 printf ("\tif (%s >= 18) %s -= 18;\n", var, var);
807 printf ("\tif (%s >= 9) %s -= 9;\n", var, var);
808 break;
809 }
810 }
811
812 static const char *cmask (wordsizes size)
813 {
814 switch (size) {
815 case sz_byte: return "0x80";
816 case sz_word: return "0x8000";
817 case sz_long: return "0x80000000";
818 default: abort ();
819 }
820 }
821
822 static int source_is_imm1_8 (struct instr *i)
823 {
824 return i->stype == 3;
825 }
826
827 static void gen_opcode (unsigned long int opcode)
828 {
829 struct instr *curi = table68k + opcode;
830 insn_n_cycles = 2;
831
832 start_brace ();
833 #if 0
834 printf ("uae_u8 *m68k_pc = regs.pc_p;\n");
835 #endif
836 m68k_pc_offset = 2;
837 switch (curi->plev) {
838 case 0: /* not privileged */
839 break;
840 case 1: /* unprivileged only on 68000 */
841 if (cpu_level == 0)
842 break;
843 if (next_cpu_level < 0)
844 next_cpu_level = 0;
845
846 /* fall through */
847 case 2: /* priviledged */
848 printf ("if (!regs.s) { Exception(8,0); goto %s; }\n", endlabelstr);
849 need_endlabel = 1;
850 start_brace ();
851 break;
852 case 3: /* privileged if size == word */
853 if (curi->size == sz_byte)
854 break;
855 printf ("if (!regs.s) { Exception(8,0); goto %s; }\n", endlabelstr);
856 need_endlabel = 1;
857 start_brace ();
858 break;
859 }
860 switch (curi->mnemo) {
861 case i_OR:
862 case i_AND:
863 case i_EOR:
864 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
865 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
866 printf ("\tsrc %c= dst;\n", curi->mnemo == i_OR ? '|' : curi->mnemo == i_AND ? '&' : '^');
867 genflags (flag_logical, curi->size, "src", "", "");
868 genastore ("src", curi->dmode, "dstreg", curi->size, "dst");
869 break;
870 case i_ORSR:
871 case i_EORSR:
872 printf ("\tMakeSR();\n");
873 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
874 if (curi->size == sz_byte) {
875 printf ("\tsrc &= 0xFF;\n");
876 }
877 printf ("\tregs.sr %c= src;\n", curi->mnemo == i_EORSR ? '^' : '|');
878 printf ("\tMakeFromSR();\n");
879 break;
880 case i_ANDSR:
881 printf ("\tMakeSR();\n");
882 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
883 if (curi->size == sz_byte) {
884 printf ("\tsrc |= 0xFF00;\n");
885 }
886 printf ("\tregs.sr &= src;\n");
887 printf ("\tMakeFromSR();\n");
888 break;
889 case i_SUB:
890 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
891 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
892 start_brace ();
893 genflags (flag_sub, curi->size, "newv", "src", "dst");
894 genastore ("newv", curi->dmode, "dstreg", curi->size, "dst");
895 break;
896 case i_SUBA:
897 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
898 genamode (curi->dmode, "dstreg", sz_long, "dst", 1, 0);
899 start_brace ();
900 printf ("\tuae_u32 newv = dst - src;\n");
901 genastore ("newv", curi->dmode, "dstreg", sz_long, "dst");
902 break;
903 case i_SUBX:
904 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
905 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
906 start_brace ();
907 printf ("\tuae_u32 newv = dst - src - (GET_XFLG ? 1 : 0);\n");
908 genflags (flag_subx, curi->size, "newv", "src", "dst");
909 genflags (flag_zn, curi->size, "newv", "", "");
910 genastore ("newv", curi->dmode, "dstreg", curi->size, "dst");
911 break;
912 case i_SBCD:
913 /* Let's hope this works... */
914 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
915 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
916 start_brace ();
917 printf ("\tuae_u16 newv_lo = (dst & 0xF) - (src & 0xF) - (GET_XFLG ? 1 : 0);\n");
918 printf ("\tuae_u16 newv_hi = (dst & 0xF0) - (src & 0xF0);\n");
919 printf ("\tuae_u16 newv;\n");
920 printf ("\tint cflg;\n");
921 printf ("\tif (newv_lo > 9) { newv_lo-=6; newv_hi-=0x10; }\n");
922 printf ("\tnewv = newv_hi + (newv_lo & 0xF);");
923 printf ("\tcflg = (newv_hi & 0x1F0) > 0x90;\n");
924 printf ("\tSET_CFLG (cflg);\n");
925 duplicate_carry ();
926 printf ("\tif (cflg) newv -= 0x60;\n");
927 genflags (flag_zn, curi->size, "newv", "", "");
928 genflags (flag_sv, curi->size, "newv", "src", "dst");
929 genastore ("newv", curi->dmode, "dstreg", curi->size, "dst");
930 break;
931 case i_ADD:
932 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
933 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
934 start_brace ();
935 genflags (flag_add, curi->size, "newv", "src", "dst");
936 genastore ("newv", curi->dmode, "dstreg", curi->size, "dst");
937 break;
938 case i_ADDA:
939 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
940 genamode (curi->dmode, "dstreg", sz_long, "dst", 1, 0);
941 start_brace ();
942 printf ("\tuae_u32 newv = dst + src;\n");
943 genastore ("newv", curi->dmode, "dstreg", sz_long, "dst");
944 break;
945 case i_ADDX:
946 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
947 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
948 start_brace ();
949 printf ("\tuae_u32 newv = dst + src + (GET_XFLG ? 1 : 0);\n");
950 genflags (flag_addx, curi->size, "newv", "src", "dst");
951 genflags (flag_zn, curi->size, "newv", "", "");
952 genastore ("newv", curi->dmode, "dstreg", curi->size, "dst");
953 break;
954 case i_ABCD:
955 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
956 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
957 start_brace ();
958 printf ("\tuae_u16 newv_lo = (src & 0xF) + (dst & 0xF) + (GET_XFLG ? 1 : 0);\n");
959 printf ("\tuae_u16 newv_hi = (src & 0xF0) + (dst & 0xF0);\n");
960 printf ("\tuae_u16 newv;\n");
961 printf ("\tint cflg;\n");
962 printf ("\tif (newv_lo > 9) { newv_lo +=6; }\n");
963 printf ("\tnewv = newv_hi + newv_lo;");
964 printf ("\tcflg = (newv & 0x1F0) > 0x90;\n");
965 printf ("\tSET_CFLG (cflg);\n");
966 duplicate_carry ();
967 printf ("\tif (cflg) newv += 0x60;\n");
968 genflags (flag_zn, curi->size, "newv", "", "");
969 genflags (flag_sv, curi->size, "newv", "src", "dst");
970 genastore ("newv", curi->dmode, "dstreg", curi->size, "dst");
971 break;
972 case i_NEG:
973 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
974 start_brace ();
975 genflags (flag_sub, curi->size, "dst", "src", "0");
976 genastore ("dst", curi->smode, "srcreg", curi->size, "src");
977 break;
978 case i_NEGX:
979 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
980 start_brace ();
981 printf ("\tuae_u32 newv = 0 - src - (GET_XFLG ? 1 : 0);\n");
982 genflags (flag_subx, curi->size, "newv", "src", "0");
983 genflags (flag_zn, curi->size, "newv", "", "");
984 genastore ("newv", curi->smode, "srcreg", curi->size, "src");
985 break;
986 case i_NBCD:
987 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
988 start_brace ();
989 printf ("\tuae_u16 newv_lo = - (src & 0xF) - (GET_XFLG ? 1 : 0);\n");
990 printf ("\tuae_u16 newv_hi = - (src & 0xF0);\n");
991 printf ("\tuae_u16 newv;\n");
992 printf ("\tint cflg;\n");
993 printf ("\tif (newv_lo > 9) { newv_lo-=6; newv_hi-=0x10; }\n");
994 printf ("\tnewv = newv_hi + (newv_lo & 0xF);");
995 printf ("\tcflg = cflg = (newv_hi & 0x1F0) > 0x90;\n");
996 printf ("\tSET_CFLG (cflg);\n");
997 duplicate_carry();
998 printf ("\tif (cflg) newv -= 0x60;\n");
999 genflags (flag_zn, curi->size, "newv", "", "");
1000 genastore ("newv", curi->smode, "srcreg", curi->size, "src");
1001 break;
1002 case i_CLR:
1003 genamode (curi->smode, "srcreg", curi->size, "src", 2, 0);
1004 genflags (flag_logical, curi->size, "0", "", "");
1005 genastore ("0", curi->smode, "srcreg", curi->size, "src");
1006 break;
1007 case i_NOT:
1008 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1009 start_brace ();
1010 printf ("\tuae_u32 dst = ~src;\n");
1011 genflags (flag_logical, curi->size, "dst", "", "");
1012 genastore ("dst", curi->smode, "srcreg", curi->size, "src");
1013 break;
1014 case i_TST:
1015 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1016 genflags (flag_logical, curi->size, "src", "", "");
1017 break;
1018 case i_BTST:
1019 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1020 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1021 if (curi->size == sz_byte)
1022 printf ("\tsrc &= 7;\n");
1023 else
1024 printf ("\tsrc &= 31;\n");
1025 printf ("\tSET_ZFLG (1 ^ ((dst >> src) & 1));\n");
1026 break;
1027 case i_BCHG:
1028 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1029 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1030 if (curi->size == sz_byte)
1031 printf ("\tsrc &= 7;\n");
1032 else
1033 printf ("\tsrc &= 31;\n");
1034 printf ("\tdst ^= (1 << src);\n");
1035 printf ("\tSET_ZFLG (((uae_u32)dst & (1 << src)) >> src);\n");
1036 genastore ("dst", curi->dmode, "dstreg", curi->size, "dst");
1037 break;
1038 case i_BCLR:
1039 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1040 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1041 if (curi->size == sz_byte)
1042 printf ("\tsrc &= 7;\n");
1043 else
1044 printf ("\tsrc &= 31;\n");
1045 printf ("\tSET_ZFLG (1 ^ ((dst >> src) & 1));\n");
1046 printf ("\tdst &= ~(1 << src);\n");
1047 genastore ("dst", curi->dmode, "dstreg", curi->size, "dst");
1048 break;
1049 case i_BSET:
1050 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1051 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1052 if (curi->size == sz_byte)
1053 printf ("\tsrc &= 7;\n");
1054 else
1055 printf ("\tsrc &= 31;\n");
1056 printf ("\tSET_ZFLG (1 ^ ((dst >> src) & 1));\n");
1057 printf ("\tdst |= (1 << src);\n");
1058 genastore ("dst", curi->dmode, "dstreg", curi->size, "dst");
1059 break;
1060 case i_CMPM:
1061 case i_CMP:
1062 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1063 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1064 start_brace ();
1065 genflags (flag_cmp, curi->size, "newv", "src", "dst");
1066 break;
1067 case i_CMPA:
1068 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1069 genamode (curi->dmode, "dstreg", sz_long, "dst", 1, 0);
1070 start_brace ();
1071 genflags (flag_cmp, sz_long, "newv", "src", "dst");
1072 break;
1073 /* The next two are coded a little unconventional, but they are doing
1074 * weird things... */
1075 case i_MVPRM:
1076 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1077
1078 printf ("\tuaecptr memp = m68k_areg(regs, dstreg) + (uae_s32)(uae_s16)%s;\n", gen_nextiword ());
1079 if (curi->size == sz_word) {
1080 printf ("\tput_byte(memp, src >> 8); put_byte(memp + 2, src);\n");
1081 } else {
1082 printf ("\tput_byte(memp, src >> 24); put_byte(memp + 2, src >> 16);\n");
1083 printf ("\tput_byte(memp + 4, src >> 8); put_byte(memp + 6, src);\n");
1084 }
1085 break;
1086 case i_MVPMR:
1087 printf ("\tuaecptr memp = m68k_areg(regs, srcreg) + (uae_s32)(uae_s16)%s;\n", gen_nextiword ());
1088 genamode (curi->dmode, "dstreg", curi->size, "dst", 2, 0);
1089 if (curi->size == sz_word) {
1090 printf ("\tuae_u16 val = (get_byte(memp) << 8) + get_byte(memp + 2);\n");
1091 } else {
1092 printf ("\tuae_u32 val = (get_byte(memp) << 24) + (get_byte(memp + 2) << 16)\n");
1093 printf (" + (get_byte(memp + 4) << 8) + get_byte(memp + 6);\n");
1094 }
1095 genastore ("val", curi->dmode, "dstreg", curi->size, "dst");
1096 break;
1097 case i_MOVE:
1098 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1099 genamode (curi->dmode, "dstreg", curi->size, "dst", 2, 0);
1100 genflags (flag_logical, curi->size, "src", "", "");
1101 genastore ("src", curi->dmode, "dstreg", curi->size, "dst");
1102 break;
1103 case i_MOVEA:
1104 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1105 genamode (curi->dmode, "dstreg", curi->size, "dst", 2, 0);
1106 if (curi->size == sz_word) {
1107 printf ("\tuae_u32 val = (uae_s32)(uae_s16)src;\n");
1108 } else {
1109 printf ("\tuae_u32 val = src;\n");
1110 }
1111 genastore ("val", curi->dmode, "dstreg", sz_long, "dst");
1112 break;
1113 case i_MVSR2:
1114 genamode (curi->smode, "srcreg", sz_word, "src", 2, 0);
1115 printf ("\tMakeSR();\n");
1116 if (curi->size == sz_byte)
1117 genastore ("regs.sr & 0xff", curi->smode, "srcreg", sz_word, "src");
1118 else
1119 genastore ("regs.sr", curi->smode, "srcreg", sz_word, "src");
1120 break;
1121 case i_MV2SR:
1122 genamode (curi->smode, "srcreg", sz_word, "src", 1, 0);
1123 if (curi->size == sz_byte)
1124 printf ("\tMakeSR();\n\tregs.sr &= 0xFF00;\n\tregs.sr |= src & 0xFF;\n");
1125 else {
1126 printf ("\tregs.sr = src;\n");
1127 }
1128 printf ("\tMakeFromSR();\n");
1129 break;
1130 case i_SWAP:
1131 genamode (curi->smode, "srcreg", sz_long, "src", 1, 0);
1132 start_brace ();
1133 printf ("\tuae_u32 dst = ((src >> 16)&0xFFFF) | ((src&0xFFFF)<<16);\n");
1134 genflags (flag_logical, sz_long, "dst", "", "");
1135 genastore ("dst", curi->smode, "srcreg", sz_long, "src");
1136 break;
1137 case i_EXG:
1138 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1139 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1140 genastore ("dst", curi->smode, "srcreg", curi->size, "src");
1141 genastore ("src", curi->dmode, "dstreg", curi->size, "dst");
1142 break;
1143 case i_EXT:
1144 genamode (curi->smode, "srcreg", sz_long, "src", 1, 0);
1145 start_brace ();
1146 switch (curi->size) {
1147 case sz_byte: printf ("\tuae_u32 dst = (uae_s32)(uae_s8)src;\n"); break;
1148 case sz_word: printf ("\tuae_u16 dst = (uae_s16)(uae_s8)src;\n"); break;
1149 case sz_long: printf ("\tuae_u32 dst = (uae_s32)(uae_s16)src;\n"); break;
1150 default: abort ();
1151 }
1152 genflags (flag_logical,
1153 curi->size == sz_word ? sz_word : sz_long, "dst", "", "");
1154 genastore ("dst", curi->smode, "srcreg",
1155 curi->size == sz_word ? sz_word : sz_long, "src");
1156 break;
1157 case i_MVMEL:
1158 genmovemel (opcode);
1159 break;
1160 case i_MVMLE:
1161 genmovemle (opcode);
1162 break;
1163 case i_TRAP:
1164 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1165 sync_m68k_pc ();
1166 printf ("\tException(src+32,0);\n");
1167 m68k_pc_offset = 0;
1168 break;
1169 case i_MVR2USP:
1170 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1171 printf ("\tregs.usp = src;\n");
1172 break;
1173 case i_MVUSP2R:
1174 genamode (curi->smode, "srcreg", curi->size, "src", 2, 0);
1175 genastore ("regs.usp", curi->smode, "srcreg", curi->size, "src");
1176 break;
1177 case i_RESET:
1178 break;
1179 case i_NOP:
1180 break;
1181 case i_STOP:
1182 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1183 printf ("\tregs.sr = src;\n");
1184 printf ("\tMakeFromSR();\n");
1185 printf ("\tm68k_setstopped(1);\n");
1186 break;
1187 case i_RTE:
1188 if (cpu_level == 0) {
1189 genamode (Aipi, "7", sz_word, "sr", 1, 0);
1190 genamode (Aipi, "7", sz_long, "pc", 1, 0);
1191 printf ("\tregs.sr = sr; m68k_setpc_rte(pc);\n");
1192 fill_prefetch_0 ();
1193 printf ("\tMakeFromSR();\n");
1194 } else {
1195 int old_brace_level = n_braces;
1196 if (next_cpu_level < 0)
1197 next_cpu_level = 0;
1198 printf ("\tuae_u16 newsr; uae_u32 newpc; for (;;) {\n");
1199 genamode (Aipi, "7", sz_word, "sr", 1, 0);
1200 genamode (Aipi, "7", sz_long, "pc", 1, 0);
1201 genamode (Aipi, "7", sz_word, "format", 1, 0);
1202 printf ("\tnewsr = sr; newpc = pc;\n");
1203 printf ("\tif ((format & 0xF000) == 0x0000) { break; }\n");
1204 printf ("\telse if ((format & 0xF000) == 0x1000) { ; }\n");
1205 printf ("\telse if ((format & 0xF000) == 0x2000) { m68k_areg(regs, 7) += 4; break; }\n");
1206 printf ("\telse if ((format & 0xF000) == 0x3000) { m68k_areg(regs, 7) += 4; break; }\n");
1207 printf ("\telse if ((format & 0xF000) == 0x7000) { m68k_areg(regs, 7) += 52; break; }\n");
1208 printf ("\telse if ((format & 0xF000) == 0x8000) { m68k_areg(regs, 7) += 50; break; }\n");
1209 printf ("\telse if ((format & 0xF000) == 0x9000) { m68k_areg(regs, 7) += 12; break; }\n");
1210 printf ("\telse if ((format & 0xF000) == 0xa000) { m68k_areg(regs, 7) += 24; break; }\n");
1211 printf ("\telse if ((format & 0xF000) == 0xb000) { m68k_areg(regs, 7) += 84; break; }\n");
1212 printf ("\telse { Exception(14,0); goto %s; }\n", endlabelstr);
1213 printf ("\tregs.sr = newsr; MakeFromSR();\n}\n");
1214 pop_braces (old_brace_level);
1215 printf ("\tregs.sr = newsr; MakeFromSR();\n");
1216 printf ("\tm68k_setpc_rte(newpc);\n");
1217 fill_prefetch_0 ();
1218 need_endlabel = 1;
1219 }
1220 /* PC is set and prefetch filled. */
1221 m68k_pc_offset = 0;
1222 break;
1223 case i_RTD:
1224 genamode (Aipi, "7", sz_long, "pc", 1, 0);
1225 genamode (curi->smode, "srcreg", curi->size, "offs", 1, 0);
1226 printf ("\tm68k_areg(regs, 7) += offs;\n");
1227 printf ("\tm68k_setpc_rte(pc);\n");
1228 fill_prefetch_0 ();
1229 /* PC is set and prefetch filled. */
1230 m68k_pc_offset = 0;
1231 break;
1232 case i_LINK:
1233 genamode (Apdi, "7", sz_long, "old", 2, 0);
1234 genamode (curi->smode, "srcreg", sz_long, "src", 1, 0);
1235 genastore ("src", Apdi, "7", sz_long, "old");
1236 genastore ("m68k_areg(regs, 7)", curi->smode, "srcreg", sz_long, "src");
1237 genamode (curi->dmode, "dstreg", curi->size, "offs", 1, 0);
1238 printf ("\tm68k_areg(regs, 7) += offs;\n");
1239 break;
1240 case i_UNLK:
1241 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1242 printf ("\tm68k_areg(regs, 7) = src;\n");
1243 genamode (Aipi, "7", sz_long, "old", 1, 0);
1244 genastore ("old", curi->smode, "srcreg", curi->size, "src");
1245 break;
1246 case i_RTS:
1247 printf ("\tm68k_do_rts();\n");
1248 fill_prefetch_0 ();
1249 m68k_pc_offset = 0;
1250 break;
1251 case i_TRAPV:
1252 sync_m68k_pc ();
1253 printf ("\tif (GET_VFLG) { Exception(7,m68k_getpc()); goto %s; }\n", endlabelstr);
1254 need_endlabel = 1;
1255 break;
1256 case i_RTR:
1257 printf ("\tMakeSR();\n");
1258 genamode (Aipi, "7", sz_word, "sr", 1, 0);
1259 genamode (Aipi, "7", sz_long, "pc", 1, 0);
1260 printf ("\tregs.sr &= 0xFF00; sr &= 0xFF;\n");
1261 printf ("\tregs.sr |= sr; m68k_setpc(pc);\n");
1262 fill_prefetch_0 ();
1263 printf ("\tMakeFromSR();\n");
1264 m68k_pc_offset = 0;
1265 break;
1266 case i_JSR:
1267 genamode (curi->smode, "srcreg", curi->size, "src", 0, 0);
1268 printf ("\tm68k_do_jsr(m68k_getpc() + %d, srca);\n", m68k_pc_offset);
1269 fill_prefetch_0 ();
1270 m68k_pc_offset = 0;
1271 break;
1272 case i_JMP:
1273 genamode (curi->smode, "srcreg", curi->size, "src", 0, 0);
1274 printf ("\tm68k_setpc(srca);\n");
1275 fill_prefetch_0 ();
1276 m68k_pc_offset = 0;
1277 break;
1278 case i_BSR:
1279 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1280 printf ("\tuae_s32 s = (uae_s32)src + 2;\n");
1281 if (using_exception_3) {
1282 printf ("\tif (src & 1) {\n");
1283 printf ("\tlast_addr_for_exception_3 = m68k_getpc() + 2;\n");
1284 printf ("\t\tlast_fault_for_exception_3 = m68k_getpc() + s;\n");
1285 printf ("\t\tlast_op_for_exception_3 = opcode; Exception(3,0); goto %s;\n", endlabelstr);
1286 printf ("\t}\n");
1287 need_endlabel = 1;
1288 }
1289 printf ("\tm68k_do_bsr(m68k_getpc() + %d, s);\n", m68k_pc_offset);
1290 fill_prefetch_0 ();
1291 m68k_pc_offset = 0;
1292 break;
1293 case i_Bcc:
1294 if (curi->size == sz_long) {
1295 if (cpu_level < 2) {
1296 printf ("\tm68k_incpc(2);\n");
1297 printf ("\tif (!cctrue(%d)) goto %s;\n", curi->cc, endlabelstr);
1298 printf ("\t\tlast_addr_for_exception_3 = m68k_getpc() + 2;\n");
1299 printf ("\t\tlast_fault_for_exception_3 = m68k_getpc() + 1;\n");
1300 printf ("\t\tlast_op_for_exception_3 = opcode; Exception(3,0); goto %s;\n", endlabelstr);
1301 need_endlabel = 1;
1302 } else {
1303 if (next_cpu_level < 1)
1304 next_cpu_level = 1;
1305 }
1306 }
1307 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1308 printf ("\tif (!cctrue(%d)) goto didnt_jump;\n", curi->cc);
1309 if (using_exception_3) {
1310 printf ("\tif (src & 1) {\n");
1311 printf ("\t\tlast_addr_for_exception_3 = m68k_getpc() + 2;\n");
1312 printf ("\t\tlast_fault_for_exception_3 = m68k_getpc() + 2 + (uae_s32)src;\n");
1313 printf ("\t\tlast_op_for_exception_3 = opcode; Exception(3,0); goto %s;\n", endlabelstr);
1314 printf ("\t}\n");
1315 need_endlabel = 1;
1316 }
1317 #ifdef USE_COMPILER
1318 printf ("\tm68k_setpc_bcc(m68k_getpc() + 2 + (uae_s32)src);\n");
1319 #else
1320 printf ("\tm68k_incpc ((uae_s32)src + 2);\n");
1321 #endif
1322 fill_prefetch_0 ();
1323 printf ("\tgoto %s;\n", endlabelstr);
1324 printf ("didnt_jump:;\n");
1325 need_endlabel = 1;
1326 break;
1327 case i_LEA:
1328 genamode (curi->smode, "srcreg", curi->size, "src", 0, 0);
1329 genamode (curi->dmode, "dstreg", curi->size, "dst", 2, 0);
1330 genastore ("srca", curi->dmode, "dstreg", curi->size, "dst");
1331 break;
1332 case i_PEA:
1333 genamode (curi->smode, "srcreg", curi->size, "src", 0, 0);
1334 genamode (Apdi, "7", sz_long, "dst", 2, 0);
1335 genastore ("srca", Apdi, "7", sz_long, "dst");
1336 break;
1337 case i_DBcc:
1338 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1339 genamode (curi->dmode, "dstreg", curi->size, "offs", 1, 0);
1340
1341 printf ("\tif (!cctrue(%d)) {\n", curi->cc);
1342 genastore ("(src-1)", curi->smode, "srcreg", curi->size, "src");
1343
1344 printf ("\t\tif (src) {\n");
1345 if (using_exception_3) {
1346 printf ("\t\t\tif (offs & 1) {\n");
1347 printf ("\t\t\tlast_addr_for_exception_3 = m68k_getpc() + 2;\n");
1348 printf ("\t\t\tlast_fault_for_exception_3 = m68k_getpc() + 2 + (uae_s32)offs + 2;\n");
1349 printf ("\t\t\tlast_op_for_exception_3 = opcode; Exception(3,0); goto %s;\n", endlabelstr);
1350 printf ("\t\t}\n");
1351 need_endlabel = 1;
1352 }
1353 #ifdef USE_COMPILER
1354 printf ("\t\t\tm68k_setpc_bcc(m68k_getpc() + (uae_s32)offs + 2);\n");
1355 #else
1356 printf ("\t\t\tm68k_incpc((uae_s32)offs + 2);\n");
1357 #endif
1358 fill_prefetch_0 ();
1359 printf ("\t\tgoto %s;\n", endlabelstr);
1360 printf ("\t\t}\n");
1361 printf ("\t}\n");
1362 need_endlabel = 1;
1363 break;
1364 case i_Scc:
1365 genamode (curi->smode, "srcreg", curi->size, "src", 2, 0);
1366 start_brace ();
1367 printf ("\tint val = cctrue(%d) ? 0xff : 0;\n", curi->cc);
1368 genastore ("val", curi->smode, "srcreg", curi->size, "src");
1369 break;
1370 case i_DIVU:
1371 printf ("\tuaecptr oldpc = m68k_getpc();\n");
1372 genamode (curi->smode, "srcreg", sz_word, "src", 1, 0);
1373 genamode (curi->dmode, "dstreg", sz_long, "dst", 1, 0);
1374 sync_m68k_pc ();
1375 /* Clear V flag when dividing by zero - Alcatraz Odyssey demo depends
1376 * on this (actually, it's doing a DIVS). */
1377 printf ("\tif (src == 0) { SET_VFLG (0); Exception (5, oldpc); goto %s; } else {\n", endlabelstr);
1378 printf ("\tuae_u32 newv = (uae_u32)dst / (uae_u32)(uae_u16)src;\n");
1379 printf ("\tuae_u32 rem = (uae_u32)dst %% (uae_u32)(uae_u16)src;\n");
1380 /* The N flag appears to be set each time there is an overflow.
1381 * Weird. */
1382 printf ("\tif (newv > 0xffff) { SET_VFLG (1); SET_NFLG (1); SET_CFLG (0); } else\n\t{\n");
1383 genflags (flag_logical, sz_word, "newv", "", "");
1384 printf ("\tnewv = (newv & 0xffff) | ((uae_u32)rem << 16);\n");
1385 genastore ("newv", curi->dmode, "dstreg", sz_long, "dst");
1386 printf ("\t}\n");
1387 printf ("\t}\n");
1388 insn_n_cycles += 68;
1389 need_endlabel = 1;
1390 break;
1391 case i_DIVS:
1392 printf ("\tuaecptr oldpc = m68k_getpc();\n");
1393 genamode (curi->smode, "srcreg", sz_word, "src", 1, 0);
1394 genamode (curi->dmode, "dstreg", sz_long, "dst", 1, 0);
1395 sync_m68k_pc ();
1396 printf ("\tif (src == 0) { SET_VFLG (0); Exception(5,oldpc); goto %s; } else {\n", endlabelstr);
1397 printf ("\tuae_s32 newv = (uae_s32)dst / (uae_s32)(uae_s16)src;\n");
1398 printf ("\tuae_u16 rem = (uae_s32)dst %% (uae_s32)(uae_s16)src;\n");
1399 printf ("\tif ((newv & 0xffff8000) != 0 && (newv & 0xffff8000) != 0xffff8000) { SET_VFLG (1); SET_NFLG (1); SET_CFLG (0); } else\n\t{\n");
1400 printf ("\tif (((uae_s16)rem < 0) != ((uae_s32)dst < 0)) rem = -rem;\n");
1401 genflags (flag_logical, sz_word, "newv", "", "");
1402 printf ("\tnewv = (newv & 0xffff) | ((uae_u32)rem << 16);\n");
1403 genastore ("newv", curi->dmode, "dstreg", sz_long, "dst");
1404 printf ("\t}\n");
1405 printf ("\t}\n");
1406 insn_n_cycles += 72;
1407 need_endlabel = 1;
1408 break;
1409 case i_MULU:
1410 genamode (curi->smode, "srcreg", sz_word, "src", 1, 0);
1411 genamode (curi->dmode, "dstreg", sz_word, "dst", 1, 0);
1412 start_brace ();
1413 printf ("\tuae_u32 newv = (uae_u32)(uae_u16)dst * (uae_u32)(uae_u16)src;\n");
1414 genflags (flag_logical, sz_long, "newv", "", "");
1415 genastore ("newv", curi->dmode, "dstreg", sz_long, "dst");
1416 insn_n_cycles += 32;
1417 break;
1418 case i_MULS:
1419 genamode (curi->smode, "srcreg", sz_word, "src", 1, 0);
1420 genamode (curi->dmode, "dstreg", sz_word, "dst", 1, 0);
1421 start_brace ();
1422 printf ("\tuae_u32 newv = (uae_s32)(uae_s16)dst * (uae_s32)(uae_s16)src;\n");
1423 genflags (flag_logical, sz_long, "newv", "", "");
1424 genastore ("newv", curi->dmode, "dstreg", sz_long, "dst");
1425 insn_n_cycles += 32;
1426 break;
1427 case i_CHK:
1428 printf ("\tuaecptr oldpc = m68k_getpc();\n");
1429 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1430 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1431 printf ("\tif ((uae_s32)dst < 0) { SET_NFLG (1); Exception(6,oldpc); goto %s; }\n", endlabelstr);
1432 printf ("\telse if (dst > src) { SET_NFLG (0); Exception(6,oldpc); goto %s; }\n", endlabelstr);
1433 need_endlabel = 1;
1434 break;
1435
1436 case i_CHK2:
1437 printf ("\tuaecptr oldpc = m68k_getpc();\n");
1438 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
1439 genamode (curi->dmode, "dstreg", curi->size, "dst", 2, 0);
1440 printf ("\t{uae_s32 upper,lower,reg = regs.regs[(extra >> 12) & 15];\n");
1441 switch (curi->size) {
1442 case sz_byte:
1443 printf ("\tlower=(uae_s32)(uae_s8)get_byte(dsta); upper = (uae_s32)(uae_s8)get_byte(dsta+1);\n");
1444 printf ("\tif ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s8)reg;\n");
1445 break;
1446 case sz_word:
1447 printf ("\tlower=(uae_s32)(uae_s16)get_word(dsta); upper = (uae_s32)(uae_s16)get_word(dsta+2);\n");
1448 printf ("\tif ((extra & 0x8000) == 0) reg = (uae_s32)(uae_s16)reg;\n");
1449 break;
1450 case sz_long:
1451 printf ("\tlower=get_long(dsta); upper = get_long(dsta+4);\n");
1452 break;
1453 default:
1454 abort ();
1455 }
1456 printf ("\tSET_ZFLG (upper == reg || lower == reg);\n");
1457 printf ("\tSET_CFLG (lower <= upper ? reg < lower || reg > upper : reg > upper || reg < lower);\n");
1458 printf ("\tif ((extra & 0x800) && GET_CFLG) { Exception(6,oldpc); goto %s; }\n}\n", endlabelstr);
1459 need_endlabel = 1;
1460 break;
1461
1462 case i_ASR:
1463 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1464 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1465 start_brace ();
1466 switch (curi->size) {
1467 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1468 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1469 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1470 default: abort ();
1471 }
1472 printf ("\tuae_u32 sign = (%s & val) >> %d;\n", cmask (curi->size), bit_size (curi->size) - 1);
1473 printf ("\tcnt &= 63;\n");
1474 printf ("\tCLEAR_CZNV;\n");
1475 printf ("\tif (cnt >= %d) {\n", bit_size (curi->size));
1476 printf ("\t\tval = %s & (uae_u32)-sign;\n", bit_mask (curi->size));
1477 printf ("\t\tSET_CFLG (sign);\n");
1478 duplicate_carry ();
1479 if (source_is_imm1_8 (curi))
1480 printf ("\t} else {\n");
1481 else
1482 printf ("\t} else if (cnt > 0) {\n");
1483 printf ("\t\tval >>= cnt - 1;\n");
1484 printf ("\t\tSET_CFLG (val & 1);\n");
1485 duplicate_carry ();
1486 printf ("\t\tval >>= 1;\n");
1487 printf ("\t\tval |= (%s << (%d - cnt)) & (uae_u32)-sign;\n",
1488 bit_mask (curi->size),
1489 bit_size (curi->size));
1490 printf ("\t\tval &= %s;\n", bit_mask (curi->size));
1491 printf ("\t}\n");
1492 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1493 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1494 break;
1495 case i_ASL:
1496 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1497 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1498 start_brace ();
1499 switch (curi->size) {
1500 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1501 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1502 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1503 default: abort ();
1504 }
1505 printf ("\tcnt &= 63;\n");
1506 printf ("\tCLEAR_CZNV;\n");
1507 printf ("\tif (cnt >= %d) {\n", bit_size (curi->size));
1508 printf ("\t\tSET_VFLG (val != 0);\n");
1509 printf ("\t\tSET_CFLG (cnt == %d ? val & 1 : 0);\n",
1510 bit_size (curi->size));
1511 duplicate_carry ();
1512 printf ("\t\tval = 0;\n");
1513 if (source_is_imm1_8 (curi))
1514 printf ("\t} else {\n");
1515 else
1516 printf ("\t} else if (cnt > 0) {\n");
1517 printf ("\t\tuae_u32 mask = (%s << (%d - cnt)) & %s;\n",
1518 bit_mask (curi->size),
1519 bit_size (curi->size) - 1,
1520 bit_mask (curi->size));
1521 printf ("\t\tSET_VFLG ((val & mask) != mask && (val & mask) != 0);\n");
1522 printf ("\t\tval <<= cnt - 1;\n");
1523 printf ("\t\tSET_CFLG ((val & %s) >> %d);\n", cmask (curi->size), bit_size (curi->size) - 1);
1524 duplicate_carry ();
1525 printf ("\t\tval <<= 1;\n");
1526 printf ("\t\tval &= %s;\n", bit_mask (curi->size));
1527 printf ("\t}\n");
1528 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1529 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1530 break;
1531 case i_LSR:
1532 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1533 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1534 start_brace ();
1535 switch (curi->size) {
1536 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1537 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1538 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1539 default: abort ();
1540 }
1541 printf ("\tcnt &= 63;\n");
1542 printf ("\tCLEAR_CZNV;\n");
1543 printf ("\tif (cnt >= %d) {\n", bit_size (curi->size));
1544 printf ("\t\tSET_CFLG ((cnt == %d) & (val >> %d));\n",
1545 bit_size (curi->size), bit_size (curi->size) - 1);
1546 duplicate_carry ();
1547 printf ("\t\tval = 0;\n");
1548 if (source_is_imm1_8 (curi))
1549 printf ("\t} else {\n");
1550 else
1551 printf ("\t} else if (cnt > 0) {\n");
1552 printf ("\t\tval >>= cnt - 1;\n");
1553 printf ("\t\tSET_CFLG (val & 1);\n");
1554 duplicate_carry ();
1555 printf ("\t\tval >>= 1;\n");
1556 printf ("\t}\n");
1557 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1558 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1559 break;
1560 case i_LSL:
1561 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1562 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1563 start_brace ();
1564 switch (curi->size) {
1565 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1566 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1567 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1568 default: abort ();
1569 }
1570 printf ("\tcnt &= 63;\n");
1571 printf ("\tCLEAR_CZNV;\n");
1572 printf ("\tif (cnt >= %d) {\n", bit_size (curi->size));
1573 printf ("\t\tSET_CFLG (cnt == %d ? val & 1 : 0);\n",
1574 bit_size (curi->size));
1575 duplicate_carry ();
1576 printf ("\t\tval = 0;\n");
1577 if (source_is_imm1_8 (curi))
1578 printf ("\t} else {\n");
1579 else
1580 printf ("\t} else if (cnt > 0) {\n");
1581 printf ("\t\tval <<= (cnt - 1);\n");
1582 printf ("\t\tSET_CFLG ((val & %s) >> %d);\n", cmask (curi->size), bit_size (curi->size) - 1);
1583 duplicate_carry ();
1584 printf ("\t\tval <<= 1;\n");
1585 printf ("\tval &= %s;\n", bit_mask (curi->size));
1586 printf ("\t}\n");
1587 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1588 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1589 break;
1590 case i_ROL:
1591 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1592 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1593 start_brace ();
1594 switch (curi->size) {
1595 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1596 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1597 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1598 default: abort ();
1599 }
1600 printf ("\tcnt &= 63;\n");
1601 printf ("\tCLEAR_CZNV;\n");
1602 if (source_is_imm1_8 (curi))
1603 printf ("{");
1604 else
1605 printf ("\tif (cnt > 0) {\n");
1606 printf ("\tuae_u32 loval;\n");
1607 printf ("\tcnt &= %d;\n", bit_size (curi->size) - 1);
1608 printf ("\tloval = val >> (%d - cnt);\n", bit_size (curi->size));
1609 printf ("\tval <<= cnt;\n");
1610 printf ("\tval |= loval;\n");
1611 printf ("\tval &= %s;\n", bit_mask (curi->size));
1612 printf ("\tSET_CFLG (val & 1);\n");
1613 printf ("}\n");
1614 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1615 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1616 break;
1617 case i_ROR:
1618 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1619 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1620 start_brace ();
1621 switch (curi->size) {
1622 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1623 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1624 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1625 default: abort ();
1626 }
1627 printf ("\tcnt &= 63;\n");
1628 printf ("\tCLEAR_CZNV;\n");
1629 if (source_is_imm1_8 (curi))
1630 printf ("{");
1631 else
1632 printf ("\tif (cnt > 0) {");
1633 printf ("\tuae_u32 hival;\n");
1634 printf ("\tcnt &= %d;\n", bit_size (curi->size) - 1);
1635 printf ("\thival = val << (%d - cnt);\n", bit_size (curi->size));
1636 printf ("\tval >>= cnt;\n");
1637 printf ("\tval |= hival;\n");
1638 printf ("\tval &= %s;\n", bit_mask (curi->size));
1639 printf ("\tSET_CFLG ((val & %s) >> %d);\n", cmask (curi->size), bit_size (curi->size) - 1);
1640 printf ("\t}\n");
1641 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1642 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1643 break;
1644 case i_ROXL:
1645 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1646 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1647 start_brace ();
1648 switch (curi->size) {
1649 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1650 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1651 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1652 default: abort ();
1653 }
1654 printf ("\tcnt &= 63;\n");
1655 printf ("\tCLEAR_CZNV;\n");
1656 if (source_is_imm1_8 (curi))
1657 printf ("{");
1658 else {
1659 force_range_for_rox ("cnt", curi->size);
1660 printf ("\tif (cnt > 0) {\n");
1661 }
1662 printf ("\tcnt--;\n");
1663 printf ("\t{\n\tuae_u32 carry;\n");
1664 printf ("\tuae_u32 loval = val >> (%d - cnt);\n", bit_size (curi->size) - 1);
1665 printf ("\tcarry = loval & 1;\n");
1666 printf ("\tval = (((val << 1) | GET_XFLG) << cnt) | (loval >> 1);\n");
1667 printf ("\tSET_XFLG (carry);\n");
1668 printf ("\tval &= %s;\n", bit_mask (curi->size));
1669 printf ("\t} }\n");
1670 printf ("\tSET_CFLG (GET_XFLG);\n");
1671 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1672 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1673 break;
1674 case i_ROXR:
1675 genamode (curi->smode, "srcreg", curi->size, "cnt", 1, 0);
1676 genamode (curi->dmode, "dstreg", curi->size, "data", 1, 0);
1677 start_brace ();
1678 switch (curi->size) {
1679 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1680 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1681 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1682 default: abort ();
1683 }
1684 printf ("\tcnt &= 63;\n");
1685 printf ("\tCLEAR_CZNV;\n");
1686 if (source_is_imm1_8 (curi))
1687 printf ("{");
1688 else {
1689 force_range_for_rox ("cnt", curi->size);
1690 printf ("\tif (cnt > 0) {\n");
1691 }
1692 printf ("\tcnt--;\n");
1693 printf ("\t{\n\tuae_u32 carry;\n");
1694 printf ("\tuae_u32 hival = (val << 1) | GET_XFLG;\n");
1695 printf ("\thival <<= (%d - cnt);\n", bit_size (curi->size) - 1);
1696 printf ("\tval >>= cnt;\n");
1697 printf ("\tcarry = val & 1;\n");
1698 printf ("\tval >>= 1;\n");
1699 printf ("\tval |= hival;\n");
1700 printf ("\tSET_XFLG (carry);\n");
1701 printf ("\tval &= %s;\n", bit_mask (curi->size));
1702 printf ("\t} }\n");
1703 printf ("\tSET_CFLG (GET_XFLG);\n");
1704 genflags (flag_logical_noclobber, curi->size, "val", "", "");
1705 genastore ("val", curi->dmode, "dstreg", curi->size, "data");
1706 break;
1707 case i_ASRW:
1708 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1709 start_brace ();
1710 switch (curi->size) {
1711 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1712 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1713 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1714 default: abort ();
1715 }
1716 printf ("\tuae_u32 sign = %s & val;\n", cmask (curi->size));
1717 printf ("\tuae_u32 cflg = val & 1;\n");
1718 printf ("\tval = (val >> 1) | sign;\n");
1719 genflags (flag_logical, curi->size, "val", "", "");
1720 printf ("\tSET_CFLG (cflg);\n");
1721 duplicate_carry ();
1722 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1723 break;
1724 case i_ASLW:
1725 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1726 start_brace ();
1727 switch (curi->size) {
1728 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1729 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1730 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1731 default: abort ();
1732 }
1733 printf ("\tuae_u32 sign = %s & val;\n", cmask (curi->size));
1734 printf ("\tuae_u32 sign2;\n");
1735 printf ("\tval <<= 1;\n");
1736 genflags (flag_logical, curi->size, "val", "", "");
1737 printf ("\tsign2 = %s & val;\n", cmask (curi->size));
1738 printf ("\tSET_CFLG (sign != 0);\n");
1739 duplicate_carry ();
1740
1741 printf ("\tSET_VFLG (GET_VFLG | (sign2 != sign));\n");
1742 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1743 break;
1744 case i_LSRW:
1745 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1746 start_brace ();
1747 switch (curi->size) {
1748 case sz_byte: printf ("\tuae_u32 val = (uae_u8)data;\n"); break;
1749 case sz_word: printf ("\tuae_u32 val = (uae_u16)data;\n"); break;
1750 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1751 default: abort ();
1752 }
1753 printf ("\tuae_u32 carry = val & 1;\n");
1754 printf ("\tval >>= 1;\n");
1755 genflags (flag_logical, curi->size, "val", "", "");
1756 printf ("SET_CFLG (carry);\n");
1757 duplicate_carry ();
1758 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1759 break;
1760 case i_LSLW:
1761 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1762 start_brace ();
1763 switch (curi->size) {
1764 case sz_byte: printf ("\tuae_u8 val = data;\n"); break;
1765 case sz_word: printf ("\tuae_u16 val = data;\n"); break;
1766 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1767 default: abort ();
1768 }
1769 printf ("\tuae_u32 carry = val & %s;\n", cmask (curi->size));
1770 printf ("\tval <<= 1;\n");
1771 genflags (flag_logical, curi->size, "val", "", "");
1772 printf ("SET_CFLG (carry >> %d);\n", bit_size (curi->size) - 1);
1773 duplicate_carry ();
1774 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1775 break;
1776 case i_ROLW:
1777 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1778 start_brace ();
1779 switch (curi->size) {
1780 case sz_byte: printf ("\tuae_u8 val = data;\n"); break;
1781 case sz_word: printf ("\tuae_u16 val = data;\n"); break;
1782 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1783 default: abort ();
1784 }
1785 printf ("\tuae_u32 carry = val & %s;\n", cmask (curi->size));
1786 printf ("\tval <<= 1;\n");
1787 printf ("\tif (carry) val |= 1;\n");
1788 genflags (flag_logical, curi->size, "val", "", "");
1789 printf ("SET_CFLG (carry >> %d);\n", bit_size (curi->size) - 1);
1790 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1791 break;
1792 case i_RORW:
1793 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1794 start_brace ();
1795 switch (curi->size) {
1796 case sz_byte: printf ("\tuae_u8 val = data;\n"); break;
1797 case sz_word: printf ("\tuae_u16 val = data;\n"); break;
1798 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1799 default: abort ();
1800 }
1801 printf ("\tuae_u32 carry = val & 1;\n");
1802 printf ("\tval >>= 1;\n");
1803 printf ("\tif (carry) val |= %s;\n", cmask (curi->size));
1804 genflags (flag_logical, curi->size, "val", "", "");
1805 printf ("SET_CFLG (carry);\n");
1806 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1807 break;
1808 case i_ROXLW:
1809 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1810 start_brace ();
1811 switch (curi->size) {
1812 case sz_byte: printf ("\tuae_u8 val = data;\n"); break;
1813 case sz_word: printf ("\tuae_u16 val = data;\n"); break;
1814 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1815 default: abort ();
1816 }
1817 printf ("\tuae_u32 carry = val & %s;\n", cmask (curi->size));
1818 printf ("\tval <<= 1;\n");
1819 printf ("\tif (GET_XFLG) val |= 1;\n");
1820 genflags (flag_logical, curi->size, "val", "", "");
1821 printf ("SET_CFLG (carry >> %d);\n", bit_size (curi->size) - 1);
1822 duplicate_carry ();
1823 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1824 break;
1825 case i_ROXRW:
1826 genamode (curi->smode, "srcreg", curi->size, "data", 1, 0);
1827 start_brace ();
1828 switch (curi->size) {
1829 case sz_byte: printf ("\tuae_u8 val = data;\n"); break;
1830 case sz_word: printf ("\tuae_u16 val = data;\n"); break;
1831 case sz_long: printf ("\tuae_u32 val = data;\n"); break;
1832 default: abort ();
1833 }
1834 printf ("\tuae_u32 carry = val & 1;\n");
1835 printf ("\tval >>= 1;\n");
1836 printf ("\tif (GET_XFLG) val |= %s;\n", cmask (curi->size));
1837 genflags (flag_logical, curi->size, "val", "", "");
1838 printf ("SET_CFLG (carry);\n");
1839 duplicate_carry ();
1840 genastore ("val", curi->smode, "srcreg", curi->size, "data");
1841 break;
1842 case i_MOVEC2:
1843 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1844 start_brace ();
1845 printf ("\tint regno = (src >> 12) & 15;\n");
1846 printf ("\tuae_u32 *regp = regs.regs + regno;\n");
1847 printf ("\tif (! m68k_movec2(src & 0xFFF, regp)) goto %s;\n", endlabelstr);
1848 break;
1849 case i_MOVE2C:
1850 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1851 start_brace ();
1852 printf ("\tint regno = (src >> 12) & 15;\n");
1853 printf ("\tuae_u32 *regp = regs.regs + regno;\n");
1854 printf ("\tif (! m68k_move2c(src & 0xFFF, regp)) goto %s;\n", endlabelstr);
1855 break;
1856 case i_CAS:
1857 {
1858 int old_brace_level;
1859 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
1860 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1861 start_brace ();
1862 printf ("\tint ru = (src >> 6) & 7;\n");
1863 printf ("\tint rc = src & 7;\n");
1864 genflags (flag_cmp, curi->size, "newv", "m68k_dreg(regs, rc)", "dst");
1865 printf ("\tif (GET_ZFLG)");
1866 old_brace_level = n_braces;
1867 start_brace ();
1868 genastore ("(m68k_dreg(regs, ru))", curi->dmode, "dstreg", curi->size, "dst");
1869 pop_braces (old_brace_level);
1870 printf ("else");
1871 start_brace ();
1872 printf ("m68k_dreg(regs, rc) = dst;\n");
1873 pop_braces (old_brace_level);
1874 }
1875 break;
1876 case i_CAS2:
1877 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
1878 printf ("\tuae_u32 rn1 = regs.regs[(extra >> 28) & 15];\n");
1879 printf ("\tuae_u32 rn2 = regs.regs[(extra >> 12) & 15];\n");
1880 if (curi->size == sz_word) {
1881 int old_brace_level = n_braces;
1882 printf ("\tuae_u16 dst1 = get_word(rn1), dst2 = get_word(rn2);\n");
1883 genflags (flag_cmp, curi->size, "newv", "m68k_dreg(regs, (extra >> 16) & 7)", "dst1");
1884 printf ("\tif (GET_ZFLG) {\n");
1885 genflags (flag_cmp, curi->size, "newv", "m68k_dreg(regs, extra & 7)", "dst2");
1886 printf ("\tif (GET_ZFLG) {\n");
1887 printf ("\tput_word(rn1, m68k_dreg(regs, (extra >> 22) & 7));\n");
1888 printf ("\tput_word(rn1, m68k_dreg(regs, (extra >> 6) & 7));\n");
1889 printf ("\t}}\n");
1890 pop_braces (old_brace_level);
1891 printf ("\tif (! GET_ZFLG) {\n");
1892 printf ("\tm68k_dreg(regs, (extra >> 22) & 7) = (m68k_dreg(regs, (extra >> 22) & 7) & ~0xffff) | (dst1 & 0xffff);\n");
1893 printf ("\tm68k_dreg(regs, (extra >> 6) & 7) = (m68k_dreg(regs, (extra >> 6) & 7) & ~0xffff) | (dst2 & 0xffff);\n");
1894 printf ("\t}\n");
1895 } else {
1896 int old_brace_level = n_braces;
1897 printf ("\tuae_u32 dst1 = get_long(rn1), dst2 = get_long(rn2);\n");
1898 genflags (flag_cmp, curi->size, "newv", "m68k_dreg(regs, (extra >> 16) & 7)", "dst1");
1899 printf ("\tif (GET_ZFLG) {\n");
1900 genflags (flag_cmp, curi->size, "newv", "m68k_dreg(regs, extra & 7)", "dst2");
1901 printf ("\tif (GET_ZFLG) {\n");
1902 printf ("\tput_long(rn1, m68k_dreg(regs, (extra >> 22) & 7));\n");
1903 printf ("\tput_long(rn1, m68k_dreg(regs, (extra >> 6) & 7));\n");
1904 printf ("\t}}\n");
1905 pop_braces (old_brace_level);
1906 printf ("\tif (! GET_ZFLG) {\n");
1907 printf ("\tm68k_dreg(regs, (extra >> 22) & 7) = dst1;\n");
1908 printf ("\tm68k_dreg(regs, (extra >> 6) & 7) = dst2;\n");
1909 printf ("\t}\n");
1910 }
1911 break;
1912 case i_MOVES: /* ignore DFC and SFC because we have no MMU */
1913 {
1914 int old_brace_level;
1915 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
1916 printf ("\tif (extra & 0x800)\n");
1917 old_brace_level = n_braces;
1918 start_brace ();
1919 printf ("\tuae_u32 src = regs.regs[(extra >> 12) & 15];\n");
1920 genamode (curi->dmode, "dstreg", curi->size, "dst", 2, 0);
1921 genastore ("src", curi->dmode, "dstreg", curi->size, "dst");
1922 pop_braces (old_brace_level);
1923 printf ("else");
1924 start_brace ();
1925 genamode (curi->dmode, "dstreg", curi->size, "src", 1, 0);
1926 printf ("\tif (extra & 0x8000) {\n");
1927 switch (curi->size) {
1928 case sz_byte: printf ("\tm68k_areg(regs, (extra >> 12) & 7) = (uae_s32)(uae_s8)src;\n"); break;
1929 case sz_word: printf ("\tm68k_areg(regs, (extra >> 12) & 7) = (uae_s32)(uae_s16)src;\n"); break;
1930 case sz_long: printf ("\tm68k_areg(regs, (extra >> 12) & 7) = src;\n"); break;
1931 default: abort ();
1932 }
1933 printf ("\t} else {\n");
1934 genastore ("src", Dreg, "(extra >> 12) & 7", curi->size, "");
1935 printf ("\t}\n");
1936 pop_braces (old_brace_level);
1937 }
1938 break;
1939 case i_BKPT: /* only needed for hardware emulators */
1940 sync_m68k_pc ();
1941 printf ("\top_illg(opcode);\n");
1942 break;
1943 case i_CALLM: /* not present in 68030 */
1944 sync_m68k_pc ();
1945 printf ("\top_illg(opcode);\n");
1946 break;
1947 case i_RTM: /* not present in 68030 */
1948 sync_m68k_pc ();
1949 printf ("\top_illg(opcode);\n");
1950 break;
1951 case i_TRAPcc:
1952 if (curi->smode != am_unknown && curi->smode != am_illg)
1953 genamode (curi->smode, "srcreg", curi->size, "dummy", 1, 0);
1954 printf ("\tif (cctrue(%d)) { Exception(7,m68k_getpc()); goto %s; }\n", curi->cc, endlabelstr);
1955 need_endlabel = 1;
1956 break;
1957 case i_DIVL:
1958 sync_m68k_pc ();
1959 start_brace ();
1960 printf ("\tuaecptr oldpc = m68k_getpc();\n");
1961 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
1962 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1963 sync_m68k_pc ();
1964 printf ("\tm68k_divl(opcode, dst, extra, oldpc);\n");
1965 break;
1966 case i_MULL:
1967 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
1968 genamode (curi->dmode, "dstreg", curi->size, "dst", 1, 0);
1969 sync_m68k_pc ();
1970 printf ("\tm68k_mull(opcode, dst, extra);\n");
1971 break;
1972 case i_BFTST:
1973 case i_BFEXTU:
1974 case i_BFCHG:
1975 case i_BFEXTS:
1976 case i_BFCLR:
1977 case i_BFFFO:
1978 case i_BFSET:
1979 case i_BFINS:
1980 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
1981 genamode (curi->dmode, "dstreg", sz_long, "dst", 2, 0);
1982 start_brace ();
1983 printf ("\tuae_s32 offset = extra & 0x800 ? m68k_dreg(regs, (extra >> 6) & 7) : (extra >> 6) & 0x1f;\n");
1984 printf ("\tint width = (((extra & 0x20 ? m68k_dreg(regs, extra & 7) : extra) -1) & 0x1f) +1;\n");
1985 if (curi->dmode == Dreg) {
1986 printf ("\tuae_u32 tmp = m68k_dreg(regs, dstreg) << (offset & 0x1f);\n");
1987 } else {
1988 printf ("\tuae_u32 tmp,bf0,bf1;\n");
1989 printf ("\tdsta += (offset >> 3) | (offset & 0x80000000 ? ~0x1fffffff : 0);\n");
1990 printf ("\tbf0 = get_long(dsta);bf1 = get_byte(dsta+4) & 0xff;\n");
1991 printf ("\ttmp = (bf0 << (offset & 7)) | (bf1 >> (8 - (offset & 7)));\n");
1992 }
1993 printf ("\ttmp >>= (32 - width);\n");
1994 printf ("\tSET_NFLG (tmp & (1 << (width-1)) ? 1 : 0);\n");
1995 printf ("\tSET_ZFLG (tmp == 0); SET_VFLG (0); SET_CFLG (0);\n");
1996 switch (curi->mnemo) {
1997 case i_BFTST:
1998 break;
1999 case i_BFEXTU:
2000 printf ("\tm68k_dreg(regs, (extra >> 12) & 7) = tmp;\n");
2001 break;
2002 case i_BFCHG:
2003 printf ("\ttmp = ~tmp;\n");
2004 break;
2005 case i_BFEXTS:
2006 printf ("\tif (GET_NFLG) tmp |= width == 32 ? 0 : (-1 << width);\n");
2007 printf ("\tm68k_dreg(regs, (extra >> 12) & 7) = tmp;\n");
2008 break;
2009 case i_BFCLR:
2010 printf ("\ttmp = 0;\n");
2011 break;
2012 case i_BFFFO:
2013 printf ("\t{ uae_u32 mask = 1 << (width-1);\n");
2014 printf ("\twhile (mask) { if (tmp & mask) break; mask >>= 1; offset++; }}\n");
2015 printf ("\tm68k_dreg(regs, (extra >> 12) & 7) = offset;\n");
2016 break;
2017 case i_BFSET:
2018 printf ("\ttmp = 0xffffffff;\n");
2019 break;
2020 case i_BFINS:
2021 printf ("\ttmp = m68k_dreg(regs, (extra >> 12) & 7);\n");
2022 break;
2023 default:
2024 break;
2025 }
2026 if (curi->mnemo == i_BFCHG
2027 || curi->mnemo == i_BFCLR
2028 || curi->mnemo == i_BFSET
2029 || curi->mnemo == i_BFINS)
2030 {
2031 printf ("\ttmp <<= (32 - width);\n");
2032 if (curi->dmode == Dreg) {
2033 printf ("\tm68k_dreg(regs, dstreg) = (m68k_dreg(regs, dstreg) & ((offset & 0x1f) == 0 ? 0 :\n");
2034 printf ("\t\t(0xffffffff << (32 - (offset & 0x1f))))) |\n");
2035 printf ("\t\t(tmp >> (offset & 0x1f)) |\n");
2036 printf ("\t\t(((offset & 0x1f) + width) >= 32 ? 0 :\n");
2037 printf (" (m68k_dreg(regs, dstreg) & ((uae_u32)0xffffffff >> ((offset & 0x1f) + width))));\n");
2038 } else {
2039 printf ("\tbf0 = (bf0 & (0xff000000 << (8 - (offset & 7)))) |\n");
2040 printf ("\t\t(tmp >> (offset & 7)) |\n");
2041 printf ("\t\t(((offset & 7) + width) >= 32 ? 0 :\n");
2042 printf ("\t\t (bf0 & ((uae_u32)0xffffffff >> ((offset & 7) + width))));\n");
2043 printf ("\tput_long(dsta,bf0 );\n");
2044 printf ("\tif (((offset & 7) + width) > 32) {\n");
2045 printf ("\t\tbf1 = (bf1 & (0xff >> (width - 32 + (offset & 7)))) |\n");
2046 printf ("\t\t\t(tmp << (8 - (offset & 7)));\n");
2047 printf ("\t\tput_byte(dsta+4,bf1);\n");
2048 printf ("\t}\n");
2049 }
2050 }
2051 break;
2052 case i_PACK:
2053 if (curi->smode == Dreg) {
2054 printf ("\tuae_u16 val = m68k_dreg(regs, srcreg) + %s;\n", gen_nextiword ());
2055 printf ("\tm68k_dreg(regs, dstreg) = (m68k_dreg(regs, dstreg) & 0xffffff00) | ((val >> 4) & 0xf0) | (val & 0xf);\n");
2056 } else {
2057 printf ("\tuae_u16 val;\n");
2058 printf ("\tm68k_areg(regs, srcreg) -= areg_byteinc[srcreg];\n");
2059 printf ("\tval = (uae_u16)get_byte(m68k_areg(regs, srcreg));\n");
2060 printf ("\tm68k_areg(regs, srcreg) -= areg_byteinc[srcreg];\n");
2061 printf ("\tval = (val | ((uae_u16)get_byte(m68k_areg(regs, srcreg)) << 8)) + %s;\n", gen_nextiword ());
2062 printf ("\tm68k_areg(regs, dstreg) -= areg_byteinc[dstreg];\n");
2063 printf ("\tput_byte(m68k_areg(regs, dstreg),((val >> 4) & 0xf0) | (val & 0xf));\n");
2064 }
2065 break;
2066 case i_UNPK:
2067 if (curi->smode == Dreg) {
2068 printf ("\tuae_u16 val = m68k_dreg(regs, srcreg);\n");
2069 printf ("\tval = (((val << 4) & 0xf00) | (val & 0xf)) + %s;\n", gen_nextiword ());
2070 printf ("\tm68k_dreg(regs, dstreg) = (m68k_dreg(regs, dstreg) & 0xffff0000) | (val & 0xffff);\n");
2071 } else {
2072 printf ("\tuae_u16 val;\n");
2073 printf ("\tm68k_areg(regs, srcreg) -= areg_byteinc[srcreg];\n");
2074 printf ("\tval = (uae_u16)get_byte(m68k_areg(regs, srcreg));\n");
2075 printf ("\tval = (((val << 4) & 0xf00) | (val & 0xf)) + %s;\n", gen_nextiword ());
2076 printf ("\tm68k_areg(regs, dstreg) -= areg_byteinc[dstreg];\n");
2077 printf ("\tput_byte(m68k_areg(regs, dstreg),val);\n");
2078 printf ("\tm68k_areg(regs, dstreg) -= areg_byteinc[dstreg];\n");
2079 printf ("\tput_byte(m68k_areg(regs, dstreg),val >> 8);\n");
2080 }
2081 break;
2082 case i_TAS:
2083 genamode (curi->smode, "srcreg", curi->size, "src", 1, 0);
2084 genflags (flag_logical, curi->size, "src", "", "");
2085 printf ("\tsrc |= 0x80;\n");
2086 genastore ("src", curi->smode, "srcreg", curi->size, "src");
2087 break;
2088 case i_FPP:
2089 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
2090 sync_m68k_pc ();
2091 swap_opcode ();
2092 printf ("\tfpp_opp(opcode,extra);\n");
2093 break;
2094 case i_FDBcc:
2095 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
2096 sync_m68k_pc ();
2097 swap_opcode ();
2098 printf ("\tfdbcc_opp(opcode,extra);\n");
2099 break;
2100 case i_FScc:
2101 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
2102 sync_m68k_pc ();
2103 swap_opcode ();
2104 printf ("\tfscc_opp(opcode,extra);\n");
2105 break;
2106 case i_FTRAPcc:
2107 sync_m68k_pc ();
2108 start_brace ();
2109 printf ("\tuaecptr oldpc = m68k_getpc();\n");
2110 if (curi->smode != am_unknown && curi->smode != am_illg)
2111 genamode (curi->smode, "srcreg", curi->size, "dummy", 1, 0);
2112 sync_m68k_pc ();
2113 swap_opcode ();
2114 printf ("\tftrapcc_opp(opcode,oldpc);\n");
2115 break;
2116 case i_FBcc:
2117 sync_m68k_pc ();
2118 start_brace ();
2119 printf ("\tuaecptr pc = m68k_getpc();\n");
2120 genamode (curi->dmode, "srcreg", curi->size, "extra", 1, 0);
2121 sync_m68k_pc ();
2122 swap_opcode ();
2123 printf ("\tfbcc_opp(opcode,pc,extra);\n");
2124 break;
2125 case i_FSAVE:
2126 sync_m68k_pc ();
2127 swap_opcode ();
2128 printf ("\tfsave_opp(opcode);\n");
2129 break;
2130 case i_FRESTORE:
2131 sync_m68k_pc ();
2132 swap_opcode ();
2133 printf ("\tfrestore_opp(opcode);\n");
2134 break;
2135 case i_CINVL:
2136 case i_CINVP:
2137 case i_CINVA:
2138 case i_CPUSHL:
2139 case i_CPUSHP:
2140 case i_CPUSHA:
2141 break;
2142 case i_MOVE16:
2143 if ((opcode & 0xfff8) == 0xf620) {
2144 /* MOVE16 (Ax)+,(Ay)+ */
2145 printf ("\tuaecptr mems = m68k_areg(regs, srcreg) & ~15, memd;\n");
2146 printf ("\tdstreg = (%s >> 12) & 7;\n", gen_nextiword());
2147 printf ("\tmemd = m68k_areg(regs, dstreg) & ~15;\n");
2148 printf ("\tput_long(memd, get_long(mems));\n");
2149 printf ("\tput_long(memd+4, get_long(mems+4));\n");
2150 printf ("\tput_long(memd+8, get_long(mems+8));\n");
2151 printf ("\tput_long(memd+12, get_long(mems+12));\n");
2152 printf ("\tif (srcreg != dstreg)\n");
2153 printf ("\tm68k_areg(regs, srcreg) += 16;\n");
2154 printf ("\tm68k_areg(regs, dstreg) += 16;\n");
2155 }
2156 else {
2157 /* Other variants */
2158 genamode (curi->smode, "srcreg", curi->size, "mems", 0, 2);
2159 genamode (curi->dmode, "dstreg", curi->size, "memd", 0, 2);
2160 printf ("\tmemsa &= ~15;\n");
2161 printf ("\tmemda &= ~15;\n");
2162 printf ("\tput_long(memda, get_long(memsa));\n");
2163 printf ("\tput_long(memda+4, get_long(memsa+4));\n");
2164 printf ("\tput_long(memda+8, get_long(memsa+8));\n");
2165 printf ("\tput_long(memda+12, get_long(memsa+12));\n");
2166 if ((opcode & 0xfff8) == 0xf600)
2167 printf ("\tm68k_areg(regs, srcreg) += 16;\n");
2168 else if ((opcode & 0xfff8) == 0xf608)
2169 printf ("\tm68k_areg(regs, dstreg) += 16;\n");
2170 }
2171 break;
2172 case i_MMUOP:
2173 genamode (curi->smode, "srcreg", curi->size, "extra", 1, 0);
2174 sync_m68k_pc ();
2175 swap_opcode ();
2176 printf ("\tmmu_op(opcode,extra);\n");
2177 break;
2178 default:
2179 abort ();
2180 break;
2181 }
2182 finish_braces ();
2183 sync_m68k_pc ();
2184 }
2185
2186 static void generate_includes (FILE * f)
2187 {
2188 fprintf (f, "#include \"sysdeps.h\"\n");
2189 fprintf (f, "#include \"m68k.h\"\n");
2190 fprintf (f, "#include \"memory.h\"\n");
2191 fprintf (f, "#include \"readcpu.h\"\n");
2192 fprintf (f, "#include \"newcpu.h\"\n");
2193 fprintf (f, "#include \"cputbl.h\"\n");
2194 }
2195
2196 static int postfix;
2197
2198 static void generate_one_opcode (int rp)
2199 {
2200 int i;
2201 uae_u16 smsk, dmsk;
2202 long int opcode = opcode_map[rp];
2203
2204 if (table68k[opcode].mnemo == i_ILLG
2205 || table68k[opcode].clev > cpu_level)
2206 return;
2207
2208 for (i = 0; lookuptab[i].name[0]; i++) {
2209 if (table68k[opcode].mnemo == lookuptab[i].mnemo)
2210 break;
2211 }
2212
2213 if (table68k[opcode].handler != -1)
2214 return;
2215
2216 if (opcode_next_clev[rp] != cpu_level) {
2217 fprintf (stblfile, "{ op_%lx_%d, 0, %ld }, /* %s */\n", opcode, opcode_last_postfix[rp],
2218 opcode, lookuptab[i].name);
2219 return;
2220 }
2221 fprintf (stblfile, "{ op_%lx_%d, 0, %ld }, /* %s */\n", opcode, postfix, opcode, lookuptab[i].name);
2222 fprintf (headerfile, "extern cpuop_func op_%lx_%d;\n", opcode, postfix);
2223 printf ("void REGPARAM2 op_%lx_%d(uae_u32 opcode) /* %s */\n{\n", opcode, postfix, lookuptab[i].name);
2224
2225 switch (table68k[opcode].stype) {
2226 case 0: smsk = 7; break;
2227 case 1: smsk = 255; break;
2228 case 2: smsk = 15; break;
2229 case 3: smsk = 7; break;
2230 case 4: smsk = 7; break;
2231 case 5: smsk = 63; break;
2232 case 7: smsk = 3; break;
2233 default: abort ();
2234 }
2235 dmsk = 7;
2236
2237 next_cpu_level = -1;
2238 if (table68k[opcode].suse
2239 && table68k[opcode].smode != imm && table68k[opcode].smode != imm0
2240 && table68k[opcode].smode != imm1 && table68k[opcode].smode != imm2
2241 && table68k[opcode].smode != absw && table68k[opcode].smode != absl
2242 && table68k[opcode].smode != PC8r && table68k[opcode].smode != PC16)
2243 {
2244 if (table68k[opcode].spos == -1) {
2245 if (((int) table68k[opcode].sreg) >= 128)
2246 printf ("\tuae_u32 srcreg = (uae_s32)(uae_s8)%d;\n", (int) table68k[opcode].sreg);
2247 else
2248 printf ("\tuae_u32 srcreg = %d;\n", (int) table68k[opcode].sreg);
2249 } else {
2250 char source[100];
2251 int pos = table68k[opcode].spos;
2252
2253 #if 0
2254 /* Check that we can do the little endian optimization safely. */
2255 if (pos < 8 && (smsk >> (8 - pos)) != 0)
2256 abort ();
2257 #endif
2258 printf ("#ifdef HAVE_GET_WORD_UNSWAPPED\n");
2259
2260 if (pos < 8 && (smsk >> (8 - pos)) != 0)
2261 sprintf (source, "(((opcode >> %d) | (opcode << %d)) & %d)",
2262 pos ^ 8, 8 - pos, dmsk);
2263 else if (pos != 8)
2264 sprintf (source, "((opcode >> %d) & %d)", pos ^ 8, smsk);
2265 else
2266 sprintf (source, "(opcode & %d)", smsk);
2267
2268 if (table68k[opcode].stype == 3)
2269 printf ("\tuae_u32 srcreg = imm8_table[%s];\n", source);
2270 else if (table68k[opcode].stype == 1)
2271 printf ("\tuae_u32 srcreg = (uae_s32)(uae_s8)%s;\n", source);
2272 else
2273 printf ("\tuae_u32 srcreg = %s;\n", source);
2274
2275 printf ("#else\n");
2276
2277 if (pos)
2278 sprintf (source, "((opcode >> %d) & %d)", pos, smsk);
2279 else
2280 sprintf (source, "(opcode & %d)", smsk);
2281
2282 if (table68k[opcode].stype == 3)
2283 printf ("\tuae_u32 srcreg = imm8_table[%s];\n", source);
2284 else if (table68k[opcode].stype == 1)
2285 printf ("\tuae_u32 srcreg = (uae_s32)(uae_s8)%s;\n", source);
2286 else
2287 printf ("\tuae_u32 srcreg = %s;\n", source);
2288
2289 printf ("#endif\n");
2290 }
2291 }
2292 if (table68k[opcode].duse
2293 /* Yes, the dmode can be imm, in case of LINK or DBcc */
2294 && table68k[opcode].dmode != imm && table68k[opcode].dmode != imm0
2295 && table68k[opcode].dmode != imm1 && table68k[opcode].dmode != imm2
2296 && table68k[opcode].dmode != absw && table68k[opcode].dmode != absl)
2297 {
2298 if (table68k[opcode].dpos == -1) {
2299 if (((int) table68k[opcode].dreg) >= 128)
2300 printf ("\tuae_u32 dstreg = (uae_s32)(uae_s8)%d;\n", (int) table68k[opcode].dreg);
2301 else
2302 printf ("\tuae_u32 dstreg = %d;\n", (int) table68k[opcode].dreg);
2303 } else {
2304 int pos = table68k[opcode].dpos;
2305 #if 0
2306 /* Check that we can do the little endian optimization safely. */
2307 if (pos < 8 && (dmsk >> (8 - pos)) != 0)
2308 abort ();
2309 #endif
2310 printf ("#ifdef HAVE_GET_WORD_UNSWAPPED\n");
2311
2312 if (pos < 8 && (dmsk >> (8 - pos)) != 0)
2313 printf ("\tuae_u32 dstreg = ((opcode >> %d) | (opcode << %d)) & %d;\n",
2314 pos ^ 8, 8 - pos, dmsk);
2315 else if (pos != 8)
2316 printf ("\tuae_u32 dstreg = (opcode >> %d) & %d;\n",
2317 pos ^ 8, dmsk);
2318 else
2319 printf ("\tuae_u32 dstreg = opcode & %d;\n", dmsk);
2320
2321 printf ("#else\n");
2322
2323 if (pos)
2324 printf ("\tuae_u32 dstreg = (opcode >> %d) & %d;\n",
2325 pos, dmsk);
2326 else
2327 printf ("\tuae_u32 dstreg = opcode & %d;\n", dmsk);
2328
2329 printf ("#endif\n");
2330 }
2331 }
2332 need_endlabel = 0;
2333 endlabelno++;
2334 sprintf (endlabelstr, "endlabel%d", endlabelno);
2335 gen_opcode (opcode);
2336 if (need_endlabel)
2337 printf ("%s: ;\n", endlabelstr);
2338 printf ("}\n");
2339 opcode_next_clev[rp] = next_cpu_level;
2340 opcode_last_postfix[rp] = postfix;
2341 }
2342
2343 static void generate_func (void)
2344 {
2345 int i, j, rp;
2346
2347 using_prefetch = 0;
2348 using_exception_3 = 0;
2349 #if !USE_PREFETCH_BUFFER
2350 /* gb-- No need for a prefetch buffer, nor exception 3 handling */
2351 /* Anyway, Basilisk2 does not use the op_smalltbl_5 table... */
2352 for (i = 0; i <= 4; i++) {
2353 #else
2354 for (i = 0; i < 6; i++) {
2355 #endif
2356 cpu_level = 4 - i;
2357 if (i == 5) {
2358 cpu_level = 0;
2359 using_prefetch = 1;
2360 using_exception_3 = 1;
2361 for (rp = 0; rp < nr_cpuop_funcs; rp++)
2362 opcode_next_clev[rp] = 0;
2363 }
2364 postfix = i;
2365 fprintf (stblfile, "struct cputbl op_smalltbl_%d[] = {\n", postfix);
2366
2367 /* sam: this is for people with low memory (eg. me :)) */
2368 printf ("\n"
2369 "#if !defined(PART_1) && !defined(PART_2) && "
2370 "!defined(PART_3) && !defined(PART_4) && "
2371 "!defined(PART_5) && !defined(PART_6) && "
2372 "!defined(PART_7) && !defined(PART_8)"
2373 "\n"
2374 "#define PART_1 1\n"
2375 "#define PART_2 1\n"
2376 "#define PART_3 1\n"
2377 "#define PART_4 1\n"
2378 "#define PART_5 1\n"
2379 "#define PART_6 1\n"
2380 "#define PART_7 1\n"
2381 "#define PART_8 1\n"
2382 "#endif\n\n");
2383
2384 rp = 0;
2385 for(j=1;j<=8;++j) {
2386 int k = (j*nr_cpuop_funcs)/8;
2387 printf ("#ifdef PART_%d\n",j);
2388 for (; rp < k; rp++)
2389 generate_one_opcode (rp);
2390 printf ("#endif\n\n");
2391 }
2392
2393 fprintf (stblfile, "{ 0, 0, 0 }};\n");
2394 }
2395 }
2396
2397 int main (int argc, char **argv)
2398 {
2399 read_table68k ();
2400 do_merges ();
2401
2402 opcode_map = (int *) malloc (sizeof (int) * nr_cpuop_funcs);
2403 opcode_last_postfix = (int *) malloc (sizeof (int) * nr_cpuop_funcs);
2404 opcode_next_clev = (int *) malloc (sizeof (int) * nr_cpuop_funcs);
2405 counts = (unsigned long *) malloc (65536 * sizeof (unsigned long));
2406 read_counts ();
2407
2408 /* It would be a lot nicer to put all in one file (we'd also get rid of
2409 * cputbl.h that way), but cpuopti can't cope. That could be fixed, but
2410 * I don't dare to touch the 68k version. */
2411
2412 headerfile = fopen ("cputbl.h", "wb");
2413 stblfile = fopen ("cpustbl.cpp", "wb");
2414 freopen ("cpuemu.cpp", "wb", stdout);
2415
2416 generate_includes (stdout);
2417 generate_includes (stblfile);
2418
2419 generate_func ();
2420
2421 free (table68k);
2422 return 0;
2423 }