aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2011-04-08 10:36:14 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2011-04-08 10:36:14 -0400
commitbb3c90f0de7b34995b5e35cf5dc97a3d428b3761 (patch)
treed5d07b61c0ab6d8688579a255e2b97b624637336 /drivers
parent3d762ca1cdf38b5fb7d1774734176d1d4d56bbb7 (diff)
parent8838101183bba239f100b0cfe31d9ebbfc2f1bd4 (diff)
Merge branch 'for-linus' of git://git390.marist.edu/pub/scm/linux-2.6
* 'for-linus' of git://git390.marist.edu/pub/scm/linux-2.6: [S390] compile fix for latest binutils [S390] cio: prevent purging of CCW devices in the online state [S390] qdio: fix init sequence [S390] Fix parameter passing for smp_switch_to_cpu() [S390] oprofile s390: prevent stack corruption
Diffstat (limited to 'drivers')
-rw-r--r--drivers/s390/cio/device.c24
-rw-r--r--drivers/s390/cio/qdio_main.c16
2 files changed, 26 insertions, 14 deletions
diff --git a/drivers/s390/cio/device.c b/drivers/s390/cio/device.c
index df14c51f6532..8e04c00cf0ad 100644
--- a/drivers/s390/cio/device.c
+++ b/drivers/s390/cio/device.c
@@ -541,15 +541,24 @@ static ssize_t online_store (struct device *dev, struct device_attribute *attr,
541 int force, ret; 541 int force, ret;
542 unsigned long i; 542 unsigned long i;
543 543
544 if (!dev_fsm_final_state(cdev) && 544 /* Prevent conflict between multiple on-/offline processing requests. */
545 cdev->private->state != DEV_STATE_DISCONNECTED)
546 return -EAGAIN;
547 if (atomic_cmpxchg(&cdev->private->onoff, 0, 1) != 0) 545 if (atomic_cmpxchg(&cdev->private->onoff, 0, 1) != 0)
548 return -EAGAIN; 546 return -EAGAIN;
547 /* Prevent conflict between internal I/Os and on-/offline processing. */
548 if (!dev_fsm_final_state(cdev) &&
549 cdev->private->state != DEV_STATE_DISCONNECTED) {
550 ret = -EAGAIN;
551 goto out_onoff;
552 }
553 /* Prevent conflict between pending work and on-/offline processing.*/
554 if (work_pending(&cdev->private->todo_work)) {
555 ret = -EAGAIN;
556 goto out_onoff;
557 }
549 558
550 if (cdev->drv && !try_module_get(cdev->drv->driver.owner)) { 559 if (cdev->drv && !try_module_get(cdev->drv->driver.owner)) {
551 atomic_set(&cdev->private->onoff, 0); 560 ret = -EINVAL;
552 return -EINVAL; 561 goto out_onoff;
553 } 562 }
554 if (!strncmp(buf, "force\n", count)) { 563 if (!strncmp(buf, "force\n", count)) {
555 force = 1; 564 force = 1;
@@ -574,6 +583,7 @@ static ssize_t online_store (struct device *dev, struct device_attribute *attr,
574out: 583out:
575 if (cdev->drv) 584 if (cdev->drv)
576 module_put(cdev->drv->driver.owner); 585 module_put(cdev->drv->driver.owner);
586out_onoff:
577 atomic_set(&cdev->private->onoff, 0); 587 atomic_set(&cdev->private->onoff, 0);
578 return (ret < 0) ? ret : count; 588 return (ret < 0) ? ret : count;
579} 589}
@@ -1311,10 +1321,12 @@ static int purge_fn(struct device *dev, void *data)
1311 1321
1312 spin_lock_irq(cdev->ccwlock); 1322 spin_lock_irq(cdev->ccwlock);
1313 if (is_blacklisted(id->ssid, id->devno) && 1323 if (is_blacklisted(id->ssid, id->devno) &&
1314 (cdev->private->state == DEV_STATE_OFFLINE)) { 1324 (cdev->private->state == DEV_STATE_OFFLINE) &&
1325 (atomic_cmpxchg(&cdev->private->onoff, 0, 1) == 0)) {
1315 CIO_MSG_EVENT(3, "ccw: purging 0.%x.%04x\n", id->ssid, 1326 CIO_MSG_EVENT(3, "ccw: purging 0.%x.%04x\n", id->ssid,
1316 id->devno); 1327 id->devno);
1317 ccw_device_sched_todo(cdev, CDEV_TODO_UNREG); 1328 ccw_device_sched_todo(cdev, CDEV_TODO_UNREG);
1329 atomic_set(&cdev->private->onoff, 0);
1318 } 1330 }
1319 spin_unlock_irq(cdev->ccwlock); 1331 spin_unlock_irq(cdev->ccwlock);
1320 /* Abort loop in case of pending signal. */ 1332 /* Abort loop in case of pending signal. */
diff --git a/drivers/s390/cio/qdio_main.c b/drivers/s390/cio/qdio_main.c
index 479c665e9e7c..c532ba929ccd 100644
--- a/drivers/s390/cio/qdio_main.c
+++ b/drivers/s390/cio/qdio_main.c
@@ -1649,26 +1649,26 @@ static int __init init_QDIO(void)
1649{ 1649{
1650 int rc; 1650 int rc;
1651 1651
1652 rc = qdio_setup_init(); 1652 rc = qdio_debug_init();
1653 if (rc) 1653 if (rc)
1654 return rc; 1654 return rc;
1655 rc = qdio_setup_init();
1656 if (rc)
1657 goto out_debug;
1655 rc = tiqdio_allocate_memory(); 1658 rc = tiqdio_allocate_memory();
1656 if (rc) 1659 if (rc)
1657 goto out_cache; 1660 goto out_cache;
1658 rc = qdio_debug_init();
1659 if (rc)
1660 goto out_ti;
1661 rc = tiqdio_register_thinints(); 1661 rc = tiqdio_register_thinints();
1662 if (rc) 1662 if (rc)
1663 goto out_debug; 1663 goto out_ti;
1664 return 0; 1664 return 0;
1665 1665
1666out_debug:
1667 qdio_debug_exit();
1668out_ti: 1666out_ti:
1669 tiqdio_free_memory(); 1667 tiqdio_free_memory();
1670out_cache: 1668out_cache:
1671 qdio_setup_exit(); 1669 qdio_setup_exit();
1670out_debug:
1671 qdio_debug_exit();
1672 return rc; 1672 return rc;
1673} 1673}
1674 1674
@@ -1676,8 +1676,8 @@ static void __exit exit_QDIO(void)
1676{ 1676{
1677 tiqdio_unregister_thinints(); 1677 tiqdio_unregister_thinints();
1678 tiqdio_free_memory(); 1678 tiqdio_free_memory();
1679 qdio_debug_exit();
1680 qdio_setup_exit(); 1679 qdio_setup_exit();
1680 qdio_debug_exit();
1681} 1681}
1682 1682
1683module_init(init_QDIO); 1683module_init(init_QDIO);