summaryrefslogtreecommitdiff
path: root/drivers/usb
diff options
context:
space:
mode:
authorVincent Palatin <vpalatin@chromium.org>2011-07-05 13:11:43 -0700
committerSimon Glass <sjg@chromium.org>2011-08-29 10:58:47 -0700
commit1320caf923d0a317813c71f650eca986c432ea76 (patch)
tree0885fbd78760db185ccda4a20025d01075399f5a /drivers/usb
parent54c7138bf288784a7e3cf051db05a232c5d2c3f3 (diff)
ehci: generic PCI support
Instead of hardcoding the PCI IDs on the USB controller, use the PCI class to detect them. Ensure the busmaster bit is properly set in the PCI configuration. BUG=chrome-os-partner:3914 TEST=Boot a Chromeos image from a USB key on Alex : "usb start ; fatload usb 1:c 3000000 syslinux/vmlinuz.a ; zboot 3000000" and launch a TFTP transfer using a USB-ethernet dongle. Change-Id: Id74bf23ce95a76d4d2c3be506d713bbef9734bd3 Reviewed-on: http://gerrit.chromium.org/gerrit/3657 Tested-by: Vincent Palatin <vpalatin@chromium.org> Reviewed-by: Stefan Reinauer <reinauer@google.com>
Diffstat (limited to 'drivers/usb')
-rw-r--r--drivers/usb/host/ehci-pci.c40
1 files changed, 40 insertions, 0 deletions
diff --git a/drivers/usb/host/ehci-pci.c b/drivers/usb/host/ehci-pci.c
index 020ab11355e..77361ea563b 100644
--- a/drivers/usb/host/ehci-pci.c
+++ b/drivers/usb/host/ehci-pci.c
@@ -33,6 +33,37 @@ static struct pci_device_id ehci_pci_ids[] = {
{0x12D8, 0x400F}, /* Pericom */
{0, 0}
};
+#else
+static pci_dev_t ehci_find_class(void)
+{
+ int bus;
+ int devnum;
+ pci_dev_t bdf;
+ uint32_t class;
+
+ for (bus = 0; bus < pci_last_busno(); bus++)
+ {
+ for (devnum = 0; devnum < PCI_MAX_PCI_DEVICES-1; devnum++)
+ {
+
+ pci_read_config_dword(PCI_BDF(bus, devnum, 0),
+ PCI_CLASS_REVISION, &class);
+ if (class >> 16 == 0xffff)
+ continue;
+
+ for (bdf = PCI_BDF(bus, devnum, 0);
+ bdf <= PCI_BDF(bus, devnum, PCI_MAX_PCI_FUNCTIONS-1);
+ bdf += PCI_BDF(0, 0, 1))
+ {
+ pci_read_config_dword(bdf, PCI_CLASS_REVISION,
+ &class);
+ if (class >> 8 == 0x0c0320)
+ return bdf;
+ }
+ }
+ }
+ return -1;
+}
#endif
/*
@@ -42,8 +73,13 @@ static struct pci_device_id ehci_pci_ids[] = {
int ehci_hcd_init(void)
{
pci_dev_t pdev;
+ uint32_t cmd;
+#ifdef CONFIG_PCI_EHCI_DEVICE
pdev = pci_find_devices(ehci_pci_ids, CONFIG_PCI_EHCI_DEVICE);
+#else
+ pdev = ehci_find_class();
+#endif
if (pdev == -1) {
printf("EHCI host controller not found\n");
return -1;
@@ -58,6 +94,10 @@ int ehci_hcd_init(void)
(uint32_t)hccr, (uint32_t)hcor,
(uint32_t)HC_LENGTH(ehci_readl(&hccr->cr_capbase)));
+ /* enable busmaster */
+ pci_read_config_dword(pdev, PCI_COMMAND, &cmd);
+ cmd |= PCI_COMMAND_MASTER;
+ pci_write_config_dword(pdev, PCI_COMMAND, cmd);
return 0;
}