diff options
Diffstat (limited to 'drivers/usb/host/xhci-hcd.c')
-rw-r--r-- | drivers/usb/host/xhci-hcd.c | 125 |
1 files changed, 125 insertions, 0 deletions
diff --git a/drivers/usb/host/xhci-hcd.c b/drivers/usb/host/xhci-hcd.c index 17f1caf2af64..c8573f874ec4 100644 --- a/drivers/usb/host/xhci-hcd.c +++ b/drivers/usb/host/xhci-hcd.c | |||
@@ -1443,6 +1443,131 @@ void xhci_endpoint_reset(struct usb_hcd *hcd, | |||
1443 | } | 1443 | } |
1444 | 1444 | ||
1445 | /* | 1445 | /* |
1446 | * This submits a Reset Device Command, which will set the device state to 0, | ||
1447 | * set the device address to 0, and disable all the endpoints except the default | ||
1448 | * control endpoint. The USB core should come back and call | ||
1449 | * xhci_address_device(), and then re-set up the configuration. If this is | ||
1450 | * called because of a usb_reset_and_verify_device(), then the old alternate | ||
1451 | * settings will be re-installed through the normal bandwidth allocation | ||
1452 | * functions. | ||
1453 | * | ||
1454 | * Wait for the Reset Device command to finish. Remove all structures | ||
1455 | * associated with the endpoints that were disabled. Clear the input device | ||
1456 | * structure? Cache the rings? Reset the control endpoint 0 max packet size? | ||
1457 | */ | ||
1458 | int xhci_reset_device(struct usb_hcd *hcd, struct usb_device *udev) | ||
1459 | { | ||
1460 | int ret, i; | ||
1461 | unsigned long flags; | ||
1462 | struct xhci_hcd *xhci; | ||
1463 | unsigned int slot_id; | ||
1464 | struct xhci_virt_device *virt_dev; | ||
1465 | struct xhci_command *reset_device_cmd; | ||
1466 | int timeleft; | ||
1467 | int last_freed_endpoint; | ||
1468 | |||
1469 | ret = xhci_check_args(hcd, udev, NULL, 0, __func__); | ||
1470 | if (ret <= 0) | ||
1471 | return ret; | ||
1472 | xhci = hcd_to_xhci(hcd); | ||
1473 | slot_id = udev->slot_id; | ||
1474 | virt_dev = xhci->devs[slot_id]; | ||
1475 | if (!virt_dev) { | ||
1476 | xhci_dbg(xhci, "%s called with invalid slot ID %u\n", | ||
1477 | __func__, slot_id); | ||
1478 | return -EINVAL; | ||
1479 | } | ||
1480 | |||
1481 | xhci_dbg(xhci, "Resetting device with slot ID %u\n", slot_id); | ||
1482 | /* Allocate the command structure that holds the struct completion. | ||
1483 | * Assume we're in process context, since the normal device reset | ||
1484 | * process has to wait for the device anyway. Storage devices are | ||
1485 | * reset as part of error handling, so use GFP_NOIO instead of | ||
1486 | * GFP_KERNEL. | ||
1487 | */ | ||
1488 | reset_device_cmd = xhci_alloc_command(xhci, false, true, GFP_NOIO); | ||
1489 | if (!reset_device_cmd) { | ||
1490 | xhci_dbg(xhci, "Couldn't allocate command structure.\n"); | ||
1491 | return -ENOMEM; | ||
1492 | } | ||
1493 | |||
1494 | /* Attempt to submit the Reset Device command to the command ring */ | ||
1495 | spin_lock_irqsave(&xhci->lock, flags); | ||
1496 | reset_device_cmd->command_trb = xhci->cmd_ring->enqueue; | ||
1497 | list_add_tail(&reset_device_cmd->cmd_list, &virt_dev->cmd_list); | ||
1498 | ret = xhci_queue_reset_device(xhci, slot_id); | ||
1499 | if (ret) { | ||
1500 | xhci_dbg(xhci, "FIXME: allocate a command ring segment\n"); | ||
1501 | list_del(&reset_device_cmd->cmd_list); | ||
1502 | spin_unlock_irqrestore(&xhci->lock, flags); | ||
1503 | goto command_cleanup; | ||
1504 | } | ||
1505 | xhci_ring_cmd_db(xhci); | ||
1506 | spin_unlock_irqrestore(&xhci->lock, flags); | ||
1507 | |||
1508 | /* Wait for the Reset Device command to finish */ | ||
1509 | timeleft = wait_for_completion_interruptible_timeout( | ||
1510 | reset_device_cmd->completion, | ||
1511 | USB_CTRL_SET_TIMEOUT); | ||
1512 | if (timeleft <= 0) { | ||
1513 | xhci_warn(xhci, "%s while waiting for reset device command\n", | ||
1514 | timeleft == 0 ? "Timeout" : "Signal"); | ||
1515 | spin_lock_irqsave(&xhci->lock, flags); | ||
1516 | /* The timeout might have raced with the event ring handler, so | ||
1517 | * only delete from the list if the item isn't poisoned. | ||
1518 | */ | ||
1519 | if (reset_device_cmd->cmd_list.next != LIST_POISON1) | ||
1520 | list_del(&reset_device_cmd->cmd_list); | ||
1521 | spin_unlock_irqrestore(&xhci->lock, flags); | ||
1522 | ret = -ETIME; | ||
1523 | goto command_cleanup; | ||
1524 | } | ||
1525 | |||
1526 | /* The Reset Device command can't fail, according to the 0.95/0.96 spec, | ||
1527 | * unless we tried to reset a slot ID that wasn't enabled, | ||
1528 | * or the device wasn't in the addressed or configured state. | ||
1529 | */ | ||
1530 | ret = reset_device_cmd->status; | ||
1531 | switch (ret) { | ||
1532 | case COMP_EBADSLT: /* 0.95 completion code for bad slot ID */ | ||
1533 | case COMP_CTX_STATE: /* 0.96 completion code for same thing */ | ||
1534 | xhci_info(xhci, "Can't reset device (slot ID %u) in %s state\n", | ||
1535 | slot_id, | ||
1536 | xhci_get_slot_state(xhci, virt_dev->out_ctx)); | ||
1537 | xhci_info(xhci, "Not freeing device rings.\n"); | ||
1538 | /* Don't treat this as an error. May change my mind later. */ | ||
1539 | ret = 0; | ||
1540 | goto command_cleanup; | ||
1541 | case COMP_SUCCESS: | ||
1542 | xhci_dbg(xhci, "Successful reset device command.\n"); | ||
1543 | break; | ||
1544 | default: | ||
1545 | if (xhci_is_vendor_info_code(xhci, ret)) | ||
1546 | break; | ||
1547 | xhci_warn(xhci, "Unknown completion code %u for " | ||
1548 | "reset device command.\n", ret); | ||
1549 | ret = -EINVAL; | ||
1550 | goto command_cleanup; | ||
1551 | } | ||
1552 | |||
1553 | /* Everything but endpoint 0 is disabled, so free or cache the rings. */ | ||
1554 | last_freed_endpoint = 1; | ||
1555 | for (i = 1; i < 31; ++i) { | ||
1556 | if (!virt_dev->eps[i].ring) | ||
1557 | continue; | ||
1558 | xhci_free_or_cache_endpoint_ring(xhci, virt_dev, i); | ||
1559 | last_freed_endpoint = i; | ||
1560 | } | ||
1561 | xhci_dbg(xhci, "Output context after successful reset device cmd:\n"); | ||
1562 | xhci_dbg_ctx(xhci, virt_dev->out_ctx, last_freed_endpoint); | ||
1563 | ret = 0; | ||
1564 | |||
1565 | command_cleanup: | ||
1566 | xhci_free_command(xhci, reset_device_cmd); | ||
1567 | return ret; | ||
1568 | } | ||
1569 | |||
1570 | /* | ||
1446 | * At this point, the struct usb_device is about to go away, the device has | 1571 | * At this point, the struct usb_device is about to go away, the device has |
1447 | * disconnected, and all traffic has been stopped and the endpoints have been | 1572 | * disconnected, and all traffic has been stopped and the endpoints have been |
1448 | * disabled. Free any HC data structures associated with that device. | 1573 | * disabled. Free any HC data structures associated with that device. |