Skip to content

Commit

Permalink
save 'jammed' status into snapshot for each cpu, fixes bug #1770
Browse files Browse the repository at this point in the history
git-svn-id: https://svn.code.sf.net/p/vice-emu/code/trunk@45313 379a1393-f5fb-40a0-bcee-ef074d9b53f7
  • Loading branch information
mrdudz committed Aug 18, 2024
1 parent 3f0c973 commit 573f0f3
Show file tree
Hide file tree
Showing 8 changed files with 64 additions and 29 deletions.
14 changes: 9 additions & 5 deletions vice/src/6510core.c
Original file line number Diff line number Diff line change
Expand Up @@ -489,7 +489,7 @@ do { \
interrupt_ack_reset(CPU_INT_STATUS); \
bank_start = bank_limit = 0; /* prevent caching */ \
LOCAL_SET_INTERRUPT(1); \
cpu_is_jammed = 0; \
CPU_IS_JAMMED = 0; \
DMA_ON_RESET; \
addr = LOAD_ADDR(0xfffc); \
CHECK_PROFILE_INTERRUPT(addr, 0xfffc); \
Expand Down Expand Up @@ -1236,7 +1236,7 @@ FIXME: perhaps we really have to add some randomness to (some) bits
uint32_t trap_result; \
EXPORT_REGISTERS(); \
if (!ROM_TRAP_ALLOWED() || (trap_result = ROM_TRAP_HANDLER()) == (uint32_t)-1) { \
cpu_is_jammed = 1; \
CPU_IS_JAMMED = 1; \
REWIND_FETCH_OPCODE(CLK); \
JAM(); \
} else { \
Expand Down Expand Up @@ -2269,7 +2269,11 @@ static const uint8_t rewind_fetch_tab[] = {
/* Here, the CPU is emulated. */

{
#ifndef CPU_IS_JAMMED
static int cpu_is_jammed = 0;
#define CPU_IS_JAMMED cpu_is_jammed
#warning "CPU_IS_JAMMED not defined, using default (internal)"
#endif
unsigned int tmpa; /* needed for some of the opcode macros */
#if !defined(DRIVE_CPU)
CLOCK profiling_clock_start;
Expand All @@ -2290,11 +2294,11 @@ static const uint8_t rewind_fetch_tab[] = {
/* HACK: when the CPU is jammed, no interrupts are served, the only way
to recover is reset. so we clear the interrupt flags and force
acknowledging them here in this case. */
if (cpu_is_jammed) {
if (CPU_IS_JAMMED) {
interrupt_ack_irq(CPU_INT_STATUS);
CPU_INT_STATUS->global_pending_int &= ~(IK_IRQ | IK_NMI);
if (CPU_INT_STATUS->global_pending_int & IK_RESET) {
cpu_is_jammed = 0;
CPU_IS_JAMMED = 0;
}
}

Expand Down Expand Up @@ -2440,7 +2444,7 @@ static const uint8_t rewind_fetch_tab[] = {
case 0x32: /* JAM */
case 0x42: /* JAM */
#endif
cpu_is_jammed = 1;
CPU_IS_JAMMED = 1;
REWIND_FETCH_OPCODE(CLK);
JAM();
break;
Expand Down
25 changes: 14 additions & 11 deletions vice/src/6510dtvcore.c
Original file line number Diff line number Diff line change
Expand Up @@ -417,7 +417,7 @@
addr |= (LOAD(0xfffd) << 8); \
bank_start = bank_limit = 0; /* prevent caching */ \
LOCAL_SET_INTERRUPT(1); \
cpu_is_jammed = 0; \
CPU_IS_JAMMED = 0; \
CHECK_PROFILE_INTERRUPT(addr, 0xfffc); \
JUMP(addr); \
DMA_ON_RESET; \
Expand Down Expand Up @@ -1016,7 +1016,7 @@ FIXME: perhaps we really have to add some randomness to (some) bits
uint32_t trap_result; \
EXPORT_REGISTERS(); \
if (!ROM_TRAP_ALLOWED() || (trap_result = ROM_TRAP_HANDLER()) == (uint32_t)-1) { \
cpu_is_jammed = 1; \
CPU_IS_JAMMED = 1; \
REWIND_FETCH_OPCODE(CLK); \
JAM(); \
} else { \
Expand Down Expand Up @@ -1700,7 +1700,11 @@ static const uint8_t fetch_tab[] = {
/* Here, the CPU is emulated. */

{
#ifndef CPU_IS_JAMMED
static int cpu_is_jammed = 0;
#define CPU_IS_JAMMED cpu_is_jammed
#warning "CPU_IS_JAMMED not defined, using default (internal)"
#endif

#if !defined(DRIVE_CPU)
CLOCK profiling_clock_start;
Expand All @@ -1718,20 +1722,20 @@ static const uint8_t fetch_tab[] = {
/* HACK: when the CPU is jammed, no interrupts are served, the only way
to recover is reset. so we clear the interrupt flags and force
acknowledging them here in this case. */
if (cpu_is_jammed) {
if (CPU_IS_JAMMED) {
interrupt_ack_irq(CPU_INT_STATUS);
CPU_INT_STATUS->global_pending_int &= ~(IK_IRQ | IK_NMI);
if (CPU_INT_STATUS->global_pending_int & IK_RESET) {
cpu_is_jammed = 0;
CPU_IS_JAMMED = 0;
}
}

{
enum cpu_int pending_interrupt;

if (!(CPU_INT_STATUS->global_pending_int & IK_IRQ)
&& (CPU_INT_STATUS->global_pending_int & IK_IRQPEND)
&& CPU_INT_STATUS->irq_pending_clk <= CLK) {
if (!(CPU_INT_STATUS->global_pending_int & IK_IRQ) &&
(CPU_INT_STATUS->global_pending_int & IK_IRQPEND) &&
(CPU_INT_STATUS->irq_pending_clk <= CLK)) {
interrupt_ack_irq(CPU_INT_STATUS);
}

Expand All @@ -1740,10 +1744,9 @@ static const uint8_t fetch_tab[] = {
#if !defined(DRIVE_CPU)
profiling_clock_start = CLK;
#endif

DO_INTERRUPT(pending_interrupt);
if (!(CPU_INT_STATUS->global_pending_int & IK_IRQ)
&& CPU_INT_STATUS->global_pending_int & IK_IRQPEND) {
if (!(CPU_INT_STATUS->global_pending_int & IK_IRQ) &&
CPU_INT_STATUS->global_pending_int & IK_IRQPEND) {
CPU_INT_STATUS->global_pending_int &= ~IK_IRQPEND;
}
while (CLK >= alarm_context_next_pending_clk(ALARM_CONTEXT)) {
Expand Down Expand Up @@ -1832,7 +1835,7 @@ static const uint8_t fetch_tab[] = {
case 0x32: /* JAM */
case 0x42: /* JAM */
#endif
cpu_is_jammed = 1;
CPU_IS_JAMMED = 1;
REWIND_FETCH_OPCODE(CLK);
JAM();
break;
Expand Down
4 changes: 4 additions & 0 deletions vice/src/drive/drivecpu.c
Original file line number Diff line number Diff line change
Expand Up @@ -392,6 +392,10 @@ void drivecpu_execute(diskunit_context_t *drv, CLOCK clk_value)
/* Run drive CPU emulation until the stop_clk clock has been reached. */
while (*drv->clk_ptr < cpu->stop_clk) {
/* Include the 6502/6510 CPU emulation core. */
#define CPU_LOG_ID (drv->log)
/* #define ANE_LOG_LEVEL ane_log_level */
/* #define LXA_LOG_LEVEL lxa_log_level */
#define CPU_IS_JAMMED cpu->is_jammed

#define CLK (*(drv->clk_ptr))
#define RMW_FLAG (cpu->rmw_flag)
Expand Down
3 changes: 3 additions & 0 deletions vice/src/drive/drivetypes.h
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,9 @@ typedef struct drivecpu_context_s {
/* Address of the last executed opcode. This is used by watchpoints. */
unsigned int last_opcode_addr;

/* jam flag */
int is_jammed;

/* Public copy of the registers. */
mos6510_regs_t cpu_regs;
R65C02_regs_t cpu_R65C02_regs;
Expand Down
14 changes: 11 additions & 3 deletions vice/src/interrupt.h
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,7 @@ inline static void interrupt_set_irq(interrupt_cpu_status_t *cs,
unsigned int int_num,
int value, CLOCK cpu_clk)
{
if (cs == NULL || int_num >= cs->num_ints) {
if ((cs == NULL) || (int_num >= cs->num_ints)) {
return;
}

Expand Down Expand Up @@ -183,7 +183,7 @@ inline static void interrupt_set_irq(interrupt_cpu_status_t *cs,
if (cs->nirq > 0) {
cs->pending_int[int_num] =
(cs->pending_int[int_num] & (unsigned int)~IK_IRQ);
if (--cs->nirq == 0) {
if ((--cs->nirq) == 0) {
cs->global_pending_int =
(cs->global_pending_int & (unsigned int)~IK_IRQ);
cs->irq_pending_clk = cpu_clk + 3;
Expand Down Expand Up @@ -249,6 +249,11 @@ inline static void interrupt_set_nmi(interrupt_cpu_status_t *cs,
}
}

/* FIXME: update the acia code and get rid of this
src/plus4/plus4acia.c:72
src/c64/cart/c64acia1.c:85
*/
#if 1
/* Change the interrupt line state: this can be used to change both NMI
and IRQ lines. It is slower than `interrupt_set_nmi()' and
`interrupt_set_irq()', but is left for backward compatibility (it works
Expand All @@ -259,6 +264,7 @@ inline static void interrupt_set_int(interrupt_cpu_status_t *cs, int int_num,
interrupt_set_nmi(cs, (unsigned int)int_num, (int)(value & IK_NMI), cpu_clk);
interrupt_set_irq(cs, (unsigned int)int_num, (int)(value & IK_IRQ), cpu_clk);
}
#endif

/* ------------------------------------------------------------------------- */

Expand All @@ -274,6 +280,7 @@ inline static void interrupt_ack_nmi(interrupt_cpu_status_t *cs)
}
}

/* clear IK_IRQPEND bit and set irq_pending_clk to CLOCK_MAX */
inline static void interrupt_ack_irq(interrupt_cpu_status_t *cs)
{
cs->global_pending_int =
Expand Down Expand Up @@ -337,9 +344,10 @@ extern CLOCK maincpu_clk;

#define maincpu_set_int(int_num, value) \
interrupt_set_int(maincpu_int_status, (int_num), (value), maincpu_clk)

#if 0
#define maincpu_set_int_clk(int_num, value, clk) \
interrupt_set_int(maincpu_int_status, (int_num), (value), (clk))
#endif

#define maincpu_trigger_reset() \
interrupt_trigger_reset(maincpu_int_status, maincpu_clk)
Expand Down
11 changes: 8 additions & 3 deletions vice/src/mainc64cpu.c
Original file line number Diff line number Diff line change
Expand Up @@ -512,10 +512,12 @@ const CLOCK maincpu_opcode_write_cycles[] = {
the values copied into this struct. */
mos6510_regs_t maincpu_regs;

static int maincpu_jammed = 0;

/* ------------------------------------------------------------------------- */

int ane_log_level = 0; /* 0: none, 1: unstable only 2: all */
int lxa_log_level = 0; /* 0: none, 1: unstable only 2: all */
static int ane_log_level = 0; /* 0: none, 1: unstable only 2: all */
static int lxa_log_level = 0; /* 0: none, 1: unstable only 2: all */

static int set_ane_log_level(int val, void *param)
{
Expand Down Expand Up @@ -756,6 +758,7 @@ void maincpu_mainloop(void)
#define CPU_LOG_ID maincpu_log
#define ANE_LOG_LEVEL ane_log_level
#define LXA_LOG_LEVEL lxa_log_level
#define CPU_IS_JAMMED maincpu_jammed
#define CLK maincpu_clk
#define RMW_FLAG maincpu_rmw_flag
#define LAST_OPCODE_INFO last_opcode_info
Expand Down Expand Up @@ -879,7 +882,7 @@ unsigned int maincpu_get_sp(void) {

static char snap_module_name[] = "MAINCPU";
#define SNAP_MAJOR 1
#define SNAP_MINOR 3
#define SNAP_MINOR 4

int maincpu_snapshot_write_module(snapshot_t *s)
{
Expand All @@ -902,6 +905,7 @@ int maincpu_snapshot_write_module(snapshot_t *s)
|| SMW_DW(m, (uint32_t)last_opcode_info) < 0
|| SMW_DW(m, (uint32_t)ane_log_level) < 0
|| SMW_DW(m, (uint32_t)lxa_log_level) < 0
|| SMW_DW(m, (uint32_t)maincpu_jammed) < 0
|| SMW_DW(m, (uint32_t)maincpu_ba_low_flags) < 0) {
goto fail;
}
Expand Down Expand Up @@ -950,6 +954,7 @@ int maincpu_snapshot_read_module(snapshot_t *s)
|| SMR_DW_UINT(m, &last_opcode_info) < 0
|| SMR_DW_INT(m, &ane_log_level) < 0
|| SMR_DW_INT(m, &lxa_log_level) < 0
|| SMR_DW_INT(m, &maincpu_jammed) < 0
|| SMR_DW_INT(m, &maincpu_ba_low_flags) < 0) {
goto fail;
}
Expand Down
7 changes: 5 additions & 2 deletions vice/src/maincpu.c
Original file line number Diff line number Diff line change
Expand Up @@ -292,10 +292,12 @@ mos6510dtv_regs_t maincpu_regs;
mos6510_regs_t maincpu_regs;
#endif

static int maincpu_jammed = 0;

/* ------------------------------------------------------------------------- */

int ane_log_level = 0; /* 0: none, 1: unstable only 2: all */
int lxa_log_level = 0; /* 0: none, 1: unstable only 2: all */
static int ane_log_level = 0; /* 0: none, 1: unstable only 2: all */
static int lxa_log_level = 0; /* 0: none, 1: unstable only 2: all */

static int set_ane_log_level(int val, void *param)
{
Expand Down Expand Up @@ -583,6 +585,7 @@ void maincpu_mainloop(void)
#define CPU_LOG_ID maincpu_log
#define ANE_LOG_LEVEL ane_log_level
#define LXA_LOG_LEVEL lxa_log_level
#define CPU_IS_JAMMED maincpu_jammed
#define CLK maincpu_clk
#define RMW_FLAG maincpu_rmw_flag
#define LAST_OPCODE_INFO last_opcode_info
Expand Down
15 changes: 10 additions & 5 deletions vice/src/mainviccpu.c
Original file line number Diff line number Diff line change
Expand Up @@ -339,10 +339,12 @@ const CLOCK maincpu_opcode_write_cycles[] = {
the values copied into this struct. */
mos6510_regs_t maincpu_regs;

static int maincpu_jammed = 0;

/* ------------------------------------------------------------------------- */

int ane_log_level = 0; /* 0: none, 1: unstable only 2: all */
int lxa_log_level = 0; /* 0: none, 1: unstable only 2: all */
static int ane_log_level = 0; /* 0: none, 1: unstable only 2: all */
static int lxa_log_level = 0; /* 0: none, 1: unstable only 2: all */

static int set_ane_log_level(int val, void *param)
{
Expand Down Expand Up @@ -583,6 +585,7 @@ void maincpu_mainloop(void)
#define CPU_LOG_ID maincpu_log
#define ANE_LOG_LEVEL ane_log_level
#define LXA_LOG_LEVEL lxa_log_level
#define CPU_IS_JAMMED maincpu_jammed
#define CLK maincpu_clk
#define RMW_FLAG maincpu_rmw_flag
#define LAST_OPCODE_INFO last_opcode_info
Expand Down Expand Up @@ -706,7 +709,7 @@ unsigned int maincpu_get_sp(void) {

static char snap_module_name[] = "MAINCPU";
#define SNAP_MAJOR 1
#define SNAP_MINOR 3
#define SNAP_MINOR 4

int maincpu_snapshot_write_module(snapshot_t *s)
{
Expand All @@ -728,7 +731,8 @@ int maincpu_snapshot_write_module(snapshot_t *s)
|| SMW_B(m, (uint8_t)MOS6510_REGS_GET_STATUS(&maincpu_regs)) < 0
|| SMW_DW(m, (uint32_t)last_opcode_info) < 0
|| SMW_DW(m, (uint32_t)ane_log_level) < 0
|| SMW_DW(m, (uint32_t)lxa_log_level) < 0) {
|| SMW_DW(m, (uint32_t)lxa_log_level) < 0
|| SMW_DW(m, (uint32_t)maincpu_jammed) < 0) {
goto fail;
}

Expand Down Expand Up @@ -775,7 +779,8 @@ int maincpu_snapshot_read_module(snapshot_t *s)
|| SMR_B(m, &status) < 0
|| SMR_DW_UINT(m, &last_opcode_info) < 0
|| SMR_DW_INT(m, &ane_log_level) < 0
|| SMR_DW_INT(m, &lxa_log_level) < 0) {
|| SMR_DW_INT(m, &lxa_log_level) < 0
|| SMR_DW_INT(m, &maincpu_jammed) < 0) {
goto fail;
}

Expand Down

0 comments on commit 573f0f3

Please sign in to comment.