1 /*
2 * MUL* and MULU* do not set OV correctly
3 * DIVX: the second operand should be treated as dword instead of word
4 * GETATE, GETPTE and GETRA should not be used
5 * UPDPSW: _CY and _OV must be cleared or unchanged? I suppose
6 * cleared, like TEST being done on the mask operand.
7 * MOVT: I cannot understand exactly what happens to the result
8 * when an overflow occurs
9 *
10 * Unimplemented opcodes:
11 * ROTC, UPDATE, UPDPTE
12 */
13
14 static UINT32 f12Op1, f12Op2;
15 static UINT8 f12Flag1, f12Flag2;
16
17
18 /*
19 * Macro to access data in operands decoded with ReadAMAddress()
20 */
21
22 #define F12LOADOPBYTE(num) \
23 if (f12Flag##num) \
24 appb = (UINT8)v60.reg[f12Op##num]; \
25 else \
26 appb = MemRead8(f12Op##num);
27
28 #define F12LOADOPHALF(num) \
29 if (f12Flag##num) \
30 apph = (UINT16)v60.reg[f12Op##num]; \
31 else \
32 apph = MemRead16(f12Op##num);
33
34 #define F12LOADOPWORD(num) \
35 if (f12Flag##num) \
36 appw = v60.reg[f12Op##num]; \
37 else \
38 appw = MemRead32(f12Op##num);
39
40 #define F12STOREOPBYTE(num) \
41 if (f12Flag##num) \
42 SETREG8(v60.reg[f12Op##num], appb); \
43 else \
44 MemWrite8(f12Op##num,appb);
45
46 #define F12STOREOPHALF(num) \
47 if (f12Flag##num) \
48 SETREG16(v60.reg[f12Op##num], apph); \
49 else \
50 MemWrite16(f12Op##num,apph);
51
52 #define F12STOREOPWORD(num) \
53 if (f12Flag##num) \
54 v60.reg[f12Op##num] = appw; \
55 else \
56 MemWrite32(f12Op##num,appw);
57
58 #define F12LOADOP1BYTE() F12LOADOPBYTE(1)
59 #define F12LOADOP1HALF() F12LOADOPHALF(1)
60 #define F12LOADOP1WORD() F12LOADOPWORD(1)
61
62 #define F12LOADOP2BYTE() F12LOADOPBYTE(2)
63 #define F12LOADOP2HALF() F12LOADOPHALF(2)
64 #define F12LOADOP2WORD() F12LOADOPWORD(2)
65
66 #define F12STOREOP1BYTE() F12STOREOPBYTE(1)
67 #define F12STOREOP1HALF() F12STOREOPHALF(1)
68 #define F12STOREOP1WORD() F12STOREOPWORD(1)
69
70 #define F12STOREOP2BYTE() F12STOREOPBYTE(2)
71 #define F12STOREOP2HALF() F12STOREOPHALF(2)
72 #define F12STOREOP2WORD() F12STOREOPWORD(2)
73
74
75
76 #define F12END() \
77 return amLength1 + amLength2 + 2;
78
79 static UINT8 if12;
80
81 // Decode the first operand of the instruction and prepare
82 // writing to the second operand.
F12DecodeFirstOperand(UINT32 (* DecodeOp1)(void),UINT8 dim1)83 static void F12DecodeFirstOperand(UINT32 (*DecodeOp1)(void), UINT8 dim1)
84 {
85 if12 = OpRead8(PC + 1);
86
87 // Check if F1 or F2
88 if (if12 & 0x80)
89 {
90 modDim = dim1;
91 modM = if12 & 0x40;
92 modAdd = PC + 2;
93 amLength1 = DecodeOp1();
94 f12Op1 = amOut;
95 f12Flag1 = amFlag;
96 }
97 else
98 {
99 // Check D flag
100 if (if12 & 0x20)
101 {
102 modDim = dim1;
103 modM = if12 & 0x40;
104 modAdd = PC + 2;
105 amLength1 = DecodeOp1();
106 f12Op1 = amOut;
107 f12Flag1 = amFlag;
108 }
109 else
110 {
111 if (DecodeOp1==ReadAM)
112 {
113 switch (dim1)
114 {
115 case 0:
116 f12Op1 = (UINT8)v60.reg[if12 & 0x1F];
117 break;
118 case 1:
119 f12Op1 = (UINT16)v60.reg[if12 & 0x1F];
120 break;
121 case 2:
122 f12Op1 = v60.reg[if12 & 0x1F];
123 break;
124 }
125
126 f12Flag1 = 0;
127 }
128 else
129 {
130 f12Flag1 = 1;
131 f12Op1 = if12 & 0x1F;
132 }
133
134 amLength1 = 0;
135 }
136 }
137 }
138
F12WriteSecondOperand(UINT8 dim2)139 static void F12WriteSecondOperand(UINT8 dim2)
140 {
141 modDim = dim2;
142
143 // Check if F1 or F2
144 if (if12 & 0x80)
145 {
146 modM = if12 & 0x20;
147 modAdd = PC + 2 + amLength1;
148 modDim = dim2;
149 amLength2 = WriteAM();
150 }
151 else
152 {
153 // Check D flag
154 if (if12 & 0x20)
155 {
156 switch (dim2)
157 {
158 case 0:
159 SETREG8(v60.reg[if12 & 0x1F], modWriteValB);
160 break;
161 case 1:
162 SETREG16(v60.reg[if12 & 0x1F], modWriteValH);
163 break;
164 case 2:
165 v60.reg[if12 & 0x1F] = modWriteValW;
166 break;
167 }
168
169 amLength2 = 0;
170 }
171 else
172 {
173 modM = if12 & 0x40;
174 modAdd = PC + 2;
175 modDim = dim2;
176 amLength2 = WriteAM();
177 }
178 }
179 }
180
181
182
183 // Decode both format 1/2 operands
F12DecodeOperands(UINT32 (* DecodeOp1)(void),UINT8 dim1,UINT32 (* DecodeOp2)(void),UINT8 dim2)184 static void F12DecodeOperands(UINT32 (*DecodeOp1)(void), UINT8 dim1, UINT32 (*DecodeOp2)(void), UINT8 dim2)
185 {
186 UINT8 _if12 = OpRead8(PC + 1);
187
188 // Check if F1 or F2
189 if (_if12 & 0x80)
190 {
191 modDim = dim1;
192 modM = _if12 & 0x40;
193 modAdd = PC + 2;
194 amLength1 = DecodeOp1();
195 f12Op1 = amOut;
196 f12Flag1 = amFlag;
197
198 modDim = dim2;
199 modM = _if12 & 0x20;
200 modAdd = PC + 2 + amLength1;
201 amLength2 = DecodeOp2();
202 f12Op2 = amOut;
203 f12Flag2 = amFlag;
204 }
205 else
206 {
207 // Check D flag
208 if (_if12 & 0x20)
209 {
210 if (DecodeOp2==ReadAMAddress)
211 {
212 f12Op2 = _if12 & 0x1F;
213 f12Flag2 = 1;
214 }
215 else
216 {
217 switch (dim2)
218 {
219 case 0:
220 f12Op2 = (UINT8)v60.reg[_if12 & 0x1F];
221 break;
222 case 1:
223 f12Op2 = (UINT16)v60.reg[_if12 & 0x1F];
224 break;
225 case 2:
226 f12Op2 = v60.reg[_if12 & 0x1F];
227 break;
228 }
229 }
230
231 amLength2 = 0;
232
233 modDim = dim1;
234 modM = _if12 & 0x40;
235 modAdd = PC + 2;
236 amLength1 = DecodeOp1();
237 f12Op1 = amOut;
238 f12Flag1 = amFlag;
239 }
240 else
241 {
242 if (DecodeOp1==ReadAMAddress)
243 {
244 f12Op1 = _if12 & 0x1F;
245 f12Flag1 = 1;
246 }
247 else
248 {
249 switch (dim1)
250 {
251 case 0:
252 f12Op1 = (UINT8)v60.reg[_if12 & 0x1F];
253 break;
254 case 1:
255 f12Op1 = (UINT16)v60.reg[_if12 & 0x1F];
256 break;
257 case 2:
258 f12Op1 = v60.reg[_if12 & 0x1F];
259 break;
260 }
261 }
262 amLength1 = 0;
263
264 modDim = dim2;
265 modM = _if12 & 0x40;
266 modAdd = PC + 2 + amLength1;
267 amLength2 = DecodeOp2();
268 f12Op2 = amOut;
269 f12Flag2 = amFlag;
270 }
271 }
272 }
273
opADDB(void)274 static UINT32 opADDB(void) /* TRUSTED (C too!)*/
275 {
276 UINT8 appb;
277 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
278
279 F12LOADOP2BYTE();
280
281 ADDB(appb, (UINT8)f12Op1);
282
283 F12STOREOP2BYTE();
284 F12END();
285 }
286
opADDH(void)287 static UINT32 opADDH(void) /* TRUSTED (C too!)*/
288 {
289 UINT16 apph;
290 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
291
292 F12LOADOP2HALF();
293
294 ADDW(apph, (UINT16)f12Op1);
295
296 F12STOREOP2HALF();
297 F12END();
298 }
299
opADDW(void)300 static UINT32 opADDW(void) /* TRUSTED (C too!) */
301 {
302 UINT32 appw;
303 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
304
305 F12LOADOP2WORD();
306
307 ADDL(appw, (UINT32)f12Op1);
308
309 F12STOREOP2WORD();
310 F12END();
311 }
312
opADDCB(void)313 static UINT32 opADDCB(void)
314 {
315 UINT8 appb, temp;
316
317 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
318
319 F12LOADOP2BYTE();
320
321 temp = ((UINT8)f12Op1 + (_CY?1:0));
322 ADDB(appb, temp);
323
324 F12STOREOP2BYTE();
325 F12END();
326 }
327
opADDCH(void)328 static UINT32 opADDCH(void)
329 {
330 UINT16 apph, temp;
331
332 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
333
334 F12LOADOP2HALF();
335
336 temp = ((UINT16)f12Op1 + (_CY?1:0));
337 ADDW(apph, temp);
338
339 F12STOREOP2HALF();
340 F12END();
341 }
342
opADDCW(void)343 static UINT32 opADDCW(void)
344 {
345 UINT32 appw, temp;
346
347 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
348
349 F12LOADOP2WORD();
350
351 temp = f12Op1 + (_CY?1:0);
352 ADDL(appw, temp);
353
354 F12STOREOP2WORD();
355 F12END();
356 }
357
opANDB(void)358 static UINT32 opANDB(void) /* TRUSTED */
359 {
360 UINT8 appb;
361 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
362
363 F12LOADOP2BYTE();
364
365 appb &= f12Op1;
366 _OV = 0;
367 _S = ((appb&0x80)!=0);
368 _Z = (appb==0);
369
370 F12STOREOP2BYTE();
371 F12END();
372 }
373
opANDH(void)374 static UINT32 opANDH(void) /* TRUSTED */
375 {
376 UINT16 apph;
377 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
378
379 F12LOADOP2HALF();
380
381 apph &= f12Op1;
382 _OV = 0;
383 _S = ((apph&0x8000)!=0);
384 _Z = (apph==0);
385
386 F12STOREOP2HALF();
387 F12END();
388 }
389
opANDW(void)390 static UINT32 opANDW(void) /* TRUSTED */
391 {
392 UINT32 appw;
393 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
394
395 F12LOADOP2WORD();
396
397 appw &= f12Op1;
398 _OV = 0;
399 _S = ((appw&0x80000000)!=0);
400 _Z = (appw==0);
401
402 F12STOREOP2WORD();
403 F12END();
404 }
405
opCALL(void)406 static UINT32 opCALL(void) /* TRUSTED */
407 {
408 F12DecodeOperands(ReadAMAddress,0,ReadAMAddress,2);
409
410 SP -= 4;
411 MemWrite32(SP, AP);
412 AP = f12Op2;
413
414 SP -= 4;
415 MemWrite32(SP, PC + amLength1 + amLength2 + 2);
416 PC = f12Op1;
417 ChangePC(PC);
418
419 return 0;
420 }
421
opCHKAR(void)422 static UINT32 opCHKAR(void)
423 {
424 F12DecodeOperands(ReadAM,0,ReadAM,0);
425
426 // No MMU and memory permissions yet @@@
427 _Z = 1;
428 _CY = 0;
429 _S = 0;
430
431 F12END();
432 }
433
opCHKAW(void)434 static UINT32 opCHKAW(void)
435 {
436 F12DecodeOperands(ReadAM,0,ReadAM,0);
437
438 // No MMU and memory permissions yet @@@
439 _Z = 1;
440 _CY = 0;
441 _S = 0;
442
443 F12END();
444 }
445
opCHKAE(void)446 static UINT32 opCHKAE(void)
447 {
448 F12DecodeOperands(ReadAM,0,ReadAM,0);
449
450 // No MMU and memory permissions yet @@@
451 _Z = 1;
452 _CY = 0;
453 _S = 0;
454
455 F12END();
456 }
457
opCHLVL(void)458 static UINT32 opCHLVL(void)
459 {
460 UINT32 oldPSW;
461
462 F12DecodeOperands(ReadAM,0,ReadAM,0);
463
464 if (f12Op1>3)
465 {
466 //fatalerror("Illegal data field on opCHLVL, PC=%x", PC);
467 }
468
469 oldPSW = v60_update_psw_for_exception(0, f12Op1);
470
471 SP -= 4;
472 MemWrite32(SP,f12Op2);
473
474 SP -= 4;
475 MemWrite32(SP,EXCEPTION_CODE_AND_SIZE(0x1800 + f12Op1*0x100, 8));
476
477 SP -= 4;
478 MemWrite32(SP,oldPSW);
479
480 SP -= 4;
481 MemWrite32(SP,PC + amLength1 + amLength2 + 2);
482
483 PC = GETINTVECT(24+f12Op1);
484 ChangePC(PC);
485
486 return 0;
487 }
488
opCLR1(void)489 static UINT32 opCLR1(void) /* TRUSTED */
490 {
491 UINT32 appw;
492 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
493
494 F12LOADOP2WORD();
495
496 _CY = ((appw & (1<<f12Op1))!=0);
497 _Z = !(_CY);
498
499 appw &= ~(1<<f12Op1);
500
501 F12STOREOP2WORD();
502 F12END();
503 }
504
opCMPB(void)505 static UINT32 opCMPB(void) /* TRUSTED (C too!) */
506 {
507 UINT8 appb;
508 F12DecodeOperands(ReadAM,0,ReadAM,0);
509
510 appb = (UINT8)f12Op2;
511 SUBB(appb, (UINT8)f12Op1);
512
513 F12END();
514 }
515
opCMPH(void)516 static UINT32 opCMPH(void) /* TRUSTED (C too!) */
517 {
518 UINT16 apph;
519 F12DecodeOperands(ReadAM,1,ReadAM,1);
520
521 apph = (UINT16)f12Op2;
522 SUBW(apph, (UINT16)f12Op1);
523
524 F12END();
525 }
526
527
opCMPW(void)528 static UINT32 opCMPW(void) /* TRUSTED (C too!)*/
529 {
530 F12DecodeOperands(ReadAM,2,ReadAM,2);
531
532 SUBL(f12Op2, (UINT32)f12Op1);
533
534 F12END();
535 }
536
opDIVB(void)537 static UINT32 opDIVB(void) /* TRUSTED */
538 {
539 UINT8 appb;
540 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
541
542 F12LOADOP2BYTE();
543
544 _OV = ((appb == 0x80) && (f12Op1==0xFF));
545 if (f12Op1 && !_OV)
546 appb= (INT8)appb / (INT8)f12Op1;
547 _Z = (appb == 0);
548 _S = ((appb & 0x80)!=0);
549
550 F12STOREOP2BYTE();
551 F12END();
552 }
553
opDIVH(void)554 static UINT32 opDIVH(void) /* TRUSTED */
555 {
556 UINT16 apph;
557 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
558
559 F12LOADOP2HALF();
560
561 _OV = ((apph == 0x8000) && (f12Op1==0xFFFF));
562 if (f12Op1 && !_OV)
563 apph = (INT16)apph / (INT16)f12Op1;
564 _Z = (apph == 0);
565 _S = ((apph & 0x8000)!=0);
566
567 F12STOREOP2HALF();
568 F12END();
569 }
570
opDIVW(void)571 static UINT32 opDIVW(void) /* TRUSTED */
572 {
573 UINT32 appw;
574 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
575
576 F12LOADOP2WORD();
577
578 _OV = ((appw == 0x80000000) && (f12Op1==0xFFFFFFFF));
579 if (f12Op1 && !_OV)
580 appw = (INT32)appw / (INT32)f12Op1;
581 _Z = (appw == 0);
582 _S = ((appw & 0x80000000)!=0);
583
584 F12STOREOP2WORD();
585 F12END();
586 }
587
opDIVX(void)588 static UINT32 opDIVX(void)
589 {
590 UINT32 a,b;
591 INT64 dv;
592
593 F12DecodeOperands(ReadAM,2,ReadAMAddress,3);
594
595 if (f12Flag2)
596 {
597 a=v60.reg[f12Op2&0x1F];
598 b=v60.reg[(f12Op2&0x1F)+1];
599 }
600 else
601 {
602 a=MemRead32(f12Op2);
603 b=MemRead32(f12Op2+4);
604 }
605
606 dv = ((UINT64)b<<32) | ((UINT64)a);
607
608 a = dv / (INT64)((INT32)f12Op1);
609 b = dv % (INT64)((INT32)f12Op1);
610
611 _S = ((a & 0x80000000)!=0);
612 _Z = (a == 0);
613
614 if (f12Flag2)
615 {
616 v60.reg[f12Op2&0x1F]=a;
617 v60.reg[(f12Op2&0x1F)+1]=b;
618 }
619 else
620 {
621 MemWrite32(f12Op2,a);
622 MemWrite32(f12Op2+4,b);
623 }
624
625 F12END();
626 }
627
opDIVUX(void)628 static UINT32 opDIVUX(void)
629 {
630 UINT32 a,b;
631 UINT64 dv;
632
633 F12DecodeOperands(ReadAM,2,ReadAMAddress,3);
634
635 if (f12Flag2)
636 {
637 a=v60.reg[f12Op2&0x1F];
638 b=v60.reg[(f12Op2&0x1F)+1];
639 }
640 else
641 {
642 a=MemRead32(f12Op2);
643 b=MemRead32(f12Op2+4);
644 }
645
646 dv = (UINT64)(((UINT64)b<<32) | (UINT64)a);
647 a = (UINT32)(dv / (UINT64)f12Op1);
648 b = (UINT32)(dv % (UINT64)f12Op1);
649
650 _S = ((a & 0x80000000) != 0);
651 _Z = (a == 0);
652
653 if (f12Flag2)
654 {
655 v60.reg[f12Op2&0x1F]=a;
656 v60.reg[(f12Op2&0x1F)+1]=b;
657 }
658 else
659 {
660 MemWrite32(f12Op2,a);
661 MemWrite32(f12Op2+4,b);
662 }
663
664 F12END();
665 }
666
667
opDIVUB(void)668 static UINT32 opDIVUB(void) /* TRUSTED */
669 {
670 UINT8 appb;
671 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
672
673 F12LOADOP2BYTE();
674
675 _OV = 0;
676 if (f12Op1) appb /= (UINT8)f12Op1;
677 _Z = (appb == 0);
678 _S = ((appb & 0x80)!=0);
679
680 F12STOREOP2BYTE();
681 F12END();
682 }
683
opDIVUH(void)684 static UINT32 opDIVUH(void) /* TRUSTED */
685 {
686 UINT16 apph;
687 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
688
689 F12LOADOP2HALF();
690
691 _OV = 0;
692 if (f12Op1) apph /= (UINT16)f12Op1;
693 _Z = (apph == 0);
694 _S = ((apph & 0x8000)!=0);
695
696 F12STOREOP2HALF();
697 F12END();
698 }
699
opDIVUW(void)700 static UINT32 opDIVUW(void) /* TRUSTED */
701 {
702 UINT32 appw;
703 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
704
705 F12LOADOP2WORD();
706
707 _OV = 0;
708 if (f12Op1) appw /= f12Op1;
709 _Z = (appw == 0);
710 _S = ((appw & 0x80000000)!=0);
711
712 F12STOREOP2WORD();
713 F12END();
714 }
715
opINB(void)716 static UINT32 opINB(void)
717 {
718 F12DecodeFirstOperand(ReadAMAddress,0);
719 modWriteValB=PortRead8(f12Op1);
720
721 if ( v60.stall_io )
722 {
723 v60.stall_io = 0;
724 return 0;
725 }
726
727 F12WriteSecondOperand(0);
728 F12END();
729 }
730
opINH(void)731 static UINT32 opINH(void)
732 {
733 F12DecodeFirstOperand(ReadAMAddress,1);
734 modWriteValH=PortRead16(f12Op1);
735
736 if ( v60.stall_io )
737 {
738 v60.stall_io = 0;
739 return 0;
740 }
741
742 F12WriteSecondOperand(1);
743 F12END();
744 }
745
opINW(void)746 static UINT32 opINW(void)
747 {
748 F12DecodeFirstOperand(ReadAMAddress,2);
749 modWriteValW=PortRead32(f12Op1);
750
751 if ( v60.stall_io )
752 {
753 v60.stall_io = 0;
754 return 0;
755 }
756
757 F12WriteSecondOperand(2);
758 F12END();
759 }
760
opLDPR(void)761 static UINT32 opLDPR(void)
762 {
763 F12DecodeOperands(ReadAMAddress,2,ReadAM,2);
764 if (f12Op2 <= 28)
765 {
766 if (f12Flag1 &&(!(OpRead8(PC + 1)&0x80 && OpRead8(PC + 2)==0xf4 ) ))
767 v60.reg[f12Op2 + 36] = v60.reg[f12Op1];
768 else
769 v60.reg[f12Op2 + 36] = f12Op1;
770 }
771 else
772 {
773 //fatalerror("Invalid operand on LDPR PC=%x", PC);
774 }
775 F12END();
776 }
777
opLDTASK(void)778 static UINT32 opLDTASK(void)
779 {
780 int i;
781 F12DecodeOperands(ReadAMAddress,2,ReadAM,2);
782
783 v60WritePSW(v60ReadPSW() & 0xefffffff);
784
785 TR = f12Op2;
786
787 TKCW = MemRead32(f12Op2);
788 f12Op2 += 4;
789 if(SYCW & 0x100) {
790 L0SP = MemRead32(f12Op2);
791 f12Op2 += 4;
792 }
793 if(SYCW & 0x200) {
794 L1SP = MemRead32(f12Op2);
795 f12Op2 += 4;
796 }
797 if(SYCW & 0x400) {
798 L2SP = MemRead32(f12Op2);
799 f12Op2 += 4;
800 }
801 if(SYCW & 0x800) {
802 L3SP = MemRead32(f12Op2);
803 f12Op2 += 4;
804 }
805
806 v60ReloadStack();
807
808 // 31 registers supported, _not_ 32
809 for(i=0; i<31; i++)
810 if(f12Op1 & (1<<i)) {
811 v60.reg[i] = MemRead32(f12Op2);
812 f12Op2 += 4;
813 }
814
815 // #### Ignore the virtual addressing crap.
816
817 F12END();
818 }
819
opMOVD(void)820 static UINT32 opMOVD(void) /* TRUSTED */
821 {
822 UINT32 a,b;
823
824 F12DecodeOperands(ReadAMAddress,3,ReadAMAddress,3);
825
826 if (f12Flag1)
827 {
828 a=v60.reg[f12Op1&0x1F];
829 b=v60.reg[(f12Op1&0x1F)+1];
830 }
831 else
832 {
833 a=MemRead32(f12Op1);
834 b=MemRead32(f12Op1+4);
835 }
836
837 if (f12Flag2)
838 {
839 v60.reg[f12Op2&0x1F]=a;
840 v60.reg[(f12Op2&0x1F)+1]=b;
841 }
842 else
843 {
844 MemWrite32(f12Op2,a);
845 MemWrite32(f12Op2+4,b);
846 }
847
848 F12END();
849 }
850
opMOVB(void)851 static UINT32 opMOVB(void) /* TRUSTED */
852 {
853 F12DecodeFirstOperand(ReadAM,0);
854 modWriteValB = (UINT8)f12Op1;
855 F12WriteSecondOperand(0);
856 F12END();
857 }
858
opMOVH(void)859 static UINT32 opMOVH(void) /* TRUSTED */
860 {
861 F12DecodeFirstOperand(ReadAM,1);
862 modWriteValH = (UINT16)f12Op1;
863 F12WriteSecondOperand(1);
864 F12END();
865 }
866
opMOVW(void)867 static UINT32 opMOVW(void) /* TRUSTED */
868 {
869 F12DecodeFirstOperand(ReadAM,2);
870 modWriteValW = f12Op1;
871 F12WriteSecondOperand(2);
872 F12END();
873 }
874
opMOVEAB(void)875 static UINT32 opMOVEAB(void) /* TRUSTED */
876 {
877 F12DecodeFirstOperand(ReadAMAddress,0);
878 modWriteValW = f12Op1;
879 F12WriteSecondOperand(2);
880 F12END();
881 }
882
opMOVEAH(void)883 static UINT32 opMOVEAH(void) /* TRUSTED */
884 {
885 F12DecodeFirstOperand(ReadAMAddress,1);
886 modWriteValW = f12Op1;
887 F12WriteSecondOperand(2);
888 F12END();
889 }
890
opMOVEAW(void)891 static UINT32 opMOVEAW(void) /* TRUSTED */
892 {
893 F12DecodeFirstOperand(ReadAMAddress,2);
894 modWriteValW = f12Op1;
895 F12WriteSecondOperand(2);
896 F12END();
897 }
898
opMOVSBH(void)899 static UINT32 opMOVSBH(void) /* TRUSTED */
900 {
901 F12DecodeFirstOperand(ReadAM,0);
902 modWriteValH = (INT8)(f12Op1&0xFF);
903 F12WriteSecondOperand(1);
904 F12END();
905 }
906
opMOVSBW(void)907 static UINT32 opMOVSBW(void) /* TRUSTED */
908 {
909 F12DecodeFirstOperand(ReadAM,0);
910 modWriteValW = (INT8)(f12Op1&0xFF);
911 F12WriteSecondOperand(2);
912 F12END();
913 }
914
opMOVSHW(void)915 static UINT32 opMOVSHW(void) /* TRUSTED */
916 {
917 F12DecodeFirstOperand(ReadAM,1);
918 modWriteValW = (INT16)(f12Op1&0xFFFF);
919 F12WriteSecondOperand(2);
920 F12END();
921 }
922
opMOVTHB(void)923 static UINT32 opMOVTHB(void)
924 {
925 F12DecodeFirstOperand(ReadAM,1);
926 modWriteValB = (UINT8)(f12Op1&0xFF);
927
928 // Check for overflow: the truncated bits must match the sign
929 // of the result, otherwise overflow
930 if (((modWriteValB&0x80)==0x80 && ((f12Op1&0xFF00)==0xFF00)) ||
931 ((modWriteValB&0x80)==0 && ((f12Op1&0xFF00)==0x0000)))
932 _OV = 0;
933 else
934 _OV = 1;
935
936 F12WriteSecondOperand(0);
937 F12END();
938 }
939
opMOVTWB(void)940 static UINT32 opMOVTWB(void)
941 {
942 F12DecodeFirstOperand(ReadAM,2);
943 modWriteValB = (UINT8)(f12Op1&0xFF);
944
945 // Check for overflow: the truncated bits must match the sign
946 // of the result, otherwise overflow
947 if (((modWriteValB&0x80)==0x80 && ((f12Op1&0xFFFFFF00)==0xFFFFFF00)) ||
948 ((modWriteValB&0x80)==0 && ((f12Op1&0xFFFFFF00)==0x00000000)))
949 _OV = 0;
950 else
951 _OV = 1;
952
953 F12WriteSecondOperand(0);
954 F12END();
955 }
956
opMOVTWH(void)957 static UINT32 opMOVTWH(void)
958 {
959 F12DecodeFirstOperand(ReadAM,2);
960 modWriteValH = (UINT16)(f12Op1&0xFFFF);
961
962 // Check for overflow: the truncated bits must match the sign
963 // of the result, otherwise overflow
964 if (((modWriteValH&0x8000)==0x8000 && ((f12Op1&0xFFFF0000)==0xFFFF0000)) ||
965 ((modWriteValH&0x8000)==0 && ((f12Op1&0xFFFF0000)==0x00000000)))
966 _OV = 0;
967 else
968 _OV = 1;
969
970 F12WriteSecondOperand(1);
971 F12END();
972 }
973
974
opMOVZBH(void)975 static UINT32 opMOVZBH(void) /* TRUSTED */
976 {
977 F12DecodeFirstOperand(ReadAM,0);
978 modWriteValH = (UINT16)f12Op1;
979 F12WriteSecondOperand(1);
980 F12END();
981 }
982
opMOVZBW(void)983 static UINT32 opMOVZBW(void) /* TRUSTED */
984 {
985 F12DecodeFirstOperand(ReadAM,0);
986 modWriteValW = f12Op1;
987 F12WriteSecondOperand(2);
988 F12END();
989 }
990
opMOVZHW(void)991 static UINT32 opMOVZHW(void) /* TRUSTED */
992 {
993 F12DecodeFirstOperand(ReadAM,1);
994 modWriteValW = f12Op1;
995 F12WriteSecondOperand(2);
996 F12END();
997 }
998
opMULB(void)999 static UINT32 opMULB(void)
1000 {
1001 UINT8 appb;
1002 UINT32 tmp;
1003 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1004
1005 F12LOADOP2BYTE();
1006
1007 tmp=(INT8)appb * (INT32)(INT8)f12Op1;
1008 appb = tmp;
1009 _Z = (appb == 0);
1010 _S = ((appb & 0x80)!=0);
1011 _OV = ((tmp >> 8)!=0);
1012
1013 F12STOREOP2BYTE();
1014 F12END();
1015 }
1016
opMULH(void)1017 static UINT32 opMULH(void)
1018 {
1019 UINT16 apph;
1020 UINT32 tmp;
1021 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
1022
1023 F12LOADOP2HALF();
1024
1025 tmp=(INT16)apph * (INT32)(INT16)f12Op1;
1026 apph = tmp;
1027 _Z = (apph == 0);
1028 _S = ((apph & 0x8000)!=0);
1029 _OV = ((tmp >> 16)!=0);
1030
1031 F12STOREOP2HALF();
1032 F12END();
1033 }
1034
opMULW(void)1035 static UINT32 opMULW(void)
1036 {
1037 UINT32 appw;
1038 UINT64 tmp;
1039 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1040
1041 F12LOADOP2WORD();
1042
1043 tmp=(INT32)appw * (INT64)(INT32)f12Op1;
1044 appw = tmp;
1045 _Z = (appw == 0);
1046 _S = ((appw & 0x80000000)!=0);
1047 _OV = ((tmp >> 32) != 0);
1048
1049 F12STOREOP2WORD();
1050 F12END();
1051 }
1052
opMULUB(void)1053 static UINT32 opMULUB(void)
1054 {
1055 UINT8 appb;
1056 UINT32 tmp;
1057 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1058
1059 F12LOADOP2BYTE();
1060
1061 tmp = appb * (UINT8)f12Op1;
1062 appb = tmp;
1063 _Z = (appb == 0);
1064 _S = ((appb & 0x80)!=0);
1065 _OV = ((tmp >> 8)!=0);
1066
1067 F12STOREOP2BYTE();
1068 F12END();
1069 }
1070
opMULUH(void)1071 static UINT32 opMULUH(void)
1072 {
1073 UINT16 apph;
1074 UINT32 tmp;
1075 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
1076
1077 F12LOADOP2HALF();
1078
1079 tmp=apph * (UINT16)f12Op1;
1080 apph = tmp;
1081 _Z = (apph == 0);
1082 _S = ((apph & 0x8000)!=0);
1083 _OV = ((tmp >> 16)!=0);
1084
1085 F12STOREOP2HALF();
1086 F12END();
1087 }
1088
opMULUW(void)1089 static UINT32 opMULUW(void)
1090 {
1091 UINT32 appw;
1092 UINT64 tmp;
1093 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1094
1095 F12LOADOP2WORD();
1096
1097 tmp=(UINT64)appw * (UINT64)f12Op1;
1098 appw = tmp;
1099 _Z = (appw == 0);
1100 _S = ((appw & 0x80000000)!=0);
1101 _OV = ((tmp >> 32)!=0);
1102
1103 F12STOREOP2WORD();
1104 F12END();
1105 }
1106
opNEGB(void)1107 static UINT32 opNEGB(void) /* TRUSTED (C too!)*/
1108 {
1109 F12DecodeFirstOperand(ReadAM,0);
1110
1111 modWriteValB = 0;
1112 SUBB(modWriteValB, (INT8)f12Op1);
1113 _CY = modWriteValB ? 1 : 0;
1114
1115 F12WriteSecondOperand(0);
1116 F12END();
1117 }
1118
opNEGH(void)1119 static UINT32 opNEGH(void) /* TRUSTED (C too!)*/
1120 {
1121 F12DecodeFirstOperand(ReadAM,1);
1122
1123 modWriteValH = 0;
1124 SUBW(modWriteValH, (INT16)f12Op1);
1125 _CY = modWriteValH ? 1 : 0;
1126
1127 F12WriteSecondOperand(1);
1128 F12END();
1129 }
1130
opNEGW(void)1131 static UINT32 opNEGW(void) /* TRUSTED (C too!)*/
1132 {
1133 F12DecodeFirstOperand(ReadAM,2);
1134
1135 modWriteValW = 0;
1136 SUBL(modWriteValW, (INT32)f12Op1);
1137 _CY = modWriteValW ? 1 : 0;
1138
1139 F12WriteSecondOperand(2);
1140 F12END();
1141 }
1142
opNOTB(void)1143 static UINT32 opNOTB(void) /* TRUSTED */
1144 {
1145 F12DecodeFirstOperand(ReadAM,0);
1146 modWriteValB=~f12Op1;
1147
1148 _OV=0;
1149 _S=((modWriteValB&0x80)!=0);
1150 _Z=(modWriteValB==0);
1151
1152 F12WriteSecondOperand(0);
1153 F12END();
1154 }
1155
opNOTH(void)1156 static UINT32 opNOTH(void) /* TRUSTED */
1157 {
1158 F12DecodeFirstOperand(ReadAM,1);
1159 modWriteValH=~f12Op1;
1160
1161 _OV=0;
1162 _S=((modWriteValH&0x8000)!=0);
1163 _Z=(modWriteValH==0);
1164
1165 F12WriteSecondOperand(1);
1166 F12END();
1167 }
1168
opNOTW(void)1169 static UINT32 opNOTW(void) /* TRUSTED */
1170 {
1171 F12DecodeFirstOperand(ReadAM,2);
1172 modWriteValW=~f12Op1;
1173
1174 _OV=0;
1175 _S=((modWriteValW&0x80000000)!=0);
1176 _Z=(modWriteValW==0);
1177
1178 F12WriteSecondOperand(2);
1179 F12END();
1180 }
1181
opNOT1(void)1182 static UINT32 opNOT1(void) /* TRUSTED */
1183 {
1184 UINT32 appw;
1185 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1186
1187 F12LOADOP2WORD();
1188
1189 _CY = ((appw & (1<<f12Op1))!=0);
1190 _Z = !(_CY);
1191
1192 if (_CY)
1193 appw &= ~(1<<f12Op1);
1194 else
1195 appw |= (1<<f12Op1);
1196
1197 F12STOREOP2WORD();
1198 F12END();
1199 }
1200
opORB(void)1201 static UINT32 opORB(void) /* TRUSTED (C too!)*/
1202 {
1203 UINT8 appb;
1204 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1205
1206 F12LOADOP2BYTE();
1207
1208 ORB(appb, (UINT8)f12Op1);
1209
1210 F12STOREOP2BYTE();
1211 F12END();
1212 }
1213
opORH(void)1214 static UINT32 opORH(void) /* TRUSTED (C too!)*/
1215 {
1216 UINT16 apph;
1217 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
1218
1219 F12LOADOP2HALF();
1220
1221 ORW(apph, (UINT16)f12Op1);
1222
1223 F12STOREOP2HALF();
1224 F12END();
1225 }
1226
opORW(void)1227 static UINT32 opORW(void) /* TRUSTED (C too!) */
1228 {
1229 UINT32 appw;
1230 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1231
1232 F12LOADOP2WORD();
1233
1234 ORL(appw, (UINT32)f12Op1);
1235
1236 F12STOREOP2WORD();
1237 F12END();
1238 }
1239
opOUTB(void)1240 static UINT32 opOUTB(void)
1241 {
1242 F12DecodeOperands(ReadAM,0,ReadAMAddress,2);
1243 PortWrite8(f12Op2,(UINT8)f12Op1);
1244 F12END();
1245 }
1246
opOUTH(void)1247 static UINT32 opOUTH(void)
1248 {
1249 F12DecodeOperands(ReadAM,1,ReadAMAddress,2);
1250 PortWrite16(f12Op2,(UINT16)f12Op1);
1251 F12END();
1252 }
1253
opOUTW(void)1254 static UINT32 opOUTW(void)
1255 {
1256 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1257 PortWrite32(f12Op2,f12Op1);
1258 F12END();
1259 }
1260
opREMB(void)1261 static UINT32 opREMB(void)
1262 {
1263 UINT8 appb;
1264 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1265
1266 F12LOADOP2BYTE();
1267
1268 _OV = 0;
1269 if (f12Op1)
1270 appb= (INT8)appb % (INT8)f12Op1;
1271 _Z = (appb == 0);
1272 _S = ((appb & 0x80)!=0);
1273
1274 F12STOREOP2BYTE();
1275 F12END();
1276 }
1277
opREMH(void)1278 static UINT32 opREMH(void)
1279 {
1280 UINT16 apph;
1281 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
1282
1283 F12LOADOP2HALF();
1284
1285 _OV = 0;
1286 if (f12Op1)
1287 apph=(INT16)apph % (INT16)f12Op1;
1288 _Z = (apph == 0);
1289 _S = ((apph & 0x8000)!=0);
1290
1291 F12STOREOP2HALF();
1292 F12END();
1293 }
1294
opREMW(void)1295 static UINT32 opREMW(void)
1296 {
1297 UINT32 appw;
1298 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1299
1300 F12LOADOP2WORD();
1301
1302 _OV = 0;
1303 if (f12Op1)
1304 appw=(INT32)appw % (INT32)f12Op1;
1305 _Z = (appw == 0);
1306 _S = ((appw & 0x80000000)!=0);
1307
1308 F12STOREOP2WORD();
1309 F12END();
1310 }
1311
opREMUB(void)1312 static UINT32 opREMUB(void)
1313 {
1314 UINT8 appb;
1315 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1316
1317 F12LOADOP2BYTE();
1318
1319 _OV = 0;
1320 if (f12Op1)
1321 appb %= (UINT8)f12Op1;
1322 _Z = (appb == 0);
1323 _S = ((appb & 0x80)!=0);
1324
1325 F12STOREOP2BYTE();
1326 F12END();
1327 }
1328
opREMUH(void)1329 static UINT32 opREMUH(void)
1330 {
1331 UINT16 apph;
1332 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
1333
1334 F12LOADOP2HALF();
1335
1336 _OV = 0;
1337 if (f12Op1)
1338 apph %= (UINT16)f12Op1;
1339 _Z = (apph == 0);
1340 _S = ((apph & 0x8000)!=0);
1341
1342 F12STOREOP2HALF();
1343 F12END();
1344 }
1345
opREMUW(void)1346 static UINT32 opREMUW(void)
1347 {
1348 UINT32 appw;
1349 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1350
1351 F12LOADOP2WORD();
1352
1353 _OV = 0;
1354 if (f12Op1)
1355 appw %= f12Op1;
1356 _Z = (appw == 0);
1357 _S = ((appw & 0x80000000)!=0);
1358
1359 F12STOREOP2WORD();
1360 F12END();
1361 }
1362
opROTB(void)1363 static UINT32 opROTB(void) /* TRUSTED */
1364 {
1365 UINT8 appb;
1366 INT8 i,count;
1367
1368 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1369
1370 F12LOADOP2BYTE();
1371
1372 count=(INT8)(f12Op1&0xFF);
1373 if (count>0)
1374 {
1375 for (i=0;i<count;i++)
1376 appb = (appb<<1) | ((appb&0x80) >> 7);
1377
1378 _CY=(appb&0x1)!=0;
1379 }
1380 else if (count<0)
1381 {
1382 count=-count;
1383 for (i=0;i<count;i++)
1384 appb = (appb>>1) | ((appb&0x1) << 7);
1385
1386 _CY=(appb&0x80)!=0;
1387 }
1388 else
1389 _CY=0;
1390
1391 _OV=0;
1392 _S=(appb&0x80)!=0;
1393 _Z=(appb==0);
1394
1395 F12STOREOP2BYTE();
1396 F12END();
1397 }
1398
opROTH(void)1399 static UINT32 opROTH(void) /* TRUSTED */
1400 {
1401 UINT16 apph;
1402 INT8 i,count;
1403
1404 F12DecodeOperands(ReadAM,0,ReadAMAddress,1);
1405
1406 F12LOADOP2HALF();
1407
1408 count=(INT8)(f12Op1&0xFF);
1409 if (count>0)
1410 {
1411 for (i=0;i<count;i++)
1412 apph = (apph<<1) | ((apph&0x8000) >> 15);
1413
1414 _CY=(apph&0x1)!=0;
1415 }
1416 else if (count<0)
1417 {
1418 count=-count;
1419 for (i=0;i<count;i++)
1420 apph = (apph>>1) | ((apph&0x1) << 15);
1421
1422 _CY=(apph&0x8000)!=0;
1423 }
1424 else
1425 _CY=0;
1426
1427 _OV=0;
1428 _S=(apph&0x8000)!=0;
1429 _Z=(apph==0);
1430
1431 F12STOREOP2HALF();
1432 F12END();
1433 }
1434
opROTW(void)1435 static UINT32 opROTW(void) /* TRUSTED */
1436 {
1437 UINT32 appw;
1438 INT8 i,count;
1439
1440 F12DecodeOperands(ReadAM,0,ReadAMAddress,2);
1441
1442 F12LOADOP2WORD();
1443
1444 count=(INT8)(f12Op1&0xFF);
1445 if (count>0)
1446 {
1447 for (i=0;i<count;i++)
1448 appw = (appw<<1) | ((appw&0x80000000) >> 31);
1449
1450 _CY=(appw&0x1)!=0;
1451 }
1452 else if (count<0)
1453 {
1454 count=-count;
1455 for (i=0;i<count;i++)
1456 appw = (appw>>1) | ((appw&0x1) << 31);
1457
1458 _CY=(appw&0x80000000)!=0;
1459 }
1460 else
1461 _CY=0;
1462
1463 _OV=0;
1464 _S=(appw&0x80000000)!=0;
1465 _Z=(appw==0);
1466
1467 F12STOREOP2WORD();
1468 F12END();
1469 }
1470
opROTCB(void)1471 static UINT32 opROTCB(void) /* TRUSTED */
1472 {
1473 UINT8 appb;
1474 INT8 i,cy,count;
1475
1476 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1477
1478 F12LOADOP2BYTE();
1479 NORMALIZEFLAGS();
1480
1481 count=(INT8)(f12Op1&0xFF);
1482 if (count>0)
1483 {
1484 for (i=0;i<count;i++)
1485 {
1486 cy = _CY;
1487 _CY = (UINT8)((appb & 0x80) >> 7);
1488 appb = (appb<<1) | cy;
1489 }
1490 }
1491 else if (count<0)
1492 {
1493 count=-count;
1494 for (i=0;i<count;i++)
1495 {
1496 cy = _CY;
1497 _CY = (appb & 1);
1498 appb = (appb>>1) | (cy << 7);
1499 }
1500 }
1501 else
1502 _CY = 0;
1503
1504 _OV=0;
1505 _S=(appb&0x80)!=0;
1506 _Z=(appb==0);
1507
1508 F12STOREOP2BYTE();
1509 F12END();
1510 }
1511
opROTCH(void)1512 static UINT32 opROTCH(void) /* TRUSTED */
1513 {
1514 UINT16 apph;
1515 INT8 i,cy,count;
1516
1517 F12DecodeOperands(ReadAM,0,ReadAMAddress,1);
1518
1519 F12LOADOP2HALF();
1520 NORMALIZEFLAGS();
1521
1522 count=(INT8)(f12Op1&0xFF);
1523 if (count>0)
1524 {
1525 for (i=0;i<count;i++)
1526 {
1527 cy = _CY;
1528 _CY = (UINT8)((apph & 0x8000) >> 15);
1529 apph = (apph<<1) | cy;
1530 }
1531 }
1532 else if (count<0)
1533 {
1534 count=-count;
1535 for (i=0;i<count;i++)
1536 {
1537 cy = _CY;
1538 _CY = (UINT8)(apph & 1);
1539 apph = (apph>>1) | ((UINT16)cy << 15);
1540 }
1541 }
1542 else
1543 _CY = 0;
1544
1545 _OV=0;
1546 _S=(apph&0x8000)!=0;
1547 _Z=(apph==0);
1548
1549 F12STOREOP2HALF();
1550 F12END();
1551 }
1552
opROTCW(void)1553 static UINT32 opROTCW(void) /* TRUSTED */
1554 {
1555 UINT32 appw;
1556 INT8 i,cy,count;
1557
1558 F12DecodeOperands(ReadAM,0,ReadAMAddress,2);
1559
1560 F12LOADOP2WORD();
1561 NORMALIZEFLAGS();
1562
1563 count=(INT8)(f12Op1&0xFF);
1564 if (count>0)
1565 {
1566 for (i=0;i<count;i++)
1567 {
1568 cy = _CY;
1569 _CY = (UINT8)((appw & 0x80000000) >> 31);
1570 appw = (appw<<1) | cy;
1571 }
1572 }
1573 else if (count<0)
1574 {
1575 count=-count;
1576 for (i=0;i<count;i++)
1577 {
1578 cy = _CY;
1579 _CY = (UINT8)(appw & 1);
1580 appw = (appw>>1) | ((UINT32)cy << 31);
1581 }
1582 }
1583 else
1584 _CY=0;
1585
1586 _OV=0;
1587 _S=(appw&0x80000000)!=0;
1588 _Z=(appw==0);
1589
1590 F12STOREOP2WORD();
1591 F12END();
1592 }
1593
opRVBIT(void)1594 static UINT32 opRVBIT(void)
1595 {
1596 F12DecodeFirstOperand(ReadAM,0);
1597
1598 modWriteValB =(UINT8)
1599 (((f12Op1 & (1<<0)) << 7) |
1600 ((f12Op1 & (1<<1)) << 5) |
1601 ((f12Op1 & (1<<2)) << 3) |
1602 ((f12Op1 & (1<<3)) << 1) |
1603 ((f12Op1 & (1<<4)) >> 1) |
1604 ((f12Op1 & (1<<5)) >> 3) |
1605 ((f12Op1 & (1<<6)) >> 5) |
1606 ((f12Op1 & (1<<7)) >> 7));
1607
1608 F12WriteSecondOperand(0);
1609 F12END();
1610 }
1611
opRVBYT(void)1612 static UINT32 opRVBYT(void) /* TRUSTED */
1613 {
1614 F12DecodeFirstOperand(ReadAM,2);
1615
1616 modWriteValW = ((f12Op1 & 0x000000FF) << 24) |
1617 ((f12Op1 & 0x0000FF00) << 8) |
1618 ((f12Op1 & 0x00FF0000) >> 8) |
1619 ((f12Op1 & 0xFF000000) >> 24);
1620
1621 F12WriteSecondOperand(2);
1622 F12END();
1623 }
1624
opSET1(void)1625 static UINT32 opSET1(void) /* TRUSTED */
1626 {
1627 UINT32 appw;
1628 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
1629
1630 F12LOADOP2WORD();
1631
1632 _CY = ((appw & (1<<f12Op1))!=0);
1633 _Z = !(_CY);
1634
1635 appw |= (1<<f12Op1);
1636
1637 F12STOREOP2WORD();
1638 F12END();
1639 }
1640
1641
opSETF(void)1642 static UINT32 opSETF(void)
1643 {
1644 F12DecodeFirstOperand(ReadAM,0);
1645
1646 // Normalize the flags
1647 NORMALIZEFLAGS();
1648
1649 switch (f12Op1 & 0xF)
1650 {
1651 case 0:
1652 if (!_OV) modWriteValB=0;
1653 else modWriteValB=1;
1654 break;
1655 case 1:
1656 if (_OV) modWriteValB=0;
1657 else modWriteValB=1;
1658 break;
1659 case 2:
1660 if (!_CY) modWriteValB=0;
1661 else modWriteValB=1;
1662 break;
1663 case 3:
1664 if (_CY) modWriteValB=0;
1665 else modWriteValB=1;
1666 break;
1667 case 4:
1668 if (!_Z) modWriteValB=0;
1669 else modWriteValB=1;
1670 break;
1671 case 5:
1672 if (_Z) modWriteValB=0;
1673 else modWriteValB=1;
1674 break;
1675 case 6:
1676 if (!(_CY | _Z)) modWriteValB=0;
1677 else modWriteValB=1;
1678 break;
1679 case 7:
1680 if ((_CY | _Z)) modWriteValB=0;
1681 else modWriteValB=1;
1682 break;
1683 case 8:
1684 if (!_S) modWriteValB=0;
1685 else modWriteValB=1;
1686 break;
1687 case 9:
1688 if (_S) modWriteValB=0;
1689 else modWriteValB=1;
1690 break;
1691 case 10:
1692 modWriteValB=1;
1693 break;
1694 case 11:
1695 modWriteValB=0;
1696 break;
1697 case 12:
1698 if (!(_S^_OV)) modWriteValB=0;
1699 else modWriteValB=1;
1700 break;
1701 case 13:
1702 if ((_S^_OV)) modWriteValB=0;
1703 else modWriteValB=1;
1704 break;
1705 case 14:
1706 if (!((_S^_OV)|_Z)) modWriteValB=0;
1707 else modWriteValB=1;
1708 break;
1709 case 15:
1710 if (((_S^_OV)|_Z)) modWriteValB=0;
1711 else modWriteValB=1;
1712 break;
1713 }
1714
1715 F12WriteSecondOperand(0);
1716
1717 F12END();
1718 }
1719
1720 /*
1721 #define SHIFTLEFT_OY(val, count, bitsize) \
1722 {\
1723 UINT32 tmp = ((val) >> (bitsize-1)) & 1; \
1724 tmp <<= count; \
1725 tmp -= 1; \
1726 tmp <<= (bitsize - (count)); \
1727 _OV = (((val) & tmp) != tmp); \
1728 _CY = (((val) & (1 << (count-1))) != 0); \
1729 }
1730 */
1731
1732 // During the shift, the overflow is set if the sign bit changes at any point during the shift
1733 #define SHIFTLEFT_OV(val, count, bitsize) \
1734 {\
1735 UINT32 tmp; \
1736 if (count == 32) \
1737 tmp = 0xFFFFFFFF; \
1738 else \
1739 tmp = ((1 << (count)) - 1); \
1740 tmp <<= (bitsize - (count)); \
1741 if (((val) >> (bitsize-1)) & 1) \
1742 _OV = (((val) & tmp) != tmp); \
1743 else \
1744 _OV = (((val) & tmp) != 0); \
1745 }
1746
1747 #define SHIFTLEFT_CY(val, count, bitsize) \
1748 _CY = (UINT8)(((val) >> (bitsize - count)) & 1);
1749
1750
1751
1752 #define SHIFTARITHMETICRIGHT_OV(val, count, bitsize) \
1753 _OV = 0;
1754
1755 #define SHIFTARITHMETICRIGHT_CY(val, count, bitsize) \
1756 _CY = (UINT8)(((val) >> (count-1)) & 1);
1757
1758
1759
opSHAB(void)1760 static UINT32 opSHAB(void)
1761 {
1762 UINT8 appb;
1763 INT8 count;
1764
1765 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1766
1767 F12LOADOP2BYTE();
1768
1769 count=(INT8)(f12Op1&0xFF);
1770
1771 // Special case: destination unchanged, flags set
1772 if (count == 0)
1773 {
1774 _CY = _OV = 0;
1775 SetSZPF_Byte(appb);
1776 }
1777 else if (count>0)
1778 {
1779 SHIFTLEFT_OV(appb, count, 8);
1780
1781 // @@@ Undefined what happens to CY when count >= bitsize
1782 SHIFTLEFT_CY(appb, count, 8);
1783
1784 // do the actual shift...
1785 if (count >= 8)
1786 appb = 0;
1787 else
1788 appb <<= count;
1789
1790 // and set zero and sign
1791 SetSZPF_Byte(appb);
1792 }
1793 else
1794 {
1795 count = -count;
1796
1797 SHIFTARITHMETICRIGHT_OV(appb, count, 8);
1798 SHIFTARITHMETICRIGHT_CY(appb, count, 8);
1799
1800 if (count >= 8)
1801 appb = (appb & 0x80) ? 0xFF : 0;
1802 else
1803 appb = ((INT8)appb) >> count;
1804
1805 SetSZPF_Byte(appb);
1806 }
1807
1808 // mame_printf_debug("SHAB: %x _CY: %d _Z: %d _OV: %d _S: %d\n", appb, _CY, _Z, _OV, _S);
1809
1810 F12STOREOP2BYTE();
1811 F12END();
1812 }
1813
opSHAH(void)1814 static UINT32 opSHAH(void)
1815 {
1816 UINT16 apph;
1817 INT8 count;
1818
1819 F12DecodeOperands(ReadAM,0,ReadAMAddress,1);
1820
1821 F12LOADOP2HALF();
1822
1823 count=(INT8)(f12Op1&0xFF);
1824
1825 // Special case: destination unchanged, flags set
1826 if (count == 0)
1827 {
1828 _CY = _OV = 0;
1829 SetSZPF_Word(apph);
1830 }
1831 else if (count>0)
1832 {
1833 SHIFTLEFT_OV(apph, count, 16);
1834
1835 // @@@ Undefined what happens to CY when count >= bitsize
1836 SHIFTLEFT_CY(apph, count, 16);
1837
1838 // do the actual shift...
1839 if (count >= 16)
1840 apph = 0;
1841 else
1842 apph <<= count;
1843
1844 // and set zero and sign
1845 SetSZPF_Word(apph);
1846 }
1847 else
1848 {
1849 count = -count;
1850
1851 SHIFTARITHMETICRIGHT_OV(apph, count, 16);
1852 SHIFTARITHMETICRIGHT_CY(apph, count, 16);
1853
1854 if (count >= 16)
1855 apph = (apph & 0x8000) ? 0xFFFF : 0;
1856 else
1857 apph = ((INT16)apph) >> count;
1858
1859 SetSZPF_Word(apph);
1860 }
1861
1862 // mame_printf_debug("SHAH: %x >> %d = %x _CY: %d _Z: %d _OV: %d _S: %d\n", oldval, count, apph, _CY, _Z, _OV, _S);
1863
1864 F12STOREOP2HALF();
1865 F12END();
1866 }
1867
opSHAW(void)1868 static UINT32 opSHAW(void)
1869 {
1870 UINT32 appw;
1871 INT8 count;
1872
1873 F12DecodeOperands(ReadAM,0,ReadAMAddress,2);
1874
1875 F12LOADOP2WORD();
1876
1877 count=(INT8)(f12Op1&0xFF);
1878
1879 // Special case: destination unchanged, flags set
1880 if (count == 0)
1881 {
1882 _CY = _OV = 0;
1883 SetSZPF_Long(appw);
1884 }
1885 else if (count>0)
1886 {
1887 SHIFTLEFT_OV(appw, count, 32);
1888
1889 // @@@ Undefined what happens to CY when count >= bitsize
1890 SHIFTLEFT_CY(appw, count, 32);
1891
1892 // do the actual shift...
1893 if (count >= 32)
1894 appw = 0;
1895 else
1896 appw <<= count;
1897
1898 // and set zero and sign
1899 SetSZPF_Long(appw);
1900 }
1901 else
1902 {
1903 count = -count;
1904
1905 SHIFTARITHMETICRIGHT_OV(appw, count, 32);
1906 SHIFTARITHMETICRIGHT_CY(appw, count, 32);
1907
1908 if (count >= 32)
1909 appw = (appw & 0x80000000) ? 0xFFFFFFFF : 0;
1910 else
1911 appw = ((INT32)appw) >> count;
1912
1913 SetSZPF_Long(appw);
1914 }
1915
1916 // mame_printf_debug("SHAW: %x >> %d = %x _CY: %d _Z: %d _OV: %d _S: %d\n", oldval, count, appw, _CY, _Z, _OV, _S);
1917
1918 F12STOREOP2WORD();
1919 F12END();
1920 }
1921
1922
opSHLB(void)1923 static UINT32 opSHLB(void) /* TRUSTED */
1924 {
1925 UINT8 appb;
1926 INT8 count;
1927 UINT32 tmp;
1928
1929 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
1930
1931 F12LOADOP2BYTE();
1932
1933 count=(INT8)(f12Op1&0xFF);
1934 if (count>0)
1935 {
1936 // left shift flags:
1937 // carry gets the last bit shifted out,
1938 // overflow is always CLEARed
1939
1940 _OV = 0; // default to no overflow
1941
1942 // now handle carry
1943 tmp = appb & 0xff;
1944 tmp <<= count;
1945 SetCFB(tmp); // set carry properly
1946
1947 // do the actual shift...
1948 appb <<= count;
1949
1950 // and set zero and sign
1951 SetSZPF_Byte(appb);
1952 }
1953 else
1954 {
1955 if (count == 0)
1956 {
1957 // special case: clear carry and overflow, do nothing else
1958 _CY = _OV = 0;
1959 SetSZPF_Byte(appb); // doc. is unclear if this is true...
1960 }
1961 else
1962 {
1963 // right shift flags:
1964 // carry = last bit shifted out
1965 // overflow always cleared
1966 tmp = appb & 0xff;
1967 tmp >>= ((-count)-1);
1968 _CY = (UINT8)(tmp & 0x1);
1969 _OV = 0;
1970
1971 appb >>= -count;
1972 SetSZPF_Byte(appb);
1973 }
1974 }
1975
1976 // mame_printf_debug("SHLB: %x _CY: %d _Z: %d _OV: %d _S: %d\n", appb, _CY, _Z, _OV, _S);
1977
1978 F12STOREOP2BYTE();
1979 F12END();
1980 }
1981
opSHLH(void)1982 static UINT32 opSHLH(void) /* TRUSTED */
1983 {
1984 UINT16 apph;
1985 INT8 count;
1986 UINT32 tmp;
1987
1988 F12DecodeOperands(ReadAM,0,ReadAMAddress,1);
1989
1990 F12LOADOP2HALF();
1991
1992 count=(INT8)(f12Op1&0xFF);
1993 // mame_printf_debug("apph: %x count: %d ", apph, count);
1994 if (count>0)
1995 {
1996 // left shift flags:
1997 // carry gets the last bit shifted out,
1998 // overflow is always CLEARed
1999
2000 _OV = 0;
2001
2002 // now handle carry
2003 tmp = apph & 0xffff;
2004 tmp <<= count;
2005 SetCFW(tmp); // set carry properly
2006
2007 // do the actual shift...
2008 apph <<= count;
2009
2010 // and set zero and sign
2011 SetSZPF_Word(apph);
2012 }
2013 else
2014 {
2015 if (count == 0)
2016 {
2017 // special case: clear carry and overflow, do nothing else
2018 _CY = _OV = 0;
2019 SetSZPF_Word(apph); // doc. is unclear if this is true...
2020 }
2021 else
2022 {
2023 // right shift flags:
2024 // carry = last bit shifted out
2025 // overflow always cleared
2026 tmp = apph & 0xffff;
2027 tmp >>= ((-count)-1);
2028 _CY = (UINT8)(tmp & 0x1);
2029 _OV = 0;
2030
2031 apph >>= -count;
2032 SetSZPF_Word(apph);
2033 }
2034 }
2035
2036 // mame_printf_debug("SHLH: %x _CY: %d _Z: %d _OV: %d _S: %d\n", apph, _CY, _Z, _OV, _S);
2037
2038 F12STOREOP2HALF();
2039 F12END();
2040 }
2041
opSHLW(void)2042 static UINT32 opSHLW(void) /* TRUSTED */
2043 {
2044 UINT32 appw;
2045 INT8 count;
2046 UINT64 tmp;
2047
2048 F12DecodeOperands(ReadAM,0,ReadAMAddress,2);
2049
2050 F12LOADOP2WORD();
2051
2052 count=(INT8)(f12Op1&0xFF);
2053 if (count>0)
2054 {
2055 // left shift flags:
2056 // carry gets the last bit shifted out,
2057 // overflow is always CLEARed
2058
2059 _OV = 0;
2060
2061 // now handle carry
2062 tmp = appw & 0xffffffff;
2063 tmp <<= count;
2064 SetCFL(tmp); // set carry properly
2065
2066 // do the actual shift...
2067 appw <<= count;
2068
2069 // and set zero and sign
2070 SetSZPF_Long(appw);
2071 }
2072 else
2073 {
2074 if (count == 0)
2075 {
2076 // special case: clear carry and overflow, do nothing else
2077 _CY = _OV = 0;
2078 SetSZPF_Long(appw); // doc. is unclear if this is true...
2079 }
2080 else
2081 {
2082 // right shift flags:
2083 // carry = last bit shifted out
2084 // overflow always cleared
2085 tmp = (UINT64)(appw & 0xffffffff);
2086 tmp >>= ((-count)-1);
2087 _CY = (UINT8)(tmp & 0x1);
2088 _OV = 0;
2089
2090 appw >>= -count;
2091 SetSZPF_Long(appw);
2092 }
2093 }
2094
2095 // mame_printf_debug("SHLW: %x _CY: %d _Z: %d _OV: %d _S: %d\n", appw, _CY, _Z, _OV, _S);
2096
2097 F12STOREOP2WORD();
2098 F12END();
2099 }
2100
opSTPR(void)2101 static UINT32 opSTPR(void)
2102 {
2103 F12DecodeFirstOperand(ReadAM,2);
2104 if (f12Op1 <= 28)
2105 modWriteValW = v60.reg[f12Op1 + 36];
2106 else
2107 {
2108 //fatalerror("Invalid operand on STPR PC=%x", PC);
2109 }
2110 F12WriteSecondOperand(2);
2111 F12END();
2112 }
2113
2114
opSUBB(void)2115 static UINT32 opSUBB(void) /* TRUSTED (C too!) */
2116 {
2117 UINT8 appb;
2118 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
2119
2120 F12LOADOP2BYTE();
2121
2122 SUBB(appb, (UINT8)f12Op1);
2123
2124 F12STOREOP2BYTE();
2125 F12END();
2126 }
2127
opSUBH(void)2128 static UINT32 opSUBH(void) /* TRUSTED (C too!) */
2129 {
2130 UINT16 apph;
2131 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
2132
2133 F12LOADOP2HALF();
2134
2135 SUBW(apph, (UINT16)f12Op1);
2136
2137 F12STOREOP2HALF();
2138 F12END();
2139 }
2140
opSUBW(void)2141 static UINT32 opSUBW(void) /* TRUSTED (C too!) */
2142 {
2143 UINT32 appw;
2144 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
2145
2146 F12LOADOP2WORD();
2147
2148 SUBL(appw, (UINT32)f12Op1);
2149
2150 F12STOREOP2WORD();
2151 F12END();
2152 }
2153
2154
opSUBCB(void)2155 static UINT32 opSUBCB(void)
2156 {
2157 UINT8 appb;
2158 UINT8 src;
2159 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
2160
2161 F12LOADOP2BYTE();
2162
2163 src = (UINT8)f12Op1 + (_CY?1:0);
2164 SUBB(appb, src);
2165
2166 F12STOREOP2BYTE();
2167 F12END();
2168 }
2169
opSUBCH(void)2170 static UINT32 opSUBCH(void)
2171 {
2172 UINT16 apph;
2173 UINT16 src;
2174
2175 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
2176
2177 F12LOADOP2HALF();
2178
2179 src = (UINT16)f12Op1 + (_CY?1:0);
2180 SUBW(apph, src);
2181
2182 F12STOREOP2HALF();
2183 F12END();
2184 }
2185
opSUBCW(void)2186 static UINT32 opSUBCW(void)
2187 {
2188 UINT32 appw;
2189 UINT32 src;
2190
2191 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
2192
2193 F12LOADOP2WORD();
2194
2195 src = (UINT32)f12Op1 + (_CY?1:0);
2196 SUBL(appw, src);
2197
2198 F12STOREOP2WORD();
2199 F12END();
2200 }
2201
opTEST1(void)2202 static UINT32 opTEST1(void)
2203 {
2204 F12DecodeOperands(ReadAM,2,ReadAM,2);
2205
2206 _CY = ((f12Op2 & (1<<f12Op1))!=0);
2207 _Z = !(_CY);
2208
2209 F12END();
2210 }
2211
opUPDPSWW(void)2212 static UINT32 opUPDPSWW(void)
2213 {
2214 F12DecodeOperands(ReadAM,2,ReadAM,2);
2215
2216 /* can only modify condition code and control fields */
2217 f12Op2 &= 0xFFFFFF;
2218 f12Op1 &= 0xFFFFFF;
2219 v60WritePSW((v60ReadPSW() & (~f12Op2)) | (f12Op1 & f12Op2));
2220
2221 F12END();
2222 }
2223
opUPDPSWH(void)2224 static UINT32 opUPDPSWH(void)
2225 {
2226 F12DecodeOperands(ReadAM,2,ReadAM,2);
2227
2228 /* can only modify condition code fields */
2229 f12Op2 &= 0xFFFF;
2230 f12Op1 &= 0xFFFF;
2231 v60WritePSW((v60ReadPSW() & (~f12Op2)) | (f12Op1 & f12Op2));
2232
2233 F12END();
2234 }
2235
opXCHB(void)2236 static UINT32 opXCHB(void) /* TRUSTED */
2237 {
2238 UINT8 appb, temp;
2239
2240 F12DecodeOperands(ReadAMAddress,0,ReadAMAddress,0);
2241
2242 F12LOADOP1BYTE();
2243 temp=appb;
2244 F12LOADOP2BYTE();
2245 F12STOREOP1BYTE();
2246 appb=temp;
2247 F12STOREOP2BYTE();
2248
2249 F12END()
2250 }
2251
opXCHH(void)2252 static UINT32 opXCHH(void) /* TRUSTED */
2253 {
2254 UINT16 apph, temp;
2255
2256 F12DecodeOperands(ReadAMAddress,1,ReadAMAddress,1);
2257
2258 F12LOADOP1HALF();
2259 temp=apph;
2260 F12LOADOP2HALF();
2261 F12STOREOP1HALF();
2262 apph=temp;
2263 F12STOREOP2HALF();
2264
2265 F12END()
2266 }
2267
opXCHW(void)2268 static UINT32 opXCHW(void) /* TRUSTED */
2269 {
2270 UINT32 appw, temp;
2271
2272 F12DecodeOperands(ReadAMAddress,2,ReadAMAddress,2);
2273
2274 F12LOADOP1WORD();
2275 temp=appw;
2276 F12LOADOP2WORD();
2277 F12STOREOP1WORD();
2278 appw=temp;
2279 F12STOREOP2WORD();
2280
2281 F12END()
2282 }
2283
opXORB(void)2284 static UINT32 opXORB(void) /* TRUSTED (C too!) */
2285 {
2286 UINT8 appb;
2287 F12DecodeOperands(ReadAM,0,ReadAMAddress,0);
2288
2289 F12LOADOP2BYTE();
2290
2291 XORB(appb, (UINT8)f12Op1);
2292
2293 F12STOREOP2BYTE();
2294 F12END();
2295 }
2296
opXORH(void)2297 static UINT32 opXORH(void) /* TRUSTED (C too!) */
2298 {
2299 UINT16 apph;
2300 F12DecodeOperands(ReadAM,1,ReadAMAddress,1);
2301
2302 F12LOADOP2HALF();
2303
2304 XORW(apph, (UINT16)f12Op1);
2305
2306 F12STOREOP2HALF();
2307 F12END();
2308 }
2309
opXORW(void)2310 static UINT32 opXORW(void) /* TRUSTED (C too!) */
2311 {
2312 UINT32 appw;
2313 F12DecodeOperands(ReadAM,2,ReadAMAddress,2);
2314
2315 F12LOADOP2WORD();
2316
2317 XORL(appw, (UINT32)f12Op1);
2318
2319 F12STOREOP2WORD();
2320 F12END();
2321 }
2322
opMULX(void)2323 static UINT32 opMULX(void)
2324 {
2325 INT32 a,b;
2326 INT64 res;
2327
2328 F12DecodeOperands(ReadAM,2,ReadAMAddress,3);
2329
2330 if (f12Flag2)
2331 {
2332 a=v60.reg[f12Op2&0x1F];
2333 }
2334 else
2335 {
2336 a=MemRead32(f12Op2);
2337 }
2338
2339 res = (INT64)a * (INT64)(INT32)f12Op1;
2340
2341 b = (INT32)((res >> 32)&0xffffffff);
2342 a = (INT32)(res&0xffffffff);
2343
2344 _S = ((b & 0x80000000) != 0);
2345 _Z = (a == 0 && b == 0);
2346
2347 if (f12Flag2)
2348 {
2349 v60.reg[f12Op2&0x1F]=a;
2350 v60.reg[(f12Op2&0x1F)+1]=b;
2351 }
2352 else
2353 {
2354 MemWrite32(f12Op2,a);
2355 MemWrite32(f12Op2+4,b);
2356 }
2357
2358 F12END();
2359 }
2360
opMULUX(void)2361 static UINT32 opMULUX(void)
2362 {
2363 INT32 a,b;
2364 UINT64 res;
2365
2366 F12DecodeOperands(ReadAM,2,ReadAMAddress,3);
2367
2368 if (f12Flag2)
2369 {
2370 a=v60.reg[f12Op2&0x1F];
2371 }
2372 else
2373 {
2374 a=MemRead32(f12Op2);
2375 }
2376
2377 res = (UINT64)a * (UINT64)f12Op1;
2378 b = (INT32)((res >> 32)&0xffffffff);
2379 a = (INT32)(res&0xffffffff);
2380
2381 _S = ((b & 0x80000000) != 0);
2382 _Z = (a == 0 && b == 0);
2383
2384 if (f12Flag2)
2385 {
2386 v60.reg[f12Op2&0x1F]=a;
2387 v60.reg[(f12Op2&0x1F)+1]=b;
2388 }
2389 else
2390 {
2391 MemWrite32(f12Op2,a);
2392 MemWrite32(f12Op2+4,b);
2393 }
2394
2395 F12END();
2396 }
2397