From: Jesse Taube Date: Thu, 12 Jan 2023 04:52:48 +0000 (-0500) Subject: works with less than base ISA qemu-system-riscv32 -M virt -bios none -kernel output... X-Git-Url: https://repo.jachan.dev/qemu.git/commitdiff_plain/228744bcba2620507e330ce7a30bf4f9f38d9c54 works with less than base ISA qemu-system-riscv32 -M virt -bios none -kernel output/images/Image -nographic -cpu rv32,mmu=off,m=off,d=off,f=off,s=off,u=off,h=off,pmp=off,Zawrs=off,c=off,a=off,Zifencei=off,Zicsr=off --- diff --git a/hw/riscv/boot.c b/hw/riscv/boot.c index ebd351c840..1aa6d7c17b 100644 --- a/hw/riscv/boot.c +++ b/hw/riscv/boot.c @@ -299,11 +299,12 @@ void riscv_setup_rom_reset_vec(MachineState *machine, RISCVHartArrayState *harts start_addr_hi32 = start_addr >> 32; fdt_load_addr_hi32 = fdt_load_addr >> 32; } + /* reset vector */ uint32_t reset_vec[10] = { 0x00000297, /* 1: auipc t0, %pcrel_hi(fw_dyn) */ 0x02828613, /* addi a2, t0, %pcrel_lo(1b) */ - 0xf1402573, /* csrr a0, mhartid */ + 0x00000513, /* csrr a0, mhartid */ 0, 0, 0x00028067, /* jr t0 */ diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c index 94ff2a1584..5f1e808038 100644 --- a/hw/riscv/virt.c +++ b/hw/riscv/virt.c @@ -74,6 +74,7 @@ static const MemMapEntry virt_memmap[] = { [VIRT_DEBUG] = { 0x0, 0x100 }, + [VIRT_CSR] = { 0x400, 0xc00 }, [VIRT_MROM] = { 0x1000, 0xf000 }, [VIRT_TEST] = { 0x100000, 0x1000 }, [VIRT_RTC] = { 0x101000, 0x1000 }, @@ -1339,12 +1340,52 @@ static void virt_machine_done(Notifier *notifier, void *data) } } +static void csr_mem_ops_wr(void *opaque, hwaddr addr, + uint64_t value, unsigned size) { + riscv_csr_operations ops; + uint32_t csrnums[18] = {0x300, 0xC00, 0x340, 0x305, 0x304, 0x344, + 0x341, 0x343, 0x342, 0xf11, 0x301,0xf14,0x3a0,0x3b0}; + CPURISCVState* env = &RISCV_CPU(qemu_get_cpu(0))->env; + if(((addr&0xff)/4) > 18) + return; + int csrno = csrnums[((addr&0xff)/4)]; + riscv_get_csr_ops(csrno,&ops); + if(ops.write){ + ops.write(env,csrno,value); + } else if (ops.op) { + ops.op(env,csrno,NULL,value,UINT32_MAX); + } +} +static uint64_t csr_mem_ops_rd(void *opaque, hwaddr addr, unsigned size){ + uint32_t value = 0; + riscv_csr_operations ops; + uint32_t csrnums[18] = {0x300, 0xC00, 0x340, 0x305, 0x304, 0x344, + 0x341, 0x343, 0x342, 0xf11, 0x301,0xf14,0x3a0,0x3b0}; + CPURISCVState* env = &RISCV_CPU(qemu_get_cpu(0))->env; + + if(((addr&0xff)/4) > 18) + return 0; + int csrno = csrnums[((addr&0xff)/4)]; + riscv_get_csr_ops(csrno,&ops); + if(ops.read){ + ops.read(env,csrno,&value); + } else if (ops.op) { + ops.op(env,csrno,&value,0,0); + } + return value; +} +static const MemoryRegionOps csr_mem_ops = { + .read = csr_mem_ops_rd, + .write = csr_mem_ops_wr, +}; + static void virt_machine_init(MachineState *machine) { const MemMapEntry *memmap = virt_memmap; RISCVVirtState *s = RISCV_VIRT_MACHINE(machine); MemoryRegion *system_memory = get_system_memory(); MemoryRegion *mask_rom = g_new(MemoryRegion, 1); + MemoryRegion *csr_ram = g_new(MemoryRegion, 1); char *soc_name; DeviceState *mmio_irqchip, *virtio_irqchip, *pcie_irqchip; int i, base_hartid, hart_count; @@ -1478,6 +1519,10 @@ static void virt_machine_init(MachineState *machine) /* boot rom */ memory_region_init_rom(mask_rom, NULL, "riscv_virt_board.mrom", memmap[VIRT_MROM].size, &error_fatal); + memory_region_init_io(csr_ram, NULL, &csr_mem_ops, NULL,"csr_ram", + memmap[VIRT_CSR].size); + memory_region_add_subregion(system_memory, memmap[VIRT_CSR].base, + csr_ram); memory_region_add_subregion(system_memory, memmap[VIRT_MROM].base, mask_rom); diff --git a/include/hw/riscv/virt.h b/include/hw/riscv/virt.h index b3d26135c0..10118200f8 100644 --- a/include/hw/riscv/virt.h +++ b/include/hw/riscv/virt.h @@ -60,6 +60,7 @@ struct RISCVVirtState { enum { VIRT_DEBUG, + VIRT_CSR, VIRT_MROM, VIRT_TEST, VIRT_RTC,