filename | src/sh4/sh4x86.c |
changeset | 374:8f80a795513e |
prev | 368:36fac4c42322 |
next | 375:4627600f7f8e |
author | nkeynes |
date | Tue Sep 11 02:14:46 2007 +0000 (16 years ago) |
permissions | -rw-r--r-- |
last change | Cache the pointer to the last FR bank (speeds fp ops up by about 10%) Implement experimental fix for FLOAT/FTRC Make read/write sr functions non-static (share with translator) Much more translator WIP |
view | annotate | diff | log | raw |
1 /**
2 * $Id: sh4x86.c,v 1.4 2007-09-11 02:14:46 nkeynes Exp $
3 *
4 * SH4 => x86 translation. This version does no real optimization, it just
5 * outputs straight-line x86 code - it mainly exists to provide a baseline
6 * to test the optimizing versions against.
7 *
8 * Copyright (c) 2007 Nathan Keynes.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 */
21 #include <assert.h>
23 #include "sh4/sh4core.h"
24 #include "sh4/sh4trans.h"
25 #include "sh4/x86op.h"
26 #include "clock.h"
28 #define DEFAULT_BACKPATCH_SIZE 4096
30 /**
31 * Struct to manage internal translation state. This state is not saved -
32 * it is only valid between calls to sh4_translate_begin_block() and
33 * sh4_translate_end_block()
34 */
35 struct sh4_x86_state {
36 gboolean in_delay_slot;
37 gboolean priv_checked; /* true if we've already checked the cpu mode. */
38 gboolean fpuen_checked; /* true if we've already checked fpu enabled. */
40 /* Allocated memory for the (block-wide) back-patch list */
41 uint32_t **backpatch_list;
42 uint32_t backpatch_posn;
43 uint32_t backpatch_size;
44 };
46 #define EXIT_DATA_ADDR_READ 0
47 #define EXIT_DATA_ADDR_WRITE 7
48 #define EXIT_ILLEGAL 14
49 #define EXIT_SLOT_ILLEGAL 21
50 #define EXIT_FPU_DISABLED 28
51 #define EXIT_SLOT_FPU_DISABLED 35
53 static struct sh4_x86_state sh4_x86;
55 void sh4_x86_init()
56 {
57 sh4_x86.backpatch_list = malloc(DEFAULT_BACKPATCH_SIZE);
58 sh4_x86.backpatch_size = DEFAULT_BACKPATCH_SIZE / sizeof(uint32_t *);
59 }
62 static void sh4_x86_add_backpatch( uint8_t *ptr )
63 {
64 if( sh4_x86.backpatch_posn == sh4_x86.backpatch_size ) {
65 sh4_x86.backpatch_size <<= 1;
66 sh4_x86.backpatch_list = realloc( sh4_x86.backpatch_list, sh4_x86.backpatch_size * sizeof(uint32_t *) );
67 assert( sh4_x86.backpatch_list != NULL );
68 }
69 sh4_x86.backpatch_list[sh4_x86.backpatch_posn++] = (uint32_t *)ptr;
70 }
72 static void sh4_x86_do_backpatch( uint8_t *reloc_base )
73 {
74 unsigned int i;
75 for( i=0; i<sh4_x86.backpatch_posn; i++ ) {
76 *sh4_x86.backpatch_list[i] += (reloc_base - ((uint8_t *)sh4_x86.backpatch_list[i]) - 4);
77 }
78 }
80 #ifndef NDEBUG
81 #define MARK_JMP(x,n) uint8_t *_mark_jmp_##x = xlat_output + n
82 #define CHECK_JMP(x) assert( _mark_jmp_##x == xlat_output )
83 #else
84 #define MARK_JMP(x,n)
85 #define CHECK_JMP(x)
86 #endif
89 /**
90 * Emit an instruction to load an SH4 reg into a real register
91 */
92 static inline void load_reg( int x86reg, int sh4reg )
93 {
94 /* mov [bp+n], reg */
95 OP(0x8B);
96 OP(0x45 + (x86reg<<3));
97 OP(REG_OFFSET(r[sh4reg]));
98 }
100 static inline void load_reg16s( int x86reg, int sh4reg )
101 {
102 OP(0x0F);
103 OP(0xBF);
104 MODRM_r32_sh4r(x86reg, REG_OFFSET(r[sh4reg]));
105 }
107 static inline void load_reg16u( int x86reg, int sh4reg )
108 {
109 OP(0x0F);
110 OP(0xB7);
111 MODRM_r32_sh4r(x86reg, REG_OFFSET(r[sh4reg]));
113 }
115 static inline void load_spreg( int x86reg, int regoffset )
116 {
117 /* mov [bp+n], reg */
118 OP(0x8B);
119 OP(0x45 + (x86reg<<3));
120 OP(regoffset);
121 }
123 /**
124 * Emit an instruction to load an immediate value into a register
125 */
126 static inline void load_imm32( int x86reg, uint32_t value ) {
127 /* mov #value, reg */
128 OP(0xB8 + x86reg);
129 OP32(value);
130 }
132 /**
133 * Emit an instruction to store an SH4 reg (RN)
134 */
135 void static inline store_reg( int x86reg, int sh4reg ) {
136 /* mov reg, [bp+n] */
137 OP(0x89);
138 OP(0x45 + (x86reg<<3));
139 OP(REG_OFFSET(r[sh4reg]));
140 }
141 void static inline store_spreg( int x86reg, int regoffset ) {
142 /* mov reg, [bp+n] */
143 OP(0x89);
144 OP(0x45 + (x86reg<<3));
145 OP(regoffset);
146 }
149 #define load_fr_bank(bankreg) load_spreg( bankreg, REG_OFFSET(fr_bank))
151 static inline void load_xf_bank( int bankreg )
152 {
153 load_spreg( bankreg, R_FPSCR );
154 SHR_imm8_r32( (21 - 6), bankreg ); // Extract bit 21 then *64 for bank size
155 AND_imm8s_r32( 0x40, bankreg ); // Complete extraction
156 OP(0x8D); OP(0x44+(bankreg<<3)); OP(0x28+bankreg); OP(REG_OFFSET(fr)); // LEA [ebp+bankreg+disp], bankreg
157 }
159 static inline void push_fr( int bankreg, int frm )
160 {
161 OP(0xD9); OP(0x40 + bankreg); OP((frm^1)<<2); // FLD.S [bankreg + frm^1*4]
162 }
164 static inline void pop_fr( int bankreg, int frm )
165 {
166 OP(0xD9); OP(0x58 + bankreg); OP((frm^1)<<2); // FST.S [bankreg + frm^1*4]
167 }
169 static inline void push_dr( int bankreg, int frm )
170 {
171 if( frm&1 ) {
172 // this is technically undefined, but it seems to work consistently - high 32 bits
173 // loaded from FRm (32-bits), low 32bits are 0.
174 OP(0xFF); OP(0x70 + bankreg); OP((frm^1)<<2); // PUSH [bankreg + frm^1]
175 PUSH_imm32(0);
178 } else {
179 OP(0xDD); OP(0x40 + bankreg); OP(frm<<2); // FLD.D [bankreg + frm*4]
180 }
181 }
183 static inline void pop_dr( int bankreg, int frm )
184 {
185 if( frm&1 ) {
186 } else {
187 OP(0xDD); OP(0x58 + bankreg); OP(frm<<2); // FST.D [bankreg + frm*4]
188 }
189 }
191 /**
192 * Note: clobbers EAX to make the indirect call - this isn't usually
193 * a problem since the callee will usually clobber it anyway.
194 */
195 static inline void call_func0( void *ptr )
196 {
197 load_imm32(R_EAX, (uint32_t)ptr);
198 CALL_r32(R_EAX);
199 }
201 static inline void call_func1( void *ptr, int arg1 )
202 {
203 PUSH_r32(arg1);
204 call_func0(ptr);
205 ADD_imm8s_r32( -4, R_ESP );
206 }
208 static inline void call_func2( void *ptr, int arg1, int arg2 )
209 {
210 PUSH_r32(arg2);
211 PUSH_r32(arg1);
212 call_func0(ptr);
213 ADD_imm8s_r32( -4, R_ESP );
214 }
216 /* Exception checks - Note that all exception checks will clobber EAX */
217 static void check_priv( )
218 {
219 if( !sh4_x86.priv_checked ) {
220 sh4_x86.priv_checked = TRUE;
221 load_spreg( R_EAX, R_SR );
222 AND_imm32_r32( SR_MD, R_EAX );
223 if( sh4_x86.in_delay_slot ) {
224 JE_exit( EXIT_SLOT_ILLEGAL );
225 } else {
226 JE_exit( EXIT_ILLEGAL );
227 }
228 }
229 }
231 static void check_fpuen( )
232 {
233 if( !sh4_x86.fpuen_checked ) {
234 sh4_x86.fpuen_checked = TRUE;
235 load_spreg( R_EAX, R_SR );
236 AND_imm32_r32( SR_FD, R_EAX );
237 if( sh4_x86.in_delay_slot ) {
238 JNE_exit(EXIT_SLOT_FPU_DISABLED);
239 } else {
240 JNE_exit(EXIT_FPU_DISABLED);
241 }
242 }
243 }
245 static void check_ralign16( int x86reg )
246 {
247 TEST_imm32_r32( 0x00000001, x86reg );
248 JNE_exit(EXIT_DATA_ADDR_READ);
249 }
251 static void check_walign16( int x86reg )
252 {
253 TEST_imm32_r32( 0x00000001, x86reg );
254 JNE_exit(EXIT_DATA_ADDR_WRITE);
255 }
257 static void check_ralign32( int x86reg )
258 {
259 TEST_imm32_r32( 0x00000003, x86reg );
260 JNE_exit(EXIT_DATA_ADDR_READ);
261 }
262 static void check_walign32( int x86reg )
263 {
264 TEST_imm32_r32( 0x00000003, x86reg );
265 JNE_exit(EXIT_DATA_ADDR_WRITE);
266 }
269 #define UNDEF()
270 #define MEM_RESULT(value_reg) if(value_reg != R_EAX) { MOV_r32_r32(R_EAX,value_reg); }
271 #define MEM_READ_BYTE( addr_reg, value_reg ) call_func1(sh4_read_byte, addr_reg ); MEM_RESULT(value_reg)
272 #define MEM_READ_WORD( addr_reg, value_reg ) call_func1(sh4_read_word, addr_reg ); MEM_RESULT(value_reg)
273 #define MEM_READ_LONG( addr_reg, value_reg ) call_func1(sh4_read_long, addr_reg ); MEM_RESULT(value_reg)
274 #define MEM_WRITE_BYTE( addr_reg, value_reg ) call_func2(sh4_write_byte, addr_reg, value_reg)
275 #define MEM_WRITE_WORD( addr_reg, value_reg ) call_func2(sh4_write_word, addr_reg, value_reg)
276 #define MEM_WRITE_LONG( addr_reg, value_reg ) call_func2(sh4_write_long, addr_reg, value_reg)
278 #define RAISE_EXCEPTION( exc ) call_func1(sh4_raise_exception, exc);
279 #define SLOTILLEGAL() RAISE_EXCEPTION(EXC_SLOT_ILLEGAL); return 1
283 /**
284 * Emit the 'start of block' assembly. Sets up the stack frame and save
285 * SI/DI as required
286 */
287 void sh4_translate_begin_block()
288 {
289 PUSH_r32(R_EBP);
290 /* mov &sh4r, ebp */
291 load_imm32( R_EBP, (uint32_t)&sh4r );
292 PUSH_r32(R_EDI);
293 PUSH_r32(R_ESI);
295 sh4_x86.in_delay_slot = FALSE;
296 sh4_x86.priv_checked = FALSE;
297 sh4_x86.fpuen_checked = FALSE;
298 sh4_x86.backpatch_posn = 0;
299 }
301 /**
302 * Exit the block early (ie branch out), conditionally or otherwise
303 */
304 void exit_block( )
305 {
306 store_spreg( R_EDI, REG_OFFSET(pc) );
307 MOV_moff32_EAX( (uint32_t)&sh4_cpu_period );
308 load_spreg( R_ECX, REG_OFFSET(slice_cycle) );
309 MUL_r32( R_ESI );
310 ADD_r32_r32( R_EAX, R_ECX );
311 store_spreg( R_ECX, REG_OFFSET(slice_cycle) );
312 XOR_r32_r32( R_EAX, R_EAX );
313 POP_r32(R_ESI);
314 POP_r32(R_EDI);
315 POP_r32(R_EBP);
316 RET();
317 }
319 /**
320 * Flush any open regs back to memory, restore SI/DI/, update PC, etc
321 */
322 void sh4_translate_end_block( sh4addr_t pc ) {
323 assert( !sh4_x86.in_delay_slot ); // should never stop here
324 // Normal termination - save PC, cycle count
325 exit_block( );
327 uint8_t *end_ptr = xlat_output;
328 // Exception termination. Jump block for various exception codes:
329 PUSH_imm32( EXC_DATA_ADDR_READ );
330 JMP_rel8( 33 );
331 PUSH_imm32( EXC_DATA_ADDR_WRITE );
332 JMP_rel8( 26 );
333 PUSH_imm32( EXC_ILLEGAL );
334 JMP_rel8( 19 );
335 PUSH_imm32( EXC_SLOT_ILLEGAL );
336 JMP_rel8( 12 );
337 PUSH_imm32( EXC_FPU_DISABLED );
338 JMP_rel8( 5 );
339 PUSH_imm32( EXC_SLOT_FPU_DISABLED );
340 // target
341 load_spreg( R_ECX, REG_OFFSET(pc) );
342 ADD_r32_r32( R_ESI, R_ECX );
343 ADD_r32_r32( R_ESI, R_ECX );
344 store_spreg( R_ECX, REG_OFFSET(pc) );
345 MOV_moff32_EAX( (uint32_t)&sh4_cpu_period );
346 load_spreg( R_ECX, REG_OFFSET(slice_cycle) );
347 MUL_r32( R_ESI );
348 ADD_r32_r32( R_EAX, R_ECX );
349 store_spreg( R_ECX, REG_OFFSET(slice_cycle) );
351 load_imm32( R_EAX, (uint32_t)sh4_raise_exception ); // 6
352 CALL_r32( R_EAX ); // 2
353 POP_r32(R_EBP);
354 RET();
356 sh4_x86_do_backpatch( end_ptr );
357 }
359 /**
360 * Translate a single instruction. Delayed branches are handled specially
361 * by translating both branch and delayed instruction as a single unit (as
362 *
363 *
364 * @return true if the instruction marks the end of a basic block
365 * (eg a branch or
366 */
367 uint32_t sh4_x86_translate_instruction( uint32_t pc )
368 {
369 uint16_t ir = sh4_read_word( pc );
371 switch( (ir&0xF000) >> 12 ) {
372 case 0x0:
373 switch( ir&0xF ) {
374 case 0x2:
375 switch( (ir&0x80) >> 7 ) {
376 case 0x0:
377 switch( (ir&0x70) >> 4 ) {
378 case 0x0:
379 { /* STC SR, Rn */
380 uint32_t Rn = ((ir>>8)&0xF);
381 call_func0(sh4_read_sr);
382 store_reg( R_EAX, Rn );
383 }
384 break;
385 case 0x1:
386 { /* STC GBR, Rn */
387 uint32_t Rn = ((ir>>8)&0xF);
388 load_spreg( R_EAX, R_GBR );
389 store_reg( R_EAX, Rn );
390 }
391 break;
392 case 0x2:
393 { /* STC VBR, Rn */
394 uint32_t Rn = ((ir>>8)&0xF);
395 load_spreg( R_EAX, R_VBR );
396 store_reg( R_EAX, Rn );
397 }
398 break;
399 case 0x3:
400 { /* STC SSR, Rn */
401 uint32_t Rn = ((ir>>8)&0xF);
402 load_spreg( R_EAX, R_SSR );
403 store_reg( R_EAX, Rn );
404 }
405 break;
406 case 0x4:
407 { /* STC SPC, Rn */
408 uint32_t Rn = ((ir>>8)&0xF);
409 load_spreg( R_EAX, R_SPC );
410 store_reg( R_EAX, Rn );
411 }
412 break;
413 default:
414 UNDEF();
415 break;
416 }
417 break;
418 case 0x1:
419 { /* STC Rm_BANK, Rn */
420 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm_BANK = ((ir>>4)&0x7);
421 load_spreg( R_EAX, REG_OFFSET(r_bank[Rm_BANK]) );
422 store_reg( R_EAX, Rn );
423 }
424 break;
425 }
426 break;
427 case 0x3:
428 switch( (ir&0xF0) >> 4 ) {
429 case 0x0:
430 { /* BSRF Rn */
431 uint32_t Rn = ((ir>>8)&0xF);
432 if( sh4_x86.in_delay_slot ) {
433 SLOTILLEGAL();
434 } else {
435 load_imm32( R_EAX, pc + 4 );
436 store_spreg( R_EAX, R_PR );
437 load_reg( R_EDI, Rn );
438 ADD_r32_r32( R_EAX, R_EDI );
439 sh4_x86.in_delay_slot = TRUE;
440 INC_r32(R_ESI);
441 return 0;
442 }
443 }
444 break;
445 case 0x2:
446 { /* BRAF Rn */
447 uint32_t Rn = ((ir>>8)&0xF);
448 if( sh4_x86.in_delay_slot ) {
449 SLOTILLEGAL();
450 } else {
451 load_reg( R_EDI, Rn );
452 sh4_x86.in_delay_slot = TRUE;
453 INC_r32(R_ESI);
454 return 0;
455 }
456 }
457 break;
458 case 0x8:
459 { /* PREF @Rn */
460 uint32_t Rn = ((ir>>8)&0xF);
461 load_reg( R_EAX, Rn );
462 PUSH_r32( R_EAX );
463 AND_imm32_r32( 0xFC000000, R_EAX );
464 CMP_imm32_r32( 0xE0000000, R_EAX );
465 JNE_rel8(8);
466 call_func0( sh4_flush_store_queue );
467 ADD_imm8s_r32( -4, R_ESP );
468 }
469 break;
470 case 0x9:
471 { /* OCBI @Rn */
472 uint32_t Rn = ((ir>>8)&0xF);
473 }
474 break;
475 case 0xA:
476 { /* OCBP @Rn */
477 uint32_t Rn = ((ir>>8)&0xF);
478 }
479 break;
480 case 0xB:
481 { /* OCBWB @Rn */
482 uint32_t Rn = ((ir>>8)&0xF);
483 }
484 break;
485 case 0xC:
486 { /* MOVCA.L R0, @Rn */
487 uint32_t Rn = ((ir>>8)&0xF);
488 load_reg( R_EAX, 0 );
489 load_reg( R_ECX, Rn );
490 check_walign32( R_ECX );
491 MEM_WRITE_LONG( R_ECX, R_EAX );
492 }
493 break;
494 default:
495 UNDEF();
496 break;
497 }
498 break;
499 case 0x4:
500 { /* MOV.B Rm, @(R0, Rn) */
501 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
502 load_reg( R_EAX, 0 );
503 load_reg( R_ECX, Rn );
504 ADD_r32_r32( R_EAX, R_ECX );
505 load_reg( R_EAX, Rm );
506 MEM_WRITE_BYTE( R_ECX, R_EAX );
507 }
508 break;
509 case 0x5:
510 { /* MOV.W Rm, @(R0, Rn) */
511 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
512 load_reg( R_EAX, 0 );
513 load_reg( R_ECX, Rn );
514 ADD_r32_r32( R_EAX, R_ECX );
515 check_walign16( R_ECX );
516 load_reg( R_EAX, Rm );
517 MEM_WRITE_WORD( R_ECX, R_EAX );
518 }
519 break;
520 case 0x6:
521 { /* MOV.L Rm, @(R0, Rn) */
522 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
523 load_reg( R_EAX, 0 );
524 load_reg( R_ECX, Rn );
525 ADD_r32_r32( R_EAX, R_ECX );
526 check_walign32( R_ECX );
527 load_reg( R_EAX, Rm );
528 MEM_WRITE_LONG( R_ECX, R_EAX );
529 }
530 break;
531 case 0x7:
532 { /* MUL.L Rm, Rn */
533 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
534 load_reg( R_EAX, Rm );
535 load_reg( R_ECX, Rn );
536 MUL_r32( R_ECX );
537 store_spreg( R_EAX, R_MACL );
538 }
539 break;
540 case 0x8:
541 switch( (ir&0xFF0) >> 4 ) {
542 case 0x0:
543 { /* CLRT */
544 CLC();
545 SETC_t();
546 }
547 break;
548 case 0x1:
549 { /* SETT */
550 STC();
551 SETC_t();
552 }
553 break;
554 case 0x2:
555 { /* CLRMAC */
556 XOR_r32_r32(R_EAX, R_EAX);
557 store_spreg( R_EAX, R_MACL );
558 store_spreg( R_EAX, R_MACH );
559 }
560 break;
561 case 0x3:
562 { /* LDTLB */
563 }
564 break;
565 case 0x4:
566 { /* CLRS */
567 CLC();
568 SETC_sh4r(R_S);
569 }
570 break;
571 case 0x5:
572 { /* SETS */
573 STC();
574 SETC_sh4r(R_S);
575 }
576 break;
577 default:
578 UNDEF();
579 break;
580 }
581 break;
582 case 0x9:
583 switch( (ir&0xF0) >> 4 ) {
584 case 0x0:
585 { /* NOP */
586 /* Do nothing. Well, we could emit an 0x90, but what would really be the point? */
587 }
588 break;
589 case 0x1:
590 { /* DIV0U */
591 XOR_r32_r32( R_EAX, R_EAX );
592 store_spreg( R_EAX, R_Q );
593 store_spreg( R_EAX, R_M );
594 store_spreg( R_EAX, R_T );
595 }
596 break;
597 case 0x2:
598 { /* MOVT Rn */
599 uint32_t Rn = ((ir>>8)&0xF);
600 load_spreg( R_EAX, R_T );
601 store_reg( R_EAX, Rn );
602 }
603 break;
604 default:
605 UNDEF();
606 break;
607 }
608 break;
609 case 0xA:
610 switch( (ir&0xF0) >> 4 ) {
611 case 0x0:
612 { /* STS MACH, Rn */
613 uint32_t Rn = ((ir>>8)&0xF);
614 load_spreg( R_EAX, R_MACH );
615 store_reg( R_EAX, Rn );
616 }
617 break;
618 case 0x1:
619 { /* STS MACL, Rn */
620 uint32_t Rn = ((ir>>8)&0xF);
621 load_spreg( R_EAX, R_MACL );
622 store_reg( R_EAX, Rn );
623 }
624 break;
625 case 0x2:
626 { /* STS PR, Rn */
627 uint32_t Rn = ((ir>>8)&0xF);
628 load_spreg( R_EAX, R_PR );
629 store_reg( R_EAX, Rn );
630 }
631 break;
632 case 0x3:
633 { /* STC SGR, Rn */
634 uint32_t Rn = ((ir>>8)&0xF);
635 load_spreg( R_EAX, R_SGR );
636 store_reg( R_EAX, Rn );
637 }
638 break;
639 case 0x5:
640 { /* STS FPUL, Rn */
641 uint32_t Rn = ((ir>>8)&0xF);
642 load_spreg( R_EAX, R_FPUL );
643 store_reg( R_EAX, Rn );
644 }
645 break;
646 case 0x6:
647 { /* STS FPSCR, Rn */
648 uint32_t Rn = ((ir>>8)&0xF);
649 load_spreg( R_EAX, R_FPSCR );
650 store_reg( R_EAX, Rn );
651 }
652 break;
653 case 0xF:
654 { /* STC DBR, Rn */
655 uint32_t Rn = ((ir>>8)&0xF);
656 load_spreg( R_EAX, R_DBR );
657 store_reg( R_EAX, Rn );
658 }
659 break;
660 default:
661 UNDEF();
662 break;
663 }
664 break;
665 case 0xB:
666 switch( (ir&0xFF0) >> 4 ) {
667 case 0x0:
668 { /* RTS */
669 if( sh4_x86.in_delay_slot ) {
670 SLOTILLEGAL();
671 } else {
672 load_spreg( R_EDI, R_PR );
673 sh4_x86.in_delay_slot = TRUE;
674 INC_r32(R_ESI);
675 return 0;
676 }
677 }
678 break;
679 case 0x1:
680 { /* SLEEP */
681 /* TODO */
682 }
683 break;
684 case 0x2:
685 { /* RTE */
686 check_priv();
687 if( sh4_x86.in_delay_slot ) {
688 SLOTILLEGAL();
689 } else {
690 load_spreg( R_EDI, R_PR );
691 load_spreg( R_EAX, R_SSR );
692 call_func1( sh4_write_sr, R_EAX );
693 sh4_x86.in_delay_slot = TRUE;
694 INC_r32(R_ESI);
695 return 0;
696 }
697 }
698 break;
699 default:
700 UNDEF();
701 break;
702 }
703 break;
704 case 0xC:
705 { /* MOV.B @(R0, Rm), Rn */
706 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
707 load_reg( R_EAX, 0 );
708 load_reg( R_ECX, Rm );
709 ADD_r32_r32( R_EAX, R_ECX );
710 MEM_READ_BYTE( R_ECX, R_EAX );
711 store_reg( R_EAX, Rn );
712 }
713 break;
714 case 0xD:
715 { /* MOV.W @(R0, Rm), Rn */
716 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
717 load_reg( R_EAX, 0 );
718 load_reg( R_ECX, Rm );
719 ADD_r32_r32( R_EAX, R_ECX );
720 check_ralign16( R_ECX );
721 MEM_READ_WORD( R_ECX, R_EAX );
722 store_reg( R_EAX, Rn );
723 }
724 break;
725 case 0xE:
726 { /* MOV.L @(R0, Rm), Rn */
727 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
728 load_reg( R_EAX, 0 );
729 load_reg( R_ECX, Rm );
730 ADD_r32_r32( R_EAX, R_ECX );
731 check_ralign32( R_ECX );
732 MEM_READ_LONG( R_ECX, R_EAX );
733 store_reg( R_EAX, Rn );
734 }
735 break;
736 case 0xF:
737 { /* MAC.L @Rm+, @Rn+ */
738 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
739 }
740 break;
741 default:
742 UNDEF();
743 break;
744 }
745 break;
746 case 0x1:
747 { /* MOV.L Rm, @(disp, Rn) */
748 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF); uint32_t disp = (ir&0xF)<<2;
749 load_reg( R_ECX, Rn );
750 load_reg( R_EAX, Rm );
751 ADD_imm32_r32( disp, R_ECX );
752 check_walign32( R_ECX );
753 MEM_WRITE_LONG( R_ECX, R_EAX );
754 }
755 break;
756 case 0x2:
757 switch( ir&0xF ) {
758 case 0x0:
759 { /* MOV.B Rm, @Rn */
760 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
761 load_reg( R_EAX, Rm );
762 load_reg( R_ECX, Rn );
763 MEM_WRITE_BYTE( R_ECX, R_EAX );
764 }
765 break;
766 case 0x1:
767 { /* MOV.W Rm, @Rn */
768 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
769 load_reg( R_ECX, Rn );
770 check_walign16( R_ECX );
771 MEM_READ_WORD( R_ECX, R_EAX );
772 store_reg( R_EAX, Rn );
773 }
774 break;
775 case 0x2:
776 { /* MOV.L Rm, @Rn */
777 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
778 load_reg( R_EAX, Rm );
779 load_reg( R_ECX, Rn );
780 check_walign32(R_ECX);
781 MEM_WRITE_LONG( R_ECX, R_EAX );
782 }
783 break;
784 case 0x4:
785 { /* MOV.B Rm, @-Rn */
786 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
787 load_reg( R_EAX, Rm );
788 load_reg( R_ECX, Rn );
789 ADD_imm8s_r32( -1, Rn );
790 store_reg( R_ECX, Rn );
791 MEM_WRITE_BYTE( R_ECX, R_EAX );
792 }
793 break;
794 case 0x5:
795 { /* MOV.W Rm, @-Rn */
796 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
797 load_reg( R_ECX, Rn );
798 check_walign16( R_ECX );
799 load_reg( R_EAX, Rm );
800 ADD_imm8s_r32( -2, R_ECX );
801 MEM_WRITE_WORD( R_ECX, R_EAX );
802 }
803 break;
804 case 0x6:
805 { /* MOV.L Rm, @-Rn */
806 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
807 load_reg( R_EAX, Rm );
808 load_reg( R_ECX, Rn );
809 check_walign32( R_ECX );
810 ADD_imm8s_r32( -4, R_ECX );
811 store_reg( R_ECX, Rn );
812 MEM_WRITE_LONG( R_ECX, R_EAX );
813 }
814 break;
815 case 0x7:
816 { /* DIV0S Rm, Rn */
817 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
818 load_reg( R_EAX, Rm );
819 load_reg( R_ECX, Rm );
820 SHR_imm8_r32( 31, R_EAX );
821 SHR_imm8_r32( 31, R_ECX );
822 store_spreg( R_EAX, R_M );
823 store_spreg( R_ECX, R_Q );
824 CMP_r32_r32( R_EAX, R_ECX );
825 SETE_t();
826 }
827 break;
828 case 0x8:
829 { /* TST Rm, Rn */
830 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
831 load_reg( R_EAX, Rm );
832 load_reg( R_ECX, Rn );
833 TEST_r32_r32( R_EAX, R_ECX );
834 SETE_t();
835 }
836 break;
837 case 0x9:
838 { /* AND Rm, Rn */
839 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
840 load_reg( R_EAX, Rm );
841 load_reg( R_ECX, Rn );
842 AND_r32_r32( R_EAX, R_ECX );
843 store_reg( R_ECX, Rn );
844 }
845 break;
846 case 0xA:
847 { /* XOR Rm, Rn */
848 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
849 load_reg( R_EAX, Rm );
850 load_reg( R_ECX, Rn );
851 XOR_r32_r32( R_EAX, R_ECX );
852 store_reg( R_ECX, Rn );
853 }
854 break;
855 case 0xB:
856 { /* OR Rm, Rn */
857 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
858 load_reg( R_EAX, Rm );
859 load_reg( R_ECX, Rn );
860 OR_r32_r32( R_EAX, R_ECX );
861 store_reg( R_ECX, Rn );
862 }
863 break;
864 case 0xC:
865 { /* CMP/STR Rm, Rn */
866 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
867 load_reg( R_EAX, Rm );
868 load_reg( R_ECX, Rn );
869 XOR_r32_r32( R_ECX, R_EAX );
870 TEST_r8_r8( R_AL, R_AL );
871 JE_rel8(13);
872 TEST_r8_r8( R_AH, R_AH ); // 2
873 JE_rel8(9);
874 SHR_imm8_r32( 16, R_EAX ); // 3
875 TEST_r8_r8( R_AL, R_AL ); // 2
876 JE_rel8(2);
877 TEST_r8_r8( R_AH, R_AH ); // 2
878 SETE_t();
879 }
880 break;
881 case 0xD:
882 { /* XTRCT Rm, Rn */
883 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
884 load_reg( R_EAX, Rm );
885 MOV_r32_r32( R_EAX, R_ECX );
886 SHR_imm8_r32( 16, R_EAX );
887 SHL_imm8_r32( 16, R_ECX );
888 OR_r32_r32( R_EAX, R_ECX );
889 store_reg( R_ECX, Rn );
890 }
891 break;
892 case 0xE:
893 { /* MULU.W Rm, Rn */
894 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
895 load_reg16u( R_EAX, Rm );
896 load_reg16u( R_ECX, Rn );
897 MUL_r32( R_ECX );
898 store_spreg( R_EAX, R_MACL );
899 }
900 break;
901 case 0xF:
902 { /* MULS.W Rm, Rn */
903 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
904 load_reg16s( R_EAX, Rm );
905 load_reg16s( R_ECX, Rn );
906 MUL_r32( R_ECX );
907 store_spreg( R_EAX, R_MACL );
908 }
909 break;
910 default:
911 UNDEF();
912 break;
913 }
914 break;
915 case 0x3:
916 switch( ir&0xF ) {
917 case 0x0:
918 { /* CMP/EQ Rm, Rn */
919 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
920 load_reg( R_EAX, Rm );
921 load_reg( R_ECX, Rn );
922 CMP_r32_r32( R_EAX, R_ECX );
923 SETE_t();
924 }
925 break;
926 case 0x2:
927 { /* CMP/HS Rm, Rn */
928 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
929 load_reg( R_EAX, Rm );
930 load_reg( R_ECX, Rn );
931 CMP_r32_r32( R_EAX, R_ECX );
932 SETAE_t();
933 }
934 break;
935 case 0x3:
936 { /* CMP/GE Rm, Rn */
937 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
938 load_reg( R_EAX, Rm );
939 load_reg( R_ECX, Rn );
940 CMP_r32_r32( R_EAX, R_ECX );
941 SETGE_t();
942 }
943 break;
944 case 0x4:
945 { /* DIV1 Rm, Rn */
946 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
947 load_reg( R_ECX, Rn );
948 LDC_t();
949 RCL1_r32( R_ECX ); // OP2
950 SETC_r32( R_EDX ); // Q
951 load_spreg( R_EAX, R_Q );
952 CMP_sh4r_r32( R_M, R_EAX );
953 JE_rel8(8);
954 ADD_sh4r_r32( REG_OFFSET(r[Rm]), R_ECX );
955 JMP_rel8(3);
956 SUB_sh4r_r32( REG_OFFSET(r[Rm]), R_ECX );
957 // TODO
958 }
959 break;
960 case 0x5:
961 { /* DMULU.L Rm, Rn */
962 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
963 load_reg( R_EAX, Rm );
964 load_reg( R_ECX, Rn );
965 MUL_r32(R_ECX);
966 store_spreg( R_EDX, R_MACH );
967 store_spreg( R_EAX, R_MACL );
968 }
969 break;
970 case 0x6:
971 { /* CMP/HI Rm, Rn */
972 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
973 load_reg( R_EAX, Rm );
974 load_reg( R_ECX, Rn );
975 CMP_r32_r32( R_EAX, R_ECX );
976 SETA_t();
977 }
978 break;
979 case 0x7:
980 { /* CMP/GT Rm, Rn */
981 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
982 load_reg( R_EAX, Rm );
983 load_reg( R_ECX, Rn );
984 CMP_r32_r32( R_EAX, R_ECX );
985 SETG_t();
986 }
987 break;
988 case 0x8:
989 { /* SUB Rm, Rn */
990 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
991 load_reg( R_EAX, Rm );
992 load_reg( R_ECX, Rn );
993 SUB_r32_r32( R_EAX, R_ECX );
994 store_reg( R_ECX, Rn );
995 }
996 break;
997 case 0xA:
998 { /* SUBC Rm, Rn */
999 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1000 load_reg( R_EAX, Rm );
1001 load_reg( R_ECX, Rn );
1002 LDC_t();
1003 SBB_r32_r32( R_EAX, R_ECX );
1004 store_reg( R_ECX, Rn );
1005 }
1006 break;
1007 case 0xB:
1008 { /* SUBV Rm, Rn */
1009 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1010 load_reg( R_EAX, Rm );
1011 load_reg( R_ECX, Rn );
1012 SUB_r32_r32( R_EAX, R_ECX );
1013 store_reg( R_ECX, Rn );
1014 SETO_t();
1015 }
1016 break;
1017 case 0xC:
1018 { /* ADD Rm, Rn */
1019 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1020 load_reg( R_EAX, Rm );
1021 load_reg( R_ECX, Rn );
1022 ADD_r32_r32( R_EAX, R_ECX );
1023 store_reg( R_ECX, Rn );
1024 }
1025 break;
1026 case 0xD:
1027 { /* DMULS.L Rm, Rn */
1028 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1029 load_reg( R_EAX, Rm );
1030 load_reg( R_ECX, Rn );
1031 IMUL_r32(R_ECX);
1032 store_spreg( R_EDX, R_MACH );
1033 store_spreg( R_EAX, R_MACL );
1034 }
1035 break;
1036 case 0xE:
1037 { /* ADDC Rm, Rn */
1038 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1039 load_reg( R_EAX, Rm );
1040 load_reg( R_ECX, Rn );
1041 LDC_t();
1042 ADC_r32_r32( R_EAX, R_ECX );
1043 store_reg( R_ECX, Rn );
1044 SETC_t();
1045 }
1046 break;
1047 case 0xF:
1048 { /* ADDV Rm, Rn */
1049 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1050 load_reg( R_EAX, Rm );
1051 load_reg( R_ECX, Rn );
1052 ADD_r32_r32( R_EAX, R_ECX );
1053 store_reg( R_ECX, Rn );
1054 SETO_t();
1055 }
1056 break;
1057 default:
1058 UNDEF();
1059 break;
1060 }
1061 break;
1062 case 0x4:
1063 switch( ir&0xF ) {
1064 case 0x0:
1065 switch( (ir&0xF0) >> 4 ) {
1066 case 0x0:
1067 { /* SHLL Rn */
1068 uint32_t Rn = ((ir>>8)&0xF);
1069 load_reg( R_EAX, Rn );
1070 SHL1_r32( R_EAX );
1071 store_reg( R_EAX, Rn );
1072 }
1073 break;
1074 case 0x1:
1075 { /* DT Rn */
1076 uint32_t Rn = ((ir>>8)&0xF);
1077 load_reg( R_EAX, Rn );
1078 ADD_imm8s_r32( -1, Rn );
1079 store_reg( R_EAX, Rn );
1080 SETE_t();
1081 }
1082 break;
1083 case 0x2:
1084 { /* SHAL Rn */
1085 uint32_t Rn = ((ir>>8)&0xF);
1086 load_reg( R_EAX, Rn );
1087 SHL1_r32( R_EAX );
1088 store_reg( R_EAX, Rn );
1089 }
1090 break;
1091 default:
1092 UNDEF();
1093 break;
1094 }
1095 break;
1096 case 0x1:
1097 switch( (ir&0xF0) >> 4 ) {
1098 case 0x0:
1099 { /* SHLR Rn */
1100 uint32_t Rn = ((ir>>8)&0xF);
1101 load_reg( R_EAX, Rn );
1102 SHR1_r32( R_EAX );
1103 store_reg( R_EAX, Rn );
1104 }
1105 break;
1106 case 0x1:
1107 { /* CMP/PZ Rn */
1108 uint32_t Rn = ((ir>>8)&0xF);
1109 load_reg( R_EAX, Rn );
1110 CMP_imm8s_r32( 0, R_EAX );
1111 SETGE_t();
1112 }
1113 break;
1114 case 0x2:
1115 { /* SHAR Rn */
1116 uint32_t Rn = ((ir>>8)&0xF);
1117 load_reg( R_EAX, Rn );
1118 SAR1_r32( R_EAX );
1119 store_reg( R_EAX, Rn );
1120 }
1121 break;
1122 default:
1123 UNDEF();
1124 break;
1125 }
1126 break;
1127 case 0x2:
1128 switch( (ir&0xF0) >> 4 ) {
1129 case 0x0:
1130 { /* STS.L MACH, @-Rn */
1131 uint32_t Rn = ((ir>>8)&0xF);
1132 load_reg( R_ECX, Rn );
1133 ADD_imm8s_r32( -4, Rn );
1134 store_reg( R_ECX, Rn );
1135 load_spreg( R_EAX, R_MACH );
1136 MEM_WRITE_LONG( R_ECX, R_EAX );
1137 }
1138 break;
1139 case 0x1:
1140 { /* STS.L MACL, @-Rn */
1141 uint32_t Rn = ((ir>>8)&0xF);
1142 load_reg( R_ECX, Rn );
1143 ADD_imm8s_r32( -4, Rn );
1144 store_reg( R_ECX, Rn );
1145 load_spreg( R_EAX, R_MACL );
1146 MEM_WRITE_LONG( R_ECX, R_EAX );
1147 }
1148 break;
1149 case 0x2:
1150 { /* STS.L PR, @-Rn */
1151 uint32_t Rn = ((ir>>8)&0xF);
1152 load_reg( R_ECX, Rn );
1153 ADD_imm8s_r32( -4, Rn );
1154 store_reg( R_ECX, Rn );
1155 load_spreg( R_EAX, R_PR );
1156 MEM_WRITE_LONG( R_ECX, R_EAX );
1157 }
1158 break;
1159 case 0x3:
1160 { /* STC.L SGR, @-Rn */
1161 uint32_t Rn = ((ir>>8)&0xF);
1162 load_reg( R_ECX, Rn );
1163 ADD_imm8s_r32( -4, Rn );
1164 store_reg( R_ECX, Rn );
1165 load_spreg( R_EAX, R_SGR );
1166 MEM_WRITE_LONG( R_ECX, R_EAX );
1167 }
1168 break;
1169 case 0x5:
1170 { /* STS.L FPUL, @-Rn */
1171 uint32_t Rn = ((ir>>8)&0xF);
1172 load_reg( R_ECX, Rn );
1173 ADD_imm8s_r32( -4, Rn );
1174 store_reg( R_ECX, Rn );
1175 load_spreg( R_EAX, R_FPUL );
1176 MEM_WRITE_LONG( R_ECX, R_EAX );
1177 }
1178 break;
1179 case 0x6:
1180 { /* STS.L FPSCR, @-Rn */
1181 uint32_t Rn = ((ir>>8)&0xF);
1182 load_reg( R_ECX, Rn );
1183 ADD_imm8s_r32( -4, Rn );
1184 store_reg( R_ECX, Rn );
1185 load_spreg( R_EAX, R_FPSCR );
1186 MEM_WRITE_LONG( R_ECX, R_EAX );
1187 }
1188 break;
1189 case 0xF:
1190 { /* STC.L DBR, @-Rn */
1191 uint32_t Rn = ((ir>>8)&0xF);
1192 load_reg( R_ECX, Rn );
1193 ADD_imm8s_r32( -4, Rn );
1194 store_reg( R_ECX, Rn );
1195 load_spreg( R_EAX, R_DBR );
1196 MEM_WRITE_LONG( R_ECX, R_EAX );
1197 }
1198 break;
1199 default:
1200 UNDEF();
1201 break;
1202 }
1203 break;
1204 case 0x3:
1205 switch( (ir&0x80) >> 7 ) {
1206 case 0x0:
1207 switch( (ir&0x70) >> 4 ) {
1208 case 0x0:
1209 { /* STC.L SR, @-Rn */
1210 uint32_t Rn = ((ir>>8)&0xF);
1211 load_reg( R_ECX, Rn );
1212 ADD_imm8s_r32( -4, Rn );
1213 store_reg( R_ECX, Rn );
1214 call_func0( sh4_read_sr );
1215 MEM_WRITE_LONG( R_ECX, R_EAX );
1216 }
1217 break;
1218 case 0x1:
1219 { /* STC.L GBR, @-Rn */
1220 uint32_t Rn = ((ir>>8)&0xF);
1221 load_reg( R_ECX, Rn );
1222 ADD_imm8s_r32( -4, Rn );
1223 store_reg( R_ECX, Rn );
1224 load_spreg( R_EAX, R_GBR );
1225 MEM_WRITE_LONG( R_ECX, R_EAX );
1226 }
1227 break;
1228 case 0x2:
1229 { /* STC.L VBR, @-Rn */
1230 uint32_t Rn = ((ir>>8)&0xF);
1231 load_reg( R_ECX, Rn );
1232 ADD_imm8s_r32( -4, Rn );
1233 store_reg( R_ECX, Rn );
1234 load_spreg( R_EAX, R_VBR );
1235 MEM_WRITE_LONG( R_ECX, R_EAX );
1236 }
1237 break;
1238 case 0x3:
1239 { /* STC.L SSR, @-Rn */
1240 uint32_t Rn = ((ir>>8)&0xF);
1241 load_reg( R_ECX, Rn );
1242 ADD_imm8s_r32( -4, Rn );
1243 store_reg( R_ECX, Rn );
1244 load_spreg( R_EAX, R_SSR );
1245 MEM_WRITE_LONG( R_ECX, R_EAX );
1246 }
1247 break;
1248 case 0x4:
1249 { /* STC.L SPC, @-Rn */
1250 uint32_t Rn = ((ir>>8)&0xF);
1251 load_reg( R_ECX, Rn );
1252 ADD_imm8s_r32( -4, Rn );
1253 store_reg( R_ECX, Rn );
1254 load_spreg( R_EAX, R_SPC );
1255 MEM_WRITE_LONG( R_ECX, R_EAX );
1256 }
1257 break;
1258 default:
1259 UNDEF();
1260 break;
1261 }
1262 break;
1263 case 0x1:
1264 { /* STC.L Rm_BANK, @-Rn */
1265 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm_BANK = ((ir>>4)&0x7);
1266 load_reg( R_ECX, Rn );
1267 ADD_imm8s_r32( -4, Rn );
1268 store_reg( R_ECX, Rn );
1269 load_spreg( R_EAX, REG_OFFSET(r_bank[Rm_BANK]) );
1270 MEM_WRITE_LONG( R_ECX, R_EAX );
1271 }
1272 break;
1273 }
1274 break;
1275 case 0x4:
1276 switch( (ir&0xF0) >> 4 ) {
1277 case 0x0:
1278 { /* ROTL Rn */
1279 uint32_t Rn = ((ir>>8)&0xF);
1280 load_reg( R_EAX, Rn );
1281 ROL1_r32( R_EAX );
1282 store_reg( R_EAX, Rn );
1283 SETC_t();
1284 }
1285 break;
1286 case 0x2:
1287 { /* ROTCL Rn */
1288 uint32_t Rn = ((ir>>8)&0xF);
1289 load_reg( R_EAX, Rn );
1290 LDC_t();
1291 RCL1_r32( R_EAX );
1292 store_reg( R_EAX, Rn );
1293 SETC_t();
1294 }
1295 break;
1296 default:
1297 UNDEF();
1298 break;
1299 }
1300 break;
1301 case 0x5:
1302 switch( (ir&0xF0) >> 4 ) {
1303 case 0x0:
1304 { /* ROTR Rn */
1305 uint32_t Rn = ((ir>>8)&0xF);
1306 load_reg( R_EAX, Rn );
1307 ROR1_r32( R_EAX );
1308 store_reg( R_EAX, Rn );
1309 SETC_t();
1310 }
1311 break;
1312 case 0x1:
1313 { /* CMP/PL Rn */
1314 uint32_t Rn = ((ir>>8)&0xF);
1315 load_reg( R_EAX, Rn );
1316 CMP_imm8s_r32( 0, R_EAX );
1317 SETG_t();
1318 }
1319 break;
1320 case 0x2:
1321 { /* ROTCR Rn */
1322 uint32_t Rn = ((ir>>8)&0xF);
1323 load_reg( R_EAX, Rn );
1324 LDC_t();
1325 RCR1_r32( R_EAX );
1326 store_reg( R_EAX, Rn );
1327 SETC_t();
1328 }
1329 break;
1330 default:
1331 UNDEF();
1332 break;
1333 }
1334 break;
1335 case 0x6:
1336 switch( (ir&0xF0) >> 4 ) {
1337 case 0x0:
1338 { /* LDS.L @Rm+, MACH */
1339 uint32_t Rm = ((ir>>8)&0xF);
1340 load_reg( R_EAX, Rm );
1341 MOV_r32_r32( R_EAX, R_ECX );
1342 ADD_imm8s_r32( 4, R_EAX );
1343 store_reg( R_EAX, Rm );
1344 MEM_READ_LONG( R_ECX, R_EAX );
1345 store_spreg( R_EAX, R_MACH );
1346 }
1347 break;
1348 case 0x1:
1349 { /* LDS.L @Rm+, MACL */
1350 uint32_t Rm = ((ir>>8)&0xF);
1351 load_reg( R_EAX, Rm );
1352 MOV_r32_r32( R_EAX, R_ECX );
1353 ADD_imm8s_r32( 4, R_EAX );
1354 store_reg( R_EAX, Rm );
1355 MEM_READ_LONG( R_ECX, R_EAX );
1356 store_spreg( R_EAX, R_MACL );
1357 }
1358 break;
1359 case 0x2:
1360 { /* LDS.L @Rm+, PR */
1361 uint32_t Rm = ((ir>>8)&0xF);
1362 load_reg( R_EAX, Rm );
1363 MOV_r32_r32( R_EAX, R_ECX );
1364 ADD_imm8s_r32( 4, R_EAX );
1365 store_reg( R_EAX, Rm );
1366 MEM_READ_LONG( R_ECX, R_EAX );
1367 store_spreg( R_EAX, R_PR );
1368 }
1369 break;
1370 case 0x3:
1371 { /* LDC.L @Rm+, SGR */
1372 uint32_t Rm = ((ir>>8)&0xF);
1373 load_reg( R_EAX, Rm );
1374 MOV_r32_r32( R_EAX, R_ECX );
1375 ADD_imm8s_r32( 4, R_EAX );
1376 store_reg( R_EAX, Rm );
1377 MEM_READ_LONG( R_ECX, R_EAX );
1378 store_spreg( R_EAX, R_SGR );
1379 }
1380 break;
1381 case 0x5:
1382 { /* LDS.L @Rm+, FPUL */
1383 uint32_t Rm = ((ir>>8)&0xF);
1384 load_reg( R_EAX, Rm );
1385 MOV_r32_r32( R_EAX, R_ECX );
1386 ADD_imm8s_r32( 4, R_EAX );
1387 store_reg( R_EAX, Rm );
1388 MEM_READ_LONG( R_ECX, R_EAX );
1389 store_spreg( R_EAX, R_FPUL );
1390 }
1391 break;
1392 case 0x6:
1393 { /* LDS.L @Rm+, FPSCR */
1394 uint32_t Rm = ((ir>>8)&0xF);
1395 load_reg( R_EAX, Rm );
1396 MOV_r32_r32( R_EAX, R_ECX );
1397 ADD_imm8s_r32( 4, R_EAX );
1398 store_reg( R_EAX, Rm );
1399 MEM_READ_LONG( R_ECX, R_EAX );
1400 store_spreg( R_EAX, R_FPSCR );
1401 }
1402 break;
1403 case 0xF:
1404 { /* LDC.L @Rm+, DBR */
1405 uint32_t Rm = ((ir>>8)&0xF);
1406 load_reg( R_EAX, Rm );
1407 MOV_r32_r32( R_EAX, R_ECX );
1408 ADD_imm8s_r32( 4, R_EAX );
1409 store_reg( R_EAX, Rm );
1410 MEM_READ_LONG( R_ECX, R_EAX );
1411 store_spreg( R_EAX, R_DBR );
1412 }
1413 break;
1414 default:
1415 UNDEF();
1416 break;
1417 }
1418 break;
1419 case 0x7:
1420 switch( (ir&0x80) >> 7 ) {
1421 case 0x0:
1422 switch( (ir&0x70) >> 4 ) {
1423 case 0x0:
1424 { /* LDC.L @Rm+, SR */
1425 uint32_t Rm = ((ir>>8)&0xF);
1426 load_reg( R_EAX, Rm );
1427 MOV_r32_r32( R_EAX, R_ECX );
1428 ADD_imm8s_r32( 4, R_EAX );
1429 store_reg( R_EAX, Rm );
1430 MEM_READ_LONG( R_ECX, R_EAX );
1431 call_func1( sh4_write_sr, R_EAX );
1432 }
1433 break;
1434 case 0x1:
1435 { /* LDC.L @Rm+, GBR */
1436 uint32_t Rm = ((ir>>8)&0xF);
1437 load_reg( R_EAX, Rm );
1438 MOV_r32_r32( R_EAX, R_ECX );
1439 ADD_imm8s_r32( 4, R_EAX );
1440 store_reg( R_EAX, Rm );
1441 MEM_READ_LONG( R_ECX, R_EAX );
1442 store_spreg( R_EAX, R_GBR );
1443 }
1444 break;
1445 case 0x2:
1446 { /* LDC.L @Rm+, VBR */
1447 uint32_t Rm = ((ir>>8)&0xF);
1448 load_reg( R_EAX, Rm );
1449 MOV_r32_r32( R_EAX, R_ECX );
1450 ADD_imm8s_r32( 4, R_EAX );
1451 store_reg( R_EAX, Rm );
1452 MEM_READ_LONG( R_ECX, R_EAX );
1453 store_spreg( R_EAX, R_VBR );
1454 }
1455 break;
1456 case 0x3:
1457 { /* LDC.L @Rm+, SSR */
1458 uint32_t Rm = ((ir>>8)&0xF);
1459 load_reg( R_EAX, Rm );
1460 MOV_r32_r32( R_EAX, R_ECX );
1461 ADD_imm8s_r32( 4, R_EAX );
1462 store_reg( R_EAX, Rm );
1463 MEM_READ_LONG( R_ECX, R_EAX );
1464 store_spreg( R_EAX, R_SSR );
1465 }
1466 break;
1467 case 0x4:
1468 { /* LDC.L @Rm+, SPC */
1469 uint32_t Rm = ((ir>>8)&0xF);
1470 load_reg( R_EAX, Rm );
1471 MOV_r32_r32( R_EAX, R_ECX );
1472 ADD_imm8s_r32( 4, R_EAX );
1473 store_reg( R_EAX, Rm );
1474 MEM_READ_LONG( R_ECX, R_EAX );
1475 store_spreg( R_EAX, R_SPC );
1476 }
1477 break;
1478 default:
1479 UNDEF();
1480 break;
1481 }
1482 break;
1483 case 0x1:
1484 { /* LDC.L @Rm+, Rn_BANK */
1485 uint32_t Rm = ((ir>>8)&0xF); uint32_t Rn_BANK = ((ir>>4)&0x7);
1486 load_reg( R_EAX, Rm );
1487 MOV_r32_r32( R_EAX, R_ECX );
1488 ADD_imm8s_r32( 4, R_EAX );
1489 store_reg( R_EAX, Rm );
1490 MEM_READ_LONG( R_ECX, R_EAX );
1491 store_spreg( R_EAX, REG_OFFSET(r_bank[Rn_BANK]) );
1492 }
1493 break;
1494 }
1495 break;
1496 case 0x8:
1497 switch( (ir&0xF0) >> 4 ) {
1498 case 0x0:
1499 { /* SHLL2 Rn */
1500 uint32_t Rn = ((ir>>8)&0xF);
1501 load_reg( R_EAX, Rn );
1502 SHL_imm8_r32( 2, R_EAX );
1503 store_reg( R_EAX, Rn );
1504 }
1505 break;
1506 case 0x1:
1507 { /* SHLL8 Rn */
1508 uint32_t Rn = ((ir>>8)&0xF);
1509 load_reg( R_EAX, Rn );
1510 SHL_imm8_r32( 8, R_EAX );
1511 store_reg( R_EAX, Rn );
1512 }
1513 break;
1514 case 0x2:
1515 { /* SHLL16 Rn */
1516 uint32_t Rn = ((ir>>8)&0xF);
1517 load_reg( R_EAX, Rn );
1518 SHL_imm8_r32( 16, R_EAX );
1519 store_reg( R_EAX, Rn );
1520 }
1521 break;
1522 default:
1523 UNDEF();
1524 break;
1525 }
1526 break;
1527 case 0x9:
1528 switch( (ir&0xF0) >> 4 ) {
1529 case 0x0:
1530 { /* SHLR2 Rn */
1531 uint32_t Rn = ((ir>>8)&0xF);
1532 load_reg( R_EAX, Rn );
1533 SHR_imm8_r32( 2, R_EAX );
1534 store_reg( R_EAX, Rn );
1535 }
1536 break;
1537 case 0x1:
1538 { /* SHLR8 Rn */
1539 uint32_t Rn = ((ir>>8)&0xF);
1540 load_reg( R_EAX, Rn );
1541 SHR_imm8_r32( 8, R_EAX );
1542 store_reg( R_EAX, Rn );
1543 }
1544 break;
1545 case 0x2:
1546 { /* SHLR16 Rn */
1547 uint32_t Rn = ((ir>>8)&0xF);
1548 load_reg( R_EAX, Rn );
1549 SHR_imm8_r32( 16, R_EAX );
1550 store_reg( R_EAX, Rn );
1551 }
1552 break;
1553 default:
1554 UNDEF();
1555 break;
1556 }
1557 break;
1558 case 0xA:
1559 switch( (ir&0xF0) >> 4 ) {
1560 case 0x0:
1561 { /* LDS Rm, MACH */
1562 uint32_t Rm = ((ir>>8)&0xF);
1563 load_reg( R_EAX, Rm );
1564 store_spreg( R_EAX, R_MACH );
1565 }
1566 break;
1567 case 0x1:
1568 { /* LDS Rm, MACL */
1569 uint32_t Rm = ((ir>>8)&0xF);
1570 load_reg( R_EAX, Rm );
1571 store_spreg( R_EAX, R_MACL );
1572 }
1573 break;
1574 case 0x2:
1575 { /* LDS Rm, PR */
1576 uint32_t Rm = ((ir>>8)&0xF);
1577 load_reg( R_EAX, Rm );
1578 store_spreg( R_EAX, R_PR );
1579 }
1580 break;
1581 case 0x3:
1582 { /* LDC Rm, SGR */
1583 uint32_t Rm = ((ir>>8)&0xF);
1584 load_reg( R_EAX, Rm );
1585 store_spreg( R_EAX, R_SGR );
1586 }
1587 break;
1588 case 0x5:
1589 { /* LDS Rm, FPUL */
1590 uint32_t Rm = ((ir>>8)&0xF);
1591 load_reg( R_EAX, Rm );
1592 store_spreg( R_EAX, R_FPUL );
1593 }
1594 break;
1595 case 0x6:
1596 { /* LDS Rm, FPSCR */
1597 uint32_t Rm = ((ir>>8)&0xF);
1598 load_reg( R_EAX, Rm );
1599 store_spreg( R_EAX, R_FPSCR );
1600 }
1601 break;
1602 case 0xF:
1603 { /* LDC Rm, DBR */
1604 uint32_t Rm = ((ir>>8)&0xF);
1605 load_reg( R_EAX, Rm );
1606 store_spreg( R_EAX, R_DBR );
1607 }
1608 break;
1609 default:
1610 UNDEF();
1611 break;
1612 }
1613 break;
1614 case 0xB:
1615 switch( (ir&0xF0) >> 4 ) {
1616 case 0x0:
1617 { /* JSR @Rn */
1618 uint32_t Rn = ((ir>>8)&0xF);
1619 if( sh4_x86.in_delay_slot ) {
1620 SLOTILLEGAL();
1621 } else {
1622 load_imm32( R_EAX, pc + 4 );
1623 store_spreg( R_EAX, R_PR );
1624 load_reg( R_EDI, Rn );
1625 sh4_x86.in_delay_slot = TRUE;
1626 INC_r32(R_ESI);
1627 return 0;
1628 }
1629 }
1630 break;
1631 case 0x1:
1632 { /* TAS.B @Rn */
1633 uint32_t Rn = ((ir>>8)&0xF);
1634 load_reg( R_ECX, Rn );
1635 MEM_READ_BYTE( R_ECX, R_EAX );
1636 TEST_r8_r8( R_AL, R_AL );
1637 SETE_t();
1638 OR_imm8_r8( 0x80, R_AL );
1639 MEM_WRITE_BYTE( R_ECX, R_EAX );
1640 }
1641 break;
1642 case 0x2:
1643 { /* JMP @Rn */
1644 uint32_t Rn = ((ir>>8)&0xF);
1645 if( sh4_x86.in_delay_slot ) {
1646 SLOTILLEGAL();
1647 } else {
1648 load_reg( R_EDI, Rn );
1649 sh4_x86.in_delay_slot = TRUE;
1650 INC_r32(R_ESI);
1651 return 0;
1652 }
1653 }
1654 break;
1655 default:
1656 UNDEF();
1657 break;
1658 }
1659 break;
1660 case 0xC:
1661 { /* SHAD Rm, Rn */
1662 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1663 /* Annoyingly enough, not directly convertible */
1664 load_reg( R_EAX, Rn );
1665 load_reg( R_ECX, Rm );
1666 CMP_imm32_r32( 0, R_ECX );
1667 JAE_rel8(9);
1669 NEG_r32( R_ECX ); // 2
1670 AND_imm8_r8( 0x1F, R_CL ); // 3
1671 SAR_r32_CL( R_EAX ); // 2
1672 JMP_rel8(5); // 2
1674 AND_imm8_r8( 0x1F, R_CL ); // 3
1675 SHL_r32_CL( R_EAX ); // 2
1677 store_reg( R_EAX, Rn );
1678 }
1679 break;
1680 case 0xD:
1681 { /* SHLD Rm, Rn */
1682 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1683 load_reg( R_EAX, Rn );
1684 load_reg( R_ECX, Rm );
1686 MOV_r32_r32( R_EAX, R_EDX );
1687 SHL_r32_CL( R_EAX );
1688 NEG_r32( R_ECX );
1689 SHR_r32_CL( R_EDX );
1690 CMP_imm8s_r32( 0, R_ECX );
1691 CMOVAE_r32_r32( R_EDX, R_EAX );
1692 store_reg( R_EAX, Rn );
1693 }
1694 break;
1695 case 0xE:
1696 switch( (ir&0x80) >> 7 ) {
1697 case 0x0:
1698 switch( (ir&0x70) >> 4 ) {
1699 case 0x0:
1700 { /* LDC Rm, SR */
1701 uint32_t Rm = ((ir>>8)&0xF);
1702 load_reg( R_EAX, Rm );
1703 call_func1( sh4_write_sr, R_EAX );
1704 }
1705 break;
1706 case 0x1:
1707 { /* LDC Rm, GBR */
1708 uint32_t Rm = ((ir>>8)&0xF);
1709 load_reg( R_EAX, Rm );
1710 store_spreg( R_EAX, R_GBR );
1711 }
1712 break;
1713 case 0x2:
1714 { /* LDC Rm, VBR */
1715 uint32_t Rm = ((ir>>8)&0xF);
1716 load_reg( R_EAX, Rm );
1717 store_spreg( R_EAX, R_VBR );
1718 }
1719 break;
1720 case 0x3:
1721 { /* LDC Rm, SSR */
1722 uint32_t Rm = ((ir>>8)&0xF);
1723 load_reg( R_EAX, Rm );
1724 store_spreg( R_EAX, R_SSR );
1725 }
1726 break;
1727 case 0x4:
1728 { /* LDC Rm, SPC */
1729 uint32_t Rm = ((ir>>8)&0xF);
1730 load_reg( R_EAX, Rm );
1731 store_spreg( R_EAX, R_SPC );
1732 }
1733 break;
1734 default:
1735 UNDEF();
1736 break;
1737 }
1738 break;
1739 case 0x1:
1740 { /* LDC Rm, Rn_BANK */
1741 uint32_t Rm = ((ir>>8)&0xF); uint32_t Rn_BANK = ((ir>>4)&0x7);
1742 load_reg( R_EAX, Rm );
1743 store_spreg( R_EAX, REG_OFFSET(r_bank[Rn_BANK]) );
1744 }
1745 break;
1746 }
1747 break;
1748 case 0xF:
1749 { /* MAC.W @Rm+, @Rn+ */
1750 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1751 }
1752 break;
1753 }
1754 break;
1755 case 0x5:
1756 { /* MOV.L @(disp, Rm), Rn */
1757 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF); uint32_t disp = (ir&0xF)<<2;
1758 load_reg( R_ECX, Rm );
1759 ADD_imm8s_r32( disp, R_ECX );
1760 check_ralign32( R_ECX );
1761 MEM_READ_LONG( R_ECX, R_EAX );
1762 store_reg( R_EAX, Rn );
1763 }
1764 break;
1765 case 0x6:
1766 switch( ir&0xF ) {
1767 case 0x0:
1768 { /* MOV.B @Rm, Rn */
1769 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1770 load_reg( R_ECX, Rm );
1771 MEM_READ_BYTE( R_ECX, R_EAX );
1772 store_reg( R_ECX, Rn );
1773 }
1774 break;
1775 case 0x1:
1776 { /* MOV.W @Rm, Rn */
1777 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1778 load_reg( R_ECX, Rm );
1779 check_ralign16( R_ECX );
1780 MEM_READ_WORD( R_ECX, R_EAX );
1781 store_reg( R_EAX, Rn );
1782 }
1783 break;
1784 case 0x2:
1785 { /* MOV.L @Rm, Rn */
1786 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1787 load_reg( R_ECX, Rm );
1788 check_ralign32( R_ECX );
1789 MEM_READ_LONG( R_ECX, R_EAX );
1790 store_reg( R_EAX, Rn );
1791 }
1792 break;
1793 case 0x3:
1794 { /* MOV Rm, Rn */
1795 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1796 load_reg( R_EAX, Rm );
1797 store_reg( R_EAX, Rn );
1798 }
1799 break;
1800 case 0x4:
1801 { /* MOV.B @Rm+, Rn */
1802 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1803 load_reg( R_ECX, Rm );
1804 MOV_r32_r32( R_ECX, R_EAX );
1805 ADD_imm8s_r32( 1, R_EAX );
1806 store_reg( R_EAX, Rm );
1807 MEM_READ_BYTE( R_ECX, R_EAX );
1808 store_reg( R_EAX, Rn );
1809 }
1810 break;
1811 case 0x5:
1812 { /* MOV.W @Rm+, Rn */
1813 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1814 load_reg( R_EAX, Rm );
1815 check_ralign16( R_EAX );
1816 MOV_r32_r32( R_EAX, R_ECX );
1817 ADD_imm8s_r32( 2, R_EAX );
1818 store_reg( R_EAX, Rm );
1819 MEM_READ_WORD( R_ECX, R_EAX );
1820 store_reg( R_EAX, Rn );
1821 }
1822 break;
1823 case 0x6:
1824 { /* MOV.L @Rm+, Rn */
1825 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1826 load_reg( R_EAX, Rm );
1827 check_ralign32( R_ECX );
1828 MOV_r32_r32( R_EAX, R_ECX );
1829 ADD_imm8s_r32( 4, R_EAX );
1830 store_reg( R_EAX, Rm );
1831 MEM_READ_LONG( R_ECX, R_EAX );
1832 store_reg( R_EAX, Rn );
1833 }
1834 break;
1835 case 0x7:
1836 { /* NOT Rm, Rn */
1837 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1838 load_reg( R_EAX, Rm );
1839 NOT_r32( R_EAX );
1840 store_reg( R_EAX, Rn );
1841 }
1842 break;
1843 case 0x8:
1844 { /* SWAP.B Rm, Rn */
1845 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1846 load_reg( R_EAX, Rm );
1847 XCHG_r8_r8( R_AL, R_AH );
1848 store_reg( R_EAX, Rn );
1849 }
1850 break;
1851 case 0x9:
1852 { /* SWAP.W Rm, Rn */
1853 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1854 load_reg( R_EAX, Rm );
1855 MOV_r32_r32( R_EAX, R_ECX );
1856 SHL_imm8_r32( 16, R_ECX );
1857 SHR_imm8_r32( 16, R_EAX );
1858 OR_r32_r32( R_EAX, R_ECX );
1859 store_reg( R_ECX, Rn );
1860 }
1861 break;
1862 case 0xA:
1863 { /* NEGC Rm, Rn */
1864 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1865 load_reg( R_EAX, Rm );
1866 XOR_r32_r32( R_ECX, R_ECX );
1867 LDC_t();
1868 SBB_r32_r32( R_EAX, R_ECX );
1869 store_reg( R_ECX, Rn );
1870 SETC_t();
1871 }
1872 break;
1873 case 0xB:
1874 { /* NEG Rm, Rn */
1875 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1876 load_reg( R_EAX, Rm );
1877 NEG_r32( R_EAX );
1878 store_reg( R_EAX, Rn );
1879 }
1880 break;
1881 case 0xC:
1882 { /* EXTU.B Rm, Rn */
1883 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1884 load_reg( R_EAX, Rm );
1885 MOVZX_r8_r32( R_EAX, R_EAX );
1886 store_reg( R_EAX, Rn );
1887 }
1888 break;
1889 case 0xD:
1890 { /* EXTU.W Rm, Rn */
1891 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1892 load_reg( R_EAX, Rm );
1893 MOVZX_r16_r32( R_EAX, R_EAX );
1894 store_reg( R_EAX, Rn );
1895 }
1896 break;
1897 case 0xE:
1898 { /* EXTS.B Rm, Rn */
1899 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1900 load_reg( R_EAX, Rm );
1901 MOVSX_r8_r32( R_EAX, R_EAX );
1902 store_reg( R_EAX, Rn );
1903 }
1904 break;
1905 case 0xF:
1906 { /* EXTS.W Rm, Rn */
1907 uint32_t Rn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
1908 load_reg( R_EAX, Rm );
1909 MOVSX_r16_r32( R_EAX, R_EAX );
1910 store_reg( R_EAX, Rn );
1911 }
1912 break;
1913 }
1914 break;
1915 case 0x7:
1916 { /* ADD #imm, Rn */
1917 uint32_t Rn = ((ir>>8)&0xF); int32_t imm = SIGNEXT8(ir&0xFF);
1918 load_reg( R_EAX, Rn );
1919 ADD_imm8s_r32( imm, R_EAX );
1920 store_reg( R_EAX, Rn );
1921 }
1922 break;
1923 case 0x8:
1924 switch( (ir&0xF00) >> 8 ) {
1925 case 0x0:
1926 { /* MOV.B R0, @(disp, Rn) */
1927 uint32_t Rn = ((ir>>4)&0xF); uint32_t disp = (ir&0xF);
1928 load_reg( R_EAX, 0 );
1929 load_reg( R_ECX, Rn );
1930 ADD_imm32_r32( disp, R_ECX );
1931 MEM_WRITE_BYTE( R_ECX, R_EAX );
1932 }
1933 break;
1934 case 0x1:
1935 { /* MOV.W R0, @(disp, Rn) */
1936 uint32_t Rn = ((ir>>4)&0xF); uint32_t disp = (ir&0xF)<<1;
1937 load_reg( R_ECX, Rn );
1938 load_reg( R_EAX, 0 );
1939 ADD_imm32_r32( disp, R_ECX );
1940 check_walign16( R_ECX );
1941 MEM_WRITE_WORD( R_ECX, R_EAX );
1942 }
1943 break;
1944 case 0x4:
1945 { /* MOV.B @(disp, Rm), R0 */
1946 uint32_t Rm = ((ir>>4)&0xF); uint32_t disp = (ir&0xF);
1947 load_reg( R_ECX, Rm );
1948 ADD_imm32_r32( disp, R_ECX );
1949 MEM_READ_BYTE( R_ECX, R_EAX );
1950 store_reg( R_EAX, 0 );
1951 }
1952 break;
1953 case 0x5:
1954 { /* MOV.W @(disp, Rm), R0 */
1955 uint32_t Rm = ((ir>>4)&0xF); uint32_t disp = (ir&0xF)<<1;
1956 load_reg( R_ECX, Rm );
1957 ADD_imm32_r32( disp, R_ECX );
1958 check_ralign16( R_ECX );
1959 MEM_READ_WORD( R_ECX, R_EAX );
1960 store_reg( R_EAX, 0 );
1961 }
1962 break;
1963 case 0x8:
1964 { /* CMP/EQ #imm, R0 */
1965 int32_t imm = SIGNEXT8(ir&0xFF);
1966 load_reg( R_EAX, 0 );
1967 CMP_imm8s_r32(imm, R_EAX);
1968 SETE_t();
1969 }
1970 break;
1971 case 0x9:
1972 { /* BT disp */
1973 int32_t disp = SIGNEXT8(ir&0xFF)<<1;
1974 if( sh4_x86.in_delay_slot ) {
1975 SLOTILLEGAL();
1976 } else {
1977 load_imm32( R_EDI, pc + 2 );
1978 CMP_imm8s_sh4r( 0, R_T );
1979 JE_rel8( 5 );
1980 load_imm32( R_EDI, disp + pc + 4 );
1981 INC_r32(R_ESI);
1982 return 1;
1983 }
1984 }
1985 break;
1986 case 0xB:
1987 { /* BF disp */
1988 int32_t disp = SIGNEXT8(ir&0xFF)<<1;
1989 if( sh4_x86.in_delay_slot ) {
1990 SLOTILLEGAL();
1991 } else {
1992 load_imm32( R_EDI, pc + 2 );
1993 CMP_imm8s_sh4r( 0, R_T );
1994 JNE_rel8( 5 );
1995 load_imm32( R_EDI, disp + pc + 4 );
1996 INC_r32(R_ESI);
1997 return 1;
1998 }
1999 }
2000 break;
2001 case 0xD:
2002 { /* BT/S disp */
2003 int32_t disp = SIGNEXT8(ir&0xFF)<<1;
2004 if( sh4_x86.in_delay_slot ) {
2005 SLOTILLEGAL();
2006 } else {
2007 load_imm32( R_EDI, pc + 2 );
2008 CMP_imm8s_sh4r( 0, R_T );
2009 JE_rel8( 5 );
2010 load_imm32( R_EDI, disp + pc + 4 );
2011 sh4_x86.in_delay_slot = TRUE;
2012 INC_r32(R_ESI);
2013 return 0;
2014 }
2015 }
2016 break;
2017 case 0xF:
2018 { /* BF/S disp */
2019 int32_t disp = SIGNEXT8(ir&0xFF)<<1;
2020 if( sh4_x86.in_delay_slot ) {
2021 SLOTILLEGAL();
2022 } else {
2023 load_imm32( R_EDI, pc + 2 );
2024 CMP_imm8s_sh4r( 0, R_T );
2025 JNE_rel8( 5 );
2026 load_imm32( R_EDI, disp + pc + 4 );
2027 sh4_x86.in_delay_slot = TRUE;
2028 INC_r32(R_ESI);
2029 return 0;
2030 }
2031 }
2032 break;
2033 default:
2034 UNDEF();
2035 break;
2036 }
2037 break;
2038 case 0x9:
2039 { /* MOV.W @(disp, PC), Rn */
2040 uint32_t Rn = ((ir>>8)&0xF); uint32_t disp = (ir&0xFF)<<1;
2041 if( sh4_x86.in_delay_slot ) {
2042 SLOTILLEGAL();
2043 } else {
2044 load_imm32( R_ECX, pc + disp + 4 );
2045 MEM_READ_WORD( R_ECX, R_EAX );
2046 store_reg( R_EAX, Rn );
2047 }
2048 }
2049 break;
2050 case 0xA:
2051 { /* BRA disp */
2052 int32_t disp = SIGNEXT12(ir&0xFFF)<<1;
2053 if( sh4_x86.in_delay_slot ) {
2054 SLOTILLEGAL();
2055 } else {
2056 load_imm32( R_EDI, disp + pc + 4 );
2057 sh4_x86.in_delay_slot = TRUE;
2058 INC_r32(R_ESI);
2059 return 0;
2060 }
2061 }
2062 break;
2063 case 0xB:
2064 { /* BSR disp */
2065 int32_t disp = SIGNEXT12(ir&0xFFF)<<1;
2066 if( sh4_x86.in_delay_slot ) {
2067 SLOTILLEGAL();
2068 } else {
2069 load_imm32( R_EAX, pc + 4 );
2070 store_spreg( R_EAX, R_PR );
2071 load_imm32( R_EDI, disp + pc + 4 );
2072 sh4_x86.in_delay_slot = TRUE;
2073 INC_r32(R_ESI);
2074 return 0;
2075 }
2076 }
2077 break;
2078 case 0xC:
2079 switch( (ir&0xF00) >> 8 ) {
2080 case 0x0:
2081 { /* MOV.B R0, @(disp, GBR) */
2082 uint32_t disp = (ir&0xFF);
2083 load_reg( R_EAX, 0 );
2084 load_spreg( R_ECX, R_GBR );
2085 ADD_imm32_r32( disp, R_ECX );
2086 MEM_WRITE_BYTE( R_ECX, R_EAX );
2087 }
2088 break;
2089 case 0x1:
2090 { /* MOV.W R0, @(disp, GBR) */
2091 uint32_t disp = (ir&0xFF)<<1;
2092 load_spreg( R_ECX, R_GBR );
2093 load_reg( R_EAX, 0 );
2094 ADD_imm32_r32( disp, R_ECX );
2095 check_walign16( R_ECX );
2096 MEM_WRITE_WORD( R_ECX, R_EAX );
2097 }
2098 break;
2099 case 0x2:
2100 { /* MOV.L R0, @(disp, GBR) */
2101 uint32_t disp = (ir&0xFF)<<2;
2102 load_spreg( R_ECX, R_GBR );
2103 load_reg( R_EAX, 0 );
2104 ADD_imm32_r32( disp, R_ECX );
2105 check_walign32( R_ECX );
2106 MEM_WRITE_LONG( R_ECX, R_EAX );
2107 }
2108 break;
2109 case 0x3:
2110 { /* TRAPA #imm */
2111 uint32_t imm = (ir&0xFF);
2112 if( sh4_x86.in_delay_slot ) {
2113 SLOTILLEGAL();
2114 } else {
2115 // TODO: Write TRA
2116 RAISE_EXCEPTION(EXC_TRAP);
2117 }
2118 }
2119 break;
2120 case 0x4:
2121 { /* MOV.B @(disp, GBR), R0 */
2122 uint32_t disp = (ir&0xFF);
2123 load_spreg( R_ECX, R_GBR );
2124 ADD_imm32_r32( disp, R_ECX );
2125 MEM_READ_BYTE( R_ECX, R_EAX );
2126 store_reg( R_EAX, 0 );
2127 }
2128 break;
2129 case 0x5:
2130 { /* MOV.W @(disp, GBR), R0 */
2131 uint32_t disp = (ir&0xFF)<<1;
2132 load_spreg( R_ECX, R_GBR );
2133 ADD_imm32_r32( disp, R_ECX );
2134 check_ralign16( R_ECX );
2135 MEM_READ_WORD( R_ECX, R_EAX );
2136 store_reg( R_EAX, 0 );
2137 }
2138 break;
2139 case 0x6:
2140 { /* MOV.L @(disp, GBR), R0 */
2141 uint32_t disp = (ir&0xFF)<<2;
2142 load_spreg( R_ECX, R_GBR );
2143 ADD_imm32_r32( disp, R_ECX );
2144 check_ralign32( R_ECX );
2145 MEM_READ_LONG( R_ECX, R_EAX );
2146 store_reg( R_EAX, 0 );
2147 }
2148 break;
2149 case 0x7:
2150 { /* MOVA @(disp, PC), R0 */
2151 uint32_t disp = (ir&0xFF)<<2;
2152 if( sh4_x86.in_delay_slot ) {
2153 SLOTILLEGAL();
2154 } else {
2155 load_imm32( R_ECX, (pc & 0xFFFFFFFC) + disp + 4 );
2156 store_reg( R_ECX, 0 );
2157 }
2158 }
2159 break;
2160 case 0x8:
2161 { /* TST #imm, R0 */
2162 uint32_t imm = (ir&0xFF);
2163 load_reg( R_EAX, 0 );
2164 TEST_imm32_r32( imm, R_EAX );
2165 SETE_t();
2166 }
2167 break;
2168 case 0x9:
2169 { /* AND #imm, R0 */
2170 uint32_t imm = (ir&0xFF);
2171 load_reg( R_EAX, 0 );
2172 AND_imm32_r32(imm, R_EAX);
2173 store_reg( R_EAX, 0 );
2174 }
2175 break;
2176 case 0xA:
2177 { /* XOR #imm, R0 */
2178 uint32_t imm = (ir&0xFF);
2179 load_reg( R_EAX, 0 );
2180 XOR_imm32_r32( imm, R_EAX );
2181 store_reg( R_EAX, 0 );
2182 }
2183 break;
2184 case 0xB:
2185 { /* OR #imm, R0 */
2186 uint32_t imm = (ir&0xFF);
2187 load_reg( R_EAX, 0 );
2188 OR_imm32_r32(imm, R_EAX);
2189 store_reg( R_EAX, 0 );
2190 }
2191 break;
2192 case 0xC:
2193 { /* TST.B #imm, @(R0, GBR) */
2194 uint32_t imm = (ir&0xFF);
2195 load_reg( R_EAX, 0);
2196 load_reg( R_ECX, R_GBR);
2197 ADD_r32_r32( R_EAX, R_ECX );
2198 MEM_READ_BYTE( R_ECX, R_EAX );
2199 TEST_imm8_r8( imm, R_EAX );
2200 SETE_t();
2201 }
2202 break;
2203 case 0xD:
2204 { /* AND.B #imm, @(R0, GBR) */
2205 uint32_t imm = (ir&0xFF);
2206 load_reg( R_EAX, 0 );
2207 load_spreg( R_ECX, R_GBR );
2208 ADD_r32_r32( R_EAX, R_ECX );
2209 MEM_READ_BYTE( R_ECX, R_EAX );
2210 AND_imm32_r32(imm, R_ECX );
2211 MEM_WRITE_BYTE( R_ECX, R_EAX );
2212 }
2213 break;
2214 case 0xE:
2215 { /* XOR.B #imm, @(R0, GBR) */
2216 uint32_t imm = (ir&0xFF);
2217 load_reg( R_EAX, 0 );
2218 load_spreg( R_ECX, R_GBR );
2219 ADD_r32_r32( R_EAX, R_ECX );
2220 MEM_READ_BYTE( R_ECX, R_EAX );
2221 XOR_imm32_r32( imm, R_EAX );
2222 MEM_WRITE_BYTE( R_ECX, R_EAX );
2223 }
2224 break;
2225 case 0xF:
2226 { /* OR.B #imm, @(R0, GBR) */
2227 uint32_t imm = (ir&0xFF);
2228 load_reg( R_EAX, 0 );
2229 load_spreg( R_ECX, R_GBR );
2230 ADD_r32_r32( R_EAX, R_ECX );
2231 MEM_READ_BYTE( R_ECX, R_EAX );
2232 OR_imm32_r32(imm, R_ECX );
2233 MEM_WRITE_BYTE( R_ECX, R_EAX );
2234 }
2235 break;
2236 }
2237 break;
2238 case 0xD:
2239 { /* MOV.L @(disp, PC), Rn */
2240 uint32_t Rn = ((ir>>8)&0xF); uint32_t disp = (ir&0xFF)<<2;
2241 if( sh4_x86.in_delay_slot ) {
2242 SLOTILLEGAL();
2243 } else {
2244 load_imm32( R_ECX, (pc & 0xFFFFFFFC) + disp + 4 );
2245 MEM_READ_LONG( R_ECX, R_EAX );
2246 store_reg( R_EAX, 0 );
2247 }
2248 }
2249 break;
2250 case 0xE:
2251 { /* MOV #imm, Rn */
2252 uint32_t Rn = ((ir>>8)&0xF); int32_t imm = SIGNEXT8(ir&0xFF);
2253 load_imm32( R_EAX, imm );
2254 store_reg( R_EAX, Rn );
2255 }
2256 break;
2257 case 0xF:
2258 switch( ir&0xF ) {
2259 case 0x0:
2260 { /* FADD FRm, FRn */
2261 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2262 }
2263 break;
2264 case 0x1:
2265 { /* FSUB FRm, FRn */
2266 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2267 }
2268 break;
2269 case 0x2:
2270 { /* FMUL FRm, FRn */
2271 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2272 }
2273 break;
2274 case 0x3:
2275 { /* FDIV FRm, FRn */
2276 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2277 }
2278 break;
2279 case 0x4:
2280 { /* FCMP/EQ FRm, FRn */
2281 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2282 }
2283 break;
2284 case 0x5:
2285 { /* FCMP/GT FRm, FRn */
2286 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2287 }
2288 break;
2289 case 0x6:
2290 { /* FMOV @(R0, Rm), FRn */
2291 uint32_t FRn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
2292 }
2293 break;
2294 case 0x7:
2295 { /* FMOV FRm, @(R0, Rn) */
2296 uint32_t Rn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2297 }
2298 break;
2299 case 0x8:
2300 { /* FMOV @Rm, FRn */
2301 uint32_t FRn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
2302 }
2303 break;
2304 case 0x9:
2305 { /* FMOV @Rm+, FRn */
2306 uint32_t FRn = ((ir>>8)&0xF); uint32_t Rm = ((ir>>4)&0xF);
2307 }
2308 break;
2309 case 0xA:
2310 { /* FMOV FRm, @Rn */
2311 uint32_t Rn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2312 }
2313 break;
2314 case 0xB:
2315 { /* FMOV FRm, @-Rn */
2316 uint32_t Rn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2317 }
2318 break;
2319 case 0xC:
2320 { /* FMOV FRm, FRn */
2321 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2322 }
2323 break;
2324 case 0xD:
2325 switch( (ir&0xF0) >> 4 ) {
2326 case 0x0:
2327 { /* FSTS FPUL, FRn */
2328 uint32_t FRn = ((ir>>8)&0xF);
2329 }
2330 break;
2331 case 0x1:
2332 { /* FLDS FRm, FPUL */
2333 uint32_t FRm = ((ir>>8)&0xF);
2334 }
2335 break;
2336 case 0x2:
2337 { /* FLOAT FPUL, FRn */
2338 uint32_t FRn = ((ir>>8)&0xF);
2339 }
2340 break;
2341 case 0x3:
2342 { /* FTRC FRm, FPUL */
2343 uint32_t FRm = ((ir>>8)&0xF);
2344 }
2345 break;
2346 case 0x4:
2347 { /* FNEG FRn */
2348 uint32_t FRn = ((ir>>8)&0xF);
2349 }
2350 break;
2351 case 0x5:
2352 { /* FABS FRn */
2353 uint32_t FRn = ((ir>>8)&0xF);
2354 load_spreg( R_ECX, R_FPSCR );
2355 load_spreg( R_EDX, REG_OFFSET(fr_bank) );
2356 TEST_imm32_r32( FPSCR_PR, R_ECX );
2357 JNE_rel8(10);
2358 push_fr(R_EDX, FRn); // 3
2359 FABS_st0(); // 2
2360 pop_fr( R_EDX, FRn); //3
2361 JMP_rel8(8); // 2
2362 push_dr(R_EDX, FRn);
2363 FABS_st0();
2364 pop_dr(R_EDX, FRn);
2365 }
2366 break;
2367 case 0x6:
2368 { /* FSQRT FRn */
2369 uint32_t FRn = ((ir>>8)&0xF);
2370 }
2371 break;
2372 case 0x7:
2373 { /* FSRRA FRn */
2374 uint32_t FRn = ((ir>>8)&0xF);
2375 }
2376 break;
2377 case 0x8:
2378 { /* FLDI0 FRn */
2379 uint32_t FRn = ((ir>>8)&0xF);
2380 }
2381 break;
2382 case 0x9:
2383 { /* FLDI1 FRn */
2384 uint32_t FRn = ((ir>>8)&0xF);
2385 }
2386 break;
2387 case 0xA:
2388 { /* FCNVSD FPUL, FRn */
2389 uint32_t FRn = ((ir>>8)&0xF);
2390 }
2391 break;
2392 case 0xB:
2393 { /* FCNVDS FRm, FPUL */
2394 uint32_t FRm = ((ir>>8)&0xF);
2395 }
2396 break;
2397 case 0xE:
2398 { /* FIPR FVm, FVn */
2399 uint32_t FVn = ((ir>>10)&0x3); uint32_t FVm = ((ir>>8)&0x3);
2400 }
2401 break;
2402 case 0xF:
2403 switch( (ir&0x100) >> 8 ) {
2404 case 0x0:
2405 { /* FSCA FPUL, FRn */
2406 uint32_t FRn = ((ir>>9)&0x7)<<1;
2407 }
2408 break;
2409 case 0x1:
2410 switch( (ir&0x200) >> 9 ) {
2411 case 0x0:
2412 { /* FTRV XMTRX, FVn */
2413 uint32_t FVn = ((ir>>10)&0x3);
2414 }
2415 break;
2416 case 0x1:
2417 switch( (ir&0xC00) >> 10 ) {
2418 case 0x0:
2419 { /* FSCHG */
2420 }
2421 break;
2422 case 0x2:
2423 { /* FRCHG */
2424 }
2425 break;
2426 case 0x3:
2427 { /* UNDEF */
2428 if( sh4_x86.in_delay_slot ) {
2429 RAISE_EXCEPTION(EXC_SLOT_ILLEGAL);
2430 } else {
2431 RAISE_EXCEPTION(EXC_ILLEGAL);
2432 }
2433 return 1;
2434 }
2435 break;
2436 default:
2437 UNDEF();
2438 break;
2439 }
2440 break;
2441 }
2442 break;
2443 }
2444 break;
2445 default:
2446 UNDEF();
2447 break;
2448 }
2449 break;
2450 case 0xE:
2451 { /* FMAC FR0, FRm, FRn */
2452 uint32_t FRn = ((ir>>8)&0xF); uint32_t FRm = ((ir>>4)&0xF);
2453 }
2454 break;
2455 default:
2456 UNDEF();
2457 break;
2458 }
2459 break;
2460 }
2462 INC_r32(R_ESI);
2463 if( sh4_x86.in_delay_slot ) {
2464 sh4_x86.in_delay_slot = FALSE;
2465 return 1;
2466 }
2467 return 0;
2468 }
.