diff options
162 files changed, 4995 insertions, 3964 deletions
diff --git a/Documentation/devicetree/bindings/arm/msm/msm.txt b/Documentation/devicetree/bindings/arm/msm/msm.txt index 53f3d6875e7a..4fadd0ccbcf7 100644 --- a/Documentation/devicetree/bindings/arm/msm/msm.txt +++ b/Documentation/devicetree/bindings/arm/msm/msm.txt @@ -89,15 +89,24 @@ SoCs: - MSMHAMSTER compatible = "qcom,msmhamster" +- SDM658 + compatible = "qcom,sdm658" + - SDM660 compatible = "qcom,sdm660" +- SDA658 + compatible = "qcom,sda658" + - SDA660 compatible = "qcom,sda660" - SDM630 compatible = "qcom,sdm630" +- SDA630 + compatible = "qcom,sda630" + - MSM8952 compatible = "qcom,msm8952" @@ -263,14 +272,23 @@ compatible = "qcom,msm8998-qrd" compatible = "qcom,msmhamster-rumi" compatible = "qcom,msmhamster-cdp" compatible = "qcom,msmhamster-mtp" +compatible = "qcom,sdm658-cdp" +compatible = "qcom,sdm658-mtp" +compatible = "qcom,sdm658-qrd" compatible = "qcom,sdm660-sim" compatible = "qcom,sdm660-rumi" compatible = "qcom,sdm660-cdp" compatible = "qcom,sdm660-mtp" compatible = "qcom,sdm660-qrd" +compatible = "qcom,sda658-mtp" +compatible = "qcom,sda658-cdp" compatible = "qcom,sda660-mtp" compatible = "qcom,sda660-cdp" compatible = "qcom,sdm630-rumi" +compatible = "qcom,sdm630-mtp" +compatible = "qcom,sdm630-cdp" +compatible = "qcom,sda630-mtp" +compatible = "qcom,sda630-cdp" compatible = "qcom,msm8952-rumi" compatible = "qcom,msm8952-sim" compatible = "qcom,msm8952-qrd" diff --git a/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt b/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt index 0299b1aef2b6..52ffbe5c7207 100644 --- a/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt +++ b/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt @@ -37,8 +37,8 @@ Required properties: "display_2" = DISPLAY_2 - qcom,mdss-dsi-panel-timings: An array of length 12 that specifies the PHY timing settings for the panel. -- qcom,mdss-dsi-panel-timings-8996: An array of length 40 char that specifies the 8996 PHY lane - timing settings for the panel. +- qcom,mdss-dsi-panel-timings-phy-v2: An array of length 40 char that specifies the PHY version 2 + lane timing settings for the panel. - qcom,mdss-dsi-on-command: A byte stream formed by multiple dcs packets base on qcom dsi controller protocol. byte 0: dcs data type @@ -638,7 +638,7 @@ Example: qcom,mdss-mdp-transfer-time-us = <12500>; qcom,mdss-dsi-panel-timings = [7d 25 1d 00 37 33 22 27 1e 03 04 00]; - qcom,mdss-dsi-panel-timings-8996 = [23 20 06 09 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 diff --git a/Documentation/devicetree/bindings/power/qcom-charger/qpnp-fg-gen3.txt b/Documentation/devicetree/bindings/power/qcom-charger/qpnp-fg-gen3.txt index ac63b3c3bf01..35d8d0d7d50b 100644 --- a/Documentation/devicetree/bindings/power/qcom-charger/qpnp-fg-gen3.txt +++ b/Documentation/devicetree/bindings/power/qcom-charger/qpnp-fg-gen3.txt @@ -273,6 +273,45 @@ First Level Node - FG Gen3 device is specified, then ESR to Rslow scaling factors will be updated to account it for an accurate ESR. +- qcom,fg-esr-filter-switch-temp + Usage: optional + Value type: <u32> + Definition: Battery temperature threshold below which low temperature + ESR filter coefficients will be switched to normal + temperature ESR filter coefficients. If this is not + specified, then the default value used will be 100. Unit is + in decidegC. + +- qcom,fg-esr-tight-filter-micro-pct + Usage: optional + Value type: <u32> + Definition: Value in micro percentage for ESR tight filter. If this is + not specified, then a default value of 3907 (0.39 %) will + be used. Lowest possible value is 1954 (0.19 %). + +- qcom,fg-esr-broad-filter-micro-pct + Usage: optional + Value type: <u32> + Definition: Value in micro percentage for ESR broad filter. If this is + not specified, then a default value of 99610 (9.96 %) will + be used. Lowest possible value is 1954 (0.19 %). + +- qcom,fg-esr-tight-lt-filter-micro-pct + Usage: optional + Value type: <u32> + Definition: Value in micro percentage for low temperature ESR tight + filter. If this is not specified, then a default value of + 48829 (4.88 %) will be used. Lowest possible value is 1954 + (0.19 %). + +- qcom,fg-esr-broad-lt-filter-micro-pct + Usage: optional + Value type: <u32> + Definition: Value in micro percentage for low temperature ESR broad + filter. If this is not specified, then a default value of + 148438 (14.84 %) will be used. Lowest possible value is + 1954 (0.19 %). + ========================================================== Second Level Nodes - Peripherals managed by FG Gen3 driver ========================================================== diff --git a/Documentation/devicetree/bindings/regulator/cprh-kbss-regulator.txt b/Documentation/devicetree/bindings/regulator/cprh-kbss-regulator.txt index 5b0770785dbe..ff800352cc05 100644 --- a/Documentation/devicetree/bindings/regulator/cprh-kbss-regulator.txt +++ b/Documentation/devicetree/bindings/regulator/cprh-kbss-regulator.txt @@ -33,7 +33,8 @@ KBSS specific properties: Definition: should be one of the following: "qcom,cprh-msm8998-v1-kbss-regulator", "qcom,cprh-msm8998-v2-kbss-regulator", - "qcom,cprh-msm8998-kbss-regulator". + "qcom,cprh-msm8998-kbss-regulator", + "qcom,cprh-sdm660-kbss-regulator". If the SoC revision is not specified, then it is assumed to be the most recent revision of MSM8998, i.e. v2. diff --git a/arch/arm/boot/dts/qcom/Makefile b/arch/arm/boot/dts/qcom/Makefile index 97508071c18b..65c42b8de30c 100644 --- a/arch/arm/boot/dts/qcom/Makefile +++ b/arch/arm/boot/dts/qcom/Makefile @@ -159,10 +159,48 @@ dtb-$(CONFIG_ARCH_SDM660) += sdm660-sim.dtb \ sda660-rcm.dtb \ sda660-pm660a-cdp.dtb \ sda660-pm660a-mtp.dtb \ - sda660-pm660a-rcm.dtb + sda660-pm660a-rcm.dtb \ + sdm658-mtp.dtb \ + sdm658-cdp.dtb \ + sdm658-rcm.dtb \ + sdm658-qrd.dtb \ + sdm658-pm660a-mtp.dtb \ + sdm658-pm660a-cdp.dtb \ + sdm658-pm660a-rcm.dtb \ + sdm658-pm660a-qrd.dtb \ + sdm658-internal-codec-mtp.dtb \ + sdm658-internal-codec-cdp.dtb \ + sdm658-internal-codec-rcm.dtb \ + sdm658-internal-codec-pm660a-mtp.dtb \ + sdm658-internal-codec-pm660a-cdp.dtb \ + sdm658-internal-codec-pm660a-rcm.dtb \ + sda658-cdp.dtb \ + sda658-mtp.dtb \ + sda658-rcm.dtb \ + sda658-pm660a-mtp.dtb \ + sda658-pm660a-cdp.dtb \ + sda658-pm660a-rcm.dtb dtb-$(CONFIG_ARCH_SDM630) += sdm630-rumi.dtb \ - sdm630-pm660a-rumi.dtb + sdm630-pm660a-rumi.dtb \ + sdm630-mtp.dtb \ + sdm630-cdp.dtb \ + sdm630-rcm.dtb \ + sdm630-internal-codec-mtp.dtb \ + sdm630-internal-codec-cdp.dtb \ + sdm630-internal-codec-rcm.dtb \ + sdm630-pm660a-cdp.dtb \ + sdm630-pm660a-mtp.dtb \ + sdm630-pm660a-rcm.dtb \ + sdm630-internal-codec-pm660a-cdp.dtb \ + sdm630-internal-codec-pm660a-mtp.dtb \ + sdm630-internal-codec-pm660a-rcm.dtb \ + sda630-mtp.dtb \ + sda630-cdp.dtb \ + sda630-rcm.dtb \ + sda630-pm660a-mtp.dtb \ + sda630-pm660a-cdp.dtb \ + sda630-pm660a-rcm.dtb ifeq ($(CONFIG_ARM64),y) always := $(dtb-y) diff --git a/arch/arm/boot/dts/qcom/dsi-adv7533-1080p.dtsi b/arch/arm/boot/dts/qcom/dsi-adv7533-1080p.dtsi index d67922a865fb..7994285f13f1 100644 --- a/arch/arm/boot/dts/qcom/dsi-adv7533-1080p.dtsi +++ b/arch/arm/boot/dts/qcom/dsi-adv7533-1080p.dtsi @@ -64,7 +64,7 @@ qcom,mdss-pan-physical-height-dimension = <90>; qcom,mdss-dsi-force-clock-lane-hs; qcom,mdss-dsi-always-on; - qcom,mdss-dsi-panel-timings-8996 = [1d 1a 03 05 01 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [1d 1a 03 05 01 03 04 a0 1d 1a 03 05 01 03 04 a0 1d 1a 03 05 01 03 04 a0 1d 1a 03 05 01 03 04 a0 diff --git a/arch/arm/boot/dts/qcom/dsi-adv7533-720p.dtsi b/arch/arm/boot/dts/qcom/dsi-adv7533-720p.dtsi index f6a42b430b58..b84488c0cef3 100644 --- a/arch/arm/boot/dts/qcom/dsi-adv7533-720p.dtsi +++ b/arch/arm/boot/dts/qcom/dsi-adv7533-720p.dtsi @@ -63,7 +63,7 @@ dsi_adv7533_720p: qcom,mdss_dsi_adv7533_720p { qcom,mdss-pan-physical-height-dimension = <90>; qcom,mdss-dsi-force-clock-lane-hs; qcom,mdss-dsi-always-on; - qcom,mdss-dsi-panel-timings-8996 = [1c 19 02 03 01 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [1c 19 02 03 01 03 04 a0 1c 19 02 03 01 03 04 a0 1c 19 02 03 01 03 04 a0 1c 19 02 03 01 03 04 a0 diff --git a/arch/arm/boot/dts/qcom/dsi-panel-nt35597-truly-dsc-wqxga-cmd.dtsi b/arch/arm/boot/dts/qcom/dsi-panel-nt35597-truly-dsc-wqxga-cmd.dtsi new file mode 100644 index 000000000000..7a3660a3b480 --- /dev/null +++ b/arch/arm/boot/dts/qcom/dsi-panel-nt35597-truly-dsc-wqxga-cmd.dtsi @@ -0,0 +1,266 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +&mdss_mdp { + dsi_nt35597_truly_dsc_video: qcom,mdss_dsi_nt35597_dsc_cmd_truly { + qcom,mdss-dsi-panel-name = + "nt35597 cmd mode dsi truly panel with DSC"; + qcom,mdss-dsi-panel-type = "dsi_cmd_mode"; + qcom,mdss-dsi-panel-framerate = <60>; + qcom,mdss-dsi-virtual-channel-id = <0>; + qcom,mdss-dsi-stream = <0>; + qcom,mdss-dsi-panel-width = <1440>; + qcom,mdss-dsi-panel-height = <2560>; + qcom,mdss-dsi-h-front-porch = <100>; + qcom,mdss-dsi-h-back-porch = <32>; + qcom,mdss-dsi-h-pulse-width = <16>; + qcom,mdss-dsi-h-sync-skew = <0>; + qcom,mdss-dsi-v-back-porch = <8>; + qcom,mdss-dsi-v-front-porch = <10>; + qcom,mdss-dsi-v-pulse-width = <2>; + qcom,mdss-dsi-h-left-border = <0>; + qcom,mdss-dsi-h-right-border = <0>; + qcom,mdss-dsi-v-top-border = <0>; + qcom,mdss-dsi-v-bottom-border = <0>; + qcom,mdss-dsi-bpp = <24>; + qcom,mdss-dsi-color-order = "rgb_swap_rgb"; + qcom,mdss-dsi-underflow-color = <0xff>; + qcom,mdss-dsi-border-color = <0>; + qcom,mdss-dsi-on-command = [ + /* CMD2_P0 */ + 15 01 00 00 10 00 02 ff 20 + 15 01 00 00 10 00 02 fb 01 + 15 01 00 00 10 00 02 00 01 + 15 01 00 00 10 00 02 01 55 + 15 01 00 00 10 00 02 02 45 + 15 01 00 00 10 00 02 05 40 + 15 01 00 00 10 00 02 06 19 + 15 01 00 00 10 00 02 07 1e + 15 01 00 00 10 00 02 0b 73 + 15 01 00 00 10 00 02 0c 73 + 15 01 00 00 10 00 02 0e b0 + 15 01 00 00 10 00 02 0f ae + 15 01 00 00 10 00 02 11 b8 + 15 01 00 00 10 00 02 13 00 + 15 01 00 00 10 00 02 58 80 + 15 01 00 00 10 00 02 59 01 + 15 01 00 00 10 00 02 5a 00 + 15 01 00 00 10 00 02 5b 01 + 15 01 00 00 10 00 02 5c 80 + 15 01 00 00 10 00 02 5d 81 + 15 01 00 00 10 00 02 5e 00 + 15 01 00 00 10 00 02 5f 01 + 15 01 00 00 10 00 02 72 31 + 15 01 00 00 10 00 02 68 03 + /* CMD2_P4 */ + 15 01 00 00 10 00 02 ff 24 + 15 01 00 00 10 00 02 fb 01 + 15 01 00 00 10 00 02 00 1c + 15 01 00 00 10 00 02 01 0b + 15 01 00 00 10 00 02 02 0c + 15 01 00 00 10 00 02 03 01 + 15 01 00 00 10 00 02 04 0f + 15 01 00 00 10 00 02 05 10 + 15 01 00 00 10 00 02 06 10 + 15 01 00 00 10 00 02 07 10 + 15 01 00 00 10 00 02 08 89 + 15 01 00 00 10 00 02 09 8a + 15 01 00 00 10 00 02 0a 13 + 15 01 00 00 10 00 02 0b 13 + 15 01 00 00 10 00 02 0c 15 + 15 01 00 00 10 00 02 0d 15 + 15 01 00 00 10 00 02 0e 17 + 15 01 00 00 10 00 02 0f 17 + 15 01 00 00 10 00 02 10 1c + 15 01 00 00 10 00 02 11 0b + 15 01 00 00 10 00 02 12 0c + 15 01 00 00 10 00 02 13 01 + 15 01 00 00 10 00 02 14 0f + 15 01 00 00 10 00 02 15 10 + 15 01 00 00 10 00 02 16 10 + 15 01 00 00 10 00 02 17 10 + 15 01 00 00 10 00 02 18 89 + 15 01 00 00 10 00 02 19 8a + 15 01 00 00 10 00 02 1a 13 + 15 01 00 00 10 00 02 1b 13 + 15 01 00 00 10 00 02 1c 15 + 15 01 00 00 10 00 02 1d 15 + 15 01 00 00 10 00 02 1e 17 + 15 01 00 00 10 00 02 1f 17 + /* STV */ + 15 01 00 00 10 00 02 20 40 + 15 01 00 00 10 00 02 21 01 + 15 01 00 00 10 00 02 22 00 + 15 01 00 00 10 00 02 23 40 + 15 01 00 00 10 00 02 24 40 + 15 01 00 00 10 00 02 25 6d + 15 01 00 00 10 00 02 26 40 + 15 01 00 00 10 00 02 27 40 + /* Vend */ + 15 01 00 00 10 00 02 e0 00 + 15 01 00 00 10 00 02 dc 21 + 15 01 00 00 10 00 02 dd 22 + 15 01 00 00 10 00 02 de 07 + 15 01 00 00 10 00 02 df 07 + 15 01 00 00 10 00 02 e3 6D + 15 01 00 00 10 00 02 e1 07 + 15 01 00 00 10 00 02 e2 07 + /* UD */ + 15 01 00 00 10 00 02 29 d8 + 15 01 00 00 10 00 02 2a 2a + /* CLK */ + 15 01 00 00 10 00 02 4b 03 + 15 01 00 00 10 00 02 4c 11 + 15 01 00 00 10 00 02 4d 10 + 15 01 00 00 10 00 02 4e 01 + 15 01 00 00 10 00 02 4f 01 + 15 01 00 00 10 00 02 50 10 + 15 01 00 00 10 00 02 51 00 + 15 01 00 00 10 00 02 52 80 + 15 01 00 00 10 00 02 53 00 + 15 01 00 00 10 00 02 56 00 + 15 01 00 00 10 00 02 54 07 + 15 01 00 00 10 00 02 58 07 + 15 01 00 00 10 00 02 55 25 + /* Reset XDONB */ + 15 01 00 00 10 00 02 5b 43 + 15 01 00 00 10 00 02 5c 00 + 15 01 00 00 10 00 02 5f 73 + 15 01 00 00 10 00 02 60 73 + 15 01 00 00 10 00 02 63 22 + 15 01 00 00 10 00 02 64 00 + 15 01 00 00 10 00 02 67 08 + 15 01 00 00 10 00 02 68 04 + /* Resolution:1440x2560*/ + 15 01 00 00 10 00 02 72 02 + /* mux */ + 15 01 00 00 10 00 02 7a 80 + 15 01 00 00 10 00 02 7b 91 + 15 01 00 00 10 00 02 7c D8 + 15 01 00 00 10 00 02 7d 60 + 15 01 00 00 10 00 02 7f 15 + 15 01 00 00 10 00 02 75 15 + /* ABOFF */ + 15 01 00 00 10 00 02 b3 C0 + 15 01 00 00 10 00 02 b4 00 + 15 01 00 00 10 00 02 b5 00 + /* Source EQ */ + 15 01 00 00 10 00 02 78 00 + 15 01 00 00 10 00 02 79 00 + 15 01 00 00 10 00 02 80 00 + 15 01 00 00 10 00 02 83 00 + /* FP BP */ + 15 01 00 00 10 00 02 93 0a + 15 01 00 00 10 00 02 94 0a + /* Inversion Type */ + 15 01 00 00 10 00 02 8a 00 + 15 01 00 00 10 00 02 9b ff + /* IMGSWAP =1 @PortSwap=1 */ + 15 01 00 00 10 00 02 9d b0 + 15 01 00 00 10 00 02 9f 63 + 15 01 00 00 10 00 02 98 10 + /* FRM */ + 15 01 00 00 10 00 02 ec 00 + /* CMD1 */ + 15 01 00 00 10 00 02 ff 10 + /* VESA DSC PPS settings(1440x2560 slide 16H) */ + 39 01 00 00 10 00 11 c1 09 20 00 10 02 00 02 68 + 01 bb 00 0a 06 67 04 c5 + 39 01 00 00 10 00 03 c2 10 f0 + /* C0h = 0x0(2 Port SDC)0x01(1 PortA FBC) + * 0x02(MTK) 0x03(1 PortA VESA) + */ + 15 01 00 00 10 00 02 c0 03 + /* VBP+VSA=,VFP = 10H */ + 15 01 00 00 10 00 04 3b 03 0a 0a + /* FTE on */ + 15 01 00 00 10 00 02 35 00 + /* EN_BK =1(auto black) */ + 15 01 00 00 10 00 02 e5 01 + /* CMD mode(10) VDO mode(03) */ + 15 01 00 00 10 00 02 bb 10 + /* Non Reload MTP */ + 15 01 00 00 10 00 02 fb 01 + /* SlpOut + DispOn */ + 05 01 00 00 a0 00 02 11 00 + 05 01 00 00 a0 00 02 29 00 + ]; + qcom,mdss-dsi-off-command = [05 01 00 00 78 00 02 28 00 + 05 01 00 00 78 00 02 10 00]; + + qcom,mdss-dsi-on-command-state = "dsi_hs_mode"; + qcom,mdss-dsi-off-command-state = "dsi_hs_mode"; + qcom,mdss-dsi-h-sync-pulse = <0>; + qcom,mdss-dsi-traffic-mode = "non_burst_sync_event"; + qcom,mdss-dsi-bllp-eof-power-mode; + qcom,mdss-dsi-bllp-power-mode; + qcom,mdss-dsi-lane-0-state; + qcom,mdss-dsi-lane-1-state; + qcom,mdss-dsi-lane-2-state; + qcom,mdss-dsi-lane-3-state; + qcom,mdss-dsi-panel-timings = [cd 32 22 00 60 64 26 34 29 03 + 04 00]; + qcom,mdss-dsi-t-clk-post = <0x0b>; + qcom,mdss-dsi-t-clk-pre = <0x23>; + qcom,mdss-dsi-dma-trigger = "trigger_sw"; + qcom,mdss-dsi-mdp-trigger = "none"; + qcom,mdss-dsi-reset-sequence = <1 10>, <0 10>, <1 10>; + + qcom,mdss-dsi-bl-max-level = <4095>; + qcom,adjust-timer-wakeup-ms = <1>; + qcom,mdss-dsi-te-pin-select = <1>; + qcom,mdss-dsi-wr-mem-start = <0x2c>; + qcom,mdss-dsi-wr-mem-continue = <0x3c>; + qcom,mdss-dsi-te-dcs-command = <1>; + qcom,mdss-dsi-te-check-enable; + qcom,mdss-dsi-te-using-te-pin; + qcom,ulps-enabled; + + qcom,compression-mode = "dsc"; + qcom,config-select = <&dsi_nt35597_truly_dsc_cmd_config0>; + + dsi_nt35597_truly_dsc_cmd_config0: config0 { + qcom,mdss-dsc-encoders = <1>; + qcom,mdss-dsc-slice-height = <16>; + qcom,mdss-dsc-slice-width = <720>; + qcom,mdss-dsc-slice-per-pkt = <2>; + + qcom,mdss-dsc-bit-per-component = <8>; + qcom,mdss-dsc-bit-per-pixel = <8>; + qcom,mdss-dsc-block-prediction-enable; + }; + + dsi_nt35597_truly_dsc_cmd_config1: config1 { + qcom,lm-split = <720 720>; + qcom,mdss-dsc-encoders = <1>; /* 3D Mux */ + qcom,mdss-dsc-slice-height = <16>; + qcom,mdss-dsc-slice-width = <720>; + qcom,mdss-dsc-slice-per-pkt = <2>; + + qcom,mdss-dsc-bit-per-component = <8>; + qcom,mdss-dsc-bit-per-pixel = <8>; + qcom,mdss-dsc-block-prediction-enable; + }; + + dsi_nt35597_truly_dsc_cmd_config2: config2 { + qcom,lm-split = <720 720>; + qcom,mdss-dsc-encoders = <2>; /* DSC Merge */ + qcom,mdss-dsc-slice-height = <16>; + qcom,mdss-dsc-slice-width = <720>; + qcom,mdss-dsc-slice-per-pkt = <2>; + + qcom,mdss-dsc-bit-per-component = <8>; + qcom,mdss-dsc-bit-per-pixel = <8>; + qcom,mdss-dsc-block-prediction-enable; + }; + }; +}; diff --git a/arch/arm/boot/dts/qcom/dsi-panel-nt35597-truly-dsc-wqxga-video.dtsi b/arch/arm/boot/dts/qcom/dsi-panel-nt35597-truly-dsc-wqxga-video.dtsi new file mode 100644 index 000000000000..ca2ff6eb4924 --- /dev/null +++ b/arch/arm/boot/dts/qcom/dsi-panel-nt35597-truly-dsc-wqxga-video.dtsi @@ -0,0 +1,252 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +&mdss_mdp { + dsi_nt35597_truly_dsc_video: qcom,mdss_dsi_nt35597_dsc_video_truly { + qcom,mdss-dsi-panel-name = + "nt35597 video mode dsi truly panel with DSC"; + qcom,mdss-dsi-panel-type = "dsi_video_mode"; + qcom,mdss-dsi-panel-framerate = <60>; + qcom,mdss-dsi-virtual-channel-id = <0>; + qcom,mdss-dsi-stream = <0>; + qcom,mdss-dsi-panel-width = <1440>; + qcom,mdss-dsi-panel-height = <2560>; + qcom,mdss-dsi-h-front-porch = <100>; + qcom,mdss-dsi-h-back-porch = <32>; + qcom,mdss-dsi-h-pulse-width = <16>; + qcom,mdss-dsi-h-sync-skew = <0>; + qcom,mdss-dsi-v-back-porch = <8>; + qcom,mdss-dsi-v-front-porch = <10>; + qcom,mdss-dsi-v-pulse-width = <2>; + qcom,mdss-dsi-bpp = <24>; + qcom,mdss-dsi-underflow-color = <0xff>; + qcom,mdss-dsi-border-color = <0>; + qcom,mdss-dsi-on-command = [ + /* CMD2_P0 */ + 15 01 00 00 10 00 02 ff 20 + 15 01 00 00 10 00 02 fb 01 + 15 01 00 00 10 00 02 00 01 + 15 01 00 00 10 00 02 01 55 + 15 01 00 00 10 00 02 02 45 + 15 01 00 00 10 00 02 05 40 + 15 01 00 00 10 00 02 06 19 + 15 01 00 00 10 00 02 07 1e + 15 01 00 00 10 00 02 0b 73 + 15 01 00 00 10 00 02 0c 73 + 15 01 00 00 10 00 02 0e b0 + 15 01 00 00 10 00 02 0f aE + 15 01 00 00 10 00 02 11 b8 + 15 01 00 00 10 00 02 13 00 + 15 01 00 00 10 00 02 58 80 + 15 01 00 00 10 00 02 59 01 + 15 01 00 00 10 00 02 5a 00 + 15 01 00 00 10 00 02 5b 01 + 15 01 00 00 10 00 02 5c 80 + 15 01 00 00 10 00 02 5d 81 + 15 01 00 00 10 00 02 5e 00 + 15 01 00 00 10 00 02 5f 01 + 15 01 00 00 10 00 02 72 31 + 15 01 00 00 10 00 02 68 03 + /* CMD2_P4 */ + 15 01 00 00 10 00 02 ff 24 + 15 01 00 00 10 00 02 fb 01 + 15 01 00 00 10 00 02 00 1c + 15 01 00 00 10 00 02 01 0b + 15 01 00 00 10 00 02 02 0c + 15 01 00 00 10 00 02 03 01 + 15 01 00 00 10 00 02 04 0f + 15 01 00 00 10 00 02 05 10 + 15 01 00 00 10 00 02 06 10 + 15 01 00 00 10 00 02 07 10 + 15 01 00 00 10 00 02 08 89 + 15 01 00 00 10 00 02 09 8a + 15 01 00 00 10 00 02 0a 13 + 15 01 00 00 10 00 02 0b 13 + 15 01 00 00 10 00 02 0c 15 + 15 01 00 00 10 00 02 0d 15 + 15 01 00 00 10 00 02 0e 17 + 15 01 00 00 10 00 02 0f 17 + 15 01 00 00 10 00 02 10 1c + 15 01 00 00 10 00 02 11 0b + 15 01 00 00 10 00 02 12 0c + 15 01 00 00 10 00 02 13 01 + 15 01 00 00 10 00 02 14 0f + 15 01 00 00 10 00 02 15 10 + 15 01 00 00 10 00 02 16 10 + 15 01 00 00 10 00 02 17 10 + 15 01 00 00 10 00 02 18 89 + 15 01 00 00 10 00 02 19 8a + 15 01 00 00 10 00 02 1a 13 + 15 01 00 00 10 00 02 1b 13 + 15 01 00 00 10 00 02 1c 15 + 15 01 00 00 10 00 02 1d 15 + 15 01 00 00 10 00 02 1e 17 + 15 01 00 00 10 00 02 1f 17 + /* STV */ + 15 01 00 00 10 00 02 20 40 + 15 01 00 00 10 00 02 21 01 + 15 01 00 00 10 00 02 22 00 + 15 01 00 00 10 00 02 23 40 + 15 01 00 00 10 00 02 24 40 + 15 01 00 00 10 00 02 25 6d + 15 01 00 00 10 00 02 26 40 + 15 01 00 00 10 00 02 27 40 + /* Vend */ + 15 01 00 00 10 00 02 e0 00 + 15 01 00 00 10 00 02 dc 21 + 15 01 00 00 10 00 02 dd 22 + 15 01 00 00 10 00 02 de 07 + 15 01 00 00 10 00 02 df 07 + 15 01 00 00 10 00 02 e3 6d + 15 01 00 00 10 00 02 e1 07 + 15 01 00 00 10 00 02 e2 07 + /* UD */ + 15 01 00 00 10 00 02 29 d8 + 15 01 00 00 10 00 02 2a 2a + /* CLK */ + 15 01 00 00 10 00 02 4b 03 + 15 01 00 00 10 00 02 4c 11 + 15 01 00 00 10 00 02 4d 10 + 15 01 00 00 10 00 02 4e 01 + 15 01 00 00 10 00 02 4f 01 + 15 01 00 00 10 00 02 50 10 + 15 01 00 00 10 00 02 51 00 + 15 01 00 00 10 00 02 52 80 + 15 01 00 00 10 00 02 53 00 + 15 01 00 00 10 00 02 56 00 + 15 01 00 00 10 00 02 54 07 + 15 01 00 00 10 00 02 58 07 + 15 01 00 00 10 00 02 55 25 + /* Reset XDONB */ + 15 01 00 00 10 00 02 5b 43 + 15 01 00 00 10 00 02 5c 00 + 15 01 00 00 10 00 02 5f 73 + 15 01 00 00 10 00 02 60 73 + 15 01 00 00 10 00 02 63 22 + 15 01 00 00 10 00 02 64 00 + 15 01 00 00 10 00 02 67 08 + 15 01 00 00 10 00 02 68 04 + /* Resolution:1440x2560*/ + 15 01 00 00 10 00 02 72 02 + /* mux */ + 15 01 00 00 10 00 02 7a 80 + 15 01 00 00 10 00 02 7b 91 + 15 01 00 00 10 00 02 7c d8 + 15 01 00 00 10 00 02 7d 60 + 15 01 00 00 10 00 02 7f 15 + 15 01 00 00 10 00 02 75 15 + /* ABOFF */ + 15 01 00 00 10 00 02 b3 c0 + 15 01 00 00 10 00 02 b4 00 + 15 01 00 00 10 00 02 b5 00 + /* Source EQ */ + 15 01 00 00 10 00 02 78 00 + 15 01 00 00 10 00 02 79 00 + 15 01 00 00 10 00 02 80 00 + 15 01 00 00 10 00 02 83 00 + /* FP BP */ + 15 01 00 00 10 00 02 93 0a + 15 01 00 00 10 00 02 94 0a + /* Inversion Type */ + 15 01 00 00 10 00 02 8a 00 + 15 01 00 00 10 00 02 9b ff + /* IMGSWAP =1 @PortSwap=1 */ + 15 01 00 00 10 00 02 9d b0 + 15 01 00 00 10 00 02 9f 63 + 15 01 00 00 10 00 02 98 10 + /* FRM */ + 15 01 00 00 10 00 02 ec 00 + /* CMD1 */ + 15 01 00 00 10 00 02 ff 10 + /* VESA DSC PPS settings(1440x2560 slide 16H) */ + 39 01 00 00 10 00 11 c1 09 20 00 10 02 00 02 68 01 + bb 00 0a 06 67 04 c5 + 39 01 00 00 10 00 03 c2 10 f0 + /* C0h = 0x00(2 Port SDC); 0x01(1 PortA FBC); + * 0x02(MTK); 0x03(1 PortA VESA) + */ + 15 01 00 00 10 00 02 c0 03 + /* VBP+VSA=,VFP = 10H */ + 39 01 00 00 10 00 04 3b 03 0a 0a + /* FTE on */ + 15 01 00 00 10 00 02 35 00 + /* EN_BK =1(auto black) */ + 15 01 00 00 10 00 02 e5 01 + /* CMD mode(10) VDO mode(03) */ + 15 01 00 00 10 00 02 bb 03 + /* Non Reload MTP */ + 15 01 00 00 10 00 02 fb 01 + /* SlpOut + DispOn */ + 05 01 00 00 a0 00 02 11 00 + 05 01 00 00 a0 00 02 29 00 + ]; + qcom,mdss-dsi-off-command = [05 01 00 00 78 00 02 28 00 + 05 01 00 00 78 00 02 10 00]; + qcom,mdss-dsi-on-command-state = "dsi_lp_mode"; + qcom,mdss-dsi-off-command-state = "dsi_hs_mode"; + qcom,mdss-dsi-h-sync-pulse = <0>; + qcom,mdss-dsi-traffic-mode = "non_burst_sync_event"; + qcom,mdss-dsi-bllp-eof-power-mode; + qcom,mdss-dsi-bllp-power-mode; + qcom,mdss-dsi-lane-0-state; + qcom,mdss-dsi-lane-1-state; + qcom,mdss-dsi-lane-2-state; + qcom,mdss-dsi-lane-3-state; + qcom,mdss-dsi-panel-timings = [00 11 04 04 07 0c 04 04 03 03 + 04 00]; + qcom,mdss-dsi-t-clk-post = <0xb>; + qcom,mdss-dsi-t-clk-pre = <0x23>; + qcom,mdss-dsi-dma-trigger = "trigger_sw"; + qcom,mdss-dsi-mdp-trigger = "none"; + qcom,mdss-dsi-reset-sequence = <1 10>, <0 10>, <1 10>; + qcom,mdss-pan-physical-width-dimension = <74>; + qcom,mdss-pan-physical-height-dimension = <131>; + + qcom,compression-mode = "dsc"; + qcom,config-select = <&dsi_nt35597_truly_dsc_video_config0>; + + dsi_nt35597_truly_dsc_video_config0: config0 { + qcom,mdss-dsc-encoders = <1>; + qcom,mdss-dsc-slice-height = <16>; + qcom,mdss-dsc-slice-width = <720>; + qcom,mdss-dsc-slice-per-pkt = <2>; + + qcom,mdss-dsc-bit-per-component = <8>; + qcom,mdss-dsc-bit-per-pixel = <8>; + qcom,mdss-dsc-block-prediction-enable; + }; + + dsi_nt35597_truly_dsc_video_config1: config1 { + qcom,lm-split = <720 720>; + qcom,mdss-dsc-encoders = <1>; /* 3D Mux */ + qcom,mdss-dsc-slice-height = <16>; + qcom,mdss-dsc-slice-width = <720>; + qcom,mdss-dsc-slice-per-pkt = <2>; + + qcom,mdss-dsc-bit-per-component = <8>; + qcom,mdss-dsc-bit-per-pixel = <8>; + qcom,mdss-dsc-block-prediction-enable; + }; + + dsi_nt35597_truly_dsc_video_config2: config2 { + qcom,lm-split = <720 720>; + qcom,mdss-dsc-encoders = <2>; /* DSC Merge */ + qcom,mdss-dsc-slice-height = <16>; + qcom,mdss-dsc-slice-width = <720>; + qcom,mdss-dsc-slice-per-pkt = <2>; + + qcom,mdss-dsc-bit-per-component = <8>; + qcom,mdss-dsc-bit-per-pixel = <8>; + qcom,mdss-dsc-block-prediction-enable; + }; + }; +}; diff --git a/arch/arm/boot/dts/qcom/msm-pm660l.dtsi b/arch/arm/boot/dts/qcom/msm-pm660l.dtsi index a9820cfbc02c..d0033d5bf3bc 100644 --- a/arch/arm/boot/dts/qcom/msm-pm660l.dtsi +++ b/arch/arm/boot/dts/qcom/msm-pm660l.dtsi @@ -167,6 +167,17 @@ qcom,supported-sizes = <6>, <9>; qcom,ramp-index = <2>; #pwm-cells = <2>; + qcom,period = <6000000>; + + qcom,lpg { + label = "lpg"; + cell-index = <0>; + qcom,duty-percents = + <0x01 0x0a 0x14 0x1e 0x28 0x32 0x3c + 0x46 0x50 0x5a 0x64 + 0x64 0x5a 0x50 0x46 0x3c 0x32 0x28 0x1e + 0x14 0x0a 0x01>; + }; }; pm660l_pwm_4: pwm@b400 { @@ -197,8 +208,12 @@ qcom,max-current = <12>; qcom,default-state = "off"; linux,name = "red"; - linux,default-trigger = - "battery-charging"; + qcom,start-idx = <0>; + qcom,idx-len = <22>; + qcom,duty-pcts = + [01 0a 14 1e 28 32 3c 46 50 5a 64 + 64 5a 50 46 3c 32 28 1e 14 0a 01]; + qcom,use-blink; }; green_led: qcom,rgb_1 { @@ -210,7 +225,6 @@ qcom,max-current = <12>; qcom,default-state = "off"; linux,name = "green"; - linux,default-trigger = "battery-full"; }; blue_led: qcom,rgb_2 { @@ -222,7 +236,6 @@ qcom,max-current = <12>; qcom,default-state = "off"; linux,name = "blue"; - linux,default-trigger = "boot-indication"; }; }; diff --git a/arch/arm/boot/dts/qcom/msm8996-mdss-panels.dtsi b/arch/arm/boot/dts/qcom/msm8996-mdss-panels.dtsi index e62c7fbcc1af..bfb85274846f 100644 --- a/arch/arm/boot/dts/qcom/msm8996-mdss-panels.dtsi +++ b/arch/arm/boot/dts/qcom/msm8996-mdss-panels.dtsi @@ -131,7 +131,7 @@ }; &dsi_nt35950_4k_dsc_cmd { - qcom,mdss-dsi-panel-timings-8996 = [21 1e 06 08 04 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 @@ -139,7 +139,7 @@ }; &dsi_sharp_4k_dsc_video { - qcom,mdss-dsi-panel-timings-8996 = [21 1e 06 08 04 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 @@ -147,7 +147,7 @@ }; &dsi_sharp_4k_dsc_cmd { - qcom,mdss-dsi-panel-timings-8996 = [21 1e 06 08 04 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 21 1e 06 08 04 03 04 a0 @@ -155,7 +155,7 @@ }; &dsi_dual_sharp_video { - qcom,mdss-dsi-panel-timings-8996 = [23 20 06 09 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 @@ -163,7 +163,7 @@ }; &dsi_dual_jdi_cmd { - qcom,mdss-dsi-panel-timings-8996 = [22 1e 06 08 04 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [22 1e 06 08 04 03 04 a0 22 1e 06 08 04 03 04 a0 22 1e 06 08 04 03 04 a0 22 1e 06 08 04 03 04 a0 @@ -173,7 +173,7 @@ }; &dsi_dual_jdi_video { - qcom,mdss-dsi-panel-timings-8996 = [22 1e 06 08 04 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [22 1e 06 08 04 03 04 a0 22 1e 06 08 04 03 04 a0 22 1e 06 08 04 03 04 a0 22 1e 06 08 04 03 04 a0 @@ -181,7 +181,7 @@ }; &dsi_dual_sharp_1080_120hz_cmd { - qcom,mdss-dsi-panel-timings-8996 = [23 1e 07 08 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 @@ -189,7 +189,7 @@ }; &dsi_dual_nt35597_video { - qcom,mdss-dsi-panel-timings-8996 = [23 1e 07 08 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 @@ -199,7 +199,7 @@ }; &dsi_dual_nt35597_cmd { - qcom,mdss-dsi-panel-timings-8996 = [23 1e 07 08 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 @@ -209,7 +209,7 @@ }; &dsi_nt35597_dsc_video { - qcom,mdss-dsi-panel-timings-8996 = [20 1d 05 07 03 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [20 1d 05 07 03 03 04 a0 20 1d 05 07 03 03 04 a0 20 1d 05 07 03 03 04 a0 20 1d 05 07 03 03 04 a0 @@ -219,7 +219,7 @@ }; &dsi_nt35597_dsc_cmd { - qcom,mdss-dsi-panel-timings-8996 = [20 1d 05 07 03 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [20 1d 05 07 03 03 04 a0 20 1d 05 07 03 03 04 a0 20 1d 05 07 03 03 04 a0 20 1d 05 07 03 03 04 a0 @@ -229,7 +229,7 @@ }; &dsi_dual_jdi_4k_nofbc_video { - qcom,mdss-dsi-panel-timings-8996 = [ + qcom,mdss-dsi-panel-timings-phy-v2 = [ 2c 27 0e 10 0a 03 04 a0 2c 27 0e 10 0a 03 04 a0 2c 27 0e 10 0a 03 04 a0 @@ -238,14 +238,14 @@ }; &dsi_hx8379a_fwvga_truly_vid { - qcom,mdss-dsi-panel-timings-8996 = [23 20 06 09 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 20 06 09 05 03 04 a0 23 2e 06 08 05 03 04 a0]; }; &dsi_r69007_wqxga_cmd { - qcom,mdss-dsi-panel-timings-8996 = [23 1f 07 09 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1f 07 09 05 03 04 a0 23 1f 07 09 05 03 04 a0 23 1f 07 09 05 03 04 a0 23 1f 07 09 05 03 04 a0 @@ -253,7 +253,7 @@ }; &dsi_sharp_1080_cmd { - qcom,mdss-dsi-panel-timings-8996 = [23 1f 07 09 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1f 07 09 05 03 04 a0 23 1f 07 09 05 03 04 a0 23 1f 07 09 05 03 04 a0 23 1f 07 09 05 03 04 a0 diff --git a/arch/arm/boot/dts/qcom/msm8996.dtsi b/arch/arm/boot/dts/qcom/msm8996.dtsi index 2735cfb93be0..f69c388fbbef 100644 --- a/arch/arm/boot/dts/qcom/msm8996.dtsi +++ b/arch/arm/boot/dts/qcom/msm8996.dtsi @@ -3901,6 +3901,7 @@ clock-names = "core_clk"; clocks = <&clock_mmss clk_camss_cpp_clk>; parent-supply = <&gdsc_camss_top>; + qcom,support-hw-trigger; status = "ok"; }; diff --git a/arch/arm/boot/dts/qcom/msm8998-coresight.dtsi b/arch/arm/boot/dts/qcom/msm8998-coresight.dtsi index 75a90b0499e1..4b81d2754255 100644 --- a/arch/arm/boot/dts/qcom/msm8998-coresight.dtsi +++ b/arch/arm/boot/dts/qcom/msm8998-coresight.dtsi @@ -1132,6 +1132,8 @@ <&clock_gcc clk_qdss_a_clk>; clock-names = "core_clk", "core_a_clk"; + qcom,msr-fix-req; + port{ tpdm_qm_out_tpda: endpoint { remote-endpoint = <&tpda_in_tpdm_qm>; @@ -1151,6 +1153,8 @@ <&clock_gcc clk_qdss_a_clk>; clock-names = "core_clk", "core_a_clk"; + qcom,msr-fix-req; + port{ tpdm_pimem_out_tpda: endpoint { remote-endpoint = <&tpda_in_tpdm_pimem>; @@ -1205,6 +1209,8 @@ <&clock_gcc clk_qdss_a_clk>; clock-names = "core_clk", "core_a_clk"; + qcom,msr-fix-req; + port{ tpdm_apss_out_tpda_apss: endpoint { remote-endpoint = <&tpda_apss_in_tpdm_apss>; @@ -1259,6 +1265,8 @@ <&clock_gcc clk_qdss_a_clk>; clock-names = "core_clk", "core_a_clk"; + qcom,msr-fix-req; + port{ tpdm_mss_out_tpda_mss: endpoint { remote-endpoint = <&tpda_mss_in_tpdm_mss>; @@ -1453,6 +1461,8 @@ <&clock_gcc clk_qdss_a_clk>; clock-names = "core_clk", "core_a_clk"; + qcom,msr-fix-req; + port{ tpdm_spss_out_tpda_spss: endpoint { remote-endpoint = <&tpda_spss_in_tpdm_spss>; diff --git a/arch/arm/boot/dts/qcom/msm8998-interposer-sdm660.dtsi b/arch/arm/boot/dts/qcom/msm8998-interposer-sdm660.dtsi index d6b278e2a789..cfb71e3b1cb3 100644 --- a/arch/arm/boot/dts/qcom/msm8998-interposer-sdm660.dtsi +++ b/arch/arm/boot/dts/qcom/msm8998-interposer-sdm660.dtsi @@ -3067,6 +3067,7 @@ &gdsc_cpp { parent-supply = <&gdsc_camss_top>; + qcom,support-hw-trigger; status = "ok"; }; diff --git a/arch/arm/boot/dts/qcom/msm8998-v2.dtsi b/arch/arm/boot/dts/qcom/msm8998-v2.dtsi index 99975877658d..fa7cdd5194a3 100644 --- a/arch/arm/boot/dts/qcom/msm8998-v2.dtsi +++ b/arch/arm/boot/dts/qcom/msm8998-v2.dtsi @@ -1,4 +1,4 @@ -/* Copyright (c) 2016 The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017 The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -298,6 +298,7 @@ &devfreq_memlat_0 { qcom,core-dev-table = + < 300000 1525 >, < 595200 3143 >, < 1324800 4173 >, < 1555200 5859 >, diff --git a/arch/arm/boot/dts/qcom/msm8998.dtsi b/arch/arm/boot/dts/qcom/msm8998.dtsi index 91bd35a8ce07..6a11e7c51ca5 100644 --- a/arch/arm/boot/dts/qcom/msm8998.dtsi +++ b/arch/arm/boot/dts/qcom/msm8998.dtsi @@ -3153,6 +3153,7 @@ &gdsc_cpp { parent-supply = <&gdsc_camss_top>; + qcom,support-hw-trigger; status = "ok"; }; diff --git a/arch/arm/boot/dts/qcom/sda630-cdp.dts b/arch/arm/boot/dts/qcom/sda630-cdp.dts new file mode 100644 index 000000000000..8db5a9e76126 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda630.dtsi" +#include "sdm630-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630 PM660 + PM660L CDP"; + compatible = "qcom,sda630-cdp", "qcom,sda630", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda630-mtp.dts b/arch/arm/boot/dts/qcom/sda630-mtp.dts new file mode 100644 index 000000000000..5c4372600ad7 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda630.dtsi" +#include "sdm630-mtp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630 PM660 + PM660L MTP"; + compatible = "qcom,sda630-mtp", "qcom,sda630", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda630-pm660a-cdp.dts b/arch/arm/boot/dts/qcom/sda630-pm660a-cdp.dts new file mode 100644 index 000000000000..9afa16ff920d --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630-pm660a-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda630.dtsi" +#include "sdm630-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630 PM660 + PM660A CDP"; + compatible = "qcom,sda630-cdp", "qcom,sda630", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda630-pm660a-mtp.dts b/arch/arm/boot/dts/qcom/sda630-pm660a-mtp.dts new file mode 100644 index 000000000000..8bfd54e46e72 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630-pm660a-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda630.dtsi" +#include "sdm630-mtp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630 PM660 + PM660A MTP"; + compatible = "qcom,sda630-mtp", "qcom,sda630", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda630-pm660a-rcm.dts b/arch/arm/boot/dts/qcom/sda630-pm660a-rcm.dts new file mode 100644 index 000000000000..04f2c3726a05 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630-pm660a-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda630.dtsi" +#include "sdm630-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630 PM660 + PM660A RCM"; + compatible = "qcom,sda630-cdp", "qcom,sda630", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda630-rcm.dts b/arch/arm/boot/dts/qcom/sda630-rcm.dts new file mode 100644 index 000000000000..4a2ed2624a0d --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda630.dtsi" +#include "sdm630-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630 PM660 + PM660L RCM"; + compatible = "qcom,sda630-cdp", "qcom,sda630", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda630.dtsi b/arch/arm/boot/dts/qcom/sda630.dtsi new file mode 100644 index 000000000000..87af4de959af --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda630.dtsi @@ -0,0 +1,19 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include "sdm630.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 630"; + compatible = "qcom,sda630"; + qcom,msm-id = <327 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658-cdp.dts b/arch/arm/boot/dts/qcom/sda658-cdp.dts new file mode 100644 index 000000000000..9992963b8705 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda658.dtsi" +#include "sdm660-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658 PM660 + PM660L CDP"; + compatible = "qcom,sda658-cdp", "qcom,sda658", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658-mtp.dts b/arch/arm/boot/dts/qcom/sda658-mtp.dts new file mode 100644 index 000000000000..f4322ecfd701 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda658.dtsi" +#include "sdm660-mtp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658 PM660 + PM660L MTP"; + compatible = "qcom,sda658-mtp", "qcom,sda658", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658-pm660a-cdp.dts b/arch/arm/boot/dts/qcom/sda658-pm660a-cdp.dts new file mode 100644 index 000000000000..c280c4afda51 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658-pm660a-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda658.dtsi" +#include "sdm660-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658 PM660 + PM660A CDP"; + compatible = "qcom,sda658-cdp", "qcom,sda658", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658-pm660a-mtp.dts b/arch/arm/boot/dts/qcom/sda658-pm660a-mtp.dts new file mode 100644 index 000000000000..ba8741e2a068 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658-pm660a-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda658.dtsi" +#include "sdm660-mtp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658 PM660 + PM660A MTP"; + compatible = "qcom,sda658-mtp", "qcom,sda658", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658-pm660a-rcm.dts b/arch/arm/boot/dts/qcom/sda658-pm660a-rcm.dts new file mode 100644 index 000000000000..f3edc9a5d29f --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658-pm660a-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda658.dtsi" +#include "sdm660-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658 PM660 + PM660A RCM"; + compatible = "qcom,sda658-cdp", "qcom,sda658", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658-rcm.dts b/arch/arm/boot/dts/qcom/sda658-rcm.dts new file mode 100644 index 000000000000..9fafd9632c8d --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sda658.dtsi" +#include "sdm660-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658 PM660 + PM660L RCM"; + compatible = "qcom,sda658-cdp", "qcom,sda658", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sda658.dtsi b/arch/arm/boot/dts/qcom/sda658.dtsi new file mode 100644 index 000000000000..33018a177b41 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sda658.dtsi @@ -0,0 +1,19 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include "sdm658.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDA 658"; + compatible = "qcom,sda658"; + qcom,msm-id = <326 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-cdp.dts b/arch/arm/boot/dts/qcom/sdm630-cdp.dts new file mode 100644 index 000000000000..9ad4322f2af0 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660L CDP"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-cdp.dtsi b/arch/arm/boot/dts/qcom/sdm630-cdp.dtsi new file mode 100644 index 000000000000..6779d80d76cf --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-cdp.dtsi @@ -0,0 +1,24 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include "sdm660-pinctrl.dtsi" +/ { +}; + +&uartblsp1dm1 { + status = "ok"; + pinctrl-names = "default"; + pinctrl-0 = <&uart_console_active>; +}; + +&soc { +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-internal-codec-cdp.dts b/arch/arm/boot/dts/qcom/sdm630-internal-codec-cdp.dts new file mode 100644 index 000000000000..c15abc5ffa39 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-internal-codec-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660L Int. Audio Codec CDP"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <1 1>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-internal-codec-mtp.dts b/arch/arm/boot/dts/qcom/sdm630-internal-codec-mtp.dts new file mode 100644 index 000000000000..0e180392e9de --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-internal-codec-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-mtp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660L Int. Audio Codec MTP"; + compatible = "qcom,sdm630-mtp", "qcom,sdm630", "qcom,mtp"; + qcom,board-id = <8 1>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-cdp.dts b/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-cdp.dts new file mode 100644 index 000000000000..fc4c216b2b57 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660A Int. Audio Codec CDP"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <1 1>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-mtp.dts b/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-mtp.dts new file mode 100644 index 000000000000..aab0eda3448b --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-mtp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660A Int. Audio Codec MTP"; + compatible = "qcom,sdm630-mtp", "qcom,sdm630", "qcom,mtp"; + qcom,board-id = <8 1>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-rcm.dts b/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-rcm.dts new file mode 100644 index 000000000000..f6e2d180ccb6 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-internal-codec-pm660a-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660A Int. Audio Codec RCM"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <21 1>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-internal-codec-rcm.dts b/arch/arm/boot/dts/qcom/sdm630-internal-codec-rcm.dts new file mode 100644 index 000000000000..a6d318cea8e0 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-internal-codec-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660L Int. Audio Codec RCM"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <21 1>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-mtp.dts b/arch/arm/boot/dts/qcom/sdm630-mtp.dts new file mode 100644 index 000000000000..4933fcb8fce3 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-mtp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660L MTP"; + compatible = "qcom,sdm630-mtp", "qcom,sdm630", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-mtp.dtsi b/arch/arm/boot/dts/qcom/sdm630-mtp.dtsi new file mode 100644 index 000000000000..6779d80d76cf --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-mtp.dtsi @@ -0,0 +1,24 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include "sdm660-pinctrl.dtsi" +/ { +}; + +&uartblsp1dm1 { + status = "ok"; + pinctrl-names = "default"; + pinctrl-0 = <&uart_console_active>; +}; + +&soc { +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-pm660a-cdp.dts b/arch/arm/boot/dts/qcom/sdm630-pm660a-cdp.dts new file mode 100644 index 000000000000..478f3acde81e --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-pm660a-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660A CDP"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-pm660a-mtp.dts b/arch/arm/boot/dts/qcom/sdm630-pm660a-mtp.dts new file mode 100644 index 000000000000..3da1116c4352 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-pm660a-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-mtp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660A MTP"; + compatible = "qcom,sdm630-mtp", "qcom,sdm630", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-pm660a-rcm.dts b/arch/arm/boot/dts/qcom/sdm630-pm660a-rcm.dts new file mode 100644 index 000000000000..49938fa254cb --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-pm660a-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660A RCM"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630-rcm.dts b/arch/arm/boot/dts/qcom/sdm630-rcm.dts new file mode 100644 index 000000000000..79b3f8edfcc2 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm630-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm630.dtsi" +#include "sdm630-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 630 PM660 + PM660L RCM"; + compatible = "qcom,sdm630-cdp", "qcom,sdm630", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm630.dtsi b/arch/arm/boot/dts/qcom/sdm630.dtsi index a82979d63244..2ebabab84f11 100644 --- a/arch/arm/boot/dts/qcom/sdm630.dtsi +++ b/arch/arm/boot/dts/qcom/sdm630.dtsi @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -48,7 +48,7 @@ reg = <0x0 0x100>; enable-method = "psci"; qcom,limits-info = <&mitigation_profile0>; - efficiency = <1024>; + efficiency = <1126>; next-level-cache = <&L2_1>; L2_1: l2-cache { compatible = "arm,arch-cache"; @@ -72,7 +72,7 @@ reg = <0x0 0x101>; enable-method = "psci"; qcom,limits-info = <&mitigation_profile1>; - efficiency = <1024>; + efficiency = <1126>; next-level-cache = <&L2_1>; L1_I_101: l1-icache { compatible = "arm,arch-cache"; @@ -90,7 +90,7 @@ reg = <0x0 0x102>; enable-method = "psci"; qcom,limits-info = <&mitigation_profile2>; - efficiency = <1024>; + efficiency = <1126>; next-level-cache = <&L2_1>; L1_I_102: l1-icache { compatible = "arm,arch-cache"; @@ -108,7 +108,7 @@ reg = <0x0 0x103>; enable-method = "psci"; qcom,limits-info = <&mitigation_profile3>; - efficiency = <1024>; + efficiency = <1126>; next-level-cache = <&L2_1>; L1_I_103: l1-icache { compatible = "arm,arch-cache"; @@ -875,6 +875,35 @@ label = "rpm"; }; + glink_spi_xprt_wdsp: qcom,glink-spi-xprt-wdsp { + compatible = "qcom,glink-spi-xprt"; + label = "wdsp"; + qcom,remote-fifo-config = <&glink_fifo_wdsp>; + qcom,qos-config = <&glink_qos_wdsp>; + qcom,ramp-time = <0x10>, + <0x20>, + <0x30>, + <0x40>; + }; + + glink_fifo_wdsp: qcom,glink-fifo-config-wdsp { + compatible = "qcom,glink-fifo-config"; + qcom,out-read-idx-reg = <0x12000>; + qcom,out-write-idx-reg = <0x12004>; + qcom,in-read-idx-reg = <0x1200c>; + qcom,in-write-idx-reg = <0x12010>; + }; + + glink_qos_wdsp: qcom,glink-qos-config-wdsp { + compatible = "qcom,glink-qos-config"; + qcom,flow-info = <0x80 0x0>, + <0x70 0x1>, + <0x60 0x2>, + <0x50 0x3>; + qcom,mtu-size = <0x800>; + qcom,tput-stats-cycle = <0xa>; + }; + qcom,glink_pkt { compatible = "qcom,glinkpkt"; @@ -1244,6 +1273,7 @@ #include "msm-pm660l.dtsi" #include "msm-pm660-rpm-regulator.dtsi" #include "msm-pm660l-rpm-regulator.dtsi" +#include "sdm660-bus.dtsi" #include "sdm630-regulator.dtsi" #include "msm-gdsc-660.dtsi" #include "sdm660-common.dtsi" @@ -1294,6 +1324,7 @@ &gdsc_cpp { parent-supply = <&gdsc_camss_top>; + qcom,support-hw-trigger; status = "ok"; }; diff --git a/arch/arm/boot/dts/qcom/sdm658-cdp.dts b/arch/arm/boot/dts/qcom/sdm658-cdp.dts new file mode 100644 index 000000000000..8569af157049 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L CDP"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-internal-codec-cdp.dts b/arch/arm/boot/dts/qcom/sdm658-internal-codec-cdp.dts new file mode 100644 index 000000000000..d0f5c14223ff --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-internal-codec-cdp.dts @@ -0,0 +1,73 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L Int. Audio Codec CDP"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <1 1>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; + +&slim_aud { + status = "disabled"; +}; + +&dai_slim { + status = "disabled"; +}; + +&wcd9335 { + status = "disabled"; +}; + +&wcd934x_cdc { + status = "disabled"; +}; + +&clock_audio { + status = "disabled"; +}; + +&wcd_rst_gpio { + status = "disabled"; +}; + +&wcd9xxx_intc { + status = "disabled"; +}; + +&tasha_snd { + status = "disabled"; +}; + +&tavil_snd { + status = "disabled"; +}; + +&int_codec { + status = "okay"; +}; + +&pmic_analog_codec { + status = "okay"; +}; + +&msm_sdw_codec { + status = "okay"; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-internal-codec-mtp.dts b/arch/arm/boot/dts/qcom/sdm658-internal-codec-mtp.dts new file mode 100644 index 000000000000..acec15e0615f --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-internal-codec-mtp.dts @@ -0,0 +1,74 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-mtp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L Int. Audio Codec MTP"; + compatible = "qcom,sdm658-mtp", "qcom,sdm658", "qcom,mtp"; + qcom,board-id = <8 1>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; + +&slim_aud { + status = "disabled"; +}; + +&dai_slim { + status = "disabled"; +}; + +&wcd9335 { + status = "disabled"; +}; + +&wcd934x_cdc { + status = "disabled"; +}; + +&clock_audio { + status = "disabled"; +}; + +&wcd_rst_gpio { + status = "disabled"; +}; + +&wcd9xxx_intc { + status = "disabled"; +}; + +&tasha_snd { + status = "disabled"; +}; + +&tavil_snd { + status = "disabled"; +}; + +&int_codec { + qcom,model = "sdm660-snd-card-mtp"; + status = "okay"; +}; + +&pmic_analog_codec { + status = "okay"; +}; + +&msm_sdw_codec { + status = "okay"; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-cdp.dts b/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-cdp.dts new file mode 100644 index 000000000000..b7f2e70ce962 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A Int. Audio Codec CDP"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <1 1>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-mtp.dts b/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-mtp.dts new file mode 100644 index 000000000000..949d7ae7faa5 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-mtp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A Int. Audio Codec MTP"; + compatible = "qcom,sdm658-mtp", "qcom,sdm658", "qcom,mtp"; + qcom,board-id = <8 1>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-rcm.dts b/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-rcm.dts new file mode 100644 index 000000000000..c0b3e3a6b34f --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-internal-codec-pm660a-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A Int. Audio Codec RCM"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <21 1>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-internal-codec-rcm.dts b/arch/arm/boot/dts/qcom/sdm658-internal-codec-rcm.dts new file mode 100644 index 000000000000..69a089c41c32 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-internal-codec-rcm.dts @@ -0,0 +1,73 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L Int. Audio Codec RCM"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <21 1>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; + +&slim_aud { + status = "disabled"; +}; + +&dai_slim { + status = "disabled"; +}; + +&wcd9335 { + status = "disabled"; +}; + +&wcd934x_cdc { + status = "disabled"; +}; + +&clock_audio { + status = "disabled"; +}; + +&wcd_rst_gpio { + status = "disabled"; +}; + +&wcd9xxx_intc { + status = "disabled"; +}; + +&tasha_snd { + status = "disabled"; +}; + +&tavil_snd { + status = "disabled"; +}; + +&int_codec { + status = "okay"; +}; + +&pmic_analog_codec { + status = "okay"; +}; + +&msm_sdw_codec { + status = "okay"; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-mtp.dts b/arch/arm/boot/dts/qcom/sdm658-mtp.dts new file mode 100644 index 000000000000..2fbe9b0a6201 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-mtp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L MTP"; + compatible = "qcom,sdm658-mtp", "qcom,sdm658", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-pm660a-cdp.dts b/arch/arm/boot/dts/qcom/sdm658-pm660a-cdp.dts new file mode 100644 index 000000000000..39e2df958347 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-pm660a-cdp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A CDP"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <1 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-pm660a-mtp.dts b/arch/arm/boot/dts/qcom/sdm658-pm660a-mtp.dts new file mode 100644 index 000000000000..4d205ef403f4 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-pm660a-mtp.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-mtp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A MTP"; + compatible = "qcom,sdm658-mtp", "qcom,sdm658", "qcom,mtp"; + qcom,board-id = <8 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-pm660a-qrd.dts b/arch/arm/boot/dts/qcom/sdm658-pm660a-qrd.dts new file mode 100644 index 000000000000..f1edf6b244a8 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-pm660a-qrd.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-qrd.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A QRD"; + compatible = "qcom,sdm658-qrd", "qcom,sdm658", "qcom,qrd"; + qcom,board-id = <0x1000b 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-pm660a-rcm.dts b/arch/arm/boot/dts/qcom/sdm658-pm660a-rcm.dts new file mode 100644 index 000000000000..e0ab5725dcd7 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-pm660a-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" +#include "msm-pm660a.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660A RCM"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-qrd.dts b/arch/arm/boot/dts/qcom/sdm658-qrd.dts new file mode 100644 index 000000000000..bd7d76ee1f6c --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-qrd.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-qrd.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L QRD"; + compatible = "qcom,sdm658-qrd", "qcom,sdm658", "qcom,qrd"; + qcom,board-id = <0x1000b 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658-rcm.dts b/arch/arm/boot/dts/qcom/sdm658-rcm.dts new file mode 100644 index 000000000000..67e03f2e2adb --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658-rcm.dts @@ -0,0 +1,25 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + + +/dts-v1/; + +#include "sdm658.dtsi" +#include "sdm660-cdp.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658 PM660 + PM660L RCM"; + compatible = "qcom,sdm658-cdp", "qcom,sdm658", "qcom,cdp"; + qcom,board-id = <21 0>; + qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>, + <0x0001001b 0x0201011a 0x0 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm658.dtsi b/arch/arm/boot/dts/qcom/sdm658.dtsi new file mode 100644 index 000000000000..3eca3dc30e50 --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm658.dtsi @@ -0,0 +1,19 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include "sdm660.dtsi" + +/ { + model = "Qualcomm Technologies, Inc. SDM 658"; + compatible = "qcom,sdm658"; + qcom,msm-id = <325 0x0>; +}; diff --git a/arch/arm/boot/dts/qcom/sdm660-camera-sensor-qrd.dtsi b/arch/arm/boot/dts/qcom/sdm660-camera-sensor-qrd.dtsi new file mode 100644 index 000000000000..ae8da056d12b --- /dev/null +++ b/arch/arm/boot/dts/qcom/sdm660-camera-sensor-qrd.dtsi @@ -0,0 +1,426 @@ +/* + * Copyright (c) 2017, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +&soc { + led_flash0: qcom,camera-flash@0 { + cell-index = <0>; + compatible = "qcom,camera-flash"; + qcom,flash-source = <&pm660l_flash0 &pm660l_flash1>; + qcom,torch-source = <&pm660l_torch0 &pm660l_torch1>; + qcom,switch-source = <&pm660l_switch0>; + status = "ok"; + }; + + cam_avdd_gpio_regulator:fixed_regulator@1 { + compatible = "regulator-fixed"; + regulator-name = "cam_vadd_gpio_regulator"; + regulator-min-microvolt = <2800000>; + regulator-max-microvolt = <2800000>; + enable-active-high; + gpio = <&tlmm 51 0>; + vin-supply = <&pm660l_bob>; + }; + + cam_dvdd_gpio_regulator:fixed_regulator@1 { + compatible = "regulator-fixed"; + regulator-name = "cam_vadd_gpio_regulator"; + regulator-min-microvolt = <1050000>; + regulator-max-microvolt = <1050000>; + enable-active-high; + gpio = <&pm660l_gpios 4>; + vin-supply = <&pm660_s5>; + }; + + cam_vaf_gpio_regulator:fixed_regulator@2 { + compatible = "regulator-fixed"; + regulator-name = "cam_vaf_gpio_regulator"; + regulator-min-microvolt = <2800000>; + regulator-max-microvolt = <2800000>; + enable-active-high; + gpio = <&tlmm 50 0>; + vin-supply = <&pm660l_bob>; + }; +}; + +&tlmm { + cam_sensor_rear_active: cam_sensor_rear_active { + /* RESET */ + mux { + pins = "gpio46"; + function = "gpio"; + }; + + config { + pins = "gpio46"; + bias-disable; /* No PULL */ + drive-strength = <2>; /* 2 MA */ + }; + }; + + cam_sensor_rear_suspend: cam_sensor_rear_suspend { + /* RESET */ + mux { + pins = "gpio46"; + function = "gpio"; + }; + + config { + pins = "gpio46"; + bias-disable; /* No PULL */ + drive-strength = <2>; /* 2 MA */ + }; + }; + + cam_sensor_rear2_active: cam_sensor_rear2_active { + /* RESET */ + mux { + pins = "gpio48"; + function = "gpio"; + }; + + config { + pins = "gpio48"; + bias-disable; /* No PULL */ + drive-strength = <2>; /* 2 MA */ + }; + }; + + cam_sensor_rear2_suspend: cam_sensor_rear2_suspend { + /* RESET */ + mux { + pins = "gpio48"; + function = "gpio"; + }; + + config { + pins = "gpio48"; + bias-disable; /* No PULL */ + drive-strength = <2>; /* 2 MA */ + }; + }; + + cam_sensor_front_active: cam_sensor_front_active { + /* RESET */ + mux { + pins = "gpio47"; + function = "gpio"; + }; + + config { + pins = "gpio47"; + bias-disable; /* No PULL */ + drive-strength = <2>; /* 2 MA */ + }; + }; + + cam_sensor_front_suspend: cam_sensor_front_suspend { + /* RESET */ + mux { + pins = "gpio47"; + function = "gpio"; + }; + + config { + pins = "gpio47"; + bias-disable; /* No PULL */ + drive-strength = <2>; /* 2 MA */ + }; + }; +}; + +&cci { + actuator0: qcom,actuator@0 { + cell-index = <0>; + reg = <0x0>; + compatible = "qcom,actuator"; + qcom,cci-master = <0>; + cam_vaf-supply = <&cam_vaf_gpio_regulator>; + qcom,cam-vreg-name = "cam_vaf"; + qcom,cam-vreg-min-voltage = <2800000>; + qcom,cam-vreg-max-voltage = <2800000>; + qcom,cam-vreg-op-mode = <0>; + }; + + actuator1: qcom,actuator@1 { + cell-index = <1>; + reg = <0x1>; + compatible = "qcom,actuator"; + qcom,cci-master = <0>; + cam_vaf-supply = <&cam_vaf_gpio_regulator>; + qcom,cam-vreg-name = "cam_vaf"; + qcom,cam-vreg-min-voltage = <2800000>; + qcom,cam-vreg-max-voltage = <2800000>; + qcom,cam-vreg-op-mode = <0>; + }; + + ois0: qcom,ois@0 { + cell-index = <0>; + reg = <0x0>; + compatible = "qcom,ois"; + qcom,cci-master = <0>; + cam_vaf-supply = <&cam_vaf_gpio_regulator>; + qcom,cam-vreg-name = "cam_vaf"; + qcom,cam-vreg-min-voltage = <2800000>; + qcom,cam-vreg-max-voltage = <2800000>; + qcom,cam-vreg-op-mode = <0>; + status = "disabled"; + }; + + eeprom0: qcom,eeprom@0 { + cell-index = <0>; + reg = <0>; + compatible = "qcom,eeprom"; + cam_vio-supply = <&pm660_l11>; + cam_vana-supply = <&cam_avdd_gpio_regulator>; + cam_vdig-supply = <&cam_dvdd_gpio_regulator>; + qcom,cam-vreg-name = "cam_vio", "cam_vana", "cam_vdig"; + qcom,cam-vreg-min-voltage = <1750000 0 0>; + qcom,cam-vreg-max-voltage = <1980000 0 0>; + qcom,cam-vreg-op-mode = <105000 0 0>; + qcom,gpio-no-mux = <0>; + pinctrl-names = "cam_default", "cam_suspend"; + pinctrl-0 = <&cam_sensor_mclk0_active + &cam_sensor_rear_active>; + pinctrl-1 = <&cam_sensor_mclk0_suspend + &cam_sensor_rear_suspend>; + gpios = <&tlmm 32 0>, + <&tlmm 46 0>; + qcom,gpio-reset = <1>; + qcom,gpio-req-tbl-num = <0 1>; + qcom,gpio-req-tbl-flags = <1 0>; + qcom,gpio-req-tbl-label = "CAMIF_MCLK0", + "CAM_RESET0"; + qcom,sensor-position = <0>; + qcom,sensor-mode = <0>; + qcom,cci-master = <0>; + status = "ok"; + clocks = <&clock_mmss MCLK0_CLK_SRC>, + <&clock_mmss MMSS_CAMSS_MCLK0_CLK>; + clock-names = "cam_src_clk", "cam_clk"; + qcom,clock-rates = <24000000 0>; + }; + + eeprom1: qcom,eeprom@1 { + cell-index = <1>; + reg = <0x1>; + compatible = "qcom,eeprom"; + cam_vio-supply = <&pm660_l11>; + cam_vana-supply = <&cam_avdd_gpio_regulator>; + cam_vdig-supply = <&cam_dvdd_gpio_regulator>; + qcom,cam-vreg-name = "cam_vio", "cam_vana", "cam_vdig"; + qcom,cam-vreg-min-voltage = <1750000 0 0>; + qcom,cam-vreg-max-voltage = <1980000 0 0>; + qcom,cam-vreg-op-mode = <105000 0 0>; + qcom,gpio-no-mux = <0>; + pinctrl-names = "cam_default", "cam_suspend"; + pinctrl-0 = <&cam_sensor_mclk2_active + &cam_sensor_rear2_active>; + pinctrl-1 = <&cam_sensor_mclk2_suspend + &cam_sensor_rear2_suspend>; + gpios = <&tlmm 34 0>, + <&tlmm 48 0>; + qcom,gpio-reset = <1>; + qcom,gpio-req-tbl-num = <0 1>; + qcom,gpio-req-tbl-flags = <1 0>; + qcom,gpio-req-tbl-label = "CAMIF_MCLK1", + "CAM_RESET1"; + qcom,sensor-position = <0>; + qcom,sensor-mode = <0>; + qcom,cci-master = <0>; + status = "ok"; + clocks = <&clock_mmss MCLK2_CLK_SRC>, + <&clock_mmss MMSS_CAMSS_MCLK2_CLK>; + clock-names = "cam_src_clk", "cam_clk"; + qcom,clock-rates = <24000000 0>; + }; + + eeprom2: qcom,eeprom@2 { + cell-index = <2>; + reg = <0x2>; + compatible = "qcom,eeprom"; + cam_vio-supply = <&pm660_l11>; + cam_vana-supply = <&cam_avdd_gpio_regulator>; + cam_vdig-supply = <&pm660_s5>; + qcom,cam-vreg-name = "cam_vio", "cam_vana", "cam_vdig"; + qcom,cam-vreg-min-voltage = <1780000 0 1352000>; + qcom,cam-vreg-max-voltage = <1950000 0 1352000>; + qcom,cam-vreg-op-mode = <105000 0 105000>; + qcom,gpio-no-mux = <0>; + pinctrl-names = "cam_default", "cam_suspend"; + pinctrl-0 = <&cam_sensor_mclk1_active + &cam_sensor_front_active>; + pinctrl-1 = <&cam_sensor_mclk1_suspend + &cam_sensor_front_suspend>; + gpios = <&tlmm 33 0>, + <&tlmm 47 0>, + <&pm660l_gpios 3 0>; + qcom,gpio-reset = <1>; + qcom,gpio-vdig = <2>; + qcom,gpio-req-tbl-num = <0 1 2>; + qcom,gpio-req-tbl-flags = <1 0 0>; + qcom,gpio-req-tbl-label = "CAMIF_MCLK2", + "CAM_RESET2", + "CAM_VDIG"; + qcom,sensor-position = <1>; + qcom,sensor-mode = <0>; + qcom,cci-master = <1>; + status = "ok"; + clocks = <&clock_mmss MCLK1_CLK_SRC>, + <&clock_mmss MMSS_CAMSS_MCLK1_CLK>; + clock-names = "cam_src_clk", "cam_clk"; + qcom,clock-rates = <24000000 0>; + }; + + qcom,camera@0 { + cell-index = <0>; + compatible = "qcom,camera"; + reg = <0x0>; + qcom,csiphy-sd-index = <0>; + qcom,csid-sd-index = <0>; + qcom,mount-angle = <90>; + qcom,led-flash-src = <&led_flash0>; + qcom,actuator-src = <&actuator0>; + qcom,ois-src = <&ois0>; + qcom,eeprom-src = <&eeprom0>; + cam_vio-supply = <&pm660_l11>; + cam_vana-supply = <&cam_avdd_gpio_regulator>; + cam_vdig-supply = <&cam_dvdd_gpio_regulator>; + qcom,cam-vreg-name = "cam_vio", "cam_vana", "cam_vdig"; + qcom,cam-vreg-min-voltage = <1780000 0 0>; + qcom,cam-vreg-max-voltage = <1950000 0 0>; + qcom,cam-vreg-op-mode = <105000 0 0>; + qcom,gpio-no-mux = <0>; + pinctrl-names = "cam_default", "cam_suspend"; + pinctrl-0 = <&cam_sensor_mclk0_active + &cam_sensor_rear_active>; + pinctrl-1 = <&cam_sensor_mclk0_suspend + &cam_sensor_rear_suspend>; + gpios = <&tlmm 32 0>, + <&tlmm 46 0>; + qcom,gpio-reset = <1>; + qcom,gpio-req-tbl-num = <0 1>; + qcom,gpio-req-tbl-flags = <1 0>; + qcom,gpio-req-tbl-label = "CAMIF_MCLK2", + "CAM_RESET0"; + qcom,sensor-position = <0>; + qcom,sensor-mode = <0>; + qcom,cci-master = <0>; + status = "ok"; + clocks = <&clock_mmss MCLK0_CLK_SRC>, + <&clock_mmss MMSS_CAMSS_MCLK0_CLK>; + clock-names = "cam_src_clk", "cam_clk"; + qcom,clock-rates = <24000000 0>; + }; + + qcom,camera@1 { + cell-index = <1>; + compatible = "qcom,camera"; + reg = <0x1>; + qcom,csiphy-sd-index = <1>; + qcom,csid-sd-index = <1>; + qcom,mount-angle = <90>; + qcom,actuator-src = <&actuator1>; + qcom,eeprom-src = <&eeprom1>; + cam_vio-supply = <&pm660_l11>; + cam_vana-supply = <&cam_avdd_gpio_regulator>; + cam_vdig-supply = <&cam_dvdd_gpio_regulator>; + qcom,cam-vreg-name = "cam_vio", "cam_vana", "cam_vdig"; + qcom,cam-vreg-min-voltage = <1780000 0 0>; + qcom,cam-vreg-max-voltage = <1950000 0 0>; + qcom,cam-vreg-op-mode = <105000 0 0>; + qcom,gpio-no-mux = <0>; + pinctrl-names = "cam_default", "cam_suspend"; + pinctrl-0 = <&cam_sensor_mclk2_active + &cam_sensor_rear2_active>; + pinctrl-1 = <&cam_sensor_mclk2_suspend + &cam_sensor_rear2_suspend>; + gpios = <&tlmm 34 0>, + <&tlmm 48 0>; + qcom,gpio-reset = <1>; + qcom,gpio-req-tbl-num = <0 1>; + qcom,gpio-req-tbl-flags = <1 0>; + qcom,gpio-req-tbl-label = "CAMIF_MCLK1", + "CAM_RESET1"; + qcom,sensor-position = <0>; + qcom,sensor-mode = <0>; + qcom,cci-master = <0>; + status = "ok"; + clocks = <&clock_mmss MCLK2_CLK_SRC>, + <&clock_mmss MMSS_CAMSS_MCLK2_CLK>; + clock-names = "cam_src_clk", "cam_clk"; + qcom,clock-rates = <24000000 0>; + }; + + qcom,camera@2 { + cell-index = <2>; + compatible = "qcom,camera"; + reg = <0x02>; + qcom,csiphy-sd-index = <2>; + qcom,csid-sd-index = <2>; + qcom,mount-angle = <270>; + qcom,eeprom-src = <&eeprom2>; + cam_vio-supply = <&pm660_l11>; + cam_vana-supply = <&cam_avdd_gpio_regulator>; + cam_vdig-supply = <&pm660_s5>; + qcom,cam-vreg-name = "cam_vio", "cam_vana", "cam_vdig"; + qcom,cam-vreg-min-voltage = <1780000 0 1350000>; + qcom,cam-vreg-max-voltage = <1950000 0 1350000>; + qcom,cam-vreg-op-mode = <105000 0 105000>; + qcom,gpio-no-mux = <0>; + pinctrl-names = "cam_default", "cam_suspend"; + pinctrl-0 = <&cam_sensor_mclk1_active + &cam_sensor_front_active>; + pinctrl-1 = <&cam_sensor_mclk1_suspend + &cam_sensor_front_suspend>; + gpios = <&tlmm 33 0>, + <&tlmm 47 0>, + <&pm660l_gpios 3 0>; + qcom,gpio-reset = <1>; + qcom,gpio-vdig = <2>; + qcom,gpio-req-tbl-num = <0 1 2>; + qcom,gpio-req-tbl-flags = <1 0 0>; + qcom,gpio-req-tbl-label = "CAMIF_MCLK2", + "CAM_RESET2", + "CAM_VDIG"; + qcom,sensor-position = <1>; + qcom,sensor-mode = <0>; + qcom,cci-master = <1>; + status = "ok"; + clocks = <&clock_mmss MCLK1_CLK_SRC>, + <&clock_mmss MMSS_CAMSS_MCLK1_CLK>; + clock-names = "cam_src_clk", "cam_clk"; + qcom,clock-rates = <24000000 0>; + }; +}; + +&pm660l_gpios { + gpio@c300 { /* GPIO4 -CAMERA SENSOR 0 VDIG*/ + qcom,mode = <1>; /* Output */ + qcom,pull = <5>; /* No Pull */ + qcom,vin-sel = <0>; /* VIN1 GPIO_LV */ + qcom,src-sel = <0>; /* GPIO */ + qcom,invert = <0>; /* Invert */ + qcom,master-en = <1>; /* Enable GPIO */ + status = "ok"; + }; + + gpio@c200 { /* GPIO3 -CAMERA SENSOR 2 VDIG*/ + qcom,mode = <1>; /* Output */ + qcom,pull = <5>; /* No Pull */ + qcom,vin-sel = <0>; /* VIN1 GPIO_LV */ + qcom,src-sel = <0>; /* GPIO */ + qcom,invert = <0>; /* Invert */ + qcom,master-en = <1>; /* Enable GPIO */ + status = "ok"; + }; +}; diff --git a/arch/arm/boot/dts/qcom/sdm660-mdss-panels.dtsi b/arch/arm/boot/dts/qcom/sdm660-mdss-panels.dtsi index 28e5f6ba8b45..84a99be7371e 100644 --- a/arch/arm/boot/dts/qcom/sdm660-mdss-panels.dtsi +++ b/arch/arm/boot/dts/qcom/sdm660-mdss-panels.dtsi @@ -67,7 +67,7 @@ }; &dsi_dual_nt35597_truly_video { - qcom,mdss-dsi-panel-timings-8996 = [23 1e 07 08 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 @@ -75,7 +75,7 @@ }; &dsi_dual_nt35597_truly_cmd { - qcom,mdss-dsi-panel-timings-8996 = [23 1e 07 08 05 03 04 a0 + qcom,mdss-dsi-panel-timings-phy-v2 = [23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 23 1e 07 08 05 03 04 a0 diff --git a/arch/arm/boot/dts/qcom/sdm660-pm660a-qrd.dts b/arch/arm/boot/dts/qcom/sdm660-pm660a-qrd.dts index b1078c53acdf..48e02bbdfbfe 100644 --- a/arch/arm/boot/dts/qcom/sdm660-pm660a-qrd.dts +++ b/arch/arm/boot/dts/qcom/sdm660-pm660a-qrd.dts @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -20,6 +20,6 @@ / { model = "Qualcomm Technologies, Inc. SDM 660 PM660 + PM660A QRD"; compatible = "qcom,sdm660-qrd", "qcom,sdm660", "qcom,qrd"; - qcom,board-id = <0x1000b 0>; + qcom,board-id = <0x0012000b 0>; qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>; }; diff --git a/arch/arm/boot/dts/qcom/sdm660-qrd.dtsi b/arch/arm/boot/dts/qcom/sdm660-qrd.dtsi index d90e18459d36..a20ea718b815 100644 --- a/arch/arm/boot/dts/qcom/sdm660-qrd.dtsi +++ b/arch/arm/boot/dts/qcom/sdm660-qrd.dtsi @@ -11,6 +11,7 @@ */ #include "sdm660-pinctrl.dtsi" +#include "sdm660-camera-sensor-qrd.dtsi" / { }; @@ -46,5 +47,101 @@ status = "ok"; }; +&sdhc_2 { + /* device core power supply */ + vdd-supply = <&pm660l_l5>; + qcom,vdd-voltage-level = <2950000 2950000>; + qcom,vdd-current-level = <15000 900000>; + + /* device communication power supply */ + vdd-io-supply = <&pm660l_l2>; + qcom,vdd-io-voltage-level = <1800000 2950000>; + qcom,vdd-io-current-level = <200 22000>; + + pinctrl-names = "active", "sleep"; + pinctrl-0 = <&sdc2_clk_on &sdc2_cmd_on &sdc2_data_on &sdc2_cd_on>; + pinctrl-1 = <&sdc2_clk_off &sdc2_cmd_off &sdc2_data_off &sdc2_cd_off>; + + #address-cells = <0>; + interrupt-parent = <&sdhc_2>; + interrupts = <0 1 2>; + #interrupt-cells = <1>; + interrupt-map-mask = <0xffffffff>; + interrupt-map = <0 &intc 0 125 0 + 1 &intc 0 221 0 + 2 &tlmm 54 0>; + interrupt-names = "hc_irq", "pwr_irq", "status_irq"; + cd-gpios = <&tlmm 54 0x1>; + + qcom,clk-rates = <400000 20000000 25000000 50000000 100000000 + 200000000>; + qcom,bus-speed-mode = "SDR12", "SDR25", "SDR50", "DDR50", "SDR104"; + + status = "ok"; +}; + +&ufsphy1 { + vdda-phy-supply = <&pm660l_l1>; + vdda-pll-supply = <&pm660_l10>; + vddp-ref-clk-supply = <&pm660_l1>; + vdda-phy-max-microamp = <51400>; + vdda-pll-max-microamp = <14200>; + vddp-ref-clk-max-microamp = <100>; + vddp-ref-clk-always-on; + status = "ok"; +}; + +&ufs1 { + vdd-hba-supply = <&gdsc_ufs>; + vdd-hba-fixed-regulator; + vcc-supply = <&pm660l_l4>; + vccq2-supply = <&pm660_l8>; + vcc-max-microamp = <500000>; + vccq2-max-microamp = <600000>; + status = "ok"; +}; + +&soc { +}; + +&pm660l_gpios { + /* GPIO 7 for VOL_UP */ + gpio@c600 { + status = "ok"; + qcom,mode = <0>; + qcom,pull = <0>; + qcom,vin-sel = <0>; + qcom,src-sel = <0>; + qcom,out-strength = <1>; + }; +}; + &soc { + gpio_keys { + compatible = "gpio-keys"; + input-name = "gpio-keys"; + status = "ok"; + + vol_up { + label = "volume_up"; + gpios = <&pm660l_gpios 7 0x1>; + linux,input-type = <1>; + linux,code = <115>; + gpio-key,wakeup; + debounce-interval = <15>; + }; + }; +}; + +/ { + qrd_batterydata: qcom,battery-data { + qcom,batt-id-range-pct = <15>; + + #include "fg-gen3-batterydata-qrd-skuk-4v4-3000mah.dtsi" + }; +}; + +&pm660_fg { + qcom,battery-data = <&qrd_batterydata>; + qcom,fg-jeita-thresholds = <0 5 55 55>; }; diff --git a/arch/arm/boot/dts/qcom/sdm660-regulator.dtsi b/arch/arm/boot/dts/qcom/sdm660-regulator.dtsi index fc88c324e5e2..479a9fdd91ca 100644 --- a/arch/arm/boot/dts/qcom/sdm660-regulator.dtsi +++ b/arch/arm/boot/dts/qcom/sdm660-regulator.dtsi @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -10,6 +10,7 @@ * GNU General Public License for more details. */ +#include <dt-bindings/clock/qcom,gcc-sdm660.h> #include <dt-bindings/clock/qcom,gpu-sdm660.h> #include <dt-bindings/clock/qcom,rpmcc.h> #include <dt-bindings/interrupt-controller/arm-gic.h> @@ -633,4 +634,158 @@ }; }; }; + + /* APC0 CPR Controller node for Silver cluster */ + apc0_cpr: cprh-ctrl@179c8000 { + compatible = "qcom,cprh-sdm660-kbss-regulator"; + reg = <0x179c8000 0x4000>, <0x00784000 0x1000>; + reg-names = "cpr_ctrl", "fuse_base"; + clocks = <&clock_gcc GCC_HMSS_RBCPR_CLK>; + clock-names = "core_clk"; + qcom,cpr-ctrl-name = "apc0"; + qcom,cpr-controller-id = <0>; + + qcom,cpr-sensor-time = <1000>; + qcom,cpr-loop-time = <5000000>; + qcom,cpr-idle-cycles = <15>; + qcom,cpr-up-down-delay-time = <3000>; + qcom,cpr-step-quot-init-min = <12>; + qcom,cpr-step-quot-init-max = <14>; + qcom,cpr-count-mode = <0>; /* All at once */ + qcom,cpr-count-repeat = <14>; + qcom,cpr-down-error-step-limit = <1>; + qcom,cpr-up-error-step-limit = <1>; + qcom,cpr-corner-switch-delay-time = <1042>; + qcom,cpr-voltage-settling-time = <1760>; + + qcom,apm-threshold-voltage = <872000>; + qcom,apm-crossover-voltage = <872000>; + qcom,apm-hysteresis-voltage = <20000>; + qcom,voltage-step = <4000>; + qcom,voltage-base = <400000>; + qcom,cpr-saw-use-unit-mV; + + qcom,cpr-panic-reg-addr-list = + <0x179cbaa4 0x17912c18>; + qcom,cpr-panic-reg-name-list = + "PWR_CPRH_STATUS", "APCLUS0_L2_SAW4_PMIC_STS"; + + thread@0 { + qcom,cpr-thread-id = <0>; + qcom,cpr-consecutive-up = <0>; + qcom,cpr-consecutive-down = <2>; + qcom,cpr-up-threshold = <2>; + qcom,cpr-down-threshold = <2>; + + apc0_pwrcl_vreg: regulator { + regulator-name = "apc0_pwrcl_corner"; + regulator-min-microvolt = <1>; + regulator-max-microvolt = <8>; + + qcom,cpr-fuse-corners = <5>; + qcom,cpr-fuse-combos = <16>; + qcom,cpr-speed-bins = <2>; + qcom,cpr-speed-bin-corners = <8 8>; + qcom,cpr-corners = <8>; + qcom,cpr-corner-fmax-map = <2 3 4 5 8>; + + qcom,cpr-voltage-ceiling = + <724000 724000 724000 788000 868000 + 924000 988000 1068000>; + + qcom,cpr-voltage-floor = + <588000 588000 596000 652000 712000 + 744000 784000 844000>; + + qcom,corner-frequencies = + <300000000 633600000 902400000 + 1113600000 1401600000 1536000000 + 1747200000 1843200000>; + + qcom,allow-voltage-interpolation; + qcom,allow-quotient-interpolation; + qcom,cpr-scaled-open-loop-voltage-as-ceiling; + }; + }; + }; + + /* APC1 CPR Controller node for Gold cluster */ + apc1_cpr: cprh-ctrl@179c4000 { + compatible = "qcom,cprh-sdm660-kbss-regulator"; + reg = <0x179c4000 0x4000>, <0x00784000 0x1000>; + reg-names = "cpr_ctrl", "fuse_base"; + clocks = <&clock_gcc GCC_HMSS_RBCPR_CLK>; + clock-names = "core_clk"; + qcom,cpr-ctrl-name = "apc1"; + qcom,cpr-controller-id = <1>; + + qcom,cpr-sensor-time = <1000>; + qcom,cpr-loop-time = <5000000>; + qcom,cpr-idle-cycles = <15>; + qcom,cpr-up-down-delay-time = <3000>; + qcom,cpr-step-quot-init-min = <12>; + qcom,cpr-step-quot-init-max = <14>; + qcom,cpr-count-mode = <0>; /* All at once */ + qcom,cpr-count-repeat = <14>; + qcom,cpr-down-error-step-limit = <1>; + qcom,cpr-up-error-step-limit = <1>; + qcom,cpr-corner-switch-delay-time = <1042>; + qcom,cpr-voltage-settling-time = <1760>; + + qcom,apm-threshold-voltage = <872000>; + qcom,apm-crossover-voltage = <872000>; + qcom,apm-hysteresis-voltage = <20000>; + qcom,voltage-step = <4000>; + qcom,voltage-base = <400000>; + qcom,cpr-saw-use-unit-mV; + + qcom,cpr-panic-reg-addr-list = + <0x179c7aa4 0x17812c18>; + qcom,cpr-panic-reg-name-list = + "PERF_CPRH_STATUS", "APCLUS1_L2_SAW4_PMIC_STS"; + + thread@0 { + qcom,cpr-thread-id = <0>; + qcom,cpr-consecutive-up = <0>; + qcom,cpr-consecutive-down = <2>; + qcom,cpr-up-threshold = <2>; + qcom,cpr-down-threshold = <2>; + + apc1_perfcl_vreg: regulator { + regulator-name = "apc1_perfcl_corner"; + regulator-min-microvolt = <1>; + regulator-max-microvolt = <7>; + + qcom,cpr-fuse-corners = <5>; + qcom,cpr-fuse-combos = <16>; + qcom,cpr-speed-bins = <2>; + qcom,cpr-speed-bin-corners = <7 7>; + qcom,cpr-corners = <7>; + qcom,cpr-corner-fmax-map = <2 3 4 6 7>; + + qcom,cpr-voltage-ceiling = + <724000 724000 788000 868000 + 924000 988000 1068000>; + + qcom,cpr-voltage-floor = + <588000 596000 652000 712000 + 744000 784000 844000>; + + qcom,corner-frequencies = + /* Speed bin 0 */ + <300000000 1113600000 1401600000 + 1747200000 1958400000 2150400000 + 2457600000>, + + /* Speed bin 1 */ + <300000000 1113600000 1401600000 + 1747200000 1958400000 2150400000 + 2208000000>; + + qcom,allow-voltage-interpolation; + qcom,allow-quotient-interpolation; + qcom,cpr-scaled-open-loop-voltage-as-ceiling; + }; + }; + }; }; diff --git a/arch/arm/boot/dts/qcom/sdm660-vidc.dtsi b/arch/arm/boot/dts/qcom/sdm660-vidc.dtsi index 8e5561da5deb..10cf4de2a8e0 100644 --- a/arch/arm/boot/dts/qcom/sdm660-vidc.dtsi +++ b/arch/arm/boot/dts/qcom/sdm660-vidc.dtsi @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -28,9 +28,9 @@ qcom,firmware-name = "venus"; qcom,sw-power-collapse; qcom,reg-presets = - <0x80010 0x00000003>, - <0x80018 0x05555556>, - <0x8001c 0x05555556>; + <0x80010 0x001f001f>, + <0x80018 0x00000156>, + <0x8001c 0x00000156>; qcom,max-hw-load = <1036800>; /* Full 4k @ 30 */ qcom,allowed-clock-rates = diff --git a/arch/arm/boot/dts/qcom/sdm660.dtsi b/arch/arm/boot/dts/qcom/sdm660.dtsi index b32742ab00f6..54aa729352a3 100644 --- a/arch/arm/boot/dts/qcom/sdm660.dtsi +++ b/arch/arm/boot/dts/qcom/sdm660.dtsi @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -18,6 +18,7 @@ #include <dt-bindings/clock/audio-ext-clk.h> #include <dt-bindings/interrupt-controller/arm-gic.h> #include <dt-bindings/regulator/qcom,rpm-smd-regulator.h> +#include <dt-bindings/clock/qcom,cpu-osm.h> / { model = "Qualcomm Technologies, Inc. SDM 660"; @@ -1093,7 +1094,8 @@ reg-names = "osm", "pwrcl_pll", "perfcl_pll", "apcs_common", "perfcl_efuse"; - /* ToDo: Add power and perf supply rails */ + vdd-pwrcl-supply = <&apc0_pwrcl_vreg>; + vdd-perfcl-supply = <&apc1_perfcl_vreg>; interrupts = <GIC_SPI 35 IRQ_TYPE_EDGE_RISING>, <GIC_SPI 36 IRQ_TYPE_EDGE_RISING>; @@ -1101,31 +1103,31 @@ qcom,pwrcl-speedbin0-v0 = < 300000000 0x0004000f 0x01200020 0x1 1 >, - < 633600000 0x05040021 0x03200020 0x1 1 >, - < 902400000 0x0404002f 0x04260026 0x1 2 >, - < 1113600000 0x0404003a 0x052e002e 0x2 3 >, - < 1401600000 0x04040049 0x073a003a 0x2 4 >, - < 1536000000 0x04040050 0x08400040 0x3 5 >, - < 1747200000 0x0404005b 0x09480048 0x3 6 >, - < 1843200000 0x04040060 0x094c004c 0x3 7 >; + < 633600000 0x05040021 0x03200020 0x1 2 >, + < 902400000 0x0404002f 0x04260026 0x1 3 >, + < 1113600000 0x0404003a 0x052e002e 0x2 4 >, + < 1401600000 0x04040049 0x073a003a 0x2 5 >, + < 1536000000 0x04040050 0x08400040 0x3 6 >, + < 1747200000 0x0404005b 0x09480048 0x3 7 >, + < 1843200000 0x04040060 0x094c004c 0x3 8 >; qcom,perfcl-speedbin0-v0 = < 300000000 0x0004000f 0x01200020 0x1 1 >, - < 1113600000 0x0404003a 0x052e002e 0x1 1 >, - < 1401600000 0x04040049 0x073a003a 0x2 2 >, - < 1747200000 0x0404005b 0x09480048 0x2 3 >, - < 1958400000 0x04040066 0x0a510051 0x3 4 >, - < 2150400000 0x04040070 0x0b590059 0x3 5 >, - < 2457600000 0x04040080 0x0c660066 0x3 6 >; + < 1113600000 0x0404003a 0x052e002e 0x1 2 >, + < 1401600000 0x04040049 0x073a003a 0x2 3 >, + < 1747200000 0x0404005b 0x09480048 0x2 4 >, + < 1958400000 0x04040066 0x0a510051 0x3 5 >, + < 2150400000 0x04040070 0x0b590059 0x3 6 >, + < 2457600000 0x04040080 0x0c660066 0x3 7 >; qcom,perfcl-speedbin1-v0 = < 300000000 0x0004000f 0x01200020 0x1 1 >, - < 1113600000 0x0404003a 0x052e002e 0x1 1 >, - < 1401600000 0x04040049 0x073a003a 0x2 2 >, - < 1747200000 0x0404005b 0x09480048 0x2 3 >, - < 1958400000 0x04040066 0x0a510051 0x3 4 >, - < 2150400000 0x04040070 0x0b590059 0x3 5 >, - < 2208000000 0x04040073 0x0b5c005c 0x3 6 >; + < 1113600000 0x0404003a 0x052e002e 0x1 2 >, + < 1401600000 0x04040049 0x073a003a 0x2 3 >, + < 1747200000 0x0404005b 0x09480048 0x2 4 >, + < 1958400000 0x04040066 0x0a510051 0x3 5 >, + < 2150400000 0x04040070 0x0b590059 0x3 6 >, + < 2208000000 0x04040073 0x0b5c005c 0x3 7 >; qcom,up-timer = <1000 1000>; qcom,down-timer = <1000 1000>; @@ -1159,19 +1161,6 @@ qcom,wfx-fsm-en; qcom,pc-fsm-en; - qcom,pwrcl-apcs-mem-acc-cfg = - <0x179d1360 0x179d1364 0x179d1364>; - qcom,perfcl-apcs-mem-acc-cfg = - <0x179d1368 0x179d136C 0x179d1370>; - qcom,pwrcl-apcs-mem-acc-val = - <0x00000000 0x80000000 0x80000000>, - <0x00000000 0x00000000 0x00000000>, - <0x00000000 0x00000001 0x00000001>; - qcom,perfcl-apcs-mem-acc-val = - <0x00000000 0x00000000 0x80000000>, - <0x00000000 0x00000000 0x00000000>, - <0x00000000 0x00000000 0x00000001>; - clock-names = "aux_clk", "xo_a"; clocks = <&clock_gcc HMSS_GPLL0_CLK_SRC>, <&clock_rpmcc RPM_XO_A_CLK_SRC>; @@ -1179,6 +1168,43 @@ #clock-cells = <1>; }; + msm_cpufreq: qcom,msm-cpufreq { + compatible = "qcom,msm-cpufreq"; + clock-names = "cpu0_clk", "cpu1_clk", "cpu2_clk", + "cpu3_clk", "cpu4_clk", "cpu5_clk", + "cpu6_clk", "cpu7_clk"; + clocks = <&clock_cpu PWRCL_CLK>, + <&clock_cpu PWRCL_CLK>, + <&clock_cpu PWRCL_CLK>, + <&clock_cpu PWRCL_CLK>, + <&clock_cpu PERFCL_CLK>, + <&clock_cpu PERFCL_CLK>, + <&clock_cpu PERFCL_CLK>, + <&clock_cpu PERFCL_CLK>; + + qcom,governor-per-policy; + + qcom,cpufreq-table-0 = + < 300000 >, + < 633600 >, + < 902400 >, + < 1113600 >, + < 1401600 >, + < 1536000 >, + < 1747200 >, + < 1843200 >; + + qcom,cpufreq-table-4 = + < 300000 >, + < 1113600 >, + < 1401600 >, + < 1747200 >, + < 1958400 >, + < 2150400 >, + < 2208000 >, + < 2457600 >; + }; + sdhc_1: sdhci@c0c4000 { compatible = "qcom,sdhci-msm-v5"; reg = <0xc0c4000 0x1000>, <0xc0c5000 0x1000>; @@ -1527,6 +1553,35 @@ qcom,xprt = "smem"; }; + glink_spi_xprt_wdsp: qcom,glink-spi-xprt-wdsp { + compatible = "qcom,glink-spi-xprt"; + label = "wdsp"; + qcom,remote-fifo-config = <&glink_fifo_wdsp>; + qcom,qos-config = <&glink_qos_wdsp>; + qcom,ramp-time = <0x10>, + <0x20>, + <0x30>, + <0x40>; + }; + + glink_fifo_wdsp: qcom,glink-fifo-config-wdsp { + compatible = "qcom,glink-fifo-config"; + qcom,out-read-idx-reg = <0x12000>; + qcom,out-write-idx-reg = <0x12004>; + qcom,in-read-idx-reg = <0x1200c>; + qcom,in-write-idx-reg = <0x12010>; + }; + + glink_qos_wdsp: qcom,glink-qos-config-wdsp { + compatible = "qcom,glink-qos-config"; + qcom,flow-info = <0x80 0x0>, + <0x70 0x1>, + <0x60 0x2>, + <0x50 0x3>; + qcom,mtu-size = <0x800>; + qcom,tput-stats-cycle = <0xa>; + }; + qcom,glink_pkt { compatible = "qcom,glinkpkt"; @@ -2141,7 +2196,7 @@ <&clock_rpmcc RPM_QDSS_A_CLK>; clock-names = "core_clk", "core_a_clk"; - qcom,coresight-jtagmm-cpu = <&CPU0>; + qcom,coresight-jtagmm-cpu = <&CPU4>; }; jtag_mm5: jtagmm@7d40000 { @@ -2153,7 +2208,7 @@ <&clock_rpmcc RPM_QDSS_A_CLK>; clock-names = "core_clk", "core_a_clk"; - qcom,coresight-jtagmm-cpu = <&CPU1>; + qcom,coresight-jtagmm-cpu = <&CPU5>; }; jtag_mm6: jtagmm@7e40000 { @@ -2165,7 +2220,7 @@ <&clock_rpmcc RPM_QDSS_A_CLK>; clock-names = "core_clk", "core_a_clk"; - qcom,coresight-jtagmm-cpu = <&CPU2>; + qcom,coresight-jtagmm-cpu = <&CPU6>; }; jtag_mm7: jtagmm@7f40000 { @@ -2177,7 +2232,7 @@ <&clock_rpmcc RPM_QDSS_A_CLK>; clock-names = "core_clk", "core_a_clk"; - qcom,coresight-jtagmm-cpu = <&CPU3>; + qcom,coresight-jtagmm-cpu = <&CPU7>; }; }; @@ -2247,6 +2302,7 @@ &gdsc_cpp { parent-supply = <&gdsc_camss_top>; + qcom,support-hw-trigger; status = "ok"; }; diff --git a/arch/arm/configs/msmcortex_defconfig b/arch/arm/configs/msmcortex_defconfig index c5c7d924aab6..9cf5a15e80eb 100644 --- a/arch/arm/configs/msmcortex_defconfig +++ b/arch/arm/configs/msmcortex_defconfig @@ -254,7 +254,6 @@ CONFIG_PPPOPNS=y CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -266,6 +265,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_KEYCHORD=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y diff --git a/arch/arm/configs/sdm660-perf_defconfig b/arch/arm/configs/sdm660-perf_defconfig index ac968edff299..d555a1b179d8 100644 --- a/arch/arm/configs/sdm660-perf_defconfig +++ b/arch/arm/configs/sdm660-perf_defconfig @@ -280,7 +280,6 @@ CONFIG_USB_USBNET=y CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -292,6 +291,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_KEYCHORD=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y @@ -483,7 +483,9 @@ CONFIG_GPIO_USB_DETECT=y CONFIG_SEEMP_CORE=y CONFIG_USB_BAM=y CONFIG_QCOM_CLK_SMD_RPM=y -CONFIG_MSM_GCC_660=y +CONFIG_MSM_GPUCC_660=y +CONFIG_MSM_MMCC_660=y +CONFIG_CLOCK_CPU_OSM=y CONFIG_QCOM_MDSS_PLL=y CONFIG_REMOTE_SPINLOCK_MSM=y CONFIG_ARM_SMMU=y diff --git a/arch/arm/configs/sdm660_defconfig b/arch/arm/configs/sdm660_defconfig index 10b8666a2d40..2c94274b0637 100644 --- a/arch/arm/configs/sdm660_defconfig +++ b/arch/arm/configs/sdm660_defconfig @@ -279,7 +279,6 @@ CONFIG_USB_USBNET=y CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -291,6 +290,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_KEYCHORD=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y diff --git a/arch/arm/mach-qcom/board-660.c b/arch/arm/mach-qcom/board-660.c index 597df4d2450b..5cd11f09e3a4 100644 --- a/arch/arm/mach-qcom/board-660.c +++ b/arch/arm/mach-qcom/board-660.c @@ -48,3 +48,20 @@ DT_MACHINE_START(SDM630_DT, .init_machine = sdm630_init, .dt_compat = sdm630_dt_match, MACHINE_END + +static const char *sdm658_dt_match[] __initconst = { + "qcom,sdm658", + "qcom,sda658", + NULL +}; + +static void __init sdm658_init(void) +{ + board_dt_populate(NULL); +} + +DT_MACHINE_START(SDM658_DT, + "Qualcomm Technologies, Inc. SDM 658 (Flattened Device Tree)") + .init_machine = sdm658_init, + .dt_compat = sdm658_dt_match, +MACHINE_END diff --git a/arch/arm64/configs/msm-perf_defconfig b/arch/arm64/configs/msm-perf_defconfig index 08dccf8e5022..07e413e31234 100644 --- a/arch/arm64/configs/msm-perf_defconfig +++ b/arch/arm64/configs/msm-perf_defconfig @@ -279,7 +279,6 @@ CONFIG_WIL6210=m CONFIG_CNSS=y CONFIG_CLD_LL_CORE=y CONFIG_BUS_AUTO_SUSPEND=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -293,6 +292,7 @@ CONFIG_SECURE_TOUCH=y CONFIG_TOUCHSCREEN_GEN_VKEYS=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_KEYCHORD=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y diff --git a/arch/arm64/configs/msm_defconfig b/arch/arm64/configs/msm_defconfig index 4620e74de5bc..76d949319dfa 100644 --- a/arch/arm64/configs/msm_defconfig +++ b/arch/arm64/configs/msm_defconfig @@ -265,7 +265,6 @@ CONFIG_WIL6210=m CONFIG_CNSS=y CONFIG_CLD_LL_CORE=y CONFIG_BUS_AUTO_SUSPEND=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -280,6 +279,7 @@ CONFIG_SECURE_TOUCH=y CONFIG_TOUCHSCREEN_GEN_VKEYS=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y # CONFIG_SERIO_SERPORT is not set diff --git a/arch/arm64/configs/msmcortex-perf_defconfig b/arch/arm64/configs/msmcortex-perf_defconfig index 71d067b27ddd..07d24ea6b707 100644 --- a/arch/arm64/configs/msmcortex-perf_defconfig +++ b/arch/arm64/configs/msmcortex-perf_defconfig @@ -275,7 +275,6 @@ CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_WIL6210=m CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -286,6 +285,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_UINPUT=y # CONFIG_SERIO_SERPORT is not set # CONFIG_VT is not set diff --git a/arch/arm64/configs/msmcortex_defconfig b/arch/arm64/configs/msmcortex_defconfig index 02b9e08955f6..25b5c206e1ae 100644 --- a/arch/arm64/configs/msmcortex_defconfig +++ b/arch/arm64/configs/msmcortex_defconfig @@ -275,7 +275,6 @@ CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_WIL6210=m CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -287,6 +286,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_KEYCHORD=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y diff --git a/arch/arm64/configs/sdm660-perf_defconfig b/arch/arm64/configs/sdm660-perf_defconfig index f15fd895e65c..d4a11009d60a 100644 --- a/arch/arm64/configs/sdm660-perf_defconfig +++ b/arch/arm64/configs/sdm660-perf_defconfig @@ -278,7 +278,6 @@ CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_WIL6210=m CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -289,6 +288,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_UINPUT=y # CONFIG_SERIO_SERPORT is not set # CONFIG_VT is not set diff --git a/arch/arm64/configs/sdm660_defconfig b/arch/arm64/configs/sdm660_defconfig index b52a672a5b5e..54cc7415b9a8 100644 --- a/arch/arm64/configs/sdm660_defconfig +++ b/arch/arm64/configs/sdm660_defconfig @@ -278,7 +278,6 @@ CONFIG_WCNSS_MEM_PRE_ALLOC=y CONFIG_ATH_CARDS=y CONFIG_WIL6210=m CONFIG_CLD_LL_CORE=y -CONFIG_QPNP_POWER_ON=y CONFIG_INPUT_EVDEV=y CONFIG_INPUT_KEYRESET=y CONFIG_KEYBOARD_GPIO=y @@ -290,6 +289,7 @@ CONFIG_TOUCHSCREEN_SYNAPTICS_DSX_FW_UPDATE_v21=y CONFIG_SECURE_TOUCH=y CONFIG_INPUT_MISC=y CONFIG_INPUT_HBTP_INPUT=y +CONFIG_INPUT_QPNP_POWER_ON=y CONFIG_INPUT_KEYCHORD=y CONFIG_INPUT_UINPUT=y CONFIG_INPUT_GPIO=y diff --git a/drivers/clk/qcom/clk-cpu-osm.c b/drivers/clk/qcom/clk-cpu-osm.c index ab6a1384ffbd..5ed0dba189f7 100644 --- a/drivers/clk/qcom/clk-cpu-osm.c +++ b/drivers/clk/qcom/clk-cpu-osm.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016, The Linux Foundation. All rights reserved. + * Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -88,6 +88,7 @@ enum clk_osm_trace_packet_id { #define CORE_COUNT_VAL(val) ((val & GENMASK(18, 16)) >> 16) #define SINGLE_CORE 1 #define MAX_CORE_COUNT 4 +#define DEBUG_REG_NUM 3 #define ENABLE_REG 0x1004 #define INDEX_REG 0x1150 @@ -321,6 +322,13 @@ static struct dentry *osm_debugfs_base; static struct regulator *vdd_pwrcl; static struct regulator *vdd_perfcl; +const char *clk_panic_reg_names[] = {"WDOG_DOMAIN_PSTATE_STATUS", + "WDOG_PROGRAM_COUNTER", + "APM_STATUS"}; + +const int clk_panic_reg_offsets[] = {WDOG_DOMAIN_PSTATE_STATUS, + WDOG_PROGRAM_COUNTER}; + static const struct regmap_config osm_qcom_regmap_config = { .reg_bits = 32, .reg_stride = 4, @@ -336,6 +344,7 @@ struct clk_osm { struct platform_device *vdd_dev; void *vbases[NUM_BASES]; unsigned long pbases[NUM_BASES]; + void __iomem *debug_regs[DEBUG_REG_NUM]; spinlock_t lock; u32 cpu_reg_mask; @@ -1366,6 +1375,64 @@ static int clk_osm_resources_init(struct platform_device *pdev) perfcl_clk.acd_init = false; } + pwrcl_clk.debug_regs[0] = devm_ioremap(&pdev->dev, + pwrcl_clk.pbases[OSM_BASE] + + clk_panic_reg_offsets[0], + 0x4); + if (!pwrcl_clk.debug_regs[0]) { + dev_err(&pdev->dev, "Failed to map %s debug register\n", + clk_panic_reg_names[0]); + return -ENOMEM; + } + + pwrcl_clk.debug_regs[1] = devm_ioremap(&pdev->dev, + pwrcl_clk.pbases[OSM_BASE] + + clk_panic_reg_offsets[1], + 0x4); + if (!pwrcl_clk.debug_regs[1]) { + dev_err(&pdev->dev, "Failed to map %s debug register\n", + clk_panic_reg_names[1]); + return -ENOMEM; + } + + pwrcl_clk.debug_regs[2] = devm_ioremap(&pdev->dev, + pwrcl_clk.apm_ctrl_status, + 0x4); + if (!pwrcl_clk.debug_regs[2]) { + dev_err(&pdev->dev, "Failed to map %s debug register\n", + clk_panic_reg_names[2]); + return -ENOMEM; + }; + + perfcl_clk.debug_regs[0] = devm_ioremap(&pdev->dev, + perfcl_clk.pbases[OSM_BASE] + + clk_panic_reg_offsets[0], + 0x4); + if (!perfcl_clk.debug_regs[0]) { + dev_err(&pdev->dev, "Failed to map %s debug register\n", + clk_panic_reg_names[0]); + return -ENOMEM; + } + + perfcl_clk.debug_regs[1] = devm_ioremap(&pdev->dev, + perfcl_clk.pbases[OSM_BASE] + + clk_panic_reg_offsets[1], + 0x4); + if (!perfcl_clk.debug_regs[1]) { + dev_err(&pdev->dev, "Failed to map %s debug register\n", + clk_panic_reg_names[1]); + return -ENOMEM; + } + + perfcl_clk.debug_regs[2] = devm_ioremap(&pdev->dev, + perfcl_clk.apm_ctrl_status, + 0x4); + if (!perfcl_clk.debug_regs[2]) { + dev_err(&pdev->dev, "Failed to map %s debug register\n", + clk_panic_reg_names[2]); + return -ENOMEM; + }; + vdd_pwrcl = devm_regulator_get(&pdev->dev, "vdd-pwrcl"); if (IS_ERR(vdd_pwrcl)) { rc = PTR_ERR(vdd_pwrcl); @@ -2859,36 +2926,16 @@ static int clk_osm_panic_callback(struct notifier_block *nfb, unsigned long event, void *data) { - void __iomem *virt_addr; - u32 value, reg; + int i; + u32 value; struct clk_osm *c = container_of(nfb, struct clk_osm, panic_notifier); - reg = c->pbases[OSM_BASE] + WDOG_DOMAIN_PSTATE_STATUS; - virt_addr = ioremap(reg, 0x4); - if (virt_addr != NULL) { - value = readl_relaxed(virt_addr); - pr_err("DOM%d_PSTATE_STATUS[0x%08x]=0x%08x\n", c->cluster_num, - reg, value); - iounmap(virt_addr); - } - - reg = c->pbases[OSM_BASE] + WDOG_PROGRAM_COUNTER; - virt_addr = ioremap(reg, 0x4); - if (virt_addr != NULL) { - value = readl_relaxed(virt_addr); - pr_err("DOM%d_PROGRAM_COUNTER[0x%08x]=0x%08x\n", c->cluster_num, - reg, value); - iounmap(virt_addr); - } - - virt_addr = ioremap(c->apm_ctrl_status, 0x4); - if (virt_addr != NULL) { - value = readl_relaxed(virt_addr); - pr_err("APM_CTLER_STATUS_%d[0x%08x]=0x%08x\n", c->cluster_num, - c->apm_ctrl_status, value); - iounmap(virt_addr); + for (i = 0; i < DEBUG_REG_NUM; i++) { + value = readl_relaxed(c->debug_regs[i]); + pr_err("%s_%d=0x%08x\n", clk_panic_reg_names[i], + c->cluster_num, value); } return NOTIFY_OK; @@ -3020,17 +3067,17 @@ static int clk_cpu_osm_driver_probe(struct platform_device *pdev) clk_data->clk_num = num_clks; - rc = clk_osm_resources_init(pdev); + rc = clk_osm_parse_dt_configs(pdev); if (rc) { - if (rc != -EPROBE_DEFER) - dev_err(&pdev->dev, "resources init failed, rc=%d\n", - rc); + dev_err(&pdev->dev, "Unable to parse device tree configurations\n"); return rc; } - rc = clk_osm_parse_dt_configs(pdev); + rc = clk_osm_resources_init(pdev); if (rc) { - dev_err(&pdev->dev, "Unable to parse device tree configurations\n"); + if (rc != -EPROBE_DEFER) + dev_err(&pdev->dev, "resources init failed, rc=%d\n", + rc); return rc; } diff --git a/drivers/clk/qcom/clk-smd-rpm.c b/drivers/clk/qcom/clk-smd-rpm.c index 9015d505f4dc..79db93ac5ae1 100644 --- a/drivers/clk/qcom/clk-smd-rpm.c +++ b/drivers/clk/qcom/clk-smd-rpm.c @@ -1,6 +1,6 @@ /* * Copyright (c) 2016, Linaro Limited - * Copyright (c) 2014, 2016, The Linux Foundation. All rights reserved. + * Copyright (c) 2014, 2016-2017, The Linux Foundation. All rights reserved. * * This software is licensed under the terms of the GNU General Public * License version 2, as published by the Free Software Foundation, and @@ -591,8 +591,6 @@ static DEFINE_CLK_VOTER(pnoc_msmbus_clk, pnoc_clk, LONG_MAX); static DEFINE_CLK_VOTER(pnoc_msmbus_a_clk, pnoc_a_clk, LONG_MAX); static DEFINE_CLK_VOTER(pnoc_pm_clk, pnoc_clk, LONG_MAX); static DEFINE_CLK_VOTER(pnoc_sps_clk, pnoc_clk, 0); -static DEFINE_CLK_VOTER(mmssnoc_a_clk_cpu_vote, mmssnoc_axi_rpm_a_clk, - 19200000); static DEFINE_CLK_VOTER(mmssnoc_a_cpu_clk, mmssnoc_axi_a_clk, 19200000); @@ -667,7 +665,6 @@ static struct clk_hw *msm8996_clks[] = { [CXO_OTG_CLK] = &cxo_otg_clk.hw, [CXO_PIL_LPASS_CLK] = &cxo_pil_lpass_clk.hw, [CXO_PIL_SSC_CLK] = &cxo_pil_ssc_clk.hw, - [MMSSNOC_A_CLK_CPU_VOTE] = &mmssnoc_a_clk_cpu_vote.hw }; static const struct rpm_smd_clk_desc rpm_clk_msm8996 = { @@ -879,8 +876,6 @@ static int rpm_smd_clk_probe(struct platform_device *pdev) /* Hold an active set vote for the pnoc_keepalive_a_clk */ clk_set_rate(pnoc_keepalive_a_clk.hw.clk, 19200000); clk_prepare_enable(pnoc_keepalive_a_clk.hw.clk); - - clk_prepare_enable(mmssnoc_a_clk_cpu_vote.hw.clk); } else if (is_660) { clk_prepare_enable(sdm660_cxo_a.hw.clk); diff --git a/drivers/cpufreq/cpufreq.c b/drivers/cpufreq/cpufreq.c index 118dbf1cef44..6ec828805428 100644 --- a/drivers/cpufreq/cpufreq.c +++ b/drivers/cpufreq/cpufreq.c @@ -2333,6 +2333,9 @@ static int cpufreq_cpu_callback(struct notifier_block *nfb, { unsigned int cpu = (unsigned long)hcpu; + if (!cpufreq_driver) + return NOTIFY_OK; + switch (action & ~CPU_TASKS_FROZEN) { case CPU_ONLINE: cpufreq_online(cpu); @@ -2499,6 +2502,9 @@ int cpufreq_register_driver(struct cpufreq_driver *driver_data) pr_debug("trying to register driver %s\n", driver_data->name); + /* Register for hotplug notifers before blocking hotplug. */ + register_hotcpu_notifier(&cpufreq_cpu_notifier); + /* Protect against concurrent CPU online/offline. */ get_online_cpus(); @@ -2530,7 +2536,6 @@ int cpufreq_register_driver(struct cpufreq_driver *driver_data) goto err_if_unreg; } - register_hotcpu_notifier(&cpufreq_cpu_notifier); pr_info("driver %s up and running\n", driver_data->name); out: diff --git a/drivers/cpufreq/cpufreq_interactive.c b/drivers/cpufreq/cpufreq_interactive.c index 30e1a2138002..24ac49019b29 100644 --- a/drivers/cpufreq/cpufreq_interactive.c +++ b/drivers/cpufreq/cpufreq_interactive.c @@ -490,7 +490,7 @@ static void cpufreq_interactive_timer(unsigned long data) spin_lock_irqsave(&ppol->target_freq_lock, flags); spin_lock(&ppol->load_lock); - skip_hispeed_logic = tunables->enable_prediction ? true : + skip_hispeed_logic = tunables->ignore_hispeed_on_notif && ppol->notif_pending; skip_min_sample_time = tunables->fast_ramp_down && ppol->notif_pending; ppol->notif_pending = false; diff --git a/drivers/gpu/msm/adreno-gpulist.h b/drivers/gpu/msm/adreno-gpulist.h index e6163384f9c1..2418ee003c22 100644 --- a/drivers/gpu/msm/adreno-gpulist.h +++ b/drivers/gpu/msm/adreno-gpulist.h @@ -1,4 +1,4 @@ -/* Copyright (c) 2002,2007-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2002,2007-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -289,9 +289,11 @@ static const struct adreno_gpu_core adreno_gpulist[] = { .major = 1, .minor = 2, .patchid = ANY_ID, - .features = ADRENO_64BIT, + .features = ADRENO_64BIT | ADRENO_CONTENT_PROTECTION | + ADRENO_CPZ_RETENTION, .pm4fw_name = "a530_pm4.fw", .pfpfw_name = "a530_pfp.fw", + .zap_name = "a512_zap", .gpudev = &adreno_a5xx_gpudev, .gmem_size = (SZ_256K + SZ_16K), .num_protected_regs = 0x20, diff --git a/drivers/input/Kconfig b/drivers/input/Kconfig index 9b8bcdffdfba..2557dcda7621 100644 --- a/drivers/input/Kconfig +++ b/drivers/input/Kconfig @@ -25,14 +25,6 @@ config INPUT if INPUT -config QPNP_POWER_ON - tristate "QPNP PMIC POWER-ON Driver" - depends on SPMI && ARCH_QCOM - help - This driver supports the power-on functionality on Qualcomm - PNP PMIC. It currently supports reporting the change in status of - the KPDPWR_N line (connected to the power-key). - config INPUT_LEDS tristate "Export input device LEDs in sysfs" depends on LEDS_CLASS diff --git a/drivers/input/Makefile b/drivers/input/Makefile index fd35ebf6acd9..2a6d05ab9170 100644 --- a/drivers/input/Makefile +++ b/drivers/input/Makefile @@ -7,7 +7,6 @@ obj-$(CONFIG_INPUT) += input-core.o input-core-y := input.o input-compat.o input-mt.o ff-core.o -obj-$(CONFIG_QPNP_POWER_ON) += qpnp-power-on.o obj-$(CONFIG_INPUT_FF_MEMLESS) += ff-memless.o obj-$(CONFIG_INPUT_POLLDEV) += input-polldev.o obj-$(CONFIG_INPUT_SPARSEKMAP) += sparse-keymap.o diff --git a/drivers/input/misc/Kconfig b/drivers/input/misc/Kconfig index 9c1380b65b77..5cfa1848e37c 100644 --- a/drivers/input/misc/Kconfig +++ b/drivers/input/misc/Kconfig @@ -161,6 +161,15 @@ config INPUT_PMIC8XXX_PWRKEY To compile this driver as a module, choose M here: the module will be called pmic8xxx-pwrkey. +config INPUT_QPNP_POWER_ON + tristate "QPNP PMIC Power-on support" + depends on SPMI + help + This option enables device driver support for the power-on + functionality of Qualcomm Technologies, Inc. PNP PMICs. It supports + reporting the change in status of the KPDPWR_N line (connected to the + power-key) as well as reset features. + config INPUT_SPARCSPKR tristate "SPARC Speaker support" depends on PCI && SPARC64 diff --git a/drivers/input/misc/Makefile b/drivers/input/misc/Makefile index 4e806ac056ce..a5ab4b762d31 100644 --- a/drivers/input/misc/Makefile +++ b/drivers/input/misc/Makefile @@ -57,6 +57,7 @@ obj-$(CONFIG_INPUT_PCSPKR) += pcspkr.o obj-$(CONFIG_INPUT_PM8941_PWRKEY) += pm8941-pwrkey.o obj-$(CONFIG_INPUT_PM8XXX_VIBRATOR) += pm8xxx-vibrator.o obj-$(CONFIG_INPUT_PMIC8XXX_PWRKEY) += pmic8xxx-pwrkey.o +obj-$(CONFIG_INPUT_QPNP_POWER_ON) += qpnp-power-on.o obj-$(CONFIG_INPUT_POWERMATE) += powermate.o obj-$(CONFIG_INPUT_PWM_BEEPER) += pwm-beeper.o obj-$(CONFIG_INPUT_RB532_BUTTON) += rb532_button.o diff --git a/drivers/input/qpnp-power-on.c b/drivers/input/misc/qpnp-power-on.c index 967b23cae05c..e1c16aa5da43 100644 --- a/drivers/input/qpnp-power-on.c +++ b/drivers/input/misc/qpnp-power-on.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2012-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2012-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -30,7 +30,7 @@ #include <linux/regulator/driver.h> #include <linux/regulator/machine.h> #include <linux/regulator/of_regulator.h> -#include <linux/qpnp/power-on.h> +#include <linux/input/qpnp-power-on.h> #include <linux/power_supply.h> #define PMIC_VER_8941 0x01 @@ -223,7 +223,7 @@ struct qpnp_pon { static int pon_ship_mode_en; module_param_named( - ship_mode_en, pon_ship_mode_en, int, S_IRUSR | S_IWUSR + ship_mode_en, pon_ship_mode_en, int, 0600 ); static struct qpnp_pon *sys_reset_dev; diff --git a/drivers/media/dvb-core/dvb_ringbuffer.c b/drivers/media/dvb-core/dvb_ringbuffer.c index 0d44deed65bd..8ab60a4fec00 100644 --- a/drivers/media/dvb-core/dvb_ringbuffer.c +++ b/drivers/media/dvb-core/dvb_ringbuffer.c @@ -233,9 +233,11 @@ ssize_t dvb_ringbuffer_write_user(struct dvb_ringbuffer *rbuf, */ smp_store_release(&rbuf->pwrite, 0); } - status = copy_from_user(rbuf->data+rbuf->pwrite, buf, todo); - if (status) - return len - todo; + + if (copy_from_user(rbuf->data + rbuf->pwrite, buf, todo)) { + smp_store_release(&rbuf->pwrite, oldpwrite); + return -EFAULT; + } /* smp_store_release() for write pointer update, see above */ smp_store_release(&rbuf->pwrite, (rbuf->pwrite + todo) % rbuf->size); diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp.c index 35daf30bac63..840d84388a17 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp.c @@ -500,6 +500,10 @@ static int vfe_probe(struct platform_device *pdev) memset(&vfe_common_data, 0, sizeof(vfe_common_data)); mutex_init(&vfe_common_data.vfe_common_mutex); spin_lock_init(&vfe_common_data.common_dev_data_lock); + spin_lock_init(&vfe_common_data.vfe_irq_dump. + common_dev_irq_dump_lock); + spin_lock_init(&vfe_common_data.vfe_irq_dump. + common_dev_tasklet_dump_lock); for (i = 0; i < (VFE_AXI_SRC_MAX * MAX_VFE); i++) spin_lock_init(&(vfe_common_data.streams[i].lock)); for (i = 0; i < (MSM_ISP_STATS_MAX * MAX_VFE); i++) diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp.h b/drivers/media/platform/msm/camera_v2/isp/msm_isp.h index 9c7eba21fde1..4b881f4fd7b6 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp.h +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp.h @@ -66,6 +66,8 @@ #define MAX_BUFFERS_IN_HW 2 #define MAX_VFE 2 +#define MAX_VFE_IRQ_DEBUG_DUMP_SIZE 10 +#define MAX_RECOVERY_THRESHOLD 5 struct vfe_device; struct msm_vfe_axi_stream; @@ -133,6 +135,8 @@ struct msm_isp_timestamp { }; struct msm_vfe_irq_ops { + void (*read_and_clear_irq_status)(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1); void (*read_irq_status)(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1); void (*process_reg_update)(struct vfe_device *vfe_dev, @@ -525,6 +529,7 @@ struct msm_vfe_axi_shared_data { uint16_t stream_handle_cnt; uint32_t event_mask; uint8_t enable_frameid_recovery; + uint8_t recovery_count; }; struct msm_vfe_stats_hardware_info { @@ -691,6 +696,26 @@ struct master_slave_resource_info { enum msm_vfe_dual_cam_sync_mode dual_sync_mode; }; +struct msm_vfe_irq_debug_info { + uint32_t vfe_id; + struct msm_isp_timestamp ts; + uint32_t core_id; + uint32_t irq_status0[MAX_VFE]; + uint32_t irq_status1[MAX_VFE]; + uint32_t ping_pong_status[MAX_VFE]; +}; + +struct msm_vfe_irq_dump { + spinlock_t common_dev_irq_dump_lock; + spinlock_t common_dev_tasklet_dump_lock; + uint8_t current_irq_index; + uint8_t current_tasklet_index; + struct msm_vfe_irq_debug_info + irq_debug[MAX_VFE_IRQ_DEBUG_DUMP_SIZE]; + struct msm_vfe_irq_debug_info + tasklet_debug[MAX_VFE_IRQ_DEBUG_DUMP_SIZE]; +}; + struct msm_vfe_common_dev_data { spinlock_t common_dev_data_lock; struct dual_vfe_resource *dual_vfe_res; @@ -698,6 +723,8 @@ struct msm_vfe_common_dev_data { struct msm_vfe_axi_stream streams[VFE_AXI_SRC_MAX * MAX_VFE]; struct msm_vfe_stats_stream stats_streams[MSM_ISP_STATS_MAX * MAX_VFE]; struct mutex vfe_common_mutex; + /* Irq debug Info */ + struct msm_vfe_irq_dump vfe_irq_dump; }; struct msm_vfe_common_subdev { @@ -790,8 +817,9 @@ struct vfe_device { /* irq info */ uint32_t irq0_mask; uint32_t irq1_mask; - uint32_t bus_err_ign_mask; + uint32_t recovery_irq0_mask; + uint32_t recovery_irq1_mask; }; struct vfe_parent_device { diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp32.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp32.c index 43f562b18209..bf18fc59585c 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp32.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp32.c @@ -576,7 +576,7 @@ static void msm_vfe32_process_error_status(struct vfe_device *vfe_dev) pr_err("%s: axi error\n", __func__); } -static void msm_vfe32_read_irq_status(struct vfe_device *vfe_dev, +static void msm_vfe32_read_and_clear_irq_status(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1) { *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x2C); @@ -594,6 +594,13 @@ static void msm_vfe32_read_irq_status(struct vfe_device *vfe_dev, msm_camera_io_r(vfe_dev->vfe_base + 0x7B4); } +static void msm_vfe32_read_irq_status(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t irq_status1) +{ + *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x2C); + *irq_status1 = msm_camera_io_r(vfe_dev->vfe_base + 0x30); +} + static void msm_vfe32_process_reg_update(struct vfe_device *vfe_dev, uint32_t irq_status0, uint32_t irq_status1, struct msm_isp_timestamp *ts) @@ -1423,6 +1430,8 @@ struct msm_vfe_hardware_info vfe32_hw_info = { .vfe_clk_idx = VFE32_CLK_IDX, .vfe_ops = { .irq_ops = { + .read_and_clear_irq_status = + msm_vfe32_read_and_clear_irq_status, .read_irq_status = msm_vfe32_read_irq_status, .process_camif_irq = msm_vfe32_process_camif_irq, .process_reset_irq = msm_vfe32_process_reset_irq, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp40.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp40.c index ab01d37790d6..8e549c338bdd 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp40.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp40.c @@ -566,7 +566,7 @@ static void msm_vfe40_process_error_status(struct vfe_device *vfe_dev) msm_isp_update_last_overflow_ab_ib(vfe_dev); } -static void msm_vfe40_read_irq_status(struct vfe_device *vfe_dev, +static void msm_vfe40_read_and_clear_irq_status(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1) { *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x38); @@ -599,6 +599,13 @@ static void msm_vfe40_read_irq_status(struct vfe_device *vfe_dev, } +static void msm_vfe40_read_irq_status(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1) +{ + *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x38); + *irq_status1 = msm_camera_io_r(vfe_dev->vfe_base + 0x3C); +} + static void msm_vfe40_process_reg_update(struct vfe_device *vfe_dev, uint32_t irq_status0, uint32_t irq_status1, struct msm_isp_timestamp *ts) @@ -1770,7 +1777,8 @@ static int msm_vfe40_axi_halt(struct vfe_device *vfe_dev, static void msm_vfe40_axi_restart(struct vfe_device *vfe_dev, uint32_t blocking, uint32_t enable_camif) { - msm_vfe40_config_irq(vfe_dev, 0x800000E0, 0xFEFFFF7E, + msm_vfe40_config_irq(vfe_dev, vfe_dev->recovery_irq0_mask, + vfe_dev->recovery_irq1_mask, MSM_ISP_IRQ_ENABLE); msm_camera_io_w_mb(0x140000, vfe_dev->vfe_base + 0x318); @@ -2198,6 +2206,8 @@ struct msm_vfe_hardware_info vfe40_hw_info = { .min_ib = 12000000, .vfe_ops = { .irq_ops = { + .read_and_clear_irq_status = + msm_vfe40_read_and_clear_irq_status, .read_irq_status = msm_vfe40_read_irq_status, .process_camif_irq = msm_vfe40_process_input_irq, .process_reset_irq = msm_vfe40_process_reset_irq, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp44.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp44.c index 0a72a041de28..957cbc292be3 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp44.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp44.c @@ -401,7 +401,7 @@ static void msm_vfe44_process_error_status(struct vfe_device *vfe_dev) } } -static void msm_vfe44_read_irq_status(struct vfe_device *vfe_dev, +static void msm_vfe44_read_and_clear_irq_status(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1) { *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x38); @@ -429,6 +429,13 @@ static void msm_vfe44_read_irq_status(struct vfe_device *vfe_dev, } +static void msm_vfe44_read_irq_status(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1) +{ + *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x38); + *irq_status1 = msm_camera_io_r(vfe_dev->vfe_base + 0x3C); +} + static void msm_vfe44_process_reg_update(struct vfe_device *vfe_dev, uint32_t irq_status0, uint32_t irq_status1, struct msm_isp_timestamp *ts) @@ -1341,8 +1348,8 @@ static int msm_vfe44_axi_halt(struct vfe_device *vfe_dev, static void msm_vfe44_axi_restart(struct vfe_device *vfe_dev, uint32_t blocking, uint32_t enable_camif) { - msm_vfe44_config_irq(vfe_dev, 0x800000E0, 0xFFFFFF7E, - MSM_ISP_IRQ_ENABLE); + msm_vfe44_config_irq(vfe_dev, vfe_dev->recovery_irq0_mask, + vfe_dev->recovery_irq1_mask, MSM_ISP_IRQ_ENABLE); msm_camera_io_w_mb(0x140000, vfe_dev->vfe_base + 0x318); /* Start AXI */ @@ -1806,6 +1813,8 @@ struct msm_vfe_hardware_info vfe44_hw_info = { .min_ib = 100000000, .vfe_ops = { .irq_ops = { + .read_and_clear_irq_status = + msm_vfe44_read_and_clear_irq_status, .read_irq_status = msm_vfe44_read_irq_status, .process_camif_irq = msm_vfe44_process_input_irq, .process_reset_irq = msm_vfe44_process_reset_irq, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp46.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp46.c index f2d53c956fdc..cc768db875db 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp46.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp46.c @@ -345,7 +345,7 @@ static void msm_vfe46_process_error_status(struct vfe_device *vfe_dev) pr_err("%s: status bf scale bus overflow\n", __func__); } -static void msm_vfe46_read_irq_status(struct vfe_device *vfe_dev, +static void msm_vfe46_read_and_clear_irq_status(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1) { *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x6C); @@ -369,6 +369,13 @@ static void msm_vfe46_read_irq_status(struct vfe_device *vfe_dev, } +static void msm_vfe46_read_irq_status(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1) +{ + *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x6C); + *irq_status1 = msm_camera_io_r(vfe_dev->vfe_base + 0x70); +} + static void msm_vfe46_process_reg_update(struct vfe_device *vfe_dev, uint32_t irq_status0, uint32_t irq_status1, struct msm_isp_timestamp *ts) @@ -1406,7 +1413,8 @@ static int msm_vfe46_axi_halt(struct vfe_device *vfe_dev, static void msm_vfe46_axi_restart(struct vfe_device *vfe_dev, uint32_t blocking, uint32_t enable_camif) { - msm_vfe46_config_irq(vfe_dev, 0x810000E0, 0xFFFFFF7E, + msm_vfe46_config_irq(vfe_dev, vfe_dev->recovery_irq0_mask, + vfe_dev->recovery_irq1_mask, MSM_ISP_IRQ_ENABLE); msm_camera_io_w_mb(0x20000, vfe_dev->vfe_base + 0x3CC); @@ -1882,6 +1890,8 @@ struct msm_vfe_hardware_info vfe46_hw_info = { .min_ib = 100000000, .vfe_ops = { .irq_ops = { + .read_and_clear_irq_status = + msm_vfe46_read_and_clear_irq_status, .read_irq_status = msm_vfe46_read_irq_status, .process_camif_irq = msm_vfe46_process_input_irq, .process_reset_irq = msm_vfe46_process_reset_irq, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp47.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp47.c index 71ee9211a434..9747cfd6dca3 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp47.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp47.c @@ -556,7 +556,7 @@ void msm_vfe47_process_error_status(struct vfe_device *vfe_dev) pr_err("%s: status dsp error\n", __func__); } -void msm_vfe47_read_irq_status(struct vfe_device *vfe_dev, +void msm_vfe47_read_and_clear_irq_status(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1) { *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x6C); @@ -582,6 +582,13 @@ void msm_vfe47_read_irq_status(struct vfe_device *vfe_dev, } +void msm_vfe47_read_irq_status(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1) +{ + *irq_status0 = msm_camera_io_r(vfe_dev->vfe_base + 0x6C); + *irq_status1 = msm_camera_io_r(vfe_dev->vfe_base + 0x70); +} + void msm_vfe47_process_reg_update(struct vfe_device *vfe_dev, uint32_t irq_status0, uint32_t irq_status1, struct msm_isp_timestamp *ts) @@ -1931,7 +1938,9 @@ void msm_vfe47_axi_restart(struct vfe_device *vfe_dev, uint32_t blocking, uint32_t enable_camif) { vfe_dev->hw_info->vfe_ops.irq_ops.config_irq(vfe_dev, - 0x810000E0, 0xFFFFFF7E, MSM_ISP_IRQ_ENABLE); + vfe_dev->recovery_irq0_mask, + vfe_dev->recovery_irq1_mask, + MSM_ISP_IRQ_ENABLE); /* Start AXI */ msm_camera_io_w(0x0, vfe_dev->vfe_base + 0x400); @@ -2783,7 +2792,8 @@ struct msm_vfe_hardware_info vfe47_hw_info = { .min_ab = 100000000, .vfe_ops = { .irq_ops = { - .read_irq_status = msm_vfe47_read_irq_status, + .read_and_clear_irq_status = + msm_vfe47_read_and_clear_irq_status, .process_camif_irq = msm_vfe47_process_input_irq, .process_reset_irq = msm_vfe47_process_reset_irq, .process_halt_irq = msm_vfe47_process_halt_irq, @@ -2793,6 +2803,7 @@ struct msm_vfe_hardware_info vfe47_hw_info = { .process_stats_irq = msm_isp_process_stats_irq, .process_epoch_irq = msm_vfe47_process_epoch_irq, .config_irq = msm_vfe47_config_irq, + .read_irq_status = msm_vfe47_read_irq_status, }, .axi_ops = { .reload_wm = msm_vfe47_axi_reload_wm, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp47.h b/drivers/media/platform/msm/camera_v2/isp/msm_isp47.h index 55cf6a17b18c..22a1a21bce9a 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp47.h +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp47.h @@ -30,6 +30,8 @@ enum msm_vfe47_stats_comp_idx { extern struct msm_vfe_hardware_info vfe47_hw_info; +void msm_vfe47_read_and_clear_irq_status(struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1); void msm_vfe47_read_irq_status(struct vfe_device *vfe_dev, uint32_t *irq_status0, uint32_t *irq_status1); void msm_vfe47_enable_camif_error(struct vfe_device *vfe_dev, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp48.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp48.c index f346ceb6c9e5..916f30049bf0 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp48.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp48.c @@ -269,6 +269,8 @@ struct msm_vfe_hardware_info vfe48_hw_info = { .min_ab = 100000000, .vfe_ops = { .irq_ops = { + .read_and_clear_irq_status = + msm_vfe47_read_and_clear_irq_status, .read_irq_status = msm_vfe47_read_irq_status, .process_camif_irq = msm_vfe47_process_input_irq, .process_reset_irq = msm_vfe47_process_reset_irq, diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c index 941119fad78e..60801ff6be0a 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c @@ -558,6 +558,7 @@ static int msm_isp_composite_irq(struct vfe_device *vfe_dev, { /* interrupt recv on same vfe w/o recv on other vfe */ if (stream_info->composite_irq[irq] & (1 << vfe_dev->pdev->id)) { + msm_isp_dump_ping_pong_mismatch(vfe_dev); pr_err("%s: irq %d out of sync for dual vfe on vfe %d\n", __func__, irq, vfe_dev->pdev->id); return -EINVAL; @@ -1604,7 +1605,23 @@ void msm_isp_halt_send_error(struct vfe_device *vfe_dev, uint32_t event) struct msm_isp_event_data error_event; struct msm_vfe_axi_halt_cmd halt_cmd; struct vfe_device *temp_dev = NULL; + uint32_t irq_status0 = 0, irq_status1 = 0; + if (atomic_read(&vfe_dev->error_info.overflow_state) != + NO_OVERFLOW) + /* Recovery is already in Progress */ + return; + + if (event == ISP_EVENT_PING_PONG_MISMATCH && + vfe_dev->axi_data.recovery_count < MAX_RECOVERY_THRESHOLD) { + pr_err("%s: ping pong mismatch on vfe%d recovery count %d\n", + __func__, vfe_dev->pdev->id, + vfe_dev->axi_data.recovery_count); + msm_isp_process_overflow_irq(vfe_dev, + &irq_status0, &irq_status1, 1); + vfe_dev->axi_data.recovery_count++; + return; + } memset(&halt_cmd, 0, sizeof(struct msm_vfe_axi_halt_cmd)); memset(&error_event, 0, sizeof(struct msm_isp_event_data)); halt_cmd.stop_camif = 1; @@ -3777,6 +3794,7 @@ void msm_isp_process_axi_irq_stream(struct vfe_device *vfe_dev, (~(pingpong_status >> stream_info->wm[vfe_idx][i]) & 0x1)) { spin_unlock_irqrestore(&stream_info->lock, flags); + msm_isp_dump_ping_pong_mismatch(vfe_dev); pr_err("%s: Write master ping pong mismatch. Status: 0x%x %x\n", __func__, pingpong_status, stream_info->stream_src); @@ -3798,7 +3816,7 @@ void msm_isp_process_axi_irq_stream(struct vfe_device *vfe_dev, spin_unlock_irqrestore(&stream_info->lock, flags); if (rc < 0) msm_isp_halt_send_error(vfe_dev, - ISP_EVENT_BUF_FATAL_ERROR); + ISP_EVENT_PING_PONG_MISMATCH); return; } diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp_stats_util.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp_stats_util.c index 38ce78d941c9..72703c9590ed 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp_stats_util.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp_stats_util.c @@ -195,7 +195,7 @@ static int32_t msm_isp_stats_buf_divert(struct vfe_device *vfe_dev, spin_unlock_irqrestore(&stream_info->lock, flags); if (rc < 0) msm_isp_halt_send_error(vfe_dev, - ISP_EVENT_BUF_FATAL_ERROR); + ISP_EVENT_PING_PONG_MISMATCH); return rc; } diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.c index 4abb6d1d91a8..e238f54a9100 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.c +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.c @@ -21,6 +21,9 @@ #include "msm_camera_io_util.h" #include "cam_smmu_api.h" #include "msm_isp48.h" +#define CREATE_TRACE_POINTS +#include "trace/events/msm_cam.h" + #define MAX_ISP_V4l2_EVENTS 100 static DEFINE_MUTEX(bandwidth_mgr_mutex); @@ -1784,9 +1787,10 @@ static inline void msm_isp_update_error_info(struct vfe_device *vfe_dev, vfe_dev->error_info.error_count++; } -static int msm_isp_process_overflow_irq( +int msm_isp_process_overflow_irq( struct vfe_device *vfe_dev, - uint32_t *irq_status0, uint32_t *irq_status1) + uint32_t *irq_status0, uint32_t *irq_status1, + uint8_t force_overflow) { uint32_t overflow_mask; uint32_t bus_err = 0; @@ -1816,7 +1820,7 @@ static int msm_isp_process_overflow_irq( get_overflow_mask(&overflow_mask); overflow_mask &= *irq_status1; - if (overflow_mask) { + if (overflow_mask || force_overflow) { struct msm_isp_event_data error_event; int i; struct msm_vfe_axi_shared_data *axi_data = &vfe_dev->axi_data; @@ -1840,7 +1844,8 @@ static int msm_isp_process_overflow_irq( pr_err("%s: wm %d assigned to stream handle %x\n", __func__, i, axi_data->free_wm[i]); } - + vfe_dev->recovery_irq0_mask = vfe_dev->irq0_mask; + vfe_dev->recovery_irq1_mask = vfe_dev->irq1_mask; vfe_dev->hw_info->vfe_ops.core_ops. set_halt_restart_mask(vfe_dev); /* mask off other vfe if dual vfe is used */ @@ -1855,6 +1860,8 @@ static int msm_isp_process_overflow_irq( atomic_set(&temp_vfe->error_info.overflow_state, OVERFLOW_DETECTED); + temp_vfe->recovery_irq0_mask = temp_vfe->irq0_mask; + temp_vfe->recovery_irq1_mask = temp_vfe->irq1_mask; temp_vfe->hw_info->vfe_ops.core_ops. set_halt_restart_mask(temp_vfe); } @@ -1889,6 +1896,77 @@ void msm_isp_reset_burst_count_and_frame_drop( msm_isp_reset_framedrop(vfe_dev, stream_info); } +void msm_isp_prepare_irq_debug_info(struct vfe_device *vfe_dev, + uint32_t irq_status0, uint32_t irq_status1) +{ + + unsigned long flags; + struct msm_vfe_irq_debug_info *irq_debug; + uint8_t current_index; + + spin_lock_irqsave(&vfe_dev->common_data->vfe_irq_dump. + common_dev_irq_dump_lock, flags); + /* Fill current VFE debug info */ + current_index = vfe_dev->common_data->vfe_irq_dump. + current_irq_index % MAX_VFE_IRQ_DEBUG_DUMP_SIZE; + irq_debug = &vfe_dev->common_data->vfe_irq_dump. + irq_debug[current_index]; + irq_debug->vfe_id = vfe_dev->pdev->id; + irq_debug->core_id = smp_processor_id(); + msm_isp_get_timestamp(&irq_debug->ts, vfe_dev); + irq_debug->irq_status0[vfe_dev->pdev->id] = irq_status0; + irq_debug->irq_status1[vfe_dev->pdev->id] = irq_status1; + irq_debug->ping_pong_status[vfe_dev->pdev->id] = + vfe_dev->hw_info->vfe_ops.axi_ops. + get_pingpong_status(vfe_dev); + if (vfe_dev->is_split && + (vfe_dev->common_data-> + dual_vfe_res->vfe_dev[!vfe_dev->pdev->id]) + && (vfe_dev->common_data->dual_vfe_res-> + vfe_dev[!vfe_dev->pdev->id]->vfe_open_cnt)) { + /* Fill other VFE debug Info */ + vfe_dev->hw_info->vfe_ops.irq_ops.read_irq_status( + vfe_dev->common_data->dual_vfe_res-> + vfe_dev[!vfe_dev->pdev->id], + &irq_debug->irq_status0[!vfe_dev->pdev->id], + &irq_debug->irq_status1[!vfe_dev->pdev->id]); + irq_debug->ping_pong_status[!vfe_dev->pdev->id] = + vfe_dev->hw_info->vfe_ops.axi_ops. + get_pingpong_status(vfe_dev->common_data-> + dual_vfe_res->vfe_dev[!vfe_dev->pdev->id]); + } + vfe_dev->common_data->vfe_irq_dump.current_irq_index++; + spin_unlock_irqrestore(&vfe_dev->common_data->vfe_irq_dump. + common_dev_irq_dump_lock, flags); +} + +void msm_isp_prepare_tasklet_debug_info(struct vfe_device *vfe_dev, + uint32_t irq_status0, uint32_t irq_status1, + struct msm_isp_timestamp ts) +{ + struct msm_vfe_irq_debug_info *irq_debug; + uint8_t current_index; + unsigned long flags; + + spin_lock_irqsave(&vfe_dev->common_data->vfe_irq_dump. + common_dev_tasklet_dump_lock, flags); + current_index = vfe_dev->common_data->vfe_irq_dump. + current_tasklet_index % MAX_VFE_IRQ_DEBUG_DUMP_SIZE; + irq_debug = &vfe_dev->common_data->vfe_irq_dump. + tasklet_debug[current_index]; + irq_debug->vfe_id = vfe_dev->pdev->id; + irq_debug->core_id = smp_processor_id(); + irq_debug->ts = ts; + irq_debug->irq_status0[vfe_dev->pdev->id] = irq_status0; + irq_debug->irq_status1[vfe_dev->pdev->id] = irq_status1; + irq_debug->ping_pong_status[vfe_dev->pdev->id] = + vfe_dev->hw_info->vfe_ops.axi_ops. + get_pingpong_status(vfe_dev); + vfe_dev->common_data->vfe_irq_dump.current_tasklet_index++; + spin_unlock_irqrestore(&vfe_dev->common_data->vfe_irq_dump. + common_dev_tasklet_dump_lock, flags); +} + static void msm_isp_enqueue_tasklet_cmd(struct vfe_device *vfe_dev, uint32_t irq_status0, uint32_t irq_status1) { @@ -1923,7 +2001,7 @@ irqreturn_t msm_isp_process_irq(int irq_num, void *data) uint32_t error_mask0, error_mask1; vfe_dev->hw_info->vfe_ops.irq_ops. - read_irq_status(vfe_dev, &irq_status0, &irq_status1); + read_and_clear_irq_status(vfe_dev, &irq_status0, &irq_status1); if ((irq_status0 == 0) && (irq_status1 == 0)) { ISP_DBG("%s:VFE%d irq_status0 & 1 are both 0\n", @@ -1932,7 +2010,7 @@ irqreturn_t msm_isp_process_irq(int irq_num, void *data) } if (msm_isp_process_overflow_irq(vfe_dev, - &irq_status0, &irq_status1)) { + &irq_status0, &irq_status1, 0)) { /* if overflow initiated no need to handle the interrupts */ pr_err("overflow processed\n"); return IRQ_HANDLED; @@ -1953,7 +2031,7 @@ irqreturn_t msm_isp_process_irq(int irq_num, void *data) ISP_DBG("%s: error_mask0/1 & error_count are set!\n", __func__); return IRQ_HANDLED; } - + msm_isp_prepare_irq_debug_info(vfe_dev, irq_status0, irq_status1); msm_isp_enqueue_tasklet_cmd(vfe_dev, irq_status0, irq_status1); return IRQ_HANDLED; @@ -1991,6 +2069,8 @@ void msm_isp_do_tasklet(unsigned long data) irq_status1 = queue_cmd->vfeInterruptStatus1; ts = queue_cmd->ts; spin_unlock_irqrestore(&vfe_dev->tasklet_lock, flags); + msm_isp_prepare_tasklet_debug_info(vfe_dev, + irq_status0, irq_status1, ts); ISP_DBG("%s: vfe_id %d status0: 0x%x status1: 0x%x\n", __func__, vfe_dev->pdev->id, irq_status0, irq_status1); irq_ops->process_reset_irq(vfe_dev, @@ -2242,3 +2322,53 @@ void msm_isp_flush_tasklet(struct vfe_device *vfe_dev) return; } +void msm_isp_irq_debug_dump(struct vfe_device *vfe_dev) +{ + + uint8_t i, dump_index; + unsigned long flags; + + spin_lock_irqsave(&vfe_dev->common_data->vfe_irq_dump. + common_dev_irq_dump_lock, flags); + dump_index = vfe_dev->common_data->vfe_irq_dump. + current_irq_index; + for (i = 0; i < MAX_VFE_IRQ_DEBUG_DUMP_SIZE; i++) { + trace_msm_cam_ping_pong_debug_dump( + vfe_dev->common_data->vfe_irq_dump. + irq_debug[dump_index % MAX_VFE_IRQ_DEBUG_DUMP_SIZE]); + dump_index++; + } + spin_unlock_irqrestore(&vfe_dev->common_data->vfe_irq_dump. + common_dev_irq_dump_lock, flags); +} + + +void msm_isp_tasklet_debug_dump(struct vfe_device *vfe_dev) +{ + + uint8_t i, dump_index; + unsigned long flags; + + spin_lock_irqsave(&vfe_dev->common_data->vfe_irq_dump. + common_dev_tasklet_dump_lock, flags); + dump_index = vfe_dev->common_data->vfe_irq_dump. + current_tasklet_index; + for (i = 0; i < MAX_VFE_IRQ_DEBUG_DUMP_SIZE; i++) { + trace_msm_cam_tasklet_debug_dump( + vfe_dev->common_data->vfe_irq_dump. + tasklet_debug[ + dump_index % MAX_VFE_IRQ_DEBUG_DUMP_SIZE]); + dump_index++; + } + spin_unlock_irqrestore(&vfe_dev->common_data->vfe_irq_dump. + common_dev_tasklet_dump_lock, flags); +} + +void msm_isp_dump_ping_pong_mismatch(struct vfe_device *vfe_dev) +{ + + trace_msm_cam_string(" ***** msm_isp_dump_irq_debug ****"); + msm_isp_irq_debug_dump(vfe_dev); + trace_msm_cam_string(" ***** msm_isp_dump_taskelet_debug ****"); + msm_isp_tasklet_debug_dump(vfe_dev); +} diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.h b/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.h index f4280581a730..d075bd1721ac 100644 --- a/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.h +++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp_util.h @@ -72,4 +72,9 @@ void msm_isp_print_fourcc_error(const char *origin, uint32_t fourcc_format); void msm_isp_flush_tasklet(struct vfe_device *vfe_dev); void msm_isp_get_timestamp(struct msm_isp_timestamp *time_stamp, struct vfe_device *vfe_dev); +void msm_isp_dump_ping_pong_mismatch(struct vfe_device *vfe_dev); +int msm_isp_process_overflow_irq( + struct vfe_device *vfe_dev, + uint32_t *irq_status0, uint32_t *irq_status1, + uint8_t force_overflow); #endif /* __MSM_ISP_UTIL_H__ */ diff --git a/drivers/media/platform/msm/camera_v2/pproc/cpp/msm_cpp.c b/drivers/media/platform/msm/camera_v2/pproc/cpp/msm_cpp.c index 4527d6699b88..2c661fbcd83c 100644 --- a/drivers/media/platform/msm/camera_v2/pproc/cpp/msm_cpp.c +++ b/drivers/media/platform/msm/camera_v2/pproc/cpp/msm_cpp.c @@ -2479,7 +2479,7 @@ static int msm_cpp_cfg_frame(struct cpp_device *cpp_dev, struct msm_buf_mngr_info buff_mgr_info, dup_buff_mgr_info; int32_t in_fd; int32_t num_output_bufs = 1; - int32_t stripe_base = 0; + uint32_t stripe_base = 0; uint32_t stripe_size; uint8_t tnr_enabled; enum msm_camera_buf_mngr_buf_type buf_type = @@ -2514,6 +2514,13 @@ static int msm_cpp_cfg_frame(struct cpp_device *cpp_dev, return -EINVAL; } + if (stripe_base == UINT_MAX || new_frame->num_strips > + (UINT_MAX - 1 - stripe_base) / stripe_size) { + pr_err("Invalid frame message,num_strips %d is large\n", + new_frame->num_strips); + return -EINVAL; + } + if ((stripe_base + new_frame->num_strips * stripe_size + 1) != new_frame->msg_len) { pr_err("Invalid frame message,len=%d,expected=%d\n", diff --git a/drivers/media/platform/msm/sde/rotator/sde_rotator_dev.c b/drivers/media/platform/msm/sde/rotator/sde_rotator_dev.c index 4008bae5ffee..347c0bef163f 100644 --- a/drivers/media/platform/msm/sde/rotator/sde_rotator_dev.c +++ b/drivers/media/platform/msm/sde/rotator/sde_rotator_dev.c @@ -416,23 +416,10 @@ static int sde_rotator_start_streaming(struct vb2_queue *q, unsigned int count) { struct sde_rotator_ctx *ctx = vb2_get_drv_priv(q); struct sde_rotator_device *rot_dev = ctx->rot_dev; - struct sde_rotation_config config; - int ret; SDEDEV_DBG(rot_dev->dev, "start streaming s:%d t:%d\n", ctx->session_id, q->type); - sde_rot_mgr_lock(rot_dev->mgr); - sde_rotator_get_config_from_ctx(ctx, &config); - ret = sde_rotator_session_config(rot_dev->mgr, ctx->private, &config); - sde_rot_mgr_unlock(rot_dev->mgr); - if (ret < 0) { - SDEDEV_ERR(rot_dev->dev, - "fail config in stream on s:%d t:%d r:%d\n", - ctx->session_id, q->type, ret); - return -EINVAL; - } - if (!IS_ERR_OR_NULL(ctx->request) || atomic_read(&ctx->command_pending)) SDEDEV_ERR(rot_dev->dev, @@ -1501,11 +1488,39 @@ static int sde_rotator_streamon(struct file *file, void *fh, enum v4l2_buf_type buf_type) { struct sde_rotator_ctx *ctx = sde_rotator_ctx_from_fh(fh); + struct sde_rotator_device *rot_dev = ctx->rot_dev; + struct sde_rotation_config config; + struct vb2_queue *vq; int ret; SDEDEV_DBG(ctx->rot_dev->dev, "stream on s:%d t:%d\n", ctx->session_id, buf_type); + vq = v4l2_m2m_get_vq(ctx->fh.m2m_ctx, + buf_type == V4L2_BUF_TYPE_VIDEO_OUTPUT ? + V4L2_BUF_TYPE_VIDEO_CAPTURE : + V4L2_BUF_TYPE_VIDEO_OUTPUT); + + if (!vq) { + SDEDEV_ERR(ctx->rot_dev->dev, "fail to get vq on s:%d t:%d\n", + ctx->session_id, buf_type); + return -EINVAL; + } + + if (vb2_is_streaming(vq)) { + sde_rot_mgr_lock(rot_dev->mgr); + sde_rotator_get_config_from_ctx(ctx, &config); + ret = sde_rotator_session_config(rot_dev->mgr, ctx->private, + &config); + sde_rot_mgr_unlock(rot_dev->mgr); + if (ret < 0) { + SDEDEV_ERR(rot_dev->dev, + "fail config in stream on s:%d t:%d r:%d\n", + ctx->session_id, buf_type, ret); + return ret; + } + } + ret = v4l2_m2m_streamon(file, ctx->fh.m2m_ctx, buf_type); if (ret < 0) SDEDEV_ERR(ctx->rot_dev->dev, "fail stream on s:%d t:%d\n", diff --git a/drivers/misc/qseecom.c b/drivers/misc/qseecom.c index 6b3d84a2c145..20949487f859 100644 --- a/drivers/misc/qseecom.c +++ b/drivers/misc/qseecom.c @@ -7660,11 +7660,11 @@ static void __qseecom_deinit_clk(enum qseecom_ce_hw_instance ce) } if (qclk->ce_core_clk != NULL) { clk_put(qclk->ce_core_clk); - qclk->ce_clk = NULL; + qclk->ce_core_clk = NULL; } if (qclk->ce_bus_clk != NULL) { clk_put(qclk->ce_bus_clk); - qclk->ce_clk = NULL; + qclk->ce_bus_clk = NULL; } if (qclk->ce_core_src_clk != NULL) { clk_put(qclk->ce_core_src_clk); diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c index 9ec0928658cd..5743588aa52b 100644 --- a/drivers/mmc/card/block.c +++ b/drivers/mmc/card/block.c @@ -136,6 +136,7 @@ struct mmc_blk_data { #define MMC_BLK_DISCARD BIT(2) #define MMC_BLK_SECDISCARD BIT(3) #define MMC_BLK_FLUSH BIT(4) +#define MMC_BLK_PARTSWITCH BIT(5) /* * Only set in main mmc_blk_data associated @@ -1416,8 +1417,13 @@ static inline int mmc_blk_part_switch(struct mmc_card *card, ret = mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_PART_CONFIG, part_config, card->ext_csd.part_time); - if (ret) + + if (ret) { + pr_err("%s: mmc_blk_part_switch failure, %d -> %d\n", + mmc_hostname(card->host), main_md->part_curr, + md->part_type); return ret; + } card->ext_csd.part_config = part_config; card->part_curr = md->part_type; @@ -3933,6 +3939,7 @@ static int mmc_blk_issue_rq(struct mmc_queue *mq, struct request *req) struct mmc_host *host = card->host; unsigned long flags; unsigned int cmd_flags = req ? req->cmd_flags : 0; + int err; if (req && !mq->mqrq_prev->req) { /* claim host only for the first request */ @@ -3946,7 +3953,17 @@ static int mmc_blk_issue_rq(struct mmc_queue *mq, struct request *req) } ret = mmc_blk_part_switch(card, md); + if (ret) { + err = mmc_blk_reset(md, card->host, MMC_BLK_PARTSWITCH); + if (!err) { + pr_err("%s: mmc_blk_reset(MMC_BLK_PARTSWITCH) succeeded.\n", + mmc_hostname(host)); + mmc_blk_reset_success(md, MMC_BLK_PARTSWITCH); + } else + pr_err("%s: mmc_blk_reset(MMC_BLK_PARTSWITCH) failed.\n", + mmc_hostname(host)); + if (req) { blk_end_request_all(req, -EIO); } diff --git a/drivers/net/ppp/ppp_generic.c b/drivers/net/ppp/ppp_generic.c index e5bb870b5461..fa76ca128e1b 100644 --- a/drivers/net/ppp/ppp_generic.c +++ b/drivers/net/ppp/ppp_generic.c @@ -2390,6 +2390,8 @@ ppp_unregister_channel(struct ppp_channel *chan) spin_lock_bh(&pn->all_channels_lock); list_del(&pch->list); spin_unlock_bh(&pn->all_channels_lock); + put_net(pch->chan_net); + pch->chan_net = NULL; pch->file.dead = 1; wake_up_interruptible(&pch->file.rwait); diff --git a/drivers/pci/host/pci-msm.c b/drivers/pci/host/pci-msm.c index 9a6f1aed82e8..7c8b5e3e57a1 100644 --- a/drivers/pci/host/pci-msm.c +++ b/drivers/pci/host/pci-msm.c @@ -589,6 +589,7 @@ struct msm_pcie_dev_t { bool cfg_access; spinlock_t cfg_lock; unsigned long irqsave_flags; + struct mutex enumerate_lock; struct mutex setup_lock; struct irq_domain *irq_domain; @@ -4964,12 +4965,15 @@ int msm_pcie_enumerate(u32 rc_idx) int ret = 0, bus_ret = 0, scan_ret = 0; struct msm_pcie_dev_t *dev = &msm_pcie_dev[rc_idx]; + mutex_lock(&dev->enumerate_lock); + PCIE_DBG(dev, "Enumerate RC%d\n", rc_idx); if (!dev->drv_ready) { PCIE_DBG(dev, "RC%d has not been successfully probed yet\n", rc_idx); - return -EPROBE_DEFER; + ret = -EPROBE_DEFER; + goto out; } if (!dev->enumerated) { @@ -4996,8 +5000,7 @@ int msm_pcie_enumerate(u32 rc_idx) PCIE_ERR(dev, "PCIe: failed to get host bridge resources for RC%d: %d\n", dev->rc_idx, ret); - - return ret; + goto out; } bus = pci_create_root_bus(&dev->pdev->dev, 0, @@ -5008,8 +5011,8 @@ int msm_pcie_enumerate(u32 rc_idx) PCIE_ERR(dev, "PCIe: failed to create root bus for RC%d\n", dev->rc_idx); - - return -ENOMEM; + ret = -ENOMEM; + goto out; } scan_ret = pci_scan_child_bus(bus); @@ -5057,7 +5060,8 @@ int msm_pcie_enumerate(u32 rc_idx) PCIE_ERR(dev, "PCIe: Did not find PCI device for RC%d.\n", dev->rc_idx); - return -ENODEV; + ret = -ENODEV; + goto out; } bus_ret = bus_for_each_dev(&pci_bus_type, NULL, dev, @@ -5067,7 +5071,8 @@ int msm_pcie_enumerate(u32 rc_idx) PCIE_ERR(dev, "PCIe: Failed to set up device table for RC%d\n", dev->rc_idx); - return -ENODEV; + ret = -ENODEV; + goto out; } } else { PCIE_ERR(dev, "PCIe: failed to enable RC%d.\n", @@ -5078,6 +5083,9 @@ int msm_pcie_enumerate(u32 rc_idx) dev->rc_idx); } +out: + mutex_unlock(&dev->enumerate_lock); + return ret; } EXPORT_SYMBOL(msm_pcie_enumerate); @@ -6436,6 +6444,7 @@ int __init pcie_init(void) rc_name, i); spin_lock_init(&msm_pcie_dev[i].cfg_lock); msm_pcie_dev[i].cfg_access = true; + mutex_init(&msm_pcie_dev[i].enumerate_lock); mutex_init(&msm_pcie_dev[i].setup_lock); mutex_init(&msm_pcie_dev[i].recovery_lock); spin_lock_init(&msm_pcie_dev[i].linkdown_lock); diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa.c b/drivers/platform/msm/ipa/ipa_v2/ipa.c index 73add50cf224..d82651f7b492 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa.c @@ -450,7 +450,7 @@ static int ipa_open(struct inode *inode, struct file *filp) { struct ipa_context *ctx = NULL; - IPADBG("ENTER\n"); + IPADBG_LOW("ENTER\n"); ctx = container_of(inode->i_cdev, struct ipa_context, cdev); filp->private_data = ctx; @@ -2936,11 +2936,11 @@ static int ipa_get_clks(struct device *dev) void _ipa_enable_clks_v2_0(void) { - IPADBG("enabling gcc_ipa_clk\n"); + IPADBG_LOW("enabling gcc_ipa_clk\n"); if (ipa_clk) { clk_prepare(ipa_clk); clk_enable(ipa_clk); - IPADBG("curr_ipa_clk_rate=%d", ipa_ctx->curr_ipa_clk_rate); + IPADBG_LOW("curr_ipa_clk_rate=%d", ipa_ctx->curr_ipa_clk_rate); clk_set_rate(ipa_clk, ipa_ctx->curr_ipa_clk_rate); ipa_uc_notify_clk_state(true); } else { @@ -3072,7 +3072,7 @@ void _ipa_disable_clks_v1_1(void) void _ipa_disable_clks_v2_0(void) { - IPADBG("disabling gcc_ipa_clk\n"); + IPADBG_LOW("disabling gcc_ipa_clk\n"); ipa_suspend_apps_pipes(true); ipa_sps_irq_control_all(false); ipa_uc_notify_clk_state(false); @@ -3093,7 +3093,7 @@ void _ipa_disable_clks_v2_0(void) */ void ipa_disable_clks(void) { - IPADBG("disabling IPA clocks and bus voting\n"); + IPADBG_LOW("disabling IPA clocks and bus voting\n"); ipa_ctx->ctrl->ipa_disable_clks(); @@ -3237,7 +3237,7 @@ void ipa2_inc_client_enable_clks(struct ipa_active_client_logging_info *id) ipa_ctx->ipa_active_clients.cnt++; if (ipa_ctx->ipa_active_clients.cnt == 1) ipa_enable_clks(); - IPADBG("active clients = %d\n", ipa_ctx->ipa_active_clients.cnt); + IPADBG_LOW("active clients = %d\n", ipa_ctx->ipa_active_clients.cnt); ipa_active_clients_unlock(); } @@ -3269,7 +3269,7 @@ int ipa2_inc_client_enable_clks_no_block(struct ipa_active_client_logging_info ipa2_active_clients_log_inc(id, true); ipa_ctx->ipa_active_clients.cnt++; - IPADBG("active clients = %d\n", ipa_ctx->ipa_active_clients.cnt); + IPADBG_LOW("active clients = %d\n", ipa_ctx->ipa_active_clients.cnt); bail: ipa_active_clients_trylock_unlock(&flags); @@ -3297,7 +3297,7 @@ void ipa2_dec_client_disable_clks(struct ipa_active_client_logging_info *id) ipa_active_clients_lock(); ipa2_active_clients_log_dec(id, false); ipa_ctx->ipa_active_clients.cnt--; - IPADBG("active clients = %d\n", ipa_ctx->ipa_active_clients.cnt); + IPADBG_LOW("active clients = %d\n", ipa_ctx->ipa_active_clients.cnt); if (ipa_ctx->ipa_active_clients.cnt == 0) { if (ipa_ctx->tag_process_before_gating) { IPA_ACTIVE_CLIENTS_PREP_SPECIAL(log_info, @@ -3337,7 +3337,7 @@ void ipa_inc_acquire_wakelock(enum ipa_wakelock_ref_client ref_client) ipa_ctx->wakelock_ref_cnt.cnt |= (1 << ref_client); if (ipa_ctx->wakelock_ref_cnt.cnt) __pm_stay_awake(&ipa_ctx->w_lock); - IPADBG("active wakelock ref cnt = %d client enum %d\n", + IPADBG_LOW("active wakelock ref cnt = %d client enum %d\n", ipa_ctx->wakelock_ref_cnt.cnt, ref_client); spin_unlock_irqrestore(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); } @@ -3358,7 +3358,7 @@ void ipa_dec_release_wakelock(enum ipa_wakelock_ref_client ref_client) return; spin_lock_irqsave(&ipa_ctx->wakelock_ref_cnt.spinlock, flags); ipa_ctx->wakelock_ref_cnt.cnt &= ~(1 << ref_client); - IPADBG("active wakelock ref cnt = %d client enum %d\n", + IPADBG_LOW("active wakelock ref cnt = %d client enum %d\n", ipa_ctx->wakelock_ref_cnt.cnt, ref_client); if (ipa_ctx->wakelock_ref_cnt.cnt == 0) __pm_relax(&ipa_ctx->w_lock); @@ -3402,7 +3402,7 @@ int ipa2_set_required_perf_profile(enum ipa_voltage_level floor_voltage, enum ipa_voltage_level needed_voltage; u32 clk_rate; - IPADBG("floor_voltage=%d, bandwidth_mbps=%u", + IPADBG_LOW("floor_voltage=%d, bandwidth_mbps=%u", floor_voltage, bandwidth_mbps); if (floor_voltage < IPA_VOLTAGE_UNSPECIFIED || @@ -3412,7 +3412,7 @@ int ipa2_set_required_perf_profile(enum ipa_voltage_level floor_voltage, } if (ipa_ctx->enable_clock_scaling) { - IPADBG("Clock scaling is enabled\n"); + IPADBG_LOW("Clock scaling is enabled\n"); if (bandwidth_mbps >= ipa_ctx->ctrl->clock_scaling_bw_threshold_turbo) needed_voltage = IPA_VOLTAGE_TURBO; @@ -3422,7 +3422,7 @@ int ipa2_set_required_perf_profile(enum ipa_voltage_level floor_voltage, else needed_voltage = IPA_VOLTAGE_SVS; } else { - IPADBG("Clock scaling is disabled\n"); + IPADBG_LOW("Clock scaling is disabled\n"); needed_voltage = IPA_VOLTAGE_NOMINAL; } @@ -3444,13 +3444,13 @@ int ipa2_set_required_perf_profile(enum ipa_voltage_level floor_voltage, } if (clk_rate == ipa_ctx->curr_ipa_clk_rate) { - IPADBG("Same voltage\n"); + IPADBG_LOW("Same voltage\n"); return 0; } ipa_active_clients_lock(); ipa_ctx->curr_ipa_clk_rate = clk_rate; - IPADBG("setting clock rate to %u\n", ipa_ctx->curr_ipa_clk_rate); + IPADBG_LOW("setting clock rate to %u\n", ipa_ctx->curr_ipa_clk_rate); if (ipa_ctx->ipa_active_clients.cnt > 0) { clk_set_rate(ipa_clk, ipa_ctx->curr_ipa_clk_rate); if (ipa_ctx->ipa_hw_mode != IPA_HW_MODE_VIRTUAL) @@ -3458,10 +3458,10 @@ int ipa2_set_required_perf_profile(enum ipa_voltage_level floor_voltage, ipa_ctx->ipa_bus_hdl, ipa_get_bus_vote())) WARN_ON(1); } else { - IPADBG("clocks are gated, not setting rate\n"); + IPADBG_LOW("clocks are gated, not setting rate\n"); } ipa_active_clients_unlock(); - IPADBG("Done\n"); + IPADBG_LOW("Done\n"); return 0; } @@ -3755,6 +3755,13 @@ static int ipa_init(const struct ipa_plat_drv_res *resource_p, goto fail_mem_ctx; } + ipa_ctx->logbuf = ipc_log_context_create(IPA_IPC_LOG_PAGES, "ipa", 0); + if (ipa_ctx->logbuf == NULL) { + IPAERR("failed to get logbuf\n"); + result = -ENOMEM; + goto fail_logbuf; + } + ipa_ctx->pdev = ipa_dev; ipa_ctx->uc_pdev = ipa_dev; ipa_ctx->smmu_present = smmu_info.present; @@ -4289,6 +4296,8 @@ fail_bus_reg: fail_bind: kfree(ipa_ctx->ctrl); fail_mem_ctrl: + ipc_log_context_destroy(ipa_ctx->logbuf); +fail_logbuf: kfree(ipa_ctx); ipa_ctx = NULL; fail_mem_ctx: diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_debugfs.c b/drivers/platform/msm/ipa/ipa_v2/ipa_debugfs.c index 50c387ec785d..7ce51fccb822 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_debugfs.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_debugfs.c @@ -1804,6 +1804,44 @@ static ssize_t ipa_write_polling_iteration(struct file *file, return count; } +static ssize_t ipa_enable_ipc_low(struct file *file, + const char __user *ubuf, size_t count, loff_t *ppos) +{ + unsigned long missing; + s8 option = 0; + + if (sizeof(dbg_buff) < count + 1) + return -EFAULT; + + missing = copy_from_user(dbg_buff, ubuf, count); + if (missing) + return -EFAULT; + + dbg_buff[count] = '\0'; + if (kstrtos8(dbg_buff, 0, &option)) + return -EFAULT; + + if (option) { + if (!ipa_ctx->logbuf_low) { + ipa_ctx->logbuf_low = + ipc_log_context_create(IPA_IPC_LOG_PAGES, + "ipa_low", 0); + } + + if (ipa_ctx->logbuf_low == NULL) { + IPAERR("failed to get logbuf_low\n"); + return -EFAULT; + } + + } else { + if (ipa_ctx->logbuf_low) + ipc_log_context_destroy(ipa_ctx->logbuf_low); + ipa_ctx->logbuf_low = NULL; + } + + return count; +} + const struct file_operations ipa_gen_reg_ops = { .read = ipa_read_gen_reg, }; @@ -1882,6 +1920,10 @@ const struct file_operations ipa2_active_clients = { .write = ipa2_clear_active_clients_log, }; +const struct file_operations ipa_ipc_low_ops = { + .write = ipa_enable_ipc_low, +}; + const struct file_operations ipa_rx_poll_time_ops = { .read = ipa_read_rx_polling_timeout, .write = ipa_write_rx_polling_timeout, @@ -2097,6 +2139,13 @@ void ipa_debugfs_init(void) goto fail; } + file = debugfs_create_file("enable_low_prio_print", write_only_mode, + dent, 0, &ipa_ipc_low_ops); + if (!file) { + IPAERR("could not create enable_low_prio_print file\n"); + goto fail; + } + return; fail: diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_dma.c b/drivers/platform/msm/ipa/ipa_v2/ipa_dma.c index e08f281b1864..21be67aa2494 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_dma.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_dma.c @@ -32,16 +32,39 @@ #define IPADMA_DRV_NAME "ipa_dma" #define IPADMA_DBG(fmt, args...) \ - pr_debug(IPADMA_DRV_NAME " %s:%d " fmt, \ - __func__, __LINE__, ## args) + do { \ + pr_debug(IPADMA_DRV_NAME " %s:%d " fmt, \ + __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + IPADMA_DRV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + IPADMA_DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) + +#define IPADMA_DBG_LOW(fmt, args...) \ + do { \ + pr_debug(IPADMA_DRV_NAME " %s:%d " fmt, \ + __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + IPADMA_DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) + #define IPADMA_ERR(fmt, args...) \ - pr_err(IPADMA_DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args) + do { \ + pr_err(IPADMA_DRV_NAME " %s:%d " fmt, \ + __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + IPADMA_DRV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + IPADMA_DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) #define IPADMA_FUNC_ENTRY() \ - IPADMA_DBG("ENTRY\n") + IPADMA_DBG_LOW("ENTRY\n") #define IPADMA_FUNC_EXIT() \ - IPADMA_DBG("EXIT\n") + IPADMA_DBG_LOW("EXIT\n") + #ifdef CONFIG_DEBUG_FS #define IPADMA_MAX_MSG_LEN 1024 @@ -270,7 +293,7 @@ int ipa2_dma_enable(void) } mutex_lock(&ipa_dma_ctx->enable_lock); if (ipa_dma_ctx->is_enabled) { - IPADMA_DBG("Already enabled.\n"); + IPADMA_ERR("Already enabled.\n"); mutex_unlock(&ipa_dma_ctx->enable_lock); return -EPERM; } @@ -296,7 +319,7 @@ static bool ipa_dma_work_pending(void) IPADMA_DBG("pending uc\n"); return true; } - IPADMA_DBG("no pending work\n"); + IPADMA_DBG_LOW("no pending work\n"); return false; } @@ -324,7 +347,7 @@ int ipa2_dma_disable(void) mutex_lock(&ipa_dma_ctx->enable_lock); spin_lock_irqsave(&ipa_dma_ctx->pending_lock, flags); if (!ipa_dma_ctx->is_enabled) { - IPADMA_DBG("Already disabled.\n"); + IPADMA_ERR("Already disabled.\n"); spin_unlock_irqrestore(&ipa_dma_ctx->pending_lock, flags); mutex_unlock(&ipa_dma_ctx->enable_lock); return -EPERM; @@ -371,6 +394,8 @@ int ipa2_dma_sync_memcpy(u64 dest, u64 src, int len) IPADMA_FUNC_ENTRY(); + IPADMA_DBG_LOW("dest = 0x%llx, src = 0x%llx, len = %d\n", + dest, src, len); if (ipa_dma_ctx == NULL) { IPADMA_ERR("IPADMA isn't initialized, can't memcpy\n"); return -EPERM; @@ -398,7 +423,7 @@ int ipa2_dma_sync_memcpy(u64 dest, u64 src, int len) if (atomic_read(&ipa_dma_ctx->sync_memcpy_pending_cnt) >= IPA_DMA_MAX_PENDING_SYNC) { atomic_dec(&ipa_dma_ctx->sync_memcpy_pending_cnt); - IPADMA_DBG("Reached pending requests limit\n"); + IPADMA_ERR("Reached pending requests limit\n"); return -EFAULT; } @@ -531,6 +556,8 @@ int ipa2_dma_async_memcpy(u64 dest, u64 src, int len, unsigned long flags; IPADMA_FUNC_ENTRY(); + IPADMA_DBG_LOW("dest = 0x%llx, src = 0x%llx, len = %d\n", + dest, src, len); if (ipa_dma_ctx == NULL) { IPADMA_ERR("IPADMA isn't initialized, can't memcpy\n"); return -EPERM; @@ -562,7 +589,7 @@ int ipa2_dma_async_memcpy(u64 dest, u64 src, int len, if (atomic_read(&ipa_dma_ctx->async_memcpy_pending_cnt) >= IPA_DMA_MAX_PENDING_ASYNC) { atomic_dec(&ipa_dma_ctx->async_memcpy_pending_cnt); - IPADMA_DBG("Reached pending requests limit\n"); + IPADMA_ERR("Reached pending requests limit\n"); return -EFAULT; } @@ -692,7 +719,7 @@ void ipa2_dma_destroy(void) IPADMA_FUNC_ENTRY(); if (!ipa_dma_ctx) { - IPADMA_DBG("IPADMA isn't initialized\n"); + IPADMA_ERR("IPADMA isn't initialized\n"); return; } @@ -836,7 +863,7 @@ static ssize_t ipa_dma_debugfs_reset_statistics(struct file *file, switch (in_num) { case 0: if (ipa_dma_work_pending()) - IPADMA_DBG("Note, there are pending memcpy\n"); + IPADMA_ERR("Note, there are pending memcpy\n"); atomic_set(&ipa_dma_ctx->total_async_memcpy, 0); atomic_set(&ipa_dma_ctx->total_sync_memcpy, 0); diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_dp.c b/drivers/platform/msm/ipa/ipa_v2/ipa_dp.c index a7f1f9a040f9..7b48991cba65 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_dp.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_dp.c @@ -346,7 +346,7 @@ int ipa_send_one(struct ipa_sys_context *sys, struct ipa_desc *desc, if (desc->type == IPA_IMM_CMD_DESC) { sps_flags |= SPS_IOVEC_FLAG_IMME; len = desc->opcode; - IPADBG("sending cmd=%d pyld_len=%d sps_flags=%x\n", + IPADBG_LOW("sending cmd=%d pyld_len=%d sps_flags=%x\n", desc->opcode, desc->len, sps_flags); IPA_DUMP_BUFF(desc->pyld, dma_address, desc->len); } else { @@ -624,7 +624,7 @@ static void ipa_sps_irq_cmd_ack(void *user1, int user2) WARN_ON(1); return; } - IPADBG("got ack for cmd=%d\n", desc->opcode); + IPADBG_LOW("got ack for cmd=%d\n", desc->opcode); complete(&desc->xfer_done); } @@ -641,11 +641,12 @@ static void ipa_sps_irq_cmd_ack(void *user1, int user2) int ipa_send_cmd(u16 num_desc, struct ipa_desc *descr) { struct ipa_desc *desc; - int result = 0; + int i, result = 0; struct ipa_sys_context *sys; int ep_idx; - IPADBG("sending command\n"); + for (i = 0; i < num_desc; i++) + IPADBG_LOW("sending imm cmd %d\n", descr[i].opcode); ep_idx = ipa2_get_ep_mapping(IPA_CLIENT_APPS_CMD_PROD); if (-1 == ep_idx) { @@ -706,7 +707,7 @@ static void ipa_sps_irq_tx_notify(struct sps_event_notify *notify) struct ipa_sys_context *sys = (struct ipa_sys_context *)notify->user; int ret; - IPADBG("event %d notified\n", notify->event_id); + IPADBG_LOW("event %d notified\n", notify->event_id); switch (notify->event_id) { case SPS_EVENT_EOT: @@ -749,7 +750,7 @@ static void ipa_sps_irq_tx_no_aggr_notify(struct sps_event_notify *notify) { struct ipa_tx_pkt_wrapper *tx_pkt; - IPADBG("event %d notified\n", notify->event_id); + IPADBG_LOW("event %d notified\n", notify->event_id); switch (notify->event_id) { case SPS_EVENT_EOT: @@ -1596,7 +1597,7 @@ static void ipa_tx_comp_usr_notify_release(void *user1, int user2) struct sk_buff *skb = (struct sk_buff *)user1; int ep_idx = user2; - IPADBG("skb=%p ep=%d\n", skb, ep_idx); + IPADBG_LOW("skb=%p ep=%d\n", skb, ep_idx); IPA_STATS_INC_CNT(ipa_ctx->stats.tx_pkts_compl); @@ -1916,7 +1917,7 @@ static void ipa_replenish_wlan_rx_cache(struct ipa_sys_context *sys) int ret; u32 rx_len_cached = 0; - IPADBG("\n"); + IPADBG_LOW("\n"); spin_lock_bh(&ipa_ctx->wc_memb.wlan_spinlock); rx_len_cached = sys->len; @@ -2339,7 +2340,7 @@ static int ipa_lan_rx_pyld_hdlr(struct sk_buff *skb, } if (sys->len_partial) { - IPADBG("len_partial %d\n", sys->len_partial); + IPADBG_LOW("len_partial %d\n", sys->len_partial); buf = skb_push(skb, sys->len_partial); memcpy(buf, sys->prev_skb->data, sys->len_partial); sys->len_partial = 0; @@ -2351,7 +2352,7 @@ static int ipa_lan_rx_pyld_hdlr(struct sk_buff *skb, /* this pipe has TX comp (status only) + mux-ed LAN RX data * (status+data) */ if (sys->len_rem) { - IPADBG("rem %d skb %d pad %d\n", sys->len_rem, skb->len, + IPADBG_LOW("rem %d skb %d pad %d\n", sys->len_rem, skb->len, sys->len_pad); if (sys->len_rem <= skb->len) { if (sys->prev_skb) { @@ -2402,7 +2403,7 @@ static int ipa_lan_rx_pyld_hdlr(struct sk_buff *skb, begin: while (skb->len) { sys->drop_packet = false; - IPADBG("LEN_REM %d\n", skb->len); + IPADBG_LOW("LEN_REM %d\n", skb->len); if (skb->len < IPA_PKT_STATUS_SIZE) { WARN_ON(sys->prev_skb != NULL); @@ -2413,7 +2414,7 @@ begin: } status = (struct ipa_hw_pkt_status *)skb->data; - IPADBG("STATUS opcode=%d src=%d dst=%d len=%d\n", + IPADBG_LOW("STATUS opcode=%d src=%d dst=%d len=%d\n", status->status_opcode, status->endp_src_idx, status->endp_dest_idx, status->pkt_len); if (sys->status_stat) { @@ -2451,7 +2452,7 @@ begin: if (status->status_mask & IPA_HW_PKT_STATUS_MASK_TAG_VALID) { struct ipa_tag_completion *comp; - IPADBG("TAG packet arrived\n"); + IPADBG_LOW("TAG packet arrived\n"); if (status->tag_f_2 == IPA_COOKIE) { skb_pull(skb, IPA_PKT_STATUS_SIZE); if (skb->len < sizeof(comp)) { @@ -2491,7 +2492,7 @@ begin: if (skb->len == IPA_PKT_STATUS_SIZE && !status->exception) { WARN_ON(sys->prev_skb != NULL); - IPADBG("Ins header in next buffer\n"); + IPADBG_LOW("Ins header in next buffer\n"); sys->prev_skb = skb_copy(skb, GFP_KERNEL); sys->len_partial = skb->len; return rc; @@ -2502,12 +2503,13 @@ begin: len = status->pkt_len + pad_len_byte + IPA_SIZE_DL_CSUM_META_TRAILER; - IPADBG("pad %d pkt_len %d len %d\n", pad_len_byte, + IPADBG_LOW("pad %d pkt_len %d len %d\n", pad_len_byte, status->pkt_len, len); if (status->exception == IPA_HW_PKT_STATUS_EXCEPTION_DEAGGR) { - IPADBG("Dropping packet on DeAggr Exception\n"); + IPADBG_LOW("Dropping packet"); + IPADBG_LOW(" on DeAggr Exception\n"); sys->drop_packet = true; } @@ -2516,7 +2518,7 @@ begin: skb2 = ipa_skb_copy_for_client(skb, skb2_len); if (likely(skb2)) { if (skb->len < len + IPA_PKT_STATUS_SIZE) { - IPADBG("SPL skb len %d len %d\n", + IPADBG_LOW("SPL skb len %d len %d\n", skb->len, len); sys->prev_skb = skb2; sys->len_rem = len - skb->len + @@ -2526,7 +2528,7 @@ begin: } else { skb_trim(skb2, status->pkt_len + IPA_PKT_STATUS_SIZE); - IPADBG("rx avail for %d\n", + IPADBG_LOW("rx avail for %d\n", status->endp_dest_idx); if (sys->drop_packet) { dev_kfree_skb_any(skb2); @@ -2570,11 +2572,12 @@ begin: } /* TX comp */ ipa_wq_write_done_status(src_pipe); - IPADBG("tx comp imp for %d\n", src_pipe); + IPADBG_LOW("tx comp imp for %d\n", src_pipe); } else { /* TX comp */ ipa_wq_write_done_status(status->endp_src_idx); - IPADBG("tx comp exp for %d\n", status->endp_src_idx); + IPADBG_LOW + ("tx comp exp for %d\n", status->endp_src_idx); skb_pull(skb, IPA_PKT_STATUS_SIZE); IPA_STATS_INC_CNT(ipa_ctx->stats.stat_compl); IPA_STATS_DEC_CNT( @@ -2610,13 +2613,13 @@ static void wan_rx_handle_splt_pyld(struct sk_buff *skb, { struct sk_buff *skb2; - IPADBG("rem %d skb %d\n", sys->len_rem, skb->len); + IPADBG_LOW("rem %d skb %d\n", sys->len_rem, skb->len); if (sys->len_rem <= skb->len) { if (sys->prev_skb) { skb2 = join_prev_skb(sys->prev_skb, skb, sys->len_rem); if (likely(skb2)) { - IPADBG( + IPADBG_LOW( "removing Status element from skb and sending to WAN client"); skb_pull(skb2, IPA_PKT_STATUS_SIZE); skb2->truesize = skb2->len + @@ -2679,14 +2682,14 @@ static int ipa_wan_rx_pyld_hdlr(struct sk_buff *skb, while (skb->len) { - IPADBG("LEN_REM %d\n", skb->len); + IPADBG_LOW("LEN_REM %d\n", skb->len); if (skb->len < IPA_PKT_STATUS_SIZE) { IPAERR("status straddles buffer\n"); WARN_ON(1); goto bail; } status = (struct ipa_hw_pkt_status *)skb->data; - IPADBG("STATUS opcode=%d src=%d dst=%d len=%d\n", + IPADBG_LOW("STATUS opcode=%d src=%d dst=%d len=%d\n", status->status_opcode, status->endp_src_idx, status->endp_dest_idx, status->pkt_len); @@ -2717,7 +2720,7 @@ static int ipa_wan_rx_pyld_hdlr(struct sk_buff *skb, goto bail; } if (status->pkt_len == 0) { - IPADBG("Skip aggr close status\n"); + IPADBG_LOW("Skip aggr close status\n"); skb_pull(skb, IPA_PKT_STATUS_SIZE); IPA_STATS_DEC_CNT(ipa_ctx->stats.rx_pkts); IPA_STATS_INC_CNT(ipa_ctx->stats.wan_aggr_close); @@ -2744,11 +2747,11 @@ static int ipa_wan_rx_pyld_hdlr(struct sk_buff *skb, /*QMAP is BE: convert the pkt_len field from BE to LE*/ pkt_len_with_pad = ntohs((qmap_hdr>>16) & 0xffff); - IPADBG("pkt_len with pad %d\n", pkt_len_with_pad); + IPADBG_LOW("pkt_len with pad %d\n", pkt_len_with_pad); /*get the CHECKSUM_PROCESS bit*/ checksum_trailer_exists = status->status_mask & IPA_HW_PKT_STATUS_MASK_CKSUM_PROCESS; - IPADBG("checksum_trailer_exists %d\n", + IPADBG_LOW("checksum_trailer_exists %d\n", checksum_trailer_exists); frame_len = IPA_PKT_STATUS_SIZE + @@ -2756,7 +2759,7 @@ static int ipa_wan_rx_pyld_hdlr(struct sk_buff *skb, pkt_len_with_pad; if (checksum_trailer_exists) frame_len += IPA_DL_CHECKSUM_LENGTH; - IPADBG("frame_len %d\n", frame_len); + IPADBG_LOW("frame_len %d\n", frame_len); skb2 = skb_clone(skb, GFP_KERNEL); if (likely(skb2)) { @@ -2765,16 +2768,16 @@ static int ipa_wan_rx_pyld_hdlr(struct sk_buff *skb, * payload split across 2 buff */ if (skb->len < frame_len) { - IPADBG("SPL skb len %d len %d\n", + IPADBG_LOW("SPL skb len %d len %d\n", skb->len, frame_len); sys->prev_skb = skb2; sys->len_rem = frame_len - skb->len; skb_pull(skb, skb->len); } else { skb_trim(skb2, frame_len); - IPADBG("rx avail for %d\n", + IPADBG_LOW("rx avail for %d\n", status->endp_dest_idx); - IPADBG( + IPADBG_LOW( "removing Status element from skb and sending to WAN client"); skb_pull(skb2, IPA_PKT_STATUS_SIZE); skb2->truesize = skb2->len + @@ -2914,7 +2917,7 @@ void ipa_lan_rx_cb(void *priv, enum ipa_dp_evt_type evt, unsigned long data) ------------------------------------------ */ *(u16 *)rx_skb->cb = ((metadata >> 16) & 0xFFFF); - IPADBG("meta_data: 0x%x cb: 0x%x\n", + IPADBG_LOW("meta_data: 0x%x cb: 0x%x\n", metadata, *(u32 *)rx_skb->cb); ep->client_notify(ep->priv, IPA_RECEIVE, (unsigned long)(rx_skb)); @@ -3017,7 +3020,7 @@ static void ipa_wlan_wq_rx_common(struct ipa_sys_context *sys, u32 size) static void ipa_dma_memcpy_notify(struct ipa_sys_context *sys, struct sps_iovec *iovec) { - IPADBG("ENTER.\n"); + IPADBG_LOW("ENTER.\n"); if (unlikely(list_empty(&sys->head_desc_list))) { IPAERR("descriptor list is empty!\n"); WARN_ON(1); @@ -3064,7 +3067,8 @@ void ipa_sps_irq_rx_no_aggr_notify(struct sps_event_notify *notify) if (IPA_CLIENT_IS_APPS_CONS(rx_pkt->sys->ep->client)) atomic_set(&ipa_ctx->sps_pm.eot_activity, 1); rx_pkt->len = notify->data.transfer.iovec.size; - IPADBG("event %d notified sys=%p len=%u\n", notify->event_id, + IPADBG_LOW + ("event %d notified sys=%p len=%u\n", notify->event_id, notify->user, rx_pkt->len); queue_work(rx_pkt->sys->wq, &rx_pkt->work); break; @@ -3370,15 +3374,15 @@ static void ipa_tx_client_rx_notify_release(void *user1, int user2) struct ipa_tx_data_desc *dd = (struct ipa_tx_data_desc *)user1; int ep_idx = user2; - IPADBG("Received data desc anchor:%p\n", dd); + IPADBG_LOW("Received data desc anchor:%p\n", dd); atomic_inc(&ipa_ctx->ep[ep_idx].avail_fifo_desc); ipa_ctx->ep[ep_idx].wstats.rx_pkts_status_rcvd++; /* wlan host driver waits till tx complete before unload */ - IPADBG("ep=%d fifo_desc_free_count=%d\n", + IPADBG_LOW("ep=%d fifo_desc_free_count=%d\n", ep_idx, atomic_read(&ipa_ctx->ep[ep_idx].avail_fifo_desc)); - IPADBG("calling client notify callback with priv:%p\n", + IPADBG_LOW("calling client notify callback with priv:%p\n", ipa_ctx->ep[ep_idx].priv); if (ipa_ctx->ep[ep_idx].client_notify) { @@ -3442,7 +3446,7 @@ int ipa2_tx_dp_mul(enum ipa_client_type src, return -EINVAL; } - IPADBG("Received data desc anchor:%p\n", data_desc); + IPADBG_LOW("Received data desc anchor:%p\n", data_desc); spin_lock_bh(&ipa_ctx->wc_memb.ipa_tx_mul_spinlock); @@ -3451,7 +3455,7 @@ int ipa2_tx_dp_mul(enum ipa_client_type src, IPAERR("dest EP does not exist.\n"); goto fail_send; } - IPADBG("ep idx:%d\n", ep_idx); + IPADBG_LOW("ep idx:%d\n", ep_idx); sys = ipa_ctx->ep[ep_idx].sys; if (unlikely(ipa_ctx->ep[ep_idx].valid == 0)) { @@ -3465,7 +3469,7 @@ int ipa2_tx_dp_mul(enum ipa_client_type src, list_for_each_entry(entry, &data_desc->link, link) { num_desc++; } - IPADBG("Number of Data Descriptors:%d", num_desc); + IPADBG_LOW("Number of Data Descriptors:%d", num_desc); if (atomic_read(&sys->ep->avail_fifo_desc) < num_desc) { IPAERR("Insufficient data descriptors available\n"); @@ -3475,7 +3479,7 @@ int ipa2_tx_dp_mul(enum ipa_client_type src, /* Assign callback only for last data descriptor */ cnt = 0; list_for_each_entry(entry, &data_desc->link, link) { - IPADBG("Parsing data desc :%d\n", cnt); + IPADBG_LOW("Parsing data desc :%d\n", cnt); cnt++; ((u8 *)entry->pyld_buffer)[IPA_WLAN_HDR_QMAP_ID_OFFSET] = (u8)sys->ep->cfg.meta.qmap_id; @@ -3484,18 +3488,18 @@ int ipa2_tx_dp_mul(enum ipa_client_type src, desc.type = IPA_DATA_DESC_SKB; desc.user1 = data_desc; desc.user2 = ep_idx; - IPADBG("priv:%p pyld_buf:0x%p pyld_len:%d\n", + IPADBG_LOW("priv:%p pyld_buf:0x%p pyld_len:%d\n", entry->priv, desc.pyld, desc.len); /* In case of last descriptor populate callback */ if (cnt == num_desc) { - IPADBG("data desc:%p\n", data_desc); + IPADBG_LOW("data desc:%p\n", data_desc); desc.callback = ipa_tx_client_rx_notify_release; } else { desc.callback = ipa_tx_client_rx_pkt_status; } - IPADBG("calling ipa_send_one()\n"); + IPADBG_LOW("calling ipa_send_one()\n"); if (ipa_send_one(sys, &desc, true)) { IPAERR("fail to send skb\n"); sys->ep->wstats.rx_pkt_leak += (cnt-1); @@ -3507,7 +3511,7 @@ int ipa2_tx_dp_mul(enum ipa_client_type src, atomic_dec(&sys->ep->avail_fifo_desc); sys->ep->wstats.rx_pkts_rcvd++; - IPADBG("ep=%d fifo desc=%d\n", + IPADBG_LOW("ep=%d fifo desc=%d\n", ep_idx, atomic_read(&sys->ep->avail_fifo_desc)); } diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_flt.c b/drivers/platform/msm/ipa/ipa_v2/ipa_flt.c index d6e563b935b6..7ca2314d5839 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_flt.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_flt.c @@ -209,7 +209,7 @@ static int ipa_generate_flt_hw_rule(enum ipa_ip_type ip, } } - IPADBG("en_rule 0x%x, action=%d, rt_idx=%d, uc=%d, retain_hdr=%d\n", + IPADBG_LOW("en_rule 0x%x, action=%d, rt_idx=%d, uc=%d, retain_hdr=%d\n", en_rule, hdr->u.hdr.action, hdr->u.hdr.rt_tbl_idx, @@ -601,7 +601,7 @@ static void __ipa_reap_sys_flt_tbls(enum ipa_ip_type ip) tbl = &ipa_ctx->glob_flt_tbl[ip]; if (tbl->prev_mem.phys_base) { - IPADBG("reaping glob flt tbl (prev) ip=%d\n", ip); + IPADBG_LOW("reaping glob flt tbl (prev) ip=%d\n", ip); dma_free_coherent(ipa_ctx->pdev, tbl->prev_mem.size, tbl->prev_mem.base, tbl->prev_mem.phys_base); memset(&tbl->prev_mem, 0, sizeof(tbl->prev_mem)); @@ -609,7 +609,7 @@ static void __ipa_reap_sys_flt_tbls(enum ipa_ip_type ip) if (list_empty(&tbl->head_flt_rule_list)) { if (tbl->curr_mem.phys_base) { - IPADBG("reaping glob flt tbl (curr) ip=%d\n", ip); + IPADBG_LOW("reaping glob flt tbl (curr) ip=%d\n", ip); dma_free_coherent(ipa_ctx->pdev, tbl->curr_mem.size, tbl->curr_mem.base, tbl->curr_mem.phys_base); @@ -620,7 +620,8 @@ static void __ipa_reap_sys_flt_tbls(enum ipa_ip_type ip) for (i = 0; i < ipa_ctx->ipa_num_pipes; i++) { tbl = &ipa_ctx->flt_tbl[i][ip]; if (tbl->prev_mem.phys_base) { - IPADBG("reaping flt tbl (prev) pipe=%d ip=%d\n", i, ip); + IPADBG_LOW("reaping flt tbl"); + IPADBG_LOW("(prev) pipe=%d ip=%d\n", i, ip); dma_free_coherent(ipa_ctx->pdev, tbl->prev_mem.size, tbl->prev_mem.base, tbl->prev_mem.phys_base); @@ -629,7 +630,8 @@ static void __ipa_reap_sys_flt_tbls(enum ipa_ip_type ip) if (list_empty(&tbl->head_flt_rule_list)) { if (tbl->curr_mem.phys_base) { - IPADBG("reaping flt tbl (curr) pipe=%d ip=%d\n", + IPADBG_LOW("reaping flt tbl"); + IPADBG_LOW("(curr) pipe=%d ip=%d\n", i, ip); dma_free_coherent(ipa_ctx->pdev, tbl->curr_mem.size, @@ -897,7 +899,7 @@ int __ipa_commit_flt_v2(enum ipa_ip_type ip) for (i = 0; i < 6; i++) { if (ipa_ctx->skip_ep_cfg_shadow[i]) { - IPADBG("skip %d\n", i); + IPADBG_LOW("skip %d\n", i); continue; } @@ -906,7 +908,7 @@ int __ipa_commit_flt_v2(enum ipa_ip_type ip) ipa2_get_ep_mapping(IPA_CLIENT_APPS_CMD_PROD) == i || (ipa2_get_ep_mapping(IPA_CLIENT_APPS_LAN_WAN_PROD) == i && ipa_ctx->modem_cfg_emb_pipe_flt)) { - IPADBG("skip %d\n", i); + IPADBG_LOW("skip %d\n", i); continue; } @@ -932,12 +934,12 @@ int __ipa_commit_flt_v2(enum ipa_ip_type ip) for (i = 11; i < ipa_ctx->ipa_num_pipes; i++) { if (ipa_ctx->skip_ep_cfg_shadow[i]) { - IPADBG("skip %d\n", i); + IPADBG_LOW("skip %d\n", i); continue; } if (ipa2_get_ep_mapping(IPA_CLIENT_APPS_LAN_WAN_PROD) == i && ipa_ctx->modem_cfg_emb_pipe_flt) { - IPADBG("skip %d\n", i); + IPADBG_LOW("skip %d\n", i); continue; } if (ip == IPA_IP_v4) { @@ -1066,7 +1068,7 @@ static int __ipa_add_flt_rule(struct ipa_flt_tbl *tbl, enum ipa_ip_type ip, } *rule_hdl = id; entry->id = id; - IPADBG("add flt rule rule_cnt=%d\n", tbl->rule_cnt); + IPADBG_LOW("add flt rule rule_cnt=%d\n", tbl->rule_cnt); return 0; @@ -1095,7 +1097,7 @@ static int __ipa_del_flt_rule(u32 rule_hdl) entry->tbl->rule_cnt--; if (entry->rt_tbl) entry->rt_tbl->ref_cnt--; - IPADBG("del flt rule rule_cnt=%d\n", entry->tbl->rule_cnt); + IPADBG_LOW("del flt rule rule_cnt=%d\n", entry->tbl->rule_cnt); entry->cookie = 0; kmem_cache_free(ipa_ctx->flt_rule_cache, entry); @@ -1176,7 +1178,7 @@ static int __ipa_add_global_flt_rule(enum ipa_ip_type ip, } tbl = &ipa_ctx->glob_flt_tbl[ip]; - IPADBG("add global flt rule ip=%d\n", ip); + IPADBG_LOW("add global flt rule ip=%d\n", ip); return __ipa_add_flt_rule(tbl, ip, rule, add_rear, rule_hdl); } @@ -1203,7 +1205,7 @@ static int __ipa_add_ep_flt_rule(enum ipa_ip_type ip, enum ipa_client_type ep, IPADBG("ep not connected ep_idx=%d\n", ipa_ep_idx); tbl = &ipa_ctx->flt_tbl[ipa_ep_idx][ip]; - IPADBG("add ep flt rule ip=%d ep=%d\n", ip, ep); + IPADBG_LOW("add ep flt rule ip=%d ep=%d\n", ip, ep); return __ipa_add_flt_rule(tbl, ip, rule, add_rear, rule_hdl); } diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_hdr.c b/drivers/platform/msm/ipa/ipa_v2/ipa_hdr.c index 62e026262663..40d42e1775a9 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_hdr.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_hdr.c @@ -43,7 +43,7 @@ static int ipa_generate_hdr_hw_tbl(struct ipa_mem_buffer *mem) IPAERR("hdr tbl empty\n"); return -EPERM; } - IPADBG("tbl_sz=%d\n", ipa_ctx->hdr_tbl.end); + IPADBG_LOW("tbl_sz=%d\n", ipa_ctx->hdr_tbl.end); mem->base = dma_alloc_coherent(ipa_ctx->pdev, mem->size, &mem->phys_base, GFP_KERNEL); @@ -57,7 +57,7 @@ static int ipa_generate_hdr_hw_tbl(struct ipa_mem_buffer *mem) link) { if (entry->is_hdr_proc_ctx) continue; - IPADBG("hdr of len %d ofst=%d\n", entry->hdr_len, + IPADBG_LOW("hdr of len %d ofst=%d\n", entry->hdr_len, entry->offset_entry->offset); memcpy(mem->base + entry->offset_entry->offset, entry->hdr, entry->hdr_len); @@ -74,7 +74,7 @@ static void ipa_hdr_proc_ctx_to_hw_format(struct ipa_mem_buffer *mem, list_for_each_entry(entry, &ipa_ctx->hdr_proc_ctx_tbl.head_proc_ctx_entry_list, link) { - IPADBG("processing type %d ofst=%d\n", + IPADBG_LOW("processing type %d ofst=%d\n", entry->type, entry->offset_entry->offset); if (entry->type == IPA_HDR_PROC_NONE) { struct ipa_hdr_proc_ctx_add_hdr_seq *ctx; @@ -88,7 +88,7 @@ static void ipa_hdr_proc_ctx_to_hw_format(struct ipa_mem_buffer *mem, entry->hdr->phys_base : hdr_base_addr + entry->hdr->offset_entry->offset; - IPADBG("header address 0x%x\n", + IPADBG_LOW("header address 0x%x\n", ctx->hdr_add.hdr_addr); ctx->end.type = IPA_PROC_CTX_TLV_TYPE_END; ctx->end.length = 0; @@ -105,7 +105,7 @@ static void ipa_hdr_proc_ctx_to_hw_format(struct ipa_mem_buffer *mem, entry->hdr->phys_base : hdr_base_addr + entry->hdr->offset_entry->offset; - IPADBG("header address 0x%x\n", + IPADBG_LOW("header address 0x%x\n", ctx->hdr_add.hdr_addr); ctx->cmd.type = IPA_PROC_CTX_TLV_TYPE_PROC_CMD; ctx->cmd.length = 0; @@ -117,7 +117,7 @@ static void ipa_hdr_proc_ctx_to_hw_format(struct ipa_mem_buffer *mem, ctx->cmd.value = IPA_HDR_UCP_802_3_TO_ETHII; else if (entry->type == IPA_HDR_PROC_802_3_TO_802_3) ctx->cmd.value = IPA_HDR_UCP_802_3_TO_802_3; - IPADBG("command id %d\n", ctx->cmd.value); + IPADBG_LOW("command id %d\n", ctx->cmd.value); ctx->end.type = IPA_PROC_CTX_TLV_TYPE_END; ctx->end.length = 0; ctx->end.value = 0; @@ -144,7 +144,7 @@ static int ipa_generate_hdr_proc_ctx_hw_tbl(u32 hdr_sys_addr, /* make sure table is aligned */ mem->size += IPA_HDR_PROC_CTX_TABLE_ALIGNMENT_BYTE; - IPADBG("tbl_sz=%d\n", ipa_ctx->hdr_proc_ctx_tbl.end); + IPADBG_LOW("tbl_sz=%d\n", ipa_ctx->hdr_proc_ctx_tbl.end); mem->base = dma_alloc_coherent(ipa_ctx->pdev, mem->size, &mem->phys_base, GFP_KERNEL); @@ -487,7 +487,7 @@ static int __ipa_add_hdr_proc_ctx(struct ipa_hdr_proc_ctx_add *proc_ctx, int needed_len; int mem_size; - IPADBG("processing type %d hdr_hdl %d\n", + IPADBG_LOW("processing type %d hdr_hdl %d\n", proc_ctx->type, proc_ctx->hdr_hdl); if (!HDR_PROC_TYPE_IS_VALID(proc_ctx->type)) { @@ -566,7 +566,7 @@ static int __ipa_add_hdr_proc_ctx(struct ipa_hdr_proc_ctx_add *proc_ctx, entry->offset_entry = offset; list_add(&entry->link, &htbl->head_proc_ctx_entry_list); htbl->proc_ctx_cnt++; - IPADBG("add proc ctx of sz=%d cnt=%d ofst=%d\n", needed_len, + IPADBG_LOW("add proc ctx of sz=%d cnt=%d ofst=%d\n", needed_len, htbl->proc_ctx_cnt, offset->offset); id = ipa_id_alloc(entry); @@ -692,12 +692,12 @@ static int __ipa_add_hdr(struct ipa_hdr_add *hdr) list_add(&entry->link, &htbl->head_hdr_entry_list); htbl->hdr_cnt++; if (entry->is_hdr_proc_ctx) - IPADBG("add hdr of sz=%d hdr_cnt=%d phys_base=%pa\n", + IPADBG_LOW("add hdr of sz=%d hdr_cnt=%d phys_base=%pa\n", hdr->hdr_len, htbl->hdr_cnt, &entry->phys_base); else - IPADBG("add hdr of sz=%d hdr_cnt=%d ofst=%d\n", + IPADBG_LOW("add hdr of sz=%d hdr_cnt=%d ofst=%d\n", hdr->hdr_len, htbl->hdr_cnt, entry->offset_entry->offset); diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_i.h b/drivers/platform/msm/ipa/ipa_v2/ipa_i.h index fd61435db5e2..6515d29e497a 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_i.h +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_i.h @@ -54,10 +54,37 @@ #define IPA_MAX_STATUS_STAT_NUM 30 +#define IPA_IPC_LOG_PAGES 50 + #define IPADBG(fmt, args...) \ - pr_debug(DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args) + do { \ + pr_debug(DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args);\ + if (ipa_ctx) { \ + IPA_IPC_LOGGING(ipa_ctx->logbuf, \ + DRV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_ctx->logbuf_low, \ + DRV_NAME " %s:%d " fmt, ## args); \ + } \ + } while (0) + +#define IPADBG_LOW(fmt, args...) \ + do { \ + pr_debug(DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args);\ + if (ipa_ctx) \ + IPA_IPC_LOGGING(ipa_ctx->logbuf_low, \ + DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) + #define IPAERR(fmt, args...) \ - pr_err(DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args) + do { \ + pr_err(DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args);\ + if (ipa_ctx) { \ + IPA_IPC_LOGGING(ipa_ctx->logbuf, \ + DRV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_ctx->logbuf_low, \ + DRV_NAME " %s:%d " fmt, ## args); \ + } \ + } while (0) #define WLAN_AMPDU_TX_EP 15 #define WLAN_PROD_TX_EP 19 @@ -1003,6 +1030,8 @@ struct ipacm_client_info { * @use_ipa_teth_bridge: use tethering bridge driver * @ipa_bam_remote_mode: ipa bam is in remote mode * @modem_cfg_emb_pipe_flt: modem configure embedded pipe filtering rules + * @logbuf: ipc log buffer for high priority messages + * @logbuf_low: ipc log buffer for low priority messages * @ipa_wdi2: using wdi-2.0 * @ipa_bus_hdl: msm driver handle for the data path bus * @ctrl: holds the core specific operations based on @@ -1095,6 +1124,8 @@ struct ipa_context { /* featurize if memory footprint becomes a concern */ struct ipa_stats stats; void *smem_pipe_mem; + void *logbuf; + void *logbuf_low; u32 ipa_bus_hdl; struct ipa_controller *ctrl; struct idr ipa_idr; diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_interrupts.c b/drivers/platform/msm/ipa/ipa_v2/ipa_interrupts.c index 17f577ab6c4c..c17dee939f1c 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_interrupts.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_interrupts.c @@ -103,11 +103,12 @@ static int handle_interrupt(int irq_num, bool isr_context) switch (interrupt_info.interrupt) { case IPA_TX_SUSPEND_IRQ: + IPADBG_LOW("processing TX_SUSPEND interrupt work-around\n"); suspend_data = ipa_read_reg(ipa_ctx->mmio, IPA_IRQ_SUSPEND_INFO_EE_n_ADDR(ipa_ee)); if (!is_valid_ep(suspend_data)) return 0; - + IPADBG_LOW("get interrupt %d\n", suspend_data); suspend_interrupt_data = kzalloc(sizeof(*suspend_interrupt_data), GFP_ATOMIC); if (!suspend_interrupt_data) { @@ -167,9 +168,11 @@ static void ipa_process_interrupts(bool isr_context) u32 i = 0; u32 en; bool uc_irq; - en = ipa_read_reg(ipa_ctx->mmio, IPA_IRQ_EN_EE_n_ADDR(ipa_ee)); reg = ipa_read_reg(ipa_ctx->mmio, IPA_IRQ_STTS_EE_n_ADDR(ipa_ee)); + IPADBG_LOW( + "ISR enter\n isr_ctx = %d EN reg = 0x%x STTS reg = 0x%x\n", + isr_context, en, reg); while (en & reg) { bmsk = 1; for (i = 0; i < IPA_IRQ_NUM_MAX; i++) { @@ -206,21 +209,22 @@ static void ipa_process_interrupts(bool isr_context) reg = ipa_read_reg(ipa_ctx->mmio, IPA_IRQ_STTS_EE_n_ADDR(ipa_ee)); } + IPADBG_LOW("Exit\n"); } static void ipa_interrupt_defer(struct work_struct *work) { - IPADBG("processing interrupts in wq\n"); + IPADBG_LOW("processing interrupts in wq\n"); IPA_ACTIVE_CLIENTS_INC_SIMPLE(); ipa_process_interrupts(false); IPA_ACTIVE_CLIENTS_DEC_SIMPLE(); - IPADBG("Done\n"); + IPADBG_LOW("Done\n"); } static irqreturn_t ipa_isr(int irq, void *ctxt) { unsigned long flags; - + IPADBG_LOW("Enter\n"); /* defer interrupt handling in case IPA is not clocked on */ if (ipa_active_clients_trylock(&flags) == 0) { IPADBG("defer interrupt processing\n"); @@ -235,7 +239,7 @@ static irqreturn_t ipa_isr(int irq, void *ctxt) } ipa_process_interrupts(true); - + IPADBG_LOW("Exit\n"); bail: ipa_active_clients_trylock_unlock(&flags); return IRQ_HANDLED; @@ -260,7 +264,7 @@ int ipa2_add_interrupt_handler(enum ipa_irq_type interrupt, u32 bmsk; int irq_num; - IPADBG("in ipa2_add_interrupt_handler\n"); + IPADBG_LOW("in ipa2_add_interrupt_handler\n"); if (interrupt < IPA_BAD_SNOC_ACCESS_IRQ || interrupt >= IPA_IRQ_MAX) { IPAERR("invalid interrupt number %d\n", interrupt); @@ -284,7 +288,7 @@ int ipa2_add_interrupt_handler(enum ipa_irq_type interrupt, bmsk = 1 << irq_num; val |= bmsk; ipa_write_reg(ipa_ctx->mmio, IPA_IRQ_EN_EE_n_ADDR(ipa_ee), val); - IPADBG("wrote IPA_IRQ_EN_EE_n_ADDR register. reg = %d\n", val); + IPADBG_LOW("wrote IPA_IRQ_EN_EE_n_ADDR register. reg = %d\n", val); return 0; } diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_intf.c b/drivers/platform/msm/ipa/ipa_v2/ipa_intf.c index f5afb4b0141c..dfc3e06f452b 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_intf.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_intf.c @@ -532,9 +532,8 @@ ssize_t ipa_read(struct file *filp, char __user *buf, size_t count, list_del(&msg->link); } - IPADBG("msg=%p\n", msg); - if (msg) { + IPADBG("msg=%pK\n", msg); locked = 0; mutex_unlock(&ipa_ctx->msg_lock); if (copy_to_user(buf, &msg->meta, @@ -558,6 +557,7 @@ ssize_t ipa_read(struct file *filp, char __user *buf, size_t count, IPA_STATS_INC_CNT( ipa_ctx->stats.msg_r[msg->meta.msg_type]); kfree(msg); + msg = NULL; } ret = -EAGAIN; diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_mhi.c b/drivers/platform/msm/ipa/ipa_v2/ipa_mhi.c index e8f25c9c23d3..0ab4a6882a63 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_mhi.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_mhi.c @@ -20,16 +20,40 @@ #include "ipa_i.h" #include "ipa_qmi_service.h" -#define IPA_MHI_DRV_NAME +#define IPA_MHI_DRV_NAME "ipa_mhi" #define IPA_MHI_DBG(fmt, args...) \ - pr_debug(IPA_MHI_DRV_NAME " %s:%d " fmt, \ - __func__, __LINE__, ## args) + do { \ + pr_debug(IPA_MHI_DRV_NAME " %s:%d " fmt, \ + __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + IPA_MHI_DRV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + IPA_MHI_DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) + +#define IPA_MHI_DBG_LOW(fmt, args...) \ + do { \ + pr_debug(IPA_MHI_DRV_NAME " %s:%d " fmt, \ + __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + IPA_MHI_DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) + #define IPA_MHI_ERR(fmt, args...) \ - pr_err(IPA_MHI_DRV_NAME " %s:%d " fmt, __func__, __LINE__, ## args) + do { \ + pr_err(IPA_MHI_DRV_NAME " %s:%d " fmt, \ + __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + IPA_MHI_DRV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + IPA_MHI_DRV_NAME " %s:%d " fmt, ## args); \ + } while (0) + #define IPA_MHI_FUNC_ENTRY() \ - IPA_MHI_DBG("ENTRY\n") + IPA_MHI_DBG_LOW("ENTRY\n") #define IPA_MHI_FUNC_EXIT() \ - IPA_MHI_DBG("EXIT\n") + IPA_MHI_DBG_LOW("EXIT\n") + bool ipa2_mhi_sps_channel_empty(enum ipa_client_type client) { diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.c b/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.c index 3f20941155a5..0f5d7b7719b5 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.c @@ -310,7 +310,7 @@ static void ipa_a5_svc_recv_msg(struct work_struct *work) int rc; do { - IPAWANDBG("Notified about a Receive Event"); + IPAWANDBG_LOW("Notified about a Receive Event"); rc = qmi_recv_msg(ipa_svc_handle); } while (rc == 0); if (rc != -ENOMSG) @@ -384,7 +384,7 @@ static int ipa_check_qmi_response(int rc, req_id, result, error); return result; } - IPAWANDBG("Received %s successfully\n", resp_type); + IPAWANDBG_LOW("Received %s successfully\n", resp_type); return 0; } @@ -711,7 +711,7 @@ static void ipa_q6_clnt_recv_msg(struct work_struct *work) int rc; do { - IPAWANDBG("Notified about a Receive Event"); + IPAWANDBG_LOW("Notified about a Receive Event"); rc = qmi_recv_msg(ipa_q6_clnt); } while (rc == 0); if (rc != -ENOMSG) @@ -723,7 +723,7 @@ static void ipa_q6_clnt_notify(struct qmi_handle *handle, { switch (event) { case QMI_RECV_MSG: - IPAWANDBG("client qmi recv message called"); + IPAWANDBG_LOW("client qmi recv message called"); if (!atomic_read(&workqueues_stopped)) queue_delayed_work(ipa_clnt_resp_workqueue, &work_recv_msg_client, 0); @@ -1094,7 +1094,7 @@ int ipa_qmi_get_data_stats(struct ipa_get_data_stats_req_msg_v01 *req, resp_desc.msg_id = QMI_IPA_GET_DATA_STATS_RESP_V01; resp_desc.ei_array = ipa_get_data_stats_resp_msg_data_v01_ei; - IPAWANDBG("Sending QMI_IPA_GET_DATA_STATS_REQ_V01\n"); + IPAWANDBG_LOW("Sending QMI_IPA_GET_DATA_STATS_REQ_V01\n"); if (unlikely(!ipa_q6_clnt)) return -ETIMEDOUT; rc = qmi_send_req_wait(ipa_q6_clnt, &req_desc, req, @@ -1103,7 +1103,7 @@ int ipa_qmi_get_data_stats(struct ipa_get_data_stats_req_msg_v01 *req, sizeof(struct ipa_get_data_stats_resp_msg_v01), QMI_SEND_STATS_REQ_TIMEOUT_MS); - IPAWANDBG("QMI_IPA_GET_DATA_STATS_RESP_V01 received\n"); + IPAWANDBG_LOW("QMI_IPA_GET_DATA_STATS_RESP_V01 received\n"); return ipa_check_qmi_response(rc, QMI_IPA_GET_DATA_STATS_REQ_V01, resp->resp.result, @@ -1124,7 +1124,7 @@ int ipa_qmi_get_network_stats(struct ipa_get_apn_data_stats_req_msg_v01 *req, resp_desc.msg_id = QMI_IPA_GET_APN_DATA_STATS_RESP_V01; resp_desc.ei_array = ipa_get_apn_data_stats_resp_msg_data_v01_ei; - IPAWANDBG("Sending QMI_IPA_GET_APN_DATA_STATS_REQ_V01\n"); + IPAWANDBG_LOW("Sending QMI_IPA_GET_APN_DATA_STATS_REQ_V01\n"); if (unlikely(!ipa_q6_clnt)) return -ETIMEDOUT; rc = qmi_send_req_wait(ipa_q6_clnt, &req_desc, req, @@ -1133,7 +1133,7 @@ int ipa_qmi_get_network_stats(struct ipa_get_apn_data_stats_req_msg_v01 *req, sizeof(struct ipa_get_apn_data_stats_resp_msg_v01), QMI_SEND_STATS_REQ_TIMEOUT_MS); - IPAWANDBG("QMI_IPA_GET_APN_DATA_STATS_RESP_V01 received\n"); + IPAWANDBG_LOW("QMI_IPA_GET_APN_DATA_STATS_RESP_V01 received\n"); return ipa_check_qmi_response(rc, QMI_IPA_GET_APN_DATA_STATS_REQ_V01, resp->resp.result, @@ -1157,7 +1157,7 @@ int ipa_qmi_set_data_quota(struct ipa_set_data_usage_quota_req_msg_v01 *req) resp_desc.msg_id = QMI_IPA_SET_DATA_USAGE_QUOTA_RESP_V01; resp_desc.ei_array = ipa_set_data_usage_quota_resp_msg_data_v01_ei; - IPAWANDBG("Sending QMI_IPA_SET_DATA_USAGE_QUOTA_REQ_V01\n"); + IPAWANDBG_LOW("Sending QMI_IPA_SET_DATA_USAGE_QUOTA_REQ_V01\n"); if (unlikely(!ipa_q6_clnt)) return -ETIMEDOUT; rc = qmi_send_req_wait(ipa_q6_clnt, &req_desc, req, @@ -1165,7 +1165,7 @@ int ipa_qmi_set_data_quota(struct ipa_set_data_usage_quota_req_msg_v01 *req) &resp_desc, &resp, sizeof(resp), QMI_SEND_STATS_REQ_TIMEOUT_MS); - IPAWANDBG("QMI_IPA_SET_DATA_USAGE_QUOTA_RESP_V01 received\n"); + IPAWANDBG_LOW("QMI_IPA_SET_DATA_USAGE_QUOTA_RESP_V01 received\n"); return ipa_check_qmi_response(rc, QMI_IPA_SET_DATA_USAGE_QUOTA_REQ_V01, resp.resp.result, @@ -1192,14 +1192,14 @@ int ipa_qmi_stop_data_qouta(void) resp_desc.msg_id = QMI_IPA_STOP_DATA_USAGE_QUOTA_RESP_V01; resp_desc.ei_array = ipa_stop_data_usage_quota_resp_msg_data_v01_ei; - IPAWANDBG("Sending QMI_IPA_STOP_DATA_USAGE_QUOTA_REQ_V01\n"); + IPAWANDBG_LOW("Sending QMI_IPA_STOP_DATA_USAGE_QUOTA_REQ_V01\n"); if (unlikely(!ipa_q6_clnt)) return -ETIMEDOUT; rc = qmi_send_req_wait(ipa_q6_clnt, &req_desc, &req, sizeof(req), &resp_desc, &resp, sizeof(resp), QMI_SEND_STATS_REQ_TIMEOUT_MS); - IPAWANDBG("QMI_IPA_STOP_DATA_USAGE_QUOTA_RESP_V01 received\n"); + IPAWANDBG_LOW("QMI_IPA_STOP_DATA_USAGE_QUOTA_RESP_V01 received\n"); return ipa_check_qmi_response(rc, QMI_IPA_STOP_DATA_USAGE_QUOTA_REQ_V01, resp.resp.result, diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.h b/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.h index 7793fc05a339..c7c6234aae0e 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.h +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_qmi_service.h @@ -31,9 +31,39 @@ #define SUBSYS_MODEM "modem" #define IPAWANDBG(fmt, args...) \ - pr_debug(DEV_NAME " %s:%d " fmt, __func__, __LINE__, ## args) + do { \ + pr_debug(DEV_NAME " %s:%d " fmt, __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + } while (0) + +#define IPAWANDBG_LOW(fmt, args...) \ + do { \ + pr_debug(DEV_NAME " %s:%d " fmt, __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + } while (0) + #define IPAWANERR(fmt, args...) \ - pr_err(DEV_NAME " %s:%d " fmt, __func__, __LINE__, ## args) + do { \ + pr_err(DEV_NAME " %s:%d " fmt, __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + } while (0) + +#define IPAWANINFO(fmt, args...) \ + do { \ + pr_info(DEV_NAME " %s:%d " fmt, __func__, __LINE__, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \ + DEV_NAME " %s:%d " fmt, ## args); \ + } while (0) + extern struct ipa_qmi_context *ipa_qmi_ctx; extern struct mutex ipa_qmi_lock; diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_rt.c b/drivers/platform/msm/ipa/ipa_v2/ipa_rt.c index 5e7a5383334c..069c5cbcf4f3 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_rt.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_rt.c @@ -87,7 +87,7 @@ int __ipa_generate_rt_hw_rule_v2(enum ipa_ip_type ip, return -EPERM; } - IPADBG("en_rule 0x%x\n", en_rule); + IPADBG_LOW("en_rule 0x%x\n", en_rule); rule_hdr->u.hdr.en_rule = en_rule; ipa_write_32(rule_hdr->u.word, (u8 *)rule_hdr); @@ -490,7 +490,9 @@ static void __ipa_reap_sys_rt_tbls(enum ipa_ip_type ip) set = &ipa_ctx->rt_tbl_set[ip]; list_for_each_entry(tbl, &set->head_rt_tbl_list, link) { if (tbl->prev_mem.phys_base) { - IPADBG("reaping rt tbl name=%s ip=%d\n", tbl->name, ip); + IPADBG_LOW("reaping rt"); + IPADBG_LOW("tbl name=%s ip=%d\n", + tbl->name, ip); dma_free_coherent(ipa_ctx->pdev, tbl->prev_mem.size, tbl->prev_mem.base, tbl->prev_mem.phys_base); @@ -503,8 +505,9 @@ static void __ipa_reap_sys_rt_tbls(enum ipa_ip_type ip) list_del(&tbl->link); WARN_ON(tbl->prev_mem.phys_base != 0); if (tbl->curr_mem.phys_base) { - IPADBG("reaping sys rt tbl name=%s ip=%d\n", tbl->name, - ip); + IPADBG_LOW("reaping sys"); + IPADBG_LOW("rt tbl name=%s ip=%d\n", + tbl->name, ip); dma_free_coherent(ipa_ctx->pdev, tbl->curr_mem.size, tbl->curr_mem.base, tbl->curr_mem.phys_base); @@ -931,7 +934,7 @@ static int __ipa_del_rt_tbl(struct ipa_rt_tbl *entry) list_del(&entry->link); clear_bit(entry->idx, &ipa_ctx->rt_idx_bitmap[ip]); entry->set->tbl_cnt--; - IPADBG("del rt tbl_idx=%d tbl_cnt=%d\n", entry->idx, + IPADBG_LOW("del rt tbl_idx=%d tbl_cnt=%d\n", entry->idx, entry->set->tbl_cnt); kmem_cache_free(ipa_ctx->rt_tbl_cache, entry); } else { @@ -939,7 +942,7 @@ static int __ipa_del_rt_tbl(struct ipa_rt_tbl *entry) &ipa_ctx->reap_rt_tbl_set[ip].head_rt_tbl_list); clear_bit(entry->idx, &ipa_ctx->rt_idx_bitmap[ip]); entry->set->tbl_cnt--; - IPADBG("del sys rt tbl_idx=%d tbl_cnt=%d\n", entry->idx, + IPADBG_LOW("del sys rt tbl_idx=%d tbl_cnt=%d\n", entry->idx, entry->set->tbl_cnt); } @@ -1019,7 +1022,8 @@ static int __ipa_add_rt_rule(enum ipa_ip_type ip, const char *name, WARN_ON(1); goto ipa_insert_failed; } - IPADBG("add rt rule tbl_idx=%d rule_cnt=%d\n", tbl->idx, tbl->rule_cnt); + IPADBG_LOW("add rt rule tbl_idx=%d", tbl->idx); + IPADBG_LOW("rule_cnt=%d\n", tbl->rule_cnt); *rule_hdl = id; entry->id = id; @@ -1103,7 +1107,7 @@ int __ipa_del_rt_rule(u32 rule_hdl) __ipa_release_hdr_proc_ctx(entry->proc_ctx->id); list_del(&entry->link); entry->tbl->rule_cnt--; - IPADBG("del rt rule tbl_idx=%d rule_cnt=%d\n", entry->tbl->idx, + IPADBG_LOW("del rt rule tbl_idx=%d rule_cnt=%d\n", entry->tbl->idx, entry->tbl->rule_cnt); if (entry->tbl->rule_cnt == 0 && entry->tbl->ref_cnt == 0) { if (__ipa_del_rt_tbl(entry->tbl)) diff --git a/drivers/platform/msm/ipa/ipa_v2/ipa_utils.c b/drivers/platform/msm/ipa/ipa_v2/ipa_utils.c index 8968d5d4509f..87d84b43c829 100644 --- a/drivers/platform/msm/ipa/ipa_v2/ipa_utils.c +++ b/drivers/platform/msm/ipa/ipa_v2/ipa_utils.c @@ -1675,6 +1675,7 @@ int ipa_generate_hw_rule(enum ipa_ip_type ip, * OFFSET_MEQ32_0 with mask of 0 and val of 0 and offset 0 */ if (attrib->attrib_mask == 0) { + IPADBG_LOW("building default rule\n"); if (ipa_ofst_meq32[ofst_meq32] == -1) { IPAERR("ran out of meq32 eq\n"); return -EPERM; @@ -4913,13 +4914,17 @@ static int ipa2_stop_gsi_channel(u32 clnt_hdl) static void *ipa2_get_ipc_logbuf(void) { - /* no support for IPC logging in IPAv2 */ + if (ipa_ctx) + return ipa_ctx->logbuf; + return NULL; } static void *ipa2_get_ipc_logbuf_low(void) { - /* no support for IPC logging in IPAv2 */ + if (ipa_ctx) + return ipa_ctx->logbuf_low; + return NULL; } diff --git a/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa.c b/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa.c index b1f27ceb492b..b7583b990a84 100644 --- a/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa.c +++ b/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa.c @@ -1052,7 +1052,7 @@ static int ipa_wwan_xmit(struct sk_buff *skb, struct net_device *dev) struct ipa_tx_meta meta; if (skb->protocol != htons(ETH_P_MAP)) { - IPAWANDBG + IPAWANDBG_LOW ("SW filtering out none QMAP packet received from %s", current->comm); dev_kfree_skb_any(skb); @@ -1077,7 +1077,8 @@ static int ipa_wwan_xmit(struct sk_buff *skb, struct net_device *dev) if (atomic_read(&wwan_ptr->outstanding_pkts) >= wwan_ptr->outstanding_high) { if (!qmap_check) { - IPAWANDBG("pending(%d)/(%d)- stop(%d), qmap_chk(%d)\n", + IPAWANDBG_LOW + ("pending(%d)/(%d)- stop(%d), qmap_chk(%d)\n", atomic_read(&wwan_ptr->outstanding_pkts), wwan_ptr->outstanding_high, netif_queue_stopped(dev), @@ -1171,7 +1172,8 @@ static void apps_ipa_tx_complete_notify(void *priv, netif_queue_stopped(wwan_ptr->net) && atomic_read(&wwan_ptr->outstanding_pkts) < (wwan_ptr->outstanding_low)) { - IPAWANDBG("Outstanding low (%d) - wake up queue\n", + IPAWANDBG_LOW + ("Outstanding low (%d) - wake up queue\n", wwan_ptr->outstanding_low); netif_wake_queue(wwan_ptr->net); } @@ -1201,7 +1203,7 @@ static void apps_ipa_packet_receive_notify(void *priv, int result; unsigned int packet_len = skb->len; - IPAWANDBG("Rx packet was received"); + IPAWANDBG_LOW("Rx packet was received"); skb->dev = ipa_netdevs[0]; skb->protocol = htons(ETH_P_MAP); @@ -1763,10 +1765,10 @@ static void q6_rm_notify_cb(void *user_data, { switch (event) { case IPA_RM_RESOURCE_GRANTED: - IPAWANDBG("%s: Q6_PROD GRANTED CB\n", __func__); + IPAWANDBG_LOW("%s: Q6_PROD GRANTED CB\n", __func__); break; case IPA_RM_RESOURCE_RELEASED: - IPAWANDBG("%s: Q6_PROD RELEASED CB\n", __func__); + IPAWANDBG_LOW("%s: Q6_PROD RELEASED CB\n", __func__); break; default: return; @@ -1873,7 +1875,7 @@ static void wake_tx_queue(struct work_struct *work) */ static void ipa_rm_resource_granted(void *dev) { - IPAWANDBG("Resource Granted - starting queue\n"); + IPAWANDBG_LOW("Resource Granted - starting queue\n"); schedule_work(&ipa_tx_wakequeue_work); } @@ -2246,7 +2248,7 @@ static int rmnet_ipa_ap_suspend(struct device *dev) struct net_device *netdev = ipa_netdevs[0]; struct wwan_private *wwan_ptr = netdev_priv(netdev); - IPAWANDBG("Enter...\n"); + IPAWANDBG_LOW("Enter...\n"); /* Do not allow A7 to suspend in case there are oustanding packets */ if (atomic_read(&wwan_ptr->outstanding_pkts) != 0) { IPAWANDBG("Outstanding packets, postponing AP suspend.\n"); @@ -2257,7 +2259,7 @@ static int rmnet_ipa_ap_suspend(struct device *dev) netif_tx_lock_bh(netdev); ipa_rm_release_resource(IPA_RM_RESOURCE_WWAN_0_PROD); netif_tx_unlock_bh(netdev); - IPAWANDBG("Exit\n"); + IPAWANDBG_LOW("Exit\n"); return 0; } @@ -2276,9 +2278,9 @@ static int rmnet_ipa_ap_resume(struct device *dev) { struct net_device *netdev = ipa_netdevs[0]; - IPAWANDBG("Enter...\n"); + IPAWANDBG_LOW("Enter...\n"); netif_wake_queue(netdev); - IPAWANDBG("Exit\n"); + IPAWANDBG_LOW("Exit\n"); return 0; } @@ -2355,6 +2357,7 @@ static int ssr_notifier_cb(struct notifier_block *this, return NOTIFY_DONE; } } + IPAWANDBG_LOW("Exit\n"); return NOTIFY_DONE; } @@ -2658,7 +2661,7 @@ int rmnet_ipa_query_tethering_stats(struct wan_ioctl_query_tether_stats *data, IPAWANERR("reset the pipe stats\n"); } else { /* print tethered-client enum */ - IPAWANDBG("Tethered-client enum(%d)\n", data->ipa_client); + IPAWANDBG_LOW("Tethered-client enum(%d)\n", data->ipa_client); } rc = ipa_qmi_get_data_stats(req, resp); @@ -2676,10 +2679,11 @@ int rmnet_ipa_query_tethering_stats(struct wan_ioctl_query_tether_stats *data, if (resp->dl_dst_pipe_stats_list_valid) { for (pipe_len = 0; pipe_len < resp->dl_dst_pipe_stats_list_len; pipe_len++) { - IPAWANDBG("Check entry(%d) dl_dst_pipe(%d)\n", + IPAWANDBG_LOW("Check entry(%d) dl_dst_pipe(%d)\n", pipe_len, resp->dl_dst_pipe_stats_list [pipe_len].pipe_index); - IPAWANDBG("dl_p_v4(%lu)v6(%lu) dl_b_v4(%lu)v6(%lu)\n", + IPAWANDBG_LOW + ("dl_p_v4(%lu)v6(%lu) dl_b_v4(%lu)v6(%lu)\n", (unsigned long int) resp-> dl_dst_pipe_stats_list[pipe_len]. num_ipv4_packets, @@ -2715,7 +2719,7 @@ int rmnet_ipa_query_tethering_stats(struct wan_ioctl_query_tether_stats *data, } } } - IPAWANDBG("v4_rx_p(%lu) v6_rx_p(%lu) v4_rx_b(%lu) v6_rx_b(%lu)\n", + IPAWANDBG_LOW("v4_rx_p(%lu) v6_rx_p(%lu) v4_rx_b(%lu) v6_rx_b(%lu)\n", (unsigned long int) data->ipv4_rx_packets, (unsigned long int) data->ipv6_rx_packets, (unsigned long int) data->ipv4_rx_bytes, @@ -2724,11 +2728,12 @@ int rmnet_ipa_query_tethering_stats(struct wan_ioctl_query_tether_stats *data, if (resp->ul_src_pipe_stats_list_valid) { for (pipe_len = 0; pipe_len < resp->ul_src_pipe_stats_list_len; pipe_len++) { - IPAWANDBG("Check entry(%d) ul_dst_pipe(%d)\n", + IPAWANDBG_LOW("Check entry(%d) ul_dst_pipe(%d)\n", pipe_len, resp->ul_src_pipe_stats_list[pipe_len]. pipe_index); - IPAWANDBG("ul_p_v4(%lu)v6(%lu)ul_b_v4(%lu)v6(%lu)\n", + IPAWANDBG_LOW + ("ul_p_v4(%lu)v6(%lu)ul_b_v4(%lu)v6(%lu)\n", (unsigned long int) resp-> ul_src_pipe_stats_list[pipe_len]. num_ipv4_packets, @@ -2764,7 +2769,7 @@ int rmnet_ipa_query_tethering_stats(struct wan_ioctl_query_tether_stats *data, } } } - IPAWANDBG("tx_p_v4(%lu)v6(%lu)tx_b_v4(%lu) v6(%lu)\n", + IPAWANDBG_LOW("tx_p_v4(%lu)v6(%lu)tx_b_v4(%lu) v6(%lu)\n", (unsigned long int) data->ipv4_tx_packets, (unsigned long int) data->ipv6_tx_packets, (unsigned long int) data->ipv4_tx_bytes, diff --git a/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa_fd_ioctl.c b/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa_fd_ioctl.c index 811dba4ab756..6a92c5fb7d52 100644 --- a/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa_fd_ioctl.c +++ b/drivers/platform/msm/ipa/ipa_v2/rmnet_ipa_fd_ioctl.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2013-2015, The Linux Foundation. All rights reserved. +/* Copyright (c) 2013-2016, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -145,8 +145,7 @@ static long wan_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) break; case WAN_IOC_POLL_TETHERING_STATS: - IPAWANDBG("device %s got WAN_IOCTL_POLL_TETHERING_STATS :>>>\n", - DRIVER_NAME); + IPAWANDBG_LOW("got WAN_IOCTL_POLL_TETHERING_STATS :>>>\n"); pyld_sz = sizeof(struct wan_ioctl_poll_tethering_stats); param = kzalloc(pyld_sz, GFP_KERNEL); if (!param) { @@ -170,8 +169,7 @@ static long wan_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) break; case WAN_IOC_SET_DATA_QUOTA: - IPAWANDBG("device %s got WAN_IOCTL_SET_DATA_QUOTA :>>>\n", - DRIVER_NAME); + IPAWANDBG_LOW("got WAN_IOCTL_SET_DATA_QUOTA :>>>\n"); pyld_sz = sizeof(struct wan_ioctl_set_data_quota); param = kzalloc(pyld_sz, GFP_KERNEL); if (!param) { @@ -195,8 +193,7 @@ static long wan_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) break; case WAN_IOC_SET_TETHER_CLIENT_PIPE: - IPAWANDBG("device %s got WAN_IOC_SET_TETHER_CLIENT_PIPE :>>>\n", - DRIVER_NAME); + IPAWANDBG_LOW("got WAN_IOC_SET_TETHER_CLIENT_PIPE :>>>\n"); pyld_sz = sizeof(struct wan_ioctl_set_tether_client_pipe); param = kzalloc(pyld_sz, GFP_KERNEL); if (!param) { @@ -216,8 +213,7 @@ static long wan_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) break; case WAN_IOC_QUERY_TETHER_STATS: - IPAWANDBG("device %s got WAN_IOC_QUERY_TETHER_STATS :>>>\n", - DRIVER_NAME); + IPAWANDBG_LOW("got WAN_IOC_QUERY_TETHER_STATS :>>>\n"); pyld_sz = sizeof(struct wan_ioctl_query_tether_stats); param = kzalloc(pyld_sz, GFP_KERNEL); if (!param) { @@ -243,8 +239,7 @@ static long wan_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) break; case WAN_IOC_RESET_TETHER_STATS: - IPAWANDBG("device %s got WAN_IOC_RESET_TETHER_STATS :>>>\n", - DRIVER_NAME); + IPAWANDBG_LOW("got WAN_IOC_RESET_TETHER_STATS :>>>\n"); pyld_sz = sizeof(struct wan_ioctl_reset_tether_stats); param = kzalloc(pyld_sz, GFP_KERNEL); if (!param) { diff --git a/drivers/platform/msm/ipa/ipa_v3/ipa.c b/drivers/platform/msm/ipa/ipa_v3/ipa.c index 214ae08234a9..3d276b0f535d 100644 --- a/drivers/platform/msm/ipa/ipa_v3/ipa.c +++ b/drivers/platform/msm/ipa/ipa_v3/ipa.c @@ -3616,6 +3616,7 @@ static int ipa3_apps_cons_request_resource(void) static void ipa3_sps_release_resource(struct work_struct *work) { + mutex_lock(&ipa3_ctx->transport_pm.transport_pm_mutex); /* check whether still need to decrease client usage */ if (atomic_read(&ipa3_ctx->transport_pm.dec_clients)) { if (atomic_read(&ipa3_ctx->transport_pm.eot_activity)) { @@ -3627,6 +3628,7 @@ static void ipa3_sps_release_resource(struct work_struct *work) } } atomic_set(&ipa3_ctx->transport_pm.eot_activity, 0); + mutex_unlock(&ipa3_ctx->transport_pm.transport_pm_mutex); } int ipa3_create_apps_resource(void) @@ -4406,6 +4408,8 @@ static int ipa3_pre_init(const struct ipa3_plat_drv_res *resource_p, goto fail_create_transport_wq; } + /* Initialize the SPS PM lock. */ + mutex_init(&ipa3_ctx->transport_pm.transport_pm_mutex); spin_lock_init(&ipa3_ctx->transport_pm.lock); ipa3_ctx->transport_pm.res_granted = false; ipa3_ctx->transport_pm.res_rel_in_prog = false; diff --git a/drivers/platform/msm/ipa/ipa_v3/ipa_i.h b/drivers/platform/msm/ipa/ipa_v3/ipa_i.h index 8aeaad612065..fe7c88a25374 100644 --- a/drivers/platform/msm/ipa/ipa_v3/ipa_i.h +++ b/drivers/platform/msm/ipa/ipa_v3/ipa_i.h @@ -974,6 +974,7 @@ struct ipa3_uc_wdi_ctx { * @lock: lock for ensuring atomic operations * @res_granted: true if SPS requested IPA resource and IPA granted it * @res_rel_in_prog: true if releasing IPA resource is in progress + * @transport_pm_mutex: Mutex to protect the transport_pm functionality. */ struct ipa3_transport_pm { spinlock_t lock; @@ -981,6 +982,7 @@ struct ipa3_transport_pm { bool res_rel_in_prog; atomic_t dec_clients; atomic_t eot_activity; + struct mutex transport_pm_mutex; }; /** diff --git a/drivers/power/qcom-charger/fg-core.h b/drivers/power/qcom-charger/fg-core.h index 6f8266a3161c..07bde30524ac 100644 --- a/drivers/power/qcom-charger/fg-core.h +++ b/drivers/power/qcom-charger/fg-core.h @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -62,6 +62,7 @@ CHARS_PER_ITEM) + 1) \ #define FG_SRAM_ADDRESS_MAX 255 +#define FG_SRAM_LEN 504 #define PROFILE_LEN 224 #define PROFILE_COMP_LEN 148 #define BUCKET_COUNT 8 @@ -160,6 +161,8 @@ enum fg_sram_param_id { FG_SRAM_RECHARGE_VBATT_THR, FG_SRAM_KI_COEFF_MED_DISCHG, FG_SRAM_KI_COEFF_HI_DISCHG, + FG_SRAM_ESR_TIGHT_FILTER, + FG_SRAM_ESR_BROAD_FILTER, FG_SRAM_MAX, }; @@ -224,6 +227,11 @@ struct fg_dt_props { int cl_min_cap_limit; int jeita_hyst_temp; int batt_temp_delta; + int esr_flt_switch_temp; + int esr_tight_flt_upct; + int esr_broad_flt_upct; + int esr_tight_lt_flt_upct; + int esr_broad_lt_flt_upct; int jeita_thresholds[NUM_JEITA_LEVELS]; int ki_coeff_soc[KI_COEFF_SOC_LEVELS]; int ki_coeff_med_dischg[KI_COEFF_SOC_LEVELS]; @@ -336,12 +344,14 @@ struct fg_chip { bool ki_coeff_dischg_en; bool esr_fcc_ctrl_en; bool soc_reporting_ready; + bool esr_flt_cold_temp_en; struct completion soc_update; struct completion soc_ready; struct delayed_work profile_load_work; struct work_struct status_change_work; struct work_struct cycle_count_work; struct delayed_work batt_avg_work; + struct delayed_work sram_dump_work; struct fg_circ_buf ibatt_circ_buf; struct fg_circ_buf vbatt_circ_buf; }; @@ -392,6 +402,7 @@ extern int fg_clear_ima_errors_if_any(struct fg_chip *chip, bool check_hw_sts); extern int fg_clear_dma_errors_if_any(struct fg_chip *chip); extern int fg_debugfs_create(struct fg_chip *chip); extern void fill_string(char *str, size_t str_len, u8 *buf, int buf_len); +extern void dump_sram(u8 *buf, int addr, int len); extern int64_t twos_compliment_extend(int64_t val, int s_bit_pos); extern s64 fg_float_decode(u16 val); extern bool is_input_present(struct fg_chip *chip); diff --git a/drivers/power/qcom-charger/fg-util.c b/drivers/power/qcom-charger/fg-util.c index 405d875ea7df..41d2af0fbdc6 100644 --- a/drivers/power/qcom-charger/fg-util.c +++ b/drivers/power/qcom-charger/fg-util.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -10,8 +10,6 @@ * GNU General Public License for more details. */ -#define pr_fmt(fmt) "FG: %s: " fmt, __func__ - #include "fg-core.h" void fg_circ_buf_add(struct fg_circ_buf *buf, int val) @@ -174,6 +172,24 @@ void fill_string(char *str, size_t str_len, u8 *buf, int buf_len) } } +void dump_sram(u8 *buf, int addr, int len) +{ + int i; + char str[16]; + + /* + * Length passed should be in multiple of 4 as each FG SRAM word + * holds 4 bytes. To keep this simple, even if a length which is + * not a multiple of 4 bytes or less than 4 bytes is passed, SRAM + * registers dumped will be always in multiple of 4 bytes. + */ + for (i = 0; i < len; i += 4) { + str[0] = '\0'; + fill_string(str, sizeof(str), buf + i, 4); + pr_info("%03d %s\n", addr + (i / 4), str); + } +} + static inline bool fg_sram_address_valid(u16 address, int len) { if (address > FG_SRAM_ADDRESS_MAX) diff --git a/drivers/power/qcom-charger/qpnp-fg-gen3.c b/drivers/power/qcom-charger/qpnp-fg-gen3.c index edd9b9ff28cf..02f5ea06e22d 100644 --- a/drivers/power/qcom-charger/qpnp-fg-gen3.c +++ b/drivers/power/qcom-charger/qpnp-fg-gen3.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -12,6 +12,7 @@ #define pr_fmt(fmt) "FG: %s: " fmt, __func__ +#include <linux/ktime.h> #include <linux/of.h> #include <linux/of_irq.h> #include <linux/of_platform.h> @@ -36,6 +37,11 @@ #define SYS_TERM_CURR_OFFSET 0 #define VBATT_FULL_WORD 7 #define VBATT_FULL_OFFSET 0 +#define ESR_FILTER_WORD 8 +#define ESR_UPD_TIGHT_OFFSET 0 +#define ESR_UPD_BROAD_OFFSET 1 +#define ESR_UPD_TIGHT_LOW_TEMP_OFFSET 2 +#define ESR_UPD_BROAD_LOW_TEMP_OFFSET 3 #define KI_COEFF_MED_DISCHG_WORD 9 #define KI_COEFF_MED_DISCHG_OFFSET 3 #define KI_COEFF_HI_DISCHG_WORD 10 @@ -202,6 +208,10 @@ static struct fg_sram_param pmi8998_v1_sram_params[] = { PARAM(KI_COEFF_HI_DISCHG, KI_COEFF_HI_DISCHG_WORD, KI_COEFF_HI_DISCHG_OFFSET, 1, 1000, 244141, 0, fg_encode_default, NULL), + PARAM(ESR_TIGHT_FILTER, ESR_FILTER_WORD, ESR_UPD_TIGHT_OFFSET, + 1, 512, 1000000, 0, fg_encode_default, NULL), + PARAM(ESR_BROAD_FILTER, ESR_FILTER_WORD, ESR_UPD_BROAD_OFFSET, + 1, 512, 1000000, 0, fg_encode_default, NULL), }; static struct fg_sram_param pmi8998_v2_sram_params[] = { @@ -262,6 +272,10 @@ static struct fg_sram_param pmi8998_v2_sram_params[] = { PARAM(KI_COEFF_HI_DISCHG, KI_COEFF_HI_DISCHG_v2_WORD, KI_COEFF_HI_DISCHG_v2_OFFSET, 1, 1000, 244141, 0, fg_encode_default, NULL), + PARAM(ESR_TIGHT_FILTER, ESR_FILTER_WORD, ESR_UPD_TIGHT_OFFSET, + 1, 512, 1000000, 0, fg_encode_default, NULL), + PARAM(ESR_BROAD_FILTER, ESR_FILTER_WORD, ESR_UPD_BROAD_OFFSET, + 1, 512, 1000000, 0, fg_encode_default, NULL), }; static struct fg_alg_flag pmi8998_v1_alg_flags[] = { @@ -330,17 +344,18 @@ module_param_named( debug_mask, fg_gen3_debug_mask, int, S_IRUSR | S_IWUSR ); -static int fg_sram_update_period_ms = 30000; +static bool fg_profile_dump; module_param_named( - sram_update_period_ms, fg_sram_update_period_ms, int, S_IRUSR | S_IWUSR + profile_dump, fg_profile_dump, bool, S_IRUSR | S_IWUSR ); -static bool fg_sram_dump; +static int fg_sram_dump_period_ms = 20000; module_param_named( - sram_dump, fg_sram_dump, bool, S_IRUSR | S_IWUSR + sram_dump_period_ms, fg_sram_dump_period_ms, int, S_IRUSR | S_IWUSR ); static int fg_restart; +static bool fg_sram_dump; /* All getters HERE */ @@ -797,7 +812,7 @@ static const char *fg_get_battery_type(struct fg_chip *chip) if (chip->bp.batt_type_str) { if (chip->profile_loaded) return chip->bp.batt_type_str; - else + else if (chip->profile_available) return LOADING_BATT_TYPE; } @@ -1548,6 +1563,65 @@ static int fg_adjust_recharge_soc(struct fg_chip *chip) return 0; } +static int fg_esr_filter_config(struct fg_chip *chip, int batt_temp) +{ + u8 esr_tight_lt_flt, esr_broad_lt_flt; + bool cold_temp = false; + int rc; + + /* + * If the battery temperature is lower than -20 C, then skip modifying + * ESR filter. + */ + if (batt_temp < -210) + return 0; + + /* + * If battery temperature is lesser than 10 C (default), then apply the + * normal ESR tight and broad filter values to ESR low temperature tight + * and broad filters. If battery temperature is higher than 10 C, then + * apply back the low temperature ESR filter coefficients to ESR low + * temperature tight and broad filters. + */ + if (batt_temp > chip->dt.esr_flt_switch_temp + && chip->esr_flt_cold_temp_en) { + fg_encode(chip->sp, FG_SRAM_ESR_TIGHT_FILTER, + chip->dt.esr_tight_lt_flt_upct, &esr_tight_lt_flt); + fg_encode(chip->sp, FG_SRAM_ESR_BROAD_FILTER, + chip->dt.esr_broad_lt_flt_upct, &esr_broad_lt_flt); + } else if (batt_temp <= chip->dt.esr_flt_switch_temp + && !chip->esr_flt_cold_temp_en) { + fg_encode(chip->sp, FG_SRAM_ESR_TIGHT_FILTER, + chip->dt.esr_tight_flt_upct, &esr_tight_lt_flt); + fg_encode(chip->sp, FG_SRAM_ESR_BROAD_FILTER, + chip->dt.esr_broad_flt_upct, &esr_broad_lt_flt); + cold_temp = true; + } else { + return 0; + } + + rc = fg_sram_write(chip, ESR_FILTER_WORD, + ESR_UPD_TIGHT_LOW_TEMP_OFFSET, &esr_tight_lt_flt, 1, + FG_IMA_DEFAULT); + if (rc < 0) { + pr_err("Error in writing ESR LT tight filter, rc=%d\n", rc); + return rc; + } + + rc = fg_sram_write(chip, ESR_FILTER_WORD, + ESR_UPD_BROAD_LOW_TEMP_OFFSET, &esr_broad_lt_flt, 1, + FG_IMA_DEFAULT); + if (rc < 0) { + pr_err("Error in writing ESR LT broad filter, rc=%d\n", rc); + return rc; + } + + chip->esr_flt_cold_temp_en = cold_temp; + fg_dbg(chip, FG_STATUS, "applied %s ESR filter values\n", + cold_temp ? "cold" : "normal"); + return 0; +} + static int fg_esr_fcc_config(struct fg_chip *chip) { union power_supply_propval prop = {0, }; @@ -1615,6 +1689,18 @@ static int fg_esr_fcc_config(struct fg_chip *chip) return 0; } +static int fg_batt_missing_config(struct fg_chip *chip, bool enable) +{ + int rc; + + rc = fg_masked_write(chip, BATT_INFO_BATT_MISS_CFG(chip), + BM_FROM_BATT_ID_BIT, enable ? BM_FROM_BATT_ID_BIT : 0); + if (rc < 0) + pr_err("Error in writing to %04x, rc=%d\n", + BATT_INFO_BATT_MISS_CFG(chip), rc); + return rc; +} + static void fg_batt_avg_update(struct fg_chip *chip) { if (chip->charge_status == chip->prev_charge_status) @@ -1838,18 +1924,6 @@ static int fg_get_cycle_count(struct fg_chip *chip) return count; } -static void dump_sram(u8 *buf, int len) -{ - int i; - char str[16]; - - for (i = 0; i < len; i += 4) { - str[0] = '\0'; - fill_string(str, sizeof(str), buf + i, 4); - pr_info("%03d %s\n", PROFILE_LOAD_WORD + (i / 4), str); - } -} - #define PROFILE_LOAD_BIT BIT(0) #define BOOTLOADER_LOAD_BIT BIT(1) #define BOOTLOADER_RESTART_BIT BIT(2) @@ -1885,11 +1959,13 @@ static bool is_profile_load_required(struct fg_chip *chip) if (!chip->dt.force_load_profile) { pr_warn("Profiles doesn't match, skipping loading it since force_load_profile is disabled\n"); - if (fg_sram_dump) { + if (fg_profile_dump) { pr_info("FG: loaded profile:\n"); - dump_sram(buf, PROFILE_COMP_LEN); + dump_sram(buf, PROFILE_LOAD_WORD, + PROFILE_COMP_LEN); pr_info("FG: available profile:\n"); - dump_sram(chip->batt_profile, PROFILE_LEN); + dump_sram(chip->batt_profile, PROFILE_LOAD_WORD, + PROFILE_LEN); } return false; } @@ -1897,14 +1973,26 @@ static bool is_profile_load_required(struct fg_chip *chip) fg_dbg(chip, FG_STATUS, "Profiles are different, loading the correct one\n"); } else { fg_dbg(chip, FG_STATUS, "Profile integrity bit is not set\n"); - if (fg_sram_dump) { + if (fg_profile_dump) { pr_info("FG: profile to be loaded:\n"); - dump_sram(chip->batt_profile, PROFILE_LEN); + dump_sram(chip->batt_profile, PROFILE_LOAD_WORD, + PROFILE_LEN); } } return true; } +static void clear_battery_profile(struct fg_chip *chip) +{ + u8 val = 0; + int rc; + + rc = fg_sram_write(chip, PROFILE_INTEGRITY_WORD, + PROFILE_INTEGRITY_OFFSET, &val, 1, FG_IMA_DEFAULT); + if (rc < 0) + pr_err("failed to write profile integrity rc=%d\n", rc); +} + #define SOC_READY_WAIT_MS 2000 static int __fg_restart(struct fg_chip *chip) { @@ -2056,6 +2144,71 @@ out: vote(chip->awake_votable, PROFILE_LOAD, false, 0); } +static void sram_dump_work(struct work_struct *work) +{ + struct fg_chip *chip = container_of(work, struct fg_chip, + sram_dump_work.work); + u8 buf[FG_SRAM_LEN]; + int rc; + s64 timestamp_ms; + + rc = fg_sram_read(chip, 0, 0, buf, FG_SRAM_LEN, FG_IMA_DEFAULT); + if (rc < 0) { + pr_err("Error in reading FG SRAM, rc:%d\n", rc); + goto resched; + } + + timestamp_ms = ktime_to_ms(ktime_get_boottime()); + fg_dbg(chip, FG_STATUS, "SRAM Dump Started at %lld.%lld\n", + timestamp_ms / 1000, timestamp_ms % 1000); + dump_sram(buf, 0, FG_SRAM_LEN); + timestamp_ms = ktime_to_ms(ktime_get_boottime()); + fg_dbg(chip, FG_STATUS, "SRAM Dump done at %lld.%lld\n", + timestamp_ms / 1000, timestamp_ms % 1000); +resched: + schedule_delayed_work(&chip->sram_dump_work, + msecs_to_jiffies(fg_sram_dump_period_ms)); +} + +static int fg_sram_dump_sysfs(const char *val, const struct kernel_param *kp) +{ + int rc; + struct power_supply *bms_psy; + struct fg_chip *chip; + bool old_val = fg_sram_dump; + + rc = param_set_bool(val, kp); + if (rc) { + pr_err("Unable to set fg_sram_dump: %d\n", rc); + return rc; + } + + if (fg_sram_dump == old_val) + return 0; + + bms_psy = power_supply_get_by_name("bms"); + if (!bms_psy) { + pr_err("bms psy not found\n"); + return -ENODEV; + } + + chip = power_supply_get_drvdata(bms_psy); + if (fg_sram_dump) + schedule_delayed_work(&chip->sram_dump_work, + msecs_to_jiffies(fg_sram_dump_period_ms)); + else + cancel_delayed_work_sync(&chip->sram_dump_work); + + return 0; +} + +static struct kernel_param_ops fg_sram_dump_ops = { + .set = fg_sram_dump_sysfs, + .get = param_get_bool, +}; + +module_param_cb(sram_dump_en, &fg_sram_dump_ops, &fg_sram_dump, 0644); + static int fg_restart_sysfs(const char *val, const struct kernel_param *kp) { int rc; @@ -2355,7 +2508,7 @@ static int fg_psy_get_property(struct power_supply *psy, pval->intval = chip->cl.nom_cap_uah; break; case POWER_SUPPLY_PROP_RESISTANCE_ID: - rc = fg_get_batt_id(chip, &pval->intval); + pval->intval = chip->batt_id_ohms; break; case POWER_SUPPLY_PROP_BATTERY_TYPE: pval->strval = fg_get_battery_type(chip); @@ -2709,6 +2862,26 @@ static int fg_hw_init(struct fg_chip *chip) } } + fg_encode(chip->sp, FG_SRAM_ESR_TIGHT_FILTER, + chip->dt.esr_tight_flt_upct, buf); + rc = fg_sram_write(chip, chip->sp[FG_SRAM_ESR_TIGHT_FILTER].addr_word, + chip->sp[FG_SRAM_ESR_TIGHT_FILTER].addr_byte, buf, + chip->sp[FG_SRAM_ESR_TIGHT_FILTER].len, FG_IMA_DEFAULT); + if (rc < 0) { + pr_err("Error in writing ESR tight filter, rc=%d\n", rc); + return rc; + } + + fg_encode(chip->sp, FG_SRAM_ESR_BROAD_FILTER, + chip->dt.esr_broad_flt_upct, buf); + rc = fg_sram_write(chip, chip->sp[FG_SRAM_ESR_BROAD_FILTER].addr_word, + chip->sp[FG_SRAM_ESR_BROAD_FILTER].addr_byte, buf, + chip->sp[FG_SRAM_ESR_BROAD_FILTER].len, FG_IMA_DEFAULT); + if (rc < 0) { + pr_err("Error in writing ESR broad filter, rc=%d\n", rc); + return rc; + } + return 0; } @@ -2764,7 +2937,6 @@ static irqreturn_t fg_batt_missing_irq_handler(int irq, void *data) u8 status; int rc; - fg_dbg(chip, FG_IRQ, "irq %d triggered\n", irq); rc = fg_read(chip, BATT_INFO_INT_RT_STS(chip), &status, 1); if (rc < 0) { pr_err("failed to read addr=0x%04x, rc=%d\n", @@ -2772,23 +2944,39 @@ static irqreturn_t fg_batt_missing_irq_handler(int irq, void *data) return IRQ_HANDLED; } + fg_dbg(chip, FG_IRQ, "irq %d triggered sts:%d\n", irq, status); chip->battery_missing = (status & BT_MISS_BIT); if (chip->battery_missing) { chip->profile_available = false; chip->profile_loaded = false; - clear_cycle_counter(chip); chip->soc_reporting_ready = false; - } else { - rc = fg_get_batt_profile(chip); - if (rc < 0) { - chip->soc_reporting_ready = true; - pr_err("Error in getting battery profile, rc:%d\n", rc); - return IRQ_HANDLED; - } - schedule_delayed_work(&chip->profile_load_work, 0); + return IRQ_HANDLED; } + rc = fg_batt_missing_config(chip, false); + if (rc < 0) { + pr_err("Error in disabling BMD, rc=%d\n", rc); + return IRQ_HANDLED; + } + + rc = fg_get_batt_profile(chip); + if (rc < 0) { + chip->soc_reporting_ready = true; + pr_err("Error in getting battery profile, rc:%d\n", rc); + goto enable_bmd; + } + + clear_battery_profile(chip); + schedule_delayed_work(&chip->profile_load_work, 0); + +enable_bmd: + /* Wait for 200ms before enabling BMD again */ + msleep(200); + rc = fg_batt_missing_config(chip, true); + if (rc < 0) + pr_err("Error in enabling BMD, rc=%d\n", rc); + return IRQ_HANDLED; } @@ -2805,6 +2993,10 @@ static irqreturn_t fg_delta_batt_temp_irq_handler(int irq, void *data) return IRQ_HANDLED; } + rc = fg_esr_filter_config(chip, batt_temp); + if (rc < 0) + pr_err("Error in configuring ESR filter rc:%d\n", rc); + if (!is_charger_available(chip)) { chip->last_batt_temp = batt_temp; return IRQ_HANDLED; @@ -3111,6 +3303,11 @@ static int fg_parse_ki_coefficients(struct fg_chip *chip) #define DEFAULT_CL_MAX_LIM_DECIPERC 0 #define BTEMP_DELTA_LOW 2 #define BTEMP_DELTA_HIGH 10 +#define DEFAULT_ESR_FLT_TEMP_DECIDEGC 100 +#define DEFAULT_ESR_TIGHT_FLT_UPCT 3907 +#define DEFAULT_ESR_BROAD_FLT_UPCT 99610 +#define DEFAULT_ESR_TIGHT_LT_FLT_UPCT 48829 +#define DEFAULT_ESR_BROAD_LT_FLT_UPCT 148438 static int fg_parse_dt(struct fg_chip *chip) { struct device_node *child, *revid_node, *node = chip->dev->of_node; @@ -3387,6 +3584,40 @@ static int fg_parse_dt(struct fg_chip *chip) else chip->dt.rconn_mohms = temp; + rc = of_property_read_u32(node, "qcom,fg-esr-filter-switch-temp", + &temp); + if (rc < 0) + chip->dt.esr_flt_switch_temp = DEFAULT_ESR_FLT_TEMP_DECIDEGC; + else + chip->dt.esr_flt_switch_temp = temp; + + rc = of_property_read_u32(node, "qcom,fg-esr-tight-filter-micro-pct", + &temp); + if (rc < 0) + chip->dt.esr_tight_flt_upct = DEFAULT_ESR_TIGHT_FLT_UPCT; + else + chip->dt.esr_tight_flt_upct = temp; + + rc = of_property_read_u32(node, "qcom,fg-esr-broad-filter-micro-pct", + &temp); + if (rc < 0) + chip->dt.esr_broad_flt_upct = DEFAULT_ESR_BROAD_FLT_UPCT; + else + chip->dt.esr_broad_flt_upct = temp; + + rc = of_property_read_u32(node, "qcom,fg-esr-tight-lt-filter-micro-pct", + &temp); + if (rc < 0) + chip->dt.esr_tight_lt_flt_upct = DEFAULT_ESR_TIGHT_LT_FLT_UPCT; + else + chip->dt.esr_tight_lt_flt_upct = temp; + + rc = of_property_read_u32(node, "qcom,fg-esr-broad-lt-filter-micro-pct", + &temp); + if (rc < 0) + chip->dt.esr_broad_lt_flt_upct = DEFAULT_ESR_BROAD_LT_FLT_UPCT; + else + chip->dt.esr_broad_lt_flt_upct = temp; return 0; } @@ -3449,6 +3680,7 @@ static int fg_gen3_probe(struct platform_device *pdev) INIT_WORK(&chip->status_change_work, status_change_work); INIT_WORK(&chip->cycle_count_work, cycle_count_work); INIT_DELAYED_WORK(&chip->batt_avg_work, batt_avg_work); + INIT_DELAYED_WORK(&chip->sram_dump_work, sram_dump_work); rc = fg_memif_init(chip); if (rc < 0) { @@ -3511,9 +3743,13 @@ static int fg_gen3_probe(struct platform_device *pdev) if (!rc) rc = fg_get_battery_temp(chip, &batt_temp); - if (!rc) + if (!rc) { pr_info("battery SOC:%d voltage: %duV temp: %d id: %dKOhms\n", msoc, volt_uv, batt_temp, chip->batt_id_ohms / 1000); + rc = fg_esr_filter_config(chip, batt_temp); + if (rc < 0) + pr_err("Error in configuring ESR filter rc:%d\n", rc); + } device_init_wakeup(chip->dev, true); if (chip->profile_available) @@ -3542,6 +3778,8 @@ static int fg_gen3_suspend(struct device *dev) } cancel_delayed_work_sync(&chip->batt_avg_work); + if (fg_sram_dump) + cancel_delayed_work_sync(&chip->sram_dump_work); return 0; } @@ -3563,6 +3801,9 @@ static int fg_gen3_resume(struct device *dev) fg_circ_buf_clr(&chip->ibatt_circ_buf); fg_circ_buf_clr(&chip->vbatt_circ_buf); schedule_delayed_work(&chip->batt_avg_work, 0); + if (fg_sram_dump) + schedule_delayed_work(&chip->sram_dump_work, + msecs_to_jiffies(fg_sram_dump_period_ms)); return 0; } diff --git a/drivers/power/qcom-charger/smb-lib.c b/drivers/power/qcom-charger/smb-lib.c index 86140386f0e3..7bface5a411c 100644 --- a/drivers/power/qcom-charger/smb-lib.c +++ b/drivers/power/qcom-charger/smb-lib.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2016 The Linux Foundation. All rights reserved. +/* Copyright (c) 2016-2017 The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -16,7 +16,7 @@ #include <linux/iio/consumer.h> #include <linux/power_supply.h> #include <linux/regulator/driver.h> -#include <linux/qpnp/power-on.h> +#include <linux/input/qpnp-power-on.h> #include <linux/irq.h> #include "smb-lib.h" #include "smb-reg.h" diff --git a/drivers/power/reset/msm-poweroff.c b/drivers/power/reset/msm-poweroff.c index 267df592ba8a..cd02ed5bd46a 100644 --- a/drivers/power/reset/msm-poweroff.c +++ b/drivers/power/reset/msm-poweroff.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2013-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2013-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -23,7 +23,7 @@ #include <linux/reboot.h> #include <linux/pm.h> #include <linux/delay.h> -#include <linux/qpnp/power-on.h> +#include <linux/input/qpnp-power-on.h> #include <linux/of_address.h> #include <asm/cacheflush.h> diff --git a/drivers/regulator/cprh-kbss-regulator.c b/drivers/regulator/cprh-kbss-regulator.c index 9cbd1ee18ec3..0472ce13197b 100644 --- a/drivers/regulator/cprh-kbss-regulator.c +++ b/drivers/regulator/cprh-kbss-regulator.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2015-2016, The Linux Foundation. All rights reserved. + * Copyright (c) 2015-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -36,9 +36,10 @@ #include "cpr3-regulator.h" #define MSM8998_KBSS_FUSE_CORNERS 4 +#define SDM660_KBSS_FUSE_CORNERS 5 /** - * struct cprh_msm8998_kbss_fuses - KBSS specific fuse data for MSM8998 + * struct cprh_kbss_fuses - KBSS specific fuse data * @ro_sel: Ring oscillator select fuse parameter value for each * fuse corner * @init_voltage: Initial (i.e. open-loop) voltage fuse parameter value @@ -59,11 +60,11 @@ * * This struct holds the values for all of the fuses read from memory. */ -struct cprh_msm8998_kbss_fuses { - u64 ro_sel[MSM8998_KBSS_FUSE_CORNERS]; - u64 init_voltage[MSM8998_KBSS_FUSE_CORNERS]; - u64 target_quot[MSM8998_KBSS_FUSE_CORNERS]; - u64 quot_offset[MSM8998_KBSS_FUSE_CORNERS]; +struct cprh_kbss_fuses { + u64 *ro_sel; + u64 *init_voltage; + u64 *target_quot; + u64 *quot_offset; u64 speed_bin; u64 cpr_fusing_rev; u64 force_highest_corner; @@ -76,7 +77,8 @@ struct cprh_msm8998_kbss_fuses { * Fuse combos 16 - 23 map to CPR fusing revision 0 - 7 with speed bin fuse = 2. * Fuse combos 24 - 31 map to CPR fusing revision 0 - 7 with speed bin fuse = 3. */ -#define CPRH_MSM8998_KBSS_FUSE_COMBO_COUNT 32 +#define CPRH_MSM8998_KBSS_FUSE_COMBO_COUNT 32 +#define CPRH_SDM660_KBSS_FUSE_COMBO_COUNT 16 /* * Constants which define the name of each fuse corner. @@ -95,13 +97,45 @@ static const char * const cprh_msm8998_kbss_fuse_corner_name[] = { [CPRH_MSM8998_KBSS_FUSE_CORNER_TURBO_L1] = "TURBO_L1", }; +enum cprh_sdm660_power_kbss_fuse_corner { + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_LOWSVS = 0, + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_SVS = 1, + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_SVSPLUS = 2, + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_NOM = 3, + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_TURBO_L1 = 4, +}; + +static const char * const cprh_sdm660_power_kbss_fuse_corner_name[] = { + [CPRH_SDM660_POWER_KBSS_FUSE_CORNER_LOWSVS] = "LowSVS", + [CPRH_SDM660_POWER_KBSS_FUSE_CORNER_SVS] = "SVS", + [CPRH_SDM660_POWER_KBSS_FUSE_CORNER_SVSPLUS] = "SVSPLUS", + [CPRH_SDM660_POWER_KBSS_FUSE_CORNER_NOM] = "NOM", + [CPRH_SDM660_POWER_KBSS_FUSE_CORNER_TURBO_L1] = "TURBO_L1", +}; + +enum cprh_sdm660_perf_kbss_fuse_corner { + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_SVS = 0, + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_SVSPLUS = 1, + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_NOM = 2, + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_TURBO = 3, + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_TURBO_L2 = 4, +}; + +static const char * const cprh_sdm660_perf_kbss_fuse_corner_name[] = { + [CPRH_SDM660_PERF_KBSS_FUSE_CORNER_SVS] = "SVS", + [CPRH_SDM660_PERF_KBSS_FUSE_CORNER_SVSPLUS] = "SVSPLUS", + [CPRH_SDM660_PERF_KBSS_FUSE_CORNER_NOM] = "NOM", + [CPRH_SDM660_PERF_KBSS_FUSE_CORNER_TURBO] = "TURBO", + [CPRH_SDM660_PERF_KBSS_FUSE_CORNER_TURBO_L2] = "TURBO_L2", +}; + /* KBSS cluster IDs */ -#define MSM8998_KBSS_POWER_CLUSTER_ID 0 -#define MSM8998_KBSS_PERFORMANCE_CLUSTER_ID 1 +#define CPRH_KBSS_POWER_CLUSTER_ID 0 +#define CPRH_KBSS_PERFORMANCE_CLUSTER_ID 1 /* KBSS controller IDs */ -#define MSM8998_KBSS_MIN_CONTROLLER_ID 0 -#define MSM8998_KBSS_MAX_CONTROLLER_ID 1 +#define CPRH_KBSS_MIN_CONTROLLER_ID 0 +#define CPRH_KBSS_MAX_CONTROLLER_ID 1 /* * MSM8998 KBSS fuse parameter locations: @@ -119,13 +153,13 @@ static const char * const cprh_msm8998_kbss_fuse_corner_name[] = { */ static const struct cpr3_fuse_param msm8998_kbss_ro_sel_param[2][MSM8998_KBSS_FUSE_CORNERS][2] = { - [MSM8998_KBSS_POWER_CLUSTER_ID] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { {{67, 12, 15}, {} }, {{67, 8, 11}, {} }, {{67, 4, 7}, {} }, {{67, 0, 3}, {} }, }, - [MSM8998_KBSS_PERFORMANCE_CLUSTER_ID] = { + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { {{69, 26, 29}, {} }, {{69, 22, 25}, {} }, {{69, 18, 21}, {} }, @@ -134,14 +168,32 @@ msm8998_kbss_ro_sel_param[2][MSM8998_KBSS_FUSE_CORNERS][2] = { }; static const struct cpr3_fuse_param +sdm660_kbss_ro_sel_param[2][SDM660_KBSS_FUSE_CORNERS][3] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { + {{67, 12, 15}, {} }, + {{67, 8, 11}, {} }, + {{65, 56, 59}, {} }, + {{67, 4, 7}, {} }, + {{67, 0, 3}, {} }, + }, + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { + {{68, 61, 63}, {69, 0, 0} }, + {{69, 1, 4}, {} }, + {{68, 57, 60}, {} }, + {{68, 53, 56}, {} }, + {{66, 14, 17}, {} }, + }, +}; + +static const struct cpr3_fuse_param msm8998_kbss_init_voltage_param[2][MSM8998_KBSS_FUSE_CORNERS][2] = { - [MSM8998_KBSS_POWER_CLUSTER_ID] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { {{67, 34, 39}, {} }, {{67, 28, 33}, {} }, {{67, 22, 27}, {} }, {{67, 16, 21}, {} }, }, - [MSM8998_KBSS_PERFORMANCE_CLUSTER_ID] = { + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { {{69, 48, 53}, {} }, {{69, 42, 47}, {} }, {{69, 36, 41}, {} }, @@ -150,14 +202,32 @@ msm8998_kbss_init_voltage_param[2][MSM8998_KBSS_FUSE_CORNERS][2] = { }; static const struct cpr3_fuse_param +sdm660_kbss_init_voltage_param[2][SDM660_KBSS_FUSE_CORNERS][2] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { + {{67, 34, 39}, {} }, + {{67, 28, 33}, {} }, + {{71, 3, 8}, {} }, + {{67, 22, 27}, {} }, + {{67, 16, 21}, {} }, + }, + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { + {{69, 17, 22}, {} }, + {{69, 23, 28}, {} }, + {{69, 11, 16}, {} }, + {{69, 5, 10}, {} }, + {{70, 42, 47}, {} }, + }, +}; + +static const struct cpr3_fuse_param msm8998_kbss_target_quot_param[2][MSM8998_KBSS_FUSE_CORNERS][3] = { - [MSM8998_KBSS_POWER_CLUSTER_ID] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { {{68, 18, 29}, {} }, {{68, 6, 17}, {} }, {{67, 58, 63}, {68, 0, 5} }, {{67, 46, 57}, {} }, }, - [MSM8998_KBSS_PERFORMANCE_CLUSTER_ID] = { + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { {{70, 32, 43}, {} }, {{70, 20, 31}, {} }, {{70, 8, 19}, {} }, @@ -166,14 +236,32 @@ msm8998_kbss_target_quot_param[2][MSM8998_KBSS_FUSE_CORNERS][3] = { }; static const struct cpr3_fuse_param +sdm660_kbss_target_quot_param[2][SDM660_KBSS_FUSE_CORNERS][3] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { + {{68, 12, 23}, {} }, + {{68, 0, 11}, {} }, + {{71, 9, 20}, {} }, + {{67, 52, 63}, {} }, + {{67, 40, 51}, {} }, + }, + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { + {{69, 53, 63}, {70, 0, 0}, {} }, + {{70, 1, 12}, {} }, + {{69, 41, 52}, {} }, + {{69, 29, 40}, {} }, + {{70, 48, 59}, {} }, + }, +}; + +static const struct cpr3_fuse_param msm8998_kbss_quot_offset_param[2][MSM8998_KBSS_FUSE_CORNERS][3] = { - [MSM8998_KBSS_POWER_CLUSTER_ID] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { {{} }, {{68, 63, 63}, {69, 0, 5}, {} }, {{68, 56, 62}, {} }, {{68, 49, 55}, {} }, }, - [MSM8998_KBSS_PERFORMANCE_CLUSTER_ID] = { + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { {{} }, {{71, 13, 15}, {71, 21, 24}, {} }, {{71, 6, 12}, {} }, @@ -181,12 +269,35 @@ msm8998_kbss_quot_offset_param[2][MSM8998_KBSS_FUSE_CORNERS][3] = { }, }; +static const struct cpr3_fuse_param +sdm660_kbss_quot_offset_param[2][SDM660_KBSS_FUSE_CORNERS][3] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { + {{} }, + {{68, 38, 44}, {} }, + {{71, 21, 27}, {} }, + {{68, 31, 37}, {} }, + {{68, 24, 30}, {} }, + }, + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { + {{} }, + {{70, 27, 33}, {} }, + {{70, 20, 26}, {} }, + {{70, 13, 19}, {} }, + {{70, 60, 63}, {71, 0, 2}, {} }, + }, +}; + static const struct cpr3_fuse_param msm8998_cpr_fusing_rev_param[] = { {39, 51, 53}, {}, }; -static const struct cpr3_fuse_param msm8998_kbss_speed_bin_param[] = { +static const struct cpr3_fuse_param sdm660_cpr_fusing_rev_param[] = { + {71, 28, 30}, + {}, +}; + +static const struct cpr3_fuse_param kbss_speed_bin_param[] = { {38, 29, 31}, {}, }; @@ -199,16 +310,28 @@ msm8998_cpr_force_highest_corner_param[] = { static const struct cpr3_fuse_param msm8998_kbss_aging_init_quot_diff_param[2][2] = { - [MSM8998_KBSS_POWER_CLUSTER_ID] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { {69, 6, 13}, {}, }, - [MSM8998_KBSS_PERFORMANCE_CLUSTER_ID] = { + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { {71, 25, 32}, {}, }, }; +static const struct cpr3_fuse_param +sdm660_kbss_aging_init_quot_diff_param[2][2] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { + {68, 45, 52}, + {}, + }, + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { + {70, 34, 41}, + {}, + }, +}; + /* * Open loop voltage fuse reference voltages in microvolts for MSM8998 v1 */ @@ -225,13 +348,13 @@ msm8998_v1_kbss_fuse_ref_volt[MSM8998_KBSS_FUSE_CORNERS] = { */ static const int msm8998_v2_kbss_fuse_ref_volt[2][MSM8998_KBSS_FUSE_CORNERS] = { - [MSM8998_KBSS_POWER_CLUSTER_ID] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { 688000, 756000, 828000, 1056000, }, - [MSM8998_KBSS_PERFORMANCE_CLUSTER_ID] = { + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { 756000, 756000, 828000, @@ -239,24 +362,49 @@ msm8998_v2_kbss_fuse_ref_volt[2][MSM8998_KBSS_FUSE_CORNERS] = { }, }; -#define MSM8998_KBSS_FUSE_STEP_VOLT 10000 -#define MSM8998_KBSS_VOLTAGE_FUSE_SIZE 6 -#define MSM8998_KBSS_QUOT_OFFSET_SCALE 5 -#define MSM8998_KBSS_AGING_INIT_QUOT_DIFF_SIZE 8 -#define MSM8998_KBSS_AGING_INIT_QUOT_DIFF_SCALE 1 +/* + * Open loop voltage fuse reference voltages in microvolts for SDM660 + */ +static const int +sdm660_kbss_fuse_ref_volt[2][SDM660_KBSS_FUSE_CORNERS] = { + [CPRH_KBSS_POWER_CLUSTER_ID] = { + 644000, + 724000, + 788000, + 868000, + 1068000, + }, + [CPRH_KBSS_PERFORMANCE_CLUSTER_ID] = { + 724000, + 788000, + 868000, + 988000, + 1068000, + }, +}; -#define MSM8998_KBSS_POWER_CPR_SENSOR_COUNT 6 -#define MSM8998_KBSS_PERFORMANCE_CPR_SENSOR_COUNT 9 +#define CPRH_KBSS_FUSE_STEP_VOLT 10000 +#define CPRH_KBSS_VOLTAGE_FUSE_SIZE 6 +#define CPRH_KBSS_QUOT_OFFSET_SCALE 5 +#define CPRH_KBSS_AGING_INIT_QUOT_DIFF_SIZE 8 +#define CPRH_KBSS_AGING_INIT_QUOT_DIFF_SCALE 1 -#define MSM8998_KBSS_CPR_CLOCK_RATE 19200000 +#define CPRH_KBSS_CPR_CLOCK_RATE 19200000 -#define MSM8998_KBSS_MAX_CORNER_BAND_COUNT 4 -#define MSM8998_KBSS_MAX_CORNER_COUNT 40 +#define CPRH_KBSS_MAX_CORNER_BAND_COUNT 4 +#define CPRH_KBSS_MAX_CORNER_COUNT 40 -#define MSM8998_KBSS_CPR_SDELTA_CORE_COUNT 4 +#define CPRH_KBSS_CPR_SDELTA_CORE_COUNT 4 -#define MSM8998_KBSS_MAX_TEMP_POINTS 3 -#define MSM8998_KBSS_POWER_TEMP_SENSOR_ID_START 1 +#define CPRH_KBSS_MAX_TEMP_POINTS 3 + +/* + * msm8998 configuration + */ +#define MSM8998_KBSS_POWER_CPR_SENSOR_COUNT 6 +#define MSM8998_KBSS_PERFORMANCE_CPR_SENSOR_COUNT 9 + +#define MSM8998_KBSS_POWER_TEMP_SENSOR_ID_START 1 #define MSM8998_KBSS_POWER_TEMP_SENSOR_ID_END 5 #define MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_START 6 #define MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_END 10 @@ -267,34 +415,49 @@ msm8998_v2_kbss_fuse_ref_volt[2][MSM8998_KBSS_FUSE_CORNERS] = { #define MSM8998_KBSS_PERFORMANCE_AGING_SENSOR_ID 0 #define MSM8998_KBSS_PERFORMANCE_AGING_BYPASS_MASK0 0 +/* + * sdm660 configuration + */ +#define SDM660_KBSS_POWER_CPR_SENSOR_COUNT 6 +#define SDM660_KBSS_PERFORMANCE_CPR_SENSOR_COUNT 9 + +#define SDM660_KBSS_POWER_TEMP_SENSOR_ID_START 10 +#define SDM660_KBSS_POWER_TEMP_SENSOR_ID_END 11 +#define SDM660_KBSS_PERFORMANCE_TEMP_SENSOR_ID_START 4 +#define SDM660_KBSS_PERFORMANCE_TEMP_SENSOR_ID_END 9 + +#define SDM660_KBSS_POWER_AGING_SENSOR_ID 0 +#define SDM660_KBSS_POWER_AGING_BYPASS_MASK0 0 + +#define SDM660_KBSS_PERFORMANCE_AGING_SENSOR_ID 0 +#define SDM660_KBSS_PERFORMANCE_AGING_BYPASS_MASK0 0 + +/* + * SOC IDs + */ +enum soc_id { + MSM8998_V1_SOC_ID = 1, + MSM8998_V2_SOC_ID = 2, + SDM660_SOC_ID = 3, +}; + /** - * cprh_msm8998_kbss_read_fuse_data() - load KBSS specific fuse parameter values + * cprh_msm8998_kbss_read_fuse_data() - load msm8998 KBSS specific fuse + * parameter values * @vreg: Pointer to the CPR3 regulator + * @fuse: KBSS specific fuse data * - * This function allocates a cprh_msm8998_kbss_fuses struct, fills it with - * values read out of hardware fuses, and finally copies common fuse values - * into the CPR3 regulator struct. + * This function fills cprh_kbss_fuses struct with values read out of hardware + * fuses. * * Return: 0 on success, errno on failure */ -static int cprh_msm8998_kbss_read_fuse_data(struct cpr3_regulator *vreg) +static int cprh_msm8998_kbss_read_fuse_data(struct cpr3_regulator *vreg, + struct cprh_kbss_fuses *fuse) { void __iomem *base = vreg->thread->ctrl->fuse_base; - struct cprh_msm8998_kbss_fuses *fuse; int i, id, rc; - fuse = devm_kzalloc(vreg->thread->ctrl->dev, sizeof(*fuse), GFP_KERNEL); - if (!fuse) - return -ENOMEM; - - rc = cpr3_read_fuse_param(base, msm8998_kbss_speed_bin_param, - &fuse->speed_bin); - if (rc) { - cpr3_err(vreg, "Unable to read speed bin fuse, rc=%d\n", rc); - return rc; - } - cpr3_info(vreg, "speed bin = %llu\n", fuse->speed_bin); - rc = cpr3_read_fuse_param(base, msm8998_cpr_fusing_rev_param, &fuse->cpr_fusing_rev); if (rc) { @@ -305,7 +468,6 @@ static int cprh_msm8998_kbss_read_fuse_data(struct cpr3_regulator *vreg) cpr3_info(vreg, "CPR fusing revision = %llu\n", fuse->cpr_fusing_rev); id = vreg->thread->ctrl->ctrl_id; - for (i = 0; i < MSM8998_KBSS_FUSE_CORNERS; i++) { rc = cpr3_read_fuse_param(base, msm8998_kbss_init_voltage_param[id][i], @@ -355,8 +517,8 @@ static int cprh_msm8998_kbss_read_fuse_data(struct cpr3_regulator *vreg) } rc = cpr3_read_fuse_param(base, - msm8998_cpr_force_highest_corner_param, - &fuse->force_highest_corner); + msm8998_cpr_force_highest_corner_param, + &fuse->force_highest_corner); if (rc) { cpr3_err(vreg, "Unable to read CPR force highest corner fuse, rc=%d\n", rc); @@ -373,9 +535,174 @@ static int cprh_msm8998_kbss_read_fuse_data(struct cpr3_regulator *vreg) return -EINVAL; } + return rc; +}; + +/** + * cprh_sdm660_kbss_read_fuse_data() - load SDM660 KBSS specific fuse parameter + * values + * @vreg: Pointer to the CPR3 regulator + * @fuse: KBSS specific fuse data + * + * This function fills cprh_kbss_fuses struct with values read out of hardware + * fuses. + * + * Return: 0 on success, errno on failure + */ +static int cprh_sdm660_kbss_read_fuse_data(struct cpr3_regulator *vreg, + struct cprh_kbss_fuses *fuse) +{ + void __iomem *base = vreg->thread->ctrl->fuse_base; + int i, id, rc; + + rc = cpr3_read_fuse_param(base, sdm660_cpr_fusing_rev_param, + &fuse->cpr_fusing_rev); + if (rc) { + cpr3_err(vreg, "Unable to read CPR fusing revision fuse, rc=%d\n", + rc); + return rc; + } + cpr3_info(vreg, "CPR fusing revision = %llu\n", fuse->cpr_fusing_rev); + + id = vreg->thread->ctrl->ctrl_id; + for (i = 0; i < SDM660_KBSS_FUSE_CORNERS; i++) { + rc = cpr3_read_fuse_param(base, + sdm660_kbss_init_voltage_param[id][i], + &fuse->init_voltage[i]); + if (rc) { + cpr3_err(vreg, "Unable to read fuse-corner %d initial voltage fuse, rc=%d\n", + i, rc); + return rc; + } + + rc = cpr3_read_fuse_param(base, + sdm660_kbss_target_quot_param[id][i], + &fuse->target_quot[i]); + if (rc) { + cpr3_err(vreg, "Unable to read fuse-corner %d target quotient fuse, rc=%d\n", + i, rc); + return rc; + } + + rc = cpr3_read_fuse_param(base, + sdm660_kbss_ro_sel_param[id][i], + &fuse->ro_sel[i]); + if (rc) { + cpr3_err(vreg, "Unable to read fuse-corner %d RO select fuse, rc=%d\n", + i, rc); + return rc; + } + + rc = cpr3_read_fuse_param(base, + sdm660_kbss_quot_offset_param[id][i], + &fuse->quot_offset[i]); + if (rc) { + cpr3_err(vreg, "Unable to read fuse-corner %d quotient offset fuse, rc=%d\n", + i, rc); + return rc; + } + } + + rc = cpr3_read_fuse_param(base, + sdm660_kbss_aging_init_quot_diff_param[id], + &fuse->aging_init_quot_diff); + if (rc) { + cpr3_err(vreg, "Unable to read aging initial quotient difference fuse, rc=%d\n", + rc); + return rc; + } + + vreg->fuse_combo = fuse->cpr_fusing_rev + 8 * fuse->speed_bin; + if (vreg->fuse_combo >= CPRH_SDM660_KBSS_FUSE_COMBO_COUNT) { + cpr3_err(vreg, "invalid CPR fuse combo = %d found\n", + vreg->fuse_combo); + return -EINVAL; + } + + return rc; +}; + +/** + * cprh_kbss_read_fuse_data() - load KBSS specific fuse parameter values + * @vreg: Pointer to the CPR3 regulator + * + * This function allocates a cprh_kbss_fuses struct, fills it with values + * read out of hardware fuses, and finally copies common fuse values + * into the CPR3 regulator struct. + * + * Return: 0 on success, errno on failure + */ +static int cprh_kbss_read_fuse_data(struct cpr3_regulator *vreg) +{ + void __iomem *base = vreg->thread->ctrl->fuse_base; + struct cprh_kbss_fuses *fuse; + int rc, fuse_corners; + enum soc_id soc_revision; + + fuse = devm_kzalloc(vreg->thread->ctrl->dev, sizeof(*fuse), GFP_KERNEL); + if (!fuse) + return -ENOMEM; + + soc_revision = vreg->thread->ctrl->soc_revision; + switch (soc_revision) { + case SDM660_SOC_ID: + fuse_corners = SDM660_KBSS_FUSE_CORNERS; + break; + case MSM8998_V1_SOC_ID: + case MSM8998_V2_SOC_ID: + fuse_corners = MSM8998_KBSS_FUSE_CORNERS; + break; + default: + cpr3_err(vreg, "unsupported soc id = %d\n", soc_revision); + return -EINVAL; + } + + fuse->ro_sel = devm_kcalloc(vreg->thread->ctrl->dev, fuse_corners, + sizeof(*fuse->ro_sel), GFP_KERNEL); + fuse->init_voltage = devm_kcalloc(vreg->thread->ctrl->dev, fuse_corners, + sizeof(*fuse->init_voltage), GFP_KERNEL); + fuse->target_quot = devm_kcalloc(vreg->thread->ctrl->dev, fuse_corners, + sizeof(*fuse->target_quot), GFP_KERNEL); + fuse->quot_offset = devm_kcalloc(vreg->thread->ctrl->dev, fuse_corners, + sizeof(*fuse->quot_offset), GFP_KERNEL); + + if (!fuse->ro_sel || !fuse->init_voltage || !fuse->target_quot + || !fuse->quot_offset) + return -ENOMEM; + + rc = cpr3_read_fuse_param(base, kbss_speed_bin_param, &fuse->speed_bin); + if (rc) { + cpr3_err(vreg, "Unable to read speed bin fuse, rc=%d\n", rc); + return rc; + } + cpr3_info(vreg, "speed bin = %llu\n", fuse->speed_bin); + + switch (soc_revision) { + case SDM660_SOC_ID: + rc = cprh_sdm660_kbss_read_fuse_data(vreg, fuse); + if (rc) { + cpr3_err(vreg, "sdm660 kbss fuse data read failed, rc=%d\n", + rc); + return rc; + } + break; + case MSM8998_V1_SOC_ID: + case MSM8998_V2_SOC_ID: + rc = cprh_msm8998_kbss_read_fuse_data(vreg, fuse); + if (rc) { + cpr3_err(vreg, "msm8998 kbss fuse data read failed, rc=%d\n", + rc); + return rc; + } + break; + default: + cpr3_err(vreg, "unsupported soc id = %d\n", soc_revision); + return -EINVAL; + } + vreg->speed_bin_fuse = fuse->speed_bin; vreg->cpr_rev_fuse = fuse->cpr_fusing_rev; - vreg->fuse_corner_count = MSM8998_KBSS_FUSE_CORNERS; + vreg->fuse_corner_count = fuse_corners; vreg->platform_fuses = fuse; return 0; @@ -399,13 +726,13 @@ static int cprh_kbss_parse_corner_data(struct cpr3_regulator *vreg) } /* - * A total of MSM8998_KBSS_MAX_CORNER_COUNT - 1 corners + * A total of CPRH_KBSS_MAX_CORNER_COUNT - 1 corners * may be specified in device tree as an additional corner * must be allocated to correspond to the APM crossover voltage. */ - if (vreg->corner_count > MSM8998_KBSS_MAX_CORNER_COUNT - 1) { + if (vreg->corner_count > CPRH_KBSS_MAX_CORNER_COUNT - 1) { cpr3_err(vreg, "corner count %d exceeds supported maximum %d\n", - vreg->corner_count, MSM8998_KBSS_MAX_CORNER_COUNT - 1); + vreg->corner_count, CPRH_KBSS_MAX_CORNER_COUNT - 1); return -EINVAL; } @@ -413,7 +740,7 @@ static int cprh_kbss_parse_corner_data(struct cpr3_regulator *vreg) } /** - * cprh_msm8998_kbss_calculate_open_loop_voltages() - calculate the open-loop + * cprh_kbss_calculate_open_loop_voltages() - calculate the open-loop * voltage for each corner of a CPR3 regulator * @vreg: Pointer to the CPR3 regulator * @@ -429,17 +756,18 @@ static int cprh_kbss_parse_corner_data(struct cpr3_regulator *vreg) * * Return: 0 on success, errno on failure */ -static int cprh_msm8998_kbss_calculate_open_loop_voltages( - struct cpr3_regulator *vreg) +static int cprh_kbss_calculate_open_loop_voltages(struct cpr3_regulator *vreg) { struct device_node *node = vreg->of_node; - struct cprh_msm8998_kbss_fuses *fuse = vreg->platform_fuses; - int i, j, soc_revision, id, rc = 0; + struct cprh_kbss_fuses *fuse = vreg->platform_fuses; + int i, j, id, rc = 0; bool allow_interpolation; u64 freq_low, volt_low, freq_high, volt_high; const int *ref_volt; int *fuse_volt; int *fmax_corner; + const char * const *corner_name; + enum soc_id soc_revision; fuse_volt = kcalloc(vreg->fuse_corner_count, sizeof(*fuse_volt), GFP_KERNEL); @@ -452,20 +780,36 @@ static int cprh_msm8998_kbss_calculate_open_loop_voltages( id = vreg->thread->ctrl->ctrl_id; soc_revision = vreg->thread->ctrl->soc_revision; - if (soc_revision == 1) + + switch (soc_revision) { + case SDM660_SOC_ID: + ref_volt = sdm660_kbss_fuse_ref_volt[id]; + if (id == CPRH_KBSS_POWER_CLUSTER_ID) + corner_name = cprh_sdm660_power_kbss_fuse_corner_name; + else + corner_name = cprh_sdm660_perf_kbss_fuse_corner_name; + break; + case MSM8998_V1_SOC_ID: ref_volt = msm8998_v1_kbss_fuse_ref_volt; - else + corner_name = cprh_msm8998_kbss_fuse_corner_name; + break; + case MSM8998_V2_SOC_ID: ref_volt = msm8998_v2_kbss_fuse_ref_volt[id]; + corner_name = cprh_msm8998_kbss_fuse_corner_name; + break; + default: + cpr3_err(vreg, "unsupported soc id = %d\n", soc_revision); + rc = -EINVAL; + goto done; + } for (i = 0; i < vreg->fuse_corner_count; i++) { - fuse_volt[i] = cpr3_convert_open_loop_voltage_fuse( - ref_volt[i], - MSM8998_KBSS_FUSE_STEP_VOLT, fuse->init_voltage[i], - MSM8998_KBSS_VOLTAGE_FUSE_SIZE); + fuse_volt[i] = cpr3_convert_open_loop_voltage_fuse(ref_volt[i], + CPRH_KBSS_FUSE_STEP_VOLT, fuse->init_voltage[i], + CPRH_KBSS_VOLTAGE_FUSE_SIZE); /* Log fused open-loop voltage values for debugging purposes. */ - cpr3_info(vreg, "fused %8s: open-loop=%7d uV\n", - cprh_msm8998_kbss_fuse_corner_name[i], + cpr3_info(vreg, "fused %8s: open-loop=%7d uV\n", corner_name[i], fuse_volt[i]); } @@ -563,7 +907,7 @@ done: */ static int cprh_msm8998_partial_binning_override(struct cpr3_regulator *vreg) { - struct cprh_msm8998_kbss_fuses *fuse = vreg->platform_fuses; + struct cprh_kbss_fuses *fuse = vreg->platform_fuses; struct cpr3_corner *corner; struct cpr4_sdelta *sdelta; int i; @@ -659,11 +1003,11 @@ static int cprh_kbss_parse_core_count_temp_adj_properties( kfree(combo_corner_bands); if (vreg->corner_band_count <= 0 || - vreg->corner_band_count > MSM8998_KBSS_MAX_CORNER_BAND_COUNT || + vreg->corner_band_count > CPRH_KBSS_MAX_CORNER_BAND_COUNT || vreg->corner_band_count > vreg->corner_count) { cpr3_err(vreg, "invalid corner band count %d > %d (max) for %d corners\n", vreg->corner_band_count, - MSM8998_KBSS_MAX_CORNER_BAND_COUNT, + CPRH_KBSS_MAX_CORNER_BAND_COUNT, vreg->corner_count); return -EINVAL; } @@ -761,9 +1105,9 @@ static int cprh_kbss_parse_core_count_temp_adj_properties( temp_point_count = len / sizeof(u32); if (temp_point_count <= 0 || temp_point_count > - MSM8998_KBSS_MAX_TEMP_POINTS) { + CPRH_KBSS_MAX_TEMP_POINTS) { cpr3_err(ctrl, "invalid number of temperature points %d > %d (max)\n", - temp_point_count, MSM8998_KBSS_MAX_TEMP_POINTS); + temp_point_count, CPRH_KBSS_MAX_TEMP_POINTS); rc = -EINVAL; goto free_temp; } @@ -811,18 +1155,35 @@ static int cprh_kbss_parse_core_count_temp_adj_properties( goto free_temp; } - ctrl->temp_sensor_id_start = ctrl->ctrl_id == - MSM8998_KBSS_POWER_CLUSTER_ID - ? MSM8998_KBSS_POWER_TEMP_SENSOR_ID_START : - MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_START; - ctrl->temp_sensor_id_end = ctrl->ctrl_id == - MSM8998_KBSS_POWER_CLUSTER_ID - ? MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_START : - MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_END; + switch (ctrl->soc_revision) { + case SDM660_SOC_ID: + ctrl->temp_sensor_id_start = ctrl->ctrl_id == + CPRH_KBSS_POWER_CLUSTER_ID + ? SDM660_KBSS_POWER_TEMP_SENSOR_ID_START : + SDM660_KBSS_PERFORMANCE_TEMP_SENSOR_ID_START; + ctrl->temp_sensor_id_end = ctrl->ctrl_id == + CPRH_KBSS_POWER_CLUSTER_ID + ? SDM660_KBSS_POWER_TEMP_SENSOR_ID_END : + SDM660_KBSS_PERFORMANCE_TEMP_SENSOR_ID_END; + break; + case MSM8998_V1_SOC_ID: + case MSM8998_V2_SOC_ID: + ctrl->temp_sensor_id_start = ctrl->ctrl_id == + CPRH_KBSS_POWER_CLUSTER_ID + ? MSM8998_KBSS_POWER_TEMP_SENSOR_ID_START : + MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_START; + ctrl->temp_sensor_id_end = ctrl->ctrl_id == + CPRH_KBSS_POWER_CLUSTER_ID + ? MSM8998_KBSS_POWER_TEMP_SENSOR_ID_END : + MSM8998_KBSS_PERFORMANCE_TEMP_SENSOR_ID_END; + break; + default: + cpr3_err(ctrl, "unsupported soc id = %d\n", ctrl->soc_revision); + rc = -EINVAL; + goto free_temp; + } ctrl->allow_temp_adj = true; - return 0; - free_temp: kfree(temp); @@ -906,8 +1267,8 @@ static int cprh_kbss_mem_acc_crossover_as_corner(struct cpr3_regulator *vreg) } /** - * cprh_msm8998_kbss_set_no_interpolation_quotients() - use the fused target - * quotient values for lower frequencies. + * cprh_kbss_set_no_interpolation_quotients() - use the fused target quotient + * values for lower frequencies. * @vreg: Pointer to the CPR3 regulator * @volt_adjust: Pointer to array of per-corner closed-loop adjustment * voltages @@ -918,11 +1279,10 @@ static int cprh_kbss_mem_acc_crossover_as_corner(struct cpr3_regulator *vreg) * * Return: 0 on success, errno on failure */ -static int cprh_msm8998_kbss_set_no_interpolation_quotients( - struct cpr3_regulator *vreg, int *volt_adjust, - int *volt_adjust_fuse, int *ro_scale) +static int cprh_kbss_set_no_interpolation_quotients(struct cpr3_regulator *vreg, + int *volt_adjust, int *volt_adjust_fuse, int *ro_scale) { - struct cprh_msm8998_kbss_fuses *fuse = vreg->platform_fuses; + struct cprh_kbss_fuses *fuse = vreg->platform_fuses; u32 quot, ro; int quot_adjust; int i, fuse_corner; @@ -949,7 +1309,7 @@ static int cprh_msm8998_kbss_set_no_interpolation_quotients( } /** - * cprh_msm8998_kbss_calculate_target_quotients() - calculate the CPR target + * cprh_kbss_calculate_target_quotients() - calculate the CPR target * quotient for each corner of a CPR3 regulator * @vreg: Pointer to the CPR3 regulator * @@ -965,10 +1325,9 @@ static int cprh_msm8998_kbss_set_no_interpolation_quotients( * * Return: 0 on success, errno on failure */ -static int cprh_msm8998_kbss_calculate_target_quotients( - struct cpr3_regulator *vreg) +static int cprh_kbss_calculate_target_quotients(struct cpr3_regulator *vreg) { - struct cprh_msm8998_kbss_fuses *fuse = vreg->platform_fuses; + struct cprh_kbss_fuses *fuse = vreg->platform_fuses; int rc; bool allow_interpolation; u64 freq_low, freq_high, prev_quot; @@ -978,18 +1337,49 @@ static int cprh_msm8998_kbss_calculate_target_quotients( int i, j, fuse_corner, quot_adjust; int *fmax_corner; int *volt_adjust, *volt_adjust_fuse, *ro_scale; + int lowest_fuse_corner, highest_fuse_corner; + const char * const *corner_name; + + switch (vreg->thread->ctrl->soc_revision) { + case SDM660_SOC_ID: + if (vreg->thread->ctrl->ctrl_id == CPRH_KBSS_POWER_CLUSTER_ID) { + corner_name = cprh_sdm660_power_kbss_fuse_corner_name; + lowest_fuse_corner = + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_LOWSVS; + highest_fuse_corner = + CPRH_SDM660_POWER_KBSS_FUSE_CORNER_TURBO_L1; + } else { + corner_name = cprh_sdm660_perf_kbss_fuse_corner_name; + lowest_fuse_corner = + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_SVS; + highest_fuse_corner = + CPRH_SDM660_PERF_KBSS_FUSE_CORNER_TURBO_L2; + } + break; + case MSM8998_V1_SOC_ID: + case MSM8998_V2_SOC_ID: + corner_name = cprh_msm8998_kbss_fuse_corner_name; + lowest_fuse_corner = + CPRH_MSM8998_KBSS_FUSE_CORNER_LOWSVS; + highest_fuse_corner = + CPRH_MSM8998_KBSS_FUSE_CORNER_TURBO_L1; + break; + default: + cpr3_err(vreg, "unsupported soc id = %d\n", + vreg->thread->ctrl->soc_revision); + return -EINVAL; + } /* Log fused quotient values for debugging purposes. */ - cpr3_info(vreg, "fused LowSVS: quot[%2llu]=%4llu\n", - fuse->ro_sel[CPRH_MSM8998_KBSS_FUSE_CORNER_LOWSVS], - fuse->target_quot[CPRH_MSM8998_KBSS_FUSE_CORNER_LOWSVS]); - for (i = CPRH_MSM8998_KBSS_FUSE_CORNER_SVS; - i <= CPRH_MSM8998_KBSS_FUSE_CORNER_TURBO_L1; i++) + cpr3_info(vreg, "fused %8s: quot[%2llu]=%4llu\n", + corner_name[lowest_fuse_corner], + fuse->ro_sel[lowest_fuse_corner], + fuse->target_quot[lowest_fuse_corner]); + for (i = lowest_fuse_corner + 1; i <= highest_fuse_corner; i++) cpr3_info(vreg, "fused %8s: quot[%2llu]=%4llu, quot_offset[%2llu]=%4llu\n", - cprh_msm8998_kbss_fuse_corner_name[i], - fuse->ro_sel[i], fuse->target_quot[i], + corner_name[i], fuse->ro_sel[i], fuse->target_quot[i], fuse->ro_sel[i], fuse->quot_offset[i] * - MSM8998_KBSS_QUOT_OFFSET_SCALE); + CPRH_KBSS_QUOT_OFFSET_SCALE); allow_interpolation = of_property_read_bool(vreg->of_node, "qcom,allow-quotient-interpolation"); @@ -1022,8 +1412,8 @@ static int cprh_msm8998_kbss_calculate_target_quotients( if (!allow_interpolation) { /* Use fused target quotients for lower frequencies. */ - return cprh_msm8998_kbss_set_no_interpolation_quotients( - vreg, volt_adjust, volt_adjust_fuse, ro_scale); + return cprh_kbss_set_no_interpolation_quotients(vreg, + volt_adjust, volt_adjust_fuse, ro_scale); } /* Determine highest corner mapped to each fuse corner */ @@ -1044,7 +1434,7 @@ static int cprh_msm8998_kbss_calculate_target_quotients( * Interpolation is not possible for corners mapped to the lowest fuse * corner so use the fuse corner value directly. */ - i = CPRH_MSM8998_KBSS_FUSE_CORNER_LOWSVS; + i = lowest_fuse_corner; quot_adjust = cpr3_quot_adjustment(ro_scale[i], volt_adjust_fuse[i]); quot = fuse->target_quot[i] + quot_adjust; quot_high[i] = quot_low[i] = quot; @@ -1053,19 +1443,17 @@ static int cprh_msm8998_kbss_calculate_target_quotients( cpr3_debug(vreg, "adjusted fuse corner %d RO%u target quot: %llu --> %u (%d uV)\n", i, ro, fuse->target_quot[i], quot, volt_adjust_fuse[i]); - for (i = 0; i <= fmax_corner[CPRH_MSM8998_KBSS_FUSE_CORNER_LOWSVS]; - i++) + for (i = 0; i <= fmax_corner[lowest_fuse_corner]; i++) vreg->corner[i].target_quot[ro] = quot; - for (i = CPRH_MSM8998_KBSS_FUSE_CORNER_SVS; - i < vreg->fuse_corner_count; i++) { + for (i = lowest_fuse_corner + 1; i < vreg->fuse_corner_count; i++) { quot_high[i] = fuse->target_quot[i]; if (fuse->ro_sel[i] == fuse->ro_sel[i - 1]) quot_low[i] = quot_high[i - 1]; else quot_low[i] = quot_high[i] - fuse->quot_offset[i] - * MSM8998_KBSS_QUOT_OFFSET_SCALE; + * CPRH_KBSS_QUOT_OFFSET_SCALE; if (quot_high[i] < quot_low[i]) { cpr3_debug(vreg, "quot_high[%d]=%llu < quot_low[%d]=%llu; overriding: quot_high[%d]=%llu\n", i, quot_high[i], i, quot_low[i], @@ -1203,10 +1591,10 @@ static int cprh_kbss_init_thread(struct cpr3_thread *thread) */ static int cprh_kbss_init_regulator(struct cpr3_regulator *vreg) { - struct cprh_msm8998_kbss_fuses *fuse; + struct cprh_kbss_fuses *fuse; int rc; - rc = cprh_msm8998_kbss_read_fuse_data(vreg); + rc = cprh_kbss_read_fuse_data(vreg); if (rc) { cpr3_err(vreg, "unable to read CPR fuse data, rc=%d\n", rc); return rc; @@ -1221,7 +1609,7 @@ static int cprh_kbss_init_regulator(struct cpr3_regulator *vreg) return rc; } - rc = cprh_msm8998_kbss_calculate_open_loop_voltages(vreg); + rc = cprh_kbss_calculate_open_loop_voltages(vreg); if (rc) { cpr3_err(vreg, "unable to calculate open-loop voltages, rc=%d\n", rc); @@ -1246,7 +1634,7 @@ static int cprh_kbss_init_regulator(struct cpr3_regulator *vreg) return rc; } - rc = cprh_msm8998_kbss_calculate_target_quotients(vreg); + rc = cprh_kbss_calculate_target_quotients(vreg); if (rc) { cpr3_err(vreg, "unable to calculate target quotients, rc=%d\n", rc); @@ -1269,7 +1657,7 @@ static int cprh_kbss_init_regulator(struct cpr3_regulator *vreg) if (vreg->allow_core_count_adj && (vreg->max_core_count <= 0 || vreg->max_core_count > - MSM8998_KBSS_CPR_SDELTA_CORE_COUNT)) { + CPRH_KBSS_CPR_SDELTA_CORE_COUNT)) { cpr3_err(vreg, "qcom,max-core-count has invalid value = %d\n", vreg->max_core_count); return -EINVAL; @@ -1310,10 +1698,10 @@ static int cprh_kbss_init_regulator(struct cpr3_regulator *vreg) */ static int cprh_kbss_init_aging(struct cpr3_controller *ctrl) { - struct cprh_msm8998_kbss_fuses *fuse = NULL; + struct cprh_kbss_fuses *fuse = NULL; struct cpr3_regulator *vreg; u32 aging_ro_scale; - int i, j, rc; + int i, j, rc = 0; for (i = 0; i < ctrl->thread_count; i++) { for (j = 0; j < ctrl->thread[i].vreg_count; j++) { @@ -1344,28 +1732,51 @@ static int cprh_kbss_init_aging(struct cpr3_controller *ctrl) ctrl->aging_complete_vdd_mode = REGULATOR_MODE_IDLE; ctrl->aging_sensor_count = 1; - ctrl->aging_sensor = kzalloc(sizeof(*ctrl->aging_sensor), GFP_KERNEL); + ctrl->aging_sensor = devm_kzalloc(ctrl->dev, + sizeof(*ctrl->aging_sensor), + GFP_KERNEL); if (!ctrl->aging_sensor) return -ENOMEM; - if (ctrl->ctrl_id == MSM8998_KBSS_POWER_CLUSTER_ID) { - ctrl->aging_sensor->sensor_id - = MSM8998_KBSS_POWER_AGING_SENSOR_ID; - ctrl->aging_sensor->bypass_mask[0] - = MSM8998_KBSS_POWER_AGING_BYPASS_MASK0; - } else { - ctrl->aging_sensor->sensor_id - = MSM8998_KBSS_PERFORMANCE_AGING_SENSOR_ID; - ctrl->aging_sensor->bypass_mask[0] - = MSM8998_KBSS_PERFORMANCE_AGING_BYPASS_MASK0; + switch (ctrl->soc_revision) { + case SDM660_SOC_ID: + if (ctrl->ctrl_id == CPRH_KBSS_POWER_CLUSTER_ID) { + ctrl->aging_sensor->sensor_id + = SDM660_KBSS_POWER_AGING_SENSOR_ID; + ctrl->aging_sensor->bypass_mask[0] + = SDM660_KBSS_POWER_AGING_BYPASS_MASK0; + } else { + ctrl->aging_sensor->sensor_id + = SDM660_KBSS_PERFORMANCE_AGING_SENSOR_ID; + ctrl->aging_sensor->bypass_mask[0] + = SDM660_KBSS_PERFORMANCE_AGING_BYPASS_MASK0; + } + break; + case MSM8998_V1_SOC_ID: + case MSM8998_V2_SOC_ID: + if (ctrl->ctrl_id == CPRH_KBSS_POWER_CLUSTER_ID) { + ctrl->aging_sensor->sensor_id + = MSM8998_KBSS_POWER_AGING_SENSOR_ID; + ctrl->aging_sensor->bypass_mask[0] + = MSM8998_KBSS_POWER_AGING_BYPASS_MASK0; + } else { + ctrl->aging_sensor->sensor_id + = MSM8998_KBSS_PERFORMANCE_AGING_SENSOR_ID; + ctrl->aging_sensor->bypass_mask[0] + = MSM8998_KBSS_PERFORMANCE_AGING_BYPASS_MASK0; + } + break; + default: + cpr3_err(ctrl, "unsupported soc id = %d\n", ctrl->soc_revision); + return -EINVAL; } ctrl->aging_sensor->ro_scale = aging_ro_scale; ctrl->aging_sensor->init_quot_diff = cpr3_convert_open_loop_voltage_fuse(0, - MSM8998_KBSS_AGING_INIT_QUOT_DIFF_SCALE, + CPRH_KBSS_AGING_INIT_QUOT_DIFF_SCALE, fuse->aging_init_quot_diff, - MSM8998_KBSS_AGING_INIT_QUOT_DIFF_SIZE); + CPRH_KBSS_AGING_INIT_QUOT_DIFF_SIZE); cpr3_debug(ctrl, "sensor %u aging init quotient diff = %d, aging RO scale = %u QUOT/V\n", ctrl->aging_sensor->sensor_id, @@ -1403,8 +1814,8 @@ static int cprh_kbss_init_controller(struct cpr3_controller *ctrl) return rc; } - if (ctrl->ctrl_id < MSM8998_KBSS_MIN_CONTROLLER_ID || - ctrl->ctrl_id > MSM8998_KBSS_MAX_CONTROLLER_ID) { + if (ctrl->ctrl_id < CPRH_KBSS_MIN_CONTROLLER_ID || + ctrl->ctrl_id > CPRH_KBSS_MAX_CONTROLLER_ID) { cpr3_err(ctrl, "invalid qcom,cpr-controller-id specified\n"); return -EINVAL; } @@ -1503,9 +1914,28 @@ static int cprh_kbss_init_controller(struct cpr3_controller *ctrl) "qcom,cpr-corner-switch-delay-time", &ctrl->corner_switch_delay_time); - ctrl->sensor_count = ctrl->ctrl_id == MSM8998_KBSS_POWER_CLUSTER_ID ? - MSM8998_KBSS_POWER_CPR_SENSOR_COUNT : - MSM8998_KBSS_PERFORMANCE_CPR_SENSOR_COUNT; + switch (ctrl->soc_revision) { + case SDM660_SOC_ID: + if (ctrl->ctrl_id == CPRH_KBSS_POWER_CLUSTER_ID) + ctrl->sensor_count = + SDM660_KBSS_POWER_CPR_SENSOR_COUNT; + else + ctrl->sensor_count = + SDM660_KBSS_PERFORMANCE_CPR_SENSOR_COUNT; + break; + case MSM8998_V1_SOC_ID: + case MSM8998_V2_SOC_ID: + if (ctrl->ctrl_id == CPRH_KBSS_POWER_CLUSTER_ID) + ctrl->sensor_count = + MSM8998_KBSS_POWER_CPR_SENSOR_COUNT; + else + ctrl->sensor_count = + MSM8998_KBSS_PERFORMANCE_CPR_SENSOR_COUNT; + break; + default: + cpr3_err(ctrl, "unsupported soc id = %d\n", ctrl->soc_revision); + return -EINVAL; + } /* * KBSS only has one thread (0) per controller so the zeroed @@ -1516,7 +1946,7 @@ static int cprh_kbss_init_controller(struct cpr3_controller *ctrl) if (!ctrl->sensor_owner) return -ENOMEM; - ctrl->cpr_clock_rate = MSM8998_KBSS_CPR_CLOCK_RATE; + ctrl->cpr_clock_rate = CPRH_KBSS_CPR_CLOCK_RATE; ctrl->supports_hw_closed_loop = true; ctrl->use_hw_closed_loop = of_property_read_bool(ctrl->dev->of_node, "qcom,cpr-hw-closed-loop"); @@ -1580,15 +2010,19 @@ static int cprh_kbss_regulator_resume(struct platform_device *pdev) static struct of_device_id cprh_regulator_match_table[] = { { .compatible = "qcom,cprh-msm8998-v1-kbss-regulator", - .data = (void *)(uintptr_t)1 + .data = (void *)(uintptr_t)MSM8998_V1_SOC_ID, }, { .compatible = "qcom,cprh-msm8998-v2-kbss-regulator", - .data = (void *)(uintptr_t)2 + .data = (void *)(uintptr_t)MSM8998_V2_SOC_ID, }, { .compatible = "qcom,cprh-msm8998-kbss-regulator", - .data = (void *)(uintptr_t)2 + .data = (void *)(uintptr_t)MSM8998_V2_SOC_ID, + }, + { + .compatible = "qcom,cprh-sdm660-kbss-regulator", + .data = (void *)(uintptr_t)SDM660_SOC_ID, }, {} }; diff --git a/drivers/soc/qcom/Kconfig b/drivers/soc/qcom/Kconfig index 21733633cb6c..281e83d90970 100644 --- a/drivers/soc/qcom/Kconfig +++ b/drivers/soc/qcom/Kconfig @@ -483,6 +483,15 @@ config PANIC_ON_GLADIATOR_ERROR_V2 If unsure, say N. +config MSM_GLADIATOR_ERROR_V2_MAIN_LOGGER_ONLY + depends on MSM_GLADIATOR_ERP_V2 + bool "QCOM Gladiator error v2 main logger support only" + help + Gladiator has two error loggers to report error captured. + By default, two error loggers will both be enabled. + This option enables only the main error logger. + If unsure, say no + config MSM_GLADIATOR_HANG_DETECT tristate "MSM Gladiator Hang Detection Support" help diff --git a/drivers/soc/qcom/gladiator_erp_v2.c b/drivers/soc/qcom/gladiator_erp_v2.c index 91b5d39be242..256b1a4fcdd5 100644 --- a/drivers/soc/qcom/gladiator_erp_v2.c +++ b/drivers/soc/qcom/gladiator_erp_v2.c @@ -23,6 +23,11 @@ #include <linux/clk.h> #define MODULE_NAME "gladiator-v2_error_reporting" +#ifdef CONFIG_MSM_GLADIATOR_ERROR_V2_MAIN_LOGGER_ONLY +#define OBSERVER_ERROR_ENABLE 0 +#else +#define OBSERVER_ERROR_ENABLE 1 +#endif /* Register Offsets */ #define GLADIATOR_ID_COREID 0x0 @@ -733,7 +738,8 @@ static int parse_dt_node(struct platform_device *pdev, static inline void gladiator_irq_init(void __iomem *gladiator_virt_base) { writel_relaxed(1, gladiator_virt_base + GLADIATOR_FAULTEN); - writel_relaxed(1, gladiator_virt_base + OBSERVER_0_FAULTEN); + writel_relaxed(OBSERVER_ERROR_ENABLE, + gladiator_virt_base + OBSERVER_0_FAULTEN); } #define CCI_LEVEL 2 diff --git a/drivers/soc/qcom/msm_glink_pkt.c b/drivers/soc/qcom/msm_glink_pkt.c index 9ebc6a3c23c9..78f6a2aa8f66 100644 --- a/drivers/soc/qcom/msm_glink_pkt.c +++ b/drivers/soc/qcom/msm_glink_pkt.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -502,13 +502,21 @@ static void glink_pkt_queue_rx_intent_worker(struct work_struct *work) struct queue_rx_intent_work, work); struct glink_pkt_dev *devp = work_item->devp; - if (!devp || !devp->handle) { + if (!devp) { + GLINK_PKT_ERR("%s: Invalid device\n", __func__); + kfree(work_item); + return; + } + mutex_lock(&devp->ch_lock); + if (!devp->handle) { GLINK_PKT_ERR("%s: Invalid device Handle\n", __func__); + mutex_unlock(&devp->ch_lock); kfree(work_item); return; } ret = glink_queue_rx_intent(devp->handle, devp, work_item->intent_size); + mutex_unlock(&devp->ch_lock); GLINK_PKT_INFO("%s: Triggered with size[%zu] ret[%d]\n", __func__, work_item->intent_size, ret); if (ret) @@ -1051,6 +1059,27 @@ error: } /** + * pop_rx_pkt() - return first pkt from rx pkt_list + * devp: pointer to G-Link packet device. + * + * This function return first item from rx pkt_list and NULL if list is empty. + */ +struct glink_rx_pkt *pop_rx_pkt(struct glink_pkt_dev *devp) +{ + unsigned long flags; + struct glink_rx_pkt *pkt = NULL; + + spin_lock_irqsave(&devp->pkt_list_lock, flags); + if (!list_empty(&devp->pkt_list)) { + pkt = list_first_entry(&devp->pkt_list, + struct glink_rx_pkt, list); + list_del(&pkt->list); + } + spin_unlock_irqrestore(&devp->pkt_list_lock, flags); + return pkt; +} + +/** * glink_pkt_release() - release operation on glink_pkt device * inode: Pointer to the inode structure. * file: Pointer to the file structure. @@ -1064,6 +1093,7 @@ int glink_pkt_release(struct inode *inode, struct file *file) int ret = 0; struct glink_pkt_dev *devp = file->private_data; unsigned long flags; + struct glink_rx_pkt *pkt; GLINK_PKT_INFO("%s() on dev id:%d by [%s] ref_cnt[%d]\n", __func__, devp->i, current->comm, devp->ref_cnt); @@ -1072,9 +1102,14 @@ int glink_pkt_release(struct inode *inode, struct file *file) devp->ref_cnt--; if (devp->handle && devp->ref_cnt == 0) { + while ((pkt = pop_rx_pkt(devp))) { + glink_rx_done(devp->handle, pkt->data, false); + kfree(pkt); + } wake_up(&devp->ch_read_wait_queue); wake_up_interruptible(&devp->ch_opened_wait_queue); ret = glink_close(devp->handle); + devp->handle = NULL; if (ret) { GLINK_PKT_ERR("%s: close failed ret[%d]\n", __func__, ret); diff --git a/drivers/soc/qcom/msm_smem.c b/drivers/soc/qcom/msm_smem.c index 8f5ad7af8d0d..9c4d89ac704d 100644 --- a/drivers/soc/qcom/msm_smem.c +++ b/drivers/soc/qcom/msm_smem.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2013-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2013-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -375,7 +375,7 @@ static void *__smem_get_entry_secure(unsigned id, uint32_t a_hdr_size; int rc; - SMEM_DBG("%s(%u, %u, %u, %u, %d, %d)\n", __func__, id, *size, to_proc, + SMEM_DBG("%s(%u, %u, %u, %d, %d)\n", __func__, id, to_proc, flags, skip_init_check, use_rspinlock); if (!skip_init_check && !smem_initialized_check()) @@ -817,7 +817,7 @@ EXPORT_SYMBOL(smem_alloc); void *smem_get_entry(unsigned id, unsigned *size, unsigned to_proc, unsigned flags) { - SMEM_DBG("%s(%u, %u, %u, %u)\n", __func__, id, *size, to_proc, flags); + SMEM_DBG("%s(%u, %u, %u)\n", __func__, id, to_proc, flags); /* * Handle the circular dependecy between SMEM and software implemented diff --git a/drivers/soc/qcom/socinfo.c b/drivers/soc/qcom/socinfo.c index e79599d73a34..dd3e545eb7da 100644 --- a/drivers/soc/qcom/socinfo.c +++ b/drivers/soc/qcom/socinfo.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2009-2016, The Linux Foundation. All rights reserved. + * Copyright (c) 2009-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -538,9 +538,12 @@ static struct msm_soc_info cpu_of_id[] = { /* 660 ID */ [317] = {MSM_CPU_660, "SDM660"}, [324] = {MSM_CPU_660, "SDA660"}, + [325] = {MSM_CPU_660, "SDM658"}, + [326] = {MSM_CPU_660, "SDA658"}, /* 630 ID */ [318] = {MSM_CPU_630, "SDM630"}, + [327] = {MSM_CPU_630, "SDA630"}, /* Uninitialized IDs are not known to run Linux. MSM_CPU_UNKNOWN is set to 0 to ensure these IDs are @@ -1216,10 +1219,22 @@ static void * __init setup_dummy_socinfo(void) dummy_socinfo.id = 324; strlcpy(dummy_socinfo.build_id, "sda660 - ", sizeof(dummy_socinfo.build_id)); + } else if (early_machine_is_sdm658()) { + dummy_socinfo.id = 325; + strlcpy(dummy_socinfo.build_id, "sdm658 - ", + sizeof(dummy_socinfo.build_id)); + } else if (early_machine_is_sda658()) { + dummy_socinfo.id = 326; + strlcpy(dummy_socinfo.build_id, "sda658 - ", + sizeof(dummy_socinfo.build_id)); } else if (early_machine_is_sdm630()) { dummy_socinfo.id = 318; strlcpy(dummy_socinfo.build_id, "sdm630 - ", sizeof(dummy_socinfo.build_id)); + } else if (early_machine_is_sda630()) { + dummy_socinfo.id = 327; + strlcpy(dummy_socinfo.build_id, "sda630 - ", + sizeof(dummy_socinfo.build_id)); } else if (early_machine_is_apq8998()) { dummy_socinfo.id = 319; strlcpy(dummy_socinfo.build_id, "apq8998 - ", diff --git a/drivers/soc/qcom/spcom.c b/drivers/soc/qcom/spcom.c index e8ea99827403..9b71083e4f27 100644 --- a/drivers/soc/qcom/spcom.c +++ b/drivers/soc/qcom/spcom.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2015-2016, The Linux Foundation. All rights reserved. + * Copyright (c) 2015-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -274,6 +274,8 @@ static int spcom_open(struct spcom_channel *ch, unsigned int timeout_msec); static int spcom_close(struct spcom_channel *ch); static void spcom_notify_rx_abort(void *handle, const void *priv, const void *pkt_priv); +static struct spcom_channel *spcom_find_channel_by_name(const char *name); +static int spcom_unlock_ion_buf(struct spcom_channel *ch, int fd); /** * spcom_is_ready() - driver is initialized and ready. @@ -347,6 +349,9 @@ static int spcom_create_predefined_channels_chardev(void) static void spcom_link_state_notif_cb(struct glink_link_state_cb_info *cb_info, void *priv) { + struct spcom_channel *ch = NULL; + const char *ch_name = "sp_kernel"; + spcom_dev->link_state = cb_info->link_state; pr_debug("spcom_link_state_notif_cb called. transport = %s edge = %s\n", @@ -359,6 +364,17 @@ static void spcom_link_state_notif_cb(struct glink_link_state_cb_info *cb_info, break; case GLINK_LINK_STATE_DOWN: pr_err("GLINK_LINK_STATE_DOWN.\n"); + + /* + * Free all the SKP ION buffers that were locked + * for SPSS app swapping, when remote subsystem reset. + */ + pr_debug("Free all SKP ION buffers on SSR.\n"); + ch = spcom_find_channel_by_name(ch_name); + if (!ch) + pr_err("failed to find channel [%s].\n", ch_name); + else + spcom_unlock_ion_buf(ch, SPCOM_ION_FD_UNLOCK_ALL); break; default: pr_err("unknown link_state [%d].\n", cb_info->link_state); @@ -1643,24 +1659,18 @@ static int spcom_handle_lock_ion_buf_command(struct spcom_channel *ch, } /** - * spcom_handle_unlock_ion_buf_command() - Unlock an ION buffer. + * spcom_unlock_ion_buf() - Unlock an ION buffer. * * Unlock an ION buffer, let it be free, when it is no longer being used by * the remote subsystem. */ -static int spcom_handle_unlock_ion_buf_command(struct spcom_channel *ch, - void *cmd_buf, int size) +static int spcom_unlock_ion_buf(struct spcom_channel *ch, int fd) { - struct spcom_user_command *cmd = cmd_buf; - int fd = cmd->arg; struct ion_client *ion_client = spcom_dev->ion_client; int i; + bool found = false; - if (size != sizeof(*cmd)) { - pr_err("cmd size [%d] , expected [%d].\n", - (int) size, (int) sizeof(*cmd)); - return -EINVAL; - } + pr_debug("Unlock ion buf ch [%s] fd [%d].\n", ch->name, fd); /* Check ION client */ if (ion_client == NULL) { @@ -1669,6 +1679,8 @@ static int spcom_handle_unlock_ion_buf_command(struct spcom_channel *ch, } if (fd == (int) SPCOM_ION_FD_UNLOCK_ALL) { + pr_debug("unlocked ALL ion buf ch [%s].\n", ch->name); + found = true; /* unlock all ION buf */ for (i = 0 ; i < ARRAY_SIZE(ch->ion_handle_table) ; i++) { if (ch->ion_handle_table[i] != NULL) { @@ -1686,15 +1698,45 @@ static int spcom_handle_unlock_ion_buf_command(struct spcom_channel *ch, ch->ion_handle_table[i] = NULL; ch->ion_fd_table[i] = -1; pr_debug("unlocked ion buf#[%d].\n", i); + found = true; break; } } } + if (!found) { + pr_err("ch [%s] fd [%d] was not found.\n", ch->name, fd); + return -ENODEV; + } + return 0; } /** + * spcom_handle_unlock_ion_buf_command() - Unlock an ION buffer. + * + * Unlock an ION buffer, let it be free, when it is no longer being used by + * the remote subsystem. + */ +static int spcom_handle_unlock_ion_buf_command(struct spcom_channel *ch, + void *cmd_buf, int size) +{ + int ret; + struct spcom_user_command *cmd = cmd_buf; + int fd = cmd->arg; + + if (size != sizeof(*cmd)) { + pr_err("cmd size [%d] , expected [%d].\n", + (int) size, (int) sizeof(*cmd)); + return -EINVAL; + } + + ret = spcom_unlock_ion_buf(ch, fd); + + return ret; +} + +/** * spcom_handle_fake_ssr_command() - Handle fake ssr command from user space. */ static int spcom_handle_fake_ssr_command(struct spcom_channel *ch, int arg) diff --git a/drivers/thermal/msm-tsens.c b/drivers/thermal/msm-tsens.c index 8afda2352001..4585313772ff 100644 --- a/drivers/thermal/msm-tsens.c +++ b/drivers/thermal/msm-tsens.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2012-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2012-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -140,215 +140,7 @@ #define TSENS_CTRL_ADDR(n) (n) #define TSENS_EN BIT(0) -#define TSENS_SW_RST BIT(1) -#define TSENS_ADC_CLK_SEL BIT(2) -#define TSENS_SENSOR0_SHIFT 3 -#define TSENS_62_5_MS_MEAS_PERIOD 1 -#define TSENS_312_5_MS_MEAS_PERIOD 2 -#define TSENS_MEAS_PERIOD_SHIFT 18 - -#define TSENS_GLOBAL_CONFIG(n) ((n) + 0x34) -#define TSENS_S0_MAIN_CONFIG(n) ((n) + 0x38) -#define TSENS_SN_REMOTE_CONFIG(n) ((n) + 0x3c) - -#define TSENS_EEPROM(n) ((n) + 0xd0) -#define TSENS_EEPROM_REDUNDANCY_SEL(n) ((n) + 0x444) -#define TSENS_EEPROM_BACKUP_REGION(n) ((n) + 0x440) - -#define TSENS_MAIN_CALIB_ADDR_RANGE 6 -#define TSENS_BACKUP_CALIB_ADDR_RANGE 4 - -#define TSENS_EEPROM_8X26_1(n) ((n) + 0x1c0) -#define TSENS_EEPROM_8X26_2(n) ((n) + 0x444) -#define TSENS_8X26_MAIN_CALIB_ADDR_RANGE 4 - -#define TSENS_EEPROM_8X10_1(n) ((n) + 0x1a4) -#define TSENS_EEPROM_8X10_1_OFFSET 8 -#define TSENS_EEPROM_8X10_2(n) ((n) + 0x1a8) -#define TSENS_EEPROM_8X10_SPARE_1(n) ((n) + 0xd8) -#define TSENS_EEPROM_8X10_SPARE_2(n) ((n) + 0xdc) - -#define TSENS_9900_EEPROM(n) ((n) + 0xd0) -#define TSENS_9900_EEPROM_REDUNDANCY_SEL(n) ((n) + 0x1c4) -#define TSENS_9900_EEPROM_BACKUP_REGION(n) ((n) + 0x450) -#define TSENS_9900_CALIB_ADDR_RANGE 4 - -#define TSENS_8939_EEPROM(n) ((n) + 0xa0) - -#define TSENS_8994_EEPROM(n) ((n) + 0xd0) -#define TSENS_8994_EEPROM_REDUN_SEL(n) ((n) + 0x464) -#define TSENS_REDUN_REGION1_EEPROM(n) ((n) + 0x1c0) -#define TSENS_REDUN_REGION2_EEPROM(n) ((n) + 0x1c4) -#define TSENS_REDUN_REGION3_EEPROM(n) ((n) + 0x1cc) -#define TSENS_REDUN_REGION4_EEPROM(n) ((n) + 0x440) -#define TSENS_REDUN_REGION5_EEPROM(n) ((n) + 0x444) - -/* TSENS calibration Mask data */ -#define TSENS_BASE1_MASK 0xff -#define TSENS0_POINT1_MASK 0x3f00 -#define TSENS1_POINT1_MASK 0xfc000 -#define TSENS2_POINT1_MASK 0x3f00000 -#define TSENS3_POINT1_MASK 0xfc000000 -#define TSENS4_POINT1_MASK 0x3f -#define TSENS5_POINT1_MASK 0xfc0 -#define TSENS6_POINT1_MASK 0x3f000 -#define TSENS7_POINT1_MASK 0xfc0000 -#define TSENS8_POINT1_MASK 0x3f000000 -#define TSENS8_POINT1_MASK_BACKUP 0x3f -#define TSENS9_POINT1_MASK 0x3f -#define TSENS9_POINT1_MASK_BACKUP 0xfc0 -#define TSENS10_POINT1_MASK 0xfc0 -#define TSENS10_POINT1_MASK_BACKUP 0x3f000 -#define TSENS_CAL_SEL_0_1 0xc0000000 -#define TSENS_CAL_SEL_2 0x40000000 -#define TSENS_CAL_SEL_SHIFT 30 -#define TSENS_CAL_SEL_SHIFT_2 28 -#define TSENS_ONE_POINT_CALIB 0x1 -#define TSENS_ONE_POINT_CALIB_OPTION_2 0x2 -#define TSENS_TWO_POINT_CALIB 0x3 - -#define TSENS0_POINT1_SHIFT 8 -#define TSENS1_POINT1_SHIFT 14 -#define TSENS2_POINT1_SHIFT 20 -#define TSENS3_POINT1_SHIFT 26 -#define TSENS5_POINT1_SHIFT 6 -#define TSENS6_POINT1_SHIFT 12 -#define TSENS7_POINT1_SHIFT 18 -#define TSENS8_POINT1_SHIFT 24 -#define TSENS9_POINT1_BACKUP_SHIFT 6 -#define TSENS10_POINT1_SHIFT 6 -#define TSENS10_POINT1_BACKUP_SHIFT 12 - -#define TSENS_POINT2_BASE_SHIFT 12 -#define TSENS_POINT2_BASE_BACKUP_SHIFT 18 -#define TSENS0_POINT2_SHIFT 20 -#define TSENS0_POINT2_BACKUP_SHIFT 26 -#define TSENS1_POINT2_SHIFT 26 -#define TSENS2_POINT2_BACKUP_SHIFT 6 -#define TSENS3_POINT2_SHIFT 6 -#define TSENS3_POINT2_BACKUP_SHIFT 12 -#define TSENS4_POINT2_SHIFT 12 -#define TSENS4_POINT2_BACKUP_SHIFT 18 -#define TSENS5_POINT2_SHIFT 18 -#define TSENS5_POINT2_BACKUP_SHIFT 24 -#define TSENS6_POINT2_SHIFT 24 -#define TSENS7_POINT2_BACKUP_SHIFT 6 -#define TSENS8_POINT2_SHIFT 6 -#define TSENS8_POINT2_BACKUP_SHIFT 12 -#define TSENS9_POINT2_SHIFT 12 -#define TSENS9_POINT2_BACKUP_SHIFT 18 -#define TSENS10_POINT2_SHIFT 18 -#define TSENS10_POINT2_BACKUP_SHIFT 24 - -#define TSENS_BASE2_MASK 0xff000 -#define TSENS_BASE2_BACKUP_MASK 0xfc0000 -#define TSENS0_POINT2_MASK 0x3f00000 -#define TSENS0_POINT2_BACKUP_MASK 0xfc000000 -#define TSENS1_POINT2_MASK 0xfc000000 -#define TSENS1_POINT2_BACKUP_MASK 0x3f -#define TSENS2_POINT2_MASK 0x3f -#define TSENS2_POINT2_BACKUP_MASK 0xfc0 -#define TSENS3_POINT2_MASK 0xfc0 -#define TSENS3_POINT2_BACKUP_MASK 0x3f000 -#define TSENS4_POINT2_MASK 0x3f000 -#define TSENS4_POINT2_BACKUP_MASK 0xfc0000 -#define TSENS5_POINT2_MASK 0xfc0000 -#define TSENS5_POINT2_BACKUP_MASK 0x3f000000 -#define TSENS6_POINT2_MASK 0x3f000000 -#define TSENS6_POINT2_BACKUP_MASK 0x3f -#define TSENS7_POINT2_MASK 0x3f -#define TSENS7_POINT2_BACKUP_MASK 0xfc0 -#define TSENS8_POINT2_MASK 0xfc0 -#define TSENS8_POINT2_BACKUP_MASK 0x3f000 -#define TSENS9_POINT2_MASK 0x3f000 -#define TSENS9_POINT2_BACKUP_MASK 0xfc0000 -#define TSENS10_POINT2_MASK 0xfc0000 -#define TSENS10_POINT2_BACKUP_MASK 0x3f000000 - -#define TSENS_8X26_BASE0_MASK 0x1fe000 -#define TSENS0_8X26_POINT1_MASK 0x7e00000 -#define TSENS1_8X26_POINT1_MASK 0x3f -#define TSENS2_8X26_POINT1_MASK 0xfc0 -#define TSENS3_8X26_POINT1_MASK 0x3f000 -#define TSENS4_8X26_POINT1_MASK 0xfc0000 -#define TSENS5_8X26_POINT1_MASK 0x3f000000 -#define TSENS6_8X26_POINT1_MASK 0x3f00000 -#define TSENS_8X26_TSENS_CAL_SEL 0xe0000000 -#define TSENS_8X26_BASE1_MASK 0xff -#define TSENS0_8X26_POINT2_MASK 0x3f00 -#define TSENS1_8X26_POINT2_MASK 0xfc000 -#define TSENS2_8X26_POINT2_MASK 0x3f00000 -#define TSENS3_8X26_POINT2_MASK 0xfc000000 -#define TSENS4_8X26_POINT2_MASK 0x3f00000 -#define TSENS5_8X26_POINT2_MASK 0xfc000000 -#define TSENS6_8X26_POINT2_MASK 0x7e0000 - -#define TSENS_8X26_CAL_SEL_SHIFT 29 -#define TSENS_8X26_BASE0_SHIFT 13 -#define TSENS0_8X26_POINT1_SHIFT 21 -#define TSENS2_8X26_POINT1_SHIFT 6 -#define TSENS3_8X26_POINT1_SHIFT 12 -#define TSENS4_8X26_POINT1_SHIFT 18 -#define TSENS5_8X26_POINT1_SHIFT 24 -#define TSENS6_8X26_POINT1_SHIFT 20 - -#define TSENS0_8X26_POINT2_SHIFT 8 -#define TSENS1_8X26_POINT2_SHIFT 14 -#define TSENS2_8X26_POINT2_SHIFT 20 -#define TSENS3_8X26_POINT2_SHIFT 26 -#define TSENS4_8X26_POINT2_SHIFT 20 -#define TSENS5_8X26_POINT2_SHIFT 26 -#define TSENS6_8X26_POINT2_SHIFT 17 - -#define TSENS_8X10_CAL_SEL_SHIFT 28 -#define TSENS_8X10_BASE1_SHIFT 8 -#define TSENS0_8X10_POINT1_SHIFT 16 -#define TSENS0_8X10_POINT2_SHIFT 22 -#define TSENS1_8X10_POINT2_SHIFT 6 -#define TSENS_8X10_BASE0_MASK 0xff -#define TSENS_8X10_BASE1_MASK 0xff00 -#define TSENS0_8X10_POINT1_MASK 0x3f0000 -#define TSENS0_8X10_POINT2_MASK 0xfc00000 -#define TSENS_8X10_TSENS_CAL_SEL 0x70000000 -#define TSENS1_8X10_POINT1_MASK 0x3f -#define TSENS1_8X10_POINT2_MASK 0xfc0 -#define TSENS_8X10_REDUN_SEL_MASK 0x6000000 -#define TSENS_8X10_REDUN_SEL_SHIFT 25 - -#define TSENS0_9900_POINT1_SHIFT 19 -#define TSENS2_9900_POINT1_SHIFT 12 -#define TSENS3_9900_POINT1_SHIFT 24 -#define TSENS4_9900_POINT1_SHIFT 6 -#define TSENS5_9900_POINT1_SHIFT 18 -#define TSENS_9900_BASE1_MASK 0xff -#define TSENS0_9900_POINT1_MASK 0x1f80000 -#define TSENS1_9900_POINT1_MASK 0x3f -#define TSENS2_9900_POINT1_MASK 0x3f000 -#define TSENS3_9900_POINT1_MASK 0x3f000000 -#define TSENS4_9900_POINT1_MASK 0xfc0 -#define TSENS5_9900_POINT1_MASK 0xfc0000 -#define TSENS6_9900_POINT1_MASK 0x3f - -#define TSENS_9900_BASE2_SHIFT 8 -#define TSENS0_9900_POINT2_SHIFT 25 -#define TSENS1_9900_POINT2_SHIFT 6 -#define TSENS2_9900_POINT2_SHIFT 18 -#define TSENS4_9900_POINT2_SHIFT 12 -#define TSENS5_9900_POINT2_SHIFT 24 -#define TSENS6_9900_POINT2_SHIFT 6 -#define TSENS_9900_BASE2_MASK 0xff00 -#define TSENS0_9900_POINT2_MASK 0x7e000000 -#define TSENS1_9900_POINT2_MASK 0xfc0 -#define TSENS2_9900_POINT2_MASK 0xfc0000 -#define TSENS3_9900_POINT2_MASK 0x3f -#define TSENS4_9900_POINT2_MASK 0x3f000 -#define TSENS5_9900_POINT2_MASK 0x3f000000 -#define TSENS6_9900_POINT2_MASK 0xfc0 - -#define TSENS_9900_CAL_SEL_SHIFT 16 -#define TSENS_9900_TSENS_CAL_SEL 0x00070000 - -#define TSENS_BIT_APPEND 0x3 + #define TSENS_CAL_DEGC_POINT1 30 #define TSENS_CAL_DEGC_POINT2 120 #define TSENS_SLOPE_FACTOR 1000 @@ -359,354 +151,11 @@ #define TSENS_THRESHOLD_MAX_CODE 0x3ff #define TSENS_THRESHOLD_MIN_CODE 0x0 -#define TSENS_GLOBAL_INIT_DATA 0x302f16c -#define TSENS_S0_MAIN_CFG_INIT_DATA 0x1c3 -#define TSENS_SN_REMOTE_CFG_DATA 0x11c3 - -#define TSENS_QFPROM_BACKUP_SEL 0x3 -#define TSENS_QFPROM_BACKUP_REDUN_SEL 0xe0000000 -#define TSENS_QFPROM_BACKUP_REDUN_SHIFT 29 - -#define TSENS_QFPROM_BACKUP_9900_REDUN_SEL 0x07000000 -#define TSENS_QFPROM_BACKUP_9900_REDUN_SHIFT 24 - -#define TSENS_TORINO_BASE0 0x3ff -#define TSENS_TORINO_BASE1 0xffc00 -#define TSENS_TORINO_POINT0 0xf00000 -#define TSENS_TORINO_POINT1 0xf0000000 -#define TSENS_TORINO_POINT2 0xf0 -#define TSENS_TORINO_POINT3 0xf000 -#define TSENS_TORINO_POINT4 0xf00000 -#define TSENS_TORINO_CALIB_PT 0x70000000 - -#define TSENS_TORINO_BASE1_SHIFT 10 -#define TSENS_TORINO_POINT0_SHIFT 20 -#define TSENS_TORINO_POINT1_SHIFT 28 -#define TSENS_TORINO_POINT2_SHIFT 4 -#define TSENS_TORINO_POINT3_SHIFT 12 -#define TSENS_TORINO_POINT4_SHIFT 20 -#define TSENS_TORINO_CALIB_SHIFT 28 - #define TSENS_TYPE0 0 #define TSENS_TYPE2 2 #define TSENS_TYPE3 3 #define TSENS_TYPE4 4 -#define TSENS_8916_BASE0_MASK 0x0000007f -#define TSENS_8916_BASE1_MASK 0xfe000000 - -#define TSENS0_8916_POINT1_MASK 0x00000f80 -#define TSENS1_8916_POINT1_MASK 0x003e0000 -#define TSENS2_8916_POINT1_MASK 0xf8000000 -#define TSENS3_8916_POINT1_MASK 0x000003e0 -#define TSENS4_8916_POINT1_MASK 0x000f8000 - -#define TSENS0_8916_POINT2_MASK 0x0001f000 -#define TSENS1_8916_POINT2_MASK 0x07c00000 -#define TSENS2_8916_POINT2_MASK 0x0000001f -#define TSENS3_8916_POINT2_MASK 0x00007c00 -#define TSENS4_8916_POINT2_MASK 0x01f00000 - -#define TSENS_8916_TSENS_CAL_SEL 0xe0000000 - -#define TSENS_8916_CAL_SEL_SHIFT 29 -#define TSENS_8916_BASE1_SHIFT 25 - -#define TSENS0_8916_POINT1_SHIFT 7 -#define TSENS1_8916_POINT1_SHIFT 17 -#define TSENS2_8916_POINT1_SHIFT 27 -#define TSENS3_8916_POINT1_SHIFT 5 -#define TSENS4_8916_POINT1_SHIFT 15 - -#define TSENS0_8916_POINT2_SHIFT 12 -#define TSENS1_8916_POINT2_SHIFT 22 -#define TSENS3_8916_POINT2_SHIFT 10 -#define TSENS4_8916_POINT2_SHIFT 20 -#define TSENS_VALID_CNT_2 2 - -#define TSENS_8939_BASE0_MASK 0x000000ff -#define TSENS_8939_BASE1_MASK 0xff000000 - -#define TSENS0_8939_POINT1_MASK 0x000001f8 -#define TSENS1_8939_POINT1_MASK 0x001f8000 -#define TSENS2_8939_POINT1_MASK_0_4 0xf8000000 -#define TSENS2_8939_POINT1_MASK_5 0x00000001 -#define TSENS3_8939_POINT1_MASK 0x00001f80 -#define TSENS4_8939_POINT1_MASK 0x01f80000 -#define TSENS5_8939_POINT1_MASK 0x00003f00 -#define TSENS6_8939_POINT1_MASK 0x03f00000 -#define TSENS7_8939_POINT1_MASK 0x0000003f -#define TSENS8_8939_POINT1_MASK 0x0003f000 - -#define TSENS0_8939_POINT2_MASK 0x00007e00 -#define TSENS1_8939_POINT2_MASK 0x07e00000 -#define TSENS2_8939_POINT2_MASK 0x0000007e -#define TSENS3_8939_POINT2_MASK 0x0007e000 -#define TSENS4_8939_POINT2_MASK 0x7e000000 -#define TSENS5_8939_POINT2_MASK 0x000fc000 -#define TSENS6_8939_POINT2_MASK 0xfc000000 -#define TSENS7_8939_POINT2_MASK 0x00000fc0 -#define TSENS8_8939_POINT2_MASK 0x00fc0000 - -#define TSENS_8939_TSENS_CAL_SEL 0x7 -#define TSENS_8939_CAL_SEL_SHIFT 0 -#define TSENS_8939_BASE1_SHIFT 24 - -#define TSENS0_8939_POINT1_SHIFT 3 -#define TSENS1_8939_POINT1_SHIFT 15 -#define TSENS2_8939_POINT1_SHIFT_0_4 27 -#define TSENS2_8939_POINT1_SHIFT_5 5 -#define TSENS3_8939_POINT1_SHIFT 7 -#define TSENS4_8939_POINT1_SHIFT 19 -#define TSENS5_8939_POINT1_SHIFT 8 -#define TSENS6_8939_POINT1_SHIFT 20 -#define TSENS8_8939_POINT1_SHIFT 12 - -#define TSENS0_8939_POINT2_SHIFT 9 -#define TSENS1_8939_POINT2_SHIFT 21 -#define TSENS2_8939_POINT2_SHIFT 1 -#define TSENS3_8939_POINT2_SHIFT 13 -#define TSENS4_8939_POINT2_SHIFT 25 -#define TSENS5_8939_POINT2_SHIFT 14 -#define TSENS6_8939_POINT2_SHIFT 26 -#define TSENS7_8939_POINT2_SHIFT 6 -#define TSENS8_8939_POINT2_SHIFT 18 - -#define TSENS_BASE0_8994_MASK 0x3ff -#define TSENS_BASE1_8994_MASK 0xffc00 -#define TSENS_BASE1_8994_SHIFT 10 -#define TSENS0_OFFSET_8994_MASK 0xf00000 -#define TSENS0_OFFSET_8994_SHIFT 20 -#define TSENS1_OFFSET_8994_MASK 0xf000000 -#define TSENS1_OFFSET_8994_SHIFT 24 -#define TSENS2_OFFSET_8994_MASK 0xf0000000 -#define TSENS2_OFFSET_8994_SHIFT 28 -#define TSENS3_OFFSET_8994_MASK 0xf -#define TSENS4_OFFSET_8994_MASK 0xf0 -#define TSENS4_OFFSET_8994_SHIFT 4 -#define TSENS5_OFFSET_8994_MASK 0xf00 -#define TSENS5_OFFSET_8994_SHIFT 8 -#define TSENS6_OFFSET_8994_MASK 0xf000 -#define TSENS6_OFFSET_8994_SHIFT 12 -#define TSENS7_OFFSET_8994_MASK 0xf0000 -#define TSENS7_OFFSET_8994_SHIFT 16 -#define TSENS8_OFFSET_8994_MASK 0xf00000 -#define TSENS8_OFFSET_8994_SHIFT 20 -#define TSENS9_OFFSET_8994_MASK 0xf000000 -#define TSENS9_OFFSET_8994_SHIFT 24 -#define TSENS10_OFFSET_8994_MASK 0xf0000000 -#define TSENS10_OFFSET_8994_SHIFT 28 -#define TSENS11_OFFSET_8994_MASK 0xf -#define TSENS12_OFFSET_8994_MASK 0xf0 -#define TSENS12_OFFSET_8994_SHIFT 4 -#define TSENS13_OFFSET_8994_MASK 0xf00 -#define TSENS13_OFFSET_8994_SHIFT 8 -#define TSENS14_OFFSET_8994_MASK 0xf000 -#define TSENS14_OFFSET_8994_SHIFT 12 -#define TSENS15_OFFSET_8994_MASK 0xf0000 -#define TSENS15_OFFSET_8994_SHIFT 16 -#define TSENS_8994_CAL_SEL_MASK 0x700000 -#define TSENS_8994_CAL_SEL_SHIFT 20 - -#define TSENS_BASE0_8994_REDUN_MASK 0x7fe00000 -#define TSENS_BASE0_8994_REDUN_MASK_SHIFT 21 -#define TSENS_BASE1_BIT0_8994_REDUN_MASK 0x80000000 -#define TSENS_BASE1_BIT0_SHIFT_COMPUTE 31 -#define TSENS_BASE1_BIT1_9_8994_REDUN_MASK 0x1ff -#define TSENS0_OFFSET_8994_REDUN_MASK 0x1e00 -#define TSENS0_OFFSET_8994_REDUN_SHIFT 9 -#define TSENS1_OFFSET_8994_REDUN_MASK 0x1e000 -#define TSENS1_OFFSET_8994_REDUN_SHIFT 13 -#define TSENS2_OFFSET_8994_REDUN_MASK 0x1e0000 -#define TSENS2_OFFSET_8994_REDUN_SHIFT 17 -#define TSENS3_OFFSET_8994_REDUN_MASK 0x1e00000 -#define TSENS3_OFFSET_8994_REDUN_SHIFT 21 -#define TSENS4_OFFSET_8994_REDUN_MASK 0x1e000000 -#define TSENS4_OFFSET_8994_REDUN_SHIFT 25 -#define TSENS5_OFFSET_8994_REDUN_MASK_BIT0_2 0xe0000000 -#define TSENS5_OFFSET_8994_REDUN_SHIFT_BIT0_2 29 -#define TSENS5_OFFSET_8994_REDUN_MASK_BIT3 0x800000 -#define TSENS5_OFFSET_8994_REDUN_SHIFT_BIT3 23 -#define TSENS6_OFFSET_8994_REDUN_MASK 0xf000000 -#define TSENS6_OFFSET_8994_REDUN_SHIFT 24 -#define TSENS7_OFFSET_8994_REDUN_MASK 0xf0000000 -#define TSENS7_OFFSET_8994_REDUN_SHIFT 28 -#define TSENS8_OFFSET_8994_REDUN_MASK 0xf -#define TSENS9_OFFSET_8994_REDUN_MASK 0xf0 -#define TSENS9_OFFSET_8994_REDUN_SHIFT 4 -#define TSENS10_OFFSET_8994_REDUN_MASK 0xf00 -#define TSENS10_OFFSET_8994_REDUN_SHIFT 8 -#define TSENS11_OFFSET_8994_REDUN_MASK 0xf000 -#define TSENS11_OFFSET_8994_REDUN_SHIFT 12 -#define TSENS12_OFFSET_8994_REDUN_MASK 0xf0000 -#define TSENS12_OFFSET_8994_REDUN_SHIFT 16 -#define TSENS13_OFFSET_8994_REDUN_MASK 0xf00000 -#define TSENS13_OFFSET_8994_REDUN_SHIFT 20 -#define TSENS14_OFFSET_8994_REDUN_MASK 0xf000000 -#define TSENS14_OFFSET_8994_REDUN_SHIFT 24 -#define TSENS15_OFFSET_8994_REDUN_MASK 0xf0000000 -#define TSENS15_OFFSET_8994_REDUN_SHIFT 28 -#define TSENS_8994_REDUN_SEL_MASK 0x7 -#define TSENS_8994_CAL_SEL_REDUN_MASK 0xe0000000 -#define TSENS_8994_CAL_SEL_REDUN_SHIFT 29 - -#define TSENS_MSM8909_BASE0_MASK 0x000000ff -#define TSENS_MSM8909_BASE1_MASK 0x0000ff00 - -#define TSENS0_MSM8909_POINT1_MASK 0x0000003f -#define TSENS1_MSM8909_POINT1_MASK 0x0003f000 -#define TSENS2_MSM8909_POINT1_MASK 0x3f000000 -#define TSENS3_MSM8909_POINT1_MASK 0x000003f0 -#define TSENS4_MSM8909_POINT1_MASK 0x003f0000 - -#define TSENS0_MSM8909_POINT2_MASK 0x00000fc0 -#define TSENS1_MSM8909_POINT2_MASK 0x00fc0000 -#define TSENS2_MSM8909_POINT2_MASK_0_1 0xc0000000 -#define TSENS2_MSM8909_POINT2_MASK_2_5 0x0000000f -#define TSENS3_MSM8909_POINT2_MASK 0x0000fc00 -#define TSENS4_MSM8909_POINT2_MASK 0x0fc00000 - -#define TSENS_MSM8909_TSENS_CAL_SEL 0x00070000 -#define TSENS_MSM8909_CAL_SEL_SHIFT 16 -#define TSENS_MSM8909_BASE1_SHIFT 8 - -#define TSENS1_MSM8909_POINT1_SHIFT 12 -#define TSENS2_MSM8909_POINT1_SHIFT 24 -#define TSENS3_MSM8909_POINT1_SHIFT 4 -#define TSENS4_MSM8909_POINT1_SHIFT 16 - -#define TSENS0_MSM8909_POINT2_SHIFT 6 -#define TSENS1_MSM8909_POINT2_SHIFT 18 -#define TSENS2_MSM8909_POINT2_SHIFT_0_1 30 -#define TSENS2_MSM8909_POINT2_SHIFT_2_5 2 -#define TSENS3_MSM8909_POINT2_SHIFT 10 -#define TSENS4_MSM8909_POINT2_SHIFT 22 - -#define TSENS_ZIRC_CAL_SEL 0x700 -#define TSENS_ZIRC_CAL_SEL_SHIFT 8 -#define TSENS_BASE0_ZIRC_MASK 0x3ff -#define TSENS_BASE1_ZIRC_MASK 0xffc00 -#define TSENS_BASE1_ZIRC_SHIFT 10 -#define TSENS0_OFFSET_ZIRC_MASK 0xf00000 -#define TSENS0_OFFSET_ZIRC_SHIFT 20 -#define TSENS1_OFFSET_ZIRC_MASK 0xf000000 -#define TSENS1_OFFSET_ZIRC_SHIFT 24 -#define TSENS2_OFFSET_ZIRC_MASK 0xf0000000 -#define TSENS2_OFFSET_ZIRC_SHIFT 28 -#define TSENS3_OFFSET_ZIRC_MASK 0xf -#define TSENS4_OFFSET_ZIRC_MASK 0xf0 -#define TSENS4_OFFSET_ZIRC_SHIFT 4 - -#define TSENS_CONTR_14_BASE0_MASK 0x000000ff -#define TSENS_CONTR_14_BASE1_MASK 0xff000000 - -#define TSENS0_CONTR_14_POINT1_MASK 0x000001f8 -#define TSENS1_CONTR_14_POINT1_MASK 0x001f8000 -#define TSENS2_CONTR_14_POINT1_MASK_0_4 0xf8000000 -#define TSENS2_CONTR_14_POINT1_MASK_5 0x00000001 -#define TSENS3_CONTR_14_POINT1_MASK 0x00001f80 -#define TSENS4_CONTR_14_POINT1_MASK 0x01f80000 -#define TSENS5_CONTR_14_POINT1_MASK 0x00003f00 -#define TSENS6_CONTR_14_POINT1_MASK 0x03f00000 -#define TSENS7_CONTR_14_POINT1_MASK 0x0000003f -#define TSENS8_CONTR_14_POINT1_MASK 0x0003f000 -#define TSENS9_CONTR_14_POINT1_MASK 0x0000003f -#define TSENS10_CONTR_14_POINT1_MASK 0x0003f000 - -#define TSENS0_CONTR_14_POINT2_MASK 0x00007e00 -#define TSENS1_CONTR_14_POINT2_MASK 0x07e00000 -#define TSENS2_CONTR_14_POINT2_MASK 0x0000007e -#define TSENS3_CONTR_14_POINT2_MASK 0x0007e000 -#define TSENS4_CONTR_14_POINT2_MASK 0x7e000000 -#define TSENS5_CONTR_14_POINT2_MASK 0x000fc000 -#define TSENS6_CONTR_14_POINT2_MASK 0xfc000000 -#define TSENS7_CONTR_14_POINT2_MASK 0x00000fc0 -#define TSENS8_CONTR_14_POINT2_MASK 0x00fc0000 -#define TSENS9_CONTR_14_POINT2_MASK 0x00000fc0 -#define TSENS10_CONTR_14_POINT2_MASK 0x00fc0000 - -#define TSENS_CONTR_14_TSENS_CAL_SEL 0x00000007 -#define TSENS_CONTR_14_BASE1_SHIFT 24 - -#define TSENS0_CONTR_14_POINT1_SHIFT 3 -#define TSENS1_CONTR_14_POINT1_SHIFT 15 -#define TSENS2_CONTR_14_POINT1_SHIFT_0_4 27 -#define TSENS2_CONTR_14_POINT1_SHIFT_5 5 -#define TSENS3_CONTR_14_POINT1_SHIFT 7 -#define TSENS4_CONTR_14_POINT1_SHIFT 19 -#define TSENS5_CONTR_14_POINT1_SHIFT 8 -#define TSENS6_CONTR_14_POINT1_SHIFT 20 -#define TSENS8_CONTR_14_POINT1_SHIFT 12 -#define TSENS10_CONTR_14_POINT1_SHIFT 12 - -#define TSENS0_CONTR_14_POINT2_SHIFT 9 -#define TSENS1_CONTR_14_POINT2_SHIFT 21 -#define TSENS2_CONTR_14_POINT2_SHIFT 1 -#define TSENS3_CONTR_14_POINT2_SHIFT 13 -#define TSENS4_CONTR_14_POINT2_SHIFT 25 -#define TSENS5_CONTR_14_POINT2_SHIFT 14 -#define TSENS6_CONTR_14_POINT2_SHIFT 26 -#define TSENS7_CONTR_14_POINT2_SHIFT 6 -#define TSENS8_CONTR_14_POINT2_SHIFT 18 -#define TSENS9_CONTR_14_POINT2_SHIFT 6 -#define TSENS10_CONTR_14_POINT2_SHIFT 18 - -#define TSENS_TWO_POINT_CALIB_N_WA 0x6 -#define TSENS_TWO_POINT_CALIB_N_OFFSET_WA 0x7 - -#define TSENS_MSM8952_D30_WA_S0 2 -#define TSENS_MSM8952_D30_WA_S1 4 -#define TSENS_MSM8952_D30_WA_S2 4 -#define TSENS_MSM8952_D30_WA_S3 1 -#define TSENS_MSM8952_D30_WA_S4 2 -#define TSENS_MSM8952_D30_WA_S5 1 -#define TSENS_MSM8952_D30_WA_S7 3 -#define TSENS_MSM8952_D30_WA_S8 2 -#define TSENS_MSM8952_D30_WA_S10 3 - -#define TSENS_MSM8952_D120_WA_S0 1 -#define TSENS_MSM8952_D120_WA_S1 4 -#define TSENS_MSM8952_D120_WA_S2 5 -#define TSENS_MSM8952_D120_WA_S3 1 -#define TSENS_MSM8952_D120_WA_S4 3 -#define TSENS_MSM8952_D120_WA_S5 1 -#define TSENS_MSM8952_D120_WA_S6 1 -#define TSENS_MSM8952_D120_WA_S7 4 -#define TSENS_MSM8952_D120_WA_S8 4 -#define TSENS_MSM8952_D120_WA_S10 2 - -#define TSENS_NO_CALIB_POINT1_DATA 500 -#define TSENS_NO_CALIB_POINT2_DATA 780 - -#define TSENS_MDM9607_TSENS_CAL_SEL 0x00700000 -#define TSENS_MDM9607_CAL_SEL_SHIFT 20 -#define TSENS_MDM9607_BASE1_SHIFT 12 - -#define TSENS_MDM9607_BASE0_MASK 0x000000ff -#define TSENS_MDM9607_BASE1_MASK 0x000ff000 - -#define TSENS0_MDM9607_POINT1_MASK 0x00003f00 -#define TSENS1_MDM9607_POINT1_MASK 0x03f00000 -#define TSENS2_MDM9607_POINT1_MASK 0x0000003f -#define TSENS3_MDM9607_POINT1_MASK 0x0003f000 -#define TSENS4_MDM9607_POINT1_MASK 0x0000003f - -#define TSENS0_MDM9607_POINT2_MASK 0x000fc000 -#define TSENS1_MDM9607_POINT2_MASK 0xfc000000 -#define TSENS2_MDM9607_POINT2_MASK 0x00000fc0 -#define TSENS3_MDM9607_POINT2_MASK 0x00fc0000 -#define TSENS4_MDM9607_POINT2_MASK 0x0000fc00 - -#define TSENS0_MDM9607_POINT1_SHIFT 8 -#define TSENS1_MDM9607_POINT1_SHIFT 20 -#define TSENS3_MDM9607_POINT1_SHIFT 12 - -#define TSENS0_MDM9607_POINT2_SHIFT 14 -#define TSENS1_MDM9607_POINT2_SHIFT 26 -#define TSENS2_MDM9607_POINT2_SHIFT 6 -#define TSENS3_MDM9607_POINT2_SHIFT 18 -#define TSENS4_MDM9607_POINT2_SHIFT 6 - /* debug defines */ #define TSENS_DBG_BUS_ID_0 0 #define TSENS_DBG_BUS_ID_1 1 @@ -733,26 +182,6 @@ static uint32_t tsens_sec_to_msec_value = 1000; static uint32_t tsens_completion_timeout_hz = HZ/2; static uint32_t tsens_poll_check = 1; -enum tsens_calib_fuse_map_type { - TSENS_CALIB_FUSE_MAP_8974 = 0, - TSENS_CALIB_FUSE_MAP_8X26, - TSENS_CALIB_FUSE_MAP_8X10, - TSENS_CALIB_FUSE_MAP_9900, - TSENS_CALIB_FUSE_MAP_9630, - TSENS_CALIB_FUSE_MAP_8916, - TSENS_CALIB_FUSE_MAP_8939, - TSENS_CALIB_FUSE_MAP_8994, - TSENS_CALIB_FUSE_MAP_MSM8909, - TSENS_CALIB_FUSE_MAP_MSMZIRC, - TSENS_CALIB_FUSE_MAP_NONE, - TSENS_CALIB_FUSE_MAP_8992, - TSENS_CALIB_FUSE_MAP_MSM8952, - TSENS_CALIB_FUSE_MAP_MDM9607, - TSENS_CALIB_FUSE_MAP_MSM8937, - TSENS_CALIB_FUSE_MAP_MSMGOLD, - TSENS_CALIB_FUSE_MAP_NUM, -}; - /* Trips: warm and cool */ enum tsens_trip_type { TSENS_TRIP_WARM = 0, @@ -848,7 +277,6 @@ struct tsens_tm_device { int calib_len; struct resource *res_tsens_mem; struct resource *res_calib_mem; - uint32_t calib_mode; uint32_t tsens_type; bool tsens_valid_status_check; struct tsens_dbg_counter tsens_thread_iq_dbg; @@ -880,68 +308,17 @@ static struct dentry *dent; static struct dentry *dfile_stats; static struct of_device_id tsens_match[] = { - { .compatible = "qcom,msm-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8974, - }, - { .compatible = "qcom,msm8x26-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8X26, - }, - { .compatible = "qcom,msm8x10-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8X10, - }, - { .compatible = "qcom,fsm9900-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_9900, - }, - { .compatible = "qcom,mdm9630-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_9630, - }, - { .compatible = "qcom,msm8916-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8916, - }, - { .compatible = "qcom,msm8939-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8939, - }, - { .compatible = "qcom,msm8994-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8994, - }, - { .compatible = "qcom,msm8909-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_MSM8909, - }, - { .compatible = "qcom,msmzirc-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_MSMZIRC, - }, { .compatible = "qcom,msm8996-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_NONE, - }, - { .compatible = "qcom,msm8992-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_8992, - }, - { .compatible = "qcom,msm8952-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_MSM8952, - }, - { .compatible = "qcom,mdm9607-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_MDM9607, }, { .compatible = "qcom,msmtitanium-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_NONE, - }, - { .compatible = "qcom,msm8937-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_MSM8937, - }, - { .compatible = "qcom,msmgold-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_MSMGOLD, }, { .compatible = "qcom,msm8998-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_NONE, }, { .compatible = "qcom,msmhamster-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_NONE, }, { .compatible = "qcom,sdm660-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_NONE, }, { .compatible = "qcom,sdm630-tsens", - .data = (void *)TSENS_CALIB_FUSE_MAP_NONE, }, {} }; @@ -2737,2639 +2114,6 @@ static int tsens_hw_init(struct tsens_tm_device *tmdev) return 0; } -static int tsens_calib_msm8937_msmgold_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens_base1_data = 0, ext_sen = 1; - int tsens0_point1 = 0, tsens0_point2 = 0; - int tsens1_point1 = 0, tsens1_point2 = 0; - int tsens2_point1 = 0, tsens2_point2 = 0; - int tsens3_point1 = 0, tsens3_point2 = 0; - int tsens4_point1 = 0, tsens4_point2 = 0; - int tsens5_point1 = 0, tsens5_point2 = 0; - int tsens6_point1 = 0, tsens6_point2 = 0; - int tsens7_point1 = 0, tsens7_point2 = 0; - int tsens8_point1 = 0, tsens8_point2 = 0; - int tsens9_point1 = 0, tsens9_point2 = 0; - int tsens10_point1 = 0, tsens10_point2 = 0; - - int tsens_calibration_mode = 0, temp = 0; - uint32_t calib_data[5] = {0, 0, 0, 0, 0}; - uint32_t calib_tsens_point1_data[11], calib_tsens_point2_data[11]; - - if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MSMGOLD) - ext_sen = 0; - - if (!tmdev->calibration_less_mode) { - - calib_data[0] = readl_relaxed(tmdev->tsens_calib_addr + 0x1D8); - calib_data[1] = readl_relaxed(tmdev->tsens_calib_addr + 0x1DC); - calib_data[2] = readl_relaxed(tmdev->tsens_calib_addr + 0x210); - calib_data[3] = readl_relaxed(tmdev->tsens_calib_addr + 0x214); - calib_data[4] = readl_relaxed(tmdev->tsens_calib_addr + 0x230); - - tsens_calibration_mode = - (calib_data[2] & - TSENS_CONTR_14_TSENS_CAL_SEL); - - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[0] & - TSENS_CONTR_14_BASE0_MASK); - tsens0_point1 = (calib_data[2] & - TSENS0_CONTR_14_POINT1_MASK) - >> TSENS0_CONTR_14_POINT1_SHIFT; - tsens1_point1 = (calib_data[2] & - TSENS1_CONTR_14_POINT1_MASK) - >> TSENS1_CONTR_14_POINT1_SHIFT; - tsens2_point1 = (calib_data[2] & - TSENS2_CONTR_14_POINT1_MASK_0_4) - >> TSENS2_CONTR_14_POINT1_SHIFT_0_4; - temp = (calib_data[3] & TSENS2_CONTR_14_POINT1_MASK_5) - << TSENS2_CONTR_14_POINT1_SHIFT_5; - tsens2_point1 |= temp; - tsens3_point1 = (calib_data[3] & - TSENS3_CONTR_14_POINT1_MASK) - >> TSENS3_CONTR_14_POINT1_SHIFT; - tsens4_point1 = (calib_data[3] & - TSENS4_CONTR_14_POINT1_MASK) - >> TSENS4_CONTR_14_POINT1_SHIFT; - tsens5_point1 = (calib_data[0] & - TSENS5_CONTR_14_POINT1_MASK) - >> TSENS5_CONTR_14_POINT1_SHIFT; - tsens6_point1 = (calib_data[0] & - TSENS6_CONTR_14_POINT1_MASK) - >> TSENS6_CONTR_14_POINT1_SHIFT; - tsens7_point1 = (calib_data[1] & - TSENS7_CONTR_14_POINT1_MASK); - tsens8_point1 = (calib_data[1] & - TSENS8_CONTR_14_POINT1_MASK) - >> TSENS8_CONTR_14_POINT1_SHIFT; - tsens9_point1 = (calib_data[4] & - TSENS9_CONTR_14_POINT1_MASK); - if (ext_sen) - tsens10_point1 = (calib_data[4] & - TSENS10_CONTR_14_POINT1_MASK) - >> TSENS10_CONTR_14_POINT1_SHIFT; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[1] & - TSENS_CONTR_14_BASE1_MASK) - >> TSENS_CONTR_14_BASE1_SHIFT; - tsens0_point2 = (calib_data[2] & - TSENS0_CONTR_14_POINT2_MASK) - >> TSENS0_CONTR_14_POINT2_SHIFT; - tsens1_point2 = (calib_data[2] & - TSENS1_CONTR_14_POINT2_MASK) - >> TSENS1_CONTR_14_POINT2_SHIFT; - tsens2_point2 = (calib_data[3] & - TSENS2_CONTR_14_POINT2_MASK) - >> TSENS2_CONTR_14_POINT2_SHIFT; - tsens3_point2 = (calib_data[3] & - TSENS3_CONTR_14_POINT2_MASK) - >> TSENS3_CONTR_14_POINT2_SHIFT; - tsens4_point2 = (calib_data[3] & - TSENS4_CONTR_14_POINT2_MASK) - >> TSENS4_CONTR_14_POINT2_SHIFT; - tsens5_point2 = (calib_data[0] & - TSENS5_CONTR_14_POINT2_MASK) - >> TSENS5_CONTR_14_POINT2_SHIFT; - tsens6_point2 = (calib_data[0] & - TSENS6_CONTR_14_POINT2_MASK) - >> TSENS6_CONTR_14_POINT2_SHIFT; - tsens7_point2 = (calib_data[1] & - TSENS7_CONTR_14_POINT2_MASK) - >> TSENS7_CONTR_14_POINT2_SHIFT; - tsens8_point2 = (calib_data[1] & - TSENS8_CONTR_14_POINT2_MASK) - >> TSENS8_CONTR_14_POINT2_SHIFT; - tsens9_point2 = (calib_data[4] & - TSENS9_CONTR_14_POINT2_MASK) - >> TSENS9_CONTR_14_POINT2_SHIFT; - if (ext_sen) - tsens10_point2 = (calib_data[4] & - TSENS10_CONTR_14_POINT2_MASK) - >> TSENS10_CONTR_14_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { - pr_debug("TSENS in calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - calib_tsens_point2_data[i] = TSENS_NO_CALIB_POINT2_DATA; - calib_tsens_point1_data[i] = TSENS_NO_CALIB_POINT1_DATA; - } - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 2) + - tmdev->sensor[0].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 2) + - tmdev->sensor[1].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 2) + - tmdev->sensor[2].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 2) + - tmdev->sensor[3].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 2) + - tmdev->sensor[4].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[5] = - (((tsens_base0_data) + tsens5_point1) << 2) + - tmdev->sensor[5].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[6] = - (((tsens_base0_data) + tsens6_point1) << 2) + - tmdev->sensor[6].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[7] = - (((tsens_base0_data) + tsens7_point1) << 2) + - tmdev->sensor[7].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[8] = - (((tsens_base0_data) + tsens8_point1) << 2) + - tmdev->sensor[8].wa_temp1_calib_offset_factor; - calib_tsens_point1_data[9] = - (((tsens_base0_data) + tsens9_point1) << 2) + - tmdev->sensor[9].wa_temp1_calib_offset_factor; - if (ext_sen) - calib_tsens_point1_data[10] = - (((tsens_base0_data) + tsens10_point1) << 2) + - tmdev->sensor[10].wa_temp1_calib_offset_factor; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 2) + - tmdev->sensor[0].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 2) + - tmdev->sensor[1].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 2) + - tmdev->sensor[2].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 2) + - tmdev->sensor[3].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 2) + - tmdev->sensor[4].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[5] = - ((tsens_base1_data + tsens5_point2) << 2) + - tmdev->sensor[5].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[6] = - ((tsens_base1_data + tsens6_point2) << 2) + - tmdev->sensor[6].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[7] = - ((tsens_base1_data + tsens7_point2) << 2) + - tmdev->sensor[7].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[8] = - ((tsens_base1_data + tsens8_point2) << 2) + - tmdev->sensor[8].wa_temp2_calib_offset_factor; - calib_tsens_point2_data[9] = - ((tsens_base1_data + tsens9_point2) << 2) + - tmdev->sensor[9].wa_temp2_calib_offset_factor; - if (ext_sen) - calib_tsens_point2_data[10] = - ((tsens_base1_data + tsens10_point2) << 2) + - tmdev->sensor[10].wa_temp2_calib_offset_factor; - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* - * slope (m) = adc_code2 - adc_code1 (y2 - y1) - * temp_120_degc - temp_30_degc (x2 - x1) - */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - return 0; -} - -static int tsens_calib_mdm9607_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens_base1_data = 0; - int tsens0_point1 = 0, tsens0_point2 = 0; - int tsens1_point1 = 0, tsens1_point2 = 0; - int tsens2_point1 = 0, tsens2_point2 = 0; - int tsens3_point1 = 0, tsens3_point2 = 0; - int tsens4_point1 = 0, tsens4_point2 = 0; - int tsens_calibration_mode = 0; - uint32_t calib_data[3] = {0, 0, 0}; - uint32_t calib_tsens_point1_data[5], calib_tsens_point2_data[5]; - - if (!tmdev->calibration_less_mode) { - calib_data[0] = readl_relaxed(tmdev->tsens_calib_addr + 0x228); - calib_data[1] = readl_relaxed(tmdev->tsens_calib_addr + 0x22c); - calib_data[2] = readl_relaxed(tmdev->tsens_calib_addr + 0x230); - - tsens_calibration_mode = - (calib_data[2] & TSENS_MDM9607_TSENS_CAL_SEL) >> - TSENS_MDM9607_CAL_SEL_SHIFT; - - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = - (calib_data[0] & TSENS_MDM9607_BASE0_MASK); - tsens0_point1 = (calib_data[0] & TSENS0_MDM9607_POINT1_MASK) - >> TSENS0_MDM9607_POINT1_SHIFT; - tsens1_point1 = (calib_data[0] & TSENS1_MDM9607_POINT1_MASK) - >> TSENS1_MDM9607_POINT1_SHIFT; - tsens2_point1 = (calib_data[1] & TSENS2_MDM9607_POINT1_MASK); - tsens3_point1 = (calib_data[1] & TSENS3_MDM9607_POINT1_MASK) - >> TSENS3_MDM9607_POINT1_SHIFT; - tsens4_point1 = (calib_data[2] & TSENS4_MDM9607_POINT1_MASK); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[2] & TSENS_MDM9607_BASE1_MASK) - >> TSENS_MDM9607_BASE1_SHIFT; - tsens0_point2 = (calib_data[0] & TSENS0_MDM9607_POINT2_MASK) - >> TSENS0_MDM9607_POINT2_SHIFT; - tsens1_point2 = (calib_data[0] & TSENS1_MDM9607_POINT2_MASK) - >> TSENS1_MDM9607_POINT2_SHIFT; - tsens2_point2 = (calib_data[1] & TSENS2_MDM9607_POINT2_MASK) - >> TSENS2_MDM9607_POINT2_SHIFT; - tsens3_point2 = (calib_data[1] & TSENS3_MDM9607_POINT2_MASK) - >> TSENS3_MDM9607_POINT2_SHIFT; - tsens4_point2 = (calib_data[2] & TSENS4_MDM9607_POINT2_MASK) - >> TSENS4_MDM9607_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { - pr_debug("TSENS in calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - calib_tsens_point2_data[i] = TSENS_NO_CALIB_POINT2_DATA; - calib_tsens_point1_data[i] = TSENS_NO_CALIB_POINT1_DATA; - } - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 2); - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 2); - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 2); - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 2); - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 2); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 2); - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 2); - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 2); - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 2); - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 2); - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* - * slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - * temp_120_degc - temp_30_degc (x2 - x1) - */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_msm8952_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens_base1_data = 0; - int tsens0_point1 = 0, tsens0_point2 = 0; - int tsens1_point1 = 0, tsens1_point2 = 0; - int tsens2_point1 = 0, tsens2_point2 = 0; - int tsens3_point1 = 0, tsens3_point2 = 0; - int tsens4_point1 = 0, tsens4_point2 = 0; - int tsens5_point1 = 0, tsens5_point2 = 0; - int tsens6_point1 = 0, tsens6_point2 = 0; - int tsens7_point1 = 0, tsens7_point2 = 0; - int tsens8_point1 = 0, tsens8_point2 = 0; - int tsens9_point1 = 0, tsens9_point2 = 0; - int tsens10_point1 = 0, tsens10_point2 = 0; - - int tsens_calibration_mode = 0, temp = 0; - uint32_t calib_data[5] = {0, 0, 0, 0, 0}; - uint32_t calib_tsens_point1_data[11], calib_tsens_point2_data[11]; - - if (!tmdev->calibration_less_mode) { - calib_data[0] = readl_relaxed( - TSENS_8939_EEPROM - (tmdev->tsens_calib_addr) + 0x30); - calib_data[1] = readl_relaxed( - (TSENS_8939_EEPROM - (tmdev->tsens_calib_addr) + 0x34)); - calib_data[2] = readl_relaxed( - (TSENS_8939_EEPROM - (tmdev->tsens_calib_addr))); - calib_data[3] = readl_relaxed( - (TSENS_8939_EEPROM - (tmdev->tsens_calib_addr) + 0x4)); - calib_data[4] = readl_relaxed( - (TSENS_8939_EEPROM - (tmdev->tsens_calib_addr) + 0x50)); - - tsens_calibration_mode = - (calib_data[0] & - TSENS_CONTR_14_TSENS_CAL_SEL); - - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[2] & - TSENS_CONTR_14_BASE0_MASK); - tsens0_point1 = (calib_data[0] & - TSENS0_CONTR_14_POINT1_MASK) - >> TSENS0_CONTR_14_POINT1_SHIFT; - tsens1_point1 = (calib_data[0] & - TSENS1_CONTR_14_POINT1_MASK) - >> TSENS1_CONTR_14_POINT1_SHIFT; - tsens2_point1 = (calib_data[0] & - TSENS2_CONTR_14_POINT1_MASK_0_4) - >> TSENS2_CONTR_14_POINT1_SHIFT_0_4; - temp = (calib_data[1] & TSENS2_CONTR_14_POINT1_MASK_5) - << TSENS2_CONTR_14_POINT1_SHIFT_5; - tsens2_point1 |= temp; - tsens3_point1 = (calib_data[1] & - TSENS3_CONTR_14_POINT1_MASK) - >> TSENS3_CONTR_14_POINT1_SHIFT; - tsens4_point1 = (calib_data[1] & - TSENS4_CONTR_14_POINT1_MASK) - >> TSENS4_CONTR_14_POINT1_SHIFT; - tsens5_point1 = (calib_data[2] & - TSENS5_CONTR_14_POINT1_MASK) - >> TSENS5_CONTR_14_POINT1_SHIFT; - tsens6_point1 = (calib_data[2] & - TSENS6_CONTR_14_POINT1_MASK) - >> TSENS6_CONTR_14_POINT1_SHIFT; - tsens7_point1 = (calib_data[3] & - TSENS7_CONTR_14_POINT1_MASK); - tsens8_point1 = (calib_data[3] & - TSENS8_CONTR_14_POINT1_MASK) - >> TSENS8_CONTR_14_POINT1_SHIFT; - tsens9_point1 = (calib_data[4] & - TSENS9_CONTR_14_POINT1_MASK); - tsens10_point1 = (calib_data[4] & - TSENS10_CONTR_14_POINT1_MASK) - >> TSENS10_CONTR_14_POINT1_SHIFT; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[3] & - TSENS_CONTR_14_BASE1_MASK) - >> TSENS_CONTR_14_BASE1_SHIFT; - tsens0_point2 = (calib_data[0] & - TSENS0_CONTR_14_POINT2_MASK) - >> TSENS0_CONTR_14_POINT2_SHIFT; - tsens1_point2 = (calib_data[0] & - TSENS1_CONTR_14_POINT2_MASK) - >> TSENS1_CONTR_14_POINT2_SHIFT; - tsens2_point2 = (calib_data[1] & - TSENS2_CONTR_14_POINT2_MASK) - >> TSENS2_CONTR_14_POINT2_SHIFT; - tsens3_point2 = (calib_data[1] & - TSENS3_CONTR_14_POINT2_MASK) - >> TSENS3_CONTR_14_POINT2_SHIFT; - tsens4_point2 = (calib_data[1] & - TSENS4_CONTR_14_POINT2_MASK) - >> TSENS4_CONTR_14_POINT2_SHIFT; - tsens5_point2 = (calib_data[2] & - TSENS5_CONTR_14_POINT2_MASK) - >> TSENS5_CONTR_14_POINT2_SHIFT; - tsens6_point2 = (calib_data[2] & - TSENS6_CONTR_14_POINT2_MASK) - >> TSENS6_CONTR_14_POINT2_SHIFT; - tsens7_point2 = (calib_data[3] & - TSENS7_CONTR_14_POINT2_MASK) - >> TSENS7_CONTR_14_POINT2_SHIFT; - tsens8_point2 = (calib_data[3] & - TSENS8_CONTR_14_POINT2_MASK) - >> TSENS8_CONTR_14_POINT2_SHIFT; - tsens9_point2 = (calib_data[4] & - TSENS9_CONTR_14_POINT2_MASK) - >> TSENS9_CONTR_14_POINT2_SHIFT; - tsens10_point2 = (calib_data[4] & - TSENS10_CONTR_14_POINT2_MASK) - >> TSENS10_CONTR_14_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { - pr_debug("TSENS in calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - calib_tsens_point2_data[i] = TSENS_NO_CALIB_POINT2_DATA; - calib_tsens_point1_data[i] = TSENS_NO_CALIB_POINT1_DATA; - } - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 2); - calib_tsens_point1_data[0] = calib_tsens_point1_data[0] + - TSENS_MSM8952_D30_WA_S0; - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 2); - calib_tsens_point1_data[1] = calib_tsens_point1_data[1] - - TSENS_MSM8952_D30_WA_S1; - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 2); - calib_tsens_point1_data[2] = calib_tsens_point1_data[2] + - TSENS_MSM8952_D30_WA_S2; - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 2); - calib_tsens_point1_data[3] = calib_tsens_point1_data[3] + - TSENS_MSM8952_D30_WA_S3; - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 2); - calib_tsens_point1_data[4] = calib_tsens_point1_data[4] + - TSENS_MSM8952_D30_WA_S4; - calib_tsens_point1_data[5] = - (((tsens_base0_data) + tsens5_point1) << 2); - calib_tsens_point1_data[5] = calib_tsens_point1_data[5] - - TSENS_MSM8952_D30_WA_S5; - calib_tsens_point1_data[6] = - (((tsens_base0_data) + tsens6_point1) << 2); - calib_tsens_point1_data[7] = - (((tsens_base0_data) + tsens7_point1) << 2); - calib_tsens_point1_data[7] = calib_tsens_point1_data[7] + - TSENS_MSM8952_D30_WA_S7; - calib_tsens_point1_data[8] = - (((tsens_base0_data) + tsens8_point1) << 2); - calib_tsens_point1_data[8] = calib_tsens_point1_data[8] + - TSENS_MSM8952_D30_WA_S8; - calib_tsens_point1_data[9] = - (((tsens_base0_data) + tsens9_point1) << 2); - calib_tsens_point1_data[10] = - (((tsens_base0_data) + tsens10_point1) << 2); - calib_tsens_point1_data[10] = calib_tsens_point1_data[10] - - TSENS_MSM8952_D30_WA_S10; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 2); - calib_tsens_point1_data[0] = calib_tsens_point1_data[0] - - TSENS_MSM8952_D120_WA_S0; - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 2); - calib_tsens_point1_data[1] = calib_tsens_point1_data[1] - - TSENS_MSM8952_D120_WA_S1; - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 2); - calib_tsens_point1_data[2] = calib_tsens_point1_data[2] + - TSENS_MSM8952_D120_WA_S2; - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 2); - calib_tsens_point1_data[3] = calib_tsens_point1_data[3] + - TSENS_MSM8952_D120_WA_S3; - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 2); - calib_tsens_point1_data[4] = calib_tsens_point1_data[4] + - TSENS_MSM8952_D120_WA_S4; - calib_tsens_point2_data[5] = - ((tsens_base1_data + tsens5_point2) << 2); - calib_tsens_point1_data[5] = calib_tsens_point1_data[5] - - TSENS_MSM8952_D120_WA_S5; - calib_tsens_point2_data[6] = - ((tsens_base1_data + tsens6_point2) << 2); - calib_tsens_point1_data[6] = calib_tsens_point1_data[6] - - TSENS_MSM8952_D120_WA_S6; - calib_tsens_point2_data[7] = - ((tsens_base1_data + tsens7_point2) << 2); - calib_tsens_point1_data[7] = calib_tsens_point1_data[7] + - TSENS_MSM8952_D120_WA_S7; - calib_tsens_point2_data[8] = - ((tsens_base1_data + tsens8_point2) << 2); - calib_tsens_point1_data[8] = calib_tsens_point1_data[8] + - TSENS_MSM8952_D120_WA_S8; - calib_tsens_point2_data[9] = - ((tsens_base1_data + tsens9_point2) << 2); - calib_tsens_point2_data[10] = - ((tsens_base1_data + tsens10_point2) << 2); - calib_tsens_point1_data[10] = calib_tsens_point1_data[10] - - TSENS_MSM8952_D120_WA_S10; - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB_N_WA) || - (tsens_calibration_mode == - TSENS_TWO_POINT_CALIB_N_OFFSET_WA)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 2); - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 2); - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 2); - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 2); - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 2); - calib_tsens_point1_data[5] = - (((tsens_base0_data) + tsens5_point1) << 2); - calib_tsens_point1_data[6] = - (((tsens_base0_data) + tsens6_point1) << 2); - calib_tsens_point1_data[7] = - (((tsens_base0_data) + tsens7_point1) << 2); - calib_tsens_point1_data[8] = - (((tsens_base0_data) + tsens8_point1) << 2); - calib_tsens_point1_data[9] = - (((tsens_base0_data) + tsens9_point1) << 2); - calib_tsens_point1_data[10] = - (((tsens_base0_data) + tsens10_point1) << 2); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB_N_WA) || - (tsens_calibration_mode == - TSENS_TWO_POINT_CALIB_N_OFFSET_WA)) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 2); - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 2); - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 2); - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 2); - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 2); - calib_tsens_point2_data[5] = - ((tsens_base1_data + tsens5_point2) << 2); - calib_tsens_point2_data[6] = - ((tsens_base1_data + tsens6_point2) << 2); - calib_tsens_point2_data[7] = - ((tsens_base1_data + tsens7_point2) << 2); - calib_tsens_point2_data[8] = - ((tsens_base1_data + tsens8_point2) << 2); - calib_tsens_point2_data[9] = - ((tsens_base1_data + tsens9_point2) << 2); - calib_tsens_point2_data[10] = - ((tsens_base1_data + tsens10_point2) << 2); - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* - * slope (m) = adc_code2 - adc_code1 (y2 - y1) - * temp_120_degc - temp_30_degc (x2 - x1) - */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - return 0; -} - -static int tsens_calib_msm8909_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens_base1_data = 0; - int tsens0_point1 = 0, tsens0_point2 = 0; - int tsens1_point1 = 0, tsens1_point2 = 0; - int tsens2_point1 = 0, tsens2_point2 = 0; - int tsens3_point1 = 0, tsens3_point2 = 0; - int tsens4_point1 = 0, tsens4_point2 = 0; - int tsens_calibration_mode = 0, temp = 0; - uint32_t calib_data[3] = {0, 0, 0}; - uint32_t calib_tsens_point1_data[5], calib_tsens_point2_data[5]; - - if (!tmdev->calibration_less_mode) { - - calib_data[0] = readl_relaxed( - TSENS_8939_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_8939_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - calib_data[2] = readl_relaxed( - (TSENS_8939_EEPROM(tmdev->tsens_calib_addr) + 0x3c)); - - tsens_calibration_mode = - (calib_data[2] & TSENS_MSM8909_TSENS_CAL_SEL) >> - TSENS_MSM8909_CAL_SEL_SHIFT; - - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[2] & TSENS_MSM8909_BASE0_MASK); - tsens0_point1 = (calib_data[0] & TSENS0_MSM8909_POINT1_MASK); - tsens1_point1 = (calib_data[0] & TSENS1_MSM8909_POINT1_MASK) - >> TSENS1_MSM8909_POINT1_SHIFT; - tsens2_point1 = (calib_data[0] & TSENS2_MSM8909_POINT1_MASK) - >> TSENS2_MSM8909_POINT1_SHIFT; - tsens3_point1 = (calib_data[1] & TSENS3_MSM8909_POINT1_MASK) - >> TSENS3_MSM8909_POINT1_SHIFT; - tsens4_point1 = (calib_data[1] & TSENS4_MSM8909_POINT1_MASK) - >> TSENS4_MSM8909_POINT1_SHIFT; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[2] & TSENS_MSM8909_BASE1_MASK) - >> TSENS_MSM8909_BASE1_SHIFT; - tsens0_point2 = (calib_data[0] & TSENS0_MSM8909_POINT2_MASK) - >> TSENS0_MSM8909_POINT2_SHIFT; - tsens1_point2 = (calib_data[0] & TSENS1_MSM8909_POINT2_MASK) - >> TSENS1_MSM8909_POINT2_SHIFT; - tsens2_point2 = - (calib_data[0] & TSENS2_MSM8909_POINT2_MASK_0_1) - >> TSENS2_MSM8909_POINT2_SHIFT_0_1; - temp = (calib_data[1] & TSENS2_MSM8909_POINT2_MASK_2_5) << - TSENS2_MSM8909_POINT2_SHIFT_2_5; - tsens2_point2 |= temp; - tsens3_point2 = (calib_data[1] & TSENS3_MSM8909_POINT2_MASK) - >> TSENS3_MSM8909_POINT2_SHIFT; - tsens4_point2 = (calib_data[1] & TSENS4_MSM8909_POINT2_MASK) - >> TSENS4_MSM8909_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 500; - calib_tsens_point1_data[1] = 500; - calib_tsens_point1_data[2] = 500; - calib_tsens_point1_data[3] = 500; - calib_tsens_point1_data[4] = 500; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 2); - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 2); - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 2); - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 2); - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 2); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 2); - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 2); - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 2); - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 2); - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 2); - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - * temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8939_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens_base1_data = 0; - int tsens0_point1 = 0, tsens0_point2 = 0; - int tsens1_point1 = 0, tsens1_point2 = 0; - int tsens2_point1 = 0, tsens2_point2 = 0; - int tsens3_point1 = 0, tsens3_point2 = 0; - int tsens4_point1 = 0, tsens4_point2 = 0; - int tsens5_point1 = 0, tsens5_point2 = 0; - int tsens6_point1 = 0, tsens6_point2 = 0; - int tsens7_point1 = 0, tsens7_point2 = 0; - int tsens8_point1 = 0, tsens8_point2 = 0; - int tsens_calibration_mode = 0, temp = 0; - uint32_t calib_data[4] = {0, 0, 0, 0}; - uint32_t calib_tsens_point1_data[9], calib_tsens_point2_data[9]; - - if (!tmdev->calibration_less_mode) { - - calib_data[0] = readl_relaxed( - TSENS_8939_EEPROM(tmdev->tsens_calib_addr) + 0x30); - calib_data[1] = readl_relaxed( - (TSENS_8939_EEPROM(tmdev->tsens_calib_addr) + 0x34)); - calib_data[2] = readl_relaxed( - (TSENS_8939_EEPROM(tmdev->tsens_calib_addr))); - calib_data[3] = readl_relaxed( - (TSENS_8939_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - - tsens_calibration_mode = - (calib_data[0] & TSENS_8939_TSENS_CAL_SEL); - - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[2] & TSENS_8939_BASE0_MASK); - tsens0_point1 = (calib_data[0] & TSENS0_8939_POINT1_MASK) >> - TSENS0_8939_POINT1_SHIFT; - tsens1_point1 = (calib_data[0] & TSENS1_8939_POINT1_MASK) >> - TSENS1_8939_POINT1_SHIFT; - tsens2_point1 = (calib_data[0] & TSENS2_8939_POINT1_MASK_0_4) - >> TSENS2_8939_POINT1_SHIFT_0_4; - temp = (calib_data[1] & TSENS2_8939_POINT1_MASK_5) << - TSENS2_8939_POINT1_SHIFT_5; - tsens2_point1 |= temp; - tsens3_point1 = (calib_data[1] & TSENS3_8939_POINT1_MASK) >> - TSENS3_8939_POINT1_SHIFT; - tsens4_point1 = (calib_data[1] & TSENS4_8939_POINT1_MASK) >> - TSENS4_8939_POINT1_SHIFT; - tsens5_point1 = (calib_data[2] & TSENS5_8939_POINT1_MASK) >> - TSENS5_8939_POINT1_SHIFT; - tsens6_point1 = (calib_data[2] & TSENS6_8939_POINT1_MASK) >> - TSENS6_8939_POINT1_SHIFT; - tsens7_point1 = (calib_data[3] & TSENS7_8939_POINT1_MASK); - tsens8_point1 = (calib_data[3] & TSENS8_8939_POINT1_MASK) >> - TSENS8_8939_POINT1_SHIFT; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[3] & TSENS_8939_BASE1_MASK) >> - TSENS_8939_BASE1_SHIFT; - tsens0_point2 = (calib_data[0] & TSENS0_8939_POINT2_MASK) >> - TSENS0_8939_POINT2_SHIFT; - tsens1_point2 = (calib_data[0] & TSENS1_8939_POINT2_MASK) >> - TSENS1_8939_POINT2_SHIFT; - tsens2_point2 = (calib_data[1] & TSENS2_8939_POINT2_MASK) >> - TSENS2_8939_POINT2_SHIFT; - tsens3_point2 = (calib_data[1] & TSENS3_8939_POINT2_MASK) >> - TSENS3_8939_POINT2_SHIFT; - tsens4_point2 = (calib_data[1] & TSENS4_8939_POINT2_MASK) >> - TSENS4_8939_POINT2_SHIFT; - tsens5_point2 = (calib_data[2] & TSENS5_8939_POINT2_MASK) >> - TSENS5_8939_POINT2_SHIFT; - tsens6_point2 = (calib_data[2] & TSENS6_8939_POINT2_MASK) >> - TSENS6_8939_POINT2_SHIFT; - tsens7_point2 = (calib_data[3] & TSENS7_8939_POINT2_MASK) >> - TSENS7_8939_POINT2_SHIFT; - tsens8_point2 = (calib_data[3] & TSENS8_8939_POINT2_MASK) >> - TSENS8_8939_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 500; - calib_tsens_point1_data[1] = 500; - calib_tsens_point1_data[2] = 500; - calib_tsens_point1_data[3] = 500; - calib_tsens_point1_data[4] = 500; - calib_tsens_point1_data[5] = 500; - calib_tsens_point1_data[6] = 500; - calib_tsens_point1_data[7] = 500; - calib_tsens_point1_data[8] = 500; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 2); - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 2); - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 2); - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 2); - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 2); - calib_tsens_point1_data[5] = - (((tsens_base0_data) + tsens5_point1) << 2); - calib_tsens_point1_data[6] = - (((tsens_base0_data) + tsens6_point1) << 2); - calib_tsens_point1_data[7] = - (((tsens_base0_data) + tsens7_point1) << 2); - calib_tsens_point1_data[8] = - (((tsens_base0_data) + tsens8_point1) << 2); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 2); - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 2); - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 2); - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 2); - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 2); - calib_tsens_point2_data[5] = - ((tsens_base1_data + tsens5_point2) << 2); - calib_tsens_point2_data[6] = - ((tsens_base1_data + tsens6_point2) << 2); - calib_tsens_point2_data[7] = - ((tsens_base1_data + tsens7_point2) << 2); - calib_tsens_point2_data[8] = - ((tsens_base1_data + tsens8_point2) << 2); - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - * temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8916_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens_base1_data = 0; - int tsens0_point1 = 0, tsens0_point2 = 0; - int tsens1_point1 = 0, tsens1_point2 = 0; - int tsens2_point1 = 0, tsens2_point2 = 0; - int tsens3_point1 = 0, tsens3_point2 = 0; - int tsens4_point1 = 0, tsens4_point2 = 0; - int tsens_calibration_mode = 0; - uint32_t calib_data[3] = {0, 0, 0}; - uint32_t calib_tsens_point1_data[5], calib_tsens_point2_data[5]; - - if (!tmdev->calibration_less_mode) { - - calib_data[0] = readl_relaxed( - TSENS_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - calib_data[2] = readl_relaxed( - (TSENS_EEPROM(tmdev->tsens_calib_addr) + 0x1c)); - - tsens_calibration_mode = - (calib_data[2] & TSENS_8916_TSENS_CAL_SEL) >> - TSENS_8916_CAL_SEL_SHIFT; - - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[0] & TSENS_8916_BASE0_MASK); - tsens0_point1 = (calib_data[0] & TSENS0_8916_POINT1_MASK) >> - TSENS0_8916_POINT1_SHIFT; - tsens1_point1 = (calib_data[0] & TSENS1_8916_POINT1_MASK) >> - TSENS1_8916_POINT1_SHIFT; - tsens2_point1 = (calib_data[0] & TSENS2_8916_POINT1_MASK) >> - TSENS2_8916_POINT1_SHIFT; - tsens3_point1 = (calib_data[1] & TSENS3_8916_POINT1_MASK) >> - TSENS3_8916_POINT1_SHIFT; - tsens4_point1 = (calib_data[1] & TSENS4_8916_POINT1_MASK) >> - TSENS4_8916_POINT1_SHIFT; - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[1] & TSENS_8916_BASE1_MASK) >> - TSENS_8916_BASE1_SHIFT; - tsens0_point2 = (calib_data[0] & TSENS0_8916_POINT2_MASK) >> - TSENS0_8916_POINT2_SHIFT; - tsens1_point2 = (calib_data[0] & TSENS1_8916_POINT2_MASK) >> - TSENS1_8916_POINT2_SHIFT; - tsens2_point2 = (calib_data[1] & TSENS2_8916_POINT2_MASK); - tsens3_point2 = (calib_data[1] & TSENS3_8916_POINT2_MASK) >> - TSENS3_8916_POINT2_SHIFT; - tsens4_point2 = (calib_data[1] & TSENS4_8916_POINT2_MASK) >> - TSENS4_8916_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 500; - calib_tsens_point1_data[1] = 500; - calib_tsens_point1_data[2] = 500; - calib_tsens_point1_data[3] = 500; - calib_tsens_point1_data[4] = 500; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - (((tsens_base0_data) + tsens0_point1) << 3); - calib_tsens_point1_data[1] = - (((tsens_base0_data) + tsens1_point1) << 3); - calib_tsens_point1_data[2] = - (((tsens_base0_data) + tsens2_point1) << 3); - calib_tsens_point1_data[3] = - (((tsens_base0_data) + tsens3_point1) << 3); - calib_tsens_point1_data[4] = - (((tsens_base0_data) + tsens4_point1) << 3); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - ((tsens_base1_data + tsens0_point2) << 3); - calib_tsens_point2_data[1] = - ((tsens_base1_data + tsens1_point2) << 3); - calib_tsens_point2_data[2] = - ((tsens_base1_data + tsens2_point2) << 3); - calib_tsens_point2_data[3] = - ((tsens_base1_data + tsens3_point2) << 3); - calib_tsens_point2_data[4] = - ((tsens_base1_data + tsens4_point2) << 3); - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - * temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_9630_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens0_point = 0, tsens1_point = 0; - int tsens2_point = 0, tsens3_point = 0, tsens4_point = 0; - int tsens_base1_data = 0, tsens_calibration_mode = 0, calib_mode = 0; - uint32_t calib_data[2], calib_tsens_point_data[5]; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - calib_data[0] = readl_relaxed( - TSENS_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - - calib_mode = (calib_data[1] & TSENS_TORINO_CALIB_PT) >> - TSENS_TORINO_CALIB_SHIFT; - pr_debug("calib mode is %d\n", calib_mode); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - tsens_base0_data = (calib_data[0] & TSENS_TORINO_BASE0); - tsens_base1_data = (calib_data[0] & TSENS_TORINO_BASE1) >> - TSENS_TORINO_BASE1_SHIFT; - tsens0_point = (calib_data[0] & TSENS_TORINO_POINT0) >> - TSENS_TORINO_POINT0_SHIFT; - tsens1_point = (calib_data[0] & TSENS_TORINO_POINT1) >> - TSENS_TORINO_POINT1_SHIFT; - tsens2_point = (calib_data[0] & TSENS_TORINO_POINT2) >> - TSENS_TORINO_POINT2_SHIFT; - tsens3_point = (calib_data[0] & TSENS_TORINO_POINT3) >> - TSENS_TORINO_POINT3_SHIFT; - tsens4_point = (calib_data[0] & TSENS_TORINO_POINT4) >> - TSENS_TORINO_POINT4_SHIFT; - calib_tsens_point_data[0] = tsens0_point; - calib_tsens_point_data[1] = tsens1_point; - calib_tsens_point_data[2] = tsens2_point; - calib_tsens_point_data[3] = tsens3_point; - calib_tsens_point_data[4] = tsens4_point; - } - - if (calib_mode == 0) { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - calib_tsens_point_data[0] = 532; - calib_tsens_point_data[1] = 532; - calib_tsens_point_data[2] = 532; - calib_tsens_point_data[3] = 532; - calib_tsens_point_data[4] = 532; - goto compute_intercept_slope; - } - -compute_intercept_slope: - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0, adc_code_of_tempx = 0; - - tmdev->sensor[i].calib_data_point2 = tsens_base1_data; - tmdev->sensor[i].calib_data_point1 = tsens_base0_data; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - adc_code_of_tempx = - tsens_base0_data + calib_tsens_point_data[i]; - pr_debug("offset_adc_code_of_tempx:0x%x\n", - adc_code_of_tempx); - tmdev->sensor[i].offset = (adc_code_of_tempx * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8994_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens0_point = 0, tsens1_point = 0; - int tsens2_point = 0, tsens3_point = 0, tsens4_point = 0; - int tsens5_point = 0, tsens6_point = 0, tsens7_point = 0; - int tsens8_point = 0, tsens9_point = 0, tsens10_point = 0; - int tsens11_point = 0, tsens12_point = 0, tsens13_point = 0; - int tsens14_point = 0, tsens15_point = 0; - int tsens_base1_data = 0, calib_mode = 0; - uint32_t calib_data[6], calib_tsens_point_data[16], calib_redun_sel; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - calib_redun_sel = readl_relaxed( - TSENS_8994_EEPROM_REDUN_SEL(tmdev->tsens_calib_addr)); - calib_redun_sel = calib_redun_sel & TSENS_8994_CAL_SEL_REDUN_MASK; - calib_redun_sel >>= TSENS_8994_CAL_SEL_REDUN_SHIFT; - - if (calib_redun_sel == TSENS_QFPROM_BACKUP_SEL) { - calib_data[0] = readl_relaxed( - TSENS_REDUN_REGION1_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - TSENS_REDUN_REGION2_EEPROM(tmdev->tsens_calib_addr)); - calib_data[2] = readl_relaxed( - TSENS_REDUN_REGION3_EEPROM(tmdev->tsens_calib_addr)); - calib_data[3] = readl_relaxed( - TSENS_REDUN_REGION4_EEPROM(tmdev->tsens_calib_addr)); - calib_data[4] = readl_relaxed( - TSENS_REDUN_REGION5_EEPROM(tmdev->tsens_calib_addr)); - - calib_mode = (calib_data[4] & TSENS_8994_REDUN_SEL_MASK); - pr_debug("calib mode is %d\n", calib_mode); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - tsens_base0_data = (calib_data[0] & - TSENS_BASE0_8994_REDUN_MASK) >> - TSENS_BASE0_8994_REDUN_MASK_SHIFT; - tsens_base1_data = (calib_data[0] & - TSENS_BASE1_BIT0_8994_REDUN_MASK) >> - TSENS_BASE1_BIT0_SHIFT_COMPUTE; - tsens_base1_data |= (calib_data[1] & - TSENS_BASE1_BIT1_9_8994_REDUN_MASK); - tsens0_point = (calib_data[1] & - TSENS0_OFFSET_8994_REDUN_MASK) >> - TSENS0_OFFSET_8994_REDUN_SHIFT; - tsens1_point = (calib_data[1] & - TSENS1_OFFSET_8994_REDUN_MASK) >> - TSENS1_OFFSET_8994_REDUN_SHIFT; - tsens2_point = (calib_data[1] & - TSENS2_OFFSET_8994_REDUN_MASK) >> - TSENS2_OFFSET_8994_REDUN_SHIFT; - tsens3_point = (calib_data[1] & - TSENS3_OFFSET_8994_REDUN_MASK) >> - TSENS3_OFFSET_8994_REDUN_SHIFT; - tsens4_point = (calib_data[1] & - TSENS4_OFFSET_8994_REDUN_MASK) >> - TSENS4_OFFSET_8994_REDUN_SHIFT; - tsens5_point = (calib_data[1] & - TSENS5_OFFSET_8994_REDUN_MASK_BIT0_2) >> - TSENS5_OFFSET_8994_REDUN_SHIFT_BIT0_2; - tsens5_point |= ((calib_data[2] & - TSENS5_OFFSET_8994_REDUN_MASK_BIT3) >> - TSENS5_OFFSET_8994_REDUN_SHIFT_BIT3); - tsens6_point = (calib_data[2] & - TSENS6_OFFSET_8994_REDUN_MASK) >> - TSENS6_OFFSET_8994_REDUN_SHIFT; - tsens7_point = (calib_data[2] & - TSENS7_OFFSET_8994_REDUN_MASK) >> - TSENS7_OFFSET_8994_REDUN_SHIFT; - tsens8_point = (calib_data[3] & - TSENS8_OFFSET_8994_REDUN_MASK); - tsens9_point = (calib_data[3] & - TSENS9_OFFSET_8994_REDUN_MASK) >> - TSENS9_OFFSET_8994_REDUN_SHIFT; - tsens10_point = (calib_data[3] & - TSENS10_OFFSET_8994_REDUN_MASK) >> - TSENS10_OFFSET_8994_REDUN_SHIFT; - tsens11_point = (calib_data[3] & - TSENS11_OFFSET_8994_REDUN_MASK) >> - TSENS11_OFFSET_8994_REDUN_SHIFT; - tsens12_point = (calib_data[3] & - TSENS12_OFFSET_8994_REDUN_MASK) >> - TSENS12_OFFSET_8994_REDUN_SHIFT; - tsens13_point = (calib_data[3] & - TSENS13_OFFSET_8994_REDUN_MASK) >> - TSENS13_OFFSET_8994_REDUN_SHIFT; - tsens14_point = (calib_data[3] & - TSENS14_OFFSET_8994_REDUN_MASK) >> - TSENS14_OFFSET_8994_REDUN_SHIFT; - tsens15_point = (calib_data[3] & - TSENS15_OFFSET_8994_REDUN_MASK) >> - TSENS15_OFFSET_8994_REDUN_SHIFT; - calib_tsens_point_data[0] = tsens0_point; - calib_tsens_point_data[1] = tsens1_point; - calib_tsens_point_data[2] = tsens2_point; - calib_tsens_point_data[3] = tsens3_point; - calib_tsens_point_data[4] = tsens4_point; - calib_tsens_point_data[5] = tsens5_point; - calib_tsens_point_data[6] = tsens6_point; - calib_tsens_point_data[7] = tsens7_point; - calib_tsens_point_data[8] = tsens8_point; - calib_tsens_point_data[9] = tsens9_point; - calib_tsens_point_data[10] = tsens10_point; - calib_tsens_point_data[11] = tsens11_point; - calib_tsens_point_data[12] = tsens12_point; - calib_tsens_point_data[13] = tsens13_point; - calib_tsens_point_data[14] = tsens14_point; - calib_tsens_point_data[15] = tsens15_point; - } else - goto calibration_less_mode; - } else { - calib_data[0] = readl_relaxed( - TSENS_8994_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_8994_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - calib_data[2] = readl_relaxed( - (TSENS_8994_EEPROM(tmdev->tsens_calib_addr) + 0x8)); - - calib_mode = (calib_data[2] & TSENS_8994_CAL_SEL_MASK) >> - TSENS_8994_CAL_SEL_SHIFT; - pr_debug("calib mode is %d\n", calib_mode); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - tsens_base0_data = (calib_data[0] & - TSENS_BASE0_8994_MASK); - tsens_base1_data = (calib_data[0] & - TSENS_BASE1_8994_MASK) >> - TSENS_BASE1_8994_SHIFT; - tsens0_point = (calib_data[0] & - TSENS0_OFFSET_8994_MASK) >> - TSENS0_OFFSET_8994_SHIFT; - tsens1_point = (calib_data[0] & - TSENS1_OFFSET_8994_MASK) >> - TSENS1_OFFSET_8994_SHIFT; - tsens2_point = (calib_data[0] & - TSENS2_OFFSET_8994_MASK) >> - TSENS2_OFFSET_8994_SHIFT; - tsens3_point = (calib_data[1] & - TSENS3_OFFSET_8994_MASK); - tsens4_point = (calib_data[1] & - TSENS4_OFFSET_8994_MASK) >> - TSENS4_OFFSET_8994_SHIFT; - tsens5_point = (calib_data[1] & - TSENS5_OFFSET_8994_MASK) >> - TSENS5_OFFSET_8994_SHIFT; - tsens6_point = (calib_data[1] & - TSENS6_OFFSET_8994_MASK) >> - TSENS6_OFFSET_8994_SHIFT; - tsens7_point = (calib_data[1] & - TSENS7_OFFSET_8994_MASK) >> - TSENS7_OFFSET_8994_SHIFT; - tsens8_point = (calib_data[1] & - TSENS8_OFFSET_8994_MASK) >> - TSENS8_OFFSET_8994_SHIFT; - tsens9_point = (calib_data[1] & - TSENS9_OFFSET_8994_MASK) >> - TSENS9_OFFSET_8994_SHIFT; - tsens10_point = (calib_data[1] & - TSENS10_OFFSET_8994_MASK) >> - TSENS10_OFFSET_8994_SHIFT; - tsens11_point = (calib_data[2] & - TSENS11_OFFSET_8994_MASK); - tsens12_point = (calib_data[2] & - TSENS12_OFFSET_8994_MASK) >> - TSENS12_OFFSET_8994_SHIFT; - tsens13_point = (calib_data[2] & - TSENS13_OFFSET_8994_MASK) >> - TSENS13_OFFSET_8994_SHIFT; - tsens14_point = (calib_data[2] & - TSENS14_OFFSET_8994_MASK) >> - TSENS14_OFFSET_8994_SHIFT; - tsens15_point = (calib_data[2] & - TSENS15_OFFSET_8994_MASK) >> - TSENS15_OFFSET_8994_SHIFT; - calib_tsens_point_data[0] = tsens0_point; - calib_tsens_point_data[1] = tsens1_point; - calib_tsens_point_data[2] = tsens2_point; - calib_tsens_point_data[3] = tsens3_point; - calib_tsens_point_data[4] = tsens4_point; - calib_tsens_point_data[5] = tsens5_point; - calib_tsens_point_data[6] = tsens6_point; - calib_tsens_point_data[7] = tsens7_point; - calib_tsens_point_data[8] = tsens8_point; - calib_tsens_point_data[9] = tsens9_point; - calib_tsens_point_data[10] = tsens10_point; - calib_tsens_point_data[11] = tsens11_point; - calib_tsens_point_data[12] = tsens12_point; - calib_tsens_point_data[13] = tsens13_point; - calib_tsens_point_data[14] = tsens14_point; - calib_tsens_point_data[15] = tsens15_point; - } else { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - calib_tsens_point_data[0] = 532; - calib_tsens_point_data[1] = 532; - calib_tsens_point_data[2] = 532; - calib_tsens_point_data[3] = 532; - calib_tsens_point_data[4] = 532; - calib_tsens_point_data[5] = 532; - calib_tsens_point_data[6] = 532; - calib_tsens_point_data[7] = 532; - calib_tsens_point_data[8] = 532; - calib_tsens_point_data[9] = 532; - calib_tsens_point_data[10] = 532; - calib_tsens_point_data[11] = 532; - calib_tsens_point_data[12] = 532; - calib_tsens_point_data[13] = 532; - calib_tsens_point_data[14] = 532; - calib_tsens_point_data[15] = 532; - } - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0, adc_code_of_tempx = 0; - - tmdev->sensor[i].calib_data_point2 = tsens_base1_data; - tmdev->sensor[i].calib_data_point1 = tsens_base0_data; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - adc_code_of_tempx = - tsens_base0_data + calib_tsens_point_data[i]; - pr_debug("offset_adc_code_of_tempx:0x%x\n", - adc_code_of_tempx); - tmdev->sensor[i].offset = (adc_code_of_tempx * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8992_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens0_point = 0, tsens1_point = 0; - int tsens2_point = 0, tsens3_point = 0, tsens4_point = 0; - int tsens5_point = 0, tsens6_point = 0, tsens7_point = 0; - int tsens8_point = 0, tsens9_point = 0, tsens10_point = 0; - int tsens11_point = 0, tsens12_point = 0, tsens13_point = 0; - int tsens14_point = 0, tsens15_point = 0; - int tsens_base1_data = 0, calib_mode = 0; - uint32_t calib_data[6], calib_tsens_point_data[16], calib_redun_sel; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - calib_redun_sel = readl_relaxed( - TSENS_8994_EEPROM_REDUN_SEL(tmdev->tsens_calib_addr)); - calib_redun_sel = calib_redun_sel & TSENS_8994_CAL_SEL_REDUN_MASK; - calib_redun_sel >>= TSENS_8994_CAL_SEL_REDUN_SHIFT; - - if (calib_redun_sel == TSENS_QFPROM_BACKUP_SEL) { - calib_data[0] = readl_relaxed( - TSENS_REDUN_REGION1_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - TSENS_REDUN_REGION2_EEPROM(tmdev->tsens_calib_addr)); - calib_data[2] = readl_relaxed( - TSENS_REDUN_REGION3_EEPROM(tmdev->tsens_calib_addr)); - calib_data[3] = readl_relaxed( - TSENS_REDUN_REGION4_EEPROM(tmdev->tsens_calib_addr)); - calib_data[4] = readl_relaxed( - TSENS_REDUN_REGION5_EEPROM(tmdev->tsens_calib_addr)); - - calib_mode = (calib_data[4] & TSENS_8994_REDUN_SEL_MASK); - pr_debug("calib mode is %d\n", calib_mode); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - tsens_base0_data = (calib_data[0] & - TSENS_BASE0_8994_REDUN_MASK) >> - TSENS_BASE0_8994_REDUN_MASK_SHIFT; - tsens_base1_data = (calib_data[0] & - TSENS_BASE1_BIT0_8994_REDUN_MASK) >> - TSENS_BASE1_BIT0_SHIFT_COMPUTE; - tsens_base1_data |= (calib_data[1] & - TSENS_BASE1_BIT1_9_8994_REDUN_MASK); - tsens0_point = (calib_data[1] & - TSENS0_OFFSET_8994_REDUN_MASK) >> - TSENS0_OFFSET_8994_REDUN_SHIFT; - tsens1_point = (calib_data[1] & - TSENS1_OFFSET_8994_REDUN_MASK) >> - TSENS1_OFFSET_8994_REDUN_SHIFT; - tsens2_point = (calib_data[1] & - TSENS2_OFFSET_8994_REDUN_MASK) >> - TSENS2_OFFSET_8994_REDUN_SHIFT; - tsens3_point = (calib_data[1] & - TSENS3_OFFSET_8994_REDUN_MASK) >> - TSENS3_OFFSET_8994_REDUN_SHIFT; - tsens4_point = (calib_data[1] & - TSENS4_OFFSET_8994_REDUN_MASK) >> - TSENS4_OFFSET_8994_REDUN_SHIFT; - tsens5_point = (calib_data[1] & - TSENS5_OFFSET_8994_REDUN_MASK_BIT0_2) >> - TSENS5_OFFSET_8994_REDUN_SHIFT_BIT0_2; - tsens5_point |= ((calib_data[2] & - TSENS5_OFFSET_8994_REDUN_MASK_BIT3) >> - TSENS5_OFFSET_8994_REDUN_SHIFT_BIT3); - tsens6_point = (calib_data[2] & - TSENS6_OFFSET_8994_REDUN_MASK) >> - TSENS6_OFFSET_8994_REDUN_SHIFT; - tsens7_point = (calib_data[2] & - TSENS7_OFFSET_8994_REDUN_MASK) >> - TSENS7_OFFSET_8994_REDUN_SHIFT; - tsens8_point = (calib_data[3] & - TSENS8_OFFSET_8994_REDUN_MASK); - tsens9_point = (calib_data[3] & - TSENS9_OFFSET_8994_REDUN_MASK) >> - TSENS9_OFFSET_8994_REDUN_SHIFT; - tsens10_point = (calib_data[3] & - TSENS10_OFFSET_8994_REDUN_MASK) >> - TSENS10_OFFSET_8994_REDUN_SHIFT; - tsens11_point = (calib_data[3] & - TSENS11_OFFSET_8994_REDUN_MASK) >> - TSENS11_OFFSET_8994_REDUN_SHIFT; - tsens12_point = (calib_data[3] & - TSENS12_OFFSET_8994_REDUN_MASK) >> - TSENS12_OFFSET_8994_REDUN_SHIFT; - tsens13_point = (calib_data[3] & - TSENS13_OFFSET_8994_REDUN_MASK) >> - TSENS13_OFFSET_8994_REDUN_SHIFT; - tsens14_point = (calib_data[3] & - TSENS14_OFFSET_8994_REDUN_MASK) >> - TSENS14_OFFSET_8994_REDUN_SHIFT; - tsens15_point = (calib_data[3] & - TSENS15_OFFSET_8994_REDUN_MASK) >> - TSENS15_OFFSET_8994_REDUN_SHIFT; - calib_tsens_point_data[0] = tsens0_point; - calib_tsens_point_data[1] = tsens1_point; - calib_tsens_point_data[2] = tsens2_point; - calib_tsens_point_data[3] = tsens3_point; - calib_tsens_point_data[4] = tsens4_point; - calib_tsens_point_data[5] = tsens5_point; - calib_tsens_point_data[6] = tsens7_point; - calib_tsens_point_data[7] = tsens9_point; - calib_tsens_point_data[8] = tsens10_point; - calib_tsens_point_data[9] = tsens11_point; - calib_tsens_point_data[10] = tsens12_point; - calib_tsens_point_data[11] = tsens13_point; - calib_tsens_point_data[12] = tsens14_point; - } else - goto calibration_less_mode; - } else { - calib_data[0] = readl_relaxed( - TSENS_8994_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_8994_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - calib_data[2] = readl_relaxed( - (TSENS_8994_EEPROM(tmdev->tsens_calib_addr) + 0x8)); - - calib_mode = (calib_data[2] & TSENS_8994_CAL_SEL_MASK) >> - TSENS_8994_CAL_SEL_SHIFT; - pr_debug("calib mode is %d\n", calib_mode); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - tsens_base0_data = (calib_data[0] & - TSENS_BASE0_8994_MASK); - tsens_base1_data = (calib_data[0] & - TSENS_BASE1_8994_MASK) >> - TSENS_BASE1_8994_SHIFT; - tsens0_point = (calib_data[0] & - TSENS0_OFFSET_8994_MASK) >> - TSENS0_OFFSET_8994_SHIFT; - tsens1_point = (calib_data[0] & - TSENS1_OFFSET_8994_MASK) >> - TSENS1_OFFSET_8994_SHIFT; - tsens2_point = (calib_data[0] & - TSENS2_OFFSET_8994_MASK) >> - TSENS2_OFFSET_8994_SHIFT; - tsens3_point = (calib_data[1] & - TSENS3_OFFSET_8994_MASK); - tsens4_point = (calib_data[1] & - TSENS4_OFFSET_8994_MASK) >> - TSENS4_OFFSET_8994_SHIFT; - tsens5_point = (calib_data[1] & - TSENS5_OFFSET_8994_MASK) >> - TSENS5_OFFSET_8994_SHIFT; - tsens7_point = (calib_data[1] & - TSENS6_OFFSET_8994_MASK) >> - TSENS6_OFFSET_8994_SHIFT; - tsens9_point = (calib_data[1] & - TSENS7_OFFSET_8994_MASK) >> - TSENS7_OFFSET_8994_SHIFT; - tsens10_point = (calib_data[1] & - TSENS8_OFFSET_8994_MASK) >> - TSENS8_OFFSET_8994_SHIFT; - tsens11_point = (calib_data[1] & - TSENS9_OFFSET_8994_MASK) >> - TSENS9_OFFSET_8994_SHIFT; - tsens12_point = (calib_data[1] & - TSENS10_OFFSET_8994_MASK) >> - TSENS10_OFFSET_8994_SHIFT; - tsens13_point = (calib_data[2] & - TSENS11_OFFSET_8994_MASK); - tsens14_point = (calib_data[2] & - TSENS12_OFFSET_8994_MASK) >> - TSENS12_OFFSET_8994_SHIFT; - calib_tsens_point_data[0] = tsens0_point; - calib_tsens_point_data[1] = tsens1_point; - calib_tsens_point_data[2] = tsens2_point; - calib_tsens_point_data[3] = tsens3_point; - calib_tsens_point_data[4] = tsens4_point; - calib_tsens_point_data[5] = tsens5_point; - calib_tsens_point_data[6] = tsens7_point; - calib_tsens_point_data[7] = tsens9_point; - calib_tsens_point_data[8] = tsens10_point; - calib_tsens_point_data[9] = tsens11_point; - calib_tsens_point_data[10] = tsens12_point; - calib_tsens_point_data[11] = tsens13_point; - calib_tsens_point_data[12] = tsens14_point; - } else { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - calib_tsens_point_data[0] = 532; - calib_tsens_point_data[1] = 532; - calib_tsens_point_data[2] = 532; - calib_tsens_point_data[3] = 532; - calib_tsens_point_data[4] = 532; - calib_tsens_point_data[5] = 532; - calib_tsens_point_data[6] = 532; - calib_tsens_point_data[7] = 532; - calib_tsens_point_data[8] = 532; - calib_tsens_point_data[9] = 532; - calib_tsens_point_data[10] = 532; - calib_tsens_point_data[11] = 532; - calib_tsens_point_data[12] = 532; - calib_tsens_point_data[13] = 532; - calib_tsens_point_data[14] = 532; - calib_tsens_point_data[15] = 532; - } - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0, adc_code_of_tempx = 0; - - tmdev->sensor[i].calib_data_point2 = tsens_base1_data; - tmdev->sensor[i].calib_data_point1 = tsens_base0_data; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (calib_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - adc_code_of_tempx = - tsens_base0_data + calib_tsens_point_data[i]; - pr_debug("offset_adc_code_of_tempx:0x%x\n", - adc_code_of_tempx); - tmdev->sensor[i].offset = (adc_code_of_tempx * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8x10_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens0_point1 = 0, tsens1_point1 = 0; - int tsens0_point2 = 0, tsens1_point2 = 0; - int tsens_base1_data = 0, tsens_calibration_mode = 0; - uint32_t calib_data[2], calib_redun_sel; - uint32_t calib_tsens_point1_data[2], calib_tsens_point2_data[2]; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - calib_redun_sel = readl_relaxed( - TSENS_EEPROM_8X10_2(tmdev->tsens_calib_addr)); - calib_redun_sel = calib_redun_sel & TSENS_8X10_REDUN_SEL_MASK; - calib_redun_sel >>= TSENS_8X10_REDUN_SEL_SHIFT; - pr_debug("calib_redun_sel:%x\n", calib_redun_sel); - - if (calib_redun_sel == TSENS_QFPROM_BACKUP_SEL) { - calib_data[0] = readl_relaxed( - TSENS_EEPROM_8X10_SPARE_1(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - TSENS_EEPROM_8X10_SPARE_2(tmdev->tsens_calib_addr)); - } else { - calib_data[0] = readl_relaxed( - TSENS_EEPROM_8X10_1(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_EEPROM_8X10_1(tmdev->tsens_calib_addr) + - TSENS_EEPROM_8X10_1_OFFSET)); - } - - tsens_calibration_mode = (calib_data[0] & TSENS_8X10_TSENS_CAL_SEL) - >> TSENS_8X10_CAL_SEL_SHIFT; - pr_debug("calib mode scheme:%x\n", tsens_calibration_mode); - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[0] & TSENS_8X10_BASE0_MASK); - tsens0_point1 = (calib_data[0] & TSENS0_8X10_POINT1_MASK) >> - TSENS0_8X10_POINT1_SHIFT; - tsens1_point1 = calib_data[1] & TSENS1_8X10_POINT1_MASK; - } else - goto calibration_less_mode; - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[0] & TSENS_8X10_BASE1_MASK) >> - TSENS_8X10_BASE1_SHIFT; - tsens0_point2 = (calib_data[0] & TSENS0_8X10_POINT2_MASK) >> - TSENS0_8X10_POINT2_SHIFT; - tsens1_point2 = (calib_data[1] & TSENS1_8X10_POINT2_MASK) >> - TSENS1_8X10_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 595; - calib_tsens_point1_data[1] = 629; - goto compute_intercept_slope; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - ((((tsens_base0_data) + tsens0_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[1] = - ((((tsens_base0_data) + tsens1_point1) << 2) | - TSENS_BIT_APPEND); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - (((tsens_base1_data + tsens0_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[1] = - (((tsens_base1_data + tsens1_point2) << 2) | - TSENS_BIT_APPEND); - } - -compute_intercept_slope: - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8x26_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base0_data = 0, tsens0_point1 = 0, tsens1_point1 = 0; - int tsens2_point1 = 0, tsens3_point1 = 0, tsens4_point1 = 0; - int tsens5_point1 = 0, tsens6_point1 = 0, tsens6_point2 = 0; - int tsens0_point2 = 0, tsens1_point2 = 0, tsens2_point2 = 0; - int tsens3_point2 = 0, tsens4_point2 = 0, tsens5_point2 = 0; - int tsens_base1_data = 0, tsens_calibration_mode = 0; - uint32_t calib_data[6]; - uint32_t calib_tsens_point1_data[7], calib_tsens_point2_data[7]; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - for (i = 0; i < TSENS_8X26_MAIN_CALIB_ADDR_RANGE; i++) - calib_data[i] = readl_relaxed( - (TSENS_EEPROM_8X26_1(tmdev->tsens_calib_addr)) - + (i * TSENS_SN_ADDR_OFFSET)); - calib_data[4] = readl_relaxed( - (TSENS_EEPROM_8X26_2(tmdev->tsens_calib_addr))); - calib_data[5] = readl_relaxed( - (TSENS_EEPROM_8X26_2(tmdev->tsens_calib_addr)) + 0x8); - - tsens_calibration_mode = (calib_data[5] & TSENS_8X26_TSENS_CAL_SEL) - >> TSENS_8X26_CAL_SEL_SHIFT; - pr_debug("calib mode scheme:%x\n", tsens_calibration_mode); - - if ((tsens_calibration_mode == TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base0_data = (calib_data[0] & TSENS_8X26_BASE0_MASK) - >> TSENS_8X26_BASE0_SHIFT; - tsens0_point1 = (calib_data[0] & TSENS0_8X26_POINT1_MASK) >> - TSENS0_8X26_POINT1_SHIFT; - tsens1_point1 = calib_data[1] & TSENS1_8X26_POINT1_MASK; - tsens2_point1 = (calib_data[1] & TSENS2_8X26_POINT1_MASK) >> - TSENS2_8X26_POINT1_SHIFT; - tsens3_point1 = (calib_data[1] & TSENS3_8X26_POINT1_MASK) >> - TSENS3_8X26_POINT1_SHIFT; - tsens4_point1 = (calib_data[1] & TSENS4_8X26_POINT1_MASK) >> - TSENS4_8X26_POINT1_SHIFT; - tsens5_point1 = (calib_data[1] & TSENS5_8X26_POINT1_MASK) >> - TSENS5_8X26_POINT1_SHIFT; - tsens6_point1 = (calib_data[2] & TSENS6_8X26_POINT1_MASK) >> - TSENS6_8X26_POINT1_SHIFT; - } else - goto calibration_less_mode; - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base1_data = (calib_data[3] & TSENS_8X26_BASE1_MASK); - tsens0_point2 = (calib_data[3] & TSENS0_8X26_POINT2_MASK) >> - TSENS0_8X26_POINT2_SHIFT; - tsens1_point2 = (calib_data[3] & TSENS1_8X26_POINT2_MASK) >> - TSENS1_8X26_POINT2_SHIFT; - tsens2_point2 = (calib_data[3] & TSENS2_8X26_POINT2_MASK) >> - TSENS2_8X26_POINT2_SHIFT; - tsens3_point2 = (calib_data[3] & TSENS3_8X26_POINT2_MASK) >> - TSENS3_8X26_POINT2_SHIFT; - tsens4_point2 = (calib_data[4] & TSENS4_8X26_POINT2_MASK) >> - TSENS4_8X26_POINT2_SHIFT; - tsens5_point2 = (calib_data[4] & TSENS5_8X26_POINT2_MASK) >> - TSENS5_8X26_POINT2_SHIFT; - tsens6_point2 = (calib_data[5] & TSENS6_8X26_POINT2_MASK) >> - TSENS6_8X26_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 595; - calib_tsens_point1_data[1] = 625; - calib_tsens_point1_data[2] = 553; - calib_tsens_point1_data[3] = 578; - calib_tsens_point1_data[4] = 505; - calib_tsens_point1_data[5] = 509; - calib_tsens_point1_data[6] = 507; - goto compute_intercept_slope; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - calib_tsens_point1_data[0] = - ((((tsens_base0_data) + tsens0_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[1] = - ((((tsens_base0_data) + tsens1_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[2] = - ((((tsens_base0_data) + tsens2_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[3] = - ((((tsens_base0_data) + tsens3_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[4] = - ((((tsens_base0_data) + tsens4_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[5] = - ((((tsens_base0_data) + tsens5_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[6] = - ((((tsens_base0_data) + tsens6_point1) << 2) | - TSENS_BIT_APPEND); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - (((tsens_base1_data + tsens0_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[1] = - (((tsens_base1_data + tsens1_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[2] = - (((tsens_base1_data + tsens2_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[3] = - (((tsens_base1_data + tsens3_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[4] = - (((tsens_base1_data + tsens4_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[5] = - (((tsens_base1_data + tsens5_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[6] = - (((tsens_base1_data + tsens6_point2) << 2) | - TSENS_BIT_APPEND); - } - -compute_intercept_slope: - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_8974_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base1_data = 0, tsens0_point1 = 0, tsens1_point1 = 0; - int tsens2_point1 = 0, tsens3_point1 = 0, tsens4_point1 = 0; - int tsens5_point1 = 0, tsens6_point1 = 0, tsens7_point1 = 0; - int tsens8_point1 = 0, tsens9_point1 = 0, tsens10_point1 = 0; - int tsens0_point2 = 0, tsens1_point2 = 0, tsens2_point2 = 0; - int tsens3_point2 = 0, tsens4_point2 = 0, tsens5_point2 = 0; - int tsens6_point2 = 0, tsens7_point2 = 0, tsens8_point2 = 0; - int tsens9_point2 = 0, tsens10_point2 = 0; - int tsens_base2_data = 0, tsens_calibration_mode = 0, temp = 0; - uint32_t calib_data[6], calib_redun_sel, calib_data_backup[4]; - uint32_t calib_tsens_point1_data[11], calib_tsens_point2_data[11]; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - calib_redun_sel = readl_relaxed( - TSENS_EEPROM_REDUNDANCY_SEL(tmdev->tsens_calib_addr)); - calib_redun_sel = calib_redun_sel & TSENS_QFPROM_BACKUP_REDUN_SEL; - calib_redun_sel >>= TSENS_QFPROM_BACKUP_REDUN_SHIFT; - pr_debug("calib_redun_sel:%x\n", calib_redun_sel); - - for (i = 0; i < TSENS_MAIN_CALIB_ADDR_RANGE; i++) { - calib_data[i] = readl_relaxed( - (TSENS_EEPROM(tmdev->tsens_calib_addr)) - + (i * TSENS_SN_ADDR_OFFSET)); - pr_debug("calib raw data row%d:0x%x\n", i, calib_data[i]); - } - - if (calib_redun_sel == TSENS_QFPROM_BACKUP_SEL) { - tsens_calibration_mode = (calib_data[4] & TSENS_CAL_SEL_0_1) - >> TSENS_CAL_SEL_SHIFT; - temp = (calib_data[5] & TSENS_CAL_SEL_2) - >> TSENS_CAL_SEL_SHIFT_2; - tsens_calibration_mode |= temp; - pr_debug("backup calib mode:%x\n", calib_redun_sel); - - for (i = 0; i < TSENS_BACKUP_CALIB_ADDR_RANGE; i++) - calib_data_backup[i] = readl_relaxed( - (TSENS_EEPROM_BACKUP_REGION( - tmdev->tsens_calib_addr)) - + (i * TSENS_SN_ADDR_OFFSET)); - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB) - || (tsens_calibration_mode == - TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == - TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base1_data = (calib_data_backup[0] & - TSENS_BASE1_MASK); - tsens0_point1 = (calib_data_backup[0] & - TSENS0_POINT1_MASK) >> - TSENS0_POINT1_SHIFT; - tsens1_point1 = (calib_data_backup[0] & - TSENS1_POINT1_MASK) >> TSENS1_POINT1_SHIFT; - tsens2_point1 = (calib_data_backup[0] & - TSENS2_POINT1_MASK) >> TSENS2_POINT1_SHIFT; - tsens3_point1 = (calib_data_backup[0] & - TSENS3_POINT1_MASK) >> TSENS3_POINT1_SHIFT; - tsens4_point1 = (calib_data_backup[1] & - TSENS4_POINT1_MASK); - tsens5_point1 = (calib_data_backup[1] & - TSENS5_POINT1_MASK) >> TSENS5_POINT1_SHIFT; - tsens6_point1 = (calib_data_backup[1] & - TSENS6_POINT1_MASK) >> TSENS6_POINT1_SHIFT; - tsens7_point1 = (calib_data_backup[1] & - TSENS7_POINT1_MASK) >> TSENS7_POINT1_SHIFT; - tsens8_point1 = (calib_data_backup[2] & - TSENS8_POINT1_MASK_BACKUP) >> - TSENS8_POINT1_SHIFT; - tsens9_point1 = (calib_data_backup[2] & - TSENS9_POINT1_MASK_BACKUP) >> - TSENS9_POINT1_BACKUP_SHIFT; - tsens10_point1 = (calib_data_backup[2] & - TSENS10_POINT1_MASK_BACKUP) >> - TSENS10_POINT1_BACKUP_SHIFT; - } else - goto calibration_less_mode; - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base2_data = (calib_data_backup[2] & - TSENS_BASE2_BACKUP_MASK) >> - TSENS_POINT2_BASE_BACKUP_SHIFT; - tsens0_point2 = (calib_data_backup[2] & - TSENS0_POINT2_BACKUP_MASK) >> - TSENS0_POINT2_BACKUP_SHIFT; - tsens1_point2 = (calib_data_backup[3] & - TSENS1_POINT2_BACKUP_MASK); - tsens2_point2 = (calib_data_backup[3] & - TSENS2_POINT2_BACKUP_MASK) >> - TSENS2_POINT2_BACKUP_SHIFT; - tsens3_point2 = (calib_data_backup[3] & - TSENS3_POINT2_BACKUP_MASK) >> - TSENS3_POINT2_BACKUP_SHIFT; - tsens4_point2 = (calib_data_backup[3] & - TSENS4_POINT2_BACKUP_MASK) >> - TSENS4_POINT2_BACKUP_SHIFT; - tsens5_point2 = (calib_data[4] & - TSENS5_POINT2_BACKUP_MASK) >> - TSENS5_POINT2_BACKUP_SHIFT; - tsens6_point2 = (calib_data[5] & - TSENS6_POINT2_BACKUP_MASK); - tsens7_point2 = (calib_data[5] & - TSENS7_POINT2_BACKUP_MASK) >> - TSENS7_POINT2_BACKUP_SHIFT; - tsens8_point2 = (calib_data[5] & - TSENS8_POINT2_BACKUP_MASK) >> - TSENS8_POINT2_BACKUP_SHIFT; - tsens9_point2 = (calib_data[5] & - TSENS9_POINT2_BACKUP_MASK) >> - TSENS9_POINT2_BACKUP_SHIFT; - tsens10_point2 = (calib_data[5] & - TSENS10_POINT2_BACKUP_MASK) - >> TSENS10_POINT2_BACKUP_SHIFT; - } - } else { - tsens_calibration_mode = (calib_data[1] & TSENS_CAL_SEL_0_1) - >> TSENS_CAL_SEL_SHIFT; - temp = (calib_data[3] & TSENS_CAL_SEL_2) - >> TSENS_CAL_SEL_SHIFT_2; - tsens_calibration_mode |= temp; - pr_debug("calib mode scheme:%x\n", tsens_calibration_mode); - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB) || - (tsens_calibration_mode == - TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - tsens_base1_data = (calib_data[0] & TSENS_BASE1_MASK); - tsens0_point1 = (calib_data[0] & TSENS0_POINT1_MASK) >> - TSENS0_POINT1_SHIFT; - tsens1_point1 = (calib_data[0] & TSENS1_POINT1_MASK) >> - TSENS1_POINT1_SHIFT; - tsens2_point1 = (calib_data[0] & TSENS2_POINT1_MASK) >> - TSENS2_POINT1_SHIFT; - tsens3_point1 = (calib_data[0] & TSENS3_POINT1_MASK) >> - TSENS3_POINT1_SHIFT; - tsens4_point1 = (calib_data[1] & TSENS4_POINT1_MASK); - tsens5_point1 = (calib_data[1] & TSENS5_POINT1_MASK) >> - TSENS5_POINT1_SHIFT; - tsens6_point1 = (calib_data[1] & TSENS6_POINT1_MASK) >> - TSENS6_POINT1_SHIFT; - tsens7_point1 = (calib_data[1] & TSENS7_POINT1_MASK) >> - TSENS7_POINT1_SHIFT; - tsens8_point1 = (calib_data[1] & TSENS8_POINT1_MASK) >> - TSENS8_POINT1_SHIFT; - tsens9_point1 = (calib_data[2] & TSENS9_POINT1_MASK); - tsens10_point1 = (calib_data[2] & TSENS10_POINT1_MASK) - >> TSENS10_POINT1_SHIFT; - } else - goto calibration_less_mode; - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base2_data = (calib_data[2] & TSENS_BASE2_MASK) >> - TSENS_POINT2_BASE_SHIFT; - tsens0_point2 = (calib_data[2] & TSENS0_POINT2_MASK) >> - TSENS0_POINT2_SHIFT; - tsens1_point2 = (calib_data[2] & TSENS1_POINT2_MASK) >> - TSENS1_POINT2_SHIFT; - tsens2_point2 = (calib_data[3] & TSENS2_POINT2_MASK); - tsens3_point2 = (calib_data[3] & TSENS3_POINT2_MASK) >> - TSENS3_POINT2_SHIFT; - tsens4_point2 = (calib_data[3] & TSENS4_POINT2_MASK) >> - TSENS4_POINT2_SHIFT; - tsens5_point2 = (calib_data[3] & TSENS5_POINT2_MASK) >> - TSENS5_POINT2_SHIFT; - tsens6_point2 = (calib_data[3] & TSENS6_POINT2_MASK) >> - TSENS6_POINT2_SHIFT; - tsens7_point2 = (calib_data[4] & TSENS7_POINT2_MASK); - tsens8_point2 = (calib_data[4] & TSENS8_POINT2_MASK) >> - TSENS8_POINT2_SHIFT; - tsens9_point2 = (calib_data[4] & TSENS9_POINT2_MASK) >> - TSENS9_POINT2_SHIFT; - tsens10_point2 = (calib_data[4] & TSENS10_POINT2_MASK) - >> TSENS10_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 502; - calib_tsens_point1_data[1] = 509; - calib_tsens_point1_data[2] = 503; - calib_tsens_point1_data[3] = 509; - calib_tsens_point1_data[4] = 505; - calib_tsens_point1_data[5] = 509; - calib_tsens_point1_data[6] = 507; - calib_tsens_point1_data[7] = 510; - calib_tsens_point1_data[8] = 508; - calib_tsens_point1_data[9] = 509; - calib_tsens_point1_data[10] = 508; - goto compute_intercept_slope; - } - } - - if (tsens_calibration_mode == TSENS_ONE_POINT_CALIB) { - calib_tsens_point1_data[0] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens0_point1; - calib_tsens_point1_data[1] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens1_point1; - calib_tsens_point1_data[2] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens2_point1; - calib_tsens_point1_data[3] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens3_point1; - calib_tsens_point1_data[4] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens4_point1; - calib_tsens_point1_data[5] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens5_point1; - calib_tsens_point1_data[6] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens6_point1; - calib_tsens_point1_data[7] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens7_point1; - calib_tsens_point1_data[8] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens8_point1; - calib_tsens_point1_data[9] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens9_point1; - calib_tsens_point1_data[10] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens10_point1; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - pr_debug("one point calibration calculation\n"); - calib_tsens_point1_data[0] = - ((((tsens_base1_data) + tsens0_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[1] = - ((((tsens_base1_data) + tsens1_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[2] = - ((((tsens_base1_data) + tsens2_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[3] = - ((((tsens_base1_data) + tsens3_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[4] = - ((((tsens_base1_data) + tsens4_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[5] = - ((((tsens_base1_data) + tsens5_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[6] = - ((((tsens_base1_data) + tsens6_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[7] = - ((((tsens_base1_data) + tsens7_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[8] = - ((((tsens_base1_data) + tsens8_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[9] = - ((((tsens_base1_data) + tsens9_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[10] = - ((((tsens_base1_data) + tsens10_point1) << 2) | - TSENS_BIT_APPEND); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - (((tsens_base2_data + tsens0_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[1] = - (((tsens_base2_data + tsens1_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[2] = - (((tsens_base2_data + tsens2_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[3] = - (((tsens_base2_data + tsens3_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[4] = - (((tsens_base2_data + tsens4_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[5] = - (((tsens_base2_data + tsens5_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[6] = - (((tsens_base2_data + tsens6_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[7] = - (((tsens_base2_data + tsens7_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[8] = - (((tsens_base2_data + tsens8_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[9] = - (((tsens_base2_data + tsens9_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[10] = - (((tsens_base2_data + tsens10_point2) << 2) | - TSENS_BIT_APPEND); - } - -compute_intercept_slope: - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d\n", tmdev->sensor[i].offset); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_9900_sensors(struct tsens_tm_device *tmdev) -{ - int i, tsens_base1_data = 0, tsens0_point1 = 0, tsens1_point1 = 0; - int tsens2_point1 = 0, tsens3_point1 = 0, tsens4_point1 = 0; - int tsens5_point1 = 0, tsens6_point1 = 0, tsens0_point2 = 0; - int tsens1_point2 = 0, tsens2_point2 = 0, tsens3_point2 = 0; - int tsens4_point2 = 0, tsens5_point2 = 0, tsens6_point2 = 0; - int tsens_base2_data = 0, tsens_calibration_mode = 0; - uint32_t calib_data[4], calib_redun_sel, calib_data_backup[4]; - uint32_t calib_tsens_point1_data[7], calib_tsens_point2_data[7]; - - if (tmdev->calibration_less_mode) - goto calibration_less_mode; - - calib_redun_sel = readl_relaxed( - TSENS_9900_EEPROM_REDUNDANCY_SEL(tmdev->tsens_calib_addr)); - calib_redun_sel = calib_redun_sel & TSENS_QFPROM_BACKUP_9900_REDUN_SEL; - calib_redun_sel >>= TSENS_QFPROM_BACKUP_9900_REDUN_SHIFT; - pr_debug("calib_redun_sel:%x\n", calib_redun_sel); - - if (calib_redun_sel == TSENS_QFPROM_BACKUP_SEL) { - for (i = 0; i < TSENS_9900_CALIB_ADDR_RANGE; i++) { - calib_data_backup[i] = readl_relaxed( - (TSENS_9900_EEPROM_BACKUP_REGION( - tmdev->tsens_calib_addr)) - + (i * TSENS_SN_ADDR_OFFSET)); - pr_debug("backup calib raw data row%d:0x%x\n", - i, calib_data_backup[i]); - } - - tsens_calibration_mode = (calib_data_backup[0] & - TSENS_9900_TSENS_CAL_SEL) >> TSENS_9900_CAL_SEL_SHIFT; - pr_debug("backup calib mode:%x\n", tsens_calibration_mode); - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB) - || (tsens_calibration_mode == - TSENS_TWO_POINT_CALIB) || - (tsens_calibration_mode == - TSENS_ONE_POINT_CALIB_OPTION_2)) { - tsens_base1_data = (calib_data_backup[0] & - TSENS_9900_BASE1_MASK); - tsens0_point1 = (calib_data_backup[0] & - TSENS0_9900_POINT1_MASK) >> - TSENS0_9900_POINT1_SHIFT; - tsens1_point1 = (calib_data_backup[1] & - TSENS1_9900_POINT1_MASK); - tsens2_point1 = (calib_data_backup[1] & - TSENS2_9900_POINT1_MASK) >> - TSENS2_9900_POINT1_SHIFT; - tsens3_point1 = (calib_data_backup[1] & - TSENS3_9900_POINT1_MASK) >> - TSENS3_9900_POINT1_SHIFT; - tsens4_point1 = (calib_data_backup[2] & - TSENS4_9900_POINT1_MASK) >> - TSENS4_9900_POINT1_SHIFT; - tsens5_point1 = (calib_data_backup[2] & - TSENS5_9900_POINT1_MASK) >> - TSENS5_9900_POINT1_SHIFT; - tsens6_point1 = (calib_data_backup[3] & - TSENS6_9900_POINT1_MASK); - } else - goto calibration_less_mode; - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base2_data = (calib_data_backup[0] & - TSENS_9900_BASE2_MASK) >> - TSENS_9900_BASE2_SHIFT; - tsens0_point2 = (calib_data_backup[0] & - TSENS0_9900_POINT2_MASK) >> - TSENS0_9900_POINT2_SHIFT; - tsens1_point2 = (calib_data_backup[1] & - TSENS1_9900_POINT2_MASK)>> - TSENS1_9900_POINT2_SHIFT; - tsens2_point2 = (calib_data_backup[1] & - TSENS2_9900_POINT2_MASK) >> - TSENS2_9900_POINT2_SHIFT; - tsens3_point2 = (calib_data_backup[2] & - TSENS3_9900_POINT2_MASK); - tsens4_point2 = (calib_data_backup[2] & - TSENS4_9900_POINT2_MASK) >> - TSENS4_9900_POINT2_SHIFT; - tsens5_point2 = (calib_data_backup[2] & - TSENS5_9900_POINT2_MASK) >> - TSENS5_9900_POINT2_SHIFT; - tsens6_point2 = (calib_data_backup[3] & - TSENS6_9900_POINT2_MASK) >> - TSENS6_9900_POINT2_SHIFT; - } - } else { - for (i = 0; i < TSENS_9900_CALIB_ADDR_RANGE; i++) { - calib_data[i] = readl_relaxed( - (TSENS_9900_EEPROM(tmdev->tsens_calib_addr)) - + (i * TSENS_SN_ADDR_OFFSET)); - pr_debug("calib raw data row%d:0x%x\n", i , calib_data[i]); - } - - tsens_calibration_mode = (calib_data[0] & - TSENS_9900_TSENS_CAL_SEL) >> TSENS_9900_CAL_SEL_SHIFT; - pr_debug("calib mode:%x\n", tsens_calibration_mode); - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB) || - (tsens_calibration_mode == - TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - tsens_base1_data = (calib_data[0] & - TSENS_9900_BASE1_MASK); - tsens0_point1 = (calib_data[0] & - TSENS0_9900_POINT1_MASK) >> - TSENS0_9900_POINT1_SHIFT; - tsens1_point1 = (calib_data[1] & - TSENS1_9900_POINT1_MASK); - tsens2_point1 = (calib_data[1] & - TSENS2_9900_POINT1_MASK) >> - TSENS2_9900_POINT1_SHIFT; - tsens3_point1 = (calib_data[1] & - TSENS3_9900_POINT1_MASK) >> - TSENS3_9900_POINT1_SHIFT; - tsens4_point1 = (calib_data[2] & - TSENS4_9900_POINT1_MASK) >> - TSENS4_9900_POINT1_SHIFT; - tsens5_point1 = (calib_data[2] & - TSENS5_9900_POINT1_MASK) >> - TSENS5_9900_POINT1_SHIFT; - tsens6_point1 = (calib_data[3] & - TSENS6_9900_POINT1_MASK); - } else - goto calibration_less_mode; - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base2_data = (calib_data[0] & - TSENS_9900_BASE2_MASK) >> - TSENS_9900_BASE2_SHIFT; - tsens0_point2 = (calib_data[0] & - TSENS0_9900_POINT2_MASK) >> - TSENS0_9900_POINT2_SHIFT; - tsens1_point2 = (calib_data[1] & - TSENS1_9900_POINT2_MASK) >> - TSENS1_9900_POINT2_SHIFT; - tsens2_point2 = (calib_data[1] & - TSENS2_9900_POINT2_MASK)>> - TSENS2_9900_POINT2_SHIFT; - tsens3_point2 = (calib_data[2] & - TSENS3_9900_POINT2_MASK); - tsens4_point2 = (calib_data[2] & - TSENS4_9900_POINT2_MASK) >> - TSENS4_9900_POINT2_SHIFT; - tsens5_point2 = (calib_data[2] & - TSENS5_9900_POINT2_MASK) >> - TSENS5_9900_POINT2_SHIFT; - tsens6_point2 = (calib_data[3] & - TSENS6_9900_POINT2_MASK) >> - TSENS6_9900_POINT2_SHIFT; - } - - if (tsens_calibration_mode == 0) { -calibration_less_mode: - pr_debug("TSENS is calibrationless mode\n"); - for (i = 0; i < tmdev->tsens_num_sensor; i++) - calib_tsens_point2_data[i] = 780; - calib_tsens_point1_data[0] = 502; - calib_tsens_point1_data[1] = 509; - calib_tsens_point1_data[2] = 503; - calib_tsens_point1_data[3] = 509; - calib_tsens_point1_data[4] = 505; - calib_tsens_point1_data[5] = 509; - calib_tsens_point1_data[6] = 507; - goto compute_intercept_slope; - } - } - - if (tsens_calibration_mode == TSENS_ONE_POINT_CALIB) { - calib_tsens_point1_data[0] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens0_point1; - calib_tsens_point1_data[1] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens1_point1; - calib_tsens_point1_data[2] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens2_point1; - calib_tsens_point1_data[3] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens3_point1; - calib_tsens_point1_data[4] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens4_point1; - calib_tsens_point1_data[5] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens5_point1; - calib_tsens_point1_data[6] = - (((tsens_base1_data) << 2) | TSENS_BIT_APPEND) - + tsens6_point1; - } - - if ((tsens_calibration_mode == TSENS_ONE_POINT_CALIB_OPTION_2) || - (tsens_calibration_mode == TSENS_TWO_POINT_CALIB)) { - pr_debug("one point calibration calculation\n"); - calib_tsens_point1_data[0] = - ((((tsens_base1_data) + tsens0_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[1] = - ((((tsens_base1_data) + tsens1_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[2] = - ((((tsens_base1_data) + tsens2_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[3] = - ((((tsens_base1_data) + tsens3_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[4] = - ((((tsens_base1_data) + tsens4_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[5] = - ((((tsens_base1_data) + tsens5_point1) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point1_data[6] = - ((((tsens_base1_data) + tsens6_point1) << 2) | - TSENS_BIT_APPEND); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - pr_debug("two point calibration calculation\n"); - calib_tsens_point2_data[0] = - (((tsens_base2_data + tsens0_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[1] = - (((tsens_base2_data + tsens1_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[2] = - (((tsens_base2_data + tsens2_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[3] = - (((tsens_base2_data + tsens3_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[4] = - (((tsens_base2_data + tsens4_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[5] = - (((tsens_base2_data + tsens5_point2) << 2) | - TSENS_BIT_APPEND); - calib_tsens_point2_data[6] = - (((tsens_base2_data + tsens6_point2) << 2) | - TSENS_BIT_APPEND); - } - -compute_intercept_slope: - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0; - - tmdev->sensor[i].calib_data_point2 = calib_tsens_point2_data[i]; - tmdev->sensor[i].calib_data_point1 = calib_tsens_point1_data[i]; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - tmdev->sensor[i].offset = (tmdev->sensor[i].calib_data_point1 * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d\n", tmdev->sensor[i].offset); - tmdev->prev_reading_avail = false; - } - - return 0; -} - -static int tsens_calib_msmzirc_sensors(struct tsens_tm_device *tmdev) -{ - int i = 0, tsens_base0_data = 0, tsens_base1_data = 0; - int tsens0_point = 0, tsens1_point = 0, tsens2_point = 0; - int tsens3_point = 0, tsens4_point = 0; - int tsens_calibration_mode = 0; - uint32_t calib_data[2] = {0, 0}; - uint32_t calib_tsens_point_data[5]; - - if (!tmdev->calibration_less_mode) { - calib_data[0] = readl_relaxed( - TSENS_EEPROM(tmdev->tsens_calib_addr)); - calib_data[1] = readl_relaxed( - (TSENS_EEPROM(tmdev->tsens_calib_addr) + 0x4)); - - tsens_calibration_mode = - (calib_data[1] & TSENS_ZIRC_CAL_SEL) >> - TSENS_ZIRC_CAL_SEL_SHIFT; - pr_debug("calib mode is %d\n", tsens_calibration_mode); - } - - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - tsens_base0_data = (calib_data[0] & TSENS_BASE0_ZIRC_MASK); - tsens_base1_data = (calib_data[0] & TSENS_BASE1_ZIRC_MASK) >> - TSENS_BASE1_ZIRC_SHIFT; - tsens0_point = (calib_data[0] & TSENS0_OFFSET_ZIRC_MASK) >> - TSENS0_OFFSET_ZIRC_SHIFT; - tsens1_point = (calib_data[0] & TSENS1_OFFSET_ZIRC_MASK) >> - TSENS1_OFFSET_ZIRC_SHIFT; - tsens2_point = (calib_data[0] & TSENS2_OFFSET_ZIRC_MASK) >> - TSENS2_OFFSET_ZIRC_SHIFT; - tsens3_point = (calib_data[1] & TSENS3_OFFSET_ZIRC_MASK); - tsens4_point = (calib_data[1] & TSENS4_OFFSET_ZIRC_MASK) >> - TSENS4_OFFSET_ZIRC_SHIFT; - calib_tsens_point_data[0] = tsens0_point; - calib_tsens_point_data[1] = tsens1_point; - calib_tsens_point_data[2] = tsens2_point; - calib_tsens_point_data[3] = tsens3_point; - calib_tsens_point_data[4] = tsens4_point; - } else { - if (tsens_calibration_mode == 0) { - pr_debug("TSENS is calibrationless mode\n"); - calib_tsens_point_data[0] = 532; - calib_tsens_point_data[1] = 532; - calib_tsens_point_data[2] = 532; - calib_tsens_point_data[3] = 532; - calib_tsens_point_data[4] = 532; - } - } - - for (i = 0; i < tmdev->tsens_num_sensor; i++) { - int32_t num = 0, den = 0, adc_code_of_tempx = 0; - - tmdev->sensor[i].calib_data_point2 = tsens_base1_data; - tmdev->sensor[i].calib_data_point1 = tsens_base0_data; - pr_debug("sensor:%d - calib_data_point1:0x%x, calib_data_point2:0x%x\n", - i, tmdev->sensor[i].calib_data_point1, - tmdev->sensor[i].calib_data_point2); - if (tsens_calibration_mode == TSENS_TWO_POINT_CALIB) { - /* slope (m) = adc_code2 - adc_code1 (y2 - y1)/ - * temp_120_degc - temp_30_degc (x2 - x1) */ - num = tmdev->sensor[i].calib_data_point2 - - tmdev->sensor[i].calib_data_point1; - num *= tmdev->tsens_factor; - den = TSENS_CAL_DEGC_POINT2 - TSENS_CAL_DEGC_POINT1; - tmdev->sensor[i].slope_mul_tsens_factor = num/den; - } - adc_code_of_tempx = - tsens_base0_data + calib_tsens_point_data[i]; - pr_debug("offset_adc_code_of_tempx:0x%x\n", - adc_code_of_tempx); - tmdev->sensor[i].offset = (adc_code_of_tempx * - tmdev->tsens_factor) - (TSENS_CAL_DEGC_POINT1 * - tmdev->sensor[i].slope_mul_tsens_factor); - pr_debug("offset:%d and slope:%d\n", tmdev->sensor[i].offset, - tmdev->sensor[i].slope_mul_tsens_factor); - tmdev->prev_reading_avail = false; - } - - return 0; -} -static int tsens_calib_sensors(struct tsens_tm_device *tmdev) -{ - int rc = 0; - - pr_debug("%s\n", __func__); - - if (!tmdev) - return -ENODEV; - - if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8974) - rc = tsens_calib_8974_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8X26) - rc = tsens_calib_8x26_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8X10) - rc = tsens_calib_8x10_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_9900) - rc = tsens_calib_9900_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_9630) - rc = tsens_calib_9630_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8916) - rc = tsens_calib_8916_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8939) - rc = tsens_calib_8939_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8994) - rc = tsens_calib_8994_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MSM8909) - rc = tsens_calib_msm8909_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MSMZIRC) - rc = tsens_calib_msmzirc_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_8992) - rc = tsens_calib_8992_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MSM8952) - rc = tsens_calib_msm8952_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MDM9607) - rc = tsens_calib_mdm9607_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MSM8937) - rc = tsens_calib_msm8937_msmgold_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_MSMGOLD) - rc = tsens_calib_msm8937_msmgold_sensors(tmdev); - else if (tmdev->calib_mode == TSENS_CALIB_FUSE_MAP_NONE) { - pr_debug("Fuse map info not required\n"); - rc = 0; - } else { - pr_err("TSENS Calib fuse not found\n"); - rc = -ENODEV; - } - - return rc; -} - static int get_device_tree_data(struct platform_device *pdev, struct tsens_tm_device *tmdev) { @@ -5436,7 +2180,6 @@ static int get_device_tree_data(struct platform_device *pdev, "qcom,calibration-less-mode"); tmdev->tsens_local_init = of_property_read_bool(of_node, "qcom,tsens-local-init"); - tmdev->calib_mode = (u32)(uintptr_t) id->data; sensor_id = devm_kzalloc(&pdev->dev, tsens_num_sensors * sizeof(u32), GFP_KERNEL); @@ -5498,41 +2241,27 @@ static int get_device_tree_data(struct platform_device *pdev, tmdev->wd_bark_val = wd_bark; } - if (!strcmp(id->compatible, "qcom,mdm9630-tsens") || - (!strcmp(id->compatible, "qcom,msmzirc-tsens")) || - (!strcmp(id->compatible, "qcom,msm8994-tsens")) || - (!strcmp(id->compatible, "qcom,msm8992-tsens"))) - tmdev->tsens_type = TSENS_TYPE2; - else if (!strcmp(id->compatible, "qcom,msm8996-tsens") || + if (!strcmp(id->compatible, "qcom,msm8996-tsens") || (!strcmp(id->compatible, "qcom,msm8998-tsens"))) tmdev->tsens_type = TSENS_TYPE3; else if (!strcmp(id->compatible, "qcom,msmtitanium-tsens") || - (!strcmp(id->compatible, "qcom,sdm660-tsens") || - (!strcmp(id->compatible, "qcom,sdm630-tsens") || - (!strcmp(id->compatible, "qcom,msmhamster-tsens"))))) { + (!strcmp(id->compatible, "qcom,sdm660-tsens")) || + (!strcmp(id->compatible, "qcom,sdm630-tsens")) || + (!strcmp(id->compatible, "qcom,msmhamster-tsens"))) { tmdev->tsens_type = TSENS_TYPE3; tsens_poll_check = 0; - } else if (!strcmp(id->compatible, "qcom,msm8952-tsens") || - (!strcmp(id->compatible, "qcom,msmgold-tsens")) || - (!strcmp(id->compatible, "qcom,msm8937-tsens"))) - tmdev->tsens_type = TSENS_TYPE4; - else + } else tmdev->tsens_type = TSENS_TYPE0; tmdev->tsens_valid_status_check = of_property_read_bool(of_node, "qcom,valid-status-check"); if (!tmdev->tsens_valid_status_check) { - if (!strcmp(id->compatible, "qcom,msm8994-tsens") || - (!strcmp(id->compatible, "qcom,msmzirc-tsens")) || - (!strcmp(id->compatible, "qcom,msm8992-tsens")) || - (!strcmp(id->compatible, "qcom,msm8996-tsens")) || - (!strcmp(id->compatible, "qcom,msm8952-tsens")) || - (!strcmp(id->compatible, "qcom,msm8937-tsens")) || + if (!strcmp(id->compatible, "qcom,msm8996-tsens") || (!strcmp(id->compatible, "qcom,msmtitanium-tsens")) || (!strcmp(id->compatible, "qcom,msm8998-tsens")) || - (!strcmp(id->compatible, "qcom,sdm660-tsens") || - (!strcmp(id->compatible, "qcom,sdm630-tsens") || - (!strcmp(id->compatible, "qcom,msmhamster-tsens"))))) + (!strcmp(id->compatible, "qcom,sdm660-tsens")) || + (!strcmp(id->compatible, "qcom,sdm630-tsens")) || + (!strcmp(id->compatible, "qcom,msmhamster-tsens"))) tmdev->tsens_valid_status_check = true; } @@ -5547,9 +2276,9 @@ static int get_device_tree_data(struct platform_device *pdev, if (!strcmp(id->compatible, "qcom,msm8996-tsens") || (!strcmp(id->compatible, "qcom,msm8998-tsens")) || (!strcmp(id->compatible, "qcom,msmhamster-tsens")) || - (!strcmp(id->compatible, "qcom,sdm660-tsens") || - (!strcmp(id->compatible, "qcom,sdm630-tsens") || - (!strcmp(id->compatible, "qcom,msmtitanium-tsens"))))) { + (!strcmp(id->compatible, "qcom,sdm660-tsens")) || + (!strcmp(id->compatible, "qcom,sdm630-tsens")) || + (!strcmp(id->compatible, "qcom,msmtitanium-tsens"))) { tmdev->tsens_critical_irq = platform_get_irq_byname(pdev, "tsens-critical"); @@ -5690,12 +2419,6 @@ static int tsens_tm_probe(struct platform_device *pdev) goto fail; } - rc = tsens_calib_sensors(tmdev); - if (rc < 0) { - pr_err("Calibration failed\n"); - goto fail; - } - rc = tsens_hw_init(tmdev); if (rc) return rc; diff --git a/drivers/video/fbdev/msm/mdss.h b/drivers/video/fbdev/msm/mdss.h index 23a5ef2af249..0cdf91da920c 100644 --- a/drivers/video/fbdev/msm/mdss.h +++ b/drivers/video/fbdev/msm/mdss.h @@ -164,6 +164,7 @@ enum mdss_hw_quirk { MDSS_QUIRK_SRC_SPLIT_ALWAYS, MDSS_QUIRK_MMSS_GDSC_COLLAPSE, MDSS_QUIRK_MDP_CLK_SET_RATE, + MDSS_QUIRK_HDR_SUPPORT_ENABLED, MDSS_QUIRK_MAX, }; diff --git a/drivers/video/fbdev/msm/mdss_compat_utils.c b/drivers/video/fbdev/msm/mdss_compat_utils.c index 9f1a24431de9..f499cdfd85ef 100644 --- a/drivers/video/fbdev/msm/mdss_compat_utils.c +++ b/drivers/video/fbdev/msm/mdss_compat_utils.c @@ -225,6 +225,7 @@ static struct mdp_input_layer *__create_layer_list( layer->transp_mask = layer32->transp_mask; layer->bg_color = layer32->bg_color; layer->blend_op = layer32->blend_op; + layer->color_space = layer32->color_space; layer->src_rect = layer32->src_rect; layer->dst_rect = layer32->dst_rect; layer->buffer = layer32->buffer; @@ -312,6 +313,8 @@ static int __compat_atomic_commit(struct fb_info *info, unsigned int cmd, ret = -EFAULT; return ret; } + + memset(&commit, 0, sizeof(struct mdp_layer_commit)); __copy_atomic_commit_struct(&commit, &commit32); if (commit32.commit_v1.output_layer) { diff --git a/drivers/video/fbdev/msm/mdss_compat_utils.h b/drivers/video/fbdev/msm/mdss_compat_utils.h index d6f85a493315..626792925cb6 100644 --- a/drivers/video/fbdev/msm/mdss_compat_utils.h +++ b/drivers/video/fbdev/msm/mdss_compat_utils.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2014-2015, The Linux Foundation. All rights reserved. + * Copyright (c) 2014-2016, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -15,6 +15,15 @@ #ifndef MDSS_COMPAT_UTILS_H #define MDSS_COMPAT_UTILS_H +/* + * To allow proper structure padding for 64bit/32bit target + */ +#ifdef __LP64 +#define MDP_LAYER_COMMIT_V1_PAD 3 +#else +#define MDP_LAYER_COMMIT_V1_PAD 4 +#endif + struct mdp_buf_sync32 { u32 flags; u32 acq_fen_fd_cnt; @@ -498,7 +507,8 @@ struct mdp_input_layer32 { uint16_t z_order; uint32_t transp_mask; uint32_t bg_color; - enum mdss_mdp_blend_op blend_op; + enum mdss_mdp_blend_op blend_op; + enum mdp_color_space color_space; struct mdp_rect src_rect; struct mdp_rect dst_rect; compat_caddr_t scale; @@ -512,7 +522,8 @@ struct mdp_output_layer32 { uint32_t flags; uint32_t writeback_ndx; struct mdp_layer_buffer buffer; - uint32_t reserved[6]; + enum mdp_color_space color_space; + uint32_t reserved[5]; }; struct mdp_layer_commit_v1_32 { uint32_t flags; @@ -523,7 +534,10 @@ struct mdp_layer_commit_v1_32 { uint32_t input_layer_cnt; compat_caddr_t output_layer; int retire_fence; - uint32_t reserved[6]; + compat_caddr_t dest_scaler; + uint32_t dest_scaler_cnt; + compat_caddr_t frc_info; + uint32_t reserved[MDP_LAYER_COMMIT_V1_PAD]; }; struct mdp_layer_commit32 { diff --git a/drivers/video/fbdev/msm/mdss_debug.c b/drivers/video/fbdev/msm/mdss_debug.c index 9ab88d4a7a52..8d06edf01d1d 100644 --- a/drivers/video/fbdev/msm/mdss_debug.c +++ b/drivers/video/fbdev/msm/mdss_debug.c @@ -169,7 +169,8 @@ static ssize_t panel_debug_base_reg_write(struct file *file, break; } /* End of a hex value in given string */ - bufp[NEXT_VALUE_OFFSET - 1] = 0; + if ((bufp + NEXT_VALUE_OFFSET - 1) < (buf + count)) + bufp[NEXT_VALUE_OFFSET - 1] = 0; } if (len < PANEL_CMD_MIN_TX_COUNT) { pr_err("wrong input reg len\n"); diff --git a/drivers/video/fbdev/msm/mdss_dsi_panel.c b/drivers/video/fbdev/msm/mdss_dsi_panel.c index 79e74df12988..29288f0bca74 100644 --- a/drivers/video/fbdev/msm/mdss_dsi_panel.c +++ b/drivers/video/fbdev/msm/mdss_dsi_panel.c @@ -2366,9 +2366,9 @@ static int mdss_dsi_panel_timing_from_dt(struct device_node *np, phy_timings_present = true; } - data = of_get_property(np, "qcom,mdss-dsi-panel-timings-8996", &len); + data = of_get_property(np, "qcom,mdss-dsi-panel-timings-phy-v2", &len); if ((!data) || (len != 40)) { - pr_debug("%s:%d, Unable to read 8996 Phy lane timing settings", + pr_debug("%s:%d, Unable to read phy-v2 lane timing settings", __func__, __LINE__); } else { for (i = 0; i < len; i++) diff --git a/drivers/video/fbdev/msm/mdss_fb.c b/drivers/video/fbdev/msm/mdss_fb.c index 0f5a156d638c..082986b0ade7 100644 --- a/drivers/video/fbdev/msm/mdss_fb.c +++ b/drivers/video/fbdev/msm/mdss_fb.c @@ -76,6 +76,12 @@ #define BLANK_FLAG_ULP FB_BLANK_NORMAL #endif +/* + * Time period for fps calulation in micro seconds. + * Default value is set to 1 sec. + */ +#define MDP_TIME_PERIOD_CALC_FPS_US 1000000 + static struct fb_info *fbi_list[MAX_FBI_LIST]; static int fbi_list_index; @@ -502,6 +508,22 @@ static void __mdss_fb_idle_notify_work(struct work_struct *work) mfd->idle_state = MDSS_FB_IDLE; } + +static ssize_t mdss_fb_get_fps_info(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct fb_info *fbi = dev_get_drvdata(dev); + struct msm_fb_data_type *mfd = fbi->par; + unsigned int fps_int, fps_float; + + if (mfd->panel_power_state != MDSS_PANEL_POWER_ON) + mfd->fps_info.measured_fps = 0; + fps_int = (unsigned int) mfd->fps_info.measured_fps; + fps_float = do_div(fps_int, 10); + return scnprintf(buf, PAGE_SIZE, "%d.%d\n", fps_int, fps_float); + +} + static ssize_t mdss_fb_get_idle_time(struct device *dev, struct device_attribute *attr, char *buf) { @@ -815,6 +837,8 @@ static DEVICE_ATTR(msm_fb_panel_status, S_IRUGO | S_IWUSR, mdss_fb_get_panel_status, mdss_fb_force_panel_dead); static DEVICE_ATTR(msm_fb_dfps_mode, S_IRUGO | S_IWUSR, mdss_fb_get_dfps_mode, mdss_fb_change_dfps_mode); +static DEVICE_ATTR(measured_fps, S_IRUGO | S_IWUSR | S_IWGRP, + mdss_fb_get_fps_info, NULL); static struct attribute *mdss_fb_attrs[] = { &dev_attr_msm_fb_type.attr, &dev_attr_msm_fb_split.attr, @@ -826,6 +850,7 @@ static struct attribute *mdss_fb_attrs[] = { &dev_attr_msm_fb_thermal_level.attr, &dev_attr_msm_fb_panel_status.attr, &dev_attr_msm_fb_dfps_mode.attr, + &dev_attr_measured_fps.attr, NULL, }; @@ -1196,6 +1221,7 @@ static int mdss_fb_probe(struct platform_device *pdev) return rc; } } + mdss_fb_init_fps_info(mfd); rc = pm_runtime_set_active(mfd->fbi->dev); if (rc < 0) @@ -2098,6 +2124,10 @@ err_put: dma_buf_put(mfd->fbmem_buf); fb_mmap_failed: ion_free(mfd->fb_ion_client, mfd->fb_ion_handle); + mfd->fb_attachment = NULL; + mfd->fb_table = NULL; + mfd->fb_ion_handle = NULL; + mfd->fbmem_buf = NULL; return rc; } @@ -2825,7 +2855,7 @@ static int __mdss_fb_wait_for_fence_sub(struct msm_sync_pt_data *sync_pt_data, wait_ms); pr_warn("%s: sync_fence_wait timed out! ", - sync_pt_data->fence_name); + fences[i]->name); pr_cont("Waiting %ld.%ld more seconds\n", (wait_ms/MSEC_PER_SEC), (wait_ms%MSEC_PER_SEC)); @@ -2977,6 +3007,7 @@ static int __mdss_fb_sync_buf_done_callback(struct notifier_block *p, case MDP_NOTIFY_FRAME_DONE: pr_debug("%s: frame done\n", sync_pt_data->fence_name); mdss_fb_signal_timeline(sync_pt_data); + mdss_fb_calc_fps(mfd); break; case MDP_NOTIFY_FRAME_CFG_DONE: if (sync_pt_data->async_wait_fences) @@ -5031,3 +5062,34 @@ void mdss_fb_report_panel_dead(struct msm_fb_data_type *mfd) KOBJ_CHANGE, envp); pr_err("Panel has gone bad, sending uevent - %s\n", envp[0]); } + + +/* + * mdss_fb_calc_fps() - Calculates fps value. + * @mfd : frame buffer structure associated with fb device. + * + * This function is called at frame done. It counts the number + * of frames done for every 1 sec. Stores the value in measured_fps. + * measured_fps value is 10 times the calculated fps value. + * For example, measured_fps= 594 for calculated fps of 59.4 + */ +void mdss_fb_calc_fps(struct msm_fb_data_type *mfd) +{ + ktime_t current_time_us; + u64 fps, diff_us; + + current_time_us = ktime_get(); + diff_us = (u64)ktime_us_delta(current_time_us, + mfd->fps_info.last_sampled_time_us); + mfd->fps_info.frame_count++; + + if (diff_us >= MDP_TIME_PERIOD_CALC_FPS_US) { + fps = ((u64)mfd->fps_info.frame_count) * 10000000; + do_div(fps, diff_us); + mfd->fps_info.measured_fps = (unsigned int)fps; + pr_debug(" MDP_FPS for fb%d is %d.%d\n", + mfd->index, (unsigned int)fps/10, (unsigned int)fps%10); + mfd->fps_info.last_sampled_time_us = current_time_us; + mfd->fps_info.frame_count = 0; + } +} diff --git a/drivers/video/fbdev/msm/mdss_fb.h b/drivers/video/fbdev/msm/mdss_fb.h index 2eb6c6456f29..1487c4e7f6e2 100644 --- a/drivers/video/fbdev/msm/mdss_fb.h +++ b/drivers/video/fbdev/msm/mdss_fb.h @@ -253,6 +253,12 @@ struct msm_fb_backup_type { bool atomic_commit; }; +struct msm_fb_fps_info { + u32 frame_count; + ktime_t last_sampled_time_us; + u32 measured_fps; +}; + struct msm_fb_data_type { u32 key; u32 index; @@ -271,6 +277,7 @@ struct msm_fb_data_type { int idle_time; u32 idle_state; + struct msm_fb_fps_info fps_info; struct delayed_work idle_notify_work; bool atomic_commit_pending; @@ -426,6 +433,10 @@ static inline bool mdss_fb_is_hdmi_primary(struct msm_fb_data_type *mfd) (mfd->panel_info->type == DTV_PANEL)); } +static inline void mdss_fb_init_fps_info(struct msm_fb_data_type *mfd) +{ + memset(&mfd->fps_info, 0, sizeof(mfd->fps_info)); +} int mdss_fb_get_phys_info(dma_addr_t *start, unsigned long *len, int fb_num); void mdss_fb_set_backlight(struct msm_fb_data_type *mfd, u32 bkl_lvl); void mdss_fb_update_backlight(struct msm_fb_data_type *mfd); @@ -449,4 +460,5 @@ u32 mdss_fb_get_mode_switch(struct msm_fb_data_type *mfd); void mdss_fb_report_panel_dead(struct msm_fb_data_type *mfd); void mdss_panelinfo_to_fb_var(struct mdss_panel_info *pinfo, struct fb_var_screeninfo *var); +void mdss_fb_calc_fps(struct msm_fb_data_type *mfd); #endif /* MDSS_FB_H */ diff --git a/drivers/video/fbdev/msm/mdss_mdp.c b/drivers/video/fbdev/msm/mdss_mdp.c index d9cfd2360ab3..7ed4b5404868 100644 --- a/drivers/video/fbdev/msm/mdss_mdp.c +++ b/drivers/video/fbdev/msm/mdss_mdp.c @@ -2146,6 +2146,7 @@ static void mdss_mdp_hw_rev_caps_init(struct mdss_data_type *mdata) mdata->has_wb_ubwc = true; set_bit(MDSS_CAPS_10_BIT_SUPPORTED, mdata->mdss_caps_map); set_bit(MDSS_CAPS_SEC_DETACH_SMMU, mdata->mdss_caps_map); + mdss_set_quirk(mdata, MDSS_QUIRK_HDR_SUPPORT_ENABLED); break; default: mdata->max_target_zorder = 4; /* excluding base layer */ @@ -2416,13 +2417,16 @@ static int mdss_mdp_get_pan_cfg(struct mdss_panel_cfg *pan_cfg) char *t = NULL; char pan_intf_str[MDSS_MAX_PANEL_LEN]; int rc, i, panel_len; - char pan_name[MDSS_MAX_PANEL_LEN]; + char pan_name[MDSS_MAX_PANEL_LEN] = {'\0'}; if (!pan_cfg) return -EINVAL; if (mdss_mdp_panel[0] == '0') { + pr_debug("panel name is not set\n"); pan_cfg->lk_cfg = false; + pan_cfg->pan_intf = MDSS_PANEL_INTF_INVALID; + return -EINVAL; } else if (mdss_mdp_panel[0] == '1') { pan_cfg->lk_cfg = true; } else { @@ -2432,7 +2436,7 @@ static int mdss_mdp_get_pan_cfg(struct mdss_panel_cfg *pan_cfg) return -EINVAL; } - /* skip lk cfg and delimiter; ex: "0:" */ + /* skip lk cfg and delimiter; ex: "1:" */ strlcpy(pan_name, &mdss_mdp_panel[2], MDSS_MAX_PANEL_LEN); t = strnstr(pan_name, ":", MDSS_MAX_PANEL_LEN); if (!t) { @@ -2689,6 +2693,8 @@ ssize_t mdss_mdp_show_capabilities(struct device *dev, SPRINT(" concurrent_writeback"); if (test_bit(MDSS_CAPS_AVR_SUPPORTED, mdata->mdss_caps_map)) SPRINT(" avr"); + if (mdss_has_quirk(mdata, MDSS_QUIRK_HDR_SUPPORT_ENABLED)) + SPRINT(" hdr"); SPRINT("\n"); #undef SPRINT @@ -2814,7 +2820,10 @@ static int mdss_mdp_probe(struct platform_device *pdev) struct resource *res; int rc; struct mdss_data_type *mdata; - bool display_on = false; + uint32_t intf_sel = 0; + uint32_t split_display = 0; + int num_of_display_on = 0; + int i = 0; if (!pdev->dev.of_node) { pr_err("MDP driver only supports device tree probe\n"); @@ -2941,7 +2950,6 @@ static int mdss_mdp_probe(struct platform_device *pdev) */ mdss_mdp_footswitch_ctrl_splash(true); mdss_hw_rev_init(mdata); - display_on = true; /*populate hw iomem base info from device tree*/ rc = mdss_mdp_parse_dt(pdev); @@ -3010,10 +3018,34 @@ static int mdss_mdp_probe(struct platform_device *pdev) * clk/regulator votes else turn off clk/regulators because purpose * here is to get mdp_rev. */ - display_on = (bool)readl_relaxed(mdata->mdp_base + + intf_sel = readl_relaxed(mdata->mdp_base + MDSS_MDP_REG_DISP_INTF_SEL); - if (!display_on) + split_display = readl_relaxed(mdata->mdp_base + + MDSS_MDP_REG_SPLIT_DISPLAY_EN); + if (intf_sel != 0) { + for (i = 0; i < 4; i++) + num_of_display_on += ((intf_sel >> i*8) & 0x000000FF); + + /* + * For split display enabled - DSI0, DSI1 interfaces are + * considered as single display. So decrement + * 'num_of_display_on' by 1 + */ + if (split_display) + num_of_display_on--; + } + if (!num_of_display_on) { mdss_mdp_footswitch_ctrl_splash(false); + } else { + mdata->handoff_pending = true; + /* + * If multiple displays are enabled in LK, ctrl_splash off will + * be called multiple times during splash_cleanup. Need to + * enable it symmetrically + */ + for (i = 1; i < num_of_display_on; i++) + mdss_mdp_footswitch_ctrl_splash(true); + } mdp_intr_cb = kcalloc(ARRAY_SIZE(mdp_irq_map), sizeof(struct intr_callback), GFP_KERNEL); @@ -3055,12 +3087,13 @@ static int mdss_mdp_probe(struct platform_device *pdev) mdss_res->mdp_irq_export[0] = MDSS_MDP_INTR_WB_0_DONE | MDSS_MDP_INTR_WB_1_DONE; - pr_info("mdss version = 0x%x, bootloader display is %s\n", - mdata->mdp_rev, display_on ? "on" : "off"); + pr_info("mdss version = 0x%x, bootloader display is %s, num %d, intf_sel=0x%08x\n", + mdata->mdp_rev, num_of_display_on ? "on" : "off", + num_of_display_on, intf_sel); probe_done: if (IS_ERR_VALUE(rc)) { - if (display_on) + if (!num_of_display_on) mdss_mdp_footswitch_ctrl_splash(false); if (mdata->regulator_notif_register) @@ -4800,6 +4833,14 @@ static void apply_dynamic_ot_limit(u32 *ot_lim, else *ot_lim = 6; break; + case MDSS_MDP_HW_REV_320: + if ((res <= RES_1080p) && (params->frame_rate <= 30)) + *ot_lim = 2; + else if ((res <= RES_1080p) && (params->frame_rate <= 60)) + *ot_lim = 6; + else if ((res <= RES_UHD) && (params->frame_rate <= 30)) + *ot_lim = 16; + break; default: if (res <= RES_1080p) { *ot_lim = 2; diff --git a/drivers/video/fbdev/msm/mdss_mdp.h b/drivers/video/fbdev/msm/mdss_mdp.h index ab2a7184aa45..d3d332d780d5 100644 --- a/drivers/video/fbdev/msm/mdss_mdp.h +++ b/drivers/video/fbdev/msm/mdss_mdp.h @@ -424,6 +424,7 @@ struct mdss_mdp_ctl_intfs_ops { struct mdss_mdp_cwb { struct mutex queue_lock; struct list_head data_queue; + struct list_head cleanup_queue; int valid; u32 wb_idx; struct mdp_output_layer layer; @@ -1322,12 +1323,21 @@ static inline int mdss_mdp_get_wb_ctl_support(struct mdss_data_type *mdata, bool rotator_session) { /* - * Initial control paths are used for primary and external - * interfaces and remaining control paths are used for WB - * interfaces. + * Any control path can be routed to any of the hardware datapaths. + * But there is a HW restriction for 3D Mux block. As the 3D Mux + * settings in the CTL registers are double buffered, if an interface + * uses it and disconnects, then the subsequent interface which gets + * connected should use the same control path in order to clear the + * 3D MUX settings. + * To handle this restriction, we are allowing WB also, to loop through + * all the avialable control paths, so that it can reuse the control + * path left by the external interface, thereby clearing the 3D Mux + * settings. + * The initial control paths can be used by Primary, External and WB. + * The rotator can use the remaining available control paths. */ return rotator_session ? (mdata->nctl - mdata->nmixers_wb) : - (mdata->nctl - mdata->nwb); + MDSS_MDP_CTL0; } static inline bool mdss_mdp_is_nrt_vbif_client(struct mdss_data_type *mdata, diff --git a/drivers/video/fbdev/msm/mdss_mdp_ctl.c b/drivers/video/fbdev/msm/mdss_mdp_ctl.c index 5744f7d037b4..5246e5d1166c 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_ctl.c +++ b/drivers/video/fbdev/msm/mdss_mdp_ctl.c @@ -703,6 +703,7 @@ int mdss_mdp_get_panel_params(struct mdss_mdp_pipe *pipe, *v_total = mixer->height; *xres = mixer->width; *h_total = mixer->width; + *fps = DEFAULT_FRAME_RATE; } return 0; @@ -714,7 +715,8 @@ int mdss_mdp_get_pipe_overlap_bw(struct mdss_mdp_pipe *pipe, struct mdss_data_type *mdata = mdss_mdp_get_mdata(); struct mdss_mdp_mixer *mixer = pipe->mixer_left; struct mdss_rect src, dst; - u32 v_total, fps, h_total, xres, src_h; + u32 v_total = 0, h_total = 0, xres = 0, src_h = 0; + u32 fps = DEFAULT_FRAME_RATE; *quota = 0; *quota_nocr = 0; @@ -3563,6 +3565,11 @@ int mdss_mdp_cwb_setup(struct mdss_mdp_ctl *ctl) goto cwb_setup_fail; } + /* Add to cleanup list */ + mutex_lock(&cwb->queue_lock); + list_add_tail(&cwb_data->next, &mdp5_data->cwb.cleanup_queue); + mutex_unlock(&cwb->queue_lock); + memset(&wb_args, 0, sizeof(wb_args)); wb_args.data = &cwb_data->data; diff --git a/drivers/video/fbdev/msm/mdss_mdp_intf_cmd.c b/drivers/video/fbdev/msm/mdss_mdp_intf_cmd.c index 6d5927cf3cdc..c249cac87b8a 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_intf_cmd.c +++ b/drivers/video/fbdev/msm/mdss_mdp_intf_cmd.c @@ -35,6 +35,8 @@ static DEFINE_MUTEX(cmd_clk_mtx); +static DEFINE_MUTEX(cmd_off_mtx); + enum mdss_mdp_cmd_autorefresh_state { MDP_AUTOREFRESH_OFF, MDP_AUTOREFRESH_ON_REQUESTED, @@ -1351,7 +1353,7 @@ static int mdss_mdp_cmd_add_lineptr_handler(struct mdss_mdp_ctl *ctl, unsigned long flags; int ret = 0; - mutex_lock(&ctl->offlock); + mutex_lock(&cmd_off_mtx); ctx = (struct mdss_mdp_cmd_ctx *) ctl->intf_ctx[MASTER_CTX]; if (!ctx || !ctl->is_master) { ret = -EINVAL; @@ -1379,7 +1381,7 @@ static int mdss_mdp_cmd_add_lineptr_handler(struct mdss_mdp_ctl *ctl, if (ctl->mfd->split_mode == MDP_DUAL_LM_DUAL_DISPLAY) mutex_unlock(&cmd_clk_mtx); done: - mutex_unlock(&ctl->offlock); + mutex_unlock(&cmd_off_mtx); return ret; } @@ -1820,7 +1822,7 @@ static int mdss_mdp_cmd_add_vsync_handler(struct mdss_mdp_ctl *ctl, bool enable_rdptr = false; int ret = 0; - mutex_lock(&ctl->offlock); + mutex_lock(&cmd_off_mtx); ctx = (struct mdss_mdp_cmd_ctx *) ctl->intf_ctx[MASTER_CTX]; if (!ctx) { pr_err("%s: invalid ctx\n", __func__); @@ -1857,7 +1859,7 @@ static int mdss_mdp_cmd_add_vsync_handler(struct mdss_mdp_ctl *ctl, } done: - mutex_unlock(&ctl->offlock); + mutex_unlock(&cmd_off_mtx); return ret; } @@ -3190,6 +3192,7 @@ int mdss_mdp_cmd_stop(struct mdss_mdp_ctl *ctl, int panel_power_state) MDSS_XLOG(ctx->panel_power_state, panel_power_state); mutex_lock(&ctl->offlock); + mutex_lock(&cmd_off_mtx); if (mdss_panel_is_power_off(panel_power_state)) { /* Transition to display off */ send_panel_events = true; @@ -3309,6 +3312,7 @@ end: } MDSS_XLOG(ctl->num, atomic_read(&ctx->koff_cnt), XLOG_FUNC_EXIT); + mutex_unlock(&cmd_off_mtx); mutex_unlock(&ctl->offlock); pr_debug("%s:-\n", __func__); diff --git a/drivers/video/fbdev/msm/mdss_mdp_overlay.c b/drivers/video/fbdev/msm/mdss_mdp_overlay.c index 4ae91cf8e81d..8f48956680fc 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_overlay.c +++ b/drivers/video/fbdev/msm/mdss_mdp_overlay.c @@ -3228,6 +3228,7 @@ int mdss_mdp_dfps_update_params(struct msm_fb_data_type *mfd, pr_warn("Unsupported FPS. Configuring to max_fps = %d\n", pdata->panel_info.max_fps); dfps = pdata->panel_info.max_fps; + dfps_data->fps = dfps; } dfps_update_panel_params(pdata, dfps_data); @@ -5872,10 +5873,24 @@ __vsync_retire_get_fence(struct msm_sync_pt_data *sync_pt_data) static void __cwb_wq_handler(struct work_struct *cwb_work) { struct mdss_mdp_cwb *cwb = NULL; + struct mdss_mdp_wb_data *cwb_data = NULL; cwb = container_of(cwb_work, struct mdss_mdp_cwb, cwb_work); blocking_notifier_call_chain(&cwb->notifier_head, MDP_NOTIFY_FRAME_DONE, NULL); + + /* free the buffer from cleanup queue */ + mutex_lock(&cwb->queue_lock); + cwb_data = list_first_entry_or_null(&cwb->cleanup_queue, + struct mdss_mdp_wb_data, next); + __list_del_entry(&cwb_data->next); + mutex_unlock(&cwb->queue_lock); + if (cwb_data == NULL) { + pr_err("no output buffer for cwb cleanup\n"); + return; + } + mdss_mdp_data_free(&cwb_data->data, true, DMA_FROM_DEVICE); + kfree(cwb_data); } static int __vsync_set_vsync_handler(struct msm_fb_data_type *mfd) @@ -6106,6 +6121,7 @@ int mdss_mdp_overlay_init(struct msm_fb_data_type *mfd) mutex_init(&mdp5_data->cwb.queue_lock); mutex_init(&mdp5_data->cwb.cwb_sync_pt_data.sync_mutex); INIT_LIST_HEAD(&mdp5_data->cwb.data_queue); + INIT_LIST_HEAD(&mdp5_data->cwb.cleanup_queue); snprintf(timeline_name, sizeof(timeline_name), "cwb%d", mfd->index); mdp5_data->cwb.cwb_sync_pt_data.fence_name = "cwb-fence"; diff --git a/drivers/video/fbdev/msm/mdss_mdp_pp.c b/drivers/video/fbdev/msm/mdss_mdp_pp.c index 917e6889124d..30dd3c856c7f 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_pp.c +++ b/drivers/video/fbdev/msm/mdss_mdp_pp.c @@ -1655,10 +1655,6 @@ int mdss_mdp_scaler_lut_cfg(struct mdp_scale_data_v2 *scaler, } } - if (scaler->lut_flag & SCALER_LUT_SWAP) - writel_relaxed(BIT(0), MDSS_MDP_REG_SCALER_COEF_LUT_CTRL + - offset); - return 0; } @@ -1795,6 +1791,10 @@ int mdss_mdp_qseed3_setup(struct mdp_scale_data_v2 *scaler, __func__); return -EINVAL; } + if (scaler->lut_flag & SCALER_LUT_SWAP) + writel_relaxed(BIT(0), + MDSS_MDP_REG_SCALER_COEF_LUT_CTRL + + offset); } writel_relaxed(phase_init, diff --git a/drivers/video/fbdev/msm/mdss_mdp_pp_cache_config.c b/drivers/video/fbdev/msm/mdss_mdp_pp_cache_config.c index e51cf44c2de2..017a2f10dfbc 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_pp_cache_config.c +++ b/drivers/video/fbdev/msm/mdss_mdp_pp_cache_config.c @@ -1394,7 +1394,6 @@ exit: ret = -EFAULT; kfree(cfg_payload); cfg_payload = NULL; - goto exit; } pp_info->igc_cfg.cfg_payload = cfg_payload; return ret; diff --git a/drivers/video/fbdev/msm/mdss_rotator.c b/drivers/video/fbdev/msm/mdss_rotator.c index 8612d60deeca..d001f148b443 100644 --- a/drivers/video/fbdev/msm/mdss_rotator.c +++ b/drivers/video/fbdev/msm/mdss_rotator.c @@ -2386,6 +2386,31 @@ handle_request32_err: return ret; } +static unsigned int __do_compat_ioctl_rot(unsigned int cmd32) +{ + unsigned int cmd; + + switch (cmd32) { + case MDSS_ROTATION_REQUEST32: + cmd = MDSS_ROTATION_REQUEST; + break; + case MDSS_ROTATION_OPEN32: + cmd = MDSS_ROTATION_OPEN; + break; + case MDSS_ROTATION_CLOSE32: + cmd = MDSS_ROTATION_CLOSE; + break; + case MDSS_ROTATION_CONFIG32: + cmd = MDSS_ROTATION_CONFIG; + break; + default: + cmd = cmd32; + break; + } + + return cmd; +} + static long mdss_rotator_compat_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { @@ -2408,6 +2433,8 @@ static long mdss_rotator_compat_ioctl(struct file *file, unsigned int cmd, return -EINVAL; } + cmd = __do_compat_ioctl_rot(cmd); + switch (cmd) { case MDSS_ROTATION_REQUEST: ATRACE_BEGIN("rotator_request32"); diff --git a/drivers/video/fbdev/msm/mdss_rotator_internal.h b/drivers/video/fbdev/msm/mdss_rotator_internal.h index dae5f5cb117e..30d460abf5b7 100644 --- a/drivers/video/fbdev/msm/mdss_rotator_internal.h +++ b/drivers/video/fbdev/msm/mdss_rotator_internal.h @@ -187,6 +187,23 @@ struct mdss_rot_mgr { }; #ifdef CONFIG_COMPAT + +/* open a rotation session */ +#define MDSS_ROTATION_OPEN32 \ + _IOWR(MDSS_ROTATOR_IOCTL_MAGIC, 1, compat_caddr_t) + +/* change the rotation session configuration */ +#define MDSS_ROTATION_CONFIG32 \ + _IOWR(MDSS_ROTATOR_IOCTL_MAGIC, 2, compat_caddr_t) + +/* queue the rotation request */ +#define MDSS_ROTATION_REQUEST32 \ + _IOWR(MDSS_ROTATOR_IOCTL_MAGIC, 3, compat_caddr_t) + +/* close a rotation session with the specified rotation session ID */ +#define MDSS_ROTATION_CLOSE32 \ + _IOW(MDSS_ROTATOR_IOCTL_MAGIC, 4, unsigned int) + struct mdp_rotation_request32 { uint32_t version; uint32_t flags; diff --git a/drivers/video/fbdev/msm/mdss_smmu.c b/drivers/video/fbdev/msm/mdss_smmu.c index 2239791fdad0..a08eec8e1606 100644 --- a/drivers/video/fbdev/msm/mdss_smmu.c +++ b/drivers/video/fbdev/msm/mdss_smmu.c @@ -177,7 +177,6 @@ static int mdss_smmu_attach_v2(struct mdss_data_type *mdata) struct mdss_smmu_client *mdss_smmu; int i, rc = 0; - mutex_lock(&mdp_iommu_lock); for (i = 0; i < MDSS_IOMMU_MAX_DOMAIN; i++) { if (!mdss_smmu_is_valid_domain_type(mdata, i)) continue; @@ -211,11 +210,9 @@ static int mdss_smmu_attach_v2(struct mdss_data_type *mdata) } } else { pr_err("iommu device not attached for domain[%d]\n", i); - mutex_unlock(&mdp_iommu_lock); return -ENODEV; } } - mutex_unlock(&mdp_iommu_lock); return 0; @@ -228,7 +225,6 @@ err: mdss_smmu->domain_attached = false; } } - mutex_unlock(&mdp_iommu_lock); return rc; } @@ -245,7 +241,6 @@ static int mdss_smmu_detach_v2(struct mdss_data_type *mdata) struct mdss_smmu_client *mdss_smmu; int i; - mutex_lock(&mdp_iommu_lock); for (i = 0; i < MDSS_IOMMU_MAX_DOMAIN; i++) { if (!mdss_smmu_is_valid_domain_type(mdata, i)) continue; @@ -270,7 +265,6 @@ static int mdss_smmu_detach_v2(struct mdss_data_type *mdata) } } } - mutex_unlock(&mdp_iommu_lock); return 0; } diff --git a/drivers/video/fbdev/msm/mdss_smmu.h b/drivers/video/fbdev/msm/mdss_smmu.h index f7e6e275c16a..73b978b72f0e 100644 --- a/drivers/video/fbdev/msm/mdss_smmu.h +++ b/drivers/video/fbdev/msm/mdss_smmu.h @@ -150,18 +150,26 @@ static inline int mdss_smmu_attach(struct mdss_data_type *mdata) { int rc; + mdata->mdss_util->iommu_lock(); MDSS_XLOG(mdata->iommu_attached); + if (mdata->iommu_attached) { pr_debug("mdp iommu already attached\n"); - return 0; + rc = 0; + goto end; } - if (!mdata->smmu_ops.smmu_attach) - return -ENOSYS; + if (!mdata->smmu_ops.smmu_attach) { + rc = -ENODEV; + goto end; + } rc = mdata->smmu_ops.smmu_attach(mdata); if (!rc) mdata->iommu_attached = true; + +end: + mdata->mdss_util->iommu_unlock(); return rc; } @@ -169,19 +177,26 @@ static inline int mdss_smmu_detach(struct mdss_data_type *mdata) { int rc; + mdata->mdss_util->iommu_lock(); MDSS_XLOG(mdata->iommu_attached); if (!mdata->iommu_attached) { pr_debug("mdp iommu already dettached\n"); - return 0; + rc = 0; + goto end; } - if (!mdata->smmu_ops.smmu_detach) - return -ENOSYS; + if (!mdata->smmu_ops.smmu_detach) { + rc = -ENODEV; + goto end; + } rc = mdata->smmu_ops.smmu_detach(mdata); if (!rc) mdata->iommu_attached = false; + +end: + mdata->mdss_util->iommu_unlock(); return rc; } @@ -247,7 +262,7 @@ static inline void mdss_smmu_dma_free_coherent(struct device *dev, size_t size, void *cpu_addr, dma_addr_t phys, dma_addr_t iova, int domain) { struct mdss_data_type *mdata = mdss_mdp_get_mdata(); - if (mdata->smmu_ops.smmu_dma_free_coherent) + if (mdata && mdata->smmu_ops.smmu_dma_free_coherent) mdata->smmu_ops.smmu_dma_free_coherent(dev, size, cpu_addr, phys, iova, domain); } diff --git a/include/linux/qpnp/power-on.h b/include/linux/input/qpnp-power-on.h index da8f5a8622dd..a2624ab57826 100644 --- a/include/linux/qpnp/power-on.h +++ b/include/linux/input/qpnp-power-on.h @@ -1,4 +1,4 @@ -/* Copyright (c) 2012-2015, The Linux Foundation. All rights reserved. +/* Copyright (c) 2012-2015, 2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -60,7 +60,7 @@ enum pon_restart_reason { PON_RESTART_REASON_KEYS_CLEAR = 0x06, }; -#ifdef CONFIG_QPNP_POWER_ON +#ifdef CONFIG_INPUT_QPNP_POWER_ON int qpnp_pon_system_pwr_off(enum pon_power_off_type type); int qpnp_pon_is_warm_reset(void); int qpnp_pon_trigger_config(enum pon_trigger_source pon_src, bool enable); diff --git a/include/soc/qcom/socinfo.h b/include/soc/qcom/socinfo.h index 611bdf856d1d..ac36df5769ee 100644 --- a/include/soc/qcom/socinfo.h +++ b/include/soc/qcom/socinfo.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2009-2016, The Linux Foundation. All rights reserved. + * Copyright (c) 2009-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -98,8 +98,14 @@ of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sdm660") #define early_machine_is_sda660() \ of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sda660") +#define early_machine_is_sdm658() \ + of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sdm658") +#define early_machine_is_sda658() \ + of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sda658") #define early_machine_is_sdm630() \ of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sdm630") +#define early_machine_is_sda630() \ + of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sda630") #else #define of_board_is_sim() 0 #define of_board_is_rumi() 0 @@ -138,7 +144,10 @@ #define early_machine_is_msmhamster() 0 #define early_machine_is_sdm660() 0 #define early_machine_is_sda660() 0 +#define early_machine_is_sdm658() 0 +#define early_machine_is_sda658() 0 #define early_machine_is_sdm630() 0 +#define early_machine_is_sda630() 0 #endif #define PLATFORM_SUBTYPE_MDM 1 diff --git a/include/trace/events/msm_cam.h b/include/trace/events/msm_cam.h new file mode 100644 index 000000000000..b52845407ef0 --- /dev/null +++ b/include/trace/events/msm_cam.h @@ -0,0 +1,136 @@ +/* Copyright (c) 2016, The Linux Foundation. All rights reserved. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 and + * only version 2 as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + */ +#undef TRACE_SYSTEM +#define TRACE_SYSTEM msm_cam + +#if !defined(_TRACE_MSM_VFE_H) || defined(TRACE_HEADER_MULTI_READ) +#define _TRACE_MSM_VFE_H + +#include "msm_isp.h" +#include <linux/types.h> +#include <linux/tracepoint.h> + +#define STRING_LEN 80 + + +TRACE_EVENT(msm_cam_string, + TP_PROTO(const char *str), + TP_ARGS(str), + TP_STRUCT__entry( + __array(char, str, STRING_LEN) + ), + TP_fast_assign( + strlcpy(__entry->str, str, STRING_LEN); + ), + TP_printk("msm_cam: %s", __entry->str) +); + +TRACE_EVENT(msm_cam_tasklet_debug_dump, + TP_PROTO(struct msm_vfe_irq_debug_info tasklet_state), + TP_ARGS(tasklet_state), + TP_STRUCT__entry( + __field(unsigned int, vfe_id) + __field(unsigned int, core_id) + __field(unsigned int, irq_status0) + __field(unsigned int, irq_status1) + __field(unsigned int, ping_pong_status) + __field(long, tv_sec) + __field(long, tv_usec) + ), + TP_fast_assign( + __entry->vfe_id = tasklet_state.vfe_id; + __entry->irq_status0 = + tasklet_state.irq_status0[tasklet_state.vfe_id]; + __entry->irq_status1 = + tasklet_state.irq_status1[tasklet_state.vfe_id]; + __entry->core_id = tasklet_state.core_id; + __entry->ping_pong_status = + tasklet_state.ping_pong_status[tasklet_state.vfe_id]; + __entry->tv_sec = + tasklet_state.ts.buf_time.tv_sec; + __entry->tv_usec = + tasklet_state.ts.buf_time.tv_usec; + ), + TP_printk("vfe_id %d, core %d, irq_st0 0x%x, irq_st1 0x%x\n" + "pi_po_st 0x%x, time %ld:%ld", + __entry->vfe_id, + __entry->core_id, + __entry->irq_status0, + __entry->irq_status1, + __entry->ping_pong_status, + __entry->tv_sec, + __entry->tv_usec + ) +); + +TRACE_EVENT(msm_cam_ping_pong_debug_dump, + TP_PROTO(struct msm_vfe_irq_debug_info ping_pong_state), + TP_ARGS(ping_pong_state), + TP_STRUCT__entry( + __field(unsigned int, curr_vfe_id) + __field(unsigned int, curr_irq_status0) + __field(unsigned int, curr_irq_status1) + __field(unsigned int, curr_ping_pong_status) + __field(unsigned int, othr_vfe_id) + __field(unsigned int, othr_irq_status0) + __field(unsigned int, othr_irq_status1) + __field(unsigned int, othr_ping_pong_status) + __field(long, othr_tv_sec) + __field(long, othr_tv_usec) + __field(unsigned int, core_id) + ), + TP_fast_assign( + __entry->curr_vfe_id = + ping_pong_state.vfe_id; + __entry->curr_irq_status0 = + ping_pong_state.irq_status0[ping_pong_state.vfe_id]; + __entry->curr_irq_status1 = + ping_pong_state.irq_status1[ping_pong_state.vfe_id]; + __entry->curr_ping_pong_status = + ping_pong_state. + ping_pong_status[ping_pong_state.vfe_id]; + __entry->othr_vfe_id = + !ping_pong_state.vfe_id; + __entry->othr_irq_status0 = + ping_pong_state.irq_status0[!ping_pong_state.vfe_id]; + __entry->othr_irq_status1 = + ping_pong_state.irq_status1[!ping_pong_state.vfe_id]; + __entry->othr_ping_pong_status = + ping_pong_state. + ping_pong_status[!ping_pong_state.vfe_id]; + __entry->othr_tv_sec = + ping_pong_state.ts.buf_time.tv_sec; + __entry->othr_tv_usec = + ping_pong_state.ts.buf_time.tv_usec; + __entry->core_id = ping_pong_state.core_id; + ), + TP_printk("vfe_id %d, irq_st0 0x%x, irq_st1 0x%x, pi_po_st 0x%x\n" + "other vfe_id %d, irq_st0 0x%x, irq_st1 0x%x\n" + "pi_po_st 0x%x, time %ld:%ld core %d", + __entry->curr_vfe_id, + __entry->curr_irq_status0, + __entry->curr_irq_status1, + __entry->curr_ping_pong_status, + __entry->othr_vfe_id, + __entry->othr_irq_status0, + __entry->othr_irq_status1, + __entry->othr_ping_pong_status, + __entry->othr_tv_sec, + __entry->othr_tv_usec, + __entry->core_id + ) +); + +#endif /* _MSM_CAM_TRACE_H */ +/* This part must be outside protection */ +#include <trace/define_trace.h> diff --git a/kernel/sched/hmp.c b/kernel/sched/hmp.c index a8bf39c6d7d7..d3547391b937 100644 --- a/kernel/sched/hmp.c +++ b/kernel/sched/hmp.c @@ -1,4 +1,4 @@ -/* Copyright (c) 2012-2016, The Linux Foundation. All rights reserved. +/* Copyright (c) 2012-2017, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -774,13 +774,6 @@ __read_mostly unsigned int sched_ravg_window = MIN_SCHED_RAVG_WINDOW; /* Temporarily disable window-stats activity on all cpus */ unsigned int __read_mostly sched_disable_window_stats; -/* - * Major task runtime. If a task runs for more than sched_major_task_runtime - * in a window, it's considered to be generating majority of workload - * for this window. Prediction could be adjusted for such tasks. - */ -__read_mostly unsigned int sched_major_task_runtime = 10000000; - static unsigned int sync_cpu; struct related_thread_group *related_thread_groups[MAX_NUM_CGROUP_COLOC_ID]; @@ -1015,9 +1008,6 @@ void set_hmp_defaults(void) update_up_down_migrate(); - sched_major_task_runtime = - mult_frac(sched_ravg_window, MAJOR_TASK_PCT, 100); - sched_init_task_load_windows = div64_u64((u64)sysctl_sched_init_task_load_pct * (u64)sched_ravg_window, 100); @@ -1470,7 +1460,20 @@ int sched_hmp_proc_update_handler(struct ctl_table *table, int write, int ret; unsigned int old_val; unsigned int *data = (unsigned int *)table->data; - int update_min_nice = 0; + int update_task_count = 0; + + if (!sched_enable_hmp) + return 0; + + /* + * The policy mutex is acquired with cpu_hotplug.lock + * held from cpu_up()->cpufreq_governor_interactive()-> + * sched_set_window(). So enforce the same order here. + */ + if (write && (data == &sysctl_sched_upmigrate_pct)) { + update_task_count = 1; + get_online_cpus(); + } mutex_lock(&policy_mutex); @@ -1478,7 +1481,7 @@ int sched_hmp_proc_update_handler(struct ctl_table *table, int write, ret = proc_dointvec_minmax(table, write, buffer, lenp, ppos); - if (ret || !write || !sched_enable_hmp) + if (ret || !write) goto done; if (write && (old_val == *data)) @@ -1500,20 +1503,18 @@ int sched_hmp_proc_update_handler(struct ctl_table *table, int write, * includes taking runqueue lock of all online cpus and re-initiatizing * their big counter values based on changed criteria. */ - if ((data == &sysctl_sched_upmigrate_pct || update_min_nice)) { - get_online_cpus(); + if (update_task_count) pre_big_task_count_change(cpu_online_mask); - } set_hmp_defaults(); - if ((data == &sysctl_sched_upmigrate_pct || update_min_nice)) { + if (update_task_count) post_big_task_count_change(cpu_online_mask); - put_online_cpus(); - } done: mutex_unlock(&policy_mutex); + if (update_task_count) + put_online_cpus(); return ret; } @@ -1950,8 +1951,6 @@ scale_load_to_freq(u64 load, unsigned int src_freq, unsigned int dst_freq) return div64_u64(load * (u64)src_freq, (u64)dst_freq); } -#define HEAVY_TASK_SKIP 2 -#define HEAVY_TASK_SKIP_LIMIT 4 /* * get_pred_busy - calculate predicted demand for a task on runqueue * @@ -1979,7 +1978,7 @@ static u32 get_pred_busy(struct rq *rq, struct task_struct *p, u32 *hist = p->ravg.sum_history; u32 dmin, dmax; u64 cur_freq_runtime = 0; - int first = NUM_BUSY_BUCKETS, final, skip_to; + int first = NUM_BUSY_BUCKETS, final; u32 ret = runtime; /* skip prediction for new tasks due to lack of history */ @@ -1999,36 +1998,6 @@ static u32 get_pred_busy(struct rq *rq, struct task_struct *p, /* compute the bucket for prediction */ final = first; - if (first < HEAVY_TASK_SKIP_LIMIT) { - /* compute runtime at current CPU frequency */ - cur_freq_runtime = mult_frac(runtime, max_possible_efficiency, - rq->cluster->efficiency); - cur_freq_runtime = scale_load_to_freq(cur_freq_runtime, - max_possible_freq, rq->cluster->cur_freq); - /* - * if the task runs for majority of the window, try to - * pick higher buckets. - */ - if (cur_freq_runtime >= sched_major_task_runtime) { - int next = NUM_BUSY_BUCKETS; - /* - * if there is a higher bucket that's consistently - * hit, don't jump beyond that. - */ - for (i = start + 1; i <= HEAVY_TASK_SKIP_LIMIT && - i < NUM_BUSY_BUCKETS; i++) { - if (buckets[i] > CONSISTENT_THRES) { - next = i; - break; - } - } - skip_to = min(next, start + HEAVY_TASK_SKIP); - /* don't jump beyond HEAVY_TASK_SKIP_LIMIT */ - skip_to = min(HEAVY_TASK_SKIP_LIMIT, skip_to); - /* don't go below first non-empty bucket, if any */ - final = max(first, skip_to); - } - } /* determine demand range for the predicted bucket */ if (final < 2) { @@ -3897,7 +3866,7 @@ static void transfer_busy_time(struct rq *rq, struct related_thread_group *grp, struct migration_sum_data d; int migrate_type; int cpu = cpu_of(rq); - bool new_task = is_new_task(p); + bool new_task; int i; if (!sched_freq_aggregate) @@ -3907,6 +3876,7 @@ static void transfer_busy_time(struct rq *rq, struct related_thread_group *grp, update_task_ravg(rq->curr, rq, TASK_UPDATE, wallclock, 0); update_task_ravg(p, rq, TASK_UPDATE, wallclock, 0); + new_task = is_new_task(p); /* cpu_time protected by related_thread_group_lock, grp->lock rq_lock */ cpu_time = _group_cpu_time(grp, cpu); @@ -4001,6 +3971,8 @@ static void transfer_busy_time(struct rq *rq, struct related_thread_group *grp, BUG_ON((s64)*src_curr_runnable_sum < 0); BUG_ON((s64)*src_prev_runnable_sum < 0); + BUG_ON((s64)*src_nt_curr_runnable_sum < 0); + BUG_ON((s64)*src_nt_prev_runnable_sum < 0); } static inline struct group_cpu_time * diff --git a/kernel/sched/sched.h b/kernel/sched/sched.h index afccfd0878b1..a3abdf19ff4c 100644 --- a/kernel/sched/sched.h +++ b/kernel/sched/sched.h @@ -1066,7 +1066,6 @@ static inline void sched_ttwu_pending(void) { } #define FREQ_REPORT_CPU_LOAD 1 #define FREQ_REPORT_TOP_TASK 2 -#define MAJOR_TASK_PCT 85 #define SCHED_UPMIGRATE_MIN_NICE 15 #define EXITING_TASK_MARKER 0xdeaddead @@ -1093,7 +1092,6 @@ extern unsigned int sched_init_task_load_windows; extern unsigned int up_down_migrate_scale_factor; extern unsigned int sysctl_sched_restrict_cluster_spill; extern unsigned int sched_pred_alert_load; -extern unsigned int sched_major_task_runtime; extern struct sched_cluster init_cluster; extern unsigned int __read_mostly sched_short_sleep_task_threshold; extern unsigned int __read_mostly sched_long_cpu_selection_threshold; diff --git a/net/netfilter/xt_IDLETIMER.c b/net/netfilter/xt_IDLETIMER.c index 456a1dff692d..80b32de1d99c 100644 --- a/net/netfilter/xt_IDLETIMER.c +++ b/net/netfilter/xt_IDLETIMER.c @@ -49,6 +49,7 @@ #include <linux/notifier.h> #include <net/net_namespace.h> #include <net/sock.h> +#include <net/inet_sock.h> struct idletimer_tg_attr { struct attribute attr; @@ -360,8 +361,8 @@ static void reset_timer(const struct idletimer_tg_info *info, /* Stores the uid resposible for waking up the radio */ if (skb && (skb->sk)) { - timer->uid = from_kuid_munged(current_user_ns(), - sock_i_uid(skb->sk)); + timer->uid = from_kuid_munged + (current_user_ns(), sock_i_uid(skb_to_full_sk(skb))); } /* checks if there is a pending inactive notification*/ |
