Commit 6b8f1020 authored by Cornelia Huck's avatar Cornelia Huck Committed by Michael S. Tsirkin
Browse files

virtio: move host_features



Move host_features from the individual transport proxies into
the virtio device. Transports may continue to add feature bits
during device plugging.

This should it make easier to offer different sets of host features
for virtio-1/transitional support.

Tested-by: default avatarShannon Zhao <shannon.zhao@linaro.org>
Signed-off-by: default avatarCornelia Huck <cornelia.huck@de.ibm.com>
Reviewed-by: default avatarMichael S. Tsirkin <mst@redhat.com>
Signed-off-by: default avatarMichael S. Tsirkin <mst@redhat.com>
parent 2332333c
Loading
Loading
Loading
Loading
+2 −16
Original line number Diff line number Diff line
@@ -139,8 +139,6 @@ static void s390_virtio_device_init(VirtIOS390Device *dev,

    bus->dev_offs += dev_len;

    dev->host_features = virtio_bus_get_vdev_features(&dev->bus,
                                                      dev->host_features);
    s390_virtio_device_sync(dev);
    s390_virtio_reset_idx(dev);
    if (dev->qdev.hotplugged) {
@@ -433,7 +431,8 @@ void s390_virtio_device_sync(VirtIOS390Device *dev)
    cur_offs += num_vq * VIRTIO_VQCONFIG_LEN;

    /* Sync feature bitmap */
    address_space_stl_le(&address_space_memory, cur_offs, dev->host_features,
    address_space_stl_le(&address_space_memory, cur_offs,
                         dev->vdev->host_features,
                         MEMTXATTRS_UNSPECIFIED, NULL);

    dev->feat_offs = cur_offs + dev->feat_len;
@@ -528,12 +527,6 @@ static void virtio_s390_notify(DeviceState *d, uint16_t vector)
    s390_virtio_irq(0, token);
}

static unsigned virtio_s390_get_features(DeviceState *d)
{
    VirtIOS390Device *dev = to_virtio_s390_device(d);
    return dev->host_features;
}

/**************** S390 Virtio Bus Device Descriptions *******************/

static void s390_virtio_net_class_init(ObjectClass *klass, void *data)
@@ -626,16 +619,10 @@ static void s390_virtio_busdev_reset(DeviceState *dev)
    virtio_reset(_dev->vdev);
}

static Property virtio_s390_properties[] = {
    DEFINE_VIRTIO_COMMON_FEATURES(VirtIOS390Device, host_features),
    DEFINE_PROP_END_OF_LIST(),
};

static void virtio_s390_device_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *dc = DEVICE_CLASS(klass);

    dc->props = virtio_s390_properties;
    dc->realize = s390_virtio_busdev_realize;
    dc->bus_type = TYPE_S390_VIRTIO_BUS;
    dc->reset = s390_virtio_busdev_reset;
@@ -733,7 +720,6 @@ static void virtio_s390_bus_class_init(ObjectClass *klass, void *data)
    BusClass *bus_class = BUS_CLASS(klass);
    bus_class->max_dev = 1;
    k->notify = virtio_s390_notify;
    k->get_features = virtio_s390_get_features;
}

