14d5c29caSScott Wood /* 24d5c29caSScott Wood * Generic device-tree-driven paravirt PPC e500 platform 34d5c29caSScott Wood * 44d5c29caSScott Wood * Copyright 2012 Freescale Semiconductor, Inc. 54d5c29caSScott Wood * 64d5c29caSScott Wood * This is free software; you can redistribute it and/or modify 74d5c29caSScott Wood * it under the terms of the GNU General Public License as published by 84d5c29caSScott Wood * the Free Software Foundation; either version 2 of the License, or 94d5c29caSScott Wood * (at your option) any later version. 104d5c29caSScott Wood */ 114d5c29caSScott Wood 120d75590dSPeter Maydell #include "qemu/osdep.h" 13ab3dd749SPhilippe Mathieu-Daudé #include "qemu/units.h" 144d5c29caSScott Wood #include "e500.h" 1550d01d24SEduardo Habkost #include "hw/net/fsl_etsec/etsec.h" 169c17d615SPaolo Bonzini #include "sysemu/device_tree.h" 1777ac58ddSPaolo Bonzini #include "sysemu/kvm.h" 180bd1909dSEduardo Habkost #include "hw/sysbus.h" 199c17d615SPaolo Bonzini #include "hw/pci/pci.h" 200d09e41aSPaolo Bonzini #include "hw/ppc/openpic.h" 213b961124SStuart Yoder #include "kvm_ppc.h" 224d5c29caSScott Wood 2303f04809SIgor Mammedov static void e500plat_fixup_devtree(void *fdt) 244d5c29caSScott Wood { 254d5c29caSScott Wood const char model[] = "QEMU ppce500"; 264d5c29caSScott Wood const char compatible[] = "fsl,qemu-e500"; 274d5c29caSScott Wood 285a4348d1SPeter Crosthwaite qemu_fdt_setprop(fdt, "/", "model", model, sizeof(model)); 295a4348d1SPeter Crosthwaite qemu_fdt_setprop(fdt, "/", "compatible", compatible, 304d5c29caSScott Wood sizeof(compatible)); 314d5c29caSScott Wood } 324d5c29caSScott Wood 333ef96221SMarcel Apfelbaum static void e500plat_init(MachineState *machine) 344d5c29caSScott Wood { 3503f04809SIgor Mammedov PPCE500MachineClass *pmc = PPCE500_MACHINE_GET_CLASS(machine); 363b961124SStuart Yoder /* Older KVM versions don't support EPR which breaks guests when we announce 373b961124SStuart Yoder MPIC variants that support EPR. Revert to an older one for those */ 383b961124SStuart Yoder if (kvm_enabled() && !kvmppc_has_cap_epr()) { 3903f04809SIgor Mammedov pmc->mpic_version = OPENPIC_MODEL_FSL_MPIC_20; 403b961124SStuart Yoder } 413b961124SStuart Yoder 4203f04809SIgor Mammedov ppce500_init(machine); 434d5c29caSScott Wood } 444d5c29caSScott Wood 45a3fc8396SIgor Mammedov static void e500plat_machine_device_plug_cb(HotplugHandler *hotplug_dev, 46a3fc8396SIgor Mammedov DeviceState *dev, Error **errp) 47a3fc8396SIgor Mammedov { 48a3fc8396SIgor Mammedov PPCE500MachineState *pms = PPCE500_MACHINE(hotplug_dev); 49a3fc8396SIgor Mammedov 50a3fc8396SIgor Mammedov if (pms->pbus_dev) { 51e7e0d52dSPeter Maydell MachineClass *mc = MACHINE_GET_CLASS(pms); 52e7e0d52dSPeter Maydell 53e7e0d52dSPeter Maydell if (device_is_dynamic_sysbus(mc, dev)) { 54a3fc8396SIgor Mammedov platform_bus_link_device(pms->pbus_dev, SYS_BUS_DEVICE(dev)); 55a3fc8396SIgor Mammedov } 56a3fc8396SIgor Mammedov } 57a3fc8396SIgor Mammedov } 58a3fc8396SIgor Mammedov 59a3fc8396SIgor Mammedov static 60a3fc8396SIgor Mammedov HotplugHandler *e500plat_machine_get_hotpug_handler(MachineState *machine, 61a3fc8396SIgor Mammedov DeviceState *dev) 62a3fc8396SIgor Mammedov { 63e7e0d52dSPeter Maydell MachineClass *mc = MACHINE_GET_CLASS(machine); 64e7e0d52dSPeter Maydell 65e7e0d52dSPeter Maydell if (device_is_dynamic_sysbus(mc, dev)) { 66a3fc8396SIgor Mammedov return HOTPLUG_HANDLER(machine); 67a3fc8396SIgor Mammedov } 68a3fc8396SIgor Mammedov 69a3fc8396SIgor Mammedov return NULL; 70a3fc8396SIgor Mammedov } 71a3fc8396SIgor Mammedov 7203f04809SIgor Mammedov #define TYPE_E500PLAT_MACHINE MACHINE_TYPE_NAME("ppce500") 7303f04809SIgor Mammedov 7403f04809SIgor Mammedov static void e500plat_machine_class_init(ObjectClass *oc, void *data) 754d5c29caSScott Wood { 7603f04809SIgor Mammedov PPCE500MachineClass *pmc = PPCE500_MACHINE_CLASS(oc); 77a3fc8396SIgor Mammedov HotplugHandlerClass *hc = HOTPLUG_HANDLER_CLASS(oc); 7803f04809SIgor Mammedov MachineClass *mc = MACHINE_CLASS(oc); 7903f04809SIgor Mammedov 80debbdc00SIgor Mammedov assert(!mc->get_hotplug_handler); 81a3fc8396SIgor Mammedov mc->get_hotplug_handler = e500plat_machine_get_hotpug_handler; 82a3fc8396SIgor Mammedov hc->plug = e500plat_machine_device_plug_cb; 83a3fc8396SIgor Mammedov 8403f04809SIgor Mammedov pmc->pci_first_slot = 0x1; 8503f04809SIgor Mammedov pmc->pci_nr_slots = PCI_SLOT_MAX - 1; 8603f04809SIgor Mammedov pmc->fixup_devtree = e500plat_fixup_devtree; 8703f04809SIgor Mammedov pmc->mpic_version = OPENPIC_MODEL_FSL_MPIC_42; 8803f04809SIgor Mammedov pmc->has_mpc8xxx_gpio = true; 89*3f288c4bSPhilippe Mathieu-Daudé pmc->has_esdhc = true; 9003f04809SIgor Mammedov pmc->platform_bus_base = 0xf00000000ULL; 91ab3dd749SPhilippe Mathieu-Daudé pmc->platform_bus_size = 128 * MiB; 9203f04809SIgor Mammedov pmc->platform_bus_first_irq = 5; 9303f04809SIgor Mammedov pmc->platform_bus_num_irqs = 10; 9403f04809SIgor Mammedov pmc->ccsrbar_base = 0xFE0000000ULL; 9503f04809SIgor Mammedov pmc->pci_pio_base = 0xFE1000000ULL; 9603f04809SIgor Mammedov pmc->pci_mmio_base = 0xC00000000ULL; 9703f04809SIgor Mammedov pmc->pci_mmio_bus_base = 0xE0000000ULL; 9803f04809SIgor Mammedov pmc->spin_base = 0xFEF000000ULL; 9903f04809SIgor Mammedov 100e264d29dSEduardo Habkost mc->desc = "generic paravirt e500 platform"; 101e264d29dSEduardo Habkost mc->init = e500plat_init; 102e264d29dSEduardo Habkost mc->max_cpus = 32; 10359e816fdSIgor Mammedov mc->default_cpu_type = POWERPC_CPU_TYPE_NAME("e500v2_v30"); 10497316645SIgor Mammedov mc->default_ram_id = "mpc8544ds.ram"; 10503f04809SIgor Mammedov machine_class_allow_dynamic_sysbus_dev(mc, TYPE_ETSEC_COMMON); 1064d5c29caSScott Wood } 1074d5c29caSScott Wood 10803f04809SIgor Mammedov static const TypeInfo e500plat_info = { 10903f04809SIgor Mammedov .name = TYPE_E500PLAT_MACHINE, 11003f04809SIgor Mammedov .parent = TYPE_PPCE500_MACHINE, 11103f04809SIgor Mammedov .class_init = e500plat_machine_class_init, 112a3fc8396SIgor Mammedov .interfaces = (InterfaceInfo[]) { 113a3fc8396SIgor Mammedov { TYPE_HOTPLUG_HANDLER }, 114a3fc8396SIgor Mammedov { } 115a3fc8396SIgor Mammedov } 11603f04809SIgor Mammedov }; 11703f04809SIgor Mammedov 11803f04809SIgor Mammedov static void e500plat_register_types(void) 11903f04809SIgor Mammedov { 12003f04809SIgor Mammedov type_register_static(&e500plat_info); 12103f04809SIgor Mammedov } 12203f04809SIgor Mammedov type_init(e500plat_register_types) 123