Merge tag 'sound-fix-3.18-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai...
[cascardo/linux.git] / drivers / s390 / block / dasd.c
index 5df05f2..329db99 100644 (file)
@@ -1660,6 +1660,14 @@ void dasd_int_handler(struct ccw_device *cdev, unsigned long intparm,
                device->discipline->check_for_device_change(device, cqr, irb);
                dasd_put_device(device);
        }
+
+       /* check for for attention message */
+       if (scsw_dstat(&irb->scsw) & DEV_STAT_ATTENTION) {
+               device = dasd_device_from_cdev_locked(cdev);
+               device->discipline->check_attention(device, irb->esw.esw1.lpum);
+               dasd_put_device(device);
+       }
+
        if (!cqr)
                return;
 
@@ -2261,8 +2269,8 @@ static inline int _wait_for_wakeup_queue(struct list_head *ccw_queue)
 static int _dasd_sleep_on_queue(struct list_head *ccw_queue, int interruptible)
 {
        struct dasd_device *device;
-       int rc;
        struct dasd_ccw_req *cqr, *n;
+       int rc;
 
 retry:
        list_for_each_entry_safe(cqr, n, ccw_queue, blocklist) {
@@ -2310,21 +2318,26 @@ retry:
                /*
                 * for alias devices simplify error recovery and
                 * return to upper layer
+                * do not skip ERP requests
                 */
-               if (cqr->startdev != cqr->basedev &&
+               if (cqr->startdev != cqr->basedev && !cqr->refers &&
                    (cqr->status == DASD_CQR_TERMINATED ||
                     cqr->status == DASD_CQR_NEED_ERP))
                        return -EAGAIN;
-               else {
-                       /* normal recovery for basedev IO */
-                       if (__dasd_sleep_on_erp(cqr)) {
-                               if (!cqr->status == DASD_CQR_TERMINATED &&
-                                   !cqr->status == DASD_CQR_NEED_ERP)
-                                       break;
-                               rc = 1;
-                       }
+
+               /* normal recovery for basedev IO */
+               if (__dasd_sleep_on_erp(cqr)) {
+                       goto retry;
+                       /* remember that ERP was needed */
+                       rc = 1;
+                       /* skip processing for active cqr */
+                       if (cqr->status != DASD_CQR_TERMINATED &&
+                           cqr->status != DASD_CQR_NEED_ERP)
+                               break;
                }
        }
+
+       /* start ERP requests in upper loop */
        if (rc)
                goto retry;