diff options
-rw-r--r-- | drivers/usb/dwc2/Kconfig | 7 | ||||
-rw-r--r-- | drivers/usb/dwc2/pci.c | 159 |
2 files changed, 76 insertions, 90 deletions
diff --git a/drivers/usb/dwc2/Kconfig b/drivers/usb/dwc2/Kconfig index 76b9ba4dc925..3db204f21ff9 100644 --- a/drivers/usb/dwc2/Kconfig +++ b/drivers/usb/dwc2/Kconfig | |||
@@ -59,11 +59,12 @@ config USB_DWC2_PLATFORM | |||
59 | 59 | ||
60 | config USB_DWC2_PCI | 60 | config USB_DWC2_PCI |
61 | tristate "DWC2 PCI" | 61 | tristate "DWC2 PCI" |
62 | depends on USB_DWC2_HOST && PCI | 62 | depends on PCI |
63 | default USB_DWC2_HOST | 63 | default n |
64 | select USB_DWC2_PLATFORM | ||
64 | help | 65 | help |
65 | The Designware USB2.0 PCI interface module for controllers | 66 | The Designware USB2.0 PCI interface module for controllers |
66 | connected to a PCI bus. This is only used for host mode. | 67 | connected to a PCI bus. |
67 | 68 | ||
68 | config USB_DWC2_DEBUG | 69 | config USB_DWC2_DEBUG |
69 | bool "Enable Debugging Messages" | 70 | bool "Enable Debugging Messages" |
diff --git a/drivers/usb/dwc2/pci.c b/drivers/usb/dwc2/pci.c index 6646adb1fb17..ae419615a176 100644 --- a/drivers/usb/dwc2/pci.c +++ b/drivers/usb/dwc2/pci.c | |||
@@ -50,112 +50,97 @@ | |||
50 | 50 | ||
51 | #include <linux/usb/hcd.h> | 51 | #include <linux/usb/hcd.h> |
52 | #include <linux/usb/ch11.h> | 52 | #include <linux/usb/ch11.h> |
53 | 53 | #include <linux/platform_device.h> | |
54 | #include "core.h" | 54 | #include <linux/usb/usb_phy_generic.h> |
55 | #include "hcd.h" | ||
56 | 55 | ||
57 | #define PCI_PRODUCT_ID_HAPS_HSOTG 0xabc0 | 56 | #define PCI_PRODUCT_ID_HAPS_HSOTG 0xabc0 |
58 | 57 | ||
59 | static const char dwc2_driver_name[] = "dwc2"; | 58 | static const char dwc2_driver_name[] = "dwc2-pci"; |
60 | 59 | ||
61 | static const struct dwc2_core_params dwc2_module_params = { | 60 | struct dwc2_pci_glue { |
62 | .otg_cap = -1, | 61 | struct platform_device *dwc2; |
63 | .otg_ver = -1, | 62 | struct platform_device *phy; |
64 | .dma_enable = -1, | ||
65 | .dma_desc_enable = 0, | ||
66 | .speed = -1, | ||
67 | .enable_dynamic_fifo = -1, | ||
68 | .en_multiple_tx_fifo = -1, | ||
69 | .host_rx_fifo_size = 1024, | ||
70 | .host_nperio_tx_fifo_size = 256, | ||
71 | .host_perio_tx_fifo_size = 1024, | ||
72 | .max_transfer_size = 65535, | ||
73 | .max_packet_count = 511, | ||
74 | .host_channels = -1, | ||
75 | .phy_type = -1, | ||
76 | .phy_utmi_width = -1, | ||
77 | .phy_ulpi_ddr = -1, | ||
78 | .phy_ulpi_ext_vbus = -1, | ||
79 | .i2c_enable = -1, | ||
80 | .ulpi_fs_ls = -1, | ||
81 | .host_support_fs_ls_low_power = -1, | ||
82 | .host_ls_low_power_phy_clk = -1, | ||
83 | .ts_dline = -1, | ||
84 | .reload_ctl = -1, | ||
85 | .ahbcfg = -1, | ||
86 | .uframe_sched = -1, | ||
87 | }; | 63 | }; |
88 | 64 | ||
89 | /** | 65 | static void dwc2_pci_remove(struct pci_dev *pci) |
90 | * dwc2_driver_remove() - Called when the DWC_otg core is unregistered with the | ||
91 | * DWC_otg driver | ||
92 | * | ||
93 | * @dev: Bus device | ||
94 | * | ||
95 | * This routine is called, for example, when the rmmod command is executed. The | ||
96 | * device may or may not be electrically present. If it is present, the driver | ||
97 | * stops device processing. Any resources used on behalf of this device are | ||
98 | * freed. | ||
99 | */ | ||
100 | static void dwc2_driver_remove(struct pci_dev *dev) | ||
101 | { | 66 | { |
102 | struct dwc2_hsotg *hsotg = pci_get_drvdata(dev); | 67 | struct dwc2_pci_glue *glue = pci_get_drvdata(pci); |
103 | 68 | ||
104 | dwc2_hcd_remove(hsotg); | 69 | platform_device_unregister(glue->dwc2); |
105 | pci_disable_device(dev); | 70 | usb_phy_generic_unregister(glue->phy); |
71 | kfree(glue); | ||
72 | pci_set_drvdata(pci, NULL); | ||
106 | } | 73 | } |
107 | 74 | ||
108 | /** | 75 | static int dwc2_pci_probe(struct pci_dev *pci, |
109 | * dwc2_driver_probe() - Called when the DWC_otg core is bound to the DWC_otg | 76 | const struct pci_device_id *id) |
110 | * driver | ||
111 | * | ||
112 | * @dev: Bus device | ||
113 | * | ||
114 | * This routine creates the driver components required to control the device | ||
115 | * (core, HCD, and PCD) and initializes the device. The driver components are | ||
116 | * stored in a dwc2_hsotg structure. A reference to the dwc2_hsotg is saved | ||
117 | * in the device private data. This allows the driver to access the dwc2_hsotg | ||
118 | * structure on subsequent calls to driver methods for this device. | ||
119 | */ | ||
120 | static int dwc2_driver_probe(struct pci_dev *dev, | ||
121 | const struct pci_device_id *id) | ||
122 | { | 77 | { |
123 | struct dwc2_hsotg *hsotg; | 78 | struct resource res[2]; |
124 | int retval; | 79 | struct platform_device *dwc2; |
80 | struct platform_device *phy; | ||
81 | int ret; | ||
82 | struct device *dev = &pci->dev; | ||
83 | struct dwc2_pci_glue *glue; | ||
84 | |||
85 | ret = pcim_enable_device(pci); | ||
86 | if (ret) { | ||
87 | dev_err(dev, "failed to enable pci device\n"); | ||
88 | return -ENODEV; | ||
89 | } | ||
90 | |||
91 | pci_set_master(pci); | ||
125 | 92 | ||
126 | hsotg = devm_kzalloc(&dev->dev, sizeof(*hsotg), GFP_KERNEL); | 93 | dwc2 = platform_device_alloc("dwc2", PLATFORM_DEVID_AUTO); |
127 | if (!hsotg) | 94 | if (!dwc2) { |
95 | dev_err(dev, "couldn't allocate dwc2 device\n"); | ||
128 | return -ENOMEM; | 96 | return -ENOMEM; |
97 | } | ||
129 | 98 | ||
130 | hsotg->dev = &dev->dev; | 99 | memset(res, 0x00, sizeof(struct resource) * ARRAY_SIZE(res)); |
131 | hsotg->regs = devm_ioremap_resource(&dev->dev, &dev->resource[0]); | ||
132 | if (IS_ERR(hsotg->regs)) | ||
133 | return PTR_ERR(hsotg->regs); | ||
134 | 100 | ||
135 | dev_dbg(&dev->dev, "mapped PA %08lx to VA %p\n", | 101 | res[0].start = pci_resource_start(pci, 0); |
136 | (unsigned long)pci_resource_start(dev, 0), hsotg->regs); | 102 | res[0].end = pci_resource_end(pci, 0); |
103 | res[0].name = "dwc2"; | ||
104 | res[0].flags = IORESOURCE_MEM; | ||
137 | 105 | ||
138 | if (pci_enable_device(dev) < 0) | 106 | res[1].start = pci->irq; |
139 | return -ENODEV; | 107 | res[1].name = "dwc2"; |
108 | res[1].flags = IORESOURCE_IRQ; | ||
140 | 109 | ||
141 | pci_set_master(dev); | 110 | ret = platform_device_add_resources(dwc2, res, ARRAY_SIZE(res)); |
111 | if (ret) { | ||
112 | dev_err(dev, "couldn't add resources to dwc2 device\n"); | ||
113 | return ret; | ||
114 | } | ||
142 | 115 | ||
143 | retval = devm_request_irq(hsotg->dev, dev->irq, | 116 | dwc2->dev.parent = dev; |
144 | dwc2_handle_common_intr, IRQF_SHARED, | ||
145 | dev_name(hsotg->dev), hsotg); | ||
146 | if (retval) | ||
147 | return retval; | ||
148 | 117 | ||
149 | spin_lock_init(&hsotg->lock); | 118 | phy = usb_phy_generic_register(); |
150 | retval = dwc2_hcd_init(hsotg, dev->irq, &dwc2_module_params); | 119 | if (IS_ERR(phy)) { |
151 | if (retval) { | 120 | dev_err(dev, "error registering generic PHY (%ld)\n", |
152 | pci_disable_device(dev); | 121 | PTR_ERR(phy)); |
153 | return retval; | 122 | return PTR_ERR(phy); |
154 | } | 123 | } |
155 | 124 | ||
156 | pci_set_drvdata(dev, hsotg); | 125 | ret = platform_device_add(dwc2); |
126 | if (ret) { | ||
127 | dev_err(dev, "failed to register dwc2 device\n"); | ||
128 | goto err; | ||
129 | } | ||
130 | |||
131 | glue = kzalloc(sizeof(*glue), GFP_KERNEL); | ||
132 | if (!glue) | ||
133 | return -ENOMEM; | ||
134 | |||
135 | glue->phy = phy; | ||
136 | glue->dwc2 = dwc2; | ||
137 | pci_set_drvdata(pci, glue); | ||
157 | 138 | ||
158 | return retval; | 139 | return 0; |
140 | err: | ||
141 | usb_phy_generic_unregister(phy); | ||
142 | platform_device_put(dwc2); | ||
143 | return ret; | ||
159 | } | 144 | } |
160 | 145 | ||
161 | static const struct pci_device_id dwc2_pci_ids[] = { | 146 | static const struct pci_device_id dwc2_pci_ids[] = { |
@@ -173,8 +158,8 @@ MODULE_DEVICE_TABLE(pci, dwc2_pci_ids); | |||
173 | static struct pci_driver dwc2_pci_driver = { | 158 | static struct pci_driver dwc2_pci_driver = { |
174 | .name = dwc2_driver_name, | 159 | .name = dwc2_driver_name, |
175 | .id_table = dwc2_pci_ids, | 160 | .id_table = dwc2_pci_ids, |
176 | .probe = dwc2_driver_probe, | 161 | .probe = dwc2_pci_probe, |
177 | .remove = dwc2_driver_remove, | 162 | .remove = dwc2_pci_remove, |
178 | }; | 163 | }; |
179 | 164 | ||
180 | module_pci_driver(dwc2_pci_driver); | 165 | module_pci_driver(dwc2_pci_driver); |