1 /* 2 * ap bridge 3 * 4 * Copyright 2018 IBM Corp. 5 * 6 * This work is licensed under the terms of the GNU GPL, version 2 or (at 7 * your option) any later version. See the COPYING file in the top-level 8 * directory. 9 */ 10 11 #include "qemu/osdep.h" 12 #include "qapi/error.h" 13 #include "hw/sysbus.h" 14 #include "qemu/bitops.h" 15 #include "qemu/module.h" 16 #include "hw/s390x/ap-bridge.h" 17 #include "cpu.h" 18 19 static char *ap_bus_get_dev_path(DeviceState *dev) 20 { 21 /* at most one */ 22 return g_strdup_printf("/1"); 23 } 24 25 static void ap_bus_class_init(ObjectClass *oc, void *data) 26 { 27 BusClass *k = BUS_CLASS(oc); 28 29 k->get_dev_path = ap_bus_get_dev_path; 30 /* More than one ap device does not make sense */ 31 k->max_dev = 1; 32 } 33 34 static const TypeInfo ap_bus_info = { 35 .name = TYPE_AP_BUS, 36 .parent = TYPE_BUS, 37 .instance_size = 0, 38 .class_init = ap_bus_class_init, 39 }; 40 41 void s390_init_ap(void) 42 { 43 DeviceState *dev; 44 BusState *bus; 45 46 /* If no AP instructions then no need for AP bridge */ 47 if (!s390_has_feat(S390_FEAT_AP)) { 48 return; 49 } 50 51 /* Create bridge device */ 52 dev = qdev_new(TYPE_AP_BRIDGE); 53 object_property_add_child(qdev_get_machine(), TYPE_AP_BRIDGE, 54 OBJECT(dev)); 55 sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal); 56 57 /* Create bus on bridge device */ 58 bus = qbus_create(TYPE_AP_BUS, dev, TYPE_AP_BUS); 59 60 /* Enable hotplugging */ 61 qbus_set_hotplug_handler(bus, OBJECT(dev)); 62 } 63 64 static void ap_bridge_class_init(ObjectClass *oc, void *data) 65 { 66 DeviceClass *dc = DEVICE_CLASS(oc); 67 HotplugHandlerClass *hc = HOTPLUG_HANDLER_CLASS(oc); 68 69 hc->unplug = qdev_simple_device_unplug_cb; 70 set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories); 71 } 72 73 static const TypeInfo ap_bridge_info = { 74 .name = TYPE_AP_BRIDGE, 75 .parent = TYPE_SYS_BUS_DEVICE, 76 .instance_size = 0, 77 .class_init = ap_bridge_class_init, 78 .interfaces = (InterfaceInfo[]) { 79 { TYPE_HOTPLUG_HANDLER }, 80 { } 81 } 82 }; 83 84 static void ap_register(void) 85 { 86 type_register_static(&ap_bridge_info); 87 type_register_static(&ap_bus_info); 88 } 89 90 type_init(ap_register) 91