2 #include "sim-options.h"
4 #include "sim-assert.h"
29 /* For compatibility */
34 /* v850 interrupt model */
49 char *interrupt_names
[] = {
62 do_interrupt (sd
, data
)
66 char **interrupt_name
= (char**)data
;
67 enum interrupt_type inttype
;
68 inttype
= (interrupt_name
- STATE_WATCHPOINTS (sd
)->interrupt_names
);
70 /* For a hardware reset, drop everything and jump to the start
72 if (inttype
== int_reset
)
77 sim_engine_restart (sd
, NULL
, NULL
, NULL_CIA
);
80 /* Deliver an NMI when allowed */
81 if (inttype
== int_nmi
)
85 /* We're already working on an NMI, so this one must wait
86 around until the previous one is done. The processor
87 ignores subsequent NMIs, so we don't need to count them.
88 Just keep re-scheduling a single NMI until it manages to
90 if (STATE_CPU (sd
, 0)->pending_nmi
!= NULL
)
91 sim_events_deschedule (sd
, STATE_CPU (sd
, 0)->pending_nmi
);
92 STATE_CPU (sd
, 0)->pending_nmi
=
93 sim_events_schedule (sd
, 1, do_interrupt
, data
);
98 /* NMI can be delivered. Do not deschedule pending_nmi as
99 that, if still in the event queue, is a second NMI that
100 needs to be delivered later. */
103 /* Set the FECC part of the ECR. */
110 sim_engine_restart (sd
, NULL
, NULL
, NULL_CIA
);
114 /* deliver maskable interrupt when allowed */
115 if (inttype
> int_nmi
&& inttype
< num_int_types
)
117 if ((PSW
& PSW_NP
) || (PSW
& PSW_ID
))
119 /* Can't deliver this interrupt, reschedule it for later */
120 sim_events_schedule (sd
, 1, do_interrupt
, data
);
128 /* Disable further interrupts. */
130 /* Indicate that we're doing interrupt not exception processing. */
132 /* Clear the EICC part of the ECR, will set below. */
161 /* Should never be possible. */
162 sim_engine_abort (sd
, NULL
, NULL_CIA
,
163 "do_interrupt - internal error - bad switch");
167 sim_engine_restart (sd
, NULL
, NULL
, NULL_CIA
);
170 /* some other interrupt? */
171 sim_engine_abort (sd
, NULL
, NULL_CIA
,
172 "do_interrupt - internal error - interrupt %d unknown",
176 /* These default values correspond to expected usage for the chip. */
182 sim_open (kind
, cb
, abfd
, argv
)
188 SIM_DESC sd
= sim_state_alloc (kind
, cb
);
191 SIM_ASSERT (STATE_MAGIC (sd
) == SIM_MAGIC_NUMBER
);
193 /* for compatibility */
196 /* FIXME: should be better way of setting up interrupts */
197 STATE_WATCHPOINTS (sd
)->pc
= &(PC
);
198 STATE_WATCHPOINTS (sd
)->sizeof_pc
= sizeof (PC
);
199 STATE_WATCHPOINTS (sd
)->interrupt_handler
= do_interrupt
;
200 STATE_WATCHPOINTS (sd
)->interrupt_names
= interrupt_names
;
202 if (sim_pre_argv_init (sd
, argv
[0]) != SIM_RC_OK
)
205 /* Allocate core managed memory */
207 /* "Mirror" the ROM addresses below 1MB. */
208 sim_do_commandf (sd
, "memory region 0,0x100000,0x%lx", V850_ROM_SIZE
);
209 /* Chunk of ram adjacent to rom */
210 sim_do_commandf (sd
, "memory region 0x100000,0x%lx", V850_LOW_END
-0x100000);
211 /* peripheral I/O region - mirror 1K across 4k (0x1000) */
212 sim_do_command (sd
, "memory region 0xfff000,0x1000,1024");
213 /* similarly if in the internal RAM region */
214 sim_do_command (sd
, "memory region 0xffe000,0x1000,1024");
216 /* getopt will print the error message so we just have to exit if this fails.
217 FIXME: Hmmm... in the case of gdb we need getopt to call
219 if (sim_parse_args (sd
, argv
) != SIM_RC_OK
)
221 /* Uninstall the modules to avoid memory leaks,
222 file descriptor leaks, etc. */
223 sim_module_uninstall (sd
);
227 /* check for/establish the a reference program image */
228 if (sim_analyze_program (sd
,
229 (STATE_PROG_ARGV (sd
) != NULL
230 ? *STATE_PROG_ARGV (sd
)
234 sim_module_uninstall (sd
);
238 /* establish any remaining configuration options */
239 if (sim_config (sd
) != SIM_RC_OK
)
241 sim_module_uninstall (sd
);
245 if (sim_post_argv_init (sd
) != SIM_RC_OK
)
247 /* Uninstall the modules to avoid memory leaks,
248 file descriptor leaks, etc. */
249 sim_module_uninstall (sd
);
254 /* determine the machine type */
255 if (STATE_ARCHITECTURE (sd
) != NULL
256 && STATE_ARCHITECTURE (sd
)->arch
== bfd_arch_v850
)
257 mach
= STATE_ARCHITECTURE (sd
)->mach
;
259 mach
= bfd_mach_v850
; /* default */
261 /* set machine specific configuration */
265 /* start-sanitize-v850e */
267 STATE_CPU (sd
, 0)->psw_mask
= (PSW_NP
| PSW_EP
| PSW_ID
| PSW_SAT
268 | PSW_CY
| PSW_OV
| PSW_S
| PSW_Z
);
270 case bfd_mach_v850ea
:
272 STATE_CPU (sd
, 0)->psw_mask
= (PSW_US
273 | PSW_NP
| PSW_EP
| PSW_ID
| PSW_SAT
274 | PSW_CY
| PSW_OV
| PSW_S
| PSW_Z
);
276 /* end-sanitize-v850e */
284 sim_close (sd
, quitting
)
288 sim_module_uninstall (sd
);
299 sim_create_inferior (sd
, prog_bfd
, argv
, env
)
301 struct _bfd
*prog_bfd
;
305 memset (&State
, 0, sizeof (State
));
306 if (prog_bfd
!= NULL
)
307 PC
= bfd_get_start_address (prog_bfd
);
308 /* start-sanitize-v850e */
309 /* For v850ea, set PSW[US] by default */
310 if (STATE_ARCHITECTURE (sd
) != NULL
311 && STATE_ARCHITECTURE (sd
)->arch
== bfd_arch_v850
312 && STATE_ARCHITECTURE (sd
)->mach
== bfd_mach_v850ea
)
314 /* end-sanitize-v850e */
319 sim_fetch_register (sd
, rn
, memory
, length
)
322 unsigned char *memory
;
325 *(unsigned32
*)memory
= H2T_4 (State
.regs
[rn
]);
330 sim_store_register (sd
, rn
, memory
, length
)
333 unsigned char *memory
;
336 State
.regs
[rn
] = T2H_4 (*(unsigned32
*)memory
);
341 sim_do_command (sd
, cmd
)
345 char *mm_cmd
= "memory-map";
346 char *int_cmd
= "interrupt";
348 if (sim_args_command (sd
, cmd
) != SIM_RC_OK
)
350 if (strncmp (cmd
, mm_cmd
, strlen (mm_cmd
) == 0))
351 sim_io_eprintf (sd
, "`memory-map' command replaced by `sim memory'\n");
352 else if (strncmp (cmd
, int_cmd
, strlen (int_cmd
)) == 0)
353 sim_io_eprintf (sd
, "`interrupt' command replaced by `sim watch'\n");
355 sim_io_eprintf (sd
, "Unknown command `%s'\n", cmd
);