@@ -35,6 +35,7 @@
#include "hw/qdev-properties-system.h"
#include "sysemu/kvm.h"
#include "qom/object.h"
+#include "kvm/kvm_i386.h"
#define KVM_PIT_REINJECT_BIT 0
@@ -59,6 +60,23 @@ struct KVMPITClass {
DeviceRealize parent_realize;
};
+ISADevice *i8254_pit_create_try_kvm(ISABus *bus, int iobase, qemu_irq irq_in)
+{
+ DeviceState *dev;
+ ISADevice *d;
+
+ if (!kvm_pit_in_kernel()) {
+ return i8254_pit_create(bus, iobase, irq_in);
+ }
+
+ d = isa_new(TYPE_KVM_I8254);
+ dev = DEVICE(d);
+ qdev_prop_set_uint32(dev, "iobase", iobase);
+ isa_realize_and_unref(d, bus, &error_fatal);
+
+ return d;
+}
+
static void kvm_pit_update_clock_offset(KVMPITState *s)
{
int64_t offset, clock_offset;
@@ -258,11 +258,7 @@ static void microvm_devices_init(MicrovmMachineState *mms)
}
if (x86ms->pit == ON_OFF_AUTO_ON || x86ms->pit == ON_OFF_AUTO_AUTO) {
- if (kvm_pit_in_kernel()) {
- kvm_pit_init(isa_bus, 0x40);
- } else {
- i8254_pit_create(isa_bus, 0x40, isa_bus_get_irq(isa_bus, 0));
- }
+ i8254_pit_create_try_kvm(isa_bus, 0x40, isa_bus_get_irq(isa_bus, 0));
}
if (mms->rtc == ON_OFF_AUTO_ON ||
@@ -1311,11 +1311,8 @@ void pc_basic_device_init(struct PCMachineState *pcms,
if (!xen_enabled() &&
(x86ms->pit == ON_OFF_AUTO_AUTO || x86ms->pit == ON_OFF_AUTO_ON)) {
- if (kvm_pit_in_kernel()) {
- pit = kvm_pit_init(isa_bus, 0x40);
- } else {
- pit = i8254_pit_create(isa_bus, 0x40, pit_irq);
- }
+ pit = i8254_pit_create_try_kvm(isa_bus, 0x40, pit_irq);
+
if (hpet) {
/* connect PIT to output control line of the HPET */
qdev_connect_gpio_out(hpet, 0, qdev_get_gpio_in(DEVICE(pit), 0));
@@ -25,9 +25,6 @@
#ifndef HW_I8254_H
#define HW_I8254_H
-#include "hw/qdev-properties.h"
-#include "hw/isa/isa.h"
-#include "qapi/error.h"
#include "qom/object.h"
#define PIT_FREQ 1193182
@@ -55,19 +52,12 @@ OBJECT_DECLARE_TYPE(PITCommonState, PITCommonClass, PIT_COMMON)
* specified ISA @bus, and drop the reference to it (the device is realized).
*/
ISADevice *i8254_pit_create(ISABus *bus, int iobase, qemu_irq irq_in);
-
-static inline ISADevice *kvm_pit_init(ISABus *bus, int base)
-{
- DeviceState *dev;
- ISADevice *d;
-
- d = isa_new(TYPE_KVM_I8254);
- dev = DEVICE(d);
- qdev_prop_set_uint32(dev, "iobase", base);
- isa_realize_and_unref(d, bus, &error_fatal);
-
- return d;
-}
+/**
+ * Try to create and realize a in-kernel I8254 PIT device on the heap.
+ * If KVM is not available or doesn't have in-kernel PIT support, a
+ * emulated PIT is used. See i8254_pit_create.
+ */
+ISADevice *i8254_pit_create_try_kvm(ISABus *bus, int iobase, qemu_irq irq_in);
void pit_set_gate(ISADevice *dev, int channel, int val);
void pit_get_channel_info(ISADevice *dev, int channel, PITChannelInfo *info);
@@ -10,6 +10,7 @@
*
*/
#include "qemu/osdep.h"
+#include "hw/timer/i8254.h"
#include "cpu.h"
#include "kvm_i386.h"
@@ -49,3 +50,8 @@ void kvm_set_max_apic_id(uint32_t max_apic_id)
{
return;
}
+
+ISADevice *i8254_pit_create_try_kvm(ISABus *bus, int iobase, qemu_irq irq_in)
+{
+ return i8254_pit_create(bus, iobase, irq_in);
+}
Factor a new i8254_pit_create_try_kvm() helper out of the following patter: if (kvm_pit_in_kernel()) { kvm_pit_init(...); } else } i8254_pit_create(...); } (adding a stub for non-KVM builds). Since kvm_pit_init() is only used once, un-inline it and remove the now unused headers from "hw/timer/i8254.h". Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org> --- hw/i386/kvm/i8254.c | 18 ++++++++++++++++++ hw/i386/microvm.c | 6 +----- hw/i386/pc.c | 7 ++----- include/hw/timer/i8254.h | 22 ++++++---------------- target/i386/kvm/kvm-stub.c | 6 ++++++ 5 files changed, 33 insertions(+), 26 deletions(-)