aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb/host/xhci-ring.c
diff options
context:
space:
mode:
authorElric Fu <elricfu1@gmail.com>2012-06-27 04:31:12 -0400
committerSarah Sharp <sarah.a.sharp@linux.intel.com>2012-09-13 18:49:28 -0400
commitb92cc66c047ff7cf587b318fe377061a353c120f (patch)
treec4c7e2f695ed5c796b2b7fcb88ddaaa5480f1d59 /drivers/usb/host/xhci-ring.c
parentc181bc5b5d5c79b71203cd10cef97f802fb6f9c1 (diff)
xHCI: add aborting command ring function
Software have to abort command ring and cancel command when a command is failed or hang. Otherwise, the command ring will hang up and can't handle the others. An example of a command that may hang is the Address Device Command, because waiting for a SET_ADDRESS request to be acknowledged by a USB device is outside of the xHC's ability to control. To cancel a command, software will initialize a command descriptor for the cancel command, and add it into a cancel_cmd_list of xhci. Sarah: Fixed missing newline on "Have the command ring been stopped?" debugging statement. This patch should be backported to kernels as old as 3.0, that contain the commit 7ed603ecf8b68ab81f4c83097d3063d43ec73bb8 "xhci: Add an assertion to check for virt_dev=0 bug." That commit papers over a NULL pointer dereference, and this patch fixes the underlying issue that caused the NULL pointer dereference. Signed-off-by: Elric Fu <elricfu1@gmail.com> Signed-off-by: Sarah Sharp <sarah.a.sharp@linux.intel.com> Tested-by: Miroslav Sabljic <miroslav.sabljic@avl.com> Cc: stable@vger.kernel.org
Diffstat (limited to 'drivers/usb/host/xhci-ring.c')
-rw-r--r--drivers/usb/host/xhci-ring.c108
1 files changed, 108 insertions, 0 deletions
diff --git a/drivers/usb/host/xhci-ring.c b/drivers/usb/host/xhci-ring.c
index 75c857ec55b9..0b0e720521f8 100644
--- a/drivers/usb/host/xhci-ring.c
+++ b/drivers/usb/host/xhci-ring.c
@@ -289,6 +289,114 @@ void xhci_ring_cmd_db(struct xhci_hcd *xhci)
289 xhci_readl(xhci, &xhci->dba->doorbell[0]); 289 xhci_readl(xhci, &xhci->dba->doorbell[0]);
290} 290}
291 291
292static int xhci_abort_cmd_ring(struct xhci_hcd *xhci)
293{
294 u64 temp_64;
295 int ret;
296
297 xhci_dbg(xhci, "Abort command ring\n");
298
299 if (!(xhci->cmd_ring_state & CMD_RING_STATE_RUNNING)) {
300 xhci_dbg(xhci, "The command ring isn't running, "
301 "Have the command ring been stopped?\n");
302 return 0;
303 }
304
305 temp_64 = xhci_read_64(xhci, &xhci->op_regs->cmd_ring);
306 if (!(temp_64 & CMD_RING_RUNNING)) {
307 xhci_dbg(xhci, "Command ring had been stopped\n");
308 return 0;
309 }
310 xhci->cmd_ring_state = CMD_RING_STATE_ABORTED;
311 xhci_write_64(xhci, temp_64 | CMD_RING_ABORT,
312 &xhci->op_regs->cmd_ring);
313
314 /* Section 4.6.1.2 of xHCI 1.0 spec says software should
315 * time the completion od all xHCI commands, including
316 * the Command Abort operation. If software doesn't see
317 * CRR negated in a timely manner (e.g. longer than 5
318 * seconds), then it should assume that the there are
319 * larger problems with the xHC and assert HCRST.
320 */
321 ret = handshake(xhci, &xhci->op_regs->cmd_ring,
322 CMD_RING_RUNNING, 0, 5 * 1000 * 1000);
323 if (ret < 0) {
324 xhci_err(xhci, "Stopped the command ring failed, "
325 "maybe the host is dead\n");
326 xhci->xhc_state |= XHCI_STATE_DYING;
327 xhci_quiesce(xhci);
328 xhci_halt(xhci);
329 return -ESHUTDOWN;
330 }
331
332 return 0;
333}
334
335static int xhci_queue_cd(struct xhci_hcd *xhci,
336 struct xhci_command *command,
337 union xhci_trb *cmd_trb)
338{
339 struct xhci_cd *cd;
340 cd = kzalloc(sizeof(struct xhci_cd), GFP_ATOMIC);
341 if (!cd)
342 return -ENOMEM;
343 INIT_LIST_HEAD(&cd->cancel_cmd_list);
344
345 cd->command = command;
346 cd->cmd_trb = cmd_trb;
347 list_add_tail(&cd->cancel_cmd_list, &xhci->cancel_cmd_list);
348
349 return 0;
350}
351
352/*
353 * Cancel the command which has issue.
354 *
355 * Some commands may hang due to waiting for acknowledgement from
356 * usb device. It is outside of the xHC's ability to control and
357 * will cause the command ring is blocked. When it occurs software
358 * should intervene to recover the command ring.
359 * See Section 4.6.1.1 and 4.6.1.2
360 */
361int xhci_cancel_cmd(struct xhci_hcd *xhci, struct xhci_command *command,
362 union xhci_trb *cmd_trb)
363{
364 int retval = 0;
365 unsigned long flags;
366
367 spin_lock_irqsave(&xhci->lock, flags);
368
369 if (xhci->xhc_state & XHCI_STATE_DYING) {
370 xhci_warn(xhci, "Abort the command ring,"
371 " but the xHCI is dead.\n");
372 retval = -ESHUTDOWN;
373 goto fail;
374 }
375
376 /* queue the cmd desriptor to cancel_cmd_list */
377 retval = xhci_queue_cd(xhci, command, cmd_trb);
378 if (retval) {
379 xhci_warn(xhci, "Queuing command descriptor failed.\n");
380 goto fail;
381 }
382
383 /* abort command ring */
384 retval = xhci_abort_cmd_ring(xhci);
385 if (retval) {
386 xhci_err(xhci, "Abort command ring failed\n");
387 if (unlikely(retval == -ESHUTDOWN)) {
388 spin_unlock_irqrestore(&xhci->lock, flags);
389 usb_hc_died(xhci_to_hcd(xhci)->primary_hcd);
390 xhci_dbg(xhci, "xHCI host controller is dead.\n");
391 return retval;
392 }
393 }
394
395fail:
396 spin_unlock_irqrestore(&xhci->lock, flags);
397 return retval;
398}
399
292void xhci_ring_ep_doorbell(struct xhci_hcd *xhci, 400void xhci_ring_ep_doorbell(struct xhci_hcd *xhci,
293 unsigned int slot_id, 401 unsigned int slot_id,
294 unsigned int ep_index, 402 unsigned int ep_index,