aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/char/virtio_console.c27
1 files changed, 21 insertions, 6 deletions
diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
index 0057bae2036..c40703759e2 100644
--- a/drivers/char/virtio_console.c
+++ b/drivers/char/virtio_console.c
@@ -1057,25 +1057,30 @@ static void config_intr(struct virtio_device *vdev)
1057 resize_console(find_port_by_id(portdev, 0)); 1057 resize_console(find_port_by_id(portdev, 0));
1058} 1058}
1059 1059
1060static void fill_queue(struct virtqueue *vq, spinlock_t *lock) 1060static unsigned int fill_queue(struct virtqueue *vq, spinlock_t *lock)
1061{ 1061{
1062 struct port_buffer *buf; 1062 struct port_buffer *buf;
1063 int ret; 1063 unsigned int ret;
1064 int err;
1064 1065
1066 ret = 0;
1065 do { 1067 do {
1066 buf = alloc_buf(PAGE_SIZE); 1068 buf = alloc_buf(PAGE_SIZE);
1067 if (!buf) 1069 if (!buf)
1068 break; 1070 break;
1069 1071
1070 spin_lock_irq(lock); 1072 spin_lock_irq(lock);
1071 ret = add_inbuf(vq, buf); 1073 err = add_inbuf(vq, buf);
1072 if (ret < 0) { 1074 if (err < 0) {
1073 spin_unlock_irq(lock); 1075 spin_unlock_irq(lock);
1074 free_buf(buf); 1076 free_buf(buf);
1075 break; 1077 break;
1076 } 1078 }
1079 ret++;
1077 spin_unlock_irq(lock); 1080 spin_unlock_irq(lock);
1078 } while (ret > 0); 1081 } while (err > 0);
1082
1083 return ret;
1079} 1084}
1080 1085
1081static int add_port(struct ports_device *portdev, u32 id) 1086static int add_port(struct ports_device *portdev, u32 id)
@@ -1430,7 +1435,13 @@ static int __devinit virtcons_probe(struct virtio_device *vdev)
1430 INIT_WORK(&portdev->control_work, &control_work_handler); 1435 INIT_WORK(&portdev->control_work, &control_work_handler);
1431 INIT_WORK(&portdev->config_work, &config_work_handler); 1436 INIT_WORK(&portdev->config_work, &config_work_handler);
1432 1437
1433 fill_queue(portdev->c_ivq, &portdev->cvq_lock); 1438 err = fill_queue(portdev->c_ivq, &portdev->cvq_lock);
1439 if (!err) {
1440 dev_err(&vdev->dev,
1441 "Error allocating buffers for control queue\n");
1442 err = -ENOMEM;
1443 goto free_vqs;
1444 }
1434 } 1445 }
1435 1446
1436 for (i = 0; i < portdev->config.nr_ports; i++) 1447 for (i = 0; i < portdev->config.nr_ports; i++)
@@ -1440,6 +1451,10 @@ static int __devinit virtcons_probe(struct virtio_device *vdev)
1440 early_put_chars = NULL; 1451 early_put_chars = NULL;
1441 return 0; 1452 return 0;
1442 1453
1454free_vqs:
1455 vdev->config->del_vqs(vdev);
1456 kfree(portdev->in_vqs);
1457 kfree(portdev->out_vqs);
1443free_chrdev: 1458free_chrdev:
1444 unregister_chrdev(portdev->chr_major, "virtio-portsdev"); 1459 unregister_chrdev(portdev->chr_major, "virtio-portsdev");
1445free: 1460free: