| .. | .. |
|---|
| 16 | 16 | #include <linux/export.h> |
|---|
| 17 | 17 | #include <linux/acpi.h> |
|---|
| 18 | 18 | #include <linux/dmi.h> |
|---|
| 19 | +#include <linux/of.h> |
|---|
| 20 | +#include <linux/iopoll.h> |
|---|
| 21 | + |
|---|
| 19 | 22 | #include "pci-quirks.h" |
|---|
| 20 | 23 | #include "xhci-ext-caps.h" |
|---|
| 21 | 24 | |
|---|
| .. | .. |
|---|
| 132 | 135 | struct amd_chipset_type sb_type; |
|---|
| 133 | 136 | int isoc_reqs; |
|---|
| 134 | 137 | int probe_count; |
|---|
| 135 | | - int probe_result; |
|---|
| 138 | + bool need_pll_quirk; |
|---|
| 136 | 139 | } amd_chipset; |
|---|
| 137 | 140 | |
|---|
| 138 | 141 | static DEFINE_SPINLOCK(amd_lock); |
|---|
| .. | .. |
|---|
| 201 | 204 | } |
|---|
| 202 | 205 | EXPORT_SYMBOL_GPL(sb800_prefetch); |
|---|
| 203 | 206 | |
|---|
| 204 | | -int usb_amd_find_chipset_info(void) |
|---|
| 207 | +static void usb_amd_find_chipset_info(void) |
|---|
| 205 | 208 | { |
|---|
| 206 | 209 | unsigned long flags; |
|---|
| 207 | 210 | struct amd_chipset_info info; |
|---|
| 208 | | - int need_pll_quirk = 0; |
|---|
| 211 | + info.need_pll_quirk = false; |
|---|
| 209 | 212 | |
|---|
| 210 | 213 | spin_lock_irqsave(&amd_lock, flags); |
|---|
| 211 | 214 | |
|---|
| .. | .. |
|---|
| 213 | 216 | if (amd_chipset.probe_count > 0) { |
|---|
| 214 | 217 | amd_chipset.probe_count++; |
|---|
| 215 | 218 | spin_unlock_irqrestore(&amd_lock, flags); |
|---|
| 216 | | - return amd_chipset.probe_result; |
|---|
| 219 | + return; |
|---|
| 217 | 220 | } |
|---|
| 218 | 221 | memset(&info, 0, sizeof(info)); |
|---|
| 219 | 222 | spin_unlock_irqrestore(&amd_lock, flags); |
|---|
| .. | .. |
|---|
| 224 | 227 | |
|---|
| 225 | 228 | switch (info.sb_type.gen) { |
|---|
| 226 | 229 | case AMD_CHIPSET_SB700: |
|---|
| 227 | | - need_pll_quirk = info.sb_type.rev <= 0x3B; |
|---|
| 230 | + info.need_pll_quirk = info.sb_type.rev <= 0x3B; |
|---|
| 228 | 231 | break; |
|---|
| 229 | 232 | case AMD_CHIPSET_SB800: |
|---|
| 230 | 233 | case AMD_CHIPSET_HUDSON2: |
|---|
| 231 | 234 | case AMD_CHIPSET_BOLTON: |
|---|
| 232 | | - need_pll_quirk = 1; |
|---|
| 235 | + info.need_pll_quirk = true; |
|---|
| 233 | 236 | break; |
|---|
| 234 | 237 | default: |
|---|
| 235 | | - need_pll_quirk = 0; |
|---|
| 238 | + info.need_pll_quirk = false; |
|---|
| 236 | 239 | break; |
|---|
| 237 | 240 | } |
|---|
| 238 | 241 | |
|---|
| 239 | | - if (!need_pll_quirk) { |
|---|
| 242 | + if (!info.need_pll_quirk) { |
|---|
| 240 | 243 | if (info.smbus_dev) { |
|---|
| 241 | 244 | pci_dev_put(info.smbus_dev); |
|---|
| 242 | 245 | info.smbus_dev = NULL; |
|---|
| .. | .. |
|---|
| 259 | 262 | } |
|---|
| 260 | 263 | } |
|---|
| 261 | 264 | |
|---|
| 262 | | - need_pll_quirk = info.probe_result = 1; |
|---|
| 263 | 265 | printk(KERN_DEBUG "QUIRK: Enable AMD PLL fix\n"); |
|---|
| 264 | 266 | |
|---|
| 265 | 267 | commit: |
|---|
| .. | .. |
|---|
| 270 | 272 | |
|---|
| 271 | 273 | /* Mark that we where here */ |
|---|
| 272 | 274 | amd_chipset.probe_count++; |
|---|
| 273 | | - need_pll_quirk = amd_chipset.probe_result; |
|---|
| 274 | 275 | |
|---|
| 275 | 276 | spin_unlock_irqrestore(&amd_lock, flags); |
|---|
| 276 | 277 | |
|---|
| .. | .. |
|---|
| 283 | 284 | amd_chipset = info; |
|---|
| 284 | 285 | spin_unlock_irqrestore(&amd_lock, flags); |
|---|
| 285 | 286 | } |
|---|
| 286 | | - |
|---|
| 287 | | - return need_pll_quirk; |
|---|
| 288 | 287 | } |
|---|
| 289 | | -EXPORT_SYMBOL_GPL(usb_amd_find_chipset_info); |
|---|
| 290 | 288 | |
|---|
| 291 | 289 | int usb_hcd_amd_remote_wakeup_quirk(struct pci_dev *pdev) |
|---|
| 292 | 290 | { |
|---|
| .. | .. |
|---|
| 321 | 319 | return amd_chipset.sb_type.gen == AMD_CHIPSET_SB800; |
|---|
| 322 | 320 | } |
|---|
| 323 | 321 | EXPORT_SYMBOL_GPL(usb_amd_prefetch_quirk); |
|---|
| 322 | + |
|---|
| 323 | +bool usb_amd_quirk_pll_check(void) |
|---|
| 324 | +{ |
|---|
| 325 | + usb_amd_find_chipset_info(); |
|---|
| 326 | + return amd_chipset.need_pll_quirk; |
|---|
| 327 | +} |
|---|
| 328 | +EXPORT_SYMBOL_GPL(usb_amd_quirk_pll_check); |
|---|
| 324 | 329 | |
|---|
| 325 | 330 | /* |
|---|
| 326 | 331 | * The hardware normally enables the A-link power management feature, which |
|---|
| .. | .. |
|---|
| 527 | 532 | amd_chipset.nb_type = 0; |
|---|
| 528 | 533 | memset(&amd_chipset.sb_type, 0, sizeof(amd_chipset.sb_type)); |
|---|
| 529 | 534 | amd_chipset.isoc_reqs = 0; |
|---|
| 530 | | - amd_chipset.probe_result = 0; |
|---|
| 535 | + amd_chipset.need_pll_quirk = false; |
|---|
| 531 | 536 | |
|---|
| 532 | 537 | spin_unlock_irqrestore(&amd_lock, flags); |
|---|
| 533 | 538 | |
|---|
| .. | .. |
|---|
| 726 | 731 | if (!pio_enabled(pdev)) |
|---|
| 727 | 732 | return; |
|---|
| 728 | 733 | |
|---|
| 729 | | - for (i = 0; i < PCI_ROM_RESOURCE; i++) |
|---|
| 734 | + for (i = 0; i < PCI_STD_NUM_BARS; i++) |
|---|
| 730 | 735 | if ((pci_resource_flags(pdev, i) & IORESOURCE_IO)) { |
|---|
| 731 | 736 | base = pci_resource_start(pdev, i); |
|---|
| 732 | 737 | break; |
|---|
| .. | .. |
|---|
| 790 | 795 | /* disable interrupts */ |
|---|
| 791 | 796 | writel((u32) ~0, base + OHCI_INTRDISABLE); |
|---|
| 792 | 797 | |
|---|
| 793 | | - /* Reset the USB bus, if the controller isn't already in RESET */ |
|---|
| 794 | | - if (control & OHCI_HCFS) { |
|---|
| 795 | | - /* Go into RESET, preserving RWC (and possibly IR) */ |
|---|
| 796 | | - writel(control & OHCI_CTRL_MASK, base + OHCI_CONTROL); |
|---|
| 797 | | - readl(base + OHCI_CONTROL); |
|---|
| 798 | | - |
|---|
| 799 | | - /* drive bus reset for at least 50 ms (7.1.7.5) */ |
|---|
| 800 | | - msleep(50); |
|---|
| 801 | | - } |
|---|
| 798 | + /* Go into the USB_RESET state, preserving RWC (and possibly IR) */ |
|---|
| 799 | + writel(control & OHCI_CTRL_MASK, base + OHCI_CONTROL); |
|---|
| 800 | + readl(base + OHCI_CONTROL); |
|---|
| 802 | 801 | |
|---|
| 803 | 802 | /* software reset of the controller, preserving HcFmInterval */ |
|---|
| 804 | 803 | if (!no_fminterval) |
|---|
| .. | .. |
|---|
| 958 | 957 | ehci_bios_handoff(pdev, op_reg_base, cap, offset); |
|---|
| 959 | 958 | break; |
|---|
| 960 | 959 | case 0: /* Illegal reserved cap, set cap=0 so we exit */ |
|---|
| 961 | | - cap = 0; /* fall through */ |
|---|
| 960 | + cap = 0; |
|---|
| 961 | + fallthrough; |
|---|
| 962 | 962 | default: |
|---|
| 963 | 963 | dev_warn(&pdev->dev, |
|---|
| 964 | 964 | "EHCI: unrecognized capability %02x\n", |
|---|
| .. | .. |
|---|
| 1013 | 1013 | { |
|---|
| 1014 | 1014 | u32 result; |
|---|
| 1015 | 1015 | |
|---|
| 1016 | | - do { |
|---|
| 1017 | | - result = readl(ptr); |
|---|
| 1018 | | - result &= mask; |
|---|
| 1019 | | - if (result == done) |
|---|
| 1020 | | - return 0; |
|---|
| 1021 | | - udelay(delay_usec); |
|---|
| 1022 | | - wait_usec -= delay_usec; |
|---|
| 1023 | | - } while (wait_usec > 0); |
|---|
| 1024 | | - return -ETIMEDOUT; |
|---|
| 1016 | + return readl_poll_timeout_atomic(ptr, result, |
|---|
| 1017 | + ((result & mask) == done), |
|---|
| 1018 | + delay_usec, wait_usec); |
|---|
| 1025 | 1019 | } |
|---|
| 1026 | 1020 | |
|---|
| 1027 | 1021 | /* |
|---|
| .. | .. |
|---|
| 1134 | 1128 | } |
|---|
| 1135 | 1129 | EXPORT_SYMBOL_GPL(usb_disable_xhci_ports); |
|---|
| 1136 | 1130 | |
|---|
| 1137 | | -/** |
|---|
| 1131 | +/* |
|---|
| 1138 | 1132 | * PCI Quirks for xHCI. |
|---|
| 1139 | 1133 | * |
|---|
| 1140 | 1134 | * Takes care of the handoff between the Pre-OS (i.e. BIOS) and the OS. |
|---|
| .. | .. |
|---|
| 1154 | 1148 | if (!mmio_resource_enabled(pdev, 0)) |
|---|
| 1155 | 1149 | return; |
|---|
| 1156 | 1150 | |
|---|
| 1157 | | - base = ioremap_nocache(pci_resource_start(pdev, 0), len); |
|---|
| 1151 | + base = ioremap(pci_resource_start(pdev, 0), len); |
|---|
| 1158 | 1152 | if (base == NULL) |
|---|
| 1159 | 1153 | return; |
|---|
| 1160 | 1154 | |
|---|
| .. | .. |
|---|
| 1247 | 1241 | |
|---|
| 1248 | 1242 | static void quirk_usb_early_handoff(struct pci_dev *pdev) |
|---|
| 1249 | 1243 | { |
|---|
| 1244 | + struct device_node *parent; |
|---|
| 1245 | + bool is_rpi; |
|---|
| 1246 | + |
|---|
| 1250 | 1247 | /* Skip Netlogic mips SoC's internal PCI USB controller. |
|---|
| 1251 | 1248 | * This device does not need/support EHCI/OHCI handoff |
|---|
| 1252 | 1249 | */ |
|---|
| 1253 | 1250 | if (pdev->vendor == 0x184e) /* vendor Netlogic */ |
|---|
| 1254 | 1251 | return; |
|---|
| 1252 | + |
|---|
| 1253 | + /* |
|---|
| 1254 | + * Bypass the Raspberry Pi 4 controller xHCI controller, things are |
|---|
| 1255 | + * taken care of by the board's co-processor. |
|---|
| 1256 | + */ |
|---|
| 1257 | + if (pdev->vendor == PCI_VENDOR_ID_VIA && pdev->device == 0x3483) { |
|---|
| 1258 | + parent = of_get_parent(pdev->bus->dev.of_node); |
|---|
| 1259 | + is_rpi = of_device_is_compatible(parent, "brcm,bcm2711-pcie"); |
|---|
| 1260 | + of_node_put(parent); |
|---|
| 1261 | + if (is_rpi) |
|---|
| 1262 | + return; |
|---|
| 1263 | + } |
|---|
| 1264 | + |
|---|
| 1255 | 1265 | if (pdev->class != PCI_CLASS_SERIAL_USB_UHCI && |
|---|
| 1256 | 1266 | pdev->class != PCI_CLASS_SERIAL_USB_OHCI && |
|---|
| 1257 | 1267 | pdev->class != PCI_CLASS_SERIAL_USB_EHCI && |
|---|