|
|
1.1 ! root 1: /* ! 2: * QEMU MIPS Jazz support ! 3: * ! 4: * Copyright (c) 2007-2008 Hervé Poussineau ! 5: * ! 6: * Permission is hereby granted, free of charge, to any person obtaining a copy ! 7: * of this software and associated documentation files (the "Software"), to deal ! 8: * in the Software without restriction, including without limitation the rights ! 9: * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell ! 10: * copies of the Software, and to permit persons to whom the Software is ! 11: * furnished to do so, subject to the following conditions: ! 12: * ! 13: * The above copyright notice and this permission notice shall be included in ! 14: * all copies or substantial portions of the Software. ! 15: * ! 16: * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ! 17: * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ! 18: * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ! 19: * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ! 20: * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, ! 21: * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN ! 22: * THE SOFTWARE. ! 23: */ ! 24: ! 25: #include "hw.h" ! 26: #include "mips.h" ! 27: #include "pc.h" ! 28: #include "isa.h" ! 29: #include "fdc.h" ! 30: #include "sysemu.h" ! 31: #include "audio/audio.h" ! 32: #include "boards.h" ! 33: #include "net.h" ! 34: #include "scsi.h" ! 35: ! 36: #ifdef TARGET_WORDS_BIGENDIAN ! 37: #define BIOS_FILENAME "mips_bios.bin" ! 38: #else ! 39: #define BIOS_FILENAME "mipsel_bios.bin" ! 40: #endif ! 41: ! 42: enum jazz_model_e ! 43: { ! 44: JAZZ_MAGNUM, ! 45: JAZZ_PICA61, ! 46: }; ! 47: ! 48: static void main_cpu_reset(void *opaque) ! 49: { ! 50: CPUState *env = opaque; ! 51: cpu_reset(env); ! 52: } ! 53: ! 54: static uint32_t rtc_readb(void *opaque, target_phys_addr_t addr) ! 55: { ! 56: CPUState *env = opaque; ! 57: return cpu_inw(env, 0x71); ! 58: } ! 59: ! 60: static void rtc_writeb(void *opaque, target_phys_addr_t addr, uint32_t val) ! 61: { ! 62: CPUState *env = opaque; ! 63: cpu_outw(env, 0x71, val & 0xff); ! 64: } ! 65: ! 66: static CPUReadMemoryFunc *rtc_read[3] = { ! 67: rtc_readb, ! 68: rtc_readb, ! 69: rtc_readb, ! 70: }; ! 71: ! 72: static CPUWriteMemoryFunc *rtc_write[3] = { ! 73: rtc_writeb, ! 74: rtc_writeb, ! 75: rtc_writeb, ! 76: }; ! 77: ! 78: static void dma_dummy_writeb(void *opaque, target_phys_addr_t addr, uint32_t val) ! 79: { ! 80: /* Nothing to do. That is only to ensure that ! 81: * the current DMA acknowledge cycle is completed. */ ! 82: } ! 83: ! 84: static CPUReadMemoryFunc *dma_dummy_read[3] = { ! 85: NULL, ! 86: NULL, ! 87: NULL, ! 88: }; ! 89: ! 90: static CPUWriteMemoryFunc *dma_dummy_write[3] = { ! 91: dma_dummy_writeb, ! 92: dma_dummy_writeb, ! 93: dma_dummy_writeb, ! 94: }; ! 95: ! 96: #ifdef HAS_AUDIO ! 97: static void audio_init(qemu_irq *pic) ! 98: { ! 99: struct soundhw *c; ! 100: int audio_enabled = 0; ! 101: ! 102: for (c = soundhw; !audio_enabled && c->name; ++c) { ! 103: audio_enabled = c->enabled; ! 104: } ! 105: ! 106: if (audio_enabled) { ! 107: AudioState *s; ! 108: ! 109: s = AUD_init(); ! 110: if (s) { ! 111: for (c = soundhw; c->name; ++c) { ! 112: if (c->enabled) { ! 113: if (c->isa) { ! 114: c->init.init_isa(s, pic); ! 115: } ! 116: } ! 117: } ! 118: } ! 119: } ! 120: } ! 121: #endif ! 122: ! 123: #define MAGNUM_BIOS_SIZE_MAX 0x7e000 ! 124: #define MAGNUM_BIOS_SIZE (BIOS_SIZE < MAGNUM_BIOS_SIZE_MAX ? BIOS_SIZE : MAGNUM_BIOS_SIZE_MAX) ! 125: ! 126: static ! 127: void mips_jazz_init (ram_addr_t ram_size, int vga_ram_size, ! 128: const char *cpu_model, ! 129: enum jazz_model_e jazz_model) ! 130: { ! 131: char buf[1024]; ! 132: unsigned long bios_offset; ! 133: int bios_size, n; ! 134: CPUState *env; ! 135: qemu_irq *rc4030, *i8259; ! 136: rc4030_dma *dmas; ! 137: rc4030_dma_function dma_read, dma_write; ! 138: void *scsi_hba; ! 139: int hd; ! 140: int s_rtc, s_dma_dummy; ! 141: PITState *pit; ! 142: BlockDriverState *fds[MAX_FD]; ! 143: qemu_irq esp_reset; ! 144: ! 145: /* init CPUs */ ! 146: if (cpu_model == NULL) { ! 147: #ifdef TARGET_MIPS64 ! 148: cpu_model = "R4000"; ! 149: #else ! 150: /* FIXME: All wrong, this maybe should be R3000 for the older JAZZs. */ ! 151: cpu_model = "24Kf"; ! 152: #endif ! 153: } ! 154: env = cpu_init(cpu_model); ! 155: if (!env) { ! 156: fprintf(stderr, "Unable to find CPU definition\n"); ! 157: exit(1); ! 158: } ! 159: qemu_register_reset(main_cpu_reset, env); ! 160: ! 161: /* allocate RAM */ ! 162: cpu_register_physical_memory(0, ram_size, IO_MEM_RAM); ! 163: ! 164: /* load the BIOS image. */ ! 165: bios_offset = ram_size + vga_ram_size; ! 166: if (bios_name == NULL) ! 167: bios_name = BIOS_FILENAME; ! 168: snprintf(buf, sizeof(buf), "%s/%s", bios_dir, bios_name); ! 169: bios_size = load_image(buf, phys_ram_base + bios_offset); ! 170: if (bios_size < 0 || bios_size > MAGNUM_BIOS_SIZE) { ! 171: fprintf(stderr, "qemu: Could not load MIPS bios '%s'\n", ! 172: buf); ! 173: exit(1); ! 174: } ! 175: ! 176: cpu_register_physical_memory(0x1fc00000LL, ! 177: MAGNUM_BIOS_SIZE, bios_offset | IO_MEM_ROM); ! 178: cpu_register_physical_memory(0xfff00000LL, ! 179: MAGNUM_BIOS_SIZE, bios_offset | IO_MEM_ROM); ! 180: ! 181: /* Init CPU internal devices */ ! 182: cpu_mips_irq_init_cpu(env); ! 183: cpu_mips_clock_init(env); ! 184: ! 185: /* Chipset */ ! 186: rc4030 = rc4030_init(env->irq[6], env->irq[3], ! 187: &dmas, &dma_read, &dma_write); ! 188: s_dma_dummy = cpu_register_io_memory(0, dma_dummy_read, dma_dummy_write, NULL); ! 189: cpu_register_physical_memory(0x8000d000, 0x00001000, s_dma_dummy); ! 190: ! 191: /* ISA devices */ ! 192: i8259 = i8259_init(env->irq[4]); ! 193: DMA_init(0); ! 194: pit = pit_init(0x40, i8259[0]); ! 195: pcspk_init(pit); ! 196: ! 197: /* ISA IO space at 0x90000000 */ ! 198: isa_mmio_init(0x90000000, 0x01000000); ! 199: isa_mem_base = 0x11000000; ! 200: ! 201: /* Video card */ ! 202: switch (jazz_model) { ! 203: case JAZZ_MAGNUM: ! 204: g364fb_mm_init(phys_ram_base + ram_size, ram_size, vga_ram_size, ! 205: 0x40000000, 0x60000000, 0, rc4030[3]); ! 206: break; ! 207: case JAZZ_PICA61: ! 208: isa_vga_mm_init(phys_ram_base + ram_size, ram_size, vga_ram_size, ! 209: 0x40000000, 0x60000000, 0); ! 210: break; ! 211: default: ! 212: break; ! 213: } ! 214: ! 215: /* Network controller */ ! 216: /* FIXME: missing NS SONIC DP83932 */ ! 217: ! 218: /* SCSI adapter */ ! 219: scsi_hba = esp_init(0x80002000, 0, ! 220: dma_read, dma_write, dmas[0], ! 221: rc4030[5], &esp_reset); ! 222: for (n = 0; n < ESP_MAX_DEVS; n++) { ! 223: hd = drive_get_index(IF_SCSI, 0, n); ! 224: if (hd != -1) { ! 225: esp_scsi_attach(scsi_hba, drives_table[hd].bdrv, n); ! 226: } ! 227: } ! 228: ! 229: /* Floppy */ ! 230: if (drive_get_max_bus(IF_FLOPPY) >= MAX_FD) { ! 231: fprintf(stderr, "qemu: too many floppy drives\n"); ! 232: exit(1); ! 233: } ! 234: for (n = 0; n < MAX_FD; n++) { ! 235: int fd = drive_get_index(IF_FLOPPY, 0, n); ! 236: if (fd != -1) ! 237: fds[n] = drives_table[fd].bdrv; ! 238: else ! 239: fds[n] = NULL; ! 240: } ! 241: fdctrl_init(rc4030[1], 0, 1, 0x80003000, fds); ! 242: ! 243: /* Real time clock */ ! 244: rtc_init(0x70, i8259[8], 1980); ! 245: s_rtc = cpu_register_io_memory(0, rtc_read, rtc_write, env); ! 246: cpu_register_physical_memory(0x80004000, 0x00001000, s_rtc); ! 247: ! 248: /* Keyboard (i8042) */ ! 249: i8042_mm_init(rc4030[6], rc4030[7], 0x80005000, 0x1000, 0x1); ! 250: ! 251: /* Serial ports */ ! 252: if (serial_hds[0]) ! 253: serial_mm_init(0x80006000, 0, rc4030[8], 8000000/16, serial_hds[0], 1); ! 254: if (serial_hds[1]) ! 255: serial_mm_init(0x80007000, 0, rc4030[9], 8000000/16, serial_hds[1], 1); ! 256: ! 257: /* Parallel port */ ! 258: if (parallel_hds[0]) ! 259: parallel_mm_init(0x80008000, 0, rc4030[0], parallel_hds[0]); ! 260: ! 261: /* Sound card */ ! 262: /* FIXME: missing Jazz sound at 0x8000c000, rc4030[2] */ ! 263: #ifdef HAS_AUDIO ! 264: audio_init(i8259); ! 265: #endif ! 266: ! 267: /* NVRAM: Unprotected at 0x9000, Protected at 0xa000, Read only at 0xb000 */ ! 268: ds1225y_init(0x80009000, "nvram"); ! 269: ! 270: /* LED indicator */ ! 271: jazz_led_init(0x8000f000); ! 272: } ! 273: ! 274: static ! 275: void mips_magnum_init (ram_addr_t ram_size, int vga_ram_size, ! 276: const char *boot_device, ! 277: const char *kernel_filename, const char *kernel_cmdline, ! 278: const char *initrd_filename, const char *cpu_model) ! 279: { ! 280: mips_jazz_init(ram_size, vga_ram_size, cpu_model, JAZZ_MAGNUM); ! 281: } ! 282: ! 283: static ! 284: void mips_pica61_init (ram_addr_t ram_size, int vga_ram_size, ! 285: const char *boot_device, ! 286: const char *kernel_filename, const char *kernel_cmdline, ! 287: const char *initrd_filename, const char *cpu_model) ! 288: { ! 289: mips_jazz_init(ram_size, vga_ram_size, cpu_model, JAZZ_PICA61); ! 290: } ! 291: ! 292: QEMUMachine mips_magnum_machine = { ! 293: .name = "magnum", ! 294: .desc = "MIPS Magnum", ! 295: .init = mips_magnum_init, ! 296: .ram_require = MAGNUM_BIOS_SIZE + VGA_RAM_SIZE, ! 297: .nodisk_ok = 1, ! 298: .use_scsi = 1, ! 299: }; ! 300: ! 301: QEMUMachine mips_pica61_machine = { ! 302: .name = "pica61", ! 303: .desc = "Acer Pica 61", ! 304: .init = mips_pica61_init, ! 305: .ram_require = MAGNUM_BIOS_SIZE + VGA_RAM_SIZE, ! 306: .nodisk_ok = 1, ! 307: .use_scsi = 1, ! 308: };
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.