Loading drivers/scsi/scsi_lib.c +4 −5 Original line number Original line Diff line number Diff line Loading @@ -276,11 +276,10 @@ int scsi_execute(struct scsi_device *sdev, const unsigned char *cmd, } } EXPORT_SYMBOL(scsi_execute); EXPORT_SYMBOL(scsi_execute); int scsi_execute_req_flags(struct scsi_device *sdev, const unsigned char *cmd, int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, int data_direction, void *buffer, unsigned bufflen, int data_direction, void *buffer, unsigned bufflen, struct scsi_sense_hdr *sshdr, int timeout, int retries, struct scsi_sense_hdr *sshdr, int timeout, int retries, int *resid) int *resid, int flags) { { char *sense = NULL; char *sense = NULL; int result; int result; Loading @@ -291,14 +290,14 @@ int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, return DRIVER_ERROR << 24; return DRIVER_ERROR << 24; } } result = scsi_execute(sdev, cmd, data_direction, buffer, bufflen, result = scsi_execute(sdev, cmd, data_direction, buffer, bufflen, sense, timeout, retries, 0, resid); sense, timeout, retries, flags, resid); if (sshdr) if (sshdr) scsi_normalize_sense(sense, SCSI_SENSE_BUFFERSIZE, sshdr); scsi_normalize_sense(sense, SCSI_SENSE_BUFFERSIZE, sshdr); kfree(sense); kfree(sense); return result; return result; } } EXPORT_SYMBOL(scsi_execute_req); EXPORT_SYMBOL(scsi_execute_req_flags); /* /* * Function: scsi_init_cmd_errh() * Function: scsi_init_cmd_errh() Loading drivers/scsi/scsi_pm.c +71 −13 Original line number Original line Diff line number Diff line Loading @@ -144,33 +144,83 @@ static int scsi_bus_restore(struct device *dev) #ifdef CONFIG_PM_RUNTIME #ifdef CONFIG_PM_RUNTIME static int scsi_runtime_suspend(struct device *dev) static int sdev_blk_runtime_suspend(struct scsi_device *sdev, int (*cb)(struct device *)) { int err; err = blk_pre_runtime_suspend(sdev->request_queue); if (err) return err; if (cb) err = cb(&sdev->sdev_gendev); blk_post_runtime_suspend(sdev->request_queue, err); return err; } static int sdev_runtime_suspend(struct device *dev) { { int err = 0; const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; int (*cb)(struct device *) = pm ? pm->runtime_suspend : NULL; struct scsi_device *sdev = to_scsi_device(dev); int err; dev_dbg(dev, "scsi_runtime_suspend\n"); if (sdev->request_queue->dev) if (scsi_is_sdev_device(dev)) { return sdev_blk_runtime_suspend(sdev, cb); err = scsi_dev_type_suspend(dev, pm ? pm->runtime_suspend : NULL); err = scsi_dev_type_suspend(dev, cb); if (err == -EAGAIN) if (err == -EAGAIN) pm_schedule_suspend(dev, jiffies_to_msecs( pm_schedule_suspend(dev, jiffies_to_msecs( round_jiffies_up_relative(HZ/10))); round_jiffies_up_relative(HZ/10))); return err; } } static int scsi_runtime_suspend(struct device *dev) { int err = 0; dev_dbg(dev, "scsi_runtime_suspend\n"); if (scsi_is_sdev_device(dev)) err = sdev_runtime_suspend(dev); /* Insert hooks here for targets, hosts, and transport classes */ /* Insert hooks here for targets, hosts, and transport classes */ return err; return err; } } static int scsi_runtime_resume(struct device *dev) static int sdev_blk_runtime_resume(struct scsi_device *sdev, int (*cb)(struct device *)) { { int err = 0; int err = 0; blk_pre_runtime_resume(sdev->request_queue); if (cb) err = cb(&sdev->sdev_gendev); blk_post_runtime_resume(sdev->request_queue, err); return err; } static int sdev_runtime_resume(struct device *dev) { struct scsi_device *sdev = to_scsi_device(dev); const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; int (*cb)(struct device *) = pm ? pm->runtime_resume : NULL; if (sdev->request_queue->dev) return sdev_blk_runtime_resume(sdev, cb); else return scsi_dev_type_resume(dev, cb); } static int scsi_runtime_resume(struct device *dev) { int err = 0; dev_dbg(dev, "scsi_runtime_resume\n"); dev_dbg(dev, "scsi_runtime_resume\n"); if (scsi_is_sdev_device(dev)) if (scsi_is_sdev_device(dev)) err = scsi_dev_type_resume(dev, pm ? pm->runtime_resume : NULL); err = sdev_runtime_resume(dev); /* Insert hooks here for targets, hosts, and transport classes */ /* Insert hooks here for targets, hosts, and transport classes */ Loading @@ -185,10 +235,18 @@ static int scsi_runtime_idle(struct device *dev) /* Insert hooks here for targets, hosts, and transport classes */ /* Insert hooks here for targets, hosts, and transport classes */ if (scsi_is_sdev_device(dev)) if (scsi_is_sdev_device(dev)) { err = pm_schedule_suspend(dev, 100); struct scsi_device *sdev = to_scsi_device(dev); else if (sdev->request_queue->dev) { pm_runtime_mark_last_busy(dev); err = pm_runtime_autosuspend(dev); } else { err = pm_runtime_suspend(dev); err = pm_runtime_suspend(dev); } } else { err = pm_runtime_suspend(dev); } return err; return err; } } Loading drivers/scsi/sd.c +6 −16 Original line number Original line Diff line number Diff line Loading @@ -1136,10 +1136,6 @@ static int sd_open(struct block_device *bdev, fmode_t mode) sdev = sdkp->device; sdev = sdkp->device; retval = scsi_autopm_get_device(sdev); if (retval) goto error_autopm; /* /* * If the device is in error recovery, wait until it is done. * If the device is in error recovery, wait until it is done. * If the device is offline, then disallow any access to it. * If the device is offline, then disallow any access to it. Loading Loading @@ -1184,8 +1180,6 @@ static int sd_open(struct block_device *bdev, fmode_t mode) return 0; return 0; error_out: error_out: scsi_autopm_put_device(sdev); error_autopm: scsi_disk_put(sdkp); scsi_disk_put(sdkp); return retval; return retval; } } Loading Loading @@ -1220,7 +1214,6 @@ static void sd_release(struct gendisk *disk, fmode_t mode) * XXX is followed by a "rmmod sd_mod"? * XXX is followed by a "rmmod sd_mod"? */ */ scsi_autopm_put_device(sdev); scsi_disk_put(sdkp); scsi_disk_put(sdkp); } } Loading Loading @@ -1381,14 +1374,9 @@ static unsigned int sd_check_events(struct gendisk *disk, unsigned int clearing) retval = -ENODEV; retval = -ENODEV; if (scsi_block_when_processing_errors(sdp)) { if (scsi_block_when_processing_errors(sdp)) { retval = scsi_autopm_get_device(sdp); if (retval) goto out; sshdr = kzalloc(sizeof(*sshdr), GFP_KERNEL); sshdr = kzalloc(sizeof(*sshdr), GFP_KERNEL); retval = scsi_test_unit_ready(sdp, SD_TIMEOUT, SD_MAX_RETRIES, retval = scsi_test_unit_ready(sdp, SD_TIMEOUT, SD_MAX_RETRIES, sshdr); sshdr); scsi_autopm_put_device(sdp); } } /* failed to execute TUR, assume media not present */ /* failed to execute TUR, assume media not present */ Loading Loading @@ -1438,8 +1426,9 @@ static int sd_sync_cache(struct scsi_disk *sdkp) * Leave the rest of the command zero to indicate * Leave the rest of the command zero to indicate * flush everything. * flush everything. */ */ res = scsi_execute_req(sdp, cmd, DMA_NONE, NULL, 0, &sshdr, res = scsi_execute_req_flags(sdp, cmd, DMA_NONE, NULL, 0, SD_FLUSH_TIMEOUT, SD_MAX_RETRIES, NULL); &sshdr, SD_FLUSH_TIMEOUT, SD_MAX_RETRIES, NULL, REQ_PM); if (res == 0) if (res == 0) break; break; } } Loading Loading @@ -2857,6 +2846,7 @@ static void sd_probe_async(void *data, async_cookie_t cookie) sd_printk(KERN_NOTICE, sdkp, "Attached SCSI %sdisk\n", sd_printk(KERN_NOTICE, sdkp, "Attached SCSI %sdisk\n", sdp->removable ? "removable " : ""); sdp->removable ? "removable " : ""); blk_pm_runtime_init(sdp->request_queue, dev); scsi_autopm_put_device(sdp); scsi_autopm_put_device(sdp); put_device(&sdkp->dev); put_device(&sdkp->dev); } } Loading Loading @@ -3040,8 +3030,8 @@ static int sd_start_stop_device(struct scsi_disk *sdkp, int start) if (!scsi_device_online(sdp)) if (!scsi_device_online(sdp)) return -ENODEV; return -ENODEV; res = scsi_execute_req(sdp, cmd, DMA_NONE, NULL, 0, &sshdr, res = scsi_execute_req_flags(sdp, cmd, DMA_NONE, NULL, 0, &sshdr, SD_TIMEOUT, SD_MAX_RETRIES, NULL); SD_TIMEOUT, SD_MAX_RETRIES, NULL, REQ_PM); if (res) { if (res) { sd_printk(KERN_WARNING, sdkp, "START_STOP FAILED\n"); sd_printk(KERN_WARNING, sdkp, "START_STOP FAILED\n"); sd_print_result(sdkp, res); sd_print_result(sdkp, res); Loading include/scsi/scsi_device.h +12 −4 Original line number Original line Diff line number Diff line Loading @@ -394,10 +394,18 @@ extern int scsi_execute(struct scsi_device *sdev, const unsigned char *cmd, int data_direction, void *buffer, unsigned bufflen, int data_direction, void *buffer, unsigned bufflen, unsigned char *sense, int timeout, int retries, unsigned char *sense, int timeout, int retries, int flag, int *resid); int flag, int *resid); extern int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, extern int scsi_execute_req_flags(struct scsi_device *sdev, int data_direction, void *buffer, unsigned bufflen, const unsigned char *cmd, int data_direction, void *buffer, struct scsi_sense_hdr *, int timeout, int retries, unsigned bufflen, struct scsi_sense_hdr *sshdr, int timeout, int *resid); int retries, int *resid, int flags); static inline int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, int data_direction, void *buffer, unsigned bufflen, struct scsi_sense_hdr *sshdr, int timeout, int retries, int *resid) { return scsi_execute_req_flags(sdev, cmd, data_direction, buffer, bufflen, sshdr, timeout, retries, resid, 0); } extern void sdev_disable_disk_events(struct scsi_device *sdev); extern void sdev_disable_disk_events(struct scsi_device *sdev); extern void sdev_enable_disk_events(struct scsi_device *sdev); extern void sdev_enable_disk_events(struct scsi_device *sdev); Loading Loading
drivers/scsi/scsi_lib.c +4 −5 Original line number Original line Diff line number Diff line Loading @@ -276,11 +276,10 @@ int scsi_execute(struct scsi_device *sdev, const unsigned char *cmd, } } EXPORT_SYMBOL(scsi_execute); EXPORT_SYMBOL(scsi_execute); int scsi_execute_req_flags(struct scsi_device *sdev, const unsigned char *cmd, int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, int data_direction, void *buffer, unsigned bufflen, int data_direction, void *buffer, unsigned bufflen, struct scsi_sense_hdr *sshdr, int timeout, int retries, struct scsi_sense_hdr *sshdr, int timeout, int retries, int *resid) int *resid, int flags) { { char *sense = NULL; char *sense = NULL; int result; int result; Loading @@ -291,14 +290,14 @@ int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, return DRIVER_ERROR << 24; return DRIVER_ERROR << 24; } } result = scsi_execute(sdev, cmd, data_direction, buffer, bufflen, result = scsi_execute(sdev, cmd, data_direction, buffer, bufflen, sense, timeout, retries, 0, resid); sense, timeout, retries, flags, resid); if (sshdr) if (sshdr) scsi_normalize_sense(sense, SCSI_SENSE_BUFFERSIZE, sshdr); scsi_normalize_sense(sense, SCSI_SENSE_BUFFERSIZE, sshdr); kfree(sense); kfree(sense); return result; return result; } } EXPORT_SYMBOL(scsi_execute_req); EXPORT_SYMBOL(scsi_execute_req_flags); /* /* * Function: scsi_init_cmd_errh() * Function: scsi_init_cmd_errh() Loading
drivers/scsi/scsi_pm.c +71 −13 Original line number Original line Diff line number Diff line Loading @@ -144,33 +144,83 @@ static int scsi_bus_restore(struct device *dev) #ifdef CONFIG_PM_RUNTIME #ifdef CONFIG_PM_RUNTIME static int scsi_runtime_suspend(struct device *dev) static int sdev_blk_runtime_suspend(struct scsi_device *sdev, int (*cb)(struct device *)) { int err; err = blk_pre_runtime_suspend(sdev->request_queue); if (err) return err; if (cb) err = cb(&sdev->sdev_gendev); blk_post_runtime_suspend(sdev->request_queue, err); return err; } static int sdev_runtime_suspend(struct device *dev) { { int err = 0; const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; int (*cb)(struct device *) = pm ? pm->runtime_suspend : NULL; struct scsi_device *sdev = to_scsi_device(dev); int err; dev_dbg(dev, "scsi_runtime_suspend\n"); if (sdev->request_queue->dev) if (scsi_is_sdev_device(dev)) { return sdev_blk_runtime_suspend(sdev, cb); err = scsi_dev_type_suspend(dev, pm ? pm->runtime_suspend : NULL); err = scsi_dev_type_suspend(dev, cb); if (err == -EAGAIN) if (err == -EAGAIN) pm_schedule_suspend(dev, jiffies_to_msecs( pm_schedule_suspend(dev, jiffies_to_msecs( round_jiffies_up_relative(HZ/10))); round_jiffies_up_relative(HZ/10))); return err; } } static int scsi_runtime_suspend(struct device *dev) { int err = 0; dev_dbg(dev, "scsi_runtime_suspend\n"); if (scsi_is_sdev_device(dev)) err = sdev_runtime_suspend(dev); /* Insert hooks here for targets, hosts, and transport classes */ /* Insert hooks here for targets, hosts, and transport classes */ return err; return err; } } static int scsi_runtime_resume(struct device *dev) static int sdev_blk_runtime_resume(struct scsi_device *sdev, int (*cb)(struct device *)) { { int err = 0; int err = 0; blk_pre_runtime_resume(sdev->request_queue); if (cb) err = cb(&sdev->sdev_gendev); blk_post_runtime_resume(sdev->request_queue, err); return err; } static int sdev_runtime_resume(struct device *dev) { struct scsi_device *sdev = to_scsi_device(dev); const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; const struct dev_pm_ops *pm = dev->driver ? dev->driver->pm : NULL; int (*cb)(struct device *) = pm ? pm->runtime_resume : NULL; if (sdev->request_queue->dev) return sdev_blk_runtime_resume(sdev, cb); else return scsi_dev_type_resume(dev, cb); } static int scsi_runtime_resume(struct device *dev) { int err = 0; dev_dbg(dev, "scsi_runtime_resume\n"); dev_dbg(dev, "scsi_runtime_resume\n"); if (scsi_is_sdev_device(dev)) if (scsi_is_sdev_device(dev)) err = scsi_dev_type_resume(dev, pm ? pm->runtime_resume : NULL); err = sdev_runtime_resume(dev); /* Insert hooks here for targets, hosts, and transport classes */ /* Insert hooks here for targets, hosts, and transport classes */ Loading @@ -185,10 +235,18 @@ static int scsi_runtime_idle(struct device *dev) /* Insert hooks here for targets, hosts, and transport classes */ /* Insert hooks here for targets, hosts, and transport classes */ if (scsi_is_sdev_device(dev)) if (scsi_is_sdev_device(dev)) { err = pm_schedule_suspend(dev, 100); struct scsi_device *sdev = to_scsi_device(dev); else if (sdev->request_queue->dev) { pm_runtime_mark_last_busy(dev); err = pm_runtime_autosuspend(dev); } else { err = pm_runtime_suspend(dev); err = pm_runtime_suspend(dev); } } else { err = pm_runtime_suspend(dev); } return err; return err; } } Loading
drivers/scsi/sd.c +6 −16 Original line number Original line Diff line number Diff line Loading @@ -1136,10 +1136,6 @@ static int sd_open(struct block_device *bdev, fmode_t mode) sdev = sdkp->device; sdev = sdkp->device; retval = scsi_autopm_get_device(sdev); if (retval) goto error_autopm; /* /* * If the device is in error recovery, wait until it is done. * If the device is in error recovery, wait until it is done. * If the device is offline, then disallow any access to it. * If the device is offline, then disallow any access to it. Loading Loading @@ -1184,8 +1180,6 @@ static int sd_open(struct block_device *bdev, fmode_t mode) return 0; return 0; error_out: error_out: scsi_autopm_put_device(sdev); error_autopm: scsi_disk_put(sdkp); scsi_disk_put(sdkp); return retval; return retval; } } Loading Loading @@ -1220,7 +1214,6 @@ static void sd_release(struct gendisk *disk, fmode_t mode) * XXX is followed by a "rmmod sd_mod"? * XXX is followed by a "rmmod sd_mod"? */ */ scsi_autopm_put_device(sdev); scsi_disk_put(sdkp); scsi_disk_put(sdkp); } } Loading Loading @@ -1381,14 +1374,9 @@ static unsigned int sd_check_events(struct gendisk *disk, unsigned int clearing) retval = -ENODEV; retval = -ENODEV; if (scsi_block_when_processing_errors(sdp)) { if (scsi_block_when_processing_errors(sdp)) { retval = scsi_autopm_get_device(sdp); if (retval) goto out; sshdr = kzalloc(sizeof(*sshdr), GFP_KERNEL); sshdr = kzalloc(sizeof(*sshdr), GFP_KERNEL); retval = scsi_test_unit_ready(sdp, SD_TIMEOUT, SD_MAX_RETRIES, retval = scsi_test_unit_ready(sdp, SD_TIMEOUT, SD_MAX_RETRIES, sshdr); sshdr); scsi_autopm_put_device(sdp); } } /* failed to execute TUR, assume media not present */ /* failed to execute TUR, assume media not present */ Loading Loading @@ -1438,8 +1426,9 @@ static int sd_sync_cache(struct scsi_disk *sdkp) * Leave the rest of the command zero to indicate * Leave the rest of the command zero to indicate * flush everything. * flush everything. */ */ res = scsi_execute_req(sdp, cmd, DMA_NONE, NULL, 0, &sshdr, res = scsi_execute_req_flags(sdp, cmd, DMA_NONE, NULL, 0, SD_FLUSH_TIMEOUT, SD_MAX_RETRIES, NULL); &sshdr, SD_FLUSH_TIMEOUT, SD_MAX_RETRIES, NULL, REQ_PM); if (res == 0) if (res == 0) break; break; } } Loading Loading @@ -2857,6 +2846,7 @@ static void sd_probe_async(void *data, async_cookie_t cookie) sd_printk(KERN_NOTICE, sdkp, "Attached SCSI %sdisk\n", sd_printk(KERN_NOTICE, sdkp, "Attached SCSI %sdisk\n", sdp->removable ? "removable " : ""); sdp->removable ? "removable " : ""); blk_pm_runtime_init(sdp->request_queue, dev); scsi_autopm_put_device(sdp); scsi_autopm_put_device(sdp); put_device(&sdkp->dev); put_device(&sdkp->dev); } } Loading Loading @@ -3040,8 +3030,8 @@ static int sd_start_stop_device(struct scsi_disk *sdkp, int start) if (!scsi_device_online(sdp)) if (!scsi_device_online(sdp)) return -ENODEV; return -ENODEV; res = scsi_execute_req(sdp, cmd, DMA_NONE, NULL, 0, &sshdr, res = scsi_execute_req_flags(sdp, cmd, DMA_NONE, NULL, 0, &sshdr, SD_TIMEOUT, SD_MAX_RETRIES, NULL); SD_TIMEOUT, SD_MAX_RETRIES, NULL, REQ_PM); if (res) { if (res) { sd_printk(KERN_WARNING, sdkp, "START_STOP FAILED\n"); sd_printk(KERN_WARNING, sdkp, "START_STOP FAILED\n"); sd_print_result(sdkp, res); sd_print_result(sdkp, res); Loading
include/scsi/scsi_device.h +12 −4 Original line number Original line Diff line number Diff line Loading @@ -394,10 +394,18 @@ extern int scsi_execute(struct scsi_device *sdev, const unsigned char *cmd, int data_direction, void *buffer, unsigned bufflen, int data_direction, void *buffer, unsigned bufflen, unsigned char *sense, int timeout, int retries, unsigned char *sense, int timeout, int retries, int flag, int *resid); int flag, int *resid); extern int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, extern int scsi_execute_req_flags(struct scsi_device *sdev, int data_direction, void *buffer, unsigned bufflen, const unsigned char *cmd, int data_direction, void *buffer, struct scsi_sense_hdr *, int timeout, int retries, unsigned bufflen, struct scsi_sense_hdr *sshdr, int timeout, int *resid); int retries, int *resid, int flags); static inline int scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, int data_direction, void *buffer, unsigned bufflen, struct scsi_sense_hdr *sshdr, int timeout, int retries, int *resid) { return scsi_execute_req_flags(sdev, cmd, data_direction, buffer, bufflen, sshdr, timeout, retries, resid, 0); } extern void sdev_disable_disk_events(struct scsi_device *sdev); extern void sdev_disable_disk_events(struct scsi_device *sdev); extern void sdev_enable_disk_events(struct scsi_device *sdev); extern void sdev_enable_disk_events(struct scsi_device *sdev); Loading