aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/s390/cio/device.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/s390/cio/device.c')
-rw-r--r--drivers/s390/cio/device.c71
1 files changed, 36 insertions, 35 deletions
diff --git a/drivers/s390/cio/device.c b/drivers/s390/cio/device.c
index d8d9b5b5cc56..dfef5e63cb7b 100644
--- a/drivers/s390/cio/device.c
+++ b/drivers/s390/cio/device.c
@@ -678,18 +678,11 @@ static const struct attribute_group *ccwdev_attr_groups[] = {
678 NULL, 678 NULL,
679}; 679};
680 680
681/* this is a simple abstraction for device_register that sets the 681static int ccw_device_add(struct ccw_device *cdev)
682 * correct bus type and adds the bus specific files */
683static int ccw_device_register(struct ccw_device *cdev)
684{ 682{
685 struct device *dev = &cdev->dev; 683 struct device *dev = &cdev->dev;
686 int ret;
687 684
688 dev->bus = &ccw_bus_type; 685 dev->bus = &ccw_bus_type;
689 ret = dev_set_name(&cdev->dev, "0.%x.%04x", cdev->private->dev_id.ssid,
690 cdev->private->dev_id.devno);
691 if (ret)
692 return ret;
693 return device_add(dev); 686 return device_add(dev);
694} 687}
695 688
@@ -764,22 +757,46 @@ static void ccw_device_todo(struct work_struct *work);
764static int io_subchannel_initialize_dev(struct subchannel *sch, 757static int io_subchannel_initialize_dev(struct subchannel *sch,
765 struct ccw_device *cdev) 758 struct ccw_device *cdev)
766{ 759{
767 cdev->private->cdev = cdev; 760 struct ccw_device_private *priv = cdev->private;
768 cdev->private->int_class = IRQIO_CIO; 761 int ret;
769 atomic_set(&cdev->private->onoff, 0); 762
763 priv->cdev = cdev;
764 priv->int_class = IRQIO_CIO;
765 priv->state = DEV_STATE_NOT_OPER;
766 priv->dev_id.devno = sch->schib.pmcw.dev;
767 priv->dev_id.ssid = sch->schid.ssid;
768 priv->schid = sch->schid;
769
770 INIT_WORK(&priv->todo_work, ccw_device_todo);
771 INIT_LIST_HEAD(&priv->cmb_list);
772 init_waitqueue_head(&priv->wait_q);
773 init_timer(&priv->timer);
774
775 atomic_set(&priv->onoff, 0);
776 cdev->ccwlock = sch->lock;
770 cdev->dev.parent = &sch->dev; 777 cdev->dev.parent = &sch->dev;
771 cdev->dev.release = ccw_device_release; 778 cdev->dev.release = ccw_device_release;
772 INIT_WORK(&cdev->private->todo_work, ccw_device_todo);
773 cdev->dev.groups = ccwdev_attr_groups; 779 cdev->dev.groups = ccwdev_attr_groups;
774 /* Do first half of device_register. */ 780 /* Do first half of device_register. */
775 device_initialize(&cdev->dev); 781 device_initialize(&cdev->dev);
782 ret = dev_set_name(&cdev->dev, "0.%x.%04x", cdev->private->dev_id.ssid,
783 cdev->private->dev_id.devno);
784 if (ret)
785 goto out_put;
776 if (!get_device(&sch->dev)) { 786 if (!get_device(&sch->dev)) {
777 /* Release reference from device_initialize(). */ 787 ret = -ENODEV;
778 put_device(&cdev->dev); 788 goto out_put;
779 return -ENODEV;
780 } 789 }
781 cdev->private->flags.initialized = 1; 790 priv->flags.initialized = 1;
791 spin_lock_irq(sch->lock);
792 sch_set_cdev(sch, cdev);
793 spin_unlock_irq(sch->lock);
782 return 0; 794 return 0;
795
796out_put:
797 /* Release reference from device_initialize(). */
798 put_device(&cdev->dev);
799 return ret;
783} 800}
784 801
785static struct ccw_device * io_subchannel_create_ccwdev(struct subchannel *sch) 802static struct ccw_device * io_subchannel_create_ccwdev(struct subchannel *sch)
@@ -858,7 +875,7 @@ static void io_subchannel_register(struct ccw_device *cdev)
858 dev_set_uevent_suppress(&sch->dev, 0); 875 dev_set_uevent_suppress(&sch->dev, 0);
859 kobject_uevent(&sch->dev.kobj, KOBJ_ADD); 876 kobject_uevent(&sch->dev.kobj, KOBJ_ADD);
860 /* make it known to the system */ 877 /* make it known to the system */
861 ret = ccw_device_register(cdev); 878 ret = ccw_device_add(cdev);
862 if (ret) { 879 if (ret) {
863 CIO_MSG_EVENT(0, "Could not register ccw dev 0.%x.%04x: %d\n", 880 CIO_MSG_EVENT(0, "Could not register ccw dev 0.%x.%04x: %d\n",
864 cdev->private->dev_id.ssid, 881 cdev->private->dev_id.ssid,
@@ -923,26 +940,11 @@ io_subchannel_recog_done(struct ccw_device *cdev)
923 940
924static void io_subchannel_recog(struct ccw_device *cdev, struct subchannel *sch) 941static void io_subchannel_recog(struct ccw_device *cdev, struct subchannel *sch)
925{ 942{
926 struct ccw_device_private *priv;
927
928 cdev->ccwlock = sch->lock;
929
930 /* Init private data. */
931 priv = cdev->private;
932 priv->dev_id.devno = sch->schib.pmcw.dev;
933 priv->dev_id.ssid = sch->schid.ssid;
934 priv->schid = sch->schid;
935 priv->state = DEV_STATE_NOT_OPER;
936 INIT_LIST_HEAD(&priv->cmb_list);
937 init_waitqueue_head(&priv->wait_q);
938 init_timer(&priv->timer);
939
940 /* Increase counter of devices currently in recognition. */ 943 /* Increase counter of devices currently in recognition. */
941 atomic_inc(&ccw_device_init_count); 944 atomic_inc(&ccw_device_init_count);
942 945
943 /* Start async. device sensing. */ 946 /* Start async. device sensing. */
944 spin_lock_irq(sch->lock); 947 spin_lock_irq(sch->lock);
945 sch_set_cdev(sch, cdev);
946 ccw_device_recognition(cdev); 948 ccw_device_recognition(cdev);
947 spin_unlock_irq(sch->lock); 949 spin_unlock_irq(sch->lock);
948} 950}
@@ -1083,7 +1085,7 @@ static int io_subchannel_probe(struct subchannel *sch)
1083 dev_set_uevent_suppress(&sch->dev, 0); 1085 dev_set_uevent_suppress(&sch->dev, 0);
1084 kobject_uevent(&sch->dev.kobj, KOBJ_ADD); 1086 kobject_uevent(&sch->dev.kobj, KOBJ_ADD);
1085 cdev = sch_get_cdev(sch); 1087 cdev = sch_get_cdev(sch);
1086 rc = ccw_device_register(cdev); 1088 rc = ccw_device_add(cdev);
1087 if (rc) { 1089 if (rc) {
1088 /* Release online reference. */ 1090 /* Release online reference. */
1089 put_device(&cdev->dev); 1091 put_device(&cdev->dev);
@@ -1597,7 +1599,6 @@ int __init ccw_device_enable_console(struct ccw_device *cdev)
1597 if (rc) 1599 if (rc)
1598 return rc; 1600 return rc;
1599 sch->driver = &io_subchannel_driver; 1601 sch->driver = &io_subchannel_driver;
1600 sch_set_cdev(sch, cdev);
1601 io_subchannel_recog(cdev, sch); 1602 io_subchannel_recog(cdev, sch);
1602 /* Now wait for the async. recognition to come to an end. */ 1603 /* Now wait for the async. recognition to come to an end. */
1603 spin_lock_irq(cdev->ccwlock); 1604 spin_lock_irq(cdev->ccwlock);
@@ -1639,6 +1640,7 @@ struct ccw_device * __init ccw_device_create_console(struct ccw_driver *drv)
1639 put_device(&sch->dev); 1640 put_device(&sch->dev);
1640 return ERR_PTR(-ENOMEM); 1641 return ERR_PTR(-ENOMEM);
1641 } 1642 }
1643 set_io_private(sch, io_priv);
1642 cdev = io_subchannel_create_ccwdev(sch); 1644 cdev = io_subchannel_create_ccwdev(sch);
1643 if (IS_ERR(cdev)) { 1645 if (IS_ERR(cdev)) {
1644 put_device(&sch->dev); 1646 put_device(&sch->dev);
@@ -1646,7 +1648,6 @@ struct ccw_device * __init ccw_device_create_console(struct ccw_driver *drv)
1646 return cdev; 1648 return cdev;
1647 } 1649 }
1648 cdev->drv = drv; 1650 cdev->drv = drv;
1649 set_io_private(sch, io_priv);
1650 ccw_device_set_int_class(cdev); 1651 ccw_device_set_int_class(cdev);
1651 return cdev; 1652 return cdev;
1652} 1653}