30 /* FIXME - should be including a version of syscall.h that does not
31 pollute the name space */
32 #include "../../libgloss/v850/sys/syscall.h"
34 #include "libiberty.h"
37 #if !defined(__GO32__) && !defined(_WIN32)
39 #include <sys/times.h>
43 /* start-sanitize-v850e */
44 /* This is an array of the bit positions of registers r20 .. r31 in
45 that order in a prepare/dispose instruction. */
46 int type1_regs
[12] = { 27, 26, 25, 24, 31, 30, 29, 28, 23, 22, 0, 21 };
47 /* end-sanitize-v850e */
48 /* start-sanitize-v850eq */
49 /* This is an array of the bit positions of registers r16 .. r31 in
50 that order in a push/pop instruction. */
51 int type2_regs
[16] = { 3, 2, 1, 0, 27, 26, 25, 24, 31, 30, 29, 28, 23, 22, 20, 21};
52 /* This is an array of the bit positions of registers r1 .. r15 in
53 that order in a push/pop instruction. */
54 int type3_regs
[15] = { 2, 1, 0, 27, 26, 25, 24, 31, 30, 29, 28, 23, 22, 20, 21};
55 /* end-sanitize-v850eq */
58 #ifndef SIZE_INSTRUCTION
59 #define SIZE_INSTRUCTION 18
63 #define SIZE_VALUES 11
67 unsigned32 trace_values
[3];
70 const char *trace_name
;
71 const char *trace_module
;
75 trace_input (name
, type
, size
)
81 if (!TRACE_ALU_P (STATE_CPU (simulator
, 0)))
99 trace_values
[0] = State
.regs
[OP
[0]];
100 trace_num_values
= 1;
103 /* start-sanitize-v850e */
105 /* end-sanitize-v850e */
108 trace_values
[0] = State
.regs
[OP
[1]];
109 trace_values
[1] = State
.regs
[OP
[0]];
110 trace_num_values
= 2;
115 trace_values
[0] = SEXT5 (OP
[0]);
116 trace_values
[1] = OP
[1];
117 trace_num_values
= 2;
120 case OP_IMM_REG_MOVE
:
121 trace_values
[0] = SEXT5 (OP
[0]);
122 trace_num_values
= 1;
126 trace_values
[0] = State
.pc
;
127 trace_values
[1] = SEXT9 (OP
[0]);
128 trace_values
[2] = PSW
;
129 trace_num_values
= 3;
133 trace_values
[0] = OP
[1] * size
;
134 trace_values
[1] = State
.regs
[30];
135 trace_num_values
= 2;
139 trace_values
[0] = State
.regs
[OP
[0]];
140 trace_values
[1] = OP
[1] * size
;
141 trace_values
[2] = State
.regs
[30];
142 trace_num_values
= 3;
146 trace_values
[0] = EXTEND16 (OP
[2]);
147 trace_values
[1] = State
.regs
[OP
[0]];
148 trace_num_values
= 2;
152 trace_values
[0] = State
.regs
[OP
[1]];
153 trace_values
[1] = EXTEND16 (OP
[2]);
154 trace_values
[2] = State
.regs
[OP
[0]];
155 trace_num_values
= 3;
159 trace_values
[0] = SEXT22 (OP
[0]);
160 trace_values
[1] = State
.pc
;
161 trace_num_values
= 2;
165 trace_values
[0] = EXTEND16 (OP
[0]) << size
;
166 trace_values
[1] = State
.regs
[OP
[1]];
167 trace_num_values
= 2;
170 case OP_IMM16_REG_REG
:
171 trace_values
[0] = EXTEND16 (OP
[2]) << size
;
172 trace_values
[1] = State
.regs
[OP
[1]];
173 trace_num_values
= 2;
176 case OP_UIMM_REG_REG
:
177 trace_values
[0] = (OP
[0] & 0xffff) << size
;
178 trace_values
[1] = State
.regs
[OP
[1]];
179 trace_num_values
= 2;
182 case OP_UIMM16_REG_REG
:
183 trace_values
[0] = (OP
[2]) << size
;
184 trace_values
[1] = State
.regs
[OP
[1]];
185 trace_num_values
= 2;
189 trace_num_values
= 0;
193 trace_values
[0] = PSW
;
194 trace_num_values
= 1;
198 trace_num_values
= 0;
202 trace_values
[0] = State
.regs
[OP
[0]];
203 trace_num_values
= 1;
207 trace_values
[0] = State
.sregs
[OP
[1]];
208 trace_num_values
= 1;
214 trace_result (int has_result
, unsigned32 result
)
222 /* write out the values saved during the trace_input call */
225 for (i
= 0; i
< trace_num_values
; i
++)
227 sprintf (chp
, "%*s0x%.8lx", SIZE_VALUES
- 10, "", trace_values
[i
]);
228 chp
= strchr (chp
, '\0');
232 sprintf (chp
, "%*s", SIZE_VALUES
, "");
233 chp
= strchr (chp
, '\0');
237 /* append any result to the end of the buffer */
239 sprintf (chp
, " :: 0x%.8lx", (unsigned long)result
);
241 trace_one_insn (simulator
, STATE_CPU (simulator
, 0), trace_pc
,
242 TRACE_LINENUM_P (STATE_CPU (simulator
, 0)),
243 "simops", __LINE__
, trace_module
,
244 "%-*s -%s", SIZE_INSTRUCTION
, trace_name
, buf
);
248 trace_output (result
)
249 enum op_types result
;
251 if (!TRACE_ALU_P (STATE_CPU (simulator
, 0)))
273 trace_result (1, State
.regs
[OP
[0]]);
277 case OP_REG_REG_MOVE
:
279 case OP_IMM_REG_MOVE
:
282 trace_result (1, State
.regs
[OP
[1]]);
286 case OP_UIMM_REG_REG
:
287 case OP_IMM16_REG_REG
:
288 case OP_UIMM16_REG_REG
:
289 trace_result (1, State
.regs
[OP
[1]]);
294 trace_result (1, State
.regs
[OP
[1]]);
300 trace_result (1, State
.sregs
[OP
[1]]);
307 /* Returns 1 if the specific condition is met, returns 0 otherwise. */
309 condition_met (unsigned code
)
311 unsigned int psw
= PSW
;
315 case 0x0: return ((psw
& PSW_OV
) != 0);
316 case 0x1: return ((psw
& PSW_CY
) != 0);
317 case 0x2: return ((psw
& PSW_Z
) != 0);
318 case 0x3: return ((((psw
& PSW_CY
) != 0) | ((psw
& PSW_Z
) != 0)) != 0);
319 case 0x4: return ((psw
& PSW_S
) != 0);
320 /*case 0x5: return 1;*/
321 case 0x6: return ((((psw
& PSW_S
) != 0) ^ ((psw
& PSW_OV
) != 0)) != 0);
322 case 0x7: return (((((psw
& PSW_S
) != 0) ^ ((psw
& PSW_OV
) != 0)) || ((psw
& PSW_Z
) != 0)) != 0);
323 case 0x8: return ((psw
& PSW_OV
) == 0);
324 case 0x9: return ((psw
& PSW_CY
) == 0);
325 case 0xa: return ((psw
& PSW_Z
) == 0);
326 case 0xb: return ((((psw
& PSW_CY
) != 0) | ((psw
& PSW_Z
) != 0)) == 0);
327 case 0xc: return ((psw
& PSW_S
) == 0);
328 case 0xd: return ((psw
& PSW_SAT
) != 0);
329 case 0xe: return ((((psw
& PSW_S
) != 0) ^ ((psw
& PSW_OV
) != 0)) == 0);
330 case 0xf: return (((((psw
& PSW_S
) != 0) ^ ((psw
& PSW_OV
) != 0)) || ((psw
& PSW_Z
) != 0)) == 0);
335 /* start-sanitize-v850e */
338 Add32 (unsigned long a1
, unsigned long a2
, int * carry
)
340 unsigned long result
= (a1
+ a2
);
342 * carry
= (result
< a1
);
348 Multiply64 (boolean sign
, unsigned long op0
)
359 op1
= State
.regs
[ OP
[1] ];
363 /* Compute sign of result and adjust operands if necessary. */
365 sign
= (op0
^ op1
) & 0x80000000;
367 if (((signed long) op0
) < 0)
370 if (((signed long) op1
) < 0)
374 /* We can split the 32x32 into four 16x16 operations. This ensures
375 that we do not lose precision on 32bit only hosts: */
376 lo
= ( (op0
& 0xFFFF) * (op1
& 0xFFFF));
377 mid1
= ( (op0
& 0xFFFF) * ((op1
>> 16) & 0xFFFF));
378 mid2
= (((op0
>> 16) & 0xFFFF) * (op1
& 0xFFFF));
379 hi
= (((op0
>> 16) & 0xFFFF) * ((op1
>> 16) & 0xFFFF));
381 /* We now need to add all of these results together, taking care
382 to propogate the carries from the additions: */
383 RdLo
= Add32 (lo
, (mid1
<< 16), & carry
);
385 RdLo
= Add32 (RdLo
, (mid2
<< 16), & carry
);
386 RdHi
+= (carry
+ ((mid1
>> 16) & 0xFFFF) + ((mid2
>> 16) & 0xFFFF) + hi
);
390 /* Negate result if necessary. */
394 if (RdLo
== 0xFFFFFFFF)
403 /* Don't store into register 0. */
405 State
.regs
[ OP
[1] ] = RdLo
;
407 State
.regs
[ OP
[2] >> 11 ] = RdHi
;
412 /* end-sanitize-v850e */
414 /* Read a null terminated string from memory, return in a buffer */
422 while (sim_core_read_1 (STATE_CPU (sd
, 0),
423 PC
, sim_core_read_map
, addr
+ nr
) != 0)
425 buf
= NZALLOC (char, nr
+ 1);
426 sim_read (simulator
, addr
, buf
, nr
);
430 /* Read a null terminated argument vector from memory, return in a
433 fetch_argv (sd
, addr
)
439 char **buf
= xmalloc (max_nr
* sizeof (char*));
442 unsigned32 a
= sim_core_read_4 (STATE_CPU (sd
, 0),
443 PC
, sim_core_read_map
, addr
+ nr
* 4);
445 buf
[nr
] = fetch_str (sd
, a
);
447 if (nr
== max_nr
- 1)
450 buf
= xrealloc (buf
, max_nr
* sizeof (char*));
462 trace_input ("sst.b", OP_STORE16
, 1);
464 store_mem (State
.regs
[30] + (OP
[3] & 0x7f), 1, State
.regs
[ OP
[1] ]);
466 trace_output (OP_STORE16
);
475 trace_input ("sst.h", OP_STORE16
, 2);
477 store_mem (State
.regs
[30] + ((OP
[3] & 0x7f) << 1), 2, State
.regs
[ OP
[1] ]);
479 trace_output (OP_STORE16
);
488 trace_input ("sst.w", OP_STORE16
, 4);
490 store_mem (State
.regs
[30] + ((OP
[3] & 0x7e) << 1), 4, State
.regs
[ OP
[1] ]);
492 trace_output (OP_STORE16
);
503 trace_input ("ld.b", OP_LOAD32
, 1);
505 adr
= State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2]);
507 State
.regs
[ OP
[1] ] = EXTEND8 (load_mem (adr
, 1));
509 trace_output (OP_LOAD32
);
520 trace_input ("ld.h", OP_LOAD32
, 2);
522 adr
= State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2]);
525 State
.regs
[ OP
[1] ] = EXTEND16 (load_mem (adr
, 2));
527 trace_output (OP_LOAD32
);
538 trace_input ("ld.w", OP_LOAD32
, 4);
540 adr
= State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2] & ~1);
543 State
.regs
[ OP
[1] ] = load_mem (adr
, 4);
545 trace_output (OP_LOAD32
);
554 trace_input ("st.b", OP_STORE32
, 1);
556 store_mem (State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2]), 1, State
.regs
[ OP
[1] ]);
558 trace_output (OP_STORE32
);
569 trace_input ("st.h", OP_STORE32
, 2);
571 adr
= State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2]);
574 store_mem (adr
, 2, State
.regs
[ OP
[1] ]);
576 trace_output (OP_STORE32
);
587 trace_input ("st.w", OP_STORE32
, 4);
589 adr
= State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2] & ~1);
592 store_mem (adr
, 4, State
.regs
[ OP
[1] ]);
594 trace_output (OP_STORE32
);
603 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
605 trace_input ("add", OP_REG_REG
, 0);
607 /* Compute the result. */
609 op0
= State
.regs
[ OP
[0] ];
610 op1
= State
.regs
[ OP
[1] ];
614 /* Compute the condition codes. */
616 s
= (result
& 0x80000000);
617 cy
= (result
< op0
|| result
< op1
);
618 ov
= ((op0
& 0x80000000) == (op1
& 0x80000000)
619 && (op0
& 0x80000000) != (result
& 0x80000000));
621 /* Store the result and condition codes. */
622 State
.regs
[OP
[1]] = result
;
623 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
624 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
625 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
626 trace_output (OP_REG_REG
);
631 /* add sign_extend(imm5), reg */
635 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
638 trace_input ("add", OP_IMM_REG
, 0);
640 /* Compute the result. */
641 temp
= SEXT5 (OP
[0]);
643 op1
= State
.regs
[OP
[1]];
646 /* Compute the condition codes. */
648 s
= (result
& 0x80000000);
649 cy
= (result
< op0
|| result
< op1
);
650 ov
= ((op0
& 0x80000000) == (op1
& 0x80000000)
651 && (op0
& 0x80000000) != (result
& 0x80000000));
653 /* Store the result and condition codes. */
654 State
.regs
[OP
[1]] = result
;
655 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
656 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
657 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
658 trace_output (OP_IMM_REG
);
663 /* addi sign_extend(imm16), reg, reg */
667 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
669 trace_input ("addi", OP_IMM16_REG_REG
, 0);
671 /* Compute the result. */
673 op0
= EXTEND16 (OP
[2]);
674 op1
= State
.regs
[ OP
[0] ];
677 /* Compute the condition codes. */
679 s
= (result
& 0x80000000);
680 cy
= (result
< op0
|| result
< op1
);
681 ov
= ((op0
& 0x80000000) == (op1
& 0x80000000)
682 && (op0
& 0x80000000) != (result
& 0x80000000));
684 /* Store the result and condition codes. */
685 State
.regs
[OP
[1]] = result
;
686 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
687 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
688 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
689 trace_output (OP_IMM16_REG_REG
);
698 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
700 trace_input ("sub", OP_REG_REG
, 0);
701 /* Compute the result. */
702 op0
= State
.regs
[ OP
[0] ];
703 op1
= State
.regs
[ OP
[1] ];
706 /* Compute the condition codes. */
708 s
= (result
& 0x80000000);
710 ov
= ((op1
& 0x80000000) != (op0
& 0x80000000)
711 && (op1
& 0x80000000) != (result
& 0x80000000));
713 /* Store the result and condition codes. */
714 State
.regs
[OP
[1]] = result
;
715 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
716 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
717 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
718 trace_output (OP_REG_REG
);
723 /* subr reg1, reg2 */
727 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
729 trace_input ("subr", OP_REG_REG
, 0);
730 /* Compute the result. */
731 op0
= State
.regs
[ OP
[0] ];
732 op1
= State
.regs
[ OP
[1] ];
735 /* Compute the condition codes. */
737 s
= (result
& 0x80000000);
739 ov
= ((op0
& 0x80000000) != (op1
& 0x80000000)
740 && (op0
& 0x80000000) != (result
& 0x80000000));
742 /* Store the result and condition codes. */
743 State
.regs
[OP
[1]] = result
;
744 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
745 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
746 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
747 trace_output (OP_REG_REG
);
756 trace_input ("mulh", OP_REG_REG
, 0);
758 State
.regs
[ OP
[1] ] = (EXTEND16 (State
.regs
[ OP
[1] ]) * EXTEND16 (State
.regs
[ OP
[0] ]));
760 trace_output (OP_REG_REG
);
765 /* mulh sign_extend(imm5), reg2 */
769 trace_input ("mulh", OP_IMM_REG
, 0);
771 State
.regs
[ OP
[1] ] = EXTEND16 (State
.regs
[ OP
[1] ]) * SEXT5 (OP
[0]);
773 trace_output (OP_IMM_REG
);
778 /* mulhi imm16, reg1, reg2 */
782 trace_input ("mulhi", OP_IMM16_REG_REG
, 0);
784 State
.regs
[ OP
[1] ] = EXTEND16 (State
.regs
[ OP
[0] ]) * EXTEND16 (OP
[2]);
786 trace_output (OP_IMM16_REG_REG
);
791 /* divh reg1, reg2 */
795 unsigned int op0
, op1
, result
, ov
, s
, z
;
798 trace_input ("divh", OP_REG_REG
, 0);
800 /* Compute the result. */
801 temp
= EXTEND16 (State
.regs
[ OP
[0] ]);
803 op1
= State
.regs
[OP
[1]];
805 if (op0
== 0xffffffff && op1
== 0x80000000)
821 /* Compute the condition codes. */
823 s
= (result
& 0x80000000);
825 /* Store the result and condition codes. */
826 State
.regs
[OP
[1]] = result
;
827 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
828 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
829 | (ov
? PSW_OV
: 0));
830 trace_output (OP_REG_REG
);
839 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
841 trace_input ("cmp", OP_REG_REG_CMP
, 0);
842 /* Compute the result. */
843 op0
= State
.regs
[ OP
[0] ];
844 op1
= State
.regs
[ OP
[1] ];
847 /* Compute the condition codes. */
849 s
= (result
& 0x80000000);
851 ov
= ((op1
& 0x80000000) != (op0
& 0x80000000)
852 && (op1
& 0x80000000) != (result
& 0x80000000));
854 /* Set condition codes. */
855 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
856 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
857 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
858 trace_output (OP_REG_REG_CMP
);
863 /* cmp sign_extend(imm5), reg */
867 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
;
870 /* Compute the result. */
871 trace_input ("cmp", OP_IMM_REG_CMP
, 0);
872 temp
= SEXT5 (OP
[0]);
874 op1
= State
.regs
[OP
[1]];
877 /* Compute the condition codes. */
879 s
= (result
& 0x80000000);
881 ov
= ((op1
& 0x80000000) != (op0
& 0x80000000)
882 && (op1
& 0x80000000) != (result
& 0x80000000));
884 /* Set condition codes. */
885 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
886 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
887 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0));
888 trace_output (OP_IMM_REG_CMP
);
897 trace_input ("setf", OP_EX1
, 0);
899 State
.regs
[ OP
[1] ] = condition_met (OP
[0]);
901 trace_output (OP_EX1
);
910 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
, sat
;
912 trace_input ("satadd", OP_REG_REG
, 0);
913 /* Compute the result. */
914 op0
= State
.regs
[ OP
[0] ];
915 op1
= State
.regs
[ OP
[1] ];
918 /* Compute the condition codes. */
920 s
= (result
& 0x80000000);
921 cy
= (result
< op0
|| result
< op1
);
922 ov
= ((op0
& 0x80000000) == (op1
& 0x80000000)
923 && (op0
& 0x80000000) != (result
& 0x80000000));
926 /* Store the result and condition codes. */
927 State
.regs
[OP
[1]] = result
;
928 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
929 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
930 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0)
931 | (sat
? PSW_SAT
: 0));
933 /* Handle saturated results. */
935 State
.regs
[OP
[1]] = 0x80000000;
937 State
.regs
[OP
[1]] = 0x7fffffff;
938 trace_output (OP_REG_REG
);
943 /* satadd sign_extend(imm5), reg */
947 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
, sat
;
951 trace_input ("satadd", OP_IMM_REG
, 0);
953 /* Compute the result. */
954 temp
= SEXT5 (OP
[0]);
956 op1
= State
.regs
[OP
[1]];
959 /* Compute the condition codes. */
961 s
= (result
& 0x80000000);
962 cy
= (result
< op0
|| result
< op1
);
963 ov
= ((op0
& 0x80000000) == (op1
& 0x80000000)
964 && (op0
& 0x80000000) != (result
& 0x80000000));
967 /* Store the result and condition codes. */
968 State
.regs
[OP
[1]] = result
;
969 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
970 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
971 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0)
972 | (sat
? PSW_SAT
: 0));
974 /* Handle saturated results. */
976 State
.regs
[OP
[1]] = 0x80000000;
978 State
.regs
[OP
[1]] = 0x7fffffff;
979 trace_output (OP_IMM_REG
);
984 /* satsub reg1, reg2 */
988 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
, sat
;
990 trace_input ("satsub", OP_REG_REG
, 0);
992 /* Compute the result. */
993 op0
= State
.regs
[ OP
[0] ];
994 op1
= State
.regs
[ OP
[1] ];
997 /* Compute the condition codes. */
999 s
= (result
& 0x80000000);
1001 ov
= ((op1
& 0x80000000) != (op0
& 0x80000000)
1002 && (op1
& 0x80000000) != (result
& 0x80000000));
1005 /* Store the result and condition codes. */
1006 State
.regs
[OP
[1]] = result
;
1007 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
1008 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1009 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0)
1010 | (sat
? PSW_SAT
: 0));
1012 /* Handle saturated results. */
1014 State
.regs
[OP
[1]] = 0x80000000;
1016 State
.regs
[OP
[1]] = 0x7fffffff;
1017 trace_output (OP_REG_REG
);
1021 /* satsubi sign_extend(imm16), reg */
1025 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
, sat
;
1028 trace_input ("satsubi", OP_IMM_REG
, 0);
1030 /* Compute the result. */
1031 temp
= EXTEND16 (OP
[2]);
1033 op1
= State
.regs
[ OP
[0] ];
1036 /* Compute the condition codes. */
1038 s
= (result
& 0x80000000);
1040 ov
= ((op1
& 0x80000000) != (op0
& 0x80000000)
1041 && (op1
& 0x80000000) != (result
& 0x80000000));
1044 /* Store the result and condition codes. */
1045 State
.regs
[OP
[1]] = result
;
1046 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
1047 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1048 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0)
1049 | (sat
? PSW_SAT
: 0));
1051 /* Handle saturated results. */
1053 State
.regs
[OP
[1]] = 0x80000000;
1055 State
.regs
[OP
[1]] = 0x7fffffff;
1056 trace_output (OP_IMM_REG
);
1061 /* satsubr reg,reg */
1065 unsigned int op0
, op1
, result
, z
, s
, cy
, ov
, sat
;
1067 trace_input ("satsubr", OP_REG_REG
, 0);
1069 /* Compute the result. */
1070 op0
= State
.regs
[ OP
[0] ];
1071 op1
= State
.regs
[ OP
[1] ];
1074 /* Compute the condition codes. */
1076 s
= (result
& 0x80000000);
1077 cy
= (result
< op0
);
1078 ov
= ((op1
& 0x80000000) != (op0
& 0x80000000)
1079 && (op1
& 0x80000000) != (result
& 0x80000000));
1082 /* Store the result and condition codes. */
1083 State
.regs
[OP
[1]] = result
;
1084 PSW
&= ~(PSW_Z
| PSW_S
| PSW_CY
| PSW_OV
);
1085 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1086 | (cy
? PSW_CY
: 0) | (ov
? PSW_OV
: 0)
1087 | (sat
? PSW_SAT
: 0));
1089 /* Handle saturated results. */
1091 State
.regs
[OP
[1]] = 0x80000000;
1093 State
.regs
[OP
[1]] = 0x7fffffff;
1094 trace_output (OP_REG_REG
);
1103 unsigned int op0
, op1
, result
, z
, s
;
1105 trace_input ("tst", OP_REG_REG_CMP
, 0);
1107 /* Compute the result. */
1108 op0
= State
.regs
[ OP
[0] ];
1109 op1
= State
.regs
[ OP
[1] ];
1112 /* Compute the condition codes. */
1114 s
= (result
& 0x80000000);
1116 /* Store the condition codes. */
1117 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1118 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1119 trace_output (OP_REG_REG_CMP
);
1124 /* mov sign_extend(imm5), reg */
1128 int value
= SEXT5 (OP
[0]);
1130 trace_input ("mov", OP_IMM_REG_MOVE
, 0);
1132 State
.regs
[ OP
[1] ] = value
;
1134 trace_output (OP_IMM_REG_MOVE
);
1139 /* movhi imm16, reg, reg */
1143 trace_input ("movhi", OP_UIMM16_REG_REG
, 16);
1145 State
.regs
[ OP
[1] ] = State
.regs
[ OP
[0] ] + (OP
[2] << 16);
1147 trace_output (OP_UIMM16_REG_REG
);
1152 /* sar zero_extend(imm5),reg1 */
1156 unsigned int op0
, op1
, result
, z
, s
, cy
;
1158 trace_input ("sar", OP_IMM_REG
, 0);
1160 op1
= State
.regs
[ OP
[1] ];
1161 result
= (signed)op1
>> op0
;
1163 /* Compute the condition codes. */
1165 s
= (result
& 0x80000000);
1166 cy
= (op1
& (1 << (op0
- 1)));
1168 /* Store the result and condition codes. */
1169 State
.regs
[ OP
[1] ] = result
;
1170 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
| PSW_CY
);
1171 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1172 | (cy
? PSW_CY
: 0));
1173 trace_output (OP_IMM_REG
);
1178 /* sar reg1, reg2 */
1182 unsigned int op0
, op1
, result
, z
, s
, cy
;
1184 trace_input ("sar", OP_REG_REG
, 0);
1186 op0
= State
.regs
[ OP
[0] ] & 0x1f;
1187 op1
= State
.regs
[ OP
[1] ];
1188 result
= (signed)op1
>> op0
;
1190 /* Compute the condition codes. */
1192 s
= (result
& 0x80000000);
1193 cy
= (op1
& (1 << (op0
- 1)));
1195 /* Store the result and condition codes. */
1196 State
.regs
[OP
[1]] = result
;
1197 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
| PSW_CY
);
1198 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1199 | (cy
? PSW_CY
: 0));
1200 trace_output (OP_REG_REG
);
1205 /* shl zero_extend(imm5),reg1 */
1209 unsigned int op0
, op1
, result
, z
, s
, cy
;
1211 trace_input ("shl", OP_IMM_REG
, 0);
1213 op1
= State
.regs
[ OP
[1] ];
1214 result
= op1
<< op0
;
1216 /* Compute the condition codes. */
1218 s
= (result
& 0x80000000);
1219 cy
= (op1
& (1 << (32 - op0
)));
1221 /* Store the result and condition codes. */
1222 State
.regs
[OP
[1]] = result
;
1223 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
| PSW_CY
);
1224 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1225 | (cy
? PSW_CY
: 0));
1226 trace_output (OP_IMM_REG
);
1231 /* shl reg1, reg2 */
1235 unsigned int op0
, op1
, result
, z
, s
, cy
;
1237 trace_input ("shl", OP_REG_REG
, 0);
1238 op0
= State
.regs
[ OP
[0] ] & 0x1f;
1239 op1
= State
.regs
[ OP
[1] ];
1240 result
= op1
<< op0
;
1242 /* Compute the condition codes. */
1244 s
= (result
& 0x80000000);
1245 cy
= (op1
& (1 << (32 - op0
)));
1247 /* Store the result and condition codes. */
1248 State
.regs
[OP
[1]] = result
;
1249 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
| PSW_CY
);
1250 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1251 | (cy
? PSW_CY
: 0));
1252 trace_output (OP_REG_REG
);
1257 /* shr zero_extend(imm5),reg1 */
1261 unsigned int op0
, op1
, result
, z
, s
, cy
;
1263 trace_input ("shr", OP_IMM_REG
, 0);
1265 op1
= State
.regs
[ OP
[1] ];
1266 result
= op1
>> op0
;
1268 /* Compute the condition codes. */
1270 s
= (result
& 0x80000000);
1271 cy
= (op1
& (1 << (op0
- 1)));
1273 /* Store the result and condition codes. */
1274 State
.regs
[OP
[1]] = result
;
1275 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
| PSW_CY
);
1276 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1277 | (cy
? PSW_CY
: 0));
1278 trace_output (OP_IMM_REG
);
1283 /* shr reg1, reg2 */
1287 unsigned int op0
, op1
, result
, z
, s
, cy
;
1289 trace_input ("shr", OP_REG_REG
, 0);
1290 op0
= State
.regs
[ OP
[0] ] & 0x1f;
1291 op1
= State
.regs
[ OP
[1] ];
1292 result
= op1
>> op0
;
1294 /* Compute the condition codes. */
1296 s
= (result
& 0x80000000);
1297 cy
= (op1
& (1 << (op0
- 1)));
1299 /* Store the result and condition codes. */
1300 State
.regs
[OP
[1]] = result
;
1301 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
| PSW_CY
);
1302 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0)
1303 | (cy
? PSW_CY
: 0));
1304 trace_output (OP_REG_REG
);
1313 unsigned int op0
, op1
, result
, z
, s
;
1315 trace_input ("or", OP_REG_REG
, 0);
1317 /* Compute the result. */
1318 op0
= State
.regs
[ OP
[0] ];
1319 op1
= State
.regs
[ OP
[1] ];
1322 /* Compute the condition codes. */
1324 s
= (result
& 0x80000000);
1326 /* Store the result and condition codes. */
1327 State
.regs
[OP
[1]] = result
;
1328 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1329 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1330 trace_output (OP_REG_REG
);
1335 /* ori zero_extend(imm16), reg, reg */
1339 unsigned int op0
, op1
, result
, z
, s
;
1341 trace_input ("ori", OP_UIMM16_REG_REG
, 0);
1343 op1
= State
.regs
[ OP
[0] ];
1346 /* Compute the condition codes. */
1348 s
= (result
& 0x80000000);
1350 /* Store the result and condition codes. */
1351 State
.regs
[OP
[1]] = result
;
1352 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1353 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1354 trace_output (OP_UIMM16_REG_REG
);
1363 unsigned int op0
, op1
, result
, z
, s
;
1365 trace_input ("and", OP_REG_REG
, 0);
1367 /* Compute the result. */
1368 op0
= State
.regs
[ OP
[0] ];
1369 op1
= State
.regs
[ OP
[1] ];
1372 /* Compute the condition codes. */
1374 s
= (result
& 0x80000000);
1376 /* Store the result and condition codes. */
1377 State
.regs
[OP
[1]] = result
;
1378 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1379 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1380 trace_output (OP_REG_REG
);
1385 /* andi zero_extend(imm16), reg, reg */
1389 unsigned int result
, z
;
1391 trace_input ("andi", OP_UIMM16_REG_REG
, 0);
1393 result
= OP
[2] & State
.regs
[ OP
[0] ];
1395 /* Compute the condition codes. */
1398 /* Store the result and condition codes. */
1399 State
.regs
[ OP
[1] ] = result
;
1401 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1402 PSW
|= (z
? PSW_Z
: 0);
1404 trace_output (OP_UIMM16_REG_REG
);
1413 unsigned int op0
, op1
, result
, z
, s
;
1415 trace_input ("xor", OP_REG_REG
, 0);
1417 /* Compute the result. */
1418 op0
= State
.regs
[ OP
[0] ];
1419 op1
= State
.regs
[ OP
[1] ];
1422 /* Compute the condition codes. */
1424 s
= (result
& 0x80000000);
1426 /* Store the result and condition codes. */
1427 State
.regs
[OP
[1]] = result
;
1428 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1429 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1430 trace_output (OP_REG_REG
);
1435 /* xori zero_extend(imm16), reg, reg */
1439 unsigned int op0
, op1
, result
, z
, s
;
1441 trace_input ("xori", OP_UIMM16_REG_REG
, 0);
1443 op1
= State
.regs
[ OP
[0] ];
1446 /* Compute the condition codes. */
1448 s
= (result
& 0x80000000);
1450 /* Store the result and condition codes. */
1451 State
.regs
[OP
[1]] = result
;
1452 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1453 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1454 trace_output (OP_UIMM16_REG_REG
);
1459 /* not reg1, reg2 */
1463 unsigned int op0
, result
, z
, s
;
1465 trace_input ("not", OP_REG_REG_MOVE
, 0);
1466 /* Compute the result. */
1467 op0
= State
.regs
[ OP
[0] ];
1470 /* Compute the condition codes. */
1472 s
= (result
& 0x80000000);
1474 /* Store the result and condition codes. */
1475 State
.regs
[OP
[1]] = result
;
1476 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
1477 PSW
|= ((z
? PSW_Z
: 0) | (s
? PSW_S
: 0));
1478 trace_output (OP_REG_REG_MOVE
);
1487 unsigned int op0
, op1
, op2
;
1490 trace_input ("set1", OP_BIT
, 0);
1491 op0
= State
.regs
[ OP
[0] ];
1493 temp
= EXTEND16 (OP
[2]);
1495 temp
= load_mem (op0
+ op2
, 1);
1497 if ((temp
& (1 << op1
)) == 0)
1500 store_mem (op0
+ op2
, 1, temp
);
1501 trace_output (OP_BIT
);
1510 unsigned int op0
, op1
, op2
;
1513 trace_input ("not1", OP_BIT
, 0);
1514 op0
= State
.regs
[ OP
[0] ];
1516 temp
= EXTEND16 (OP
[2]);
1518 temp
= load_mem (op0
+ op2
, 1);
1520 if ((temp
& (1 << op1
)) == 0)
1523 store_mem (op0
+ op2
, 1, temp
);
1524 trace_output (OP_BIT
);
1533 unsigned int op0
, op1
, op2
;
1536 trace_input ("clr1", OP_BIT
, 0);
1537 op0
= State
.regs
[ OP
[0] ];
1539 temp
= EXTEND16 (OP
[2]);
1541 temp
= load_mem (op0
+ op2
, 1);
1543 if ((temp
& (1 << op1
)) == 0)
1545 temp
&= ~(1 << op1
);
1546 store_mem (op0
+ op2
, 1, temp
);
1547 trace_output (OP_BIT
);
1556 unsigned int op0
, op1
, op2
;
1559 trace_input ("tst1", OP_BIT
, 0);
1560 op0
= State
.regs
[ OP
[0] ];
1562 temp
= EXTEND16 (OP
[2]);
1564 temp
= load_mem (op0
+ op2
, 1);
1566 if ((temp
& (1 << op1
)) == 0)
1568 trace_output (OP_BIT
);
1577 trace_input ("di", OP_NONE
, 0);
1579 trace_output (OP_NONE
);
1588 trace_input ("ei", OP_NONE
, 0);
1590 trace_output (OP_NONE
);
1599 trace_input ("halt", OP_NONE
, 0);
1600 /* FIXME this should put processor into a mode where NMI still handled */
1601 trace_output (OP_NONE
);
1602 sim_engine_halt (simulator
, STATE_CPU (simulator
, 0), NULL
, PC
,
1603 sim_stopped
, SIGTRAP
);
1611 trace_input ("trap", OP_TRAP
, 0);
1612 trace_output (OP_TRAP
);
1614 /* Trap 31 is used for simulating OS I/O functions */
1618 int save_errno
= errno
;
1621 /* Registers passed to trap 0 */
1623 #define FUNC State.regs[6] /* function number, return value */
1624 #define PARM1 State.regs[7] /* optional parm 1 */
1625 #define PARM2 State.regs[8] /* optional parm 2 */
1626 #define PARM3 State.regs[9] /* optional parm 3 */
1628 /* Registers set by trap 0 */
1630 #define RETVAL State.regs[10] /* return value */
1631 #define RETERR State.regs[11] /* return error code */
1633 /* Turn a pointer in a register into a pointer into real memory. */
1635 #define MEMPTR(x) (map (x))
1652 char *path
= fetch_str (simulator
, PARM1
);
1653 char **argv
= fetch_argv (simulator
, PARM2
);
1654 char **envp
= fetch_argv (simulator
, PARM3
);
1655 RETVAL
= execve (path
, argv
, envp
);
1668 char *path
= fetch_str (simulator
, PARM1
);
1669 char **argv
= fetch_argv (simulator
, PARM2
);
1670 RETVAL
= execv (path
, argv
);
1686 RETVAL
= pipe (host_fd
);
1687 SW (buf
, host_fd
[0]);
1688 buf
+= sizeof(uint16
);
1689 SW (buf
, host_fd
[1]);
1701 RETVAL
= wait (&status
);
1711 char *buf
= zalloc (PARM3
);
1712 RETVAL
= sim_io_read (simulator
, PARM1
, buf
, PARM3
);
1713 sim_write (simulator
, PARM2
, buf
, PARM3
);
1722 char *buf
= zalloc (PARM3
);
1723 sim_read (simulator
, PARM2
, buf
, PARM3
);
1725 RETVAL
= sim_io_write_stdout (simulator
, buf
, PARM3
);
1727 RETVAL
= sim_io_write (simulator
, PARM1
, buf
, PARM3
);
1735 RETVAL
= sim_io_lseek (simulator
, PARM1
, PARM2
, PARM3
);
1741 RETVAL
= sim_io_close (simulator
, PARM1
);
1748 char *buf
= fetch_str (simulator
, PARM1
);
1749 RETVAL
= sim_io_open (simulator
, buf
, PARM2
);
1757 if ((PARM1
& 0xffff0000) == 0xdead0000 && (PARM1
& 0xffff) != 0)
1758 /* get signal encoded by kill */
1759 sim_engine_halt (simulator
, STATE_CPU (simulator
, 0), NULL
, PC
,
1760 sim_signalled
, PARM1
& 0xffff);
1761 else if (PARM1
== 0xdead)
1763 sim_engine_halt (simulator
, STATE_CPU (simulator
, 0), NULL
, PC
,
1764 sim_exited
, SIGABRT
);
1766 /* PARM1 has exit status */
1767 sim_engine_halt (simulator
, STATE_CPU (simulator
, 0), NULL
, PC
,
1772 #if !defined(__GO32__) && !defined(_WIN32)
1774 case SYS_stat
: /* added at hmsi */
1775 /* stat system call */
1777 struct stat host_stat
;
1779 char *path
= fetch_str (simulator
, PARM1
);
1781 RETVAL
= stat (path
, &host_stat
);
1786 /* Just wild-assed guesses. */
1787 store_mem (buf
, 2, host_stat
.st_dev
);
1788 store_mem (buf
+ 2, 2, host_stat
.st_ino
);
1789 store_mem (buf
+ 4, 4, host_stat
.st_mode
);
1790 store_mem (buf
+ 8, 2, host_stat
.st_nlink
);
1791 store_mem (buf
+ 10, 2, host_stat
.st_uid
);
1792 store_mem (buf
+ 12, 2, host_stat
.st_gid
);
1793 store_mem (buf
+ 14, 2, host_stat
.st_rdev
);
1794 store_mem (buf
+ 16, 4, host_stat
.st_size
);
1795 store_mem (buf
+ 20, 4, host_stat
.st_atime
);
1796 store_mem (buf
+ 28, 4, host_stat
.st_mtime
);
1797 store_mem (buf
+ 36, 4, host_stat
.st_ctime
);
1807 char *path
= fetch_str (simulator
, PARM1
);
1808 RETVAL
= chown (path
, PARM2
, PARM3
);
1819 char *path
= fetch_str (simulator
, PARM1
);
1820 RETVAL
= chmod (path
, PARM2
);
1832 RETVAL
= time (&now
);
1833 store_mem (PARM1
, 4, now
);
1839 #if !defined(__GO32__) && !defined(_WIN32)
1844 RETVAL
= times (&tms
);
1845 store_mem (PARM1
, 4, tms
.tms_utime
);
1846 store_mem (PARM1
+ 4, 4, tms
.tms_stime
);
1847 store_mem (PARM1
+ 8, 4, tms
.tms_cutime
);
1848 store_mem (PARM1
+ 12, 4, tms
.tms_cstime
);
1854 #ifdef SYS_gettimeofday
1855 #if !defined(__GO32__) && !defined(_WIN32)
1856 case SYS_gettimeofday
:
1860 RETVAL
= gettimeofday (&t
, &tz
);
1861 store_mem (PARM1
, 4, t
.tv_sec
);
1862 store_mem (PARM1
+ 4, 4, t
.tv_usec
);
1863 store_mem (PARM2
, 4, tz
.tz_minuteswest
);
1864 store_mem (PARM2
+ 4, 4, tz
.tz_dsttime
);
1874 /* Cast the second argument to void *, to avoid type mismatch
1875 if a prototype is present. */
1876 sim_io_error (simulator
, "Utime not supported");
1877 /* RETVAL = utime (path, (void *) MEMPTR (PARM2)); */
1892 { /* Trap 0 -> 30 */
1897 ECR
|= 0x40 + OP
[0];
1898 /* Flag that we are now doing exception processing. */
1899 PSW
|= PSW_EP
| PSW_ID
;
1900 PC
= ((OP
[0] < 0x10) ? 0x40 : 0x50) - 4;
1906 /* start-sanitize-v850e */
1907 /* tst1 reg2, [reg1] */
1913 trace_input ("tst1", OP_BIT
, 1);
1915 temp
= load_mem (State
.regs
[ OP
[0] ], 1);
1918 if ((temp
& (1 << State
.regs
[ OP
[1] & 0x7 ])) == 0)
1921 trace_output (OP_BIT
);
1926 /* end-sanitize-v850e */
1927 /* start-sanitize-v850e */
1928 /* mulu reg1, reg2, reg3 */
1932 trace_input ("mulu", OP_REG_REG_REG
, 0);
1934 Multiply64 (false, State
.regs
[ OP
[0] ]);
1936 trace_output (OP_REG_REG_REG
);
1941 /* end-sanitize-v850e */
1942 /* start-sanitize-v850e */
1944 #define BIT_CHANGE_OP( name, binop ) \
1946 unsigned int temp; \
1948 trace_input (name, OP_BIT_CHANGE, 0); \
1950 bit = 1 << State.regs[ OP[1] & 0x7 ]; \
1951 temp = load_mem (State.regs[ OP[0] ], 1); \
1954 if ((temp & bit) == 0) \
1958 store_mem (State.regs[ OP[0] ], 1, temp); \
1960 trace_output (OP_BIT_CHANGE); \
1964 /* clr1 reg2, [reg1] */
1968 BIT_CHANGE_OP ("clr1", &= ~ );
1971 /* not1 reg2, [reg1] */
1975 BIT_CHANGE_OP ("not1", ^= );
1982 BIT_CHANGE_OP ("set1", |= );
1989 trace_input ("sasf", OP_EX1
, 0);
1991 State
.regs
[ OP
[1] ] = (State
.regs
[ OP
[1] ] << 1) | condition_met (OP
[0]);
1993 trace_output (OP_EX1
);
1997 /* end-sanitize-v850e */
1998 /* start-sanitize-v850eq */
1999 /* This function is courtesy of Sugimoto at NEC, via Seow Tan (Soew_Tan@el.nec.com) */
2004 unsigned long int als
,
2005 unsigned long int sfi
,
2006 unsigned long int * quotient_ptr
,
2007 unsigned long int * remainder_ptr
,
2008 boolean
* overflow_ptr
2011 unsigned long ald
= sfi
>> (N
- 1);
2012 unsigned long alo
= als
;
2017 unsigned int R1
= 1;
2018 unsigned int DBZ
= (als
== 0) ? 1 : 0;
2019 unsigned long alt
= Q
? ~als
: als
;
2022 alo
= ald
+ alt
+ Q
;
2023 C
= (((alt
>> 31) & (ald
>> 31))
2024 | (((alt
>> 31) ^ (ald
>> 31)) & (~alo
>> 31)));
2027 R1
= (alo
== 0) ? 0 : (R1
& Q
);
2028 if ((S
^ (alo
>>31)) && !C
)
2033 sfi
= (sfi
<< (32-N
+1)) | Q
;
2034 ald
= (alo
<< 1) | (sfi
>> 31);
2036 /* 2nd - N-1th Loop */
2037 for (i
= 2; i
< N
; i
++)
2039 alt
= Q
? ~als
: als
;
2040 alo
= ald
+ alt
+ Q
;
2041 C
= (((alt
>> 31) & (ald
>> 31))
2042 | (((alt
>> 31) ^ (ald
>> 31)) & (~alo
>> 31)));
2045 R1
= (alo
== 0) ? 0 : (R1
& Q
);
2046 if ((S
^ (alo
>>31)) && !C
&& !DBZ
)
2051 sfi
= (sfi
<< 1) | Q
;
2052 ald
= (alo
<< 1) | (sfi
>> 31);
2056 alt
= Q
? ~als
: als
;
2057 alo
= ald
+ alt
+ Q
;
2058 C
= (((alt
>> 31) & (ald
>> 31))
2059 | (((alt
>> 31) ^ (ald
>> 31)) & (~alo
>> 31)));
2062 R1
= (alo
== 0) ? 0 : (R1
& Q
);
2063 if ((S
^ (alo
>>31)) && !C
)
2068 * quotient_ptr
= (sfi
<< 1) | Q
;
2069 * remainder_ptr
= Q
? alo
: (alo
+ als
);
2070 * overflow_ptr
= DBZ
| R1
;
2073 /* This function is courtesy of Sugimoto at NEC, via Seow Tan (Soew_Tan@el.nec.com) */
2078 unsigned long int als
,
2079 unsigned long int sfi
,
2080 signed long int * quotient_ptr
,
2081 signed long int * remainder_ptr
,
2082 boolean
* overflow_ptr
2085 unsigned long ald
= (signed long) sfi
>> (N
- 1);
2086 unsigned long alo
= als
;
2087 unsigned int SS
= als
>> 31;
2088 unsigned int SD
= sfi
>> 31;
2089 unsigned int R1
= 1;
2091 unsigned int DBZ
= als
== 0 ? 1 : 0;
2092 unsigned int Q
= ~(SS
^ SD
) & 1;
2096 unsigned long alt
= Q
? ~als
: als
;
2101 alo
= ald
+ alt
+ Q
;
2102 C
= (((alt
>> 31) & (ald
>> 31))
2103 | (((alt
>> 31) ^ (ald
>> 31)) & (~alo
>> 31)));
2105 R1
= (alo
== 0) ? 0 : (R1
& (Q
^ (SS
^ SD
)));
2107 sfi
= (sfi
<< (32-N
+1)) | Q
;
2108 ald
= (alo
<< 1) | (sfi
>> 31);
2109 if ((alo
>> 31) ^ (ald
>> 31))
2114 /* 2nd - N-1th Loop */
2116 for (i
= 2; i
< N
; i
++)
2118 alt
= Q
? ~als
: als
;
2119 alo
= ald
+ alt
+ Q
;
2120 C
= (((alt
>> 31) & (ald
>> 31))
2121 | (((alt
>> 31) ^ (ald
>> 31)) & (~alo
>> 31)));
2123 R1
= (alo
== 0) ? 0 : (R1
& (Q
^ (SS
^ SD
)));
2125 sfi
= (sfi
<< 1) | Q
;
2126 ald
= (alo
<< 1) | (sfi
>> 31);
2127 if ((alo
>> 31) ^ (ald
>> 31))
2134 alt
= Q
? ~als
: als
;
2135 alo
= ald
+ alt
+ Q
;
2136 C
= (((alt
>> 31) & (ald
>> 31))
2137 | (((alt
>> 31) ^ (ald
>> 31)) & (~alo
>> 31)));
2139 R1
= (alo
== 0) ? 0 : (R1
& (Q
^ (SS
^ SD
)));
2140 sfi
= (sfi
<< (32-N
+1));
2146 alt
= Q
? ~als
: als
;
2147 alo
= ald
+ alt
+ Q
;
2149 R1
= R1
& ((~alo
>> 31) ^ SD
);
2150 if ((alo
!= 0) && ((Q
^ (SS
^ SD
)) ^ R1
)) alo
= ald
;
2152 ald
= sfi
= (long) ((sfi
>> 1) | (SS
^ SD
) << 31) >> (32-N
-1) | Q
;
2154 ald
= sfi
= sfi
| Q
;
2156 OV
= DBZ
| ((alo
== 0) ? 0 : R1
);
2158 * remainder_ptr
= alo
;
2161 if (((alo
!= 0) && ((SS
^ SD
) ^ R1
))
2162 || ((alo
== 0) && (SS
^ R1
)))
2167 OV
= (DBZ
| R1
) ? OV
: ((alo
>> 31) & (~ald
>> 31));
2169 * quotient_ptr
= alo
;
2170 * overflow_ptr
= OV
;
2173 /* sdivun imm5, reg1, reg2, reg3 */
2177 unsigned long int quotient
;
2178 unsigned long int remainder
;
2179 unsigned long int divide_by
;
2180 unsigned long int divide_this
;
2181 boolean overflow
= false;
2184 trace_input ("sdivun", OP_IMM_REG_REG_REG
, 0);
2186 imm5
= 32 - ((OP
[3] & 0x3c0000) >> 17);
2188 divide_by
= State
.regs
[ OP
[0] ];
2189 divide_this
= State
.regs
[ OP
[1] ] << imm5
;
2191 divun (imm5
, divide_by
, divide_this
, & quotient
, & remainder
, & overflow
);
2193 State
.regs
[ OP
[1] ] = quotient
;
2194 State
.regs
[ OP
[2] >> 11 ] = remainder
;
2196 /* Set condition codes. */
2197 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2199 if (overflow
) PSW
|= PSW_OV
;
2200 if (quotient
== 0) PSW
|= PSW_Z
;
2201 if (quotient
& 0x80000000) PSW
|= PSW_S
;
2203 trace_output (OP_IMM_REG_REG_REG
);
2208 /* sdivn imm5, reg1, reg2, reg3 */
2212 signed long int quotient
;
2213 signed long int remainder
;
2214 signed long int divide_by
;
2215 signed long int divide_this
;
2216 boolean overflow
= false;
2219 trace_input ("sdivn", OP_IMM_REG_REG_REG
, 0);
2221 imm5
= 32 - ((OP
[3] & 0x3c0000) >> 17);
2223 divide_by
= State
.regs
[ OP
[0] ];
2224 divide_this
= State
.regs
[ OP
[1] ] << imm5
;
2226 divn (imm5
, divide_by
, divide_this
, & quotient
, & remainder
, & overflow
);
2228 State
.regs
[ OP
[1] ] = quotient
;
2229 State
.regs
[ OP
[2] >> 11 ] = remainder
;
2231 /* Set condition codes. */
2232 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2234 if (overflow
) PSW
|= PSW_OV
;
2235 if (quotient
== 0) PSW
|= PSW_Z
;
2236 if (quotient
< 0) PSW
|= PSW_S
;
2238 trace_output (OP_IMM_REG_REG_REG
);
2243 /* sdivhun imm5, reg1, reg2, reg3 */
2247 unsigned long int quotient
;
2248 unsigned long int remainder
;
2249 unsigned long int divide_by
;
2250 unsigned long int divide_this
;
2251 boolean overflow
= false;
2254 trace_input ("sdivhun", OP_IMM_REG_REG_REG
, 0);
2256 imm5
= 32 - ((OP
[3] & 0x3c0000) >> 17);
2258 divide_by
= State
.regs
[ OP
[0] ] & 0xffff;
2259 divide_this
= State
.regs
[ OP
[1] ] << imm5
;
2261 divun (imm5
, divide_by
, divide_this
, & quotient
, & remainder
, & overflow
);
2263 State
.regs
[ OP
[1] ] = quotient
;
2264 State
.regs
[ OP
[2] >> 11 ] = remainder
;
2266 /* Set condition codes. */
2267 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2269 if (overflow
) PSW
|= PSW_OV
;
2270 if (quotient
== 0) PSW
|= PSW_Z
;
2271 if (quotient
& 0x80000000) PSW
|= PSW_S
;
2273 trace_output (OP_IMM_REG_REG_REG
);
2278 /* sdivhn imm5, reg1, reg2, reg3 */
2282 signed long int quotient
;
2283 signed long int remainder
;
2284 signed long int divide_by
;
2285 signed long int divide_this
;
2286 boolean overflow
= false;
2289 trace_input ("sdivhn", OP_IMM_REG_REG_REG
, 0);
2291 imm5
= 32 - ((OP
[3] & 0x3c0000) >> 17);
2293 divide_by
= EXTEND16 (State
.regs
[ OP
[0] ]);
2294 divide_this
= State
.regs
[ OP
[1] ] << imm5
;
2296 divn (imm5
, divide_by
, divide_this
, & quotient
, & remainder
, & overflow
);
2298 State
.regs
[ OP
[1] ] = quotient
;
2299 State
.regs
[ OP
[2] >> 11 ] = remainder
;
2301 /* Set condition codes. */
2302 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2304 if (overflow
) PSW
|= PSW_OV
;
2305 if (quotient
== 0) PSW
|= PSW_Z
;
2306 if (quotient
< 0) PSW
|= PSW_S
;
2308 trace_output (OP_IMM_REG_REG_REG
);
2313 /* end-sanitize-v850eq */
2314 /* start-sanitize-v850e */
2315 /* divu reg1, reg2, reg3 */
2319 unsigned long int quotient
;
2320 unsigned long int remainder
;
2321 unsigned long int divide_by
;
2322 unsigned long int divide_this
;
2323 boolean overflow
= false;
2325 trace_input ("divu", OP_REG_REG_REG
, 0);
2327 /* Compute the result. */
2329 divide_by
= State
.regs
[ OP
[0] ];
2330 divide_this
= State
.regs
[ OP
[1] ];
2338 State
.regs
[ OP
[1] ] = quotient
= divide_this
/ divide_by
;
2339 State
.regs
[ OP
[2] >> 11 ] = remainder
= divide_this
% divide_by
;
2341 /* Set condition codes. */
2342 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2344 if (overflow
) PSW
|= PSW_OV
;
2345 if (quotient
== 0) PSW
|= PSW_Z
;
2346 if (quotient
& 0x80000000) PSW
|= PSW_S
;
2348 trace_output (OP_REG_REG_REG
);
2353 /* end-sanitize-v850e */
2354 /* start-sanitize-v850e */
2355 /* div reg1, reg2, reg3 */
2359 signed long int quotient
;
2360 signed long int remainder
;
2361 signed long int divide_by
;
2362 signed long int divide_this
;
2363 boolean overflow
= false;
2365 trace_input ("div", OP_REG_REG_REG
, 0);
2367 /* Compute the result. */
2369 divide_by
= State
.regs
[ OP
[0] ];
2370 divide_this
= State
.regs
[ OP
[1] ];
2372 if (divide_by
== 0 || (divide_by
== -1 && divide_this
== (1 << 31)))
2378 State
.regs
[ OP
[1] ] = quotient
= divide_this
/ divide_by
;
2379 State
.regs
[ OP
[2] >> 11 ] = remainder
= divide_this
% divide_by
;
2381 /* Set condition codes. */
2382 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2384 if (overflow
) PSW
|= PSW_OV
;
2385 if (quotient
== 0) PSW
|= PSW_Z
;
2386 if (quotient
< 0) PSW
|= PSW_S
;
2388 trace_output (OP_REG_REG_REG
);
2393 /* end-sanitize-v850e */
2394 /* start-sanitize-v850e */
2395 /* divhu reg1, reg2, reg3 */
2399 unsigned long int quotient
;
2400 unsigned long int remainder
;
2401 unsigned long int divide_by
;
2402 unsigned long int divide_this
;
2403 boolean overflow
= false;
2405 trace_input ("divhu", OP_REG_REG_REG
, 0);
2407 /* Compute the result. */
2409 divide_by
= State
.regs
[ OP
[0] ] & 0xffff;
2410 divide_this
= State
.regs
[ OP
[1] ];
2418 State
.regs
[ OP
[1] ] = quotient
= divide_this
/ divide_by
;
2419 State
.regs
[ OP
[2] >> 11 ] = remainder
= divide_this
% divide_by
;
2421 /* Set condition codes. */
2422 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2424 if (overflow
) PSW
|= PSW_OV
;
2425 if (quotient
== 0) PSW
|= PSW_Z
;
2426 if (quotient
& 0x80000000) PSW
|= PSW_S
;
2428 trace_output (OP_REG_REG_REG
);
2433 /* end-sanitize-v850e */
2434 /* start-sanitize-v850e */
2435 /* divh reg1, reg2, reg3 */
2439 signed long int quotient
;
2440 signed long int remainder
;
2441 signed long int divide_by
;
2442 signed long int divide_this
;
2443 boolean overflow
= false;
2445 trace_input ("divh", OP_REG_REG_REG
, 0);
2447 /* Compute the result. */
2449 divide_by
= State
.regs
[ OP
[0] ];
2450 divide_this
= EXTEND16 (State
.regs
[ OP
[1] ]);
2452 if (divide_by
== 0 || (divide_by
== -1 && divide_this
== (1 << 31)))
2458 State
.regs
[ OP
[1] ] = quotient
= divide_this
/ divide_by
;
2459 State
.regs
[ OP
[2] >> 11 ] = remainder
= divide_this
% divide_by
;
2461 /* Set condition codes. */
2462 PSW
&= ~(PSW_Z
| PSW_S
| PSW_OV
);
2464 if (overflow
) PSW
|= PSW_OV
;
2465 if (quotient
== 0) PSW
|= PSW_Z
;
2466 if (quotient
< 0) PSW
|= PSW_S
;
2468 trace_output (OP_REG_REG_REG
);
2473 /* end-sanitize-v850e */
2474 /* start-sanitize-v850e */
2475 /* mulu imm9, reg2, reg3 */
2479 trace_input ("mulu", OP_IMM_REG_REG
, 0);
2481 Multiply64 (false, (OP
[3] & 0x1f) | ((OP
[3] >> 13) & 0x1e0));
2483 trace_output (OP_IMM_REG_REG
);
2488 /* end-sanitize-v850e */
2489 /* start-sanitize-v850e */
2490 /* mul imm9, reg2, reg3 */
2494 trace_input ("mul", OP_IMM_REG_REG
, 0);
2496 Multiply64 (true, (OP
[3] & 0x1f) | ((OP
[3] >> 13) & 0x1e0));
2498 trace_output (OP_IMM_REG_REG
);
2503 /* end-sanitize-v850e */
2504 /* start-sanitize-v850e */
2511 trace_input ("ld.hu", OP_LOAD32
, 2);
2513 adr
= State
.regs
[ OP
[0] ] + EXTEND16 (OP
[2] & ~1);
2516 State
.regs
[ OP
[1] ] = load_mem (adr
, 2);
2518 trace_output (OP_LOAD32
);
2523 /* end-sanitize-v850e */
2524 /* start-sanitize-v850e */
2531 trace_input ("ld.bu", OP_LOAD32
, 1);
2533 adr
= (State
.regs
[ OP
[0] ]
2534 + (EXTEND16 (OP
[2] & ~1) | ((OP
[3] >> 5) & 1)));
2536 State
.regs
[ OP
[1] ] = load_mem (adr
, 1);
2538 trace_output (OP_LOAD32
);
2543 /* prepare list12, imm5, imm32 */
2549 trace_input ("prepare", OP_PUSHPOP1
, 0);
2551 /* Store the registers with lower number registers being placed at higher addresses. */
2552 for (i
= 0; i
< 12; i
++)
2553 if ((OP
[3] & (1 << type1_regs
[ i
])))
2556 store_mem (SP
, 4, State
.regs
[ 20 + i
]);
2559 SP
-= (OP
[3] & 0x3e) << 1;
2561 EP
= load_mem (PC
+ 4, 4);
2563 trace_output (OP_PUSHPOP1
);
2568 /* prepare list12, imm5, imm16-32 */
2574 trace_input ("prepare", OP_PUSHPOP1
, 0);
2576 /* Store the registers with lower number registers being placed at higher addresses. */
2577 for (i
= 0; i
< 12; i
++)
2578 if ((OP
[3] & (1 << type1_regs
[ i
])))
2581 store_mem (SP
, 4, State
.regs
[ 20 + i
]);
2584 SP
-= (OP
[3] & 0x3e) << 1;
2586 EP
= load_mem (PC
+ 4, 2) << 16;
2588 trace_output (OP_PUSHPOP1
);
2593 /* prepare list12, imm5, imm16 */
2599 trace_input ("prepare", OP_PUSHPOP1
, 0);
2601 /* Store the registers with lower number registers being placed at higher addresses. */
2602 for (i
= 0; i
< 12; i
++)
2603 if ((OP
[3] & (1 << type1_regs
[ i
])))
2606 store_mem (SP
, 4, State
.regs
[ 20 + i
]);
2609 SP
-= (OP
[3] & 0x3e) << 1;
2611 EP
= EXTEND16 (load_mem (PC
+ 4, 2));
2613 trace_output (OP_PUSHPOP1
);
2618 /* prepare list12, imm5, sp */
2624 trace_input ("prepare", OP_PUSHPOP1
, 0);
2626 /* Store the registers with lower number registers being placed at higher addresses. */
2627 for (i
= 0; i
< 12; i
++)
2628 if ((OP
[3] & (1 << type1_regs
[ i
])))
2631 store_mem (SP
, 4, State
.regs
[ 20 + i
]);
2634 SP
-= (OP
[3] & 0x3e) << 1;
2638 trace_output (OP_PUSHPOP1
);
2643 /* end-sanitize-v850e */
2644 /* start-sanitize-v850e */
2645 /* mul reg1, reg2, reg3 */
2649 trace_input ("mul", OP_REG_REG_REG
, 0);
2651 Multiply64 (true, State
.regs
[ OP
[0] ]);
2653 trace_output (OP_REG_REG_REG
);
2658 /* end-sanitize-v850e */
2659 /* start-sanitize-v850eq */
2667 trace_input ("popmh", OP_PUSHPOP2
, 0);
2669 if (OP
[3] & (1 << 19))
2671 if ((PSW
& PSW_NP
) && ((PSW
& PSW_EP
) == 0))
2673 FEPSW
= load_mem ( SP
& ~ 3, 4);
2674 FEPC
= load_mem ((SP
+ 4) & ~ 3, 4);
2678 EIPSW
= load_mem ( SP
& ~ 3, 4);
2679 EIPC
= load_mem ((SP
+ 4) & ~ 3, 4);
2685 /* Load the registers with lower number registers being retrieved from higher addresses. */
2687 if ((OP
[3] & (1 << type2_regs
[ i
])))
2689 State
.regs
[ i
+ 16 ] = load_mem (SP
& ~ 3, 4);
2693 trace_output (OP_PUSHPOP2
);
2704 trace_input ("popml", OP_PUSHPOP3
, 0);
2706 if (OP
[3] & (1 << 19))
2708 if ((PSW
& PSW_NP
) && ((PSW
& PSW_EP
) == 0))
2710 FEPSW
= load_mem ( SP
& ~ 3, 4);
2711 FEPC
= load_mem ((SP
+ 4) & ~ 3, 4);
2715 EIPSW
= load_mem ( SP
& ~ 3, 4);
2716 EIPC
= load_mem ((SP
+ 4) & ~ 3, 4);
2722 if (OP
[3] & (1 << 3))
2724 PSW
= load_mem (SP
& ~ 3, 4);
2728 /* Load the registers with lower number registers being retrieved from higher addresses. */
2730 if ((OP
[3] & (1 << type3_regs
[ i
])))
2732 State
.regs
[ i
+ 1 ] = load_mem (SP
& ~ 3, 4);
2736 trace_output (OP_PUSHPOP2
);
2747 trace_input ("pushmh", OP_PUSHPOP2
, 0);
2749 /* Store the registers with lower number registers being placed at higher addresses. */
2750 for (i
= 0; i
< 16; i
++)
2751 if ((OP
[3] & (1 << type2_regs
[ i
])))
2754 store_mem (SP
& ~ 3, 4, State
.regs
[ i
+ 16 ]);
2757 if (OP
[3] & (1 << 19))
2761 if ((PSW
& PSW_NP
) && ((PSW
& PSW_EP
) == 0))
2763 store_mem ((SP
+ 4) & ~ 3, 4, FEPC
);
2764 store_mem ( SP
& ~ 3, 4, FEPSW
);
2768 store_mem ((SP
+ 4) & ~ 3, 4, EIPC
);
2769 store_mem ( SP
& ~ 3, 4, EIPSW
);
2773 trace_output (OP_PUSHPOP2
);
2778 /* end-sanitize-v850eq */
This page took 0.089452 seconds and 4 git commands to generate.