aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/libsas/sas_scsi_host.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/libsas/sas_scsi_host.c')
-rw-r--r--drivers/scsi/libsas/sas_scsi_host.c258
1 files changed, 183 insertions, 75 deletions
diff --git a/drivers/scsi/libsas/sas_scsi_host.c b/drivers/scsi/libsas/sas_scsi_host.c
index 22672d54aa27..cd2378010c7e 100644
--- a/drivers/scsi/libsas/sas_scsi_host.c
+++ b/drivers/scsi/libsas/sas_scsi_host.c
@@ -34,6 +34,7 @@
34#include <scsi/scsi_transport_sas.h> 34#include <scsi/scsi_transport_sas.h>
35#include "../scsi_sas_internal.h" 35#include "../scsi_sas_internal.h"
36#include "../scsi_transport_api.h" 36#include "../scsi_transport_api.h"
37#include "../scsi_priv.h"
37 38
38#include <linux/err.h> 39#include <linux/err.h>
39#include <linux/blkdev.h> 40#include <linux/blkdev.h>
@@ -130,7 +131,7 @@ static enum task_attribute sas_scsi_get_task_attr(struct scsi_cmnd *cmd)
130 if (cmd->request && blk_rq_tagged(cmd->request)) { 131 if (cmd->request && blk_rq_tagged(cmd->request)) {
131 if (cmd->device->ordered_tags && 132 if (cmd->device->ordered_tags &&
132 (cmd->request->cmd_flags & REQ_HARDBARRIER)) 133 (cmd->request->cmd_flags & REQ_HARDBARRIER))
133 ta = TASK_ATTR_HOQ; 134 ta = TASK_ATTR_ORDERED;
134 } 135 }
135 return ta; 136 return ta;
136} 137}
@@ -281,6 +282,7 @@ enum task_disposition {
281 TASK_IS_ABORTED, 282 TASK_IS_ABORTED,
282 TASK_IS_AT_LU, 283 TASK_IS_AT_LU,
283 TASK_IS_NOT_AT_LU, 284 TASK_IS_NOT_AT_LU,
285 TASK_ABORT_FAILED,
284}; 286};
285 287
286static enum task_disposition sas_scsi_find_task(struct sas_task *task) 288static enum task_disposition sas_scsi_find_task(struct sas_task *task)
@@ -310,15 +312,6 @@ static enum task_disposition sas_scsi_find_task(struct sas_task *task)
310 spin_unlock_irqrestore(&core->task_queue_lock, flags); 312 spin_unlock_irqrestore(&core->task_queue_lock, flags);
311 } 313 }
312 314
313 spin_lock_irqsave(&task->task_state_lock, flags);
314 if (task->task_state_flags & SAS_TASK_INITIATOR_ABORTED) {
315 spin_unlock_irqrestore(&task->task_state_lock, flags);
316 SAS_DPRINTK("%s: task 0x%p already aborted\n",
317 __FUNCTION__, task);
318 return TASK_IS_ABORTED;
319 }
320 spin_unlock_irqrestore(&task->task_state_lock, flags);
321
322 for (i = 0; i < 5; i++) { 315 for (i = 0; i < 5; i++) {
323 SAS_DPRINTK("%s: aborting task 0x%p\n", __FUNCTION__, task); 316 SAS_DPRINTK("%s: aborting task 0x%p\n", __FUNCTION__, task);
324 res = si->dft->lldd_abort_task(task); 317 res = si->dft->lldd_abort_task(task);
@@ -340,15 +333,21 @@ static enum task_disposition sas_scsi_find_task(struct sas_task *task)
340 SAS_DPRINTK("%s: querying task 0x%p\n", 333 SAS_DPRINTK("%s: querying task 0x%p\n",
341 __FUNCTION__, task); 334 __FUNCTION__, task);
342 res = si->dft->lldd_query_task(task); 335 res = si->dft->lldd_query_task(task);
343 if (res == TMF_RESP_FUNC_SUCC) { 336 switch (res) {
337 case TMF_RESP_FUNC_SUCC:
344 SAS_DPRINTK("%s: task 0x%p at LU\n", 338 SAS_DPRINTK("%s: task 0x%p at LU\n",
345 __FUNCTION__, task); 339 __FUNCTION__, task);
346 return TASK_IS_AT_LU; 340 return TASK_IS_AT_LU;
347 } else if (res == TMF_RESP_FUNC_COMPLETE) { 341 case TMF_RESP_FUNC_COMPLETE:
348 SAS_DPRINTK("%s: task 0x%p not at LU\n", 342 SAS_DPRINTK("%s: task 0x%p not at LU\n",
349 __FUNCTION__, task); 343 __FUNCTION__, task);
350 return TASK_IS_NOT_AT_LU; 344 return TASK_IS_NOT_AT_LU;
351 } 345 case TMF_RESP_FUNC_FAILED:
346 SAS_DPRINTK("%s: task 0x%p failed to abort\n",
347 __FUNCTION__, task);
348 return TASK_ABORT_FAILED;
349 }
350
352 } 351 }
353 } 352 }
354 return res; 353 return res;
@@ -398,35 +397,82 @@ static int sas_recover_I_T(struct domain_device *dev)
398 return res; 397 return res;
399} 398}
400 399
401void sas_scsi_recover_host(struct Scsi_Host *shost) 400/* Find the sas_phy that's attached to this device */
401struct sas_phy *find_local_sas_phy(struct domain_device *dev)
402{
403 struct domain_device *pdev = dev->parent;
404 struct ex_phy *exphy = NULL;
405 int i;
406
407 /* Directly attached device */
408 if (!pdev)
409 return dev->port->phy;
410
411 /* Otherwise look in the expander */
412 for (i = 0; i < pdev->ex_dev.num_phys; i++)
413 if (!memcmp(dev->sas_addr,
414 pdev->ex_dev.ex_phy[i].attached_sas_addr,
415 SAS_ADDR_SIZE)) {
416 exphy = &pdev->ex_dev.ex_phy[i];
417 break;
418 }
419
420 BUG_ON(!exphy);
421 return exphy->phy;
422}
423
424/* Attempt to send a target reset message to a device */
425int sas_eh_device_reset_handler(struct scsi_cmnd *cmd)
426{
427 struct domain_device *dev = cmd_to_domain_dev(cmd);
428 struct sas_phy *phy = find_local_sas_phy(dev);
429 int res;
430
431 res = sas_phy_reset(phy, 1);
432 if (res)
433 SAS_DPRINTK("Device reset of %s failed 0x%x\n",
434 phy->dev.kobj.k_name,
435 res);
436 if (res == TMF_RESP_FUNC_SUCC || res == TMF_RESP_FUNC_COMPLETE)
437 return SUCCESS;
438
439 return FAILED;
440}
441
442/* Try to reset a device */
443static int try_to_reset_cmd_device(struct Scsi_Host *shost,
444 struct scsi_cmnd *cmd)
445{
446 if (!shost->hostt->eh_device_reset_handler)
447 return FAILED;
448
449 return shost->hostt->eh_device_reset_handler(cmd);
450}
451
452static int sas_eh_handle_sas_errors(struct Scsi_Host *shost,
453 struct list_head *work_q,
454 struct list_head *done_q)
402{ 455{
403 struct sas_ha_struct *ha = SHOST_TO_SAS_HA(shost);
404 unsigned long flags;
405 LIST_HEAD(error_q);
406 struct scsi_cmnd *cmd, *n; 456 struct scsi_cmnd *cmd, *n;
407 enum task_disposition res = TASK_IS_DONE; 457 enum task_disposition res = TASK_IS_DONE;
408 int tmf_resp; 458 int tmf_resp, need_reset;
409 struct sas_internal *i = to_sas_internal(shost->transportt); 459 struct sas_internal *i = to_sas_internal(shost->transportt);
460 unsigned long flags;
461 struct sas_ha_struct *ha = SHOST_TO_SAS_HA(shost);
410 462
411 spin_lock_irqsave(shost->host_lock, flags);
412 list_splice_init(&shost->eh_cmd_q, &error_q);
413 spin_unlock_irqrestore(shost->host_lock, flags);
414
415 SAS_DPRINTK("Enter %s\n", __FUNCTION__);
416
417 /* All tasks on this list were marked SAS_TASK_STATE_ABORTED
418 * by sas_scsi_timed_out() callback.
419 */
420Again: 463Again:
421 SAS_DPRINTK("going over list...\n"); 464 list_for_each_entry_safe(cmd, n, work_q, eh_entry) {
422 list_for_each_entry_safe(cmd, n, &error_q, eh_entry) {
423 struct sas_task *task = TO_SAS_TASK(cmd); 465 struct sas_task *task = TO_SAS_TASK(cmd);
424 list_del_init(&cmd->eh_entry);
425 466
426 if (!task) { 467 if (!task)
427 SAS_DPRINTK("%s: taskless cmd?!\n", __FUNCTION__);
428 continue; 468 continue;
429 } 469
470 list_del_init(&cmd->eh_entry);
471
472 spin_lock_irqsave(&task->task_state_lock, flags);
473 need_reset = task->task_state_flags & SAS_TASK_NEED_DEV_RESET;
474 spin_unlock_irqrestore(&task->task_state_lock, flags);
475
430 SAS_DPRINTK("trying to find task 0x%p\n", task); 476 SAS_DPRINTK("trying to find task 0x%p\n", task);
431 res = sas_scsi_find_task(task); 477 res = sas_scsi_find_task(task);
432 478
@@ -437,11 +483,15 @@ Again:
437 SAS_DPRINTK("%s: task 0x%p is done\n", __FUNCTION__, 483 SAS_DPRINTK("%s: task 0x%p is done\n", __FUNCTION__,
438 task); 484 task);
439 task->task_done(task); 485 task->task_done(task);
486 if (need_reset)
487 try_to_reset_cmd_device(shost, cmd);
440 continue; 488 continue;
441 case TASK_IS_ABORTED: 489 case TASK_IS_ABORTED:
442 SAS_DPRINTK("%s: task 0x%p is aborted\n", 490 SAS_DPRINTK("%s: task 0x%p is aborted\n",
443 __FUNCTION__, task); 491 __FUNCTION__, task);
444 task->task_done(task); 492 task->task_done(task);
493 if (need_reset)
494 try_to_reset_cmd_device(shost, cmd);
445 continue; 495 continue;
446 case TASK_IS_AT_LU: 496 case TASK_IS_AT_LU:
447 SAS_DPRINTK("task 0x%p is at LU: lu recover\n", task); 497 SAS_DPRINTK("task 0x%p is at LU: lu recover\n", task);
@@ -452,11 +502,14 @@ Again:
452 SAS_ADDR(task->dev), 502 SAS_ADDR(task->dev),
453 cmd->device->lun); 503 cmd->device->lun);
454 task->task_done(task); 504 task->task_done(task);
455 sas_scsi_clear_queue_lu(&error_q, cmd); 505 if (need_reset)
506 try_to_reset_cmd_device(shost, cmd);
507 sas_scsi_clear_queue_lu(work_q, cmd);
456 goto Again; 508 goto Again;
457 } 509 }
458 /* fallthrough */ 510 /* fallthrough */
459 case TASK_IS_NOT_AT_LU: 511 case TASK_IS_NOT_AT_LU:
512 case TASK_ABORT_FAILED:
460 SAS_DPRINTK("task 0x%p is not at LU: I_T recover\n", 513 SAS_DPRINTK("task 0x%p is not at LU: I_T recover\n",
461 task); 514 task);
462 tmf_resp = sas_recover_I_T(task->dev); 515 tmf_resp = sas_recover_I_T(task->dev);
@@ -464,7 +517,9 @@ Again:
464 SAS_DPRINTK("I_T %016llx recovered\n", 517 SAS_DPRINTK("I_T %016llx recovered\n",
465 SAS_ADDR(task->dev->sas_addr)); 518 SAS_ADDR(task->dev->sas_addr));
466 task->task_done(task); 519 task->task_done(task);
467 sas_scsi_clear_queue_I_T(&error_q, task->dev); 520 if (need_reset)
521 try_to_reset_cmd_device(shost, cmd);
522 sas_scsi_clear_queue_I_T(work_q, task->dev);
468 goto Again; 523 goto Again;
469 } 524 }
470 /* Hammer time :-) */ 525 /* Hammer time :-) */
@@ -477,7 +532,9 @@ Again:
477 SAS_DPRINTK("clear nexus port:%d " 532 SAS_DPRINTK("clear nexus port:%d "
478 "succeeded\n", port->id); 533 "succeeded\n", port->id);
479 task->task_done(task); 534 task->task_done(task);
480 sas_scsi_clear_queue_port(&error_q, 535 if (need_reset)
536 try_to_reset_cmd_device(shost, cmd);
537 sas_scsi_clear_queue_port(work_q,
481 port); 538 port);
482 goto Again; 539 goto Again;
483 } 540 }
@@ -489,6 +546,8 @@ Again:
489 SAS_DPRINTK("clear nexus ha " 546 SAS_DPRINTK("clear nexus ha "
490 "succeeded\n"); 547 "succeeded\n");
491 task->task_done(task); 548 task->task_done(task);
549 if (need_reset)
550 try_to_reset_cmd_device(shost, cmd);
492 goto out; 551 goto out;
493 } 552 }
494 } 553 }
@@ -502,20 +561,54 @@ Again:
502 cmd->device->lun); 561 cmd->device->lun);
503 562
504 task->task_done(task); 563 task->task_done(task);
564 if (need_reset)
565 try_to_reset_cmd_device(shost, cmd);
505 goto clear_q; 566 goto clear_q;
506 } 567 }
507 } 568 }
508out: 569out:
509 scsi_eh_flush_done_q(&ha->eh_done_q); 570 return list_empty(work_q);
510 SAS_DPRINTK("--- Exit %s\n", __FUNCTION__);
511 return;
512clear_q: 571clear_q:
513 SAS_DPRINTK("--- Exit %s -- clear_q\n", __FUNCTION__); 572 SAS_DPRINTK("--- Exit %s -- clear_q\n", __FUNCTION__);
514 list_for_each_entry_safe(cmd, n, &error_q, eh_entry) { 573 list_for_each_entry_safe(cmd, n, work_q, eh_entry) {
515 struct sas_task *task = TO_SAS_TASK(cmd); 574 struct sas_task *task = TO_SAS_TASK(cmd);
516 list_del_init(&cmd->eh_entry); 575 list_del_init(&cmd->eh_entry);
517 task->task_done(task); 576 task->task_done(task);
518 } 577 }
578 return list_empty(work_q);
579}
580
581void sas_scsi_recover_host(struct Scsi_Host *shost)
582{
583 struct sas_ha_struct *ha = SHOST_TO_SAS_HA(shost);
584 unsigned long flags;
585 LIST_HEAD(eh_work_q);
586
587 spin_lock_irqsave(shost->host_lock, flags);
588 list_splice_init(&shost->eh_cmd_q, &eh_work_q);
589 spin_unlock_irqrestore(shost->host_lock, flags);
590
591 SAS_DPRINTK("Enter %s\n", __FUNCTION__);
592 /*
593 * Deal with commands that still have SAS tasks (i.e. they didn't
594 * complete via the normal sas_task completion mechanism)
595 */
596 if (sas_eh_handle_sas_errors(shost, &eh_work_q, &ha->eh_done_q))
597 goto out;
598
599 /*
600 * Now deal with SCSI commands that completed ok but have a an error
601 * code (and hopefully sense data) attached. This is roughly what
602 * scsi_unjam_host does, but we skip scsi_eh_abort_cmds because any
603 * command we see here has no sas_task and is thus unknown to the HA.
604 */
605 if (!scsi_eh_get_sense(&eh_work_q, &ha->eh_done_q))
606 scsi_eh_ready_devs(shost, &eh_work_q, &ha->eh_done_q);
607
608out:
609 scsi_eh_flush_done_q(&ha->eh_done_q);
610 SAS_DPRINTK("--- Exit %s\n", __FUNCTION__);
611 return;
519} 612}
520 613
521enum scsi_eh_timer_return sas_scsi_timed_out(struct scsi_cmnd *cmd) 614enum scsi_eh_timer_return sas_scsi_timed_out(struct scsi_cmnd *cmd)
@@ -524,24 +617,30 @@ enum scsi_eh_timer_return sas_scsi_timed_out(struct scsi_cmnd *cmd)
524 unsigned long flags; 617 unsigned long flags;
525 618
526 if (!task) { 619 if (!task) {
527 SAS_DPRINTK("command 0x%p, task 0x%p, gone: EH_HANDLED\n", 620 cmd->timeout_per_command /= 2;
528 cmd, task); 621 SAS_DPRINTK("command 0x%p, task 0x%p, gone: %s\n",
529 return EH_HANDLED; 622 cmd, task, (cmd->timeout_per_command ?
623 "EH_RESET_TIMER" : "EH_NOT_HANDLED"));
624 if (!cmd->timeout_per_command)
625 return EH_NOT_HANDLED;
626 return EH_RESET_TIMER;
530 } 627 }
531 628
532 spin_lock_irqsave(&task->task_state_lock, flags); 629 spin_lock_irqsave(&task->task_state_lock, flags);
533 if (task->task_state_flags & SAS_TASK_INITIATOR_ABORTED) { 630 BUG_ON(task->task_state_flags & SAS_TASK_STATE_ABORTED);
534 spin_unlock_irqrestore(&task->task_state_lock, flags);
535 SAS_DPRINTK("command 0x%p, task 0x%p, aborted by initiator: "
536 "EH_NOT_HANDLED\n", cmd, task);
537 return EH_NOT_HANDLED;
538 }
539 if (task->task_state_flags & SAS_TASK_STATE_DONE) { 631 if (task->task_state_flags & SAS_TASK_STATE_DONE) {
540 spin_unlock_irqrestore(&task->task_state_lock, flags); 632 spin_unlock_irqrestore(&task->task_state_lock, flags);
541 SAS_DPRINTK("command 0x%p, task 0x%p, timed out: EH_HANDLED\n", 633 SAS_DPRINTK("command 0x%p, task 0x%p, timed out: EH_HANDLED\n",
542 cmd, task); 634 cmd, task);
543 return EH_HANDLED; 635 return EH_HANDLED;
544 } 636 }
637 if (!(task->task_state_flags & SAS_TASK_AT_INITIATOR)) {
638 spin_unlock_irqrestore(&task->task_state_lock, flags);
639 SAS_DPRINTK("command 0x%p, task 0x%p, not at initiator: "
640 "EH_RESET_TIMER\n",
641 cmd, task);
642 return EH_RESET_TIMER;
643 }
545 task->task_state_flags |= SAS_TASK_STATE_ABORTED; 644 task->task_state_flags |= SAS_TASK_STATE_ABORTED;
546 spin_unlock_irqrestore(&task->task_state_lock, flags); 645 spin_unlock_irqrestore(&task->task_state_lock, flags);
547 646
@@ -557,8 +656,9 @@ struct domain_device *sas_find_dev_by_rphy(struct sas_rphy *rphy)
557 struct sas_ha_struct *ha = SHOST_TO_SAS_HA(shost); 656 struct sas_ha_struct *ha = SHOST_TO_SAS_HA(shost);
558 struct domain_device *found_dev = NULL; 657 struct domain_device *found_dev = NULL;
559 int i; 658 int i;
659 unsigned long flags;
560 660
561 spin_lock(&ha->phy_port_lock); 661 spin_lock_irqsave(&ha->phy_port_lock, flags);
562 for (i = 0; i < ha->num_phys; i++) { 662 for (i = 0; i < ha->num_phys; i++) {
563 struct asd_sas_port *port = ha->sas_port[i]; 663 struct asd_sas_port *port = ha->sas_port[i];
564 struct domain_device *dev; 664 struct domain_device *dev;
@@ -574,7 +674,7 @@ struct domain_device *sas_find_dev_by_rphy(struct sas_rphy *rphy)
574 spin_unlock(&port->dev_list_lock); 674 spin_unlock(&port->dev_list_lock);
575 } 675 }
576 found: 676 found:
577 spin_unlock(&ha->phy_port_lock); 677 spin_unlock_irqrestore(&ha->phy_port_lock, flags);
578 678
579 return found_dev; 679 return found_dev;
580} 680}
@@ -623,6 +723,8 @@ int sas_slave_configure(struct scsi_device *scsi_dev)
623 scsi_deactivate_tcq(scsi_dev, 1); 723 scsi_deactivate_tcq(scsi_dev, 1);
624 } 724 }
625 725
726 scsi_dev->allow_restart = 1;
727
626 return 0; 728 return 0;
627} 729}
628 730
@@ -799,46 +901,42 @@ void sas_shutdown_queue(struct sas_ha_struct *sas_ha)
799 spin_unlock_irqrestore(&core->task_queue_lock, flags); 901 spin_unlock_irqrestore(&core->task_queue_lock, flags);
800} 902}
801 903
802static int do_sas_task_abort(struct sas_task *task) 904/*
905 * Call the LLDD task abort routine directly. This function is intended for
906 * use by upper layers that need to tell the LLDD to abort a task.
907 */
908int __sas_task_abort(struct sas_task *task)
803{ 909{
804 struct scsi_cmnd *sc = task->uldd_task;
805 struct sas_internal *si = 910 struct sas_internal *si =
806 to_sas_internal(task->dev->port->ha->core.shost->transportt); 911 to_sas_internal(task->dev->port->ha->core.shost->transportt);
807 unsigned long flags; 912 unsigned long flags;
808 int res; 913 int res;
809 914
810 spin_lock_irqsave(&task->task_state_lock, flags); 915 spin_lock_irqsave(&task->task_state_lock, flags);
811 if (task->task_state_flags & SAS_TASK_STATE_ABORTED) { 916 if (task->task_state_flags & SAS_TASK_STATE_ABORTED ||
917 task->task_state_flags & SAS_TASK_STATE_DONE) {
812 spin_unlock_irqrestore(&task->task_state_lock, flags); 918 spin_unlock_irqrestore(&task->task_state_lock, flags);
813 SAS_DPRINTK("%s: Task %p already aborted.\n", __FUNCTION__, 919 SAS_DPRINTK("%s: Task %p already finished.\n", __FUNCTION__,
814 task); 920 task);
815 return 0; 921 return 0;
816 } 922 }
817 923 task->task_state_flags |= SAS_TASK_STATE_ABORTED;
818 task->task_state_flags |= SAS_TASK_INITIATOR_ABORTED;
819 if (!(task->task_state_flags & SAS_TASK_STATE_DONE))
820 task->task_state_flags |= SAS_TASK_STATE_ABORTED;
821 spin_unlock_irqrestore(&task->task_state_lock, flags); 924 spin_unlock_irqrestore(&task->task_state_lock, flags);
822 925
823 if (!si->dft->lldd_abort_task) 926 if (!si->dft->lldd_abort_task)
824 return -ENODEV; 927 return -ENODEV;
825 928
826 res = si->dft->lldd_abort_task(task); 929 res = si->dft->lldd_abort_task(task);
930
931 spin_lock_irqsave(&task->task_state_lock, flags);
827 if ((task->task_state_flags & SAS_TASK_STATE_DONE) || 932 if ((task->task_state_flags & SAS_TASK_STATE_DONE) ||
828 (res == TMF_RESP_FUNC_COMPLETE)) 933 (res == TMF_RESP_FUNC_COMPLETE))
829 { 934 {
830 /* SMP commands don't have scsi_cmds(?) */ 935 spin_unlock_irqrestore(&task->task_state_lock, flags);
831 if (!sc) { 936 task->task_done(task);
832 task->task_done(task);
833 return 0;
834 }
835 scsi_req_abort_cmd(sc);
836 scsi_schedule_eh(sc->device->host);
837 return 0; 937 return 0;
838 } 938 }
839 939
840 spin_lock_irqsave(&task->task_state_lock, flags);
841 task->task_state_flags &= ~SAS_TASK_INITIATOR_ABORTED;
842 if (!(task->task_state_flags & SAS_TASK_STATE_DONE)) 940 if (!(task->task_state_flags & SAS_TASK_STATE_DONE))
843 task->task_state_flags &= ~SAS_TASK_STATE_ABORTED; 941 task->task_state_flags &= ~SAS_TASK_STATE_ABORTED;
844 spin_unlock_irqrestore(&task->task_state_lock, flags); 942 spin_unlock_irqrestore(&task->task_state_lock, flags);
@@ -846,17 +944,24 @@ static int do_sas_task_abort(struct sas_task *task)
846 return -EAGAIN; 944 return -EAGAIN;
847} 945}
848 946
849void sas_task_abort(struct work_struct *work) 947/*
948 * Tell an upper layer that it needs to initiate an abort for a given task.
949 * This should only ever be called by an LLDD.
950 */
951void sas_task_abort(struct sas_task *task)
850{ 952{
851 struct sas_task *task = 953 struct scsi_cmnd *sc = task->uldd_task;
852 container_of(work, struct sas_task, abort_work);
853 int i;
854 954
855 for (i = 0; i < 5; i++) 955 /* Escape for libsas internal commands */
856 if (!do_sas_task_abort(task)) 956 if (!sc) {
957 if (!del_timer(&task->timer))
857 return; 958 return;
959 task->timer.function(task->timer.data);
960 return;
961 }
858 962
859 SAS_DPRINTK("%s: Could not kill task!\n", __FUNCTION__); 963 scsi_req_abort_cmd(sc);
964 scsi_schedule_eh(sc->device->host);
860} 965}
861 966
862EXPORT_SYMBOL_GPL(sas_queuecommand); 967EXPORT_SYMBOL_GPL(sas_queuecommand);
@@ -866,5 +971,8 @@ EXPORT_SYMBOL_GPL(sas_slave_destroy);
866EXPORT_SYMBOL_GPL(sas_change_queue_depth); 971EXPORT_SYMBOL_GPL(sas_change_queue_depth);
867EXPORT_SYMBOL_GPL(sas_change_queue_type); 972EXPORT_SYMBOL_GPL(sas_change_queue_type);
868EXPORT_SYMBOL_GPL(sas_bios_param); 973EXPORT_SYMBOL_GPL(sas_bios_param);
974EXPORT_SYMBOL_GPL(__sas_task_abort);
869EXPORT_SYMBOL_GPL(sas_task_abort); 975EXPORT_SYMBOL_GPL(sas_task_abort);
870EXPORT_SYMBOL_GPL(sas_phy_reset); 976EXPORT_SYMBOL_GPL(sas_phy_reset);
977EXPORT_SYMBOL_GPL(sas_phy_enable);
978EXPORT_SYMBOL_GPL(sas_eh_device_reset_handler);