1 /*
2 * QEMU HPPA hardware system emulator.
3 * (C) Copyright 2018-2023 Helge Deller <deller@gmx.de>
4 *
5 * This work is licensed under the GNU GPL license version 2 or later.
6 */
7
8 #include "qemu/osdep.h"
9 #include "qemu/datadir.h"
10 #include "cpu.h"
11 #include "elf.h"
12 #include "hw/loader.h"
13 #include "qemu/error-report.h"
14 #include "system/reset.h"
15 #include "system/system.h"
16 #include "system/qtest.h"
17 #include "system/runstate.h"
18 #include "hw/rtc/mc146818rtc.h"
19 #include "hw/timer/i8254.h"
20 #include "hw/char/serial-mm.h"
21 #include "hw/char/parallel.h"
22 #include "hw/intc/i8259.h"
23 #include "hw/input/lasips2.h"
24 #include "hw/net/lasi_82596.h"
25 #include "hw/nmi.h"
26 #include "hw/usb.h"
27 #include "hw/pci/pci.h"
28 #include "hw/pci/pci_device.h"
29 #include "hw/pci-host/astro.h"
30 #include "hw/pci-host/dino.h"
31 #include "hw/misc/lasi.h"
32 #include "hppa_hardware.h"
33 #include "qemu/units.h"
34 #include "qapi/error.h"
35 #include "net/net.h"
36 #include "qemu/log.h"
37
38 #define MIN_SEABIOS_HPPA_VERSION 12 /* require at least this fw version */
39
40 #define HPA_POWER_BUTTON (FIRMWARE_END - 0x10)
41 static hwaddr soft_power_reg;
42
43 #define enable_lasi_lan() 0
44
45 static DeviceState *lasi_dev;
46
hppa_powerdown_req(Notifier * n,void * opaque)47 static void hppa_powerdown_req(Notifier *n, void *opaque)
48 {
49 uint32_t val;
50
51 val = ldl_be_phys(&address_space_memory, soft_power_reg);
52 if ((val >> 8) == 0) {
53 /* immediately shut down when under hardware control */
54 qemu_system_shutdown_request(SHUTDOWN_CAUSE_GUEST_SHUTDOWN);
55 return;
56 }
57
58 /* clear bit 31 to indicate that the power switch was pressed. */
59 val &= ~1;
60 stl_be_phys(&address_space_memory, soft_power_reg, val);
61 }
62
63 static Notifier hppa_system_powerdown_notifier = {
64 .notify = hppa_powerdown_req
65 };
66
67 /* Fallback for unassigned PCI I/O operations. Avoids MCHK. */
ignore_read(void * opaque,hwaddr addr,unsigned size)68 static uint64_t ignore_read(void *opaque, hwaddr addr, unsigned size)
69 {
70 return 0;
71 }
72
ignore_write(void * opaque,hwaddr addr,uint64_t v,unsigned size)73 static void ignore_write(void *opaque, hwaddr addr, uint64_t v, unsigned size)
74 {
75 }
76
77 static const MemoryRegionOps hppa_pci_ignore_ops = {
78 .read = ignore_read,
79 .write = ignore_write,
80 .endianness = DEVICE_BIG_ENDIAN,
81 .valid = {
82 .min_access_size = 1,
83 .max_access_size = 8,
84 },
85 .impl = {
86 .min_access_size = 1,
87 .max_access_size = 8,
88 },
89 };
90
hppa_isa_bus(hwaddr addr)91 static ISABus *hppa_isa_bus(hwaddr addr)
92 {
93 ISABus *isa_bus;
94 qemu_irq *isa_irqs;
95 MemoryRegion *isa_region;
96
97 isa_region = g_new(MemoryRegion, 1);
98 memory_region_init_io(isa_region, NULL, &hppa_pci_ignore_ops,
99 NULL, "isa-io", 0x800);
100 memory_region_add_subregion(get_system_memory(), addr, isa_region);
101
102 isa_bus = isa_bus_new(NULL, get_system_memory(), isa_region,
103 &error_abort);
104 isa_irqs = i8259_init(isa_bus, NULL);
105 isa_bus_register_input_irqs(isa_bus, isa_irqs);
106
107 return isa_bus;
108 }
109
110 /*
111 * Helper functions to emulate RTC clock and DebugOutputPort
112 */
113 static time_t rtc_ref;
114
io_cpu_read(void * opaque,hwaddr addr,unsigned size)115 static uint64_t io_cpu_read(void *opaque, hwaddr addr, unsigned size)
116 {
117 uint64_t val = 0;
118
119 switch (addr) {
120 case 0: /* RTC clock */
121 val = time(NULL);
122 val += rtc_ref;
123 break;
124 case 8: /* DebugOutputPort */
125 return 0xe9; /* readback */
126 }
127 return val;
128 }
129
io_cpu_write(void * opaque,hwaddr addr,uint64_t val,unsigned size)130 static void io_cpu_write(void *opaque, hwaddr addr,
131 uint64_t val, unsigned size)
132 {
133 unsigned char ch;
134 Chardev *debugout;
135
136 switch (addr) {
137 case 0: /* RTC clock */
138 rtc_ref = val - time(NULL);
139 break;
140 case 8: /* DebugOutputPort */
141 ch = val;
142 debugout = serial_hd(0);
143 if (debugout) {
144 qemu_chr_fe_write_all(debugout->be, &ch, 1);
145 } else {
146 fprintf(stderr, "%c", ch);
147 }
148 break;
149 }
150 }
151
152 static const MemoryRegionOps hppa_io_helper_ops = {
153 .read = io_cpu_read,
154 .write = io_cpu_write,
155 .endianness = DEVICE_BIG_ENDIAN,
156 .valid = {
157 .min_access_size = 1,
158 .max_access_size = 8,
159 },
160 .impl = {
161 .min_access_size = 1,
162 .max_access_size = 8,
163 },
164 };
165
166 typedef uint64_t TranslateFn(void *opaque, uint64_t addr);
167
linux_kernel_virt_to_phys(void * opaque,uint64_t addr)168 static uint64_t linux_kernel_virt_to_phys(void *opaque, uint64_t addr)
169 {
170 addr &= (0x10000000 - 1);
171 return addr;
172 }
173
translate_pa10(void * dummy,uint64_t addr)174 static uint64_t translate_pa10(void *dummy, uint64_t addr)
175 {
176 return (uint32_t)addr;
177 }
178
translate_pa20(void * dummy,uint64_t addr)179 static uint64_t translate_pa20(void *dummy, uint64_t addr)
180 {
181 return hppa_abs_to_phys_pa2_w0(addr);
182 }
183
184 static HPPACPU *cpu[HPPA_MAX_CPUS];
185 static uint64_t firmware_entry;
186
fw_cfg_boot_set(void * opaque,const char * boot_device,Error ** errp)187 static void fw_cfg_boot_set(void *opaque, const char *boot_device,
188 Error **errp)
189 {
190 fw_cfg_modify_i16(opaque, FW_CFG_BOOT_DEVICE, boot_device[0]);
191 }
192
create_fw_cfg(MachineState * ms,PCIBus * pci_bus,hwaddr addr)193 static FWCfgState *create_fw_cfg(MachineState *ms, PCIBus *pci_bus,
194 hwaddr addr)
195 {
196 FWCfgState *fw_cfg;
197 uint64_t val;
198 const char qemu_version[] = QEMU_VERSION;
199 MachineClass *mc = MACHINE_GET_CLASS(ms);
200 int btlb_entries = HPPA_BTLB_ENTRIES(&cpu[0]->env);
201 int len;
202
203 fw_cfg = fw_cfg_init_mem(addr, addr + 4);
204 fw_cfg_add_i16(fw_cfg, FW_CFG_NB_CPUS, ms->smp.cpus);
205 fw_cfg_add_i16(fw_cfg, FW_CFG_MAX_CPUS, HPPA_MAX_CPUS);
206 fw_cfg_add_i64(fw_cfg, FW_CFG_RAM_SIZE, ms->ram_size);
207
208 val = cpu_to_le64(MIN_SEABIOS_HPPA_VERSION);
209 fw_cfg_add_file(fw_cfg, "/etc/firmware-min-version",
210 g_memdup2(&val, sizeof(val)), sizeof(val));
211
212 val = cpu_to_le64(HPPA_TLB_ENTRIES - btlb_entries);
213 fw_cfg_add_file(fw_cfg, "/etc/cpu/tlb_entries",
214 g_memdup2(&val, sizeof(val)), sizeof(val));
215
216 val = cpu_to_le64(btlb_entries);
217 fw_cfg_add_file(fw_cfg, "/etc/cpu/btlb_entries",
218 g_memdup2(&val, sizeof(val)), sizeof(val));
219
220 len = strlen(mc->name) + 1;
221 fw_cfg_add_file(fw_cfg, "/etc/hppa/machine",
222 g_memdup2(mc->name, len), len);
223
224 val = cpu_to_le64(soft_power_reg);
225 fw_cfg_add_file(fw_cfg, "/etc/hppa/power-button-addr",
226 g_memdup2(&val, sizeof(val)), sizeof(val));
227
228 val = cpu_to_le64(CPU_HPA + 16);
229 fw_cfg_add_file(fw_cfg, "/etc/hppa/rtc-addr",
230 g_memdup2(&val, sizeof(val)), sizeof(val));
231
232 val = cpu_to_le64(CPU_HPA + 24);
233 fw_cfg_add_file(fw_cfg, "/etc/hppa/DebugOutputPort",
234 g_memdup2(&val, sizeof(val)), sizeof(val));
235
236 fw_cfg_add_i16(fw_cfg, FW_CFG_BOOT_DEVICE, ms->boot_config.order[0]);
237 qemu_register_boot_set(fw_cfg_boot_set, fw_cfg);
238
239 fw_cfg_add_file(fw_cfg, "/etc/qemu-version",
240 g_memdup2(qemu_version, sizeof(qemu_version)),
241 sizeof(qemu_version));
242
243 pci_bus_add_fw_cfg_extra_pci_roots(fw_cfg, pci_bus, &error_abort);
244
245 return fw_cfg;
246 }
247
lasi_init(void)248 static LasiState *lasi_init(void)
249 {
250 DeviceState *dev;
251
252 dev = qdev_new(TYPE_LASI_CHIP);
253 sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
254
255 return LASI_CHIP(dev);
256 }
257
dino_init(MemoryRegion * addr_space)258 static DinoState *dino_init(MemoryRegion *addr_space)
259 {
260 DeviceState *dev;
261
262 dev = qdev_new(TYPE_DINO_PCI_HOST_BRIDGE);
263 object_property_set_link(OBJECT(dev), "memory-as", OBJECT(addr_space),
264 &error_fatal);
265 sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
266
267 return DINO_PCI_HOST_BRIDGE(dev);
268 }
269
270 /*
271 * Step 1: Create CPUs and Memory
272 */
machine_HP_common_init_cpus(MachineState * machine)273 static TranslateFn *machine_HP_common_init_cpus(MachineState *machine)
274 {
275 MemoryRegion *addr_space = get_system_memory();
276 unsigned int smp_cpus = machine->smp.cpus;
277 TranslateFn *translate;
278 MemoryRegion *cpu_region;
279 uint64_t ram_max;
280
281 /* Create CPUs. */
282 for (unsigned int i = 0; i < smp_cpus; i++) {
283 cpu[i] = HPPA_CPU(cpu_create(machine->cpu_type));
284 }
285
286 /* Initialize memory */
287 if (hppa_is_pa20(&cpu[0]->env)) {
288 translate = translate_pa20;
289 ram_max = 256 * GiB; /* like HP rp8440 */
290 } else {
291 translate = translate_pa10;
292 ram_max = FIRMWARE_START; /* 3.75 GB (32-bit CPU) */
293 }
294
295 soft_power_reg = translate(NULL, HPA_POWER_BUTTON);
296
297 for (unsigned int i = 0; i < smp_cpus; i++) {
298 g_autofree char *name = g_strdup_printf("cpu%u-io-eir", i);
299
300 cpu_region = g_new(MemoryRegion, 1);
301 memory_region_init_io(cpu_region, OBJECT(cpu[i]), &hppa_io_eir_ops,
302 cpu[i], name, 4);
303 memory_region_add_subregion(addr_space,
304 translate(NULL, CPU_HPA + i * 0x1000),
305 cpu_region);
306 }
307
308 /* RTC and DebugOutputPort on CPU #0 */
309 cpu_region = g_new(MemoryRegion, 1);
310 memory_region_init_io(cpu_region, OBJECT(cpu[0]), &hppa_io_helper_ops,
311 cpu[0], "cpu0-io-rtc", 2 * sizeof(uint64_t));
312 memory_region_add_subregion(addr_space, translate(NULL, CPU_HPA + 16),
313 cpu_region);
314
315 /* Main memory region. */
316 if (machine->ram_size > ram_max) {
317 info_report("Max RAM size limited to %" PRIu64 " MB", ram_max / MiB);
318 machine->ram_size = ram_max;
319 }
320 if (machine->ram_size <= FIRMWARE_START) {
321 /* contiguous memory up to 3.75 GB RAM */
322 memory_region_add_subregion_overlap(addr_space, 0, machine->ram, -1);
323 } else {
324 /* non-contiguous: Memory above 3.75 GB is mapped at RAM_MAP_HIGH */
325 MemoryRegion *mem_region;
326 mem_region = g_new(MemoryRegion, 2);
327 memory_region_init_alias(&mem_region[0], &addr_space->parent_obj,
328 "LowMem", machine->ram, 0, FIRMWARE_START);
329 memory_region_init_alias(&mem_region[1], &addr_space->parent_obj,
330 "HighMem", machine->ram, FIRMWARE_START,
331 machine->ram_size - FIRMWARE_START);
332 memory_region_add_subregion_overlap(addr_space, 0, &mem_region[0], -1);
333 memory_region_add_subregion_overlap(addr_space, RAM_MAP_HIGH,
334 &mem_region[1], -1);
335 }
336
337 return translate;
338 }
339
340 /*
341 * Last creation step: Add SCSI discs, NICs, graphics & load firmware
342 */
machine_HP_common_init_tail(MachineState * machine,PCIBus * pci_bus,TranslateFn * translate)343 static void machine_HP_common_init_tail(MachineState *machine, PCIBus *pci_bus,
344 TranslateFn *translate)
345 {
346 const char *kernel_filename = machine->kernel_filename;
347 const char *kernel_cmdline = machine->kernel_cmdline;
348 const char *initrd_filename = machine->initrd_filename;
349 const char *firmware = machine->firmware;
350 MachineClass *mc = MACHINE_GET_CLASS(machine);
351 DeviceState *dev;
352 PCIDevice *pci_dev;
353 char *firmware_filename;
354 uint64_t firmware_low, firmware_high;
355 long size;
356 uint64_t kernel_entry = 0, kernel_low, kernel_high;
357 MemoryRegion *addr_space = get_system_memory();
358 MemoryRegion *rom_region;
359 SysBusDevice *s;
360
361 /* SCSI disk setup. */
362 if (drive_get_max_bus(IF_SCSI) >= 0) {
363 dev = DEVICE(pci_create_simple(pci_bus, -1, "lsi53c895a"));
364 lsi53c8xx_handle_legacy_cmdline(dev);
365 }
366
367 /* Graphics setup. */
368 if (machine->enable_graphics && vga_interface_type != VGA_NONE) {
369 dev = qdev_new("artist");
370 s = SYS_BUS_DEVICE(dev);
371 bool disabled = object_property_get_bool(OBJECT(dev), "disable", NULL);
372 if (!disabled) {
373 sysbus_realize_and_unref(s, &error_fatal);
374 vga_interface_created = true;
375 sysbus_mmio_map(s, 0, translate(NULL, LASI_GFX_HPA));
376 sysbus_mmio_map(s, 1, translate(NULL, ARTIST_FB_ADDR));
377 }
378 }
379
380 /* Network setup. */
381 if (lasi_dev) {
382 lasi_82596_init(addr_space, translate(NULL, LASI_LAN_HPA),
383 qdev_get_gpio_in(lasi_dev, LASI_IRQ_LAN_HPA),
384 enable_lasi_lan());
385 }
386
387 pci_init_nic_devices(pci_bus, mc->default_nic);
388
389 /* BMC board: HP Diva GSP */
390 dev = qdev_new("diva-gsp");
391 if (!object_property_get_bool(OBJECT(dev), "disable", NULL)) {
392 pci_dev = pci_new_multifunction(PCI_DEVFN(2, 0), "diva-gsp");
393 if (!lasi_dev) {
394 /* bind default keyboard/serial to Diva card */
395 qdev_prop_set_chr(DEVICE(pci_dev), "chardev1", serial_hd(0));
396 qdev_prop_set_chr(DEVICE(pci_dev), "chardev2", serial_hd(1));
397 qdev_prop_set_chr(DEVICE(pci_dev), "chardev3", serial_hd(2));
398 qdev_prop_set_chr(DEVICE(pci_dev), "chardev4", serial_hd(3));
399 }
400 pci_realize_and_unref(pci_dev, pci_bus, &error_fatal);
401 }
402
403 /* create USB OHCI controller for USB keyboard & mouse on Astro machines */
404 if (!lasi_dev && machine->enable_graphics && defaults_enabled()) {
405 USBBus *usb_bus;
406
407 pci_create_simple(pci_bus, -1, "pci-ohci");
408 usb_bus = USB_BUS(object_resolve_type_unambiguous(TYPE_USB_BUS,
409 &error_abort));
410 usb_create_simple(usb_bus, "usb-kbd");
411 usb_create_simple(usb_bus, "usb-mouse");
412 }
413
414 /* register power switch emulation */
415 qemu_register_powerdown_notifier(&hppa_system_powerdown_notifier);
416
417 /* fw_cfg configuration interface */
418 create_fw_cfg(machine, pci_bus, translate(NULL, FW_CFG_IO_BASE));
419
420 /* Load firmware. Given that this is not "real" firmware,
421 but one explicitly written for the emulation, we might as
422 well load it directly from an ELF image. Load the 64-bit
423 firmware on 64-bit machines by default if not specified
424 on command line. */
425 if (!qtest_enabled()) {
426 if (!firmware) {
427 firmware = lasi_dev ? "hppa-firmware.img" : "hppa-firmware64.img";
428 }
429 firmware_filename = qemu_find_file(QEMU_FILE_TYPE_BIOS, firmware);
430 if (firmware_filename == NULL) {
431 error_report("no firmware provided");
432 exit(1);
433 }
434
435 size = load_elf(firmware_filename, NULL, translate, NULL,
436 &firmware_entry, &firmware_low, &firmware_high, NULL,
437 ELFDATA2MSB, EM_PARISC, 0, 0);
438
439 if (size < 0) {
440 error_report("could not load firmware '%s'", firmware_filename);
441 exit(1);
442 }
443 qemu_log_mask(CPU_LOG_PAGE, "Firmware loaded at 0x%08" PRIx64
444 "-0x%08" PRIx64 ", entry at 0x%08" PRIx64 ".\n",
445 firmware_low, firmware_high, firmware_entry);
446 if (firmware_low < translate(NULL, FIRMWARE_START) ||
447 firmware_high >= translate(NULL, FIRMWARE_END)) {
448 error_report("Firmware overlaps with memory or IO space");
449 exit(1);
450 }
451 g_free(firmware_filename);
452 }
453
454 rom_region = g_new(MemoryRegion, 1);
455 memory_region_init_ram(rom_region, NULL, "firmware",
456 (FIRMWARE_END - FIRMWARE_START), &error_fatal);
457 memory_region_add_subregion(addr_space,
458 translate(NULL, FIRMWARE_START), rom_region);
459
460 /* Load kernel */
461 if (kernel_filename) {
462 size = load_elf(kernel_filename, NULL, linux_kernel_virt_to_phys,
463 NULL, &kernel_entry, &kernel_low, &kernel_high, NULL,
464 ELFDATA2MSB, EM_PARISC, 0, 0);
465
466 kernel_entry = linux_kernel_virt_to_phys(NULL, kernel_entry);
467
468 if (size < 0) {
469 error_report("could not load kernel '%s'", kernel_filename);
470 exit(1);
471 }
472 qemu_log_mask(CPU_LOG_PAGE, "Kernel loaded at 0x%08" PRIx64
473 "-0x%08" PRIx64 ", entry at 0x%08" PRIx64
474 ", size %" PRIu64 " kB\n",
475 kernel_low, kernel_high, kernel_entry, size / KiB);
476
477 if (kernel_cmdline) {
478 cpu[0]->env.cmdline_or_bootorder = 0x4000;
479 pstrcpy_targphys("cmdline", cpu[0]->env.cmdline_or_bootorder,
480 TARGET_PAGE_SIZE, kernel_cmdline);
481 }
482
483 if (initrd_filename) {
484 ram_addr_t initrd_base;
485 int64_t initrd_size;
486
487 initrd_size = get_image_size(initrd_filename);
488 if (initrd_size < 0) {
489 error_report("could not load initial ram disk '%s'",
490 initrd_filename);
491 exit(1);
492 }
493
494 /* Load the initrd image high in memory.
495 Mirror the algorithm used by palo:
496 (1) Due to sign-extension problems and PDC,
497 put the initrd no higher than 1G.
498 (2) Reserve 64k for stack. */
499 initrd_base = MIN(machine->ram_size, 1 * GiB);
500 initrd_base = initrd_base - 64 * KiB;
501 initrd_base = (initrd_base - initrd_size) & TARGET_PAGE_MASK;
502
503 if (initrd_base < kernel_high) {
504 error_report("kernel and initial ram disk too large!");
505 exit(1);
506 }
507
508 load_image_targphys(initrd_filename, initrd_base, initrd_size);
509 cpu[0]->env.initrd_base = initrd_base;
510 cpu[0]->env.initrd_end = initrd_base + initrd_size;
511 }
512 }
513
514 if (!kernel_entry) {
515 /* When booting via firmware, tell firmware if we want interactive
516 * mode (kernel_entry=1), and to boot from CD (cmdline_or_bootorder='d')
517 * or hard disc (cmdline_or_bootorder='c').
518 */
519 kernel_entry = machine->boot_config.has_menu ? machine->boot_config.menu : 0;
520 cpu[0]->env.cmdline_or_bootorder = machine->boot_config.order[0];
521 }
522
523 /* Keep initial kernel_entry for first boot */
524 cpu[0]->env.kernel_entry = kernel_entry;
525 }
526
527 /*
528 * Create HP B160L workstation
529 */
machine_HP_B160L_init(MachineState * machine)530 static void machine_HP_B160L_init(MachineState *machine)
531 {
532 DeviceState *dev, *dino_dev;
533 MemoryRegion *addr_space = get_system_memory();
534 TranslateFn *translate;
535 ISABus *isa_bus;
536 PCIBus *pci_bus;
537
538 /* Create CPUs and RAM. */
539 translate = machine_HP_common_init_cpus(machine);
540
541 if (hppa_is_pa20(&cpu[0]->env)) {
542 error_report("The HP B160L workstation requires a 32-bit "
543 "CPU. Use '-machine C3700' instead.");
544 exit(1);
545 }
546
547 /* Init Lasi chip */
548 lasi_dev = DEVICE(lasi_init());
549 memory_region_add_subregion(addr_space, translate(NULL, LASI_HPA),
550 sysbus_mmio_get_region(
551 SYS_BUS_DEVICE(lasi_dev), 0));
552
553 /* Init Dino (PCI host bus chip). */
554 dino_dev = DEVICE(dino_init(addr_space));
555 memory_region_add_subregion(addr_space, translate(NULL, DINO_HPA),
556 sysbus_mmio_get_region(
557 SYS_BUS_DEVICE(dino_dev), 0));
558 pci_bus = PCI_BUS(qdev_get_child_bus(dino_dev, "pci"));
559 assert(pci_bus);
560
561 /* Create ISA bus, needed for PS/2 kbd/mouse port emulation */
562 isa_bus = hppa_isa_bus(translate(NULL, IDE_HPA));
563 assert(isa_bus);
564
565 /* Serial ports: Lasi and Dino use a 7.272727 MHz clock. */
566 serial_mm_init(addr_space, translate(NULL, LASI_UART_HPA + 0x800), 0,
567 qdev_get_gpio_in(lasi_dev, LASI_IRQ_UART_HPA), 7272727 / 16,
568 serial_hd(0), DEVICE_BIG_ENDIAN);
569
570 serial_mm_init(addr_space, translate(NULL, DINO_UART_HPA + 0x800), 0,
571 qdev_get_gpio_in(dino_dev, DINO_IRQ_RS232INT), 7272727 / 16,
572 serial_hd(1), DEVICE_BIG_ENDIAN);
573
574 /* Parallel port */
575 parallel_mm_init(addr_space, translate(NULL, LASI_LPT_HPA + 0x800), 0,
576 qdev_get_gpio_in(lasi_dev, LASI_IRQ_LAN_HPA),
577 parallel_hds[0]);
578
579 /* PS/2 Keyboard/Mouse */
580 dev = qdev_new(TYPE_LASIPS2);
581 sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
582 sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0,
583 qdev_get_gpio_in(lasi_dev, LASI_IRQ_PS2KBD_HPA));
584 memory_region_add_subregion(addr_space,
585 translate(NULL, LASI_PS2KBD_HPA),
586 sysbus_mmio_get_region(SYS_BUS_DEVICE(dev),
587 0));
588 memory_region_add_subregion(addr_space,
589 translate(NULL, LASI_PS2KBD_HPA + 0x100),
590 sysbus_mmio_get_region(SYS_BUS_DEVICE(dev),
591 1));
592
593 /* Add SCSI discs, NICs, graphics & load firmware */
594 machine_HP_common_init_tail(machine, pci_bus, translate);
595 }
596
astro_init(void)597 static AstroState *astro_init(void)
598 {
599 DeviceState *dev;
600
601 dev = qdev_new(TYPE_ASTRO_CHIP);
602 sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
603
604 return ASTRO_CHIP(dev);
605 }
606
607 /*
608 * Create HP C3700 workstation
609 */
machine_HP_C3700_init(MachineState * machine)610 static void machine_HP_C3700_init(MachineState *machine)
611 {
612 PCIBus *pci_bus;
613 AstroState *astro;
614 DeviceState *astro_dev;
615 MemoryRegion *addr_space = get_system_memory();
616 TranslateFn *translate;
617
618 /* Create CPUs and RAM. */
619 translate = machine_HP_common_init_cpus(machine);
620
621 if (!hppa_is_pa20(&cpu[0]->env)) {
622 error_report("The HP C3000 workstation requires a 64-bit CPU. "
623 "Use '-machine B160L' instead.");
624 exit(1);
625 }
626
627 /* Init Astro and the Elroys (PCI host bus chips). */
628 astro = astro_init();
629 astro_dev = DEVICE(astro);
630 memory_region_add_subregion(addr_space, translate(NULL, ASTRO_HPA),
631 sysbus_mmio_get_region(
632 SYS_BUS_DEVICE(astro_dev), 0));
633 pci_bus = PCI_BUS(qdev_get_child_bus(DEVICE(astro->elroy[0]), "pci"));
634 assert(pci_bus);
635
636 /* Add SCSI discs, NICs, graphics & load firmware */
637 machine_HP_common_init_tail(machine, pci_bus, translate);
638 }
639
hppa_machine_reset(MachineState * ms,ResetType type)640 static void hppa_machine_reset(MachineState *ms, ResetType type)
641 {
642 unsigned int smp_cpus = ms->smp.cpus;
643 int i;
644
645 qemu_devices_reset(type);
646
647 /* Start all CPUs at the firmware entry point.
648 * Monarch CPU will initialize firmware, secondary CPUs
649 * will enter a small idle loop and wait for rendevouz. */
650 for (i = 0; i < smp_cpus; i++) {
651 CPUState *cs = CPU(cpu[i]);
652
653 /* reset CPU */
654 resettable_reset(OBJECT(cs), RESET_TYPE_COLD);
655
656 cpu_set_pc(cs, firmware_entry);
657 cpu[i]->env.psw = PSW_Q;
658 cpu[i]->env.gr[5] = CPU_HPA + i * 0x1000;
659 }
660
661 cpu[0]->env.gr[26] = ms->ram_size;
662 cpu[0]->env.gr[25] = cpu[0]->env.kernel_entry;
663 cpu[0]->env.gr[24] = cpu[0]->env.cmdline_or_bootorder;
664 cpu[0]->env.gr[23] = cpu[0]->env.initrd_base;
665 cpu[0]->env.gr[22] = cpu[0]->env.initrd_end;
666 cpu[0]->env.gr[21] = smp_cpus;
667 cpu[0]->env.gr[19] = FW_CFG_IO_BASE;
668
669 /* reset static fields to avoid starting Linux kernel & initrd on reboot */
670 cpu[0]->env.kernel_entry = 0;
671 cpu[0]->env.initrd_base = 0;
672 cpu[0]->env.initrd_end = 0;
673 cpu[0]->env.cmdline_or_bootorder = 'c';
674 }
675
hppa_nmi(NMIState * n,int cpu_index,Error ** errp)676 static void hppa_nmi(NMIState *n, int cpu_index, Error **errp)
677 {
678 CPUState *cs;
679
680 CPU_FOREACH(cs) {
681 cpu_interrupt(cs, CPU_INTERRUPT_NMI);
682 }
683 }
684
HP_B160L_machine_init_class_init(ObjectClass * oc,void * data)685 static void HP_B160L_machine_init_class_init(ObjectClass *oc, void *data)
686 {
687 static const char * const valid_cpu_types[] = {
688 TYPE_HPPA_CPU,
689 NULL
690 };
691 MachineClass *mc = MACHINE_CLASS(oc);
692 NMIClass *nc = NMI_CLASS(oc);
693
694 mc->desc = "HP B160L workstation";
695 mc->default_cpu_type = TYPE_HPPA_CPU;
696 mc->valid_cpu_types = valid_cpu_types;
697 mc->init = machine_HP_B160L_init;
698 mc->reset = hppa_machine_reset;
699 mc->block_default_type = IF_SCSI;
700 mc->max_cpus = HPPA_MAX_CPUS;
701 mc->default_cpus = 1;
702 mc->is_default = true;
703 mc->default_ram_size = 512 * MiB;
704 mc->default_boot_order = "cd";
705 mc->default_ram_id = "ram";
706 mc->default_nic = "tulip";
707
708 nc->nmi_monitor_handler = hppa_nmi;
709 }
710
711 static const TypeInfo HP_B160L_machine_init_typeinfo = {
712 .name = MACHINE_TYPE_NAME("B160L"),
713 .parent = TYPE_MACHINE,
714 .class_init = HP_B160L_machine_init_class_init,
715 .interfaces = (InterfaceInfo[]) {
716 { TYPE_NMI },
717 { }
718 },
719 };
720
HP_C3700_machine_init_class_init(ObjectClass * oc,void * data)721 static void HP_C3700_machine_init_class_init(ObjectClass *oc, void *data)
722 {
723 static const char * const valid_cpu_types[] = {
724 TYPE_HPPA64_CPU,
725 NULL
726 };
727 MachineClass *mc = MACHINE_CLASS(oc);
728 NMIClass *nc = NMI_CLASS(oc);
729
730 mc->desc = "HP C3700 workstation";
731 mc->default_cpu_type = TYPE_HPPA64_CPU;
732 mc->valid_cpu_types = valid_cpu_types;
733 mc->init = machine_HP_C3700_init;
734 mc->reset = hppa_machine_reset;
735 mc->block_default_type = IF_SCSI;
736 mc->max_cpus = HPPA_MAX_CPUS;
737 mc->default_cpus = 1;
738 mc->is_default = false;
739 mc->default_ram_size = 1024 * MiB;
740 mc->default_boot_order = "cd";
741 mc->default_ram_id = "ram";
742 mc->default_nic = "tulip";
743
744 nc->nmi_monitor_handler = hppa_nmi;
745 }
746
747 static const TypeInfo HP_C3700_machine_init_typeinfo = {
748 .name = MACHINE_TYPE_NAME("C3700"),
749 .parent = TYPE_MACHINE,
750 .class_init = HP_C3700_machine_init_class_init,
751 .interfaces = (InterfaceInfo[]) {
752 { TYPE_NMI },
753 { }
754 },
755 };
756
hppa_machine_init_register_types(void)757 static void hppa_machine_init_register_types(void)
758 {
759 type_register_static(&HP_B160L_machine_init_typeinfo);
760 type_register_static(&HP_C3700_machine_init_typeinfo);
761 }
762
763 type_init(hppa_machine_init_register_types)
764