diff options
Diffstat (limited to 'src/devices/cpu/unsp/unsp.c')
-rw-r--r-- | src/devices/cpu/unsp/unsp.c | 867 |
1 files changed, 867 insertions, 0 deletions
diff --git a/src/devices/cpu/unsp/unsp.c b/src/devices/cpu/unsp/unsp.c new file mode 100644 index 00000000000..717ddb2a0de --- /dev/null +++ b/src/devices/cpu/unsp/unsp.c @@ -0,0 +1,867 @@ +// license:BSD-3-Clause +// copyright-holders:Ryan Holtz +/**************************\ +* +* SunPlus u'nSP core +* +* by Ryan Holtz +* +\**************************/ + +#include "emu.h" +#include "debugger.h" +#include "unsp.h" + + +const device_type UNSP = &device_creator<unsp_device>; + + +unsp_device::unsp_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) + : cpu_device(mconfig, UNSP, "u'nSP", tag, owner, clock, "unsp", __FILE__) + , m_program_config("program", ENDIANNESS_BIG, 16, 23, -1) +{ +} + + +offs_t unsp_device::disasm_disassemble(char *buffer, offs_t pc, const UINT8 *oprom, const UINT8 *opram, UINT32 options) +{ + extern CPU_DISASSEMBLE( unsp ); + return CPU_DISASSEMBLE_NAME(unsp)(this, buffer, pc, oprom, opram, options); +} + + +/*****************************************************************************/ + +#define OP0 (op >> 12) +#define OPA ((op >> 9) & 7) +#define OP1 ((op >> 6) & 7) +#define OPN ((op >> 3) & 7) +#define OPB (op & 7) +#define OPIMM (op & 0x3f) + +#define UNSP_LPC (((UNSP_REG(SR) & 0x3f) << 16) | UNSP_REG(PC)) + +#define UNSP_REG(reg) m_r[UNSP_##reg - 1] +#define UNSP_REG_I(reg) m_r[reg] +#define UNSP_LREG_I(reg) (((UNSP_REG(SR) << 6) & 0x3f0000) | UNSP_REG_I(reg)) + +#define UNSP_N 0x0200 +#define UNSP_Z 0x0100 +#define UNSP_S 0x0080 +#define UNSP_C 0x0040 + +#define STANDARD_ALU_CASES \ + case 0: \ + lres = r0 + r1; \ + unsp_update_nzsc(lres, r0, r1); \ + break; \ + case 1: \ + lres = r0 + r1; \ + if(UNSP_REG(SR) & UNSP_C) lres++; \ + unsp_update_nzsc(lres, r0, r1); \ + break; \ + case 3: \ + lres = r0 + (~r1 & 0x0000ffff); \ + if(UNSP_REG(SR) & UNSP_C) lres++; \ + unsp_update_nzsc(lres, r0, r1); \ + break; \ + case 2: \ + case 4: \ + lres = r0 + (~r1 & 0x0000ffff) + 1; \ + unsp_update_nzsc(lres, r0, r1); \ + break; \ + case 6: \ + lres = -r1; \ + unsp_update_nz(lres); \ + break; \ + case 8: \ + lres = r0 ^ r1; \ + unsp_update_nz(lres); \ + break; \ + case 9: \ + lres = r1; \ + unsp_update_nz(lres); \ + break; \ + case 10: \ + lres = r0 | r1; \ + unsp_update_nz(lres); \ + break; \ + case 11: \ + case 12: \ + lres = r0 & r1; \ + unsp_update_nz(lres); \ + break + +#define WRITEBACK_OPA \ + if(OP0 != 4 && OP0 < 12) \ + { \ + UNSP_REG_I(OPA) = (UINT16)lres; \ + } + +/*****************************************************************************/ + +void unsp_device::unimplemented_opcode(UINT16 op) +{ + fatalerror("UNSP: unknown opcode %04x at %04x\n", op, UNSP_LPC); +} + +/*****************************************************************************/ + +UINT16 unsp_device::READ16(UINT32 address) +{ + return m_program->read_word(address<<1); +} + +void unsp_device::WRITE16(UINT32 address, UINT16 data) +{ + m_program->write_word(address<<1, data); +} + +/*****************************************************************************/ + +void unsp_device::device_start() +{ + memset(m_r, 0, sizeof(UINT16) * UNSP_GPR_COUNT); + m_irq = 0; + m_fiq = 0; + m_curirq = 0; + m_sirq = 0; + m_sb = 0; + m_saved_sb = 0; + m_debugger_temp = 0; + + m_program = &space(AS_PROGRAM); + + state_add( UNSP_SP, "SP", UNSP_REG(SP)).formatstr("%04X"); + state_add( UNSP_R1, "R1", UNSP_REG(R1)).formatstr("%04X"); + state_add( UNSP_R2, "R2", UNSP_REG(R2)).formatstr("%04X"); + state_add( UNSP_R3, "R3", UNSP_REG(R3)).formatstr("%04X"); + state_add( UNSP_R4, "R4", UNSP_REG(R4)).formatstr("%04X"); + state_add( UNSP_BP, "BP", UNSP_REG(BP)).formatstr("%04X"); + state_add( UNSP_SR, "SR", UNSP_REG(SR)).formatstr("%04X"); + state_add( UNSP_PC, "PC", m_debugger_temp).callimport().callexport().formatstr("%06X"); + state_add( UNSP_IRQ, "IRQ", m_irq).formatstr("%1u"); + state_add( UNSP_FIQ, "FIQ", m_fiq).formatstr("%1u"); + state_add( UNSP_SB, "SB", m_sb).formatstr("%1u"); + + state_add(STATE_GENPC, "GENPC", m_debugger_temp).callexport().noshow(); + + m_icountptr = &m_icount; +} + +void unsp_device::state_export(const device_state_entry &entry) +{ + switch (entry.index()) + { + case UNSP_PC: + m_debugger_temp = UNSP_LPC; + break; + + case STATE_GENPC: + m_debugger_temp = UNSP_LPC; + break; + } +} + +void unsp_device::state_import(const device_state_entry &entry) +{ + switch (entry.index()) + { + case UNSP_PC: + UNSP_REG(PC) = m_debugger_temp & 0x0000ffff; + UNSP_REG(SR) = (UNSP_REG(SR) & 0xffc0) | ((m_debugger_temp & 0x003f0000) >> 16); + break; + } +} + +void unsp_device::device_reset() +{ + memset(m_r, 0, sizeof(UINT16) * UNSP_GPR_COUNT); + + UNSP_REG(PC) = READ16(0xfff7); + m_irq = 0; + m_fiq = 0; +} + +/*****************************************************************************/ + +void unsp_device::unsp_update_nz(UINT32 value) +{ + UNSP_REG(SR) &= ~(UNSP_N | UNSP_Z); + if(value & 0x8000) + { + UNSP_REG(SR) |= UNSP_N; + } + if((UINT16)value == 0) + { + UNSP_REG(SR) |= UNSP_Z; + } +} + +void unsp_device::unsp_update_nzsc(UINT32 value, UINT16 r0, UINT16 r1) +{ + UNSP_REG(SR) &= ~(UNSP_C | UNSP_S); + unsp_update_nz(value); + if(value != (UINT16)value) + { + UNSP_REG(SR) |= UNSP_C; + } + + if((INT16)r0 < (INT16)r1) + { + UNSP_REG(SR) |= UNSP_S; + } +} + +void unsp_device::unsp_push(UINT16 value, UINT16 *reg) +{ + WRITE16((*reg)--, value); +} + +UINT16 unsp_device::unsp_pop(UINT16 *reg) +{ + return READ16(++(*reg)); +} + +void unsp_device::execute_run() +{ + UINT32 op; + UINT32 lres; + UINT16 r0, r1; + lres = 0; + + while (m_icount > 0) + { + debugger_instruction_hook(this, UNSP_LPC); + op = READ16(UNSP_LPC); + + UNSP_REG(PC)++; + + if(OP0 < 0xf && OPA == 0x7 && OP1 < 2) + { + switch(OP0) + { + case 0: // JB + if(!(UNSP_REG(SR) & UNSP_C)) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 1: // JAE + if(UNSP_REG(SR) & UNSP_C) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 2: // JGE + if(!(UNSP_REG(SR) & UNSP_S)) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 3: // JL + if(UNSP_REG(SR) & UNSP_S) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 4: // JNE + if(!(UNSP_REG(SR) & UNSP_Z)) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 5: // JE + if(UNSP_REG(SR) & UNSP_Z) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 6: // JPL + if(!(UNSP_REG(SR) & UNSP_N)) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 7: // JMI + if(UNSP_REG(SR) & UNSP_N) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 8: // JBE + if((UNSP_REG(SR) & (UNSP_Z | UNSP_C)) != UNSP_C) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 9: // JA + if((UNSP_REG(SR) & (UNSP_Z | UNSP_C)) == UNSP_C) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 10: // JLE + if(UNSP_REG(SR) & (UNSP_Z | UNSP_S)) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 11: // JG + if(!(UNSP_REG(SR) & (UNSP_Z | UNSP_S))) + { + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + } + break; + case 14: // JMP + UNSP_REG(PC) += (OP1 == 0) ? OPIMM : (0 - OPIMM); + break; + } + } + else + { + switch((OP1 << 4) | OP0) + { + // r, [bp+imm6] + case 0x00: case 0x01: case 0x02: case 0x03: case 0x04: case 0x06: case 0x08: case 0x09: case 0x0a: case 0x0b: case 0x0c: case 0x0d: + r0 = UNSP_REG_I(OPA); + r1 = READ16(UNSP_REG(BP) + OPIMM); + switch(OP0) + { + STANDARD_ALU_CASES; + case 13: // store r, [bp+imm6] + WRITE16(UNSP_REG(BP) + OPIMM, UNSP_REG_I(OPA)); + break; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + break; + + // r, imm6 + case 0x10: case 0x11: case 0x12: case 0x13: case 0x14: case 0x16: case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: + r0 = UNSP_REG_I(OPA); + r1 = OPIMM; + switch(OP0) + { + STANDARD_ALU_CASES; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + break; + + // Pop / Interrupt return + case 0x29: + if(op == 0x9a90) // retf + { + UNSP_REG(SR) = unsp_pop(&UNSP_REG(SP)); + UNSP_REG(PC) = unsp_pop(&UNSP_REG(SP)); + break; + } + else if(op == 0x9a98) // reti + { + int i; + UNSP_REG(SR) = unsp_pop(&UNSP_REG(SP)); + UNSP_REG(PC) = unsp_pop(&UNSP_REG(SP)); + if(m_fiq & 2) + { + m_fiq &= 1; + } + else if(m_irq & 2) + { + m_irq &= 1; + } + m_sirq &= ~(1 << m_curirq); + for(i = 0; i < 9; i++) + { + if((m_sirq & (1 << i)) != 0 && i != m_curirq) + { + m_sirq &= ~(1 << i); + m_curirq = 0; + execute_set_input(UNSP_IRQ0_LINE + i, 1); + i = -1; + break; + } + } + if(i != -1) + { + m_curirq = 0; + } + break; + } + else + { + r0 = OPN; + r1 = OPA; + while(r0--) + { + UNSP_REG_I(++r1) = unsp_pop(&UNSP_REG_I(OPB)); + } + } + break; + + // Push + case 0x2d: + r0 = OPN; + r1 = OPA; + while(r0--) + { + unsp_push(UNSP_REG_I(r1--), &UNSP_REG_I(OPB)); + } + break; + + // ALU, Indirect + case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x36: case 0x38: case 0x39: case 0x3a: case 0x3b: case 0x3c: case 0x3d: + switch(OPN & 3) + { + case 0: // r, [r] + r0 = UNSP_REG_I(OPA); + r1 = READ16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB)); + switch(OP0) + { + STANDARD_ALU_CASES; + case 13: // store r, [r] + WRITE16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB), UNSP_REG_I(OPA)); + break; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + break; + case 1: // r, [<ds:>r--] + r0 = UNSP_REG_I(OPA); + r1 = READ16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB)); + switch(OP0) + { + STANDARD_ALU_CASES; + case 13: // store r, [<ds:>r--] + WRITE16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB), UNSP_REG_I(OPA)); + break; + default: + unimplemented_opcode(op); + break; + } + UNSP_REG_I(OPB)--; + WRITEBACK_OPA; + break; + case 2: // r, [<ds:>r++] + r0 = UNSP_REG_I(OPA); + r1 = READ16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB)); + switch(OP0) + { + STANDARD_ALU_CASES; + case 13: // store r, [<ds:>r++] + WRITE16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB), UNSP_REG_I(OPA)); + break; + default: + unimplemented_opcode(op); + break; + } + UNSP_REG_I(OPB)++; + WRITEBACK_OPA; + break; + case 3: // r, [<ds:>++r] + UNSP_REG_I(OPB)++; + r0 = UNSP_REG_I(OPA); + r1 = READ16((OPN & 4) ? UNSP_LREG_I(OPB) : UNSP_REG_I(OPB)); + switch(OP0) + { + STANDARD_ALU_CASES; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + break; + } + break; + + // ALU, 16-bit ops + case 0x40: case 0x41: case 0x42: case 0x43: case 0x44: case 0x46: case 0x48: case 0x49: case 0x4a: case 0x4b: case 0x4c: + switch(OPN) + { + // r, r + case 0: + r0 = UNSP_REG_I(OPA); + r1 = UNSP_REG_I(OPB); + switch(OP0) + { + STANDARD_ALU_CASES; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + break; + + // ALU, 16-bit Immediate + case 1: // r, r, imm16 + if(!((OP0 == 4 || OP0 == 6 || OP0 == 9 || OP0 == 12) && OPA != OPB)) + { + r0 = UNSP_REG_I(OPB); + r1 = READ16(UNSP_LPC); + UNSP_REG(PC)++; + switch(OP0) + { + STANDARD_ALU_CASES; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + } + else + { + unimplemented_opcode(op); + } + break; + + // ALU, Direct 16 + case 2: // r, [imm16] + r0 = UNSP_REG_I(OPB); + r1 = READ16(READ16(UNSP_LPC)); + UNSP_REG(PC)++; + switch(OP0) + { + STANDARD_ALU_CASES; + default: + unimplemented_opcode(op); + break; + } + WRITEBACK_OPA; + break; + + // ALU, Direct 16 + case 3: // [imm16], r + r0 = UNSP_REG_I(OPB); + r1 = UNSP_REG_I(OPA); + switch(OP0) + { + STANDARD_ALU_CASES; + default: + unimplemented_opcode(op); + break; + } + if(OP0 != 4 && OP0 < 12) + { + WRITE16(READ16(UNSP_LPC), (UINT16)lres); + } + UNSP_REG(PC)++; + break; + + // ALU, Shifted + default: + { + UINT32 shift = (UNSP_REG_I(OPB) << 4) | m_sb; + if(shift & 0x80000) + { + shift |= 0xf00000; + } + shift >>= (OPN - 3); + m_sb = shift & 0x0f; + r1 = (shift >> 4) & 0x0000ffff; + + switch(OP0) + { + case 9: // load r, r asr n + unsp_update_nz(r1); + UNSP_REG_I(OPA) = r1; + break; + default: + unimplemented_opcode(op); + break; + } + break; + } + } + break; + + case 0x4d: + if(OPN == 3) + { + if(OPA == OPB) + { + WRITE16(READ16(UNSP_LPC), UNSP_REG_I(OPB)); + UNSP_REG(PC)++; + } + else + { + unimplemented_opcode(op); + } + } + else + { + unimplemented_opcode(op); + } + break; + + // ALU, Shifted + case 0x50: case 0x51: case 0x52: case 0x53: case 0x54: case 0x56: case 0x58: case 0x59: case 0x5a: case 0x5b: case 0x5c: + if(OPN & 4) + { + switch(OP0) + { + case 9: // load r, r >> imm2 + lres = ((UNSP_REG_I(OPB) << 4) | m_sb) >> (OPN - 3); + m_sb = lres & 0x0f; + unsp_update_nz((UINT16)(lres >> 4)); + UNSP_REG_I(OPA) = (UINT16)(lres >> 4); + break; + default: + unimplemented_opcode(op); + break; + } + } + else + { + UINT32 shift = ((m_sb << 16) | UNSP_REG_I(OPB)) << (OPN + 1); + m_sb = (shift >> 16) & 0x0f; + r0 = UNSP_REG_I(OPA); + r1 = shift & 0x0000ffff; + + switch(OP0) + { + case 0: // add r, r << imm2 + lres = r0 + r1; + unsp_update_nzsc(lres, r0, r1); + UNSP_REG_I(OPA) = (UINT16)lres; + break; + case 9: // load r, r << imm2 + lres = r1; + unsp_update_nz(lres); + UNSP_REG_I(OPA) = (UINT16)lres; + break; + case 10: // or r, r << imm2 + lres = r0 | r1; + unsp_update_nz(lres); + UNSP_REG_I(OPA) = (UINT16)lres; + break; + default: + unimplemented_opcode(op); + break; + } + } + break; + + // ALU, Rotated + case 0x60: case 0x61: case 0x62: case 0x63: case 0x64: case 0x66: case 0x68: case 0x69: case 0x6a: case 0x6b: case 0x6c: + if(OPN & 4) // ROR + { + lres = ((((m_sb << 16) | UNSP_REG_I(OPB)) << 4) | m_sb) >> (OPN - 3); + m_sb = lres & 0x0f; + r1 = (UINT16)(lres >> 4); + } + else + { + lres = ((((m_sb << 16) | UNSP_REG_I(OPB)) << 4) | m_sb) << (OPN + 1); + m_sb = (lres >> 20) & 0x0f; + r1 = (UINT16)(lres >> 4); + } + + switch(OP0) + { + case 9: // load r, r ror imm2 + unsp_update_nz(r1); + UNSP_REG_I(OPA) = r1; + break; + default: + unimplemented_opcode(op); + break; + } + break; + + // ALU, Direct 8 + case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x76: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: + //print("%s %s, [%02x]", alu[OP0], reg[OPA], OPIMM); + unimplemented_opcode(op); + break; + + // Call + case 0x1f: + if(OPA == 0) + { + r1 = READ16(UNSP_LPC); + UNSP_REG(PC)++; + unsp_push(UNSP_REG(PC), &UNSP_REG(SP)); + unsp_push(UNSP_REG(SR), &UNSP_REG(SP)); + UNSP_REG(PC) = r1; + UNSP_REG(SR) &= 0xffc0; + UNSP_REG(SR) |= OPIMM; + } + else + { + unimplemented_opcode(op); + } + break; + + // Far Jump + case 0x2f: case 0x3f: case 0x6f: case 0x7f: + if (OPA == 7 && OP1 == 2) + { + UNSP_REG(PC) = READ16(UNSP_LPC); + UNSP_REG(SR) &= 0xffc0; + UNSP_REG(SR) |= OPIMM; + } + break; + + // Multiply, Unsigned * Signed + case 0x0f: + if(OPN == 1 && OPA != 7) + { + lres = UNSP_REG_I(OPA) * UNSP_REG_I(OPB); + if(UNSP_REG_I(OPB) & 0x8000) + { + lres -= UNSP_REG_I(OPA) << 16; + } + UNSP_REG(R4) = lres >> 16; + UNSP_REG(R3) = (UINT16)lres; + break; + } + else + { + unimplemented_opcode(op); + } + break; + + // Multiply, Signed * Signed + case 0x4f: + if(OPN == 1 && OPA != 7) + { + lres = UNSP_REG_I(OPA) * UNSP_REG_I(OPB); + if(UNSP_REG_I(OPB) & 0x8000) + { + lres -= UNSP_REG_I(OPA) << 16; + } + if(UNSP_REG_I(OPA) & 0x8000) + { + lres -= UNSP_REG_I(OPB) << 16; + } + UNSP_REG(R4) = lres >> 16; + UNSP_REG(R3) = (UINT16)lres; + break; + } + else + { + unimplemented_opcode(op); + } + break; + + // Interrupt flags + case 0x5f: + if(OPA == 0) + { + switch(OPIMM) + { + case 0: + m_irq &= ~1; + m_fiq &= ~1; + break; + case 1: + m_irq |= 1; + m_fiq &= ~1; + break; + case 2: + m_irq &= ~1; + m_fiq |= 1; + break; + case 3: + m_irq |= 1; + m_fiq |= 1; + break; + case 8: // irq off + m_irq &= ~1; + break; + case 9: // irq on + m_irq |= 1; + break; + case 12: // fiq off + m_fiq &= ~1; + break; + case 13: // fiq on + m_fiq |= 1; + break; + case 37: // nop + break; + } + } + else + { + unimplemented_opcode(op); + } + break; + } + } + + m_icount -= 5; + m_icount = MAX(m_icount, 0); + } +} + + +/*****************************************************************************/ + +void unsp_device::execute_set_input(int irqline, int state) +{ + UINT16 irq_vector = 0; + + m_sirq &= ~(1 << irqline); + + if(!state) + { + logerror("clearing irq %d (%04x, %04x)\n", irqline, m_sirq, m_curirq); + return; + } + + switch (irqline) + { + case UNSP_IRQ0_LINE: + case UNSP_IRQ1_LINE: + case UNSP_IRQ2_LINE: + case UNSP_IRQ3_LINE: + case UNSP_IRQ4_LINE: + case UNSP_IRQ5_LINE: + case UNSP_IRQ6_LINE: + case UNSP_IRQ7_LINE: + if(m_fiq & 2) + { + // FIQ is being serviced, ignore this IRQ trigger. + m_sirq |= state << irqline; + return; + } + if(m_irq != 1) + { + // IRQ is disabled, ignore this IRQ trigger. + m_sirq |= state << irqline; + return; + } + m_irq |= 2; + m_curirq |= (1 << irqline); + logerror("taking irq %d (%04x, %04x)\n", irqline, m_sirq, m_curirq); + irq_vector = 0xfff8 + (irqline - UNSP_IRQ0_LINE); + break; + case UNSP_FIQ_LINE: + if(m_fiq != 1) + { + // FIQ is disabled, ignore this FIQ trigger. + m_sirq |= state << irqline; + return; + } + m_fiq |= 2; + m_curirq |= (1 << irqline); + logerror("taking fiq %d (%04x, %04x)\n", irqline, m_sirq, m_curirq); + irq_vector = 0xfff6; + break; + case UNSP_BRK_LINE: + break; + } + + m_saved_sb = m_sb; + unsp_push(UNSP_REG(PC), &UNSP_REG(SP)); + unsp_push(UNSP_REG(SR), &UNSP_REG(SP)); + UNSP_REG(PC) = READ16(irq_vector); + UNSP_REG(SR) = 0; +} |