1 /*- 2 * Copyright (c) 2007-2008, Juniper Networks, Inc. 3 * All rights reserved. 4 * 5 * SPDX-License-Identifier: GPL-2.0 6 */ 7 8 #include <common.h> 9 #include <dm.h> 10 #include <errno.h> 11 #include <pci.h> 12 #include <usb.h> 13 14 #include "ehci.h" 15 16 /* Information about a USB port */ 17 struct ehci_pci_priv { 18 struct ehci_ctrl ehci; 19 }; 20 21 static void ehci_pci_common_init(pci_dev_t pdev, struct ehci_hccr **ret_hccr, 22 struct ehci_hcor **ret_hcor) 23 { 24 struct ehci_hccr *hccr; 25 struct ehci_hcor *hcor; 26 uint32_t cmd; 27 28 hccr = (struct ehci_hccr *)pci_map_bar(pdev, 29 PCI_BASE_ADDRESS_0, PCI_REGION_MEM); 30 hcor = (struct ehci_hcor *)((uint32_t) hccr + 31 HC_LENGTH(ehci_readl(&hccr->cr_capbase))); 32 33 debug("EHCI-PCI init hccr 0x%x and hcor 0x%x hc_length %d\n", 34 (uint32_t)hccr, (uint32_t)hcor, 35 (uint32_t)HC_LENGTH(ehci_readl(&hccr->cr_capbase))); 36 37 *ret_hccr = hccr; 38 *ret_hcor = hcor; 39 40 /* enable busmaster */ 41 pci_read_config_dword(pdev, PCI_COMMAND, &cmd); 42 cmd |= PCI_COMMAND_MASTER; 43 pci_write_config_dword(pdev, PCI_COMMAND, cmd); 44 } 45 46 #ifndef CONFIG_DM_USB 47 48 #ifdef CONFIG_PCI_EHCI_DEVICE 49 static struct pci_device_id ehci_pci_ids[] = { 50 /* Please add supported PCI EHCI controller ids here */ 51 {0x1033, 0x00E0}, /* NEC */ 52 {0x10B9, 0x5239}, /* ULI1575 PCI EHCI module ids */ 53 {0x12D8, 0x400F}, /* Pericom */ 54 {0, 0} 55 }; 56 #endif 57 58 /* 59 * Create the appropriate control structures to manage 60 * a new EHCI host controller. 61 */ 62 int ehci_hcd_init(int index, enum usb_init_type init, 63 struct ehci_hccr **ret_hccr, struct ehci_hcor **ret_hcor) 64 { 65 pci_dev_t pdev; 66 67 #ifdef CONFIG_PCI_EHCI_DEVICE 68 pdev = pci_find_devices(ehci_pci_ids, CONFIG_PCI_EHCI_DEVICE); 69 #else 70 pdev = pci_find_class(PCI_CLASS_SERIAL_USB_EHCI, index); 71 #endif 72 if (pdev < 0) { 73 printf("EHCI host controller not found\n"); 74 return -1; 75 } 76 ehci_pci_common_init(pdev, ret_hccr, ret_hcor); 77 78 return 0; 79 } 80 81 /* 82 * Destroy the appropriate control structures corresponding 83 * the the EHCI host controller. 84 */ 85 int ehci_hcd_stop(int index) 86 { 87 return 0; 88 } 89 #endif /* nCONFIG_DM_USB */ 90 91 #ifdef CONFIG_DM_USB 92 static int ehci_pci_probe(struct udevice *dev) 93 { 94 struct ehci_hccr *hccr; 95 struct ehci_hcor *hcor; 96 97 ehci_pci_common_init(pci_get_bdf(dev), &hccr, &hcor); 98 99 return ehci_register(dev, hccr, hcor, NULL, 0, USB_INIT_HOST); 100 } 101 102 static int ehci_pci_remove(struct udevice *dev) 103 { 104 int ret; 105 106 ret = ehci_deregister(dev); 107 if (ret) 108 return ret; 109 110 return 0; 111 } 112 113 U_BOOT_DRIVER(ehci_pci) = { 114 .name = "ehci_pci", 115 .id = UCLASS_USB, 116 .probe = ehci_pci_probe, 117 .remove = ehci_pci_remove, 118 .ops = &ehci_usb_ops, 119 .platdata_auto_alloc_size = sizeof(struct usb_platdata), 120 .priv_auto_alloc_size = sizeof(struct ehci_pci_priv), 121 .flags = DM_FLAG_ALLOC_PRIV_DMA, 122 }; 123 124 static struct pci_device_id ehci_pci_supported[] = { 125 { PCI_DEVICE_CLASS(PCI_CLASS_SERIAL_USB_EHCI, ~0) }, 126 {}, 127 }; 128 129 U_BOOT_PCI_DEVICE(ehci_pci, ehci_pci_supported); 130 131 #endif /* CONFIG_DM_USB */ 132