summaryrefslogtreecommitdiffstats
path: root/drivers/s390
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/s390')
-rw-r--r--drivers/s390/kvm/kvm_virtio.c11
-rw-r--r--drivers/s390/kvm/virtio_ccw.c20
2 files changed, 18 insertions, 13 deletions
diff --git a/drivers/s390/kvm/kvm_virtio.c b/drivers/s390/kvm/kvm_virtio.c
index 6711e65764b5..2ea6165366b6 100644
--- a/drivers/s390/kvm/kvm_virtio.c
+++ b/drivers/s390/kvm/kvm_virtio.c
@@ -443,29 +443,30 @@ static int __init test_devices_support(unsigned long addr)
}
/*
* Init function for virtio
- * devices are in a single page above top of "normal" mem
+ * devices are in a single page above top of "normal" + standby mem
*/
static int __init kvm_devices_init(void)
{
int rc;
+ unsigned long total_memory_size = sclp_get_rzm() * sclp_get_rnmax();
if (!MACHINE_IS_KVM)
return -ENODEV;
- if (test_devices_support(real_memory_size) < 0)
+ if (test_devices_support(total_memory_size) < 0)
return -ENODEV;
- rc = vmem_add_mapping(real_memory_size, PAGE_SIZE);
+ rc = vmem_add_mapping(total_memory_size, PAGE_SIZE);
if (rc)
return rc;
- kvm_devices = (void *) real_memory_size;
+ kvm_devices = (void *) total_memory_size;
kvm_root = root_device_register("kvm_s390");
if (IS_ERR(kvm_root)) {
rc = PTR_ERR(kvm_root);
printk(KERN_ERR "Could not register kvm_s390 root device");
- vmem_remove_mapping(real_memory_size, PAGE_SIZE);
+ vmem_remove_mapping(total_memory_size, PAGE_SIZE);
return rc;
}
diff --git a/drivers/s390/kvm/virtio_ccw.c b/drivers/s390/kvm/virtio_ccw.c
index fb877b59ec57..779dc5136291 100644
--- a/drivers/s390/kvm/virtio_ccw.c
+++ b/drivers/s390/kvm/virtio_ccw.c
@@ -31,6 +31,7 @@
#include <asm/irq.h>
#include <asm/cio.h>
#include <asm/ccwdev.h>
+#include <asm/virtio-ccw.h>
/*
* virtio related functions
@@ -77,12 +78,9 @@ struct virtio_ccw_vq_info {
void *queue;
struct vq_info_block *info_block;
struct list_head node;
+ long cookie;
};
-#define KVM_VIRTIO_CCW_RING_ALIGN 4096
-
-#define KVM_S390_VIRTIO_CCW_NOTIFY 3
-
#define CCW_CMD_SET_VQ 0x13
#define CCW_CMD_VDEV_RESET 0x33
#define CCW_CMD_SET_IND 0x43
@@ -135,8 +133,11 @@ static int ccw_io_helper(struct virtio_ccw_device *vcdev,
do {
spin_lock_irqsave(get_ccwdev_lock(vcdev->cdev), flags);
ret = ccw_device_start(vcdev->cdev, ccw, intparm, 0, 0);
- if (!ret)
+ if (!ret) {
+ if (!vcdev->curr_io)
+ vcdev->err = 0;
vcdev->curr_io |= flag;
+ }
spin_unlock_irqrestore(get_ccwdev_lock(vcdev->cdev), flags);
cpu_relax();
} while (ret == -EBUSY);
@@ -145,15 +146,18 @@ static int ccw_io_helper(struct virtio_ccw_device *vcdev,
}
static inline long do_kvm_notify(struct subchannel_id schid,
- unsigned long queue_index)
+ unsigned long queue_index,
+ long cookie)
{
register unsigned long __nr asm("1") = KVM_S390_VIRTIO_CCW_NOTIFY;
register struct subchannel_id __schid asm("2") = schid;
register unsigned long __index asm("3") = queue_index;
register long __rc asm("2");
+ register long __cookie asm("4") = cookie;
asm volatile ("diag 2,4,0x500\n"
- : "=d" (__rc) : "d" (__nr), "d" (__schid), "d" (__index)
+ : "=d" (__rc) : "d" (__nr), "d" (__schid), "d" (__index),
+ "d"(__cookie)
: "memory", "cc");
return __rc;
}
@@ -166,7 +170,7 @@ static void virtio_ccw_kvm_notify(struct virtqueue *vq)
vcdev = to_vc_device(info->vq->vdev);
ccw_device_get_schid(vcdev->cdev, &schid);
- do_kvm_notify(schid, vq->index);
+ info->cookie = do_kvm_notify(schid, vq->index, info->cookie);
}
static int virtio_ccw_read_vq_conf(struct virtio_ccw_device *vcdev,