aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--hw/microblaze/petalogix_s3adsp1800_mmu.c4
-rw-r--r--target/microblaze/cpu.c14
-rw-r--r--target/microblaze/cpu.h9
-rw-r--r--target/microblaze/op_helper.c22
4 files changed, 34 insertions, 15 deletions
diff --git a/hw/microblaze/petalogix_s3adsp1800_mmu.c b/hw/microblaze/petalogix_s3adsp1800_mmu.c
index 5cf7b84..b9f0b0d 100644
--- a/hw/microblaze/petalogix_s3adsp1800_mmu.c
+++ b/hw/microblaze/petalogix_s3adsp1800_mmu.c
@@ -35,6 +35,7 @@
#include "sysemu/sysemu.h"
#include "hw/devices.h"
#include "hw/boards.h"
+#include "hw/misc/unimp.h"
#include "exec/address-spaces.h"
#include "hw/char/xilinx_uartlite.h"
@@ -47,6 +48,7 @@
#define MEMORY_BASEADDR 0x90000000
#define FLASH_BASEADDR 0xa0000000
+#define GPIO_BASEADDR 0x81400000
#define INTC_BASEADDR 0x81800000
#define TIMER_BASEADDR 0x83c00000
#define UARTLITE_BASEADDR 0x84000000
@@ -122,6 +124,8 @@ petalogix_s3adsp1800_init(MachineState *machine)
sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, ETHLITE_BASEADDR);
sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0, irq[ETHLITE_IRQ]);
+ create_unimplemented_device("gpio", GPIO_BASEADDR, 0x10000);
+
microblaze_load_kernel(cpu, ddr_base, ram_size,
machine->initrd_filename,
BINARY_DEVICE_TREE_FILE,
diff --git a/target/microblaze/cpu.c b/target/microblaze/cpu.c
index 9b546a2..5596cd5 100644
--- a/target/microblaze/cpu.c
+++ b/target/microblaze/cpu.c
@@ -202,7 +202,11 @@ static void mb_cpu_realizefn(DeviceState *dev, Error **errp)
(cpu->cfg.use_barrel ? PVR2_USE_BARREL_MASK : 0) |
(cpu->cfg.use_div ? PVR2_USE_DIV_MASK : 0) |
(cpu->cfg.use_msr_instr ? PVR2_USE_MSR_INSTR : 0) |
- (cpu->cfg.use_pcmp_instr ? PVR2_USE_PCMP_INSTR : 0);
+ (cpu->cfg.use_pcmp_instr ? PVR2_USE_PCMP_INSTR : 0) |
+ (cpu->cfg.dopb_bus_exception ?
+ PVR2_DOPB_BUS_EXC_MASK : 0) |
+ (cpu->cfg.iopb_bus_exception ?
+ PVR2_IOPB_BUS_EXC_MASK : 0);
env->pvr.regs[5] |= cpu->cfg.dcache_writeback ?
PVR5_DCACHE_WRITEBACK_MASK : 0;
@@ -265,6 +269,12 @@ static Property mb_properties[] = {
DEFINE_PROP_BOOL("dcache-writeback", MicroBlazeCPU, cfg.dcache_writeback,
false),
DEFINE_PROP_BOOL("endianness", MicroBlazeCPU, cfg.endi, false),
+ /* Enables bus exceptions on failed data accesses (load/stores). */
+ DEFINE_PROP_BOOL("dopb-bus-exception", MicroBlazeCPU,
+ cfg.dopb_bus_exception, false),
+ /* Enables bus exceptions on failed instruction fetches. */
+ DEFINE_PROP_BOOL("iopb-bus-exception", MicroBlazeCPU,
+ cfg.iopb_bus_exception, false),
DEFINE_PROP_STRING("version", MicroBlazeCPU, cfg.version),
DEFINE_PROP_UINT8("pvr", MicroBlazeCPU, cfg.pvr, C_PVR_FULL),
DEFINE_PROP_END_OF_LIST(),
@@ -297,7 +307,7 @@ static void mb_cpu_class_init(ObjectClass *oc, void *data)
#ifdef CONFIG_USER_ONLY
cc->handle_mmu_fault = mb_cpu_handle_mmu_fault;
#else
- cc->do_unassigned_access = mb_cpu_unassigned_access;
+ cc->do_transaction_failed = mb_cpu_transaction_failed;
cc->get_phys_page_debug = mb_cpu_get_phys_page_debug;
#endif
dc->vmsd = &vmstate_mb_cpu;
diff --git a/target/microblaze/cpu.h b/target/microblaze/cpu.h
index 3c4e0ba..792bbc9 100644
--- a/target/microblaze/cpu.h
+++ b/target/microblaze/cpu.h
@@ -308,6 +308,8 @@ struct MicroBlazeCPU {
bool use_mmu;
bool dcache_writeback;
bool endi;
+ bool dopb_bus_exception;
+ bool iopb_bus_exception;
char *version;
uint8_t pvr;
} cfg;
@@ -388,9 +390,10 @@ static inline void cpu_get_tb_cpu_state(CPUMBState *env, target_ulong *pc,
}
#if !defined(CONFIG_USER_ONLY)
-void mb_cpu_unassigned_access(CPUState *cpu, hwaddr addr,
- bool is_write, bool is_exec, int is_asi,
- unsigned size);
+void mb_cpu_transaction_failed(CPUState *cs, hwaddr physaddr, vaddr addr,
+ unsigned size, MMUAccessType access_type,
+ int mmu_idx, MemTxAttrs attrs,
+ MemTxResult response, uintptr_t retaddr);
#endif
#endif
diff --git a/target/microblaze/op_helper.c b/target/microblaze/op_helper.c
index 7cdbbcc..e23dcfd 100644
--- a/target/microblaze/op_helper.c
+++ b/target/microblaze/op_helper.c
@@ -486,26 +486,28 @@ void helper_mmu_write(CPUMBState *env, uint32_t ext, uint32_t rn, uint32_t v)
mmu_write(env, ext, rn, v);
}
-void mb_cpu_unassigned_access(CPUState *cs, hwaddr addr,
- bool is_write, bool is_exec, int is_asi,
- unsigned size)
+void mb_cpu_transaction_failed(CPUState *cs, hwaddr physaddr, vaddr addr,
+ unsigned size, MMUAccessType access_type,
+ int mmu_idx, MemTxAttrs attrs,
+ MemTxResult response, uintptr_t retaddr)
{
MicroBlazeCPU *cpu;
CPUMBState *env;
-
- qemu_log_mask(CPU_LOG_INT, "Unassigned " TARGET_FMT_plx " wr=%d exe=%d\n",
- addr, is_write ? 1 : 0, is_exec ? 1 : 0);
- if (cs == NULL) {
- return;
- }
+ qemu_log_mask(CPU_LOG_INT, "Transaction failed: vaddr 0x%" VADDR_PRIx
+ " physaddr 0x" TARGET_FMT_plx " size %d access type %s\n",
+ addr, physaddr, size,
+ access_type == MMU_INST_FETCH ? "INST_FETCH" :
+ (access_type == MMU_DATA_LOAD ? "DATA_LOAD" : "DATA_STORE"));
cpu = MICROBLAZE_CPU(cs);
env = &cpu->env;
+
+ cpu_restore_state(cs, retaddr, true);
if (!(env->sregs[SR_MSR] & MSR_EE)) {
return;
}
env->sregs[SR_EAR] = addr;
- if (is_exec) {
+ if (access_type == MMU_INST_FETCH) {
if ((env->pvr.regs[2] & PVR2_IOPB_BUS_EXC_MASK)) {
env->sregs[SR_ESR] = ESR_EC_INSN_BUS;
helper_raise_exception(env, EXCP_HW_EXCP);