diff options
Diffstat (limited to 'src/devices/cpu/i960/i960.cpp')
-rw-r--r-- | src/devices/cpu/i960/i960.cpp | 282 |
1 files changed, 171 insertions, 111 deletions
diff --git a/src/devices/cpu/i960/i960.cpp b/src/devices/cpu/i960/i960.cpp index fe6d4dc9534..738037e60b5 100644 --- a/src/devices/cpu/i960/i960.cpp +++ b/src/devices/cpu/i960/i960.cpp @@ -3,11 +3,10 @@ #include "emu.h" #include "i960.h" #include "i960dis.h" -#include "debugger.h" #ifdef _MSC_VER /* logb prototype is different for MS Visual C */ -#include <float.h> +#include <cfloat> #define logb _logb #endif @@ -17,10 +16,16 @@ DEFINE_DEVICE_TYPE(I960, i960_cpu_device, "i960kb", "Intel i960KB") i960_cpu_device::i960_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : cpu_device(mconfig, I960, tag, owner, clock) - , m_program_config("program", ENDIANNESS_LITTLE, 32, 32, 0) - , m_rcache_pos(0), m_SAT(0), m_PRCB(0), m_PC(0), m_AC(0), m_IP(0), m_PIP(0), m_ICR(0), m_bursting(0), m_immediate_irq(0) - , m_immediate_vector(0), m_immediate_pri(0), m_program(nullptr), m_cache(nullptr), m_icount(0) + , m_stalled(false), m_program_config("program", ENDIANNESS_LITTLE, 32, 32, 0) + , m_rcache_pos(0), m_SAT(0), m_PRCB(0), m_PC(0), m_AC(0), m_IP(0), m_PIP(0), m_ICR(0), m_immediate_irq(0) + , m_immediate_vector(0), m_immediate_pri(0), m_icount(0) { + std::fill(std::begin(m_r), std::end(m_r), 0); + std::fill(std::begin(m_rcache_frame_addr), std::end(m_rcache_frame_addr), 0); + std::fill(std::begin(m_fp), std::end(m_fp), 0); + + for (int i = 0; i <I960_RCACHE_SIZE; i++) + std::fill(std::begin(m_rcache[i]), std::end(m_rcache[i]), 0); } @@ -35,31 +40,56 @@ device_memory_interface::space_config_vector i960_cpu_device::memory_space_confi uint32_t i960_cpu_device::i960_read_dword_unaligned(uint32_t address) { if (!DWORD_ALIGNED(address)) - return m_program->read_byte(address) | m_program->read_byte(address+1)<<8 | m_program->read_byte(address+2)<<16 | m_program->read_byte(address+3)<<24; + return m_program.read_byte(address) | m_program.read_byte(address+1)<<8 | m_program.read_byte(address+2)<<16 | m_program.read_byte(address+3)<<24; else - return m_program->read_dword(address); + return m_program.read_dword(address); +} + +std::pair<uint32_t, uint16_t> i960_cpu_device::i960_read_dword_unaligned_flags(uint32_t address) +{ + if (!DWORD_ALIGNED(address)) { + auto v = m_program.read_byte_flags(address); + return std::pair<uint32_t, uint16_t>(v.first | m_program.read_byte(address+1)<<8 | m_program.read_byte(address+2)<<16 | m_program.read_byte(address+3)<<24, v.second); + } else + return m_program.read_dword_flags(address); } uint16_t i960_cpu_device::i960_read_word_unaligned(uint32_t address) { if (!WORD_ALIGNED(address)) - return m_program->read_byte(address) | m_program->read_byte(address+1)<<8; + return m_program.read_byte(address) | m_program.read_byte(address+1)<<8; else - return m_program->read_word(address); + return m_program.read_word(address); } void i960_cpu_device::i960_write_dword_unaligned(uint32_t address, uint32_t data) { if (!DWORD_ALIGNED(address)) { - m_program->write_byte(address, data & 0xff); - m_program->write_byte(address+1, (data>>8)&0xff); - m_program->write_byte(address+2, (data>>16)&0xff); - m_program->write_byte(address+3, (data>>24)&0xff); + m_program.write_byte(address, data & 0xff); + m_program.write_byte(address+1, (data>>8)&0xff); + m_program.write_byte(address+2, (data>>16)&0xff); + m_program.write_byte(address+3, (data>>24)&0xff); } else { - m_program->write_dword(address, data); + m_program.write_dword(address, data); + } +} + +uint16_t i960_cpu_device::i960_write_dword_unaligned_flags(uint32_t address, uint32_t data) +{ + if (!DWORD_ALIGNED(address)) + { + uint16_t flags = m_program.write_byte_flags(address, data & 0xff); + m_program.write_byte(address+1, (data>>8)&0xff); + m_program.write_byte(address+2, (data>>16)&0xff); + m_program.write_byte(address+3, (data>>24)&0xff); + return flags; + } + else + { + return m_program.write_dword_flags(address, data); } } @@ -67,24 +97,50 @@ void i960_cpu_device::i960_write_word_unaligned(uint32_t address, uint16_t data) { if (!WORD_ALIGNED(address)) { - m_program->write_byte(address, data & 0xff); - m_program->write_byte(address+1, (data>>8)&0xff); + m_program.write_byte(address, data & 0xff); + m_program.write_byte(address+1, (data>>8)&0xff); } else { - m_program->write_word(address, data); + m_program.write_word(address, data); } } void i960_cpu_device::send_iac(uint32_t adr) { uint32_t iac[4]; - iac[0] = m_program->read_dword(adr); - iac[1] = m_program->read_dword(adr+4); - iac[2] = m_program->read_dword(adr+8); - iac[3] = m_program->read_dword(adr+12); + iac[0] = m_program.read_dword(adr); + iac[1] = m_program.read_dword(adr+4); + iac[2] = m_program.read_dword(adr+8); + iac[3] = m_program.read_dword(adr+12); switch(iac[0]>>24) { + case 0x40: // generate irq + logerror("I960: %x: IAC %08x %08x %08x %08x (generate IRQ)\n", m_PIP, iac[0], iac[1], iac[2], iac[3]); + break; + case 0x41: // test for pending interrupts + logerror("I960: %x: IAC %08x %08x %08x %08x (test for pending interrupts)\n", m_PIP, iac[0], iac[1], iac[2], iac[3]); + // check_irqs() seems to take care of this though it may not be entirely accurate + check_irqs(); + break; + case 0x80: // store SAT & PRCB in memory + m_program.write_dword(iac[1], m_SAT); + m_program.write_dword(iac[1]+4, m_PRCB); + break; + case 0x89: // invalidate internal instruction cache + logerror("I960: %x: IAC %08x %08x %08x %08x (invalidate internal instruction cache)\n", m_PIP, iac[0], iac[1], iac[2], iac[3]); + // we do not emulate the instruction cache, so this is safe to ignore + break; + case 0x8f: // enable/disable breakpoints + logerror("I960: %x: IAC %08x %08x %08x %08x (enable/disable breakpoints)\n", m_PIP, iac[0], iac[1], iac[2], iac[3]); + // processor breakpoints are not emulated, safe to ignore + break; + case 0x91: // stop processor + logerror("I960: %x: IAC %08x %08x %08x %08x (stop processor)\n", m_PIP, iac[0], iac[1], iac[2], iac[3]); + break; + case 0x92: // continue initialization + logerror("I960: %x: IAC %08x %08x %08x %08x (continue initialization)\n", m_PIP, iac[0], iac[1], iac[2], iac[3]); + break; case 0x93: // reinit m_SAT = iac[1]; m_PRCB = iac[2]; @@ -116,7 +172,7 @@ uint32_t i960_cpu_device::get_ea(uint32_t opcode) case 0x5: // address of this instruction + the offset dword + 8 // which in reality is "address of next instruction + the offset dword" - ret = m_cache->read_dword(m_IP); + ret = m_cache.read_dword(m_IP); m_IP += 4; ret += m_IP; return ret; @@ -125,22 +181,22 @@ uint32_t i960_cpu_device::get_ea(uint32_t opcode) return m_r[abase] + (m_r[index] << scale); case 0xc: - ret = m_cache->read_dword(m_IP); + ret = m_cache.read_dword(m_IP); m_IP += 4; return ret; case 0xd: - ret = m_cache->read_dword(m_IP) + m_r[abase]; + ret = m_cache.read_dword(m_IP) + m_r[abase]; m_IP += 4; return ret; case 0xe: - ret = m_cache->read_dword(m_IP) + (m_r[index] << scale); + ret = m_cache.read_dword(m_IP) + (m_r[index] << scale); m_IP += 4; return ret; case 0xf: - ret = m_cache->read_dword(m_IP) + m_r[abase] + (m_r[index] << scale); + ret = m_cache.read_dword(m_IP) + m_r[abase] + (m_r[index] << scale); m_IP += 4; return ret; @@ -301,20 +357,12 @@ uint32_t i960_cpu_device::get_2_ci(uint32_t opcode) uint32_t i960_cpu_device::get_disp(uint32_t opcode) { - uint32_t disp; - disp = opcode & 0xffffff; - if(disp & 0x00800000) - disp |= 0xff000000; - return disp-4; + return util::sext(opcode, 24) - 4; } uint32_t i960_cpu_device::get_disp_s(uint32_t opcode) { - uint32_t disp; - disp = opcode & 0x1fff; - if(disp & 0x00001000) - disp |= 0xffffe000; - return disp-4; + return util::sext(opcode, 13) - 4; } void i960_cpu_device::cmp_s(int32_t v1, int32_t v2) @@ -403,12 +451,12 @@ void i960_cpu_device::test(uint32_t opcode, int mask) // interrupt dispatch void i960_cpu_device::take_interrupt(int vector, int lvl) { - int int_tab = m_program->read_dword(m_PRCB+20); // interrupt table - int int_SP = m_program->read_dword(m_PRCB+24); // interrupt stack + int int_tab = m_program.read_dword(m_PRCB+20); // interrupt table + int int_SP = m_program.read_dword(m_PRCB+24); // interrupt stack int SP; uint32_t IRQV; - IRQV = m_program->read_dword(int_tab + 36 + (vector-8)*4); + IRQV = m_program.read_dword(int_tab + 36 + (vector-8)*4); // start the process if(!(m_PC & 0x2000)) // if this is a nested interrupt, don't re-get int_SP @@ -421,15 +469,15 @@ void i960_cpu_device::take_interrupt(int vector, int lvl) } SP = (SP + 63) & ~63; - SP += 128; // emulate ElSemi's core, this fixes the crash in sonic the fighters + SP += 64; // add padding to prevent buffer underflow when saving processor state do_call(IRQV, 7, SP); // save the processor state - m_program->write_dword(m_r[I960_FP]-16, m_PC); - m_program->write_dword(m_r[I960_FP]-12, m_AC); + m_program.write_dword(m_r[I960_FP]-16, m_PC); + m_program.write_dword(m_r[I960_FP]-12, m_AC); // store the vector - m_program->write_dword(m_r[I960_FP]-8, vector-8); + m_program.write_dword(m_r[I960_FP]-8, vector-8); m_PC &= ~0x1f00; // clear priority, state, trace-fault pending, and trace enable m_PC |= (lvl<<16); // set CPU level to current IRQ level @@ -438,14 +486,14 @@ void i960_cpu_device::take_interrupt(int vector, int lvl) void i960_cpu_device::check_irqs() { - int int_tab = m_program->read_dword(m_PRCB+20); // interrupt table + int int_tab = m_program.read_dword(m_PRCB+20); // interrupt table int cpu_pri = (m_PC>>16)&0x1f; int pending_pri; int lvl, irq, take = -1; int vword; static const uint32_t lvlmask[4] = { 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; - pending_pri = m_program->read_dword(int_tab); // read pending priorities + pending_pri = m_program.read_dword(int_tab); // read pending priorities if ((m_immediate_irq) && ((cpu_pri < m_immediate_pri) || (m_immediate_pri == 31))) { @@ -463,14 +511,14 @@ void i960_cpu_device::check_irqs() wordl = (lvl % 4) * 8; wordh = (wordl + 8) - 1; - vword = m_program->read_dword(int_tab + word); + vword = m_program.read_dword(int_tab + word); // take the first vector we find for this level for (irq = wordh; irq >= wordl; irq--) { if(vword & (1 << irq)) { // clear pending bit vword &= ~(1 << irq); - m_program->write_dword(int_tab + word, vword); + m_program.write_dword(int_tab + word, vword); take = irq; break; } @@ -482,14 +530,14 @@ void i960_cpu_device::check_irqs() // try to recover... pending_pri &= ~(1 << lvl); - m_program->write_dword(int_tab, pending_pri); + m_program.write_dword(int_tab, pending_pri); return; } // if no vectors are waiting for this level, clear the level bit if(!(vword & lvlmask[lvl % 4])) { pending_pri &= ~(1 << lvl); - m_program->write_dword(int_tab, pending_pri); + m_program.write_dword(int_tab, pending_pri); } take += ((lvl/4) * 32); @@ -518,7 +566,7 @@ void i960_cpu_device::do_call(uint32_t adr, int type, uint32_t stack) // flush the current register set to the current frame FP = m_r[I960_FP] & ~0x3f; for (i = 0; i < 16; i++) { - m_program->write_dword(FP + (i*4), m_r[i]); + m_program.write_dword(FP + (i*4), m_r[i]); } } else // a cache entry is available, use it @@ -557,7 +605,7 @@ void i960_cpu_device::do_ret_0() { int i; for(i=0; i<0x10; i++) - m_r[i] = m_program->read_dword(m_r[I960_FP]+4*i); + m_r[i] = m_program.read_dword(m_r[I960_FP]+4*i); if (m_rcache_pos < 0) { @@ -583,8 +631,8 @@ void i960_cpu_device::do_ret() break; case 7: - x = m_program->read_dword(m_r[I960_FP]-16); - y = m_program->read_dword(m_r[I960_FP]-12); + x = m_program.read_dword(m_r[I960_FP]-16); + y = m_program.read_dword(m_r[I960_FP]-12); do_ret_0(); m_AC = y; // #### test supervisor @@ -1062,14 +1110,16 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount--; t1 = get_1_ri(opcode); t2 = get_2_ri(opcode); - set_ri(opcode, t2>>t1); + set_ri(opcode, t1 >= 32 ? 0 : t2>>t1); break; case 0xa: // shrdi m_icount--; t1 = get_1_ri(opcode); t2 = get_2_ri(opcode); - if(((int32_t)t2) < 0) { + if(t1 >= 32) + set_ri(opcode, 0); + else if(((int32_t)t2) < 0) { if(t2 & ((1<<t1)-1)) set_ri(opcode, (((int32_t)t2)>>t1)+1); else @@ -1082,21 +1132,24 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount--; t1 = get_1_ri(opcode); t2 = get_2_ri(opcode); - set_ri(opcode, ((int32_t)t2)>>t1); + if(t1 >= 32) + set_ri(opcode, (int32_t)t2 < 0 ? -1 : 0); + else + set_ri(opcode, ((int32_t)t2)>>t1); break; case 0xc: // shlo m_icount--; t1 = get_1_ri(opcode); t2 = get_2_ri(opcode); - set_ri(opcode, t2<<t1); + set_ri(opcode, t1 >= 32 ? 0 : t2<<t1); break; case 0xd: // rotate m_icount--; t1 = get_1_ri(opcode) & 0x1f; t2 = get_2_ri(opcode); - set_ri(opcode, (t2<<t1)|(t2>>(32-t1))); + set_ri(opcode, rotl_32(t2, t1)); break; case 0xe: // shli @@ -1104,7 +1157,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount--; t1 = get_1_ri(opcode); t2 = get_2_ri(opcode); - set_ri(opcode, t2<<t1); + set_ri(opcode, (t2 & 0x80000000) | (t1 >= 32 ? 0 : (t2<<t1) & 0x7fffffff)); // sign is preserved break; default: @@ -1322,9 +1375,9 @@ void i960_cpu_device::execute_op(uint32_t opcode) t2 = get_2_ri(opcode); // interrupt control register if(t1 == 0xff000004) - m_ICR = m_program->read_dword(t2); + m_ICR = m_program.read_dword(t2); else - m_program->write_dword(t1, m_program->read_dword(t2)); + m_program.write_dword(t1, m_program.read_dword(t2)); m_AC = (m_AC & ~7) | 2; break; @@ -1335,10 +1388,10 @@ void i960_cpu_device::execute_op(uint32_t opcode) if(t1 == 0xff000010) send_iac(t2); else { - m_program->write_dword(t1, m_program->read_dword(t2)); - m_program->write_dword(t1+4, m_program->read_dword(t2+4)); - m_program->write_dword(t1+8, m_program->read_dword(t2+8)); - m_program->write_dword(t1+12, m_program->read_dword(t2+12)); + m_program.write_dword(t1, m_program.read_dword(t2)); + m_program.write_dword(t1+4, m_program.read_dword(t2+4)); + m_program.write_dword(t1+8, m_program.read_dword(t2+8)); + m_program.write_dword(t1+12, m_program.read_dword(t2+12)); } m_AC = (m_AC & ~7) | 2; break; @@ -1398,6 +1451,23 @@ void i960_cpu_device::execute_op(uint32_t opcode) } break; + case 0x4: // dmovt + /* + The dmovt instruction moves a 32-bit word from one register to another + and tests the least-significant byte of the operand to determine if it is a + valid ASCII-coded decimal digit (001100002 through 001110012, + corresponding to the decimal digits 0 through 9). For valid digits, the + condition code (CC) is set to 000; otherwise the condition code is set to + 010. + */ + m_icount -= 7; + t1 = get_1_ri(opcode); + set_ri(opcode, t1); + m_AC &= 0xfff8; + if ((t1 & 0xff) < 0x30 || (t1 & 0xff) > 0x39) + m_AC |= 2; + break; + case 0x5: // modac m_icount -= 10; t1 = get_1_ri(opcode); @@ -1430,8 +1500,8 @@ void i960_cpu_device::execute_op(uint32_t opcode) switch((opcode >> 7) & 0xf) { case 0x0: // calls t1 = get_1_ri(opcode); - t2 = m_program->read_dword(m_SAT + 152); // get pointer to system procedure table - t2 = m_program->read_dword(t2 + 48 + (t1 * 4)); + t2 = m_program.read_dword(m_SAT + 152); // get pointer to system procedure table + t2 = m_program.read_dword(t2 + 48 + (t1 * 4)); if ((t2 & 3) != 0) { fatalerror("I960: system calls that jump into supervisor mode aren't yet supported\n"); @@ -1450,7 +1520,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) for (i = 0; i < 0x10; i++) { - m_program->write_dword(m_rcache_frame_addr[t1] + (i * sizeof(uint32_t)), m_rcache[t1][i]); + m_program.write_dword(m_rcache_frame_addr[t1] + (i * sizeof(uint32_t)), m_rcache[t1][i]); } } m_rcache_pos = 0; @@ -1468,7 +1538,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) t1 = get_1_ri(opcode); t2 = get_2_ri(opcode); - set_ri64(opcode, (int64_t)t1 * (int64_t)t2); + set_ri64(opcode, mulu_32x32(t1, t2)); break; case 0x1: // ediv @@ -1908,7 +1978,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) case 0x80: { // ldob m_icount -= 4; - u8 v = m_program->read_byte(get_ea(opcode)); + u8 v = m_program.read_byte(get_ea(opcode)); if(!m_stalled) m_r[(opcode>>19)&0x1f] = v; break; @@ -1916,7 +1986,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) case 0x82: // stob m_icount -= 2; - m_program->write_byte(get_ea(opcode), m_r[(opcode>>19)&0x1f]); + m_program.write_byte(get_ea(opcode), m_r[(opcode>>19)&0x1f]); break; case 0x84: // bx @@ -1972,16 +2042,15 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount -= 5; t1 = get_ea(opcode); t2 = (opcode>>19)&0x1e; - m_bursting = 1; for(i=0; i<2; i++) { - u32 v = i960_read_dword_unaligned(t1); + auto pack = i960_read_dword_unaligned_flags(t1); if(m_stalled) { burst_stall_save(t1,t2,i,2,false); return; } - m_r[t2+i] = v; - if(m_bursting) + m_r[t2+i] = pack.first; + if(pack.second & BURST) t1 += 4; } break; @@ -1992,15 +2061,14 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount -= 3; t1 = get_ea(opcode); t2 = (opcode>>19)&0x1e; - m_bursting = 1; for(i=0; i<2; i++) { - i960_write_dword_unaligned(t1, m_r[t2+i]); + auto flags = i960_write_dword_unaligned_flags(t1, m_r[t2+i]); if(m_stalled) { burst_stall_save(t1,t2,i,2,true); return; } - if(m_bursting) + if(flags & BURST) t1 += 4; } break; @@ -2011,16 +2079,15 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount -= 6; t1 = get_ea(opcode); t2 = (opcode>>19)&0x1c; - m_bursting = 1; for(i=0; i<3; i++) { - u32 v = i960_read_dword_unaligned(t1); + auto pack = i960_read_dword_unaligned_flags(t1); if(m_stalled) { burst_stall_save(t1,t2,i,3,false); return; } - m_r[t2+i] = v; - if(m_bursting) + m_r[t2+i] = pack.first; + if(pack.second & BURST) t1 += 4; } break; @@ -2031,15 +2098,14 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount -= 4; t1 = get_ea(opcode); t2 = (opcode>>19)&0x1c; - m_bursting = 1; for(i=0; i<3; i++) { - i960_write_dword_unaligned(t1, m_r[t2+i]); + auto flags = i960_write_dword_unaligned_flags(t1, m_r[t2+i]); if(m_stalled) { burst_stall_save(t1,t2,i,3,true); return; } - if(m_bursting) + if(flags & BURST) t1 += 4; } break; @@ -2050,16 +2116,15 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount -= 7; t1 = get_ea(opcode); t2 = (opcode>>19)&0x1c; - m_bursting = 1; for(i=0; i<4; i++) { - u32 v = i960_read_dword_unaligned(t1); + auto pack = i960_read_dword_unaligned_flags(t1); if(m_stalled) { burst_stall_save(t1,t2,i,4,false); return; } - m_r[t2+i] = v; - if(m_bursting) + m_r[t2+i] = pack.first; + if(pack.second & BURST) t1 += 4; } break; @@ -2070,15 +2135,14 @@ void i960_cpu_device::execute_op(uint32_t opcode) m_icount -= 5; t1 = get_ea(opcode); t2 = (opcode>>19)&0x1c; - m_bursting = 1; for(i=0; i<4; i++) { - i960_write_dword_unaligned(t1, m_r[t2+i]); + auto flags = i960_write_dword_unaligned_flags(t1, m_r[t2+i]); if(m_stalled) { burst_stall_save(t1,t2,i,4,true); return; } - if(m_bursting) + if(flags & BURST) t1 += 4; } break; @@ -2086,7 +2150,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) case 0xc0: { // ldib m_icount -= 4; - s8 v = m_program->read_byte(get_ea(opcode)); + s8 v = m_program.read_byte(get_ea(opcode)); if(!m_stalled) m_r[(opcode>>19)&0x1f] = v; break; @@ -2094,7 +2158,7 @@ void i960_cpu_device::execute_op(uint32_t opcode) case 0xc2: // stib m_icount -= 2; - m_program->write_byte(get_ea(opcode), m_r[(opcode>>19)&0x1f]); + m_program.write_byte(get_ea(opcode), m_r[(opcode>>19)&0x1f]); break; case 0xc8: { // ldis @@ -2128,9 +2192,7 @@ void i960_cpu_device::execute_run() m_PIP = m_IP; debugger_instruction_hook(m_IP); - m_bursting = 0; - - opcode = m_cache->read_dword(m_IP); + opcode = m_cache.read_dword(m_IP); m_IP += 4; m_stalled = false; @@ -2144,7 +2206,7 @@ void i960_cpu_device::execute_run() void i960_cpu_device::execute_set_input(int irqline, int state) { - int int_tab = m_program->read_dword(m_PRCB+20); // interrupt table + int int_tab = m_program.read_dword(m_PRCB+20); // interrupt table int cpu_pri = (m_PC>>16)&0x1f; int vector =0; int priority; @@ -2193,28 +2255,28 @@ void i960_cpu_device::execute_set_input(int irqline, int state) else { // store the interrupt in the "pending" table - pend = m_program->read_dword(int_tab); + pend = m_program.read_dword(int_tab); pend |= (1 << priority); - m_program->write_dword(int_tab, pend); + m_program.write_dword(int_tab, pend); // now bitfield-ize the vector word = ((vector / 32) * 4) + 4; wordofs = vector % 32; - pend = m_program->read_dword(int_tab + word); + pend = m_program.read_dword(int_tab + word); pend |= (1 << wordofs); - m_program->write_dword(int_tab + word, pend); + m_program.write_dword(int_tab + word, pend); } // and ack it to the core now that it's queued - standard_irq_callback(irqline); + standard_irq_callback(irqline, m_IP); } } void i960_cpu_device::device_start() { - m_program = &space(AS_PROGRAM); - m_cache = m_program->cache<2, 0, ENDIANNESS_LITTLE>(); + space(AS_PROGRAM).cache(m_cache); + space(AS_PROGRAM).specific(m_program); save_item(NAME(m_IP)); save_item(NAME(m_PIP)); @@ -2231,7 +2293,6 @@ void i960_cpu_device::device_start() save_item(NAME(m_immediate_irq)); save_item(NAME(m_immediate_vector)); save_item(NAME(m_immediate_pri)); - save_item(NAME(m_bursting)); save_item(NAME(m_stalled)); save_item(NAME(m_stall_state.index)); save_item(NAME(m_stall_state.size)); @@ -2309,19 +2370,18 @@ void i960_cpu_device::state_string_export(const device_state_entry &entry, std:: void i960_cpu_device::device_reset() { - m_SAT = m_program->read_dword(0); - m_PRCB = m_program->read_dword(4); - m_IP = m_program->read_dword(12); + m_SAT = m_program.read_dword(0); + m_PRCB = m_program.read_dword(4); + m_IP = m_program.read_dword(12); m_PC = 0x001f2002; m_AC = 0; m_ICR = 0xff000000; - m_bursting = 0; m_immediate_irq = 0; memset(m_r, 0, sizeof(m_r)); memset(m_rcache, 0, sizeof(m_rcache)); - m_r[I960_FP] = m_program->read_dword(m_PRCB+24); + m_r[I960_FP] = m_program.read_dword(m_PRCB+24); m_r[I960_SP] = m_r[I960_FP] + 64; m_rcache_pos = 0; } |