summaryrefslogtreecommitdiffstatshomepage
path: root/src/devices/cpu/m68000/m68kcpu.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/devices/cpu/m68000/m68kcpu.cpp')
-rw-r--r--src/devices/cpu/m68000/m68kcpu.cpp37
1 files changed, 31 insertions, 6 deletions
diff --git a/src/devices/cpu/m68000/m68kcpu.cpp b/src/devices/cpu/m68000/m68kcpu.cpp
index f7a61d6f77a..5ccc2f43424 100644
--- a/src/devices/cpu/m68000/m68kcpu.cpp
+++ b/src/devices/cpu/m68000/m68kcpu.cpp
@@ -775,12 +775,12 @@ void m68000_base_device::m68k_cause_bus_error()
else if (CPU_TYPE_IS_010())
{
/* only the 68010 throws this unique type-1000 frame */
- m68ki_stack_frame_1000(m_ppc, sr, EXCEPTION_BUS_ERROR);
+ m68ki_stack_frame_1000(m_ppc, sr, EXCEPTION_BUS_ERROR, m_mmu_tmp_buserror_address);
}
else if (CPU_TYPE_IS_070())
{
/* only the 68070 throws this unique type-1111 frame */
- m68ki_stack_frame_1111(m_ppc, sr, EXCEPTION_BUS_ERROR);
+ m68ki_stack_frame_1111(m_ppc, sr, EXCEPTION_BUS_ERROR, m_mmu_tmp_buserror_address);
}
else if (m_mmu_tmp_buserror_address == m_ppc)
{
@@ -901,7 +901,7 @@ void m68000_base_device::execute_run()
try
{
- if (!m_pmmu_enabled)
+ if (!m_instruction_restart)
{
m_run_mode = RUN_MODE_NORMAL;
/* Read an instruction and call its handler */
@@ -959,7 +959,7 @@ void m68000_base_device::execute_run()
{
if (CPU_TYPE_IS_010())
{
- m68ki_stack_frame_1000(m_ppc, sr, EXCEPTION_BUS_ERROR);
+ m68ki_stack_frame_1000(m_ppc, sr, EXCEPTION_BUS_ERROR, m_mmu_tmp_buserror_address);
}
else
{
@@ -1029,6 +1029,8 @@ void m68000_base_device::init_cpu_common(void)
m_has_hmmu = 0;
m_pmmu_enabled = 0;
m_hmmu_enabled = 0;
+ m_emmu_enabled = 0;
+ m_instruction_restart = 0;
/* The first call to this function initializes the opcode handler jump table */
if(!emulation_initialized)
@@ -1062,6 +1064,8 @@ void m68000_base_device::init_cpu_common(void)
save_item(NAME(m_has_hmmu));
save_item(NAME(m_pmmu_enabled));
save_item(NAME(m_hmmu_enabled));
+ save_item(NAME(m_emmu_enabled));
+ save_item(NAME(m_instruction_restart));
save_item(NAME(m_mmu_crp_aptr));
save_item(NAME(m_mmu_crp_limit));
@@ -1098,6 +1102,8 @@ void m68000_base_device::device_reset()
/* Disable the PMMU/HMMU on reset, if any */
m_pmmu_enabled = 0;
m_hmmu_enabled = 0;
+ m_emmu_enabled = 0;
+ m_instruction_restart = 0;
m_mmu_tc = 0;
m_mmu_tt0 = 0;
@@ -1297,6 +1303,13 @@ void m68000_base_device::set_hmmu_enable(int enable)
m_hmmu_enabled = enable;
}
+/* set for external MMU and instruction restart */
+void m68000_base_device::set_emmu_enable(int enable)
+{
+ m_emmu_enabled = enable;
+ m_instruction_restart = m_pmmu_enabled || m_emmu_enabled;
+}
+
void m68000_base_device::set_fpu_enable(int enable)
{
m_has_fpu = enable;
@@ -1662,12 +1675,22 @@ void m68000_base_device::init32hmmu(address_space &space, address_space &ospace)
// fault_addr = address to indicate fault at
// rw = 1 for read, 0 for write
// fc = 3-bit function code of access (usually you'd just put what m68k_get_fc() returns here)
-void m68000_base_device::set_buserror_details(u32 fault_addr, u8 rw, u8 fc)
+// rerun = trigger bus error and rerun instruction after RTE, intended for external MMU use
+// do not call set_input_line(M68K_LINE_BUSERROR) when using rerun flag
+void m68000_base_device::set_buserror_details(u32 fault_addr, u8 rw, u8 fc, bool rerun)
{
+ if (m_instruction_restart && rerun) m_mmu_tmp_buserror_occurred = 1; // hack for external MMU
+
+ // save values for 68000 specific bus error
m_aerr_address = fault_addr;
m_aerr_write_mode = (rw << 4);
m_aerr_fc = fc;
- m_mmu_tmp_buserror_address = fault_addr; // Hack for x68030
+
+ // Hack for x68030 and external MMU
+ m_mmu_tmp_buserror_address = fault_addr;
+ m_mmu_tmp_buserror_rw = m_mmu_tmp_rw;
+ m_mmu_tmp_buserror_fc = m_mmu_tmp_fc;
+ m_mmu_tmp_buserror_sz = m_mmu_tmp_sz;
}
u16 m68000_base_device::get_fc()
@@ -2395,6 +2418,8 @@ void m68000_base_device::clear_all()
m_has_hmmu= 0;
m_pmmu_enabled= 0;
m_hmmu_enabled= 0;
+ m_emmu_enabled= 0;
+ m_instruction_restart= 0;
m_has_fpu= 0;
m_fpu_just_reset= 0;