xref: /openbmc/qemu/hw/arm/xen-pvh.c (revision b5ab62b3c0050612c7f9b0b4baeb44ebab42775a)
1  /*
2   * QEMU ARM Xen PVH Machine
3   *
4   * SPDX-License-Identifier: MIT
5   */
6  
7  #include "qemu/osdep.h"
8  #include "qemu/error-report.h"
9  #include "qapi/qapi-commands-migration.h"
10  #include "hw/boards.h"
11  #include "sysemu/sysemu.h"
12  #include "hw/xen/xen-pvh-common.h"
13  #include "hw/xen/arch_hvm.h"
14  
15  #define TYPE_XEN_ARM  MACHINE_TYPE_NAME("xenpvh")
16  
17  /*
18   * VIRTIO_MMIO_DEV_SIZE is imported from tools/libs/light/libxl_arm.c under Xen
19   * repository.
20   *
21   * Origin: git://xenbits.xen.org/xen.git 2128143c114c
22   */
23  #define VIRTIO_MMIO_DEV_SIZE   0x200
24  
25  #define NR_VIRTIO_MMIO_DEVICES   \
26     (GUEST_VIRTIO_MMIO_SPI_LAST - GUEST_VIRTIO_MMIO_SPI_FIRST)
27  
28  static void xen_arm_instance_init(Object *obj)
29  {
30      XenPVHMachineState *s = XEN_PVH_MACHINE(obj);
31  
32      /* Default values.  */
33      s->cfg.ram_low = (MemMapEntry) { GUEST_RAM0_BASE, GUEST_RAM0_SIZE };
34      s->cfg.ram_high = (MemMapEntry) { GUEST_RAM1_BASE, GUEST_RAM1_SIZE };
35  
36      s->cfg.virtio_mmio_num = NR_VIRTIO_MMIO_DEVICES;
37      s->cfg.virtio_mmio_irq_base = GUEST_VIRTIO_MMIO_SPI_FIRST;
38      s->cfg.virtio_mmio = (MemMapEntry) { GUEST_VIRTIO_MMIO_BASE,
39                                           VIRTIO_MMIO_DEV_SIZE };
40  }
41  
42  static void xen_pvh_set_pci_intx_irq(void *opaque, int intx_irq, int level)
43  {
44      XenPVHMachineState *s = XEN_PVH_MACHINE(opaque);
45      int irq = s->cfg.pci_intx_irq_base + intx_irq;
46  
47      if (xendevicemodel_set_irq_level(xen_dmod, xen_domid, irq, level)) {
48          error_report("xendevicemodel_set_pci_intx_level failed");
49      }
50  }
51  
52  static void xen_arm_machine_class_init(ObjectClass *oc, void *data)
53  {
54      XenPVHMachineClass *xpc = XEN_PVH_MACHINE_CLASS(oc);
55      MachineClass *mc = MACHINE_CLASS(oc);
56  
57      mc->desc = "Xen PVH ARM machine";
58  
59      /*
60       * mc->max_cpus holds the MAX value allowed in the -smp command-line opts.
61       *
62       * 1. If users don't pass any -smp option:
63       *   ms->smp.cpus will default to 1.
64       *   ms->smp.max_cpus will default to 1.
65       *
66       * 2. If users pass -smp X:
67       *   ms->smp.cpus will be set to X.
68       *   ms->smp.max_cpus will also be set to X.
69       *
70       * 3. If users pass -smp X,maxcpus=Y:
71       *   ms->smp.cpus will be set to X.
72       *   ms->smp.max_cpus will be set to Y.
73       *
74       * In scenarios 2 and 3, if X or Y are set to something larger than
75       * mc->max_cpus, QEMU will bail out with an error message.
76       */
77      mc->max_cpus = GUEST_MAX_VCPUS;
78  
79      /* Xen/ARM does not use buffered IOREQs.  */
80      xpc->handle_bufioreq = HVM_IOREQSRV_BUFIOREQ_OFF;
81  
82      /* PCI INTX delivery.  */
83      xpc->set_pci_intx_irq = xen_pvh_set_pci_intx_irq;
84  
85      /* List of supported features known to work on PVH ARM.  */
86      xpc->has_pci = true;
87      xpc->has_tpm = true;
88      xpc->has_virtio_mmio = true;
89  
90      xen_pvh_class_setup_common_props(xpc);
91  }
92  
93  static const TypeInfo xen_arm_machine_type = {
94      .name = TYPE_XEN_ARM,
95      .parent = TYPE_XEN_PVH_MACHINE,
96      .class_init = xen_arm_machine_class_init,
97      .instance_size = sizeof(XenPVHMachineState),
98      .instance_init = xen_arm_instance_init,
99  };
100  
101  static void xen_arm_machine_register_types(void)
102  {
103      type_register_static(&xen_arm_machine_type);
104  }
105  
106  type_init(xen_arm_machine_register_types)
107