blob: d022b5ff4cd092235365ec8233bf58e26dba1e75 [file] [log] [blame]
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001/*
2 * USB Attached SCSI
3 * Note that this is not the same as the USB Mass Storage driver
4 *
Hans de Goede13630742016-04-12 12:27:09 +02005 * Copyright Hans de Goede <hdegoede@redhat.com> for Red Hat, Inc. 2013 - 2016
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02006 * Copyright Matthew Wilcox for Intel Corp, 2010
7 * Copyright Sarah Sharp for Intel Corp, 2010
8 *
9 * Distributed under the terms of the GNU GPL, version two.
10 */
11
12#include <linux/blkdev.h>
13#include <linux/slab.h>
14#include <linux/types.h>
Paul Gortmaker6eb0de82011-07-03 16:09:31 -040015#include <linux/module.h>
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020016#include <linux/usb.h>
Hans de Goede79b4c062013-10-25 17:04:33 +010017#include <linux/usb_usual.h>
Sebastian Andrzej Siewiorc898add2012-01-11 12:42:32 +010018#include <linux/usb/hcd.h>
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020019#include <linux/usb/storage.h>
Sebastian Andrzej Siewior348748b2012-01-11 12:45:56 +010020#include <linux/usb/uas.h>
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020021
22#include <scsi/scsi.h>
Hans de Goede4de7a3732013-10-22 16:10:44 +010023#include <scsi/scsi_eh.h>
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020024#include <scsi/scsi_dbg.h>
25#include <scsi/scsi_cmnd.h>
26#include <scsi/scsi_device.h>
27#include <scsi/scsi_host.h>
28#include <scsi/scsi_tcq.h>
29
Hans de Goede82aa0382013-10-21 08:53:31 +010030#include "uas-detect.h"
Hans de Goede59307852014-09-15 16:04:12 +020031#include "scsiglue.h"
Hans de Goede82aa0382013-10-21 08:53:31 +010032
Hans de Goede5e61aed2014-09-13 12:26:32 +020033#define MAX_CMNDS 256
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020034
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020035struct uas_dev_info {
36 struct usb_interface *intf;
37 struct usb_device *udev;
Gerd Hoffmanna0e39e32012-09-25 10:47:04 +020038 struct usb_anchor cmd_urbs;
Gerd Hoffmannbdd000f2012-06-19 09:54:53 +020039 struct usb_anchor sense_urbs;
40 struct usb_anchor data_urbs;
Hans de Goede59307852014-09-15 16:04:12 +020041 unsigned long flags;
Gerd Hoffmann023b5152012-06-19 09:54:54 +020042 int qdepth, resetting;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020043 unsigned cmd_pipe, status_pipe, data_in_pipe, data_out_pipe;
44 unsigned use_streams:1;
Hans de Goededa65c2b2013-11-11 11:51:42 +010045 unsigned shutdown:1;
Hans de Goede5e61aed2014-09-13 12:26:32 +020046 struct scsi_cmnd *cmnd[MAX_CMNDS];
Gerd Hoffmanne0648522012-09-25 10:47:08 +020047 spinlock_t lock;
Gerd Hoffmann1bf81982013-09-13 13:27:12 +020048 struct work_struct work;
EJ Hsu25399d52020-01-30 01:25:06 -080049 struct work_struct scan_work; /* for async scanning */
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020050};
51
52enum {
Oliver Neukum76433192015-11-05 16:20:36 +010053 SUBMIT_STATUS_URB = BIT(1),
54 ALLOC_DATA_IN_URB = BIT(2),
55 SUBMIT_DATA_IN_URB = BIT(3),
56 ALLOC_DATA_OUT_URB = BIT(4),
57 SUBMIT_DATA_OUT_URB = BIT(5),
58 ALLOC_CMD_URB = BIT(6),
59 SUBMIT_CMD_URB = BIT(7),
60 COMMAND_INFLIGHT = BIT(8),
61 DATA_IN_URB_INFLIGHT = BIT(9),
62 DATA_OUT_URB_INFLIGHT = BIT(10),
63 COMMAND_ABORTED = BIT(11),
64 IS_IN_WORK_LIST = BIT(12),
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020065};
66
67/* Overrides scsi_pointer */
68struct uas_cmd_info {
69 unsigned int state;
Hans de Goedee28e2f2f2014-10-12 12:19:40 +020070 unsigned int uas_tag;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020071 struct urb *cmd_urb;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020072 struct urb *data_in_urb;
73 struct urb *data_out_urb;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020074};
75
76/* I hate forward declarations, but I actually have a loop */
77static int uas_submit_urbs(struct scsi_cmnd *cmnd,
Oliver Neukumb36d8392015-11-03 16:43:17 +010078 struct uas_dev_info *devinfo);
Sarah Sharpea9da1c2011-12-02 11:55:44 -080079static void uas_do_work(struct work_struct *work);
Gerd Hoffmann4c456972012-11-30 11:54:44 +010080static int uas_try_complete(struct scsi_cmnd *cmnd, const char *caller);
Gerd Hoffmannd89bd832013-09-13 13:27:11 +020081static void uas_free_streams(struct uas_dev_info *devinfo);
Hans de Goede1ad7ed52014-09-13 12:26:49 +020082static void uas_log_cmd_state(struct scsi_cmnd *cmnd, const char *prefix,
83 int status);
Gerd Hoffmannaa8f6122012-11-30 11:54:40 +010084
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020085static void uas_do_work(struct work_struct *work)
86{
Gerd Hoffmann1bf81982013-09-13 13:27:12 +020087 struct uas_dev_info *devinfo =
88 container_of(work, struct uas_dev_info, work);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020089 struct uas_cmd_info *cmdinfo;
Hans de Goede43cd99c2014-09-13 12:26:38 +020090 struct scsi_cmnd *cmnd;
Gerd Hoffmanne0648522012-09-25 10:47:08 +020091 unsigned long flags;
Hans de Goede43cd99c2014-09-13 12:26:38 +020092 int i, err;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +020093
Gerd Hoffmann1bf81982013-09-13 13:27:12 +020094 spin_lock_irqsave(&devinfo->lock, flags);
Hans de Goedeb7b5d112014-09-13 12:26:30 +020095
96 if (devinfo->resetting)
97 goto out;
98
Hans de Goede43cd99c2014-09-13 12:26:38 +020099 for (i = 0; i < devinfo->qdepth; i++) {
100 if (!devinfo->cmnd[i])
101 continue;
102
103 cmnd = devinfo->cmnd[i];
104 cmdinfo = (void *)&cmnd->SCp;
Hans de Goede61c09ce2013-11-12 13:44:20 +0100105
106 if (!(cmdinfo->state & IS_IN_WORK_LIST))
107 continue;
108
Oliver Neukumb36d8392015-11-03 16:43:17 +0100109 err = uas_submit_urbs(cmnd, cmnd->device->hostdata);
Hans de Goede61c09ce2013-11-12 13:44:20 +0100110 if (!err)
Gerd Hoffmannefefecf2012-11-30 11:54:42 +0100111 cmdinfo->state &= ~IS_IN_WORK_LIST;
Hans de Goede61c09ce2013-11-12 13:44:20 +0100112 else
Gerd Hoffmann1bf81982013-09-13 13:27:12 +0200113 schedule_work(&devinfo->work);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200114 }
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200115out:
Gerd Hoffmann4c456972012-11-30 11:54:44 +0100116 spin_unlock_irqrestore(&devinfo->lock, flags);
117}
118
EJ Hsu25399d52020-01-30 01:25:06 -0800119static void uas_scan_work(struct work_struct *work)
120{
121 struct uas_dev_info *devinfo =
122 container_of(work, struct uas_dev_info, scan_work);
123 struct Scsi_Host *shost = usb_get_intfdata(devinfo->intf);
124
125 dev_dbg(&devinfo->intf->dev, "starting scan\n");
126 scsi_scan_host(shost);
127 dev_dbg(&devinfo->intf->dev, "scan complete\n");
128}
129
Gerd Hoffmann1bf81982013-09-13 13:27:12 +0200130static void uas_add_work(struct uas_cmd_info *cmdinfo)
131{
132 struct scsi_pointer *scp = (void *)cmdinfo;
133 struct scsi_cmnd *cmnd = container_of(scp, struct scsi_cmnd, SCp);
134 struct uas_dev_info *devinfo = cmnd->device->hostdata;
135
Sanjeev Sharmaab945ef2014-08-12 12:10:21 +0530136 lockdep_assert_held(&devinfo->lock);
Gerd Hoffmann1bf81982013-09-13 13:27:12 +0200137 cmdinfo->state |= IS_IN_WORK_LIST;
138 schedule_work(&devinfo->work);
139}
140
Hans de Goede15893492014-09-13 12:26:36 +0200141static void uas_zap_pending(struct uas_dev_info *devinfo, int result)
Gerd Hoffmann326349f2013-09-13 13:27:13 +0200142{
143 struct uas_cmd_info *cmdinfo;
Hans de Goede43cd99c2014-09-13 12:26:38 +0200144 struct scsi_cmnd *cmnd;
Gerd Hoffmann326349f2013-09-13 13:27:13 +0200145 unsigned long flags;
Hans de Goede43cd99c2014-09-13 12:26:38 +0200146 int i, err;
Gerd Hoffmann326349f2013-09-13 13:27:13 +0200147
148 spin_lock_irqsave(&devinfo->lock, flags);
Hans de Goede43cd99c2014-09-13 12:26:38 +0200149 for (i = 0; i < devinfo->qdepth; i++) {
150 if (!devinfo->cmnd[i])
151 continue;
152
153 cmnd = devinfo->cmnd[i];
154 cmdinfo = (void *)&cmnd->SCp;
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200155 uas_log_cmd_state(cmnd, __func__, 0);
Hans de Goede9c15c572014-09-13 12:26:37 +0200156 /* Sense urbs were killed, clear COMMAND_INFLIGHT manually */
157 cmdinfo->state &= ~COMMAND_INFLIGHT;
Hans de Goede15893492014-09-13 12:26:36 +0200158 cmnd->result = result << 16;
Hans de Goede9c15c572014-09-13 12:26:37 +0200159 err = uas_try_complete(cmnd, __func__);
160 WARN_ON(err != 0);
Gerd Hoffmann326349f2013-09-13 13:27:13 +0200161 }
162 spin_unlock_irqrestore(&devinfo->lock, flags);
163}
164
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200165static void uas_sense(struct urb *urb, struct scsi_cmnd *cmnd)
166{
167 struct sense_iu *sense_iu = urb->transfer_buffer;
168 struct scsi_device *sdev = cmnd->device;
169
170 if (urb->actual_length > 16) {
171 unsigned len = be16_to_cpup(&sense_iu->len);
172 if (len + 16 != urb->actual_length) {
173 int newlen = min(len + 16, urb->actual_length) - 16;
174 if (newlen < 0)
175 newlen = 0;
176 sdev_printk(KERN_INFO, sdev, "%s: urb length %d "
177 "disagrees with IU sense data length %d, "
178 "using %d bytes of sense data\n", __func__,
179 urb->actual_length, len, newlen);
180 len = newlen;
181 }
182 memcpy(cmnd->sense_buffer, sense_iu->sense, len);
183 }
184
185 cmnd->result = sense_iu->status;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200186}
187
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200188static void uas_log_cmd_state(struct scsi_cmnd *cmnd, const char *prefix,
189 int status)
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200190{
191 struct uas_cmd_info *ci = (void *)&cmnd->SCp;
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200192 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200193
Hans de Goede60d9f672014-09-13 12:26:34 +0200194 scmd_printk(KERN_INFO, cmnd,
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200195 "%s %d uas-tag %d inflight:%s%s%s%s%s%s%s%s%s%s%s%s ",
196 prefix, status, cmdinfo->uas_tag,
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200197 (ci->state & SUBMIT_STATUS_URB) ? " s-st" : "",
198 (ci->state & ALLOC_DATA_IN_URB) ? " a-in" : "",
199 (ci->state & SUBMIT_DATA_IN_URB) ? " s-in" : "",
200 (ci->state & ALLOC_DATA_OUT_URB) ? " a-out" : "",
201 (ci->state & SUBMIT_DATA_OUT_URB) ? " s-out" : "",
202 (ci->state & ALLOC_CMD_URB) ? " a-cmd" : "",
203 (ci->state & SUBMIT_CMD_URB) ? " s-cmd" : "",
204 (ci->state & COMMAND_INFLIGHT) ? " CMD" : "",
205 (ci->state & DATA_IN_URB_INFLIGHT) ? " IN" : "",
206 (ci->state & DATA_OUT_URB_INFLIGHT) ? " OUT" : "",
Gerd Hoffmannb06e48a2012-11-30 11:54:41 +0100207 (ci->state & COMMAND_ABORTED) ? " abort" : "",
Gerd Hoffmannefefecf2012-11-30 11:54:42 +0100208 (ci->state & IS_IN_WORK_LIST) ? " work" : "");
Hans de Goede6dcd8ec2014-09-13 12:26:45 +0200209 scsi_print_command(cmnd);
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200210}
211
Hans de Goede4c5481e2014-09-13 12:26:41 +0200212static void uas_free_unsubmitted_urbs(struct scsi_cmnd *cmnd)
213{
214 struct uas_cmd_info *cmdinfo;
215
216 if (!cmnd)
217 return;
218
219 cmdinfo = (void *)&cmnd->SCp;
220
221 if (cmdinfo->state & SUBMIT_CMD_URB)
222 usb_free_urb(cmdinfo->cmd_urb);
223
224 /* data urbs may have never gotten their submit flag set */
225 if (!(cmdinfo->state & DATA_IN_URB_INFLIGHT))
226 usb_free_urb(cmdinfo->data_in_urb);
227 if (!(cmdinfo->state & DATA_OUT_URB_INFLIGHT))
228 usb_free_urb(cmdinfo->data_out_urb);
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200229}
230
231static int uas_try_complete(struct scsi_cmnd *cmnd, const char *caller)
232{
233 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200234 struct uas_dev_info *devinfo = (void *)cmnd->device->hostdata;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200235
Sanjeev Sharmaab945ef2014-08-12 12:10:21 +0530236 lockdep_assert_held(&devinfo->lock);
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200237 if (cmdinfo->state & (COMMAND_INFLIGHT |
238 DATA_IN_URB_INFLIGHT |
Gerd Hoffmannb06e48a2012-11-30 11:54:41 +0100239 DATA_OUT_URB_INFLIGHT |
Hans de Goede616f0e62014-09-13 12:26:40 +0200240 COMMAND_ABORTED))
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200241 return -EBUSY;
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200242 devinfo->cmnd[cmdinfo->uas_tag - 1] = NULL;
Hans de Goede4c5481e2014-09-13 12:26:41 +0200243 uas_free_unsubmitted_urbs(cmnd);
Gerd Hoffmannc621a812012-06-19 09:54:48 +0200244 cmnd->scsi_done(cmnd);
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200245 return 0;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200246}
247
248static void uas_xfer_data(struct urb *urb, struct scsi_cmnd *cmnd,
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200249 unsigned direction)
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200250{
251 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
252 int err;
253
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200254 cmdinfo->state |= direction | SUBMIT_STATUS_URB;
Oliver Neukumb36d8392015-11-03 16:43:17 +0100255 err = uas_submit_urbs(cmnd, cmnd->device->hostdata);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200256 if (err) {
Gerd Hoffmann1bf81982013-09-13 13:27:12 +0200257 uas_add_work(cmdinfo);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200258 }
259}
260
Oliver Neukumaa742682016-01-19 10:51:09 +0100261static bool uas_evaluate_response_iu(struct response_iu *riu, struct scsi_cmnd *cmnd)
262{
263 u8 response_code = riu->response_code;
264
265 switch (response_code) {
266 case RC_INCORRECT_LUN:
267 cmnd->result = DID_BAD_TARGET << 16;
268 break;
269 case RC_TMF_SUCCEEDED:
270 cmnd->result = DID_OK << 16;
271 break;
272 case RC_TMF_NOT_SUPPORTED:
273 cmnd->result = DID_TARGET_FAILURE << 16;
274 break;
275 default:
276 uas_log_cmd_state(cmnd, "response iu", response_code);
277 cmnd->result = DID_ERROR << 16;
278 break;
279 }
280
281 return response_code == RC_TMF_SUCCEEDED;
282}
283
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200284static void uas_stat_cmplt(struct urb *urb)
285{
286 struct iu *iu = urb->transfer_buffer;
Sebastian Andrzej Siewior22188f42011-12-19 20:22:39 +0100287 struct Scsi_Host *shost = urb->context;
Hans de Goede21fc05b2013-11-13 09:32:22 +0100288 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goede60d9f672014-09-13 12:26:34 +0200289 struct urb *data_in_urb = NULL;
290 struct urb *data_out_urb = NULL;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200291 struct scsi_cmnd *cmnd;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200292 struct uas_cmd_info *cmdinfo;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200293 unsigned long flags;
Hans de Goede5e61aed2014-09-13 12:26:32 +0200294 unsigned int idx;
Oliver Neukumcca26be2015-08-24 11:10:43 +0200295 int status = urb->status;
Oliver Neukumaa742682016-01-19 10:51:09 +0100296 bool success;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200297
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200298 spin_lock_irqsave(&devinfo->lock, flags);
299
300 if (devinfo->resetting)
301 goto out;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200302
Oliver Neukumcca26be2015-08-24 11:10:43 +0200303 if (status) {
304 if (status != -ENOENT && status != -ECONNRESET && status != -ESHUTDOWN)
305 dev_err(&urb->dev->dev, "stat urb: status %d\n", status);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200306 goto out;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200307 }
308
Hans de Goede5e61aed2014-09-13 12:26:32 +0200309 idx = be16_to_cpup(&iu->tag) - 1;
310 if (idx >= MAX_CMNDS || !devinfo->cmnd[idx]) {
311 dev_err(&urb->dev->dev,
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200312 "stat urb: no pending cmd for uas-tag %d\n", idx + 1);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200313 goto out;
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200314 }
315
Hans de Goede5e61aed2014-09-13 12:26:32 +0200316 cmnd = devinfo->cmnd[idx];
Gerd Hoffmanne0423de2012-09-26 10:29:03 +0200317 cmdinfo = (void *)&cmnd->SCp;
Hans de Goeded89da032014-09-13 12:26:33 +0200318
319 if (!(cmdinfo->state & COMMAND_INFLIGHT)) {
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200320 uas_log_cmd_state(cmnd, "unexpected status cmplt", 0);
Hans de Goeded89da032014-09-13 12:26:33 +0200321 goto out;
322 }
323
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200324 switch (iu->iu_id) {
325 case IU_ID_STATUS:
Hans de Goede5ad22cf2014-09-13 12:26:47 +0200326 uas_sense(urb, cmnd);
Gerd Hoffmann8aac8632012-06-19 09:54:52 +0200327 if (cmnd->result != 0) {
328 /* cancel data transfers on error */
Hans de Goede60d9f672014-09-13 12:26:34 +0200329 data_in_urb = usb_get_urb(cmdinfo->data_in_urb);
330 data_out_urb = usb_get_urb(cmdinfo->data_out_urb);
Gerd Hoffmann8aac8632012-06-19 09:54:52 +0200331 }
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200332 cmdinfo->state &= ~COMMAND_INFLIGHT;
333 uas_try_complete(cmnd, __func__);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200334 break;
335 case IU_ID_READ_READY:
Hans de Goede8e453152013-11-15 10:04:11 +0100336 if (!cmdinfo->data_in_urb ||
337 (cmdinfo->state & DATA_IN_URB_INFLIGHT)) {
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200338 uas_log_cmd_state(cmnd, "unexpected read rdy", 0);
Hans de Goede8e453152013-11-15 10:04:11 +0100339 break;
340 }
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200341 uas_xfer_data(urb, cmnd, SUBMIT_DATA_IN_URB);
342 break;
343 case IU_ID_WRITE_READY:
Hans de Goede8e453152013-11-15 10:04:11 +0100344 if (!cmdinfo->data_out_urb ||
345 (cmdinfo->state & DATA_OUT_URB_INFLIGHT)) {
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200346 uas_log_cmd_state(cmnd, "unexpected write rdy", 0);
Hans de Goede8e453152013-11-15 10:04:11 +0100347 break;
348 }
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200349 uas_xfer_data(urb, cmnd, SUBMIT_DATA_OUT_URB);
350 break;
Hans de Goedefac1f482014-09-13 12:26:51 +0200351 case IU_ID_RESPONSE:
Hans de Goedefac1f482014-09-13 12:26:51 +0200352 cmdinfo->state &= ~COMMAND_INFLIGHT;
Oliver Neukumaa742682016-01-19 10:51:09 +0100353 success = uas_evaluate_response_iu((struct response_iu *)iu, cmnd);
354 if (!success) {
355 /* Error, cancel data transfers */
356 data_in_urb = usb_get_urb(cmdinfo->data_in_urb);
357 data_out_urb = usb_get_urb(cmdinfo->data_out_urb);
358 }
Hans de Goedefac1f482014-09-13 12:26:51 +0200359 uas_try_complete(cmnd, __func__);
360 break;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200361 default:
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200362 uas_log_cmd_state(cmnd, "bogus IU", iu->iu_id);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200363 }
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200364out:
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200365 usb_free_urb(urb);
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200366 spin_unlock_irqrestore(&devinfo->lock, flags);
Hans de Goede60d9f672014-09-13 12:26:34 +0200367
368 /* Unlinking of data urbs must be done without holding the lock */
369 if (data_in_urb) {
370 usb_unlink_urb(data_in_urb);
371 usb_put_urb(data_in_urb);
372 }
373 if (data_out_urb) {
374 usb_unlink_urb(data_out_urb);
375 usb_put_urb(data_out_urb);
376 }
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200377}
378
Gerd Hoffmannc621a812012-06-19 09:54:48 +0200379static void uas_data_cmplt(struct urb *urb)
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200380{
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200381 struct scsi_cmnd *cmnd = urb->context;
382 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200383 struct uas_dev_info *devinfo = (void *)cmnd->device->hostdata;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200384 struct scsi_data_buffer *sdb = NULL;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200385 unsigned long flags;
Oliver Neukumcca26be2015-08-24 11:10:43 +0200386 int status = urb->status;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200387
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200388 spin_lock_irqsave(&devinfo->lock, flags);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200389
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200390 if (cmdinfo->data_in_urb == urb) {
391 sdb = scsi_in(cmnd);
392 cmdinfo->state &= ~DATA_IN_URB_INFLIGHT;
Hans de Goede85fea822014-09-13 12:26:35 +0200393 cmdinfo->data_in_urb = NULL;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200394 } else if (cmdinfo->data_out_urb == urb) {
395 sdb = scsi_out(cmnd);
396 cmdinfo->state &= ~DATA_OUT_URB_INFLIGHT;
Hans de Goede85fea822014-09-13 12:26:35 +0200397 cmdinfo->data_out_urb = NULL;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200398 }
Gerd Hoffmannf491ecb2013-09-13 13:27:14 +0200399 if (sdb == NULL) {
400 WARN_ON_ONCE(1);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200401 goto out;
402 }
403
404 if (devinfo->resetting)
405 goto out;
406
Hans de Goeded89da032014-09-13 12:26:33 +0200407 /* Data urbs should not complete before the cmd urb is submitted */
408 if (cmdinfo->state & SUBMIT_CMD_URB) {
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200409 uas_log_cmd_state(cmnd, "unexpected data cmplt", 0);
Hans de Goeded89da032014-09-13 12:26:33 +0200410 goto out;
411 }
412
Oliver Neukumcca26be2015-08-24 11:10:43 +0200413 if (status) {
414 if (status != -ENOENT && status != -ECONNRESET && status != -ESHUTDOWN)
415 uas_log_cmd_state(cmnd, "data cmplt err", status);
Gerd Hoffmann8aac8632012-06-19 09:54:52 +0200416 /* error: no data transfered */
417 sdb->resid = sdb->length;
418 } else {
419 sdb->resid = sdb->length - urb->actual_length;
420 }
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200421 uas_try_complete(cmnd, __func__);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200422out:
Hans de Goede85fea822014-09-13 12:26:35 +0200423 usb_free_urb(urb);
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200424 spin_unlock_irqrestore(&devinfo->lock, flags);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200425}
426
Hans de Goede876285c2013-11-07 08:52:42 +0100427static void uas_cmd_cmplt(struct urb *urb)
428{
Hans de Goedeb6823c52014-09-13 12:26:39 +0200429 if (urb->status)
430 dev_err(&urb->dev->dev, "cmd cmplt err %d\n", urb->status);
Hans de Goede876285c2013-11-07 08:52:42 +0100431
Hans de Goede876285c2013-11-07 08:52:42 +0100432 usb_free_urb(urb);
433}
434
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200435static struct urb *uas_alloc_data_urb(struct uas_dev_info *devinfo, gfp_t gfp,
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200436 struct scsi_cmnd *cmnd,
437 enum dma_data_direction dir)
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200438{
439 struct usb_device *udev = devinfo->udev;
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200440 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200441 struct urb *urb = usb_alloc_urb(0, gfp);
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200442 struct scsi_data_buffer *sdb = (dir == DMA_FROM_DEVICE)
443 ? scsi_in(cmnd) : scsi_out(cmnd);
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200444 unsigned int pipe = (dir == DMA_FROM_DEVICE)
445 ? devinfo->data_in_pipe : devinfo->data_out_pipe;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200446
447 if (!urb)
448 goto out;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200449 usb_fill_bulk_urb(urb, udev, pipe, NULL, sdb->length,
450 uas_data_cmplt, cmnd);
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200451 if (devinfo->use_streams)
452 urb->stream_id = cmdinfo->uas_tag;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200453 urb->num_sgs = udev->bus->sg_tablesize ? sdb->table.nents : 0;
454 urb->sg = sdb->table.sgl;
455 out:
456 return urb;
457}
458
459static struct urb *uas_alloc_sense_urb(struct uas_dev_info *devinfo, gfp_t gfp,
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200460 struct scsi_cmnd *cmnd)
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200461{
462 struct usb_device *udev = devinfo->udev;
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200463 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200464 struct urb *urb = usb_alloc_urb(0, gfp);
465 struct sense_iu *iu;
466
467 if (!urb)
468 goto out;
469
Matthew Wilcoxac563cf2010-12-15 15:44:03 -0500470 iu = kzalloc(sizeof(*iu), gfp);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200471 if (!iu)
472 goto free;
473
474 usb_fill_bulk_urb(urb, udev, devinfo->status_pipe, iu, sizeof(*iu),
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200475 uas_stat_cmplt, cmnd->device->host);
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200476 if (devinfo->use_streams)
477 urb->stream_id = cmdinfo->uas_tag;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200478 urb->transfer_flags |= URB_FREE_BUFFER;
479 out:
480 return urb;
481 free:
482 usb_free_urb(urb);
483 return NULL;
484}
485
486static struct urb *uas_alloc_cmd_urb(struct uas_dev_info *devinfo, gfp_t gfp,
Hans de Goedea887cd32013-10-17 19:47:28 +0200487 struct scsi_cmnd *cmnd)
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200488{
489 struct usb_device *udev = devinfo->udev;
490 struct scsi_device *sdev = cmnd->device;
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200491 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200492 struct urb *urb = usb_alloc_urb(0, gfp);
493 struct command_iu *iu;
494 int len;
495
496 if (!urb)
497 goto out;
498
499 len = cmnd->cmd_len - 16;
500 if (len < 0)
501 len = 0;
502 len = ALIGN(len, 4);
Matthew Wilcoxac563cf2010-12-15 15:44:03 -0500503 iu = kzalloc(sizeof(*iu) + len, gfp);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200504 if (!iu)
505 goto free;
506
507 iu->iu_id = IU_ID_COMMAND;
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200508 iu->tag = cpu_to_be16(cmdinfo->uas_tag);
Christoph Hellwig02e031c2010-11-10 14:54:09 +0100509 iu->prio_attr = UAS_SIMPLE_TAG;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200510 iu->len = len;
511 int_to_scsilun(sdev->lun, &iu->lun);
512 memcpy(iu->cdb, cmnd->cmnd, cmnd->cmd_len);
513
514 usb_fill_bulk_urb(urb, udev, devinfo->cmd_pipe, iu, sizeof(*iu) + len,
Hans de Goedeb6823c52014-09-13 12:26:39 +0200515 uas_cmd_cmplt, NULL);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200516 urb->transfer_flags |= URB_FREE_BUFFER;
517 out:
518 return urb;
519 free:
520 usb_free_urb(urb);
521 return NULL;
522}
523
524/*
525 * Why should I request the Status IU before sending the Command IU? Spec
526 * says to, but also says the device may receive them in any order. Seems
527 * daft to me.
528 */
529
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200530static struct urb *uas_submit_sense_urb(struct scsi_cmnd *cmnd, gfp_t gfp)
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200531{
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200532 struct uas_dev_info *devinfo = cmnd->device->hostdata;
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200533 struct urb *urb;
Hans de Goede876285c2013-11-07 08:52:42 +0100534 int err;
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200535
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200536 urb = uas_alloc_sense_urb(devinfo, gfp, cmnd);
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200537 if (!urb)
Hans de Goede70cf0fb2013-10-29 10:37:23 +0100538 return NULL;
Hans de Goeded5f808d2013-10-17 19:30:26 +0200539 usb_anchor_urb(urb, &devinfo->sense_urbs);
Hans de Goede876285c2013-11-07 08:52:42 +0100540 err = usb_submit_urb(urb, gfp);
541 if (err) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200542 usb_unanchor_urb(urb);
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200543 uas_log_cmd_state(cmnd, "sense submit err", err);
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200544 usb_free_urb(urb);
Hans de Goede70cf0fb2013-10-29 10:37:23 +0100545 return NULL;
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200546 }
Hans de Goede70cf0fb2013-10-29 10:37:23 +0100547 return urb;
Gerd Hoffmanne9bd7e12012-06-19 09:54:50 +0200548}
549
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200550static int uas_submit_urbs(struct scsi_cmnd *cmnd,
Oliver Neukumb36d8392015-11-03 16:43:17 +0100551 struct uas_dev_info *devinfo)
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200552{
553 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Hans de Goede70cf0fb2013-10-29 10:37:23 +0100554 struct urb *urb;
Hans de Goede876285c2013-11-07 08:52:42 +0100555 int err;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200556
Sanjeev Sharmaab945ef2014-08-12 12:10:21 +0530557 lockdep_assert_held(&devinfo->lock);
Matthew Wilcox92a3f762010-12-15 15:44:04 -0500558 if (cmdinfo->state & SUBMIT_STATUS_URB) {
Oliver Neukumb36d8392015-11-03 16:43:17 +0100559 urb = uas_submit_sense_urb(cmnd, GFP_ATOMIC);
Hans de Goede70cf0fb2013-10-29 10:37:23 +0100560 if (!urb)
561 return SCSI_MLQUEUE_DEVICE_BUSY;
Matthew Wilcox92a3f762010-12-15 15:44:04 -0500562 cmdinfo->state &= ~SUBMIT_STATUS_URB;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200563 }
564
565 if (cmdinfo->state & ALLOC_DATA_IN_URB) {
Oliver Neukumb36d8392015-11-03 16:43:17 +0100566 cmdinfo->data_in_urb = uas_alloc_data_urb(devinfo, GFP_ATOMIC,
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200567 cmnd, DMA_FROM_DEVICE);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200568 if (!cmdinfo->data_in_urb)
569 return SCSI_MLQUEUE_DEVICE_BUSY;
570 cmdinfo->state &= ~ALLOC_DATA_IN_URB;
571 }
572
573 if (cmdinfo->state & SUBMIT_DATA_IN_URB) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200574 usb_anchor_urb(cmdinfo->data_in_urb, &devinfo->data_urbs);
Oliver Neukumb36d8392015-11-03 16:43:17 +0100575 err = usb_submit_urb(cmdinfo->data_in_urb, GFP_ATOMIC);
Hans de Goede876285c2013-11-07 08:52:42 +0100576 if (err) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200577 usb_unanchor_urb(cmdinfo->data_in_urb);
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200578 uas_log_cmd_state(cmnd, "data in submit err", err);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200579 return SCSI_MLQUEUE_DEVICE_BUSY;
580 }
581 cmdinfo->state &= ~SUBMIT_DATA_IN_URB;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200582 cmdinfo->state |= DATA_IN_URB_INFLIGHT;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200583 }
584
585 if (cmdinfo->state & ALLOC_DATA_OUT_URB) {
Oliver Neukumb36d8392015-11-03 16:43:17 +0100586 cmdinfo->data_out_urb = uas_alloc_data_urb(devinfo, GFP_ATOMIC,
Hans de Goede2d75b9c2014-10-03 12:08:56 +0200587 cmnd, DMA_TO_DEVICE);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200588 if (!cmdinfo->data_out_urb)
589 return SCSI_MLQUEUE_DEVICE_BUSY;
590 cmdinfo->state &= ~ALLOC_DATA_OUT_URB;
591 }
592
593 if (cmdinfo->state & SUBMIT_DATA_OUT_URB) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200594 usb_anchor_urb(cmdinfo->data_out_urb, &devinfo->data_urbs);
Oliver Neukumb36d8392015-11-03 16:43:17 +0100595 err = usb_submit_urb(cmdinfo->data_out_urb, GFP_ATOMIC);
Hans de Goede876285c2013-11-07 08:52:42 +0100596 if (err) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200597 usb_unanchor_urb(cmdinfo->data_out_urb);
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200598 uas_log_cmd_state(cmnd, "data out submit err", err);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200599 return SCSI_MLQUEUE_DEVICE_BUSY;
600 }
601 cmdinfo->state &= ~SUBMIT_DATA_OUT_URB;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200602 cmdinfo->state |= DATA_OUT_URB_INFLIGHT;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200603 }
604
605 if (cmdinfo->state & ALLOC_CMD_URB) {
Oliver Neukumb36d8392015-11-03 16:43:17 +0100606 cmdinfo->cmd_urb = uas_alloc_cmd_urb(devinfo, GFP_ATOMIC, cmnd);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200607 if (!cmdinfo->cmd_urb)
608 return SCSI_MLQUEUE_DEVICE_BUSY;
609 cmdinfo->state &= ~ALLOC_CMD_URB;
610 }
611
612 if (cmdinfo->state & SUBMIT_CMD_URB) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200613 usb_anchor_urb(cmdinfo->cmd_urb, &devinfo->cmd_urbs);
Oliver Neukumb36d8392015-11-03 16:43:17 +0100614 err = usb_submit_urb(cmdinfo->cmd_urb, GFP_ATOMIC);
Hans de Goede876285c2013-11-07 08:52:42 +0100615 if (err) {
Hans de Goeded5f808d2013-10-17 19:30:26 +0200616 usb_unanchor_urb(cmdinfo->cmd_urb);
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200617 uas_log_cmd_state(cmnd, "cmd submit err", err);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200618 return SCSI_MLQUEUE_DEVICE_BUSY;
619 }
Gerd Hoffmanna0e39e32012-09-25 10:47:04 +0200620 cmdinfo->cmd_urb = NULL;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200621 cmdinfo->state &= ~SUBMIT_CMD_URB;
Gerd Hoffmannb1d67692012-06-19 09:54:51 +0200622 cmdinfo->state |= COMMAND_INFLIGHT;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200623 }
624
625 return 0;
626}
627
Jeff Garzikf2812332010-11-16 02:10:29 -0500628static int uas_queuecommand_lck(struct scsi_cmnd *cmnd,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200629 void (*done)(struct scsi_cmnd *))
630{
631 struct scsi_device *sdev = cmnd->device;
632 struct uas_dev_info *devinfo = sdev->hostdata;
633 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200634 unsigned long flags;
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200635 int idx, err;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200636
637 BUILD_BUG_ON(sizeof(struct uas_cmd_info) > sizeof(struct scsi_pointer));
638
Hans de Goedef9dc0242014-09-13 12:26:42 +0200639 /* Re-check scsi_block_requests now that we've the host-lock */
640 if (cmnd->device->host->host_self_blocked)
641 return SCSI_MLQUEUE_DEVICE_BUSY;
642
Hans de Goede59307852014-09-15 16:04:12 +0200643 if ((devinfo->flags & US_FL_NO_ATA_1X) &&
644 (cmnd->cmnd[0] == ATA_12 || cmnd->cmnd[0] == ATA_16)) {
645 memcpy(cmnd->sense_buffer, usb_stor_sense_invalidCDB,
646 sizeof(usb_stor_sense_invalidCDB));
647 cmnd->result = SAM_STAT_CHECK_CONDITION;
648 cmnd->scsi_done(cmnd);
649 return 0;
650 }
651
Hans de Goedec6f63202013-11-13 09:24:15 +0100652 spin_lock_irqsave(&devinfo->lock, flags);
653
Gerd Hoffmannf8be6bf2012-11-30 11:54:45 +0100654 if (devinfo->resetting) {
655 cmnd->result = DID_ERROR << 16;
656 cmnd->scsi_done(cmnd);
Hans de Goedec6f63202013-11-13 09:24:15 +0100657 spin_unlock_irqrestore(&devinfo->lock, flags);
Gerd Hoffmannf8be6bf2012-11-30 11:54:45 +0100658 return 0;
659 }
660
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200661 /* Find a free uas-tag */
662 for (idx = 0; idx < devinfo->qdepth; idx++) {
663 if (!devinfo->cmnd[idx])
664 break;
665 }
666 if (idx == devinfo->qdepth) {
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200667 spin_unlock_irqrestore(&devinfo->lock, flags);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200668 return SCSI_MLQUEUE_DEVICE_BUSY;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200669 }
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200670
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200671 cmnd->scsi_done = done;
672
Hans de Goede5e61aed2014-09-13 12:26:32 +0200673 memset(cmdinfo, 0, sizeof(*cmdinfo));
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200674 cmdinfo->uas_tag = idx + 1; /* uas-tag == usb-stream-id, so 1 based */
Hans de Goedee0620002014-09-13 12:26:31 +0200675 cmdinfo->state = SUBMIT_STATUS_URB | ALLOC_CMD_URB | SUBMIT_CMD_URB;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200676
677 switch (cmnd->sc_data_direction) {
678 case DMA_FROM_DEVICE:
679 cmdinfo->state |= ALLOC_DATA_IN_URB | SUBMIT_DATA_IN_URB;
680 break;
681 case DMA_BIDIRECTIONAL:
682 cmdinfo->state |= ALLOC_DATA_IN_URB | SUBMIT_DATA_IN_URB;
683 case DMA_TO_DEVICE:
684 cmdinfo->state |= ALLOC_DATA_OUT_URB | SUBMIT_DATA_OUT_URB;
685 case DMA_NONE:
686 break;
687 }
688
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200689 if (!devinfo->use_streams)
Gerd Hoffmanndb32de12012-06-19 09:54:49 +0200690 cmdinfo->state &= ~(SUBMIT_DATA_IN_URB | SUBMIT_DATA_OUT_URB);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200691
Oliver Neukumb36d8392015-11-03 16:43:17 +0100692 err = uas_submit_urbs(cmnd, devinfo);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200693 if (err) {
694 /* If we did nothing, give up now */
Matthew Wilcox92a3f762010-12-15 15:44:04 -0500695 if (cmdinfo->state & SUBMIT_STATUS_URB) {
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200696 spin_unlock_irqrestore(&devinfo->lock, flags);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200697 return SCSI_MLQUEUE_DEVICE_BUSY;
698 }
Gerd Hoffmann1bf81982013-09-13 13:27:12 +0200699 uas_add_work(cmdinfo);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200700 }
701
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200702 devinfo->cmnd[idx] = cmnd;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200703 spin_unlock_irqrestore(&devinfo->lock, flags);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200704 return 0;
705}
706
Jeff Garzikf2812332010-11-16 02:10:29 -0500707static DEF_SCSI_QCMD(uas_queuecommand)
708
Hans de Goede616f0e62014-09-13 12:26:40 +0200709/*
710 * For now we do not support actually sending an abort to the device, so
711 * this eh always fails. Still we must define it to make sure that we've
712 * dropped all references to the cmnd in question once this function exits.
713 */
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200714static int uas_eh_abort_handler(struct scsi_cmnd *cmnd)
715{
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200716 struct uas_cmd_info *cmdinfo = (void *)&cmnd->SCp;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200717 struct uas_dev_info *devinfo = (void *)cmnd->device->hostdata;
Hans de Goede616f0e62014-09-13 12:26:40 +0200718 struct urb *data_in_urb = NULL;
719 struct urb *data_out_urb = NULL;
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200720 unsigned long flags;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200721
Gerd Hoffmanne0648522012-09-25 10:47:08 +0200722 spin_lock_irqsave(&devinfo->lock, flags);
Hans de Goedec6f63202013-11-13 09:24:15 +0100723
Hans de Goede1ad7ed52014-09-13 12:26:49 +0200724 uas_log_cmd_state(cmnd, __func__, 0);
Hans de Goede616f0e62014-09-13 12:26:40 +0200725
726 /* Ensure that try_complete does not call scsi_done */
727 cmdinfo->state |= COMMAND_ABORTED;
728
729 /* Drop all refs to this cmnd, kill data urbs to break their ref */
Hans de Goedee28e2f2f2014-10-12 12:19:40 +0200730 devinfo->cmnd[cmdinfo->uas_tag - 1] = NULL;
Hans de Goede616f0e62014-09-13 12:26:40 +0200731 if (cmdinfo->state & DATA_IN_URB_INFLIGHT)
732 data_in_urb = usb_get_urb(cmdinfo->data_in_urb);
733 if (cmdinfo->state & DATA_OUT_URB_INFLIGHT)
734 data_out_urb = usb_get_urb(cmdinfo->data_out_urb);
735
Hans de Goede4c5481e2014-09-13 12:26:41 +0200736 uas_free_unsubmitted_urbs(cmnd);
737
Hans de Goede616f0e62014-09-13 12:26:40 +0200738 spin_unlock_irqrestore(&devinfo->lock, flags);
739
740 if (data_in_urb) {
741 usb_kill_urb(data_in_urb);
742 usb_put_urb(data_in_urb);
743 }
744 if (data_out_urb) {
745 usb_kill_urb(data_out_urb);
746 usb_put_urb(data_out_urb);
Hans de Goedec6f63202013-11-13 09:24:15 +0100747 }
748
Hans de Goede616f0e62014-09-13 12:26:40 +0200749 return FAILED;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200750}
751
752static int uas_eh_bus_reset_handler(struct scsi_cmnd *cmnd)
753{
754 struct scsi_device *sdev = cmnd->device;
755 struct uas_dev_info *devinfo = sdev->hostdata;
756 struct usb_device *udev = devinfo->udev;
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200757 unsigned long flags;
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200758 int err;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200759
Hans de Goedebe326f42013-09-22 16:27:02 +0200760 err = usb_lock_device_for_reset(udev, devinfo->intf);
761 if (err) {
762 shost_printk(KERN_ERR, sdev->host,
763 "%s FAILED to get lock err %d\n", __func__, err);
764 return FAILED;
765 }
766
Gerd Hoffmann326349f2013-09-13 13:27:13 +0200767 shost_printk(KERN_INFO, sdev->host, "%s start\n", __func__);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200768
769 spin_lock_irqsave(&devinfo->lock, flags);
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200770 devinfo->resetting = 1;
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200771 spin_unlock_irqrestore(&devinfo->lock, flags);
772
Gerd Hoffmanna0e39e32012-09-25 10:47:04 +0200773 usb_kill_anchored_urbs(&devinfo->cmd_urbs);
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200774 usb_kill_anchored_urbs(&devinfo->sense_urbs);
775 usb_kill_anchored_urbs(&devinfo->data_urbs);
Hans de Goede15893492014-09-13 12:26:36 +0200776 uas_zap_pending(devinfo, DID_RESET);
777
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200778 err = usb_reset_device(udev);
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200779
780 spin_lock_irqsave(&devinfo->lock, flags);
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200781 devinfo->resetting = 0;
Hans de Goedeb7b5d112014-09-13 12:26:30 +0200782 spin_unlock_irqrestore(&devinfo->lock, flags);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200783
Hans de Goedebe326f42013-09-22 16:27:02 +0200784 usb_unlock_device(udev);
785
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200786 if (err) {
Hans de Goedece39fe62014-09-13 12:26:50 +0200787 shost_printk(KERN_INFO, sdev->host, "%s FAILED err %d\n",
788 __func__, err);
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200789 return FAILED;
790 }
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200791
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200792 shost_printk(KERN_INFO, sdev->host, "%s success\n", __func__);
793 return SUCCESS;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200794}
795
Hans de Goede13630742016-04-12 12:27:09 +0200796static int uas_target_alloc(struct scsi_target *starget)
797{
798 struct uas_dev_info *devinfo = (struct uas_dev_info *)
799 dev_to_shost(starget->dev.parent)->hostdata;
800
801 if (devinfo->flags & US_FL_NO_REPORT_LUNS)
802 starget->no_report_luns = 1;
803
804 return 0;
805}
806
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200807static int uas_slave_alloc(struct scsi_device *sdev)
808{
Hans de Goedeee136af2015-04-21 11:20:31 +0200809 struct uas_dev_info *devinfo =
810 (struct uas_dev_info *)sdev->host->hostdata;
811
812 sdev->hostdata = devinfo;
Hans de Goede37599f92013-11-15 10:04:31 +0100813
Felipe Balbif0183a32016-04-18 13:09:11 +0300814 /*
Oliver Neukum361622e2019-04-30 12:21:45 +0200815 * The protocol has no requirements on alignment in the strict sense.
816 * Controllers may or may not have alignment restrictions.
817 * As this is not exported, we use an extremely conservative guess.
Hans de Goede37599f92013-11-15 10:04:31 +0100818 */
819 blk_queue_update_dma_alignment(sdev->request_queue, (512 - 1));
820
Hans de Goedeee136af2015-04-21 11:20:31 +0200821 if (devinfo->flags & US_FL_MAX_SECTORS_64)
822 blk_queue_max_hw_sectors(sdev->request_queue, 64);
823 else if (devinfo->flags & US_FL_MAX_SECTORS_240)
824 blk_queue_max_hw_sectors(sdev->request_queue, 240);
825
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200826 return 0;
827}
828
829static int uas_slave_configure(struct scsi_device *sdev)
830{
831 struct uas_dev_info *devinfo = sdev->hostdata;
Hans de Goede734016b2014-09-16 18:36:52 +0200832
833 if (devinfo->flags & US_FL_NO_REPORT_OPCODES)
834 sdev->no_report_opcodes = 1;
835
Dmitry Katsubo9fa62b12015-11-20 01:30:44 +0100836 /* A few buggy USB-ATA bridges don't understand FUA */
837 if (devinfo->flags & US_FL_BROKEN_FUA)
838 sdev->broken_fua = 1;
839
Alexander Kappner187941e2018-05-18 21:50:15 -0700840 /* UAS also needs to support FL_ALWAYS_SYNC */
841 if (devinfo->flags & US_FL_ALWAYS_SYNC) {
842 sdev->skip_ms_page_3f = 1;
843 sdev->skip_ms_page_8 = 1;
844 sdev->wce_default_on = 1;
845 }
Oliver Neukumcdddc622018-08-09 16:03:37 +0200846
Oliver Neukum4b881312019-11-14 12:27:56 +0100847 /* Some disks cannot handle READ_CAPACITY_16 */
848 if (devinfo->flags & US_FL_NO_READ_CAPACITY_16)
849 sdev->no_read_capacity_16 = 1;
850
Oliver Neukumcdddc622018-08-09 16:03:37 +0200851 /*
852 * Some disks return the total number of blocks in response
853 * to READ CAPACITY rather than the highest block number.
854 * If this device makes that mistake, tell the sd driver.
855 */
856 if (devinfo->flags & US_FL_FIX_CAPACITY)
857 sdev->fix_capacity = 1;
858
859 /*
Oliver Neukum7e2ae622019-11-14 12:27:57 +0100860 * in some cases we have to guess
861 */
862 if (devinfo->flags & US_FL_CAPACITY_HEURISTICS)
863 sdev->guess_capacity = 1;
864
865 /*
Oliver Neukumcdddc622018-08-09 16:03:37 +0200866 * Some devices don't like MODE SENSE with page=0x3f,
867 * which is the command used for checking if a device
868 * is write-protected. Now that we tell the sd driver
869 * to do a 192-byte transfer with this command the
870 * majority of devices work fine, but a few still can't
871 * handle it. The sd driver will simply assume those
872 * devices are write-enabled.
873 */
874 if (devinfo->flags & US_FL_NO_WP_DETECT)
875 sdev->skip_ms_page_3f = 1;
876
Hans de Goede593224e2016-05-31 09:18:03 +0200877 scsi_change_queue_depth(sdev, devinfo->qdepth - 2);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200878 return 0;
879}
880
881static struct scsi_host_template uas_host_template = {
882 .module = THIS_MODULE,
883 .name = "uas",
884 .queuecommand = uas_queuecommand,
Hans de Goede13630742016-04-12 12:27:09 +0200885 .target_alloc = uas_target_alloc,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200886 .slave_alloc = uas_slave_alloc,
887 .slave_configure = uas_slave_configure,
888 .eh_abort_handler = uas_eh_abort_handler,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200889 .eh_bus_reset_handler = uas_eh_bus_reset_handler,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200890 .this_id = -1,
891 .sg_tablesize = SG_NONE,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200892 .skip_settle_delay = 1,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200893};
894
Hans de Goede79b4c062013-10-25 17:04:33 +0100895#define UNUSUAL_DEV(id_vendor, id_product, bcdDeviceMin, bcdDeviceMax, \
896 vendorName, productName, useProtocol, useTransport, \
897 initFunction, flags) \
898{ USB_DEVICE_VER(id_vendor, id_product, bcdDeviceMin, bcdDeviceMax), \
899 .driver_info = (flags) }
900
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200901static struct usb_device_id uas_usb_ids[] = {
Hans de Goede79b4c062013-10-25 17:04:33 +0100902# include "unusual_uas.h"
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200903 { USB_INTERFACE_INFO(USB_CLASS_MASS_STORAGE, USB_SC_SCSI, USB_PR_BULK) },
904 { USB_INTERFACE_INFO(USB_CLASS_MASS_STORAGE, USB_SC_SCSI, USB_PR_UAS) },
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200905 { }
906};
907MODULE_DEVICE_TABLE(usb, uas_usb_ids);
908
Hans de Goede79b4c062013-10-25 17:04:33 +0100909#undef UNUSUAL_DEV
910
Hans de Goedee1be0672013-10-21 08:00:58 +0100911static int uas_switch_interface(struct usb_device *udev,
912 struct usb_interface *intf)
913{
Alan Sternd77606e2017-09-22 11:56:49 -0400914 struct usb_host_interface *alt;
Hans de Goedee1be0672013-10-21 08:00:58 +0100915
916 alt = uas_find_uas_alt_setting(intf);
Alan Sternd77606e2017-09-22 11:56:49 -0400917 if (!alt)
918 return -ENODEV;
Hans de Goedee1be0672013-10-21 08:00:58 +0100919
Alan Sternd77606e2017-09-22 11:56:49 -0400920 return usb_set_interface(udev, alt->desc.bInterfaceNumber,
921 alt->desc.bAlternateSetting);
Hans de Goedee1be0672013-10-21 08:00:58 +0100922}
923
Hans de Goede58d51442013-10-29 10:23:26 +0100924static int uas_configure_endpoints(struct uas_dev_info *devinfo)
Hans de Goede34f11e52013-10-29 08:54:48 +0100925{
926 struct usb_host_endpoint *eps[4] = { };
927 struct usb_device *udev = devinfo->udev;
928 int r;
929
Hans de Goede34f11e52013-10-29 08:54:48 +0100930 r = uas_find_endpoints(devinfo->intf->cur_altsetting, eps);
Hans de Goede74d71ae2013-10-29 10:10:36 +0100931 if (r)
932 return r;
Hans de Goede34f11e52013-10-29 08:54:48 +0100933
Hans de Goede74d71ae2013-10-29 10:10:36 +0100934 devinfo->cmd_pipe = usb_sndbulkpipe(udev,
935 usb_endpoint_num(&eps[0]->desc));
936 devinfo->status_pipe = usb_rcvbulkpipe(udev,
937 usb_endpoint_num(&eps[1]->desc));
938 devinfo->data_in_pipe = usb_rcvbulkpipe(udev,
939 usb_endpoint_num(&eps[2]->desc));
940 devinfo->data_out_pipe = usb_sndbulkpipe(udev,
941 usb_endpoint_num(&eps[3]->desc));
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200942
Hans de Goedee5e55812014-09-13 12:26:43 +0200943 if (udev->speed < USB_SPEED_SUPER) {
Hans de Goedee2875c32014-08-01 17:33:08 +0200944 devinfo->qdepth = 32;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200945 devinfo->use_streams = 0;
946 } else {
Hans de Goede58d51442013-10-29 10:23:26 +0100947 devinfo->qdepth = usb_alloc_streams(devinfo->intf, eps + 1,
Hans de Goede5e61aed2014-09-13 12:26:32 +0200948 3, MAX_CMNDS, GFP_NOIO);
Hans de Goede58d51442013-10-29 10:23:26 +0100949 if (devinfo->qdepth < 0)
950 return devinfo->qdepth;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200951 devinfo->use_streams = 1;
952 }
Hans de Goede58d51442013-10-29 10:23:26 +0100953
954 return 0;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200955}
956
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +0100957static void uas_free_streams(struct uas_dev_info *devinfo)
958{
959 struct usb_device *udev = devinfo->udev;
960 struct usb_host_endpoint *eps[3];
961
962 eps[0] = usb_pipe_endpoint(udev, devinfo->status_pipe);
963 eps[1] = usb_pipe_endpoint(udev, devinfo->data_in_pipe);
964 eps[2] = usb_pipe_endpoint(udev, devinfo->data_out_pipe);
Oliver Neukum94d72f02014-03-28 11:25:50 +0100965 usb_free_streams(devinfo->intf, eps, 3, GFP_NOIO);
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +0100966}
967
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200968static int uas_probe(struct usb_interface *intf, const struct usb_device_id *id)
969{
Hans de Goede6ce82132013-10-17 19:00:45 +0200970 int result = -ENOMEM;
971 struct Scsi_Host *shost = NULL;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200972 struct uas_dev_info *devinfo;
973 struct usb_device *udev = interface_to_usbdev(intf);
Hans de Goedea5011d42015-04-21 11:20:30 +0200974 unsigned long dev_flags;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200975
Hans de Goedea5011d42015-04-21 11:20:30 +0200976 if (!uas_use_uas_driver(intf, id, &dev_flags))
Hans de Goede79b4c062013-10-25 17:04:33 +0100977 return -ENODEV;
978
Matthew Wilcox89dc2902010-12-15 15:44:05 -0500979 if (uas_switch_interface(udev, intf))
980 return -ENODEV;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200981
Hans de Goede21fc05b2013-11-13 09:32:22 +0100982 shost = scsi_host_alloc(&uas_host_template,
983 sizeof(struct uas_dev_info));
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200984 if (!shost)
Hans de Goede6ce82132013-10-17 19:00:45 +0200985 goto set_alt0;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200986
987 shost->max_cmd_len = 16 + 252;
988 shost->max_id = 1;
Gerd Hoffmannbde027b2013-01-25 15:03:36 +0100989 shost->max_lun = 256;
990 shost->max_channel = 0;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200991 shost->sg_tablesize = udev->bus->sg_tablesize;
992
Hans de Goede21fc05b2013-11-13 09:32:22 +0100993 devinfo = (struct uas_dev_info *)shost->hostdata;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +0200994 devinfo->intf = intf;
995 devinfo->udev = udev;
Gerd Hoffmann023b5152012-06-19 09:54:54 +0200996 devinfo->resetting = 0;
Hans de Goededa65c2b2013-11-11 11:51:42 +0100997 devinfo->shutdown = 0;
Hans de Goedea5011d42015-04-21 11:20:30 +0200998 devinfo->flags = dev_flags;
Gerd Hoffmanna0e39e32012-09-25 10:47:04 +0200999 init_usb_anchor(&devinfo->cmd_urbs);
Gerd Hoffmannbdd000f2012-06-19 09:54:53 +02001000 init_usb_anchor(&devinfo->sense_urbs);
1001 init_usb_anchor(&devinfo->data_urbs);
Gerd Hoffmanne0648522012-09-25 10:47:08 +02001002 spin_lock_init(&devinfo->lock);
Gerd Hoffmann1bf81982013-09-13 13:27:12 +02001003 INIT_WORK(&devinfo->work, uas_do_work);
EJ Hsu25399d52020-01-30 01:25:06 -08001004 INIT_WORK(&devinfo->scan_work, uas_scan_work);
Hans de Goede58d51442013-10-29 10:23:26 +01001005
1006 result = uas_configure_endpoints(devinfo);
1007 if (result)
1008 goto set_alt0;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001009
Hans de Goede198de512016-04-12 12:27:08 +02001010 /*
1011 * 1 tag is reserved for untagged commands +
1012 * 1 tag to avoid off by one errors in some bridge firmwares
1013 */
1014 shost->can_queue = devinfo->qdepth - 2;
1015
Oliver Neukumc637f1f2014-03-28 11:29:25 +01001016 usb_set_intfdata(intf, shost);
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +01001017 result = scsi_add_host(shost, &intf->dev);
1018 if (result)
Hans de Goede6ce82132013-10-17 19:00:45 +02001019 goto free_streams;
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +01001020
EJ Hsu25399d52020-01-30 01:25:06 -08001021 /* Submit the delayed_work for SCSI-device scanning */
1022 schedule_work(&devinfo->scan_work);
1023
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001024 return result;
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +01001025
Hans de Goede6ce82132013-10-17 19:00:45 +02001026free_streams:
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +01001027 uas_free_streams(devinfo);
Oliver Neukumc637f1f2014-03-28 11:29:25 +01001028 usb_set_intfdata(intf, NULL);
Hans de Goede6ce82132013-10-17 19:00:45 +02001029set_alt0:
1030 usb_set_interface(udev, intf->altsetting[0].desc.bInterfaceNumber, 0);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001031 if (shost)
1032 scsi_host_put(shost);
1033 return result;
1034}
1035
Hans de Goedef9dc0242014-09-13 12:26:42 +02001036static int uas_cmnd_list_empty(struct uas_dev_info *devinfo)
1037{
1038 unsigned long flags;
1039 int i, r = 1;
1040
1041 spin_lock_irqsave(&devinfo->lock, flags);
1042
1043 for (i = 0; i < devinfo->qdepth; i++) {
1044 if (devinfo->cmnd[i]) {
1045 r = 0; /* Not empty */
1046 break;
1047 }
1048 }
1049
1050 spin_unlock_irqrestore(&devinfo->lock, flags);
1051
1052 return r;
1053}
1054
1055/*
1056 * Wait for any pending cmnds to complete, on usb-2 sense_urbs may temporarily
1057 * get empty while there still is more work to do due to sense-urbs completing
1058 * with a READ/WRITE_READY iu code, so keep waiting until the list gets empty.
1059 */
1060static int uas_wait_for_pending_cmnds(struct uas_dev_info *devinfo)
1061{
1062 unsigned long start_time;
1063 int r;
1064
1065 start_time = jiffies;
1066 do {
1067 flush_work(&devinfo->work);
1068
1069 r = usb_wait_anchor_empty_timeout(&devinfo->sense_urbs, 5000);
1070 if (r == 0)
1071 return -ETIME;
1072
1073 r = usb_wait_anchor_empty_timeout(&devinfo->data_urbs, 500);
1074 if (r == 0)
1075 return -ETIME;
1076
1077 if (time_after(jiffies, start_time + 5 * HZ))
1078 return -ETIME;
1079 } while (!uas_cmnd_list_empty(devinfo));
1080
1081 return 0;
1082}
1083
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001084static int uas_pre_reset(struct usb_interface *intf)
1085{
Hans de Goede4de7a3732013-10-22 16:10:44 +01001086 struct Scsi_Host *shost = usb_get_intfdata(intf);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001087 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goede4de7a3732013-10-22 16:10:44 +01001088 unsigned long flags;
1089
Hans de Goededa65c2b2013-11-11 11:51:42 +01001090 if (devinfo->shutdown)
1091 return 0;
1092
Hans de Goede4de7a3732013-10-22 16:10:44 +01001093 /* Block new requests */
1094 spin_lock_irqsave(shost->host_lock, flags);
1095 scsi_block_requests(shost);
1096 spin_unlock_irqrestore(shost->host_lock, flags);
1097
Hans de Goedef9dc0242014-09-13 12:26:42 +02001098 if (uas_wait_for_pending_cmnds(devinfo) != 0) {
Hans de Goede4de7a3732013-10-22 16:10:44 +01001099 shost_printk(KERN_ERR, shost, "%s: timed out\n", __func__);
Hans de Goedef9dc0242014-09-13 12:26:42 +02001100 scsi_unblock_requests(shost);
Hans de Goede4de7a3732013-10-22 16:10:44 +01001101 return 1;
1102 }
1103
1104 uas_free_streams(devinfo);
1105
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001106 return 0;
1107}
1108
1109static int uas_post_reset(struct usb_interface *intf)
1110{
Hans de Goede4de7a3732013-10-22 16:10:44 +01001111 struct Scsi_Host *shost = usb_get_intfdata(intf);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001112 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goede4de7a3732013-10-22 16:10:44 +01001113 unsigned long flags;
Hans de Goedece39fe62014-09-13 12:26:50 +02001114 int err;
Hans de Goede4de7a3732013-10-22 16:10:44 +01001115
Hans de Goededa65c2b2013-11-11 11:51:42 +01001116 if (devinfo->shutdown)
1117 return 0;
1118
Hans de Goedece39fe62014-09-13 12:26:50 +02001119 err = uas_configure_endpoints(devinfo);
Oliver Neukum438fd542018-03-06 15:04:24 +01001120 if (err && err != -ENODEV)
Hans de Goede58d51442013-10-29 10:23:26 +01001121 shost_printk(KERN_ERR, shost,
Hans de Goedece39fe62014-09-13 12:26:50 +02001122 "%s: alloc streams error %d after reset",
1123 __func__, err);
Hans de Goede4de7a3732013-10-22 16:10:44 +01001124
Oliver Neukum92e64a12018-01-11 13:10:16 +01001125 /* we must unblock the host in every case lest we deadlock */
Hans de Goede4de7a3732013-10-22 16:10:44 +01001126 spin_lock_irqsave(shost->host_lock, flags);
1127 scsi_report_bus_reset(shost, 0);
1128 spin_unlock_irqrestore(shost->host_lock, flags);
1129
1130 scsi_unblock_requests(shost);
1131
Oliver Neukum92e64a12018-01-11 13:10:16 +01001132 return err ? 1 : 0;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001133}
1134
Hans de Goede0df1f662013-11-07 08:47:05 +01001135static int uas_suspend(struct usb_interface *intf, pm_message_t message)
1136{
1137 struct Scsi_Host *shost = usb_get_intfdata(intf);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001138 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goede0df1f662013-11-07 08:47:05 +01001139
Hans de Goedef9dc0242014-09-13 12:26:42 +02001140 if (uas_wait_for_pending_cmnds(devinfo) != 0) {
Hans de Goede0df1f662013-11-07 08:47:05 +01001141 shost_printk(KERN_ERR, shost, "%s: timed out\n", __func__);
1142 return -ETIME;
1143 }
1144
1145 return 0;
1146}
1147
1148static int uas_resume(struct usb_interface *intf)
1149{
1150 return 0;
1151}
1152
1153static int uas_reset_resume(struct usb_interface *intf)
1154{
1155 struct Scsi_Host *shost = usb_get_intfdata(intf);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001156 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goede0df1f662013-11-07 08:47:05 +01001157 unsigned long flags;
Hans de Goedece39fe62014-09-13 12:26:50 +02001158 int err;
Hans de Goede0df1f662013-11-07 08:47:05 +01001159
Hans de Goedece39fe62014-09-13 12:26:50 +02001160 err = uas_configure_endpoints(devinfo);
1161 if (err) {
Hans de Goede0df1f662013-11-07 08:47:05 +01001162 shost_printk(KERN_ERR, shost,
Hans de Goedece39fe62014-09-13 12:26:50 +02001163 "%s: alloc streams error %d after reset",
1164 __func__, err);
Hans de Goede0df1f662013-11-07 08:47:05 +01001165 return -EIO;
1166 }
1167
1168 spin_lock_irqsave(shost->host_lock, flags);
1169 scsi_report_bus_reset(shost, 0);
1170 spin_unlock_irqrestore(shost->host_lock, flags);
1171
1172 return 0;
1173}
1174
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001175static void uas_disconnect(struct usb_interface *intf)
1176{
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001177 struct Scsi_Host *shost = usb_get_intfdata(intf);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001178 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goedeb7b5d112014-09-13 12:26:30 +02001179 unsigned long flags;
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001180
Hans de Goedeb7b5d112014-09-13 12:26:30 +02001181 spin_lock_irqsave(&devinfo->lock, flags);
Gerd Hoffmann4c456972012-11-30 11:54:44 +01001182 devinfo->resetting = 1;
Hans de Goedeb7b5d112014-09-13 12:26:30 +02001183 spin_unlock_irqrestore(&devinfo->lock, flags);
1184
Gerd Hoffmann1bf81982013-09-13 13:27:12 +02001185 cancel_work_sync(&devinfo->work);
Gerd Hoffmanna0e39e32012-09-25 10:47:04 +02001186 usb_kill_anchored_urbs(&devinfo->cmd_urbs);
Gerd Hoffmannbdd000f2012-06-19 09:54:53 +02001187 usb_kill_anchored_urbs(&devinfo->sense_urbs);
1188 usb_kill_anchored_urbs(&devinfo->data_urbs);
Hans de Goede15893492014-09-13 12:26:36 +02001189 uas_zap_pending(devinfo, DID_NO_CONNECT);
1190
EJ Hsu25399d52020-01-30 01:25:06 -08001191 /*
1192 * Prevent SCSI scanning (if it hasn't started yet)
1193 * or wait for the SCSI-scanning routine to stop.
1194 */
1195 cancel_work_sync(&devinfo->scan_work);
1196
Gerd Hoffmann4c456972012-11-30 11:54:44 +01001197 scsi_remove_host(shost);
Sebastian Andrzej Siewiordae51542011-12-19 17:06:08 +01001198 uas_free_streams(devinfo);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001199 scsi_host_put(shost);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001200}
1201
Hans de Goededa65c2b2013-11-11 11:51:42 +01001202/*
1203 * Put the device back in usb-storage mode on shutdown, as some BIOS-es
1204 * hang on reboot when the device is still in uas mode. Note the reset is
1205 * necessary as some devices won't revert to usb-storage mode without it.
1206 */
1207static void uas_shutdown(struct device *dev)
1208{
1209 struct usb_interface *intf = to_usb_interface(dev);
1210 struct usb_device *udev = interface_to_usbdev(intf);
1211 struct Scsi_Host *shost = usb_get_intfdata(intf);
Hans de Goede21fc05b2013-11-13 09:32:22 +01001212 struct uas_dev_info *devinfo = (struct uas_dev_info *)shost->hostdata;
Hans de Goededa65c2b2013-11-11 11:51:42 +01001213
1214 if (system_state != SYSTEM_RESTART)
1215 return;
1216
1217 devinfo->shutdown = 1;
1218 uas_free_streams(devinfo);
1219 usb_set_interface(udev, intf->altsetting[0].desc.bInterfaceNumber, 0);
1220 usb_reset_device(udev);
1221}
1222
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001223static struct usb_driver uas_driver = {
1224 .name = "uas",
1225 .probe = uas_probe,
1226 .disconnect = uas_disconnect,
1227 .pre_reset = uas_pre_reset,
1228 .post_reset = uas_post_reset,
Hans de Goede0df1f662013-11-07 08:47:05 +01001229 .suspend = uas_suspend,
1230 .resume = uas_resume,
1231 .reset_resume = uas_reset_resume,
Hans de Goededa65c2b2013-11-11 11:51:42 +01001232 .drvwrap.driver.shutdown = uas_shutdown,
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001233 .id_table = uas_usb_ids,
1234};
1235
Greg Kroah-Hartman65db4302011-11-18 09:34:02 -08001236module_usb_driver(uas_driver);
Matthew Wilcox115bb1f2010-10-07 13:05:23 +02001237
1238MODULE_LICENSE("GPL");
Hans de Goedef50a4962013-10-28 10:48:04 +00001239MODULE_AUTHOR(
1240 "Hans de Goede <hdegoede@redhat.com>, Matthew Wilcox and Sarah Sharp");