diff options
author | Sarah Sharp <sarah.a.sharp@linux.intel.com> | 2009-04-27 19:53:42 -0700 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2009-06-15 21:44:48 -0700 |
commit | a74588f94655263b96dacbbf14aac0958d8b7409 (patch) | |
tree | 0c4a53d0e6aa00fe9226c9c915f22da9171043ad /drivers/usb/host/xhci-mem.c | |
parent | 0ebbab37422315a5d0cb29792271085bafdf38c0 (diff) | |
download | blackbird-op-linux-a74588f94655263b96dacbbf14aac0958d8b7409.tar.gz blackbird-op-linux-a74588f94655263b96dacbbf14aac0958d8b7409.zip |
USB: xhci: Device context array allocation.
Instead of keeping a "frame list" like older host controllers, the xHCI
host controller keeps internal representations of the USB devices, with a
transfer ring per endpoint. The host controller queues Transfer Request
Blocks (TRBs) to the endpoint ring, and then "rings the doorbell" for that
device. The host controller processes the transfer, places a transfer
completion event on the event ring, and interrupts the system.
The device context base address array must be allocated by the xHCI host
controller driver, along with the device contexts it points to.
Signed-off-by: Sarah Sharp <sarah.a.sharp@linux.intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/usb/host/xhci-mem.c')
-rw-r--r-- | drivers/usb/host/xhci-mem.c | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/drivers/usb/host/xhci-mem.c b/drivers/usb/host/xhci-mem.c index 7cf15ca854be..be5a05b2021c 100644 --- a/drivers/usb/host/xhci-mem.c +++ b/drivers/usb/host/xhci-mem.c @@ -220,6 +220,12 @@ void xhci_mem_cleanup(struct xhci_hcd *xhci) dma_pool_destroy(xhci->segment_pool); xhci->segment_pool = NULL; xhci_dbg(xhci, "Freed segment pool\n"); + xhci_writel(xhci, 0, &xhci->op_regs->dcbaa_ptr[1]); + xhci_writel(xhci, 0, &xhci->op_regs->dcbaa_ptr[0]); + if (xhci->dcbaa) + pci_free_consistent(pdev, sizeof(*xhci->dcbaa), + xhci->dcbaa, xhci->dcbaa->dma); + xhci->dcbaa = NULL; xhci->page_size = 0; xhci->page_shift = 0; } @@ -263,6 +269,21 @@ int xhci_mem_init(struct xhci_hcd *xhci, gfp_t flags) xhci_writel(xhci, val, &xhci->op_regs->config_reg); /* + * Section 5.4.8 - doorbell array must be + * "physically contiguous and 64-byte (cache line) aligned". + */ + xhci->dcbaa = pci_alloc_consistent(to_pci_dev(dev), + sizeof(*xhci->dcbaa), &dma); + if (!xhci->dcbaa) + goto fail; + memset(xhci->dcbaa, 0, sizeof *(xhci->dcbaa)); + xhci->dcbaa->dma = dma; + xhci_dbg(xhci, "// Setting device context base array address to 0x%x\n", + xhci->dcbaa->dma); + xhci_writel(xhci, (u32) 0, &xhci->op_regs->dcbaa_ptr[1]); + xhci_writel(xhci, dma, &xhci->op_regs->dcbaa_ptr[0]); + + /* * Initialize the ring segment pool. The ring must be a contiguous * structure comprised of TRBs. The TRBs must be 16 byte aligned, * however, the command ring segment needs 64-byte aligned segments, |