summaryrefslogtreecommitdiffstats
path: root/drivers/usb/storage/transport.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/usb/storage/transport.c')
-rw-r--r--drivers/usb/storage/transport.c93
1 files changed, 46 insertions, 47 deletions
diff --git a/drivers/usb/storage/transport.c b/drivers/usb/storage/transport.c
index 5186508ba6..be3b18dc66 100644
--- a/drivers/usb/storage/transport.c
+++ b/drivers/usb/storage/transport.c
@@ -1,21 +1,10 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
/*
* Most of this source has been derived from the Linux and
* U-Boot USB Mass Storage driver implementations.
*
* Adapted for barebox:
* Copyright (c) 2011, AMK Drives & Controls Ltd.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation; either version 2 of
- * the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- *
*/
#include <common.h>
@@ -60,7 +49,7 @@ static int usb_stor_Bulk_clear_endpt_stall(struct us_data *us, unsigned int pipe
/* Determine what the maximum LUN supported is */
int usb_stor_Bulk_max_lun(struct us_data *us)
{
- struct device_d *dev = &us->pusb_dev->dev;
+ struct device *dev = &us->pusb_dev->dev;
int len, ret = 0;
unsigned char *iobuf = dma_alloc(1);
@@ -96,40 +85,45 @@ int usb_stor_Bulk_transport(struct us_blk_dev *usb_blkdev,
void *data, u32 datalen)
{
struct us_data *us = usb_blkdev->us;
- struct device_d *dev = &us->pusb_dev->dev;
- struct bulk_cb_wrap cbw;
- struct bulk_cs_wrap csw;
+ struct device *dev = &us->pusb_dev->dev;
+ struct bulk_cb_wrap *cbw;
+ struct bulk_cs_wrap *csw;
int actlen, data_actlen;
int result;
unsigned int residue;
unsigned int pipein = usb_rcvbulkpipe(us->pusb_dev, us->recv_bulk_ep);
unsigned int pipeout = usb_sndbulkpipe(us->pusb_dev, us->send_bulk_ep);
int dir_in = US_DIRECTION(cmd[0]);
+ int ret = 0;
+
+ cbw = dma_alloc(sizeof(*cbw));
+ csw = dma_alloc(sizeof(*csw));
/* set up the command wrapper */
- cbw.Signature = cpu_to_le32(US_BULK_CB_SIGN);
- cbw.DataTransferLength = cpu_to_le32(datalen);
- cbw.Flags = (dir_in ? US_BULK_FLAG_IN : US_BULK_FLAG_OUT);
- cbw.Tag = ++cbw_tag;
- cbw.Lun = usb_blkdev->lun;
- cbw.Length = cmdlen;
+ cbw->Signature = cpu_to_le32(US_BULK_CB_SIGN);
+ cbw->DataTransferLength = cpu_to_le32(datalen);
+ cbw->Flags = (dir_in ? US_BULK_FLAG_IN : US_BULK_FLAG_OUT);
+ cbw->Tag = ++cbw_tag;
+ cbw->Lun = usb_blkdev->lun;
+ cbw->Length = cmdlen;
/* copy the command payload */
- memset(cbw.CDB, 0, sizeof(cbw.CDB));
- memcpy(cbw.CDB, cmd, cbw.Length);
+ memset(cbw->CDB, 0, sizeof(cbw->CDB));
+ memcpy(cbw->CDB, cmd, cbw->Length);
/* send it to out endpoint */
dev_dbg(dev, "Bulk Command S 0x%x T 0x%x L %d F %d Trg %d LUN %d CL %d\n",
- le32_to_cpu(cbw.Signature), cbw.Tag,
- le32_to_cpu(cbw.DataTransferLength), cbw.Flags,
- (cbw.Lun >> 4), (cbw.Lun & 0x0F),
- cbw.Length);
- result = usb_bulk_msg(us->pusb_dev, pipeout, &cbw, US_BULK_CB_WRAP_LEN,
+ le32_to_cpu(cbw->Signature), cbw->Tag,
+ le32_to_cpu(cbw->DataTransferLength), cbw->Flags,
+ (cbw->Lun >> 4), (cbw->Lun & 0x0F),
+ cbw->Length);
+ result = usb_bulk_msg(us->pusb_dev, pipeout, cbw, US_BULK_CB_WRAP_LEN,
&actlen, USB_BULK_TO);
dev_dbg(dev, "Bulk command transfer result=%d\n", result);
if (result < 0) {
usb_stor_Bulk_reset(us);
- return USB_STOR_TRANSPORT_FAILED;
+ ret = USB_STOR_TRANSPORT_FAILED;
+ goto fail;
}
/* DATA STAGE */
@@ -152,13 +146,14 @@ int usb_stor_Bulk_transport(struct us_blk_dev *usb_blkdev,
if (result < 0) {
dev_dbg(dev, "Device status: %lx\n", us->pusb_dev->status);
usb_stor_Bulk_reset(us);
- return USB_STOR_TRANSPORT_FAILED;
+ ret = USB_STOR_TRANSPORT_FAILED;
+ goto fail;
}
}
/* STATUS phase + error handling */
dev_dbg(dev, "Attempting to get CSW...\n");
- result = usb_bulk_msg(us->pusb_dev, pipein, &csw, US_BULK_CS_WRAP_LEN,
+ result = usb_bulk_msg(us->pusb_dev, pipein, csw, US_BULK_CS_WRAP_LEN,
&actlen, USB_BULK_TO);
/* did the endpoint stall? */
@@ -169,7 +164,7 @@ int usb_stor_Bulk_transport(struct us_blk_dev *usb_blkdev,
if (result >= 0) {
dev_dbg(dev, "Attempting to get CSW...\n");
result = usb_bulk_msg(us->pusb_dev, pipein,
- &csw, US_BULK_CS_WRAP_LEN,
+ csw, US_BULK_CS_WRAP_LEN,
&actlen, USB_BULK_TO);
}
}
@@ -177,35 +172,39 @@ int usb_stor_Bulk_transport(struct us_blk_dev *usb_blkdev,
if (result < 0) {
dev_dbg(dev, "Device status: %lx\n", us->pusb_dev->status);
usb_stor_Bulk_reset(us);
- return USB_STOR_TRANSPORT_FAILED;
+ ret = USB_STOR_TRANSPORT_FAILED;
+ goto fail;
}
/* check bulk status */
- residue = le32_to_cpu(csw.Residue);
+ residue = le32_to_cpu(csw->Residue);
dev_dbg(dev, "Bulk Status S 0x%x T 0x%x R %u Stat 0x%x\n",
- le32_to_cpu(csw.Signature), csw.Tag, residue, csw.Status);
- if (csw.Signature != cpu_to_le32(US_BULK_CS_SIGN)) {
+ le32_to_cpu(csw->Signature), csw->Tag, residue, csw->Status);
+ if (csw->Signature != cpu_to_le32(US_BULK_CS_SIGN)) {
dev_dbg(dev, "Bad CSW signature\n");
usb_stor_Bulk_reset(us);
- return USB_STOR_TRANSPORT_FAILED;
- } else if (csw.Tag != cbw_tag) {
+ ret = USB_STOR_TRANSPORT_FAILED;
+ } else if (csw->Tag != cbw_tag) {
dev_dbg(dev, "Mismatching tag\n");
usb_stor_Bulk_reset(us);
- return USB_STOR_TRANSPORT_FAILED;
- } else if (csw.Status >= US_BULK_STAT_PHASE) {
+ ret = USB_STOR_TRANSPORT_FAILED;
+ } else if (csw->Status >= US_BULK_STAT_PHASE) {
dev_dbg(dev, "Status >= phase\n");
usb_stor_Bulk_reset(us);
- return USB_STOR_TRANSPORT_ERROR;
+ ret = USB_STOR_TRANSPORT_ERROR;
} else if (residue > datalen) {
dev_dbg(dev, "residue (%uB) > req data (%uB)\n",
residue, datalen);
- return USB_STOR_TRANSPORT_FAILED;
- } else if (csw.Status == US_BULK_STAT_FAIL) {
+ ret = USB_STOR_TRANSPORT_FAILED;
+ } else if (csw->Status == US_BULK_STAT_FAIL) {
dev_dbg(dev, "FAILED\n");
- return USB_STOR_TRANSPORT_FAILED;
+ ret = USB_STOR_TRANSPORT_FAILED;
}
- return 0;
+fail:
+ dma_free(cbw);
+ dma_free(csw);
+ return ret;
}
@@ -214,7 +213,7 @@ int usb_stor_Bulk_transport(struct us_blk_dev *usb_blkdev,
*/
int usb_stor_Bulk_reset(struct us_data *us)
{
- struct device_d *dev = &us->pusb_dev->dev;
+ struct device *dev = &us->pusb_dev->dev;
int result;
int result2;
unsigned int pipe;