Commit b319feb72d1aba5141f86bec46942ee34e53897e
1 parent
0fd3ca30
sh4: Add R2D-PLUS FPGA support.
This adds trivial support for the R2D-PLUS FPGA, mostly just for the versioning information that the kernel uses for IRL mappings, in addition to handling the heartbeat and poweroff writes. Signed-off-by: Paul Mundt <lethal@linux-sh.org> Signed-off-by: Aurelien Jarno <aurelien@aurel32.net> git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5134 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
1 changed file
with
111 additions
and
0 deletions
hw/r2d.c
| ... | ... | @@ -2,6 +2,7 @@ |
| 2 | 2 | * Renesas SH7751R R2D-PLUS emulation |
| 3 | 3 | * |
| 4 | 4 | * Copyright (c) 2007 Magnus Damm |
| 5 | + * Copyright (c) 2008 Paul Mundt | |
| 5 | 6 | * |
| 6 | 7 | * Permission is hereby granted, free of charge, to any person obtaining a copy |
| 7 | 8 | * of this software and associated documentation files (the "Software"), to deal |
| ... | ... | @@ -26,10 +27,119 @@ |
| 26 | 27 | #include "sh.h" |
| 27 | 28 | #include "sysemu.h" |
| 28 | 29 | #include "boards.h" |
| 30 | +#include "assert.h" | |
| 29 | 31 | |
| 30 | 32 | #define SDRAM_BASE 0x0c000000 /* Physical location of SDRAM: Area 3 */ |
| 31 | 33 | #define SDRAM_SIZE 0x04000000 |
| 32 | 34 | |
| 35 | +#define PA_POWOFF 0x30 | |
| 36 | +#define PA_VERREG 0x32 | |
| 37 | +#define PA_OUTPORT 0x36 | |
| 38 | + | |
| 39 | +typedef struct { | |
| 40 | + target_phys_addr_t base; | |
| 41 | + | |
| 42 | + uint16_t bcr; | |
| 43 | + uint16_t irlmon; | |
| 44 | + uint16_t cfctl; | |
| 45 | + uint16_t cfpow; | |
| 46 | + uint16_t dispctl; | |
| 47 | + uint16_t sdmpow; | |
| 48 | + uint16_t rtcce; | |
| 49 | + uint16_t pcicd; | |
| 50 | + uint16_t voyagerrts; | |
| 51 | + uint16_t cfrst; | |
| 52 | + uint16_t admrts; | |
| 53 | + uint16_t extrst; | |
| 54 | + uint16_t cfcdintclr; | |
| 55 | + uint16_t keyctlclr; | |
| 56 | + uint16_t pad0; | |
| 57 | + uint16_t pad1; | |
| 58 | + uint16_t powoff; | |
| 59 | + uint16_t verreg; | |
| 60 | + uint16_t inport; | |
| 61 | + uint16_t outport; | |
| 62 | + uint16_t bverreg; | |
| 63 | +} r2d_fpga_t; | |
| 64 | + | |
| 65 | +static uint32_t r2d_fpga_read(void *opaque, target_phys_addr_t addr) | |
| 66 | +{ | |
| 67 | + r2d_fpga_t *s = opaque; | |
| 68 | + | |
| 69 | + addr -= s->base; | |
| 70 | + | |
| 71 | + switch (addr) { | |
| 72 | + case PA_OUTPORT: | |
| 73 | + return s->outport; | |
| 74 | + case PA_POWOFF: | |
| 75 | + return s->powoff; | |
| 76 | + case PA_VERREG: | |
| 77 | + return 0x10; | |
| 78 | + } | |
| 79 | + | |
| 80 | + return 0; | |
| 81 | +} | |
| 82 | + | |
| 83 | +static void | |
| 84 | +r2d_fpga_write(void *opaque, target_phys_addr_t addr, uint32_t value) | |
| 85 | +{ | |
| 86 | + r2d_fpga_t *s = opaque; | |
| 87 | + | |
| 88 | + addr -= s->base; | |
| 89 | + | |
| 90 | + switch (addr) { | |
| 91 | + case PA_OUTPORT: | |
| 92 | + s->outport = value; | |
| 93 | + break; | |
| 94 | + case PA_POWOFF: | |
| 95 | + s->powoff = value; | |
| 96 | + break; | |
| 97 | + case PA_VERREG: | |
| 98 | + /* Discard writes */ | |
| 99 | + break; | |
| 100 | + } | |
| 101 | +} | |
| 102 | + | |
| 103 | +static uint32_t invalid_read(void *opaque, target_phys_addr_t addr) | |
| 104 | +{ | |
| 105 | + assert(0); | |
| 106 | + | |
| 107 | + return 0; | |
| 108 | +} | |
| 109 | + | |
| 110 | +static void invalid_write(void *opaque, target_phys_addr_t addr, | |
| 111 | + uint32_t mem_value) | |
| 112 | +{ | |
| 113 | + assert(0); | |
| 114 | +} | |
| 115 | + | |
| 116 | +static CPUReadMemoryFunc *r2d_fpga_readfn[] = { | |
| 117 | + r2d_fpga_read, | |
| 118 | + r2d_fpga_read, | |
| 119 | + invalid_read, | |
| 120 | +}; | |
| 121 | + | |
| 122 | +static CPUWriteMemoryFunc *r2d_fpga_writefn[] = { | |
| 123 | + r2d_fpga_write, | |
| 124 | + r2d_fpga_write, | |
| 125 | + invalid_write, | |
| 126 | +}; | |
| 127 | + | |
| 128 | +static void r2d_fpga_init(target_phys_addr_t base) | |
| 129 | +{ | |
| 130 | + int iomemtype; | |
| 131 | + r2d_fpga_t *s; | |
| 132 | + | |
| 133 | + s = qemu_mallocz(sizeof(r2d_fpga_t)); | |
| 134 | + if (!s) | |
| 135 | + return; | |
| 136 | + | |
| 137 | + s->base = base; | |
| 138 | + iomemtype = cpu_register_io_memory(0, r2d_fpga_readfn, | |
| 139 | + r2d_fpga_writefn, s); | |
| 140 | + cpu_register_physical_memory(base, 0x40, iomemtype); | |
| 141 | +} | |
| 142 | + | |
| 33 | 143 | static void r2d_init(ram_addr_t ram_size, int vga_ram_size, |
| 34 | 144 | const char *boot_device, DisplayState * ds, |
| 35 | 145 | const char *kernel_filename, const char *kernel_cmdline, |
| ... | ... | @@ -50,6 +160,7 @@ static void r2d_init(ram_addr_t ram_size, int vga_ram_size, |
| 50 | 160 | /* Allocate memory space */ |
| 51 | 161 | cpu_register_physical_memory(SDRAM_BASE, SDRAM_SIZE, 0); |
| 52 | 162 | /* Register peripherals */ |
| 163 | + r2d_fpga_init(0x04000000); | |
| 53 | 164 | s = sh7750_init(env); |
| 54 | 165 | /* Todo: register on board registers */ |
| 55 | 166 | { | ... | ... |