Commit 3a378723 authored by Linus Torvalds's avatar Linus Torvalds

Merge tag 'pci-v6.12-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci

Pull pci updates from Bjorn Helgaas:
 "Enumeration:

   - Wait for device readiness after reset by polling Vendor ID and
     looking for Configuration RRS instead of polling the Command
     register and looking for non-error completions, to avoid hardware
     retries done for RRS on non-Vendor ID reads (Bjorn Helgaas)

   - Rename CRS Completion Status to RRS ('Request Retry Status') to
     match PCIe r6.0 spec usage (Bjorn Helgaas)

   - Clear LBMS bit after a manual link retrain so we don't try to
     retrain a link when there's no downstream device anymore (Maciej W.
     Rozycki)

   - Revert to the original link speed after retraining fails instead of
     leaving it restricted to 2.5GT/s, so a future device has a chance
     to use higher speeds (Maciej W. Rozycki)

   - Wait for each level of downstream bus, not just the first, to
     become accessible before restoring devices on that bus (Ilpo
     Järvinen)

   - Add ARCH_PCI_DEV_GROUPS so s390 can add its own attribute_groups
     without having to stomp on the core's pdev->dev.groups (Lukas
     Wunner)

  Driver binding:

   - Export pcim_request_region(), a managed counterpart of
     pci_request_region(), for use by drivers (Philipp Stanner)

   - Export pcim_iomap_region() and deprecate pcim_iomap_regions()
     (Philipp Stanner)

   - Request the PCI BAR used by xboxvideo (Philipp Stanner)

   - Request and map drm/ast BARs with pcim_iomap_region() (Philipp
     Stanner)

  MSI:

   - Add MSI_FLAG_NO_AFFINITY flag for devices that mux MSIs onto a
     single IRQ line and cannot set the affinity of each MSI to a
     specific CPU core (Marek Vasut)

   - Use MSI_FLAG_NO_AFFINITY and remove unnecessary .irq_set_affinity()
     implementations in aardvark, altera, brcmstb, dwc, mediatek-gen3,
     mediatek, mobiveil, plda, rcar, tegra, vmd, xilinx-nwl,
     xilinx-xdma, and xilinx drivers to avoid 'IRQ: set affinity failed'
     warnings (Marek Vasut)

  Power management:

   - Add pwrctl support for ATH11K inside the WCN6855 package (Konrad
     Dybcio)

  PCI device hotplug:

   - Remove unnecessary hpc_ops struct from shpchp (ngn)

   - Check for PCI_POSSIBLE_ERROR(), not 0xffffffff, in cpqphp
     (weiyufeng)

  Virtualization:

   - Mark Creative Labs EMU20k2 INTx masking as broken (Alex Williamson)

   - Add an ACS quirk for Qualcomm SA8775P, which doesn't advertise ACS
     but does provide ACS-like features (Subramanian Ananthanarayanan)

  IOMMU:

   - Add function 0 DMA alias quirk for Glenfly Arise audio function,
     which uses the function 0 Requester ID (WangYuli)

  NPEM:

   - Add Native PCIe Enclosure Management (NPEM) support for sysfs
     control of NVMe RAID storage indicators (ok/fail/locate/
     rebuild/etc) (Mariusz Tkaczyk)

   - Add support for the ACPI _DSM PCIe SSD status LED management, which
     is functionally similar to NPEM but mediated by platform firmware
     (Mariusz Tkaczyk)

  Device trees:

   - Drop minItems and maxItems from ranges in PCI generic host binding
     since host bridges may have several MMIO and I/O port apertures
     (Frank Li)

   - Add kirin, rcar-gen2, uniphier DT binding top-level constraints for
     clocks (Krzysztof Kozlowski)

  Altera PCIe controller driver:

   - Convert altera DT bindings from text to YAML (Matthew Gerlach)

   - Replace TLP_REQ_ID() with macro PCI_DEVID(), which does the same
     thing and is what other drivers use (Jinjie Ruan)

  Broadcom STB PCIe controller driver:

   - Add DT binding maxItems for reset controllers (Jim Quinlan)

   - Use the 'bridge' reset method if described in the DT (Jim Quinlan)

   - Use the 'swinit' reset method if described in the DT (Jim Quinlan)

   - Add 'has_phy' so the existence of a 'rescal' reset controller
     doesn't imply software control of it (Jim Quinlan)

   - Add support for many inbound DMA windows (Jim Quinlan)

   - Rename SoC 'type' to 'soc_base' express the fact that SoCs come in
     families of multiple similar devices (Jim Quinlan)

   - Add Broadcom 7712 DT description and driver support (Jim Quinlan)

   - Sort enums, pcie_offsets[], pcie_cfg_data, .compatible strings for
     maintainability (Bjorn Helgaas)

  Freescale i.MX6 PCIe controller driver:

   - Add imx6q-pcie 'dbi2' and 'atu' reg-names for i.MX8M Endpoints
     (Richard Zhu)

   - Fix a code restructuring error that caused i.MX8MM and i.MX8MP
     Endpoints to fail to establish link (Richard Zhu)

   - Fix i.MX8MP Endpoint occasional failure to trigger MSI by enforcing
     outbound alignment requirement (Richard Zhu)

   - Call phy_power_off() in the .probe() error path (Frank Li)

   - Rename internal names from imx6_* to imx_* since i.MX7/8/9 are also
     supported (Frank Li)

   - Manage Refclk by using SoC-specific callbacks instead of switch
     statements (Frank Li)

   - Manage core reset by using SoC-specific callbacks instead of switch
     statements (Frank Li)

   - Expand comments for erratum ERR010728 workaround (Frank Li)

   - Use generic PHY APIs to configure mode, speed, and submode, which
     is harmless for devices that implement their own internal PHY
     management and don't set the generic imx_pcie->phy (Frank Li)

   - Add i.MX8Q (i.MX8QM, i.MX8QXP, and i.MX8DXL) DT binding and driver
     Root Complex support (Richard Zhu)

  Freescale Layerscape PCIe controller driver:

   - Replace layerscape-pcie DT binding compatible fsl,lx2160a-pcie with
     fsl,lx2160ar2-pcie (Frank Li)

   - Add layerscape-pcie DT binding deprecated 'num-viewport' property
     to address a DT checker warning (Frank Li)

   - Change layerscape-pcie DT binding 'fsl,pcie-scfg' to phandle-array
     (Frank Li)

  Loongson PCIe controller driver:

   - Increase max PCI hosts to 8 for Loongson-3C6000 and newer chipsets
     (Huacai Chen)

  Marvell Aardvark PCIe controller driver:

   - Fix issue with emulating Configuration RRS for two-byte reads of
     Vendor ID; previously it only worked for four-byte reads (Bjorn
     Helgaas)

  MediaTek PCIe Gen3 controller driver:

   - Add per-SoC struct mtk_gen3_pcie_pdata to support multiple SoC
     types (Lorenzo Bianconi)

   - Use reset_bulk APIs to manage PHY reset lines (Lorenzo Bianconi)

   - Add DT and driver support for Airoha EN7581 PCIe controller
     (Lorenzo Bianconi)

  Qualcomm PCIe controller driver:

   - Update qcom,pcie-sc7280 DT binding with eight interrupts (Rayyan
     Ansari)

   - Add back DT 'vddpe-3v3-supply', which was incorrectly removed
     earlier (Johan Hovold)

   - Drop endpoint redundant masking of global IRQ events (Manivannan
     Sadhasivam)

   - Clarify unknown global IRQ message and only log it once to avoid a
     flood (Manivannan Sadhasivam)

   - Add 'linux,pci-domain' property to endpoint DT binding (Manivannan
     Sadhasivam)

   - Assign PCI domain number for endpoint controllers (Manivannan
     Sadhasivam)

   - Add 'qcom_pcie_ep' and the PCI domain number to IRQ names for
     endpoint controller (Manivannan Sadhasivam)

   - Add global SPI interrupt for PCIe link events to DT binding
     (Manivannan Sadhasivam)

   - Add global RC interrupt handler to handle 'Link up' events and
     automatically enumerate hot-added devices (Manivannan Sadhasivam)

   - Avoid mirroring of DBI and iATU register space so it doesn't
     overlap BAR MMIO space (Prudhvi Yarlagadda)

   - Enable controller resources like PHY only after PERST# is
     deasserted to partially avoid the problem that the endpoint SoC
     crashes when accessing things when Refclk is absent (Manivannan
     Sadhasivam)

   - Add 16.0 GT/s equalization and RX lane margining settings (Shashank
     Babu Chinta Venkata)

   - Pass domain number to pci_bus_release_domain_nr() explicitly to
     avoid a NULL pointer dereference (Manivannan Sadhasivam)

  Renesas R-Car PCIe controller driver:

   - Make the read-only const array 'check_addr' static (Colin Ian King)

   - Add R-Car V4M (R8A779H0) PCIe host and endpoint to DT binding
     (Yoshihiro Shimoda)

  TI DRA7xx PCIe controller driver:

   - Request IRQF_ONESHOT for 'dra7xx-pcie-main' IRQ since the primary
     handler is NULL (Siddharth Vadapalli)

   - Handle IRQ request errors during root port and endpoint probe
     (Siddharth Vadapalli)

  TI J721E PCIe driver:

   - Add DT 'ti,syscon-acspcie-proxy-ctrl' and driver support to enable
     the ACSPCIE module to drive Refclk for the Endpoint (Siddharth
     Vadapalli)

   - Extract the cadence link setup from cdns_pcie_host_setup() so link
     setup can be done separately during resume (Thomas Richard)

   - Add T_PERST_CLK_US definition for the mandatory delay between
     Refclk becoming stable and PERST# being deasserted (Thomas Richard)

   - Add j721e suspend and resume support (Théo Lebrun)

  TI Keystone PCIe controller driver:

   - Fix NULL pointer checking when applying MRRS limitation quirk for
     AM65x SR 1.0 Errata #i2037 (Dan Carpenter)

  Xilinx NWL PCIe controller driver:

   - Fix off-by-one error in INTx IRQ handler that caused INTx
     interrupts to be lost or delivered as the wrong interrupt (Sean
     Anderson)

   - Rate-limit misc interrupt messages (Sean Anderson)

   - Turn off the clock on probe failure and device removal (Sean
     Anderson)

   - Add DT binding and driver support for enabling/disabling PHYs (Sean
     Anderson)

   - Add PCIe phy bindings for the ZCU102 (Sean Anderson)

  Xilinx XDMA PCIe controller driver:

   - Add support for Xilinx QDMA Soft IP PCIe Root Port Bridge to DT
     binding and xilinx-dma-pl driver (Thippeswamy Havalige)

  Miscellaneous:

   - Fix buffer overflow in kirin_pcie_parse_port() (Alexandra Diupina)

   - Fix minor kerneldoc issues and typos (Bjorn Helgaas)

   - Use PCI_DEVID() macro in aer_inject() instead of open-coding it
     (Jinjie Ruan)

   - Check pcie_find_root_port() return in x86 fixups to avoid NULL
     pointer dereferences (Samasth Norway Ananda)

   - Make pci_bus_type constant (Kunwu Chan)

   - Remove unused declarations of __pci_pme_wakeup() and
     pci_vpd_release() (Yue Haibing)

   - Remove any leftover .*.cmd files with make clean (zhang jiao)

   - Remove unused BILLION macro (zhang jiao)"

* tag 'pci-v6.12-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci: (132 commits)
  PCI: Fix typos
  dt-bindings: PCI: qcom: Allow 'vddpe-3v3-supply' again
  tools: PCI: Remove unused BILLION macro
  tools: PCI: Remove .*.cmd files with make clean
  PCI: Pass domain number to pci_bus_release_domain_nr() explicitly
  PCI: dra7xx: Fix error handling when IRQ request fails in probe
  PCI: dra7xx: Fix threaded IRQ request for "dra7xx-pcie-main" IRQ
  PCI: qcom: Add RX lane margining settings for 16.0 GT/s
  PCI: qcom: Add equalization settings for 16.0 GT/s
  PCI: dwc: Always cache the maximum link speed value in dw_pcie::max_link_speed
  PCI: dwc: Rename 'dw_pcie::link_gen' to 'dw_pcie::max_link_speed'
  PCI: qcom-ep: Enable controller resources like PHY only after refclk is available
  PCI: Mark Creative Labs EMU20k2 INTx masking as broken
  dt-bindings: PCI: imx6q-pcie: Add reg-name "dbi2" and "atu" for i.MX8M PCIe Endpoint
  dt-bindings: PCI: altera: msi: Convert to YAML
  PCI: imx6: Add i.MX8Q PCIe Root Complex (RC) support
  PCI: Rename CRS Completion Status to RRS
  PCI: aardvark: Correct Configuration RRS checking
  PCI: Wait for device readiness with Configuration RRS
  PCI: brcmstb: Sort enums, pcie_offsets[], pcie_cfg_data, .compatible strings
  ...
