aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/ide/ide-io.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/ide/ide-io.c')
-rw-r--r--drivers/ide/ide-io.c72
1 files changed, 22 insertions, 50 deletions
diff --git a/drivers/ide/ide-io.c b/drivers/ide/ide-io.c
index 28057747c1f8..661b75a89d4d 100644
--- a/drivers/ide/ide-io.c
+++ b/drivers/ide/ide-io.c
@@ -504,55 +504,6 @@ ide_startstop_t ide_error (ide_drive_t *drive, const char *msg, u8 stat)
504 504
505EXPORT_SYMBOL_GPL(ide_error); 505EXPORT_SYMBOL_GPL(ide_error);
506 506
507ide_startstop_t __ide_abort(ide_drive_t *drive, struct request *rq)
508{
509 if (drive->media != ide_disk)
510 rq->errors |= ERROR_RESET;
511
512 ide_kill_rq(drive, rq);
513
514 return ide_stopped;
515}
516
517EXPORT_SYMBOL_GPL(__ide_abort);
518
519/**
520 * ide_abort - abort pending IDE operations
521 * @drive: drive the error occurred on
522 * @msg: message to report
523 *
524 * ide_abort kills and cleans up when we are about to do a
525 * host initiated reset on active commands. Longer term we
526 * want handlers to have sensible abort handling themselves
527 *
528 * This differs fundamentally from ide_error because in
529 * this case the command is doing just fine when we
530 * blow it away.
531 */
532
533ide_startstop_t ide_abort(ide_drive_t *drive, const char *msg)
534{
535 struct request *rq;
536
537 if (drive == NULL || (rq = HWGROUP(drive)->rq) == NULL)
538 return ide_stopped;
539
540 /* retry only "normal" I/O: */
541 if (!blk_fs_request(rq)) {
542 rq->errors = 1;
543 ide_end_drive_cmd(drive, BUSY_STAT, 0);
544 return ide_stopped;
545 }
546
547 if (rq->rq_disk) {
548 ide_driver_t *drv;
549
550 drv = *(ide_driver_t **)rq->rq_disk->private_data;
551 return drv->abort(drive, rq);
552 } else
553 return __ide_abort(drive, rq);
554}
555
556static void ide_tf_set_specify_cmd(ide_drive_t *drive, struct ide_taskfile *tf) 507static void ide_tf_set_specify_cmd(ide_drive_t *drive, struct ide_taskfile *tf)
557{ 508{
558 tf->nsect = drive->sect; 509 tf->nsect = drive->sect;
@@ -766,6 +717,18 @@ static ide_startstop_t execute_drive_cmd (ide_drive_t *drive,
766 return ide_stopped; 717 return ide_stopped;
767} 718}
768 719
720static ide_startstop_t ide_special_rq(ide_drive_t *drive, struct request *rq)
721{
722 switch (rq->cmd[0]) {
723 case REQ_DRIVE_RESET:
724 return ide_do_reset(drive);
725 default:
726 blk_dump_rq_flags(rq, "ide_special_rq - bad request");
727 ide_end_request(drive, 0, 0);
728 return ide_stopped;
729 }
730}
731
769static void ide_check_pm_state(ide_drive_t *drive, struct request *rq) 732static void ide_check_pm_state(ide_drive_t *drive, struct request *rq)
770{ 733{
771 struct request_pm_state *pm = rq->data; 734 struct request_pm_state *pm = rq->data;
@@ -869,7 +832,16 @@ static ide_startstop_t start_request (ide_drive_t *drive, struct request *rq)
869 pm->pm_step == ide_pm_state_completed) 832 pm->pm_step == ide_pm_state_completed)
870 ide_complete_pm_request(drive, rq); 833 ide_complete_pm_request(drive, rq);
871 return startstop; 834 return startstop;
872 } 835 } else if (!rq->rq_disk && blk_special_request(rq))
836 /*
837 * TODO: Once all ULDs have been modified to
838 * check for specific op codes rather than
839 * blindly accepting any special request, the
840 * check for ->rq_disk above may be replaced
841 * by a more suitable mechanism or even
842 * dropped entirely.
843 */
844 return ide_special_rq(drive, rq);
873 845
874 drv = *(ide_driver_t **)rq->rq_disk->private_data; 846 drv = *(ide_driver_t **)rq->rq_disk->private_data;
875 return drv->do_request(drive, rq, block); 847 return drv->do_request(drive, rq, block);