1 /* m6811_cpu.c -- 68HC11&68HC12 CPU Emulation
2 Copyright 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
3 Written by Stephane Carrez (stcarrez@worldnet.fr)
5 This file is part of GDB, GAS, and the GNU binutils.
7 GDB, GAS, and the GNU binutils are free software; you can redistribute
8 them and/or modify them under the terms of the GNU General Public
9 License as published by the Free Software Foundation; either version
10 1, or (at your option) any later version.
12 GDB, GAS, and the GNU binutils are distributed in the hope that they
13 will be useful, but WITHOUT ANY WARRANTY; without even the implied
14 warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
15 the GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this file; see the file COPYING. If not, write to the Free
19 Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
22 #include "sim-assert.h"
23 #include "sim-module.h"
24 #include "sim-options.h"
26 void cpu_free_frame (sim_cpu
* cpu
, struct cpu_frame
*frame
);
29 OPTION_CPU_RESET
= OPTION_START
,
35 static DECLARE_OPTION_HANDLER (cpu_option_handler
);
37 static const OPTION cpu_options
[] =
39 { {"cpu-reset", no_argument
, NULL
, OPTION_CPU_RESET
},
40 '\0', NULL
, "Reset the CPU",
43 { {"emulos", no_argument
, NULL
, OPTION_EMUL_OS
},
44 '\0', NULL
, "Emulate some OS system calls (read, write, ...)",
47 { {"cpu-config", required_argument
, NULL
, OPTION_CPU_CONFIG
},
48 '\0', NULL
, "Specify the initial CPU configuration register",
51 { {NULL
, no_argument
, NULL
, 0}, '\0', NULL
, NULL
, NULL
}
56 cpu_option_handler (SIM_DESC sd
, sim_cpu
*cpu
,
57 int opt
, char *arg
, int is_command
)
62 cpu
= STATE_CPU (sd
, 0);
65 case OPTION_CPU_RESET
:
70 cpu
->cpu_emul_syscall
= 1;
73 case OPTION_CPU_CONFIG
:
74 if (sscanf(arg
, "0x%x", &val
) == 1
75 || sscanf(arg
, "%d", &val
) == 1)
77 cpu
->cpu_config
= val
;
78 cpu
->cpu_use_local_config
= 1;
81 cpu
->cpu_use_local_config
= 0;
91 /* Tentative to keep track of the cpu frame. */
93 cpu_find_frame (sim_cpu
*cpu
, uint16 sp
)
95 struct cpu_frame_list
*flist
;
97 flist
= cpu
->cpu_frames
;
100 struct cpu_frame
*frame
;
102 frame
= flist
->frame
;
105 if (frame
->sp_low
<= sp
&& frame
->sp_high
>= sp
)
107 cpu
->cpu_current_frame
= flist
;
118 struct cpu_frame_list
*
119 cpu_create_frame_list (sim_cpu
*cpu
)
121 struct cpu_frame_list
*flist
;
123 flist
= (struct cpu_frame_list
*) malloc (sizeof (struct cpu_frame_list
));
125 flist
->next
= cpu
->cpu_frames
;
128 flist
->next
->prev
= flist
;
129 cpu
->cpu_frames
= flist
;
130 cpu
->cpu_current_frame
= flist
;
135 cpu_remove_frame_list (sim_cpu
*cpu
, struct cpu_frame_list
*flist
)
137 struct cpu_frame
*frame
;
139 if (flist
->prev
== 0)
140 cpu
->cpu_frames
= flist
->next
;
142 flist
->prev
->next
= flist
->next
;
144 flist
->next
->prev
= flist
->prev
;
146 frame
= flist
->frame
;
149 struct cpu_frame
* up
= frame
->up
;
150 cpu_free_frame (cpu
, frame
);
158 cpu_create_frame (sim_cpu
*cpu
, uint16 pc
, uint16 sp
)
160 struct cpu_frame
*frame
;
162 frame
= (struct cpu_frame
*) malloc (sizeof(struct cpu_frame
));
171 cpu_free_frame (sim_cpu
*cpu
, struct cpu_frame
*frame
)
177 cpu_frame_reg (sim_cpu
*cpu
, uint16 rn
)
179 struct cpu_frame
*frame
;
181 if (cpu
->cpu_current_frame
== 0)
184 frame
= cpu
->cpu_current_frame
->frame
;
188 return frame
->sp_high
;
196 cpu_call (sim_cpu
*cpu
, uint16 addr
)
199 uint16 pc
= cpu
->cpu_insn_pc
;
201 struct cpu_frame_list
*flist
;
202 struct cpu_frame
* frame
;
203 struct cpu_frame
* new_frame
;
206 cpu_set_pc (cpu
, addr
);
208 sp
= cpu_get_sp (cpu
);
210 cpu
->cpu_need_update_frame
= 0;
211 flist
= cpu
->cpu_current_frame
;
213 flist
= cpu_create_frame_list (cpu
);
215 frame
= flist
->frame
;
216 if (frame
&& frame
->sp_low
> sp
)
219 new_frame
= cpu_create_frame (cpu
, pc
, sp
);
220 new_frame
->up
= frame
;
221 flist
->frame
= new_frame
;
226 cpu_update_frame (sim_cpu
*cpu
, int do_create
)
229 struct cpu_frame
*frame
;
231 frame
= cpu_find_frame (cpu
, cpu_get_sp (cpu
));
234 while (frame
!= cpu
->cpu_current_frame
->frame
)
236 struct cpu_frame
* up
;
238 up
= cpu
->cpu_current_frame
->frame
->up
;
239 cpu_free_frame (cpu
, cpu
->cpu_current_frame
->frame
);
240 cpu
->cpu_current_frame
->frame
= up
;
247 cpu_create_frame_list (cpu
);
248 frame
= cpu_create_frame (cpu
, cpu_get_pc (cpu
), cpu_get_sp (cpu
));
249 cpu
->cpu_current_frame
->frame
= frame
;
255 cpu_return (sim_cpu
*cpu
)
258 uint16 sp
= cpu_get_sp (cpu
);
259 struct cpu_frame
*frame
;
260 struct cpu_frame_list
*flist
;
262 cpu
->cpu_need_update_frame
= 0;
263 flist
= cpu
->cpu_current_frame
;
264 if (flist
&& flist
->frame
&& flist
->frame
->up
)
266 frame
= flist
->frame
->up
;
267 if (frame
->sp_low
<= sp
&& frame
->sp_high
>= sp
)
269 cpu_free_frame (cpu
, flist
->frame
);
270 flist
->frame
= frame
;
274 cpu_update_frame (cpu
, 1);
279 cpu_print_frame (SIM_DESC sd
, sim_cpu
*cpu
)
281 struct cpu_frame
* frame
;
284 if (cpu
->cpu_current_frame
== 0 || cpu
->cpu_current_frame
->frame
== 0)
286 sim_io_printf (sd
, "No frame.\n");
289 sim_io_printf (sd
, " # PC SP-L SP-H\n");
290 frame
= cpu
->cpu_current_frame
->frame
;
293 sim_io_printf (sd
, "%3d 0x%04x 0x%04x 0x%04x\n",
294 level
, frame
->pc
, frame
->sp_low
, frame
->sp_high
);
300 /* Set the stack pointer and re-compute the current frame. */
302 cpu_set_sp (sim_cpu
*cpu
, uint16 val
)
304 cpu
->cpu_regs
.sp
= val
;
305 cpu_update_frame (cpu
, 0);
309 cpu_get_reg (sim_cpu
* cpu
, uint8 reg
)
314 return cpu_get_x (cpu
);
317 return cpu_get_y (cpu
);
320 return cpu_get_sp (cpu
);
323 return cpu_get_pc (cpu
);
331 cpu_get_src_reg (sim_cpu
* cpu
, uint8 reg
)
336 return cpu_get_a (cpu
);
339 return cpu_get_b (cpu
);
342 return cpu_get_ccr (cpu
);
345 return cpu_get_tmp3 (cpu
);
348 return cpu_get_d (cpu
);
351 return cpu_get_x (cpu
);
354 return cpu_get_y (cpu
);
357 return cpu_get_sp (cpu
);
365 cpu_set_dst_reg (sim_cpu
* cpu
, uint8 reg
, uint16 val
)
370 cpu_set_a (cpu
, val
);
374 cpu_set_b (cpu
, val
);
378 cpu_set_ccr (cpu
, val
);
382 cpu_set_tmp2 (cpu
, val
);
386 cpu_set_d (cpu
, val
);
390 cpu_set_x (cpu
, val
);
394 cpu_set_y (cpu
, val
);
398 cpu_set_sp (cpu
, val
);
407 cpu_set_reg (sim_cpu
* cpu
, uint8 reg
, uint16 val
)
412 cpu_set_x (cpu
, val
);
416 cpu_set_y (cpu
, val
);
420 cpu_set_sp (cpu
, val
);
424 cpu_set_pc (cpu
, val
);
432 /* Returns the address of a 68HC12 indexed operand.
433 Pre and post modifications are handled on the source register. */
435 cpu_get_indexed_operand_addr (sim_cpu
* cpu
, int restrict
)
442 code
= cpu_fetch8 (cpu
);
444 /* n,r with 5-bit signed constant. */
445 if ((code
& 0x20) == 0)
447 reg
= (code
>> 6) & 3;
448 sval
= (code
& 0x1f);
452 addr
= cpu_get_reg (cpu
, reg
);
456 /* Auto pre/post increment/decrement. */
457 else if ((code
& 0xc0) != 0xc0)
459 reg
= (code
>> 6) & 3;
460 sval
= (code
& 0x0f);
469 addr
= cpu_get_reg (cpu
, reg
);
470 cpu_set_reg (cpu
, reg
, addr
+ sval
);
471 if ((code
& 0x10) == 0)
477 /* [n,r] 16-bits offset indexed indirect. */
478 else if ((code
& 0x07) == 3)
484 reg
= (code
>> 3) & 0x03;
485 addr
= cpu_get_reg (cpu
, reg
);
486 addr
+= cpu_fetch16 (cpu
);
487 addr
= memory_read16 (cpu
, addr
);
488 cpu_add_cycles (cpu
, 1);
490 else if ((code
& 0x4) == 0)
496 reg
= (code
>> 3) & 0x03;
497 addr
= cpu_get_reg (cpu
, reg
);
500 sval
= cpu_fetch16 (cpu
);
501 cpu_add_cycles (cpu
, 1);
505 sval
= cpu_fetch8 (cpu
);
508 cpu_add_cycles (cpu
, 1);
514 reg
= (code
>> 3) & 0x03;
515 addr
= cpu_get_reg (cpu
, reg
);
519 addr
+= cpu_get_a (cpu
);
522 addr
+= cpu_get_b (cpu
);
525 addr
+= cpu_get_d (cpu
);
529 addr
+= cpu_get_d (cpu
);
530 addr
= memory_read16 (cpu
, addr
);
531 cpu_add_cycles (cpu
, 1);
540 cpu_get_indexed_operand8 (sim_cpu
* cpu
, int restrict
)
544 addr
= cpu_get_indexed_operand_addr (cpu
, restrict
);
545 return memory_read8 (cpu
, addr
);
549 cpu_get_indexed_operand16 (sim_cpu
* cpu
, int restrict
)
553 addr
= cpu_get_indexed_operand_addr (cpu
, restrict
);
554 return memory_read16 (cpu
, addr
);
558 cpu_move8 (sim_cpu
*cpu
, uint8 code
)
566 src
= cpu_fetch8 (cpu
);
567 addr
= cpu_fetch16 (cpu
);
571 addr
= cpu_get_indexed_operand_addr (cpu
, 1);
572 src
= cpu_fetch8 (cpu
);
576 addr
= cpu_fetch16 (cpu
);
577 src
= memory_read8 (cpu
, addr
);
578 addr
= cpu_fetch16 (cpu
);
582 addr
= cpu_get_indexed_operand_addr (cpu
, 1);
583 src
= memory_read8 (cpu
, cpu_fetch16 (cpu
));
587 src
= cpu_get_indexed_operand8 (cpu
, 1);
588 addr
= cpu_fetch16 (cpu
);
592 src
= cpu_get_indexed_operand8 (cpu
, 1);
593 addr
= cpu_get_indexed_operand_addr (cpu
, 1);
597 memory_write8 (cpu
, addr
, src
);
601 cpu_move16 (sim_cpu
*cpu
, uint8 code
)
609 src
= cpu_fetch16 (cpu
);
610 addr
= cpu_fetch16 (cpu
);
614 addr
= cpu_get_indexed_operand_addr (cpu
, 1);
615 src
= cpu_fetch16 (cpu
);
619 addr
= cpu_fetch16 (cpu
);
620 src
= memory_read16 (cpu
, addr
);
621 addr
= cpu_fetch16 (cpu
);
625 addr
= cpu_get_indexed_operand_addr (cpu
, 1);
626 src
= memory_read16 (cpu
, cpu_fetch16 (cpu
));
630 src
= cpu_get_indexed_operand16 (cpu
, 1);
631 addr
= cpu_fetch16 (cpu
);
635 src
= cpu_get_indexed_operand16 (cpu
, 1);
636 addr
= cpu_get_indexed_operand_addr (cpu
, 1);
640 memory_write16 (cpu
, addr
, src
);
644 cpu_initialize (SIM_DESC sd
, sim_cpu
*cpu
)
646 sim_add_option_table (sd
, 0, cpu_options
);
648 memset (&cpu
->cpu_regs
, 0, sizeof(cpu
->cpu_regs
));
650 cpu
->cpu_absolute_cycle
= 0;
651 cpu
->cpu_current_cycle
= 0;
652 cpu
->cpu_emul_syscall
= 1;
653 cpu
->cpu_running
= 1;
654 cpu
->cpu_stop_on_interrupt
= 0;
655 cpu
->cpu_frequency
= 8 * 1000 * 1000;
657 cpu
->cpu_current_frame
= 0;
658 cpu
->cpu_use_elf_start
= 0;
659 cpu
->cpu_elf_start
= 0;
660 cpu
->cpu_use_local_config
= 0;
661 cpu
->cpu_config
= M6811_NOSEC
| M6811_NOCOP
| M6811_ROMON
|
663 interrupts_initialize (sd
, cpu
);
665 cpu
->cpu_is_initialized
= 1;
670 /* Reinitialize the processor after a reset. */
672 cpu_reset (sim_cpu
*cpu
)
674 cpu
->cpu_need_update_frame
= 0;
675 cpu
->cpu_current_frame
= 0;
676 while (cpu
->cpu_frames
)
677 cpu_remove_frame_list (cpu
, cpu
->cpu_frames
);
679 /* Initialize the config register.
680 It is only initialized at reset time. */
681 memset (cpu
->ios
, 0, sizeof (cpu
->ios
));
682 if (cpu
->cpu_configured_arch
->arch
== bfd_arch_m68hc11
)
683 cpu
->ios
[M6811_INIT
] = 0x1;
685 cpu
->ios
[M6811_INIT
] = 0;
687 /* Output compare registers set to 0xFFFF. */
688 cpu
->ios
[M6811_TOC1_H
] = 0xFF;
689 cpu
->ios
[M6811_TOC1_L
] = 0xFF;
690 cpu
->ios
[M6811_TOC2_H
] = 0xFF;
691 cpu
->ios
[M6811_TOC2_L
] = 0xFF;
692 cpu
->ios
[M6811_TOC3_H
] = 0xFF;
693 cpu
->ios
[M6811_TOC4_L
] = 0xFF;
694 cpu
->ios
[M6811_TOC5_H
] = 0xFF;
695 cpu
->ios
[M6811_TOC5_L
] = 0xFF;
697 /* Setup the processor registers. */
698 memset (&cpu
->cpu_regs
, 0, sizeof(cpu
->cpu_regs
));
699 cpu
->cpu_absolute_cycle
= 0;
700 cpu
->cpu_current_cycle
= 0;
701 cpu
->cpu_is_initialized
= 0;
703 /* Reset interrupts. */
704 interrupts_reset (&cpu
->cpu_interrupts
);
706 /* Reinitialize the CPU operating mode. */
707 cpu
->ios
[M6811_HPRIO
] = cpu
->cpu_mode
;
711 /* Reinitialize the processor after a reset. */
713 cpu_restart (sim_cpu
*cpu
)
717 /* Get CPU starting address depending on the CPU mode. */
718 if (cpu
->cpu_use_elf_start
== 0)
720 switch ((cpu
->ios
[M6811_HPRIO
]) & (M6811_SMOD
| M6811_MDA
))
725 addr
= memory_read16 (cpu
, 0xFFFE);
728 /* Expanded Multiplexed */
730 addr
= memory_read16 (cpu
, 0xFFFE);
733 /* Special Bootstrap */
739 case M6811_MDA
| M6811_SMOD
:
740 addr
= memory_read16 (cpu
, 0xFFFE);
746 addr
= cpu
->cpu_elf_start
;
749 /* Setup the processor registers. */
750 cpu
->cpu_insn_pc
= addr
;
751 cpu
->cpu_regs
.pc
= addr
;
752 cpu
->cpu_regs
.ccr
= M6811_X_BIT
| M6811_I_BIT
| M6811_S_BIT
;
753 cpu
->cpu_absolute_cycle
= 0;
754 cpu
->cpu_is_initialized
= 1;
755 cpu
->cpu_current_cycle
= 0;
757 cpu_call (cpu
, addr
);
763 print_io_reg_desc (SIM_DESC sd
, io_reg_desc
*desc
, int val
, int mode
)
767 if (val
& desc
->mask
)
768 sim_io_printf (sd
, "%s",
769 mode
== 0 ? desc
->short_name
: desc
->long_name
);
775 print_io_byte (SIM_DESC sd
, const char *name
, io_reg_desc
*desc
,
776 uint8 val
, uint16 addr
)
778 sim_io_printf (sd
, " %-9.9s @ 0x%04x 0x%02x ", name
, addr
, val
);
780 print_io_reg_desc (sd
, desc
, val
, 0);
784 cpu_ccr_update_tst8 (sim_cpu
*proc
, uint8 val
)
786 cpu_set_ccr_V (proc
, 0);
787 cpu_set_ccr_N (proc
, val
& 0x80 ? 1 : 0);
788 cpu_set_ccr_Z (proc
, val
== 0 ? 1 : 0);
793 cpu_fetch_relbranch (sim_cpu
*cpu
)
795 uint16 addr
= (uint16
) cpu_fetch8 (cpu
);
801 addr
+= cpu
->cpu_regs
.pc
;
806 cpu_fetch_relbranch16 (sim_cpu
*cpu
)
808 uint16 addr
= cpu_fetch16 (cpu
);
810 addr
+= cpu
->cpu_regs
.pc
;
814 /* Push all the CPU registers (when an interruption occurs). */
816 cpu_push_all (sim_cpu
*cpu
)
818 if (cpu
->cpu_configured_arch
->arch
== bfd_arch_m68hc11
)
820 cpu_m68hc11_push_uint16 (cpu
, cpu
->cpu_regs
.pc
);
821 cpu_m68hc11_push_uint16 (cpu
, cpu
->cpu_regs
.iy
);
822 cpu_m68hc11_push_uint16 (cpu
, cpu
->cpu_regs
.ix
);
823 cpu_m68hc11_push_uint16 (cpu
, cpu
->cpu_regs
.d
);
824 cpu_m68hc11_push_uint8 (cpu
, cpu
->cpu_regs
.ccr
);
828 cpu_m68hc12_push_uint16 (cpu
, cpu
->cpu_regs
.pc
);
829 cpu_m68hc12_push_uint16 (cpu
, cpu
->cpu_regs
.iy
);
830 cpu_m68hc12_push_uint16 (cpu
, cpu
->cpu_regs
.ix
);
831 cpu_m68hc12_push_uint16 (cpu
, cpu
->cpu_regs
.d
);
832 cpu_m68hc12_push_uint8 (cpu
, cpu
->cpu_regs
.ccr
);
836 /* Simulation of the dbcc/ibcc/tbcc 68HC12 conditional branch operations. */
838 cpu_dbcc (sim_cpu
* cpu
)
845 code
= cpu_fetch8 (cpu
);
848 case 0x80: /* ibcc */
851 case 0x40: /* tbcc */
862 addr
= cpu_fetch8 (cpu
);
866 addr
+= cpu_get_pc (cpu
);
867 reg
= cpu_get_src_reg (cpu
, code
& 0x07);
870 /* Branch according to register value. */
871 if ((reg
!= 0 && (code
& 0x20)) || (reg
== 0 && !(code
& 0x20)))
873 cpu_set_pc (cpu
, addr
);
875 cpu_set_dst_reg (cpu
, code
& 0x07, reg
);
879 cpu_exg (sim_cpu
* cpu
, uint8 code
)
885 r1
= (code
>> 4) & 0x07;
889 src1
= cpu_get_src_reg (cpu
, r1
);
890 src2
= cpu_get_src_reg (cpu
, r2
);
891 if (r2
== 1 || r2
== 2)
894 cpu_set_dst_reg (cpu
, r2
, src1
);
895 cpu_set_dst_reg (cpu
, r1
, src2
);
899 src1
= cpu_get_src_reg (cpu
, r1
);
901 /* Sign extend the 8-bit registers (A, B, CCR). */
902 if ((r1
== 0 || r1
== 1 || r1
== 2) && (src1
& 0x80))
905 cpu_set_dst_reg (cpu
, r2
, src1
);
909 /* Handle special instructions. */
911 cpu_special (sim_cpu
*cpu
, enum M6811_Special special
)
919 ccr
= cpu_m68hc11_pop_uint8 (cpu
);
920 cpu_set_ccr (cpu
, ccr
);
921 cpu_set_d (cpu
, cpu_m68hc11_pop_uint16 (cpu
));
922 cpu_set_x (cpu
, cpu_m68hc11_pop_uint16 (cpu
));
923 cpu_set_y (cpu
, cpu_m68hc11_pop_uint16 (cpu
));
924 cpu_set_pc (cpu
, cpu_m68hc11_pop_uint16 (cpu
));
933 ccr
= cpu_m68hc12_pop_uint8 (cpu
);
934 cpu_set_ccr (cpu
, ccr
);
935 cpu_set_d (cpu
, cpu_m68hc12_pop_uint16 (cpu
));
936 cpu_set_x (cpu
, cpu_m68hc12_pop_uint16 (cpu
));
937 cpu_set_y (cpu
, cpu_m68hc12_pop_uint16 (cpu
));
938 cpu_set_pc (cpu
, cpu_m68hc12_pop_uint16 (cpu
));
944 /* In the ELF-start mode, we are in a special mode where
945 the WAI corresponds to an exit. */
946 if (cpu
->cpu_use_elf_start
)
948 cpu_set_pc (cpu
, cpu
->cpu_insn_pc
);
949 sim_engine_halt (CPU_STATE (cpu
), cpu
,
950 NULL
, NULL_CIA
, sim_exited
,
954 /* SCz: not correct... */
959 interrupts_raise (&cpu
->cpu_interrupts
, M6811_INT_SWI
);
960 interrupts_process (&cpu
->cpu_interrupts
);
963 case M6811_EMUL_SYSCALL
:
965 if (cpu
->cpu_emul_syscall
)
967 uint8 op
= memory_read8 (cpu
,
968 cpu_get_pc (cpu
) - 1);
971 cpu_set_pc (cpu
, cpu
->cpu_insn_pc
);
972 sim_engine_halt (CPU_STATE (cpu
), cpu
,
973 NULL
, NULL_CIA
, sim_exited
,
984 interrupts_raise (&cpu
->cpu_interrupts
, M6811_INT_ILLEGAL
);
985 interrupts_process (&cpu
->cpu_interrupts
);
993 sd
= CPU_STATE (cpu
);
995 /* Breakpoint instruction if we are under gdb. */
996 if (STATE_OPEN_KIND (sd
) == SIM_OPEN_DEBUG
)
999 sim_engine_halt (CPU_STATE (cpu
), cpu
,
1000 0, cpu_get_pc (cpu
), sim_stopped
,
1003 /* else this is a nop but not in test factory mode. */
1009 int32 src1
= (int16
) cpu_get_d (cpu
);
1010 int32 src2
= (int16
) cpu_get_x (cpu
);
1014 cpu_set_ccr_C (cpu
, 1);
1018 cpu_set_d (cpu
, src1
% src2
);
1020 cpu_set_x (cpu
, src1
);
1021 cpu_set_ccr_C (cpu
, 0);
1022 cpu_set_ccr_Z (cpu
, src1
== 0);
1023 cpu_set_ccr_N (cpu
, src1
& 0x8000);
1024 cpu_set_ccr_V (cpu
, src1
>= 32768 || src1
< -32768);
1031 uint32 src1
= (uint32
) cpu_get_x (cpu
);
1032 uint32 src2
= (uint32
) (cpu_get_y (cpu
) << 16)
1033 | (uint32
) (cpu_get_d (cpu
));
1037 cpu_set_ccr_C (cpu
, 1);
1041 cpu_set_ccr_C (cpu
, 0);
1042 cpu_set_d (cpu
, src2
% src1
);
1044 cpu_set_y (cpu
, src2
);
1045 cpu_set_ccr_Z (cpu
, src2
== 0);
1046 cpu_set_ccr_N (cpu
, (src2
& 0x8000) != 0);
1047 cpu_set_ccr_V (cpu
, (src2
& 0xffff0000) != 0);
1054 int32 src1
= (int16
) cpu_get_x (cpu
);
1055 int32 src2
= (uint32
) (cpu_get_y (cpu
) << 16)
1056 | (uint32
) (cpu_get_d (cpu
));
1060 cpu_set_ccr_C (cpu
, 1);
1064 cpu_set_ccr_C (cpu
, 0);
1065 cpu_set_d (cpu
, src2
% src1
);
1067 cpu_set_y (cpu
, src2
);
1068 cpu_set_ccr_Z (cpu
, src2
== 0);
1069 cpu_set_ccr_N (cpu
, (src2
& 0x8000) != 0);
1070 cpu_set_ccr_V (cpu
, src2
> 32767 || src2
< -32768);
1079 src1
= (int16
) cpu_get_d (cpu
);
1080 src2
= (int16
) cpu_get_y (cpu
);
1082 cpu_set_d (cpu
, src1
& 0x0ffff);
1083 cpu_set_y (cpu
, src1
>> 16);
1084 cpu_set_ccr_Z (cpu
, src1
== 0);
1085 cpu_set_ccr_N (cpu
, (src1
& 0x80000000) != 0);
1086 cpu_set_ccr_C (cpu
, (src1
& 0x00008000) != 0);
1095 addr
= cpu_fetch16 (cpu
);
1096 src1
= (int16
) memory_read16 (cpu
, cpu_get_x (cpu
));
1097 src2
= (int16
) memory_read16 (cpu
, cpu_get_y (cpu
));
1099 src2
= (((uint32
) memory_read16 (cpu
, addr
)) << 16)
1100 | (uint32
) memory_read16 (cpu
, addr
+ 2);
1102 memory_write16 (cpu
, addr
, (src1
+ src2
) >> 16);
1103 memory_write16 (cpu
, addr
+ 2, (src1
+ src2
));
1111 sim_engine_halt (CPU_STATE (cpu
), cpu
, NULL
,
1112 cpu_get_pc (cpu
), sim_stopped
,
1120 cpu_single_step (sim_cpu
*cpu
)
1122 cpu
->cpu_current_cycle
= 0;
1123 cpu
->cpu_insn_pc
= cpu_get_pc (cpu
);
1125 /* Handle the pending interrupts. If an interrupt is handled,
1126 treat this as an single step. */
1127 if (interrupts_process (&cpu
->cpu_interrupts
))
1129 cpu
->cpu_absolute_cycle
+= cpu
->cpu_current_cycle
;
1133 /* printf("PC = 0x%04x\n", cpu_get_pc (cpu));*/
1134 cpu
->cpu_interpretor (cpu
);
1135 cpu
->cpu_absolute_cycle
+= cpu
->cpu_current_cycle
;
1140 sim_memory_error (sim_cpu
*cpu
, SIM_SIGNAL excep
,
1141 uint16 addr
, const char *message
, ...)
1146 va_start (args
, message
);
1147 vsprintf (buf
, message
, args
);
1150 printf("%s\n", buf
);
1151 cpu_memory_exception (cpu
, excep
, addr
, buf
);
1156 cpu_memory_exception (sim_cpu
*cpu
, SIM_SIGNAL excep
,
1157 uint16 addr
, const char *message
)
1159 if (cpu
->cpu_running
== 0)
1162 cpu_set_pc (cpu
, cpu
->cpu_insn_pc
);
1163 sim_engine_halt (CPU_STATE (cpu
), cpu
, NULL
,
1164 cpu_get_pc (cpu
), sim_stopped
, excep
);
1167 cpu
->mem_exception
= excep
;
1168 cpu
->fault_addr
= addr
;
1169 cpu
->fault_msg
= strdup (message
);
1171 if (cpu
->cpu_use_handler
)
1173 longjmp (&cpu
->cpu_exception_handler
, 1);
1175 (* cpu
->callback
->printf_filtered
)
1176 (cpu
->callback
, "Fault at 0x%04x: %s\n", addr
, message
);
1181 cpu_info (SIM_DESC sd
, sim_cpu
*cpu
)
1183 sim_io_printf (sd
, "CPU info:\n");
1184 sim_io_printf (sd
, " Absolute cycle: %s\n",
1185 cycle_to_string (cpu
, cpu
->cpu_absolute_cycle
));
1187 sim_io_printf (sd
, " Syscall emulation: %s\n",
1188 cpu
->cpu_emul_syscall
? "yes, via 0xcd <n>" : "no");
1189 sim_io_printf (sd
, " Memory errors detection: %s\n",
1190 cpu
->cpu_check_memory
? "yes" : "no");
1191 sim_io_printf (sd
, " Stop on interrupt: %s\n",
1192 cpu
->cpu_stop_on_interrupt
? "yes" : "no");
This page took 0.053164 seconds and 5 git commands to generate.