parents 18ba6034 81e53c0d
......@@ -500,3 +500,75 @@ Description:
console drivers from the device. Raw users of pci-sysfs
resourceN attributes must be terminated prior to resizing.
Success of the resizing operation is not guaranteed.
What: /sys/bus/pci/devices/.../leds/*:enclosure:*/brightness
What: /sys/class/leds/*:enclosure:*/brightness
Date: August 2024
KernelVersion: 6.12
Description:
LED indications on PCIe storage enclosures which are controlled
through the NPEM interface (Native PCIe Enclosure Management,
PCIe r6.1 sec 6.28) are accessible as led class devices, both
below /sys/class/leds and below NPEM-capable PCI devices.
Although these led class devices could be manipulated manually,
in practice they are typically manipulated automatically by an
application such as ledmon(8).
The name of a led class device is as follows:
<bdf>:enclosure:<indication>
where:
- <bdf> is the domain, bus, device and function number
(e.g. 10000:02:05.0)
- <indication> is a short description of the LED indication
Valid indications per PCIe r6.1 table 6-27 are:
- ok (drive is functioning normally)
- locate (drive is being identified by an admin)
- fail (drive is not functioning properly)
- rebuild (drive is part of an array that is rebuilding)
- pfa (drive is predicted to fail soon)
- hotspare (drive is marked to be used as a replacement)
- ica (drive is part of an array that is degraded)
- ifa (drive is part of an array that is failed)
- idt (drive is not the right type for the connector)
- disabled (drive is disabled, removal is safe)
- specific0 to specific7 (enclosure-specific indications)
Broadly, the indications fall into one of these categories:
- to signify drive state (ok, locate, fail, idt, disabled)
- to signify drive role or state in a software RAID array
(rebuild, pfa, hotspare, ica, ifa)
- to signify any other role or state (specific0 to specific7)
Mandatory indications per PCIe r6.1 sec 7.9.19.2 comprise:
ok, locate, fail, rebuild. All others are optional.
A led class device is only visible if the corresponding
indication is supported by the device.
To manipulate the indications, write 0 (LED_OFF) or 1 (LED_ON)
to the "brightness" file. Note that manipulating an indication
may implicitly manipulate other indications at the vendor's
discretion. E.g. when the user lights up the "ok" indication,
the vendor may choose to automatically turn off the "fail"
indication. The current state of an indication can be
retrieved by reading its "brightness" file.
The PCIe Base Specification allows vendors leeway to choose
different colors or blinking patterns for the indications,
but they typically follow the IBPI standard. E.g. the "locate"
indication is usually presented as one or two LEDs blinking at
4 Hz frequency:
https://en.wikipedia.org/wiki/International_Blinking_Pattern_Interpretation
PCI Firmware Specification r3.3 sec 4.7 defines a DSM interface
to facilitate shared access by operating system and platform
firmware to a device's NPEM registers. The kernel will use
this DSM interface where available, instead of accessing NPEM
registers directly. The DSM interface does not support the
enclosure-specific indications "specific0" to "specific7",
hence the corresponding led class devices are unavailable if
the DSM interface is used.
* Altera PCIe MSI controller
Required properties:
- compatible: should contain "altr,msi-1.0"
- reg: specifies the physical base address of the controller and
the length of the memory mapped region.
- reg-names: must include the following entries:
"csr": CSR registers
"vector_slave": vectors slave port region
- interrupts: specifies the interrupt source of the parent interrupt
controller. The format of the interrupt specifier depends on the
parent interrupt controller.
- num-vectors: number of vectors, range 1 to 32.
- msi-controller: indicates that this is MSI controller node
Example
msi0: msi@0xFF200000 {
compatible = "altr,msi-1.0";
reg = <0xFF200000 0x00000010
0xFF200010 0x00000080>;
reg-names = "csr", "vector_slave";
interrupt-parent = <&hps_0_arm_gic_0>;
interrupts = <0 42 4>;
msi-controller;
num-vectors = <32>;
};
* Altera PCIe controller
Required properties:
- compatible : should contain "altr,pcie-root-port-1.0" or "altr,pcie-root-port-2.0"
- reg: a list of physical base address and length for TXS and CRA.
For "altr,pcie-root-port-2.0", additional HIP base address and length.
- reg-names: must include the following entries:
"Txs": TX slave port region
"Cra": Control register access region
"Hip": Hard IP region (if "altr,pcie-root-port-2.0")
- interrupts: specifies the interrupt source of the parent interrupt
controller. The format of the interrupt specifier depends
on the parent interrupt controller.
- device_type: must be "pci"
- #address-cells: set to <3>
- #size-cells: set to <2>
- #interrupt-cells: set to <1>
- ranges: describes the translation of addresses for root ports and
standard PCI regions.
- interrupt-map-mask and interrupt-map: standard PCI properties to define the
mapping of the PCIe interface to interrupt numbers.
Optional properties:
- msi-parent: Link to the hardware entity that serves as the MSI controller
for this PCIe controller.
- bus-range: PCI bus numbers covered
Example
pcie_0: pcie@c00000000 {
compatible = "altr,pcie-root-port-1.0";
reg = <0xc0000000 0x20000000>,
<0xff220000 0x00004000>;
reg-names = "Txs", "Cra";
interrupt-parent = <&hps_0_arm_gic_0>;
interrupts = <0 40 4>;
interrupt-controller;
#interrupt-cells = <1>;
bus-range = <0x0 0xFF>;
device_type = "pci";
msi-parent = <&msi_to_gic_gen_0>;
#address-cells = <3>;
#size-cells = <2>;
interrupt-map-mask = <0 0 0 7>;
interrupt-map = <0 0 0 1 &pcie_0 1>,
<0 0 0 2 &pcie_0 2>,
<0 0 0 3 &pcie_0 3>,
<0 0 0 4 &pcie_0 4>;
ranges = <0x82000000 0x00000000 0x00000000 0xc0000000 0x00000000 0x10000000
0x82000000 0x00000000 0x10000000 0xd0000000 0x00000000 0x10000000>;
};
# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
# Copyright (C) 2015, 2024, Intel Corporation
%YAML 1.2
---
$id: http://devicetree.org/schemas/altr,msi-controller.yaml#
$schema: http://devicetree.org/meta-schemas/core.yaml#
title: Altera PCIe MSI controller
maintainers:
- Matthew Gerlach <matthew.gerlach@linux.intel.com>
properties:
compatible:
enum:
- altr,msi-1.0
reg:
items:
- description: CSR registers
- description: Vectors slave port region
reg-names:
items:
- const: csr
- const: vector_slave
interrupts:
maxItems: 1
msi-controller: true
num-vectors:
description: number of vectors
$ref: /schemas/types.yaml#/definitions/uint32
minimum: 1
maximum: 32
required:
- compatible
- reg
- reg-names
- interrupts
- msi-controller
- num-vectors
allOf:
- $ref: /schemas/interrupt-controller/msi-controller.yaml#
unevaluatedProperties: false
examples:
- |
#include <dt-bindings/interrupt-controller/arm-gic.h>
#include <dt-bindings/interrupt-controller/irq.h>
msi@ff200000 {
compatible = "altr,msi-1.0";
reg = <0xff200000 0x00000010>,
<0xff200010 0x00000080>;
reg-names = "csr", "vector_slave";
interrupt-parent = <&hps_0_arm_gic_0>;
interrupts = <GIC_SPI 42 IRQ_TYPE_LEVEL_HIGH>;
msi-controller;
num-vectors = <32>;
};
# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
# Copyright (C) 2015, 2019, 2024, Intel Corporation
%YAML 1.2
---
$id: http://devicetree.org/schemas/altr,pcie-root-port.yaml#
$schema: http://devicetree.org/meta-schemas/core.yaml#
title: Altera PCIe Root Port
maintainers:
- Matthew Gerlach <matthew.gerlach@linux.intel.com>
properties:
compatible:
enum:
- altr,pcie-root-port-1.0
- altr,pcie-root-port-2.0
reg:
items:
- description: TX slave port region
- description: Control register access region
- description: Hard IP region
minItems: 2
reg-names:
items:
- const: Txs
- const: Cra
- const: Hip
minItems: 2
interrupts:
maxItems: 1
interrupt-controller: true
interrupt-map-mask:
items:
- const: 0
- const: 0
- const: 0
- const: 7
interrupt-map:
maxItems: 4
"#interrupt-cells":
const: 1
msi-parent: true
required:
- compatible
- reg
- reg-names
- interrupts
- "#interrupt-cells"
- interrupt-controller
- interrupt-map
- interrupt-map-mask
allOf:
- $ref: /schemas/pci/pci-host-bridge.yaml#
- if:
properties:
compatible:
enum:
- altr,pcie-root-port-1.0
then:
properties:
reg:
maxItems: 2
reg-names:
maxItems: 2
else:
properties:
reg:
minItems: 3
reg-names:
minItems: 3
unevaluatedProperties: false
examples:
- |
#include <dt-bindings/interrupt-controller/arm-gic.h>
#include <dt-bindings/interrupt-controller/irq.h>
pcie_0: pcie@c00000000 {
compatible = "altr,pcie-root-port-1.0";
reg = <0xc0000000 0x20000000>,
<0xff220000 0x00004000>;
reg-names = "Txs", "Cra";
interrupt-parent = <&hps_0_arm_gic_0>;
interrupts = <GIC_SPI 40 IRQ_TYPE_LEVEL_HIGH>;
interrupt-controller;
#interrupt-cells = <1>;
bus-range = <0x0 0xff>;
device_type = "pci";
msi-parent = <&msi_to_gic_gen_0>;
#address-cells = <3>;
#size-cells = <2>;
interrupt-map-mask = <0 0 0 7>;
interrupt-map = <0 0 0 1 &pcie_0 0 0 0 1>,
<0 0 0 2 &pcie_0 0 0 0 2>,
<0 0 0 3 &pcie_0 0 0 0 3>,
<0 0 0 4 &pcie_0 0 0 0 4>;
ranges = <0x82000000 0x00000000 0x00000000 0xc0000000 0x00000000 0x10000000>,
<0x82000000 0x00000000 0x10000000 0xd0000000 0x00000000 0x10000000>;
};
......@@ -7,7 +7,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml#
title: Brcmstb PCIe Host Controller
maintainers:
- Nicolas Saenz Julienne <nsaenzjulienne@suse.de>
- Jim Quinlan <james.quinlan@broadcom.com>
properties:
compatible:
......@@ -16,11 +16,12 @@ properties:
- brcm,bcm2711-pcie # The Raspberry Pi 4
- brcm,bcm4908-pcie
- brcm,bcm7211-pcie # Broadcom STB version of RPi4
- brcm,bcm7278-pcie # Broadcom 7278 Arm
- brcm,bcm7216-pcie # Broadcom 7216 Arm
- brcm,bcm7445-pcie # Broadcom 7445 Arm
- brcm,bcm7278-pcie # Broadcom 7278 Arm
- brcm,bcm7425-pcie # Broadcom 7425 MIPs
- brcm,bcm7435-pcie # Broadcom 7435 MIPs
- brcm,bcm7445-pcie # Broadcom 7445 Arm
- brcm,bcm7712-pcie # Broadcom STB sibling of Rpi 5
reg:
maxItems: 1
......@@ -95,6 +96,14 @@ properties:
minItems: 1
maxItems: 3
resets:
minItems: 1
maxItems: 3
reset-names:
minItems: 1
maxItems: 3
required:
- compatible
- reg
......@@ -118,8 +127,7 @@ allOf:
then:
properties:
resets:
items:
- description: reset controller handling the PERST# signal
maxItems: 1
reset-names:
items:
......@@ -136,12 +144,32 @@ allOf:
then:
properties:
resets:
maxItems: 1
reset-names:
items:
- description: phandle pointing to the RESCAL reset controller
- const: rescal
required:
- resets
- reset-names
- if:
properties:
compatible:
contains:
const: brcm,bcm7712-pcie
then:
properties:
resets:
minItems: 3
maxItems: 3
reset-names:
items:
- const: rescal
- const: bridge
- const: swinit
required:
- resets
......
......@@ -65,12 +65,14 @@ allOf:
then:
properties:
reg:
minItems: 2
maxItems: 2
minItems: 4
maxItems: 4
reg-names:
items:
- const: dbi
- const: addr_space
- const: dbi2
- const: atu
- if:
properties:
......@@ -129,8 +131,11 @@ examples:
pcie_ep: pcie-ep@33800000 {
compatible = "fsl,imx8mp-pcie-ep";
reg = <0x33800000 0x000400000>, <0x18000000 0x08000000>;
reg-names = "dbi", "addr_space";
reg = <0x33800000 0x100000>,
<0x18000000 0x8000000>,
<0x33900000 0x100000>,
<0x33b00000 0x100000>;
reg-names = "dbi", "addr_space", "dbi2", "atu";
clocks = <&clk IMX8MP_CLK_HSIO_ROOT>,
<&clk IMX8MP_CLK_HSIO_AXI>,
<&clk IMX8MP_CLK_PCIE_ROOT>;
......
......@@ -30,6 +30,7 @@ properties:
- fsl,imx8mm-pcie
- fsl,imx8mp-pcie
- fsl,imx95-pcie
- fsl,imx8q-pcie
clocks:
minItems: 3
......@@ -184,6 +185,21 @@ allOf:
- const: pcie_bus
- const: pcie_aux
- if:
properties:
compatible:
enum:
- fsl,imx8q-pcie
then:
properties:
clocks:
maxItems: 3
clock-names:
items:
- const: dbi
- const: mstr
- const: slv
unevaluatedProperties: false
examples:
......
......@@ -22,18 +22,20 @@ description:
properties:
compatible:
enum:
- fsl,ls1021a-pcie
- fsl,ls2080a-pcie
- fsl,ls2085a-pcie
- fsl,ls2088a-pcie
- fsl,ls1088a-pcie
- fsl,ls1046a-pcie
- fsl,ls1043a-pcie
- fsl,ls1012a-pcie
- fsl,ls1028a-pcie
- fsl,lx2160a-pcie
oneOf:
- enum:
- fsl,ls1012a-pcie
- fsl,ls1021a-pcie
- fsl,ls1028a-pcie
- fsl,ls1043a-pcie
- fsl,ls1046a-pcie
- fsl,ls1088a-pcie
- fsl,ls2080a-pcie
- fsl,ls2085a-pcie
- fsl,ls2088a-pcie
- items:
- const: fsl,lx2160ar2-pcie
- const: fsl,ls2088a-pcie
reg:
maxItems: 2
......@@ -43,10 +45,15 @@ properties:
- const: config
fsl,pcie-scfg:
$ref: /schemas/types.yaml#/definitions/phandle
$ref: /schemas/types.yaml#/definitions/phandle-array
description: A phandle to the SCFG device node. The second entry is the
physical PCIe controller index starting from '0'. This is used to get
SCFG PEXN registers.
items:
items:
- description: A phandle to the SCFG device node
- description: PCIe controller index starting from '0'
maxItems: 1
big-endian:
$ref: /schemas/types.yaml#/definitions/flag
......@@ -67,6 +74,14 @@ properties:
minItems: 1
maxItems: 2
num-viewport:
$ref: /schemas/types.yaml#/definitions/uint32
deprecated: true
description:
Number of outbound view ports configured in hardware. It's the same as
the number of outbound AT windows.
maximum: 256
required:
- compatible
- reg
......
......@@ -37,7 +37,8 @@ properties:
minItems: 3
maxItems: 4
clocks: true
clocks:
maxItems: 5
clock-names:
items:
......
......@@ -102,8 +102,6 @@ properties:
As described in IEEE Std 1275-1994, but must provide at least a
definition of non-prefetchable memory. One or both of prefetchable Memory
and IO Space may also be provided.
minItems: 1
maxItems: 3
dma-coherent: true
iommu-map: true
......
......@@ -53,6 +53,7 @@ properties:
- mediatek,mt8195-pcie
- const: mediatek,mt8192-pcie
- const: mediatek,mt8192-pcie
- const: airoha,en7581-pcie
reg:
maxItems: 1
......@@ -76,20 +77,20 @@ properties:
resets:
minItems: 1
maxItems: 2
maxItems: 3
reset-names:
minItems: 1
maxItems: 2
maxItems: 3
items:
enum: [ phy, mac ]
enum: [ phy, mac, phy-lane0, phy-lane1, phy-lane2 ]
clocks:
minItems: 4
minItems: 1
maxItems: 6
clock-names:
minItems: 4
minItems: 1
maxItems: 6
assigned-clocks:
......@@ -147,6 +148,9 @@ allOf:
const: mediatek,mt8192-pcie
then:
properties:
clocks:
minItems: 4
clock-names:
items:
- const: pl_250m
......@@ -155,6 +159,15 @@ allOf:
- const: tl_32k
- const: peri_26m
- const: top_133m
resets:
minItems: 1
maxItems: 2
reset-names:
minItems: 1
maxItems: 2
- if:
properties:
compatible:
......@@ -164,6 +177,9 @@ allOf:
- mediatek,mt8195-pcie
then:
properties:
clocks:
minItems: 4
clock-names:
items:
- const: pl_250m
......@@ -172,6 +188,15 @@ allOf:
- const: tl_32k
- const: peri_26m
- const: peri_mem
resets:
minItems: 1
maxItems: 2
reset-names:
minItems: 1
maxItems: 2
- if:
properties:
compatible:
......@@ -180,6 +205,9 @@ allOf:
- mediatek,mt7986-pcie
then:
properties:
clocks:
minItems: 4
clock-names:
items:
- const: pl_250m
......@@ -187,6 +215,36 @@ allOf:
- const: peri_26m
- const: top_133m
resets:
minItems: 1
maxItems: 2
reset-names:
minItems: 1
maxItems: 2
- if:
properties:
compatible:
const: airoha,en7581-pcie
then:
properties:
clocks:
maxItems: 1
clock-names:
items:
- const: sys-ck
resets:
minItems: 3
reset-names:
items:
- const: phy-lane0
- const: phy-lane1
- const: phy-lane2
unevaluatedProperties: false
examples:
......
......@@ -10,7 +10,8 @@ description: |
Common properties for PCI Endpoint Controller Nodes.
maintainers:
- Kishon Vijay Abraham I <kishon@ti.com>
- Kishon Vijay Abraham I <kishon@kernel.org>
- Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
properties:
$nodename:
......@@ -41,6 +42,17 @@ properties:
default: 1
maximum: 16
linux,pci-domain:
description:
If present this property assigns a fixed PCI domain number to a PCI
Endpoint Controller, otherwise an unstable (across boots) unique number
will be assigned. It is required to either not set this property at all
or set it for all PCI endpoint controllers in the system, otherwise
potentially conflicting domain numbers may be assigned to endpoint
controllers. The domain number for each endpoint controller in the system
must be unique.
$ref: /schemas/types.yaml#/definitions/uint32
required:
- compatible
......
......@@ -21,11 +21,11 @@ properties:
interrupts:
minItems: 1
maxItems: 8
maxItems: 9
interrupt-names:
minItems: 1
maxItems: 8
maxItems: 9
iommu-map:
minItems: 1
......@@ -78,6 +78,9 @@ properties:
description: GPIO controlled connection to WAKE# signal
maxItems: 1
vddpe-3v3-supply:
description: PCIe endpoint power supply
required:
- reg
- reg-names
......
......@@ -280,4 +280,5 @@ examples:
phy-names = "pciephy";
max-link-speed = <3>;
num-lanes = <2>;
linux,pci-domain = <0>;
};
......@@ -53,11 +53,19 @@ properties:
- const: aggre1 # Aggre NoC PCIe1 AXI clock
interrupts:
maxItems: 1
minItems: 8
maxItems: 8
interrupt-names:
items:
- const: msi
- const: msi0
- const: msi1
- const: msi2
- const: msi3
- const: msi4
- const: msi5
- const: msi6
- const: msi7
resets:
maxItems: 1
......@@ -66,9 +74,6 @@ properties:
items:
- const: pci
vddpe-3v3-supply:
description: PCIe endpoint power supply
allOf:
- $ref: qcom,pcie-common.yaml#
......@@ -137,8 +142,16 @@ examples:
dma-coherent;
interrupts = <GIC_SPI 307 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "msi";
interrupts = <GIC_SPI 307 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 308 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 309 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 312 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 313 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 314 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 374 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 375 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "msi0", "msi1", "msi2", "msi3",
"msi4", "msi5", "msi6", "msi7";
#interrupt-cells = <1>;
interrupt-map-mask = <0 0 0 0x7>;
interrupt-map = <0 0 0 1 &intc 0 0 0 434 IRQ_TYPE_LEVEL_HIGH>,
......
......@@ -58,9 +58,6 @@ properties:
items:
- const: pci
vddpe-3v3-supply:
description: A phandle to the PCIe endpoint power supply
required:
- interconnects
- interconnect-names
......
......@@ -55,8 +55,8 @@ properties:
- const: aggre1 # Aggre NoC PCIe1 AXI clock
interrupts:
minItems: 8
maxItems: 8
minItems: 9
maxItems: 9
interrupt-names:
items:
......@@ -68,6 +68,7 @@ properties:
- const: msi5
- const: msi6
- const: msi7
- const: global
operating-points-v2: true
opp-table:
......@@ -149,9 +150,10 @@ examples:
<GIC_SPI 145 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 146 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 147 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 148 IRQ_TYPE_LEVEL_HIGH>;
<GIC_SPI 148 IRQ_TYPE_LEVEL_HIGH>,
<GIC_SPI 140 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "msi0", "msi1", "msi2", "msi3",
"msi4", "msi5", "msi6", "msi7";
"msi4", "msi5", "msi6", "msi7", "global";
#interrupt-cells = <1>;
interrupt-map-mask = <0 0 0 0x7>;
interrupt-map = <0 0 0 1 &intc 0 0 0 149 IRQ_TYPE_LEVEL_HIGH>, /* int_a */
......
......@@ -91,6 +91,9 @@ properties:
vdda_refclk-supply:
description: A phandle to the core analog power supply for IC which generates reference clock
vddpe-3v3-supply:
description: A phandle to the PCIe endpoint power supply
phys:
maxItems: 1
......
......@@ -19,6 +19,7 @@ properties:
- enum:
- renesas,r8a779f0-pcie-ep # R-Car S4-8
- renesas,r8a779g0-pcie-ep # R-Car V4H
- renesas,r8a779h0-pcie-ep # R-Car V4M
- const: renesas,rcar-gen4-pcie-ep # R-Car Gen4
reg:
......
......@@ -19,6 +19,7 @@ properties:
- enum:
- renesas,r8a779f0-pcie # R-Car S4-8
- renesas,r8a779g0-pcie # R-Car V4H
- renesas,r8a779h0-pcie # R-Car V4M
- const: renesas,rcar-gen4-pcie # R-Car Gen4
reg:
......
......@@ -42,9 +42,13 @@ properties:
interrupts:
maxItems: 1
clocks: true
clocks:
minItems: 1
maxItems: 3
clock-names: true
clock-names:
minItems: 1
maxItems: 3
resets:
maxItems: 1
......
......@@ -38,13 +38,17 @@ properties:
minItems: 1
maxItems: 2
clock-names: true
clock-names:
minItems: 1
maxItems: 2
resets:
minItems: 1
maxItems: 2
reset-names: true
reset-names:
minItems: 1
maxItems: 2
num-ib-windows:
const: 16
......
......@@ -38,6 +38,16 @@ properties:
- const: reg
- const: cfg
ti,syscon-acspcie-proxy-ctrl:
$ref: /schemas/types.yaml#/definitions/phandle-array
items:
- items:
- description: Phandle to the ACSPCIE Proxy Control Register
- description: Bitmask corresponding to the PAD IO Buffer
output enable fields (Active Low).
description: Specifier for enabling the ACSPCIE PAD outputs to drive
the reference clock to the Endpoint device.
ti,syscon-pcie-ctrl:
$ref: /schemas/types.yaml#/definitions/phandle-array
items:
......
......@@ -61,6 +61,11 @@ properties:
interrupt-map:
maxItems: 4
phys:
minItems: 1
maxItems: 4
description: One phy per logical lane, in order
power-domains:
maxItems: 1
......@@ -110,6 +115,7 @@ examples:
- |
#include <dt-bindings/interrupt-controller/arm-gic.h>
#include <dt-bindings/interrupt-controller/irq.h>
#include <dt-bindings/phy/phy.h>
#include <dt-bindings/power/xlnx-zynqmp-power.h>
soc {
#address-cells = <2>;
......@@ -138,6 +144,7 @@ examples:
<0x0 0x0 0x0 0x3 &pcie_intc 0x3>,
<0x0 0x0 0x0 0x4 &pcie_intc 0x4>;
msi-parent = <&nwl_pcie>;
phys = <&psgtr 0 PHY_TYPE_PCIE 0 0>;
power-domains = <&zynqmp_firmware PD_PCIE>;
iommus = <&smmu 0x4d0>;
pcie_intc: legacy-interrupt-controller {
......
......@@ -14,10 +14,21 @@ allOf:
properties:
compatible:
const: xlnx,xdma-host-3.00
enum:
- xlnx,xdma-host-3.00
- xlnx,qdma-host-3.00
reg:
maxItems: 1
items:
- description: configuration region and XDMA bridge register.
- description: QDMA bridge register.
minItems: 1
reg-names:
items:
- const: cfg
- const: breg
minItems: 1
ranges:
maxItems: 2
......@@ -76,6 +87,27 @@ required:
- "#interrupt-cells"
- interrupt-controller
if:
properties:
compatible:
contains:
enum:
- xlnx,qdma-host-3.00
then:
properties:
reg:
minItems: 2
reg-names:
minItems: 2
required:
- reg-names
else:
properties:
reg:
maxItems: 1
reg-names:
maxItems: 1
unevaluatedProperties: false
examples:
......
......@@ -2793,7 +2793,7 @@ F: drivers/iommu/msm*
F: drivers/mfd/ssbi.c
F: drivers/mmc/host/mmci_qcom*
F: drivers/mmc/host/sdhci-msm.c
F: drivers/pci/controller/dwc/pcie-qcom.c
F: drivers/pci/controller/dwc/pcie-qcom*
F: drivers/phy/qualcomm/
F: drivers/power/*/msm*
F: drivers/reset/reset-qcom-*
......@@ -17544,7 +17544,7 @@ PCI DRIVER FOR ALTERA PCIE IP
M: Joyce Ooi <joyce.ooi@intel.com>
L: linux-pci@vger.kernel.org
S: Supported
F: Documentation/devicetree/bindings/pci/altera-pcie.txt
F: Documentation/devicetree/bindings/pci/altr,pcie-root-port.yaml
F: drivers/pci/controller/pcie-altera.c
PCI DRIVER FOR APPLIEDMICRO XGENE
......@@ -17776,7 +17776,7 @@ PCI MSI DRIVER FOR ALTERA MSI IP
M: Joyce Ooi <joyce.ooi@intel.com>
L: linux-pci@vger.kernel.org
S: Supported
F: Documentation/devicetree/bindings/pci/altera-pcie-msi.txt
F: Documentation/devicetree/bindings/pci/altr,msi-controller.yaml
F: drivers/pci/controller/pcie-altera-msi.c
PCI MSI DRIVER FOR APPLIEDMICRO XGENE
......@@ -17929,6 +17929,7 @@ M: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
L: linux-pci@vger.kernel.org
L: linux-arm-msm@vger.kernel.org
S: Maintained
F: drivers/pci/controller/dwc/pcie-qcom-common.c
F: drivers/pci/controller/dwc/pcie-qcom.c
PCIE DRIVER FOR ROCKCHIP
......@@ -17965,6 +17966,7 @@ L: linux-pci@vger.kernel.org
L: linux-arm-msm@vger.kernel.org
S: Maintained
F: Documentation/devicetree/bindings/pci/qcom,pcie-ep.yaml
F: drivers/pci/controller/dwc/pcie-qcom-common.c
F: drivers/pci/controller/dwc/pcie-qcom-ep.c
PCMCIA SUBSYSTEM
......
......@@ -941,6 +941,7 @@ conf-pull-none {
&pcie {
status = "okay";
phys = <&psgtr 0 PHY_TYPE_PCIE 0 0>;
};
&psgtr {
......
......@@ -191,7 +191,14 @@ static inline bool zdev_enabled(struct zpci_dev *zdev)
return (zdev->fh & (1UL << 31)) ? true : false;
}
extern const struct attribute_group *zpci_attr_groups[];
extern const struct attribute_group zpci_attr_group;
extern const struct attribute_group pfip_attr_group;
extern const struct attribute_group zpci_ident_attr_group;
#define ARCH_PCI_DEV_GROUPS &zpci_attr_group, \
&pfip_attr_group, \
&zpci_ident_attr_group,
extern unsigned int s390_pci_force_floating __initdata;
extern unsigned int s390_pci_no_rid;
......
......@@ -3,7 +3,8 @@
# Makefile for the s390 PCI subsystem.
#
obj-$(CONFIG_PCI) += pci.o pci_irq.o pci_clp.o pci_sysfs.o \
obj-$(CONFIG_PCI) += pci.o pci_irq.o pci_clp.o \
pci_event.o pci_debug.o pci_insn.o pci_mmio.o \
pci_bus.o pci_kvm_hook.o
obj-$(CONFIG_PCI_IOV) += pci_iov.o
obj-$(CONFIG_SYSFS) += pci_sysfs.o
......@@ -587,7 +587,6 @@ int pcibios_device_add(struct pci_dev *pdev)
if (pdev->is_physfn)
pdev->no_vf_scan = 1;
pdev->dev.groups = zpci_attr_groups;
zpci_map_resources(pdev);
for (i = 0; i < PCI_STD_NUM_BARS; i++) {
......
......@@ -197,7 +197,7 @@ static struct attribute *zpci_ident_attrs[] = {
NULL,
};
static struct attribute_group zpci_ident_attr_group = {
const struct attribute_group zpci_ident_attr_group = {
.attrs = zpci_ident_attrs,
.is_visible = zpci_index_is_visible,
};
......@@ -223,7 +223,7 @@ static struct attribute *zpci_dev_attrs[] = {
NULL,
};
static struct attribute_group zpci_attr_group = {
const struct attribute_group zpci_attr_group = {
.attrs = zpci_dev_attrs,
.bin_attrs = zpci_bin_attrs,
};
......@@ -235,14 +235,8 @@ static struct attribute *pfip_attrs[] = {
&dev_attr_segment3.attr,
NULL,
};
static struct attribute_group pfip_attr_group = {
const struct attribute_group pfip_attr_group = {
.name = "pfip",
.attrs = pfip_attrs,
};
const struct attribute_group *zpci_attr_groups[] = {
&zpci_attr_group,
&pfip_attr_group,
&zpci_ident_attr_group,
NULL,
};
......@@ -980,7 +980,7 @@ static void amd_rp_pme_suspend(struct pci_dev *dev)
return;
rp = pcie_find_root_port(dev);
if (!rp->pm_cap)
if (!rp || !rp->pm_cap)
return;
rp->pme_support &= ~((PCI_PM_CAP_PME_D3hot|PCI_PM_CAP_PME_D3cold) >>
......@@ -994,7 +994,7 @@ static void amd_rp_pme_resume(struct pci_dev *dev)
u16 pmc;
rp = pcie_find_root_port(dev);
if (!rp->pm_cap)
if (!rp || !rp->pm_cap)
return;
pci_read_config_word(rp, rp->pm_cap + PCI_PM_PMC, &pmc);
......
......@@ -17,6 +17,9 @@ obj-$(CONFIG_PINCTRL) += pinctrl/
obj-$(CONFIG_GPIOLIB) += gpio/
obj-y += pwm/
# LEDs must come before PCI, it is needed by NPEM driver
obj-y += leds/
obj-y += pci/
obj-$(CONFIG_PARISC) += parisc/
......@@ -130,7 +133,6 @@ obj-$(CONFIG_CPU_IDLE) += cpuidle/
obj-y += mmc/
obj-y += ufs/
obj-$(CONFIG_MEMSTICK) += memstick/
obj-y += leds/
obj-$(CONFIG_INFINIBAND) += infiniband/
obj-y += firmware/
obj-$(CONFIG_CRYPTO) += crypto/
......
......@@ -181,6 +181,18 @@ static struct mcfg_fixup mcfg_quirks[] = {
LOONGSON_ECAM_MCFG("LOONGSON", 0),
LOONGSON_ECAM_MCFG("\0", 1),
LOONGSON_ECAM_MCFG("LOONGSON", 1),
LOONGSON_ECAM_MCFG("\0", 2),
LOONGSON_ECAM_MCFG("LOONGSON", 2),
LOONGSON_ECAM_MCFG("\0", 3),
LOONGSON_ECAM_MCFG("LOONGSON", 3),
LOONGSON_ECAM_MCFG("\0", 4),
LOONGSON_ECAM_MCFG("LOONGSON", 4),
LOONGSON_ECAM_MCFG("\0", 5),
LOONGSON_ECAM_MCFG("LOONGSON", 5),
LOONGSON_ECAM_MCFG("\0", 6),
LOONGSON_ECAM_MCFG("LOONGSON", 6),
LOONGSON_ECAM_MCFG("\0", 7),
LOONGSON_ECAM_MCFG("LOONGSON", 7),
#endif /* LOONGARCH */
};
......
......@@ -334,7 +334,7 @@ static u8 bcma_find_pci_capability(struct bcma_drv_pci *pc, unsigned int dev,
}
/* If the root port is capable of returning Config Request
* Retry Status (CRS) Completion Status to software then
* Retry Status (RRS) Completion Status to software then
* enable the feature.
*/
static void bcma_core_pci_enable_crs(struct bcma_drv_pci *pc)
......@@ -348,10 +348,10 @@ static void bcma_core_pci_enable_crs(struct bcma_drv_pci *pc)
NULL);
root_cap = cap_ptr + PCI_EXP_RTCAP;
bcma_extpci_read_config(pc, 0, 0, root_cap, &val16, sizeof(u16));
if (val16 & BCMA_CORE_PCI_RC_CRS_VISIBILITY) {
/* Enable CRS software visibility */
if (val16 & BCMA_CORE_PCI_RC_RRS_VISIBILITY) {
/* Enable Configuration RRS Software Visibility */
root_ctrl = cap_ptr + PCI_EXP_RTCTL;
val16 = PCI_EXP_RTCTL_CRSSVE;
val16 = PCI_EXP_RTCTL_RRS_SVE;
bcma_extpci_read_config(pc, 0, 0, root_ctrl, &val16,
sizeof(u16));
......@@ -360,7 +360,7 @@ static void bcma_core_pci_enable_crs(struct bcma_drv_pci *pc)
* 100 ms wait time from the end of Reset. If the device is
* not done with its internal initialization, it must at
* least return a completion TLP, with a completion status
* of "Configuration Request Retry Status (CRS)". The root
* of "Configuration Request Retry Status (RRS)". The root
* complex must complete the request to the host by returning
* a read-data value of 0001h for the Vendor ID field and
* all 1s for any additional bytes included in the request.
......
......@@ -287,9 +287,9 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
if (ret)
return ret;
regs = pcim_iomap(pdev, 1, 0);
if (!regs)
return -EIO;
regs = pcim_iomap_region(pdev, 1, "ast");
if (IS_ERR(regs))
return PTR_ERR(regs);
if (pdev->revision >= 0x40) {
/*
......@@ -311,9 +311,9 @@ static int ast_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
if (len < AST_IO_MM_LENGTH)
return -EIO;
ioregs = pcim_iomap(pdev, 2, 0);
if (!ioregs)
return -EIO;
ioregs = pcim_iomap_region(pdev, 2, "ast");
if (IS_ERR(ioregs))
return PTR_ERR(ioregs);
} else {
/*
* Anything else is best effort.
......
......@@ -114,6 +114,10 @@ int vbox_hw_init(struct vbox_private *vbox)
DRM_INFO("VRAM %08x\n", vbox->full_vram_size);
ret = pcim_request_region(pdev, 0, "vboxvideo");
if (ret)
return ret;
/* Map guest-heap at end of vram */
vbox->guest_heap = pcim_iomap_range(pdev, 0,
GUEST_HEAP_OFFSET(vbox), GUEST_HEAP_SIZE);
......
......@@ -143,6 +143,15 @@ config PCI_IOV
If unsure, say N.
config PCI_NPEM
bool "Native PCIe Enclosure Management"
depends on LEDS_CLASS=y
help
Support for Native PCIe Enclosure Management. It allows managing LED
indications in storage enclosures. Enclosure must support following
indications: OK, Locate, Fail, Rebuild, other indications are
optional.
config PCI_PRI
bool "PCI PRI support"
select PCI_ATS
......
......@@ -35,6 +35,7 @@ obj-$(CONFIG_XEN_PCIDEV_FRONTEND) += xen-pcifront.o
obj-$(CONFIG_VGA_ARB) += vgaarb.o
obj-$(CONFIG_PCI_DOE) += doe.o
obj-$(CONFIG_PCI_DYNAMIC_OF_NODES) += of_property.o
obj-$(CONFIG_PCI_NPEM) += npem.o
# Endpoint library must be initialized before its users
obj-$(CONFIG_PCI_ENDPOINT) += endpoint/
......
......@@ -488,8 +488,8 @@ void pci_restore_pasid_state(struct pci_dev *pdev)
* pci_pasid_features - Check which PASID features are supported
* @pdev: PCI device structure
*
* Returns a negative value when no PASI capability is present.
* Otherwise is returns a bitmask with supported features. Current
* Return a negative value when no PASID capability is present.
* Otherwise return a bitmask with supported features. Current
* features reported are:
* PCI_PASID_CAP_EXEC - Execute permission supported
* PCI_PASID_CAP_PRIV - Privileged mode supported
......
......@@ -196,7 +196,7 @@ config PCIE_MEDIATEK
config PCIE_MEDIATEK_GEN3
tristate "MediaTek Gen3 PCIe controller"
depends on ARCH_MEDIATEK || COMPILE_TEST
depends on ARCH_AIROHA || ARCH_MEDIATEK || COMPILE_TEST
depends on PCI_MSI
help
Adds support for PCIe Gen3 MAC controller for MediaTek SoCs.
......
......@@ -38,7 +38,7 @@ config PCIE_CADENCE_PLAT_EP
select PCIE_CADENCE_EP
select PCIE_CADENCE_PLAT
help
Say Y here if you want to support the Cadence PCIe platform controller in
Say Y here if you want to support the Cadence PCIe platform controller in
endpoint mode. This PCIe controller may be embedded into many
different vendors SoCs.
......
......@@ -7,6 +7,8 @@
*/
#include <linux/clk.h>
#include <linux/clk-provider.h>
#include <linux/container_of.h>
#include <linux/delay.h>
#include <linux/gpio/consumer.h>
#include <linux/io.h>
......@@ -22,6 +24,8 @@
#include "../../pci.h"
#include "pcie-cadence.h"
#define cdns_pcie_to_rc(p) container_of(p, struct cdns_pcie_rc, pcie)
#define ENABLE_REG_SYS_2 0x108
#define STATUS_REG_SYS_2 0x508
#define STATUS_CLR_REG_SYS_2 0x708
......@@ -44,6 +48,7 @@ enum link_status {
#define J721E_MODE_RC BIT(7)
#define LANE_COUNT(n) ((n) << 8)
#define ACSPCIE_PAD_DISABLE_MASK GENMASK(1, 0)
#define GENERATION_SEL_MASK GENMASK(1, 0)
struct j721e_pcie {
......@@ -52,6 +57,7 @@ struct j721e_pcie {
u32 mode;
u32 num_lanes;
u32 max_lanes;
struct gpio_desc *reset_gpio;
void __iomem *user_cfg_base;
void __iomem *intd_cfg_base;
u32 linkdown_irq_regfield;
......@@ -220,6 +226,36 @@ static int j721e_pcie_set_lane_count(struct j721e_pcie *pcie,
return ret;
}
static int j721e_enable_acspcie_refclk(struct j721e_pcie *pcie,
struct regmap *syscon)
{
struct device *dev = pcie->cdns_pcie->dev;
struct device_node *node = dev->of_node;
u32 mask = ACSPCIE_PAD_DISABLE_MASK;
struct of_phandle_args args;
u32 val;
int ret;
ret = of_parse_phandle_with_fixed_args(node,
"ti,syscon-acspcie-proxy-ctrl",
1, 0, &args);
if (ret) {
dev_err(dev,
"ti,syscon-acspcie-proxy-ctrl has invalid arguments\n");
return ret;
}
/* Clear PAD IO disable bits to enable refclk output */
val = ~(args.args[0]);
ret = regmap_update_bits(syscon, 0, mask, val);
if (ret) {
dev_err(dev, "failed to enable ACSPCIE refclk: %d\n", ret);
return ret;
}
return 0;
}
static int j721e_pcie_ctrl_init(struct j721e_pcie *pcie)
{
struct device *dev = pcie->cdns_pcie->dev;
......@@ -259,7 +295,13 @@ static int j721e_pcie_ctrl_init(struct j721e_pcie *pcie)
return ret;
}
return 0;
/* Enable ACSPCIE refclk output if the optional property exists */
syscon = syscon_regmap_lookup_by_phandle_optional(node,
"ti,syscon-acspcie-proxy-ctrl");
if (!syscon)
return 0;
return j721e_enable_acspcie_refclk(pcie, syscon);
}
static int cdns_ti_pcie_config_read(struct pci_bus *bus, unsigned int devfn,
......@@ -482,20 +524,20 @@ static int j721e_pcie_probe(struct platform_device *pdev)
pm_runtime_enable(dev);
ret = pm_runtime_get_sync(dev);
if (ret < 0) {
dev_err(dev, "pm_runtime_get_sync failed\n");
dev_err_probe(dev, ret, "pm_runtime_get_sync failed\n");
goto err_get_sync;
}
ret = j721e_pcie_ctrl_init(pcie);
if (ret < 0) {
dev_err(dev, "pm_runtime_get_sync failed\n");
dev_err_probe(dev, ret, "pm_runtime_get_sync failed\n");
goto err_get_sync;
}
ret = devm_request_irq(dev, irq, j721e_pcie_link_irq_handler, 0,
"j721e-pcie-link-down-irq", pcie);
if (ret < 0) {
dev_err(dev, "failed to request link state IRQ %d\n", irq);
dev_err_probe(dev, ret, "failed to request link state IRQ %d\n", irq);
goto err_get_sync;
}
......@@ -505,42 +547,40 @@ static int j721e_pcie_probe(struct platform_device *pdev)
case PCI_MODE_RC:
gpiod = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_LOW);
if (IS_ERR(gpiod)) {
ret = PTR_ERR(gpiod);
if (ret != -EPROBE_DEFER)
dev_err(dev, "Failed to get reset GPIO\n");
ret = dev_err_probe(dev, PTR_ERR(gpiod), "Failed to get reset GPIO\n");
goto err_get_sync;
}
pcie->reset_gpio = gpiod;
ret = cdns_pcie_init_phy(dev, cdns_pcie);
if (ret) {
dev_err(dev, "Failed to init phy\n");
dev_err_probe(dev, ret, "Failed to init phy\n");
goto err_get_sync;
}
clk = devm_clk_get_optional(dev, "pcie_refclk");
if (IS_ERR(clk)) {
ret = PTR_ERR(clk);
dev_err(dev, "failed to get pcie_refclk\n");
ret = dev_err_probe(dev, PTR_ERR(clk), "failed to get pcie_refclk\n");
goto err_pcie_setup;
}
ret = clk_prepare_enable(clk);
if (ret) {
dev_err(dev, "failed to enable pcie_refclk\n");
dev_err_probe(dev, ret, "failed to enable pcie_refclk\n");
goto err_pcie_setup;
}
pcie->refclk = clk;
/*
* "Power Sequencing and Reset Signal Timings" table in
* PCI EXPRESS CARD ELECTROMECHANICAL SPECIFICATION, REV. 3.0
* indicates PERST# should be deasserted after minimum of 100us
* once REFCLK is stable. The REFCLK to the connector in RC
* mode is selected while enabling the PHY. So deassert PERST#
* after 100 us.
* The "Power Sequencing and Reset Signal Timings" table of the
* PCI Express Card Electromechanical Specification, Revision
* 5.1, Section 2.9.2, Symbol "T_PERST-CLK", indicates PERST#
* should be deasserted after minimum of 100us once REFCLK is
* stable. The REFCLK to the connector in RC mode is selected
* while enabling the PHY. So deassert PERST# after 100 us.
*/
if (gpiod) {
usleep_range(100, 200);
fsleep(PCIE_T_PERST_CLK_US);
gpiod_set_value_cansleep(gpiod, 1);
}
......@@ -554,7 +594,7 @@ static int j721e_pcie_probe(struct platform_device *pdev)
case PCI_MODE_EP:
ret = cdns_pcie_init_phy(dev, cdns_pcie);
if (ret) {
dev_err(dev, "Failed to init phy\n");
dev_err_probe(dev, ret, "Failed to init phy\n");
goto err_get_sync;
}
......@@ -589,6 +629,87 @@ static void j721e_pcie_remove(struct platform_device *pdev)
pm_runtime_disable(dev);
}
static int j721e_pcie_suspend_noirq(struct device *dev)
{
struct j721e_pcie *pcie = dev_get_drvdata(dev);
if (pcie->mode == PCI_MODE_RC) {
gpiod_set_value_cansleep(pcie->reset_gpio, 0);
clk_disable_unprepare(pcie->refclk);
}
cdns_pcie_disable_phy(pcie->cdns_pcie);
return 0;
}
static int j721e_pcie_resume_noirq(struct device *dev)
{
struct j721e_pcie *pcie = dev_get_drvdata(dev);
struct cdns_pcie *cdns_pcie = pcie->cdns_pcie;
int ret;
ret = j721e_pcie_ctrl_init(pcie);
if (ret < 0)
return ret;
j721e_pcie_config_link_irq(pcie);
/*
* This is not called explicitly in the probe, it is called by
* cdns_pcie_init_phy().
*/
ret = cdns_pcie_enable_phy(pcie->cdns_pcie);
if (ret < 0)
return ret;
if (pcie->mode == PCI_MODE_RC) {
struct cdns_pcie_rc *rc = cdns_pcie_to_rc(cdns_pcie);
ret = clk_prepare_enable(pcie->refclk);
if (ret < 0)
return ret;
/*
* The "Power Sequencing and Reset Signal Timings" table of the
* PCI Express Card Electromechanical Specification, Revision
* 5.1, Section 2.9.2, Symbol "T_PERST-CLK", indicates PERST#
* should be deasserted after minimum of 100us once REFCLK is
* stable. The REFCLK to the connector in RC mode is selected
* while enabling the PHY. So deassert PERST# after 100 us.
*/
if (pcie->reset_gpio) {
fsleep(PCIE_T_PERST_CLK_US);
gpiod_set_value_cansleep(pcie->reset_gpio, 1);
}
ret = cdns_pcie_host_link_setup(rc);
if (ret < 0) {
clk_disable_unprepare(pcie->refclk);
return ret;
}
/*
* Reset internal status of BARs to force reinitialization in
* cdns_pcie_host_init().
*/
for (enum cdns_pcie_rp_bar bar = RP_BAR0; bar <= RP_NO_BAR; bar++)
rc->avail_ib_bar[bar] = true;
ret = cdns_pcie_host_init(rc);
if (ret) {
clk_disable_unprepare(pcie->refclk);
return ret;
}
}
return 0;
}
static DEFINE_NOIRQ_DEV_PM_OPS(j721e_pcie_pm_ops,
j721e_pcie_suspend_noirq,
j721e_pcie_resume_noirq);
static struct platform_driver j721e_pcie_driver = {
.probe = j721e_pcie_probe,
.remove_new = j721e_pcie_remove,
......@@ -596,6 +717,7 @@ static struct platform_driver j721e_pcie_driver = {
.name = "j721e-pcie",
.of_match_table = of_j721e_pcie_match,
.suppress_bind_attrs = true,
.pm = pm_sleep_ptr(&j721e_pcie_pm_ops),
},
};
builtin_platform_driver(j721e_pcie_driver);
......@@ -485,8 +485,7 @@ static int cdns_pcie_host_init_address_translation(struct cdns_pcie_rc *rc)
return cdns_pcie_host_map_dma_ranges(rc);
}
static int cdns_pcie_host_init(struct device *dev,
struct cdns_pcie_rc *rc)
int cdns_pcie_host_init(struct cdns_pcie_rc *rc)
{
int err;
......@@ -497,6 +496,30 @@ static int cdns_pcie_host_init(struct device *dev,
return cdns_pcie_host_init_address_translation(rc);
}
int cdns_pcie_host_link_setup(struct cdns_pcie_rc *rc)
{
struct cdns_pcie *pcie = &rc->pcie;
struct device *dev = rc->pcie.dev;
int ret;
if (rc->quirk_detect_quiet_flag)
cdns_pcie_detect_quiet_min_delay_set(&rc->pcie);
cdns_pcie_host_enable_ptm_response(pcie);
ret = cdns_pcie_start_link(pcie);
if (ret) {
dev_err(dev, "Failed to start link\n");
return ret;
}
ret = cdns_pcie_host_start_link(rc);
if (ret)
dev_dbg(dev, "PCIe link never came up\n");
return 0;
}
int cdns_pcie_host_setup(struct cdns_pcie_rc *rc)
{
struct device *dev = rc->pcie.dev;
......@@ -533,25 +556,14 @@ int cdns_pcie_host_setup(struct cdns_pcie_rc *rc)
return PTR_ERR(rc->cfg_base);
rc->cfg_res = res;
if (rc->quirk_detect_quiet_flag)
cdns_pcie_detect_quiet_min_delay_set(&rc->pcie);
cdns_pcie_host_enable_ptm_response(pcie);
ret = cdns_pcie_start_link(pcie);
if (ret) {
dev_err(dev, "Failed to start link\n");
return ret;
}
ret = cdns_pcie_host_start_link(rc);
ret = cdns_pcie_host_link_setup(rc);
if (ret)
dev_dbg(dev, "PCIe link never came up\n");
return ret;
for (bar = RP_BAR0; bar <= RP_NO_BAR; bar++)
rc->avail_ib_bar[bar] = true;
ret = cdns_pcie_host_init(dev, rc);
ret = cdns_pcie_host_init(rc);
if (ret)
return ret;
......
......@@ -314,7 +314,6 @@ struct cdns_pcie {
/**
* struct cdns_pcie_rc - private data for this PCIe Root Complex driver
* @pcie: Cadence PCIe controller
* @dev: pointer to PCIe device
* @cfg_res: start/end offsets in the physical system memory to map PCI
* configuration space accesses
* @cfg_base: IO mapped window to access the PCI configuration space of a
......@@ -521,10 +520,22 @@ static inline bool cdns_pcie_link_up(struct cdns_pcie *pcie)
}
#ifdef CONFIG_PCIE_CADENCE_HOST
int cdns_pcie_host_link_setup(struct cdns_pcie_rc *rc);
int cdns_pcie_host_init(struct cdns_pcie_rc *rc);
int cdns_pcie_host_setup(struct cdns_pcie_rc *rc);
void __iomem *cdns_pci_map_bus(struct pci_bus *bus, unsigned int devfn,
int where);
#else
static inline int cdns_pcie_host_link_setup(struct cdns_pcie_rc *rc)
{
return 0;
}
static inline int cdns_pcie_host_init(struct cdns_pcie_rc *rc)
{
return 0;
}
static inline int cdns_pcie_host_setup(struct cdns_pcie_rc *rc)
{
return 0;
......
......@@ -265,12 +265,16 @@ config PCIE_DW_PLAT_EP
order to enable device-specific features PCI_DW_PLAT_EP must be
selected.
config PCIE_QCOM_COMMON
bool
config PCIE_QCOM
bool "Qualcomm PCIe controller (host mode)"
depends on OF && (ARCH_QCOM || COMPILE_TEST)
depends on PCI_MSI
select PCIE_DW_HOST
select CRC8
select PCIE_QCOM_COMMON
help
Say Y here to enable PCIe controller support on Qualcomm SoCs. The
PCIe controller uses the DesignWare core plus Qualcomm-specific
......@@ -281,6 +285,7 @@ config PCIE_QCOM_EP
depends on OF && (ARCH_QCOM || COMPILE_TEST)
depends on PCI_ENDPOINT
select PCIE_DW_EP
select PCIE_QCOM_COMMON
help
Say Y here to enable support for the PCIe controllers on Qualcomm SoCs
to work in endpoint mode. The PCIe controller uses the DesignWare core
......
......@@ -12,6 +12,7 @@ obj-$(CONFIG_PCIE_SPEAR13XX) += pcie-spear13xx.o
obj-$(CONFIG_PCI_KEYSTONE) += pci-keystone.o
obj-$(CONFIG_PCI_LAYERSCAPE) += pci-layerscape.o
obj-$(CONFIG_PCI_LAYERSCAPE_EP) += pci-layerscape-ep.o
obj-$(CONFIG_PCIE_QCOM_COMMON) += pcie-qcom-common.o
obj-$(CONFIG_PCIE_QCOM) += pcie-qcom.o
obj-$(CONFIG_PCIE_QCOM_EP) += pcie-qcom-ep.o
obj-$(CONFIG_PCIE_ARMADA_8K) += pcie-armada8k.o
......
......@@ -850,14 +850,21 @@ static int dra7xx_pcie_probe(struct platform_device *pdev)
dra7xx->mode = mode;
ret = devm_request_threaded_irq(dev, irq, NULL, dra7xx_pcie_irq_handler,
IRQF_SHARED, "dra7xx-pcie-main", dra7xx);
IRQF_SHARED | IRQF_ONESHOT,
"dra7xx-pcie-main", dra7xx);
if (ret) {
dev_err(dev, "failed to request irq\n");
goto err_gpio;
goto err_deinit;
}
return 0;
err_deinit:
if (dra7xx->mode == DW_PCIE_RC_TYPE)
dw_pcie_host_deinit(&dra7xx->pci->pp);
else
dw_pcie_ep_deinit(&dra7xx->pci->ep);
err_gpio:
err_get_sync:
pm_runtime_put(dev);
......
This diff is collapsed.
......@@ -189,12 +189,6 @@ static void ks_pcie_compose_msi_msg(struct irq_data *data, struct msi_msg *msg)
(int)data->hwirq, msg->address_hi, msg->address_lo);
}
static int ks_pcie_msi_set_affinity(struct irq_data *irq_data,
const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static void ks_pcie_msi_mask(struct irq_data *data)
{
struct dw_pcie_rp *pp = irq_data_get_irq_chip_data(data);
......@@ -247,7 +241,6 @@ static struct irq_chip ks_pcie_msi_irq_chip = {
.name = "KEYSTONE-PCI-MSI",
.irq_ack = ks_pcie_msi_irq_ack,
.irq_compose_msi_msg = ks_pcie_compose_msi_msg,
.irq_set_affinity = ks_pcie_msi_set_affinity,
.irq_mask = ks_pcie_msi_mask,
.irq_unmask = ks_pcie_msi_unmask,
};
......@@ -577,7 +570,7 @@ static void ks_pcie_quirk(struct pci_dev *dev)
*/
if (pci_match_id(am6_pci_devids, bridge)) {
bridge_dev = pci_get_host_bridge_device(dev);
if (!bridge_dev && !bridge_dev->parent)
if (!bridge_dev || !bridge_dev->parent)
return;
ks_pcie = dev_get_drvdata(bridge_dev->parent);
......
......@@ -48,8 +48,9 @@ static struct irq_chip dw_pcie_msi_irq_chip = {
};
static struct msi_domain_info dw_pcie_msi_domain_info = {
.flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_PCI_MSIX | MSI_FLAG_MULTI_PCI_MSI),
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_NO_AFFINITY | MSI_FLAG_PCI_MSIX |
MSI_FLAG_MULTI_PCI_MSI,
.chip = &dw_pcie_msi_irq_chip,
};
......@@ -116,12 +117,6 @@ static void dw_pci_setup_msi_msg(struct irq_data *d, struct msi_msg *msg)
(int)d->hwirq, msg->address_hi, msg->address_lo);
}
static int dw_pci_msi_set_affinity(struct irq_data *d,
const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static void dw_pci_bottom_mask(struct irq_data *d)
{
struct dw_pcie_rp *pp = irq_data_get_irq_chip_data(d);
......@@ -177,7 +172,6 @@ static struct irq_chip dw_pci_msi_bottom_irq_chip = {
.name = "DWPCI-MSI",
.irq_ack = dw_pci_bottom_ack,
.irq_compose_msi_msg = dw_pci_setup_msi_msg,
.irq_set_affinity = dw_pci_msi_set_affinity,
.irq_mask = dw_pci_bottom_mask,
.irq_unmask = dw_pci_bottom_unmask,
};
......
......@@ -112,6 +112,7 @@ int dw_pcie_get_resources(struct dw_pcie *pci)
pci->dbi_base = devm_pci_remap_cfg_resource(pci->dev, res);
if (IS_ERR(pci->dbi_base))
return PTR_ERR(pci->dbi_base);
pci->dbi_phys_addr = res->start;
}
/* DBI2 is mainly useful for the endpoint controller */
......@@ -134,6 +135,7 @@ int dw_pcie_get_resources(struct dw_pcie *pci)
pci->atu_base = devm_ioremap_resource(pci->dev, res);
if (IS_ERR(pci->atu_base))
return PTR_ERR(pci->atu_base);
pci->atu_phys_addr = res->start;
} else {
pci->atu_base = pci->dbi_base + DEFAULT_DBI_ATU_OFFSET;
}
......@@ -166,8 +168,8 @@ int dw_pcie_get_resources(struct dw_pcie *pci)
return ret;
}
if (pci->link_gen < 1)
pci->link_gen = of_pci_get_max_link_speed(np);
if (pci->max_link_speed < 1)
pci->max_link_speed = of_pci_get_max_link_speed(np);
of_property_read_u32(np, "num-lanes", &pci->num_lanes);
......@@ -687,16 +689,27 @@ void dw_pcie_upconfig_setup(struct dw_pcie *pci)
}
EXPORT_SYMBOL_GPL(dw_pcie_upconfig_setup);
static void dw_pcie_link_set_max_speed(struct dw_pcie *pci, u32 link_gen)
static void dw_pcie_link_set_max_speed(struct dw_pcie *pci)
{
u32 cap, ctrl2, link_speed;
u8 offset = dw_pcie_find_capability(pci, PCI_CAP_ID_EXP);
cap = dw_pcie_readl_dbi(pci, offset + PCI_EXP_LNKCAP);
/*
* Even if the platform doesn't want to limit the maximum link speed,
* just cache the hardware default value so that the vendor drivers can
* use it to do any link specific configuration.
*/
if (pci->max_link_speed < 1) {
pci->max_link_speed = FIELD_GET(PCI_EXP_LNKCAP_SLS, cap);
return;
}
ctrl2 = dw_pcie_readl_dbi(pci, offset + PCI_EXP_LNKCTL2);
ctrl2 &= ~PCI_EXP_LNKCTL2_TLS;
switch (pcie_link_speed[link_gen]) {
switch (pcie_link_speed[pci->max_link_speed]) {
case PCIE_SPEED_2_5GT:
link_speed = PCI_EXP_LNKCTL2_TLS_2_5GT;
break;
......@@ -1058,8 +1071,7 @@ void dw_pcie_setup(struct dw_pcie *pci)
{
u32 val;
if (pci->link_gen > 0)
dw_pcie_link_set_max_speed(pci, pci->link_gen);
dw_pcie_link_set_max_speed(pci);
/* Configure Gen1 N_FTS */
if (pci->n_fts[0]) {
......
......@@ -125,6 +125,19 @@
#define GEN3_RELATED_OFF_GEN3_EQ_DISABLE BIT(16)
#define GEN3_RELATED_OFF_RATE_SHADOW_SEL_SHIFT 24
#define GEN3_RELATED_OFF_RATE_SHADOW_SEL_MASK GENMASK(25, 24)
#define GEN3_RELATED_OFF_RATE_SHADOW_SEL_16_0GT 0x1
#define GEN3_EQ_CONTROL_OFF 0x8A8
#define GEN3_EQ_CONTROL_OFF_FB_MODE GENMASK(3, 0)
#define GEN3_EQ_CONTROL_OFF_PHASE23_EXIT_MODE BIT(4)
#define GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC GENMASK(23, 8)
#define GEN3_EQ_CONTROL_OFF_FOM_INC_INITIAL_EVAL BIT(24)
#define GEN3_EQ_FB_MODE_DIR_CHANGE_OFF 0x8AC
#define GEN3_EQ_FMDC_T_MIN_PHASE23 GENMASK(4, 0)
#define GEN3_EQ_FMDC_N_EVALS GENMASK(9, 5)
#define GEN3_EQ_FMDC_MAX_PRE_CUSROR_DELTA GENMASK(13, 10)
#define GEN3_EQ_FMDC_MAX_POST_CUSROR_DELTA GENMASK(17, 14)
#define PCIE_PORT_MULTI_LANE_CTRL 0x8C0
#define PORT_MLTI_UPCFG_SUPPORT BIT(7)
......@@ -197,6 +210,24 @@
#define PCIE_PL_CHK_REG_ERR_ADDR 0xB28
/*
* 16.0 GT/s (Gen 4) lane margining register definitions
*/
#define GEN4_LANE_MARGINING_1_OFF 0xB80
#define MARGINING_MAX_VOLTAGE_OFFSET GENMASK(29, 24)
#define MARGINING_NUM_VOLTAGE_STEPS GENMASK(22, 16)
#define MARGINING_MAX_TIMING_OFFSET GENMASK(13, 8)
#define MARGINING_NUM_TIMING_STEPS GENMASK(5, 0)
#define GEN4_LANE_MARGINING_2_OFF 0xB84
#define MARGINING_IND_ERROR_SAMPLER BIT(28)
#define MARGINING_SAMPLE_REPORTING_METHOD BIT(27)
#define MARGINING_IND_LEFT_RIGHT_TIMING BIT(26)
#define MARGINING_IND_UP_DOWN_VOLTAGE BIT(25)
#define MARGINING_VOLTAGE_SUPPORTED BIT(24)
#define MARGINING_MAXLANES GENMASK(20, 16)
#define MARGINING_SAMPLE_RATE_TIMING GENMASK(13, 8)
#define MARGINING_SAMPLE_RATE_VOLTAGE GENMASK(5, 0)
/*
* iATU Unroll-specific register definitions
* From 4.80 core version the address translation will be made by unroll
......@@ -407,8 +438,10 @@ struct dw_pcie_ops {
struct dw_pcie {
struct device *dev;
void __iomem *dbi_base;
resource_size_t dbi_phys_addr;
void __iomem *dbi_base2;
void __iomem *atu_base;
resource_size_t atu_phys_addr;
size_t atu_size;
u32 num_ib_windows;
u32 num_ob_windows;
......@@ -421,7 +454,7 @@ struct dw_pcie {
u32 type;
unsigned long caps;
int num_lanes;
int link_gen;
int max_link_speed;
u8 n_fts[2];
struct dw_edma_chip edma;
struct clk_bulk_data app_clks[DW_PCIE_NUM_APP_CLKS];
......
......@@ -132,7 +132,7 @@ static void intel_pcie_link_setup(struct intel_pcie *pcie)
static void intel_pcie_init_n_fts(struct dw_pcie *pci)
{
switch (pci->link_gen) {
switch (pci->max_link_speed) {
case 3:
pci->n_fts[1] = PORT_AFR_N_FTS_GEN3;
break;
......@@ -252,7 +252,7 @@ static int intel_pcie_wait_l2(struct intel_pcie *pcie)
int ret;
struct dw_pcie *pci = &pcie->pci;
if (pci->link_gen < 3)
if (pci->max_link_speed < 3)
return 0;
/* Send PME_TURN_OFF message */
......
......@@ -420,11 +420,11 @@ static int kirin_pcie_parse_port(struct kirin_pcie *pcie,
"unable to get a valid reset gpio\n");
}
pcie->num_slots++;
if (pcie->num_slots > MAX_PCI_SLOTS) {
if (pcie->num_slots + 1 >= MAX_PCI_SLOTS) {
dev_err(dev, "Too many PCI slots!\n");
return -EINVAL;
}
pcie->num_slots++;
ret = of_pci_get_devfn(child);
if (ret < 0) {
......
// SPDX-License-Identifier: GPL-2.0
/*
* Copyright (c) 2024 Qualcomm Innovation Center, Inc. All rights reserved.
*/
#include <linux/pci.h>
#include "pcie-designware.h"
#include "pcie-qcom-common.h"
void qcom_pcie_common_set_16gt_equalization(struct dw_pcie *pci)
{
u32 reg;
/*
* GEN3_RELATED_OFF register is repurposed to apply equalization
* settings at various data transmission rates through registers namely
* GEN3_EQ_*. The RATE_SHADOW_SEL bit field of GEN3_RELATED_OFF
* determines the data rate for which these equalization settings are
* applied.
*/
reg = dw_pcie_readl_dbi(pci, GEN3_RELATED_OFF);
reg &= ~GEN3_RELATED_OFF_GEN3_ZRXDC_NONCOMPL;
reg &= ~GEN3_RELATED_OFF_RATE_SHADOW_SEL_MASK;
reg |= FIELD_PREP(GEN3_RELATED_OFF_RATE_SHADOW_SEL_MASK,
GEN3_RELATED_OFF_RATE_SHADOW_SEL_16_0GT);
dw_pcie_writel_dbi(pci, GEN3_RELATED_OFF, reg);
reg = dw_pcie_readl_dbi(pci, GEN3_EQ_FB_MODE_DIR_CHANGE_OFF);
reg &= ~(GEN3_EQ_FMDC_T_MIN_PHASE23 |
GEN3_EQ_FMDC_N_EVALS |
GEN3_EQ_FMDC_MAX_PRE_CUSROR_DELTA |
GEN3_EQ_FMDC_MAX_POST_CUSROR_DELTA);
reg |= FIELD_PREP(GEN3_EQ_FMDC_T_MIN_PHASE23, 0x1) |
FIELD_PREP(GEN3_EQ_FMDC_N_EVALS, 0xd) |
FIELD_PREP(GEN3_EQ_FMDC_MAX_PRE_CUSROR_DELTA, 0x5) |
FIELD_PREP(GEN3_EQ_FMDC_MAX_POST_CUSROR_DELTA, 0x5);
dw_pcie_writel_dbi(pci, GEN3_EQ_FB_MODE_DIR_CHANGE_OFF, reg);
reg = dw_pcie_readl_dbi(pci, GEN3_EQ_CONTROL_OFF);
reg &= ~(GEN3_EQ_CONTROL_OFF_FB_MODE |
GEN3_EQ_CONTROL_OFF_PHASE23_EXIT_MODE |
GEN3_EQ_CONTROL_OFF_FOM_INC_INITIAL_EVAL |
GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC);
dw_pcie_writel_dbi(pci, GEN3_EQ_CONTROL_OFF, reg);
}
EXPORT_SYMBOL_GPL(qcom_pcie_common_set_16gt_equalization);
void qcom_pcie_common_set_16gt_lane_margining(struct dw_pcie *pci)
{
u32 reg;
reg = dw_pcie_readl_dbi(pci, GEN4_LANE_MARGINING_1_OFF);
reg &= ~(MARGINING_MAX_VOLTAGE_OFFSET |
MARGINING_NUM_VOLTAGE_STEPS |
MARGINING_MAX_TIMING_OFFSET |
MARGINING_NUM_TIMING_STEPS);
reg |= FIELD_PREP(MARGINING_MAX_VOLTAGE_OFFSET, 0x24) |
FIELD_PREP(MARGINING_NUM_VOLTAGE_STEPS, 0x78) |
FIELD_PREP(MARGINING_MAX_TIMING_OFFSET, 0x32) |
FIELD_PREP(MARGINING_NUM_TIMING_STEPS, 0x10);
dw_pcie_writel_dbi(pci, GEN4_LANE_MARGINING_1_OFF, reg);
reg = dw_pcie_readl_dbi(pci, GEN4_LANE_MARGINING_2_OFF);
reg |= MARGINING_IND_ERROR_SAMPLER |
MARGINING_SAMPLE_REPORTING_METHOD |
MARGINING_IND_LEFT_RIGHT_TIMING |
MARGINING_VOLTAGE_SUPPORTED;
reg &= ~(MARGINING_IND_UP_DOWN_VOLTAGE |
MARGINING_MAXLANES |
MARGINING_SAMPLE_RATE_TIMING |
MARGINING_SAMPLE_RATE_VOLTAGE);
reg |= FIELD_PREP(MARGINING_MAXLANES, pci->num_lanes) |
FIELD_PREP(MARGINING_SAMPLE_RATE_TIMING, 0x3f) |
FIELD_PREP(MARGINING_SAMPLE_RATE_VOLTAGE, 0x3f);
dw_pcie_writel_dbi(pci, GEN4_LANE_MARGINING_2_OFF, reg);
}
EXPORT_SYMBOL_GPL(qcom_pcie_common_set_16gt_lane_margining);
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (c) 2024 Qualcomm Innovation Center, Inc. All rights reserved.
*/
#ifndef _PCIE_QCOM_COMMON_H
#define _PCIE_QCOM_COMMON_H
struct dw_pcie;
void qcom_pcie_common_set_16gt_equalization(struct dw_pcie *pci);
void qcom_pcie_common_set_16gt_lane_margining(struct dw_pcie *pci);
#endif
......@@ -25,6 +25,7 @@
#include "../../pci.h"
#include "pcie-designware.h"
#include "pcie-qcom-common.h"
/* PARF registers */
#define PARF_SYS_CTRL 0x00
......@@ -498,6 +499,11 @@ static int qcom_pcie_perst_deassert(struct dw_pcie *pci)
goto err_disable_resources;
}
if (pcie_link_speed[pci->max_link_speed] == PCIE_SPEED_16_0GT) {
qcom_pcie_common_set_16gt_equalization(pci);
qcom_pcie_common_set_16gt_lane_margining(pci);
}
/*
* The physical address of the MMIO region which is exposed as the BAR
* should be written to MHI BASE registers.
......@@ -659,11 +665,9 @@ static irqreturn_t qcom_pcie_ep_global_irq_thread(int irq, void *data)
struct dw_pcie *pci = &pcie_ep->pci;
struct device *dev = pci->dev;
u32 status = readl_relaxed(pcie_ep->parf + PARF_INT_ALL_STATUS);
u32 mask = readl_relaxed(pcie_ep->parf + PARF_INT_ALL_MASK);
u32 dstate, val;
writel_relaxed(status, pcie_ep->parf + PARF_INT_ALL_CLEAR);
status &= mask;
if (FIELD_GET(PARF_INT_ALL_LINK_DOWN, status)) {
dev_dbg(dev, "Received Linkdown event\n");
......@@ -693,7 +697,8 @@ static irqreturn_t qcom_pcie_ep_global_irq_thread(int irq, void *data)
dw_pcie_ep_linkup(&pci->ep);
pcie_ep->link_status = QCOM_PCIE_EP_LINK_UP;
} else {
dev_err(dev, "Received unknown event: %d\n", status);
dev_WARN_ONCE(dev, 1, "Received unknown event. INT_STATUS: 0x%08x\n",
status);
}
return IRQ_HANDLED;
......@@ -724,8 +729,15 @@ static irqreturn_t qcom_pcie_ep_perst_irq_thread(int irq, void *data)
static int qcom_pcie_ep_enable_irq_resources(struct platform_device *pdev,
struct qcom_pcie_ep *pcie_ep)
{
struct device *dev = pcie_ep->pci.dev;
char *name;
int ret;
name = devm_kasprintf(dev, GFP_KERNEL, "qcom_pcie_ep_global_irq%d",
pcie_ep->pci.ep.epc->domain_nr);
if (!name)
return -ENOMEM;
pcie_ep->global_irq = platform_get_irq_byname(pdev, "global");
if (pcie_ep->global_irq < 0)
return pcie_ep->global_irq;
......@@ -733,18 +745,23 @@ static int qcom_pcie_ep_enable_irq_resources(struct platform_device *pdev,
ret = devm_request_threaded_irq(&pdev->dev, pcie_ep->global_irq, NULL,
qcom_pcie_ep_global_irq_thread,
IRQF_ONESHOT,
"global_irq", pcie_ep);
name, pcie_ep);
if (ret) {
dev_err(&pdev->dev, "Failed to request Global IRQ\n");
return ret;
}
name = devm_kasprintf(dev, GFP_KERNEL, "qcom_pcie_ep_perst_irq%d",
pcie_ep->pci.ep.epc->domain_nr);
if (!name)
return -ENOMEM;
pcie_ep->perst_irq = gpiod_to_irq(pcie_ep->reset);
irq_set_status_flags(pcie_ep->perst_irq, IRQ_NOAUTOEN);
ret = devm_request_threaded_irq(&pdev->dev, pcie_ep->perst_irq, NULL,
qcom_pcie_ep_perst_irq_thread,
IRQF_TRIGGER_HIGH | IRQF_ONESHOT,
"perst_irq", pcie_ep);
name, pcie_ep);
if (ret) {
dev_err(&pdev->dev, "Failed to request PERST IRQ\n");
disable_irq(pcie_ep->global_irq);
......@@ -858,21 +875,15 @@ static int qcom_pcie_ep_probe(struct platform_device *pdev)
if (ret)
return ret;
ret = qcom_pcie_enable_resources(pcie_ep);
if (ret) {
dev_err(dev, "Failed to enable resources: %d\n", ret);
return ret;
}
ret = dw_pcie_ep_init(&pcie_ep->pci.ep);
if (ret) {
dev_err(dev, "Failed to initialize endpoint: %d\n", ret);
goto err_disable_resources;
return ret;
}
ret = qcom_pcie_ep_enable_irq_resources(pdev, pcie_ep);
if (ret)
goto err_disable_resources;
goto err_ep_deinit;
name = devm_kasprintf(dev, GFP_KERNEL, "%pOFP", dev->of_node);
if (!name) {
......@@ -889,8 +900,8 @@ static int qcom_pcie_ep_probe(struct platform_device *pdev)
disable_irq(pcie_ep->global_irq);
disable_irq(pcie_ep->perst_irq);
err_disable_resources:
qcom_pcie_disable_resources(pcie_ep);
err_ep_deinit:
dw_pcie_ep_deinit(&pcie_ep->pci.ep);
return ret;
}
......
......@@ -35,6 +35,7 @@
#include "../../pci.h"
#include "pcie-designware.h"
#include "pcie-qcom-common.h"
/* PARF registers */
#define PARF_SYS_CTRL 0x00
......@@ -45,15 +46,24 @@
#define PARF_PHY_REFCLK 0x4c
#define PARF_CONFIG_BITS 0x50
#define PARF_DBI_BASE_ADDR 0x168
#define PARF_SLV_ADDR_SPACE_SIZE 0x16c
#define PARF_MHI_CLOCK_RESET_CTRL 0x174
#define PARF_AXI_MSTR_WR_ADDR_HALT 0x178
#define PARF_AXI_MSTR_WR_ADDR_HALT_V2 0x1a8
#define PARF_Q2A_FLUSH 0x1ac
#define PARF_LTSSM 0x1b0
#define PARF_INT_ALL_STATUS 0x224
#define PARF_INT_ALL_CLEAR 0x228
#define PARF_INT_ALL_MASK 0x22c
#define PARF_SID_OFFSET 0x234
#define PARF_BDF_TRANSLATE_CFG 0x24c
#define PARF_SLV_ADDR_SPACE_SIZE 0x358
#define PARF_DBI_BASE_ADDR_V2 0x350
#define PARF_DBI_BASE_ADDR_V2_HI 0x354
#define PARF_SLV_ADDR_SPACE_SIZE_V2 0x358
#define PARF_SLV_ADDR_SPACE_SIZE_V2_HI 0x35c
#define PARF_NO_SNOOP_OVERIDE 0x3d4
#define PARF_ATU_BASE_ADDR 0x634
#define PARF_ATU_BASE_ADDR_HI 0x638
#define PARF_DEVICE_TYPE 0x1000
#define PARF_BDF_TO_SID_TABLE_N 0x2000
#define PARF_BDF_TO_SID_CFG 0x2c00
......@@ -108,7 +118,7 @@
#define PHY_RX0_EQ(x) FIELD_PREP(GENMASK(26, 24), x)
/* PARF_SLV_ADDR_SPACE_SIZE register value */
#define SLV_ADDR_SPACE_SZ 0x10000000
#define SLV_ADDR_SPACE_SZ 0x80000000
/* PARF_MHI_CLOCK_RESET_CTRL register fields */
#define AHB_CLK_EN BIT(0)
......@@ -121,6 +131,9 @@
/* PARF_LTSSM register fields */
#define LTSSM_EN BIT(8)
/* PARF_INT_ALL_{STATUS/CLEAR/MASK} register fields */
#define PARF_INT_ALL_LINK_UP BIT(13)
/* PARF_NO_SNOOP_OVERIDE register fields */
#define WR_NO_SNOOP_OVERIDE_EN BIT(1)
#define RD_NO_SNOOP_OVERIDE_EN BIT(3)
......@@ -284,6 +297,11 @@ static int qcom_pcie_start_link(struct dw_pcie *pci)
{
struct qcom_pcie *pcie = to_qcom_pcie(pci);
if (pcie_link_speed[pci->max_link_speed] == PCIE_SPEED_16_0GT) {
qcom_pcie_common_set_16gt_equalization(pci);
qcom_pcie_common_set_16gt_lane_margining(pci);
}
/* Enable Link Training state machine */
if (pcie->cfg->ops->ltssm_enable)
pcie->cfg->ops->ltssm_enable(pcie);
......@@ -325,6 +343,50 @@ static void qcom_pcie_clear_hpc(struct dw_pcie *pci)
dw_pcie_dbi_ro_wr_dis(pci);
}
static void qcom_pcie_configure_dbi_base(struct qcom_pcie *pcie)
{
struct dw_pcie *pci = pcie->pci;
if (pci->dbi_phys_addr) {
/*
* PARF_DBI_BASE_ADDR register is in CPU domain and require to
* be programmed with CPU physical address.
*/
writel(lower_32_bits(pci->dbi_phys_addr), pcie->parf +
PARF_DBI_BASE_ADDR);
writel(SLV_ADDR_SPACE_SZ, pcie->parf +
PARF_SLV_ADDR_SPACE_SIZE);
}
}
static void qcom_pcie_configure_dbi_atu_base(struct qcom_pcie *pcie)
{
struct dw_pcie *pci = pcie->pci;
if (pci->dbi_phys_addr) {
/*
* PARF_DBI_BASE_ADDR_V2 and PARF_ATU_BASE_ADDR registers are
* in CPU domain and require to be programmed with CPU
* physical addresses.
*/
writel(lower_32_bits(pci->dbi_phys_addr), pcie->parf +
PARF_DBI_BASE_ADDR_V2);
writel(upper_32_bits(pci->dbi_phys_addr), pcie->parf +
PARF_DBI_BASE_ADDR_V2_HI);
if (pci->atu_phys_addr) {
writel(lower_32_bits(pci->atu_phys_addr), pcie->parf +
PARF_ATU_BASE_ADDR);
writel(upper_32_bits(pci->atu_phys_addr), pcie->parf +
PARF_ATU_BASE_ADDR_HI);
}
writel(0x0, pcie->parf + PARF_SLV_ADDR_SPACE_SIZE_V2);
writel(SLV_ADDR_SPACE_SZ, pcie->parf +
PARF_SLV_ADDR_SPACE_SIZE_V2_HI);
}
}
static void qcom_pcie_2_1_0_ltssm_enable(struct qcom_pcie *pcie)
{
u32 val;
......@@ -541,8 +603,7 @@ static int qcom_pcie_init_1_0_0(struct qcom_pcie *pcie)
static int qcom_pcie_post_init_1_0_0(struct qcom_pcie *pcie)
{
/* change DBI base address */
writel(0, pcie->parf + PARF_DBI_BASE_ADDR);
qcom_pcie_configure_dbi_base(pcie);
if (IS_ENABLED(CONFIG_PCI_MSI)) {
u32 val = readl(pcie->parf + PARF_AXI_MSTR_WR_ADDR_HALT);
......@@ -629,8 +690,7 @@ static int qcom_pcie_post_init_2_3_2(struct qcom_pcie *pcie)
val &= ~PHY_TEST_PWR_DOWN;
writel(val, pcie->parf + PARF_PHY_CTRL);
/* change DBI base address */
writel(0, pcie->parf + PARF_DBI_BASE_ADDR);
qcom_pcie_configure_dbi_base(pcie);
/* MAC PHY_POWERDOWN MUX DISABLE */
val = readl(pcie->parf + PARF_SYS_CTRL);
......@@ -812,13 +872,11 @@ static int qcom_pcie_post_init_2_3_3(struct qcom_pcie *pcie)
u16 offset = dw_pcie_find_capability(pci, PCI_CAP_ID_EXP);
u32 val;
writel(SLV_ADDR_SPACE_SZ, pcie->parf + PARF_SLV_ADDR_SPACE_SIZE);
val = readl(pcie->parf + PARF_PHY_CTRL);
val &= ~PHY_TEST_PWR_DOWN;
writel(val, pcie->parf + PARF_PHY_CTRL);
writel(0, pcie->parf + PARF_DBI_BASE_ADDR);
qcom_pcie_configure_dbi_atu_base(pcie);
writel(MST_WAKEUP_EN | SLV_WAKEUP_EN | MSTR_ACLK_CGC_DIS
| SLV_ACLK_CGC_DIS | CORE_CLK_CGC_DIS |
......@@ -914,8 +972,7 @@ static int qcom_pcie_init_2_7_0(struct qcom_pcie *pcie)
val &= ~PHY_TEST_PWR_DOWN;
writel(val, pcie->parf + PARF_PHY_CTRL);
/* change DBI base address */
writel(0, pcie->parf + PARF_DBI_BASE_ADDR);
qcom_pcie_configure_dbi_atu_base(pcie);
/* MAC PHY_POWERDOWN MUX DISABLE */
val = readl(pcie->parf + PARF_SYS_CTRL);
......@@ -1124,14 +1181,11 @@ static int qcom_pcie_post_init_2_9_0(struct qcom_pcie *pcie)
u32 val;
int i;
writel(SLV_ADDR_SPACE_SZ,
pcie->parf + PARF_SLV_ADDR_SPACE_SIZE);
val = readl(pcie->parf + PARF_PHY_CTRL);
val &= ~PHY_TEST_PWR_DOWN;
writel(val, pcie->parf + PARF_PHY_CTRL);
writel(0, pcie->parf + PARF_DBI_BASE_ADDR);
qcom_pcie_configure_dbi_atu_base(pcie);
writel(DEVICE_TYPE_RC, pcie->parf + PARF_DEVICE_TYPE);
writel(BYPASS | MSTR_AXI_CLK_EN | AHB_CLK_EN,
......@@ -1489,6 +1543,29 @@ static void qcom_pcie_init_debugfs(struct qcom_pcie *pcie)
qcom_pcie_link_transition_count);
}
static irqreturn_t qcom_pcie_global_irq_thread(int irq, void *data)
{
struct qcom_pcie *pcie = data;
struct dw_pcie_rp *pp = &pcie->pci->pp;
struct device *dev = pcie->pci->dev;
u32 status = readl_relaxed(pcie->parf + PARF_INT_ALL_STATUS);
writel_relaxed(status, pcie->parf + PARF_INT_ALL_CLEAR);
if (FIELD_GET(PARF_INT_ALL_LINK_UP, status)) {
dev_dbg(dev, "Received Link up event. Starting enumeration!\n");
/* Rescan the bus to enumerate endpoint devices */
pci_lock_rescan_remove();
pci_rescan_bus(pp->bridge->bus);
pci_unlock_rescan_remove();
} else {
dev_WARN_ONCE(dev, 1, "Received unknown event. INT_STATUS: 0x%08x\n",
status);
}
return IRQ_HANDLED;
}
static int qcom_pcie_probe(struct platform_device *pdev)
{
const struct qcom_pcie_cfg *pcie_cfg;
......@@ -1499,7 +1576,8 @@ static int qcom_pcie_probe(struct platform_device *pdev)
struct dw_pcie_rp *pp;
struct resource *res;
struct dw_pcie *pci;
int ret;
int ret, irq;
char *name;
pcie_cfg = of_device_get_match_data(dev);
if (!pcie_cfg || !pcie_cfg->ops) {
......@@ -1620,6 +1698,27 @@ static int qcom_pcie_probe(struct platform_device *pdev)
goto err_phy_exit;
}
name = devm_kasprintf(dev, GFP_KERNEL, "qcom_pcie_global_irq%d",
pci_domain_nr(pp->bridge->bus));
if (!name) {
ret = -ENOMEM;
goto err_host_deinit;
}
irq = platform_get_irq_byname_optional(pdev, "global");
if (irq > 0) {
ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
qcom_pcie_global_irq_thread,
IRQF_ONESHOT, name, pcie);
if (ret) {
dev_err_probe(&pdev->dev, ret,
"Failed to request Global IRQ\n");
goto err_host_deinit;
}
writel_relaxed(PARF_INT_ALL_LINK_UP, pcie->parf + PARF_INT_ALL_MASK);
}
qcom_pcie_icc_opp_update(pcie);
if (pcie->mhi)
......@@ -1627,6 +1726,8 @@ static int qcom_pcie_probe(struct platform_device *pdev)
return 0;
err_host_deinit:
dw_pcie_host_deinit(pp);
err_phy_exit:
phy_exit(pcie->phy);
err_pm_runtime_put:
......
......@@ -141,10 +141,10 @@ static int rcar_gen4_pcie_start_link(struct dw_pcie *dw)
}
/*
* Require direct speed change with retrying here if the link_gen is
* PCIe Gen2 or higher.
* Require direct speed change with retrying here if the max_link_speed
* is PCIe Gen2 or higher.
*/
changes = min_not_zero(dw->link_gen, RCAR_MAX_LINK_SPEED) - 1;
changes = min_not_zero(dw->max_link_speed, RCAR_MAX_LINK_SPEED) - 1;
/*
* Since dw_pcie_setup_rc() sets it once, PCIe Gen2 will be trained.
......@@ -606,7 +606,12 @@ static int rcar_gen4_pcie_reg_test_bit(struct rcar_gen4_pcie *rcar,
static int rcar_gen4_pcie_download_phy_firmware(struct rcar_gen4_pcie *rcar)
{
/* The check_addr values are magical numbers in the datasheet */
const u32 check_addr[] = { 0x00101018, 0x00101118, 0x00101021, 0x00101121};
static const u32 check_addr[] = {
0x00101018,
0x00101118,
0x00101021,
0x00101121,
};
struct dw_pcie *dw = &rcar->dw;
const struct firmware *fw;
unsigned int i, timeout;
......
......@@ -233,7 +233,7 @@ static int spear13xx_pcie_probe(struct platform_device *pdev)
}
if (of_property_read_bool(np, "st,pcie-is-gen1"))
pci->link_gen = 1;
pci->max_link_speed = 1;
platform_set_drvdata(pdev, spear13xx_pcie);
......
......@@ -177,17 +177,12 @@
#define N_FTS_VAL 52
#define FTS_VAL 52
#define GEN3_EQ_CONTROL_OFF 0x8a8
#define GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC_SHIFT 8
#define GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC_MASK GENMASK(23, 8)
#define GEN3_EQ_CONTROL_OFF_FB_MODE_MASK GENMASK(3, 0)
#define PORT_LOGIC_AMBA_ERROR_RESPONSE_DEFAULT 0x8D0
#define AMBA_ERROR_RESPONSE_CRS_SHIFT 3
#define AMBA_ERROR_RESPONSE_CRS_MASK GENMASK(1, 0)
#define AMBA_ERROR_RESPONSE_CRS_OKAY 0
#define AMBA_ERROR_RESPONSE_CRS_OKAY_FFFFFFFF 1
#define AMBA_ERROR_RESPONSE_CRS_OKAY_FFFF0001 2
#define AMBA_ERROR_RESPONSE_RRS_SHIFT 3
#define AMBA_ERROR_RESPONSE_RRS_MASK GENMASK(1, 0)
#define AMBA_ERROR_RESPONSE_RRS_OKAY 0
#define AMBA_ERROR_RESPONSE_RRS_OKAY_FFFFFFFF 1
#define AMBA_ERROR_RESPONSE_RRS_OKAY_FFFF0001 2
#define MSIX_ADDR_MATCH_LOW_OFF 0x940
#define MSIX_ADDR_MATCH_LOW_OFF_EN BIT(0)
......@@ -861,9 +856,9 @@ static void config_gen3_gen4_eq_presets(struct tegra_pcie_dw *pcie)
dw_pcie_writel_dbi(pci, GEN3_RELATED_OFF, val);
val = dw_pcie_readl_dbi(pci, GEN3_EQ_CONTROL_OFF);
val &= ~GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC_MASK;
val |= (0x3ff << GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC_SHIFT);
val &= ~GEN3_EQ_CONTROL_OFF_FB_MODE_MASK;
val &= ~GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC;
val |= FIELD_PREP(GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC, 0x3ff);
val &= ~GEN3_EQ_CONTROL_OFF_FB_MODE;
dw_pcie_writel_dbi(pci, GEN3_EQ_CONTROL_OFF, val);
val = dw_pcie_readl_dbi(pci, GEN3_RELATED_OFF);
......@@ -872,10 +867,10 @@ static void config_gen3_gen4_eq_presets(struct tegra_pcie_dw *pcie)
dw_pcie_writel_dbi(pci, GEN3_RELATED_OFF, val);
val = dw_pcie_readl_dbi(pci, GEN3_EQ_CONTROL_OFF);
val &= ~GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC_MASK;
val |= (pcie->of_data->gen4_preset_vec <<
GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC_SHIFT);
val &= ~GEN3_EQ_CONTROL_OFF_FB_MODE_MASK;
val &= ~GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC;
val |= FIELD_PREP(GEN3_EQ_CONTROL_OFF_PSET_REQ_VEC,
pcie->of_data->gen4_preset_vec);
val &= ~GEN3_EQ_CONTROL_OFF_FB_MODE;
dw_pcie_writel_dbi(pci, GEN3_EQ_CONTROL_OFF, val);
val = dw_pcie_readl_dbi(pci, GEN3_RELATED_OFF);
......@@ -907,11 +902,11 @@ static int tegra_pcie_dw_host_init(struct dw_pcie_rp *pp)
dw_pcie_writel_dbi(pci, PCI_BASE_ADDRESS_0, 0);
/* Enable as 0xFFFF0001 response for CRS */
/* Enable as 0xFFFF0001 response for RRS */
val = dw_pcie_readl_dbi(pci, PORT_LOGIC_AMBA_ERROR_RESPONSE_DEFAULT);
val &= ~(AMBA_ERROR_RESPONSE_CRS_MASK << AMBA_ERROR_RESPONSE_CRS_SHIFT);
val |= (AMBA_ERROR_RESPONSE_CRS_OKAY_FFFF0001 <<
AMBA_ERROR_RESPONSE_CRS_SHIFT);
val &= ~(AMBA_ERROR_RESPONSE_RRS_MASK << AMBA_ERROR_RESPONSE_RRS_SHIFT);
val |= (AMBA_ERROR_RESPONSE_RRS_OKAY_FFFF0001 <<
AMBA_ERROR_RESPONSE_RRS_SHIFT);
dw_pcie_writel_dbi(pci, PORT_LOGIC_AMBA_ERROR_RESPONSE_DEFAULT, val);
/* Clear Slot Clock Configuration bit if SRNS configuration */
......
......@@ -360,8 +360,8 @@ static struct irq_chip mobiveil_msi_irq_chip = {
};
static struct msi_domain_info mobiveil_msi_domain_info = {
.flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_PCI_MSIX),
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_NO_AFFINITY | MSI_FLAG_PCI_MSIX,
.chip = &mobiveil_msi_irq_chip,
};
......@@ -378,16 +378,9 @@ static void mobiveil_compose_msi_msg(struct irq_data *data, struct msi_msg *msg)
(int)data->hwirq, msg->address_hi, msg->address_lo);
}
static int mobiveil_msi_set_affinity(struct irq_data *irq_data,
const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static struct irq_chip mobiveil_msi_bottom_irq_chip = {
.name = "Mobiveil MSI",
.irq_compose_msi_msg = mobiveil_compose_msi_msg,
.irq_set_affinity = mobiveil_msi_set_affinity,
};
static int mobiveil_irq_msi_domain_alloc(struct irq_domain *domain,
......
......@@ -50,7 +50,7 @@
#define PIO_COMPLETION_STATUS_MASK GENMASK(9, 7)
#define PIO_COMPLETION_STATUS_OK 0
#define PIO_COMPLETION_STATUS_UR 1
#define PIO_COMPLETION_STATUS_CRS 2
#define PIO_COMPLETION_STATUS_RRS 2
#define PIO_COMPLETION_STATUS_CA 4
#define PIO_NON_POSTED_REQ BIT(10)
#define PIO_ERR_STATUS BIT(11)
......@@ -262,7 +262,7 @@ enum {
#define MSI_IRQ_NUM 32
#define CFG_RD_CRS_VAL 0xffff0001
#define CFG_RD_RRS_VAL 0xffff0001
struct advk_pcie {
struct platform_device *pdev;
......@@ -649,7 +649,7 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie)
advk_pcie_train_link(pcie);
}
static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_crs, u32 *val)
static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_rrs, u32 *val)
{
struct device *dev = &pcie->pdev->dev;
u32 reg;
......@@ -669,7 +669,7 @@ static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_crs, u3
* 2) value Unsupported Request(1) of COMPLETION_STATUS(bit9:7) only
* means a PIO write error, and for PIO read it is successful with
* a read value of 0xFFFFFFFF.
* 3) value Completion Retry Status(CRS) of COMPLETION_STATUS(bit9:7)
* 3) value Config Request Retry Status(RRS) of COMPLETION_STATUS(bit9:7)
* only means a PIO write error, and for PIO read it is successful
* with a read value of 0xFFFF0001.
* 4) value Completer Abort (CA) of COMPLETION_STATUS(bit9:7) means
......@@ -694,10 +694,10 @@ static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_crs, u3
strcomp_status = "UR";
ret = -EOPNOTSUPP;
break;
case PIO_COMPLETION_STATUS_CRS:
if (allow_crs && val) {
/* PCIe r4.0, sec 2.3.2, says:
* If CRS Software Visibility is enabled:
case PIO_COMPLETION_STATUS_RRS:
if (allow_rrs && val) {
/* PCIe r6.0, sec 2.3.2, says:
* If Configuration RRS Software Visibility is enabled:
* For a Configuration Read Request that includes both
* bytes of the Vendor ID field of a device Function's
* Configuration Space Header, the Root Complex must
......@@ -706,22 +706,22 @@ static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_crs, u3
* all '1's for any additional bytes included in the
* request.
*
* So CRS in this case is not an error status.
* So RRS in this case is not an error status.
*/
*val = CFG_RD_CRS_VAL;
*val = CFG_RD_RRS_VAL;
strcomp_status = NULL;
ret = 0;
break;
}
/* PCIe r4.0, sec 2.3.2, says:
* If CRS Software Visibility is not enabled, the Root Complex
/* PCIe r6.0, sec 2.3.2, says:
* If RRS Software Visibility is not enabled, the Root Complex
* must re-issue the Configuration Request as a new Request.
* If CRS Software Visibility is enabled: For a Configuration
* If RRS Software Visibility is enabled: For a Configuration
* Write Request or for any other Configuration Read Request,
* the Root Complex must re-issue the Configuration Request as
* a new Request.
* A Root Complex implementation may choose to limit the number
* of Configuration Request/CRS Completion Status loops before
* of Configuration Request/RRS Completion Status loops before
* determining that something is wrong with the target of the
* Request and taking appropriate action, e.g., complete the
* Request to the host as a failed transaction.
......@@ -729,7 +729,7 @@ static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_crs, u3
* So return -EAGAIN and caller (pci-aardvark.c driver) will
* re-issue request again up to the PIO_RETRY_CNT retries.
*/
strcomp_status = "CRS";
strcomp_status = "RRS";
ret = -EAGAIN;
break;
case PIO_COMPLETION_STATUS_CA:
......@@ -920,8 +920,8 @@ advk_pci_bridge_emul_pcie_conf_write(struct pci_bridge_emul *bridge,
case PCI_EXP_RTCTL: {
u16 rootctl = le16_to_cpu(bridge->pcie_conf.rootctl);
/* Only emulation of PMEIE and CRSSVE bits is provided */
rootctl &= PCI_EXP_RTCTL_PMEIE | PCI_EXP_RTCTL_CRSSVE;
/* Only emulation of PMEIE and RRS_SVE bits is provided */
rootctl &= PCI_EXP_RTCTL_PMEIE | PCI_EXP_RTCTL_RRS_SVE;
bridge->pcie_conf.rootctl = cpu_to_le16(rootctl);
break;
}
......@@ -1075,7 +1075,7 @@ static int advk_sw_pci_bridge_init(struct advk_pcie *pcie)
bridge->pcie_conf.slotsta = cpu_to_le16(PCI_EXP_SLTSTA_PDS);
/* Indicates supports for Completion Retry Status */
bridge->pcie_conf.rootcap = cpu_to_le16(PCI_EXP_RTCAP_CRSVIS);
bridge->pcie_conf.rootcap = cpu_to_le16(PCI_EXP_RTCAP_RRS_SV);
bridge->subsystem_vendor_id = advk_readl(pcie, PCIE_CORE_SSDEV_ID_REG) & 0xffff;
bridge->subsystem_id = advk_readl(pcie, PCIE_CORE_SSDEV_ID_REG) >> 16;
......@@ -1141,7 +1141,7 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn,
{
struct advk_pcie *pcie = bus->sysdata;
int retry_count;
bool allow_crs;
bool allow_rrs;
u32 reg;
int ret;
......@@ -1153,16 +1153,16 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn,
size, val);
/*
* Completion Retry Status is possible to return only when reading all
* 4 bytes from PCI_VENDOR_ID and PCI_DEVICE_ID registers at once and
* CRSSVE flag on Root Bridge is enabled.
* Configuration Request Retry Status (RRS) is possible to return
* only when reading both bytes from PCI_VENDOR_ID at once and
* RRS_SVE flag on Root Port is enabled.
*/
allow_crs = (where == PCI_VENDOR_ID) && (size == 4) &&
allow_rrs = (where == PCI_VENDOR_ID) && (size >= 2) &&
(le16_to_cpu(pcie->bridge.pcie_conf.rootctl) &
PCI_EXP_RTCTL_CRSSVE);
PCI_EXP_RTCTL_RRS_SVE);
if (advk_pcie_pio_is_running(pcie))
goto try_crs;
goto try_rrs;
/* Program the control register */
reg = advk_readl(pcie, PIO_CTRL);
......@@ -1189,12 +1189,12 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn,
ret = advk_pcie_wait_pio(pcie);
if (ret < 0)
goto try_crs;
goto try_rrs;
retry_count += ret;
/* Check PIO status and get the read result */
ret = advk_pcie_check_pio_status(pcie, allow_crs, val);
ret = advk_pcie_check_pio_status(pcie, allow_rrs, val);
} while (ret == -EAGAIN && retry_count < PIO_RETRY_CNT);
if (ret < 0)
......@@ -1207,13 +1207,13 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn,
return PCIBIOS_SUCCESSFUL;
try_crs:
try_rrs:
/*
* If it is possible, return Completion Retry Status so that caller
* tries to issue the request again instead of failing.
* If it is possible, return Configuration Request Retry Status so
* that caller tries to issue the request again instead of failing.
*/
if (allow_crs) {
*val = CFG_RD_CRS_VAL;
if (allow_rrs) {
*val = CFG_RD_RRS_VAL;
return PCIBIOS_SUCCESSFUL;
}
......@@ -1304,12 +1304,6 @@ static void advk_msi_irq_compose_msi_msg(struct irq_data *data,
msg->data = data->hwirq;
}
static int advk_msi_set_affinity(struct irq_data *irq_data,
const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static void advk_msi_irq_mask(struct irq_data *d)
{
struct advk_pcie *pcie = d->domain->host_data;
......@@ -1353,7 +1347,6 @@ static void advk_msi_top_irq_unmask(struct irq_data *d)
static struct irq_chip advk_msi_bottom_irq_chip = {
.name = "MSI",
.irq_compose_msi_msg = advk_msi_irq_compose_msi_msg,
.irq_set_affinity = advk_msi_set_affinity,
.irq_mask = advk_msi_irq_mask,
.irq_unmask = advk_msi_irq_unmask,
};
......@@ -1451,7 +1444,8 @@ static struct irq_chip advk_msi_irq_chip = {
static struct msi_domain_info advk_msi_domain_info = {
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_MULTI_PCI_MSI | MSI_FLAG_PCI_MSIX,
MSI_FLAG_NO_AFFINITY | MSI_FLAG_MULTI_PCI_MSI |
MSI_FLAG_PCI_MSIX,
.chip = &advk_msi_irq_chip,
};
......
......@@ -1629,11 +1629,6 @@ static void tegra_msi_irq_unmask(struct irq_data *d)
spin_unlock_irqrestore(&msi->mask_lock, flags);
}
static int tegra_msi_set_affinity(struct irq_data *d, const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static void tegra_compose_msi_msg(struct irq_data *data, struct msi_msg *msg)
{
struct tegra_msi *msi = irq_data_get_irq_chip_data(data);
......@@ -1648,7 +1643,6 @@ static struct irq_chip tegra_msi_bottom_chip = {
.irq_ack = tegra_msi_irq_ack,
.irq_mask = tegra_msi_irq_mask,
.irq_unmask = tegra_msi_irq_unmask,
.irq_set_affinity = tegra_msi_set_affinity,
.irq_compose_msi_msg = tegra_compose_msi_msg,
};
......@@ -1697,8 +1691,8 @@ static const struct irq_domain_ops tegra_msi_domain_ops = {
};
static struct msi_domain_info tegra_msi_info = {
.flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_PCI_MSIX),
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_NO_AFFINITY | MSI_FLAG_PCI_MSIX,
.chip = &tegra_msi_top_chip,
};
......
......@@ -171,17 +171,17 @@ static int xgene_pcie_config_read32(struct pci_bus *bus, unsigned int devfn,
/*
* The v1 controller has a bug in its Configuration Request Retry
* Status (CRS) logic: when CRS Software Visibility is enabled and
* Status (RRS) logic: when RRS Software Visibility is enabled and
* we read the Vendor and Device ID of a non-existent device, the
* controller fabricates return data of 0xFFFF0001 ("device exists
* but is not ready") instead of 0xFFFFFFFF (PCI_ERROR_RESPONSE)
* ("device does not exist"). This causes the PCI core to retry
* the read until it times out. Avoid this by not claiming to
* support CRS SV.
* support RRS SV.
*/
if (pci_is_root_bus(bus) && (port->version == XGENE_PCIE_IP_VER_1) &&
((where & ~0x3) == XGENE_V1_PCI_EXP_CAP + PCI_EXP_RTCTL))
*val &= ~(PCI_EXP_RTCAP_CRSVIS << 16);
*val &= ~(PCI_EXP_RTCAP_RRS_SV << 16);
if (size <= 2)
*val = (*val >> (8 * (where & 3))) & ((1 << (size * 8)) - 1);
......
......@@ -81,8 +81,8 @@ static struct irq_chip altera_msi_irq_chip = {
};
static struct msi_domain_info altera_msi_domain_info = {
.flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_PCI_MSIX),
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_NO_AFFINITY | MSI_FLAG_PCI_MSIX,
.chip = &altera_msi_irq_chip,
};
......@@ -99,16 +99,9 @@ static void altera_compose_msi_msg(struct irq_data *data, struct msi_msg *msg)
(int)data->hwirq, msg->address_hi, msg->address_lo);
}
static int altera_msi_set_affinity(struct irq_data *irq_data,
const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static struct irq_chip altera_msi_bottom_irq_chip = {
.name = "Altera MSI",
.irq_compose_msi_msg = altera_compose_msi_msg,
.irq_set_affinity = altera_msi_set_affinity,
};
static int altera_irq_domain_alloc(struct irq_domain *domain, unsigned int virq,
......
......@@ -55,12 +55,11 @@
#define TLP_READ_TAG 0x1d
#define TLP_WRITE_TAG 0x10
#define RP_DEVFN 0
#define TLP_REQ_ID(bus, devfn) (((bus) << 8) | (devfn))
#define TLP_CFG_DW0(pcie, cfg) \
(((cfg) << 24) | \
TLP_PAYLOAD_SIZE)
#define TLP_CFG_DW1(pcie, tag, be) \
(((TLP_REQ_ID(pcie->root_bus_nr, RP_DEVFN)) << 16) | (tag << 8) | (be))
(((PCI_DEVID(pcie->root_bus_nr, RP_DEVFN)) << 16) | (tag << 8) | (be))
#define TLP_CFG_DW2(bus, devfn, offset) \
(((bus) << 24) | ((devfn) << 16) | (offset))
#define TLP_COMP_STATUS(s) (((s) >> 13) & 7)
......
This diff is collapsed.
......@@ -54,7 +54,7 @@
#define CFG_RD_SUCCESS 0
#define CFG_RD_UR 1
#define CFG_RD_CRS 2
#define CFG_RD_RRS 2
#define CFG_RD_CA 3
#define CFG_RETRY_STATUS 0xffff0001
#define CFG_RETRY_STATUS_TIMEOUT_US 500000 /* 500 milliseconds */
......@@ -485,31 +485,31 @@ static unsigned int iproc_pcie_cfg_retry(struct iproc_pcie *pcie,
u32 status;
/*
* As per PCIe spec r3.1, sec 2.3.2, CRS Software Visibility only
* As per PCIe r6.0, sec 2.3.2, Config RRS Software Visibility only
* affects config reads of the Vendor ID. For config writes or any
* other config reads, the Root may automatically reissue the
* configuration request again as a new request.
*
* For config reads, this hardware returns CFG_RETRY_STATUS data
* when it receives a CRS completion, regardless of the address of
* the read or the CRS Software Visibility Enable bit. As a
* when it receives a RRS completion, regardless of the address of
* the read or the RRS Software Visibility Enable bit. As a
* partial workaround for this, we retry in software any read that
* returns CFG_RETRY_STATUS.
*
* Note that a non-Vendor ID config register may have a value of
* CFG_RETRY_STATUS. If we read that, we can't distinguish it from
* a CRS completion, so we will incorrectly retry the read and
* a RRS completion, so we will incorrectly retry the read and
* eventually return the wrong data (0xffffffff).
*/
data = readl(cfg_data_p);
while (data == CFG_RETRY_STATUS && timeout--) {
/*
* CRS state is set in CFG_RD status register
* RRS state is set in CFG_RD status register
* This will handle the case where CFG_RETRY_STATUS is
* valid config data.
*/
status = iproc_pcie_read_reg(pcie, IPROC_PCIE_CFG_RD_STATUS);
if (status != CFG_RD_CRS)
if (status != CFG_RD_RRS)
return data;
udelay(1);
......@@ -556,8 +556,8 @@ static void iproc_pcie_fix_cap(struct iproc_pcie *pcie, int where, u32 *val)
break;
case IPROC_PCI_EXP_CAP + PCI_EXP_RTCTL:
/* Don't advertise CRS SV support */
*val &= ~(PCI_EXP_RTCAP_CRSVIS << 16);
/* Don't advertise RRS SV support */
*val &= ~(PCI_EXP_RTCAP_RRS_SV << 16);
break;
default:
......
This diff is collapsed.
......@@ -211,7 +211,6 @@ struct mtk_pcie_port {
* @base: IO mapped register base
* @cfg: IO mapped register map for PCIe config
* @free_ck: free-run reference clock
* @mem: non-prefetchable memory resource
* @ports: pointer to PCIe port information
* @soc: pointer to SoC-dependent operations
*/
......@@ -407,12 +406,6 @@ static void mtk_compose_msi_msg(struct irq_data *data, struct msi_msg *msg)
(int)data->hwirq, msg->address_hi, msg->address_lo);
}
static int mtk_msi_set_affinity(struct irq_data *irq_data,
const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static void mtk_msi_ack_irq(struct irq_data *data)
{
struct mtk_pcie_port *port = irq_data_get_irq_chip_data(data);
......@@ -424,7 +417,6 @@ static void mtk_msi_ack_irq(struct irq_data *data)
static struct irq_chip mtk_msi_bottom_irq_chip = {
.name = "MTK MSI",
.irq_compose_msi_msg = mtk_compose_msi_msg,
.irq_set_affinity = mtk_msi_set_affinity,
.irq_ack = mtk_msi_ack_irq,
};
......@@ -486,8 +478,8 @@ static struct irq_chip mtk_msi_irq_chip = {
};
static struct msi_domain_info mtk_msi_domain_info = {
.flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_PCI_MSIX),
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_NO_AFFINITY | MSI_FLAG_PCI_MSIX,
.chip = &mtk_msi_irq_chip,
};
......
......@@ -658,11 +658,6 @@ static void rcar_msi_irq_unmask(struct irq_data *d)
spin_unlock_irqrestore(&msi->mask_lock, flags);
}
static int rcar_msi_set_affinity(struct irq_data *d, const struct cpumask *mask, bool force)
{
return -EINVAL;
}
static void rcar_compose_msi_msg(struct irq_data *data, struct msi_msg *msg)
{
struct rcar_msi *msi = irq_data_get_irq_chip_data(data);
......@@ -678,7 +673,6 @@ static struct irq_chip rcar_msi_bottom_chip = {
.irq_ack = rcar_msi_irq_ack,
.irq_mask = rcar_msi_irq_mask,
.irq_unmask = rcar_msi_irq_unmask,
.irq_set_affinity = rcar_msi_set_affinity,
.irq_compose_msi_msg = rcar_compose_msi_msg,
};
......@@ -725,8 +719,8 @@ static const struct irq_domain_ops rcar_msi_domain_ops = {
};
static struct msi_domain_info rcar_msi_info = {
.flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_MULTI_PCI_MSI),
.flags = MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS |
MSI_FLAG_NO_AFFINITY | MSI_FLAG_MULTI_PCI_MSI,
.chip = &rcar_msi_top_chip,
};
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
......@@ -51,11 +51,6 @@ ibmphp:
shpchp:
* There is only a single implementation of struct hpc_ops. Can the struct be
removed and its functions invoked directly? This has already been done in
pciehp with commit 82a9e79ef132 ("PCI: pciehp: remove hpc_ops"). Clarify
if there was a specific reason not to apply the same change to shpchp.
* The hardirq handler shpc_isr() queues events on a workqueue. It can be
simplified by converting it to threaded IRQ handling. Use pciehp as a
template.
......@@ -328,7 +328,7 @@ get_slot_mapping(struct pci_bus *bus, u8 bus_num, u8 dev_num, u8 *slot)
} else {
/* Did not get a match on the target PCI device. Check
* if the current IRQ table entry is a PCI-to-PCI
* bridge device. If so, and it's secondary bus
* bridge device. If so, and its secondary bus
* matches the bus number for the target device, I need
* to save the bridge's slot number. If I can not find
* an entry for the target device, I will have to
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment