Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'phy-for-5.14_v2' of git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux-phy into char-misc-next

Vinod writes:

phy-for-5.14 version 2

- Updates:
- Yaml conversion for renesas,rcar-gen3 pcie phy and
rockchip-usb-phy bindings
- Support for devm_phy_get() taking NULL phy name

- New support:
- PCIe phy for Qualcomm IPQ60xx
- PCIe phy for Qualcomm SDX55
- USB phy for RK3308
- CAN transceivers phy for TI TCAN104x
- Innosilicon-based CSI dphy for rockchip

* tag 'phy-for-5.14_v2' of git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux-phy: (36 commits)
phy: Revert "phy: ralink: Kconfig: convert mt7621-pci-phy into 'bool'"
phy: ti: dm816x: Fix the error handling path in 'dm816x_usb_phy_probe()
phy: uniphier-pcie: Fix updating phy parameters
phy/rockchip: add Innosilicon-based CSI dphy
dt-bindings: phy: add yaml binding for rockchip-inno-csi-dphy
phy: rockchip: remove redundant initialization of pointer cfg
phy: phy-can-transceiver: Add support for generic CAN transceiver driver
dt-bindings: phy: Add binding for TI TCAN104x CAN transceivers
phy: core: Reword the comment specifying the units of max_link_rate to be Mbps
phy: phy-mtk-hdmi: Remove redundant dev_err call in mtk_hdmi_phy_probe()
phy: phy-mtk-mipi-dsi: Remove redundant dev_err call in mtk_mipi_tx_probe()
phy: phy-mmp3-hsic: Remove redundant dev_err call in mmp3_hsic_phy_probe()
phy: bcm-ns-usb3: Remove redundant dev_err call in bcm_ns_usb3_mdio_probe()
MAINTAINERS: update marvell,armada-3700-utmi-phy.yaml reference
phy: phy-twl4030-usb: use DEVICE_ATTR_RO macro
dt-bindings: phy: convert rockchip-usb-phy.txt to YAML
phy: phy-rockchip-inno-usb2: add support for RK3308 USB phy
dt-bindings: phy: rockchip-inno-usb2: add compatible for rk3308 USB phy
phy: stm32: manage optional vbus regulator on phy_power_on/off
dt-bindings: phy: add vbus-supply optional property to phy-stm32-usbphyc
...