static const TypeInfo virtio_s390_bus_info = {
+0 −1
Original line number Diff line number Diff line
@@ -92,7 +92,6 @@ struct VirtIOS390Device {
    ram_addr_t feat_offs;
    uint8_t feat_len;
    VirtIODevice *vdev;
    uint32_t host_features;
    VirtioBusState bus;
};

+6 −23
Original line number Diff line number Diff line
@@ -381,8 +381,8 @@ static int virtio_ccw_cb(SubchDev *sch, CCW1 ccw)
                                                + sizeof(features.features),
                                                MEMTXATTRS_UNSPECIFIED,
                                                NULL);
            if (features.index < ARRAY_SIZE(dev->host_features)) {
                features.features = dev->host_features[features.index];
            if (features.index == 0) {
                features.features = vdev->host_features;
            } else {
                /* Return zeroes if the guest supports more feature bits. */
                features.features = 0;
@@ -417,7 +417,7 @@ static int virtio_ccw_cb(SubchDev *sch, CCW1 ccw)
                                                     ccw.cda,
                                                     MEMTXATTRS_UNSPECIFIED,
                                                     NULL);
            if (features.index < ARRAY_SIZE(dev->host_features)) {
            if (features.index == 0) {
                virtio_set_features(vdev, features.features);
            } else {
                /*
@@ -1071,14 +1071,6 @@ static void virtio_ccw_notify(DeviceState *d, uint16_t vector)
    }
}

static unsigned virtio_ccw_get_features(DeviceState *d)
{
    VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);

    /* Only the first 32 feature bits are used. */
    return dev->host_features[0];
}

static void virtio_ccw_reset(DeviceState *d)
{
    VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);
@@ -1390,14 +1382,12 @@ static void virtio_ccw_device_plugged(DeviceState *d)
{
    VirtioCcwDevice *dev = VIRTIO_CCW_DEVICE(d);
    SubchDev *sch = dev->sch;
    VirtIODevice *vdev = virtio_ccw_get_vdev(sch);

    sch->id.cu_model = virtio_bus_get_vdev_id(&dev->bus);

    /* Only the first 32 feature bits are used. */
    virtio_add_feature(&dev->host_features[0], VIRTIO_F_NOTIFY_ON_EMPTY);
    virtio_add_feature(&dev->host_features[0], VIRTIO_F_BAD_FEATURE);
    dev->host_features[0] = virtio_bus_get_vdev_features(&dev->bus,
                                                         dev->host_features[0]);
    virtio_add_feature(&vdev->host_features, VIRTIO_F_NOTIFY_ON_EMPTY);
    virtio_add_feature(&vdev->host_features, VIRTIO_F_BAD_FEATURE);

    css_generate_sch_crws(sch->cssid, sch->ssid, sch->schid,
                          d->hotplugged, 1);
@@ -1648,16 +1638,10 @@ static void virtio_ccw_busdev_unplug(HotplugHandler *hotplug_dev,
    object_unparent(OBJECT(dev));
}

static Property virtio_ccw_properties[] = {
    DEFINE_VIRTIO_COMMON_FEATURES(VirtioCcwDevice, host_features[0]),
    DEFINE_PROP_END_OF_LIST(),
};

static void virtio_ccw_device_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *dc = DEVICE_CLASS(klass);

    dc->props = virtio_ccw_properties;
    dc->realize = virtio_ccw_busdev_realize;
    dc->exit = virtio_ccw_busdev_exit;
    dc->bus_type = TYPE_VIRTUAL_CSS_BUS;
@@ -1722,7 +1706,6 @@ static void virtio_ccw_bus_class_init(ObjectClass *klass, void *data)

    bus_class->max_dev = 1;
    k->notify = virtio_ccw_notify;
    k->get_features = virtio_ccw_get_features;
    k->vmstate_change = virtio_ccw_vmstate_change;
    k->query_guest_notifiers = virtio_ccw_query_guest_notifiers;
    k->set_host_notifier = virtio_ccw_set_host_notifier;
+0 −4
Original line number Diff line number Diff line
@@ -68,9 +68,6 @@ typedef struct VirtIOCCWDeviceClass {
    int (*exit)(VirtioCcwDevice *dev);
} VirtIOCCWDeviceClass;

/* Change here if we want to support more feature bits. */
#define VIRTIO_CCW_FEATURE_SIZE 1

/* Performance improves when virtqueue kick processing is decoupled from the
 * vcpu thread using ioeventfd for some devices. */
#define VIRTIO_CCW_FLAG_USE_IOEVENTFD_BIT 1
@@ -88,7 +85,6 @@ struct VirtioCcwDevice {
    DeviceState parent_obj;
    SubchDev *sch;
    char *bus_id;
    uint32_t host_features[VIRTIO_CCW_FEATURE_SIZE];
    VirtioBusState bus;
    bool ioeventfd_started;
    bool ioeventfd_disabled;
+5 −13
Original line number Diff line number Diff line
@@ -44,12 +44,17 @@ int virtio_bus_device_plugged(VirtIODevice *vdev)
    BusState *qbus = BUS(qdev_get_parent_bus(qdev));
    VirtioBusState *bus = VIRTIO_BUS(qbus);
    VirtioBusClass *klass = VIRTIO_BUS_GET_CLASS(bus);
    VirtioDeviceClass *vdc = VIRTIO_DEVICE_GET_CLASS(vdev);

    DPRINTF("%s: plug device.\n", qbus->name);

    if (klass->device_plugged != NULL) {
        klass->device_plugged(qbus->parent);
    }

    /* Get the features of the plugged device. */
    assert(vdc->get_features != NULL);
    vdev->host_features = vdc->get_features(vdev, vdev->host_features);
    return 0;
}

@@ -96,19 +101,6 @@ size_t virtio_bus_get_vdev_config_len(VirtioBusState *bus)
    return vdev->config_len;
}

/* Get the features of the plugged device. */
uint32_t virtio_bus_get_vdev_features(VirtioBusState *bus,
                                    uint32_t requested_features)
{
    VirtIODevice *vdev = virtio_bus_get_device(bus);
    VirtioDeviceClass *k;

    assert(vdev != NULL);
    k = VIRTIO_DEVICE_GET_CLASS(vdev);
    assert(k->get_features != NULL);
    return k->get_features(vdev, requested_features);
}

/* Get bad features of the plugged device. */
uint32_t virtio_bus_get_vdev_bad_features(VirtioBusState *bus)
{
Loading