diff options
author | Boaz Harrosh <bharrosh@panasas.com> | 2007-09-10 11:01:08 -0400 |
---|---|---|
committer | James Bottomley <James.Bottomley@HansenPartnership.com> | 2008-01-11 19:22:38 -0500 |
commit | 6d416e6173394defda5933e419e805b696681b7e (patch) | |
tree | 5d2905c8a36fff50c3972d2906d46b6a4d37fad7 | |
parent | 4776e99ebb171d61c7e242db437358183f27b471 (diff) |
[SCSI] usb: transport - convert to accessors and !use_sg code path removal
- This patch depends on:
usb: transport.c use scsi_eh API in REQUEST_SENSE execution
- Use scsi data accessors and remove of !use_sg code path.
- New usb_stor_bulk_srb() for use by drivers
[jejb: updated with corrective fix.
had a bug in residual handling in the new usb_stor_bulk_srb()
function. Found by Gabriel C. in -mm tree.
Tested-by: Gabriel C <nix.or.die@googlemail.com>
]
Signed-off-by: Boaz Harrosh <bharrosh@panasas.com>
Acked-by: Matthew Dharm <mdharm-scsi@one-eyed-alien.net>
Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
-rw-r--r-- | drivers/usb/storage/transport.c | 45 | ||||
-rw-r--r-- | drivers/usb/storage/transport.h | 2 |
2 files changed, 30 insertions, 17 deletions
diff --git a/drivers/usb/storage/transport.c b/drivers/usb/storage/transport.c index c646750ccc30..d9f4912f873d 100644 --- a/drivers/usb/storage/transport.c +++ b/drivers/usb/storage/transport.c | |||
@@ -459,6 +459,22 @@ static int usb_stor_bulk_transfer_sglist(struct us_data *us, unsigned int pipe, | |||
459 | } | 459 | } |
460 | 460 | ||
461 | /* | 461 | /* |
462 | * Common used function. Transfer a complete command | ||
463 | * via usb_stor_bulk_transfer_sglist() above. Set cmnd resid | ||
464 | */ | ||
465 | int usb_stor_bulk_srb(struct us_data* us, unsigned int pipe, | ||
466 | struct scsi_cmnd* srb) | ||
467 | { | ||
468 | unsigned int partial; | ||
469 | int result = usb_stor_bulk_transfer_sglist(us, pipe, scsi_sglist(srb), | ||
470 | scsi_sg_count(srb), scsi_bufflen(srb), | ||
471 | &partial); | ||
472 | |||
473 | scsi_set_resid(srb, scsi_bufflen(srb) - partial); | ||
474 | return result; | ||
475 | } | ||
476 | |||
477 | /* | ||
462 | * Transfer an entire SCSI command's worth of data payload over the bulk | 478 | * Transfer an entire SCSI command's worth of data payload over the bulk |
463 | * pipe. | 479 | * pipe. |
464 | * | 480 | * |
@@ -508,7 +524,7 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
508 | int result; | 524 | int result; |
509 | 525 | ||
510 | /* send the command to the transport layer */ | 526 | /* send the command to the transport layer */ |
511 | srb->resid = 0; | 527 | scsi_set_resid(srb, 0); |
512 | result = us->transport(srb, us); | 528 | result = us->transport(srb, us); |
513 | 529 | ||
514 | /* if the command gets aborted by the higher layers, we need to | 530 | /* if the command gets aborted by the higher layers, we need to |
@@ -568,7 +584,7 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
568 | * A short transfer on a command where we don't expect it | 584 | * A short transfer on a command where we don't expect it |
569 | * is unusual, but it doesn't mean we need to auto-sense. | 585 | * is unusual, but it doesn't mean we need to auto-sense. |
570 | */ | 586 | */ |
571 | if ((srb->resid > 0) && | 587 | if ((scsi_get_resid(srb) > 0) && |
572 | !((srb->cmnd[0] == REQUEST_SENSE) || | 588 | !((srb->cmnd[0] == REQUEST_SENSE) || |
573 | (srb->cmnd[0] == INQUIRY) || | 589 | (srb->cmnd[0] == INQUIRY) || |
574 | (srb->cmnd[0] == MODE_SENSE) || | 590 | (srb->cmnd[0] == MODE_SENSE) || |
@@ -593,7 +609,7 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
593 | srb->cmd_len = 12; | 609 | srb->cmd_len = 12; |
594 | 610 | ||
595 | /* issue the auto-sense command */ | 611 | /* issue the auto-sense command */ |
596 | srb->resid = 0; | 612 | scsi_set_resid(srb, 0); |
597 | temp_result = us->transport(us->srb, us); | 613 | temp_result = us->transport(us->srb, us); |
598 | 614 | ||
599 | /* let's clean up right away */ | 615 | /* let's clean up right away */ |
@@ -649,7 +665,7 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
649 | 665 | ||
650 | /* Did we transfer less than the minimum amount required? */ | 666 | /* Did we transfer less than the minimum amount required? */ |
651 | if (srb->result == SAM_STAT_GOOD && | 667 | if (srb->result == SAM_STAT_GOOD && |
652 | srb->request_bufflen - srb->resid < srb->underflow) | 668 | scsi_bufflen(srb) - scsi_get_resid(srb) < srb->underflow) |
653 | srb->result = (DID_ERROR << 16) | (SUGGEST_RETRY << 24); | 669 | srb->result = (DID_ERROR << 16) | (SUGGEST_RETRY << 24); |
654 | 670 | ||
655 | return; | 671 | return; |
@@ -708,7 +724,7 @@ void usb_stor_stop_transport(struct us_data *us) | |||
708 | 724 | ||
709 | int usb_stor_CBI_transport(struct scsi_cmnd *srb, struct us_data *us) | 725 | int usb_stor_CBI_transport(struct scsi_cmnd *srb, struct us_data *us) |
710 | { | 726 | { |
711 | unsigned int transfer_length = srb->request_bufflen; | 727 | unsigned int transfer_length = scsi_bufflen(srb); |
712 | unsigned int pipe = 0; | 728 | unsigned int pipe = 0; |
713 | int result; | 729 | int result; |
714 | 730 | ||
@@ -737,9 +753,7 @@ int usb_stor_CBI_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
737 | if (transfer_length) { | 753 | if (transfer_length) { |
738 | pipe = srb->sc_data_direction == DMA_FROM_DEVICE ? | 754 | pipe = srb->sc_data_direction == DMA_FROM_DEVICE ? |
739 | us->recv_bulk_pipe : us->send_bulk_pipe; | 755 | us->recv_bulk_pipe : us->send_bulk_pipe; |
740 | result = usb_stor_bulk_transfer_sg(us, pipe, | 756 | result = usb_stor_bulk_srb(us, pipe, srb); |
741 | srb->request_buffer, transfer_length, | ||
742 | srb->use_sg, &srb->resid); | ||
743 | US_DEBUGP("CBI data stage result is 0x%x\n", result); | 757 | US_DEBUGP("CBI data stage result is 0x%x\n", result); |
744 | 758 | ||
745 | /* if we stalled the data transfer it means command failed */ | 759 | /* if we stalled the data transfer it means command failed */ |
@@ -808,7 +822,7 @@ int usb_stor_CBI_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
808 | */ | 822 | */ |
809 | int usb_stor_CB_transport(struct scsi_cmnd *srb, struct us_data *us) | 823 | int usb_stor_CB_transport(struct scsi_cmnd *srb, struct us_data *us) |
810 | { | 824 | { |
811 | unsigned int transfer_length = srb->request_bufflen; | 825 | unsigned int transfer_length = scsi_bufflen(srb); |
812 | int result; | 826 | int result; |
813 | 827 | ||
814 | /* COMMAND STAGE */ | 828 | /* COMMAND STAGE */ |
@@ -836,9 +850,7 @@ int usb_stor_CB_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
836 | if (transfer_length) { | 850 | if (transfer_length) { |
837 | unsigned int pipe = srb->sc_data_direction == DMA_FROM_DEVICE ? | 851 | unsigned int pipe = srb->sc_data_direction == DMA_FROM_DEVICE ? |
838 | us->recv_bulk_pipe : us->send_bulk_pipe; | 852 | us->recv_bulk_pipe : us->send_bulk_pipe; |
839 | result = usb_stor_bulk_transfer_sg(us, pipe, | 853 | result = usb_stor_bulk_srb(us, pipe, srb); |
840 | srb->request_buffer, transfer_length, | ||
841 | srb->use_sg, &srb->resid); | ||
842 | US_DEBUGP("CB data stage result is 0x%x\n", result); | 854 | US_DEBUGP("CB data stage result is 0x%x\n", result); |
843 | 855 | ||
844 | /* if we stalled the data transfer it means command failed */ | 856 | /* if we stalled the data transfer it means command failed */ |
@@ -904,7 +916,7 @@ int usb_stor_Bulk_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
904 | { | 916 | { |
905 | struct bulk_cb_wrap *bcb = (struct bulk_cb_wrap *) us->iobuf; | 917 | struct bulk_cb_wrap *bcb = (struct bulk_cb_wrap *) us->iobuf; |
906 | struct bulk_cs_wrap *bcs = (struct bulk_cs_wrap *) us->iobuf; | 918 | struct bulk_cs_wrap *bcs = (struct bulk_cs_wrap *) us->iobuf; |
907 | unsigned int transfer_length = srb->request_bufflen; | 919 | unsigned int transfer_length = scsi_bufflen(srb); |
908 | unsigned int residue; | 920 | unsigned int residue; |
909 | int result; | 921 | int result; |
910 | int fake_sense = 0; | 922 | int fake_sense = 0; |
@@ -955,9 +967,7 @@ int usb_stor_Bulk_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
955 | if (transfer_length) { | 967 | if (transfer_length) { |
956 | unsigned int pipe = srb->sc_data_direction == DMA_FROM_DEVICE ? | 968 | unsigned int pipe = srb->sc_data_direction == DMA_FROM_DEVICE ? |
957 | us->recv_bulk_pipe : us->send_bulk_pipe; | 969 | us->recv_bulk_pipe : us->send_bulk_pipe; |
958 | result = usb_stor_bulk_transfer_sg(us, pipe, | 970 | result = usb_stor_bulk_srb(us, pipe, srb); |
959 | srb->request_buffer, transfer_length, | ||
960 | srb->use_sg, &srb->resid); | ||
961 | US_DEBUGP("Bulk data transfer result 0x%x\n", result); | 971 | US_DEBUGP("Bulk data transfer result 0x%x\n", result); |
962 | if (result == USB_STOR_XFER_ERROR) | 972 | if (result == USB_STOR_XFER_ERROR) |
963 | return USB_STOR_TRANSPORT_ERROR; | 973 | return USB_STOR_TRANSPORT_ERROR; |
@@ -1036,7 +1046,8 @@ int usb_stor_Bulk_transport(struct scsi_cmnd *srb, struct us_data *us) | |||
1036 | if (residue) { | 1046 | if (residue) { |
1037 | if (!(us->flags & US_FL_IGNORE_RESIDUE)) { | 1047 | if (!(us->flags & US_FL_IGNORE_RESIDUE)) { |
1038 | residue = min(residue, transfer_length); | 1048 | residue = min(residue, transfer_length); |
1039 | srb->resid = max(srb->resid, (int) residue); | 1049 | scsi_set_resid(srb, max(scsi_get_resid(srb), |
1050 | (int) residue)); | ||
1040 | } | 1051 | } |
1041 | } | 1052 | } |
1042 | 1053 | ||
diff --git a/drivers/usb/storage/transport.h b/drivers/usb/storage/transport.h index 633a715850a4..ada7c2f43f84 100644 --- a/drivers/usb/storage/transport.h +++ b/drivers/usb/storage/transport.h | |||
@@ -139,6 +139,8 @@ extern int usb_stor_bulk_transfer_buf(struct us_data *us, unsigned int pipe, | |||
139 | void *buf, unsigned int length, unsigned int *act_len); | 139 | void *buf, unsigned int length, unsigned int *act_len); |
140 | extern int usb_stor_bulk_transfer_sg(struct us_data *us, unsigned int pipe, | 140 | extern int usb_stor_bulk_transfer_sg(struct us_data *us, unsigned int pipe, |
141 | void *buf, unsigned int length, int use_sg, int *residual); | 141 | void *buf, unsigned int length, int use_sg, int *residual); |
142 | extern int usb_stor_bulk_srb(struct us_data* us, unsigned int pipe, | ||
143 | struct scsi_cmnd* srb); | ||
142 | 144 | ||
143 | extern int usb_stor_port_reset(struct us_data *us); | 145 | extern int usb_stor_port_reset(struct us_data *us); |
144 | #endif | 146 | #endif |