+1601 -136
+24
Documentation/devicetree/bindings/pci/qcom,pcie.txt
··· 14 14 - "qcom,pcie-qcs404" for qcs404 15 15 - "qcom,pcie-sdm845" for sdm845 16 16 - "qcom,pcie-sm8250" for sm8250 17 + - "qcom,pcie-ipq6018" for ipq6018 17 18 18 19 - reg: 19 20 Usage: required ··· 125 124 - "aux" Auxiliary clock 126 125 127 126 - clock-names: 127 + Usage: required for ipq6018 128 + Value type: <stringlist> 129 + Definition: Should contain the following entries 130 + - "iface" PCIe to SysNOC BIU clock 131 + - "axi_m" AXI Master clock 132 + - "axi_s" AXI Slave clock 133 + - "axi_bridge" AXI bridge clock 134 + - "rchng" 135 + 136 + - clock-names: 128 137 Usage: required for qcs404 129 138 Value type: <stringlist> 130 139 Definition: Should contain the following entries ··· 219 208 - "axi_s" AXI Slave reset 220 209 - "ahb" AHB Reset 221 210 - "axi_m_sticky" AXI Master Sticky reset 211 + 212 + - reset-names: 213 + Usage: required for ipq6018 214 + Value type: <stringlist> 215 + Definition: Should contain the following entries 216 + - "pipe" PIPE reset 217 + - "sleep" Sleep reset 218 + - "sticky" Core Sticky reset 219 + - "axi_m" AXI Master reset 220 + - "axi_s" AXI Slave reset 221 + - "ahb" AHB Reset 222 + - "axi_m_sticky" AXI Master Sticky reset 223 + - "axi_s_sticky" AXI Slave Sticky reset 222 224 223 225 - reset-names: 224 226 Usage: required for qcs404
+5
Documentation/devicetree/bindings/phy/mediatek,mt7621-pci-phy.yaml
··· 16 16 reg: 17 17 maxItems: 1 18 18 19 + clocks: 20 + maxItems: 1 21 + 19 22 "#phy-cells": 20 23 const: 1 21 24 description: selects if the phy is dual-ported ··· 26 23 required: 27 24 - compatible 28 25 - reg 26 + - clocks 29 27 - "#phy-cells" 30 28 31 29 additionalProperties: false ··· 36 32 pcie0_phy: pcie-phy@1e149000 { 37 33 compatible = "mediatek,mt7621-pci-phy"; 38 34 reg = <0x1e149000 0x0700>; 35 + clocks = <&sysc 0>; 39 36 #phy-cells = <1>; 40 37 };
+1
Documentation/devicetree/bindings/phy/phy-rockchip-inno-usb2.yaml
··· 14 14 enum: 15 15 - rockchip,px30-usb2phy 16 16 - rockchip,rk3228-usb2phy 17 + - rockchip,rk3308-usb2phy 17 18 - rockchip,rk3328-usb2phy 18 19 - rockchip,rk3366-usb2phy 19 20 - rockchip,rk3399-usb2phy
+11
Documentation/devicetree/bindings/phy/phy-stm32-usbphyc.yaml
··· 74 74 "#phy-cells": 75 75 enum: [ 0x0, 0x1 ] 76 76 77 + connector: 78 + type: object 79 + allOf: 80 + - $ref: ../connector/usb-connector.yaml 81 + properties: 82 + vbus-supply: true 83 + 77 84 allOf: 78 85 - if: 79 86 properties: ··· 137 130 reg = <0>; 138 131 phy-supply = <&vdd_usb>; 139 132 #phy-cells = <0>; 133 + connector { 134 + compatible = "usb-a-connector"; 135 + vbus-supply = <&vbus_sw>; 136 + }; 140 137 }; 141 138 142 139 usbphyc_port1: usb-phy@1 {
+27
Documentation/devicetree/bindings/phy/qcom,qmp-phy.yaml
··· 17 17 properties: 18 18 compatible: 19 19 enum: 20 + - qcom,ipq6018-qmp-pcie-phy 20 21 - qcom,ipq8074-qmp-pcie-phy 21 22 - qcom,ipq8074-qmp-usb3-phy 22 23 - qcom,msm8996-qmp-pcie-phy ··· 46 45 - qcom,sm8350-qmp-ufs-phy 47 46 - qcom,sm8350-qmp-usb3-phy 48 47 - qcom,sm8350-qmp-usb3-uni-phy 48 + - qcom,sdx55-qmp-pcie-phy 49 49 - qcom,sdx55-qmp-usb3-uni-phy 50 50 51 51 reg: ··· 303 301 compatible: 304 302 contains: 305 303 enum: 304 + - qcom,ipq6018-qmp-pcie-phy 305 + then: 306 + properties: 307 + clocks: 308 + items: 309 + - description: Phy aux clock. 310 + - description: Phy config clock. 311 + clock-names: 312 + items: 313 + - const: aux 314 + - const: cfg_ahb 315 + resets: 316 + items: 317 + - description: reset of phy block. 318 + - description: phy common block reset. 319 + reset-names: 320 + items: 321 + - const: phy 322 + - const: common 323 + - if: 324 + properties: 325 + compatible: 326 + contains: 327 + enum: 306 328 - qcom,sdm845-qhp-pcie-phy 307 329 - qcom,sdm845-qmp-pcie-phy 330 + - qcom,sdx55-qmp-pcie-phy 308 331 - qcom,sm8250-qmp-gen3x1-pcie-phy 309 332 - qcom,sm8250-qmp-gen3x2-pcie-phy 310 333 - qcom,sm8250-qmp-modem-pcie-phy
-24
Documentation/devicetree/bindings/phy/rcar-gen3-phy-pcie.txt
··· 1 - * Renesas R-Car generation 3 PCIe PHY 2 - 3 - This file provides information on what the device node for the R-Car 4 - generation 3 PCIe PHY contains. 5 - 6 - Required properties: 7 - - compatible: "renesas,r8a77980-pcie-phy" if the device is a part of the 8 - R8A77980 SoC. 9 - - reg: offset and length of the register block. 10 - - clocks: clock phandle and specifier pair. 11 - - power-domains: power domain phandle and specifier pair. 12 - - resets: reset phandle and specifier pair. 13 - - #phy-cells: see phy-bindings.txt in the same directory, must be <0>. 14 - 15 - Example (R-Car V3H): 16 - 17 - pcie-phy@e65d0000 { 18 - compatible = "renesas,r8a77980-pcie-phy"; 19 - reg = <0 0xe65d0000 0 0x8000>; 20 - #phy-cells = <0>; 21 - clocks = <&cpg CPG_MOD 319>; 22 - power-domains = <&sysc 32>; 23 - resets = <&cpg 319>; 24 - };
+53
Documentation/devicetree/bindings/phy/renesas,rcar-gen3-pcie-phy.yaml
··· 1 + # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) 2 + %YAML 1.2 3 + --- 4 + $id: http://devicetree.org/schemas/phy/renesas,rcar-gen3-pcie-phy.yaml# 5 + $schema: http://devicetree.org/meta-schemas/core.yaml# 6 + 7 + title: Renesas R-Car Generation 3 PCIe PHY 8 + 9 + maintainers: 10 + - Sergei Shtylyov <sergei.shtylyov@gmail.com> 11 + 12 + properties: 13 + compatible: 14 + const: renesas,r8a77980-pcie-phy 15 + 16 + reg: 17 + maxItems: 1 18 + 19 + clocks: 20 + maxItems: 1 21 + 22 + power-domains: 23 + maxItems: 1 24 + 25 + resets: 26 + maxItems: 1 27 + 28 + '#phy-cells': 29 + const: 0 30 + 31 + required: 32 + - compatible 33 + - reg 34 + - clocks 35 + - power-domains 36 + - resets 37 + - '#phy-cells' 38 + 39 + additionalProperties: false 40 + 41 + examples: 42 + - | 43 + #include <dt-bindings/clock/r8a77980-cpg-mssr.h> 44 + #include <dt-bindings/power/r8a77980-sysc.h> 45 + 46 + pcie-phy@e65d0000 { 47 + compatible = "renesas,r8a77980-pcie-phy"; 48 + reg = <0xe65d0000 0x8000>; 49 + #phy-cells = <0>; 50 + clocks = <&cpg CPG_MOD 319>; 51 + power-domains = <&sysc R8A77980_PD_ALWAYS_ON>; 52 + resets = <&cpg 319>; 53 + };
+79
Documentation/devicetree/bindings/phy/rockchip-inno-csi-dphy.yaml
··· 1 + # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) 2 + %YAML 1.2 3 + --- 4 + $id: http://devicetree.org/schemas/phy/rockchip-inno-csi-dphy.yaml# 5 + $schema: http://devicetree.org/meta-schemas/core.yaml# 6 + 7 + title: Rockchip SoC MIPI RX0 D-PHY Device Tree Bindings 8 + 9 + maintainers: 10 + - Heiko Stuebner <heiko@sntech.de> 11 + 12 + description: | 13 + The Rockchip SoC has a MIPI CSI D-PHY based on an Innosilicon IP wich 14 + connects to the ISP1 (Image Signal Processing unit v1.0) for CSI cameras. 15 + 16 + properties: 17 + compatible: 18 + enum: 19 + - rockchip,px30-csi-dphy 20 + - rockchip,rk1808-csi-dphy 21 + - rockchip,rk3326-csi-dphy 22 + - rockchip,rk3368-csi-dphy 23 + 24 + reg: 25 + maxItems: 1 26 + 27 + clocks: 28 + maxItems: 1 29 + 30 + clock-names: 31 + const: pclk 32 + 33 + '#phy-cells': 34 + const: 0 35 + 36 + power-domains: 37 + description: Video in/out power domain. 38 + maxItems: 1 39 + 40 + resets: 41 + items: 42 + - description: exclusive PHY reset line 43 + 44 + reset-names: 45 + items: 46 + - const: apb 47 + 48 + rockchip,grf: 49 + $ref: /schemas/types.yaml#/definitions/phandle 50 + description: 51 + Some additional phy settings are access through GRF regs. 52 + 53 + required: 54 + - compatible 55 + - reg 56 + - clocks 57 + - clock-names 58 + - '#phy-cells' 59 + - power-domains 60 + - resets 61 + - reset-names 62 + - rockchip,grf 63 + 64 + additionalProperties: false 65 + 66 + examples: 67 + - | 68 + 69 + csi_dphy: phy@ff2f0000 { 70 + compatible = "rockchip,px30-csi-dphy"; 71 + reg = <0xff2f0000 0x4000>; 72 + clocks = <&cru 1>; 73 + clock-names = "pclk"; 74 + #phy-cells = <0>; 75 + power-domains = <&power 1>; 76 + resets = <&cru 1>; 77 + reset-names = "apb"; 78 + rockchip,grf = <&grf>; 79 + };
-52
Documentation/devicetree/bindings/phy/rockchip-usb-phy.txt
··· 1 - ROCKCHIP USB2 PHY 2 - 3 - Required properties: 4 - - compatible: matching the soc type, one of 5 - "rockchip,rk3066a-usb-phy" 6 - "rockchip,rk3188-usb-phy" 7 - "rockchip,rk3288-usb-phy" 8 - - #address-cells: should be 1 9 - - #size-cells: should be 0 10 - 11 - Deprecated properties: 12 - - rockchip,grf : phandle to the syscon managing the "general 13 - register files" - phy should be a child of the GRF instead 14 - 15 - Sub-nodes: 16 - Each PHY should be represented as a sub-node. 17 - 18 - Sub-nodes 19 - required properties: 20 - - #phy-cells: should be 0 21 - - reg: PHY configure reg address offset in GRF 22 - "0x320" - for PHY attach to OTG controller 23 - "0x334" - for PHY attach to HOST0 controller 24 - "0x348" - for PHY attach to HOST1 controller 25 - 26 - Optional Properties: 27 - - clocks : phandle + clock specifier for the phy clocks 28 - - clock-names: string, clock name, must be "phyclk" 29 - - #clock-cells: for users of the phy-pll, should be 0 30 - - reset-names: Only allow the following entries: 31 - - phy-reset 32 - - resets: Must contain an entry for each entry in reset-names. 33 - - vbus-supply: power-supply phandle for vbus power source 34 - 35 - Example: 36 - 37 - grf: syscon@ff770000 { 38 - compatible = "rockchip,rk3288-grf", "syscon", "simple-mfd"; 39 - 40 - ... 41 - 42 - usbphy: phy { 43 - compatible = "rockchip,rk3288-usb-phy"; 44 - #address-cells = <1>; 45 - #size-cells = <0>; 46 - 47 - usbphy0: usb-phy0 { 48 - #phy-cells = <0>; 49 - reg = <0x320>; 50 - }; 51 - }; 52 - };
+81
Documentation/devicetree/bindings/phy/rockchip-usb-phy.yaml
··· 1 + # SPDX-License-Identifier: GPL-2.0 2 + %YAML 1.2 3 + --- 4 + $id: http://devicetree.org/schemas/phy/rockchip-usb-phy.yaml# 5 + $schema: http://devicetree.org/meta-schemas/core.yaml# 6 + 7 + title: Rockchip USB2.0 phy 8 + 9 + maintainers: 10 + - Heiko Stuebner <heiko@sntech.de> 11 + 12 + properties: 13 + compatible: 14 + oneOf: 15 + - const: rockchip,rk3288-usb-phy 16 + - items: 17 + - enum: 18 + - rockchip,rk3066a-usb-phy 19 + - rockchip,rk3188-usb-phy 20 + - const: rockchip,rk3288-usb-phy 21 + 22 + "#address-cells": 23 + const: 1 24 + 25 + "#size-cells": 26 + const: 0 27 + 28 + required: 29 + - compatible 30 + - "#address-cells" 31 + - "#size-cells" 32 + 33 + additionalProperties: false 34 + 35 + patternProperties: 36 + "usb-phy@[0-9a-f]+$": 37 + type: object 38 + 39 + properties: 40 + reg: 41 + maxItems: 1 42 + 43 + "#phy-cells": 44 + const: 0 45 + 46 + clocks: 47 + maxItems: 1 48 + 49 + clock-names: 50 + const: phyclk 51 + 52 + "#clock-cells": 53 + const: 0 54 + 55 + resets: 56 + maxItems: 1 57 + 58 + reset-names: 59 + const: phy-reset 60 + 61 + vbus-supply: 62 + description: phandle for vbus power source 63 + 64 + required: 65 + - reg 66 + - "#phy-cells" 67 + 68 + additionalProperties: false 69 + 70 + examples: 71 + - | 72 + usbphy: usbphy { 73 + compatible = "rockchip,rk3288-usb-phy"; 74 + #address-cells = <1>; 75 + #size-cells = <0>; 76 + 77 + usbphy0: usb-phy@320 { 78 + reg = <0x320>; 79 + #phy-cells = <0>; 80 + }; 81 + };
+56
Documentation/devicetree/bindings/phy/ti,tcan104x-can.yaml
··· 1 + # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) 2 + %YAML 1.2 3 + --- 4 + $id: "http://devicetree.org/schemas/phy/ti,tcan104x-can.yaml#" 5 + $schema: "http://devicetree.org/meta-schemas/core.yaml#" 6 + 7 + title: TCAN104x CAN TRANSCEIVER PHY 8 + 9 + maintainers: 10 + - Aswath Govindraju <a-govindraju@ti.com> 11 + 12 + properties: 13 + $nodename: 14 + pattern: "^can-phy" 15 + 16 + compatible: 17 + enum: 18 + - ti,tcan1042 19 + - ti,tcan1043 20 + 21 + '#phy-cells': 22 + const: 0 23 + 24 + standby-gpios: 25 + description: 26 + gpio node to toggle standby signal on transceiver 27 + maxItems: 1 28 + 29 + enable-gpios: 30 + description: 31 + gpio node to toggle enable signal on transceiver 32 + maxItems: 1 33 + 34 + max-bitrate: 35 + $ref: /schemas/types.yaml#/definitions/uint32 36 + description: 37 + max bit rate supported in bps 38 + minimum: 1 39 + 40 + required: 41 + - compatible 42 + - '#phy-cells' 43 + 44 + additionalProperties: false 45 + 46 + examples: 47 + - | 48 + #include <dt-bindings/gpio/gpio.h> 49 + 50 + transceiver1: can-phy { 51 + compatible = "ti,tcan1043"; 52 + #phy-cells = <0>; 53 + max-bitrate = <5000000>; 54 + standby-gpios = <&wakeup_gpio1 16 GPIO_ACTIVE_LOW>; 55 + enable-gpios = <&main_gpio1 67 GPIO_ACTIVE_HIGH>; 56 + };
+3 -1
MAINTAINERS
··· 4041 4041 T: git git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can.git 4042 4042 T: git git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can-next.git 4043 4043 F: Documentation/devicetree/bindings/net/can/ 4044 + F: Documentation/devicetree/bindings/phy/ti,tcan104x-can.yaml 4044 4045 F: drivers/net/can/ 4046 + F: drivers/phy/phy-can-transceiver.c 4045 4047 F: include/linux/can/bittiming.h 4046 4048 F: include/linux/can/dev.h 4047 4049 F: include/linux/can/led.h ··· 10899 10897 M: Miquel Raynal <miquel.raynal@bootlin.com> 10900 10898 S: Maintained 10901 10899 F: Documentation/devicetree/bindings/phy/phy-mvebu-comphy.txt 10902 - F: Documentation/devicetree/bindings/phy/phy-mvebu-utmi.txt 10900 + F: Documentation/devicetree/bindings/phy/marvell,armada-3700-utmi-phy.yaml 10903 10901 F: drivers/phy/marvell/phy-mvebu-a3700-comphy.c 10904 10902 F: drivers/phy/marvell/phy-mvebu-a3700-utmi.c 10905 10903
+9
drivers/phy/Kconfig
··· 61 61 interface to interact with USB GEN-II and USB 3.x PHY that is part 62 62 of the Intel network SOC. 63 63 64 + config PHY_CAN_TRANSCEIVER 65 + tristate "CAN transceiver PHY" 66 + select GENERIC_PHY 67 + help 68 + This option enables support for CAN transceivers as a PHY. This 69 + driver provides function for putting the transceivers in various 70 + functional modes using gpios and sets the attribute max link 71 + rate, for CAN drivers. 72 + 64 73 source "drivers/phy/allwinner/Kconfig" 65 74 source "drivers/phy/amlogic/Kconfig" 66 75 source "drivers/phy/broadcom/Kconfig"
+1
drivers/phy/Makefile
··· 5 5 6 6 obj-$(CONFIG_GENERIC_PHY) += phy-core.o 7 7 obj-$(CONFIG_GENERIC_PHY_MIPI_DPHY) += phy-core-mipi-dphy.o 8 + obj-$(CONFIG_PHY_CAN_TRANSCEIVER) += phy-can-transceiver.o 8 9 obj-$(CONFIG_PHY_LPC18XX_USB_OTG) += phy-lpc18xx-usb-otg.o 9 10 obj-$(CONFIG_PHY_XGENE) += phy-xgene.o 10 11 obj-$(CONFIG_PHY_PISTACHIO_USB) += phy-pistachio-usb.o
+1 -3
drivers/phy/broadcom/phy-bcm-ns-usb3.c
··· 215 215 return err; 216 216 217 217 usb3->dmp = devm_ioremap_resource(dev, &res); 218 - if (IS_ERR(usb3->dmp)) { 219 - dev_err(dev, "Failed to map DMP regs\n"); 218 + if (IS_ERR(usb3->dmp)) 220 219 return PTR_ERR(usb3->dmp); 221 - } 222 220 223 221 usb3->phy = devm_phy_create(dev, NULL, &ops); 224 222 if (IS_ERR(usb3->phy)) {
+1 -3
drivers/phy/marvell/phy-mmp3-hsic.c
··· 47 47 48 48 resource = platform_get_resource(pdev, IORESOURCE_MEM, 0); 49 49 base = devm_ioremap_resource(dev, resource); 50 - if (IS_ERR(base)) { 51 - dev_err(dev, "failed to remap PHY regs\n"); 50 + if (IS_ERR(base)) 52 51 return PTR_ERR(base); 53 - } 54 52 55 53 phy = devm_phy_create(dev, NULL, &mmp3_hsic_phy_ops); 56 54 if (IS_ERR(phy)) {
+1 -3
drivers/phy/mediatek/phy-mtk-hdmi.c
··· 119 119 mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); 120 120 hdmi_phy->regs = devm_ioremap_resource(dev, mem); 121 121 if (IS_ERR(hdmi_phy->regs)) { 122 - ret = PTR_ERR(hdmi_phy->regs); 123 - dev_err(dev, "Failed to get memory resource: %d\n", ret); 124 - return ret; 122 + return PTR_ERR(hdmi_phy->regs); 125 123 } 126 124 127 125 ref_clk = devm_clk_get(dev, "pll_ref");
+1 -3
drivers/phy/mediatek/phy-mtk-mipi-dsi.c
··· 151 151 mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); 152 152 mipi_tx->regs = devm_ioremap_resource(dev, mem); 153 153 if (IS_ERR(mipi_tx->regs)) { 154 - ret = PTR_ERR(mipi_tx->regs); 155 - dev_err(dev, "Failed to get memory resource: %d\n", ret); 156 - return ret; 154 + return PTR_ERR(mipi_tx->regs); 157 155 } 158 156 159 157 ref_clk = devm_clk_get(dev, NULL);
+146
drivers/phy/phy-can-transceiver.c
··· 1 + // SPDX-License-Identifier: GPL-2.0 2 + /* 3 + * phy-can-transceiver.c - phy driver for CAN transceivers 4 + * 5 + * Copyright (C) 2021 Texas Instruments Incorporated - https://www.ti.com 6 + * 7 + */ 8 + #include<linux/phy/phy.h> 9 + #include<linux/platform_device.h> 10 + #include<linux/module.h> 11 + #include<linux/gpio.h> 12 + #include<linux/gpio/consumer.h> 13 + 14 + struct can_transceiver_data { 15 + u32 flags; 16 + #define CAN_TRANSCEIVER_STB_PRESENT BIT(0) 17 + #define CAN_TRANSCEIVER_EN_PRESENT BIT(1) 18 + }; 19 + 20 + struct can_transceiver_phy { 21 + struct phy *generic_phy; 22 + struct gpio_desc *standby_gpio; 23 + struct gpio_desc *enable_gpio; 24 + }; 25 + 26 + /* Power on function */ 27 + static int can_transceiver_phy_power_on(struct phy *phy) 28 + { 29 + struct can_transceiver_phy *can_transceiver_phy = phy_get_drvdata(phy); 30 + 31 + if (can_transceiver_phy->standby_gpio) 32 + gpiod_set_value_cansleep(can_transceiver_phy->standby_gpio, 0); 33 + if (can_transceiver_phy->enable_gpio) 34 + gpiod_set_value_cansleep(can_transceiver_phy->enable_gpio, 1); 35 + 36 + return 0; 37 + } 38 + 39 + /* Power off function */ 40 + static int can_transceiver_phy_power_off(struct phy *phy) 41 + { 42 + struct can_transceiver_phy *can_transceiver_phy = phy_get_drvdata(phy); 43 + 44 + if (can_transceiver_phy->standby_gpio) 45 + gpiod_set_value_cansleep(can_transceiver_phy->standby_gpio, 1); 46 + if (can_transceiver_phy->enable_gpio) 47 + gpiod_set_value_cansleep(can_transceiver_phy->enable_gpio, 0); 48 + 49 + return 0; 50 + } 51 + 52 + static const struct phy_ops can_transceiver_phy_ops = { 53 + .power_on = can_transceiver_phy_power_on, 54 + .power_off = can_transceiver_phy_power_off, 55 + .owner = THIS_MODULE, 56 + }; 57 + 58 + static const struct can_transceiver_data tcan1042_drvdata = { 59 + .flags = CAN_TRANSCEIVER_STB_PRESENT, 60 + }; 61 + 62 + static const struct can_transceiver_data tcan1043_drvdata = { 63 + .flags = CAN_TRANSCEIVER_STB_PRESENT | CAN_TRANSCEIVER_EN_PRESENT, 64 + }; 65 + 66 + static const struct of_device_id can_transceiver_phy_ids[] = { 67 + { 68 + .compatible = "ti,tcan1042", 69 + .data = &tcan1042_drvdata 70 + }, 71 + { 72 + .compatible = "ti,tcan1043", 73 + .data = &tcan1043_drvdata 74 + }, 75 + { } 76 + }; 77 + MODULE_DEVICE_TABLE(of, can_transceiver_phy_ids); 78 + 79 + static int can_transceiver_phy_probe(struct platform_device *pdev) 80 + { 81 + struct phy_provider *phy_provider; 82 + struct device *dev = &pdev->dev; 83 + struct can_transceiver_phy *can_transceiver_phy; 84 + const struct can_transceiver_data *drvdata; 85 + const struct of_device_id *match; 86 + struct phy *phy; 87 + struct gpio_desc *standby_gpio; 88 + struct gpio_desc *enable_gpio; 89 + u32 max_bitrate = 0; 90 + 91 + can_transceiver_phy = devm_kzalloc(dev, sizeof(struct can_transceiver_phy), GFP_KERNEL); 92 + if (!can_transceiver_phy) 93 + return -ENOMEM; 94 + 95 + match = of_match_node(can_transceiver_phy_ids, pdev->dev.of_node); 96 + drvdata = match->data; 97 + 98 + phy = devm_phy_create(dev, dev->of_node, 99 + &can_transceiver_phy_ops); 100 + if (IS_ERR(phy)) { 101 + dev_err(dev, "failed to create can transceiver phy\n"); 102 + return PTR_ERR(phy); 103 + } 104 + 105 + device_property_read_u32(dev, "max-bitrate", &max_bitrate); 106 + if (!max_bitrate) 107 + dev_warn(dev, "Invalid value for transceiver max bitrate. Ignoring bitrate limit\n"); 108 + phy->attrs.max_link_rate = max_bitrate; 109 + 110 + can_transceiver_phy->generic_phy = phy; 111 + 112 + if (drvdata->flags & CAN_TRANSCEIVER_STB_PRESENT) { 113 + standby_gpio = devm_gpiod_get(dev, "standby", GPIOD_OUT_HIGH); 114 + if (IS_ERR(standby_gpio)) 115 + return PTR_ERR(standby_gpio); 116 + can_transceiver_phy->standby_gpio = standby_gpio; 117 + } 118 + 119 + if (drvdata->flags & CAN_TRANSCEIVER_EN_PRESENT) { 120 + enable_gpio = devm_gpiod_get(dev, "enable", GPIOD_OUT_LOW); 121 + if (IS_ERR(enable_gpio)) 122 + return PTR_ERR(enable_gpio); 123 + can_transceiver_phy->enable_gpio = enable_gpio; 124 + } 125 + 126 + phy_set_drvdata(can_transceiver_phy->generic_phy, can_transceiver_phy); 127 + 128 + phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); 129 + 130 + return PTR_ERR_OR_ZERO(phy_provider); 131 + } 132 + 133 + static struct platform_driver can_transceiver_phy_driver = { 134 + .probe = can_transceiver_phy_probe, 135 + .driver = { 136 + .name = "can-transceiver-phy", 137 + .of_match_table = can_transceiver_phy_ids, 138 + }, 139 + }; 140 + 141 + module_platform_driver(can_transceiver_phy_driver); 142 + 143 + MODULE_AUTHOR("Faiz Abbas <faiz_abbas@ti.com>"); 144 + MODULE_AUTHOR("Aswath Govindraju <a-govindraju@ti.com>"); 145 + MODULE_DESCRIPTION("CAN TRANSCEIVER PHY driver"); 146 + MODULE_LICENSE("GPL v2");
+1 -1
drivers/phy/phy-core-mipi-dphy.c
··· 15 15 /* 16 16 * Minimum D-PHY timings based on MIPI D-PHY specification. Derived 17 17 * from the valid ranges specified in Section 6.9, Table 14, Page 41 18 - * of the D-PHY specification (v2.1). 18 + * of the D-PHY specification (v1.2). 19 19 */ 20 20 int phy_mipi_dphy_get_default_config(unsigned long pixel_clock, 21 21 unsigned int bpp,
+9 -7
drivers/phy/phy-core.c
··· 697 697 struct phy *phy; 698 698 struct device_link *link; 699 699 700 - if (string == NULL) { 701 - dev_WARN(dev, "missing string\n"); 702 - return ERR_PTR(-EINVAL); 703 - } 704 - 705 700 if (dev->of_node) { 706 - index = of_property_match_string(dev->of_node, "phy-names", 707 - string); 701 + if (string) 702 + index = of_property_match_string(dev->of_node, "phy-names", 703 + string); 704 + else 705 + index = 0; 708 706 phy = _of_phy_get(dev->of_node, index); 709 707 } else { 708 + if (string == NULL) { 709 + dev_WARN(dev, "missing string\n"); 710 + return ERR_PTR(-EINVAL); 711 + } 710 712 phy = phy_find(dev, string); 711 713 } 712 714 if (IS_ERR(phy))
+2 -1
drivers/phy/phy-xgene.c
··· 961 961 serdes_wr(ctx, lane, RXTX_REG1, val); 962 962 963 963 /* Latch VTT value based on the termination to ground and 964 - enable TX FIFO */ 964 + * enable TX FIFO 965 + */ 965 966 serdes_rd(ctx, lane, RXTX_REG2, &val); 966 967 val = RXTX_REG2_VTT_ENA_SET(val, 0x1); 967 968 val = RXTX_REG2_VTT_SEL_SET(val, 0x1);
+308 -7
drivers/phy/qualcomm/phy-qcom-qmp.c
··· 35 35 #define PLL_READY_GATE_EN BIT(3) 36 36 /* QPHY_PCS_STATUS bit */ 37 37 #define PHYSTATUS BIT(6) 38 + #define PHYSTATUS_4_20 BIT(7) 38 39 /* QPHY_PCS_READY_STATUS & QPHY_COM_PCS_READY_STATUS bit */ 39 40 #define PCS_READY BIT(0) 40 41 ··· 142 141 static const unsigned int msm8996_ufsphy_regs_layout[QPHY_LAYOUT_SIZE] = { 143 142 [QPHY_START_CTRL] = 0x00, 144 143 [QPHY_PCS_READY_STATUS] = 0x168, 144 + }; 145 + 146 + static const unsigned int ipq_pciephy_gen3_regs_layout[QPHY_LAYOUT_SIZE] = { 147 + [QPHY_SW_RESET] = 0x00, 148 + [QPHY_START_CTRL] = 0x44, 149 + [QPHY_PCS_STATUS] = 0x14, 150 + [QPHY_PCS_POWER_DOWN_CONTROL] = 0x40, 145 151 }; 146 152 147 153 static const unsigned int pciephy_regs_layout[QPHY_LAYOUT_SIZE] = { ··· 620 612 QMP_PHY_INIT_CFG(QPHY_LOCK_DETECT_CONFIG2, 0x1f), 621 613 QMP_PHY_INIT_CFG(QPHY_LOCK_DETECT_CONFIG3, 0x47), 622 614 QMP_PHY_INIT_CFG(QPHY_POWER_STATE_CONFIG2, 0x08), 615 + }; 616 + 617 + static const struct qmp_phy_init_tbl ipq6018_pcie_serdes_tbl[] = { 618 + QMP_PHY_INIT_CFG(QSERDES_PLL_SSC_PER1, 0x7d), 619 + QMP_PHY_INIT_CFG(QSERDES_PLL_SSC_PER2, 0x01), 620 + QMP_PHY_INIT_CFG(QSERDES_PLL_SSC_STEP_SIZE1_MODE0, 0x0a), 621 + QMP_PHY_INIT_CFG(QSERDES_PLL_SSC_STEP_SIZE2_MODE0, 0x05), 622 + QMP_PHY_INIT_CFG(QSERDES_PLL_SSC_STEP_SIZE1_MODE1, 0x08), 623 + QMP_PHY_INIT_CFG(QSERDES_PLL_SSC_STEP_SIZE2_MODE1, 0x04), 624 + QMP_PHY_INIT_CFG(QSERDES_PLL_BIAS_EN_CLKBUFLR_EN, 0x18), 625 + QMP_PHY_INIT_CFG(QSERDES_PLL_CLK_ENABLE1, 0x90), 626 + QMP_PHY_INIT_CFG(QSERDES_PLL_SYS_CLK_CTRL, 0x02), 627 + QMP_PHY_INIT_CFG(QSERDES_PLL_SYSCLK_BUF_ENABLE, 0x07), 628 + QMP_PHY_INIT_CFG(QSERDES_PLL_PLL_IVCO, 0x0f), 629 + QMP_PHY_INIT_CFG(QSERDES_PLL_LOCK_CMP1_MODE0, 0xd4), 630 + QMP_PHY_INIT_CFG(QSERDES_PLL_LOCK_CMP2_MODE0, 0x14), 631 + QMP_PHY_INIT_CFG(QSERDES_PLL_LOCK_CMP1_MODE1, 0xaa), 632 + QMP_PHY_INIT_CFG(QSERDES_PLL_LOCK_CMP2_MODE1, 0x29), 633 + QMP_PHY_INIT_CFG(QSERDES_PLL_BG_TRIM, 0x0f), 634 + QMP_PHY_INIT_CFG(QSERDES_PLL_CP_CTRL_MODE0, 0x09), 635 + QMP_PHY_INIT_CFG(QSERDES_PLL_CP_CTRL_MODE1, 0x09), 636 + QMP_PHY_INIT_CFG(QSERDES_PLL_PLL_RCTRL_MODE0, 0x16), 637 + QMP_PHY_INIT_CFG(QSERDES_PLL_PLL_RCTRL_MODE1, 0x16), 638 + QMP_PHY_INIT_CFG(QSERDES_PLL_PLL_CCTRL_MODE0, 0x28), 639 + QMP_PHY_INIT_CFG(QSERDES_PLL_PLL_CCTRL_MODE1, 0x28), 640 + QMP_PHY_INIT_CFG(QSERDES_PLL_BIAS_EN_CTRL_BY_PSM, 0x01), 641 + QMP_PHY_INIT_CFG(QSERDES_PLL_SYSCLK_EN_SEL, 0x08), 642 + QMP_PHY_INIT_CFG(QSERDES_PLL_RESETSM_CNTRL, 0x20), 643 + QMP_PHY_INIT_CFG(QSERDES_PLL_LOCK_CMP_EN, 0x42), 644 + QMP_PHY_INIT_CFG(QSERDES_PLL_DEC_START_MODE0, 0x68), 645 + QMP_PHY_INIT_CFG(QSERDES_PLL_DEC_START_MODE1, 0x53), 646 + QMP_PHY_INIT_CFG(QSERDES_PLL_DIV_FRAC_START1_MODE0, 0xab), 647 + QMP_PHY_INIT_CFG(QSERDES_PLL_DIV_FRAC_START2_MODE0, 0xaa), 648 + QMP_PHY_INIT_CFG(QSERDES_PLL_DIV_FRAC_START3_MODE0, 0x02), 649 + QMP_PHY_INIT_CFG(QSERDES_PLL_DIV_FRAC_START1_MODE1, 0x55), 650 + QMP_PHY_INIT_CFG(QSERDES_PLL_DIV_FRAC_START2_MODE1, 0x55), 651 + QMP_PHY_INIT_CFG(QSERDES_PLL_DIV_FRAC_START3_MODE1, 0x05), 652 + QMP_PHY_INIT_CFG(QSERDES_PLL_INTEGLOOP_GAIN0_MODE0, 0xa0), 653 + QMP_PHY_INIT_CFG(QSERDES_PLL_INTEGLOOP_GAIN0_MODE1, 0xa0), 654 + QMP_PHY_INIT_CFG(QSERDES_PLL_VCO_TUNE1_MODE0, 0x24), 655 + QMP_PHY_INIT_CFG(QSERDES_PLL_VCO_TUNE2_MODE0, 0x02), 656 + QMP_PHY_INIT_CFG(QSERDES_PLL_VCO_TUNE1_MODE1, 0xb4), 657 + QMP_PHY_INIT_CFG(QSERDES_PLL_VCO_TUNE2_MODE1, 0x03), 658 + QMP_PHY_INIT_CFG(QSERDES_PLL_CLK_SELECT, 0x32), 659 + QMP_PHY_INIT_CFG(QSERDES_PLL_HSCLK_SEL, 0x01), 660 + QMP_PHY_INIT_CFG(QSERDES_PLL_CORE_CLK_EN, 0x00), 661 + QMP_PHY_INIT_CFG(QSERDES_PLL_CMN_CONFIG, 0x06), 662 + QMP_PHY_INIT_CFG(QSERDES_PLL_SVS_MODE_CLK_SEL, 0x05), 663 + QMP_PHY_INIT_CFG(QSERDES_PLL_CORECLK_DIV_MODE1, 0x08), 664 + }; 665 + 666 + static const struct qmp_phy_init_tbl ipq6018_pcie_tx_tbl[] = { 667 + QMP_PHY_INIT_CFG(QSERDES_TX0_RES_CODE_LANE_OFFSET_TX, 0x02), 668 + QMP_PHY_INIT_CFG(QSERDES_TX0_LANE_MODE_1, 0x06), 669 + QMP_PHY_INIT_CFG(QSERDES_TX0_RCV_DETECT_LVL_2, 0x12), 670 + }; 671 + 672 + static const struct qmp_phy_init_tbl ipq6018_pcie_rx_tbl[] = { 673 + QMP_PHY_INIT_CFG(QSERDES_RX0_UCDR_FO_GAIN, 0x0c), 674 + QMP_PHY_INIT_CFG(QSERDES_RX0_UCDR_SO_GAIN, 0x02), 675 + QMP_PHY_INIT_CFG(QSERDES_RX0_UCDR_SO_SATURATION_AND_ENABLE, 0x7f), 676 + QMP_PHY_INIT_CFG(QSERDES_RX0_UCDR_PI_CONTROLS, 0x70), 677 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_EQU_ADAPTOR_CNTRL2, 0x61), 678 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_EQU_ADAPTOR_CNTRL3, 0x04), 679 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_EQU_ADAPTOR_CNTRL4, 0x1e), 680 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_IDAC_TSETTLE_LOW, 0xc0), 681 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_IDAC_TSETTLE_HIGH, 0x00), 682 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_EQ_OFFSET_ADAPTOR_CNTRL1, 0x73), 683 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_OFFSET_ADAPTOR_CNTRL2, 0x80), 684 + QMP_PHY_INIT_CFG(QSERDES_RX0_SIGDET_ENABLES, 0x1c), 685 + QMP_PHY_INIT_CFG(QSERDES_RX0_SIGDET_CNTRL, 0x03), 686 + QMP_PHY_INIT_CFG(QSERDES_RX0_SIGDET_DEGLITCH_CNTRL, 0x14), 687 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_00_LOW, 0xf0), 688 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_00_HIGH, 0x01), 689 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_00_HIGH2, 0x2f), 690 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_00_HIGH3, 0xd3), 691 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_00_HIGH4, 0x40), 692 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_01_LOW, 0x01), 693 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_01_HIGH, 0x02), 694 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_01_HIGH2, 0xc8), 695 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_01_HIGH3, 0x09), 696 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_01_HIGH4, 0xb1), 697 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_10_LOW, 0x00), 698 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_10_HIGH, 0x02), 699 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_10_HIGH2, 0xc8), 700 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_10_HIGH3, 0x09), 701 + QMP_PHY_INIT_CFG(QSERDES_RX0_RX_MODE_10_HIGH4, 0xb1), 702 + QMP_PHY_INIT_CFG(QSERDES_RX0_DFE_EN_TIMER, 0x04), 703 + }; 704 + 705 + static const struct qmp_phy_init_tbl ipq6018_pcie_pcs_tbl[] = { 706 + QMP_PHY_INIT_CFG(PCS_COM_FLL_CNTRL1, 0x01), 707 + QMP_PHY_INIT_CFG(PCS_COM_REFGEN_REQ_CONFIG1, 0x0d), 708 + QMP_PHY_INIT_CFG(PCS_COM_G12S1_TXDEEMPH_M3P5DB, 0x10), 709 + QMP_PHY_INIT_CFG(PCS_COM_RX_SIGDET_LVL, 0xaa), 710 + QMP_PHY_INIT_CFG(PCS_COM_P2U3_WAKEUP_DLY_TIME_AUXCLK_L, 0x01), 711 + QMP_PHY_INIT_CFG(PCS_COM_RX_DCC_CAL_CONFIG, 0x01), 712 + QMP_PHY_INIT_CFG(PCS_COM_EQ_CONFIG5, 0x01), 713 + QMP_PHY_INIT_CFG(PCS_PCIE_POWER_STATE_CONFIG2, 0x0d), 714 + QMP_PHY_INIT_CFG(PCS_PCIE_POWER_STATE_CONFIG4, 0x07), 715 + QMP_PHY_INIT_CFG(PCS_PCIE_ENDPOINT_REFCLK_DRIVE, 0xc1), 716 + QMP_PHY_INIT_CFG(PCS_PCIE_L1P1_WAKEUP_DLY_TIME_AUXCLK_L, 0x01), 717 + QMP_PHY_INIT_CFG(PCS_PCIE_L1P2_WAKEUP_DLY_TIME_AUXCLK_L, 0x01), 718 + QMP_PHY_INIT_CFG(PCS_PCIE_OSC_DTCT_ACTIONS, 0x00), 719 + QMP_PHY_INIT_CFG(PCS_PCIE_EQ_CONFIG1, 0x11), 720 + QMP_PHY_INIT_CFG(PCS_PCIE_PRESET_P10_PRE, 0x00), 721 + QMP_PHY_INIT_CFG(PCS_PCIE_PRESET_P10_POST, 0x58), 623 722 }; 624 723 625 724 static const struct qmp_phy_init_tbl ipq8074_pcie_serdes_tbl[] = { ··· 2225 2110 QMP_PHY_INIT_CFG(QSERDES_V4_RX_GM_CAL, 0x1f), 2226 2111 }; 2227 2112 2113 + static const struct qmp_phy_init_tbl sdx55_qmp_pcie_serdes_tbl[] = { 2114 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BG_TIMER, 0x02), 2115 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIAS_EN_CLKBUFLR_EN, 0x18), 2116 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_SYS_CLK_CTRL, 0x07), 2117 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_IVCO, 0x0f), 2118 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CP_CTRL_MODE0, 0x0a), 2119 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CP_CTRL_MODE1, 0x0a), 2120 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_RCTRL_MODE0, 0x19), 2121 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_RCTRL_MODE1, 0x19), 2122 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_CCTRL_MODE0, 0x03), 2123 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_PLL_CCTRL_MODE1, 0x03), 2124 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_SYSCLK_EN_SEL, 0x00), 2125 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP_EN, 0x46), 2126 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP_CFG, 0x04), 2127 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP1_MODE0, 0x7f), 2128 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP2_MODE0, 0x02), 2129 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP1_MODE1, 0xff), 2130 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_LOCK_CMP2_MODE1, 0x04), 2131 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_DEC_START_MODE0, 0x4b), 2132 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_DEC_START_MODE1, 0x50), 2133 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_DIV_FRAC_START3_MODE0, 0x00), 2134 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_INTEGLOOP_GAIN0_MODE0, 0xfb), 2135 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_INTEGLOOP_GAIN1_MODE0, 0x01), 2136 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_INTEGLOOP_GAIN0_MODE1, 0xfb), 2137 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_INTEGLOOP_GAIN1_MODE1, 0x01), 2138 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_VCO_TUNE_MAP, 0x02), 2139 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_HSCLK_SEL, 0x12), 2140 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_HSCLK_HS_SWITCH_SEL, 0x00), 2141 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CORECLK_DIV_MODE0, 0x05), 2142 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CORECLK_DIV_MODE1, 0x04), 2143 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CMN_CONFIG, 0x04), 2144 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CMN_MISC1, 0x88), 2145 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_INTERNAL_DIG_CORECLK_DIV, 0x03), 2146 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_CMN_MODE, 0x17), 2147 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_VCO_DC_LEVEL_CTRL, 0x0b), 2148 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE1_MODE0, 0x56), 2149 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE2_MODE0, 0x1d), 2150 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE1_MODE1, 0x4b), 2151 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE2_MODE1, 0x1f), 2152 + QMP_PHY_INIT_CFG(QSERDES_V4_COM_BIN_VCOCAL_HSCLK_SEL, 0x22), 2153 + }; 2154 + 2155 + static const struct qmp_phy_init_tbl sdx55_qmp_pcie_tx_tbl[] = { 2156 + QMP_PHY_INIT_CFG(QSERDES_V4_20_TX_LANE_MODE_1, 0x05), 2157 + QMP_PHY_INIT_CFG(QSERDES_V4_20_TX_LANE_MODE_2, 0xf6), 2158 + QMP_PHY_INIT_CFG(QSERDES_V4_20_TX_LANE_MODE_3, 0x13), 2159 + QMP_PHY_INIT_CFG(QSERDES_V4_20_TX_VMODE_CTRL1, 0x00), 2160 + QMP_PHY_INIT_CFG(QSERDES_V4_20_TX_PI_QEC_CTRL, 0x00), 2161 + }; 2162 + 2163 + static const struct qmp_phy_init_tbl sdx55_qmp_pcie_rx_tbl[] = { 2164 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_FO_GAIN_RATE2, 0x0c), 2165 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_UCDR_PI_CONTROLS, 0x16), 2166 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_AUX_DATA_TCOARSE_TFINE, 0x7f), 2167 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_DFE_3, 0x55), 2168 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_DFE_DAC_ENABLE1, 0x0c), 2169 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_DFE_DAC_ENABLE2, 0x00), 2170 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_VGA_CAL_CNTRL2, 0x08), 2171 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_EQ_OFFSET_ADAPTOR_CNTRL1, 0x27), 2172 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B1, 0x1a), 2173 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B2, 0x5a), 2174 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B3, 0x09), 2175 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B4, 0x37), 2176 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE2_B0, 0xbd), 2177 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE2_B1, 0xf9), 2178 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE2_B2, 0xbf), 2179 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE2_B3, 0xce), 2180 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE2_B4, 0x62), 2181 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE3_B0, 0xbf), 2182 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE3_B1, 0x7d), 2183 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE3_B2, 0xbf), 2184 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE3_B3, 0xcf), 2185 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_RX_MODE_RATE3_B4, 0xd6), 2186 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_PHPRE_CTRL, 0xa0), 2187 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_DFE_CTLE_POST_CAL_OFFSET, 0x38), 2188 + QMP_PHY_INIT_CFG(QSERDES_V4_20_RX_MARG_COARSE_CTRL2, 0x12), 2189 + }; 2190 + 2191 + static const struct qmp_phy_init_tbl sdx55_qmp_pcie_pcs_tbl[] = { 2192 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_RX_SIGDET_LVL, 0x77), 2193 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_EQ_CONFIG2, 0x01), 2194 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_EQ_CONFIG4, 0x16), 2195 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_EQ_CONFIG5, 0x02), 2196 + }; 2197 + 2198 + static const struct qmp_phy_init_tbl sdx55_qmp_pcie_pcs_misc_tbl[] = { 2199 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_PCIE_EQ_CONFIG1, 0x17), 2200 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_PCIE_G3_RXEQEVAL_TIME, 0x13), 2201 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_PCIE_G4_RXEQEVAL_TIME, 0x13), 2202 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_PCIE_G4_EQ_CONFIG2, 0x01), 2203 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_PCIE_G4_EQ_CONFIG5, 0x02), 2204 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_LANE1_INSIG_SW_CTRL2, 0x00), 2205 + QMP_PHY_INIT_CFG(QPHY_V4_20_PCS_LANE1_INSIG_MX_CTRL2, 0x00), 2206 + }; 2207 + 2228 2208 static const struct qmp_phy_init_tbl sm8350_ufsphy_serdes_tbl[] = { 2229 2209 QMP_PHY_INIT_CFG(QSERDES_V5_COM_SYSCLK_EN_SEL, 0xd9), 2230 2210 QMP_PHY_INIT_CFG(QSERDES_V5_COM_HSCLK_SEL, 0x11), ··· 2621 2411 unsigned int start_ctrl; 2622 2412 unsigned int pwrdn_ctrl; 2623 2413 unsigned int mask_com_pcs_ready; 2414 + /* bit offset of PHYSTATUS in QPHY_PCS_STATUS register */ 2415 + unsigned int phy_status; 2624 2416 2625 2417 /* true, if PHY has a separate PHY_COM control block */ 2626 2418 bool has_phy_com_ctrl; ··· 2836 2624 2837 2625 .start_ctrl = SERDES_START | PCS_START, 2838 2626 .pwrdn_ctrl = SW_PWRDN, 2627 + .phy_status = PHYSTATUS, 2839 2628 }; 2840 2629 2841 2630 static const struct qmp_phy_cfg msm8996_pciephy_cfg = { ··· 2862 2649 .start_ctrl = PCS_START | PLL_READY_GATE_EN, 2863 2650 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 2864 2651 .mask_com_pcs_ready = PCS_READY, 2652 + .phy_status = PHYSTATUS, 2865 2653 2866 2654 .has_phy_com_ctrl = true, 2867 2655 .has_lane_rst = true, ··· 2892 2678 2893 2679 .start_ctrl = SERDES_START, 2894 2680 .pwrdn_ctrl = SW_PWRDN, 2681 + .phy_status = PHYSTATUS, 2895 2682 2896 2683 .no_pcs_sw_reset = true, 2897 2684 }; ··· 2919 2704 2920 2705 .start_ctrl = SERDES_START | PCS_START, 2921 2706 .pwrdn_ctrl = SW_PWRDN, 2707 + .phy_status = PHYSTATUS, 2922 2708 }; 2923 2709 2924 2710 static const char * const ipq8074_pciephy_clk_l[] = { ··· 2949 2733 .vreg_list = NULL, 2950 2734 .num_vregs = 0, 2951 2735 .regs = pciephy_regs_layout, 2736 + 2737 + .start_ctrl = SERDES_START | PCS_START, 2738 + .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 2739 + .phy_status = PHYSTATUS, 2740 + 2741 + .has_phy_com_ctrl = false, 2742 + .has_lane_rst = false, 2743 + .has_pwrdn_delay = true, 2744 + .pwrdn_delay_min = 995, /* us */ 2745 + .pwrdn_delay_max = 1005, /* us */ 2746 + }; 2747 + 2748 + static const struct qmp_phy_cfg ipq6018_pciephy_cfg = { 2749 + .type = PHY_TYPE_PCIE, 2750 + .nlanes = 1, 2751 + 2752 + .serdes_tbl = ipq6018_pcie_serdes_tbl, 2753 + .serdes_tbl_num = ARRAY_SIZE(ipq6018_pcie_serdes_tbl), 2754 + .tx_tbl = ipq6018_pcie_tx_tbl, 2755 + .tx_tbl_num = ARRAY_SIZE(ipq6018_pcie_tx_tbl), 2756 + .rx_tbl = ipq6018_pcie_rx_tbl, 2757 + .rx_tbl_num = ARRAY_SIZE(ipq6018_pcie_rx_tbl), 2758 + .pcs_tbl = ipq6018_pcie_pcs_tbl, 2759 + .pcs_tbl_num = ARRAY_SIZE(ipq6018_pcie_pcs_tbl), 2760 + .clk_list = ipq8074_pciephy_clk_l, 2761 + .num_clks = ARRAY_SIZE(ipq8074_pciephy_clk_l), 2762 + .reset_list = ipq8074_pciephy_reset_l, 2763 + .num_resets = ARRAY_SIZE(ipq8074_pciephy_reset_l), 2764 + .vreg_list = NULL, 2765 + .num_vregs = 0, 2766 + .regs = ipq_pciephy_gen3_regs_layout, 2952 2767 2953 2768 .start_ctrl = SERDES_START | PCS_START, 2954 2769 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, ··· 3015 2768 3016 2769 .start_ctrl = PCS_START | SERDES_START, 3017 2770 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 2771 + .phy_status = PHYSTATUS, 3018 2772 3019 2773 .has_pwrdn_delay = true, 3020 2774 .pwrdn_delay_min = 995, /* us */ ··· 3044 2796 3045 2797 .start_ctrl = PCS_START | SERDES_START, 3046 2798 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 2799 + .phy_status = PHYSTATUS, 3047 2800 3048 2801 .has_pwrdn_delay = true, 3049 2802 .pwrdn_delay_min = 995, /* us */ ··· 3083 2834 3084 2835 .start_ctrl = PCS_START | SERDES_START, 3085 2836 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 2837 + .phy_status = PHYSTATUS, 3086 2838 3087 2839 .has_pwrdn_delay = true, 3088 2840 .pwrdn_delay_min = 995, /* us */ ··· 3122 2872 3123 2873 .start_ctrl = PCS_START | SERDES_START, 3124 2874 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 2875 + .phy_status = PHYSTATUS, 3125 2876 3126 2877 .is_dual_lane_phy = true, 3127 2878 .has_pwrdn_delay = true, ··· 3152 2901 3153 2902 .start_ctrl = SERDES_START | PCS_START, 3154 2903 .pwrdn_ctrl = SW_PWRDN, 2904 + .phy_status = PHYSTATUS, 3155 2905 3156 2906 .has_pwrdn_delay = true, 3157 2907 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3184 2932 3185 2933 .start_ctrl = SERDES_START | PCS_START, 3186 2934 .pwrdn_ctrl = SW_PWRDN, 2935 + .phy_status = PHYSTATUS, 3187 2936 3188 2937 .has_pwrdn_delay = true, 3189 2938 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3256 3003 3257 3004 .start_ctrl = SERDES_START | PCS_START, 3258 3005 .pwrdn_ctrl = SW_PWRDN, 3006 + .phy_status = PHYSTATUS, 3259 3007 3260 3008 .has_pwrdn_delay = true, 3261 3009 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3283 3029 3284 3030 .start_ctrl = SERDES_START, 3285 3031 .pwrdn_ctrl = SW_PWRDN, 3032 + .phy_status = PHYSTATUS, 3286 3033 3287 3034 .is_dual_lane_phy = true, 3288 3035 .no_pcs_sw_reset = true, ··· 3311 3056 3312 3057 .start_ctrl = SERDES_START | PCS_START, 3313 3058 .pwrdn_ctrl = SW_PWRDN | REFCLK_DRV_DSBL, 3059 + .phy_status = PHYSTATUS, 3314 3060 }; 3315 3061 3316 3062 static const struct qmp_phy_cfg msm8998_usb3phy_cfg = { ··· 3336 3080 3337 3081 .start_ctrl = SERDES_START | PCS_START, 3338 3082 .pwrdn_ctrl = SW_PWRDN, 3083 + .phy_status = PHYSTATUS, 3339 3084 3340 3085 .is_dual_lane_phy = true, 3341 3086 }; ··· 3361 3104 3362 3105 .start_ctrl = SERDES_START, 3363 3106 .pwrdn_ctrl = SW_PWRDN, 3107 + .phy_status = PHYSTATUS, 3364 3108 3365 3109 .is_dual_lane_phy = true, 3366 3110 }; ··· 3388 3130 3389 3131 .start_ctrl = SERDES_START | PCS_START, 3390 3132 .pwrdn_ctrl = SW_PWRDN, 3133 + .phy_status = PHYSTATUS, 3134 + 3391 3135 3392 3136 .has_pwrdn_delay = true, 3393 3137 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3421 3161 3422 3162 .start_ctrl = SERDES_START | PCS_START, 3423 3163 .pwrdn_ctrl = SW_PWRDN, 3164 + .phy_status = PHYSTATUS, 3424 3165 3425 3166 .has_pwrdn_delay = true, 3426 3167 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3450 3189 3451 3190 .start_ctrl = SERDES_START | PCS_START, 3452 3191 .pwrdn_ctrl = SW_PWRDN, 3192 + .phy_status = PHYSTATUS, 3453 3193 3454 3194 .has_pwrdn_delay = true, 3455 3195 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3482 3220 3483 3221 .start_ctrl = SERDES_START | PCS_START, 3484 3222 .pwrdn_ctrl = SW_PWRDN, 3223 + .phy_status = PHYSTATUS, 3485 3224 3486 3225 .has_pwrdn_delay = true, 3487 3226 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3551 3288 3552 3289 .start_ctrl = SERDES_START | PCS_START, 3553 3290 .pwrdn_ctrl = SW_PWRDN, 3291 + .phy_status = PHYSTATUS, 3554 3292 3555 3293 .has_pwrdn_delay = true, 3556 3294 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, 3557 3295 .pwrdn_delay_max = POWER_DOWN_DELAY_US_MAX, 3296 + }; 3297 + 3298 + static const struct qmp_phy_cfg sdx55_qmp_pciephy_cfg = { 3299 + .type = PHY_TYPE_PCIE, 3300 + .nlanes = 2, 3301 + 3302 + .serdes_tbl = sdx55_qmp_pcie_serdes_tbl, 3303 + .serdes_tbl_num = ARRAY_SIZE(sdx55_qmp_pcie_serdes_tbl), 3304 + .tx_tbl = sdx55_qmp_pcie_tx_tbl, 3305 + .tx_tbl_num = ARRAY_SIZE(sdx55_qmp_pcie_tx_tbl), 3306 + .rx_tbl = sdx55_qmp_pcie_rx_tbl, 3307 + .rx_tbl_num = ARRAY_SIZE(sdx55_qmp_pcie_rx_tbl), 3308 + .pcs_tbl = sdx55_qmp_pcie_pcs_tbl, 3309 + .pcs_tbl_num = ARRAY_SIZE(sdx55_qmp_pcie_pcs_tbl), 3310 + .pcs_misc_tbl = sdx55_qmp_pcie_pcs_misc_tbl, 3311 + .pcs_misc_tbl_num = ARRAY_SIZE(sdx55_qmp_pcie_pcs_misc_tbl), 3312 + .clk_list = sdm845_pciephy_clk_l, 3313 + .num_clks = ARRAY_SIZE(sdm845_pciephy_clk_l), 3314 + .reset_list = sdm845_pciephy_reset_l, 3315 + .num_resets = ARRAY_SIZE(sdm845_pciephy_reset_l), 3316 + .vreg_list = qmp_phy_vreg_l, 3317 + .num_vregs = ARRAY_SIZE(qmp_phy_vreg_l), 3318 + .regs = sm8250_pcie_regs_layout, 3319 + 3320 + .start_ctrl = PCS_START | SERDES_START, 3321 + .pwrdn_ctrl = SW_PWRDN, 3322 + .phy_status = PHYSTATUS_4_20, 3323 + 3324 + .is_dual_lane_phy = true, 3325 + .has_pwrdn_delay = true, 3326 + .pwrdn_delay_min = 995, /* us */ 3327 + .pwrdn_delay_max = 1005, /* us */ 3558 3328 }; 3559 3329 3560 3330 static const struct qmp_phy_cfg sm8350_ufsphy_cfg = { ··· 3610 3314 3611 3315 .start_ctrl = SERDES_START, 3612 3316 .pwrdn_ctrl = SW_PWRDN, 3317 + .phy_status = PHYSTATUS, 3613 3318 3614 3319 .is_dual_lane_phy = true, 3615 3320 }; ··· 3637 3340 3638 3341 .start_ctrl = SERDES_START | PCS_START, 3639 3342 .pwrdn_ctrl = SW_PWRDN, 3343 + .phy_status = PHYSTATUS, 3640 3344 3641 3345 .has_pwrdn_delay = true, 3642 3346 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 3669 3371 3670 3372 .start_ctrl = SERDES_START | PCS_START, 3671 3373 .pwrdn_ctrl = SW_PWRDN, 3374 + .phy_status = PHYSTATUS, 3672 3375 3673 3376 .has_pwrdn_delay = true, 3674 3377 .pwrdn_delay_min = POWER_DOWN_DELAY_US_MIN, ··· 4292 3993 } 4293 3994 4294 3995 ret = clk_bulk_prepare_enable(cfg->num_clks, qmp->clks); 4295 - if (ret) { 4296 - dev_err(qmp->dev, "failed to enable clks, err=%d\n", ret); 3996 + if (ret) 4297 3997 goto err_rst; 4298 - } 4299 3998 4300 3999 if (cfg->has_phy_dp_com_ctrl) { 4301 4000 qphy_setbits(dp_com, QPHY_V3_DP_COM_POWER_DOWN_CTRL, ··· 4535 4238 ready = PCS_READY; 4536 4239 } else { 4537 4240 status = pcs + cfg->regs[QPHY_PCS_STATUS]; 4538 - mask = PHYSTATUS; 4241 + mask = cfg->phy_status; 4539 4242 ready = 0; 4540 4243 } 4541 4244 ··· 4727 4430 } 4728 4431 4729 4432 ret = clk_bulk_prepare_enable(cfg->num_clks, qmp->clks); 4730 - if (ret) { 4731 - dev_err(qmp->dev, "failed to enable clks, err=%d\n", ret); 4433 + if (ret) 4732 4434 return ret; 4733 - } 4734 4435 4735 4436 ret = clk_prepare_enable(qphy->pipe_clk); 4736 4437 if (ret) { ··· 5223 4928 .compatible = "qcom,ipq8074-qmp-pcie-phy", 5224 4929 .data = &ipq8074_pciephy_cfg, 5225 4930 }, { 4931 + .compatible = "qcom,ipq6018-qmp-pcie-phy", 4932 + .data = &ipq6018_pciephy_cfg, 4933 + }, { 5226 4934 .compatible = "qcom,sc7180-qmp-usb3-phy", 5227 4935 .data = &sc7180_usb3phy_cfg, 5228 4936 }, { ··· 5288 4990 }, { 5289 4991 .compatible = "qcom,sm8250-qmp-modem-pcie-phy", 5290 4992 .data = &sm8250_qmp_gen3x2_pciephy_cfg, 4993 + }, { 4994 + .compatible = "qcom,sdx55-qmp-pcie-phy", 4995 + .data = &sdx55_qmp_pciephy_cfg, 5291 4996 }, { 5292 4997 .compatible = "qcom,sdx55-qmp-usb3-uni-phy", 5293 4998 .data = &sdx55_usb3_uniphy_cfg,
+188 -1
drivers/phy/qualcomm/phy-qcom-qmp.h
··· 6 6 #ifndef QCOM_PHY_QMP_H_ 7 7 #define QCOM_PHY_QMP_H_ 8 8 9 + /* QMP V2 PHY for PCIE gen3 ports - QSERDES PLL registers */ 10 + 11 + #define QSERDES_PLL_BG_TIMER 0x00c 12 + #define QSERDES_PLL_SSC_PER1 0x01c 13 + #define QSERDES_PLL_SSC_PER2 0x020 14 + #define QSERDES_PLL_SSC_STEP_SIZE1_MODE0 0x024 15 + #define QSERDES_PLL_SSC_STEP_SIZE2_MODE0 0x028 16 + #define QSERDES_PLL_SSC_STEP_SIZE1_MODE1 0x02c 17 + #define QSERDES_PLL_SSC_STEP_SIZE2_MODE1 0x030 18 + #define QSERDES_PLL_BIAS_EN_CLKBUFLR_EN 0x03c 19 + #define QSERDES_PLL_CLK_ENABLE1 0x040 20 + #define QSERDES_PLL_SYS_CLK_CTRL 0x044 21 + #define QSERDES_PLL_SYSCLK_BUF_ENABLE 0x048 22 + #define QSERDES_PLL_PLL_IVCO 0x050 23 + #define QSERDES_PLL_LOCK_CMP1_MODE0 0x054 24 + #define QSERDES_PLL_LOCK_CMP2_MODE0 0x058 25 + #define QSERDES_PLL_LOCK_CMP1_MODE1 0x060 26 + #define QSERDES_PLL_LOCK_CMP2_MODE1 0x064 27 + #define QSERDES_PLL_BG_TRIM 0x074 28 + #define QSERDES_PLL_CLK_EP_DIV_MODE0 0x078 29 + #define QSERDES_PLL_CLK_EP_DIV_MODE1 0x07c 30 + #define QSERDES_PLL_CP_CTRL_MODE0 0x080 31 + #define QSERDES_PLL_CP_CTRL_MODE1 0x084 32 + #define QSERDES_PLL_PLL_RCTRL_MODE0 0x088 33 + #define QSERDES_PLL_PLL_RCTRL_MODE1 0x08C 34 + #define QSERDES_PLL_PLL_CCTRL_MODE0 0x090 35 + #define QSERDES_PLL_PLL_CCTRL_MODE1 0x094 36 + #define QSERDES_PLL_BIAS_EN_CTRL_BY_PSM 0x0a4 37 + #define QSERDES_PLL_SYSCLK_EN_SEL 0x0a8 38 + #define QSERDES_PLL_RESETSM_CNTRL 0x0b0 39 + #define QSERDES_PLL_LOCK_CMP_EN 0x0c4 40 + #define QSERDES_PLL_DEC_START_MODE0 0x0cc 41 + #define QSERDES_PLL_DEC_START_MODE1 0x0d0 42 + #define QSERDES_PLL_DIV_FRAC_START1_MODE0 0x0d8 43 + #define QSERDES_PLL_DIV_FRAC_START2_MODE0 0x0dc 44 + #define QSERDES_PLL_DIV_FRAC_START3_MODE0 0x0e0 45 + #define QSERDES_PLL_DIV_FRAC_START1_MODE1 0x0e4 46 + #define QSERDES_PLL_DIV_FRAC_START2_MODE1 0x0e8 47 + #define QSERDES_PLL_DIV_FRAC_START3_MODE1 0x0eC 48 + #define QSERDES_PLL_INTEGLOOP_GAIN0_MODE0 0x100 49 + #define QSERDES_PLL_INTEGLOOP_GAIN1_MODE0 0x104 50 + #define QSERDES_PLL_INTEGLOOP_GAIN0_MODE1 0x108 51 + #define QSERDES_PLL_INTEGLOOP_GAIN1_MODE1 0x10c 52 + #define QSERDES_PLL_VCO_TUNE_MAP 0x120 53 + #define QSERDES_PLL_VCO_TUNE1_MODE0 0x124 54 + #define QSERDES_PLL_VCO_TUNE2_MODE0 0x128 55 + #define QSERDES_PLL_VCO_TUNE1_MODE1 0x12c 56 + #define QSERDES_PLL_VCO_TUNE2_MODE1 0x130 57 + #define QSERDES_PLL_VCO_TUNE_TIMER1 0x13c 58 + #define QSERDES_PLL_VCO_TUNE_TIMER2 0x140 59 + #define QSERDES_PLL_CLK_SELECT 0x16c 60 + #define QSERDES_PLL_HSCLK_SEL 0x170 61 + #define QSERDES_PLL_CORECLK_DIV 0x17c 62 + #define QSERDES_PLL_CORE_CLK_EN 0x184 63 + #define QSERDES_PLL_CMN_CONFIG 0x18c 64 + #define QSERDES_PLL_SVS_MODE_CLK_SEL 0x194 65 + #define QSERDES_PLL_CORECLK_DIV_MODE1 0x1b4 66 + 67 + /* QMP V2 PHY for PCIE gen3 ports - QSERDES TX registers */ 68 + 69 + #define QSERDES_TX0_RES_CODE_LANE_OFFSET_TX 0x03c 70 + #define QSERDES_TX0_HIGHZ_DRVR_EN 0x058 71 + #define QSERDES_TX0_LANE_MODE_1 0x084 72 + #define QSERDES_TX0_RCV_DETECT_LVL_2 0x09c 73 + 74 + /* QMP V2 PHY for PCIE gen3 ports - QSERDES RX registers */ 75 + 76 + #define QSERDES_RX0_UCDR_FO_GAIN 0x008 77 + #define QSERDES_RX0_UCDR_SO_GAIN 0x014 78 + #define QSERDES_RX0_UCDR_SO_SATURATION_AND_ENABLE 0x034 79 + #define QSERDES_RX0_UCDR_PI_CONTROLS 0x044 80 + #define QSERDES_RX0_RX_EQU_ADAPTOR_CNTRL2 0x0ec 81 + #define QSERDES_RX0_RX_EQU_ADAPTOR_CNTRL3 0x0f0 82 + #define QSERDES_RX0_RX_EQU_ADAPTOR_CNTRL4 0x0f4 83 + #define QSERDES_RX0_RX_IDAC_TSETTLE_LOW 0x0f8 84 + #define QSERDES_RX0_RX_IDAC_TSETTLE_HIGH 0x0fc 85 + #define QSERDES_RX0_RX_EQ_OFFSET_ADAPTOR_CNTRL1 0x110 86 + #define QSERDES_RX0_RX_OFFSET_ADAPTOR_CNTRL2 0x114 87 + #define QSERDES_RX0_SIGDET_ENABLES 0x118 88 + #define QSERDES_RX0_SIGDET_CNTRL 0x11c 89 + #define QSERDES_RX0_SIGDET_DEGLITCH_CNTRL 0x124 90 + #define QSERDES_RX0_RX_MODE_00_LOW 0x170 91 + #define QSERDES_RX0_RX_MODE_00_HIGH 0x174 92 + #define QSERDES_RX0_RX_MODE_00_HIGH2 0x178 93 + #define QSERDES_RX0_RX_MODE_00_HIGH3 0x17c 94 + #define QSERDES_RX0_RX_MODE_00_HIGH4 0x180 95 + #define QSERDES_RX0_RX_MODE_01_LOW 0x184 96 + #define QSERDES_RX0_RX_MODE_01_HIGH 0x188 97 + #define QSERDES_RX0_RX_MODE_01_HIGH2 0x18c 98 + #define QSERDES_RX0_RX_MODE_01_HIGH3 0x190 99 + #define QSERDES_RX0_RX_MODE_01_HIGH4 0x194 100 + #define QSERDES_RX0_RX_MODE_10_LOW 0x198 101 + #define QSERDES_RX0_RX_MODE_10_HIGH 0x19c 102 + #define QSERDES_RX0_RX_MODE_10_HIGH2 0x1a0 103 + #define QSERDES_RX0_RX_MODE_10_HIGH3 0x1a4 104 + #define QSERDES_RX0_RX_MODE_10_HIGH4 0x1a8 105 + #define QSERDES_RX0_DFE_EN_TIMER 0x1b4 106 + 107 + /* QMP V2 PHY for PCIE gen3 ports - PCS registers */ 108 + 109 + #define PCS_COM_FLL_CNTRL1 0x098 110 + #define PCS_COM_FLL_CNTRL2 0x09c 111 + #define PCS_COM_FLL_CNT_VAL_L 0x0a0 112 + #define PCS_COM_FLL_CNT_VAL_H_TOL 0x0a4 113 + #define PCS_COM_FLL_MAN_CODE 0x0a8 114 + #define PCS_COM_REFGEN_REQ_CONFIG1 0x0dc 115 + #define PCS_COM_G12S1_TXDEEMPH_M3P5DB 0x16c 116 + #define PCS_COM_RX_SIGDET_LVL 0x188 117 + #define PCS_COM_P2U3_WAKEUP_DLY_TIME_AUXCLK_L 0x1a4 118 + #define PCS_COM_P2U3_WAKEUP_DLY_TIME_AUXCLK_H 0x1a8 119 + #define PCS_COM_RX_DCC_CAL_CONFIG 0x1d8 120 + #define PCS_COM_EQ_CONFIG5 0x1ec 121 + 122 + /* QMP V2 PHY for PCIE gen3 ports - PCS Misc registers */ 123 + 124 + #define PCS_PCIE_POWER_STATE_CONFIG2 0x40c 125 + #define PCS_PCIE_POWER_STATE_CONFIG4 0x414 126 + #define PCS_PCIE_ENDPOINT_REFCLK_DRIVE 0x41c 127 + #define PCS_PCIE_L1P1_WAKEUP_DLY_TIME_AUXCLK_L 0x440 128 + #define PCS_PCIE_L1P1_WAKEUP_DLY_TIME_AUXCLK_H 0x444 129 + #define PCS_PCIE_L1P2_WAKEUP_DLY_TIME_AUXCLK_L 0x448 130 + #define PCS_PCIE_L1P2_WAKEUP_DLY_TIME_AUXCLK_H 0x44c 131 + #define PCS_PCIE_OSC_DTCT_CONFIG2 0x45c 132 + #define PCS_PCIE_OSC_DTCT_MODE2_CONFIG2 0x478 133 + #define PCS_PCIE_OSC_DTCT_MODE2_CONFIG4 0x480 134 + #define PCS_PCIE_OSC_DTCT_MODE2_CONFIG5 0x484 135 + #define PCS_PCIE_OSC_DTCT_ACTIONS 0x490 136 + #define PCS_PCIE_EQ_CONFIG1 0x4a0 137 + #define PCS_PCIE_EQ_CONFIG2 0x4a4 138 + #define PCS_PCIE_PRESET_P10_PRE 0x4bc 139 + #define PCS_PCIE_PRESET_P10_POST 0x4e0 140 + 9 141 /* Only for QMP V2 PHY - QSERDES COM registers */ 10 142 #define QSERDES_COM_BG_TIMER 0x00c 11 143 #define QSERDES_COM_SSC_EN_CENTER 0x010 ··· 552 420 #define QSERDES_V4_COM_SYSCLK_EN_SEL 0x094 553 421 #define QSERDES_V4_COM_RESETSM_CNTRL 0x09c 554 422 #define QSERDES_V4_COM_LOCK_CMP_EN 0x0a4 423 + #define QSERDES_V4_COM_LOCK_CMP_CFG 0x0a8 555 424 #define QSERDES_V4_COM_LOCK_CMP1_MODE0 0x0ac 556 425 #define QSERDES_V4_COM_LOCK_CMP2_MODE0 0x0b0 557 426 #define QSERDES_V4_COM_LOCK_CMP1_MODE1 0x0b4 ··· 567 434 #define QSERDES_V4_COM_DIV_FRAC_START3_MODE1 0x0e0 568 435 #define QSERDES_V4_COM_INTEGLOOP_GAIN0_MODE0 0x0ec 569 436 #define QSERDES_V4_COM_INTEGLOOP_GAIN1_MODE0 0x0f0 437 + #define QSERDES_V4_COM_INTEGLOOP_GAIN0_MODE1 0x0f4 438 + #define QSERDES_V4_COM_INTEGLOOP_GAIN1_MODE1 0x0f8 570 439 #define QSERDES_V4_COM_VCO_TUNE_CTRL 0x108 571 440 #define QSERDES_V4_COM_VCO_TUNE_MAP 0x10c 572 441 #define QSERDES_V4_COM_VCO_TUNE1_MODE0 0x110 ··· 586 451 #define QSERDES_V4_COM_C_READY_STATUS 0x178 587 452 #define QSERDES_V4_COM_CMN_CONFIG 0x17c 588 453 #define QSERDES_V4_COM_SVS_MODE_CLK_SEL 0x184 454 + #define QSERDES_V4_COM_CMN_MISC1 0x19c 455 + #define QSERDES_V4_COM_INTERNAL_DIG_CORECLK_DIV 0x1a0 456 + #define QSERDES_V4_COM_CMN_MODE 0x1a4 457 + #define QSERDES_V4_COM_VCO_DC_LEVEL_CTRL 0x1a8 589 458 #define QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE1_MODE0 0x1ac 590 459 #define QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE2_MODE0 0x1b0 591 460 #define QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE1_MODE1 0x1b4 592 - #define QSERDES_V4_COM_BIN_VCOCAL_HSCLK_SEL 0x1bc 593 461 #define QSERDES_V4_COM_BIN_VCOCAL_CMP_CODE2_MODE1 0x1b8 462 + #define QSERDES_V4_COM_BIN_VCOCAL_HSCLK_SEL 0x1bc 594 463 595 464 /* Only for QMP V4 PHY - TX registers */ 596 465 #define QSERDES_V4_TX_CLKBUF_ENABLE 0x08 ··· 623 484 #define QSERDES_V4_TX_PWM_GEAR_4_DIVIDER_BAND0_1 0xe4 624 485 #define QSERDES_V4_TX_VMODE_CTRL1 0xe8 625 486 #define QSERDES_V4_TX_PI_QEC_CTRL 0x104 487 + 488 + /* Only for QMP V4_20 PHY - TX registers */ 489 + #define QSERDES_V4_20_TX_LANE_MODE_1 0x88 490 + #define QSERDES_V4_20_TX_LANE_MODE_2 0x8c 491 + #define QSERDES_V4_20_TX_LANE_MODE_3 0x90 492 + #define QSERDES_V4_20_TX_VMODE_CTRL1 0xc4 493 + #define QSERDES_V4_20_TX_PI_QEC_CTRL 0xe0 626 494 627 495 /* Only for QMP V4 PHY - RX registers */ 628 496 #define QSERDES_V4_RX_UCDR_FO_GAIN 0x008 ··· 696 550 #define QSERDES_V4_DP_PHY_SPARE0 0x0c8 697 551 #define QSERDES_V4_DP_PHY_AUX_INTERRUPT_STATUS 0x0d8 698 552 #define QSERDES_V4_DP_PHY_STATUS 0x0dc 553 + 554 + /* Only for QMP V4_20 PHY - RX registers */ 555 + #define QSERDES_V4_20_RX_FO_GAIN_RATE2 0x008 556 + #define QSERDES_V4_20_RX_UCDR_PI_CONTROLS 0x058 557 + #define QSERDES_V4_20_RX_AUX_DATA_TCOARSE_TFINE 0x0ac 558 + #define QSERDES_V4_20_RX_DFE_3 0x110 559 + #define QSERDES_V4_20_RX_DFE_DAC_ENABLE1 0x134 560 + #define QSERDES_V4_20_RX_DFE_DAC_ENABLE2 0x138 561 + #define QSERDES_V4_20_RX_VGA_CAL_CNTRL2 0x150 562 + #define QSERDES_V4_20_RX_RX_EQ_OFFSET_ADAPTOR_CNTRL1 0x178 563 + #define QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B1 0x1c8 564 + #define QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B2 0x1cc 565 + #define QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B3 0x1d0 566 + #define QSERDES_V4_20_RX_RX_MODE_RATE_0_1_B4 0x1d4 567 + #define QSERDES_V4_20_RX_RX_MODE_RATE2_B0 0x1d8 568 + #define QSERDES_V4_20_RX_RX_MODE_RATE2_B1 0x1dc 569 + #define QSERDES_V4_20_RX_RX_MODE_RATE2_B2 0x1e0 570 + #define QSERDES_V4_20_RX_RX_MODE_RATE2_B3 0x1e4 571 + #define QSERDES_V4_20_RX_RX_MODE_RATE2_B4 0x1e8 572 + #define QSERDES_V4_20_RX_RX_MODE_RATE3_B0 0x1ec 573 + #define QSERDES_V4_20_RX_RX_MODE_RATE3_B1 0x1f0 574 + #define QSERDES_V4_20_RX_RX_MODE_RATE3_B2 0x1f4 575 + #define QSERDES_V4_20_RX_RX_MODE_RATE3_B3 0x1f8 576 + #define QSERDES_V4_20_RX_RX_MODE_RATE3_B4 0x1fc 577 + #define QSERDES_V4_20_RX_PHPRE_CTRL 0x200 578 + #define QSERDES_V4_20_RX_DFE_CTLE_POST_CAL_OFFSET 0x20c 579 + #define QSERDES_V4_20_RX_MARG_COARSE_CTRL2 0x23c 699 580 700 581 /* Only for QMP V4 PHY - UFS PCS registers */ 701 582 #define QPHY_V4_PCS_UFS_PHY_START 0x000 ··· 1009 836 #define QPHY_V4_PCS_USB3_SIGDET_STARTUP_TIMER_VAL 0x354 1010 837 #define QPHY_V4_PCS_USB3_TEST_CONTROL 0x358 1011 838 839 + /* Only for QMP V4_20 PHY - USB/PCIe PCS registers */ 840 + #define QPHY_V4_20_PCS_RX_SIGDET_LVL 0x188 841 + #define QPHY_V4_20_PCS_EQ_CONFIG2 0x1d8 842 + #define QPHY_V4_20_PCS_EQ_CONFIG4 0x1e0 843 + #define QPHY_V4_20_PCS_EQ_CONFIG5 0x1e4 844 + 1012 845 /* Only for QMP V4 PHY - UNI has 0x300 offset for PCS_USB3 regs */ 1013 846 #define QPHY_V4_PCS_USB3_UNI_LFPS_DET_HIGH_COUNT_VAL 0x618 1014 847 #define QPHY_V4_PCS_USB3_UNI_RXEQTRAINING_DFE_TIME_S2 0x638 ··· 1039 860 #define QPHY_V4_PCS_PCIE_PRESET_P6_P7_PRE 0xb4 1040 861 #define QPHY_V4_PCS_PCIE_PRESET_P10_PRE 0xbc 1041 862 #define QPHY_V4_PCS_PCIE_PRESET_P10_POST 0xe0 863 + 864 + #define QPHY_V4_20_PCS_PCIE_EQ_CONFIG1 0x0a0 865 + #define QPHY_V4_20_PCS_PCIE_G3_RXEQEVAL_TIME 0x0f0 866 + #define QPHY_V4_20_PCS_PCIE_G4_RXEQEVAL_TIME 0x0f4 867 + #define QPHY_V4_20_PCS_PCIE_G4_EQ_CONFIG2 0x0fc 868 + #define QPHY_V4_20_PCS_PCIE_G4_EQ_CONFIG5 0x108 869 + #define QPHY_V4_20_PCS_LANE1_INSIG_SW_CTRL2 0x824 870 + #define QPHY_V4_20_PCS_LANE1_INSIG_MX_CTRL2 0x828 1042 871 1043 872 /* Only for QMP V5 PHY - QSERDES COM registers */ 1044 873 #define QSERDES_V5_COM_PLL_IVCO 0x058
+1 -1
drivers/phy/ralink/Kconfig
··· 4 4 # 5 5 config PHY_MT7621_PCI 6 6 tristate "MediaTek MT7621 PCI PHY Driver" 7 - depends on RALINK && OF 7 + depends on (RALINK && OF) || COMPILE_TEST 8 8 select GENERIC_PHY 9 9 select REGMAP_MMIO 10 10 help
+22 -15
drivers/phy/ralink/phy-mt7621-pci.c
··· 5 5 */ 6 6 7 7 #include <dt-bindings/phy/phy.h> 8 + #include <linux/clk.h> 8 9 #include <linux/bitfield.h> 9 10 #include <linux/bitops.h> 10 11 #include <linux/module.h> ··· 15 14 #include <linux/platform_device.h> 16 15 #include <linux/regmap.h> 17 16 #include <linux/sys_soc.h> 18 - #include <mt7621.h> 19 - #include <ralink_regs.h> 20 17 21 18 #define RG_PE1_PIPE_REG 0x02c 22 19 #define RG_PE1_PIPE_RST BIT(12) ··· 61 62 62 63 #define RG_PE1_FRC_MSTCKDIV BIT(5) 63 64 64 - #define XTAL_MASK GENMASK(8, 6) 65 - 66 65 #define MAX_PHYS 2 67 66 68 67 /** ··· 68 71 * @dev: pointer to device 69 72 * @regmap: kernel regmap pointer 70 73 * @phy: pointer to the kernel PHY device 74 + * @sys_clk: pointer to the system XTAL clock 71 75 * @port_base: base register 72 76 * @has_dual_port: if the phy has dual ports. 73 77 * @bypass_pipe_rst: mark if 'mt7621_bypass_pipe_rst' ··· 78 80 struct device *dev; 79 81 struct regmap *regmap; 80 82 struct phy *phy; 83 + struct clk *sys_clk; 81 84 void __iomem *port_base; 82 85 bool has_dual_port; 83 86 bool bypass_pipe_rst; ··· 115 116 } 116 117 } 117 118 118 - static void mt7621_set_phy_for_ssc(struct mt7621_pci_phy *phy) 119 + static int mt7621_set_phy_for_ssc(struct mt7621_pci_phy *phy) 119 120 { 120 121 struct device *dev = phy->dev; 121 - u32 xtal_mode; 122 + unsigned long clk_rate; 122 123 123 - xtal_mode = FIELD_GET(XTAL_MASK, rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG0)); 124 + clk_rate = clk_get_rate(phy->sys_clk); 125 + if (!clk_rate) 126 + return -EINVAL; 124 127 125 128 /* Set PCIe Port PHY to disable SSC */ 126 129 /* Debug Xtal Type */ ··· 140 139 RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); 141 140 } 142 141 143 - if (xtal_mode <= 5 && xtal_mode >= 3) { /* 40MHz Xtal */ 142 + if (clk_rate == 40000000) { /* 40MHz Xtal */ 144 143 /* Set Pre-divider ratio (for host mode) */ 145 144 mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, RG_PE1_H_PLL_PREDIV, 146 145 FIELD_PREP(RG_PE1_H_PLL_PREDIV, 0x01)); 147 146 148 147 dev_dbg(dev, "Xtal is 40MHz\n"); 149 - } else if (xtal_mode >= 6) { /* 25MHz Xal */ 148 + } else if (clk_rate == 25000000) { /* 25MHz Xal */ 150 149 mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, RG_PE1_H_PLL_PREDIV, 151 150 FIELD_PREP(RG_PE1_H_PLL_PREDIV, 0x00)); 152 151 ··· 197 196 mt7621_phy_rmw(phy, RG_PE1_H_PLL_BR_REG, RG_PE1_H_PLL_BR, 198 197 FIELD_PREP(RG_PE1_H_PLL_BR, 0x00)); 199 198 200 - if (xtal_mode <= 5 && xtal_mode >= 3) { /* 40MHz Xtal */ 199 + if (clk_rate == 40000000) { /* 40MHz Xtal */ 201 200 /* set force mode enable of da_pe1_mstckdiv */ 202 201 mt7621_phy_rmw(phy, RG_PE1_MSTCKDIV_REG, 203 202 RG_PE1_MSTCKDIV | RG_PE1_FRC_MSTCKDIV, 204 203 FIELD_PREP(RG_PE1_MSTCKDIV, 0x01) | 205 204 RG_PE1_FRC_MSTCKDIV); 206 205 } 206 + 207 + return 0; 207 208 } 208 209 209 210 static int mt7621_pci_phy_init(struct phy *phy) ··· 215 212 if (mphy->bypass_pipe_rst) 216 213 mt7621_bypass_pipe_rst(mphy); 217 214 218 - mt7621_set_phy_for_ssc(mphy); 219 - 220 - return 0; 215 + return mt7621_set_phy_for_ssc(mphy); 221 216 } 222 217 223 218 static int mt7621_pci_phy_power_on(struct phy *phy) ··· 273 272 274 273 mt7621_phy->has_dual_port = args->args[0]; 275 274 276 - dev_info(dev, "PHY for 0x%08x (dual port = %d)\n", 277 - (unsigned int)mt7621_phy->port_base, mt7621_phy->has_dual_port); 275 + dev_dbg(dev, "PHY for 0x%px (dual port = %d)\n", 276 + mt7621_phy->port_base, mt7621_phy->has_dual_port); 278 277 279 278 return mt7621_phy->phy; 280 279 } ··· 323 322 if (IS_ERR(phy->phy)) { 324 323 dev_err(dev, "failed to create phy\n"); 325 324 return PTR_ERR(phy->phy); 325 + } 326 + 327 + phy->sys_clk = devm_clk_get(dev, NULL); 328 + if (IS_ERR(phy->sys_clk)) { 329 + dev_err(dev, "failed to get phy clock\n"); 330 + return PTR_ERR(phy->sys_clk); 326 331 } 327 332 328 333 phy_set_drvdata(phy->phy, phy);
+9
drivers/phy/rockchip/Kconfig
··· 48 48 help 49 49 Support for Rockchip USB2.0 PHY with Innosilicon IP block. 50 50 51 + config PHY_ROCKCHIP_INNO_CSIDPHY 52 + tristate "Rockchip Innosilicon MIPI CSI PHY driver" 53 + depends on (ARCH_ROCKCHIP || COMPILE_TEST) && OF 54 + select GENERIC_PHY 55 + select GENERIC_PHY_MIPI_DPHY 56 + help 57 + Enable this to support the Rockchip MIPI CSI PHY with 58 + Innosilicon IP block. 59 + 51 60 config PHY_ROCKCHIP_INNO_DSIDPHY 52 61 tristate "Rockchip Innosilicon MIPI/LVDS/TTL PHY driver" 53 62 depends on (ARCH_ROCKCHIP || COMPILE_TEST) && OF
+1
drivers/phy/rockchip/Makefile
··· 2 2 obj-$(CONFIG_PHY_ROCKCHIP_DP) += phy-rockchip-dp.o 3 3 obj-$(CONFIG_PHY_ROCKCHIP_DPHY_RX0) += phy-rockchip-dphy-rx0.o 4 4 obj-$(CONFIG_PHY_ROCKCHIP_EMMC) += phy-rockchip-emmc.o 5 + obj-$(CONFIG_PHY_ROCKCHIP_INNO_CSIDPHY) += phy-rockchip-inno-csidphy.o 5 6 obj-$(CONFIG_PHY_ROCKCHIP_INNO_DSIDPHY) += phy-rockchip-inno-dsidphy.o 6 7 obj-$(CONFIG_PHY_ROCKCHIP_INNO_HDMI) += phy-rockchip-inno-hdmi.o 7 8 obj-$(CONFIG_PHY_ROCKCHIP_INNO_USB2) += phy-rockchip-inno-usb2.o
+459
drivers/phy/rockchip/phy-rockchip-inno-csidphy.c
··· 1 + // SPDX-License-Identifier: GPL-2.0 2 + /* 3 + * Rockchip MIPI RX Innosilicon DPHY driver 4 + * 5 + * Copyright (C) 2021 Fuzhou Rockchip Electronics Co., Ltd. 6 + */ 7 + 8 + #include <linux/bitfield.h> 9 + #include <linux/clk.h> 10 + #include <linux/delay.h> 11 + #include <linux/io.h> 12 + #include <linux/mfd/syscon.h> 13 + #include <linux/module.h> 14 + #include <linux/of.h> 15 + #include <linux/of_platform.h> 16 + #include <linux/phy/phy.h> 17 + #include <linux/phy/phy-mipi-dphy.h> 18 + #include <linux/platform_device.h> 19 + #include <linux/pm_runtime.h> 20 + #include <linux/regmap.h> 21 + #include <linux/reset.h> 22 + 23 + /* GRF */ 24 + #define RK1808_GRF_PD_VI_CON_OFFSET 0x0430 25 + 26 + #define RK3326_GRF_PD_VI_CON_OFFSET 0x0430 27 + 28 + #define RK3368_GRF_SOC_CON6_OFFSET 0x0418 29 + 30 + /* PHY */ 31 + #define CSIDPHY_CTRL_LANE_ENABLE 0x00 32 + #define CSIDPHY_CTRL_LANE_ENABLE_CK BIT(6) 33 + #define CSIDPHY_CTRL_LANE_ENABLE_MASK GENMASK(5, 2) 34 + #define CSIDPHY_CTRL_LANE_ENABLE_UNDEFINED BIT(0) 35 + 36 + /* not present on all variants */ 37 + #define CSIDPHY_CTRL_PWRCTL 0x04 38 + #define CSIDPHY_CTRL_PWRCTL_UNDEFINED GENMASK(7, 5) 39 + #define CSIDPHY_CTRL_PWRCTL_SYNCRST BIT(2) 40 + #define CSIDPHY_CTRL_PWRCTL_LDO_PD BIT(1) 41 + #define CSIDPHY_CTRL_PWRCTL_PLL_PD BIT(0) 42 + 43 + #define CSIDPHY_CTRL_DIG_RST 0x80 44 + #define CSIDPHY_CTRL_DIG_RST_UNDEFINED 0x1e 45 + #define CSIDPHY_CTRL_DIG_RST_RESET BIT(0) 46 + 47 + /* offset after ths_settle_offset */ 48 + #define CSIDPHY_CLK_THS_SETTLE 0 49 + #define CSIDPHY_LANE_THS_SETTLE(n) (((n) + 1) * 0x80) 50 + #define CSIDPHY_THS_SETTLE_MASK GENMASK(6, 0) 51 + 52 + /* offset after calib_offset */ 53 + #define CSIDPHY_CLK_CALIB_EN 0 54 + #define CSIDPHY_LANE_CALIB_EN(n) (((n) + 1) * 0x80) 55 + #define CSIDPHY_CALIB_EN BIT(7) 56 + 57 + /* Configure the count time of the THS-SETTLE by protocol. */ 58 + #define RK1808_CSIDPHY_CLK_WR_THS_SETTLE 0x160 59 + #define RK3326_CSIDPHY_CLK_WR_THS_SETTLE 0x100 60 + #define RK3368_CSIDPHY_CLK_WR_THS_SETTLE 0x100 61 + 62 + /* Calibration reception enable */ 63 + #define RK1808_CSIDPHY_CLK_CALIB_EN 0x168 64 + 65 + /* 66 + * The higher 16-bit of this register is used for write protection 67 + * only if BIT(x + 16) set to 1 the BIT(x) can be written. 68 + */ 69 + #define HIWORD_UPDATE(val, mask, shift) \ 70 + ((val) << (shift) | (mask) << ((shift) + 16)) 71 + 72 + #define HZ_TO_MHZ(freq) div_u64(freq, 1000 * 1000) 73 + 74 + enum dphy_reg_id { 75 + /* rk1808 & rk3326 */ 76 + GRF_DPHY_CSIPHY_FORCERXMODE, 77 + GRF_DPHY_CSIPHY_CLKLANE_EN, 78 + GRF_DPHY_CSIPHY_DATALANE_EN, 79 + }; 80 + 81 + struct dphy_reg { 82 + u32 offset; 83 + u32 mask; 84 + u32 shift; 85 + }; 86 + 87 + #define PHY_REG(_offset, _width, _shift) \ 88 + { .offset = _offset, .mask = BIT(_width) - 1, .shift = _shift, } 89 + 90 + static const struct dphy_reg rk1808_grf_dphy_regs[] = { 91 + [GRF_DPHY_CSIPHY_FORCERXMODE] = PHY_REG(RK1808_GRF_PD_VI_CON_OFFSET, 4, 0), 92 + [GRF_DPHY_CSIPHY_CLKLANE_EN] = PHY_REG(RK1808_GRF_PD_VI_CON_OFFSET, 1, 8), 93 + [GRF_DPHY_CSIPHY_DATALANE_EN] = PHY_REG(RK1808_GRF_PD_VI_CON_OFFSET, 4, 4), 94 + }; 95 + 96 + static const struct dphy_reg rk3326_grf_dphy_regs[] = { 97 + [GRF_DPHY_CSIPHY_FORCERXMODE] = PHY_REG(RK3326_GRF_PD_VI_CON_OFFSET, 4, 0), 98 + [GRF_DPHY_CSIPHY_CLKLANE_EN] = PHY_REG(RK3326_GRF_PD_VI_CON_OFFSET, 1, 8), 99 + [GRF_DPHY_CSIPHY_DATALANE_EN] = PHY_REG(RK3326_GRF_PD_VI_CON_OFFSET, 4, 4), 100 + }; 101 + 102 + static const struct dphy_reg rk3368_grf_dphy_regs[] = { 103 + [GRF_DPHY_CSIPHY_FORCERXMODE] = PHY_REG(RK3368_GRF_SOC_CON6_OFFSET, 4, 8), 104 + }; 105 + 106 + struct hsfreq_range { 107 + u32 range_h; 108 + u8 cfg_bit; 109 + }; 110 + 111 + struct dphy_drv_data { 112 + int pwrctl_offset; 113 + int ths_settle_offset; 114 + int calib_offset; 115 + const struct hsfreq_range *hsfreq_ranges; 116 + int num_hsfreq_ranges; 117 + const struct dphy_reg *grf_regs; 118 + }; 119 + 120 + struct rockchip_inno_csidphy { 121 + struct device *dev; 122 + void __iomem *phy_base; 123 + struct clk *pclk; 124 + struct regmap *grf; 125 + struct reset_control *rst; 126 + const struct dphy_drv_data *drv_data; 127 + struct phy_configure_opts_mipi_dphy config; 128 + u8 hsfreq; 129 + }; 130 + 131 + static inline void write_grf_reg(struct rockchip_inno_csidphy *priv, 132 + int index, u8 value) 133 + { 134 + const struct dphy_drv_data *drv_data = priv->drv_data; 135 + const struct dphy_reg *reg = &drv_data->grf_regs[index]; 136 + 137 + if (reg->offset) 138 + regmap_write(priv->grf, reg->offset, 139 + HIWORD_UPDATE(value, reg->mask, reg->shift)); 140 + } 141 + 142 + /* These tables must be sorted by .range_h ascending. */ 143 + static const struct hsfreq_range rk1808_mipidphy_hsfreq_ranges[] = { 144 + { 109, 0x02}, { 149, 0x03}, { 199, 0x06}, { 249, 0x06}, 145 + { 299, 0x06}, { 399, 0x08}, { 499, 0x0b}, { 599, 0x0e}, 146 + { 699, 0x10}, { 799, 0x12}, { 999, 0x16}, {1199, 0x1e}, 147 + {1399, 0x23}, {1599, 0x2d}, {1799, 0x32}, {1999, 0x37}, 148 + {2199, 0x3c}, {2399, 0x41}, {2499, 0x46} 149 + }; 150 + 151 + static const struct hsfreq_range rk3326_mipidphy_hsfreq_ranges[] = { 152 + { 109, 0x00}, { 149, 0x01}, { 199, 0x02}, { 249, 0x03}, 153 + { 299, 0x04}, { 399, 0x05}, { 499, 0x06}, { 599, 0x07}, 154 + { 699, 0x08}, { 799, 0x09}, { 899, 0x0a}, {1099, 0x0b}, 155 + {1249, 0x0c}, {1349, 0x0d}, {1500, 0x0e} 156 + }; 157 + 158 + static const struct hsfreq_range rk3368_mipidphy_hsfreq_ranges[] = { 159 + { 109, 0x00}, { 149, 0x01}, { 199, 0x02}, { 249, 0x03}, 160 + { 299, 0x04}, { 399, 0x05}, { 499, 0x06}, { 599, 0x07}, 161 + { 699, 0x08}, { 799, 0x09}, { 899, 0x0a}, {1099, 0x0b}, 162 + {1249, 0x0c}, {1349, 0x0d}, {1500, 0x0e} 163 + }; 164 + 165 + static void rockchip_inno_csidphy_ths_settle(struct rockchip_inno_csidphy *priv, 166 + int hsfreq, int offset) 167 + { 168 + const struct dphy_drv_data *drv_data = priv->drv_data; 169 + u32 val; 170 + 171 + val = readl(priv->phy_base + drv_data->ths_settle_offset + offset); 172 + val &= ~CSIDPHY_THS_SETTLE_MASK; 173 + val |= hsfreq; 174 + writel(val, priv->phy_base + drv_data->ths_settle_offset + offset); 175 + } 176 + 177 + static int rockchip_inno_csidphy_configure(struct phy *phy, 178 + union phy_configure_opts *opts) 179 + { 180 + struct rockchip_inno_csidphy *priv = phy_get_drvdata(phy); 181 + const struct dphy_drv_data *drv_data = priv->drv_data; 182 + struct phy_configure_opts_mipi_dphy *config = &opts->mipi_dphy; 183 + unsigned int hsfreq = 0; 184 + unsigned int i; 185 + u64 data_rate_mbps; 186 + int ret; 187 + 188 + /* pass with phy_mipi_dphy_get_default_config (with pixel rate?) */ 189 + ret = phy_mipi_dphy_config_validate(config); 190 + if (ret) 191 + return ret; 192 + 193 + data_rate_mbps = HZ_TO_MHZ(config->hs_clk_rate); 194 + 195 + dev_dbg(priv->dev, "lanes %d - data_rate_mbps %llu\n", 196 + config->lanes, data_rate_mbps); 197 + for (i = 0; i < drv_data->num_hsfreq_ranges; i++) { 198 + if (drv_data->hsfreq_ranges[i].range_h >= data_rate_mbps) { 199 + hsfreq = drv_data->hsfreq_ranges[i].cfg_bit; 200 + break; 201 + } 202 + } 203 + if (!hsfreq) 204 + return -EINVAL; 205 + 206 + priv->hsfreq = hsfreq; 207 + priv->config = *config; 208 + return 0; 209 + } 210 + 211 + static int rockchip_inno_csidphy_power_on(struct phy *phy) 212 + { 213 + struct rockchip_inno_csidphy *priv = phy_get_drvdata(phy); 214 + const struct dphy_drv_data *drv_data = priv->drv_data; 215 + u64 data_rate_mbps = HZ_TO_MHZ(priv->config.hs_clk_rate); 216 + u32 val; 217 + int ret, i; 218 + 219 + ret = clk_enable(priv->pclk); 220 + if (ret < 0) 221 + return ret; 222 + 223 + ret = pm_runtime_resume_and_get(priv->dev); 224 + if (ret < 0) { 225 + clk_disable(priv->pclk); 226 + return ret; 227 + } 228 + 229 + /* phy start */ 230 + if (drv_data->pwrctl_offset >= 0) 231 + writel(CSIDPHY_CTRL_PWRCTL_UNDEFINED | 232 + CSIDPHY_CTRL_PWRCTL_SYNCRST, 233 + priv->phy_base + drv_data->pwrctl_offset); 234 + 235 + /* set data lane num and enable clock lane */ 236 + val = FIELD_PREP(CSIDPHY_CTRL_LANE_ENABLE_MASK, GENMASK(priv->config.lanes - 1, 0)) | 237 + FIELD_PREP(CSIDPHY_CTRL_LANE_ENABLE_CK, 1) | 238 + FIELD_PREP(CSIDPHY_CTRL_LANE_ENABLE_UNDEFINED, 1); 239 + writel(val, priv->phy_base + CSIDPHY_CTRL_LANE_ENABLE); 240 + 241 + /* Reset dphy analog part */ 242 + if (drv_data->pwrctl_offset >= 0) 243 + writel(CSIDPHY_CTRL_PWRCTL_UNDEFINED, 244 + priv->phy_base + drv_data->pwrctl_offset); 245 + usleep_range(500, 1000); 246 + 247 + /* Reset dphy digital part */ 248 + writel(CSIDPHY_CTRL_DIG_RST_UNDEFINED, 249 + priv->phy_base + CSIDPHY_CTRL_DIG_RST); 250 + writel(CSIDPHY_CTRL_DIG_RST_UNDEFINED + CSIDPHY_CTRL_DIG_RST_RESET, 251 + priv->phy_base + CSIDPHY_CTRL_DIG_RST); 252 + 253 + /* not into receive mode/wait stopstate */ 254 + write_grf_reg(priv, GRF_DPHY_CSIPHY_FORCERXMODE, 0x0); 255 + 256 + /* enable calibration */ 257 + if (data_rate_mbps > 1500 && drv_data->calib_offset >= 0) { 258 + writel(CSIDPHY_CALIB_EN, 259 + priv->phy_base + drv_data->calib_offset + 260 + CSIDPHY_CLK_CALIB_EN); 261 + for (i = 0; i < priv->config.lanes; i++) 262 + writel(CSIDPHY_CALIB_EN, 263 + priv->phy_base + drv_data->calib_offset + 264 + CSIDPHY_LANE_CALIB_EN(i)); 265 + } 266 + 267 + rockchip_inno_csidphy_ths_settle(priv, priv->hsfreq, 268 + CSIDPHY_CLK_THS_SETTLE); 269 + for (i = 0; i < priv->config.lanes; i++) 270 + rockchip_inno_csidphy_ths_settle(priv, priv->hsfreq, 271 + CSIDPHY_LANE_THS_SETTLE(i)); 272 + 273 + write_grf_reg(priv, GRF_DPHY_CSIPHY_CLKLANE_EN, 0x1); 274 + write_grf_reg(priv, GRF_DPHY_CSIPHY_DATALANE_EN, 275 + GENMASK(priv->config.lanes - 1, 0)); 276 + 277 + return 0; 278 + } 279 + 280 + static int rockchip_inno_csidphy_power_off(struct phy *phy) 281 + { 282 + struct rockchip_inno_csidphy *priv = phy_get_drvdata(phy); 283 + const struct dphy_drv_data *drv_data = priv->drv_data; 284 + 285 + /* disable all lanes */ 286 + writel(CSIDPHY_CTRL_LANE_ENABLE_UNDEFINED, 287 + priv->phy_base + CSIDPHY_CTRL_LANE_ENABLE); 288 + 289 + /* disable pll and ldo */ 290 + if (drv_data->pwrctl_offset >= 0) 291 + writel(CSIDPHY_CTRL_PWRCTL_UNDEFINED | 292 + CSIDPHY_CTRL_PWRCTL_LDO_PD | 293 + CSIDPHY_CTRL_PWRCTL_PLL_PD, 294 + priv->phy_base + drv_data->pwrctl_offset); 295 + usleep_range(500, 1000); 296 + 297 + pm_runtime_put(priv->dev); 298 + clk_disable(priv->pclk); 299 + 300 + return 0; 301 + } 302 + 303 + static int rockchip_inno_csidphy_init(struct phy *phy) 304 + { 305 + struct rockchip_inno_csidphy *priv = phy_get_drvdata(phy); 306 + 307 + return clk_prepare(priv->pclk); 308 + } 309 + 310 + static int rockchip_inno_csidphy_exit(struct phy *phy) 311 + { 312 + struct rockchip_inno_csidphy *priv = phy_get_drvdata(phy); 313 + 314 + clk_unprepare(priv->pclk); 315 + 316 + return 0; 317 + } 318 + 319 + static const struct phy_ops rockchip_inno_csidphy_ops = { 320 + .power_on = rockchip_inno_csidphy_power_on, 321 + .power_off = rockchip_inno_csidphy_power_off, 322 + .init = rockchip_inno_csidphy_init, 323 + .exit = rockchip_inno_csidphy_exit, 324 + .configure = rockchip_inno_csidphy_configure, 325 + .owner = THIS_MODULE, 326 + }; 327 + 328 + static const struct dphy_drv_data rk1808_mipidphy_drv_data = { 329 + .pwrctl_offset = -1, 330 + .ths_settle_offset = RK1808_CSIDPHY_CLK_WR_THS_SETTLE, 331 + .calib_offset = RK1808_CSIDPHY_CLK_CALIB_EN, 332 + .hsfreq_ranges = rk1808_mipidphy_hsfreq_ranges, 333 + .num_hsfreq_ranges = ARRAY_SIZE(rk1808_mipidphy_hsfreq_ranges), 334 + .grf_regs = rk1808_grf_dphy_regs, 335 + }; 336 + 337 + static const struct dphy_drv_data rk3326_mipidphy_drv_data = { 338 + .pwrctl_offset = CSIDPHY_CTRL_PWRCTL, 339 + .ths_settle_offset = RK3326_CSIDPHY_CLK_WR_THS_SETTLE, 340 + .calib_offset = -1, 341 + .hsfreq_ranges = rk3326_mipidphy_hsfreq_ranges, 342 + .num_hsfreq_ranges = ARRAY_SIZE(rk3326_mipidphy_hsfreq_ranges), 343 + .grf_regs = rk3326_grf_dphy_regs, 344 + }; 345 + 346 + static const struct dphy_drv_data rk3368_mipidphy_drv_data = { 347 + .pwrctl_offset = CSIDPHY_CTRL_PWRCTL, 348 + .ths_settle_offset = RK3368_CSIDPHY_CLK_WR_THS_SETTLE, 349 + .calib_offset = -1, 350 + .hsfreq_ranges = rk3368_mipidphy_hsfreq_ranges, 351 + .num_hsfreq_ranges = ARRAY_SIZE(rk3368_mipidphy_hsfreq_ranges), 352 + .grf_regs = rk3368_grf_dphy_regs, 353 + }; 354 + 355 + static const struct of_device_id rockchip_inno_csidphy_match_id[] = { 356 + { 357 + .compatible = "rockchip,px30-csi-dphy", 358 + .data = &rk3326_mipidphy_drv_data, 359 + }, 360 + { 361 + .compatible = "rockchip,rk1808-csi-dphy", 362 + .data = &rk1808_mipidphy_drv_data, 363 + }, 364 + { 365 + .compatible = "rockchip,rk3326-csi-dphy", 366 + .data = &rk3326_mipidphy_drv_data, 367 + }, 368 + { 369 + .compatible = "rockchip,rk3368-csi-dphy", 370 + .data = &rk3368_mipidphy_drv_data, 371 + }, 372 + {} 373 + }; 374 + MODULE_DEVICE_TABLE(of, rockchip_inno_csidphy_match_id); 375 + 376 + static int rockchip_inno_csidphy_probe(struct platform_device *pdev) 377 + { 378 + struct rockchip_inno_csidphy *priv; 379 + struct device *dev = &pdev->dev; 380 + struct phy_provider *phy_provider; 381 + struct phy *phy; 382 + 383 + priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); 384 + if (!priv) 385 + return -ENOMEM; 386 + 387 + priv->dev = dev; 388 + platform_set_drvdata(pdev, priv); 389 + 390 + priv->drv_data = of_device_get_match_data(dev); 391 + if (!priv->drv_data) { 392 + dev_err(dev, "Can't find device data\n"); 393 + return -ENODEV; 394 + } 395 + 396 + priv->grf = syscon_regmap_lookup_by_phandle(dev->of_node, 397 + "rockchip,grf"); 398 + if (IS_ERR(priv->grf)) { 399 + dev_err(dev, "Can't find GRF syscon\n"); 400 + return PTR_ERR(priv->grf); 401 + } 402 + 403 + priv->phy_base = devm_platform_ioremap_resource(pdev, 0); 404 + if (IS_ERR(priv->phy_base)) 405 + return PTR_ERR(priv->phy_base); 406 + 407 + priv->pclk = devm_clk_get(dev, "pclk"); 408 + if (IS_ERR(priv->pclk)) { 409 + dev_err(dev, "failed to get pclk\n"); 410 + return PTR_ERR(priv->pclk); 411 + } 412 + 413 + priv->rst = devm_reset_control_get(dev, "apb"); 414 + if (IS_ERR(priv->rst)) { 415 + dev_err(dev, "failed to get system reset control\n"); 416 + return PTR_ERR(priv->rst); 417 + } 418 + 419 + phy = devm_phy_create(dev, NULL, &rockchip_inno_csidphy_ops); 420 + if (IS_ERR(phy)) { 421 + dev_err(dev, "failed to create phy\n"); 422 + return PTR_ERR(phy); 423 + } 424 + 425 + phy_set_drvdata(phy, priv); 426 + 427 + phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); 428 + if (IS_ERR(phy_provider)) { 429 + dev_err(dev, "failed to register phy provider\n"); 430 + return PTR_ERR(phy_provider); 431 + } 432 + 433 + pm_runtime_enable(dev); 434 + 435 + return 0; 436 + } 437 + 438 + static int rockchip_inno_csidphy_remove(struct platform_device *pdev) 439 + { 440 + struct rockchip_inno_csidphy *priv = platform_get_drvdata(pdev); 441 + 442 + pm_runtime_disable(priv->dev); 443 + 444 + return 0; 445 + } 446 + 447 + static struct platform_driver rockchip_inno_csidphy_driver = { 448 + .driver = { 449 + .name = "rockchip-inno-csidphy", 450 + .of_match_table = rockchip_inno_csidphy_match_id, 451 + }, 452 + .probe = rockchip_inno_csidphy_probe, 453 + .remove = rockchip_inno_csidphy_remove, 454 + }; 455 + 456 + module_platform_driver(rockchip_inno_csidphy_driver); 457 + MODULE_AUTHOR("Heiko Stuebner <heiko.stuebner@theobroma-systems.com>"); 458 + MODULE_DESCRIPTION("Rockchip MIPI Innosilicon CSI-DPHY driver"); 459 + MODULE_LICENSE("GPL v2");
+2 -2
drivers/phy/rockchip/phy-rockchip-inno-hdmi.c
··· 620 620 unsigned long parent_rate) 621 621 { 622 622 struct inno_hdmi_phy *inno = to_inno_hdmi_phy(hw); 623 - const struct pre_pll_config *cfg = pre_pll_cfg_table; 623 + const struct pre_pll_config *cfg; 624 624 unsigned long tmdsclock = inno_hdmi_phy_get_tmdsclk(inno, rate); 625 625 u32 v; 626 626 int ret; ··· 774 774 unsigned long parent_rate) 775 775 { 776 776 struct inno_hdmi_phy *inno = to_inno_hdmi_phy(hw); 777 - const struct pre_pll_config *cfg = pre_pll_cfg_table; 777 + const struct pre_pll_config *cfg; 778 778 unsigned long tmdsclock = inno_hdmi_phy_get_tmdsclk(inno, rate); 779 779 u32 val; 780 780 int ret;
+44
drivers/phy/rockchip/phy-rockchip-inno-usb2.c
··· 1256 1256 { /* sentinel */ } 1257 1257 }; 1258 1258 1259 + static const struct rockchip_usb2phy_cfg rk3308_phy_cfgs[] = { 1260 + { 1261 + .reg = 0x100, 1262 + .num_ports = 2, 1263 + .clkout_ctl = { 0x108, 4, 4, 1, 0 }, 1264 + .port_cfgs = { 1265 + [USB2PHY_PORT_OTG] = { 1266 + .phy_sus = { 0x0100, 8, 0, 0, 0x1d1 }, 1267 + .bvalid_det_en = { 0x3020, 2, 2, 0, 1 }, 1268 + .bvalid_det_st = { 0x3024, 2, 2, 0, 1 }, 1269 + .bvalid_det_clr = { 0x3028, 2, 2, 0, 1 }, 1270 + .ls_det_en = { 0x3020, 0, 0, 0, 1 }, 1271 + .ls_det_st = { 0x3024, 0, 0, 0, 1 }, 1272 + .ls_det_clr = { 0x3028, 0, 0, 0, 1 }, 1273 + .utmi_avalid = { 0x0120, 10, 10, 0, 1 }, 1274 + .utmi_bvalid = { 0x0120, 9, 9, 0, 1 }, 1275 + .utmi_ls = { 0x0120, 5, 4, 0, 1 }, 1276 + }, 1277 + [USB2PHY_PORT_HOST] = { 1278 + .phy_sus = { 0x0104, 8, 0, 0, 0x1d1 }, 1279 + .ls_det_en = { 0x3020, 1, 1, 0, 1 }, 1280 + .ls_det_st = { 0x3024, 1, 1, 0, 1 }, 1281 + .ls_det_clr = { 0x3028, 1, 1, 0, 1 }, 1282 + .utmi_ls = { 0x0120, 17, 16, 0, 1 }, 1283 + .utmi_hstdet = { 0x0120, 19, 19, 0, 1 } 1284 + } 1285 + }, 1286 + .chg_det = { 1287 + .opmode = { 0x0100, 3, 0, 5, 1 }, 1288 + .cp_det = { 0x0120, 24, 24, 0, 1 }, 1289 + .dcp_det = { 0x0120, 23, 23, 0, 1 }, 1290 + .dp_det = { 0x0120, 25, 25, 0, 1 }, 1291 + .idm_sink_en = { 0x0108, 8, 8, 0, 1 }, 1292 + .idp_sink_en = { 0x0108, 7, 7, 0, 1 }, 1293 + .idp_src_en = { 0x0108, 9, 9, 0, 1 }, 1294 + .rdm_pdwn_en = { 0x0108, 10, 10, 0, 1 }, 1295 + .vdm_src_en = { 0x0108, 12, 12, 0, 1 }, 1296 + .vdp_src_en = { 0x0108, 11, 11, 0, 1 }, 1297 + }, 1298 + }, 1299 + { /* sentinel */ } 1300 + }; 1301 + 1259 1302 static const struct rockchip_usb2phy_cfg rk3328_phy_cfgs[] = { 1260 1303 { 1261 1304 .reg = 0x100, ··· 1468 1425 static const struct of_device_id rockchip_usb2phy_dt_match[] = { 1469 1426 { .compatible = "rockchip,px30-usb2phy", .data = &rk3328_phy_cfgs }, 1470 1427 { .compatible = "rockchip,rk3228-usb2phy", .data = &rk3228_phy_cfgs }, 1428 + { .compatible = "rockchip,rk3308-usb2phy", .data = &rk3308_phy_cfgs }, 1471 1429 { .compatible = "rockchip,rk3328-usb2phy", .data = &rk3328_phy_cfgs }, 1472 1430 { .compatible = "rockchip,rk3366-usb2phy", .data = &rk3366_phy_cfgs }, 1473 1431 { .compatible = "rockchip,rk3399-usb2phy", .data = &rk3399_phy_cfgs },
+7 -4
drivers/phy/socionext/phy-uniphier-pcie.c
··· 24 24 #define PORT_SEL_1 FIELD_PREP(PORT_SEL_MASK, 1) 25 25 26 26 #define PCL_PHY_TEST_I 0x2000 27 - #define PCL_PHY_TEST_O 0x2004 28 27 #define TESTI_DAT_MASK GENMASK(13, 6) 29 28 #define TESTI_ADR_MASK GENMASK(5, 1) 30 29 #define TESTI_WR_EN BIT(0) 30 + 31 + #define PCL_PHY_TEST_O 0x2004 32 + #define TESTO_DAT_MASK GENMASK(7, 0) 31 33 32 34 #define PCL_PHY_RESET 0x200c 33 35 #define PCL_PHY_RESET_N_MNMODE BIT(8) /* =1:manual */ ··· 79 77 val = FIELD_PREP(TESTI_DAT_MASK, 1); 80 78 val |= FIELD_PREP(TESTI_ADR_MASK, reg); 81 79 uniphier_pciephy_testio_write(priv, val); 82 - val = readl(priv->base + PCL_PHY_TEST_O); 80 + val = readl(priv->base + PCL_PHY_TEST_O) & TESTO_DAT_MASK; 83 81 84 82 /* update value */ 85 - val &= ~FIELD_PREP(TESTI_DAT_MASK, mask); 86 - val = FIELD_PREP(TESTI_DAT_MASK, mask & param); 83 + val &= ~mask; 84 + val |= mask & param; 85 + val = FIELD_PREP(TESTI_DAT_MASK, val); 87 86 val |= FIELD_PREP(TESTI_ADR_MASK, reg); 88 87 uniphier_pciephy_testio_write(priv, val); 89 88 uniphier_pciephy_testio_write(priv, val | TESTI_WR_EN);
+31
drivers/phy/st/phy-stm32-usbphyc.c
··· 57 57 struct stm32_usbphyc_phy { 58 58 struct phy *phy; 59 59 struct stm32_usbphyc *usbphyc; 60 + struct regulator *vbus; 60 61 u32 index; 61 62 bool active; 62 63 }; ··· 292 291 return stm32_usbphyc_pll_disable(usbphyc); 293 292 } 294 293 294 + static int stm32_usbphyc_phy_power_on(struct phy *phy) 295 + { 296 + struct stm32_usbphyc_phy *usbphyc_phy = phy_get_drvdata(phy); 297 + 298 + if (usbphyc_phy->vbus) 299 + return regulator_enable(usbphyc_phy->vbus); 300 + 301 + return 0; 302 + } 303 + 304 + static int stm32_usbphyc_phy_power_off(struct phy *phy) 305 + { 306 + struct stm32_usbphyc_phy *usbphyc_phy = phy_get_drvdata(phy); 307 + 308 + if (usbphyc_phy->vbus) 309 + return regulator_disable(usbphyc_phy->vbus); 310 + 311 + return 0; 312 + } 313 + 295 314 static const struct phy_ops stm32_usbphyc_phy_ops = { 296 315 .init = stm32_usbphyc_phy_init, 297 316 .exit = stm32_usbphyc_phy_exit, 317 + .power_on = stm32_usbphyc_phy_power_on, 318 + .power_off = stm32_usbphyc_phy_power_off, 298 319 .owner = THIS_MODULE, 299 320 }; 300 321 ··· 541 518 usbphyc->phys[port]->usbphyc = usbphyc; 542 519 usbphyc->phys[port]->index = index; 543 520 usbphyc->phys[port]->active = false; 521 + 522 + usbphyc->phys[port]->vbus = devm_regulator_get_optional(&phy->dev, "vbus"); 523 + if (IS_ERR(usbphyc->phys[port]->vbus)) { 524 + ret = PTR_ERR(usbphyc->phys[port]->vbus); 525 + if (ret == -EPROBE_DEFER) 526 + goto put_child; 527 + usbphyc->phys[port]->vbus = NULL; 528 + } 544 529 545 530 port++; 546 531 }
+13 -4
drivers/phy/ti/phy-dm816x-usb.c
··· 242 242 243 243 pm_runtime_enable(phy->dev); 244 244 generic_phy = devm_phy_create(phy->dev, NULL, &ops); 245 - if (IS_ERR(generic_phy)) 246 - return PTR_ERR(generic_phy); 245 + if (IS_ERR(generic_phy)) { 246 + error = PTR_ERR(generic_phy); 247 + goto clk_unprepare; 248 + } 247 249 248 250 phy_set_drvdata(generic_phy, phy); 249 251 250 252 phy_provider = devm_of_phy_provider_register(phy->dev, 251 253 of_phy_simple_xlate); 252 - if (IS_ERR(phy_provider)) 253 - return PTR_ERR(phy_provider); 254 + if (IS_ERR(phy_provider)) { 255 + error = PTR_ERR(phy_provider); 256 + goto clk_unprepare; 257 + } 254 258 255 259 usb_add_phy_dev(&phy->phy); 256 260 257 261 return 0; 262 + 263 + clk_unprepare: 264 + pm_runtime_disable(phy->dev); 265 + clk_unprepare(phy->refclk); 266 + return error; 258 267 } 259 268 260 269 static int dm816x_usb_phy_remove(struct platform_device *pdev)
+3 -3
drivers/phy/ti/phy-twl4030-usb.c
··· 544 544 return 0; 545 545 } 546 546 547 - static ssize_t twl4030_usb_vbus_show(struct device *dev, 548 - struct device_attribute *attr, char *buf) 547 + static ssize_t vbus_show(struct device *dev, 548 + struct device_attribute *attr, char *buf) 549 549 { 550 550 struct twl4030_usb *twl = dev_get_drvdata(dev); 551 551 int ret = -EINVAL; ··· 557 557 558 558 return ret; 559 559 } 560 - static DEVICE_ATTR(vbus, 0444, twl4030_usb_vbus_show, NULL); 560 + static DEVICE_ATTR_RO(vbus); 561 561 562 562 static irqreturn_t twl4030_usb_irq(int irq, void *_twl) 563 563 {
+1 -1
include/linux/phy/phy.h
··· 125 125 /** 126 126 * struct phy_attrs - represents phy attributes 127 127 * @bus_width: Data path width implemented by PHY 128 - * @max_link_rate: Maximum link rate supported by PHY (in Mbps) 128 + * @max_link_rate: Maximum link rate supported by PHY (units to be decided by producer and consumer) 129 129 * @mode: PHY mode 130 130 */ 131 131 struct phy_attrs {