Merge "msm: mdss: Increase fbmem buf ref count before use in mdp3"
diff --git a/Documentation/devicetree/bindings/arm/msm/lpm-levels.txt b/Documentation/devicetree/bindings/arm/msm/lpm-levels.txt
index 55d06b2..1a357b1 100644
--- a/Documentation/devicetree/bindings/arm/msm/lpm-levels.txt
+++ b/Documentation/devicetree/bindings/arm/msm/lpm-levels.txt
@@ -28,6 +28,14 @@
mask of the cluster mode in the composite state ID used to define
cluster low power modes in PSCI.
+Optional properties:
+ - qcom,disable-prediction: This property is used to indicate the LPM
+ governor will not use LPM prediction for this cluster.
+ - qcom,clstr-tmr-add: This property is used as correction timer for
+ wrong prediction by lpm prediction algorithm for cluster predictions.
+ This value should be between 100 to 1500. Higher values would mean
+ longer time staying in shallower state before waking up to select a
+ deeper state in case of wrong prediction.
qcom,pm-cluster contains qcom,pm-cluster-level nodes which identify
the various low power modes that the cluster can enter. The
qcom,pm-cluster node should also include another cluster node or a cpu
@@ -77,8 +85,22 @@
- qcom,pm-cpu-levels: The different low power modes that a CPU could
enter. The following section explains the required properties of this
node.
- -qcom,use-prediction: This optional property is used to indicate the
- the LPM governor is to apply sleep prediction to this cluster.
+
+Optional properties:
+ - qcom,disable-prediction: This property is used to indicate the
+ LPM governor is to disable sleep prediction to this cpu.
+ - qcom,ref-stddev: This property is used as reference standard deviation
+ in lpm prediction algorithm. This value should be between 100 to 1000.
+ Higher value would result in more predictions and thereby resulting in
+ shallower low power modes.
+ - qcom,tmr-add: This property is used as correction timer for wrong
+ prediction by lpm prediction algorithm. This value should be between
+ 100 to 1500. Higher values would mean longer time staying in shallower
+ state before waking up to select a deeper state in case of wrong prediction.
+ - qcom,ref-premature-cnt: This property is used as reference premature
+ count to predict next sleep state by the prediction algorithm. This value
+ should be between 1 to 5. Higher value for this parameter would result in
+ less predictions to disallow deeper low power modes.
[Node bindings for qcom,pm-cpu-levels]
Required properties:
diff --git a/Documentation/devicetree/bindings/arm/msm/msm.txt b/Documentation/devicetree/bindings/arm/msm/msm.txt
index bacaeb6..931ef7a 100644
--- a/Documentation/devicetree/bindings/arm/msm/msm.txt
+++ b/Documentation/devicetree/bindings/arm/msm/msm.txt
@@ -122,9 +122,15 @@
- SDM439
compatible = "qcom,sdm439"
+- SDA439
+ compatible = "qcom,sda439"
+
- SDM429
compatible = "qcom,sdm429"
+- SDA429
+ compatible = "qcom,sda429"
+
- MDM9640
compatible = "qcom,mdm9640"
@@ -334,9 +340,13 @@
compatible = "qcom,sdm429-cdp"
compatible = "qcom,sdm429-mtp"
compatible = "qcom,sdm429-qrd"
+compatible = "qcom,sda429-cdp"
+compatible = "qcom,sda429-mtp"
compatible = "qcom,sdm439-cdp"
compatible = "qcom,sdm439-mtp"
compatible = "qcom,sdm439-qrd"
+compatible = "qcom,sda439-cdp"
+compatible = "qcom,sda439-mtp"
compatible = "qcom,msm8953-rumi"
compatible = "qcom,msm8953-sim"
compatible = "qcom,msm8953-cdp"
diff --git a/Documentation/devicetree/bindings/batterydata/batterydata.txt b/Documentation/devicetree/bindings/batterydata/batterydata.txt
index 884b19c..84c67da 100644
--- a/Documentation/devicetree/bindings/batterydata/batterydata.txt
+++ b/Documentation/devicetree/bindings/batterydata/batterydata.txt
@@ -101,6 +101,12 @@
the low and high thresholds.
The threshold values in range should be in ascending
and shouldn't overlap. It support 8 ranges at max.
+- qcom,jeita-soft-thresholds: A tuple entry to specify ADC code for battery's soft JEITA
+ threshold.
+ <SOFT_COLD_ADC_CODE, SOFT_HOT_ADC_CODE>.
+- qcom,jeita-hard-thresholds: A tuple entry to specify ADC code for battery's hard JEITA
+ threshold.
+ <HARD_COLD_ADC_CODE, HARD_HOT_ADC_CODE>.
Profile data node required subnodes:
- qcom,fcc-temp-lut : An 1-dimensional lookup table node that encodes
@@ -165,6 +171,8 @@
qcom,v-cutoff-uv = <3400000>;
qcom,chg-term-ua = <100000>;
qcom,batt-id-kohm = <75>;
+ qcom,jeita-soft-thresholds = <0x3ecc 0x1bff>;
+ qcom,jeita-hard-thresholds = <0x4aff 0x15aa>;
qcom,step-chg-ranges = <3600000 4000000 3000000
4001000 4200000 2800000
4201000 4400000 2000000>;
diff --git a/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt b/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt
index 7bcb2dc..b8cb903 100644
--- a/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt
+++ b/Documentation/devicetree/bindings/fb/mdss-dsi-panel.txt
@@ -40,6 +40,8 @@
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-panel-timings-phy-12nm: An array of length 8 char that specifies the 12nm DSI PHY
+ 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
@@ -631,6 +633,8 @@
23 20 06 09 05 03 04 a0
23 20 06 09 05 03 04 a0
23 2e 06 08 05 03 04 a0];
+ qcom,mdss-dsi-panel-timings-phy-12nm =
+ [a9 4e 56 0b 8a 4d 0b d6];
qcom,mdss-dsi-on-command = [32 01 00 00 00 00 02 00 00
29 01 00 00 10 00 02 FF 99];
qcom,mdss-dsi-on-command-state = "dsi_lp_mode";
diff --git a/Documentation/devicetree/bindings/input/touchscreen/ft5x06-ts.txt b/Documentation/devicetree/bindings/input/touchscreen/ft5x06-ts.txt
new file mode 100644
index 0000000..f7494c4
--- /dev/null
+++ b/Documentation/devicetree/bindings/input/touchscreen/ft5x06-ts.txt
@@ -0,0 +1,120 @@
+FocalTech touch controller
+
+The focaltech controller is connected to host processor
+via i2c. The controller generates interrupts when the
+user touches the panel. The host controller is expected
+to read the touch coordinates over i2c and pass the coordinates
+to the rest of the system.
+
+Required properties:
+
+ - compatible : should be "focaltech,5x06".
+ - reg : i2c slave address of the device.
+ - interrupt-parent : parent of interrupt.
+ - interrupts : touch sample interrupt to indicate presense or release
+ of fingers on the panel.
+ - vdd-supply : Power supply needed to power up the device.
+ - vcc_i2c-supply : Power source required to power up i2c bus.
+ - focaltech,family-id : family identification of the controller.
+ - focaltech,irq-gpio : irq gpio which is to provide interrupts to host,
+ same as "interrupts" node. It will also
+ contain active low or active high information.
+ - focaltech,reset-gpio : reset gpio to control the reset of chip.
+ - focaltech,display-coords : display coordinates in pixels. It is a four
+ tuple consisting of min x, min y, max x and
+ max y values
+ - focaltech,name : name of the controller
+ - focaltech,group-id : group id of this device
+ - focaltech,hard-reset-delay-ms : hard reset delay in ms
+ - focaltech,soft-reset-delay-ms : soft reset delay in ms
+ - focaltech,fw-delay-aa-ms : specify the delay in ms after programming 0xaa
+ register for firmware upgrade
+ - focaltech,fw-delay-55-ms : specify the delay in ms after programming 0x55
+ register for firmware upgrade
+ - focaltech,fw-upgrade-id1 : specify the upgrade id1 for firmware upgrade
+ - focaltech,fw-upgrade-id2 : specify the upgrade id2 for firmware upgrade
+ - focaltech,fw-delay-readid-ms : specify the read id delay in ms for firmware upgrade
+ - focaltech,fw-delay-era-flsh-ms : specify the erase flash delay in ms for firmware upgrade
+ - pinctrl-names : This should be defined if a target uses pinctrl framework.
+ See "pinctrl" in Documentation/devicetree/bindings/pinctrl/msm-pinctrl.txt.
+ Specify the names of the configs that pinctrl can install in driver.
+ Following are the pinctrl configs that can be installed:
+ "pmx_ts_active" : Active configuration of pins, this should specify active
+ config defined in pin groups of interrupt and reset gpio.
+ "pmx_ts_suspend" : Disabled configuration of pins, this should specify sleep
+ config defined in pin groups of interrupt and reset gpio.
+ "pmx_ts_release" : Release configuration of pins, this should specify
+ release config defined in pin groups of interrupt and reset gpio.
+
+Optional properties:
+
+ - focaltech,panel-coords : panel coordinates for the chip in pixels.
+ It is a four tuple consisting of min x,
+ min y, max x and max y values.
+ - focaltech,i2c-pull-up : to specify pull up is required.
+ - focaltech,no-force-update : to specify force update is allowed.
+ - focaltech,button-map : button map of key codes. The number
+ of key codes depend on panel
+ - focaltech,fw-name : specify the firmware file name
+ - focaltech,fw-delay-aa-ms : specify the "aa" delay in ms for firmware upgrade
+ - focaltech,fw-delay-55-ms : specify the "55" delay in ms for firmware upgrade
+ - focaltech,fw-upgrade-id1 : specify the upgrade id1 for firmware upgrade
+ - focaltech,fw-upgrade-id2 : specify the upgrade id2 for firmware upgrade
+ - focaltech,fw-delay-readid-ms : specify the read id delay in ms for firmware upgrade
+ - focaltech,fw-delay-era-flsh-ms : specify the erase flash delay in ms for firmware upgrade
+ - focaltech,fw-auto-cal : specify whether calibration is needed after firmware upgrade
+ - focaltech,fw-vkey-support : specify if virtual keys are supported through firmware
+ - focaltech,ignore-id-check : specify ignore family-id check
+ - focaltech,panel-coords : panel coordinates for the chip in pixels.
+ It is a four tuple consisting of min x,
+ min y, max x and max y values
+ - focaltech,fw-name : specify the firmware file name
+ - focaltech,psensor-support : specify whether support the proximity sensor
+ - focaltech,gesture-support : specify whether support gesture feature
+ - focaltech,resume-in-workqueue : specifiy whether to defer the resume to workqueue
+ - clock-names: : Clock names used for secure touch. They are: "iface_clk", "core_clk"
+ - clocks : Defined if 'clock-names' DT property is defined. These clocks
+ are associated with the underlying I2C bus.
+
+Example:
+ i2c@f9923000{
+ focaltech@38{
+ compatible = "focaltech,5x06";
+ reg = <0x38>;
+ interrupt-parent = <&msmgpio>;
+ interrupts = <1 0x2>;
+ vdd-supply = <&pm8110_l19>;
+ vcc_i2c-supply = <&pm8110_l14>;
+ pinctrl-names = "pmx_ts_active","pmx_ts_suspend","pmx_ts_release";
+ pinctrl-0 = <&ts_int_active &ts_reset_active>;
+ pinctrl-1 = <&ts_int_suspend &ts_reset_suspend>;
+ pinctrl-2 = <&ts_release>;
+ focaltech,name = "ft6x06";
+ focaltech,family-id = <0x06>;
+ focaltech,reset-gpio = <&msmgpio 0 0x00>;
+ focaltech,irq-gpio = <&msmgpio 1 0x00>;
+ focaltech,display-coords = <0 0 480 800>;
+ focaltech,panel-coords = <0 0 480 800>;
+ focaltech,button-map= <139 102 158>;
+ focaltech,no-force-update;
+ focaltech,i2c-pull-up;
+ focaltech,group-id = <1>;
+ focaltech,hard-reset-delay = <20>;
+ focaltech,soft-reset-delay = <150>;
+ focaltech,num-max-touches = <2>;
+ focaltech,fw-name = "ft_8610_qrd_fw.bin";
+ focaltech,fw-delay-aa-ms = <100>;
+ focaltech,fw-delay-55-ms = <30>;
+ focaltech,fw-upgrade-id1 = <0x79>;
+ focaltech,fw-upgrade-id2 = <0x08>;
+ focaltech,fw-delay-readid-ms = <10>;
+ focaltech,fw-delay-era-flsh-ms = <2000>;
+ focaltech,fw-auto-cal;
+ focaltech,psensor-support;
+ focaltech,gesture-support;
+ /* Underlying clocks used by secure touch */
+ clock-names = "iface_clk", "core_clk";
+ clocks = <&clock_gcc clk_gcc_blsp1_ahb_clk>,
+ <&clock_gcc clk_gcc_blsp1_qup3_i2c_apps_clk>;
+ };
+ };
diff --git a/Documentation/devicetree/bindings/input/touchscreen/synaptics_dsxv26_i2c.txt b/Documentation/devicetree/bindings/input/touchscreen/synaptics_dsxv26_i2c.txt
index c33daab..87a551ba 100644
--- a/Documentation/devicetree/bindings/input/touchscreen/synaptics_dsxv26_i2c.txt
+++ b/Documentation/devicetree/bindings/input/touchscreen/synaptics_dsxv26_i2c.txt
@@ -26,6 +26,7 @@
- synaptics,ub-i2c-addr : microbootloader mode I2C slave address.
- synaptics,cap-button-codes : virtual key code mappings to be used.
- synaptics,vir-button-codes : virtual key code and the response region on panel.
+ - synaptics,wakeup-gestures-en: enable wakeup gestures.
- synaptics,x-flip : modify orientation of the x axis.
- synaptics,y-flip : modify orientation of the y axis.
- synaptics,reset-delay-ms : reset delay for controller (ms), default 100.
diff --git a/Documentation/devicetree/bindings/media/video/msm-csi-phy.txt b/Documentation/devicetree/bindings/media/video/msm-csi-phy.txt
index 8a6b3c4..24a3443 100644
--- a/Documentation/devicetree/bindings/media/video/msm-csi-phy.txt
+++ b/Documentation/devicetree/bindings/media/video/msm-csi-phy.txt
@@ -14,6 +14,7 @@
- "qcom,csiphy-v3.5"
- "qcom,csiphy-v5.0"
- "qcom,csiphy-v5.01"
+ - "qcom,csiphy-v10.00"
- reg : offset and length of the register set for the device
for the csiphy operating in compatible mode.
- reg-names : should specify relevant names to each reg property defined.
diff --git a/Documentation/devicetree/bindings/platform/msm/usb-bam.txt b/Documentation/devicetree/bindings/platform/msm/usb-bam.txt
index 7d2e31e..9af22e2 100644
--- a/Documentation/devicetree/bindings/platform/msm/usb-bam.txt
+++ b/Documentation/devicetree/bindings/platform/msm/usb-bam.txt
@@ -36,7 +36,6 @@
- qcom,reset-bam-on-connect: If present then BAM is RESET before connecting
pipe. This may be required if BAM peripheral is also reset before connect.
- qcom,reset-bam-on-disconnect: If present then BAM is RESET after disconnecting pipes.
-- qcom,enable-hsusb-bam-on-boot: If present then BAM is enabled at bootup itself.
A number of USB BAM pipe parameters are represented as sub-nodes:
diff --git a/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb5.txt b/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb5.txt
index b7e6a31b..de273cd 100644
--- a/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb5.txt
+++ b/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb5.txt
@@ -167,10 +167,7 @@
Usage: optional
Value type: <phandle>
Definition: Specifies the phandle of the node which contains the battery
- profiles supported on the device. This is only specified
- when step charging and sw-jeita configurations are desired
- to be get from these properties defined in battery profile:
- qcom,step-chg-ranges, qcom,jeita-fcc-ranges, qcom,jeita-fv-ranges.
+ profiles supported on the device.
- qcom,flash-derating-soc
Usage: optional
diff --git a/Documentation/devicetree/bindings/pwm/pwm-qti-lpg.txt b/Documentation/devicetree/bindings/pwm/pwm-qti-lpg.txt
index 3174ccb..ddd90e1 100644
--- a/Documentation/devicetree/bindings/pwm/pwm-qti-lpg.txt
+++ b/Documentation/devicetree/bindings/pwm/pwm-qti-lpg.txt
@@ -11,26 +11,137 @@
- reg:
Usage: required
Value type: <prop-encoded-array>
- Definition: Register base and length for LPG modules. The length
- varies based on the number of channels available in
- the PMIC chips.
+ Definition: Register base and length for LPG and LUT modules. LPG size
+ or length available per channel varies depending on the
+ number of channels in PMIC.
- reg-names:
Usage: required
Value type: <string>
Definition: The name of the register defined in the reg property.
- It must be "lpg-base".
+ It must have "lpg-base", "lut-base" is optional but
+ it's required if any LPG channels support LUT mode.
- #pwm-cells:
Usage: required
Value type: <u32>
- Definition: See Documentation/devicetree/bindings/pwm/pwm.txt;
+ Definition: The number of cells in "pwms" property specified in
+ PWM user nodes. It should be 2. The first cell is
+ the PWM channel ID indexed from 0, and the second
+ cell is the PWM default period in nanoseconds.
+- qcom,lut-patterns:
+ Usage: optional
+ Value type: <prop-encoded-array>
+ Definition: Duty ratios in percentages for LPG working at LUT mode.
+ These duty ratios will be translated into PWM values
+ and stored in LUT module. The LUT module has resource
+ to store 47 PWM values at max and shared for all LPG
+ channels. This property is required if any LPG channels
+ support LUT mode.
+
+Subnode is optional if LUT mode is not required, it's required if any LPG
+channels expected to be supported in LUT mode.
+
+Subnode properties:
+Subnodes for each LPG channel (lpg@X) can be defined if any of the following
+parameters needs to be configured for that channel.
+
+- qcom,lpg-chan-id:
+ Usage: required
+ Value type: <u32>
+ Definition: The LPG channel's hardware ID indexed from 1. Allowed
+ range is 1 - 8. Maximum value depends on the number of
+ channels supported on PMIC.
+
+- qcom,ramp-step-ms:
+ Usage: required
+ Value type: <u32>
+ Definition: The step duration in milliseconds for LPG staying at each
+ duty specified in the LUT pattern. Allowed range is
+ 1 - 511.
+
+- qcom,ramp-high-index:
+ Usage: required
+ Value type: <u32>
+ Definition: The high index of the LUT pattern where LPG ends up
+ ramping to. Allowed range is 1 - 47.
+
+- qcom,ramp-low-index:
+ Usage: required
+ Value type: <u32>
+ Definition: The low index of the LUT pattern from where LPG begins
+ ramping from. Allowed range is 0 - 46.
+
+- qcom,ramp-from-low-to-high:
+ Usage: optional
+ Value type: <empty>
+ Definition: The flag to specify the LPG ramping direction. The ramping
+ direction is from low index to high index of the LUT
+ pattern if it's specified.
+
+- qcom,ramp-pattern-repeat:
+ Usage: optional
+ Value type: <empty>
+ Definition: The flag to specify if LPG would be ramping with the LUT
+ pattern repeatedly.
+
+- qcom,ramp-toggle:
+ Usage: optional
+ Value type: <empty>
+ Definition: The flag to specify if LPG would toggle the LUT pattern
+ in ramping. If toggling enabled, LPG would return to the
+ low index when high index is reached, or return to the high
+ index when low index is reached.
+
+- qcom,ramp-pause-hi-count:
+ Usage: optional
+ Value type: <u32>
+ Definition: The step count that LPG stop the output when it ramped up
+ to the high index of the LUT.
+
+- qcom,ramp-pause-lo-count:
+ Usage: optional
+ Value type: <u32>
+ Definition: The step count that LPG stop the output when it ramped up
+ to the low index of the LUT.
Example:
pmi8998_lpg: lpg@b100 {
compatible = "qcom,pwm-lpg";
- reg = <0xb100 0x600>;
- reg-names = "lpg-base";
+ reg = <0xb100 0x600>, <0xb000 0x100>;
+ reg-names = "lpg-base", "lut-base";
#pwm-cells = <2>;
+ qcom,lut-patterns = <0 14 28 42 56 70 84 100
+ 100 84 70 56 42 28 14 0>;
+ lpg@3 {
+ qcom,lpg-chan-id = <3>;
+ qcom,ramp-step-ms = <200>;
+ qcom,ramp-pause-hi-count = <10>;
+ qcom,ramp-pause-lo-count = <10>;
+ qcom,ramp-low-index = <0>;
+ qcom,ramp-high-index = <15>;
+ qcom,ramp-from-low-to-high;
+ qcom,ramp-pattern-repeat;
+ };
+ lpg@4 {
+ qcom,lpg-chan-id = <4>;
+ qcom,ramp-step-ms = <200>;
+ qcom,ramp-pause-hi-count = <10>;
+ qcom,ramp-pause-lo-count = <10>;
+ qcom,ramp-low-index = <0>;
+ qcom,ramp-high-index = <15>;
+ qcom,ramp-from-low-to-high;
+ qcom,ramp-pattern-repeat;
+ };
+ lpg@5 {
+ qcom,lpg-chan-id = <5>;
+ qcom,ramp-step-ms = <200>;
+ qcom,ramp-pause-hi-count = <10>;
+ qcom,ramp-pause-lo-count = <10>;
+ qcom,ramp-low-index = <0>;
+ qcom,ramp-high-index = <15>;
+ qcom,ramp-from-low-to-high;
+ qcom,ramp-pattern-repeat;
+ };
};
diff --git a/Documentation/devicetree/bindings/regulator/qpnp-lcdb-regulator.txt b/Documentation/devicetree/bindings/regulator/qpnp-lcdb-regulator.txt
index 9798ac60..72c4eaf 100644
--- a/Documentation/devicetree/bindings/regulator/qpnp-lcdb-regulator.txt
+++ b/Documentation/devicetree/bindings/regulator/qpnp-lcdb-regulator.txt
@@ -212,8 +212,9 @@
- qcom,bst-headroom-mv
Usage: optional
Value type: <u16>
- Definition: Headroom of the boost (in mV). The minimum headroom is
- 200mV and if not specified defaults to 200mV.
+ Definition: Headroom of the boost (in mV). If not specified, then the
+ default value is 200 mV (PM660L) or 150 mV (for PM855L or
+ PMI632).
=======
Example
diff --git a/Documentation/devicetree/bindings/soc/qcom/bg_daemon.txt b/Documentation/devicetree/bindings/soc/qcom/bg_daemon.txt
index 149a01a..1417eb0 100644
--- a/Documentation/devicetree/bindings/soc/qcom/bg_daemon.txt
+++ b/Documentation/devicetree/bindings/soc/qcom/bg_daemon.txt
@@ -6,9 +6,15 @@
Required properties:
- compatible : should be "qcom,bg-daemon"
- qcom,bg-reset-gpio : gpio for the apps processor use to soft reset BG
+- ssr-reg1-supply : Power supply needed to power up the BG device.
+ When BG brought up this regulator will be in normal power mode.
+- ssr-reg2-supply : Power supply needed to power up the BG device.
+ When BG BG brought up this regulator will be in normal power mode.
Example:
qcom,bg-daemon {
compatible = "qcom,bg-daemon";
qcom,bg-reset-gpio = <&pm660_gpios 5 0>;
+ ssr-reg1-supply = <&pm660_l3>;
+ ssr-reg2-supply = <&pm660_l9>;
};
diff --git a/Documentation/devicetree/bindings/soc/qcom/dcc.txt b/Documentation/devicetree/bindings/soc/qcom/dcc.txt
index 5150459..c9bf3f5 100644
--- a/Documentation/devicetree/bindings/soc/qcom/dcc.txt
+++ b/Documentation/devicetree/bindings/soc/qcom/dcc.txt
@@ -8,7 +8,7 @@
Required properties:
- compatible : name of the component used for driver matching, should be
- "qcom,dcc" or "qcom,dcc_v2"
+ "qcom,dcc" or "qcom,dcc-v2"
- reg : physical base address and length of the register set(s), SRAM and XPU
of the component.
diff --git a/Documentation/devicetree/bindings/sound/aqt1000_codec.txt b/Documentation/devicetree/bindings/sound/aqt1000_codec.txt
new file mode 100644
index 0000000..af615b8
--- /dev/null
+++ b/Documentation/devicetree/bindings/sound/aqt1000_codec.txt
@@ -0,0 +1,79 @@
+Qualcomm Technologies, Inc. for AQT1000 audio CODEC
+
+Required properties:
+
+- compatible: "qcom,aqt1000-i2c-codec" for AQT1000 Codec
+
+- qcom,aqt-rst-gpio-node: Phandle reference to the DT node having codec reset gpio
+ configuration.
+
+- reg: Address of the codec. This property enabled I2C to get AQT1000 base address.
+
+- qcom,cdc-static-supplies: Static VREG_BOB Supply for AQT1000 codec.
+ All other supplies are derived from this.
+
+-qcom,cdc-micbias1-mv: micbias1 output voltage in milli volts.
+ This is used when cfilt is not user configurable
+ and micbias1 is directly controlled with a register
+ write.
+
+-qcom,cdc-mclk-clk-rate: Specifies the master clock rate in Hz required for
+ codec.
+
+Optional properties:
+
+-qcom,cdc-ext-clk-rate: External clock frequency used for AQT1000.
+ All internal clocks for AQT1000 are derived from this clock.
+ If this property is not defined then default external
+ clock rate of 9.6M will be provided.
+
+- qcom,cdc-vdd-mic-bias-supply: phandle of vreg_bob supply's regulator device tree
+ node.
+
+- qcom,cdc-vdd-mic-bias-voltage: vreg_bob supply's voltage level min and max
+ in mV.
+- qcom,cdc-vdd-mic-bias-current: vreg_bob supply's max current in mA.
+
+- qcom,cdc-micbias-ldoh-v: LDOH output in volts (should be 3V).
+
+- qcom,cdc-micbias-cfilt1-mv: cfilt1 output voltage in milli volts.
+ cfilt voltage can be set to max of qcom,cdc-micbias-ldoh-v - 0.15V.
+- qcom,cdc-micbias1-cfilt-sel: cfilt to use for micbias1
+ (should be from 1 to 3).
+
+- clock-names : clock name defined for external clock.
+- clocks : external clock defined for codec clock.
+
+Example:
+i2c@a88000 {
+ status = "ok";
+ aqt1000_cdc: aqt1000-i2c-codec@d {
+ status = "disabled";
+ compatible = "qcom,aqt1000-i2c-codec";
+ reg = <0x0d>;
+
+ interrupt-controller;
+ #interrupt-cells = <1>;
+ interrupt-parent = <&tlmm>;
+ qcom,gpio-connect = <&tlmm 79 0>;
+ pinctrl-names = "default";
+ pinctrl-0 = <&aqt_intr_default>;
+
+ qcom,aqt-rst-gpio-node = <&aqt_rst_gpio>;
+
+ qcom,cdc-vdd-mic-bias-supply = <&pm660l_bob>;
+ qcom,cdc-vdd-mic-bias-voltage = <3312000 3312000>;
+ qcom,cdc-vdd-mic-bias-current = <30400>;
+ qcom,cdc-static-supplies = "cdc-vdd-mic-bias";
+
+ qcom,cdc-micbias-ldoh-v = <3>;
+
+ qcom,cdc-ext-clk-rate = <19200000>;
+ qcom,cdc-mclk-clk-rate = <9600000>;
+
+ qcom,cdc-micbias1-mv = <1800>;
+
+ clock-names = "aqt_clk";
+ clocks = <&clock_audio_lnbb AUDIO_PMIC_LNBB_CLK>;
+ };
+};
diff --git a/Documentation/devicetree/bindings/sound/qcom-audio-dev.txt b/Documentation/devicetree/bindings/sound/qcom-audio-dev.txt
index 991e26c..f13dbde 100644
--- a/Documentation/devicetree/bindings/sound/qcom-audio-dev.txt
+++ b/Documentation/devicetree/bindings/sound/qcom-audio-dev.txt
@@ -1729,6 +1729,9 @@
- qcom,msm-mi2s-master: This property is used to inform machine driver
if MSM is the clock master of mi2s. 1 means master and 0 means slave. The
first entry is primary mi2s; the second entry is secondary mi2s, and so on.
+- qcom,mi2s-aqt-enabled: This property is used to inform machine driver
+ if AQT1000 codec is enabled or not. If this is enabled then codec name
+ for TERT_MI2S needs to be overridden with AQT codec.
- qcom,msm-mi2s-ext-mclk: This property is used to inform machine driver
if MCLK from MSM is used for any external audio connections. 1 means used
as external mclk source and 0 indicate not used. The first entry is
diff --git a/Documentation/devicetree/bindings/sound/wcd_codec.txt b/Documentation/devicetree/bindings/sound/wcd_codec.txt
index 6d2ae5e..585da1a 100644
--- a/Documentation/devicetree/bindings/sound/wcd_codec.txt
+++ b/Documentation/devicetree/bindings/sound/wcd_codec.txt
@@ -439,6 +439,7 @@
Value from 4000 to 5550 in mV in steps of 50 mV can be given.
- qcom,dig-cdc-base-addr: Specifies the digital codec base address for MSM digital
core register writes.
+ - qcom,anlg-cdc-mbhc-disable: Boolean variable that informs if AQT1000 codec is enabled or not.
Example:
diff --git a/arch/arm/boot/dts/qcom/mdm9607-ion.dtsi b/arch/arm/boot/dts/qcom/mdm9607-ion.dtsi
index 6da25c2..3deba29 100644
--- a/arch/arm/boot/dts/qcom/mdm9607-ion.dtsi
+++ b/arch/arm/boot/dts/qcom/mdm9607-ion.dtsi
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2015, 2017, Linux Foundation. All rights reserved.
+ * Copyright (c) 2015, 2017-2018, 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
diff --git a/arch/arm/boot/dts/qcom/msm-pm8019.dtsi b/arch/arm/boot/dts/qcom/msm-pm8019.dtsi
index afb4723..a8c2552 100644
--- a/arch/arm/boot/dts/qcom/msm-pm8019.dtsi
+++ b/arch/arm/boot/dts/qcom/msm-pm8019.dtsi
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, 2013, 2015, Linux Foundation. All rights reserved.
+/* Copyright (c) 2012, 2013, 2015, 2018, 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
diff --git a/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-cdp.dtsi b/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-cdp.dtsi
index 8a7b771..d447724 100644
--- a/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-cdp.dtsi
+++ b/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-cdp.dtsi
@@ -11,3 +11,28 @@
*/
#include "sdxpoorwills-cdp.dtsi"
+
+&sdhc_1 {
+ qcom,vdd-io-voltage-level = <1800000 1800000>;
+
+ qcom,core_3_0v_support;
+ qcom,nonremovable;
+
+ pinctrl-0 = <&sdc1_clk_on &sdc1_cmd_on &sdc1_data_on
+ &sdc1_wlan_gpio_active>;
+ pinctrl-1 = <&sdc1_clk_off &sdc1_cmd_off &sdc1_data_off
+ &sdc1_wlan_gpio_sleep>;
+
+ #address-cells = <0>;
+ interrupt-parent = <&sdhc_1>;
+ interrupts = <0 1 2>;
+ #interrupt-cells = <1>;
+ interrupt-map-mask = <0xffffffff>;
+ interrupt-map = <0 &intc 0 210 0
+ 1 &intc 0 227 0
+ 2 &tlmm 82 0x4>;
+ interrupt-names = "hc_irq", "pwr_irq", "sdiowakeup_irq";
+
+ /delete-property/ qcom,devfreq,freq-table;
+ /delete-property/ cd-gpios;
+};
diff --git a/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-mtp.dtsi b/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-mtp.dtsi
index 4a2ece8c..b60225a 100644
--- a/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-mtp.dtsi
+++ b/arch/arm/boot/dts/qcom/sdxpoorwills-dualwifi-mtp.dtsi
@@ -11,3 +11,28 @@
*/
#include "sdxpoorwills-mtp.dtsi"
+
+&sdhc_1 {
+ qcom,vdd-io-voltage-level = <1800000 1800000>;
+
+ qcom,core_3_0v_support;
+ qcom,nonremovable;
+
+ pinctrl-0 = <&sdc1_clk_on &sdc1_cmd_on &sdc1_data_on
+ &sdc1_wlan_gpio_active>;
+ pinctrl-1 = <&sdc1_clk_off &sdc1_cmd_off &sdc1_data_off
+ &sdc1_wlan_gpio_sleep>;
+
+ #address-cells = <0>;
+ interrupt-parent = <&sdhc_1>;
+ interrupts = <0 1 2>;
+ #interrupt-cells = <1>;
+ interrupt-map-mask = <0xffffffff>;
+ interrupt-map = <0 &intc 0 210 0
+ 1 &intc 0 227 0
+ 2 &tlmm 82 0x4>;
+ interrupt-names = "hc_irq", "pwr_irq", "sdiowakeup_irq";
+
+ /delete-property/ qcom,devfreq,freq-table;
+ /delete-property/ cd-gpios;
+};
diff --git a/arch/arm/boot/dts/qcom/sdxpoorwills-pinctrl.dtsi b/arch/arm/boot/dts/qcom/sdxpoorwills-pinctrl.dtsi
index 08c6c3b..d31916b 100644
--- a/arch/arm/boot/dts/qcom/sdxpoorwills-pinctrl.dtsi
+++ b/arch/arm/boot/dts/qcom/sdxpoorwills-pinctrl.dtsi
@@ -1585,6 +1585,34 @@
};
};
+ sdc1_wlan_gpio_active: sdc1_wlan_gpio_active {
+ mux {
+ pins = "gpio81";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio81";
+ output-high;
+ drive-strength = <8>;
+ bias-pull-up;
+ };
+ };
+
+ sdc1_wlan_gpio_sleep: sdc1_wlan_gpio_sleep {
+ mux {
+ pins = "gpio81";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio81";
+ drive-strength = <2>;
+ bias-pull-down;
+ output-low;
+ };
+ };
+
smb_int_default: smb_int_default {
mux {
pins = "gpio42";
diff --git a/arch/arm/boot/dts/qcom/sdxpoorwills-pm.dtsi b/arch/arm/boot/dts/qcom/sdxpoorwills-pm.dtsi
index ce4d882..77fc533 100644
--- a/arch/arm/boot/dts/qcom/sdxpoorwills-pm.dtsi
+++ b/arch/arm/boot/dts/qcom/sdxpoorwills-pm.dtsi
@@ -95,7 +95,7 @@
qcom,rpm-stats@c300000 {
compatible = "qcom,rpm-stats";
- reg = <0xC300000 0x1000>, <0xC3F0004 0x4>;
+ reg = <0xC300000 0x1000>, <0xC370004 0x4>;
reg-names = "phys_addr_base", "offset_addr";
};
};
diff --git a/arch/arm/boot/dts/qcom/sdxpoorwills.dtsi b/arch/arm/boot/dts/qcom/sdxpoorwills.dtsi
index 98d09de..51df1d7 100644
--- a/arch/arm/boot/dts/qcom/sdxpoorwills.dtsi
+++ b/arch/arm/boot/dts/qcom/sdxpoorwills.dtsi
@@ -565,7 +565,13 @@
compatible = "qcom,msm-imem-diag-dload";
reg = <0xc8 200>;
};
-};
+ };
+
+ qcom,mpm2-sleep-counter@c221000 {
+ compatible = "qcom,mpm2-sleep-counter";
+ reg = <0x0c221000 0x1000>;
+ clock-frequency = <32768>;
+ };
restart@c264000 {
compatible = "qcom,pshold";
@@ -654,6 +660,13 @@
qcom,fragmented-data;
};
+ qcom,glink-ssr-modem {
+ compatible = "qcom,glink_ssr";
+ label = "modem";
+ qcom,edge = "mpss";
+ qcom,xprt = "smem";
+ };
+
qcom,glink_pkt {
compatible = "qcom,glinkpkt";
@@ -817,6 +830,15 @@
qcom,ipa-advertise-sg-support;
};
+ dcc: dcc_v2@10a2000 {
+ compatible = "qcom,dcc-v2";
+ reg = <0x10a2000 0x1000>,
+ <0x10ae000 0x2000>;
+ reg-names = "dcc-base", "dcc-ram-base";
+
+ dcc-ram-offset = <0x6000>;
+ };
+
system_pm {
compatible = "qcom,system-pm";
mboxes = <&apps_rsc 0>;
@@ -1193,7 +1215,7 @@
<&pdc 0 54 4>, <&pdc 0 55 4>,
<&pdc 0 56 4>, <&pdc 0 57 4>;
interrupt-names = "sbd-intr", "lpi-intr",
- "wol-intr", "tx-ch0-intr",
+ "phy-intr", "tx-ch0-intr",
"tx-ch1-intr", "tx-ch2-intr",
"tx-ch3-intr", "tx-ch4-intr",
"rx-ch0-intr", "rx-ch1-intr",
diff --git a/arch/arm/configs/msm8909w-perf_defconfig b/arch/arm/configs/msm8909w-perf_defconfig
index 0c04f9c..cdfe536 100644
--- a/arch/arm/configs/msm8909w-perf_defconfig
+++ b/arch/arm/configs/msm8909w-perf_defconfig
@@ -15,7 +15,6 @@
CONFIG_IKCONFIG=y
CONFIG_IKCONFIG_PROC=y
CONFIG_LOG_CPU_MAX_BUF_SHIFT=17
-CONFIG_CGROUP_DEBUG=y
CONFIG_CGROUP_FREEZER=y
CONFIG_CPUSETS=y
CONFIG_CGROUP_CPUACCT=y
@@ -27,6 +26,7 @@
CONFIG_SCHED_AUTOGROUP=y
CONFIG_SCHED_TUNE=y
CONFIG_DEFAULT_USE_ENERGY_AWARE=y
+CONFIG_RELAY=y
CONFIG_BLK_DEV_INITRD=y
CONFIG_KALLSYMS_ALL=y
CONFIG_BPF_SYSCALL=y
@@ -49,7 +49,6 @@
CONFIG_AEABI=y
CONFIG_HIGHMEM=y
CONFIG_CMA=y
-CONFIG_CMA_DEBUGFS=y
CONFIG_ZSMALLOC=y
CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_SECCOMP=y
@@ -62,7 +61,6 @@
CONFIG_PM_AUTOSLEEP=y
CONFIG_PM_WAKELOCKS=y
CONFIG_PM_WAKELOCKS_LIMIT=0
-CONFIG_PM_DEBUG=y
CONFIG_NET=y
CONFIG_PACKET=y
CONFIG_UNIX=y
@@ -173,7 +171,6 @@
CONFIG_BRIDGE_NF_EBTABLES=y
CONFIG_BRIDGE_EBT_BROUTE=y
CONFIG_L2TP=y
-CONFIG_L2TP_DEBUGFS=y
CONFIG_L2TP_V3=y
CONFIG_L2TP_IP=y
CONFIG_L2TP_ETH=y
@@ -266,11 +263,10 @@
CONFIG_INPUT_MISC=y
CONFIG_INPUT_QPNP_POWER_ON=y
CONFIG_INPUT_UINPUT=y
-CONFIG_SERIAL_MSM=y
-CONFIG_SERIAL_MSM_CONSOLE=y
CONFIG_SERIAL_MSM_HS=y
CONFIG_SERIAL_MSM_SMD=y
CONFIG_DIAG_CHAR=y
+CONFIG_DIAG_USES_SMD=y
CONFIG_HW_RANDOM=y
CONFIG_HW_RANDOM_MSM_LEGACY=y
CONFIG_MSM_SMD_PKT=y
@@ -318,6 +314,7 @@
CONFIG_MEDIA_CONTROLLER=y
CONFIG_VIDEO_V4L2_SUBDEV_API=y
CONFIG_V4L_PLATFORM_DRIVERS=y
+CONFIG_QCOM_KGSL=y
CONFIG_FB=y
CONFIG_FB_VIRTUAL=y
CONFIG_BACKLIGHT_LCD_SUPPORT=y
@@ -385,6 +382,7 @@
CONFIG_RTC_DRV_QPNP=y
CONFIG_DMADEVICES=y
CONFIG_QCOM_SPS_DMA=y
+CONFIG_SYNC_FILE=y
CONFIG_UIO=y
CONFIG_UIO_MSM_SHAREDMEM=y
CONFIG_STAGING=y
@@ -399,6 +397,7 @@
CONFIG_REMOTE_SPINLOCK_MSM=y
CONFIG_MAILBOX=y
CONFIG_ARM_SMMU=y
+CONFIG_QCOM_LAZY_MAPPING=y
CONFIG_QCOM_PM=y
CONFIG_MSM_SPM=y
CONFIG_MSM_L2_SPM=y
@@ -414,6 +413,7 @@
CONFIG_MSM_SMD=y
CONFIG_MSM_SMD_DEBUG=y
CONFIG_MSM_GLINK=y
+CONFIG_MSM_TZ_SMMU=y
CONFIG_MSM_GLINK_LOOPBACK_SERVER=y
CONFIG_MSM_GLINK_SMEM_NATIVE_XPRT=y
CONFIG_MSM_GLINK_SPI_XPRT=y
@@ -431,6 +431,9 @@
CONFIG_QTI_RPM_STATS_LOG=y
CONFIG_QCOM_FORCE_WDOG_BITE_ON_PANIC=y
CONFIG_MSM_BAM_DMUX=y
+CONFIG_WCNSS_CORE=y
+CONFIG_WCNSS_CORE_PRONTO=y
+CONFIG_WCNSS_REGISTER_DUMP_ON_BITE=y
CONFIG_QCOM_DEVFREQ_DEVBW=y
CONFIG_IIO=y
CONFIG_QCOM_SPMI_IADC=y
@@ -456,27 +459,11 @@
CONFIG_NLS_CODEPAGE_437=y
CONFIG_NLS_ISO8859_1=y
CONFIG_PRINTK_TIME=y
-CONFIG_DYNAMIC_DEBUG=y
CONFIG_DEBUG_INFO=y
CONFIG_FRAME_WARN=2048
CONFIG_PAGE_OWNER=y
CONFIG_PAGE_OWNER_ENABLE_DEFAULT=y
CONFIG_MAGIC_SYSRQ=y
-CONFIG_DEBUG_PAGEALLOC=y
-CONFIG_SLUB_DEBUG_PANIC_ON=y
-CONFIG_DEBUG_PAGEALLOC_ENABLE_DEFAULT=y
-CONFIG_DEBUG_OBJECTS=y
-CONFIG_DEBUG_OBJECTS_FREE=y
-CONFIG_DEBUG_OBJECTS_TIMERS=y
-CONFIG_DEBUG_OBJECTS_WORK=y
-CONFIG_DEBUG_OBJECTS_RCU_HEAD=y
-CONFIG_DEBUG_OBJECTS_PERCPU_COUNTER=y
-CONFIG_SLUB_DEBUG_ON=y
-CONFIG_DEBUG_KMEMLEAK=y
-CONFIG_DEBUG_KMEMLEAK_EARLY_LOG_SIZE=4000
-CONFIG_DEBUG_KMEMLEAK_DEFAULT_OFF=y
-CONFIG_DEBUG_STACK_USAGE=y
-CONFIG_DEBUG_MEMORY_INIT=y
CONFIG_LOCKUP_DETECTOR=y
# CONFIG_DETECT_HUNG_TASK is not set
CONFIG_WQ_WATCHDOG=y
@@ -485,26 +472,11 @@
CONFIG_PANIC_ON_RT_THROTTLING=y
CONFIG_SCHEDSTATS=y
CONFIG_SCHED_STACK_END_CHECK=y
-CONFIG_DEBUG_SPINLOCK=y
-CONFIG_DEBUG_MUTEXES=y
-CONFIG_DEBUG_ATOMIC_SLEEP=y
-CONFIG_DEBUG_LIST=y
-CONFIG_FAULT_INJECTION=y
-CONFIG_FAIL_PAGE_ALLOC=y
-CONFIG_FAULT_INJECTION_DEBUG_FS=y
-CONFIG_FAULT_INJECTION_STACKTRACE_FILTER=y
-CONFIG_IPC_LOGGING=y
-CONFIG_QCOM_RTB=y
-CONFIG_QCOM_RTB_SEPARATE_CPUS=y
-CONFIG_FUNCTION_TRACER=y
-CONFIG_IRQSOFF_TRACER=y
-CONFIG_PREEMPT_TRACER=y
-CONFIG_BLK_DEV_IO_TRACE=y
-CONFIG_CPU_FREQ_SWITCH_PROFILER=y
+# CONFIG_DEBUG_PREEMPT is not set
+# CONFIG_FTRACE is not set
CONFIG_LKDTM=y
-CONFIG_MEMTEST=y
CONFIG_PANIC_ON_DATA_CORRUPTION=y
-CONFIG_DEBUG_USER=y
+# CONFIG_ARM_UNWIND is not set
CONFIG_PID_IN_CONTEXTIDR=y
CONFIG_DEBUG_SET_MODULE_RONX=y
CONFIG_CORESIGHT=y
diff --git a/arch/arm/configs/msm8909w_defconfig b/arch/arm/configs/msm8909w_defconfig
index 0c04f9c..46052bd 100644
--- a/arch/arm/configs/msm8909w_defconfig
+++ b/arch/arm/configs/msm8909w_defconfig
@@ -271,6 +271,7 @@
CONFIG_SERIAL_MSM_HS=y
CONFIG_SERIAL_MSM_SMD=y
CONFIG_DIAG_CHAR=y
+CONFIG_DIAG_USES_SMD=y
CONFIG_HW_RANDOM=y
CONFIG_HW_RANDOM_MSM_LEGACY=y
CONFIG_MSM_SMD_PKT=y
@@ -318,6 +319,7 @@
CONFIG_MEDIA_CONTROLLER=y
CONFIG_VIDEO_V4L2_SUBDEV_API=y
CONFIG_V4L_PLATFORM_DRIVERS=y
+CONFIG_QCOM_KGSL=y
CONFIG_FB=y
CONFIG_FB_VIRTUAL=y
CONFIG_BACKLIGHT_LCD_SUPPORT=y
@@ -385,6 +387,7 @@
CONFIG_RTC_DRV_QPNP=y
CONFIG_DMADEVICES=y
CONFIG_QCOM_SPS_DMA=y
+CONFIG_SYNC_FILE=y
CONFIG_UIO=y
CONFIG_UIO_MSM_SHAREDMEM=y
CONFIG_STAGING=y
@@ -399,6 +402,7 @@
CONFIG_REMOTE_SPINLOCK_MSM=y
CONFIG_MAILBOX=y
CONFIG_ARM_SMMU=y
+CONFIG_QCOM_LAZY_MAPPING=y
CONFIG_QCOM_PM=y
CONFIG_MSM_SPM=y
CONFIG_MSM_L2_SPM=y
@@ -414,6 +418,7 @@
CONFIG_MSM_SMD=y
CONFIG_MSM_SMD_DEBUG=y
CONFIG_MSM_GLINK=y
+CONFIG_MSM_TZ_SMMU=y
CONFIG_MSM_GLINK_LOOPBACK_SERVER=y
CONFIG_MSM_GLINK_SMEM_NATIVE_XPRT=y
CONFIG_MSM_GLINK_SPI_XPRT=y
@@ -431,6 +436,9 @@
CONFIG_QTI_RPM_STATS_LOG=y
CONFIG_QCOM_FORCE_WDOG_BITE_ON_PANIC=y
CONFIG_MSM_BAM_DMUX=y
+CONFIG_WCNSS_CORE=y
+CONFIG_WCNSS_CORE_PRONTO=y
+CONFIG_WCNSS_REGISTER_DUMP_ON_BITE=y
CONFIG_QCOM_DEVFREQ_DEVBW=y
CONFIG_IIO=y
CONFIG_QCOM_SPMI_IADC=y
diff --git a/arch/arm/configs/msm8937-perf_defconfig b/arch/arm/configs/msm8937-perf_defconfig
new file mode 100644
index 0000000..2413675
--- /dev/null
+++ b/arch/arm/configs/msm8937-perf_defconfig
@@ -0,0 +1,618 @@
+CONFIG_LOCALVERSION="-perf"
+# CONFIG_LOCALVERSION_AUTO is not set
+# CONFIG_FHANDLE is not set
+CONFIG_AUDIT=y
+CONFIG_NO_HZ=y
+CONFIG_HIGH_RES_TIMERS=y
+CONFIG_IRQ_TIME_ACCOUNTING=y
+CONFIG_SCHED_WALT=y
+CONFIG_RCU_EXPERT=y
+CONFIG_RCU_FAST_NO_HZ=y
+CONFIG_RCU_NOCB_CPU=y
+CONFIG_RCU_NOCB_CPU_ALL=y
+CONFIG_IKCONFIG=y
+CONFIG_IKCONFIG_PROC=y
+CONFIG_LOG_CPU_MAX_BUF_SHIFT=17
+CONFIG_CGROUP_FREEZER=y
+CONFIG_CPUSETS=y
+CONFIG_CGROUP_CPUACCT=y
+CONFIG_CGROUP_SCHEDTUNE=y
+CONFIG_RT_GROUP_SCHED=y
+CONFIG_CGROUP_BPF=y
+CONFIG_SCHED_CORE_CTL=y
+CONFIG_NAMESPACES=y
+# CONFIG_UTS_NS is not set
+# CONFIG_PID_NS is not set
+CONFIG_SCHED_AUTOGROUP=y
+CONFIG_SCHED_TUNE=y
+CONFIG_DEFAULT_USE_ENERGY_AWARE=y
+CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
+# CONFIG_RD_XZ is not set
+# CONFIG_RD_LZO is not set
+# CONFIG_RD_LZ4 is not set
+CONFIG_KALLSYMS_ALL=y
+CONFIG_BPF_SYSCALL=y
+# CONFIG_MEMBARRIER is not set
+CONFIG_EMBEDDED=y
+# CONFIG_COMPAT_BRK is not set
+CONFIG_PROFILING=y
+CONFIG_CC_STACKPROTECTOR_STRONG=y
+CONFIG_ARCH_MMAP_RND_BITS=16
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+CONFIG_MODULE_FORCE_UNLOAD=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SIG=y
+CONFIG_MODULE_SIG_FORCE=y
+CONFIG_MODULE_SIG_SHA512=y
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_IOSCHED_DEADLINE is not set
+CONFIG_ARCH_QCOM=y
+CONFIG_ARCH_MSM8937=y
+CONFIG_ARCH_MSM8917=y
+# CONFIG_VDSO is not set
+CONFIG_SMP=y
+CONFIG_SCHED_MC=y
+CONFIG_NR_CPUS=8
+CONFIG_ARM_PSCI=y
+CONFIG_PREEMPT=y
+CONFIG_AEABI=y
+CONFIG_HIGHMEM=y
+CONFIG_CMA=y
+CONFIG_CMA_DEBUGFS=y
+CONFIG_ZSMALLOC=y
+CONFIG_SECCOMP=y
+CONFIG_BUILD_ARM_APPENDED_DTB_IMAGE=y
+CONFIG_CPU_FREQ=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=y
+CONFIG_CPU_FREQ_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_ONDEMAND=y
+CONFIG_CPU_FREQ_GOV_INTERACTIVE=y
+CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y
+CONFIG_CPU_BOOST=y
+CONFIG_CPU_FREQ_GOV_SCHEDUTIL=y
+CONFIG_CPU_FREQ_MSM=y
+CONFIG_CPU_IDLE=y
+CONFIG_VFP=y
+CONFIG_NEON=y
+CONFIG_KERNEL_MODE_NEON=y
+# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
+CONFIG_PM_AUTOSLEEP=y
+CONFIG_PM_WAKELOCKS=y
+CONFIG_PM_WAKELOCKS_LIMIT=0
+# CONFIG_PM_WAKELOCKS_GC is not set
+CONFIG_NET=y
+CONFIG_PACKET=y
+CONFIG_UNIX=y
+CONFIG_XFRM_USER=y
+CONFIG_XFRM_STATISTICS=y
+CONFIG_NET_KEY=y
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_VERBOSE=y
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+CONFIG_INET_AH=y
+CONFIG_INET_ESP=y
+CONFIG_INET_IPCOMP=y
+CONFIG_INET_DIAG_DESTROY=y
+CONFIG_IPV6_ROUTER_PREF=y
+CONFIG_IPV6_ROUTE_INFO=y
+CONFIG_IPV6_OPTIMISTIC_DAD=y
+CONFIG_INET6_AH=y
+CONFIG_INET6_ESP=y
+CONFIG_INET6_IPCOMP=y
+CONFIG_IPV6_MIP6=y
+CONFIG_IPV6_MULTIPLE_TABLES=y
+CONFIG_IPV6_SUBTREES=y
+CONFIG_NETFILTER=y
+CONFIG_NF_CONNTRACK=y
+CONFIG_NF_CONNTRACK_SECMARK=y
+CONFIG_NF_CONNTRACK_EVENTS=y
+CONFIG_NF_CT_PROTO_DCCP=y
+CONFIG_NF_CT_PROTO_SCTP=y
+CONFIG_NF_CT_PROTO_UDPLITE=y
+CONFIG_NF_CONNTRACK_AMANDA=y
+CONFIG_NF_CONNTRACK_FTP=y
+CONFIG_NF_CONNTRACK_H323=y
+CONFIG_NF_CONNTRACK_IRC=y
+CONFIG_NF_CONNTRACK_NETBIOS_NS=y
+CONFIG_NF_CONNTRACK_PPTP=y
+CONFIG_NF_CONNTRACK_SANE=y
+CONFIG_NF_CONNTRACK_TFTP=y
+CONFIG_NF_CT_NETLINK=y
+CONFIG_NETFILTER_XT_TARGET_CLASSIFY=y
+CONFIG_NETFILTER_XT_TARGET_CONNMARK=y
+CONFIG_NETFILTER_XT_TARGET_CONNSECMARK=y
+CONFIG_NETFILTER_XT_TARGET_IDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_HARDIDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_LOG=y
+CONFIG_NETFILTER_XT_TARGET_MARK=y
+CONFIG_NETFILTER_XT_TARGET_NFLOG=y
+CONFIG_NETFILTER_XT_TARGET_NFQUEUE=y
+CONFIG_NETFILTER_XT_TARGET_NOTRACK=y
+CONFIG_NETFILTER_XT_TARGET_TEE=y
+CONFIG_NETFILTER_XT_TARGET_TPROXY=y
+CONFIG_NETFILTER_XT_TARGET_TRACE=y
+CONFIG_NETFILTER_XT_TARGET_SECMARK=y
+CONFIG_NETFILTER_XT_TARGET_TCPMSS=y
+CONFIG_NETFILTER_XT_MATCH_COMMENT=y
+CONFIG_NETFILTER_XT_MATCH_CONNLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_CONNMARK=y
+CONFIG_NETFILTER_XT_MATCH_CONNTRACK=y
+CONFIG_NETFILTER_XT_MATCH_DSCP=y
+CONFIG_NETFILTER_XT_MATCH_ESP=y
+CONFIG_NETFILTER_XT_MATCH_HASHLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_HELPER=y
+CONFIG_NETFILTER_XT_MATCH_IPRANGE=y
+# CONFIG_NETFILTER_XT_MATCH_L2TP is not set
+CONFIG_NETFILTER_XT_MATCH_LENGTH=y
+CONFIG_NETFILTER_XT_MATCH_LIMIT=y
+CONFIG_NETFILTER_XT_MATCH_MAC=y
+CONFIG_NETFILTER_XT_MATCH_MARK=y
+CONFIG_NETFILTER_XT_MATCH_MULTIPORT=y
+CONFIG_NETFILTER_XT_MATCH_POLICY=y
+CONFIG_NETFILTER_XT_MATCH_PKTTYPE=y
+CONFIG_NETFILTER_XT_MATCH_QTAGUID=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA2=y
+CONFIG_NETFILTER_XT_MATCH_SOCKET=y
+CONFIG_NETFILTER_XT_MATCH_STATE=y
+CONFIG_NETFILTER_XT_MATCH_STATISTIC=y
+CONFIG_NETFILTER_XT_MATCH_STRING=y
+CONFIG_NETFILTER_XT_MATCH_TIME=y
+CONFIG_NETFILTER_XT_MATCH_U32=y
+CONFIG_NF_CONNTRACK_IPV4=y
+CONFIG_IP_NF_IPTABLES=y
+CONFIG_IP_NF_MATCH_AH=y
+CONFIG_IP_NF_MATCH_ECN=y
+CONFIG_IP_NF_MATCH_RPFILTER=y
+CONFIG_IP_NF_MATCH_TTL=y
+CONFIG_IP_NF_FILTER=y
+CONFIG_IP_NF_TARGET_REJECT=y
+CONFIG_IP_NF_NAT=y
+CONFIG_IP_NF_TARGET_MASQUERADE=y
+CONFIG_IP_NF_TARGET_NETMAP=y
+CONFIG_IP_NF_TARGET_REDIRECT=y
+CONFIG_IP_NF_MANGLE=y
+CONFIG_IP_NF_RAW=y
+CONFIG_IP_NF_SECURITY=y
+CONFIG_IP_NF_ARPTABLES=y
+CONFIG_IP_NF_ARPFILTER=y
+CONFIG_IP_NF_ARP_MANGLE=y
+CONFIG_NF_CONNTRACK_IPV6=y
+CONFIG_IP6_NF_IPTABLES=y
+CONFIG_IP6_NF_MATCH_RPFILTER=y
+CONFIG_IP6_NF_FILTER=y
+CONFIG_IP6_NF_TARGET_REJECT=y
+CONFIG_IP6_NF_MANGLE=y
+CONFIG_IP6_NF_RAW=y
+CONFIG_BRIDGE_NF_EBTABLES=y
+CONFIG_BRIDGE_EBT_BROUTE=y
+CONFIG_L2TP=y
+CONFIG_L2TP_DEBUGFS=y
+CONFIG_L2TP_V3=y
+CONFIG_L2TP_IP=y
+CONFIG_L2TP_ETH=y
+CONFIG_BRIDGE=y
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_HTB=y
+CONFIG_NET_SCH_PRIO=y
+CONFIG_NET_SCH_MULTIQ=y
+CONFIG_NET_SCH_INGRESS=y
+CONFIG_NET_CLS_FW=y
+CONFIG_NET_CLS_U32=y
+CONFIG_CLS_U32_MARK=y
+CONFIG_NET_CLS_FLOW=y
+CONFIG_NET_EMATCH=y
+CONFIG_NET_EMATCH_CMP=y
+CONFIG_NET_EMATCH_NBYTE=y
+CONFIG_NET_EMATCH_U32=y
+CONFIG_NET_EMATCH_META=y
+CONFIG_NET_EMATCH_TEXT=y
+CONFIG_NET_CLS_ACT=y
+CONFIG_NET_ACT_GACT=y
+CONFIG_NET_ACT_MIRRED=y
+CONFIG_NET_ACT_SKBEDIT=y
+CONFIG_RMNET_DATA=y
+CONFIG_RMNET_DATA_FC=y
+CONFIG_RMNET_DATA_DEBUG_PKT=y
+CONFIG_BT=y
+CONFIG_MSM_BT_POWER=y
+CONFIG_CFG80211=y
+CONFIG_CFG80211_INTERNAL_REGDB=y
+# CONFIG_CFG80211_CRDA_SUPPORT is not set
+CONFIG_RFKILL=y
+CONFIG_NFC_NQ=y
+CONFIG_IPC_ROUTER=y
+CONFIG_IPC_ROUTER_SECURITY=y
+CONFIG_FW_LOADER_USER_HELPER_FALLBACK=y
+CONFIG_REGMAP_ALLOW_WRITE_DEBUGFS=y
+CONFIG_DMA_CMA=y
+CONFIG_ZRAM=y
+CONFIG_BLK_DEV_LOOP=y
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_HDCP_QSEECOM=y
+CONFIG_QSEECOM=y
+CONFIG_MEMORY_STATE_TIME=y
+CONFIG_SCSI=y
+CONFIG_BLK_DEV_SD=y
+CONFIG_CHR_DEV_SG=y
+CONFIG_CHR_DEV_SCH=y
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SCAN_ASYNC=y
+CONFIG_SCSI_UFSHCD=y
+CONFIG_SCSI_UFSHCD_PLATFORM=y
+CONFIG_SCSI_UFS_QCOM=y
+CONFIG_SCSI_UFS_QCOM_ICE=y
+CONFIG_SCSI_UFSHCD_CMD_LOGGING=y
+CONFIG_MD=y
+CONFIG_BLK_DEV_DM=y
+CONFIG_DM_DEBUG=y
+CONFIG_DM_CRYPT=y
+CONFIG_DM_REQ_CRYPT=y
+CONFIG_DM_UEVENT=y
+CONFIG_DM_VERITY=y
+CONFIG_DM_VERITY_FEC=y
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=y
+CONFIG_TUN=y
+CONFIG_PPP=y
+CONFIG_PPP_BSDCOMP=y
+CONFIG_PPP_DEFLATE=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_MPPE=y
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPPOE=y
+CONFIG_PPPOL2TP=y
+CONFIG_PPPOLAC=y
+CONFIG_PPPOPNS=y
+CONFIG_PPP_ASYNC=y
+CONFIG_PPP_SYNC_TTY=y
+CONFIG_USB_USBNET=y
+CONFIG_WCNSS_MEM_PRE_ALLOC=y
+CONFIG_CLD_LL_CORE=y
+CONFIG_INPUT_EVDEV=y
+CONFIG_KEYBOARD_GPIO=y
+# CONFIG_INPUT_MOUSE is not set
+CONFIG_INPUT_JOYSTICK=y
+CONFIG_INPUT_TOUCHSCREEN=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
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_DEVMEM is not set
+# CONFIG_DEVKMEM is not set
+CONFIG_SERIAL_MSM_HS=y
+CONFIG_SERIAL_MSM_SMD=y
+CONFIG_DIAG_CHAR=y
+CONFIG_DIAG_USES_SMD=y
+CONFIG_HW_RANDOM=y
+CONFIG_HW_RANDOM_MSM_LEGACY=y
+CONFIG_MSM_SMD_PKT=y
+CONFIG_MSM_ADSPRPC=y
+CONFIG_MSM_RDBG=m
+CONFIG_I2C_CHARDEV=y
+CONFIG_I2C_MSM_V2=y
+CONFIG_SPI=y
+CONFIG_SPI_QUP=y
+CONFIG_SPI_SPIDEV=y
+CONFIG_SLIMBUS_MSM_NGD=y
+CONFIG_SPMI=y
+CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
+CONFIG_PINCTRL_MSM8937=y
+CONFIG_PINCTRL_MSM8917=y
+CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
+CONFIG_GPIO_SYSFS=y
+CONFIG_GPIO_QPNP_PIN=y
+CONFIG_GPIO_QPNP_PIN_DEBUG=y
+CONFIG_POWER_RESET=y
+CONFIG_POWER_RESET_QCOM=y
+CONFIG_QCOM_DLOAD_MODE=y
+CONFIG_POWER_RESET_SYSCON=y
+CONFIG_POWER_SUPPLY=y
+CONFIG_QPNP_FG=y
+CONFIG_SMB135X_CHARGER=y
+CONFIG_SMB1351_USB_CHARGER=y
+CONFIG_QPNP_SMB5=y
+CONFIG_QPNP_SMBCHARGER=y
+CONFIG_QPNP_TYPEC=y
+CONFIG_QPNP_QG=y
+CONFIG_MSM_APM=y
+CONFIG_SENSORS_QPNP_ADC_VOLTAGE=y
+CONFIG_THERMAL=y
+CONFIG_THERMAL_QPNP=y
+CONFIG_THERMAL_QPNP_ADC_TM=y
+CONFIG_THERMAL_TSENS=y
+CONFIG_MSM_BCL_PERIPHERAL_CTL=y
+CONFIG_QTI_THERMAL_LIMITS_DCVS=y
+CONFIG_MFD_SPMI_PMIC=y
+CONFIG_REGULATOR=y
+CONFIG_REGULATOR_FIXED_VOLTAGE=y
+CONFIG_REGULATOR_PROXY_CONSUMER=y
+CONFIG_REGULATOR_CPR=y
+CONFIG_REGULATOR_CPR4_APSS=y
+CONFIG_REGULATOR_CPRH_KBSS=y
+CONFIG_REGULATOR_MEM_ACC=y
+CONFIG_REGULATOR_MSM_GFX_LDO=y
+CONFIG_REGULATOR_QPNP_LABIBB=y
+CONFIG_REGULATOR_QPNP_LCDB=y
+CONFIG_REGULATOR_QPNP=y
+CONFIG_REGULATOR_RPM_SMD=y
+CONFIG_REGULATOR_SPM=y
+CONFIG_REGULATOR_STUB=y
+CONFIG_MEDIA_SUPPORT=y
+CONFIG_MEDIA_CAMERA_SUPPORT=y
+CONFIG_MEDIA_CONTROLLER=y
+CONFIG_VIDEO_V4L2_SUBDEV_API=y
+CONFIG_MEDIA_USB_SUPPORT=y
+CONFIG_USB_VIDEO_CLASS=y
+CONFIG_V4L_PLATFORM_DRIVERS=y
+CONFIG_MSM_CAMERA=y
+CONFIG_MSM_CAMERA_DEBUG=y
+CONFIG_MSMB_CAMERA=y
+CONFIG_MSMB_CAMERA_DEBUG=y
+CONFIG_MSM_CAMERA_SENSOR=y
+CONFIG_MSM_CPP=y
+CONFIG_MSM_CCI=y
+CONFIG_MSM_CSI20_HEADER=y
+CONFIG_MSM_CSI22_HEADER=y
+CONFIG_MSM_CSI30_HEADER=y
+CONFIG_MSM_CSI31_HEADER=y
+CONFIG_MSM_CSIPHY=y
+CONFIG_MSM_CSID=y
+CONFIG_MSM_EEPROM=y
+CONFIG_MSM_ISPIF_V2=y
+CONFIG_IMX134=y
+CONFIG_IMX132=y
+CONFIG_OV9724=y
+CONFIG_OV5648=y
+CONFIG_GC0339=y
+CONFIG_OV8825=y
+CONFIG_OV8865=y
+CONFIG_s5k4e1=y
+CONFIG_OV12830=y
+CONFIG_MSM_V4L2_VIDEO_OVERLAY_DEVICE=y
+CONFIG_MSMB_JPEG=y
+CONFIG_MSM_FD=y
+CONFIG_MSM_JPEGDMA=y
+CONFIG_MSM_VIDC_3X_V4L2=y
+CONFIG_MSM_VIDC_3X_GOVERNORS=y
+CONFIG_RADIO_IRIS=y
+CONFIG_RADIO_IRIS_TRANSPORT=y
+CONFIG_QCOM_KGSL=y
+CONFIG_FB=y
+CONFIG_FB_MSM=y
+CONFIG_FB_MSM_MDSS=y
+CONFIG_FB_MSM_MDSS_WRITEBACK=y
+CONFIG_FB_MSM_MDSS_DSI_CTRL_STATUS=y
+CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
+CONFIG_BACKLIGHT_LCD_SUPPORT=y
+CONFIG_BACKLIGHT_CLASS_DEVICE=y
+CONFIG_SOUND=y
+CONFIG_SND=y
+CONFIG_SND_DYNAMIC_MINORS=y
+CONFIG_SND_USB_AUDIO=y
+CONFIG_SND_SOC=y
+CONFIG_UHID=y
+CONFIG_HID_APPLE=y
+CONFIG_HID_ELECOM=y
+CONFIG_HID_MAGICMOUSE=y
+CONFIG_HID_MICROSOFT=y
+CONFIG_HID_MULTITOUCH=y
+CONFIG_USB_HIDDEV=y
+CONFIG_USB=y
+CONFIG_USB_ANNOUNCE_NEW_DEVICES=y
+CONFIG_USB_MON=y
+CONFIG_USB_XHCI_HCD=y
+CONFIG_USB_EHCI_HCD=y
+CONFIG_USB_EHCI_MSM=y
+CONFIG_USB_EHCI_HCD_PLATFORM=y
+CONFIG_USB_OHCI_HCD=y
+CONFIG_USB_OHCI_HCD_PLATFORM=y
+CONFIG_USB_ACM=y
+CONFIG_USB_STORAGE=y
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_USBAT=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_ALAUDA=y
+CONFIG_USB_STORAGE_ONETOUCH=y
+CONFIG_USB_STORAGE_KARMA=y
+CONFIG_USB_STORAGE_CYPRESS_ATACB=y
+CONFIG_USB_DWC3=y
+CONFIG_USB_DWC3_MSM=y
+CONFIG_USB_SERIAL=y
+CONFIG_USB_EHSET_TEST_FIXTURE=y
+CONFIG_NOP_USB_XCEIV=y
+CONFIG_DUAL_ROLE_USB_INTF=y
+CONFIG_USB_MSM_SSPHY_QMP=y
+CONFIG_MSM_QUSB_PHY=y
+CONFIG_USB_GADGET=y
+CONFIG_USB_GADGET_DEBUG_FILES=y
+CONFIG_USB_GADGET_DEBUG_FS=y
+CONFIG_USB_GADGET_VBUS_DRAW=500
+CONFIG_USB_CI13XXX_MSM=y
+CONFIG_USB_CONFIGFS=y
+CONFIG_USB_CONFIGFS_SERIAL=y
+CONFIG_USB_CONFIGFS_NCM=y
+CONFIG_USB_CONFIGFS_QCRNDIS=y
+CONFIG_USB_CONFIGFS_RNDIS=y
+CONFIG_USB_CONFIGFS_RMNET_BAM=y
+CONFIG_USB_CONFIGFS_MASS_STORAGE=y
+CONFIG_USB_CONFIGFS_F_FS=y
+CONFIG_USB_CONFIGFS_F_MTP=y
+CONFIG_USB_CONFIGFS_F_PTP=y
+CONFIG_USB_CONFIGFS_F_ACC=y
+CONFIG_USB_CONFIGFS_F_AUDIO_SRC=y
+CONFIG_USB_CONFIGFS_UEVENT=y
+CONFIG_USB_CONFIGFS_F_MIDI=y
+CONFIG_USB_CONFIGFS_F_HID=y
+CONFIG_USB_CONFIGFS_F_DIAG=y
+CONFIG_USB_CONFIGFS_F_CDEV=y
+CONFIG_USB_CONFIGFS_F_CCID=y
+CONFIG_USB_CONFIGFS_F_QDSS=y
+CONFIG_MMC=y
+CONFIG_MMC_PERF_PROFILING=y
+CONFIG_MMC_PARANOID_SD_INIT=y
+CONFIG_MMC_CLKGATE=y
+CONFIG_MMC_BLOCK_MINORS=32
+CONFIG_MMC_BLOCK_DEFERRED_RESUME=y
+CONFIG_MMC_TEST=y
+CONFIG_MMC_SDHCI=y
+CONFIG_MMC_SDHCI_PLTFM=y
+CONFIG_MMC_SDHCI_MSM=y
+CONFIG_MMC_SDHCI_MSM_ICE=y
+CONFIG_MMC_CQ_HCI=y
+CONFIG_LEDS_QTI_TRI_LED=y
+CONFIG_LEDS_QPNP=y
+CONFIG_LEDS_QPNP_FLASH=y
+CONFIG_LEDS_QPNP_FLASH_V2=y
+CONFIG_LEDS_QPNP_WLED=y
+CONFIG_LEDS_QPNP_HAPTICS=y
+CONFIG_LEDS_QPNP_VIBRATOR_LDO=y
+CONFIG_LEDS_TRIGGERS=y
+CONFIG_LEDS_TRIGGER_TIMER=y
+CONFIG_EDAC=y
+CONFIG_EDAC_MM_EDAC=y
+CONFIG_RTC_CLASS=y
+CONFIG_RTC_DRV_QPNP=y
+CONFIG_DMADEVICES=y
+CONFIG_QCOM_SPS_DMA=y
+CONFIG_UIO=y
+CONFIG_UIO_MSM_SHAREDMEM=y
+CONFIG_STAGING=y
+CONFIG_ASHMEM=y
+CONFIG_ANDROID_LOW_MEMORY_KILLER=y
+CONFIG_ION=y
+CONFIG_ION_MSM=y
+CONFIG_IPA=y
+CONFIG_RMNET_IPA=y
+CONFIG_RNDIS_IPA=y
+CONFIG_SPS=y
+CONFIG_SPS_SUPPORT_NDP_BAM=y
+CONFIG_QPNP_COINCELL=y
+CONFIG_QPNP_REVID=y
+CONFIG_USB_BAM=y
+CONFIG_MSM_RMNET_BAM=y
+CONFIG_MSM_MDSS_PLL=y
+CONFIG_REMOTE_SPINLOCK_MSM=y
+CONFIG_MAILBOX=y
+CONFIG_ARM_SMMU=y
+CONFIG_QCOM_LAZY_MAPPING=y
+CONFIG_QCOM_RUN_QUEUE_STATS=y
+CONFIG_MSM_SPM=y
+CONFIG_MSM_L2_SPM=y
+CONFIG_MSM_BOOT_STATS=y
+CONFIG_QCOM_WATCHDOG_V2=y
+CONFIG_QCOM_MEMORY_DUMP_V2=y
+CONFIG_MSM_RPM_SMD=y
+CONFIG_QCOM_BUS_SCALING=y
+CONFIG_QCOM_SECURE_BUFFER=y
+CONFIG_QCOM_EARLY_RANDOM=y
+CONFIG_MSM_SMEM=y
+CONFIG_MSM_SMD=y
+CONFIG_MSM_SMD_DEBUG=y
+CONFIG_MSM_TZ_SMMU=y
+CONFIG_MSM_SMP2P=y
+CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
+CONFIG_MSM_QMI_INTERFACE=y
+CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_PIL=y
+CONFIG_MSM_PIL_SSR_GENERIC=y
+CONFIG_MSM_PIL_MSS_QDSP6V5=y
+CONFIG_ICNSS=y
+CONFIG_MSM_PERFORMANCE=y
+CONFIG_MSM_EVENT_TIMER=y
+CONFIG_MSM_AVTIMER=y
+CONFIG_MSM_PM=y
+CONFIG_QTI_RPM_STATS_LOG=y
+CONFIG_QCOM_FORCE_WDOG_BITE_ON_PANIC=y
+CONFIG_MEM_SHARE_QMI_SERVICE=y
+CONFIG_MSM_BAM_DMUX=y
+CONFIG_WCNSS_CORE=y
+CONFIG_WCNSS_CORE_PRONTO=y
+CONFIG_WCNSS_REGISTER_DUMP_ON_BITE=y
+CONFIG_QCOM_BIMC_BWMON=y
+CONFIG_DEVFREQ_GOV_QCOM_BW_HWMON=y
+CONFIG_DEVFREQ_SIMPLE_DEV=y
+CONFIG_QCOM_DEVFREQ_DEVBW=y
+CONFIG_SPDM_SCM=y
+CONFIG_DEVFREQ_SPDM=y
+CONFIG_PWM=y
+CONFIG_PWM_QPNP=y
+CONFIG_PWM_QTI_LPG=y
+CONFIG_QTI_MPM=y
+CONFIG_ANDROID=y
+CONFIG_ANDROID_BINDER_IPC=y
+CONFIG_SENSORS_SSC=y
+CONFIG_MSM_TZ_LOG=y
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT3_FS=y
+CONFIG_EXT4_FS_SECURITY=y
+CONFIG_QUOTA=y
+CONFIG_QUOTA_NETLINK_INTERFACE=y
+CONFIG_QFMT_V2=y
+CONFIG_FUSE_FS=y
+CONFIG_MSDOS_FS=y
+CONFIG_VFAT_FS=y
+CONFIG_TMPFS=y
+CONFIG_ECRYPT_FS=y
+CONFIG_ECRYPT_FS_MESSAGING=y
+# CONFIG_NETWORK_FILESYSTEMS is not set
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_ISO8859_1=y
+CONFIG_PRINTK_TIME=y
+CONFIG_DEBUG_INFO=y
+CONFIG_FRAME_WARN=2048
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_PANIC_TIMEOUT=5
+CONFIG_SCHEDSTATS=y
+CONFIG_SCHED_STACK_END_CHECK=y
+# CONFIG_DEBUG_PREEMPT is not set
+CONFIG_IPC_LOGGING=y
+CONFIG_CPU_FREQ_SWITCH_PROFILER=y
+CONFIG_CORESIGHT=y
+CONFIG_CORESIGHT_REMOTE_ETM=y
+CONFIG_CORESIGHT_REMOTE_ETM_DEFAULT_ENABLE=0
+CONFIG_CORESIGHT_STM=y
+CONFIG_CORESIGHT_TPDA=y
+CONFIG_CORESIGHT_TPDM=y
+CONFIG_CORESIGHT_CTI=y
+CONFIG_CORESIGHT_EVENT=y
+CONFIG_CORESIGHT_HWEVENT=y
+CONFIG_SECURITY_PERF_EVENTS_RESTRICT=y
+CONFIG_SECURITY=y
+CONFIG_LSM_MMAP_MIN_ADDR=4096
+CONFIG_HARDENED_USERCOPY=y
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SMACK=y
+CONFIG_CRYPTO_CTR=y
+CONFIG_CRYPTO_XCBC=y
+CONFIG_CRYPTO_MD4=y
+CONFIG_CRYPTO_TWOFISH=y
+CONFIG_CRYPTO_ANSI_CPRNG=y
+CONFIG_CRYPTO_DEV_QCOM_MSM_QCE=y
+CONFIG_CRYPTO_DEV_QCRYPTO=y
+CONFIG_CRYPTO_DEV_QCEDEV=y
+CONFIG_CRYPTO_DEV_OTA_CRYPTO=y
+CONFIG_CRYPTO_DEV_QCOM_ICE=y
+CONFIG_ARM_CRYPTO=y
+CONFIG_CRYPTO_SHA1_ARM_NEON=y
+CONFIG_CRYPTO_SHA2_ARM_CE=y
+CONFIG_CRYPTO_AES_ARM_BS=y
+CONFIG_CRYPTO_AES_ARM_CE=y
+CONFIG_QMI_ENCDEC=y
diff --git a/arch/arm/configs/msm8937_defconfig b/arch/arm/configs/msm8937_defconfig
new file mode 100644
index 0000000..df2dc40
--- /dev/null
+++ b/arch/arm/configs/msm8937_defconfig
@@ -0,0 +1,681 @@
+# CONFIG_LOCALVERSION_AUTO is not set
+# CONFIG_FHANDLE is not set
+CONFIG_AUDIT=y
+CONFIG_NO_HZ=y
+CONFIG_HIGH_RES_TIMERS=y
+CONFIG_IRQ_TIME_ACCOUNTING=y
+CONFIG_SCHED_WALT=y
+CONFIG_TASKSTATS=y
+CONFIG_TASK_DELAY_ACCT=y
+CONFIG_TASK_XACCT=y
+CONFIG_TASK_IO_ACCOUNTING=y
+CONFIG_RCU_EXPERT=y
+CONFIG_RCU_FAST_NO_HZ=y
+CONFIG_RCU_NOCB_CPU=y
+CONFIG_RCU_NOCB_CPU_ALL=y
+CONFIG_IKCONFIG=y
+CONFIG_IKCONFIG_PROC=y
+CONFIG_LOG_CPU_MAX_BUF_SHIFT=17
+CONFIG_CGROUP_DEBUG=y
+CONFIG_CGROUP_FREEZER=y
+CONFIG_CPUSETS=y
+CONFIG_CGROUP_CPUACCT=y
+CONFIG_CGROUP_SCHEDTUNE=y
+CONFIG_RT_GROUP_SCHED=y
+CONFIG_CGROUP_BPF=y
+CONFIG_SCHED_CORE_CTL=y
+CONFIG_NAMESPACES=y
+# CONFIG_UTS_NS is not set
+# CONFIG_PID_NS is not set
+CONFIG_SCHED_AUTOGROUP=y
+CONFIG_SCHED_TUNE=y
+CONFIG_DEFAULT_USE_ENERGY_AWARE=y
+CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
+# CONFIG_RD_XZ is not set
+# CONFIG_RD_LZO is not set
+# CONFIG_RD_LZ4 is not set
+CONFIG_KALLSYMS_ALL=y
+CONFIG_BPF_SYSCALL=y
+# CONFIG_MEMBARRIER is not set
+CONFIG_EMBEDDED=y
+# CONFIG_COMPAT_BRK is not set
+CONFIG_PROFILING=y
+CONFIG_OPROFILE=m
+CONFIG_KPROBES=y
+CONFIG_CC_STACKPROTECTOR_STRONG=y
+CONFIG_ARCH_MMAP_RND_BITS=16
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+CONFIG_MODULE_FORCE_UNLOAD=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SIG=y
+CONFIG_MODULE_SIG_FORCE=y
+CONFIG_MODULE_SIG_SHA512=y
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_IOSCHED_DEADLINE is not set
+CONFIG_ARCH_QCOM=y
+CONFIG_ARCH_MSM8937=y
+CONFIG_ARCH_MSM8917=y
+# CONFIG_VDSO is not set
+CONFIG_SMP=y
+CONFIG_SCHED_MC=y
+CONFIG_NR_CPUS=8
+CONFIG_ARM_PSCI=y
+CONFIG_PREEMPT=y
+CONFIG_AEABI=y
+CONFIG_HIGHMEM=y
+CONFIG_CMA=y
+CONFIG_CMA_DEBUGFS=y
+CONFIG_ZSMALLOC=y
+CONFIG_SECCOMP=y
+CONFIG_BUILD_ARM_APPENDED_DTB_IMAGE=y
+CONFIG_CPU_FREQ=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=y
+CONFIG_CPU_FREQ_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_ONDEMAND=y
+CONFIG_CPU_FREQ_GOV_INTERACTIVE=y
+CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y
+CONFIG_CPU_BOOST=y
+CONFIG_CPU_FREQ_GOV_SCHEDUTIL=y
+CONFIG_CPU_FREQ_MSM=y
+CONFIG_CPU_IDLE=y
+CONFIG_VFP=y
+CONFIG_NEON=y
+CONFIG_KERNEL_MODE_NEON=y
+# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
+CONFIG_PM_AUTOSLEEP=y
+CONFIG_PM_WAKELOCKS=y
+CONFIG_PM_WAKELOCKS_LIMIT=0
+# CONFIG_PM_WAKELOCKS_GC is not set
+CONFIG_PM_DEBUG=y
+CONFIG_NET=y
+CONFIG_PACKET=y
+CONFIG_UNIX=y
+CONFIG_XFRM_USER=y
+CONFIG_XFRM_STATISTICS=y
+CONFIG_NET_KEY=y
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_VERBOSE=y
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+CONFIG_INET_AH=y
+CONFIG_INET_ESP=y
+CONFIG_INET_IPCOMP=y
+CONFIG_INET_DIAG_DESTROY=y
+CONFIG_IPV6_ROUTER_PREF=y
+CONFIG_IPV6_ROUTE_INFO=y
+CONFIG_IPV6_OPTIMISTIC_DAD=y
+CONFIG_INET6_AH=y
+CONFIG_INET6_ESP=y
+CONFIG_INET6_IPCOMP=y
+CONFIG_IPV6_MIP6=y
+CONFIG_IPV6_MULTIPLE_TABLES=y
+CONFIG_IPV6_SUBTREES=y
+CONFIG_NETFILTER=y
+CONFIG_NF_CONNTRACK=y
+CONFIG_NF_CONNTRACK_SECMARK=y
+CONFIG_NF_CONNTRACK_EVENTS=y
+CONFIG_NF_CT_PROTO_DCCP=y
+CONFIG_NF_CT_PROTO_SCTP=y
+CONFIG_NF_CT_PROTO_UDPLITE=y
+CONFIG_NF_CONNTRACK_AMANDA=y
+CONFIG_NF_CONNTRACK_FTP=y
+CONFIG_NF_CONNTRACK_H323=y
+CONFIG_NF_CONNTRACK_IRC=y
+CONFIG_NF_CONNTRACK_NETBIOS_NS=y
+CONFIG_NF_CONNTRACK_PPTP=y
+CONFIG_NF_CONNTRACK_SANE=y
+CONFIG_NF_CONNTRACK_TFTP=y
+CONFIG_NF_CT_NETLINK=y
+CONFIG_NETFILTER_XT_TARGET_CLASSIFY=y
+CONFIG_NETFILTER_XT_TARGET_CONNMARK=y
+CONFIG_NETFILTER_XT_TARGET_CONNSECMARK=y
+CONFIG_NETFILTER_XT_TARGET_IDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_HARDIDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_LOG=y
+CONFIG_NETFILTER_XT_TARGET_MARK=y
+CONFIG_NETFILTER_XT_TARGET_NFLOG=y
+CONFIG_NETFILTER_XT_TARGET_NFQUEUE=y
+CONFIG_NETFILTER_XT_TARGET_NOTRACK=y
+CONFIG_NETFILTER_XT_TARGET_TEE=y
+CONFIG_NETFILTER_XT_TARGET_TPROXY=y
+CONFIG_NETFILTER_XT_TARGET_TRACE=y
+CONFIG_NETFILTER_XT_TARGET_SECMARK=y
+CONFIG_NETFILTER_XT_TARGET_TCPMSS=y
+CONFIG_NETFILTER_XT_MATCH_COMMENT=y
+CONFIG_NETFILTER_XT_MATCH_CONNLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_CONNMARK=y
+CONFIG_NETFILTER_XT_MATCH_CONNTRACK=y
+CONFIG_NETFILTER_XT_MATCH_DSCP=y
+CONFIG_NETFILTER_XT_MATCH_ESP=y
+CONFIG_NETFILTER_XT_MATCH_HASHLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_HELPER=y
+CONFIG_NETFILTER_XT_MATCH_IPRANGE=y
+# CONFIG_NETFILTER_XT_MATCH_L2TP is not set
+CONFIG_NETFILTER_XT_MATCH_LENGTH=y
+CONFIG_NETFILTER_XT_MATCH_LIMIT=y
+CONFIG_NETFILTER_XT_MATCH_MAC=y
+CONFIG_NETFILTER_XT_MATCH_MARK=y
+CONFIG_NETFILTER_XT_MATCH_MULTIPORT=y
+CONFIG_NETFILTER_XT_MATCH_POLICY=y
+CONFIG_NETFILTER_XT_MATCH_PKTTYPE=y
+CONFIG_NETFILTER_XT_MATCH_QTAGUID=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA2=y
+CONFIG_NETFILTER_XT_MATCH_SOCKET=y
+CONFIG_NETFILTER_XT_MATCH_STATE=y
+CONFIG_NETFILTER_XT_MATCH_STATISTIC=y
+CONFIG_NETFILTER_XT_MATCH_STRING=y
+CONFIG_NETFILTER_XT_MATCH_TIME=y
+CONFIG_NETFILTER_XT_MATCH_U32=y
+CONFIG_NF_CONNTRACK_IPV4=y
+CONFIG_IP_NF_IPTABLES=y
+CONFIG_IP_NF_MATCH_AH=y
+CONFIG_IP_NF_MATCH_ECN=y
+CONFIG_IP_NF_MATCH_RPFILTER=y
+CONFIG_IP_NF_MATCH_TTL=y
+CONFIG_IP_NF_FILTER=y
+CONFIG_IP_NF_TARGET_REJECT=y
+CONFIG_IP_NF_NAT=y
+CONFIG_IP_NF_TARGET_MASQUERADE=y
+CONFIG_IP_NF_TARGET_NETMAP=y
+CONFIG_IP_NF_TARGET_REDIRECT=y
+CONFIG_IP_NF_MANGLE=y
+CONFIG_IP_NF_RAW=y
+CONFIG_IP_NF_SECURITY=y
+CONFIG_IP_NF_ARPTABLES=y
+CONFIG_IP_NF_ARPFILTER=y
+CONFIG_IP_NF_ARP_MANGLE=y
+CONFIG_NF_CONNTRACK_IPV6=y
+CONFIG_IP6_NF_IPTABLES=y
+CONFIG_IP6_NF_MATCH_RPFILTER=y
+CONFIG_IP6_NF_FILTER=y
+CONFIG_IP6_NF_TARGET_REJECT=y
+CONFIG_IP6_NF_MANGLE=y
+CONFIG_IP6_NF_RAW=y
+CONFIG_BRIDGE_NF_EBTABLES=y
+CONFIG_BRIDGE_EBT_BROUTE=y
+CONFIG_L2TP=y
+CONFIG_L2TP_DEBUGFS=y
+CONFIG_L2TP_V3=y
+CONFIG_L2TP_IP=y
+CONFIG_L2TP_ETH=y
+CONFIG_BRIDGE=y
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_HTB=y
+CONFIG_NET_SCH_PRIO=y
+CONFIG_NET_SCH_MULTIQ=y
+CONFIG_NET_SCH_INGRESS=y
+CONFIG_NET_CLS_FW=y
+CONFIG_NET_CLS_U32=y
+CONFIG_CLS_U32_MARK=y
+CONFIG_NET_CLS_FLOW=y
+CONFIG_NET_EMATCH=y
+CONFIG_NET_EMATCH_CMP=y
+CONFIG_NET_EMATCH_NBYTE=y
+CONFIG_NET_EMATCH_U32=y
+CONFIG_NET_EMATCH_META=y
+CONFIG_NET_EMATCH_TEXT=y
+CONFIG_NET_CLS_ACT=y
+CONFIG_NET_ACT_GACT=y
+CONFIG_NET_ACT_MIRRED=y
+CONFIG_NET_ACT_SKBEDIT=y
+CONFIG_DNS_RESOLVER=y
+CONFIG_RMNET_DATA=y
+CONFIG_RMNET_DATA_FC=y
+CONFIG_RMNET_DATA_DEBUG_PKT=y
+CONFIG_BT=y
+CONFIG_MSM_BT_POWER=y
+CONFIG_CFG80211=y
+CONFIG_CFG80211_INTERNAL_REGDB=y
+# CONFIG_CFG80211_CRDA_SUPPORT is not set
+CONFIG_RFKILL=y
+CONFIG_NFC_NQ=y
+CONFIG_IPC_ROUTER=y
+CONFIG_IPC_ROUTER_SECURITY=y
+CONFIG_FW_LOADER_USER_HELPER_FALLBACK=y
+CONFIG_REGMAP_ALLOW_WRITE_DEBUGFS=y
+CONFIG_DMA_CMA=y
+CONFIG_ZRAM=y
+CONFIG_BLK_DEV_LOOP=y
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_HDCP_QSEECOM=y
+CONFIG_QSEECOM=y
+CONFIG_UID_SYS_STATS=y
+CONFIG_MEMORY_STATE_TIME=y
+CONFIG_SCSI=y
+CONFIG_BLK_DEV_SD=y
+CONFIG_CHR_DEV_SG=y
+CONFIG_CHR_DEV_SCH=y
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SCAN_ASYNC=y
+CONFIG_SCSI_UFSHCD=y
+CONFIG_SCSI_UFSHCD_PLATFORM=y
+CONFIG_SCSI_UFS_QCOM=y
+CONFIG_SCSI_UFS_QCOM_ICE=y
+CONFIG_SCSI_UFSHCD_CMD_LOGGING=y
+CONFIG_MD=y
+CONFIG_BLK_DEV_DM=y
+CONFIG_DM_DEBUG=y
+CONFIG_DM_CRYPT=y
+CONFIG_DM_REQ_CRYPT=y
+CONFIG_DM_UEVENT=y
+CONFIG_DM_VERITY=y
+CONFIG_DM_VERITY_FEC=y
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=y
+CONFIG_TUN=y
+CONFIG_PPP=y
+CONFIG_PPP_BSDCOMP=y
+CONFIG_PPP_DEFLATE=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_MPPE=y
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPPOE=y
+CONFIG_PPPOL2TP=y
+CONFIG_PPPOLAC=y
+CONFIG_PPPOPNS=y
+CONFIG_PPP_ASYNC=y
+CONFIG_PPP_SYNC_TTY=y
+CONFIG_USB_USBNET=y
+CONFIG_WCNSS_MEM_PRE_ALLOC=y
+CONFIG_CLD_LL_CORE=y
+CONFIG_INPUT_EVDEV=y
+CONFIG_KEYBOARD_GPIO=y
+# CONFIG_INPUT_MOUSE is not set
+CONFIG_INPUT_JOYSTICK=y
+CONFIG_INPUT_TOUCHSCREEN=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
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_DEVMEM is not set
+# CONFIG_DEVKMEM is not set
+CONFIG_SERIAL_MSM=y
+CONFIG_SERIAL_MSM_CONSOLE=y
+CONFIG_SERIAL_MSM_HS=y
+CONFIG_SERIAL_MSM_SMD=y
+CONFIG_DIAG_CHAR=y
+CONFIG_DIAG_USES_SMD=y
+CONFIG_HW_RANDOM=y
+CONFIG_HW_RANDOM_MSM_LEGACY=y
+CONFIG_MSM_SMD_PKT=y
+CONFIG_MSM_ADSPRPC=y
+CONFIG_MSM_RDBG=m
+CONFIG_I2C_CHARDEV=y
+CONFIG_I2C_MSM_V2=y
+CONFIG_SPI=y
+CONFIG_SPI_QUP=y
+CONFIG_SPI_SPIDEV=y
+CONFIG_SLIMBUS_MSM_NGD=y
+CONFIG_SPMI=y
+CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
+CONFIG_PINCTRL_MSM8937=y
+CONFIG_PINCTRL_MSM8917=y
+CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
+CONFIG_GPIO_SYSFS=y
+CONFIG_GPIO_QPNP_PIN=y
+CONFIG_GPIO_QPNP_PIN_DEBUG=y
+CONFIG_POWER_RESET=y
+CONFIG_POWER_RESET_QCOM=y
+CONFIG_QCOM_DLOAD_MODE=y
+CONFIG_POWER_RESET_SYSCON=y
+CONFIG_POWER_SUPPLY=y
+CONFIG_QPNP_FG=y
+CONFIG_SMB135X_CHARGER=y
+CONFIG_SMB1351_USB_CHARGER=y
+CONFIG_QPNP_SMB5=y
+CONFIG_QPNP_SMBCHARGER=y
+CONFIG_QPNP_TYPEC=y
+CONFIG_QPNP_QG=y
+CONFIG_MSM_APM=y
+CONFIG_SENSORS_QPNP_ADC_VOLTAGE=y
+CONFIG_THERMAL=y
+CONFIG_THERMAL_QPNP=y
+CONFIG_THERMAL_QPNP_ADC_TM=y
+CONFIG_THERMAL_TSENS=y
+CONFIG_MSM_BCL_PERIPHERAL_CTL=y
+CONFIG_QTI_THERMAL_LIMITS_DCVS=y
+CONFIG_MFD_SPMI_PMIC=y
+CONFIG_REGULATOR=y
+CONFIG_REGULATOR_FIXED_VOLTAGE=y
+CONFIG_REGULATOR_PROXY_CONSUMER=y
+CONFIG_REGULATOR_CPR=y
+CONFIG_REGULATOR_CPR4_APSS=y
+CONFIG_REGULATOR_CPRH_KBSS=y
+CONFIG_REGULATOR_MEM_ACC=y
+CONFIG_REGULATOR_MSM_GFX_LDO=y
+CONFIG_REGULATOR_QPNP_LABIBB=y
+CONFIG_REGULATOR_QPNP_LCDB=y
+CONFIG_REGULATOR_QPNP=y
+CONFIG_REGULATOR_RPM_SMD=y
+CONFIG_REGULATOR_SPM=y
+CONFIG_REGULATOR_STUB=y
+CONFIG_MEDIA_SUPPORT=y
+CONFIG_MEDIA_CAMERA_SUPPORT=y
+CONFIG_MEDIA_CONTROLLER=y
+CONFIG_VIDEO_V4L2_SUBDEV_API=y
+CONFIG_MEDIA_USB_SUPPORT=y
+CONFIG_USB_VIDEO_CLASS=y
+CONFIG_V4L_PLATFORM_DRIVERS=y
+CONFIG_MSM_CAMERA=y
+CONFIG_MSM_CAMERA_DEBUG=y
+CONFIG_MSMB_CAMERA=y
+CONFIG_MSMB_CAMERA_DEBUG=y
+CONFIG_MSM_CAMERA_SENSOR=y
+CONFIG_MSM_CPP=y
+CONFIG_MSM_CCI=y
+CONFIG_MSM_CSI20_HEADER=y
+CONFIG_MSM_CSI22_HEADER=y
+CONFIG_MSM_CSI30_HEADER=y
+CONFIG_MSM_CSI31_HEADER=y
+CONFIG_MSM_CSIPHY=y
+CONFIG_MSM_CSID=y
+CONFIG_MSM_EEPROM=y
+CONFIG_MSM_ISPIF_V2=y
+CONFIG_IMX134=y
+CONFIG_IMX132=y
+CONFIG_OV9724=y
+CONFIG_OV5648=y
+CONFIG_GC0339=y
+CONFIG_OV8825=y
+CONFIG_OV8865=y
+CONFIG_s5k4e1=y
+CONFIG_OV12830=y
+CONFIG_MSM_V4L2_VIDEO_OVERLAY_DEVICE=y
+CONFIG_MSMB_JPEG=y
+CONFIG_MSM_FD=y
+CONFIG_MSM_JPEGDMA=y
+CONFIG_MSM_VIDC_3X_V4L2=y
+CONFIG_MSM_VIDC_3X_GOVERNORS=y
+CONFIG_RADIO_IRIS=y
+CONFIG_RADIO_IRIS_TRANSPORT=y
+CONFIG_QCOM_KGSL=y
+CONFIG_FB=y
+CONFIG_FB_VIRTUAL=y
+CONFIG_FB_MSM=y
+CONFIG_FB_MSM_MDSS=y
+CONFIG_FB_MSM_MDSS_WRITEBACK=y
+CONFIG_FB_MSM_MDSS_DSI_CTRL_STATUS=y
+CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
+CONFIG_BACKLIGHT_LCD_SUPPORT=y
+CONFIG_BACKLIGHT_CLASS_DEVICE=y
+CONFIG_SOUND=y
+CONFIG_SND=y
+CONFIG_SND_DYNAMIC_MINORS=y
+CONFIG_SND_USB_AUDIO=y
+CONFIG_SND_SOC=y
+CONFIG_UHID=y
+CONFIG_HID_APPLE=y
+CONFIG_HID_ELECOM=y
+CONFIG_HID_MAGICMOUSE=y
+CONFIG_HID_MICROSOFT=y
+CONFIG_HID_MULTITOUCH=y
+CONFIG_USB_HIDDEV=y
+CONFIG_USB=y
+CONFIG_USB_ANNOUNCE_NEW_DEVICES=y
+CONFIG_USB_MON=y
+CONFIG_USB_XHCI_HCD=y
+CONFIG_USB_EHCI_HCD=y
+CONFIG_USB_EHCI_MSM=y
+CONFIG_USB_EHCI_HCD_PLATFORM=y
+CONFIG_USB_OHCI_HCD=y
+CONFIG_USB_OHCI_HCD_PLATFORM=y
+CONFIG_USB_ACM=y
+CONFIG_USB_STORAGE=y
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_USBAT=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_ALAUDA=y
+CONFIG_USB_STORAGE_ONETOUCH=y
+CONFIG_USB_STORAGE_KARMA=y
+CONFIG_USB_STORAGE_CYPRESS_ATACB=y
+CONFIG_USB_DWC3=y
+CONFIG_USB_DWC3_MSM=y
+CONFIG_USB_SERIAL=y
+CONFIG_USB_EHSET_TEST_FIXTURE=y
+CONFIG_NOP_USB_XCEIV=y
+CONFIG_DUAL_ROLE_USB_INTF=y
+CONFIG_USB_MSM_SSPHY_QMP=y
+CONFIG_MSM_QUSB_PHY=y
+CONFIG_USB_GADGET=y
+CONFIG_USB_GADGET_DEBUG_FILES=y
+CONFIG_USB_GADGET_DEBUG_FS=y
+CONFIG_USB_GADGET_VBUS_DRAW=500
+CONFIG_USB_CI13XXX_MSM=y
+CONFIG_USB_CONFIGFS=y
+CONFIG_USB_CONFIGFS_SERIAL=y
+CONFIG_USB_CONFIGFS_NCM=y
+CONFIG_USB_CONFIGFS_QCRNDIS=y
+CONFIG_USB_CONFIGFS_RNDIS=y
+CONFIG_USB_CONFIGFS_RMNET_BAM=y
+CONFIG_USB_CONFIGFS_MASS_STORAGE=y
+CONFIG_USB_CONFIGFS_F_FS=y
+CONFIG_USB_CONFIGFS_F_MTP=y
+CONFIG_USB_CONFIGFS_F_PTP=y
+CONFIG_USB_CONFIGFS_F_ACC=y
+CONFIG_USB_CONFIGFS_F_AUDIO_SRC=y
+CONFIG_USB_CONFIGFS_UEVENT=y
+CONFIG_USB_CONFIGFS_F_MIDI=y
+CONFIG_USB_CONFIGFS_F_HID=y
+CONFIG_USB_CONFIGFS_F_DIAG=y
+CONFIG_USB_CONFIGFS_F_CDEV=y
+CONFIG_USB_CONFIGFS_F_CCID=y
+CONFIG_USB_CONFIGFS_F_QDSS=y
+CONFIG_MMC=y
+CONFIG_MMC_PERF_PROFILING=y
+CONFIG_MMC_RING_BUFFER=y
+CONFIG_MMC_PARANOID_SD_INIT=y
+CONFIG_MMC_CLKGATE=y
+CONFIG_MMC_BLOCK_MINORS=32
+CONFIG_MMC_BLOCK_DEFERRED_RESUME=y
+CONFIG_MMC_TEST=y
+CONFIG_MMC_SDHCI=y
+CONFIG_MMC_SDHCI_PLTFM=y
+CONFIG_MMC_SDHCI_MSM=y
+CONFIG_MMC_SDHCI_MSM_ICE=y
+CONFIG_MMC_CQ_HCI=y
+CONFIG_LEDS_QTI_TRI_LED=y
+CONFIG_LEDS_QPNP=y
+CONFIG_LEDS_QPNP_FLASH=y
+CONFIG_LEDS_QPNP_FLASH_V2=y
+CONFIG_LEDS_QPNP_WLED=y
+CONFIG_LEDS_QPNP_HAPTICS=y
+CONFIG_LEDS_QPNP_VIBRATOR_LDO=y
+CONFIG_LEDS_TRIGGERS=y
+CONFIG_LEDS_TRIGGER_TIMER=y
+CONFIG_EDAC=y
+CONFIG_EDAC_MM_EDAC=y
+CONFIG_RTC_CLASS=y
+CONFIG_RTC_DRV_QPNP=y
+CONFIG_DMADEVICES=y
+CONFIG_QCOM_SPS_DMA=y
+CONFIG_UIO=y
+CONFIG_UIO_MSM_SHAREDMEM=y
+CONFIG_STAGING=y
+CONFIG_ASHMEM=y
+CONFIG_ANDROID_LOW_MEMORY_KILLER=y
+CONFIG_ION=y
+CONFIG_ION_MSM=y
+CONFIG_IPA=y
+CONFIG_RMNET_IPA=y
+CONFIG_RNDIS_IPA=y
+CONFIG_SPS=y
+CONFIG_SPS_SUPPORT_NDP_BAM=y
+CONFIG_QPNP_COINCELL=y
+CONFIG_QPNP_REVID=y
+CONFIG_USB_BAM=y
+CONFIG_MSM_EXT_DISPLAY=y
+CONFIG_MSM_RMNET_BAM=y
+CONFIG_MSM_MDSS_PLL=y
+CONFIG_REMOTE_SPINLOCK_MSM=y
+CONFIG_MAILBOX=y
+CONFIG_ARM_SMMU=y
+CONFIG_QCOM_LAZY_MAPPING=y
+CONFIG_IOMMU_DEBUG=y
+CONFIG_IOMMU_DEBUG_TRACKING=y
+CONFIG_IOMMU_TESTS=y
+CONFIG_QCOM_RUN_QUEUE_STATS=y
+CONFIG_MSM_SPM=y
+CONFIG_MSM_L2_SPM=y
+CONFIG_MSM_BOOT_STATS=y
+CONFIG_MSM_CORE_HANG_DETECT=y
+CONFIG_MSM_GLADIATOR_HANG_DETECT=y
+CONFIG_QCOM_WATCHDOG_V2=y
+CONFIG_QCOM_MEMORY_DUMP_V2=y
+CONFIG_MSM_RPM_SMD=y
+CONFIG_QCOM_BUS_SCALING=y
+CONFIG_QCOM_SECURE_BUFFER=y
+CONFIG_QCOM_EARLY_RANDOM=y
+CONFIG_MSM_SMEM=y
+CONFIG_MSM_SMD=y
+CONFIG_MSM_SMD_DEBUG=y
+CONFIG_MSM_TZ_SMMU=y
+CONFIG_TRACER_PKT=y
+CONFIG_MSM_SMP2P=y
+CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
+CONFIG_MSM_QMI_INTERFACE=y
+CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_PIL=y
+CONFIG_MSM_PIL_SSR_GENERIC=y
+CONFIG_MSM_PIL_MSS_QDSP6V5=y
+CONFIG_ICNSS=y
+CONFIG_MSM_PERFORMANCE=y
+CONFIG_MSM_EVENT_TIMER=y
+CONFIG_MSM_AVTIMER=y
+CONFIG_MSM_PM=y
+CONFIG_QTI_RPM_STATS_LOG=y
+CONFIG_QCOM_FORCE_WDOG_BITE_ON_PANIC=y
+CONFIG_MEM_SHARE_QMI_SERVICE=y
+CONFIG_MSM_BAM_DMUX=y
+CONFIG_WCNSS_CORE=y
+CONFIG_WCNSS_CORE_PRONTO=y
+CONFIG_WCNSS_REGISTER_DUMP_ON_BITE=y
+CONFIG_QCOM_BIMC_BWMON=y
+CONFIG_DEVFREQ_GOV_QCOM_BW_HWMON=y
+CONFIG_DEVFREQ_SIMPLE_DEV=y
+CONFIG_QCOM_DEVFREQ_DEVBW=y
+CONFIG_SPDM_SCM=y
+CONFIG_DEVFREQ_SPDM=y
+CONFIG_PWM=y
+CONFIG_PWM_QPNP=y
+CONFIG_PWM_QTI_LPG=y
+CONFIG_QTI_MPM=y
+CONFIG_ANDROID=y
+CONFIG_ANDROID_BINDER_IPC=y
+CONFIG_SENSORS_SSC=y
+CONFIG_MSM_TZ_LOG=y
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT3_FS=y
+CONFIG_EXT4_FS_SECURITY=y
+CONFIG_QUOTA=y
+CONFIG_QUOTA_NETLINK_INTERFACE=y
+CONFIG_QFMT_V2=y
+CONFIG_FUSE_FS=y
+CONFIG_MSDOS_FS=y
+CONFIG_VFAT_FS=y
+CONFIG_TMPFS=y
+CONFIG_ECRYPT_FS=y
+CONFIG_ECRYPT_FS_MESSAGING=y
+# CONFIG_NETWORK_FILESYSTEMS is not set
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_ISO8859_1=y
+CONFIG_PRINTK_TIME=y
+CONFIG_DYNAMIC_DEBUG=y
+CONFIG_DEBUG_INFO=y
+CONFIG_FRAME_WARN=2048
+CONFIG_PAGE_OWNER=y
+CONFIG_PAGE_OWNER_ENABLE_DEFAULT=y
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_PAGEALLOC=y
+CONFIG_SLUB_DEBUG_PANIC_ON=y
+CONFIG_DEBUG_PAGEALLOC_ENABLE_DEFAULT=y
+CONFIG_DEBUG_OBJECTS=y
+CONFIG_DEBUG_OBJECTS_FREE=y
+CONFIG_DEBUG_OBJECTS_TIMERS=y
+CONFIG_DEBUG_OBJECTS_WORK=y
+CONFIG_DEBUG_OBJECTS_RCU_HEAD=y
+CONFIG_DEBUG_OBJECTS_PERCPU_COUNTER=y
+CONFIG_SLUB_DEBUG_ON=y
+CONFIG_DEBUG_KMEMLEAK=y
+CONFIG_DEBUG_KMEMLEAK_EARLY_LOG_SIZE=4000
+CONFIG_DEBUG_KMEMLEAK_DEFAULT_OFF=y
+CONFIG_DEBUG_STACK_USAGE=y
+CONFIG_DEBUG_MEMORY_INIT=y
+CONFIG_LOCKUP_DETECTOR=y
+CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC=y
+CONFIG_WQ_WATCHDOG=y
+CONFIG_PANIC_TIMEOUT=5
+CONFIG_PANIC_ON_SCHED_BUG=y
+CONFIG_PANIC_ON_RT_THROTTLING=y
+CONFIG_SCHEDSTATS=y
+CONFIG_SCHED_STACK_END_CHECK=y
+# CONFIG_DEBUG_PREEMPT is not set
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_MUTEXES=y
+CONFIG_DEBUG_ATOMIC_SLEEP=y
+CONFIG_DEBUG_LIST=y
+CONFIG_FAULT_INJECTION=y
+CONFIG_FAIL_PAGE_ALLOC=y
+CONFIG_FAULT_INJECTION_DEBUG_FS=y
+CONFIG_FAULT_INJECTION_STACKTRACE_FILTER=y
+CONFIG_IPC_LOGGING=y
+CONFIG_QCOM_RTB=y
+CONFIG_QCOM_RTB_SEPARATE_CPUS=y
+CONFIG_FUNCTION_TRACER=y
+CONFIG_IRQSOFF_TRACER=y
+CONFIG_PREEMPT_TRACER=y
+CONFIG_BLK_DEV_IO_TRACE=y
+CONFIG_CPU_FREQ_SWITCH_PROFILER=y
+CONFIG_LKDTM=y
+CONFIG_MEMTEST=y
+CONFIG_PANIC_ON_DATA_CORRUPTION=y
+CONFIG_DEBUG_USER=y
+CONFIG_PID_IN_CONTEXTIDR=y
+CONFIG_DEBUG_SET_MODULE_RONX=y
+CONFIG_CORESIGHT=y
+CONFIG_CORESIGHT_REMOTE_ETM=y
+CONFIG_CORESIGHT_REMOTE_ETM_DEFAULT_ENABLE=0
+CONFIG_CORESIGHT_STM=y
+CONFIG_CORESIGHT_TPDA=y
+CONFIG_CORESIGHT_TPDM=y
+CONFIG_CORESIGHT_CTI=y
+CONFIG_CORESIGHT_EVENT=y
+CONFIG_CORESIGHT_HWEVENT=y
+CONFIG_SECURITY_PERF_EVENTS_RESTRICT=y
+CONFIG_SECURITY=y
+CONFIG_LSM_MMAP_MIN_ADDR=4096
+CONFIG_HARDENED_USERCOPY=y
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SMACK=y
+CONFIG_CRYPTO_CTR=y
+CONFIG_CRYPTO_XCBC=y
+CONFIG_CRYPTO_MD4=y
+CONFIG_CRYPTO_TWOFISH=y
+CONFIG_CRYPTO_ANSI_CPRNG=y
+CONFIG_CRYPTO_DEV_QCOM_MSM_QCE=y
+CONFIG_CRYPTO_DEV_QCRYPTO=y
+CONFIG_CRYPTO_DEV_QCEDEV=y
+CONFIG_CRYPTO_DEV_OTA_CRYPTO=y
+CONFIG_CRYPTO_DEV_QCOM_ICE=y
+CONFIG_ARM_CRYPTO=y
+CONFIG_CRYPTO_SHA1_ARM_NEON=y
+CONFIG_CRYPTO_SHA2_ARM_CE=y
+CONFIG_CRYPTO_AES_ARM_BS=y
+CONFIG_CRYPTO_AES_ARM_CE=y
+CONFIG_QMI_ENCDEC=y
diff --git a/arch/arm/configs/msm8953-perf_defconfig b/arch/arm/configs/msm8953-perf_defconfig
index 6ac3955..5779552 100644
--- a/arch/arm/configs/msm8953-perf_defconfig
+++ b/arch/arm/configs/msm8953-perf_defconfig
@@ -6,6 +6,9 @@
CONFIG_HIGH_RES_TIMERS=y
CONFIG_IRQ_TIME_ACCOUNTING=y
CONFIG_SCHED_WALT=y
+CONFIG_TASKSTATS=y
+CONFIG_TASK_XACCT=y
+CONFIG_TASK_IO_ACCOUNTING=y
CONFIG_RCU_EXPERT=y
CONFIG_RCU_FAST_NO_HZ=y
CONFIG_RCU_NOCB_CPU=y
@@ -27,6 +30,8 @@
CONFIG_SCHED_TUNE=y
CONFIG_DEFAULT_USE_ENERGY_AWARE=y
CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
# CONFIG_RD_XZ is not set
# CONFIG_RD_LZO is not set
# CONFIG_RD_LZ4 is not set
@@ -49,9 +54,8 @@
# CONFIG_IOSCHED_DEADLINE is not set
CONFIG_ARCH_QCOM=y
CONFIG_ARCH_MSM8953=y
-CONFIG_ARCH_MSM8937=y
-CONFIG_ARCH_MSM8917=y
CONFIG_ARCH_SDM450=y
+CONFIG_ARCH_SDM632=y
# CONFIG_VDSO is not set
CONFIG_SMP=y
CONFIG_SCHED_MC=y
@@ -63,7 +67,6 @@
CONFIG_CMA=y
CONFIG_CMA_DEBUGFS=y
CONFIG_ZSMALLOC=y
-CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_SECCOMP=y
CONFIG_BUILD_ARM_APPENDED_DTB_IMAGE=y
CONFIG_CPU_FREQ=y
@@ -240,6 +243,7 @@
CONFIG_BLK_DEV_RAM_SIZE=8192
CONFIG_HDCP_QSEECOM=y
CONFIG_QSEECOM=y
+CONFIG_UID_SYS_STATS=y
CONFIG_MEMORY_STATE_TIME=y
CONFIG_SCSI=y
CONFIG_BLK_DEV_SD=y
@@ -284,6 +288,7 @@
# CONFIG_INPUT_MOUSE is not set
CONFIG_INPUT_JOYSTICK=y
CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_FT5X06=y
CONFIG_INPUT_MISC=y
CONFIG_INPUT_HBTP_INPUT=y
CONFIG_INPUT_QPNP_POWER_ON=y
@@ -311,8 +316,6 @@
CONFIG_SPMI=y
CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
CONFIG_PINCTRL_MSM8953=y
-CONFIG_PINCTRL_MSM8937=y
-CONFIG_PINCTRL_MSM8917=y
CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
CONFIG_GPIO_SYSFS=y
CONFIG_GPIO_QPNP_PIN=y
@@ -373,7 +376,7 @@
CONFIG_MSM_CSIPHY=y
CONFIG_MSM_CSID=y
CONFIG_MSM_EEPROM=y
-CONFIG_MSM_ISPIF_V2=y
+CONFIG_MSM_ISPIF=y
CONFIG_IMX134=y
CONFIG_IMX132=y
CONFIG_OV9724=y
@@ -400,9 +403,6 @@
CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
CONFIG_BACKLIGHT_LCD_SUPPORT=y
CONFIG_BACKLIGHT_CLASS_DEVICE=y
-CONFIG_LOGO=y
-# CONFIG_LOGO_LINUX_MONO is not set
-# CONFIG_LOGO_LINUX_VGA16 is not set
CONFIG_SOUND=y
CONFIG_SND=y
CONFIG_SND_DYNAMIC_MINORS=y
@@ -535,6 +535,7 @@
CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
CONFIG_MSM_QMI_INTERFACE=y
CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_SYSMON_COMM=y
CONFIG_MSM_PIL=y
CONFIG_MSM_PIL_SSR_GENERIC=y
CONFIG_MSM_PIL_MSS_QDSP6V5=y
diff --git a/arch/arm/configs/msm8953_defconfig b/arch/arm/configs/msm8953_defconfig
index 104e206..6ac9d99 100644
--- a/arch/arm/configs/msm8953_defconfig
+++ b/arch/arm/configs/msm8953_defconfig
@@ -31,6 +31,8 @@
CONFIG_SCHED_TUNE=y
CONFIG_DEFAULT_USE_ENERGY_AWARE=y
CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
# CONFIG_RD_XZ is not set
# CONFIG_RD_LZO is not set
# CONFIG_RD_LZ4 is not set
@@ -55,9 +57,8 @@
# CONFIG_IOSCHED_DEADLINE is not set
CONFIG_ARCH_QCOM=y
CONFIG_ARCH_MSM8953=y
-CONFIG_ARCH_MSM8937=y
-CONFIG_ARCH_MSM8917=y
CONFIG_ARCH_SDM450=y
+CONFIG_ARCH_SDM632=y
# CONFIG_VDSO is not set
CONFIG_SMP=y
CONFIG_SCHED_MC=y
@@ -69,7 +70,6 @@
CONFIG_CMA=y
CONFIG_CMA_DEBUGFS=y
CONFIG_ZSMALLOC=y
-CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_SECCOMP=y
CONFIG_BUILD_ARM_APPENDED_DTB_IMAGE=y
CONFIG_CPU_FREQ=y
@@ -293,6 +293,7 @@
# CONFIG_INPUT_MOUSE is not set
CONFIG_INPUT_JOYSTICK=y
CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_FT5X06=y
CONFIG_INPUT_MISC=y
CONFIG_INPUT_HBTP_INPUT=y
CONFIG_INPUT_QPNP_POWER_ON=y
@@ -322,8 +323,6 @@
CONFIG_SPMI=y
CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
CONFIG_PINCTRL_MSM8953=y
-CONFIG_PINCTRL_MSM8937=y
-CONFIG_PINCTRL_MSM8917=y
CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
CONFIG_GPIO_SYSFS=y
CONFIG_GPIO_QPNP_PIN=y
@@ -384,7 +383,7 @@
CONFIG_MSM_CSIPHY=y
CONFIG_MSM_CSID=y
CONFIG_MSM_EEPROM=y
-CONFIG_MSM_ISPIF_V2=y
+CONFIG_MSM_ISPIF=y
CONFIG_IMX134=y
CONFIG_IMX132=y
CONFIG_OV9724=y
@@ -412,9 +411,6 @@
CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
CONFIG_BACKLIGHT_LCD_SUPPORT=y
CONFIG_BACKLIGHT_CLASS_DEVICE=y
-CONFIG_LOGO=y
-# CONFIG_LOGO_LINUX_MONO is not set
-# CONFIG_LOGO_LINUX_VGA16 is not set
CONFIG_SOUND=y
CONFIG_SND=y
CONFIG_SND_DYNAMIC_MINORS=y
@@ -555,6 +551,7 @@
CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
CONFIG_MSM_QMI_INTERFACE=y
CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_SYSMON_COMM=y
CONFIG_MSM_PIL=y
CONFIG_MSM_PIL_SSR_GENERIC=y
CONFIG_MSM_PIL_MSS_QDSP6V5=y
diff --git a/arch/arm/configs/sdxpoorwills_defconfig b/arch/arm/configs/sdxpoorwills_defconfig
index fd3d784..7a54d68 100644
--- a/arch/arm/configs/sdxpoorwills_defconfig
+++ b/arch/arm/configs/sdxpoorwills_defconfig
@@ -417,6 +417,8 @@
CONFIG_FAULT_INJECTION_STACKTRACE_FILTER=y
CONFIG_IPC_LOGGING=y
CONFIG_QCOM_RTB=y
+CONFIG_IRQSOFF_TRACER=y
+CONFIG_PREEMPT_TRACER=y
CONFIG_BLK_DEV_IO_TRACE=y
CONFIG_DEBUG_USER=y
CONFIG_CORESIGHT=y
diff --git a/arch/arm/mach-qcom/Kconfig b/arch/arm/mach-qcom/Kconfig
index 65b43ea..1ab1fbb 100644
--- a/arch/arm/mach-qcom/Kconfig
+++ b/arch/arm/mach-qcom/Kconfig
@@ -114,6 +114,30 @@
select HAVE_CLK_PREPARE
select COMMON_CLK_MSM
+config ARCH_SDM439
+ bool "Enable support for SDM439"
+ select CPU_V7
+ select HAVE_ARM_ARCH_TIMER
+ select PINCTRL
+ select QCOM_SCM if SMP
+ select PM_DEVFREQ
+ select CLKDEV_LOOKUP
+ select HAVE_CLK
+ select HAVE_CLK_PREPARE
+ select COMMON_CLK_MSM
+
+config ARCH_SDM429
+ bool "Enable support for SDM429"
+ select CPU_V7
+ select HAVE_ARM_ARCH_TIMER
+ select PINCTRL
+ select QCOM_SCM if SMP
+ select PM_DEVFREQ
+ select CLKDEV_LOOKUP
+ select HAVE_CLK
+ select HAVE_CLK_PREPARE
+ select COMMON_CLK_MSM
+
config ARCH_SDM450
bool "Enable support for SDM450"
select CPU_V7
@@ -126,6 +150,22 @@
select HAVE_CLK_PREPARE
select COMMON_CLK_MSM
+config ARCH_SDM632
+ bool "Enable Support for Qualcomm Technologies Inc. SDM632"
+ select CPU_V7
+ select PINCTRL
+ select QCOM_SCM if SMP
+ select CLKDEV_LOOKUP
+ select HAVE_CLK
+ select HAVE_CLK_PREPARE
+ select SOC_BUS
+ select PM_OPP
+ select MFD_CORE
+ select SND_SOC_COMPRESS
+ select SND_HWDEP
+ select CPU_FREQ_QCOM
+ select COMMON_CLK_MSM
+
config ARCH_MDM9650
bool "MDM9650"
select ARM_GIC
diff --git a/arch/arm/mach-qcom/Makefile b/arch/arm/mach-qcom/Makefile
index c167075..5b93fa3 100644
--- a/arch/arm/mach-qcom/Makefile
+++ b/arch/arm/mach-qcom/Makefile
@@ -5,6 +5,9 @@
obj-$(CONFIG_ARCH_MSM8937) += board-msm8937.o
obj-$(CONFIG_ARCH_MSM8909) += board-msm8909.o
obj-$(CONFIG_ARCH_MSM8917) += board-msm8917.o
+obj-$(CONFIG_ARCH_SDM429) += board-sdm429.o
+obj-$(CONFIG_ARCH_SDM439) += board-sdm439.o
obj-$(CONFIG_ARCH_SDM450) += board-sdm450.o
obj-$(CONFIG_ARCH_MDM9650) += board-9650.o
obj-$(CONFIG_ARCH_MDM9607) += board-9607.o
+obj-$(CONFIG_ARCH_SDM632) += board-sdm632.o
diff --git a/arch/arm/mach-qcom/board-sdm429.c b/arch/arm/mach-qcom/board-sdm429.c
new file mode 100644
index 0000000..c648eaf
--- /dev/null
+++ b/arch/arm/mach-qcom/board-sdm429.c
@@ -0,0 +1,32 @@
+/* Copyright (c) 2018, 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 <linux/kernel.h>
+#include "board-dt.h"
+#include <asm/mach/map.h>
+#include <asm/mach/arch.h>
+
+static const char *sdm429_dt_match[] __initconst = {
+ "qcom,sdm429",
+ NULL
+};
+
+static void __init sdm429_init(void)
+{
+ board_dt_populate(NULL);
+}
+
+DT_MACHINE_START(SDM429_DT,
+ "Qualcomm Technologies, Inc. SDM429 (Flattened Device Tree)")
+ .init_machine = sdm429_init,
+ .dt_compat = sdm429_dt_match,
+MACHINE_END
diff --git a/arch/arm/mach-qcom/board-sdm439.c b/arch/arm/mach-qcom/board-sdm439.c
new file mode 100644
index 0000000..312f3a5
--- /dev/null
+++ b/arch/arm/mach-qcom/board-sdm439.c
@@ -0,0 +1,32 @@
+/* Copyright (c) 2018, 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 <linux/kernel.h>
+#include "board-dt.h"
+#include <asm/mach/map.h>
+#include <asm/mach/arch.h>
+
+static const char *sdm439_dt_match[] __initconst = {
+ "qcom,sdm439",
+ NULL
+};
+
+static void __init sdm439_init(void)
+{
+ board_dt_populate(NULL);
+}
+
+DT_MACHINE_START(SDM439_DT,
+ "Qualcomm Technologies, Inc. SDM439 (Flattened Device Tree)")
+ .init_machine = sdm439_init,
+ .dt_compat = sdm439_dt_match,
+MACHINE_END
diff --git a/arch/arm/mach-qcom/board-sdm632.c b/arch/arm/mach-qcom/board-sdm632.c
new file mode 100644
index 0000000..c6a55f2
--- /dev/null
+++ b/arch/arm/mach-qcom/board-sdm632.c
@@ -0,0 +1,32 @@
+/* Copyright (c) 2018, 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 <linux/kernel.h>
+#include "board-dt.h"
+#include <asm/mach/map.h>
+#include <asm/mach/arch.h>
+
+static const char *sdm632_dt_match[] __initconst = {
+ "qcom,sdm632",
+ NULL
+};
+
+static void __init sdm632_init(void)
+{
+ board_dt_populate(NULL);
+}
+
+DT_MACHINE_START(SDM632_DT,
+ "Qualcomm Technologies, Inc. SDM632 (Flattened Device Tree)")
+ .init_machine = sdm632_init,
+ .dt_compat = sdm632_dt_match,
+MACHINE_END
diff --git a/arch/arm64/boot/dts/qcom/Makefile b/arch/arm64/boot/dts/qcom/Makefile
index 315b3fd..7457bbb 100644
--- a/arch/arm64/boot/dts/qcom/Makefile
+++ b/arch/arm64/boot/dts/qcom/Makefile
@@ -139,6 +139,8 @@
sda670-pm660a-mtp-overlay.dtbo \
sdm670-tasha-codec-cdp-overlay.dtbo \
sdm670-pm660a-tasha-codec-cdp-overlay.dtbo \
+ sdm670-aqt1000-cdp-overlay.dtbo \
+ sdm670-pm660a-aqt1000-cdp-overlay.dtbo \
qcs605-cdp-overlay.dtbo \
qcs605-mtp-overlay.dtbo \
qcs605-360camera-overlay.dtbo \
@@ -163,7 +165,9 @@
sdm710-usbc-external-codec-pm660a-cdp-overlay.dtbo \
sdm710-usbc-external-codec-pm660a-mtp-overlay.dtbo \
sdm710-tasha-codec-cdp-overlay.dtbo \
- sdm710-pm660a-tasha-codec-cdp-overlay.dtbo
+ sdm710-pm660a-tasha-codec-cdp-overlay.dtbo \
+ sdm710-aqt1000-cdp-overlay.dtbo \
+ sdm710-pm660a-aqt1000-cdp-overlay.dtbo
sdm670-cdp-overlay.dtbo-base := sdm670.dtb
sdm670-mtp-overlay.dtbo-base := sdm670.dtb
@@ -186,6 +190,8 @@
sdm670-usbc-external-codec-pm660a-mtp-overlay.dtbo-base := sdm670.dtb
sdm670-tasha-codec-cdp-overlay.dtbo-base := sdm670.dtb
sdm670-pm660a-tasha-codec-cdp-overlay.dtbo-base := sdm670.dtb
+sdm670-aqt1000-cdp-overlay.dtbo-base := sdm670.dtb
+sdm670-pm660a-aqt1000-cdp-overlay.dtbo-base := sdm670.dtb
sda670-cdp-overlay.dtbo-base := sda670.dtb
sda670-mtp-overlay.dtbo-base := sda670.dtb
sda670-pm660a-cdp-overlay.dtbo-base := sda670.dtb
@@ -215,6 +221,8 @@
sdm710-usbc-external-codec-pm660a-mtp-overlay.dtbo-base := sdm710.dtb
sdm710-tasha-codec-cdp-overlay.dtbo-base := sdm710.dtb
sdm710-pm660a-tasha-codec-cdp-overlay.dtbo-base := sdm710.dtb
+sdm710-aqt1000-cdp-overlay.dtbo-base := sdm710.dtb
+sdm710-pm660a-aqt1000-cdp-overlay.dtbo-base := sdm710.dtb
else
dtb-$(CONFIG_ARCH_SDM670) += sdm670-rumi.dtb \
@@ -292,7 +300,19 @@
dtbo-$(CONFIG_ARCH_SDM632) += sdm632-rumi-overlay.dtbo \
sdm450-cdp-s2-overlay.dtbo \
sdm450-mtp-s3-overlay.dtbo \
- sdm450-qrd-sku4-overlay.dtbo
+ sdm632-ext-codec-cdp-s3-overlay.dtbo \
+ sdm632-ext-codec-mtp-s4-overlay.dtbo \
+ sdm632-rcm-overlay.dtbo \
+ sdm450-qrd-sku4-overlay.dtbo \
+ sdm632-qrd-overlay.dtbo
+
+dtbo-$(CONFIG_ARCH_SDM439) += sdm439-mtp-overlay.dtbo \
+ sdm439-cdp-overlay.dtbo \
+ sdm439-qrd-overlay.dtbo
+
+dtbo-$(CONFIG_ARCH_SDM429) += sdm429-mtp-overlay.dtbo \
+ sdm429-cdp-overlay.dtbo \
+ sdm429-qrd-overlay.dtbo
msm8953-mtp-overlay.dtbo-base := sdm450.dtb \
msm8953.dtb \
@@ -325,13 +345,36 @@
msm8953-cdp-1200p-overlay.dtbo-base := msm8953.dtb
sdm450-cdp-s2-overlay.dtbo-base := sdm450-pmi632.dtb \
sdm632.dtb \
+ sdm632-pm8004.dtb \
msm8953-pmi632.dtb
sdm450-mtp-s3-overlay.dtbo-base := sdm450-pmi632.dtb \
- sdm632.dtb
+ sdm632.dtb \
+ sdm632-pm8004.dtb
sdm450-qrd-sku4-overlay.dtbo-base := sdm450-pmi632.dtb \
- sdm632.dtb
+ sdm632.dtb \
+ sdm632-pm8004.dtb
sdm632-rumi-overlay.dtbo-base := sdm632.dtb
+sdm632-ext-codec-cdp-s3-overlay.dtbo-base := sdm632.dtb \
+ sdm632-pm8004.dtb
+sdm632-ext-codec-mtp-s4-overlay.dtbo-base := sdm632.dtb \
+ sdm632-pm8004.dtb
+sdm632-rcm-overlay.dtbo-base := sdm632.dtb \
+ sdm632-pm8004.dtb
+sdm632-qrd-overlay.dtbo-base := sdm632.dtb \
+ sdm632-pm8004.dtb
+sdm439-mtp-overlay.dtbo-base := sdm439.dtb \
+ msm8937-interposer-sdm439.dtb
+sdm439-cdp-overlay.dtbo-base := sdm439.dtb \
+ msm8937-interposer-sdm439.dtb
+sdm439-qrd-overlay.dtbo-base := sdm439.dtb \
+ msm8937-interposer-sdm439.dtb
+sdm429-mtp-overlay.dtbo-base := sdm429.dtb \
+ msm8937-interposer-sdm429.dtb
+sdm429-cdp-overlay.dtbo-base := sdm429.dtb \
+ msm8937-interposer-sdm429.dtb
+sdm429-qrd-overlay.dtbo-base := sdm429.dtb \
+ msm8937-interposer-sdm429.dtb
else
dtb-$(CONFIG_ARCH_MSM8953) += msm8953-cdp.dtb \
msm8953-mtp.dtb \
@@ -362,9 +405,14 @@
dtb-$(CONFIG_ARCH_MSM8937) += msm8937-pmi8950-mtp.dtb \
msm8937-interposer-sdm439-cdp.dtb \
msm8937-interposer-sdm439-mtp.dtb \
- msm8937-interposer-sdm439-qrd.dtb
+ msm8937-interposer-sdm439-qrd.dtb \
+ msm8937-interposer-sdm429-cdp.dtb \
+ msm8937-interposer-sdm429-mtp.dtb
-dtb-$(CONFIG_ARCH_MSM8917) += msm8917-pmi8950-mtp.dtb
+dtb-$(CONFIG_ARCH_MSM8917) += msm8917-pmi8950-mtp.dtb \
+ msm8917-pmi8937-qrd-sku5.dtb \
+ msm8917-pmi8940-mtp.dtb \
+ msm8917-pmi8937-mtp.dtb
dtb-$(CONFIG_ARCH_MSM8909) += msm8909w-bg-wtp-v2.dtb \
apq8009w-bg-wtp-v2.dtb \
@@ -383,17 +431,32 @@
sdm450-pmi632-mtp-s3.dtb
dtb-$(CONFIG_ARCH_SDM632) += sdm632-rumi.dtb \
- sdm632-cdp-s2.dtb \
- sdm632-mtp-s3.dtb \
- sdm632-qrd-sku4.dtb
+ sdm632-cdp-s2.dtb \
+ sdm632-ext-codec-cdp-s3.dtb \
+ sdm632-mtp-s3.dtb \
+ sdm632-ext-codec-mtp-s4.dtb \
+ sdm632-rcm.dtb \
+ sdm632-qrd-sku4.dtb \
+ sdm632-qrd.dtb \
+ sdm632-pm8004-cdp-s2.dtb \
+ sdm632-pm8004-ext-codec-cdp-s3.dtb \
+ sdm632-pm8004-mtp-s3.dtb \
+ sdm632-pm8004-ext-codec-mtp-s4.dtb \
+ sdm632-pm8004-rcm.dtb \
+ sdm632-pm8004-qrd-sku4.dtb \
+ sdm632-pm8004-qrd.dtb
dtb-$(CONFIG_ARCH_SDM439) += sdm439-mtp.dtb \
sdm439-cdp.dtb \
- sdm439-qrd.dtb
+ sdm439-qrd.dtb \
+ sda439-mtp.dtb \
+ sda439-cdp.dtb
dtb-$(CONFIG_ARCH_SDM429) += sdm429-mtp.dtb \
sdm429-cdp.dtb \
- sdm429-qrd.dtb
+ sdm429-qrd.dtb \
+ sda429-mtp.dtb \
+ sda429-cdp.dtb
endif
diff --git a/arch/arm64/boot/dts/qcom/apq8009w-bg-memory.dtsi b/arch/arm64/boot/dts/qcom/apq8009w-bg-memory.dtsi
index d41a792..d83ae5c 100644
--- a/arch/arm64/boot/dts/qcom/apq8009w-bg-memory.dtsi
+++ b/arch/arm64/boot/dts/qcom/apq8009w-bg-memory.dtsi
@@ -12,7 +12,7 @@
*/
&external_image_mem {
- reg = <0x0 0x87b00000 0x0 0x0500000>;
+ reg = <0x0 0x87a00000 0x0 0x0600000>;
};
&modem_adsp_mem {
diff --git a/arch/arm64/boot/dts/qcom/apq8053-lite-dragon-v2.0.dtsi b/arch/arm64/boot/dts/qcom/apq8053-lite-dragon-v2.0.dtsi
index 0c70cf1..947af4d 100644
--- a/arch/arm64/boot/dts/qcom/apq8053-lite-dragon-v2.0.dtsi
+++ b/arch/arm64/boot/dts/qcom/apq8053-lite-dragon-v2.0.dtsi
@@ -12,6 +12,7 @@
*/
#include "apq8053-lite-dragon.dtsi"
+#include "msm8953-mdss-panels.dtsi"
&i2c_3 {
status = "okay";
@@ -34,6 +35,34 @@
};
};
+&mdss_mdp {
+ qcom,mdss-pref-prim-intf = "dsi";
+};
+
+&mdss_dsi {
+ hw-config = "single_dsi";
+};
+
+&mdss_dsi0 {
+ qcom,dsi-pref-prim-pan = <&dsi_boyi_hx83100a_800p_video>;
+ pinctrl-names = "mdss_default", "mdss_sleep";
+ pinctrl-0 = <&mdss_dsi_active &mdss_te_active &mdss_dsi_gpio>;
+ pinctrl-1 = <&mdss_dsi_suspend &mdss_te_suspend &mdss_dsi_gpio>;
+
+ vdd-supply = <&pm8953_l10>;
+ vddio-supply = <&pm8953_l6>;
+ lab-supply = <&lab_regulator>;
+ ibb-supply = <&ibb_regulator>;
+
+ qcom,platform-te-gpio = <&tlmm 24 0>;
+ qcom,platform-reset-gpio = <&tlmm 61 0>;
+ qcom,platform-bklight-en-gpio = <&tlmm 100 0>;
+};
+
+&mdss_dsi1 {
+ status = "disabled";
+};
+
&labibb {
status = "okay";
qpnp,qpnp-labibb-mode = "lcd";
diff --git a/arch/arm64/boot/dts/qcom/apq8053-lite-dragon.dtsi b/arch/arm64/boot/dts/qcom/apq8053-lite-dragon.dtsi
index f2d4ef3..c203e17 100644
--- a/arch/arm64/boot/dts/qcom/apq8053-lite-dragon.dtsi
+++ b/arch/arm64/boot/dts/qcom/apq8053-lite-dragon.dtsi
@@ -88,6 +88,21 @@
};
};
+&firmware {
+ android {
+ vbmeta {
+ compatible = "android,vbmeta";
+ parts = "vbmeta,boot,system,vendor,bluetooth,modem";
+ };
+ fstab {
+ /delete-node/ system;
+ vendor {
+ fsmgr_flags = "wait,slotselect,avb";
+ };
+ };
+ };
+};
+
&rpm_bus {
rpm-regulator-ldoa4 {
compatible = "qcom,rpm-smd-regulator-resource";
diff --git a/arch/arm64/boot/dts/qcom/batterydata-qrd-sku2-4v35-2590mah.dtsi b/arch/arm64/boot/dts/qcom/batterydata-qrd-sku2-4v35-2590mah.dtsi
new file mode 100644
index 0000000..1bde941
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/batterydata-qrd-sku2-4v35-2590mah.dtsi
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2015, 2018, 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.
+ */
+
+qcom,qrd_msm8937_sku2_2590mah {
+ /* #QRD8937_SKU2_2590mAh_averaged_MasterSlave_Nov25th2015*/
+ qcom,max-voltage-uv = <4350000>;
+ qcom,nom-batt-capacity-mah = <2590>;
+ qcom,batt-id-kohm = <10>;
+ qcom,battery-beta = <3380>;
+ qcom,battery-type = "qrd_msm8937_sku2_2590mah";
+ qcom,fastchg-current-ma = <3000>;
+ qcom,fg-cc-cv-threshold-mv = <4340>;
+ qcom,chg-rslow-comp-c1 = <3504694>;
+ qcom,chg-rslow-comp-c2 = <7724034>;
+ qcom,chg-rs-to-rslow = <967819>;
+ qcom,chg-rslow-comp-thr = <0xC6>;
+ qcom,checksum = <0x606D>;
+ qcom,gui-version = "PMI8937GUI - 2.0.0.15";
+ qcom,fg-profile-data = [
+ E3 83 D6 7C
+ DC 80 C6 76
+ 47 83 C1 62
+ DF 7A 98 86
+ 18 82 20 99
+ 16 B7 A5 C2
+ 5D 0F E6 83
+ 4C 7C 46 80
+ 6E 75 54 83
+ 7B 59 91 82
+ E8 8E 6C 82
+ E8 93 80 B5
+ 2E C1 52 13
+ 45 0A F2 5B
+ CE 6E 71 FD
+ E6 3C 4C 3F
+ C6 3A 00 00
+ A1 4C 45 3C
+ 36 43 00 00
+ 00 00 00 00
+ 00 00 00 00
+ 96 70 30 70
+ 29 50 A4 83
+ 97 75 55 69
+ BC 68 49 82
+ D2 74 C4 63
+ D7 68 E4 B0
+ 1E E4 63 F8
+ 64 A0 71 0C
+ 28 00 FF 36
+ F0 11 30 03
+ 00 00 00 0C
+ ];
+};
diff --git a/arch/arm64/boot/dts/qcom/dsi-panel-hx83100a-800p-video.dtsi b/arch/arm64/boot/dts/qcom/dsi-panel-hx83100a-800p-video.dtsi
new file mode 100644
index 0000000..03c3659
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/dsi-panel-hx83100a-800p-video.dtsi
@@ -0,0 +1,84 @@
+/* Copyright (c) 2018, 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_boyi_hx83100a_800p_video: qcom,mdss_dsi_boyi_hx83100a_800p_video {
+ qcom,mdss-dsi-panel-name = "hx83100a 800p video mode dsi panel";
+ qcom,mdss-dsi-panel-controller = <&mdss_dsi0>;
+ qcom,mdss-dsi-panel-type = "dsi_video_mode";
+ qcom,mdss-dsi-panel-destination = "display_2";
+ qcom,mdss-dsi-panel-framerate = <60>;
+ qcom,mdss-dsi-virtual-channel-id = <0>;
+ qcom,mdss-dsi-stream = <0>;
+ qcom,mdss-dsi-panel-width = <800>;
+ qcom,mdss-dsi-panel-height = <1280>;
+ qcom,mdss-dsi-h-front-porch = <40>;
+ qcom,mdss-dsi-h-back-porch = <40>;
+ qcom,mdss-dsi-h-pulse-width = <40>;
+ qcom,mdss-dsi-h-sync-skew = <0>;
+ qcom,mdss-dsi-v-back-porch = <8>;
+ qcom,mdss-dsi-v-front-porch = <412>;
+ qcom,mdss-dsi-v-pulse-width = <4>;
+ 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 = [
+ /*exit sleep mode and delay 120ms*/
+ 39 01 00 00 78 00 02 11 00
+ /*set display on and delay 20ms*/
+ 39 01 00 00 14 00 02 29 00
+ /*enable extended command set*/
+ 39 01 00 00 00 00 04 b9 83 10 0a
+ /*32KHZ PWM*/
+ 39 01 00 00 00 00 08 c9 1f 00 08 1e 81 1e 00
+ /*backlight enable*/
+ 39 01 00 00 00 00 02 53 24
+ /*still picture and delay 5ms*/
+ 39 01 00 00 05 00 02 55 02
+ /*about 80% duty ratio*/
+ 39 01 00 00 00 00 0a ca 40 3c 38 34 33 32 30 2c 28
+ ];
+ qcom,mdss-dsi-off-command = [05 01 00 00 96 00 02 28 00
+ 05 01 00 00 00 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 = <1>;
+ qcom,mdss-dsi-traffic-mode = "burst_mode";
+ qcom,mdss-dsi-lane-map = "lane_map_0123";
+ 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 = [9b 22 18 00 4a 4e 1c 26
+ 1d 03 04 00];
+ qcom,mdss-dsi-t-clk-post = <0x04>;
+ qcom,mdss-dsi-t-clk-pre = <0x1f>;
+ qcom,mdss-dsi-bl-min-level = <2>;
+ qcom,mdss-dsi-bl-max-level = <4095>;
+ qcom,panel-supply-entries = <&dsi_panel_pwr_supply>;
+ qcom,mdss-dsi-dma-trigger = "trigger_sw";
+ qcom,mdss-dsi-mdp-trigger = "none";
+ qcom,mdss-dsi-bl-pmic-control-type = "bl_ctrl_wled";
+ qcom,mdss-pan-physical-width-dimension = <107>;
+ qcom,mdss-pan-physical-height-dimension = <172>;
+ qcom,mdss-dsi-reset-sequence = <1 10>, <0 5>, <1 50>;
+ qcom,mdss-dsi-lp11-init;
+ qcom,mdss-dsi-post-init-delay = <1>;
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/dsi-panel-hx8394f-720p-video.dtsi b/arch/arm64/boot/dts/qcom/dsi-panel-hx8394f-720p-video.dtsi
new file mode 100644
index 0000000..749ffe6
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/dsi-panel-hx8394f-720p-video.dtsi
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2018, 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.
+ */
+
+/*---------------------------------------------------------------------------
+ * This file is autogenerated file using gcdb parser. Please do not edit it.
+ * Update input XML file to add a new entry or update variable in this file
+ * VERSION = "1.0"
+ *---------------------------------------------------------------------------
+ */
+&mdss_mdp {
+ dsi_hx8394f_720p_video: qcom,mdss_dsi_hx8394f_720p_video {
+ qcom,mdss-dsi-panel-name = "hx8394f 720p video mode dsi panel";
+ qcom,mdss-dsi-panel-controller = <&mdss_dsi0>;
+ qcom,mdss-dsi-panel-type = "dsi_video_mode";
+ qcom,mdss-dsi-panel-destination = "display_1";
+ qcom,mdss-dsi-panel-framerate = <60>;
+ qcom,mdss-dsi-virtual-channel-id = <0>;
+ qcom,mdss-dsi-stream = <0>;
+ qcom,mdss-dsi-panel-width = <720>;
+ qcom,mdss-dsi-panel-height = <1280>;
+ qcom,mdss-dsi-h-front-porch = <16>;
+ qcom,mdss-dsi-h-back-porch = <16>;
+ qcom,mdss-dsi-h-pulse-width = <10>;
+ qcom,mdss-dsi-h-sync-skew = <0>;
+ qcom,mdss-dsi-v-back-porch = <12>;
+ qcom,mdss-dsi-v-front-porch = <15>;
+ qcom,mdss-dsi-v-pulse-width = <4>;
+ 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-underflow-color = <0xff>;
+ qcom,mdss-dsi-border-color = <0>;
+ qcom,mdss-dsi-on-command = [39 01 00 00 00 00 04 B9 FF 83 94
+ 39 01 00 00 00 00 07
+ BA 63 03 68 6B B2 C0
+ 39 01 00 00 00 00 0B
+ B1 50 12 72 09 33 54 B1 31 6B 2F
+ 39 01 00 00 00 00 07
+ B2 00 80 64 0E 0D 2F
+ 39 01 00 00 00 00 16
+ B4 73 74 73 74 73 74 01 0C 86 75
+ 00 3F 73 74 73 74 73 74 01 0C 86
+ 39 01 00 00 00 00 22
+ D3 00 00 07 07 40 07 10 00 08 10
+ 08 00 08 54 15 0E 05 0E 02 15 06
+ 05 06 47 44 0A 0A 4B 10 07 07 0E
+ 40
+ 39 01 00 00 00 00 2D
+ D5 1A 1A 1B 1B 00 01 02 03 04 05
+ 06 07 08 09 0A 0B 24 25 18 18 26
+ 27 18 18 18 18 18 18 18 18 18 18
+ 18 18 18 18 18 18 20 21 18 18 18
+ 18
+ 39 01 00 00 00 00 2D
+ D6 1A 1A 1B 1B 0B 0A 09 08 07 06
+ 05 04 03 02 01 00 21 20 18 18 27
+ 26 18 18 18 18 18 18 18 18 18 18
+ 18 18 18 18 18 18 25 24 18 18 18
+ 18
+ 39 01 00 00 00 00 3B
+ E0 00 0C 19 20 23 26 29 28 51 61
+ 70 6F 76 86 89 8D 99 9A 95 A1 B0
+ 57 55 58 5C 5e 64 6B 7F 00 0C 19
+ 20 23 26 29 28 51 61 70 6F 76 86
+ 89 8D 99 9A 95 A1 B0 57 55 58 5C
+ 5E 64 6B 7F
+ 39 01 00 00 00 00 03 C0 1F 31
+ 15 01 00 00 00 00 02 CC 0B
+ 15 01 00 00 00 00 02 D4 02
+ 15 01 00 00 00 00 02 BD 02
+ 39 01 00 00 00 00 0D
+ D8 FF FF FF FF FF FF FF FF FF FF
+ FF FF
+ 15 01 00 00 00 00 02 BD 00
+ 15 01 00 00 00 00 02 BD 01
+ 15 01 00 00 00 00 02 B1 00
+ 15 01 00 00 00 00 02 BD 00
+ 39 01 00 00 00 00 08
+ BF 40 81 50 00 1A FC 01
+ 39 01 00 00 00 00 03 B6 7D 7D
+ 05 01 00 00 78 00 02 11 00
+ 39 01 00 00 00 00 0D
+ B2 00 80 64 0E 0D 2F 00 00 00 00
+ C0 18
+ 05 01 00 00 14 00 02 29 00];
+
+ qcom,mdss-dsi-off-command = [05 01 00 00 78 00 02 28 00
+ 05 01 00 00 96 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 = <1>;
+ qcom,mdss-dsi-traffic-mode = "burst_mode";
+ qcom,mdss-dsi-lane-map = "lane_map_0123";
+ 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
+ = [72 16 0e 00 38 3c 12 1a 10 03 04 00];
+ qcom,mdss-dsi-t-clk-post = <0x04>;
+ qcom,mdss-dsi-t-clk-pre = <0x18>;
+ qcom,mdss-dsi-bl-min-level = <1>;
+ qcom,mdss-dsi-bl-max-level = <4095>;
+ qcom,mdss-dsi-dma-trigger = "trigger_sw";
+ qcom,mdss-dsi-mdp-trigger = "none";
+ qcom,mdss-dsi-bl-pmic-control-type = "bl_ctrl_wled";
+ qcom,mdss-dsi-reset-sequence = <1 20>, <0 2>, <1 20>;
+ qcom,mdss-dsi-panel-status-command = [06 01 00 01 05 00 01 D9
+ 06 01 00 01 05 00 01 09
+ 06 01 00 01 05 00 01 45];
+ qcom,mdss-dsi-panel-status-command-state = "dsi_lp_mode";
+ qcom,mdss-dsi-panel-status-check-mode = "reg_read";
+ qcom,mdss-dsi-panel-status-read-length = <4 4 3>;
+ qcom,mdss-dsi-panel-status-valid-params = <1 3 2>;
+ qcom,mdss-dsi-panel-status-value =
+ <0x80 0x80 0x73 0x04 0x05 0x0f>,
+ <0x80 0x80 0x73 0x04 0x05 0x1e>;
+ qcom,mdss-dsi-panel-max-error-count = <3>;
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/dsi-panel-hx8399c-hd-plus-video.dtsi b/arch/arm64/boot/dts/qcom/dsi-panel-hx8399c-hd-plus-video.dtsi
index fc09a65..237684e 100644
--- a/arch/arm64/boot/dts/qcom/dsi-panel-hx8399c-hd-plus-video.dtsi
+++ b/arch/arm64/boot/dts/qcom/dsi-panel-hx8399c-hd-plus-video.dtsi
@@ -126,7 +126,7 @@
qcom,mdss-dsi-lane-2-state;
qcom,mdss-dsi-lane-3-state;
qcom,mdss-dsi-panel-timings =
- [7a 1a 12 00 3e 42 16 1e 03 04 00];
+ [7a 1a 12 00 3e 42 16 1e 14 03 04 00];
qcom,mdss-dsi-t-clk-post = <0x0a>;
qcom,mdss-dsi-t-clk-pre = <0x1d>;
qcom,mdss-dsi-dma-trigger = "trigger_sw";
diff --git a/arch/arm64/boot/dts/qcom/msm-arm-smmu-8909.dtsi b/arch/arm64/boot/dts/qcom/msm-arm-smmu-8909.dtsi
index a601b5f..b506fb4 100644
--- a/arch/arm64/boot/dts/qcom/msm-arm-smmu-8909.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm-arm-smmu-8909.dtsi
@@ -16,6 +16,46 @@
&soc {
+ kgsl_smmu: arm,smmu-kgsl@1f00000 {
+ status = "ok";
+ compatible = "qcom,qsmmu-v500";
+ reg = <0x1f00000 0x10000>,
+ <0x1ef2000 0x20>;
+ reg-names = "base", "tcu-base";
+ #iommu-cells = <1>;
+ qcom,tz-device-id = "GPU";
+ qcom,skip-init;
+ qcom,dynamic;
+ qcom,use-3-lvl-tables;
+ #global-interrupts = <0>;
+ #size-cells = <1>;
+ #address-cells = <1>;
+ ranges;
+ interrupts =
+ <GIC_SPI 240 IRQ_TYPE_LEVEL_HIGH>,
+ <GIC_SPI 241 IRQ_TYPE_LEVEL_HIGH>,
+ <GIC_SPI 242 IRQ_TYPE_LEVEL_HIGH>,
+ <GIC_SPI 245 IRQ_TYPE_LEVEL_HIGH>;
+
+ vdd-supply = <&gdsc_oxili_gx>;
+ qcom,regulator-names = "vdd";
+ clocks =
+ <&clock_gcc clk_gcc_oxili_ahb_clk>,
+ <&clock_gcc clk_gcc_bimc_gfx_clk>;
+ clock-names = "gpu_ahb_clk", "gcc_bimc_gfx_clk";
+ };
+
+ /* A test device to test the SMMU operation */
+ kgsl_iommu_test_device0 {
+ status = "disabled";
+ compatible = "iommu-debug-test";
+ /*
+ * The SID should be valid one to get the proper
+ * SMR,S2CR indices.
+ */
+ iommus = <&kgsl_smmu 0x0>;
+ };
+
apps_iommu: qcom,iommu@1e00000 {
compatible = "qcom,qsmmu-v500";
reg = <0x1e00000 0x40000>,
diff --git a/arch/arm64/boot/dts/qcom/msm8909-gpu.dtsi b/arch/arm64/boot/dts/qcom/msm8909-gpu.dtsi
new file mode 100644
index 0000000..dc95570
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8909-gpu.dtsi
@@ -0,0 +1,149 @@
+/* Copyright (c) 2018, 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 {
+ msm_bus: qcom,kgsl-busmon {
+ label = "kgsl-busmon";
+ compatible = "qcom,kgsl-busmon";
+ };
+
+ /* To use BIMC based bus governor */
+ gpubw: qcom,gpubw {
+ compatible = "qcom,devbw";
+ governor = "bw_hwmon";
+ qcom,src-dst-ports = <26 512>;
+ qcom,bw-tbl =
+ < 0 >, /* 9.6 MHz */
+ < 381 >, /* 50.0 MHz */
+ < 762 >, /* 100.0 MHz */
+ < 1525 >, /* 200.0 MHz */
+ < 3051 >, /* 400.0 MHz */
+ < 4066 >; /* 533.0 MHz */
+ };
+
+ qcom,gpu-bwmon@410000 {
+ compatible = "qcom,bimc-bwmon2";
+ reg = <0x00410000 0x300>, <0x00401000 0x200>;
+ reg-names = "base", "global_base";
+ interrupts = <0 183 4>;
+ qcom,mport = <2>;
+ qcom,target-dev = <&gpubw>;
+ };
+
+ msm_gpu: qcom,kgsl-3d0@01c00000 {
+ label = "kgsl-3d0";
+ compatible = "qcom,kgsl-3d0", "qcom,kgsl-3d";
+ status = "ok";
+ reg = <0x01c00000 0x10000
+ 0x01c10000 0x10000
+ 0x0005c000 0x204>;
+ reg-names = "kgsl_3d0_reg_memory" , "kgsl_3d0_shader_memory" ,
+ "qfprom_memory";
+ interrupts = <0 33 0>;
+ interrupt-names = "kgsl_3d0_irq";
+ qcom,id = <0>;
+
+ qcom,chipid = <0x03000400>;
+
+ qcom,initial-pwrlevel = <1>;
+
+ qcom,idle-timeout = <80>; /* msec */
+ qcom,strtstp-sleepwake;
+ qcom,gpu-disable-fuse = <0x44 0x00000001 27>;
+
+ /*
+ * Clocks = KGSL_CLK_CORE | KGSL_CLK_IFACE |
+ * KGSL_CLK_MEM_IFACE | KGSL_CLK_ALT_MEM_IFACE
+ */
+ qcom,clk-map = <0x00000056>;
+ clocks = <&clock_gcc clk_gcc_oxili_gfx3d_clk>,
+ <&clock_gcc clk_gcc_oxili_ahb_clk>,
+ <&clock_gcc clk_gcc_bimc_gfx_clk>,
+ <&clock_gcc clk_gcc_bimc_gpu_clk>,
+ <&clock_gcc clk_gcc_gtcu_ahb_clk>;
+ clock-names = "core_clk", "iface_clk",
+ "mem_iface_clk", "alt_mem_iface_clk",
+ "gtcu_iface_clk";
+
+ /* Bus Scale Settings */
+ qcom,gpubw-dev = <&gpubw>;
+ qcom,msm-bus,name = "grp3d";
+ qcom,msm-bus,num-cases = <4>;
+ qcom,msm-bus,num-paths = <1>;
+ qcom,msm-bus,vectors-KBps =
+ <26 512 0 0>,
+ <26 512 0 1600000>,
+ <26 512 0 3200000>,
+ <26 512 0 4264000>;
+
+ /* GDSC oxili regulators */
+ vdd-supply = <&gdsc_oxili_gx>;
+
+ /* CPU latency parameter */
+ qcom,pm-qos-active-latency = <701>;
+ qcom,pm-qos-wakeup-latency = <701>;
+
+ /* Power levels */
+ qcom,gpu-pwrlevels {
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ compatible = "qcom,gpu-pwrlevels";
+
+ qcom,gpu-pwrlevel@0 {
+ reg = <0>;
+ qcom,gpu-freq = <456000000>;
+ qcom,bus-freq = <3>;
+ };
+
+ qcom,gpu-pwrlevel@1 {
+ reg = <1>;
+ qcom,gpu-freq = <307200000>;
+ qcom,bus-freq = <2>;
+ };
+
+ qcom,gpu-pwrlevel@2 {
+ reg = <2>;
+ qcom,gpu-freq = <200000000>;
+ qcom,bus-freq = <1>;
+ };
+
+ qcom,gpu-pwrlevel@3 {
+ reg = <3>;
+ qcom,gpu-freq = <19200000>;
+ qcom,bus-freq = <0>;
+ };
+ };
+
+ };
+ kgsl_msm_iommu: qcom,kgsl-iommu@1f00000 {
+ compatible = "qcom,kgsl-smmu-v2";
+ reg = <0x1f00000 0x10000>;
+ /*
+ * The gpu can only program a single context bank
+ * at this fixed offset.
+ */
+ qcom,protect = <0xa000 0x1000>;
+ clocks = <&clock_gcc clk_gcc_smmu_cfg_clk>,
+ <&clock_gcc clk_gcc_gfx_tcu_clk>,
+ <&clock_gcc clk_gcc_gtcu_ahb_clk>,
+ <&clock_gcc clk_gcc_gfx_tbu_clk>;
+ clock-names = "scfg_clk", "gtcu_clk",
+ "gtcu_iface_clk", "gtbu_clk";
+ qcom,retention;
+ gfx3d_user: gfx3d_user {
+ compatible = "qcom,smmu-kgsl-cb";
+ iommus = <&kgsl_smmu 0>;
+ qcom,gpu-offset = <0xa000>;
+ };
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8909.dtsi b/arch/arm64/boot/dts/qcom/msm8909.dtsi
index 5e56c49..ec16e60e 100644
--- a/arch/arm64/boot/dts/qcom/msm8909.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8909.dtsi
@@ -211,6 +211,13 @@
cont_splash_mem: splash_region@83000000 {
reg = <0x0 0x83000000 0x0 0xc00000>;
};
+
+ dump_mem: mem_dump_region {
+ compatible = "shared-dma-pool";
+ reusable;
+ size = <0 0x100000>;
+ };
+
};
soc: soc { };
@@ -220,6 +227,8 @@
#include "msm8909-smp2p.dtsi"
#include "msm8909-ipcrouter.dtsi"
#include "msm-gdsc-8916.dtsi"
+#include "msm-arm-smmu-8909.dtsi"
+#include "msm8909-gpu.dtsi"
#include "msm8909-coresight.dtsi"
#include "msm8909-bus.dtsi"
#include "msm8909-mdss.dtsi"
@@ -481,6 +490,47 @@
thermal_zones: thermal-zones {};
+ mem_dump {
+ compatible = "qcom,mem-dump";
+ memory-region = <&dump_mem>;
+
+ rpm_sw_dump {
+ qcom,dump-size = <0x28000>;
+ qcom,dump-id = <0xea>;
+ };
+
+ pmic_dump {
+ qcom,dump-size = <0x10000>;
+ qcom,dump-id = <0xe4>;
+ };
+
+ vsense_dump {
+ qcom,dump-size = <0x1000>;
+ qcom,dump-id = <0xe9>;
+ };
+
+ tmc_etf_dump {
+ qcom,dump-size = <0x10000>;
+ qcom,dump-id = <0xf0>;
+ };
+
+ tmc_etr_reg_dump {
+ qcom,dump-size = <0x1000>;
+ qcom,dump-id = <0x100>;
+ };
+
+ tmc_etf_reg_dump {
+ qcom,dump-size = <0x1000>;
+ qcom,dump-id = <0x101>;
+ };
+
+ misc_data_dump {
+ qcom,dump-size = <0x1000>;
+ qcom,dump-id = <0xe8>;
+ };
+
+ };
+
qcom,sensor-information {
compatible = "qcom,sensor-information";
sensor_information0: qcom,sensor-information-0 {
@@ -1623,6 +1673,16 @@
memory-region = <&adsp_mem>;
};
+ qcom,msm-adsprpc-mem {
+ compatible = "qcom,msm-adsprpc-mem-region";
+ memory-region = <&adsp_mem>;
+ restrict-access;
+ };
+
+ qcom,msm_fastrpc {
+ compatible = "qcom,msm-fastrpc-legacy-compute";
+ };
+
qcom,msm-adsp-loader {
compatible = "qcom,adsp-loader";
qcom,adsp-state = <0>;
diff --git a/arch/arm64/boot/dts/qcom/msm8909w-bg-memory.dtsi b/arch/arm64/boot/dts/qcom/msm8909w-bg-memory.dtsi
index 945b945..f841097 100644
--- a/arch/arm64/boot/dts/qcom/msm8909w-bg-memory.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8909w-bg-memory.dtsi
@@ -12,7 +12,7 @@
*/
&external_image_mem {
- reg = <0x0 0x87b00000 0x0 0x0500000>;
+ reg = <0x0 0x87a00000 0x0 0x0600000>;
};
&modem_adsp_mem {
diff --git a/arch/arm64/boot/dts/qcom/msm8909w-bg-wtp-v2.dts b/arch/arm64/boot/dts/qcom/msm8909w-bg-wtp-v2.dts
index 24266e8..8f2eac0 100644
--- a/arch/arm64/boot/dts/qcom/msm8909w-bg-wtp-v2.dts
+++ b/arch/arm64/boot/dts/qcom/msm8909w-bg-wtp-v2.dts
@@ -14,11 +14,11 @@
/dts-v1/;
#include "msm8909-mtp.dtsi"
+#include "msm8909w-gpu.dtsi"
#include "msm8909w.dtsi"
#include "msm8909w-bg-memory.dtsi"
#include "8909w-pm660.dtsi"
#include "msm8909-audio-bg_codec.dtsi"
-#include "msm-arm-smmu-8909.dtsi"
/ {
model = "Qualcomm Technologies, Inc. MSM8909W-PM660 BLACKGHOST WTP";
diff --git a/arch/arm64/boot/dts/qcom/msm8909w-gpu.dtsi b/arch/arm64/boot/dts/qcom/msm8909w-gpu.dtsi
new file mode 100644
index 0000000..7d42127
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8909w-gpu.dtsi
@@ -0,0 +1,62 @@
+/* Copyright (c) 2018, 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.
+ */
+
+/* To use BIMC based bus governor */
+&gpubw {
+ qcom,bw-tbl =
+ < 0 >, /* 9.6 MHz */
+ < 366 >, /* 48.0 MHz */
+ < 732 >, /* 96.0 MHz */
+ < 1464 >, /* 192.0 MHz */
+ < 2929 >; /* 384.0 MHz */
+};
+
+&msm_gpu {
+
+ /* To disable GPU wake up on touch event */
+ qcom,disable-wake-on-touch;
+
+ /* Bus Scale Settings */
+ qcom,msm-bus,num-cases = <3>;
+ qcom,msm-bus,vectors-KBps =
+ <26 512 0 0>,
+ <26 512 0 1536000>,
+ <26 512 0 3070000>;
+
+ /delete-node/qcom,gpu-pwrlevels;
+
+ /* Power levels */
+ qcom,gpu-pwrlevels {
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ compatible = "qcom,gpu-pwrlevels";
+
+ qcom,gpu-pwrlevel@0 {
+ reg = <0>;
+ qcom,gpu-freq = <200000000>;
+ qcom,bus-freq = <1>;
+ qcom,bus-min = <1>;
+ qcom,bus-max = <1>;
+ };
+
+ qcom,gpu-pwrlevel@1 {
+ reg = <1>;
+ qcom,gpu-freq = <19200000>;
+ qcom,bus-freq = <0>;
+ qcom,bus-min = <0>;
+ qcom,bus-max = <0>;
+ };
+
+ };
+
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-audio.dtsi b/arch/arm64/boot/dts/qcom/msm8917-audio.dtsi
new file mode 100644
index 0000000..a46e4fe
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-audio.dtsi
@@ -0,0 +1,434 @@
+/*
+ * Copyright (c) 2018, 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 "msm-audio-lpass.dtsi"
+#include "msm8953-wsa881x.dtsi"
+
+&msm_audio_ion {
+ iommus = <&apps_iommu 0x2001 0x0>;
+ qcom,smmu-sid-mask = /bits/ 64 <0xf>;
+};
+
+&soc {
+ qcom,msm-audio-apr {
+ compatible = "qcom,msm-audio-apr";
+ msm_audio_apr_dummy {
+ compatible = "qcom,msm-audio-apr-dummy";
+ };
+ };
+
+ qcom,avtimer@c0a300c {
+ compatible = "qcom,avtimer";
+ reg = <0x0c0a300c 0x4>,
+ <0x0c0a3010 0x4>;
+ reg-names = "avtimer_lsb_addr", "avtimer_msb_addr";
+ qcom,clk-div = <27>;
+ };
+
+ int_codec: sound {
+ status = "okay";
+ compatible = "qcom,msm8952-audio-codec";
+ qcom,model = "msm8952-snd-card-mtp";
+ reg = <0xc051000 0x4>,
+ <0xc051004 0x4>,
+ <0xc055000 0x4>,
+ <0xc052000 0x4>;
+ reg-names = "csr_gp_io_mux_mic_ctl",
+ "csr_gp_io_mux_spkr_ctl",
+ "csr_gp_io_lpaif_pri_pcm_pri_mode_muxsel",
+ "csr_gp_io_mux_quin_ctl";
+
+ qcom,msm-ext-pa = "primary";
+ qcom,msm-mclk-freq = <9600000>;
+ qcom,msm-mbhc-hphl-swh = <0>;
+ qcom,msm-mbhc-gnd-swh = <0>;
+ qcom,msm-hs-micbias-type = "external";
+ qcom,msm-micbias1-ext-cap;
+
+ qcom,audio-routing =
+ "RX_BIAS", "MCLK",
+ "SPK_RX_BIAS", "MCLK",
+ "INT_LDO_H", "MCLK",
+ "RX_I2S_CLK", "MCLK",
+ "TX_I2S_CLK", "MCLK",
+ "MIC BIAS External", "Handset Mic",
+ "MIC BIAS External2", "Headset Mic",
+ "MIC BIAS External", "Secondary Mic",
+ "AMIC1", "MIC BIAS External",
+ "AMIC2", "MIC BIAS External2",
+ "AMIC3", "MIC BIAS External",
+ "ADC1_IN", "ADC1_OUT",
+ "ADC2_IN", "ADC2_OUT",
+ "ADC3_IN", "ADC3_OUT",
+ "PDM_IN_RX1", "PDM_OUT_RX1",
+ "PDM_IN_RX2", "PDM_OUT_RX2",
+ "PDM_IN_RX3", "PDM_OUT_RX3",
+ "WSA_SPK OUT", "VDD_WSA_SWITCH",
+ "SpkrMono WSA_IN", "WSA_SPK OUT";
+
+ qcom,cdc-us-euro-gpios = <&tlmm 63 0>;
+ qcom,cdc-us-eu-gpios = <&cdc_us_euro_sw>;
+ qcom,pri-mi2s-gpios = <&cdc_pri_mi2s_gpios>;
+ qcom,quin-mi2s-gpios = <&cdc_quin_mi2s_gpios>;
+
+ asoc-platform = <&pcm0>, <&pcm1>, <&pcm2>, <&voip>, <&voice>,
+ <&loopback>, <&compress>, <&hostless>,
+ <&afe>, <&lsm>, <&routing>, <&pcm_noirq>;
+ asoc-platform-names = "msm-pcm-dsp.0", "msm-pcm-dsp.1",
+ "msm-pcm-dsp.2", "msm-voip-dsp",
+ "msm-pcm-voice", "msm-pcm-loopback",
+ "msm-compress-dsp", "msm-pcm-hostless",
+ "msm-pcm-afe", "msm-lsm-client",
+ "msm-pcm-routing", "msm-pcm-dsp-noirq";
+ asoc-cpu = <&dai_pri_auxpcm>,
+ <&dai_mi2s0>, <&dai_mi2s1>,
+ <&dai_mi2s2>, <&dai_mi2s3>,
+ <&dai_mi2s4>, <&dai_mi2s5>,
+ <&sb_0_rx>, <&sb_0_tx>, <&sb_1_rx>, <&sb_1_tx>,
+ <&sb_3_rx>, <&sb_3_tx>, <&sb_4_rx>, <&sb_4_tx>,
+ <&bt_sco_rx>, <&bt_sco_tx>,
+ <&int_fm_rx>, <&int_fm_tx>,
+ <&afe_pcm_rx>, <&afe_pcm_tx>,
+ <&afe_proxy_rx>, <&afe_proxy_tx>,
+ <&incall_record_rx>, <&incall_record_tx>,
+ <&incall_music_rx>, <&incall_music_2_rx>;
+
+ asoc-cpu-names = "msm-dai-q6-auxpcm.1",
+ "msm-dai-q6-mi2s.0", "msm-dai-q6-mi2s.1",
+ "msm-dai-q6-mi2s.2", "msm-dai-q6-mi2s.3",
+ "msm-dai-q6-mi2s.4", "msm-dai-q6-mi2s.6",
+ "msm-dai-q6-dev.16384", "msmdai-q6-dev.16385",
+ "msm-dai-q6-dev.16386", "msm-dai-q6-dev.16387",
+ "msm-dai-q6-dev.16390", "msm-dai-q6-dev.16391",
+ "msm-dai-q6-dev.16392", "msm-dai-q6-dev.16393",
+ "msm-dai-q6-dev.12288", "msm-dai-q6-dev.12289",
+ "msm-dai-q6-dev.12292", "msm-dai-q6-dev.12293",
+ "msm-dai-q6-dev.224", "msm-dai-q6-dev.225",
+ "msm-dai-q6-dev.241", "msm-dai-q6-dev.240",
+ "msm-dai-q6-dev.32771", "msm-dai-q6-dev.32772",
+ "msm-dai-q6-dev.32773", "msm-dai-q6-dev.32770";
+
+ asoc-codec = <&stub_codec>, <&msm_digital_codec>,
+ <&pmic_analog_codec>;
+ asoc-codec-names = "msm-stub-codec.1", "msm-dig-codec",
+ "analog-codec";
+ asoc-wsa-codec-names = "wsa881x-i2c-codec.2-000f";
+ asoc-wsa-codec-prefixes = "SpkrMono";
+ msm-vdd-wsa-switch-supply = <&pm8937_l5>;
+ qcom,msm-vdd-wsa-switch-voltage = <1800000>;
+ qcom,msm-vdd-wsa-switch-current = <10000>;
+ };
+
+ cdc_us_euro_sw: msm_cdc_pinctrl_us_euro_sw {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&cross_conn_det_act>;
+ pinctrl-1 = <&cross_conn_det_sus>;
+ };
+
+ cdc_pri_mi2s_gpios: msm_cdc_pinctrl_pri {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&cdc_pdm_lines_act &cdc_pdm_lines_2_act>;
+ pinctrl-1 = <&cdc_pdm_lines_sus &cdc_pdm_lines_2_sus>;
+ };
+
+ cdc_quin_mi2s_gpios: msm_cdc_pinctrl_quin {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&pri_tlmm_lines_act &pri_tlmm_ws_act>;
+ pinctrl-1 = <&pri_tlmm_lines_sus &pri_tlmm_ws_sus>;
+ };
+
+
+ i2c@78b6000 {
+ status = "okay";
+ #address-cells = <1>;
+ #size-cells = <0>;
+ wsa881x_i2c_f: wsa881x-i2c-codec@f {
+ status = "okay";
+ compatible = "qcom,wsa881x-i2c-codec";
+ reg = <0x0f>;
+ qcom,wsa-analog-vi-gpio = <&wsa881x_analog_vi_gpio>;
+ qcom,wsa-analog-clk-gpio = <&wsa881x_analog_clk_gpio>;
+ qcom,wsa-analog-reset-gpio =
+ <&wsa881x_analog_reset_gpio>;
+ };
+ wsa881x_i2c_45: wsa881x-i2c-codec@45 {
+ status = "okay";
+ compatible = "qcom,wsa881x-i2c-codec";
+ reg = <0x45>;
+ };
+ };
+
+ wsa881x_analog_vi_gpio: wsa881x_analog_vi_pctrl {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&wsa_vi_on>;
+ pinctrl-1 = <&wsa_vi_off>;
+ };
+ wsa881x_analog_clk_gpio: wsa881x_analog_clk_pctrl {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&wsa_clk_on>;
+ pinctrl-1 = <&wsa_clk_off>;
+ };
+ wsa881x_analog_reset_gpio: wsa881x_analog_reset_pctrl {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&wsa_reset_on>;
+ pinctrl-1 = <&wsa_reset_off>;
+ };
+
+ ext_codec: sound-9335 {
+ status = "disabled";
+ compatible = "qcom,msm8952-audio-slim-codec";
+ qcom,model = "msm8952-tasha-snd-card";
+
+ reg = <0xc051000 0x4>,
+ <0xc051004 0x4>,
+ <0xc055000 0x4>,
+ <0xc052000 0x4>;
+ reg-names = "csr_gp_io_mux_mic_ctl",
+ "csr_gp_io_mux_spkr_ctl",
+ "csr_gp_io_lpaif_pri_pcm_pri_mode_muxsel",
+ "csr_gp_io_mux_quin_ctl";
+
+ qcom,audio-routing =
+ "AIF4 VI", "MCLK",
+ "AIF4 VI", "MICBIAS_REGULATOR",
+ "RX_BIAS", "MCLK",
+ "MADINPUT", "MCLK",
+ "AIF4 MAD", "MICBIAS_REGULATOR",
+ "AMIC2", "MIC BIAS2",
+ "MIC BIAS2", "Headset Mic",
+ "AMIC3", "MIC BIAS2",
+ "MIC BIAS2", "ANCRight Headset Mic",
+ "AMIC4", "MIC BIAS2",
+ "MIC BIAS2", "ANCLeft Headset Mic",
+ "AMIC5", "MIC BIAS3",
+ "MIC BIAS3", "Handset Mic",
+ "AMIC6", "MIC BIAS4",
+ "MIC BIAS4", "Analog Mic6",
+ "DMIC0", "MIC BIAS1",
+ "MIC BIAS1", "Digital Mic0",
+ "DMIC1", "MIC BIAS1",
+ "MIC BIAS1", "Digital Mic1",
+ "DMIC2", "MIC BIAS3",
+ "MIC BIAS3", "Digital Mic2",
+ "DMIC3", "MIC BIAS3",
+ "MIC BIAS3", "Digital Mic3",
+ "DMIC4", "MIC BIAS4",
+ "MIC BIAS4", "Digital Mic4",
+ "DMIC5", "MIC BIAS4",
+ "MIC BIAS4", "Digital Mic5",
+ "MIC BIAS1", "MICBIAS_REGULATOR",
+ "MIC BIAS2", "MICBIAS_REGULATOR",
+ "MIC BIAS3", "MICBIAS_REGULATOR",
+ "MIC BIAS4", "MICBIAS_REGULATOR",
+ "SpkrLeft IN", "SPK1 OUT",
+ "SpkrRight IN", "SPK2 OUT";
+
+ qcom,tasha-mclk-clk-freq = <9600000>;
+
+ asoc-platform = <&pcm0>, <&pcm1>, <&pcm2>, <&voip>, <&voice>,
+ <&loopback>, <&compress>, <&hostless>,
+ <&afe>, <&lsm>, <&routing>;
+ asoc-platform-names = "msm-pcm-dsp.0", "msm-pcm-dsp.1",
+ "msm-pcm-dsp.2", "msm-voip-dsp",
+ "msm-pcm-voice", "msm-pcm-loopback",
+ "msm-compress-dsp", "msm-pcm-hostless",
+ "msm-pcm-afe", "msm-lsm-client",
+ "msm-pcm-routing";
+
+ asoc-cpu = <&dai_pri_auxpcm>,
+ <&dai_mi2s2>, <&dai_mi2s3>, <&dai_mi2s5>,
+ <&sb_0_rx>, <&sb_0_tx>, <&sb_1_rx>, <&sb_1_tx>,
+ <&sb_2_rx>, <&sb_2_tx>, <&sb_3_rx>, <&sb_3_tx>,
+ <&sb_4_rx>, <&sb_4_tx>, <&sb_5_tx>,
+ <&afe_pcm_rx>, <&afe_pcm_tx>,
+ <&afe_proxy_rx>, <&afe_proxy_tx>,
+ <&incall_record_rx>, <&incall_record_tx>,
+ <&incall_music_rx>, <&incall_music_2_rx>,
+ <&sb_5_rx>, <&bt_sco_rx>, <&bt_sco_tx>,
+ <&int_fm_rx>, <&int_fm_tx>, <&sb_6_rx>;
+
+ asoc-cpu-names = "msm-dai-q6-auxpcm.1",
+ "msm-dai-q6-mi2s.2", "msm-dai-q6-mi2s.3",
+ "msm-dai-q6-mi2s.5", "msm-dai-q6-dev.16384",
+ "msm-dai-q6-dev.16385", "msm-dai-q6-dev.16386",
+ "msm-dai-q6-dev.16387", "msm-dai-q6-dev.16388",
+ "msm-dai-q6-dev.16389", "msm-dai-q6-dev.16390",
+ "msm-dai-q6-dev.16391", "msm-dai-q6-dev.16392",
+ "msm-dai-q6-dev.16393", "msm-dai-q6-dev.16395",
+ "msm-dai-q6-dev.224", "msm-dai-q6-dev.225",
+ "msm-dai-q6-dev.241", "msm-dai-q6-dev.240",
+ "msm-dai-q6-dev.32771", "msm-dai-q6-dev.32772",
+ "msm-dai-q6-dev.32773", "msm-dai-q6-dev.32770",
+ "msm-dai-q6-dev.16394", "msm-dai-q6-dev.12288",
+ "msm-dai-q6-dev.12289", "msm-dai-q6-dev.12292",
+ "msm-dai-q6-dev.12293", "msm-dai-q6-dev.16396";
+
+ qcom,cdc-us-euro-gpios = <&tlmm 63 0>;
+ qcom,msm-mbhc-hphl-swh = <0>;
+ qcom,msm-mbhc-gnd-swh = <0>;
+
+ qcom,wsa-max-devs = <2>;
+ qcom,wsa-devs = <&wsa881x_211>, <&wsa881x_212>,
+ <&wsa881x_213>, <&wsa881x_214>;
+ qcom,wsa-aux-dev-prefix = "SpkrLeft", "SpkrRight",
+ "SpkrLeft", "SpkrRight";
+ };
+
+ wcd9xxx_intc: wcd9xxx-irq {
+ status = "disabled";
+ interrupt-parent = <&tlmm>;
+ interrupts = <73 0>;
+ qcom,gpio-connect = <&tlmm 73 0>;
+ };
+
+ clock_audio: audio_ext_clk {
+ status = "disabled";
+ compatible = "qcom,audio-ref-clk";
+ clock-names = "osr_clk";
+ qcom,node_has_rpm_clock;
+ #clock-cells = <1>;
+ qcom,audio-ref-clk-gpio = <&pm8937_gpios 1 0>;
+ qcom,lpass-mclk-id = "pri_mclk";
+ clocks = <&clock_gcc clk_div_clk2>;
+ pinctrl-0 = <&cdc_mclk2_sleep>;
+ pinctrl-1 = <&cdc_mclk2_active>;
+ };
+
+ wcd_rst_gpio: wcd_gpio_ctrl {
+ status = "disabled";
+ qcom,cdc-rst-n-gpio = <&tlmm 68 0>;
+ };
+};
+
+&slim_msm {
+ status = "disabled";
+ wcd9335: tasha_codec {
+ status = "disabled";
+ compatible = "qcom,tasha-slim-pgd";
+ clock-names = "wcd_clk", "wcd_native_clk";
+ clocks = <&clock_audio clk_audio_pmi_clk>,
+ <&clock_audio clk_audio_ap_clk2>;
+
+ qcom,cdc-reset-gpio = <&tlmm 68 0>;
+
+ cdc-vdd-buck-supply = <&eldo2_pm8937>;
+ qcom,cdc-vdd-buck-voltage = <1800000 1800000>;
+ qcom,cdc-vdd-buck-current = <650000>;
+
+ cdc-buck-sido-supply = <&eldo2_pm8937>;
+ qcom,cdc-buck-sido-voltage = <1800000 1800000>;
+ qcom,cdc-buck-sido-current = <250000>;
+
+ cdc-vdd-tx-h-supply = <&pm8937_l5>;
+ qcom,cdc-vdd-tx-h-voltage = <1800000 1800000>;
+ qcom,cdc-vdd-tx-h-current = <25000>;
+
+ cdc-vdd-rx-h-supply = <&pm8937_l5>;
+ qcom,cdc-vdd-rx-h-voltage = <1800000 1800000>;
+ qcom,cdc-vdd-rx-h-current = <25000>;
+
+ cdc-vdd-px-supply = <&pm8937_l5>;
+ qcom,cdc-vdd-px-voltage = <1800000 1800000>;
+ qcom,cdc-vdd-px-current = <10000>;
+
+ cdc-vdd-mic-bias-supply = <&pm8937_l13>;
+ qcom,cdc-vdd-mic-bias-voltage = <3075000 3075000>;
+ qcom,cdc-vdd-mic-bias-current = <15000>;
+ };
+};
+
+&pm8937_gpios {
+ gpio@c000 {
+ status = "ok";
+ qcom,mode = <1>;
+ qcom,pull = <5>;
+ qcom,vin-sel = <0>;
+ qcom,src-sel = <2>;
+ qcom,master-en = <1>;
+ qcom,out-strength = <2>;
+ };
+};
+
+&pm8937_1 {
+ pmic_analog_codec: analog-codec@f000 {
+ status = "okay";
+ compatible = "qcom,pmic-analog-codec";
+ reg = <0xf000 0x200>;
+ #address-cells = <2>;
+ #size-cells = <0>;
+ interrupt-parent = <&spmi_bus>;
+ interrupts = <0x1 0xf0 0x0 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x1 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x2 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x3 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x4 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x5 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x6 IRQ_TYPE_NONE>,
+ <0x1 0xf0 0x7 IRQ_TYPE_NONE>,
+ <0x1 0xf1 0x0 IRQ_TYPE_NONE>,
+ <0x1 0xf1 0x1 IRQ_TYPE_NONE>,
+ <0x1 0xf1 0x2 IRQ_TYPE_NONE>,
+ <0x1 0xf1 0x3 IRQ_TYPE_NONE>,
+ <0x1 0xf1 0x4 IRQ_TYPE_NONE>,
+ <0x1 0xf1 0x5 IRQ_TYPE_NONE>;
+ interrupt-names = "spk_cnp_int",
+ "spk_clip_int",
+ "spk_ocp_int",
+ "ins_rem_det1",
+ "but_rel_det",
+ "but_press_det",
+ "ins_rem_det",
+ "mbhc_int",
+ "ear_ocp_int",
+ "hphr_ocp_int",
+ "hphl_ocp_det",
+ "ear_cnp_int",
+ "hphr_cnp_int",
+ "hphl_cnp_int";
+
+ cdc-vdda-cp-supply = <&pm8937_s4>;
+ qcom,cdc-vdda-cp-voltage = <2050000 2050000>;
+ qcom,cdc-vdda-cp-current = <210000>;
+
+ cdc-vdd-io-supply = <&pm8937_l5>;
+ qcom,cdc-vdd-io-voltage = <1800000 1800000>;
+ qcom,cdc-vdd-io-current = <5000>;
+
+ cdc-vdd-pa-supply = <&pm8937_s4>;
+ qcom,cdc-vdd-pa-voltage = <1900000 2050000>;
+ qcom,cdc-vdd-pa-current = <260000>;
+
+ cdc-vdd-mic-bias-supply = <&pm8937_l13>;
+ qcom,cdc-vdd-mic-bias-voltage = <3075000 3075000>;
+ qcom,cdc-vdd-mic-bias-current = <5000>;
+
+ qcom,cdc-mclk-clk-rate = <9600000>;
+
+ qcom,cdc-static-supplies = "cdc-vdd-io",
+ "cdc-vdd-pa",
+ "cdc-vdda-cp";
+
+ qcom,cdc-on-demand-supplies = "cdc-vdd-mic-bias";
+
+ msm_digital_codec: msm-dig-codec {
+ compatible = "qcom,msm-digital-codec";
+ reg = <0xc0f0000 0x0>;
+ };
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-pinctrl.dtsi b/arch/arm64/boot/dts/qcom/msm8917-pinctrl.dtsi
index b8516d5..b9229e1 100644
--- a/arch/arm64/boot/dts/qcom/msm8917-pinctrl.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8917-pinctrl.dtsi
@@ -237,6 +237,31 @@
};
};
+ cdc_mclk2_pin {
+ cdc_mclk2_sleep: cdc_mclk2_sleep {
+ mux {
+ pins = "gpio66";
+ function = "pri_mi2s";
+ };
+ config {
+ pins = "gpio66";
+ drive-strength = <2>; /* 2 mA */
+ bias-pull-down; /* PULL DOWN */
+ };
+ };
+ cdc_mclk2_active: cdc_mclk2_active {
+ mux {
+ pins = "gpio66";
+ function = "pri_mi2s";
+ };
+ config {
+ pins = "gpio66";
+ drive-strength = <8>; /* 8 mA */
+ bias-disable; /* NO PULL */
+ };
+ };
+ };
+
pmx_mdss: pmx_mdss {
mdss_dsi_active: mdss_dsi_active {
mux {
diff --git a/arch/arm64/boot/dts/qcom/msm8917-pmi8937-mtp.dts b/arch/arm64/boot/dts/qcom/msm8917-pmi8937-mtp.dts
new file mode 100644
index 0000000..e5207fe
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-pmi8937-mtp.dts
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2015-2016, 2018, 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 "msm8917.dtsi"
+#include "msm8917-mtp.dtsi"
+#include "msm8917-pmi8937.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8917-PMI8937 MTP";
+ compatible = "qcom,msm8917-mtp", "qcom,msm8917", "qcom,mtp";
+ qcom,board-id = <8 0>;
+ qcom,pmic-id = <0x10019 0x020037 0x0 0x0>;
+};
+
+&vendor {
+ mtp_batterydata: qcom,battery-data {
+ qcom,batt-id-range-pct = <15>;
+ #include "batterydata-itech-3000mah.dtsi"
+ #include "batterydata-ascent-3450mAh.dtsi"
+ };
+};
+
+&qpnp_fg {
+ qcom,battery-data = <&mtp_batterydata>;
+};
+
+&qpnp_smbcharger {
+ qcom,battery-data = <&mtp_batterydata>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-pmi8937-qrd-sku5.dts b/arch/arm64/boot/dts/qcom/msm8917-pmi8937-qrd-sku5.dts
new file mode 100644
index 0000000..d857c82
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-pmi8937-qrd-sku5.dts
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2016, 2018, 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 "msm8917.dtsi"
+#include "msm8917-qrd.dtsi"
+#include "msm8917-pmi8937.dtsi"
+#include "msm8937-mdss-panels.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8917-PMI8937 QRD SKU5";
+ compatible = "qcom,msm8917-qrd-sku5", "qcom,msm8917-qrd",
+ "qcom,msm8917", "qcom,qrd";
+ qcom,board-id = <0x1000b 0>;
+};
+
+&vendor{
+ qrd_batterydata: qcom,battery-data {
+ qcom,batt-id-range-pct = <15>;
+ #include "batterydata-qrd-sku2-4v35-2590mah.dtsi"
+ };
+};
+
+&qpnp_smbcharger {
+ qcom,battery-data = <&qrd_batterydata>;
+};
+
+&qpnp_fg {
+ qcom,battery-data = <&qrd_batterydata>;
+};
+
+&mdss_mdp {
+ qcom,mdss-pref-prim-intf = "dsi";
+};
+
+&mdss_dsi {
+ hw-config = "single_dsi";
+};
+
+&mdss_dsi0 {
+ qcom,dsi-pref-prim-pan = <&dsi_hx8394f_720p_video>;
+ pinctrl-names = "mdss_default", "mdss_sleep";
+ pinctrl-0 = <&mdss_dsi_active>;
+ pinctrl-1 = <&mdss_dsi_suspend>;
+
+ qcom,platform-reset-gpio = <&tlmm 60 0>;
+};
+
+&dsi_hx8394f_720p_video {
+ qcom,esd-check-enabled;
+ qcom,panel-supply-entries = <&dsi_panel_pwr_supply>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-pmi8937.dtsi b/arch/arm64/boot/dts/qcom/msm8917-pmi8937.dtsi
new file mode 100644
index 0000000..3b24ab7
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-pmi8937.dtsi
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018 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 "pmi8937.dtsi"
+
+&qpnp_smbcharger {
+ qcom,chg-led-sw-controls;
+ qcom,chg-led-support;
+ /delete-property/ dpdm-supply;
+};
+
+&usb_otg {
+ extcon = <&qpnp_smbcharger>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-pmi8940-mtp.dts b/arch/arm64/boot/dts/qcom/msm8917-pmi8940-mtp.dts
new file mode 100644
index 0000000..8379228
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-pmi8940-mtp.dts
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2017-2018, 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 "msm8917.dtsi"
+#include "msm8917-mtp.dtsi"
+#include "msm8917-pmi8940.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8917-PMI8940 MTP";
+ compatible = "qcom,msm8917-mtp", "qcom,msm8917", "qcom,mtp";
+ qcom,board-id = <8 0>;
+ qcom,pmic-id = <0x10019 0x020040 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-pmi8940.dtsi b/arch/arm64/boot/dts/qcom/msm8917-pmi8940.dtsi
new file mode 100644
index 0000000..528bde4
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-pmi8940.dtsi
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018 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 "pmi8940.dtsi"
+
+&qpnp_smbcharger {
+ qcom,chg-led-sw-controls;
+ qcom,chg-led-support;
+ /delete-property/ dpdm-supply;
+};
+
+&usb_otg {
+ extcon = <&qpnp_smbcharger>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917-qrd.dtsi b/arch/arm64/boot/dts/qcom/msm8917-qrd.dtsi
new file mode 100644
index 0000000..f897b59
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8917-qrd.dtsi
@@ -0,0 +1,96 @@
+/*
+ * Copyright (c) 2016, 2018, 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 "msm8917-pinctrl.dtsi"
+
+&blsp1_uart2 {
+ status = "ok";
+ pinctrl-names = "default";
+ pinctrl-0 = <&uart_console_active>;
+};
+
+&sdhc_1 {
+ /* device core power supply */
+ vdd-supply = <&pm8937_l8>;
+ qcom,vdd-voltage-level = <2900000 2900000>;
+ qcom,vdd-current-level = <200 570000>;
+
+ /* device communication power supply */
+ vdd-io-supply = <&pm8937_l5>;
+ qcom,vdd-io-always-on;
+ qcom,vdd-io-lpm-sup;
+ qcom,vdd-io-voltage-level = <1800000 1800000>;
+ qcom,vdd-io-current-level = <200 325000>;
+
+ pinctrl-names = "active", "sleep";
+ pinctrl-0 = <&sdc1_clk_on &sdc1_cmd_on &sdc1_data_on &sdc1_rclk_on>;
+ pinctrl-1 = <&sdc1_clk_off &sdc1_cmd_off &sdc1_data_off &sdc1_rclk_off>;
+
+ qcom,clk-rates = <400000 20000000 25000000 50000000 100000000 192000000
+ 384000000>;
+ qcom,nonremovable;
+ qcom,bus-speed-mode = "HS400_1p8v", "HS200_1p8v", "DDR_1p8v";
+
+ status = "ok";
+};
+
+&sdhc_2 {
+ /* device core power supply */
+ vdd-supply = <&pm8937_l11>;
+ qcom,vdd-voltage-level = <2950000 2950000>;
+ qcom,vdd-current-level = <15000 800000>;
+
+ /* device communication power supply */
+ vdd-io-supply = <&pm8937_l12>;
+ 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>;
+
+ #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 67 0>;
+ interrupt-names = "hc_irq", "pwr_irq", "status_irq";
+ cd-gpios = <&tlmm 67 0x1>;
+
+ qcom,clk-rates = <400000 20000000 25000000 50000000 100000000
+ 200000000>;
+ qcom,bus-speed-mode = "SDR12", "SDR25", "SDR50", "DDR50", "SDR104";
+
+ status = "ok";
+};
+
+&soc {
+ gpio_keys {
+ compatible = "gpio-keys";
+ input-name = "gpio-keys";
+ pinctrl-names = "tlmm_gpio_key_active","tlmm_gpio_key_suspend";
+ pinctrl-0 = <&gpio_key_active>;
+ pinctrl-1 = <&gpio_key_suspend>;
+
+ vol_up {
+ label = "volume_up";
+ gpios = <&tlmm 91 0x1>;
+ linux,input-type = <1>;
+ linux,code = <115>;
+ debounce-interval = <15>;
+ };
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8917.dtsi b/arch/arm64/boot/dts/qcom/msm8917.dtsi
index 9b91fe9..78410b3 100644
--- a/arch/arm64/boot/dts/qcom/msm8917.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8917.dtsi
@@ -1140,6 +1140,175 @@
qcom,ce-opp-freq = <100000000>;
};
+ qcom,mss@4080000 {
+ compatible = "qcom,pil-q6v55-mss";
+ reg = <0x04080000 0x100>,
+ <0x0194f000 0x010>,
+ <0x01950000 0x008>,
+ <0x01951000 0x008>,
+ <0x04020000 0x040>,
+ <0x01871000 0x004>;
+ reg-names = "qdsp6_base", "halt_q6", "halt_modem", "halt_nc",
+ "rmb_base", "restart_reg";
+
+ interrupts = <GIC_SPI 24 IRQ_TYPE_EDGE_RISING>;
+ vdd_mss-supply = <&pm8937_s1>;
+ vdd_cx-supply = <&pm8937_s2_level>;
+ vdd_cx-voltage = <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ vdd_mx-supply = <&pm8937_l3_level_ao>;
+ vdd_mx-uV = <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ vdd_pll-supply = <&pm8937_l7>;
+ qcom,vdd_pll = <1800000>;
+ vdd_mss-uV = <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+
+ clocks = <&clock_gcc clk_xo_pil_mss_clk>,
+ <&clock_gcc clk_gcc_mss_cfg_ahb_clk>,
+ <&clock_gcc clk_gcc_mss_q6_bimc_axi_clk>,
+ <&clock_gcc clk_gcc_boot_rom_ahb_clk>;
+ clock-names = "xo", "iface_clk", "bus_clk", "mem_clk";
+ qcom,proxy-clock-names = "xo";
+ qcom,active-clock-names = "iface_clk", "bus_clk", "mem_clk";
+
+ qcom,firmware-name = "modem";
+ qcom,pil-self-auth;
+ qcom,override-acc-1 = <0x80800000>;
+ qcom,sysmon-id = <0>;
+ qcom,ssctl-instance-id = <0x12>;
+ qcom,qdsp6v56-1-8-inrush-current;
+ qcom,reset-clk;
+
+ /* GPIO inputs from mss */
+ qcom,gpio-err-fatal = <&smp2pgpio_ssr_smp2p_1_in 0 0>;
+ qcom,gpio-err-ready = <&smp2pgpio_ssr_smp2p_1_in 1 0>;
+ qcom,gpio-proxy-unvote = <&smp2pgpio_ssr_smp2p_1_in 2 0>;
+ qcom,gpio-stop-ack = <&smp2pgpio_ssr_smp2p_1_in 3 0>;
+ qcom,gpio-shutdown-ack = <&smp2pgpio_ssr_smp2p_1_in 7 0>;
+
+ /* GPIO output to mss */
+ qcom,gpio-force-stop = <&smp2pgpio_ssr_smp2p_1_out 0 0>;
+
+ memory-region = <&modem_mem>;
+ };
+
+ qcom,lpass@c200000 {
+ compatible = "qcom,pil-tz-generic";
+ reg = <0xc200000 0x00100>;
+ interrupts = <GIC_SPI 293 IRQ_TYPE_EDGE_RISING>;
+
+ vdd_cx-supply = <&pm8937_s2_level>;
+ qcom,proxy-reg-names = "vdd_cx";
+ qcom,vdd_cx-uV-uA = <RPM_SMD_REGULATOR_LEVEL_TURBO 100000>;
+
+ clocks = <&clock_gcc clk_xo_pil_lpass_clk>,
+ <&clock_gcc clk_gcc_crypto_clk>,
+ <&clock_gcc clk_gcc_crypto_ahb_clk>,
+ <&clock_gcc clk_gcc_crypto_axi_clk>,
+ <&clock_gcc clk_crypto_clk_src>;
+ clock-names = "xo", "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+ qcom,proxy-clock-names = "xo", "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+ qcom,scm_core_clk_src-freq = <80000000>;
+
+ qcom,mas-crypto = <&mas_crypto>;
+ qcom,pas-id = <1>;
+ qcom,complete-ramdump;
+ qcom,proxy-timeout-ms = <10000>;
+ qcom,smem-id = <423>;
+ qcom,sysmon-id = <1>;
+ qcom,ssctl-instance-id = <0x14>;
+ qcom,firmware-name = "adsp";
+
+ /* GPIO inputs from lpass */
+ qcom,gpio-err-fatal = <&smp2pgpio_ssr_smp2p_2_in 0 0>;
+ qcom,gpio-proxy-unvote = <&smp2pgpio_ssr_smp2p_2_in 2 0>;
+ qcom,gpio-err-ready = <&smp2pgpio_ssr_smp2p_2_in 1 0>;
+ qcom,gpio-stop-ack = <&smp2pgpio_ssr_smp2p_2_in 3 0>;
+
+ /* GPIO output to lpass */
+ qcom,gpio-force-stop = <&smp2pgpio_ssr_smp2p_2_out 0 0>;
+
+ memory-region = <&adsp_fw_mem>;
+ };
+
+ qcom,pronto@a21b000 {
+ compatible = "qcom,pil-tz-generic";
+ reg = <0x0a21b000 0x3000>;
+ interrupts = <GIC_SPI 149 IRQ_TYPE_EDGE_RISING>;
+
+ vdd_pronto_pll-supply = <&pm8937_l7>;
+ proxy-reg-names = "vdd_pronto_pll";
+ vdd_pronto_pll-uV-uA = <1800000 18000>;
+ clocks = <&clock_gcc clk_xo_pil_pronto_clk>,
+ <&clock_gcc clk_gcc_crypto_clk>,
+ <&clock_gcc clk_gcc_crypto_ahb_clk>,
+ <&clock_gcc clk_gcc_crypto_axi_clk>,
+ <&clock_gcc clk_crypto_clk_src>;
+
+ clock-names = "xo", "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+ qcom,proxy-clock-names = "xo", "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+ qcom,scm_core_clk_src = <80000000>;
+
+ qcom,mas-crypto = <&mas_crypto>;
+ qcom,pas-id = <6>;
+ qcom,proxy-timeout-ms = <10000>;
+ qcom,smem-id = <422>;
+ qcom,sysmon-id = <6>;
+ qcom,ssctl-instance-id = <0x13>;
+ qcom,firmware-name = "wcnss";
+
+ /* GPIO inputs from wcnss */
+ qcom,gpio-err-fatal = <&smp2pgpio_ssr_smp2p_4_in 0 0>;
+ qcom,gpio-err-ready = <&smp2pgpio_ssr_smp2p_4_in 1 0>;
+ qcom,gpio-proxy-unvote = <&smp2pgpio_ssr_smp2p_4_in 2 0>;
+ qcom,gpio-stop-ack = <&smp2pgpio_ssr_smp2p_4_in 3 0>;
+
+ /* GPIO output to wcnss */
+ qcom,gpio-force-stop = <&smp2pgpio_ssr_smp2p_4_out 0 0>;
+ memory-region = <&wcnss_fw_mem>;
+ };
+
+ qcom,venus@1de0000 {
+ compatible = "qcom,pil-tz-generic";
+ reg = <0x1de0000 0x4000>;
+
+ vdd-supply = <&gdsc_venus>;
+ qcom,proxy-reg-names = "vdd";
+
+ clocks = <&clock_gcc clk_gcc_venus0_vcodec0_clk>,
+ <&clock_gcc clk_gcc_venus0_ahb_clk>,
+ <&clock_gcc clk_gcc_venus0_axi_clk>,
+ <&clock_gcc clk_gcc_crypto_clk>,
+ <&clock_gcc clk_gcc_crypto_ahb_clk>,
+ <&clock_gcc clk_gcc_crypto_axi_clk>,
+ <&clock_gcc clk_crypto_clk_src>;
+
+ clock-names = "core_clk", "iface_clk", "bus_clk",
+ "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+
+ qcom,proxy-clock-names = "core_clk", "iface_clk",
+ "bus_clk", "scm_core_clk",
+ "scm_iface_clk", "scm_bus_clk",
+ "scm_core_clk_src";
+ qcom,scm_core_clk_src-freq = <80000000>;
+
+ qcom,msm-bus,name = "pil-venus";
+ qcom,msm-bus,num-cases = <2>;
+ qcom,msm-bus,num-paths = <1>;
+ qcom,msm-bus,vectors-KBps =
+ <63 512 0 0>,
+ <63 512 0 304000>;
+
+ qcom,mas-crypto = <&mas_crypto>;
+ qcom,pas-id = <9>;
+ qcom,proxy-timeout-ms = <100>;
+ qcom,firmware-name = "venus";
+ memory-region = <&venus_mem>;
+ };
+
qcom_rng: qrng@e3000 {
compatible = "qcom,msm-rng";
reg = <0xe3000 0x1000>;
@@ -1258,6 +1427,7 @@
#include "pm8937-rpm-regulator.dtsi"
#include "msm8917-regulator.dtsi"
#include "pm8937.dtsi"
+#include "msm8917-audio.dtsi"
#include "msm-gdsc-8916.dtsi"
#include "msm8917-thermal.dtsi"
diff --git a/arch/arm64/boot/dts/qcom/msm8937-camera.dtsi b/arch/arm64/boot/dts/qcom/msm8937-camera.dtsi
index b5f467e..831ce61 100644
--- a/arch/arm64/boot/dts/qcom/msm8937-camera.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8937-camera.dtsi
@@ -24,7 +24,7 @@
qcom,csiphy@1b34000 {
status = "ok";
cell-index = <0>;
- compatible = "qcom,csiphy-v3.4.2", "qcom,csiphy";
+ compatible = "qcom,csiphy-v10.00", "qcom,csiphy";
reg = <0x1b34000 0x1000>,
<0x1b00030 0x4>;
reg-names = "csiphy", "csiphy_clk_mux";
@@ -45,7 +45,7 @@
qcom,csiphy@1b35000 {
status = "ok";
cell-index = <1>;
- compatible = "qcom,csiphy-v3.4.2", "qcom,csiphy";
+ compatible = "qcom,csiphy-v10.00", "qcom,csiphy";
reg = <0x1b35000 0x1000>,
<0x1b00038 0x4>;
reg-names = "csiphy", "csiphy_clk_mux";
diff --git a/arch/arm64/boot/dts/qcom/msm8937-coresight.dtsi b/arch/arm64/boot/dts/qcom/msm8937-coresight.dtsi
index f7831c5..b952908 100644
--- a/arch/arm64/boot/dts/qcom/msm8937-coresight.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8937-coresight.dtsi
@@ -1,13 +1,13 @@
/*
- * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
- *
+ * Copyright (c) 2015-2016, 2018, 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 an
+ * 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
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
@@ -28,6 +28,7 @@
qcom,force-reg-dump;
coresight-name = "coresight-tmc-etr";
+ coresight-csr = <&csr>;
coresight-ctis = <&cti0 &cti8>;
clocks = <&clock_gcc clk_qdss_clk>,
@@ -50,6 +51,7 @@
reg-names = "tmc-base";
coresight-name = "coresight-tmc-etf";
+ coresight-csr = <&csr>;
arm,default-sink;
qcom,force-reg-dump;
@@ -1094,6 +1096,10 @@
reg-names = "csr-base";
coresight-name = "coresight-csr";
+ qcom,usb-bam-support;
+ qcom,hwctrl-set-support;
+ qcom,set-byte-cntr-support;
+
qcom,blk-size = <1>;
clocks = <&clock_gcc clk_qdss_clk>,
@@ -1195,6 +1201,7 @@
"usbbam-mux", "blsp-mux";
coresight-name = "coresight-hwevent";
+ coresight-csr = <&csr>;
clocks = <&clock_gcc clk_qdss_clk>,
<&clock_gcc clk_qdss_a_clk>;
diff --git a/arch/arm64/boot/dts/qcom/msm8937-cpu.dtsi b/arch/arm64/boot/dts/qcom/msm8937-cpu.dtsi
index ec92805..05d1e45 100644
--- a/arch/arm64/boot/dts/qcom/msm8937-cpu.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8937-cpu.dtsi
@@ -269,3 +269,83 @@
};
};
};
+
+&soc {
+ cpuss_dump {
+ compatible = "qcom,cpuss-dump";
+ qcom,l2_dump0 {
+ /* L2 cache dump for A53 cluster */
+ qcom,dump-node = <&L2_0>;
+ qcom,dump-id = <0xC0>;
+ };
+ qcom,l2_dump1 {
+ /* L2 cache dump for A53 cluster */
+ qcom,dump-node = <&L2_1>;
+ qcom,dump-id = <0xC1>;
+ };
+ qcom,l1_i_cache0 {
+ qcom,dump-node = <&L1_I_0>;
+ qcom,dump-id = <0x60>;
+ };
+ qcom,l1_i_cache1 {
+ qcom,dump-node = <&L1_I_1>;
+ qcom,dump-id = <0x61>;
+ };
+ qcom,l1_i_cache2 {
+ qcom,dump-node = <&L1_I_2>;
+ qcom,dump-id = <0x62>;
+ };
+ qcom,l1_i_cache3 {
+ qcom,dump-node = <&L1_I_3>;
+ qcom,dump-id = <0x63>;
+ };
+ qcom,l1_i_cache100 {
+ qcom,dump-node = <&L1_I_100>;
+ qcom,dump-id = <0x64>;
+ };
+ qcom,l1_i_cache101 {
+ qcom,dump-node = <&L1_I_101>;
+ qcom,dump-id = <0x65>;
+ };
+ qcom,l1_i_cache102 {
+ qcom,dump-node = <&L1_I_102>;
+ qcom,dump-id = <0x66>;
+ };
+ qcom,l1_i_cache103 {
+ qcom,dump-node = <&L1_I_103>;
+ qcom,dump-id = <0x67>;
+ };
+ qcom,l1_d_cache0 {
+ qcom,dump-node = <&L1_D_0>;
+ qcom,dump-id = <0x80>;
+ };
+ qcom,l1_d_cache1 {
+ qcom,dump-node = <&L1_D_1>;
+ qcom,dump-id = <0x81>;
+ };
+ qcom,l1_d_cache2 {
+ qcom,dump-node = <&L1_D_2>;
+ qcom,dump-id = <0x82>;
+ };
+ qcom,l1_d_cache3 {
+ qcom,dump-node = <&L1_D_3>;
+ qcom,dump-id = <0x83>;
+ };
+ qcom,l1_d_cache100 {
+ qcom,dump-node = <&L1_D_100>;
+ qcom,dump-id = <0x84>;
+ };
+ qcom,l1_d_cache101 {
+ qcom,dump-node = <&L1_D_101>;
+ qcom,dump-id = <0x85>;
+ };
+ qcom,l1_d_cache102 {
+ qcom,dump-node = <&L1_D_102>;
+ qcom,dump-id = <0x86>;
+ };
+ qcom,l1_d_cache103 {
+ qcom,dump-node = <&L1_D_103>;
+ qcom,dump-id = <0x87>;
+ };
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429-cdp.dts b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429-cdp.dts
new file mode 100644
index 0000000..151a12f
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429-cdp.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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 "msm8937-interposer-sdm429.dtsi"
+#include "sdm429-cdp.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8937 Interposer SDM429 CDP";
+ compatible = "qcom,msm8937-cdp", "qcom,msm8937", "qcom,cdp";
+ qcom,board-id = <1 3>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429-mtp.dts b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429-mtp.dts
new file mode 100644
index 0000000..abf38f6
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429-mtp.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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 "msm8937-interposer-sdm429.dtsi"
+#include "sdm429-mtp.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8937 Interposer SDM429 MTP";
+ compatible = "qcom,msm8937-mtp", "qcom,msm8937", "qcom,mtp";
+ qcom,board-id = <8 2>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429.dts b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429.dts
new file mode 100644
index 0000000..ab28966
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429.dts
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2018, 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 "msm8937-interposer-sdm429.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8953 + PMI632 SOC";
+ compatible = "qcom,msm8953";
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+ qcom.pmic-name = "PMI632";
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429.dtsi b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429.dtsi
new file mode 100644
index 0000000..5ae93333
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm429.dtsi
@@ -0,0 +1,58 @@
+/*
+ * Copyright (c) 2018, 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 "msm8937-interposer-sdm439.dtsi"
+#include "sdm429-cpu.dtsi"
+
+&soc {
+ /delete-node/ etm@619c000;
+ /delete-node/ etm@619d000;
+ /delete-node/ etm@619e000;
+ /delete-node/ etm@619f000;
+ /delete-node/ cti@61b8000;
+ /delete-node/ cti@61b9000;
+ /delete-node/ cti@61ba000;
+ /delete-node/ cti@61bb000;
+
+ qcom,spm@b1d2000 {
+ qcom,cpu-vctl-list = <&CPU0 &CPU1 &CPU2 &CPU3>;
+ };
+
+ qcom,lpm-levels {
+ qcom,pm-cluster@0 {
+ /delete-node/qcom,pm-cluster@1;
+ };
+ };
+};
+
+&funnel_apss {
+ ports {
+ /delete-node/ port@1;
+ /delete-node/ port@2;
+ /delete-node/ port@3;
+ /delete-node/ port@4;
+ };
+};
+
+&thermal_zones {
+ hexa-cpu-max-step {
+ cooling-maps {
+ /delete-node/ cpu4_cdev;
+ /delete-node/ cpu5_cdev;
+ /delete-node/ cpu6_cdev;
+ /delete-node/ cpu7_cdev;
+ };
+ };
+
+ /delete-node/ cpuss0-step;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439-qrd.dts b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439-qrd.dts
index 2bad28b..71157e2 100644
--- a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439-qrd.dts
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439-qrd.dts
@@ -22,3 +22,10 @@
qcom,board-id = <0xb 2>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
+
+&pmi632_vadc {
+ chan@4a {
+ qcom,scale-function = <22>;
+ };
+};
+
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dts b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dts
new file mode 100644
index 0000000..33b2c74
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dts
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2018, 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 "msm8937-interposer-sdm439.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. MSM8953 + PMI632 SOC";
+ compatible = "qcom,msm8953";
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+ qcom.pmic-name = "PMI632";
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dtsi b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dtsi
index fbe5ce7..716ef73 100644
--- a/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8937-interposer-sdm439.dtsi
@@ -27,6 +27,12 @@
};
&soc {
+ qcom,csiphy@1b34000 {
+ compatible = "qcom,csiphy-v3.4.2", "qcom,csiphy";
+ };
+ qcom,csiphy@1b35000 {
+ compatible = "qcom,csiphy-v3.4.2", "qcom,csiphy";
+ };
qcom,csid@1b30000 {
qcom,mipi-csi-vdd-supply = <&pm8953_l2>;
};
@@ -168,3 +174,7 @@
vdd-cci-supply = <&apc_vreg_corner>;
};
};
+
+&mdss_dsi {
+ vdda-supply = <&pm8953_l2>;
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8937-mdss-panels.dtsi b/arch/arm64/boot/dts/qcom/msm8937-mdss-panels.dtsi
index bca8912..436b8a7 100644
--- a/arch/arm64/boot/dts/qcom/msm8937-mdss-panels.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8937-mdss-panels.dtsi
@@ -18,6 +18,7 @@
#include "dsi-panel-truly-720p-cmd.dtsi"
#include "dsi-panel-r69006-1080p-cmd.dtsi"
#include "dsi-panel-r69006-1080p-video.dtsi"
+#include "dsi-panel-hx8394f-720p-video.dtsi"
#include "dsi-adv7533-1080p.dtsi"
#include "dsi-adv7533-720p.dtsi"
#include "dsi-panel-hx8399c-fhd-plus-video.dtsi"
diff --git a/arch/arm64/boot/dts/qcom/msm8937.dtsi b/arch/arm64/boot/dts/qcom/msm8937.dtsi
index 8f769fe..632c924 100644
--- a/arch/arm64/boot/dts/qcom/msm8937.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8937.dtsi
@@ -53,7 +53,7 @@
};
};
- reserved-memory {
+ reserved_memory: reserved-memory {
#address-cells = <2>;
#size-cells = <2>;
ranges;
diff --git a/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-cdp.dtsi b/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-cdp.dtsi
index db9fb13..6e961b1 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-cdp.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-cdp.dtsi
@@ -45,8 +45,8 @@
cam_vdig-supply = <&pm8953_l2>;
cam_vaf-supply = <&pm8953_l17>;
qcom,cam-vreg-name = "cam_vio", "cam_vdig", "cam_vaf";
- qcom,cam-vreg-min-voltage = <0 1100000 2850000>;
- qcom,cam-vreg-max-voltage = <0 1100000 2850000>;
+ qcom,cam-vreg-min-voltage = <0 1200000 2850000>;
+ qcom,cam-vreg-max-voltage = <0 1200000 2850000>;
qcom,cam-vreg-op-mode = <0 105000 100000>;
pinctrl-names = "cam_default", "cam_suspend";
pinctrl-0 = <&cam_sensor_mclk0_default
@@ -207,8 +207,8 @@
cam_v_custom1-supply = <&pm8953_l23>;
qcom,cam-vreg-name = "cam_vio", "cam_vdig", "cam_vaf",
"cam_vana", "cam_v_custom1";
- qcom,cam-vreg-min-voltage = <0 1100000 2850000 2800000 1220000>;
- qcom,cam-vreg-max-voltage = <0 1100000 2850000 2800000 1220000>;
+ qcom,cam-vreg-min-voltage = <0 1200000 2850000 2800000 1220000>;
+ qcom,cam-vreg-max-voltage = <0 1200000 2850000 2800000 1220000>;
qcom,cam-vreg-op-mode = <0 105000 100000 80000 105000>;
pinctrl-names = "cam_default", "cam_suspend";
pinctrl-0 = <&cam_sensor_mclk0_default
@@ -297,8 +297,8 @@
cam_vaf-supply = <&pm8953_l17>;
qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana",
"cam_vaf";
- qcom,cam-vreg-min-voltage = <1175000 0 2800000 2850000>;
- qcom,cam-vreg-max-voltage = <1175000 0 2800000 2850000>;
+ qcom,cam-vreg-min-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-max-voltage = <1200000 0 2800000 2850000>;
qcom,cam-vreg-op-mode = <105000 0 80000 100000>;
qcom,gpio-no-mux = <0>;
pinctrl-names = "cam_default", "cam_suspend";
diff --git a/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-mtp.dtsi b/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-mtp.dtsi
index db9fb13..6e961b1 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-mtp.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-mtp.dtsi
@@ -45,8 +45,8 @@
cam_vdig-supply = <&pm8953_l2>;
cam_vaf-supply = <&pm8953_l17>;
qcom,cam-vreg-name = "cam_vio", "cam_vdig", "cam_vaf";
- qcom,cam-vreg-min-voltage = <0 1100000 2850000>;
- qcom,cam-vreg-max-voltage = <0 1100000 2850000>;
+ qcom,cam-vreg-min-voltage = <0 1200000 2850000>;
+ qcom,cam-vreg-max-voltage = <0 1200000 2850000>;
qcom,cam-vreg-op-mode = <0 105000 100000>;
pinctrl-names = "cam_default", "cam_suspend";
pinctrl-0 = <&cam_sensor_mclk0_default
@@ -207,8 +207,8 @@
cam_v_custom1-supply = <&pm8953_l23>;
qcom,cam-vreg-name = "cam_vio", "cam_vdig", "cam_vaf",
"cam_vana", "cam_v_custom1";
- qcom,cam-vreg-min-voltage = <0 1100000 2850000 2800000 1220000>;
- qcom,cam-vreg-max-voltage = <0 1100000 2850000 2800000 1220000>;
+ qcom,cam-vreg-min-voltage = <0 1200000 2850000 2800000 1220000>;
+ qcom,cam-vreg-max-voltage = <0 1200000 2850000 2800000 1220000>;
qcom,cam-vreg-op-mode = <0 105000 100000 80000 105000>;
pinctrl-names = "cam_default", "cam_suspend";
pinctrl-0 = <&cam_sensor_mclk0_default
@@ -297,8 +297,8 @@
cam_vaf-supply = <&pm8953_l17>;
qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana",
"cam_vaf";
- qcom,cam-vreg-min-voltage = <1175000 0 2800000 2850000>;
- qcom,cam-vreg-max-voltage = <1175000 0 2800000 2850000>;
+ qcom,cam-vreg-min-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-max-voltage = <1200000 0 2800000 2850000>;
qcom,cam-vreg-op-mode = <105000 0 80000 100000>;
qcom,gpio-no-mux = <0>;
pinctrl-names = "cam_default", "cam_suspend";
diff --git a/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-qrd.dtsi b/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-qrd.dtsi
index 8098efb..adaaec6 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-qrd.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-camera-sensor-qrd.dtsi
@@ -33,8 +33,8 @@
cam_vdig-supply = <&pm8953_l23>;
cam_vaf-supply = <&pm8953_l17>;
qcom,cam-vreg-name = "cam_vio", "cam_vdig", "cam_vaf";
- qcom,cam-vreg-min-voltage = <0 1100000 2850000>;
- qcom,cam-vreg-max-voltage = <0 1100000 2850000>;
+ qcom,cam-vreg-min-voltage = <0 1200000 2850000>;
+ qcom,cam-vreg-max-voltage = <0 1200000 2850000>;
qcom,cam-vreg-op-mode = <0 105000 100000>;
pinctrl-names = "cam_default", "cam_suspend";
pinctrl-0 = <&cam_sensor_mclk0_default
@@ -113,8 +113,8 @@
cam_vana-supply = <&pm8953_l22>;
qcom,cam-vreg-name = "cam_vio", "cam_vdig", "cam_vaf",
"cam_vana";
- qcom,cam-vreg-min-voltage = <0 1100000 2850000 2800000>;
- qcom,cam-vreg-max-voltage = <0 1100000 2850000 2800000>;
+ qcom,cam-vreg-min-voltage = <0 1200000 2850000 2800000>;
+ qcom,cam-vreg-max-voltage = <0 1200000 2850000 2800000>;
qcom,cam-vreg-op-mode = <0 105000 100000 80000>;
pinctrl-names = "cam_default", "cam_suspend";
pinctrl-0 = <&cam_sensor_mclk0_default
diff --git a/arch/arm64/boot/dts/qcom/msm8953-cdp.dtsi b/arch/arm64/boot/dts/qcom/msm8953-cdp.dtsi
index 8782325..9b78253 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-cdp.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-cdp.dtsi
@@ -42,6 +42,7 @@
qcom,nq-ven = <&tlmm 16 0x00>;
qcom,nq-firm = <&tlmm 62 0x00>;
qcom,nq-clkreq = <&pm8953_gpios 2 0x00>;
+ qcom,nq-esepwr = <&tlmm 141 0x00>;
interrupt-parent = <&tlmm>;
qcom,clk-src = "BBCLK2";
interrupts = <17 0>;
diff --git a/arch/arm64/boot/dts/qcom/msm8953-mdss-panels.dtsi b/arch/arm64/boot/dts/qcom/msm8953-mdss-panels.dtsi
index c6bc2b9..f7671dc 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-mdss-panels.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-mdss-panels.dtsi
@@ -24,6 +24,7 @@
#include "dsi-panel-lt8912-480p-video.dtsi"
#include "dsi-panel-lt8912-1080p-video.dtsi"
#include "dsi-panel-hx8399c-fhd-plus-video.dtsi"
+#include "dsi-panel-hx83100a-800p-video.dtsi"
&soc {
dsi_panel_pwr_supply: dsi_panel_pwr_supply {
@@ -118,7 +119,7 @@
qcom,mdss-dsi-panel-on-check-value = <0x9d 0x9d 0x9d 0x9d>;
qcom,mdss-dsi-panel-status-read-length = <4>;
qcom,mdss-dsi-panel-max-error-count = <3>;
- qcom,mdss-dsi-min-refresh-rate = <55>;
+ qcom,mdss-dsi-min-refresh-rate = <48>;
qcom,mdss-dsi-max-refresh-rate = <60>;
qcom,mdss-dsi-pan-enable-dynamic-fps;
qcom,mdss-dsi-pan-fps-update =
@@ -148,3 +149,11 @@
24 1f 08 09 05 03 04 a0
24 1c 08 09 05 03 04 a0];
};
+
+&dsi_boyi_hx83100a_800p_video {
+ qcom,mdss-dsi-panel-timings-phy-v2 = [1f 1c 05 06 03 03 04 a0
+ 1f 1c 05 06 03 03 04 a0
+ 1f 1c 05 06 03 03 04 a0
+ 1f 1c 05 06 03 03 04 a0
+ 1f 10 05 06 03 03 04 a0];
+};
diff --git a/arch/arm64/boot/dts/qcom/msm8953-mtp.dtsi b/arch/arm64/boot/dts/qcom/msm8953-mtp.dtsi
index a3bd5e9..cc4bc7f 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-mtp.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-mtp.dtsi
@@ -41,6 +41,7 @@
qcom,nq-ven = <&tlmm 16 0x00>;
qcom,nq-firm = <&tlmm 62 0x00>;
qcom,nq-clkreq = <&pm8953_gpios 2 0x00>;
+ qcom,nq-esepwr = <&tlmm 141 0x00>;
interrupt-parent = <&tlmm>;
qcom,clk-src = "BBCLK2";
interrupts = <17 0>;
@@ -208,4 +209,8 @@
case-therm-step {
status = "disabled";
};
+
+ quiet-therm-step {
+ status = "disabled";
+ };
};
diff --git a/arch/arm64/boot/dts/qcom/msm8953-pinctrl.dtsi b/arch/arm64/boot/dts/qcom/msm8953-pinctrl.dtsi
index 15be898..7d73a69 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-pinctrl.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-pinctrl.dtsi
@@ -425,6 +425,19 @@
bias-pull-down; /* pull down */
};
};
+ mdss_dsi_gpio: mdss_dsi_gpio {
+ mux {
+ pins = "gpio141";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio141";
+ drive-strength = <8>;
+ bias-pull-down;
+ output-low;
+ };
+ };
};
pmx_mdss_te {
@@ -733,39 +746,67 @@
};
};
- pmx_rd_nfc_int {
- /*qcom,pins = <&gp 17>;*/
- pins = "gpio17";
- qcom,pin-func = <0>;
- qcom,num-grp-pins = <1>;
- label = "pmx_nfc_int";
+ nfc {
+ nfc_int_active: nfc_int_active {
+ /* active state */
+ mux {
+ /* GPIO 17 NFC Read Interrupt */
+ pins = "gpio17";
+ function = "gpio";
+ };
- nfc_int_active: active {
- drive-strength = <6>;
- bias-pull-up;
+ config {
+ pins = "gpio17";
+ drive-strength = <2>; /* 2 MA */
+ bias-pull-up;
+ };
};
- nfc_int_suspend: suspend {
- drive-strength = <6>;
- bias-pull-up;
- };
- };
+ nfc_int_suspend: nfc_int_suspend {
+ /* sleep state */
+ mux {
+ /* GPIO 17 NFC Read Interrupt */
+ pins = "gpio17";
+ function = "gpio";
+ };
- pmx_nfc_reset {
- /*qcom,pins = <&gp 16>;*/
- pins = "gpio16";
- qcom,pin-func = <0>;
- qcom,num-grp-pins = <1>;
- label = "pmx_nfc_disable";
-
- nfc_disable_active: active {
- drive-strength = <6>;
- bias-pull-up;
+ config {
+ pins = "gpio17";
+ drive-strength = <2>; /* 2 MA */
+ bias-pull-up;
+ };
};
- nfc_disable_suspend: suspend {
- drive-strength = <6>;
- bias-disable;
+ nfc_disable_active: nfc_disable_active {
+ /* active state */
+ mux {
+ /* 16: NFC ENABLE 62: FW DNLD */
+ /* 141: ESE Enable */
+ pins = "gpio16", "gpio62", "gpio141";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio16", "gpio62", "gpio141";
+ drive-strength = <2>; /* 2 MA */
+ bias-pull-up;
+ };
+ };
+
+ nfc_disable_suspend: nfc_disable_suspend {
+ /* sleep state */
+ mux {
+ /* 16: NFC ENABLE 62: FW DNLD */
+ /* 141: ESE Enable */
+ pins = "gpio16", "gpio62", "gpio141";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio16", "gpio62", "gpio141";
+ drive-strength = <2>; /* 2 MA */
+ bias-disable;
+ };
};
};
diff --git a/arch/arm64/boot/dts/qcom/msm8953-qrd.dtsi b/arch/arm64/boot/dts/qcom/msm8953-qrd.dtsi
index 253e87e..1f0ad88 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-qrd.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-qrd.dtsi
@@ -69,6 +69,7 @@
qcom,nq-ven = <&tlmm 16 0x00>;
qcom,nq-firm = <&tlmm 62 0x00>;
qcom,nq-clkreq = <&pm8953_gpios 2 0x00>;
+ qcom,nq-esepwr = <&tlmm 141 0x00>;
interrupt-parent = <&tlmm>;
qcom,clk-src = "BBCLK2";
interrupts = <17 0>;
diff --git a/arch/arm64/boot/dts/qcom/msm8953-thermal.dtsi b/arch/arm64/boot/dts/qcom/msm8953-thermal.dtsi
index 54634ce..d84898d 100644
--- a/arch/arm64/boot/dts/qcom/msm8953-thermal.dtsi
+++ b/arch/arm64/boot/dts/qcom/msm8953-thermal.dtsi
@@ -360,7 +360,7 @@
thermal-governor = "step_wise";
trips {
pop_trip: pop-trip {
- temperature = <70000>;
+ temperature = <95000>;
hysteresis = <0>;
type = "passive";
};
diff --git a/arch/arm64/boot/dts/qcom/pmi632.dtsi b/arch/arm64/boot/dts/qcom/pmi632.dtsi
index bdd69e2..8bb9dbe 100644
--- a/arch/arm64/boot/dts/qcom/pmi632.dtsi
+++ b/arch/arm64/boot/dts/qcom/pmi632.dtsi
@@ -225,6 +225,33 @@
};
};
+ pmi632_adc_tm: vadc@3500 {
+ compatible = "qcom,qpnp-adc-tm-hc";
+ reg = <0x3500 0x100>;
+ #address-cells = <1>;
+ #size-cells = <0>;
+ interrupts = <0x2 0x35 0x0 IRQ_TYPE_EDGE_RISING>;
+ interrupt-names = "eoc-int-en-set";
+ qcom,adc-vdd-reference = <1875>;
+ qcom,adc-full-scale-code = <0x70e4>;
+ qcom,adc_tm-vadc = <&pmi632_vadc>;
+ qcom,decimation = <0>;
+ qcom,fast-avg-setup = <0>;
+ #thermal-sensor-cells = <1>;
+
+ chan@53 {
+ label = "quiet_therm";
+ reg = <0x53>;
+ qcom,pre-div-channel-scaling = <0>;
+ qcom,calibration-type = "ratiometric";
+ qcom,scale-function = <2>;
+ qcom,hw-settle-time = <0>;
+ qcom,btm-channel-number = <0x60>;
+ qcom,thermal-node;
+ };
+
+ };
+
pmi632_tz: qcom,temp-alarm@2400 {
compatible = "qcom,qpnp-temp-alarm";
reg = <0x2400 0x100>;
@@ -657,14 +684,14 @@
&thermal_zones {
pmi-ibat-lvl0 {
- polling-delay-passive = <0>;
+ polling-delay-passive = <100>;
polling-delay = <0>;
thermal-governor = "step_wise";
thermal-sensors = <&bcl_sensor 0>;
trips {
- pmi632_ibat:ibat-lvl0 {
- temperature = <3500>;
+ pmi632_ibat_lvl0: ibat-lvl0 {
+ temperature = <4000>;
hysteresis = <200>;
type = "passive";
};
@@ -679,7 +706,7 @@
trips {
ibat-lvl1 {
- temperature = <4000>;
+ temperature = <4200>;
hysteresis = <200>;
type = "passive";
};
diff --git a/arch/arm64/boot/dts/qcom/qcs605-360camera.dtsi b/arch/arm64/boot/dts/qcom/qcs605-360camera.dtsi
index aa316ba..63bb25f 100644
--- a/arch/arm64/boot/dts/qcom/qcs605-360camera.dtsi
+++ b/arch/arm64/boot/dts/qcom/qcs605-360camera.dtsi
@@ -166,6 +166,10 @@
qcom,battery-data = <&qcs_batterydata>;
};
+&pm660_charger {
+ qcom,battery-data = <&qcs_batterydata>;
+};
+
&int_codec {
qcom,model = "sdm670-360cam-snd-card";
qcom,audio-routing =
diff --git a/arch/arm64/boot/dts/qcom/qg-batterydata-ascent-3450mah.dtsi b/arch/arm64/boot/dts/qcom/qg-batterydata-ascent-3450mah.dtsi
index 4d35628..8af4254 100644
--- a/arch/arm64/boot/dts/qcom/qg-batterydata-ascent-3450mah.dtsi
+++ b/arch/arm64/boot/dts/qcom/qg-batterydata-ascent-3450mah.dtsi
@@ -38,8 +38,8 @@
};
qcom,fcc2-temp-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-data = <3474 3480 3482 3476 3492 3478 3466>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-data = <3480 3482 3476 3492 3478 3466>;
};
qcom,pc-temp-v1-lut {
@@ -115,71 +115,73 @@
};
qcom,pc-temp-v2-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <43435 43425 43415 43385 43360 43315 43295>,
- <43032 43070 43109 43097 43094 43052 43033>,
- <42666 42748 42821 42826 42838 42799 42781>,
- <42342 42462 42555 42571 42594 42557 42541>,
- <42053 42208 42308 42333 42361 42326 42312>,
- <41788 41968 42072 42101 42133 42099 42086>,
- <41531 41736 41844 41872 41904 41872 41860>,
- <41298 41516 41625 41649 41680 41649 41637>,
- <41128 41303 41405 41431 41460 41430 41419>,
- <41009 41100 41186 41217 41243 41215 41204>,
- <40843 40896 40979 41012 41034 41005 40994>,
- <40462 40694 40796 40826 40840 40802 40789>,
- <40004 40482 40616 40642 40648 40604 40590>,
- <39736 40220 40407 40432 40445 40411 40399>,
- <39556 39903 40175 40199 40233 40222 40214>,
- <39382 39636 39954 39996 40043 40042 40036>,
- <39187 39443 39759 39844 39886 39877 39868>,
- <39001 39272 39570 39700 39736 39717 39706>,
- <38839 39091 39370 39511 39573 39556 39547>,
- <38695 38908 39162 39283 39399 39396 39391>,
- <38574 38742 38973 39072 39208 39217 39217>,
- <38477 38591 38806 38886 38975 38988 38994>,
- <38393 38460 38655 38721 38760 38766 38771>,
- <38314 38358 38519 38585 38613 38613 38614>,
- <38242 38274 38396 38468 38496 38494 38494>,
- <38176 38201 38287 38362 38390 38388 38387>,
- <38117 38138 38189 38265 38294 38291 38288>,
- <38062 38080 38106 38177 38206 38202 38198>,
- <38006 38027 38039 38096 38126 38120 38114>,
- <37953 37980 37983 38021 38051 38044 38037>,
- <37900 37934 37935 37954 37984 37976 37967>,
- <37847 37889 37895 37891 37921 37915 37905>,
- <37795 37843 37856 37838 37862 37856 37846>,
- <37742 37795 37815 37799 37803 37790 37781>,
- <37690 37746 37774 37768 37746 37720 37707>,
- <37635 37692 37727 37728 37685 37643 37621>,
- <37574 37633 37677 37677 37620 37554 37517>,
- <37509 37568 37618 37617 37550 37465 37411>,
- <37441 37491 37546 37548 37475 37387 37327>,
- <37368 37404 37459 37466 37395 37313 37256>,
- <37292 37310 37360 37369 37301 37226 37174>,
- <37209 37206 37243 37246 37187 37117 37069>,
- <37119 37103 37111 37106 37050 36988 36945>,
- <37020 37005 36964 36946 36900 36839 36796>,
- <36901 36909 36860 36837 36818 36761 36712>,
- <36762 36808 36782 36769 36775 36718 36673>,
- <36671 36746 36740 36732 36741 36690 36651>,
- <36552 36670 36688 36684 36692 36649 36612>,
- <36386 36553 36594 36591 36575 36542 36528>,
- <36157 36329 36380 36368 36272 36271 36278>,
- <35824 35961 35991 35957 35796 35833 35867>,
- <35340 35436 35452 35401 35193 35271 35340>,
- <34648 34709 34745 34680 34409 34550 34676>,
- <33623 33672 33759 33677 33330 33585 33791>,
- <31758 31857 32191 32244 31867 32001 32517>,
- <27623 28160 28896 29014 27510 28586 29617>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <43425 43415 43385 43360 43315 43295>,
+ <43070 43109 43097 43094 43052 43033>,
+ <42748 42821 42826 42838 42799 42781>,
+ <42462 42555 42571 42594 42557 42541>,
+ <42208 42308 42333 42361 42326 42312>,
+ <41968 42072 42101 42133 42099 42086>,
+ <41736 41844 41872 41904 41872 41860>,
+ <41516 41625 41649 41680 41649 41637>,
+ <41303 41405 41431 41460 41430 41419>,
+ <41100 41186 41217 41243 41215 41204>,
+ <40896 40979 41012 41034 41005 40994>,
+ <40694 40796 40826 40840 40802 40789>,
+ <40482 40616 40642 40648 40604 40590>,
+ <40220 40407 40432 40445 40411 40399>,
+ <39903 40175 40199 40233 40222 40214>,
+ <39636 39954 39996 40043 40042 40036>,
+ <39443 39759 39844 39886 39877 39868>,
+ <39272 39570 39700 39736 39717 39706>,
+ <39091 39370 39511 39573 39556 39547>,
+ <38908 39162 39283 39399 39396 39391>,
+ <38742 38973 39072 39208 39217 39217>,
+ <38591 38806 38886 38975 38988 38994>,
+ <38460 38655 38721 38760 38766 38771>,
+ <38358 38519 38585 38613 38613 38614>,
+ <38274 38396 38468 38496 38494 38494>,
+ <38201 38287 38362 38390 38388 38387>,
+ <38138 38189 38265 38294 38291 38288>,
+ <38080 38106 38177 38206 38202 38198>,
+ <38027 38039 38096 38126 38120 38114>,
+ <37980 37983 38021 38051 38044 38037>,
+ <37934 37935 37954 37984 37976 37967>,
+ <37889 37895 37891 37921 37915 37905>,
+ <37843 37856 37838 37862 37856 37846>,
+ <37795 37815 37799 37803 37790 37781>,
+ <37746 37774 37768 37746 37720 37707>,
+ <37692 37727 37728 37685 37643 37621>,
+ <37633 37677 37677 37620 37554 37517>,
+ <37568 37618 37617 37550 37465 37411>,
+ <37491 37546 37548 37475 37387 37327>,
+ <37404 37459 37466 37395 37313 37256>,
+ <37310 37360 37369 37301 37226 37174>,
+ <37206 37243 37246 37187 37117 37069>,
+ <37103 37111 37106 37050 36988 36945>,
+ <37005 36964 36946 36900 36839 36796>,
+ <36909 36860 36837 36818 36761 36712>,
+ <36808 36782 36769 36775 36718 36673>,
+ <36746 36740 36732 36741 36690 36651>,
+ <36670 36688 36684 36692 36649 36612>,
+ <36553 36594 36591 36575 36542 36528>,
+ <36329 36380 36368 36272 36271 36278>,
+ <35961 35991 35957 35796 35833 35867>,
+ <35436 35452 35401 35193 35271 35340>,
+ <34709 34745 34680 34409 34550 34676>,
+ <33672 33759 33677 33330 33585 33791>,
+ <31857 32191 32244 31867 32001 32517>,
+ <28160 28896 29014 27510 28586 29617>;
};
qcom,pc-temp-z1-lut {
@@ -615,410 +617,422 @@
};
qcom,pc-temp-y1-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <7619 6963 6363 6007 5630 5512 5470>,
- <7591 6945 6361 6003 5629 5510 5471>,
- <7573 6934 6357 5999 5628 5508 5471>,
- <7563 6929 6354 5995 5627 5506 5471>,
- <7558 6928 6353 5992 5626 5505 5470>,
- <7556 6928 6357 5988 5625 5503 5470>,
- <7563 6934 6366 5985 5624 5502 5469>,
- <7573 6942 6374 5981 5624 5501 5467>,
- <7583 6939 6374 5982 5623 5500 5467>,
- <7616 6920 6366 5984 5624 5499 5467>,
- <7634 6910 6360 5985 5624 5498 5466>,
- <7600 6919 6357 5980 5623 5498 5466>,
- <7557 6931 6356 5973 5622 5498 5465>,
- <7560 6935 6362 5973 5622 5499 5465>,
- <7590 6938 6380 5978 5625 5500 5466>,
- <7605 6939 6390 5981 5628 5501 5467>,
- <7608 6942 6389 5985 5631 5501 5468>,
- <7612 6946 6387 5990 5634 5502 5469>,
- <7604 6943 6388 5989 5637 5503 5470>,
- <7584 6932 6391 5988 5639 5506 5471>,
- <7570 6929 6394 5987 5643 5508 5472>,
- <7557 6957 6397 5989 5647 5510 5473>,
- <7546 6985 6400 5994 5653 5513 5475>,
- <7543 6976 6405 6001 5658 5515 5478>,
- <7542 6942 6414 6012 5663 5518 5480>,
- <7542 6928 6418 6018 5668 5522 5483>,
- <7552 6934 6419 6019 5674 5525 5486>,
- <7565 6942 6418 6020 5681 5529 5488>,
- <7569 6951 6418 6021 5687 5533 5491>,
- <7568 6972 6418 6023 5692 5537 5493>,
- <7564 6978 6418 6025 5698 5541 5497>,
- <7549 6971 6422 6028 5705 5545 5500>,
- <7534 6961 6425 6032 5712 5550 5504>,
- <7531 6947 6422 6038 5720 5554 5507>,
- <7529 6929 6416 6048 5727 5559 5509>,
- <7527 6925 6416 6055 5734 5563 5512>,
- <7537 6932 6428 6059 5741 5569 5516>,
- <7548 6939 6438 6062 5748 5575 5522>,
- <7546 6939 6433 6063 5757 5580 5526>,
- <7534 6942 6422 6064 5767 5585 5529>,
- <7527 6944 6417 6067 5775 5591 5533>,
- <7526 6946 6416 6077 5783 5596 5537>,
- <7530 6941 6418 6083 5787 5603 5541>,
- <7568 6923 6429 6090 5790 5610 5546>,
- <7559 6953 6428 6086 5808 5622 5555>,
- <7568 6932 6433 6091 5813 5631 5561>,
- <7570 6928 6433 6099 5818 5635 5565>,
- <7608 6933 6442 6113 5834 5640 5567>,
- <7652 6932 6430 6105 5835 5645 5571>,
- <7693 6936 6436 6106 5848 5654 5578>,
- <7737 6965 6440 6099 5858 5666 5585>,
- <7770 6990 6464 6110 5873 5684 5600>,
- <7830 7027 6445 6123 5887 5704 5613>,
- <7848 7064 6471 6136 5914 5726 5633>,
- <7848 7064 6471 6136 5914 5726 5633>,
- <7848 7064 6471 6136 5914 5726 5633>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <6963 6363 6007 5630 5512 5470>,
+ <6945 6361 6003 5629 5510 5471>,
+ <6934 6357 5999 5628 5508 5471>,
+ <6929 6354 5995 5627 5506 5471>,
+ <6928 6353 5992 5626 5505 5470>,
+ <6928 6357 5988 5625 5503 5470>,
+ <6934 6366 5985 5624 5502 5469>,
+ <6942 6374 5981 5624 5501 5467>,
+ <6939 6374 5982 5623 5500 5467>,
+ <6920 6366 5984 5624 5499 5467>,
+ <6910 6360 5985 5624 5498 5466>,
+ <6919 6357 5980 5623 5498 5466>,
+ <6931 6356 5973 5622 5498 5465>,
+ <6935 6362 5973 5622 5499 5465>,
+ <6938 6380 5978 5625 5500 5466>,
+ <6939 6390 5981 5628 5501 5467>,
+ <6942 6389 5985 5631 5501 5468>,
+ <6946 6387 5990 5634 5502 5469>,
+ <6943 6388 5989 5637 5503 5470>,
+ <6932 6391 5988 5639 5506 5471>,
+ <6929 6394 5987 5643 5508 5472>,
+ <6957 6397 5989 5647 5510 5473>,
+ <6985 6400 5994 5653 5513 5475>,
+ <6976 6405 6001 5658 5515 5478>,
+ <6942 6414 6012 5663 5518 5480>,
+ <6928 6418 6018 5668 5522 5483>,
+ <6934 6419 6019 5674 5525 5486>,
+ <6942 6418 6020 5681 5529 5488>,
+ <6951 6418 6021 5687 5533 5491>,
+ <6972 6418 6023 5692 5537 5493>,
+ <6978 6418 6025 5698 5541 5497>,
+ <6971 6422 6028 5705 5545 5500>,
+ <6961 6425 6032 5712 5550 5504>,
+ <6947 6422 6038 5720 5554 5507>,
+ <6929 6416 6048 5727 5559 5509>,
+ <6925 6416 6055 5734 5563 5512>,
+ <6932 6428 6059 5741 5569 5516>,
+ <6939 6438 6062 5748 5575 5522>,
+ <6939 6433 6063 5757 5580 5526>,
+ <6942 6422 6064 5767 5585 5529>,
+ <6944 6417 6067 5775 5591 5533>,
+ <6946 6416 6077 5783 5596 5537>,
+ <6941 6418 6083 5787 5603 5541>,
+ <6923 6429 6090 5790 5610 5546>,
+ <6953 6428 6086 5808 5622 5555>,
+ <6932 6433 6091 5813 5631 5561>,
+ <6928 6433 6099 5818 5635 5565>,
+ <6933 6442 6113 5834 5640 5567>,
+ <6932 6430 6105 5835 5645 5571>,
+ <6936 6436 6106 5848 5654 5578>,
+ <6965 6440 6099 5858 5666 5585>,
+ <6990 6464 6110 5873 5684 5600>,
+ <7027 6445 6123 5887 5704 5613>,
+ <7064 6471 6136 5914 5726 5633>,
+ <7064 6471 6136 5914 5726 5633>,
+ <7064 6471 6136 5914 5726 5633>;
};
qcom,pc-temp-y2-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <9652 9643 10780 11037 11216 11097 11009>,
- <9653 9653 10747 10993 11177 11076 11016>,
- <9654 9867 10710 10945 11129 11053 11018>,
- <9655 10082 10673 10898 11080 11031 11018>,
- <9655 10246 10642 10860 11037 11010 11015>,
- <9655 10308 10624 10837 11007 10992 11010>,
- <9655 10281 10616 10826 10987 10977 10981>,
- <9655 10241 10610 10820 10968 10962 10937>,
- <9655 10275 10600 10816 10953 10942 10920>,
- <9655 10440 10586 10802 10939 10913 10908>,
- <9655 10531 10580 10792 10927 10894 10901>,
- <9654 10522 10610 10786 10915 10881 10897>,
- <9654 10502 10665 10780 10900 10869 10890>,
- <9653 10430 10721 10797 10878 10869 10877>,
- <9653 10226 10789 10873 10846 10876 10849>,
- <9653 10115 10817 10940 10834 10878 10831>,
- <9653 9949 10805 10988 10876 10871 10840>,
- <9653 9749 10791 11021 10939 10863 10860>,
- <9653 9704 10791 11014 10991 10869 10866>,
- <9653 9683 10795 10979 11041 10898 10870>,
- <9653 9677 10801 10965 11063 10936 10877>,
- <9653 9676 10808 10997 11078 11004 10940>,
- <9653 9676 10820 11042 11093 11066 11026>,
- <9652 9674 10836 11062 11099 11074 11055>,
- <9652 9670 10861 11077 11105 11063 11066>,
- <9652 9667 10915 11082 11111 11064 11068>,
- <9652 9665 11341 11085 11126 11092 11072>,
- <9652 9663 11748 11091 11149 11125 11083>,
- <9652 9661 11516 11099 11179 11148 11096>,
- <9652 9659 10816 11110 11217 11174 11118>,
- <9652 9658 10376 11118 11236 11190 11131>,
- <9652 9657 10155 11117 11245 11208 11140>,
- <9652 9656 10000 11109 11252 11224 11152>,
- <9652 9655 9892 11094 11259 11233 11175>,
- <9652 9654 9812 11060 11260 11250 11208>,
- <9652 9654 9762 11020 11250 11255 11218>,
- <9652 9653 9725 10915 11227 11244 11186>,
- <9652 9653 9701 10784 11207 11227 11146>,
- <9652 9653 9688 10695 11192 11211 11135>,
- <9651 9652 9678 10615 11172 11194 11131>,
- <9651 9652 9671 10480 11143 11192 11126>,
- <9651 9652 9665 10201 11106 11216 11112>,
- <9651 9651 9661 10108 11076 11220 11105>,
- <9651 9651 9658 10159 11042 11183 11120>,
- <9650 9651 9656 9965 10929 11157 11073>,
- <9650 9651 9654 9856 10889 11090 11023>,
- <9650 9651 9653 9796 10823 11057 10968>,
- <9649 9650 9653 9741 10794 11051 10955>,
- <9649 9650 9652 9696 10740 11029 10918>,
- <9649 9650 9652 9680 10652 10968 10907>,
- <9648 9650 9651 9670 10540 10916 10868>,
- <9648 9649 9651 9663 10397 10801 10776>,
- <9647 9648 9650 9657 10262 10712 10696>,
- <9647 9648 9650 9654 10448 10584 10596>,
- <9647 9648 9650 9654 10448 10584 10596>,
- <9647 9648 9650 9654 10448 10584 10596>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <9643 10780 11037 11216 11097 11009>,
+ <9653 10747 10993 11177 11076 11016>,
+ <9867 10710 10945 11129 11053 11018>,
+ <10082 10673 10898 11080 11031 11018>,
+ <10246 10642 10860 11037 11010 11015>,
+ <10308 10624 10837 11007 10992 11010>,
+ <10281 10616 10826 10987 10977 10981>,
+ <10241 10610 10820 10968 10962 10937>,
+ <10275 10600 10816 10953 10942 10920>,
+ <10440 10586 10802 10939 10913 10908>,
+ <10531 10580 10792 10927 10894 10901>,
+ <10522 10610 10786 10915 10881 10897>,
+ <10502 10665 10780 10900 10869 10890>,
+ <10430 10721 10797 10878 10869 10877>,
+ <10226 10789 10873 10846 10876 10849>,
+ <10115 10817 10940 10834 10878 10831>,
+ <9949 10805 10988 10876 10871 10840>,
+ <9749 10791 11021 10939 10863 10860>,
+ <9704 10791 11014 10991 10869 10866>,
+ <9683 10795 10979 11041 10898 10870>,
+ <9677 10801 10965 11063 10936 10877>,
+ <9676 10808 10997 11078 11004 10940>,
+ <9676 10820 11042 11093 11066 11026>,
+ <9674 10836 11062 11099 11074 11055>,
+ <9670 10861 11077 11105 11063 11066>,
+ <9667 10915 11082 11111 11064 11068>,
+ <9665 11341 11085 11126 11092 11072>,
+ <9663 11748 11091 11149 11125 11083>,
+ <9661 11516 11099 11179 11148 11096>,
+ <9659 10816 11110 11217 11174 11118>,
+ <9658 10376 11118 11236 11190 11131>,
+ <9657 10155 11117 11245 11208 11140>,
+ <9656 10000 11109 11252 11224 11152>,
+ <9655 9892 11094 11259 11233 11175>,
+ <9654 9812 11060 11260 11250 11208>,
+ <9654 9762 11020 11250 11255 11218>,
+ <9653 9725 10915 11227 11244 11186>,
+ <9653 9701 10784 11207 11227 11146>,
+ <9653 9688 10695 11192 11211 11135>,
+ <9652 9678 10615 11172 11194 11131>,
+ <9652 9671 10480 11143 11192 11126>,
+ <9652 9665 10201 11106 11216 11112>,
+ <9651 9661 10108 11076 11220 11105>,
+ <9651 9658 10159 11042 11183 11120>,
+ <9651 9656 9965 10929 11157 11073>,
+ <9651 9654 9856 10889 11090 11023>,
+ <9651 9653 9796 10823 11057 10968>,
+ <9650 9653 9741 10794 11051 10955>,
+ <9650 9652 9696 10740 11029 10918>,
+ <9650 9652 9680 10652 10968 10907>,
+ <9650 9651 9670 10540 10916 10868>,
+ <9649 9651 9663 10397 10801 10776>,
+ <9648 9650 9657 10262 10712 10696>,
+ <9648 9650 9654 10448 10584 10596>,
+ <9648 9650 9654 10448 10584 10596>,
+ <9648 9650 9654 10448 10584 10596>;
};
qcom,pc-temp-y3-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <14249 13491 13351 13296 13276 13275 13272>,
- <14289 13481 13348 13297 13278 13275 13272>,
- <14293 13476 13346 13298 13280 13275 13273>,
- <14269 13476 13347 13300 13282 13276 13274>,
- <14223 13480 13349 13302 13283 13276 13274>,
- <14165 13486 13352 13303 13283 13276 13275>,
- <14057 13513 13358 13303 13283 13276 13275>,
- <13951 13546 13363 13304 13283 13276 13275>,
- <13946 13543 13365 13306 13283 13277 13275>,
- <13996 13505 13365 13310 13284 13278 13275>,
- <14024 13476 13366 13315 13285 13278 13276>,
- <13979 13465 13371 13319 13285 13278 13276>,
- <13920 13456 13377 13322 13285 13278 13276>,
- <13916 13446 13376 13322 13286 13278 13276>,
- <13935 13434 13369 13321 13288 13279 13277>,
- <13956 13428 13363 13320 13290 13279 13277>,
- <13974 13428 13359 13318 13291 13280 13278>,
- <13993 13428 13354 13316 13292 13282 13278>,
- <14013 13414 13349 13313 13292 13283 13279>,
- <14037 13377 13343 13308 13291 13283 13281>,
- <14068 13356 13338 13304 13290 13284 13281>,
- <14115 13351 13336 13301 13286 13280 13278>,
- <14171 13349 13333 13299 13283 13276 13274>,
- <14221 13354 13323 13298 13282 13275 13273>,
- <14271 13374 13301 13297 13281 13275 13273>,
- <14325 13397 13289 13297 13281 13275 13273>,
- <14385 13424 13273 13297 13280 13275 13273>,
- <14448 13457 13259 13297 13280 13275 13273>,
- <14513 13494 13259 13296 13280 13275 13273>,
- <14578 13537 13259 13296 13280 13275 13273>,
- <14647 13586 13260 13295 13280 13274 13272>,
- <14717 13644 13261 13291 13280 13274 13272>,
- <14792 13708 13262 13288 13279 13274 13272>,
- <14878 13777 13264 13289 13279 13274 13272>,
- <14972 13853 13268 13293 13279 13273 13272>,
- <15069 13939 13274 13295 13279 13273 13272>,
- <15166 14040 13285 13294 13279 13274 13272>,
- <15270 14153 13299 13292 13280 13274 13273>,
- <15386 14276 13317 13292 13279 13274 13273>,
- <15514 14412 13340 13293 13279 13274 13273>,
- <15658 14564 13372 13291 13279 13274 13273>,
- <15825 14738 13423 13271 13280 13275 13273>,
- <16019 14925 13493 13262 13280 13275 13273>,
- <16253 15128 13598 13261 13280 13274 13273>,
- <16581 15354 13729 13263 13279 13275 13274>,
- <16918 15547 13885 13266 13284 13276 13275>,
- <17576 15700 13996 13270 13284 13277 13277>,
- <18634 15883 14139 13280 13288 13279 13277>,
- <20075 16098 14305 13309 13290 13280 13277>,
- <22149 16340 14489 13343 13292 13280 13276>,
- <25271 16656 14726 13389 13294 13281 13277>,
- <29950 17634 15025 13481 13299 13283 13278>,
- <37310 19636 15401 13635 13309 13286 13283>,
- <47876 22946 16005 13899 13335 13293 13287>,
- <47876 22946 16005 13899 13335 13293 13287>,
- <47876 22946 16005 13899 13335 13293 13287>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <13491 13351 13296 13276 13275 13272>,
+ <13481 13348 13297 13278 13275 13272>,
+ <13476 13346 13298 13280 13275 13273>,
+ <13476 13347 13300 13282 13276 13274>,
+ <13480 13349 13302 13283 13276 13274>,
+ <13486 13352 13303 13283 13276 13275>,
+ <13513 13358 13303 13283 13276 13275>,
+ <13546 13363 13304 13283 13276 13275>,
+ <13543 13365 13306 13283 13277 13275>,
+ <13505 13365 13310 13284 13278 13275>,
+ <13476 13366 13315 13285 13278 13276>,
+ <13465 13371 13319 13285 13278 13276>,
+ <13456 13377 13322 13285 13278 13276>,
+ <13446 13376 13322 13286 13278 13276>,
+ <13434 13369 13321 13288 13279 13277>,
+ <13428 13363 13320 13290 13279 13277>,
+ <13428 13359 13318 13291 13280 13278>,
+ <13428 13354 13316 13292 13282 13278>,
+ <13414 13349 13313 13292 13283 13279>,
+ <13377 13343 13308 13291 13283 13281>,
+ <13356 13338 13304 13290 13284 13281>,
+ <13351 13336 13301 13286 13280 13278>,
+ <13349 13333 13299 13283 13276 13274>,
+ <13354 13323 13298 13282 13275 13273>,
+ <13374 13301 13297 13281 13275 13273>,
+ <13397 13289 13297 13281 13275 13273>,
+ <13424 13273 13297 13280 13275 13273>,
+ <13457 13259 13297 13280 13275 13273>,
+ <13494 13259 13296 13280 13275 13273>,
+ <13537 13259 13296 13280 13275 13273>,
+ <13586 13260 13295 13280 13274 13272>,
+ <13644 13261 13291 13280 13274 13272>,
+ <13708 13262 13288 13279 13274 13272>,
+ <13777 13264 13289 13279 13274 13272>,
+ <13853 13268 13293 13279 13273 13272>,
+ <13939 13274 13295 13279 13273 13272>,
+ <14040 13285 13294 13279 13274 13272>,
+ <14153 13299 13292 13280 13274 13273>,
+ <14276 13317 13292 13279 13274 13273>,
+ <14412 13340 13293 13279 13274 13273>,
+ <14564 13372 13291 13279 13274 13273>,
+ <14738 13423 13271 13280 13275 13273>,
+ <14925 13493 13262 13280 13275 13273>,
+ <15128 13598 13261 13280 13274 13273>,
+ <15354 13729 13263 13279 13275 13274>,
+ <15547 13885 13266 13284 13276 13275>,
+ <15700 13996 13270 13284 13277 13277>,
+ <15883 14139 13280 13288 13279 13277>,
+ <16098 14305 13309 13290 13280 13277>,
+ <16340 14489 13343 13292 13280 13276>,
+ <16656 14726 13389 13294 13281 13277>,
+ <17634 15025 13481 13299 13283 13278>,
+ <19636 15401 13635 13309 13286 13283>,
+ <22946 16005 13899 13335 13293 13287>,
+ <22946 16005 13899 13335 13293 13287>,
+ <22946 16005 13899 13335 13293 13287>;
};
qcom,pc-temp-y4-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <17711 16973 16623 16526 16458 16452 16456>,
- <17567 16999 16632 16525 16457 16452 16456>,
- <17504 17030 16641 16525 16457 16452 16456>,
- <17504 17060 16652 16526 16457 16452 16456>,
- <17547 17082 16663 16528 16457 16452 16456>,
- <17613 17089 16674 16531 16457 16452 16456>,
- <17765 17077 16687 16535 16459 16452 16456>,
- <17948 17059 16701 16539 16462 16453 16456>,
- <18024 17098 16711 16545 16465 16453 16456>,
- <18066 17276 16720 16552 16468 16454 16457>,
- <18080 17396 16735 16563 16473 16455 16457>,
- <17811 17426 16824 16584 16480 16458 16458>,
- <17427 17443 16930 16612 16490 16461 16460>,
- <17319 17384 16951 16638 16498 16465 16462>,
- <17285 17155 16958 16663 16504 16470 16465>,
- <17245 17028 16959 16695 16515 16476 16469>,
- <17166 17014 16934 16758 16539 16486 16475>,
- <17085 17005 16887 16816 16571 16502 16486>,
- <17039 16980 16831 16800 16609 16530 16506>,
- <17007 16933 16754 16713 16656 16576 16541>,
- <16985 16886 16692 16635 16664 16593 16558>,
- <16968 16837 16644 16572 16570 16535 16521>,
- <16957 16797 16610 16522 16475 16468 16470>,
- <16954 16783 16607 16507 16460 16455 16458>,
- <16953 16776 16623 16498 16454 16451 16455>,
- <16953 16770 16632 16494 16453 16449 16454>,
- <16951 16765 16645 16493 16454 16449 16453>,
- <16951 16761 16659 16493 16455 16448 16453>,
- <16953 16761 16662 16492 16457 16449 16453>,
- <16959 16761 16663 16493 16461 16452 16454>,
- <16965 16762 16667 16493 16466 16456 16455>,
- <16974 16764 16677 16492 16474 16464 16461>,
- <16982 16767 16687 16492 16479 16471 16470>,
- <16985 16770 16690 16494 16478 16474 16476>,
- <16987 16775 16693 16500 16474 16474 16483>,
- <16990 16778 16693 16505 16467 16471 16482>,
- <16999 16782 16689 16508 16455 16458 16467>,
- <17010 16784 16685 16510 16448 16447 16453>,
- <17021 16783 16685 16511 16449 16450 16455>,
- <17033 16781 16683 16512 16452 16456 16465>,
- <17048 16779 16681 16517 16455 16459 16471>,
- <17066 16770 16670 16558 16460 16458 16470>,
- <17087 16768 16654 16579 16464 16456 16468>,
- <17112 16776 16634 16584 16465 16448 16452>,
- <17124 16801 16629 16593 16474 16448 16444>,
- <17066 16819 16647 16617 16493 16467 16470>,
- <17161 16856 16669 16641 16507 16488 16496>,
- <17324 16905 16699 16672 16536 16520 16521>,
- <17559 16944 16754 16675 16565 16529 16536>,
- <17893 16949 16780 16683 16555 16503 16488>,
- <18450 16941 16767 16681 16554 16495 16479>,
- <19496 17078 16794 16695 16582 16508 16485>,
- <21979 17565 16874 16751 16646 16545 16510>,
- <30091 19162 17124 16888 16859 16671 16581>,
- <30091 19162 17124 16888 16859 16671 16581>,
- <30091 19162 17124 16888 16859 16671 16581>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <16973 16623 16526 16458 16452 16456>,
+ <16999 16632 16525 16457 16452 16456>,
+ <17030 16641 16525 16457 16452 16456>,
+ <17060 16652 16526 16457 16452 16456>,
+ <17082 16663 16528 16457 16452 16456>,
+ <17089 16674 16531 16457 16452 16456>,
+ <17077 16687 16535 16459 16452 16456>,
+ <17059 16701 16539 16462 16453 16456>,
+ <17098 16711 16545 16465 16453 16456>,
+ <17276 16720 16552 16468 16454 16457>,
+ <17396 16735 16563 16473 16455 16457>,
+ <17426 16824 16584 16480 16458 16458>,
+ <17443 16930 16612 16490 16461 16460>,
+ <17384 16951 16638 16498 16465 16462>,
+ <17155 16958 16663 16504 16470 16465>,
+ <17028 16959 16695 16515 16476 16469>,
+ <17014 16934 16758 16539 16486 16475>,
+ <17005 16887 16816 16571 16502 16486>,
+ <16980 16831 16800 16609 16530 16506>,
+ <16933 16754 16713 16656 16576 16541>,
+ <16886 16692 16635 16664 16593 16558>,
+ <16837 16644 16572 16570 16535 16521>,
+ <16797 16610 16522 16475 16468 16470>,
+ <16783 16607 16507 16460 16455 16458>,
+ <16776 16623 16498 16454 16451 16455>,
+ <16770 16632 16494 16453 16449 16454>,
+ <16765 16645 16493 16454 16449 16453>,
+ <16761 16659 16493 16455 16448 16453>,
+ <16761 16662 16492 16457 16449 16453>,
+ <16761 16663 16493 16461 16452 16454>,
+ <16762 16667 16493 16466 16456 16455>,
+ <16764 16677 16492 16474 16464 16461>,
+ <16767 16687 16492 16479 16471 16470>,
+ <16770 16690 16494 16478 16474 16476>,
+ <16775 16693 16500 16474 16474 16483>,
+ <16778 16693 16505 16467 16471 16482>,
+ <16782 16689 16508 16455 16458 16467>,
+ <16784 16685 16510 16448 16447 16453>,
+ <16783 16685 16511 16449 16450 16455>,
+ <16781 16683 16512 16452 16456 16465>,
+ <16779 16681 16517 16455 16459 16471>,
+ <16770 16670 16558 16460 16458 16470>,
+ <16768 16654 16579 16464 16456 16468>,
+ <16776 16634 16584 16465 16448 16452>,
+ <16801 16629 16593 16474 16448 16444>,
+ <16819 16647 16617 16493 16467 16470>,
+ <16856 16669 16641 16507 16488 16496>,
+ <16905 16699 16672 16536 16520 16521>,
+ <16944 16754 16675 16565 16529 16536>,
+ <16949 16780 16683 16555 16503 16488>,
+ <16941 16767 16681 16554 16495 16479>,
+ <17078 16794 16695 16582 16508 16485>,
+ <17565 16874 16751 16646 16545 16510>,
+ <19162 17124 16888 16859 16671 16581>,
+ <19162 17124 16888 16859 16671 16581>,
+ <19162 17124 16888 16859 16671 16581>;
};
qcom,pc-temp-y5-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <9336 11501 16034 14767 13793 19407 15565>,
- <10230 11603 15822 15156 15683 19413 16938>,
- <10807 11875 15497 15333 17017 19416 18058>,
- <11133 12285 15152 15352 17855 19416 18894>,
- <11279 12803 14881 15266 18259 19413 19416>,
- <11310 13403 14778 15128 18284 19405 19590>,
- <11059 14551 14807 14793 17405 18933 19301>,
- <10701 15710 14848 14419 16236 18269 18809>,
- <11143 15425 14688 14471 15943 18195 18561>,
- <13343 13533 13983 14951 15873 18327 18385>,
- <14582 12513 13556 15219 15744 18394 18198>,
- <13448 13803 13493 14892 15050 17832 17726>,
- <11924 15473 13460 14418 14306 16921 17099>,
- <11782 15394 13744 14254 14381 16318 16821>,
- <12065 14258 14851 14181 14869 15815 16673>,
- <12212 13562 15643 14199 15070 15556 16471>,
- <12106 13428 15965 14556 14786 15450 15954>,
- <11900 13274 16199 15160 14490 15387 15465>,
- <11618 12936 16398 15863 14755 15446 15449>,
- <11196 12423 16588 16824 15793 15777 15650>,
- <11019 11952 16732 17460 16919 16267 15980>,
- <11074 11476 16879 17821 18292 17600 16933>,
- <11141 11117 16964 18087 19430 19112 18163>,
- <11133 11033 16245 18242 19821 19838 19000>,
- <11069 11009 14141 18325 19945 20331 19696>,
- <11046 11024 12876 18331 19914 20756 20093>,
- <11109 11056 11798 18517 19842 21457 20297>,
- <11170 11084 10948 18759 19785 21999 20418>,
- <11161 11132 10879 18828 19716 21658 20286>,
- <11138 11232 10862 18868 19575 20509 19563>,
- <11111 11269 10868 18768 19409 19604 18813>,
- <11071 11345 11005 17096 19184 18920 18072>,
- <11039 11421 11165 15478 19049 18499 17524>,
- <11083 11456 11261 16038 19331 18661 17776>,
- <11207 11520 11350 17571 20041 19331 19034>,
- <11252 11543 11387 18037 20606 20274 20444>,
- <11213 11613 11553 17270 21412 23017 22060>,
- <11168 11678 11697 16300 21789 25208 23225>,
- <11151 11640 11640 15861 20914 24442 22731>,
- <11145 11545 11511 15530 19618 22425 21047>,
- <11154 11506 11463 14798 19274 21559 20283>,
- <11189 11457 11412 12697 19217 21506 20308>,
- <11250 11415 11500 11853 18717 21719 20486>,
- <11392 11368 11742 11779 17923 22443 22679>,
- <11471 11364 11818 11639 16687 21754 22971>,
- <11412 11379 11581 11310 17555 18408 18279>,
- <11284 11464 11576 11214 16686 17313 17483>,
- <10955 11729 11969 11315 17033 16467 15409>,
- <10501 12142 11899 11677 16717 15881 14424>,
- <10146 11979 11895 11966 17491 17177 15372>,
- <9743 11649 12007 11983 17478 18213 16253>,
- <9402 11017 11938 11964 17190 17836 15973>,
- <9188 10265 11845 11923 16780 17343 17751>,
- <8988 9626 11312 12185 16916 17400 17911>,
- <8988 9626 11312 12185 16916 17400 17911>,
- <8988 9626 11312 12185 16916 17400 17911>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <11501 16034 14767 13793 19407 15565>,
+ <11603 15822 15156 15683 19413 16938>,
+ <11875 15497 15333 17017 19416 18058>,
+ <12285 15152 15352 17855 19416 18894>,
+ <12803 14881 15266 18259 19413 19416>,
+ <13403 14778 15128 18284 19405 19590>,
+ <14551 14807 14793 17405 18933 19301>,
+ <15710 14848 14419 16236 18269 18809>,
+ <15425 14688 14471 15943 18195 18561>,
+ <13533 13983 14951 15873 18327 18385>,
+ <12513 13556 15219 15744 18394 18198>,
+ <13803 13493 14892 15050 17832 17726>,
+ <15473 13460 14418 14306 16921 17099>,
+ <15394 13744 14254 14381 16318 16821>,
+ <14258 14851 14181 14869 15815 16673>,
+ <13562 15643 14199 15070 15556 16471>,
+ <13428 15965 14556 14786 15450 15954>,
+ <13274 16199 15160 14490 15387 15465>,
+ <12936 16398 15863 14755 15446 15449>,
+ <12423 16588 16824 15793 15777 15650>,
+ <11952 16732 17460 16919 16267 15980>,
+ <11476 16879 17821 18292 17600 16933>,
+ <11117 16964 18087 19430 19112 18163>,
+ <11033 16245 18242 19821 19838 19000>,
+ <11009 14141 18325 19945 20331 19696>,
+ <11024 12876 18331 19914 20756 20093>,
+ <11056 11798 18517 19842 21457 20297>,
+ <11084 10948 18759 19785 21999 20418>,
+ <11132 10879 18828 19716 21658 20286>,
+ <11232 10862 18868 19575 20509 19563>,
+ <11269 10868 18768 19409 19604 18813>,
+ <11345 11005 17096 19184 18920 18072>,
+ <11421 11165 15478 19049 18499 17524>,
+ <11456 11261 16038 19331 18661 17776>,
+ <11520 11350 17571 20041 19331 19034>,
+ <11543 11387 18037 20606 20274 20444>,
+ <11613 11553 17270 21412 23017 22060>,
+ <11678 11697 16300 21789 25208 23225>,
+ <11640 11640 15861 20914 24442 22731>,
+ <11545 11511 15530 19618 22425 21047>,
+ <11506 11463 14798 19274 21559 20283>,
+ <11457 11412 12697 19217 21506 20308>,
+ <11415 11500 11853 18717 21719 20486>,
+ <11368 11742 11779 17923 22443 22679>,
+ <11364 11818 11639 16687 21754 22971>,
+ <11379 11581 11310 17555 18408 18279>,
+ <11464 11576 11214 16686 17313 17483>,
+ <11729 11969 11315 17033 16467 15409>,
+ <12142 11899 11677 16717 15881 14424>,
+ <11979 11895 11966 17491 17177 15372>,
+ <11649 12007 11983 17478 18213 16253>,
+ <11017 11938 11964 17190 17836 15973>,
+ <10265 11845 11923 16780 17343 17751>,
+ <9626 11312 12185 16916 17400 17911>,
+ <9626 11312 12185 16916 17400 17911>,
+ <9626 11312 12185 16916 17400 17911>;
};
qcom,pc-temp-y6-lut {
- qcom,lut-col-legend = <(-20) (-10) 0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000 8800>,
- <8600 8400 8200 8000 7800 7600 7400>,
- <7200 7000 6800 6600 6400 6200 6000>,
- <5800 5600 5400 5200 5000 4800 4600>,
- <4400 4200 4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200 2000 1800>,
- <1600 1400 1200 1000 900 800 700>,
- <600 500 400 300 200 100 0>;
- qcom,lut-data = <7520 6106 5405 5178 5064 5046 5042>,
- <7480 6097 5401 5177 5064 5046 5042>,
- <7441 6092 5400 5176 5065 5046 5042>,
- <7405 6089 5400 5176 5066 5047 5043>,
- <7374 6088 5401 5176 5067 5047 5044>,
- <7350 6088 5403 5176 5067 5047 5044>,
- <7329 6090 5407 5176 5068 5047 5044>,
- <7314 6094 5413 5177 5068 5047 5044>,
- <7323 6102 5416 5178 5069 5047 5044>,
- <7367 6117 5418 5182 5071 5048 5044>,
- <7391 6129 5422 5187 5073 5049 5045>,
- <7291 6135 5450 5195 5075 5050 5045>,
- <7156 6139 5483 5204 5078 5051 5046>,
- <7138 6123 5488 5211 5081 5052 5047>,
- <7142 6059 5490 5218 5085 5054 5048>,
- <7144 6027 5490 5226 5089 5056 5050>,
- <7141 6030 5484 5243 5097 5060 5052>,
- <7136 6034 5472 5259 5107 5066 5055>,
- <7138 6032 5457 5253 5118 5075 5062>,
- <7150 6027 5435 5225 5131 5088 5073>,
- <7165 6025 5421 5201 5133 5093 5078>,
- <7194 6031 5414 5182 5104 5074 5065>,
- <7230 6042 5409 5169 5075 5052 5048>,
- <7265 6061 5410 5167 5071 5048 5044>,
- <7301 6095 5412 5166 5069 5047 5043>,
- <7340 6132 5415 5166 5069 5046 5042>,
- <7383 6169 5421 5168 5070 5047 5042>,
- <7430 6210 5431 5171 5071 5047 5042>,
- <7476 6254 5444 5175 5073 5048 5043>,
- <7523 6302 5464 5178 5075 5049 5043>,
- <7575 6354 5486 5181 5078 5050 5044>,
- <7633 6411 5511 5183 5081 5052 5046>,
- <7696 6471 5539 5185 5083 5055 5048>,
- <7764 6535 5569 5192 5084 5056 5050>,
- <7836 6602 5603 5205 5084 5056 5053>,
- <7911 6677 5640 5216 5084 5056 5053>,
- <7991 6759 5681 5225 5083 5053 5049>,
- <8076 6849 5727 5234 5083 5051 5046>,
- <8172 6948 5778 5244 5084 5052 5047>,
- <8278 7058 5835 5257 5087 5055 5050>,
- <8396 7178 5899 5273 5091 5057 5052>,
- <8531 7313 5971 5295 5095 5058 5052>,
- <8689 7461 6060 5322 5099 5058 5052>,
- <8881 7625 6170 5355 5104 5056 5049>,
- <9142 7801 6295 5404 5112 5059 5048>,
- <9395 7952 6438 5465 5127 5066 5057>,
- <9966 8083 6542 5513 5135 5074 5067>,
- <10874 8233 6666 5574 5150 5086 5075>,
- <12099 8404 6813 5646 5166 5090 5080>,
- <13825 8597 6972 5725 5172 5084 5066>,
- <16318 8831 7159 5819 5184 5085 5065>,
- <20019 9655 7408 5955 5214 5093 5070>,
- <25895 11356 7725 6149 5262 5110 5083>,
- <35348 14260 8288 6430 5374 5157 5109>,
- <35348 14260 8288 6430 5374 5157 5109>,
- <35348 14260 8288 6430 5374 5157 5109>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <6106 5405 5178 5064 5046 5042>,
+ <6097 5401 5177 5064 5046 5042>,
+ <6092 5400 5176 5065 5046 5042>,
+ <6089 5400 5176 5066 5047 5043>,
+ <6088 5401 5176 5067 5047 5044>,
+ <6088 5403 5176 5067 5047 5044>,
+ <6090 5407 5176 5068 5047 5044>,
+ <6094 5413 5177 5068 5047 5044>,
+ <6102 5416 5178 5069 5047 5044>,
+ <6117 5418 5182 5071 5048 5044>,
+ <6129 5422 5187 5073 5049 5045>,
+ <6135 5450 5195 5075 5050 5045>,
+ <6139 5483 5204 5078 5051 5046>,
+ <6123 5488 5211 5081 5052 5047>,
+ <6059 5490 5218 5085 5054 5048>,
+ <6027 5490 5226 5089 5056 5050>,
+ <6030 5484 5243 5097 5060 5052>,
+ <6034 5472 5259 5107 5066 5055>,
+ <6032 5457 5253 5118 5075 5062>,
+ <6027 5435 5225 5131 5088 5073>,
+ <6025 5421 5201 5133 5093 5078>,
+ <6031 5414 5182 5104 5074 5065>,
+ <6042 5409 5169 5075 5052 5048>,
+ <6061 5410 5167 5071 5048 5044>,
+ <6095 5412 5166 5069 5047 5043>,
+ <6132 5415 5166 5069 5046 5042>,
+ <6169 5421 5168 5070 5047 5042>,
+ <6210 5431 5171 5071 5047 5042>,
+ <6254 5444 5175 5073 5048 5043>,
+ <6302 5464 5178 5075 5049 5043>,
+ <6354 5486 5181 5078 5050 5044>,
+ <6411 5511 5183 5081 5052 5046>,
+ <6471 5539 5185 5083 5055 5048>,
+ <6535 5569 5192 5084 5056 5050>,
+ <6602 5603 5205 5084 5056 5053>,
+ <6677 5640 5216 5084 5056 5053>,
+ <6759 5681 5225 5083 5053 5049>,
+ <6849 5727 5234 5083 5051 5046>,
+ <6948 5778 5244 5084 5052 5047>,
+ <7058 5835 5257 5087 5055 5050>,
+ <7178 5899 5273 5091 5057 5052>,
+ <7313 5971 5295 5095 5058 5052>,
+ <7461 6060 5322 5099 5058 5052>,
+ <7625 6170 5355 5104 5056 5049>,
+ <7801 6295 5404 5112 5059 5048>,
+ <7952 6438 5465 5127 5066 5057>,
+ <8083 6542 5513 5135 5074 5067>,
+ <8233 6666 5574 5150 5086 5075>,
+ <8404 6813 5646 5166 5090 5080>,
+ <8597 6972 5725 5172 5084 5066>,
+ <8831 7159 5819 5184 5085 5065>,
+ <9655 7408 5955 5214 5093 5070>,
+ <11356 7725 6149 5262 5110 5083>,
+ <14260 8288 6430 5374 5157 5109>,
+ <14260 8288 6430 5374 5157 5109>,
+ <14260 8288 6430 5374 5157 5109>;
};
};
diff --git a/arch/arm64/boot/dts/qcom/qg-batterydata-mlp356477-2800mah.dtsi b/arch/arm64/boot/dts/qcom/qg-batterydata-mlp356477-2800mah.dtsi
index f418fa0..6bcfd37 100644
--- a/arch/arm64/boot/dts/qcom/qg-batterydata-mlp356477-2800mah.dtsi
+++ b/arch/arm64/boot/dts/qcom/qg-batterydata-mlp356477-2800mah.dtsi
@@ -11,15 +11,15 @@
*/
qcom,mlp356477_2800mah {
- /* mlp356477_2800mah_averaged_MasterSlave_Aug14th2017 */
+ /* mlp356477_2800mah_averaged_MasterSlave_Mar13th2018 */
qcom,max-voltage-uv = <4400000>;
qcom,fg-cc-cv-threshold-mv = <4390>;
qcom,fastchg-current-ma = <4200>;
qcom,batt-id-kohm = <82>;
qcom,battery-beta = <4250>;
- qcom,battery-therm-kohm = <32>;
+ qcom,battery-therm-kohm = <100>;
qcom,battery-type =
- "mlp356477_2800mah_averaged_MasterSlave_Aug14th2017";
+ "mlp356477_2800mah_averaged_MasterSlave_Mar13th2018";
qcom,qg-batt-profile-ver = <100>;
qcom,jeita-fcc-ranges = <0 150 560000
@@ -35,8 +35,8 @@
};
qcom,fcc2-temp-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-data = <2846 2860 2868 2865 2865>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-data = <2864 2846 2860 2868 2865 2865>;
};
qcom,pc-temp-v1-lut {
@@ -112,75 +112,73 @@
};
qcom,pc-temp-v2-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <43850 43830 43805 43740 43725>,
- <43429 43514 43528 43481 43467>,
- <43064 43219 43264 43228 43216>,
- <42767 42948 43012 42983 42973>,
- <42526 42700 42773 42744 42738>,
- <42296 42458 42537 42509 42505>,
- <42059 42213 42303 42277 42272>,
- <41822 41972 42071 42047 42041>,
- <41571 41739 41843 41820 41814>,
- <41298 41515 41619 41595 41589>,
- <41069 41297 41398 41374 41368>,
- <40928 41088 41181 41158 41151>,
- <40808 40884 40967 40946 40938>,
- <40611 40677 40763 40742 40734>,
- <40284 40461 40566 40541 40534>,
- <39989 40259 40373 40348 40342>,
- <39811 40087 40180 40164 40158>,
- <39662 39920 39993 39985 39980>,
- <39459 39722 39821 39814 39808>,
- <39184 39492 39664 39651 39646>,
- <38924 39264 39483 39469 39466>,
- <38721 39048 39237 39230 39230>,
- <38546 38846 38982 38986 38989>,
- <38403 38678 38799 38809 38813>,
- <38282 38535 38654 38669 38674>,
- <38189 38406 38530 38547 38552>,
- <38125 38286 38419 38438 38442>,
- <38075 38179 38320 38341 38343>,
- <38030 38090 38229 38250 38250>,
- <37992 38012 38144 38166 38164>,
- <37955 37949 38066 38089 38086>,
- <37916 37900 37993 38019 38016>,
- <37875 37857 37925 37953 37949>,
- <37832 37817 37860 37884 37875>,
- <37788 37781 37801 37812 37795>,
- <37738 37740 37738 37728 37702>,
- <37680 37688 37671 37625 37587>,
- <37613 37625 37600 37519 37469>,
- <37537 37552 37525 37430 37374>,
- <37448 37465 37446 37352 37292>,
- <37349 37363 37353 37263 37200>,
- <37237 37238 37238 37151 37088>,
- <37114 37101 37106 37022 36960>,
- <36989 36957 36952 36870 36813>,
- <36875 36859 36862 36807 36758>,
- <36792 36792 36828 36785 36734>,
- <36754 36762 36812 36769 36719>,
- <36707 36710 36780 36736 36687>,
- <36633 36613 36721 36656 36581>,
- <36472 36411 36517 36379 36276>,
- <36149 36031 36113 35946 35829>,
- <35650 35485 35584 35386 35258>,
- <34964 34771 34884 34643 34500>,
- <34007 33739 33902 33598 33440>,
- <32474 32144 32393 32025 31829>,
- <28051 26513 28737 27554 26991>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <43865 43850 43830 43805 43740 43725>,
+ <43432 43429 43514 43528 43481 43467>,
+ <43037 43064 43219 43264 43228 43216>,
+ <42685 42767 42948 43012 42983 42973>,
+ <42369 42526 42700 42773 42744 42738>,
+ <42075 42296 42458 42537 42509 42505>,
+ <41776 42059 42213 42303 42277 42272>,
+ <41517 41822 41972 42071 42047 42041>,
+ <41353 41571 41739 41843 41820 41814>,
+ <41239 41298 41515 41619 41595 41589>,
+ <41095 41069 41297 41398 41374 41368>,
+ <40895 40928 41088 41181 41158 41151>,
+ <40650 40808 40884 40967 40946 40938>,
+ <40329 40611 40677 40763 40742 40734>,
+ <39941 40284 40461 40566 40541 40534>,
+ <39654 39989 40259 40373 40348 40342>,
+ <39456 39811 40087 40180 40164 40158>,
+ <39278 39662 39920 39993 39985 39980>,
+ <39086 39459 39722 39821 39814 39808>,
+ <38900 39184 39492 39664 39651 39646>,
+ <38740 38924 39264 39483 39469 39466>,
+ <38598 38721 39048 39237 39230 39230>,
+ <38480 38546 38846 38982 38986 38989>,
+ <38386 38403 38678 38799 38809 38813>,
+ <38308 38282 38535 38654 38669 38674>,
+ <38240 38189 38406 38530 38547 38552>,
+ <38182 38125 38286 38419 38438 38442>,
+ <38127 38075 38179 38320 38341 38343>,
+ <38076 38030 38090 38229 38250 38250>,
+ <38028 37992 38012 38144 38166 38164>,
+ <37978 37955 37949 38066 38089 38086>,
+ <37927 37916 37900 37993 38019 38016>,
+ <37875 37875 37857 37925 37953 37949>,
+ <37820 37832 37817 37860 37884 37875>,
+ <37763 37788 37781 37801 37812 37795>,
+ <37699 37738 37740 37738 37728 37702>,
+ <37630 37680 37688 37671 37625 37587>,
+ <37555 37613 37625 37600 37519 37469>,
+ <37475 37537 37552 37525 37430 37374>,
+ <37392 37448 37465 37446 37352 37292>,
+ <37308 37349 37363 37353 37263 37200>,
+ <37222 37237 37238 37238 37151 37088>,
+ <37133 37114 37101 37106 37022 36960>,
+ <37035 36989 36957 36952 36870 36813>,
+ <36935 36875 36859 36862 36807 36758>,
+ <36817 36792 36792 36828 36785 36734>,
+ <36752 36754 36762 36812 36769 36719>,
+ <36667 36707 36710 36780 36736 36687>,
+ <36541 36633 36613 36721 36656 36581>,
+ <36342 36472 36411 36517 36379 36276>,
+ <36024 36149 36031 36113 35946 35829>,
+ <35575 35650 35485 35584 35386 35258>,
+ <34953 34964 34771 34884 34643 34500>,
+ <34073 34007 33739 33902 33598 33440>,
+ <32647 32474 32144 32393 32025 31829>,
+ <30018 28051 26513 28737 27554 26991>;
};
qcom,pc-temp-z1-lut {
@@ -616,435 +614,422 @@
};
qcom,pc-temp-y1-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <6704 6050 5566 5322 5235>,
- <6701 6050 5560 5320 5234>,
- <6693 6051 5554 5318 5233>,
- <6684 6051 5548 5316 5231>,
- <6676 6052 5543 5313 5230>,
- <6673 6053 5540 5311 5228>,
- <6667 6054 5539 5308 5225>,
- <6659 6054 5538 5305 5222>,
- <6663 6055 5536 5302 5222>,
- <6693 6056 5529 5299 5222>,
- <6717 6055 5525 5298 5222>,
- <6716 6050 5525 5297 5220>,
- <6707 6044 5526 5296 5217>,
- <6706 6044 5528 5295 5216>,
- <6707 6049 5533 5293 5217>,
- <6709 6052 5536 5291 5217>,
- <6705 6053 5534 5290 5219>,
- <6699 6055 5532 5288 5221>,
- <6700 6057 5532 5289 5221>,
- <6708 6062 5531 5290 5220>,
- <6715 6065 5531 5292 5219>,
- <6712 6067 5532 5294 5220>,
- <6706 6071 5532 5296 5222>,
- <6703 6071 5532 5297 5223>,
- <6702 6070 5532 5298 5225>,
- <6702 6069 5532 5299 5227>,
- <6700 6068 5535 5301 5229>,
- <6699 6065 5539 5305 5232>,
- <6697 6062 5540 5309 5236>,
- <6691 6059 5541 5311 5240>,
- <6688 6059 5542 5314 5243>,
- <6691 6063 5546 5317 5244>,
- <6695 6069 5550 5320 5245>,
- <6693 6072 5553 5324 5247>,
- <6677 6077 5556 5329 5251>,
- <6667 6080 5558 5333 5255>,
- <6679 6081 5563 5336 5258>,
- <6697 6082 5568 5339 5261>,
- <6698 6085 5570 5342 5263>,
- <6684 6094 5571 5348 5265>,
- <6675 6101 5572 5352 5268>,
- <6691 6098 5581 5353 5271>,
- <6707 6096 5586 5356 5275>,
- <6704 6102 5586 5363 5282>,
- <6708 6104 5593 5368 5284>,
- <6725 6098 5595 5370 5288>,
- <6724 6114 5601 5370 5288>,
- <6743 6089 5598 5376 5290>,
- <6750 6086 5605 5374 5291>,
- <6722 6104 5609 5381 5293>,
- <6738 6105 5608 5384 5292>,
- <6759 6112 5624 5392 5304>,
- <6766 6128 5643 5400 5313>,
- <6779 6149 5656 5417 5324>,
- <6779 6149 5656 5417 5324>,
- <6779 6149 5656 5417 5324>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <7929 6704 6050 5566 5322 5235>,
+ <8028 6701 6050 5560 5320 5234>,
+ <8101 6693 6051 5554 5318 5233>,
+ <8151 6684 6051 5548 5316 5231>,
+ <8179 6676 6052 5543 5313 5230>,
+ <8186 6673 6053 5540 5311 5228>,
+ <8157 6667 6054 5539 5308 5225>,
+ <8120 6659 6054 5538 5305 5222>,
+ <8110 6663 6055 5536 5302 5222>,
+ <8104 6693 6056 5529 5299 5222>,
+ <8099 6717 6055 5525 5298 5222>,
+ <8120 6716 6050 5525 5297 5220>,
+ <8146 6707 6044 5526 5296 5217>,
+ <8147 6706 6044 5528 5295 5216>,
+ <8147 6707 6049 5533 5293 5217>,
+ <8146 6709 6052 5536 5291 5217>,
+ <8135 6705 6053 5534 5290 5219>,
+ <8119 6699 6055 5532 5288 5221>,
+ <8100 6700 6057 5532 5289 5221>,
+ <8079 6708 6062 5531 5290 5220>,
+ <8070 6715 6065 5531 5292 5219>,
+ <8070 6712 6067 5532 5294 5220>,
+ <8076 6706 6071 5532 5296 5222>,
+ <8117 6703 6071 5532 5297 5223>,
+ <8170 6702 6070 5532 5298 5225>,
+ <8167 6702 6069 5532 5299 5227>,
+ <8118 6700 6068 5535 5301 5229>,
+ <8084 6699 6065 5539 5305 5232>,
+ <8087 6697 6062 5540 5309 5236>,
+ <8100 6691 6059 5541 5311 5240>,
+ <8092 6688 6059 5542 5314 5243>,
+ <8059 6691 6063 5546 5317 5244>,
+ <8043 6695 6069 5550 5320 5245>,
+ <8027 6693 6072 5553 5324 5247>,
+ <8011 6677 6077 5556 5329 5251>,
+ <8021 6667 6080 5558 5333 5255>,
+ <8050 6679 6081 5563 5336 5258>,
+ <8082 6697 6082 5568 5339 5261>,
+ <8123 6698 6085 5570 5342 5263>,
+ <8148 6684 6094 5571 5348 5265>,
+ <8101 6675 6101 5572 5352 5268>,
+ <8041 6691 6098 5581 5353 5271>,
+ <8104 6707 6096 5586 5356 5275>,
+ <8088 6704 6102 5586 5363 5282>,
+ <8048 6708 6104 5593 5368 5284>,
+ <8055 6725 6098 5595 5370 5288>,
+ <8059 6724 6114 5601 5370 5288>,
+ <8092 6743 6089 5598 5376 5290>,
+ <8157 6750 6086 5605 5374 5291>,
+ <8197 6722 6104 5609 5381 5293>,
+ <8269 6738 6105 5608 5384 5292>,
+ <8288 6759 6112 5624 5392 5304>,
+ <8380 6766 6128 5643 5400 5313>,
+ <8422 6779 6149 5656 5417 5324>,
+ <8422 6779 6149 5656 5417 5324>,
+ <8422 6779 6149 5656 5417 5324>;
};
qcom,pc-temp-y2-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <9643 10639 11070 11121 11086>,
- <9643 10662 11056 11097 11058>,
- <9643 10675 11037 11063 11029>,
- <9871 10680 11014 11027 11001>,
- <10190 10680 10988 10997 10976>,
- <10325 10677 10959 10981 10958>,
- <10308 10664 10918 10973 10946>,
- <10282 10644 10881 10967 10935>,
- <10301 10632 10875 10959 10916>,
- <10440 10623 10874 10933 10882>,
- <10534 10619 10874 10919 10864>,
- <10489 10626 10869 10936 10874>,
- <10417 10643 10861 10961 10888>,
- <10413 10676 10856 10952 10885>,
- <10487 10748 10851 10897 10860>,
- <10553 10801 10851 10866 10840>,
- <10580 10826 10885 10876 10837>,
- <10597 10843 10946 10896 10845>,
- <10521 10842 11018 10943 10884>,
- <10042 10822 11115 11060 10984>,
- <9696 10809 11159 11120 11034>,
- <9682 10815 11129 11098 11013>,
- <9676 10826 11091 11071 10987>,
- <9675 10835 11085 11079 11009>,
- <9676 10846 11088 11121 11106>,
- <9676 10848 11093 11154 11162>,
- <9675 10684 11108 11176 11166>,
- <9671 10460 11130 11199 11168>,
- <9668 10652 11152 11224 11182>,
- <9665 11565 11178 11263 11214>,
- <9662 12069 11192 11286 11238>,
- <9660 11796 11199 11310 11257>,
- <9659 11319 11203 11338 11277>,
- <9657 10963 11202 11344 11307>,
- <9656 10643 11198 11320 11345>,
- <9655 10423 11189 11299 11359>,
- <9654 10140 11148 11294 11325>,
- <9653 9828 11108 11301 11280>,
- <9653 9733 11099 11301 11271>,
- <9653 9707 11096 11290 11278>,
- <9652 9692 11071 11287 11277>,
- <9652 9681 10975 11329 11250>,
- <9652 9674 10939 11356 11231>,
- <9652 9668 10913 11303 11229>,
- <9652 9664 10802 11253 11135>,
- <9652 9663 10839 11180 11044>,
- <9652 9661 10832 11146 11009>,
- <9652 9660 10811 11105 10962>,
- <9651 9659 10794 11061 10965>,
- <9651 9658 10764 11053 10938>,
- <9651 9658 10711 10981 10871>,
- <9651 9656 10651 10927 10829>,
- <9651 9654 10594 10851 10747>,
- <9651 9654 10531 10798 10659>,
- <9651 9654 10531 10798 10659>,
- <9651 9654 10531 10798 10659>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <9654 9643 10639 11070 11121 11086>,
+ <9654 9643 10662 11056 11097 11058>,
+ <9655 9643 10675 11037 11063 11029>,
+ <9655 9871 10680 11014 11027 11001>,
+ <9656 10190 10680 10988 10997 10976>,
+ <9656 10325 10677 10959 10981 10958>,
+ <9657 10308 10664 10918 10973 10946>,
+ <9657 10282 10644 10881 10967 10935>,
+ <9657 10301 10632 10875 10959 10916>,
+ <9658 10440 10623 10874 10933 10882>,
+ <9658 10534 10619 10874 10919 10864>,
+ <9658 10489 10626 10869 10936 10874>,
+ <9659 10417 10643 10861 10961 10888>,
+ <9658 10413 10676 10856 10952 10885>,
+ <9657 10487 10748 10851 10897 10860>,
+ <9657 10553 10801 10851 10866 10840>,
+ <9657 10580 10826 10885 10876 10837>,
+ <9657 10597 10843 10946 10896 10845>,
+ <9657 10521 10842 11018 10943 10884>,
+ <9656 10042 10822 11115 11060 10984>,
+ <9656 9696 10809 11159 11120 11034>,
+ <9656 9682 10815 11129 11098 11013>,
+ <9656 9676 10826 11091 11071 10987>,
+ <9656 9675 10835 11085 11079 11009>,
+ <9656 9676 10846 11088 11121 11106>,
+ <9655 9676 10848 11093 11154 11162>,
+ <9655 9675 10684 11108 11176 11166>,
+ <9655 9671 10460 11130 11199 11168>,
+ <9655 9668 10652 11152 11224 11182>,
+ <9654 9665 11565 11178 11263 11214>,
+ <9654 9662 12069 11192 11286 11238>,
+ <9654 9660 11796 11199 11310 11257>,
+ <9654 9659 11319 11203 11338 11277>,
+ <9654 9657 10963 11202 11344 11307>,
+ <9654 9656 10643 11198 11320 11345>,
+ <9654 9655 10423 11189 11299 11359>,
+ <9653 9654 10140 11148 11294 11325>,
+ <9653 9653 9828 11108 11301 11280>,
+ <9653 9653 9733 11099 11301 11271>,
+ <9653 9653 9707 11096 11290 11278>,
+ <9653 9652 9692 11071 11287 11277>,
+ <9653 9652 9681 10975 11329 11250>,
+ <9653 9652 9674 10939 11356 11231>,
+ <9653 9652 9668 10913 11303 11229>,
+ <9653 9652 9664 10802 11253 11135>,
+ <9653 9652 9663 10839 11180 11044>,
+ <9653 9652 9661 10832 11146 11009>,
+ <9652 9652 9660 10811 11105 10962>,
+ <9652 9651 9659 10794 11061 10965>,
+ <9651 9651 9658 10764 11053 10938>,
+ <9650 9651 9658 10711 10981 10871>,
+ <9650 9651 9656 10651 10927 10829>,
+ <9649 9651 9654 10594 10851 10747>,
+ <9648 9651 9654 10531 10798 10659>,
+ <9648 9651 9654 10531 10798 10659>,
+ <9648 9651 9654 10531 10798 10659>;
};
qcom,pc-temp-y3-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <13677 13390 13309 13301 13279>,
- <13657 13393 13309 13294 13279>,
- <13634 13397 13311 13289 13279>,
- <13612 13400 13312 13285 13279>,
- <13596 13403 13314 13283 13279>,
- <13590 13406 13315 13282 13279>,
- <13594 13408 13315 13283 13280>,
- <13600 13410 13316 13286 13281>,
- <13594 13412 13317 13287 13282>,
- <13548 13416 13319 13287 13282>,
- <13515 13419 13321 13287 13282>,
- <13513 13421 13322 13289 13282>,
- <13512 13423 13323 13291 13282>,
- <13509 13422 13325 13291 13283>,
- <13504 13414 13328 13291 13284>,
- <13497 13407 13329 13291 13286>,
- <13488 13401 13328 13292 13287>,
- <13478 13395 13325 13294 13288>,
- <13470 13387 13324 13297 13290>,
- <13465 13376 13323 13301 13294>,
- <13458 13367 13322 13303 13296>,
- <13428 13360 13315 13297 13290>,
- <13384 13354 13306 13287 13281>,
- <13362 13349 13303 13283 13278>,
- <13349 13346 13300 13281 13277>,
- <13344 13341 13299 13280 13277>,
- <13351 13308 13299 13280 13277>,
- <13369 13266 13299 13282 13277>,
- <13391 13259 13298 13282 13277>,
- <13422 13259 13299 13283 13277>,
- <13460 13258 13299 13283 13277>,
- <13503 13258 13298 13283 13277>,
- <13554 13259 13298 13283 13277>,
- <13615 13263 13298 13283 13277>,
- <13690 13285 13299 13283 13278>,
- <13777 13302 13299 13283 13278>,
- <13879 13294 13296 13281 13277>,
- <13996 13281 13292 13279 13276>,
- <14118 13282 13292 13278 13276>,
- <14247 13299 13292 13277 13277>,
- <14377 13319 13293 13277 13277>,
- <14502 13343 13295 13277 13278>,
- <14624 13368 13298 13277 13278>,
- <14737 13402 13303 13278 13276>,
- <14824 13470 13304 13280 13278>,
- <14801 13476 13307 13284 13280>,
- <14824 13517 13316 13291 13286>,
- <14890 13560 13319 13292 13287>,
- <14961 13607 13332 13295 13287>,
- <15021 13665 13332 13292 13286>,
- <15095 13703 13333 13294 13286>,
- <15215 13779 13341 13296 13289>,
- <15382 13934 13350 13299 13292>,
- <15571 14143 13370 13308 13299>,
- <15571 14143 13370 13308 13299>,
- <15571 14143 13370 13308 13299>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <14501 13677 13390 13309 13301 13279>,
+ <14412 13657 13393 13309 13294 13279>,
+ <14328 13634 13397 13311 13289 13279>,
+ <14249 13612 13400 13312 13285 13279>,
+ <14179 13596 13403 13314 13283 13279>,
+ <14117 13590 13406 13315 13282 13279>,
+ <14063 13594 13408 13315 13283 13280>,
+ <14017 13600 13410 13316 13286 13281>,
+ <13976 13594 13412 13317 13287 13282>,
+ <13939 13548 13416 13319 13287 13282>,
+ <13929 13515 13419 13321 13287 13282>,
+ <13957 13513 13421 13322 13289 13282>,
+ <13986 13512 13423 13323 13291 13282>,
+ <13945 13509 13422 13325 13291 13283>,
+ <13843 13504 13414 13328 13291 13284>,
+ <13803 13497 13407 13329 13291 13286>,
+ <13797 13488 13401 13328 13292 13287>,
+ <13793 13478 13395 13325 13294 13288>,
+ <13788 13470 13387 13324 13297 13290>,
+ <13783 13465 13376 13323 13301 13294>,
+ <13783 13458 13367 13322 13303 13296>,
+ <13788 13428 13360 13315 13297 13290>,
+ <13796 13384 13354 13306 13287 13281>,
+ <13814 13362 13349 13303 13283 13278>,
+ <13843 13349 13346 13300 13281 13277>,
+ <13874 13344 13341 13299 13280 13277>,
+ <13910 13351 13308 13299 13280 13277>,
+ <13952 13369 13266 13299 13282 13277>,
+ <13999 13391 13259 13298 13282 13277>,
+ <14052 13422 13259 13299 13283 13277>,
+ <14110 13460 13258 13299 13283 13277>,
+ <14174 13503 13258 13298 13283 13277>,
+ <14243 13554 13259 13298 13283 13277>,
+ <14318 13615 13263 13298 13283 13277>,
+ <14398 13690 13285 13299 13283 13278>,
+ <14481 13777 13302 13299 13283 13278>,
+ <14568 13879 13294 13296 13281 13277>,
+ <14658 13996 13281 13292 13279 13276>,
+ <14750 14118 13282 13292 13278 13276>,
+ <14850 14247 13299 13292 13277 13277>,
+ <14963 14377 13319 13293 13277 13277>,
+ <15082 14502 13343 13295 13277 13278>,
+ <15198 14624 13368 13298 13277 13278>,
+ <15302 14737 13402 13303 13278 13276>,
+ <15264 14824 13470 13304 13280 13278>,
+ <15439 14801 13476 13307 13284 13280>,
+ <15557 14824 13517 13316 13291 13286>,
+ <15783 14890 13560 13319 13292 13287>,
+ <16058 14961 13607 13332 13295 13287>,
+ <16423 15021 13665 13332 13292 13286>,
+ <16935 15095 13703 13333 13294 13286>,
+ <17701 15215 13779 13341 13296 13289>,
+ <18847 15382 13934 13350 13299 13292>,
+ <20636 15571 14143 13370 13308 13299>,
+ <20636 15571 14143 13370 13308 13299>,
+ <20636 15571 14143 13370 13308 13299>;
};
qcom,pc-temp-y4-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <17305 16798 16610 16483 16470>,
- <17330 16862 16610 16486 16469>,
- <17378 16934 16609 16489 16468>,
- <17433 17001 16608 16491 16467>,
- <17479 17051 16607 16493 16467>,
- <17501 17070 16605 16493 16466>,
- <17503 17059 16603 16493 16466>,
- <17504 17041 16601 16492 16466>,
- <17511 17030 16599 16493 16466>,
- <17550 17023 16599 16497 16470>,
- <17608 17020 16599 16500 16473>,
- <17742 17034 16602 16502 16478>,
- <17902 17062 16609 16506 16483>,
- <17876 17086 16619 16512 16487>,
- <17547 17110 16638 16523 16492>,
- <17320 17134 16659 16535 16498>,
- <17344 17161 16679 16546 16506>,
- <17386 17183 16703 16560 16518>,
- <17370 17170 16748 16586 16537>,
- <17216 17080 16821 16630 16569>,
- <17060 16974 16852 16651 16585>,
- <16974 16865 16754 16602 16552>,
- <16908 16761 16616 16529 16502>,
- <16873 16703 16567 16502 16483>,
- <16851 16662 16543 16489 16473>,
- <16841 16647 16535 16485 16469>,
- <16841 16681 16535 16485 16470>,
- <16842 16727 16535 16487 16471>,
- <16843 16732 16537 16489 16474>,
- <16844 16721 16543 16497 16482>,
- <16845 16716 16549 16507 16491>,
- <16852 16721 16554 16521 16504>,
- <16866 16730 16558 16535 16515>,
- <16879 16732 16556 16540 16518>,
- <16893 16714 16549 16540 16515>,
- <16906 16704 16540 16534 16509>,
- <16920 16735 16528 16505 16492>,
- <16932 16784 16517 16477 16475>,
- <16941 16805 16517 16476 16471>,
- <16947 16815 16522 16479 16469>,
- <16950 16818 16530 16481 16469>,
- <16948 16818 16544 16482 16469>,
- <16945 16817 16555 16481 16467>,
- <16947 16815 16561 16471 16454>,
- <16965 16826 16575 16477 16456>,
- <16961 16849 16584 16493 16477>,
- <16977 16893 16606 16503 16495>,
- <17046 16954 16635 16528 16531>,
- <17107 17025 16679 16557 16532>,
- <17131 17054 16682 16515 16493>,
- <17101 17038 16673 16527 16498>,
- <17060 17051 16712 16548 16514>,
- <17063 17124 16764 16588 16554>,
- <17135 17255 16879 16727 16719>,
- <17135 17255 16879 16727 16719>,
- <17135 17255 16879 16727 16719>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <17448 17305 16798 16610 16483 16470>,
+ <17520 17330 16862 16610 16486 16469>,
+ <17601 17378 16934 16609 16489 16468>,
+ <17679 17433 17001 16608 16491 16467>,
+ <17744 17479 17051 16607 16493 16467>,
+ <17783 17501 17070 16605 16493 16466>,
+ <17798 17503 17059 16603 16493 16466>,
+ <17813 17504 17041 16601 16492 16466>,
+ <17918 17511 17030 16599 16493 16466>,
+ <18180 17550 17023 16599 16497 16470>,
+ <18279 17608 17020 16599 16500 16473>,
+ <18148 17742 17034 16602 16502 16478>,
+ <17945 17902 17062 16609 16506 16483>,
+ <17736 17876 17086 16619 16512 16487>,
+ <17506 17547 17110 16638 16523 16492>,
+ <17399 17320 17134 16659 16535 16498>,
+ <17363 17344 17161 16679 16546 16506>,
+ <17328 17386 17183 16703 16560 16518>,
+ <17266 17370 17170 16748 16586 16537>,
+ <17193 17216 17080 16821 16630 16569>,
+ <17141 17060 16974 16852 16651 16585>,
+ <17100 16974 16865 16754 16602 16552>,
+ <17077 16908 16761 16616 16529 16502>,
+ <17070 16873 16703 16567 16502 16483>,
+ <17066 16851 16662 16543 16489 16473>,
+ <17066 16841 16647 16535 16485 16469>,
+ <17066 16841 16681 16535 16485 16470>,
+ <17067 16842 16727 16535 16487 16471>,
+ <17070 16843 16732 16537 16489 16474>,
+ <17074 16844 16721 16543 16497 16482>,
+ <17079 16845 16716 16549 16507 16491>,
+ <17088 16852 16721 16554 16521 16504>,
+ <17095 16866 16730 16558 16535 16515>,
+ <17099 16879 16732 16556 16540 16518>,
+ <17103 16893 16714 16549 16540 16515>,
+ <17111 16906 16704 16540 16534 16509>,
+ <17124 16920 16735 16528 16505 16492>,
+ <17134 16932 16784 16517 16477 16475>,
+ <17142 16941 16805 16517 16476 16471>,
+ <17149 16947 16815 16522 16479 16469>,
+ <17157 16950 16818 16530 16481 16469>,
+ <17167 16948 16818 16544 16482 16469>,
+ <17187 16945 16817 16555 16481 16467>,
+ <17208 16947 16815 16561 16471 16454>,
+ <17140 16965 16826 16575 16477 16456>,
+ <17176 16961 16849 16584 16493 16477>,
+ <17202 16977 16893 16606 16503 16495>,
+ <17281 17046 16954 16635 16528 16531>,
+ <17390 17107 17025 16679 16557 16532>,
+ <17524 17131 17054 16682 16515 16493>,
+ <17690 17101 17038 16673 16527 16498>,
+ <17978 17060 17051 16712 16548 16514>,
+ <18577 17063 17124 16764 16588 16554>,
+ <20156 17135 17255 16879 16727 16719>,
+ <20156 17135 17255 16879 16727 16719>,
+ <20156 17135 17255 16879 16727 16719>;
};
qcom,pc-temp-y5-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <8712 14223 14774 19943 16308>,
- <8888 14349 15148 18667 15835>,
- <10562 14526 15365 17009 15457>,
- <12204 14713 15466 15353 15176>,
- <13579 14867 15489 14086 14997>,
- <14452 14948 15472 13593 14920>,
- <14948 14973 15335 13800 15003>,
- <15270 14986 15151 14123 15144>,
- <15028 14986 15098 14118 15087>,
- <13370 14973 15056 13826 14716>,
- <12246 14930 14978 13664 14315>,
- <13353 14287 14743 13788 13961>,
- <15163 13386 14398 13870 13634>,
- <15495 13334 14078 13643 13482>,
- <15197 13853 13740 13191 13549>,
- <14993 14346 13497 12887 13638>,
- <15443 14672 13207 12793 13546>,
- <16191 15006 12923 12796 13423>,
- <16138 15417 13004 13001 13548>,
- <14708 15994 13654 13569 14033>,
- <13284 16419 14434 14193 14440>,
- <12599 16670 15491 14905 14826>,
- <12068 16832 16433 15541 15160>,
- <11544 16827 16644 15650 15196>,
- <10962 16682 16591 15306 15346>,
- <10655 16390 16622 15048 15474>,
- <10648 14341 16597 15293 15494>,
- <10645 11728 16540 15744 15472>,
- <10665 11156 16578 15865 15229>,
- <10802 11032 16695 15749 14663>,
- <10946 10959 16756 15607 14352>,
- <11017 10901 16831 15502 14290>,
- <11076 10865 16959 15400 14311>,
- <11177 11054 17363 15705 14665>,
- <11367 12196 18097 16573 15740>,
- <11520 13011 18310 16919 16424>,
- <11584 12496 17269 16620 16376>,
- <11627 11602 15914 16091 16215>,
- <11630 11486 15213 15448 16327>,
- <11595 11681 14700 14692 16543>,
- <11570 11787 14330 14365 16550>,
- <11579 11797 14105 14243 16259>,
- <11596 11778 14219 14209 16346>,
- <11509 11647 14611 15058 16893>,
- <11331 11779 14198 14882 16382>,
- <11388 11508 14156 14882 14589>,
- <11488 11654 14603 16012 16142>,
- <11493 11662 14001 15040 14960>,
- <11613 11939 14918 15399 14828>,
- <11747 12726 15439 17093 17327>,
- <11665 12655 15981 17753 17255>,
- <11585 12280 16288 17881 17960>,
- <11459 12118 16141 17436 18200>,
- <11818 11932 16090 17352 17825>,
- <11818 11932 16090 17352 17825>,
- <11818 11932 16090 17352 17825>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <10030 8712 14223 14774 19943 16308>,
+ <10448 8888 14349 15148 18667 15835>,
+ <10794 10562 14526 15365 17009 15457>,
+ <11054 12204 14713 15466 15353 15176>,
+ <11214 13579 14867 15489 14086 14997>,
+ <11260 14452 14948 15472 13593 14920>,
+ <11143 14948 14973 15335 13800 15003>,
+ <11001 15270 14986 15151 14123 15144>,
+ <11151 15028 14986 15098 14118 15087>,
+ <11850 13370 14973 15056 13826 14716>,
+ <12871 12246 14930 14978 13664 14315>,
+ <15188 13353 14287 14743 13788 13961>,
+ <17100 15163 13386 14398 13870 13634>,
+ <15786 15495 13334 14078 13643 13482>,
+ <12439 15197 13853 13740 13191 13549>,
+ <11406 14993 14346 13497 12887 13638>,
+ <11547 15443 14672 13207 12793 13546>,
+ <11662 16191 15006 12923 12796 13423>,
+ <11574 16138 15417 13004 13001 13548>,
+ <11364 14708 15994 13654 13569 14033>,
+ <11181 13284 16419 14434 14193 14440>,
+ <10986 12599 16670 15491 14905 14826>,
+ <10835 12068 16832 16433 15541 15160>,
+ <10734 11544 16827 16644 15650 15196>,
+ <10666 10962 16682 16591 15306 15346>,
+ <10655 10655 16390 16622 15048 15474>,
+ <10654 10648 14341 16597 15293 15494>,
+ <10654 10645 11728 16540 15744 15472>,
+ <10689 10665 11156 16578 15865 15229>,
+ <10734 10802 11032 16695 15749 14663>,
+ <10745 10946 10959 16756 15607 14352>,
+ <10765 11017 10901 16831 15502 14290>,
+ <10797 11076 10865 16959 15400 14311>,
+ <10882 11177 11054 17363 15705 14665>,
+ <10953 11367 12196 18097 16573 15740>,
+ <10940 11520 13011 18310 16919 16424>,
+ <10897 11584 12496 17269 16620 16376>,
+ <10863 11627 11602 15914 16091 16215>,
+ <10835 11630 11486 15213 15448 16327>,
+ <10820 11595 11681 14700 14692 16543>,
+ <10867 11570 11787 14330 14365 16550>,
+ <10955 11579 11797 14105 14243 16259>,
+ <11030 11596 11778 14219 14209 16346>,
+ <11029 11509 11647 14611 15058 16893>,
+ <11044 11331 11779 14198 14882 16382>,
+ <11143 11388 11508 14156 14882 14589>,
+ <11321 11488 11654 14603 16012 16142>,
+ <11356 11493 11662 14001 15040 14960>,
+ <11206 11613 11939 14918 15399 14828>,
+ <10932 11747 12726 15439 17093 17327>,
+ <10539 11665 12655 15981 17753 17255>,
+ <10263 11585 12280 16288 17881 17960>,
+ <9994 11459 12118 16141 17436 18200>,
+ <9668 11818 11932 16090 17352 17825>,
+ <9668 11818 11932 16090 17352 17825>,
+ <9668 11818 11932 16090 17352 17825>;
};
qcom,pc-temp-y6-lut {
- qcom,lut-col-legend = <0 10 25 40 50>;
- qcom,lut-row-legend = <10000 9800 9600 9400 9200>,
- <9000 8800 8600 8400 8200>,
- <8000 7800 7600 7400 7200>,
- <7000 6800 6600 6400 6200>,
- <6000 5800 5600 5400 5200>,
- <5000 4800 4600 4400 4200>,
- <4000 3800 3600 3400 3200>,
- <3000 2800 2600 2400 2200>,
- <2000 1800 1600 1400 1200>,
- <1000 900 800 700 600>,
- <500 400 300 200 100>,
- <0>;
- qcom,lut-data = <6132 5538 5158 5055 5027>,
- <6176 5550 5158 5053 5026>,
- <6205 5557 5158 5050 5025>,
- <6223 5561 5157 5048 5025>,
- <6232 5562 5156 5046 5025>,
- <6234 5562 5154 5046 5025>,
- <6227 5555 5152 5046 5025>,
- <6211 5540 5150 5047 5026>,
- <6191 5531 5149 5047 5027>,
- <6161 5522 5149 5048 5028>,
- <6144 5519 5149 5049 5029>,
- <6170 5520 5150 5051 5030>,
- <6214 5522 5151 5053 5031>,
- <6207 5523 5154 5055 5033>,
- <6119 5523 5160 5058 5035>,
- <6058 5522 5167 5061 5038>,
- <6060 5524 5172 5065 5041>,
- <6065 5527 5177 5070 5045>,
- <6054 5521 5188 5079 5052>,
- <5986 5487 5208 5095 5064>,
- <5923 5449 5216 5102 5070>,
- <5892 5413 5184 5083 5056>,
- <5871 5381 5138 5056 5035>,
- <5868 5365 5122 5045 5028>,
- <5872 5355 5114 5040 5024>,
- <5878 5349 5111 5038 5023>,
- <5895 5343 5112 5039 5023>,
- <5926 5339 5113 5040 5024>,
- <5960 5339 5115 5042 5026>,
- <5999 5342 5118 5045 5028>,
- <6044 5346 5121 5048 5031>,
- <6096 5354 5124 5053 5034>,
- <6156 5367 5126 5057 5038>,
- <6222 5383 5127 5059 5039>,
- <6297 5405 5127 5060 5039>,
- <6380 5430 5127 5058 5038>,
- <6470 5458 5124 5049 5032>,
- <6568 5491 5120 5041 5027>,
- <6667 5530 5121 5040 5027>,
- <6768 5579 5127 5041 5027>,
- <6867 5632 5133 5042 5028>,
- <6963 5689 5144 5044 5028>,
- <7053 5751 5155 5044 5028>,
- <7135 5817 5167 5043 5024>,
- <7206 5905 5181 5046 5026>,
- <7192 5921 5188 5056 5034>,
- <7214 5976 5205 5063 5044>,
- <7280 6034 5219 5072 5055>,
- <7350 6096 5248 5083 5055>,
- <7405 6155 5252 5069 5043>,
- <7454 6196 5257 5074 5046>,
- <7535 6282 5285 5084 5053>,
- <7666 6442 5320 5100 5069>,
- <7846 6646 5385 5148 5123>,
- <7846 6646 5385 5148 5123>,
- <7846 6646 5385 5148 5123>;
+ qcom,lut-col-legend = <(-10) 0 10 25 40 50>;
+ qcom,lut-row-legend = <10000 9800 9600 9400 9200 9000>,
+ <8800 8600 8400 8200 8000 7800>,
+ <7600 7400 7200 7000 6800 6600>,
+ <6400 6200 6000 5800 5600 5400>,
+ <5200 5000 4800 4600 4400 4200>,
+ <4000 3800 3600 3400 3200 3000>,
+ <2800 2600 2400 2200 2000 1800>,
+ <1600 1400 1200 1000 900 800>,
+ <700 600 500 400 300 200>,
+ <100 0>;
+ qcom,lut-data = <7467 6132 5538 5158 5055 5027>,
+ <7418 6176 5550 5158 5053 5026>,
+ <7371 6205 5557 5158 5050 5025>,
+ <7326 6223 5561 5157 5048 5025>,
+ <7283 6232 5562 5156 5046 5025>,
+ <7242 6234 5562 5154 5046 5025>,
+ <7194 6227 5555 5152 5046 5025>,
+ <7159 6211 5540 5150 5047 5026>,
+ <7167 6191 5531 5149 5047 5027>,
+ <7202 6161 5522 5149 5048 5028>,
+ <7216 6144 5519 5149 5049 5029>,
+ <7195 6170 5520 5150 5051 5030>,
+ <7155 6214 5522 5151 5053 5031>,
+ <7075 6207 5523 5154 5055 5033>,
+ <6953 6119 5523 5160 5058 5035>,
+ <6899 6058 5522 5167 5061 5038>,
+ <6884 6060 5524 5172 5065 5041>,
+ <6872 6065 5527 5177 5070 5045>,
+ <6853 6054 5521 5188 5079 5052>,
+ <6834 5986 5487 5208 5095 5064>,
+ <6828 5923 5449 5216 5102 5070>,
+ <6826 5892 5413 5184 5083 5056>,
+ <6825 5871 5381 5138 5056 5035>,
+ <6839 5868 5365 5122 5045 5028>,
+ <6867 5872 5355 5114 5040 5024>,
+ <6893 5878 5349 5111 5038 5023>,
+ <6923 5895 5343 5112 5039 5023>,
+ <6956 5926 5339 5113 5040 5024>,
+ <6991 5960 5339 5115 5042 5026>,
+ <7030 5999 5342 5118 5045 5028>,
+ <7074 6044 5346 5121 5048 5031>,
+ <7122 6096 5354 5124 5053 5034>,
+ <7175 6156 5367 5126 5057 5038>,
+ <7232 6222 5383 5127 5059 5039>,
+ <7293 6297 5405 5127 5060 5039>,
+ <7357 6380 5430 5127 5058 5038>,
+ <7425 6470 5458 5124 5049 5032>,
+ <7495 6568 5491 5120 5041 5027>,
+ <7567 6667 5530 5121 5040 5027>,
+ <7643 6768 5579 5127 5041 5027>,
+ <7727 6867 5632 5133 5042 5028>,
+ <7816 6963 5689 5144 5044 5028>,
+ <7908 7053 5751 5155 5044 5028>,
+ <7994 7135 5817 5167 5043 5024>,
+ <7959 7206 5905 5181 5046 5026>,
+ <8096 7192 5921 5188 5056 5034>,
+ <8195 7214 5976 5205 5063 5044>,
+ <8412 7280 6034 5219 5072 5055>,
+ <8678 7350 6096 5248 5083 5055>,
+ <9031 7405 6155 5252 5069 5043>,
+ <9521 7454 6196 5257 5074 5046>,
+ <10251 7535 6282 5285 5084 5053>,
+ <11352 7666 6442 5320 5100 5069>,
+ <13075 7846 6646 5385 5148 5123>,
+ <13075 7846 6646 5385 5148 5123>,
+ <13075 7846 6646 5385 5148 5123>;
};
-
};
diff --git a/arch/arm64/boot/dts/qcom/sda429-cdp.dts b/arch/arm64/boot/dts/qcom/sda429-cdp.dts
new file mode 100644
index 0000000..6b895f1
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sda429-cdp.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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 "sda429.dtsi"
+#include "sdm429-cdp.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDA429 CDP";
+ compatible = "qcom,sda429-cdp", "qcom,sda429", "qcom,cdp";
+ qcom,board-id = <1 3>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sda429-mtp.dts b/arch/arm64/boot/dts/qcom/sda429-mtp.dts
new file mode 100644
index 0000000..b27fec9
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sda429-mtp.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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 "sda429.dtsi"
+#include "sdm429-mtp.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDA429 MTP";
+ compatible = "qcom,sda429-mtp", "qcom,sda429", "qcom,mtp";
+ qcom,board-id = <8 2>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sda429.dtsi b/arch/arm64/boot/dts/qcom/sda429.dtsi
new file mode 100644
index 0000000..75c8d67
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sda429.dtsi
@@ -0,0 +1,20 @@
+/*
+ * Copyright (c) 2018, 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 "sdm429.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDA429";
+ compatible = "qcom,sda429";
+ qcom,msm-id = <364 0x0>;
+ qcom,msm-name = "SDA429";
+};
diff --git a/arch/arm64/boot/dts/qcom/sda439-cdp.dts b/arch/arm64/boot/dts/qcom/sda439-cdp.dts
new file mode 100644
index 0000000..1194676
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sda439-cdp.dts
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2018, 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 "sda439.dtsi"
+#include "sdm439-cdp.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDA439 CDP";
+ compatible = "qcom,sda439-cdp", "qcom,sda439", "qcom,cdp";
+ qcom,board-id = <1 2>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sda439-mtp.dts b/arch/arm64/boot/dts/qcom/sda439-mtp.dts
new file mode 100644
index 0000000..edc5c85
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sda439-mtp.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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 "sda439.dtsi"
+#include "sdm439-mtp.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDA439 MTP";
+ compatible = "qcom,sda439-mtp", "qcom,sda439", "qcom,mtp";
+ qcom,board-id = <8 1>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sda439.dtsi b/arch/arm64/boot/dts/qcom/sda439.dtsi
new file mode 100644
index 0000000..1600bef
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sda439.dtsi
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2018, 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 "sdm439.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDA439";
+ compatible = "qcom,sda439";
+ qcom,msm-id = <363 0x0>;
+ qcom,msm-name = "SDA439";
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-cdp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm429-cdp-overlay.dts
new file mode 100644
index 0000000..93a9ae9
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm429-cdp-overlay.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/clock/msm-clocks-8953.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "sdm429-cdp.dtsi"
+
+/ {
+ model = "CDP";
+ qcom,board-id = <1 3>;
+ qcom,msm-id = <354 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-cdp.dts b/arch/arm64/boot/dts/qcom/sdm429-cdp.dts
index f3312bd..14bba82 100644
--- a/arch/arm64/boot/dts/qcom/sdm429-cdp.dts
+++ b/arch/arm64/boot/dts/qcom/sdm429-cdp.dts
@@ -19,6 +19,6 @@
/ {
model = "Qualcomm Technologies, Inc. SDM429 CDP";
compatible = "qcom,sdm429-cdp", "qcom,sdm429", "qcom,cdp";
- qcom,board-id = <1 0>;
+ qcom,board-id = <1 3>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-cdp.dtsi b/arch/arm64/boot/dts/qcom/sdm429-cdp.dtsi
index 4ba4c00..d53ba37 100644
--- a/arch/arm64/boot/dts/qcom/sdm429-cdp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm429-cdp.dtsi
@@ -12,3 +12,7 @@
*/
#include "sdm439-cdp.dtsi"
+
+&mdss_dsi0 {
+ qcom,dsi-pref-prim-pan = <&dsi_hx8399c_hd_vid>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-cpu.dtsi b/arch/arm64/boot/dts/qcom/sdm429-cpu.dtsi
index 80f7007..ab874c9 100644
--- a/arch/arm64/boot/dts/qcom/sdm429-cpu.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm429-cpu.dtsi
@@ -128,7 +128,7 @@
CPU_COST_0: core-cost0 {
busy-cost-data = <
- 800000 137
+ 960000 159
1001600 165
1305600 207
1497600 256
@@ -141,7 +141,7 @@
};
CLUSTER_COST_0: cluster-cost0 {
busy-cost-data = <
- 800000 49
+ 960000 52
1001600 53
1305600 61
1497600 71
@@ -154,3 +154,7 @@
};
};
};
+
+&soc {
+ /delete-node/ cpuss_dump;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-mtp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm429-mtp-overlay.dts
new file mode 100644
index 0000000..3a339da
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm429-mtp-overlay.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/clock/msm-clocks-8953.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "sdm429-mtp.dtsi"
+
+/ {
+ model = "MTP";
+ qcom,board-id = <8 2>;
+ qcom,msm-id = <354 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-mtp.dts b/arch/arm64/boot/dts/qcom/sdm429-mtp.dts
index a809be7..d66ee61 100644
--- a/arch/arm64/boot/dts/qcom/sdm429-mtp.dts
+++ b/arch/arm64/boot/dts/qcom/sdm429-mtp.dts
@@ -19,6 +19,6 @@
/ {
model = "Qualcomm Technologies, Inc. SDM429 MTP";
compatible = "qcom,sdm429-mtp", "qcom,sdm429", "qcom,mtp";
- qcom,board-id = <8 0>;
+ qcom,board-id = <8 2>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-mtp.dtsi b/arch/arm64/boot/dts/qcom/sdm429-mtp.dtsi
index 839fa56..4f00be1 100644
--- a/arch/arm64/boot/dts/qcom/sdm429-mtp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm429-mtp.dtsi
@@ -12,3 +12,7 @@
*/
#include "sdm439-mtp.dtsi"
+
+&mdss_dsi0 {
+ qcom,dsi-pref-prim-pan = <&dsi_hx8399c_hd_vid>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-qrd-overlay.dts b/arch/arm64/boot/dts/qcom/sdm429-qrd-overlay.dts
new file mode 100644
index 0000000..8abccb7
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm429-qrd-overlay.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/clock/msm-clocks-8953.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "sdm429-qrd.dtsi"
+
+/ {
+ model = "QRD";
+ qcom,board-id = <0xb 3>;
+ qcom,msm-id = <354 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429-qrd.dts b/arch/arm64/boot/dts/qcom/sdm429-qrd.dts
index d97cf54..034e221 100644
--- a/arch/arm64/boot/dts/qcom/sdm429-qrd.dts
+++ b/arch/arm64/boot/dts/qcom/sdm429-qrd.dts
@@ -19,6 +19,6 @@
/ {
model = "Qualcomm Technologies, Inc. SDM429 QRD";
compatible = "qcom,sdm429-qrd", "qcom,sdm429", "qcom,qrd";
- qcom,board-id = <0xb 0>;
+ qcom,board-id = <0xb 3>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
diff --git a/arch/arm64/boot/dts/qcom/sdm429.dts b/arch/arm64/boot/dts/qcom/sdm429.dts
new file mode 100644
index 0000000..d8538bb
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm429.dts
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2018, 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 "sdm429.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM429 MTP";
+ compatible = "qcom,sdm429";
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+ qcom.pmic-name = "PMI632";
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm429.dtsi b/arch/arm64/boot/dts/qcom/sdm429.dtsi
index a4d2a80..42407af 100644
--- a/arch/arm64/boot/dts/qcom/sdm429.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm429.dtsi
@@ -38,6 +38,53 @@
/delete-node/qcom,pm-cluster@1;
};
};
+
+ msm_cpufreq: qcom,msm-cpufreq {
+ compatible = "qcom,msm-cpufreq";
+ clock-names =
+ "l2_clk",
+ "cpu0_clk";
+ clocks = <&clock_cpu clk_cci_clk>,
+ <&clock_cpu clk_a53_bc_clk>;
+
+ qcom,governor-per-policy;
+
+ qcom,cpufreq-table =
+ < 960000 >,
+ < 1305600 >,
+ < 1497600 >,
+ < 1708800 >,
+ < 1958400 >;
+ };
+
+ devfreq-cpufreq {
+ cpubw-cpufreq {
+ target-dev = <&cpubw>;
+ cpu-to-dev-map =
+ < 960000 2929 >,
+ < 1305600 5053 >,
+ < 1497600 5712 >,
+ < 1708800 7031 >,
+ < 1958400 7031 >;
+ };
+
+ cci-cpufreq {
+ target-dev = <&cci_cache>;
+ cpu-to-dev-map =
+ < 960000 400000 >,
+ < 1305600 400000 >,
+ < 1497600 533333 >,
+ < 1708800 533333 >,
+ < 1958400 533333 >;
+ };
+
+ mincpubw-cpufreq {
+ target-dev = <&mincpubw>;
+ cpu-to-dev-map =
+ < 1305600 2929 >,
+ < 1958400 4248 >;
+ };
+ };
};
&funnel_apss {
diff --git a/arch/arm64/boot/dts/qcom/sdm439-camera-sensor-qrd.dtsi b/arch/arm64/boot/dts/qcom/sdm439-camera-sensor-qrd.dtsi
new file mode 100644
index 0000000..c2c9c79
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm439-camera-sensor-qrd.dtsi
@@ -0,0 +1,287 @@
+/*
+ * Copyright (c) 2015-2016, 2018 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.
+ */
+
+&cci {
+ actuator0: qcom,actuator@0 {
+ cell-index = <0>;
+ reg = <0x0>;
+ compatible = "qcom,actuator";
+ qcom,cci-master = <0>;
+ cam_vaf-supply = <&pm8953_l17>;
+ qcom,cam-vreg-name = "cam_vaf";
+ qcom,cam-vreg-min-voltage = <2850000>;
+ qcom,cam-vreg-max-voltage = <2850000>;
+ qcom,cam-vreg-op-mode = <80000>;
+ };
+
+ actuator1: qcom,actuator@1 {
+ cell-index = <1>;
+ reg = <0x1>;
+ compatible = "qcom,actuator";
+ qcom,cci-master = <0>;
+ cam_vaf-supply = <&pm8953_l17>;
+ qcom,cam-vreg-name = "cam_vaf";
+ qcom,cam-vreg-min-voltage = <2850000>;
+ qcom,cam-vreg-max-voltage = <2850000>;
+ qcom,cam-vreg-op-mode = <80000>;
+ };
+
+ eeprom0: qcom,eeprom@0 {
+ cell-index = <0>;
+ compatible = "qcom,eeprom";
+ qcom,cci-master = <0>;
+ reg = <0x0>;
+ cam_vana-supply = <&pm8953_l22>;
+ cam_vio-supply = <&pm8953_l6>;
+ cam_vaf-supply = <&pm8953_l17>;
+ cam_vdig-supply = <&pm8953_l3>;
+ qcom,cam-vreg-name = "cam_vana", "cam_vio",
+ "cam_vdig", "cam_vaf";
+ qcom,cam-vreg-min-voltage = <2800000 0 1200000 2850000>;
+ qcom,cam-vreg-max-voltage = <2800000 0 1200000 2850000>;
+ qcom,cam-vreg-op-mode = <80000 0 200000 100000>;
+ pinctrl-names = "cam_default", "cam_suspend";
+ pinctrl-0 = <&cam_sensor_mclk0_default
+ &cam_sensor_rear_reset
+ &cam_sensor_rear_vana>;
+ pinctrl-1 = <&cam_sensor_mclk0_sleep
+ &cam_sensor_rear_reset_sleep
+ &cam_sensor_rear_vana_sleep>;
+ gpios = <&tlmm 26 0>,
+ <&tlmm 36 0>,
+ <&tlmm 35 0>;
+ qcom,gpio-reset = <1>;
+ qcom,gpio-vana = <2>;
+ qcom,gpio-req-tbl-num = <0 1 2>;
+ qcom,gpio-req-tbl-flags = <1 0 0>;
+ qcom,gpio-req-tbl-label = "CAMIF_MCLK0",
+ "CAM_RESET0",
+ "CAM_VANA";
+ status = "ok";
+ clocks = <&clock_gcc clk_mclk0_clk_src>,
+ <&clock_gcc clk_gcc_camss_mclk0_clk>;
+ clock-names = "cam_src_clk", "cam_clk";
+ qcom,clock-rates = <19200000 0>;
+ };
+
+ eeprom1: qcom,eeprom@1 {
+ cell-index = <1>;
+ reg = <0x1>;
+ qcom,eeprom-name = "sunny_8865";
+ compatible = "qcom,eeprom";
+ qcom,slave-addr = <0x6c>;
+ qcom,cci-master = <0>;
+ qcom,num-blocks = <8>;
+
+ qcom,page0 = <1 0x0100 2 0x01 1 1>;
+ qcom,poll0 = <0 0x0 2 0x0 1 0>;
+ qcom,mem0 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page1 = <1 0x5002 2 0x00 1 0>;
+ qcom,poll1 = <0 0x0 2 0x0 1 0>;
+ qcom,mem1 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page2 = <1 0x3d84 2 0xc0 1 0>;
+ qcom,poll2 = <0 0x0 2 0x0 1 0>;
+ qcom,mem2 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page3 = <1 0x3d88 2 0x70 1 0>;
+ qcom,poll3 = <0 0x0 2 0x0 1 0>;
+ qcom,mem3 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page4 = <1 0x3d89 2 0x10 1 0>;
+ qcom,poll4 = <0 0x0 2 0x0 1 0>;
+ qcom,mem4 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page5 = <1 0x3d8a 2 0x70 1 0>;
+ qcom,poll5 = <0 0x0 2 0x0 1 0>;
+ qcom,mem5 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page6 = <1 0x3d8b 2 0xf4 1 0>;
+ qcom,poll6 = <0 0x0 2 0x0 1 0>;
+ qcom,mem6 = <0 0x0 2 0x0 1 0>;
+
+ qcom,page7 = <1 0x3d81 2 0x01 1 10>;
+ qcom,poll7 = <0 0x0 2 0x0 1 1>;
+ qcom,mem7 = <1536 0x7010 2 0 1 0>;
+
+ cam_vdig-supply = <&pm8953_l23>;
+ cam_vana-supply = <&pm8953_l22>;
+ cam_vio-supply = <&pm8953_l6>;
+ cam_vaf-supply = <&pm8953_l17>;
+ qcom,cam-vreg-name = "cam_vdig", "cam_vio",
+ "cam_vana", "cam_vaf";
+ qcom,cam-vreg-min-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-max-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-op-mode = <105000 0 80000 100000>;
+ qcom,gpio-no-mux = <0>;
+ pinctrl-names = "cam_default", "cam_suspend";
+ pinctrl-0 = <&cam_sensor_mclk2_default
+ &cam_sensor_front1_default>;
+ pinctrl-1 = <&cam_sensor_mclk2_sleep
+ &cam_sensor_front1_sleep>;
+ gpios = <&tlmm 28 0>,
+ <&tlmm 40 0>,
+ <&tlmm 39 0>;
+ qcom,gpio-reset = <1>;
+ qcom,gpio-standby = <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_STANDBY2";
+ qcom,cam-power-seq-type = "sensor_vreg", "sensor_vreg",
+ "sensor_vreg",
+ "sensor_gpio", "sensor_gpio" , "sensor_clk";
+ qcom,cam-power-seq-val = "cam_vdig", "cam_vana", "cam_vio",
+ "sensor_gpio_reset", "sensor_gpio_standby",
+ "sensor_cam_mclk";
+ qcom,cam-power-seq-cfg-val = <1 1 1 1 1 24000000>;
+ qcom,cam-power-seq-delay = <1 1 1 30 30 5>;
+ status = "ok";
+ clocks = <&clock_gcc clk_mclk2_clk_src>,
+ <&clock_gcc clk_gcc_camss_mclk2_clk>;
+ clock-names = "cam_src_clk", "cam_clk";
+ qcom,clock-rates = <19200000 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,eeprom-src = <&eeprom0>;
+ qcom,actuator-src = <&actuator0>;
+ cam_vana-supply = <&pm8953_l22>;
+ cam_vio-supply = <&pm8953_l6>;
+ cam_vaf-supply = <&pm8953_l17>;
+ cam_vdig-supply = <&pm8953_l3>;
+ qcom,cam-vreg-name = "cam_vana", "cam_vio",
+ "cam_vdig", "cam_vaf";
+ qcom,cam-vreg-min-voltage = <2800000 0 1200000 2850000>;
+ qcom,cam-vreg-max-voltage = <2800000 0 1200000 2850000>;
+ qcom,cam-vreg-op-mode = <80000 0 200000 100000>;
+ pinctrl-names = "cam_default", "cam_suspend";
+ pinctrl-0 = <&cam_sensor_mclk0_default
+ &cam_sensor_rear_reset
+ &cam_sensor_rear_vana>;
+ pinctrl-1 = <&cam_sensor_mclk0_sleep
+ &cam_sensor_rear_reset_sleep
+ &cam_sensor_rear_vana_sleep>;
+ gpios = <&tlmm 26 0>,
+ <&tlmm 36 0>,
+ <&tlmm 35 0>;
+ qcom,gpio-reset = <1>;
+ qcom,gpio-vana = <2>;
+ qcom,gpio-req-tbl-num = <0 1 2>;
+ qcom,gpio-req-tbl-flags = <1 0 0>;
+ qcom,gpio-req-tbl-label = "CAMIF_MCLK0",
+ "CAM_RESET0",
+ "CAM_VANA";
+ qcom,sensor-position = <0>;
+ qcom,sensor-mode = <0>;
+ qcom,cci-master = <0>;
+ status = "ok";
+ clocks = <&clock_gcc clk_mclk0_clk_src>,
+ <&clock_gcc clk_gcc_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 = <270>;
+ cam_vdig-supply = <&pm8953_l3>;
+ cam_vana-supply = <&pm8953_l22>;
+ cam_vio-supply = <&pm8953_l6>;
+ cam_vaf-supply = <&pm8953_l17>;
+ qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana",
+ "cam_vaf";
+ qcom,cam-vreg-min-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-max-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-op-mode = <200000 0 80000 100000>;
+ pinctrl-names = "cam_default", "cam_suspend";
+ pinctrl-0 = <&cam_sensor_mclk1_default
+ &cam_sensor_front_default>;
+ pinctrl-1 = <&cam_sensor_mclk1_sleep
+ &cam_sensor_front_sleep>;
+ gpios = <&tlmm 27 0>,
+ <&tlmm 38 0>,
+ <&tlmm 50 0>;
+ qcom,gpio-reset = <1>;
+ qcom,gpio-standby = <2>;
+ qcom,gpio-req-tbl-num = <0 1 2>;
+ qcom,gpio-req-tbl-flags = <1 0 0>;
+ qcom,gpio-req-tbl-label = "CAMIF_MCLK1",
+ "CAM_RESET1",
+ "CAM_STANDBY1";
+ qcom,sensor-position = <0x100>;
+ qcom,sensor-mode = <1>;
+ qcom,cci-master = <1>;
+ clocks = <&clock_gcc clk_mclk1_clk_src>,
+ <&clock_gcc clk_gcc_camss_mclk1_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 = <1>;
+ qcom,csid-sd-index = <1>;
+ qcom,mount-angle = <270>;
+ qcom,eeprom-src = <&eeprom1>;
+ qcom,actuator-src = <&actuator1>;
+ cam_vdig-supply = <&pm8953_l3>;
+ cam_vana-supply = <&pm8953_l22>;
+ cam_vio-supply = <&pm8953_l6>;
+ cam_vaf-supply = <&pm8953_l17>;
+ qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana",
+ "cam_vaf";
+ qcom,cam-vreg-min-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-max-voltage = <1200000 0 2800000 2850000>;
+ qcom,cam-vreg-op-mode = <105000 0 80000 100000>;
+ qcom,gpio-no-mux = <0>;
+ pinctrl-names = "cam_default", "cam_suspend";
+ pinctrl-0 = <&cam_sensor_mclk2_default
+ &cam_sensor_front1_default>;
+ pinctrl-1 = <&cam_sensor_mclk2_sleep
+ &cam_sensor_front1_sleep>;
+ gpios = <&tlmm 27 0>,
+ <&tlmm 38 0>,
+ <&tlmm 39 0>;
+ qcom,gpio-reset = <1>;
+ qcom,gpio-standby = <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_STANDBY2";
+ qcom,sensor-position = <1>;
+ qcom,sensor-mode = <0>;
+ qcom,cci-master = <0>;
+ status = "ok";
+ clocks = <&clock_gcc clk_mclk2_clk_src>,
+ <&clock_gcc clk_gcc_camss_mclk2_clk>;
+ clock-names = "cam_src_clk", "cam_clk";
+ qcom,clock-rates = <24000000 0>;
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-cdp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm439-cdp-overlay.dts
new file mode 100644
index 0000000..6d6f99b
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm439-cdp-overlay.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/clock/msm-clocks-8953.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "sdm439-cdp.dtsi"
+
+/ {
+ model = "CDP";
+ qcom,board-id = <1 2>;
+ qcom,msm-id = <353 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-cdp.dts b/arch/arm64/boot/dts/qcom/sdm439-cdp.dts
index 1306230..0128c65 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-cdp.dts
+++ b/arch/arm64/boot/dts/qcom/sdm439-cdp.dts
@@ -19,6 +19,6 @@
/ {
model = "Qualcomm Technologies, Inc. SDM439 CDP";
compatible = "qcom,sdm439-cdp", "qcom,sdm439", "qcom,cdp";
- qcom,board-id = <1 0>;
+ qcom,board-id = <1 2>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-cdp.dtsi b/arch/arm64/boot/dts/qcom/sdm439-cdp.dtsi
index 83a4651..b106e45 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-cdp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm439-cdp.dtsi
@@ -138,7 +138,7 @@
qcom,platform-bklight-en-gpio = <&pm8953_gpios 4 0>;
qcom,platform-te-gpio = <&tlmm 24 0>;
- qcom,platform-reset-gpio = <&tlmm 61 0>;
+ qcom,platform-reset-gpio = <&tlmm 60 0>;
lab-supply = <&lcdb_ldo_vreg>;
ibb-supply = <&lcdb_ncp_vreg>;
diff --git a/arch/arm64/boot/dts/qcom/sdm439-mtp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm439-mtp-overlay.dts
new file mode 100644
index 0000000..df8a0d7
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm439-mtp-overlay.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/clock/msm-clocks-8953.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "sdm439-mtp.dtsi"
+
+/ {
+ model = "MTP";
+ qcom,board-id = <8 1>;
+ qcom,msm-id = <353 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-mtp.dts b/arch/arm64/boot/dts/qcom/sdm439-mtp.dts
index 9f221f0..77f3039 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-mtp.dts
+++ b/arch/arm64/boot/dts/qcom/sdm439-mtp.dts
@@ -19,6 +19,6 @@
/ {
model = "Qualcomm Technologies, Inc. SDM439 MTP";
compatible = "qcom,sdm439-mtp", "qcom,sdm439", "qcom,mtp";
- qcom,board-id = <8 0>;
+ qcom,board-id = <8 1>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-mtp.dtsi b/arch/arm64/boot/dts/qcom/sdm439-mtp.dtsi
index 17218a8..01d7144 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-mtp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm439-mtp.dtsi
@@ -138,7 +138,7 @@
qcom,platform-bklight-en-gpio = <&pm8953_gpios 4 0>;
qcom,platform-te-gpio = <&tlmm 24 0>;
- qcom,platform-reset-gpio = <&tlmm 61 0>;
+ qcom,platform-reset-gpio = <&tlmm 60 0>;
lab-supply = <&lcdb_ldo_vreg>;
ibb-supply = <&lcdb_ncp_vreg>;
diff --git a/arch/arm64/boot/dts/qcom/sdm439-pm8953.dtsi b/arch/arm64/boot/dts/qcom/sdm439-pm8953.dtsi
index 3c8a298..452f0c7 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-pm8953.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm439-pm8953.dtsi
@@ -125,8 +125,8 @@
};
&mdss_dsi {
- vdda-supply = <&pm8953_l2>; /*1.2V*/
- vddio-supply = <&pm8953_l6>; /*1.8V*/
+ vdda-supply = <&pm8953_l23>;
+ vddio-supply = <&pm8953_l6>;
};
&usb_otg {
diff --git a/arch/arm64/boot/dts/qcom/sdm439-qrd-overlay.dts b/arch/arm64/boot/dts/qcom/sdm439-qrd-overlay.dts
new file mode 100644
index 0000000..ac059c4d
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm439-qrd-overlay.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+ #include <dt-bindings/gpio/gpio.h>
+ #include <dt-bindings/clock/msm-clocks-8953.h>
+ #include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "sdm439-qrd.dtsi"
+
+/ {
+ model = "QRD";
+ qcom,board-id = <0xb 2>;
+ qcom,msm-id = <353 0x0>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-qrd.dts b/arch/arm64/boot/dts/qcom/sdm439-qrd.dts
index 7b93e0c..b8a9f2b 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-qrd.dts
+++ b/arch/arm64/boot/dts/qcom/sdm439-qrd.dts
@@ -19,6 +19,13 @@
/ {
model = "Qualcomm Technologies, Inc. SDM439 QRD";
compatible = "qcom,sdm439-qrd", "qcom,sdm439", "qcom,qrd";
- qcom,board-id = <0xb 0>;
+ qcom,board-id = <0xb 2>;
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
+
+&pmi632_vadc {
+ chan@4a {
+ qcom,scale-function = <22>;
+ };
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm439-qrd.dtsi b/arch/arm64/boot/dts/qcom/sdm439-qrd.dtsi
index 24748dd..e54e46e 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-qrd.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm439-qrd.dtsi
@@ -11,6 +11,9 @@
* GNU General Public License for more details.
*/
+#include "msm8937-mdss-panels.dtsi"
+#include "sdm439-camera-sensor-qrd.dtsi"
+
&blsp1_uart2 {
status = "ok";
};
@@ -100,3 +103,152 @@
};
};
};
+
+&tlmm {
+ pmx_ts_rst_active {
+ ts_rst_active: ts_rst_active {
+ mux {
+ pins = "gpio99";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio99";
+ drive-strength = <16>;
+ bias-pull-up;
+ };
+ };
+ };
+
+ pmx_ts_rst_suspend {
+ ts_rst_suspend: ts_rst_suspend {
+ mux {
+ pins = "gpio99";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio99";
+ drive-strength = <2>;
+ bias-pull-down;
+ };
+ };
+ };
+};
+
+&soc {
+ hbtp {
+ compatible = "qcom,hbtp-input";
+ pinctrl-names = "pmx_ts_active", "pmx_ts_suspend";
+ pinctrl-0 = <&ts_rst_active>;
+ pinctrl-1 = <&ts_rst_suspend>;
+ vcc_ana-supply = <&pm8953_l10>;
+ vcc_dig-supply = <&pm8953_l5>;
+ qcom,afe-load = <20000>;
+ qcom,afe-vtg-min = <3000000>;
+ qcom,afe-vtg-max = <3000000>;
+ qcom,dig-load = <40000>;
+ qcom,dig-vtg-min = <1800000>;
+ qcom,dig-vtg-max = <1800000>;
+ qcom,fb-resume-delay-us = <1000>;
+ qcom,afe-force-power-on;
+ qcom,afe-power-on-delay-us = <6>;
+ qcom,afe-power-off-delay-us = <6>;
+ };
+};
+
+&tlmm {
+ pmx_mdss {
+ mdss_dsi_active: mdss_dsi_active {
+ mux {
+ pins = "gpio60";
+ };
+ config {
+ pins = "gpio60";
+ };
+ };
+ mdss_dsi_suspend: mdss_dsi_suspend {
+ mux {
+ pins = "gpio60";
+ };
+ config {
+ pins = "gpio60";
+ };
+ };
+ };
+};
+
+&dsi_panel_pwr_supply {
+ qcom,panel-supply-entry@0 {
+ reg = <0>;
+ qcom,supply-name = "bklight_en";
+ qcom,supply-min-voltage = <1800000>;
+ qcom,supply-max-voltage = <1800000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+
+ qcom,panel-supply-entry@2 {
+ reg = <2>;
+ qcom,supply-name = "lab";
+ qcom,supply-min-voltage = <4600000>;
+ qcom,supply-max-voltage = <6000000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+
+ qcom,panel-supply-entry@3 {
+ reg = <3>;
+ qcom,supply-name = "ibb";
+ qcom,supply-min-voltage = <4600000>;
+ qcom,supply-max-voltage = <6000000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ qcom,supply-post-on-sleep = <10>;
+ };
+};
+
+&mdss_dsi {
+ hw-config = "single_dsi";
+};
+
+&mdss_mdp {
+ qcom,mdss-pref-prim-intf = "dsi";
+};
+
+&mdss_dsi0 {
+ lab-supply = <&lcdb_ldo_vreg>;
+ ibb-supply = <&lcdb_ncp_vreg>;
+ bklight_en-supply = <&pm8953_l5>;
+ vddio-supply = <&pm8953_l6>;
+
+ qcom,dsi-pref-prim-pan = <&dsi_hx8399c_truly_vid>;
+ /delete-property/ qcom,platform-bklight-en-gpio;
+ pinctrl-names = "mdss_default", "mdss_sleep";
+ pinctrl-0 = <&mdss_dsi_active &mdss_te_active>;
+ pinctrl-1 = <&mdss_dsi_suspend &mdss_te_suspend>;
+ qcom,platform-te-gpio = <&tlmm 24 0>;
+ qcom,platform-reset-gpio = <&tlmm 60 0>;
+};
+
+&mdss_dsi1 {
+ status = "disabled";
+};
+
+&pm8953_pwm {
+ status = "ok";
+};
+
+&dsi_hx8399c_truly_vid {
+ qcom,mdss-dsi-bl-pmic-control-type = "bl_ctrl_pwm";
+ qcom,mdss-dsi-bl-pmic-pwm-frequency = <100>;
+ qcom,mdss-dsi-bl-pmic-bank-select = <0>;
+ qcom,mdss-dsi-pwm-gpio = <&pm8953_gpios 8 0>;
+ qcom,panel-supply-entries = <&dsi_panel_pwr_supply>;
+ qcom,mdss-dsi-panel-timings =
+ [7e 48 3c 00 64 59 3b 4a 5e 03 04 00];
+ qcom,mdss-dsi-t-clk-post = <0x1e>;
+ qcom,mdss-dsi-t-clk-pre = <0x32>;
+ qcom,mdss-dsi-pan-enable-dynamic-fps;
+ qcom,mdss-dsi-pan-fps-update = "dfps_immediate_porch_mode_vfp";
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439-regulator.dtsi b/arch/arm64/boot/dts/qcom/sdm439-regulator.dtsi
index 08c9e4f..f325925 100644
--- a/arch/arm64/boot/dts/qcom/sdm439-regulator.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm439-regulator.dtsi
@@ -21,7 +21,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,use-voltage-level;
status = "okay";
};
@@ -37,7 +37,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,use-voltage-level;
};
@@ -48,7 +48,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,use-voltage-floor-level;
qcom,always-send-voltage;
};
@@ -60,7 +60,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,use-voltage-level;
};
@@ -76,9 +76,9 @@
rpm-regulator-smpa3 {
status = "okay";
pm8953_s3: regulator-s3 {
- regulator-min-microvolt = <1280000>;
+ regulator-min-microvolt = <856000>;
regulator-max-microvolt = <1280000>;
- qcom,init-voltage = <1280000>;
+ qcom,init-voltage = <856000>;
status = "okay";
};
};
@@ -86,9 +86,9 @@
rpm-regulator-smpa4 {
status = "okay";
pm8953_s4: regulator-s4 {
- regulator-min-microvolt = <2040000>;
+ regulator-min-microvolt = <1900000>;
regulator-max-microvolt = <2040000>;
- qcom,init-voltage = <2040000>;
+ qcom,init-voltage = <1900000>;
status = "okay";
};
};
@@ -103,7 +103,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,init-voltage-level =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
qcom,use-voltage-level;
@@ -117,7 +117,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,use-voltage-level;
qcom,always-send-voltage;
};
@@ -129,7 +129,7 @@
regulator-min-microvolt =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
regulator-max-microvolt =
- <RPM_SMD_REGULATOR_LEVEL_TURBO>;
+ <RPM_SMD_REGULATOR_LEVEL_BINNING>;
qcom,init-voltage-level =
<RPM_SMD_REGULATOR_LEVEL_RETENTION>;
qcom,use-voltage-level;
@@ -139,9 +139,9 @@
rpm-regulator-ldoa1 {
status = "okay";
pm8953_l1: regulator-l1 {
- regulator-min-microvolt = <1000000>;
- regulator-max-microvolt = <1000000>;
- qcom,init-voltage = <1000000>;
+ regulator-min-microvolt = <968000>;
+ regulator-max-microvolt = <1152000>;
+ qcom,init-voltage = <968000>;
status = "okay";
};
};
@@ -159,9 +159,9 @@
rpm-regulator-ldoa3 {
status = "okay";
pm8953_l3: regulator-l3 {
- regulator-min-microvolt = <1200000>;
+ regulator-min-microvolt = <1140000>;
regulator-max-microvolt = <1200000>;
- qcom,init-voltage = <1200000>;
+ qcom,init-voltage = <1140000>;
status = "okay";
};
};
@@ -236,9 +236,9 @@
rpm-regulator-ldoa9 {
status = "okay";
pm8953_l9: regulator-l9 {
- regulator-min-microvolt = <3300000>;
+ regulator-min-microvolt = <3000000>;
regulator-max-microvolt = <3300000>;
- qcom,init-voltage = <3300000>;
+ qcom,init-voltage = <3000000>;
status = "okay";
};
};
@@ -246,9 +246,9 @@
rpm-regulator-ldoa10 {
status = "okay";
pm8953_l10: regulator-l10 {
- regulator-min-microvolt = <3000000>;
- regulator-max-microvolt = <3000000>;
- qcom,init-voltage = <3000000>;
+ regulator-min-microvolt = <2948000>;
+ regulator-max-microvolt = <3300000>;
+ qcom,init-voltage = <2948000>;
status = "okay";
};
};
@@ -256,9 +256,9 @@
rpm-regulator-ldoa11 {
status = "okay";
pm8953_l11: regulator-l11 {
- regulator-min-microvolt = <2950000>;
- regulator-max-microvolt = <2950000>;
- qcom,init-voltage = <2950000>;
+ regulator-min-microvolt = <2700000>;
+ regulator-max-microvolt = <3300000>;
+ qcom,init-voltage = <2700000>;
status = "okay";
};
};
@@ -266,9 +266,9 @@
rpm-regulator-ldoa12 {
status = "okay";
pm8953_l12: regulator-l12 {
- regulator-min-microvolt = <1800000>;
- regulator-max-microvolt = <2950000>;
- qcom,init-voltage = <1800000>;
+ regulator-min-microvolt = <1648000>;
+ regulator-max-microvolt = <3100000>;
+ qcom,init-voltage = <1648000>;
status = "okay";
};
};
@@ -276,9 +276,9 @@
rpm-regulator-ldoa13 {
status = "okay";
pm8953_l13: regulator-l13 {
- regulator-min-microvolt = <3075000>;
- regulator-max-microvolt = <3300000>;
- qcom,init-voltage = <3075000>;
+ regulator-min-microvolt = <3050000>;
+ regulator-max-microvolt = <3100000>;
+ qcom,init-voltage = <3050000>;
status = "okay";
};
};
@@ -295,7 +295,7 @@
regulator-name = "pm8953_l14";
qcom,set = <3>;
regulator-min-microvolt = <1800000>;
- regulator-max-microvolt = <2950000>;
+ regulator-max-microvolt = <3052000>;
qcom,init-voltage = <1800000>;
status = "okay";
};
@@ -313,7 +313,7 @@
regulator-name = "pm8953_l15";
qcom,set = <3>;
regulator-min-microvolt = <1800000>;
- regulator-max-microvolt = <2950000>;
+ regulator-max-microvolt = <3052000>;
qcom,init-voltage = <1800000>;
status = "okay";
};
@@ -332,9 +332,9 @@
rpm-regulator-ldoa17 {
status = "okay";
pm8953_l17: regulator-l17 {
- regulator-min-microvolt = <2850000>;
- regulator-max-microvolt = <2850000>;
- qcom,init-voltage = <2850000>;
+ regulator-min-microvolt = <2800000>;
+ regulator-max-microvolt = <2900000>;
+ qcom,init-voltage = <2800000>;
status = "okay";
};
};
@@ -342,9 +342,9 @@
rpm-regulator-ldoa19 {
status = "okay";
pm8953_l19: regulator-l19 {
- regulator-min-microvolt = <1300000>;
- regulator-max-microvolt = <1350000>;
- qcom,init-voltage = <1300000>;
+ regulator-min-microvolt = <1224000>;
+ regulator-max-microvolt = <1356000>;
+ qcom,init-voltage = <1224000>;
status = "okay";
};
};
@@ -352,9 +352,9 @@
rpm-regulator-ldoa22 {
status = "okay";
pm8953_l22: regulator-l22 {
- regulator-min-microvolt = <2800000>;
- regulator-max-microvolt = <2800000>;
- qcom,init-voltage = <2800000>;
+ regulator-min-microvolt = <2560000>;
+ regulator-max-microvolt = <2840000>;
+ qcom,init-voltage = <2560000>;
status = "okay";
};
};
@@ -363,7 +363,7 @@
status = "okay";
pm8953_l23: regulator-l23 {
regulator-min-microvolt = <800000>;
- regulator-max-microvolt = <800000>;
+ regulator-max-microvolt = <1000000>;
qcom,init-voltage = <800000>;
status = "okay";
};
@@ -388,3 +388,85 @@
};
};
};
+
+&soc {
+ apc_mem_acc_vreg: apc-mem-acc-regulator {
+ compatible = "qcom,mem-acc-regulator";
+ regulator-name = "apc_mem_acc_corner";
+ regulator-min-microvolt = <1>;
+ regulator-max-microvolt = <2>;
+ qcom,acc-reg-addr-list = <0x01942138 0x01942130 0x01946004>;
+ qcom,acc-init-reg-config = <1 0xff>;
+ qcom,num-acc-corners = <2>;
+ qcom,boot-acc-corner = <1>;
+ qcom,corner1-reg-config =
+ /* 1 -> 1 */
+ <(-1) (-1)>, <(-1) (-1)>,
+ /* 1 -> 2 */
+ < 2 0xffff>, < 3 0xff>;
+ qcom,corner2-reg-config =
+ /* 2 -> 1 */
+ < 2 0x5555>, < 3 0x55>,
+ /* 2 -> 2 */
+ <(-1) (-1)>, <(-1) (-1)>;
+ };
+
+ apc_vreg_corner: regulator@b018000 {
+ compatible = "qcom,cpr-regulator";
+ reg = <0xb018000 0x1000>, <0xb011064 4>, <0xa4000 0x1000>;
+ reg-names = "rbcpr", "rbcpr_clk", "efuse_addr";
+ interrupts = <0 15 0>;
+ regulator-name = "apc_corner";
+ regulator-min-microvolt = <1>;
+ regulator-max-microvolt = <5>;
+
+ qcom,cpr-fuse-corners = <3>;
+ qcom,cpr-voltage-ceiling = <760000 795000 910000>;
+ qcom,cpr-voltage-floor = <700000 700000 790000>;
+ vdd-apc-supply = <&pm8953_s5>;
+ mem-acc-supply = <&apc_mem_acc_vreg>;
+ qcom,mem-acc-corner-map = <1 1 1 1 2>;
+
+ qcom,cpr-ref-clk = <19200>;
+ qcom,cpr-timer-delay = <5000>;
+ qcom,cpr-timer-cons-up = <0>;
+ qcom,cpr-timer-cons-down = <2>;
+ qcom,cpr-irq-line = <0>;
+ qcom,cpr-step-quotient = <10>;
+ qcom,cpr-up-threshold = <2>;
+ qcom,cpr-down-threshold = <4>;
+ qcom,cpr-idle-clocks = <15>;
+ qcom,cpr-gcnt-time = <1>;
+ qcom,vdd-apc-step-up-limit = <1>;
+ qcom,vdd-apc-step-down-limit = <1>;
+ qcom,cpr-apc-volt-step = <5000>;
+
+ qcom,cpr-fuse-row = <67 0>;
+ qcom,cpr-fuse-target-quot = <42 24 6>;
+ qcom,cpr-fuse-ro-sel = <60 57 54>;
+ qcom,cpr-init-voltage-ref = <760000 795000 910000>;
+ qcom,cpr-fuse-init-voltage =
+ <67 36 6 0>,
+ <67 18 6 0>,
+ <67 0 6 0>;
+ qcom,cpr-fuse-quot-offset =
+ <71 26 6 0>,
+ <71 20 6 0>,
+ <70 54 7 0>;
+ qcom,cpr-fuse-quot-offset-scale = <5 5 5>;
+ qcom,cpr-init-voltage-step = <10000>;
+ qcom,cpr-corner-map = <1 2 3 3 3>;
+ qcom,cpr-corner-frequency-map =
+ <1 1305600000>,
+ <2 1497600000>,
+ <3 1708800000>,
+ <4 1804800000>,
+ <5 1958400000>;
+ qcom,speed-bin-fuse-sel = <37 34 3 0>;
+ qcom,cpr-speed-bin-max-corners = <(-1) (-1) 1 2 5>;
+ qcom,cpr-fuse-revision = <69 39 3 0>;
+ qcom,cpr-quot-adjust-scaling-factor-max = <0 1400 1400>;
+ qcom,cpr-voltage-scaling-factor-max = <0 2000 2000>;
+ qcom,cpr-scaled-init-voltage-as-ceiling;
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439.dts b/arch/arm64/boot/dts/qcom/sdm439.dts
new file mode 100644
index 0000000..bf7a815
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm439.dts
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2018, 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 "sdm439.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM439 MTP";
+ compatible = "qcom,sdm439";
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+ qcom.pmic-name = "PMI632";
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm439.dtsi b/arch/arm64/boot/dts/qcom/sdm439.dtsi
index 422a95f..812c0ad 100644
--- a/arch/arm64/boot/dts/qcom/sdm439.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm439.dtsi
@@ -23,13 +23,82 @@
&soc {
qcom,csid@1b30000 {
- /delete-property/ qcom,mipi-csi-vdd-supply;
+ qcom,mipi-csi-vdd-supply = <&pm8953_l23>;
};
qcom,csid@1b30400 {
- /delete-property/ qcom,mipi-csi-vdd-supply;
+ qcom,mipi-csi-vdd-supply = <&pm8953_l23>;
};
qcom,csid@1b30800 {
- /delete-property/ qcom,mipi-csi-vdd-supply;
+ qcom,mipi-csi-vdd-supply = <&pm8953_l23>;
+ };
+
+ msm_cpufreq: qcom,msm-cpufreq {
+ compatible = "qcom,msm-cpufreq";
+ clock-names =
+ "l2_clk",
+ "cpu0_clk",
+ "cpu4_clk";
+ clocks = <&clock_cpu clk_cci_clk>,
+ <&clock_cpu clk_a53_bc_clk>,
+ <&clock_cpu clk_a53_lc_clk>;
+
+ qcom,governor-per-policy;
+
+ qcom,cpufreq-table-0 =
+ < 1305600 >,
+ < 1497600 >,
+ < 1708800 >,
+ < 1958400 >;
+
+ qcom,cpufreq-table-4 =
+ < 768000 >,
+ < 1001600 >,
+ < 1171200 >,
+ < 1305600 >,
+ < 1459200 >;
+ };
+
+ devfreq-cpufreq {
+ cpubw-cpufreq {
+ target-dev = <&cpubw>;
+ cpu-to-dev-map-0 =
+ < 1305600 2929 >,
+ < 1497600 5053 >,
+ < 1708800 5712 >,
+ < 1958400 7031 >;
+ cpu-to-dev-map-4 =
+ < 768000 2929 >,
+ < 1001600 4101 >,
+ < 1171200 5053 >,
+ < 1305600 6152 >,
+ < 1459200 7031 >;
+
+ };
+
+ cci-cpufreq {
+ target-dev = <&cci_cache>;
+ cpu-to-dev-map-0 =
+ < 1305600 400000 >,
+ < 1497600 400000 >,
+ < 1708800 533333 >,
+ < 1958400 533333 >;
+ cpu-to-dev-map-4 =
+ < 768000 400000 >,
+ < 1001600 400000 >,
+ < 1171200 533333 >,
+ < 1305600 533333 >,
+ < 1459200 533333 >;
+ };
+
+ mincpubw-cpufreq {
+ target-dev = <&mincpubw>;
+ cpu-to-dev-map-0 =
+ < 1305600 2929 >,
+ < 1958400 4248 >;
+ cpu-to-dev-map-4 =
+ < 1171200 2929 >,
+ < 1459200 4248 >;
+ };
};
};
@@ -38,7 +107,7 @@
CPU_COST_0: core-cost0 {
busy-cost-data = <
- 8000000 137
+ 800000 137
1001600 165
1305600 207
1497600 256
@@ -51,7 +120,7 @@
};
CPU_COST_1: core-cost1 {
busy-cost-data = <
- 8000000 45
+ 768000 43
1001600 56
1171200 71
1305600 89
@@ -63,7 +132,7 @@
};
CLUSTER_COST_0: cluster-cost0 {
busy-cost-data = <
- 8000000 49
+ 800000 49
1001600 53
1305600 61
1497600 71
@@ -76,7 +145,7 @@
};
CLUSTER_COST_1: cluster-cost1 {
busy-cost-data = <
- 8000000 9
+ 768000 8
1001600 10
1171200 13
1305600 15
@@ -87,3 +156,44 @@
>;
};
};
+
+&kgsl_smmu {
+ qcom,enable-static-cb;
+};
+
+&reserved_memory {
+ gpu_mem: gpu_region@0 {
+ compatible = "shared-dma-pool";
+ reusable;
+ alloc-ranges = <0x0 0x80000000 0x0 0x10000000>;
+ alignment = <0 0x400000>;
+ size = <0 0x800000>;
+ };
+};
+
+&soc {
+ pil_gpu: qcom,kgsl-hyp {
+ compatible = "qcom,pil-tz-generic";
+ qcom,pas-id = <13>;
+ qcom,firmware-name = "a506_zap";
+ memory-region = <&gpu_mem>;
+ qcom,mas-crypto = <&mas_crypto>;
+ clocks = <&clock_gcc clk_gcc_crypto_clk>,
+ <&clock_gcc clk_gcc_crypto_ahb_clk>,
+ <&clock_gcc clk_gcc_crypto_axi_clk>,
+ <&clock_gcc clk_crypto_clk_src>;
+ clock-names = "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+ qcom,proxy-clock-names = "scm_core_clk", "scm_iface_clk",
+ "scm_bus_clk", "scm_core_clk_src";
+ qcom,scm_core_clk_src-freq = <80000000>;
+ };
+};
+
+&kgsl_msm_iommu {
+ gfx3d_secure: gfx3d_secure {
+ compatible = "qcom,smmu-kgsl-cb";
+ iommus = <&kgsl_smmu 2>;
+ memory-region = <&secure_mem>;
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm450-pmi632-cdp-s2.dts b/arch/arm64/boot/dts/qcom/sdm450-pmi632-cdp-s2.dts
index 692da7f..68f02a8 100644
--- a/arch/arm64/boot/dts/qcom/sdm450-pmi632-cdp-s2.dts
+++ b/arch/arm64/boot/dts/qcom/sdm450-pmi632-cdp-s2.dts
@@ -24,16 +24,3 @@
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
-&pm8953_vadc {
- pinctrl-0 = <&pa_therm1_default>;
- /delete-node/ chan@13;
-};
-
-&pm8953_mpps {
- /delete-node/ case_therm;
-};
-
-&thermal_zones {
- /delete-node/ case-therm-adc;
- /delete-node/ case-therm-step;
-};
diff --git a/arch/arm64/boot/dts/qcom/sdm450-pmi632-mtp-s3.dts b/arch/arm64/boot/dts/qcom/sdm450-pmi632-mtp-s3.dts
index 02bf751..b9aadc1 100644
--- a/arch/arm64/boot/dts/qcom/sdm450-pmi632-mtp-s3.dts
+++ b/arch/arm64/boot/dts/qcom/sdm450-pmi632-mtp-s3.dts
@@ -24,16 +24,3 @@
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
-&pm8953_vadc {
- pinctrl-0 = <&pa_therm1_default>;
- /delete-node/ chan@13;
-};
-
-&pm8953_mpps {
- /delete-node/ case_therm;
-};
-
-&thermal_zones {
- /delete-node/ case-therm-adc;
- /delete-node/ case-therm-step;
-};
diff --git a/arch/arm64/boot/dts/qcom/sdm450-pmi632.dtsi b/arch/arm64/boot/dts/qcom/sdm450-pmi632.dtsi
index d29d6fa..a4b6054 100644
--- a/arch/arm64/boot/dts/qcom/sdm450-pmi632.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm450-pmi632.dtsi
@@ -63,6 +63,27 @@
&thermal_zones {
pmi-vbat-lvl0 {
cooling-maps {
+ vbat_map0 {
+ trip = <&pmi632_vbat_lvl0>;
+ /* throttle from fmax to 1689600KHz */
+ cooling-device = <&CPU0 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ vbat_map1 {
+ trip = <&pmi632_vbat_lvl0>;
+ cooling-device = <&CPU1 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ vbat_map2 {
+ trip = <&pmi632_vbat_lvl0>;
+ cooling-device = <&CPU2 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ vbat_map3 {
+ trip = <&pmi632_vbat_lvl0>;
+ cooling-device = <&CPU3 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
vbat_map4 {
trip = <&pmi632_vbat_lvl0>;
cooling-device =
@@ -90,8 +111,79 @@
};
};
+ pmi-ibat-lvl0 {
+ cooling-maps {
+ ibat_map0 {
+ trip = <&pmi632_ibat_lvl0>;
+ /* throttle from fmax to 1689600KHz */
+ cooling-device = <&CPU0 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ ibat_map1 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device = <&CPU1 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ ibat_map2 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device = <&CPU2 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ ibat_map3 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device = <&CPU3 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ ibat_map4 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device =
+ <&CPU4 THERMAL_MAX_LIMIT
+ THERMAL_MAX_LIMIT>;
+ };
+ ibat_map5 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device =
+ <&CPU5 THERMAL_MAX_LIMIT
+ THERMAL_MAX_LIMIT>;
+ };
+ ibat_map6 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device =
+ <&CPU6 THERMAL_MAX_LIMIT
+ THERMAL_MAX_LIMIT>;
+ };
+ ibat_map7 {
+ trip = <&pmi632_ibat_lvl0>;
+ cooling-device =
+ <&CPU7 THERMAL_MAX_LIMIT
+ THERMAL_MAX_LIMIT>;
+ };
+ };
+ };
+
soc {
cooling-maps {
+ soc_map0 {
+ trip = <&pmi632_low_soc>;
+ /* throttle from fmax to 1689600KHz */
+ cooling-device = <&CPU0 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ soc_map1 {
+ trip = <&pmi632_low_soc>;
+ cooling-device = <&CPU1 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ soc_map2 {
+ trip = <&pmi632_low_soc>;
+ cooling-device = <&CPU2 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
+ soc_map3 {
+ trip = <&pmi632_low_soc>;
+ cooling-device = <&CPU3 (THERMAL_MAX_LIMIT - 4)
+ (THERMAL_MAX_LIMIT - 4)>;
+ };
soc_map4 {
trip = <&pmi632_low_soc>;
cooling-device =
@@ -119,45 +211,137 @@
};
};
- case-therm-step {
+ quiet-therm-adc {
+ polling-delay-passive = <0>;
+ polling-delay = <0>;
+ thermal-sensors = <&pmi632_adc_tm 0x53>;
+ thermal-governor = "user_space";
+
trips {
- batt_trip1: batt-trip1 {
+ active-config0 {
+ temperature = <65000>;
+ hysteresis = <1000>;
+ type = "passive";
+ };
+ };
+ };
+
+ case-therm-step {
+ status = "disabled";
+ };
+
+ quiet-therm-step {
+ polling-delay-passive = <2000>;
+ polling-delay = <0>;
+ thermal-sensors = <&pmi632_adc_tm 0x53>;
+ thermal-governor = "step_wise";
+
+ trips {
+ quiet_batt_trip1: quiet_batt-trip1 {
temperature = <38000>;
hysteresis = <3000>;
type = "passive";
};
- batt_trip2: batt-trip2 {
+ quiet_batt_trip2: quiet_batt-trip2 {
temperature = <40000>;
hysteresis = <2000>;
type = "passive";
};
- batt_trip3: batt-trip3 {
+ quiet_batt_trip3: quiet_batt-trip3 {
temperature = <43000>;
hysteresis = <3000>;
type = "passive";
};
- batt_trip4: batt-trip4 {
+ quiet_cpus_trip: quiet_cpus-trip {
+ temperature = <43000>;
+ hysteresis = <0>;
+ type = "passive";
+ };
+ quiet_modem_trip0: quiet_modem-trip0 {
+ temperature = <45000>;
+ hysteresis = <2000>;
+ type = "passive";
+ };
+ quiet_batt_trip4: quiet_batt-trip4 {
temperature = <48000>;
hysteresis = <5000>;
type = "passive";
};
+ quiet_modem_trip1: quiet_modem-trip1 {
+ temperature = <48000>;
+ hysteresis = <3000>;
+ type = "passive";
+ };
+ quiet_modem_trip2: quiet_modem-trip2 {
+ temperature = <54000>;
+ hysteresis = <4000>;
+ type = "passive";
+ };
};
-
cooling-maps {
+ skin_cpu0 {
+ trip = <&quiet_cpus_trip>;
+ /* throttle from fmax to 1689600KHz */
+ cooling-device = <&CPU0 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu1 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU1 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu2 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU2 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu3 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU3 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu4 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU4 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu5 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU5 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu6 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU6 THERMAL_NO_LIMIT 3>;
+ };
+ skin_cpu7 {
+ trip = <&quiet_cpus_trip>;
+ cooling-device = <&CPU7 THERMAL_NO_LIMIT 3>;
+ };
+ modem_lvl1 {
+ trip = <&quiet_modem_trip1>;
+ cooling-device = <&modem_pa 2 2>;
+ };
+ modem_lvl2 {
+ trip = <&quiet_modem_trip2>;
+ cooling-device = <&modem_pa 3 3>;
+ };
+ modem_proc_lvl1 {
+ trip = <&quiet_modem_trip0>;
+ cooling-device = <&modem_proc 1 1>;
+ };
+ modem_proc_lvl2 {
+ trip = <&quiet_modem_trip2>;
+ cooling-device = <&modem_proc 3 3>;
+ };
battery_lvl1 {
- trip = <&batt_trip1>;
+ trip = <&quiet_batt_trip1>;
cooling-device = <&pmi632_charger 2 2>;
};
battery_lvl2 {
- trip = <&batt_trip2>;
+ trip = <&quiet_batt_trip2>;
cooling-device = <&pmi632_charger 3 3>;
};
battery_lvl3 {
- trip = <&batt_trip3>;
+ trip = <&quiet_batt_trip3>;
cooling-device = <&pmi632_charger 4 4>;
};
battery_lvl4 {
- trip = <&batt_trip4>;
+ trip = <&quiet_batt_trip4>;
cooling-device = <&pmi632_charger 5 5>;
};
};
diff --git a/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dts b/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dts
index b0cb955..cad0c6f 100644
--- a/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dts
+++ b/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dts
@@ -14,8 +14,8 @@
/dts-v1/;
#include "sdm450.dtsi"
-#include "sdm450-qrd-sku4.dtsi"
#include "sdm450-pmi632.dtsi"
+#include "sdm450-qrd-sku4.dtsi"
/ {
model = "Qualcomm Technologies, Inc. SDM450 + PMI632 QRD SKU4";
@@ -24,22 +24,3 @@
qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
-&pmi632_vadc {
- chan@4a {
- qcom,scale-function = <22>;
- };
-};
-
-&pm8953_vadc {
- pinctrl-0 = <&pa_therm1_default>;
- /delete-node/ chan@13;
-};
-
-&pm8953_mpps {
- /delete-node/ case_therm;
-};
-
-&thermal_zones {
- /delete-node/ case-therm-adc;
- /delete-node/ case-therm-step;
-};
diff --git a/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dtsi b/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dtsi
index bdefdc9..386bd71 100644
--- a/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm450-qrd-sku4.dtsi
@@ -150,3 +150,30 @@
&sdhc_2 {
cd-gpios = <&tlmm 133 0x0>;
};
+
+&pmi632_vadc {
+ chan@4a {
+ qcom,scale-function = <22>;
+ };
+};
+
+&soc {
+ gpio_keys {
+ camera_focus {
+ label = "camera_focus";
+ gpios = <&tlmm 87 0x1>;
+ linux,input-type = <1>;
+ linux,code = <0x210>;
+ debounce-interval = <15>;
+ };
+
+ camera_snapshot {
+ label = "camera_snapshot";
+ gpios = <&tlmm 86 0x1>;
+ linux,input-type = <1>;
+ linux,code = <0x2fe>;
+ debounce-interval = <15>;
+ };
+ };
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm450.dtsi b/arch/arm64/boot/dts/qcom/sdm450.dtsi
index 1d2abd7c..34c6815 100644
--- a/arch/arm64/boot/dts/qcom/sdm450.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm450.dtsi
@@ -132,3 +132,17 @@
};
};
};
+
+&pm8953_vadc {
+ pinctrl-0 = <&pa_therm1_default>;
+ /delete-node/ chan@13;
+};
+
+&pm8953_mpps {
+ /delete-node/ case_therm;
+};
+
+&thermal_zones {
+ /delete-node/ case-therm-adc;
+ /delete-node/ case-therm-step;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm632-cdp-s2.dts b/arch/arm64/boot/dts/qcom/sdm632-cdp-s2.dts
index 2c3e830..2669d1f 100644
--- a/arch/arm64/boot/dts/qcom/sdm632-cdp-s2.dts
+++ b/arch/arm64/boot/dts/qcom/sdm632-cdp-s2.dts
@@ -18,10 +18,10 @@
#include "sdm450-pmi632.dtsi"
/ {
- model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PMI8004 CDP S2";
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 CDP S2";
compatible = "qcom,sdm632-cdp", "qcom,sdm632", "qcom,cdp";
qcom,board-id = <1 2>;
- qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
@@ -54,17 +54,3 @@
};
};
};
-
-&pm8953_vadc {
- pinctrl-0 = <&pa_therm1_default>;
- /delete-node/ chan@13;
-};
-
-&pm8953_mpps {
- /delete-node/ case_therm;
-};
-
-&thermal_zones {
- /delete-node/ case-therm-adc;
- /delete-node/ case-therm-step;
-};
diff --git a/arch/arm64/boot/dts/qcom/sdm632-cpu.dtsi b/arch/arm64/boot/dts/qcom/sdm632-cpu.dtsi
index c53bb56..de1bd1f 100644
--- a/arch/arm64/boot/dts/qcom/sdm632-cpu.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm632-cpu.dtsi
@@ -248,7 +248,7 @@
1363200 88
1536000 112
1670400 151
- 1785600 192
+ 1804800 194
>;
idle-cost-data = <
20 16 12 8
@@ -261,9 +261,9 @@
1036800 1739
1401600 2819
1555200 3532
- 1785600 4985
+ 1804800 5038
1996000 6624
- 2082800 6905
+ 2016000 6688
>;
idle-cost-data = <
100 80 60 40
@@ -277,7 +277,7 @@
1363200 28
1536000 35
1670400 43
- 1785600 54
+ 1804800 54
>;
idle-cost-data = <
4 3 2 1
@@ -290,9 +290,9 @@
1036800 132
1401600 193
1555200 233
- 1785600 289
+ 1804800 292
1996000 374
- 2082800 386
+ 2016000 377
>;
idle-cost-data = <
4 3 2 1
diff --git a/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3-overlay.dts b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3-overlay.dts
new file mode 100644
index 0000000..eb5afbd
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3-overlay.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include "sdm632-ext-codec-cdp-s3.dtsi"
+
+/ {
+ model = "Ext Codec CDP S3";
+ compatible = "qcom,cdp";
+ qcom,board-id = <1 3>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3.dts b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3.dts
new file mode 100644
index 0000000..17ae9d1
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3.dts
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-ext-codec-cdp-s3.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 Ext Codex CDP S3";
+ compatible = "qcom,sdm632-cdp", "qcom,sdm632", "qcom,cdp";
+ qcom,board-id = <1 3>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
+
+
+&soc {
+ gpio_keys {
+ /delete-node/home;
+ };
+};
+
+&tlmm {
+ tlmm_gpio_key {
+ gpio_key_active: gpio_key_active {
+ mux {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+
+ config {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+ };
+
+ gpio_key_suspend: gpio_key_suspend {
+ mux {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+
+ config {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+ };
+ };
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3.dtsi b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3.dtsi
new file mode 100644
index 0000000..14ba3b4
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-cdp-s3.dtsi
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2018, 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 "sdm450-pmi632-cdp-s2.dtsi"
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4-overlay.dts b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4-overlay.dts
new file mode 100644
index 0000000..5656fd0
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4-overlay.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include "sdm632-ext-codec-mtp-s4.dtsi"
+
+/ {
+ model = "Ext Codec MTP S4";
+ compatible = "qcom,mtp";
+ qcom,board-id = <8 4>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4.dts b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4.dts
new file mode 100644
index 0000000..b9e1178
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-ext-codec-mtp-s4.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + Ext Codec MTP S4";
+ compatible = "qcom,sdm632-mtp", "qcom,sdm632", "qcom,mtp";
+ qcom,board-id = <8 4>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4.dtsi b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4.dtsi
new file mode 100644
index 0000000..d8326ff
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-ext-codec-mtp-s4.dtsi
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2018, 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 "sdm450-pmi632-mtp-s3.dtsi"
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-mtp-s3.dts b/arch/arm64/boot/dts/qcom/sdm632-mtp-s3.dts
index 0566fbb..3662cf3 100644
--- a/arch/arm64/boot/dts/qcom/sdm632-mtp-s3.dts
+++ b/arch/arm64/boot/dts/qcom/sdm632-mtp-s3.dts
@@ -18,22 +18,9 @@
#include "sdm450-pmi632.dtsi"
/ {
- model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PMI8004 MTP S3";
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 MTP S3";
compatible = "qcom,sdm632-mtp", "qcom,sdm632", "qcom,mtp";
qcom,board-id = <8 3>;
- qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
-&pm8953_vadc {
- pinctrl-0 = <&pa_therm1_default>;
- /delete-node/ chan@13;
-};
-
-&pm8953_mpps {
- /delete-node/ case_therm;
-};
-
-&thermal_zones {
- /delete-node/ case-therm-adc;
- /delete-node/ case-therm-step;
-};
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-cdp-s2.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-cdp-s2.dts
new file mode 100644
index 0000000..4d68901
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-cdp-s2.dts
@@ -0,0 +1,58 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632-cdp-s2.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PM8004 CDP S2";
+ compatible = "qcom,sdm632-cdp", "qcom,sdm632", "qcom,cdp";
+ qcom,board-id = <1 2>;
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+};
+
+
+&soc {
+ gpio_keys {
+ /delete-node/home;
+ };
+};
+
+&tlmm {
+ tlmm_gpio_key {
+ gpio_key_active: gpio_key_active {
+ mux {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+
+ config {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+ };
+
+ gpio_key_suspend: gpio_key_suspend {
+ mux {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+
+ config {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+ };
+ };
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-ext-codec-cdp-s3.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-ext-codec-cdp-s3.dts
new file mode 100644
index 0000000..6ca2940
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-ext-codec-cdp-s3.dts
@@ -0,0 +1,58 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+#include "sdm632-ext-codec-cdp-s3.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PMI8004 Ext Codec CDP S3";
+ compatible = "qcom,sdm632-cdp", "qcom,sdm632", "qcom,cdp";
+ qcom,board-id = <1 3>;
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+};
+
+
+&soc {
+ gpio_keys {
+ /delete-node/home;
+ };
+};
+
+&tlmm {
+ tlmm_gpio_key {
+ gpio_key_active: gpio_key_active {
+ mux {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+
+ config {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+ };
+
+ gpio_key_suspend: gpio_key_suspend {
+ mux {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+
+ config {
+ pins = "gpio85", "gpio86", "gpio87";
+ };
+ };
+ };
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-ext-codec-mtp-s4.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-ext-codec-mtp-s4.dts
new file mode 100644
index 0000000..7a30bff82e
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-ext-codec-mtp-s4.dts
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+#include "sdm632-ext-codec-mtp-s4.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PMI8004 MTP S4";
+ compatible = "qcom,sdm632-mtp", "qcom,sdm632", "qcom,mtp";
+ qcom,board-id = <8 4>;
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-mtp-s3.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-mtp-s3.dts
new file mode 100644
index 0000000..d2a9cf1
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-mtp-s3.dts
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632-mtp-s3.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PM8004 MTP S3";
+ compatible = "qcom,sdm632-mtp", "qcom,sdm632", "qcom,mtp";
+ qcom,board-id = <8 3>;
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-qrd-sku4.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-qrd-sku4.dts
new file mode 100644
index 0000000..3472b86
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-qrd-sku4.dts
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm632-pm8004.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm450-qrd-sku4.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PM8004 QRD SKU4";
+ compatible = "qcom,sdm632-qrd", "qcom,sdm632", "qcom,qrd";
+ qcom,board-id = <0xb 1>;
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-qrd.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-qrd.dts
new file mode 100644
index 0000000..89a56fa
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-qrd.dts
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+#include "sdm632-qrd.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PM8004 + QRD";
+ compatible = "qcom,sdm632-qrd", "qcom,sdm632", "qcom,qrd";
+ qcom,board-id = <0xb 3>;
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004-rcm.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004-rcm.dts
new file mode 100644
index 0000000..89eb789
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004-rcm.dts
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+#include "sdm632-rcm.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PM8004 RCM";
+ compatible = "qcom,sdm632-cdp", "qcom,sdm632", "qcom,cdp";
+ qcom,board-id= <21 2>;
+ qcom,pmic-id = <0x010016 0x010011 0xC 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004.dts b/arch/arm64/boot/dts/qcom/sdm632-pm8004.dts
new file mode 100644
index 0000000..625bf40
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004.dts
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-pm8004.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PM8004 SOC";
+ compatible = "qcom,sdm450";
+ qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+ qcom,pmic-name = "PMI632 + PM8004";
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm632-pm8004.dtsi b/arch/arm64/boot/dts/qcom/sdm632-pm8004.dtsi
new file mode 100644
index 0000000..a5994c6
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-pm8004.dtsi
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2018, 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 "pm8004.dtsi"
+#include "pm8004-rpm-regulator.dtsi"
+
+&rpm_bus {
+ rpm-regulator-ldoc1 {
+ status = "okay";
+ pm8004_l1: regulator-l1 {
+ regulator-min-microvolt = <1200000>;
+ regulator-max-microvolt = <1200000>;
+ qcom,init-voltage = <1200000>;
+ status = "okay";
+ };
+ };
+};
+
+&spmi_bus {
+ qcom,pm8953@1 {
+ /delete-node/ spm-regulator@2000;
+ };
+
+ pmic@5 {
+ #size-cells = <1>;
+
+ /* PM8004 S2 + S4 + S5 = VDD_APC supply */
+ pm8004_s2: spm-regulator@1d00 {
+ compatible = "qcom,spm-regulator";
+ reg = <0x1d00 0x100>;
+ regulator-name = "pm8004_s2";
+ regulator-min-microvolt = <400000>;
+ regulator-max-microvolt = <1140000>;
+
+ pm8004_s2_limit: avs-limit-regulator {
+ regulator-name = "pm8004_s2_avs_limit";
+ regulator-min-microvolt = <400000>;
+ regulator-max-microvolt = <1140000>;
+ };
+ };
+ };
+};
+
+&apc_cpr {
+ vdd-supply = <&pm8004_s2>;
+ vdd-limit-supply = <&pm8004_s2_limit>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm632-qrd-overlay.dts b/arch/arm64/boot/dts/qcom/sdm632-qrd-overlay.dts
new file mode 100644
index 0000000..e6217e5
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-qrd-overlay.dts
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include "sdm632-qrd.dtsi"
+
+/ {
+ model = "QRD";
+ compatible = "qcom,qrd";
+ qcom,board-id = <0xb 3>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-qrd-sku4.dts b/arch/arm64/boot/dts/qcom/sdm632-qrd-sku4.dts
index fe1ac73..466c8fc 100644
--- a/arch/arm64/boot/dts/qcom/sdm632-qrd-sku4.dts
+++ b/arch/arm64/boot/dts/qcom/sdm632-qrd-sku4.dts
@@ -14,53 +14,13 @@
/dts-v1/;
#include "sdm632.dtsi"
-#include "sdm450-qrd-sku4.dtsi"
#include "sdm450-pmi632.dtsi"
-#include "msm8953-camera-sensor-qrd.dtsi"
+#include "sdm450-qrd-sku4.dtsi"
/ {
- model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + PMI8004 QRD SKU4";
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 QRD SKU4";
compatible = "qcom,sdm632-qrd", "qcom,sdm632", "qcom,qrd";
qcom,board-id = <0xb 1>;
- qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
};
-&pmi632_vadc {
- chan@4a {
- qcom,scale-function = <22>;
- };
-};
-
-&soc {
- gpio_keys {
- camera_focus {
- label = "camera_focus";
- gpios = <&tlmm 87 0x1>;
- linux,input-type = <1>;
- linux,code = <0x210>;
- debounce-interval = <15>;
- };
-
- camera_snapshot {
- label = "camera_snapshot";
- gpios = <&tlmm 86 0x1>;
- linux,input-type = <1>;
- linux,code = <0x2fe>;
- debounce-interval = <15>;
- };
- };
-};
-
-&pm8953_vadc {
- pinctrl-0 = <&pa_therm1_default>;
- /delete-node/ chan@13;
-};
-
-&pm8953_mpps {
- /delete-node/ case_therm;
-};
-
-&thermal_zones {
- /delete-node/ case-therm-adc;
- /delete-node/ case-therm-step;
-};
diff --git a/arch/arm64/boot/dts/qcom/sdm632-qrd.dts b/arch/arm64/boot/dts/qcom/sdm632-qrd.dts
new file mode 100644
index 0000000..c59fe5d
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-qrd.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-qrd.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 + QRD";
+ compatible = "qcom,sdm632-qrd", "qcom,sdm632", "qcom,qrd";
+ qcom,board-id = <0xb 3>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-qrd.dtsi b/arch/arm64/boot/dts/qcom/sdm632-qrd.dtsi
new file mode 100644
index 0000000..09077c42
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-qrd.dtsi
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2018, 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 "sdm450-qrd-sku4.dtsi"
diff --git a/arch/arm64/boot/dts/qcom/sdm632-rcm-overlay.dts b/arch/arm64/boot/dts/qcom/sdm632-rcm-overlay.dts
new file mode 100644
index 0000000..42979ad
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-rcm-overlay.dts
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2018, 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/;
+/plugin/;
+
+#include "sdm632-rcm.dtsi"
+
+/ {
+ model = "RCM";
+ qcom,board-id = <21 2>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-rcm.dts b/arch/arm64/boot/dts/qcom/sdm632-rcm.dts
new file mode 100644
index 0000000..68f0ea0
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-rcm.dts
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2018, 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 "sdm632.dtsi"
+#include "sdm450-pmi632.dtsi"
+#include "sdm632-rcm.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM632 + PMI632 RCM";
+ compatible = "qcom,sdm632-cdp", "qcom,sdm632", "qcom,cdp";
+ qcom,board-id= <21 2>;
+ qcom,pmic-id = <0x010016 0x010011 0x0 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-rcm.dtsi b/arch/arm64/boot/dts/qcom/sdm632-rcm.dtsi
new file mode 100644
index 0000000..14ba3b4
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm632-rcm.dtsi
@@ -0,0 +1,15 @@
+/*
+ * Copyright (c) 2018, 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 "sdm450-pmi632-cdp-s2.dtsi"
+
diff --git a/arch/arm64/boot/dts/qcom/sdm632-regulator.dtsi b/arch/arm64/boot/dts/qcom/sdm632-regulator.dtsi
index 060b8996..b5373a2 100644
--- a/arch/arm64/boot/dts/qcom/sdm632-regulator.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm632-regulator.dtsi
@@ -49,43 +49,6 @@
qcom,init-voltage = <2800000>;
};
-&rpm_bus {
- rpm-regulator-ldoc1 {
- status = "okay";
- pm8004_l1: regulator-l1 {
- regulator-min-microvolt = <1200000>;
- regulator-max-microvolt = <1200000>;
- qcom,init-voltage = <1200000>;
- status = "okay";
- };
- };
-};
-
-&spmi_bus {
- qcom,pm8953@1 {
- /delete-node/ spm-regulator@2000;
- };
-
- pmic@5 {
- #size-cells = <1>;
-
- /* PM8004 S2 + S4 + S5 = VDD_APC supply */
- pm8004_s2: spm-regulator@1d00 {
- compatible = "qcom,spm-regulator";
- reg = <0x1d00 0x100>;
- regulator-name = "pm8004_s2";
- regulator-min-microvolt = <400000>;
- regulator-max-microvolt = <1140000>;
-
- pm8004_s2_limit: avs-limit-regulator {
- regulator-name = "pm8004_s2_avs_limit";
- regulator-min-microvolt = <400000>;
- regulator-max-microvolt = <1140000>;
- };
- };
- };
-};
-
&soc {
/delete-node/ regulator@19461d4;
/delete-node/ cpr4-ctrl@b018000;
@@ -156,9 +119,9 @@
qcom,apm-threshold-voltage = <875000>;
qcom,apm-hysteresis-voltage = <20000>;
- vdd-supply = <&pm8004_s2>;
+ vdd-supply = <&pm8953_s5>;
qcom,voltage-step = <5000>;
- vdd-limit-supply = <&pm8004_s2_limit>;
+ vdd-limit-supply = <&pm8953_s5_limit>;
mem-acc-supply = <&apc_mem_acc_vreg>;
qcom,cpr-panic-reg-addr-list =
@@ -181,7 +144,7 @@
regulator-max-microvolt = <7>;
qcom,cpr-fuse-corners = <5>;
- qcom,cpr-fuse-combos = <8>;
+ qcom,cpr-fuse-combos = <64>;
qcom,cpr-corners = <7>;
qcom,cpr-corner-fmax-map = <1 2 3 4 7>;
@@ -231,7 +194,7 @@
regulator-max-microvolt = <5>;
qcom,cpr-fuse-corners = <3>;
- qcom,cpr-fuse-combos = <8>;
+ qcom,cpr-fuse-combos = <64>;
qcom,cpr-corners = <5>;
qcom,cpr-corner-fmax-map = <1 2 5>;
diff --git a/arch/arm64/boot/dts/qcom/sdm632.dts b/arch/arm64/boot/dts/qcom/sdm632.dts
index dab409c..65f1ea2 100644
--- a/arch/arm64/boot/dts/qcom/sdm632.dts
+++ b/arch/arm64/boot/dts/qcom/sdm632.dts
@@ -19,6 +19,6 @@
/ {
model = "Qualcomm Technologies, Inc. SDM632 + PMI632 SOC";
compatible = "qcom,sdm450";
- qcom,pmic-id = <0x010016 0x25 0xC 0x0>;
+ qcom,pmic-id = <0x010016 0x25 0x0 0x0>;
qcom,pmic-name = "PMI632";
};
diff --git a/arch/arm64/boot/dts/qcom/sdm632.dtsi b/arch/arm64/boot/dts/qcom/sdm632.dtsi
index 813b89d..62689f5 100644
--- a/arch/arm64/boot/dts/qcom/sdm632.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm632.dtsi
@@ -13,8 +13,6 @@
#include "msm8953.dtsi"
#include "sdm632-cpu.dtsi"
-#include "pm8004.dtsi"
-#include "pm8004-rpm-regulator.dtsi"
#include "sdm632-regulator.dtsi"
/ {
@@ -24,7 +22,7 @@
qcom,msm-name = "SDM632";
chosen {
- /delete-property/ bootargs;
+ bootargs = "kpti=0";
};
};
@@ -86,6 +84,10 @@
status = "disabled";
};
+ quiet-therm-step {
+ status = "disabled";
+ };
+
video-usr {
polling-delay-passive = <0>;
polling-delay = <0>;
@@ -819,13 +821,13 @@
< 1363200000 4>,
< 1536000000 5>,
< 1670400000 6>,
- < 1785600000 7>;
+ < 1804800000 7>;
qcom,speed0-bin-v0-c1 =
< 0 0>,
< 1094400000 1>,
< 1401600000 2>,
< 1555200000 3>,
- < 1785600000 4>;
+ < 1804800000 4>;
qcom,speed0-bin-v0-cci =
< 0 0>,
< 307200000 1>,
@@ -834,6 +836,56 @@
< 691200000 4>,
< 768000000 5>,
< 787200000 6>;
+
+ qcom,speed6-bin-v0-c0 =
+ < 0 0>,
+ < 614400000 1>,
+ < 883200000 2>,
+ < 1036800000 3>,
+ < 1363200000 4>,
+ < 1536000000 5>,
+ < 1670400000 6>,
+ < 1804800000 7>;
+ qcom,speed6-bin-v0-c1 =
+ < 0 0>,
+ < 1094400000 1>,
+ < 1401600000 2>,
+ < 1555200000 3>,
+ < 1804800000 4>;
+ qcom,speed6-bin-v0-cci =
+ < 0 0>,
+ < 307200000 1>,
+ < 403200000 2>,
+ < 499200000 3>,
+ < 691200000 4>,
+ < 768000000 5>,
+ < 787200000 6>;
+
+ qcom,speed2-bin-v0-c0 =
+ < 0 0>,
+ < 614400000 1>,
+ < 883200000 2>,
+ < 1036800000 3>,
+ < 1363200000 4>,
+ < 1536000000 5>,
+ < 1670400000 6>,
+ < 1804800000 7>;
+ qcom,speed2-bin-v0-c1 =
+ < 0 0>,
+ < 1094400000 1>,
+ < 1401600000 2>,
+ < 1555200000 3>,
+ < 1804800000 4>,
+ < 2016000000 5>;
+ qcom,speed2-bin-v0-cci =
+ < 0 0>,
+ < 307200000 1>,
+ < 403200000 2>,
+ < 499200000 3>,
+ < 691200000 4>,
+ < 768000000 5>,
+ < 787200000 6>;
+
#clock-cells = <1>;
};
@@ -859,15 +911,15 @@
< 1363200 >,
< 1536000 >,
< 1670400 >,
- < 1785600 >;
+ < 1804800 >;
qcom,cpufreq-table-4 =
< 1094400 >,
< 1401600 >,
< 1555200 >,
- < 1785600 >,
+ < 1804800 >,
< 1996200 >,
- < 2082800 >;
+ < 2016000 >;
};
cci_cache: qcom,cci {
@@ -891,12 +943,12 @@
cpu-to-dev-map-0 =
< 614400 1611>,
< 1363200 3221>,
- < 1785600 5859>;
+ < 1804800 5859>;
cpu-to-dev-map-4 =
< 1094400 1611>,
< 1401600 3221>,
- < 1785600 5859>,
- < 2082800 7104>;
+ < 1804800 5859>,
+ < 2016000 7104>;
};
cci-cpufreq {
@@ -912,7 +964,22 @@
< 1094400 499200>, /* SVS */
< 1401600 691200>, /* NOM */
< 1555200 768000>, /* NOM+ */
- < 1785600 787200>; /* TURBO */
+ < 1804800 787200>; /* TURBO */
};
};
};
+
+&pm8953_vadc {
+ pinctrl-0 = <&pa_therm1_default>;
+ /delete-node/ chan@13;
+};
+
+&pm8953_mpps {
+ /delete-node/ case_therm;
+};
+
+&thermal_zones {
+ /delete-node/ case-therm-adc;
+ /delete-node/ case-therm-step;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm670-aqt1000-cdp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm670-aqt1000-cdp-overlay.dts
new file mode 100644
index 0000000..001bcd4
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm670-aqt1000-cdp-overlay.dts
@@ -0,0 +1,35 @@
+/* Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/clock/qcom,gcc-sdm845.h>
+#include <dt-bindings/clock/qcom,camcc-sdm845.h>
+#include <dt-bindings/clock/qcom,dispcc-sdm845.h>
+#include <dt-bindings/clock/qcom,rpmh.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
+#include "sdm670-int-cdc-aqt.dtsi"
+#include "sdm670-cdp.dtsi"
+#include "sdm670-int-cdc-aqt-overlay.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM670 PM660 + PM660L AQT CDP";
+ compatible = "qcom,sdm670-cdp", "qcom,sdm670", "qcom,cdp";
+ qcom,msm-id = <336 0x0>;
+ qcom,board-id = <1 4>;
+ qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>,
+ <0x0001001b 0x0102001a 0x0 0x0>,
+ <0x0001001b 0x0201011a 0x0 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm670-audio-overlay.dtsi b/arch/arm64/boot/dts/qcom/sdm670-audio-overlay.dtsi
index 2b3cb39..4d6b32f 100644
--- a/arch/arm64/boot/dts/qcom/sdm670-audio-overlay.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670-audio-overlay.dtsi
@@ -320,6 +320,57 @@
wdsp_glink: qcom,wcd-dsp-glink {
compatible = "qcom,wcd-dsp-glink";
};
+
+ aqt_rst_gpio: aqt_cdc_pinctrl {
+ status = "disabled";
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&aqt_rst_active>;
+ pinctrl-1 = <&aqt_rst_idle>;
+ };
+
+ tert_mi2s_gpios: tert_mi2s_pinctrl {
+ status = "disabled";
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&ter_i2s_data0_active &ter_i2s_data1_active
+ &ter_i2s_sck_active>;
+ pinctrl-1 = <&ter_i2s_data0_sleep &ter_i2s_data1_sleep
+ &ter_i2s_sck_sleep>;
+ };
+
+ i2c@a88000 {
+ aqt1000_cdc: aqt1000-i2c-codec@d {
+ status = "disabled";
+ compatible = "qcom,aqt1000-i2c-codec";
+ reg = <0x0d>;
+
+ interrupt-controller;
+ #interrupt-cells = <1>;
+ interrupt-parent = <&tlmm>;
+ qcom,gpio-connect = <&tlmm 79 0>;
+ pinctrl-names = "default";
+ pinctrl-0 = <&aqt_intr_default>;
+
+ qcom,aqt-rst-gpio-node = <&aqt_rst_gpio>;
+
+ qcom,cdc-vdd-mic-bias-supply = <&pm660l_bob>;
+ qcom,cdc-vdd-mic-bias-voltage = <3312000 3312000>;
+ qcom,cdc-vdd-mic-bias-current = <30400>;
+
+ qcom,cdc-static-supplies = "cdc-vdd-mic-bias";
+
+ qcom,cdc-micbias-ldoh-v = <3>;
+
+ qcom,cdc-ext-clk-rate = <19200000>;
+ qcom,cdc-mclk-clk-rate = <9600000>;
+
+ qcom,cdc-micbias1-mv = <1800>;
+
+ clock-names = "aqt_clk";
+ clocks = <&clock_audio_lnbb AUDIO_PMIC_LNBB_CLK>;
+ };
+ };
};
&slim_aud {
diff --git a/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-cdp.dtsi b/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-cdp.dtsi
index 3cad0e2..f71fbd3 100644
--- a/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-cdp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-cdp.dtsi
@@ -129,7 +129,7 @@
rgltr-load-current = <0>;
};
- actuator_front: qcom,actuator@1 {
+ actuator_rear_aux: qcom,actuator@1 {
cell-index = <1>;
reg = <0x1>;
compatible = "qcom,actuator";
@@ -142,6 +142,19 @@
rgltr-load-current = <0>;
};
+ actuator_front: qcom,actuator@2 {
+ cell-index = <2>;
+ reg = <0x2>;
+ compatible = "qcom,actuator";
+ cci-master = <1>;
+ cam_vaf-supply = <&actuator_regulator>;
+ regulator-names = "cam_vaf";
+ rgltr-cntrl-support;
+ rgltr-min-voltage = <2800000>;
+ rgltr-max-voltage = <2800000>;
+ rgltr-load-current = <0>;
+ };
+
ois_rear: qcom,ois@0 {
cell-index = <0>;
reg = <0x0>;
@@ -316,10 +329,11 @@
compatible = "qcom,cam-sensor";
reg = <0x1>;
csiphy-sd-index = <1>;
- sensor-position-roll = <90>;
+ sensor-position-roll = <270>;
sensor-position-pitch = <0>;
sensor-position-yaw = <180>;
led-flash-src = <&led_flash_rear_aux>;
+ actuator-src = <&actuator_rear_aux>;
eeprom-src = <&eeprom_rear_aux>;
cam_vio-supply = <&camera_vio_ldo>;
cam_vana-supply = <&camera_vana_ldo>;
diff --git a/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-mtp.dtsi b/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-mtp.dtsi
index 3cad0e2..f71fbd3 100644
--- a/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-mtp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670-camera-sensor-mtp.dtsi
@@ -129,7 +129,7 @@
rgltr-load-current = <0>;
};
- actuator_front: qcom,actuator@1 {
+ actuator_rear_aux: qcom,actuator@1 {
cell-index = <1>;
reg = <0x1>;
compatible = "qcom,actuator";
@@ -142,6 +142,19 @@
rgltr-load-current = <0>;
};
+ actuator_front: qcom,actuator@2 {
+ cell-index = <2>;
+ reg = <0x2>;
+ compatible = "qcom,actuator";
+ cci-master = <1>;
+ cam_vaf-supply = <&actuator_regulator>;
+ regulator-names = "cam_vaf";
+ rgltr-cntrl-support;
+ rgltr-min-voltage = <2800000>;
+ rgltr-max-voltage = <2800000>;
+ rgltr-load-current = <0>;
+ };
+
ois_rear: qcom,ois@0 {
cell-index = <0>;
reg = <0x0>;
@@ -316,10 +329,11 @@
compatible = "qcom,cam-sensor";
reg = <0x1>;
csiphy-sd-index = <1>;
- sensor-position-roll = <90>;
+ sensor-position-roll = <270>;
sensor-position-pitch = <0>;
sensor-position-yaw = <180>;
led-flash-src = <&led_flash_rear_aux>;
+ actuator-src = <&actuator_rear_aux>;
eeprom-src = <&eeprom_rear_aux>;
cam_vio-supply = <&camera_vio_ldo>;
cam_vana-supply = <&camera_vana_ldo>;
diff --git a/arch/arm64/boot/dts/qcom/sdm670-int-cdc-aqt-overlay.dtsi b/arch/arm64/boot/dts/qcom/sdm670-int-cdc-aqt-overlay.dtsi
new file mode 100644
index 0000000..5f70790
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm670-int-cdc-aqt-overlay.dtsi
@@ -0,0 +1,85 @@
+/* Copyright (c) 2018, 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.
+ */
+
+&int_codec {
+ qcom,model = "sdm670-aqt-snd-card";
+ qcom,msm-mi2s-master = <1>, <1>, <0>, <1>, <1>;
+ qcom,tert-mi2s-gpios = <&tert_mi2s_gpios>;
+ qcom,us-euro-gpios = <&wcd_usbc_analog_en2_gpio>;
+ asoc-codec = <&stub_codec>, <&msm_digital_codec>,
+ <&pmic_analog_codec>, <&msm_sdw_codec>,
+ <&ext_disp_audio_codec>, <&aqt1000_cdc>;
+ qcom,audio-routing =
+ "RX_BIAS", "INT_MCLK0",
+ "SPK_RX_BIAS", "INT_MCLK0",
+ "INT_LDO_H", "INT_MCLK0",
+ "RX_I2S_CLK", "INT_MCLK0",
+ "TX_I2S_CLK", "INT_MCLK0",
+ "MIC BIAS External", "Handset Mic",
+ "AQT MIC BIAS1", "Headset Mic",
+ "MIC BIAS External", "Secondary Mic",
+ "AMIC1", "MIC BIAS External",
+ "AMIC2", "AQT MIC BIAS1",
+ "AMIC3", "MIC BIAS External",
+ "DMIC1", "MIC BIAS External",
+ "MIC BIAS External", "Digital Mic1",
+ "DMIC2", "MIC BIAS External",
+ "MIC BIAS External", "Digital Mic2",
+ "DMIC3", "MIC BIAS External",
+ "MIC BIAS External", "Digital Mic3",
+ "DMIC4", "MIC BIAS External",
+ "MIC BIAS External", "Digital Mic4",
+ "SpkrLeft IN", "SPK1 OUT",
+ "SpkrRight IN", "SPK2 OUT",
+ "PDM_IN_RX1", "PDM_OUT_RX1",
+ "PDM_IN_RX2", "PDM_OUT_RX2",
+ "PDM_IN_RX3", "PDM_OUT_RX3",
+ "ADC1_IN", "ADC1_OUT",
+ "ADC2_IN", "ADC2_OUT",
+ "ADC3_IN", "ADC3_OUT";
+ asoc-codec-names = "msm-stub-codec.1", "msm-dig-codec",
+ "analog-codec", "msm_sdw_codec",
+ "msm-ext-disp-audio-codec-rx", "aqt1000-i2c-codec";
+ qcom,mi2s-aqt-enabled;
+};
+
+&pmic_analog_codec {
+ qcom,anlg-cdc-mbhc-disable;
+};
+
+&soc {
+ i2c@a88000 {
+ status = "ok";
+ };
+ wcd_usbc_analog_en2_gpio: msm_cdc_pinctrl_usbc_audio_en2 {
+ compatible = "qcom,msm-cdc-pinctrl";
+ pinctrl-names = "aud_active", "aud_sleep";
+ pinctrl-0 = <&wcd_usbc_analog_en2_active>;
+ pinctrl-1 = <&wcd_usbc_analog_en2_idle>;
+ };
+};
+
+&tert_mi2s_gpios {
+ status = "ok";
+};
+
+&clock_audio_lnbb {
+ status = "ok";
+};
+
+&aqt1000_cdc {
+ status = "ok";
+};
+
+&aqt_rst_gpio {
+ status = "ok";
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm670-int-cdc-aqt.dtsi b/arch/arm64/boot/dts/qcom/sdm670-int-cdc-aqt.dtsi
new file mode 100644
index 0000000..56e60f2
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm670-int-cdc-aqt.dtsi
@@ -0,0 +1,64 @@
+/* Copyright (c) 2018, 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 "sdm670-audio-overlay.dtsi"
+
+&dai_mi2s2 {
+ qcom,msm-mi2s-rx-lines = <1>;
+ qcom,msm-mi2s-tx-lines = <2>;
+};
+
+&dsi_dual_nt35597_truly_video_display {
+ qcom,platform-reset-gpio = <&tlmm 90 0>;
+ qcom,panel-mode-gpio = <&tlmm 4 0>;
+};
+
+&dsi_dual_nt35597_truly_cmd_display {
+ qcom,platform-reset-gpio = <&tlmm 90 0>;
+ qcom,panel-mode-gpio = <&tlmm 4 0>;
+};
+
+&dsi_nt35597_truly_dsc_cmd_display {
+ qcom,platform-reset-gpio = <&tlmm 90 0>;
+ qcom,panel-mode-gpio = <&tlmm 4 0>;
+};
+
+&dsi_nt35597_truly_dsc_video_display {
+ qcom,platform-reset-gpio = <&tlmm 90 0>;
+ qcom,panel-mode-gpio = <&tlmm 4 0>;
+};
+
+&sde_dsi_active {
+ mux {
+ pins = "gpio90", "gpio4";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio90", "gpio4";
+ drive-strength = <8>; /* 8 mA */
+ bias-disable = <0>; /* no pull */
+ };
+};
+
+&sde_dsi_suspend {
+ mux {
+ pins = "gpio90", "gpio4";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio90", "gpio4";
+ drive-strength = <2>; /* 2 mA */
+ bias-pull-down; /* PULL DOWN */
+ };
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm670-mtp.dtsi b/arch/arm64/boot/dts/qcom/sdm670-mtp.dtsi
index 68f51e2..cc55127 100644
--- a/arch/arm64/boot/dts/qcom/sdm670-mtp.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670-mtp.dtsi
@@ -141,6 +141,10 @@
qcom,battery-data = <&mtp_batterydata>;
};
+&pm660_charger {
+ qcom,battery-data = <&mtp_batterydata>;
+};
+
&tlmm {
smb_int_default: smb_int_default {
mux {
diff --git a/arch/arm64/boot/dts/qcom/sdm670-pinctrl.dtsi b/arch/arm64/boot/dts/qcom/sdm670-pinctrl.dtsi
index 5684e19..0461429 100644
--- a/arch/arm64/boot/dts/qcom/sdm670-pinctrl.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670-pinctrl.dtsi
@@ -21,6 +21,52 @@
#interrupt-cells = <2>;
interrupt-parent = <&pdc>;
+ ufs_dev_reset_assert: ufs_dev_reset_assert {
+ config {
+ pins = "ufs_reset";
+ bias-pull-down; /* default: pull down */
+ /*
+ * UFS_RESET driver strengths are having
+ * different values/steps compared to typical
+ * GPIO drive strengths.
+ *
+ * Following table clarifies:
+ *
+ * HDRV value | UFS_RESET | Typical GPIO
+ * (dec) | (mA) | (mA)
+ * 0 | 0.8 | 2
+ * 1 | 1.55 | 4
+ * 2 | 2.35 | 6
+ * 3 | 3.1 | 8
+ * 4 | 3.9 | 10
+ * 5 | 4.65 | 12
+ * 6 | 5.4 | 14
+ * 7 | 6.15 | 16
+ *
+ * POR value for UFS_RESET HDRV is 3 which means
+ * 3.1mA and we want to use that. Hence just
+ * specify 8mA to "drive-strength" binding and
+ * that should result into writing 3 to HDRV
+ * field.
+ */
+ drive-strength = <8>; /* default: 3.1 mA */
+ output-low; /* active low reset */
+ };
+ };
+
+ ufs_dev_reset_deassert: ufs_dev_reset_deassert {
+ config {
+ pins = "ufs_reset";
+ bias-pull-down; /* default: pull down */
+ /*
+ * default: 3.1 mA
+ * check comments under ufs_dev_reset_assert
+ */
+ drive-strength = <8>;
+ output-high; /* active low reset */
+ };
+ };
+
/* QUPv3 South SE mappings */
/* SE 0 pin mappings */
qupv3_se0_i2c_pins: qupv3_se0_i2c_pins {
@@ -1679,6 +1725,132 @@
};
};
+ aqt_intr {
+ aqt_intr_default: aqt_intr_default{
+ mux {
+ pins = "gpio79";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio79";
+ drive-strength = <2>; /* 2 mA */
+ bias-pull-down; /* pull down */
+ input-enable;
+ };
+ };
+ };
+
+ aqt_rst_gpio {
+ aqt_rst_idle: aqt_rst_idle{
+ mux {
+ pins = "gpio80";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio80";
+ drive-strength = <8>;
+ bias-pull-down;
+ output-low;
+ };
+ };
+ aqt_rst_active: aqt_rst_active{
+ mux {
+ pins = "gpio80";
+ function = "gpio";
+ };
+
+ config {
+ pins = "gpio80";
+ drive-strength = <8>;
+ bias-disable;
+ output-high;
+ };
+ };
+ };
+
+ ter_i2s_sck_ws {
+ ter_i2s_sck_sleep: ter_i2s_sck_sleep {
+ mux {
+ pins = "gpio75", "gpio76";
+ function = "ter_mi2s";
+ };
+
+ config {
+ pins = "gpio75", "gpio76";
+ drive-strength = <2>; /* 2 mA */
+ };
+ };
+
+ ter_i2s_sck_active: ter_i2s_sck_active {
+ mux {
+ pins = "gpio75", "gpio76";
+ function = "ter_mi2s";
+ };
+
+ config {
+ pins = "gpio75", "gpio76";
+ drive-strength = <8>; /* 8 mA */
+ input-enable;
+ };
+ };
+ };
+
+ ter_i2s_data0 {
+ ter_i2s_data0_sleep: ter_i2s_data0_sleep {
+ mux {
+ pins = "gpio77";
+ function = "ter_mi2s";
+ };
+
+ config {
+ pins = "gpio77";
+ drive-strength = <2>; /* 2 mA */
+ };
+ };
+
+ ter_i2s_data0_active: ter_i2s_data0_active {
+ mux {
+ pins = "gpio77";
+ function = "ter_mi2s";
+ };
+
+ config {
+ pins = "gpio77";
+ drive-strength = <8>; /* 8 mA */
+ input-enable;
+ };
+ };
+ };
+
+ ter_i2s_data1 {
+ ter_i2s_data1_sleep: ter_i2s_data1_sleep {
+ mux {
+ pins = "gpio78";
+ function = "ter_mi2s";
+ };
+
+ config {
+ pins = "gpio78";
+ drive-strength = <2>; /* 2 mA */
+ };
+ };
+
+ ter_i2s_data1_active: ter_i2s_data1_active {
+ mux {
+ pins = "gpio78";
+ function = "ter_mi2s";
+ };
+
+ config {
+ pins = "gpio78";
+ drive-strength = <8>; /* 8 mA */
+ output-high;
+ };
+ };
+ };
+
pmx_sde: pmx_sde {
sde_dsi_active: sde_dsi_active {
mux {
diff --git a/arch/arm64/boot/dts/qcom/sdm670-pm.dtsi b/arch/arm64/boot/dts/qcom/sdm670-pm.dtsi
index c54b8db..bdcd039 100644
--- a/arch/arm64/boot/dts/qcom/sdm670-pm.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670-pm.dtsi
@@ -23,6 +23,7 @@
label = "L3";
qcom,psci-mode-shift = <4>;
qcom,psci-mode-mask = <0xfff>;
+ qcom,clstr-tmr-add = <1000>;
qcom,pm-cluster-level@0 { /* D1 */
reg = <0>;
@@ -77,7 +78,9 @@
#size-cells = <0>;
qcom,psci-mode-shift = <0>;
qcom,psci-mode-mask = <0xf>;
- qcom,use-prediction;
+ qcom,ref-stddev = <500>;
+ qcom,tmr-add = <1000>;
+ qcom,ref-premature-cnt = <1>;
qcom,cpu = <&CPU0 &CPU1 &CPU2 &CPU3 &CPU4
&CPU5>;
@@ -131,6 +134,7 @@
#size-cells = <0>;
qcom,psci-mode-shift = <0>;
qcom,psci-mode-mask = <0xf>;
+ qcom,disable-prediction;
qcom,cpu = <&CPU6 &CPU7>;
qcom,pm-cpu-level@0 { /* C1 */
diff --git a/arch/arm64/boot/dts/qcom/sdm670-pm660a-aqt1000-cdp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm670-pm660a-aqt1000-cdp-overlay.dts
new file mode 100644
index 0000000..1260e05
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm670-pm660a-aqt1000-cdp-overlay.dts
@@ -0,0 +1,75 @@
+/* Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/clock/qcom,gcc-sdm845.h>
+#include <dt-bindings/clock/qcom,camcc-sdm845.h>
+#include <dt-bindings/clock/qcom,dispcc-sdm845.h>
+#include <dt-bindings/clock/qcom,rpmh.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
+#include "sdm670-int-cdc-aqt.dtsi"
+#include "sdm670-cdp.dtsi"
+#include "sdm670-int-cdc-aqt-overlay.dtsi"
+#include "pm660a.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM670 PM660 + PM660A AQT CDP";
+ compatible = "qcom,sdm670-cdp", "qcom,sdm670", "qcom,cdp";
+ qcom,msm-id = <336 0x0>;
+ qcom,board-id = <1 4>;
+ qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>,
+ <0x0001001b 0x0002001a 0x0 0x0>,
+ <0x0001001b 0x0202001a 0x0 0x0>;
+};
+
+&dsi_dual_nt35597_truly_video_display {
+ /delete-property/ qcom,dsi-display-active;
+};
+
+&dsi_panel_pwr_supply_labibb_amoled {
+ qcom,panel-supply-entry@2 {
+ reg = <2>;
+ qcom,supply-name = "lab";
+ qcom,supply-min-voltage = <4600000>;
+ qcom,supply-max-voltage = <6100000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+
+ qcom,panel-supply-entry@3 {
+ reg = <3>;
+ qcom,supply-name = "ibb";
+ qcom,supply-min-voltage = <4000000>;
+ qcom,supply-max-voltage = <6300000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+
+ qcom,panel-supply-entry@4 {
+ reg = <4>;
+ qcom,supply-name = "oledb";
+ qcom,supply-min-voltage = <5000000>;
+ qcom,supply-max-voltage = <8100000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+};
+
+&dsi_rm67195_amoled_fhd_cmd_display {
+ qcom,dsi-display-active;
+ lab-supply = <&lab_regulator>;
+ ibb-supply = <&ibb_regulator>;
+ oledb-supply = <&pm660a_oledb>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm670.dtsi b/arch/arm64/boot/dts/qcom/sdm670.dtsi
index 4d4e918..3ca33b2 100644
--- a/arch/arm64/boot/dts/qcom/sdm670.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm670.dtsi
@@ -1790,7 +1790,7 @@
};
dcc: dcc_v2@10a2000 {
- compatible = "qcom,dcc_v2";
+ compatible = "qcom,dcc-v2";
reg = <0x10a2000 0x1000>,
<0x10ae000 0x2000>;
reg-names = "dcc-base", "dcc-ram-base";
@@ -1935,6 +1935,10 @@
qcom,pm-qos-cpu-group-latency-us = <67 67>;
qcom,pm-qos-default-cpu = <0>;
+ pinctrl-names = "dev-reset-assert", "dev-reset-deassert";
+ pinctrl-0 = <&ufs_dev_reset_assert>;
+ pinctrl-1 = <&ufs_dev_reset_deassert>;
+
resets = <&clock_gcc GCC_UFS_PHY_BCR>;
reset-names = "core_reset";
@@ -2007,7 +2011,7 @@
<0 432 0>;
interrupt-names = "ipa-irq", "gsi-irq";
qcom,ipa-hw-ver = <13>; /* IPA core version = IPAv3.5.1 */
- qcom,ipa-hw-mode = <1>;
+ qcom,ipa-hw-mode = <0>;
qcom,ee = <0>;
qcom,use-ipa-tethering-bridge;
qcom,modem-cfg-emb-pipe-flt;
diff --git a/arch/arm64/boot/dts/qcom/sdm710-aqt1000-cdp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm710-aqt1000-cdp-overlay.dts
new file mode 100644
index 0000000..31c99de
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm710-aqt1000-cdp-overlay.dts
@@ -0,0 +1,35 @@
+/* Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/clock/qcom,gcc-sdm845.h>
+#include <dt-bindings/clock/qcom,camcc-sdm845.h>
+#include <dt-bindings/clock/qcom,dispcc-sdm845.h>
+#include <dt-bindings/clock/qcom,rpmh.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
+#include "sdm670-int-cdc-aqt.dtsi"
+#include "sdm670-cdp.dtsi"
+#include "sdm670-int-cdc-aqt-overlay.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM710 PM660 + PM660L AQT CDP";
+ compatible = "qcom,sdm670-cdp", "qcom,sdm670", "qcom,cdp";
+ qcom,msm-id = <360 0x0>;
+ qcom,board-id = <1 4>;
+ qcom,pmic-id = <0x0001001b 0x0101011a 0x0 0x0>,
+ <0x0001001b 0x0102001a 0x0 0x0>,
+ <0x0001001b 0x0201011a 0x0 0x0>;
+};
+
diff --git a/arch/arm64/boot/dts/qcom/sdm710-pm660a-aqt1000-cdp-overlay.dts b/arch/arm64/boot/dts/qcom/sdm710-pm660a-aqt1000-cdp-overlay.dts
new file mode 100644
index 0000000..50b3470
--- /dev/null
+++ b/arch/arm64/boot/dts/qcom/sdm710-pm660a-aqt1000-cdp-overlay.dts
@@ -0,0 +1,75 @@
+/* Copyright (c) 2018, 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/;
+/plugin/;
+
+#include <dt-bindings/clock/qcom,gcc-sdm845.h>
+#include <dt-bindings/clock/qcom,camcc-sdm845.h>
+#include <dt-bindings/clock/qcom,dispcc-sdm845.h>
+#include <dt-bindings/clock/qcom,rpmh.h>
+#include <dt-bindings/interrupt-controller/arm-gic.h>
+
+#include "sdm670-cdp.dtsi"
+#include "pm660a.dtsi"
+#include "sdm670-int-cdc-aqt.dtsi"
+#include "sdm670-int-cdc-aqt-overlay.dtsi"
+
+/ {
+ model = "Qualcomm Technologies, Inc. SDM710 PM660 + PM660A AQT CDP";
+ compatible = "qcom,sdm670-cdp", "qcom,sdm670", "qcom,cdp";
+ qcom,msm-id = <360 0x0>;
+ qcom,board-id = <1 4>;
+ qcom,pmic-id = <0x0001001b 0x0001011a 0x0 0x0>,
+ <0x0001001b 0x0002001a 0x0 0x0>,
+ <0x0001001b 0x0202001a 0x0 0x0>;
+};
+
+&dsi_dual_nt35597_truly_video_display {
+ /delete-property/ qcom,dsi-display-active;
+};
+
+&dsi_panel_pwr_supply_labibb_amoled {
+ qcom,panel-supply-entry@2 {
+ reg = <2>;
+ qcom,supply-name = "lab";
+ qcom,supply-min-voltage = <4600000>;
+ qcom,supply-max-voltage = <6100000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+
+ qcom,panel-supply-entry@3 {
+ reg = <3>;
+ qcom,supply-name = "ibb";
+ qcom,supply-min-voltage = <4000000>;
+ qcom,supply-max-voltage = <6300000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+
+ qcom,panel-supply-entry@4 {
+ reg = <4>;
+ qcom,supply-name = "oledb";
+ qcom,supply-min-voltage = <5000000>;
+ qcom,supply-max-voltage = <8100000>;
+ qcom,supply-enable-load = <100000>;
+ qcom,supply-disable-load = <100>;
+ };
+};
+
+&dsi_rm67195_amoled_fhd_cmd_display {
+ qcom,dsi-display-active;
+ lab-supply = <&lab_regulator>;
+ ibb-supply = <&ibb_regulator>;
+ oledb-supply = <&pm660a_oledb>;
+};
diff --git a/arch/arm64/boot/dts/qcom/sdm710.dtsi b/arch/arm64/boot/dts/qcom/sdm710.dtsi
index 4a051b0..347e846 100644
--- a/arch/arm64/boot/dts/qcom/sdm710.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm710.dtsi
@@ -19,7 +19,7 @@
};
&msm_gpu {
- qcom,chipid = <0x06010500>;
+ qcom,chipid = <0x06010600>;
/delete-property/qcom,gpu-quirk-limit-uche-gbif-rw;
/delete-property/qcom,soc-hw-rev-efuse;
/delete-node/qcom,soc-hw-revisions;
diff --git a/arch/arm64/boot/dts/qcom/sdm845-pcie.dtsi b/arch/arm64/boot/dts/qcom/sdm845-pcie.dtsi
index af7feb5..c00c264 100644
--- a/arch/arm64/boot/dts/qcom/sdm845-pcie.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm845-pcie.dtsi
@@ -259,7 +259,7 @@
"pcie_tbu_clk", "pcie_phy_refgen_clk",
"pcie_phy_aux_clk";
- max-clock-frequency-hz = <0>, <0>, <19200000>, <0>, <0>,
+ max-clock-frequency-hz = <0>, <0>, <19200000>, <0>, <0>, <0>,
<0>, <0>, <0>, <0>, <100000000>, <0>;
resets = <&clock_gcc GCC_PCIE_0_BCR>,
@@ -382,28 +382,29 @@
0x01d0 0x30 0x0
0x01e0 0x04 0x0
0x01e8 0x73 0x0
- 0x01f0 0x1c 0x0
+ 0x01f0 0x0c 0x0
0x01fc 0x15 0x0
0x021c 0x04 0x0
0x0224 0x01 0x0
0x0228 0x22 0x0
0x022c 0x00 0x0
- 0x0098 0x05 0x0
+ 0x0098 0x20 0x0
+ 0x01c8 0x07 0x0
0x080c 0x00 0x0
0x0818 0x0d 0x0
0x0860 0x01 0x0
- 0x0864 0x3a 0x0
+ 0x0864 0x1a 0x0
0x087c 0x2f 0x0
0x08c0 0x09 0x0
0x08c4 0x09 0x0
- 0x08c8 0x1a 0x0
+ 0x08c8 0x1b 0x0
0x08d0 0x01 0x0
0x08d4 0x07 0x0
0x08d8 0x31 0x0
0x08dc 0x31 0x0
0x08e0 0x03 0x0
0x08fc 0x02 0x0
- 0x0900 0x01 0x0
+ 0x0900 0x00 0x0
0x0908 0x12 0x0
0x0914 0x25 0x0
0x0918 0x00 0x0
@@ -415,17 +416,17 @@
0x0934 0x04 0x0
0x0938 0x09 0x0
0x0954 0x15 0x0
- 0x0960 0x32 0x0
+ 0x0960 0x28 0x0
0x0968 0x7f 0x0
0x096c 0x07 0x0
0x0978 0x04 0x0
0x0980 0x70 0x0
0x0984 0x8b 0x0
0x0988 0x08 0x0
- 0x098c 0x09 0x0
+ 0x098c 0x0a 0x0
0x0990 0x03 0x0
0x0994 0x04 0x0
- 0x0998 0x02 0x0
+ 0x0998 0x04 0x0
0x099c 0x0c 0x0
0x09a4 0x02 0x0
0x09c0 0x5c 0x0
@@ -437,78 +438,22 @@
0x0aa4 0x01 0x0
0x0aac 0xc3 0x0
0x0ab0 0x00 0x0
- 0x0ab8 0x8c 0x0
+ 0x0ab8 0xbc 0x0
0x0ac0 0x7f 0x0
- 0x0ac4 0x2a 0x0
+ 0x0ac4 0x15 0x0
0x0810 0x0c 0x0
- 0x0814 0x00 0x0
+ 0x0814 0x0f 0x0
0x0acc 0x04 0x0
0x093c 0x20 0x0
- 0x100c 0x00 0x0
- 0x1018 0x0d 0x0
- 0x1060 0x01 0x0
- 0x1064 0x3a 0x0
- 0x107c 0x2f 0x0
- 0x10c0 0x09 0x0
- 0x10c4 0x09 0x0
- 0x10c8 0x1a 0x0
- 0x10d0 0x01 0x0
- 0x10d4 0x07 0x0
- 0x10d8 0x31 0x0
- 0x10dc 0x31 0x0
- 0x10e0 0x03 0x0
- 0x10fc 0x02 0x0
- 0x1100 0x01 0x0
- 0x1108 0x12 0x0
- 0x1114 0x25 0x0
- 0x1118 0x00 0x0
- 0x111c 0x05 0x0
- 0x1120 0x01 0x0
- 0x1124 0x26 0x0
- 0x1128 0x12 0x0
- 0x1130 0x04 0x0
- 0x1134 0x04 0x0
- 0x1138 0x09 0x0
- 0x1154 0x15 0x0
- 0x1160 0x32 0x0
- 0x1168 0x7f 0x0
- 0x116c 0x07 0x0
- 0x1178 0x04 0x0
- 0x1180 0x70 0x0
- 0x1184 0x8b 0x0
- 0x1188 0x08 0x0
- 0x118c 0x09 0x0
- 0x1190 0x03 0x0
- 0x1194 0x04 0x0
- 0x1198 0x02 0x0
- 0x119c 0x0c 0x0
- 0x11a4 0x02 0x0
- 0x11c0 0x5c 0x0
- 0x11c4 0x3e 0x0
- 0x11c8 0x3f 0x0
- 0x1230 0x01 0x0
- 0x1234 0xa0 0x0
- 0x1238 0x08 0x0
- 0x12a4 0x01 0x0
- 0x12ac 0xc3 0x0
- 0x12b0 0x00 0x0
- 0x12b8 0x8c 0x0
- 0x12c0 0x7f 0x0
- 0x12c4 0x2a 0x0
- 0x1010 0x0c 0x0
- 0x1014 0x00 0x0
- 0x12cc 0x04 0x0
- 0x113c 0x20 0x0
0x195c 0x3f 0x0
- 0x1974 0x58 0x0
- 0x196c 0x9f 0x0
+ 0x1974 0x50 0x0
0x182c 0x19 0x0
0x1840 0x07 0x0
0x1854 0x17 0x0
0x1868 0x09 0x0
+ 0x196c 0x9f 0x0
0x1800 0x00 0x0
0x0aa8 0x01 0x0
- 0x12a8 0x01 0x0
0x1808 0x01 0x0>;
pinctrl-names = "default";
@@ -595,7 +540,7 @@
"pcie_tbu_clk", "pcie_phy_refgen_clk",
"pcie_phy_aux_clk";
- max-clock-frequency-hz = <0>, <0>, <19200000>, <0>, <0>,
+ max-clock-frequency-hz = <0>, <0>, <19200000>, <0>, <0>, <0>,
<0>, <0>, <0>, <0>, <100000000>, <0>;
resets = <&clock_gcc GCC_PCIE_1_BCR>,
diff --git a/arch/arm64/boot/dts/qcom/sdm845-pm.dtsi b/arch/arm64/boot/dts/qcom/sdm845-pm.dtsi
index 929239a..350f156 100644
--- a/arch/arm64/boot/dts/qcom/sdm845-pm.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm845-pm.dtsi
@@ -21,6 +21,7 @@
#address-cells = <1>;
#size-cells = <0>;
label = "L3";
+ qcom,clstr-tmr-add = <1000>;
qcom,psci-mode-shift = <4>;
qcom,psci-mode-mask = <0xfff>;
@@ -52,7 +53,9 @@
#size-cells = <0>;
qcom,psci-mode-shift = <0>;
qcom,psci-mode-mask = <0xf>;
- qcom,use-prediction;
+ qcom,ref-stddev = <500>;
+ qcom,tmr-add = <1000>;
+ qcom,ref-premature-cnt = <1>;
qcom,cpu = <&CPU0 &CPU1 &CPU2 &CPU3>;
qcom,pm-cpu-level@0 { /* C1 */
@@ -95,6 +98,9 @@
#size-cells = <0>;
qcom,psci-mode-shift = <0>;
qcom,psci-mode-mask = <0xf>;
+ qcom,ref-stddev = <100>;
+ qcom,tmr-add = <100>;
+ qcom,ref-premature-cnt = <3>;
qcom,cpu = <&CPU4 &CPU5 &CPU6 &CPU7>;
qcom,pm-cpu-level@0 { /* C1 */
diff --git a/arch/arm64/boot/dts/qcom/sdm845.dtsi b/arch/arm64/boot/dts/qcom/sdm845.dtsi
index 82e55c4..ffc68d2 100644
--- a/arch/arm64/boot/dts/qcom/sdm845.dtsi
+++ b/arch/arm64/boot/dts/qcom/sdm845.dtsi
@@ -1908,6 +1908,11 @@
reg = <0x65c 4>;
};
+ dload_type@1c {
+ compatible = "qcom,msm-imem-dload-type";
+ reg = <0x1c 0x4>;
+ };
+
boot_stats@6b0 {
compatible = "qcom,msm-imem-boot_stats";
reg = <0x6b0 32>;
@@ -2838,7 +2843,7 @@
};
dcc: dcc_v2@10a2000 {
- compatible = "qcom,dcc_v2";
+ compatible = "qcom,dcc-v2";
reg = <0x10a2000 0x1000>,
<0x10ae000 0x2000>;
reg-names = "dcc-base", "dcc-ram-base";
@@ -3767,57 +3772,57 @@
compatible = "qcom,mem-dump";
memory-region = <&dump_mem>;
- rpmh_dump {
+ rpmh {
qcom,dump-size = <0x2000000>;
qcom,dump-id = <0xec>;
};
- fcm_dump {
+ fcm {
qcom,dump-size = <0x8400>;
qcom,dump-id = <0xee>;
};
- rpm_sw_dump {
+ rpm_sw {
qcom,dump-size = <0x28000>;
qcom,dump-id = <0xea>;
};
- pmic_dump {
+ pmic {
qcom,dump-size = <0x10000>;
qcom,dump-id = <0xe4>;
};
- tmc_etf_dump {
+ tmc_etf {
qcom,dump-size = <0x10000>;
qcom,dump-id = <0xf0>;
};
- tmc_etf_swao_dump {
+ tmc_etfswao {
qcom,dump-size = <0x8400>;
qcom,dump-id = <0xf1>;
};
- tmc_etr_reg_dump {
+ tmc_etr_reg {
qcom,dump-size = <0x1000>;
qcom,dump-id = <0x100>;
};
- tmc_etf_reg_dump {
+ tmc_etf_reg {
qcom,dump-size = <0x1000>;
qcom,dump-id = <0x101>;
};
- tmc_etf_swao_reg_dump {
+ etfswao_reg {
qcom,dump-size = <0x1000>;
qcom,dump-id = <0x102>;
};
- misc_data_dump {
+ misc_data {
qcom,dump-size = <0x1000>;
qcom,dump-id = <0xe8>;
};
- tpdm_swao_dump {
+ tpdm_swao {
qcom,dump-size = <0x512>;
qcom,dump-id = <0xf2>;
};
diff --git a/arch/arm64/configs/msm8937-perf_defconfig b/arch/arm64/configs/msm8937-perf_defconfig
new file mode 100644
index 0000000..363f2dd
--- /dev/null
+++ b/arch/arm64/configs/msm8937-perf_defconfig
@@ -0,0 +1,630 @@
+CONFIG_LOCALVERSION="-perf"
+# CONFIG_LOCALVERSION_AUTO is not set
+# CONFIG_FHANDLE is not set
+CONFIG_AUDIT=y
+# CONFIG_AUDITSYSCALL is not set
+CONFIG_NO_HZ=y
+CONFIG_HIGH_RES_TIMERS=y
+CONFIG_IRQ_TIME_ACCOUNTING=y
+CONFIG_SCHED_WALT=y
+CONFIG_RCU_EXPERT=y
+CONFIG_RCU_FAST_NO_HZ=y
+CONFIG_RCU_NOCB_CPU=y
+CONFIG_RCU_NOCB_CPU_ALL=y
+CONFIG_IKCONFIG=y
+CONFIG_IKCONFIG_PROC=y
+CONFIG_LOG_CPU_MAX_BUF_SHIFT=17
+CONFIG_CGROUP_FREEZER=y
+CONFIG_CPUSETS=y
+CONFIG_CGROUP_CPUACCT=y
+CONFIG_CGROUP_SCHEDTUNE=y
+CONFIG_RT_GROUP_SCHED=y
+CONFIG_CGROUP_BPF=y
+CONFIG_SCHED_CORE_CTL=y
+CONFIG_NAMESPACES=y
+# CONFIG_UTS_NS is not set
+# CONFIG_PID_NS is not set
+CONFIG_SCHED_AUTOGROUP=y
+CONFIG_SCHED_TUNE=y
+CONFIG_DEFAULT_USE_ENERGY_AWARE=y
+CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
+# CONFIG_RD_XZ is not set
+# CONFIG_RD_LZO is not set
+# CONFIG_RD_LZ4 is not set
+CONFIG_KALLSYMS_ALL=y
+CONFIG_BPF_SYSCALL=y
+# CONFIG_MEMBARRIER is not set
+CONFIG_EMBEDDED=y
+# CONFIG_COMPAT_BRK is not set
+CONFIG_PROFILING=y
+CONFIG_CC_STACKPROTECTOR_STRONG=y
+CONFIG_ARCH_MMAP_RND_COMPAT_BITS=16
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+CONFIG_MODULE_FORCE_UNLOAD=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SIG=y
+CONFIG_MODULE_SIG_FORCE=y
+CONFIG_MODULE_SIG_SHA512=y
+# CONFIG_BLK_DEV_BSG is not set
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_IOSCHED_DEADLINE is not set
+CONFIG_ARCH_QCOM=y
+CONFIG_ARCH_MSM8937=y
+CONFIG_ARCH_MSM8917=y
+CONFIG_ARCH_SDM429=y
+CONFIG_ARCH_SDM439=y
+# CONFIG_ARM64_ERRATUM_1024718 is not set
+CONFIG_SCHED_MC=y
+CONFIG_NR_CPUS=8
+CONFIG_PREEMPT=y
+CONFIG_HZ_100=y
+CONFIG_CMA=y
+CONFIG_ZSMALLOC=y
+CONFIG_SECCOMP=y
+CONFIG_HARDEN_BRANCH_PREDICTOR=y
+CONFIG_ARMV8_DEPRECATED=y
+CONFIG_SWP_EMULATION=y
+CONFIG_CP15_BARRIER_EMULATION=y
+CONFIG_SETEND_EMULATION=y
+# CONFIG_ARM64_VHE is not set
+CONFIG_RANDOMIZE_BASE=y
+CONFIG_BUILD_ARM64_APPENDED_DTB_IMAGE=y
+# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
+CONFIG_COMPAT=y
+CONFIG_PM_AUTOSLEEP=y
+CONFIG_PM_WAKELOCKS=y
+CONFIG_PM_WAKELOCKS_LIMIT=0
+# CONFIG_PM_WAKELOCKS_GC is not set
+CONFIG_CPU_IDLE=y
+CONFIG_CPU_FREQ=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=y
+CONFIG_CPU_FREQ_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_ONDEMAND=y
+CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y
+CONFIG_CPU_BOOST=y
+CONFIG_CPU_FREQ_GOV_SCHEDUTIL=y
+CONFIG_CPU_FREQ_MSM=y
+CONFIG_NET=y
+CONFIG_PACKET=y
+CONFIG_UNIX=y
+CONFIG_XFRM_USER=y
+CONFIG_XFRM_STATISTICS=y
+CONFIG_NET_KEY=y
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_VERBOSE=y
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+CONFIG_INET_AH=y
+CONFIG_INET_ESP=y
+CONFIG_INET_IPCOMP=y
+CONFIG_INET_DIAG_DESTROY=y
+CONFIG_IPV6_ROUTER_PREF=y
+CONFIG_IPV6_ROUTE_INFO=y
+CONFIG_IPV6_OPTIMISTIC_DAD=y
+CONFIG_INET6_AH=y
+CONFIG_INET6_ESP=y
+CONFIG_INET6_IPCOMP=y
+CONFIG_IPV6_MIP6=y
+CONFIG_IPV6_MULTIPLE_TABLES=y
+CONFIG_IPV6_SUBTREES=y
+CONFIG_NETFILTER=y
+CONFIG_NF_CONNTRACK=y
+CONFIG_NF_CONNTRACK_SECMARK=y
+CONFIG_NF_CONNTRACK_EVENTS=y
+CONFIG_NF_CT_PROTO_DCCP=y
+CONFIG_NF_CT_PROTO_SCTP=y
+CONFIG_NF_CT_PROTO_UDPLITE=y
+CONFIG_NF_CONNTRACK_AMANDA=y
+CONFIG_NF_CONNTRACK_FTP=y
+CONFIG_NF_CONNTRACK_H323=y
+CONFIG_NF_CONNTRACK_IRC=y
+CONFIG_NF_CONNTRACK_NETBIOS_NS=y
+CONFIG_NF_CONNTRACK_PPTP=y
+CONFIG_NF_CONNTRACK_SANE=y
+CONFIG_NF_CONNTRACK_TFTP=y
+CONFIG_NF_CT_NETLINK=y
+CONFIG_NETFILTER_XT_TARGET_CLASSIFY=y
+CONFIG_NETFILTER_XT_TARGET_CONNMARK=y
+CONFIG_NETFILTER_XT_TARGET_CONNSECMARK=y
+CONFIG_NETFILTER_XT_TARGET_IDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_HARDIDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_LOG=y
+CONFIG_NETFILTER_XT_TARGET_MARK=y
+CONFIG_NETFILTER_XT_TARGET_NFLOG=y
+CONFIG_NETFILTER_XT_TARGET_NFQUEUE=y
+CONFIG_NETFILTER_XT_TARGET_NOTRACK=y
+CONFIG_NETFILTER_XT_TARGET_TEE=y
+CONFIG_NETFILTER_XT_TARGET_TPROXY=y
+CONFIG_NETFILTER_XT_TARGET_TRACE=y
+CONFIG_NETFILTER_XT_TARGET_SECMARK=y
+CONFIG_NETFILTER_XT_TARGET_TCPMSS=y
+CONFIG_NETFILTER_XT_MATCH_COMMENT=y
+CONFIG_NETFILTER_XT_MATCH_CONNLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_CONNMARK=y
+CONFIG_NETFILTER_XT_MATCH_CONNTRACK=y
+CONFIG_NETFILTER_XT_MATCH_DSCP=y
+CONFIG_NETFILTER_XT_MATCH_ESP=y
+CONFIG_NETFILTER_XT_MATCH_HASHLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_HELPER=y
+CONFIG_NETFILTER_XT_MATCH_IPRANGE=y
+# CONFIG_NETFILTER_XT_MATCH_L2TP is not set
+CONFIG_NETFILTER_XT_MATCH_LENGTH=y
+CONFIG_NETFILTER_XT_MATCH_LIMIT=y
+CONFIG_NETFILTER_XT_MATCH_MAC=y
+CONFIG_NETFILTER_XT_MATCH_MARK=y
+CONFIG_NETFILTER_XT_MATCH_MULTIPORT=y
+CONFIG_NETFILTER_XT_MATCH_POLICY=y
+CONFIG_NETFILTER_XT_MATCH_PKTTYPE=y
+CONFIG_NETFILTER_XT_MATCH_QTAGUID=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA2=y
+CONFIG_NETFILTER_XT_MATCH_SOCKET=y
+CONFIG_NETFILTER_XT_MATCH_STATE=y
+CONFIG_NETFILTER_XT_MATCH_STATISTIC=y
+CONFIG_NETFILTER_XT_MATCH_STRING=y
+CONFIG_NETFILTER_XT_MATCH_TIME=y
+CONFIG_NETFILTER_XT_MATCH_U32=y
+CONFIG_NF_CONNTRACK_IPV4=y
+CONFIG_IP_NF_IPTABLES=y
+CONFIG_IP_NF_MATCH_AH=y
+CONFIG_IP_NF_MATCH_ECN=y
+CONFIG_IP_NF_MATCH_RPFILTER=y
+CONFIG_IP_NF_MATCH_TTL=y
+CONFIG_IP_NF_FILTER=y
+CONFIG_IP_NF_TARGET_REJECT=y
+CONFIG_IP_NF_NAT=y
+CONFIG_IP_NF_TARGET_MASQUERADE=y
+CONFIG_IP_NF_TARGET_NETMAP=y
+CONFIG_IP_NF_TARGET_REDIRECT=y
+CONFIG_IP_NF_MANGLE=y
+CONFIG_IP_NF_RAW=y
+CONFIG_IP_NF_SECURITY=y
+CONFIG_IP_NF_ARPTABLES=y
+CONFIG_IP_NF_ARPFILTER=y
+CONFIG_IP_NF_ARP_MANGLE=y
+CONFIG_NF_CONNTRACK_IPV6=y
+CONFIG_IP6_NF_IPTABLES=y
+CONFIG_IP6_NF_MATCH_RPFILTER=y
+CONFIG_IP6_NF_FILTER=y
+CONFIG_IP6_NF_TARGET_REJECT=y
+CONFIG_IP6_NF_MANGLE=y
+CONFIG_IP6_NF_RAW=y
+CONFIG_BRIDGE_NF_EBTABLES=y
+CONFIG_BRIDGE_EBT_BROUTE=y
+CONFIG_L2TP=y
+CONFIG_L2TP_V3=y
+CONFIG_L2TP_IP=y
+CONFIG_L2TP_ETH=y
+CONFIG_BRIDGE=y
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_HTB=y
+CONFIG_NET_SCH_PRIO=y
+CONFIG_NET_SCH_MULTIQ=y
+CONFIG_NET_SCH_INGRESS=y
+CONFIG_NET_CLS_FW=y
+CONFIG_NET_CLS_U32=y
+CONFIG_CLS_U32_MARK=y
+CONFIG_NET_CLS_FLOW=y
+CONFIG_NET_EMATCH=y
+CONFIG_NET_EMATCH_CMP=y
+CONFIG_NET_EMATCH_NBYTE=y
+CONFIG_NET_EMATCH_U32=y
+CONFIG_NET_EMATCH_META=y
+CONFIG_NET_EMATCH_TEXT=y
+CONFIG_NET_CLS_ACT=y
+CONFIG_NET_ACT_GACT=y
+CONFIG_NET_ACT_MIRRED=y
+CONFIG_NET_ACT_SKBEDIT=y
+CONFIG_RMNET_DATA=y
+CONFIG_RMNET_DATA_FC=y
+CONFIG_RMNET_DATA_DEBUG_PKT=y
+CONFIG_BT=y
+CONFIG_MSM_BT_POWER=y
+CONFIG_CFG80211=y
+CONFIG_CFG80211_INTERNAL_REGDB=y
+# CONFIG_CFG80211_CRDA_SUPPORT is not set
+CONFIG_RFKILL=y
+CONFIG_NFC_NQ=y
+CONFIG_IPC_ROUTER=y
+CONFIG_IPC_ROUTER_SECURITY=y
+CONFIG_FW_LOADER_USER_HELPER_FALLBACK=y
+CONFIG_REGMAP_ALLOW_WRITE_DEBUGFS=y
+CONFIG_DMA_CMA=y
+CONFIG_ZRAM=y
+CONFIG_BLK_DEV_LOOP=y
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_HDCP_QSEECOM=y
+CONFIG_QSEECOM=y
+CONFIG_MEMORY_STATE_TIME=y
+CONFIG_SCSI=y
+CONFIG_BLK_DEV_SD=y
+CONFIG_CHR_DEV_SG=y
+CONFIG_CHR_DEV_SCH=y
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SCAN_ASYNC=y
+CONFIG_SCSI_UFSHCD=y
+CONFIG_SCSI_UFSHCD_PLATFORM=y
+CONFIG_SCSI_UFS_QCOM=y
+CONFIG_SCSI_UFS_QCOM_ICE=y
+CONFIG_SCSI_UFSHCD_CMD_LOGGING=y
+CONFIG_MD=y
+CONFIG_BLK_DEV_DM=y
+CONFIG_DM_DEBUG=y
+CONFIG_DM_CRYPT=y
+CONFIG_DM_REQ_CRYPT=y
+CONFIG_DM_UEVENT=y
+CONFIG_DM_VERITY=y
+CONFIG_DM_VERITY_FEC=y
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=y
+CONFIG_TUN=y
+CONFIG_PPP=y
+CONFIG_PPP_BSDCOMP=y
+CONFIG_PPP_DEFLATE=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_MPPE=y
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPPOE=y
+CONFIG_PPPOL2TP=y
+CONFIG_PPPOLAC=y
+CONFIG_PPPOPNS=y
+CONFIG_PPP_ASYNC=y
+CONFIG_PPP_SYNC_TTY=y
+CONFIG_USB_USBNET=y
+CONFIG_WCNSS_MEM_PRE_ALLOC=y
+CONFIG_CLD_LL_CORE=y
+CONFIG_INPUT_EVDEV=y
+CONFIG_KEYBOARD_GPIO=y
+# CONFIG_INPUT_MOUSE is not set
+CONFIG_INPUT_JOYSTICK=y
+CONFIG_INPUT_TOUCHSCREEN=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
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_DEVMEM is not set
+# CONFIG_DEVKMEM is not set
+CONFIG_SERIAL_MSM_HS=y
+CONFIG_SERIAL_MSM_SMD=y
+CONFIG_DIAG_CHAR=y
+CONFIG_DIAG_USES_SMD=y
+CONFIG_HW_RANDOM=y
+CONFIG_HW_RANDOM_MSM_LEGACY=y
+CONFIG_MSM_SMD_PKT=y
+CONFIG_MSM_ADSPRPC=y
+CONFIG_MSM_RDBG=m
+CONFIG_I2C_CHARDEV=y
+CONFIG_I2C_MSM_V2=y
+CONFIG_SPI=y
+CONFIG_SPI_QUP=y
+CONFIG_SPI_SPIDEV=y
+CONFIG_SLIMBUS_MSM_NGD=y
+CONFIG_SPMI=y
+CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
+CONFIG_PINCTRL_MSM8937=y
+CONFIG_PINCTRL_MSM8917=y
+CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
+CONFIG_GPIOLIB=y
+CONFIG_GPIO_SYSFS=y
+CONFIG_GPIO_QPNP_PIN=y
+CONFIG_GPIO_QPNP_PIN_DEBUG=y
+CONFIG_POWER_RESET_QCOM=y
+CONFIG_QCOM_DLOAD_MODE=y
+CONFIG_POWER_RESET_SYSCON=y
+CONFIG_QPNP_FG=y
+CONFIG_SMB135X_CHARGER=y
+CONFIG_SMB1351_USB_CHARGER=y
+CONFIG_QPNP_SMB5=y
+CONFIG_QPNP_SMBCHARGER=y
+CONFIG_QPNP_TYPEC=y
+CONFIG_QPNP_QG=y
+CONFIG_MSM_APM=y
+CONFIG_SENSORS_QPNP_ADC_VOLTAGE=y
+CONFIG_THERMAL=y
+CONFIG_THERMAL_WRITABLE_TRIPS=y
+CONFIG_THERMAL_GOV_USER_SPACE=y
+CONFIG_THERMAL_GOV_LOW_LIMITS=y
+CONFIG_CPU_THERMAL=y
+CONFIG_DEVFREQ_THERMAL=y
+CONFIG_THERMAL_QPNP=y
+CONFIG_THERMAL_QPNP_ADC_TM=y
+CONFIG_THERMAL_TSENS=y
+CONFIG_QTI_VIRTUAL_SENSOR=y
+CONFIG_QTI_QMI_COOLING_DEVICE=y
+CONFIG_REGULATOR_COOLING_DEVICE=y
+CONFIG_QTI_BCL_PMIC5=y
+CONFIG_QTI_BCL_SOC_DRIVER=y
+CONFIG_MFD_SPMI_PMIC=y
+CONFIG_REGULATOR=y
+CONFIG_REGULATOR_FIXED_VOLTAGE=y
+CONFIG_REGULATOR_CPR=y
+CONFIG_REGULATOR_CPR4_APSS=y
+CONFIG_REGULATOR_CPRH_KBSS=y
+CONFIG_REGULATOR_MEM_ACC=y
+CONFIG_REGULATOR_MSM_GFX_LDO=y
+CONFIG_REGULATOR_QPNP_LABIBB=y
+CONFIG_REGULATOR_QPNP_LCDB=y
+CONFIG_REGULATOR_QPNP=y
+CONFIG_REGULATOR_RPM_SMD=y
+CONFIG_REGULATOR_SPM=y
+CONFIG_REGULATOR_STUB=y
+CONFIG_MEDIA_SUPPORT=y
+CONFIG_MEDIA_CAMERA_SUPPORT=y
+CONFIG_MEDIA_CONTROLLER=y
+CONFIG_VIDEO_V4L2_SUBDEV_API=y
+CONFIG_V4L_PLATFORM_DRIVERS=y
+CONFIG_MSM_CAMERA=y
+CONFIG_MSM_CAMERA_DEBUG=y
+CONFIG_MSMB_CAMERA=y
+CONFIG_MSMB_CAMERA_DEBUG=y
+CONFIG_MSM_CAMERA_SENSOR=y
+CONFIG_MSM_CPP=y
+CONFIG_MSM_CCI=y
+CONFIG_MSM_CSI20_HEADER=y
+CONFIG_MSM_CSI22_HEADER=y
+CONFIG_MSM_CSI30_HEADER=y
+CONFIG_MSM_CSI31_HEADER=y
+CONFIG_MSM_CSIPHY=y
+CONFIG_MSM_CSID=y
+CONFIG_MSM_EEPROM=y
+CONFIG_MSM_ISPIF_V2=y
+CONFIG_IMX134=y
+CONFIG_IMX132=y
+CONFIG_OV9724=y
+CONFIG_OV5648=y
+CONFIG_GC0339=y
+CONFIG_OV8825=y
+CONFIG_OV8865=y
+CONFIG_s5k4e1=y
+CONFIG_OV12830=y
+CONFIG_MSM_V4L2_VIDEO_OVERLAY_DEVICE=y
+CONFIG_MSMB_JPEG=y
+CONFIG_MSM_FD=y
+CONFIG_MSM_JPEGDMA=y
+CONFIG_MSM_VIDC_3X_V4L2=y
+CONFIG_MSM_VIDC_3X_GOVERNORS=y
+CONFIG_MSM_SDE_ROTATOR=y
+CONFIG_MSM_SDE_ROTATOR_EVTLOG_DEBUG=y
+CONFIG_RADIO_IRIS=y
+CONFIG_RADIO_IRIS_TRANSPORT=y
+CONFIG_QCOM_KGSL=y
+CONFIG_FB=y
+CONFIG_FB_MSM=y
+CONFIG_FB_MSM_MDSS=y
+CONFIG_FB_MSM_MDSS_WRITEBACK=y
+CONFIG_FB_MSM_MDSS_DSI_CTRL_STATUS=y
+CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
+CONFIG_BACKLIGHT_LCD_SUPPORT=y
+CONFIG_BACKLIGHT_CLASS_DEVICE=y
+CONFIG_SOUND=y
+CONFIG_SND=y
+CONFIG_SND_DYNAMIC_MINORS=y
+CONFIG_SND_USB_AUDIO=y
+CONFIG_SND_SOC=y
+CONFIG_UHID=y
+CONFIG_HID_APPLE=y
+CONFIG_HID_ELECOM=y
+CONFIG_HID_MAGICMOUSE=y
+CONFIG_HID_MICROSOFT=y
+CONFIG_HID_MULTITOUCH=y
+CONFIG_USB_HIDDEV=y
+CONFIG_USB=y
+CONFIG_USB_ANNOUNCE_NEW_DEVICES=y
+CONFIG_USB_MON=y
+CONFIG_USB_XHCI_HCD=y
+CONFIG_USB_EHCI_HCD=y
+CONFIG_USB_EHCI_MSM=y
+CONFIG_USB_EHCI_HCD_PLATFORM=y
+CONFIG_USB_OHCI_HCD=y
+CONFIG_USB_OHCI_HCD_PLATFORM=y
+CONFIG_USB_ACM=y
+CONFIG_USB_STORAGE=y
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_USBAT=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_ALAUDA=y
+CONFIG_USB_STORAGE_ONETOUCH=y
+CONFIG_USB_STORAGE_KARMA=y
+CONFIG_USB_STORAGE_CYPRESS_ATACB=y
+CONFIG_USB_DWC3=y
+CONFIG_USB_DWC3_MSM=y
+CONFIG_USB_SERIAL=y
+CONFIG_USB_EHSET_TEST_FIXTURE=y
+CONFIG_NOP_USB_XCEIV=y
+CONFIG_DUAL_ROLE_USB_INTF=y
+CONFIG_USB_MSM_SSPHY_QMP=y
+CONFIG_MSM_QUSB_PHY=y
+CONFIG_USB_GADGET=y
+CONFIG_USB_GADGET_DEBUG_FILES=y
+CONFIG_USB_GADGET_DEBUG_FS=y
+CONFIG_USB_GADGET_VBUS_DRAW=500
+CONFIG_USB_CI13XXX_MSM=y
+CONFIG_USB_CONFIGFS=y
+CONFIG_USB_CONFIGFS_SERIAL=y
+CONFIG_USB_CONFIGFS_NCM=y
+CONFIG_USB_CONFIGFS_QCRNDIS=y
+CONFIG_USB_CONFIGFS_RNDIS=y
+CONFIG_USB_CONFIGFS_RMNET_BAM=y
+CONFIG_USB_CONFIGFS_MASS_STORAGE=y
+CONFIG_USB_CONFIGFS_F_FS=y
+CONFIG_USB_CONFIGFS_F_MTP=y
+CONFIG_USB_CONFIGFS_F_PTP=y
+CONFIG_USB_CONFIGFS_F_ACC=y
+CONFIG_USB_CONFIGFS_F_AUDIO_SRC=y
+CONFIG_USB_CONFIGFS_UEVENT=y
+CONFIG_USB_CONFIGFS_F_MIDI=y
+CONFIG_USB_CONFIGFS_F_HID=y
+CONFIG_USB_CONFIGFS_F_DIAG=y
+CONFIG_USB_CONFIGFS_F_CDEV=y
+CONFIG_USB_CONFIGFS_F_CCID=y
+CONFIG_USB_CONFIGFS_F_QDSS=y
+CONFIG_MMC=y
+CONFIG_MMC_PERF_PROFILING=y
+CONFIG_MMC_PARANOID_SD_INIT=y
+CONFIG_MMC_CLKGATE=y
+CONFIG_MMC_BLOCK_MINORS=32
+CONFIG_MMC_BLOCK_DEFERRED_RESUME=y
+CONFIG_MMC_TEST=y
+CONFIG_MMC_SDHCI=y
+CONFIG_MMC_SDHCI_PLTFM=y
+CONFIG_MMC_SDHCI_MSM=y
+CONFIG_MMC_SDHCI_MSM_ICE=y
+CONFIG_MMC_CQ_HCI=y
+CONFIG_LEDS_QTI_TRI_LED=y
+CONFIG_LEDS_QPNP=y
+CONFIG_LEDS_QPNP_FLASH=y
+CONFIG_LEDS_QPNP_FLASH_V2=y
+CONFIG_LEDS_QPNP_WLED=y
+CONFIG_LEDS_QPNP_HAPTICS=y
+CONFIG_LEDS_QPNP_VIBRATOR_LDO=y
+CONFIG_LEDS_TRIGGERS=y
+CONFIG_LEDS_TRIGGER_TIMER=y
+CONFIG_EDAC=y
+CONFIG_EDAC_MM_EDAC=y
+CONFIG_RTC_CLASS=y
+CONFIG_RTC_DRV_QPNP=y
+CONFIG_DMADEVICES=y
+CONFIG_QCOM_SPS_DMA=y
+CONFIG_UIO=y
+CONFIG_UIO_MSM_SHAREDMEM=y
+CONFIG_STAGING=y
+CONFIG_ASHMEM=y
+CONFIG_ANDROID_LOW_MEMORY_KILLER=y
+CONFIG_ION=y
+CONFIG_ION_MSM=y
+CONFIG_IPA=y
+CONFIG_RMNET_IPA=y
+CONFIG_RNDIS_IPA=y
+CONFIG_SPS=y
+CONFIG_SPS_SUPPORT_NDP_BAM=y
+CONFIG_QPNP_COINCELL=y
+CONFIG_QPNP_REVID=y
+CONFIG_USB_BAM=y
+CONFIG_MSM_EXT_DISPLAY=y
+CONFIG_MSM_RMNET_BAM=y
+CONFIG_MSM_MDSS_PLL=y
+CONFIG_REMOTE_SPINLOCK_MSM=y
+CONFIG_MAILBOX=y
+CONFIG_ARM_SMMU=y
+CONFIG_QCOM_LAZY_MAPPING=y
+CONFIG_QCOM_RUN_QUEUE_STATS=y
+CONFIG_MSM_SPM=y
+CONFIG_MSM_L2_SPM=y
+CONFIG_QCOM_SCM=y
+CONFIG_MSM_BOOT_STATS=y
+CONFIG_QCOM_WATCHDOG_V2=y
+CONFIG_QCOM_MEMORY_DUMP_V2=y
+CONFIG_MSM_RPM_SMD=y
+CONFIG_QCOM_BUS_SCALING=y
+CONFIG_QCOM_SECURE_BUFFER=y
+CONFIG_QCOM_EARLY_RANDOM=y
+CONFIG_MSM_SMEM=y
+CONFIG_MSM_SMD=y
+CONFIG_MSM_SMD_DEBUG=y
+CONFIG_MSM_TZ_SMMU=y
+CONFIG_MSM_SMP2P=y
+CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
+CONFIG_MSM_QMI_INTERFACE=y
+CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_PIL=y
+CONFIG_MSM_PIL_SSR_GENERIC=y
+CONFIG_MSM_PIL_MSS_QDSP6V5=y
+CONFIG_ICNSS=y
+CONFIG_MSM_PERFORMANCE=y
+CONFIG_MSM_EVENT_TIMER=y
+CONFIG_MSM_AVTIMER=y
+CONFIG_MSM_PM=y
+CONFIG_QTI_RPM_STATS_LOG=y
+CONFIG_QCOM_FORCE_WDOG_BITE_ON_PANIC=y
+CONFIG_MEM_SHARE_QMI_SERVICE=y
+CONFIG_MSM_BAM_DMUX=y
+CONFIG_WCNSS_CORE=y
+CONFIG_WCNSS_CORE_PRONTO=y
+CONFIG_WCNSS_REGISTER_DUMP_ON_BITE=y
+CONFIG_QCOM_BIMC_BWMON=y
+CONFIG_DEVFREQ_GOV_QCOM_BW_HWMON=y
+CONFIG_DEVFREQ_SIMPLE_DEV=y
+CONFIG_QCOM_DEVFREQ_DEVBW=y
+CONFIG_SPDM_SCM=y
+CONFIG_DEVFREQ_SPDM=y
+CONFIG_PWM=y
+CONFIG_PWM_QPNP=y
+CONFIG_PWM_QTI_LPG=y
+CONFIG_ARM_GIC_V3_ACL=y
+CONFIG_QTI_MPM=y
+CONFIG_ANDROID=y
+CONFIG_ANDROID_BINDER_IPC=y
+CONFIG_SENSORS_SSC=y
+CONFIG_MSM_TZ_LOG=y
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT3_FS=y
+CONFIG_EXT4_FS_SECURITY=y
+CONFIG_QUOTA=y
+CONFIG_QUOTA_NETLINK_INTERFACE=y
+CONFIG_QFMT_V2=y
+CONFIG_FUSE_FS=y
+CONFIG_VFAT_FS=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_POSIX_ACL=y
+CONFIG_ECRYPT_FS=y
+CONFIG_ECRYPT_FS_MESSAGING=y
+# CONFIG_NETWORK_FILESYSTEMS is not set
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_ISO8859_1=y
+CONFIG_PRINTK_TIME=y
+CONFIG_DEBUG_INFO=y
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_PANIC_TIMEOUT=5
+CONFIG_SCHEDSTATS=y
+# CONFIG_DEBUG_PREEMPT is not set
+CONFIG_IPC_LOGGING=y
+CONFIG_CPU_FREQ_SWITCH_PROFILER=y
+CONFIG_DEBUG_ALIGN_RODATA=y
+CONFIG_CORESIGHT=y
+CONFIG_CORESIGHT_LINK_AND_SINK_TMC=y
+CONFIG_CORESIGHT_QCOM_REPLICATOR=y
+CONFIG_CORESIGHT_STM=y
+CONFIG_CORESIGHT_TPDA=y
+CONFIG_CORESIGHT_TPDM=y
+CONFIG_CORESIGHT_CTI=y
+CONFIG_CORESIGHT_EVENT=y
+CONFIG_CORESIGHT_HWEVENT=y
+CONFIG_SECURITY_PERF_EVENTS_RESTRICT=y
+CONFIG_SECURITY=y
+CONFIG_HARDENED_USERCOPY=y
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SMACK=y
+CONFIG_CRYPTO_CTR=y
+CONFIG_CRYPTO_XCBC=y
+CONFIG_CRYPTO_MD4=y
+CONFIG_CRYPTO_TWOFISH=y
+CONFIG_CRYPTO_ANSI_CPRNG=y
+CONFIG_CRYPTO_DEV_QCOM_MSM_QCE=y
+CONFIG_CRYPTO_DEV_QCRYPTO=y
+CONFIG_CRYPTO_DEV_QCEDEV=y
+CONFIG_CRYPTO_DEV_QCOM_ICE=y
+CONFIG_ARM64_CRYPTO=y
+CONFIG_CRYPTO_SHA1_ARM64_CE=y
+CONFIG_CRYPTO_SHA2_ARM64_CE=y
+CONFIG_CRYPTO_GHASH_ARM64_CE=y
+CONFIG_CRYPTO_AES_ARM64_CE_CCM=y
+CONFIG_CRYPTO_AES_ARM64_CE_BLK=y
+CONFIG_CRYPTO_AES_ARM64_NEON_BLK=y
+CONFIG_CRYPTO_CRC32_ARM64=y
+CONFIG_QMI_ENCDEC=y
diff --git a/arch/arm64/configs/msm8937_defconfig b/arch/arm64/configs/msm8937_defconfig
new file mode 100644
index 0000000..66b402f
--- /dev/null
+++ b/arch/arm64/configs/msm8937_defconfig
@@ -0,0 +1,701 @@
+# CONFIG_LOCALVERSION_AUTO is not set
+# CONFIG_FHANDLE is not set
+CONFIG_AUDIT=y
+# CONFIG_AUDITSYSCALL is not set
+CONFIG_NO_HZ=y
+CONFIG_HIGH_RES_TIMERS=y
+CONFIG_IRQ_TIME_ACCOUNTING=y
+CONFIG_SCHED_WALT=y
+CONFIG_TASKSTATS=y
+CONFIG_TASK_DELAY_ACCT=y
+CONFIG_TASK_XACCT=y
+CONFIG_TASK_IO_ACCOUNTING=y
+CONFIG_RCU_EXPERT=y
+CONFIG_RCU_FAST_NO_HZ=y
+CONFIG_RCU_NOCB_CPU=y
+CONFIG_RCU_NOCB_CPU_ALL=y
+CONFIG_IKCONFIG=y
+CONFIG_IKCONFIG_PROC=y
+CONFIG_LOG_CPU_MAX_BUF_SHIFT=17
+CONFIG_CGROUP_DEBUG=y
+CONFIG_CGROUP_FREEZER=y
+CONFIG_CPUSETS=y
+CONFIG_CGROUP_CPUACCT=y
+CONFIG_CGROUP_SCHEDTUNE=y
+CONFIG_RT_GROUP_SCHED=y
+CONFIG_CGROUP_BPF=y
+CONFIG_SCHED_CORE_CTL=y
+CONFIG_NAMESPACES=y
+# CONFIG_UTS_NS is not set
+# CONFIG_PID_NS is not set
+CONFIG_SCHED_AUTOGROUP=y
+CONFIG_SCHED_TUNE=y
+CONFIG_DEFAULT_USE_ENERGY_AWARE=y
+CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
+# CONFIG_RD_XZ is not set
+# CONFIG_RD_LZO is not set
+# CONFIG_RD_LZ4 is not set
+CONFIG_KALLSYMS_ALL=y
+CONFIG_BPF_SYSCALL=y
+# CONFIG_MEMBARRIER is not set
+CONFIG_EMBEDDED=y
+# CONFIG_COMPAT_BRK is not set
+CONFIG_PROFILING=y
+CONFIG_CC_STACKPROTECTOR_STRONG=y
+CONFIG_ARCH_MMAP_RND_COMPAT_BITS=16
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+CONFIG_MODULE_FORCE_UNLOAD=y
+CONFIG_MODVERSIONS=y
+CONFIG_MODULE_SIG=y
+CONFIG_MODULE_SIG_FORCE=y
+CONFIG_MODULE_SIG_SHA512=y
+# CONFIG_BLK_DEV_BSG is not set
+CONFIG_PARTITION_ADVANCED=y
+# CONFIG_IOSCHED_DEADLINE is not set
+CONFIG_ARCH_QCOM=y
+CONFIG_ARCH_MSM8937=y
+CONFIG_ARCH_MSM8917=y
+CONFIG_ARCH_SDM429=y
+CONFIG_ARCH_SDM439=y
+# CONFIG_ARM64_ERRATUM_1024718 is not set
+CONFIG_SCHED_MC=y
+CONFIG_NR_CPUS=8
+CONFIG_PREEMPT=y
+CONFIG_HZ_100=y
+CONFIG_CLEANCACHE=y
+CONFIG_CMA=y
+CONFIG_CMA_DEBUGFS=y
+CONFIG_ZSMALLOC=y
+CONFIG_SECCOMP=y
+CONFIG_HARDEN_BRANCH_PREDICTOR=y
+CONFIG_ARMV8_DEPRECATED=y
+CONFIG_SWP_EMULATION=y
+CONFIG_CP15_BARRIER_EMULATION=y
+CONFIG_SETEND_EMULATION=y
+# CONFIG_ARM64_VHE is not set
+CONFIG_RANDOMIZE_BASE=y
+CONFIG_BUILD_ARM64_APPENDED_DTB_IMAGE=y
+# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
+CONFIG_COMPAT=y
+CONFIG_PM_AUTOSLEEP=y
+CONFIG_PM_WAKELOCKS=y
+CONFIG_PM_WAKELOCKS_LIMIT=0
+# CONFIG_PM_WAKELOCKS_GC is not set
+CONFIG_PM_DEBUG=y
+CONFIG_CPU_IDLE=y
+CONFIG_CPU_FREQ=y
+CONFIG_CPU_FREQ_GOV_POWERSAVE=y
+CONFIG_CPU_FREQ_GOV_USERSPACE=y
+CONFIG_CPU_FREQ_GOV_ONDEMAND=y
+CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y
+CONFIG_CPU_BOOST=y
+CONFIG_CPU_FREQ_GOV_SCHEDUTIL=y
+CONFIG_CPU_FREQ_MSM=y
+CONFIG_NET=y
+CONFIG_PACKET=y
+CONFIG_UNIX=y
+CONFIG_XFRM_USER=y
+CONFIG_XFRM_STATISTICS=y
+CONFIG_NET_KEY=y
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+CONFIG_IP_ADVANCED_ROUTER=y
+CONFIG_IP_MULTIPLE_TABLES=y
+CONFIG_IP_ROUTE_VERBOSE=y
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+CONFIG_INET_AH=y
+CONFIG_INET_ESP=y
+CONFIG_INET_IPCOMP=y
+CONFIG_INET_DIAG_DESTROY=y
+CONFIG_IPV6_ROUTER_PREF=y
+CONFIG_IPV6_ROUTE_INFO=y
+CONFIG_IPV6_OPTIMISTIC_DAD=y
+CONFIG_INET6_AH=y
+CONFIG_INET6_ESP=y
+CONFIG_INET6_IPCOMP=y
+CONFIG_IPV6_MIP6=y
+CONFIG_IPV6_MULTIPLE_TABLES=y
+CONFIG_IPV6_SUBTREES=y
+CONFIG_NETFILTER=y
+CONFIG_NF_CONNTRACK=y
+CONFIG_NF_CONNTRACK_SECMARK=y
+CONFIG_NF_CONNTRACK_EVENTS=y
+CONFIG_NF_CT_PROTO_DCCP=y
+CONFIG_NF_CT_PROTO_SCTP=y
+CONFIG_NF_CT_PROTO_UDPLITE=y
+CONFIG_NF_CONNTRACK_AMANDA=y
+CONFIG_NF_CONNTRACK_FTP=y
+CONFIG_NF_CONNTRACK_H323=y
+CONFIG_NF_CONNTRACK_IRC=y
+CONFIG_NF_CONNTRACK_NETBIOS_NS=y
+CONFIG_NF_CONNTRACK_PPTP=y
+CONFIG_NF_CONNTRACK_SANE=y
+CONFIG_NF_CONNTRACK_TFTP=y
+CONFIG_NF_CT_NETLINK=y
+CONFIG_NETFILTER_XT_TARGET_CLASSIFY=y
+CONFIG_NETFILTER_XT_TARGET_CONNMARK=y
+CONFIG_NETFILTER_XT_TARGET_CONNSECMARK=y
+CONFIG_NETFILTER_XT_TARGET_IDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_HARDIDLETIMER=y
+CONFIG_NETFILTER_XT_TARGET_LOG=y
+CONFIG_NETFILTER_XT_TARGET_MARK=y
+CONFIG_NETFILTER_XT_TARGET_NFLOG=y
+CONFIG_NETFILTER_XT_TARGET_NFQUEUE=y
+CONFIG_NETFILTER_XT_TARGET_NOTRACK=y
+CONFIG_NETFILTER_XT_TARGET_TEE=y
+CONFIG_NETFILTER_XT_TARGET_TPROXY=y
+CONFIG_NETFILTER_XT_TARGET_TRACE=y
+CONFIG_NETFILTER_XT_TARGET_SECMARK=y
+CONFIG_NETFILTER_XT_TARGET_TCPMSS=y
+CONFIG_NETFILTER_XT_MATCH_COMMENT=y
+CONFIG_NETFILTER_XT_MATCH_CONNLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_CONNMARK=y
+CONFIG_NETFILTER_XT_MATCH_CONNTRACK=y
+CONFIG_NETFILTER_XT_MATCH_DSCP=y
+CONFIG_NETFILTER_XT_MATCH_ESP=y
+CONFIG_NETFILTER_XT_MATCH_HASHLIMIT=y
+CONFIG_NETFILTER_XT_MATCH_HELPER=y
+CONFIG_NETFILTER_XT_MATCH_IPRANGE=y
+# CONFIG_NETFILTER_XT_MATCH_L2TP is not set
+CONFIG_NETFILTER_XT_MATCH_LENGTH=y
+CONFIG_NETFILTER_XT_MATCH_LIMIT=y
+CONFIG_NETFILTER_XT_MATCH_MAC=y
+CONFIG_NETFILTER_XT_MATCH_MARK=y
+CONFIG_NETFILTER_XT_MATCH_MULTIPORT=y
+CONFIG_NETFILTER_XT_MATCH_POLICY=y
+CONFIG_NETFILTER_XT_MATCH_PKTTYPE=y
+CONFIG_NETFILTER_XT_MATCH_QTAGUID=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA=y
+CONFIG_NETFILTER_XT_MATCH_QUOTA2=y
+CONFIG_NETFILTER_XT_MATCH_SOCKET=y
+CONFIG_NETFILTER_XT_MATCH_STATE=y
+CONFIG_NETFILTER_XT_MATCH_STATISTIC=y
+CONFIG_NETFILTER_XT_MATCH_STRING=y
+CONFIG_NETFILTER_XT_MATCH_TIME=y
+CONFIG_NETFILTER_XT_MATCH_U32=y
+CONFIG_NF_CONNTRACK_IPV4=y
+CONFIG_IP_NF_IPTABLES=y
+CONFIG_IP_NF_MATCH_AH=y
+CONFIG_IP_NF_MATCH_ECN=y
+CONFIG_IP_NF_MATCH_RPFILTER=y
+CONFIG_IP_NF_MATCH_TTL=y
+CONFIG_IP_NF_FILTER=y
+CONFIG_IP_NF_TARGET_REJECT=y
+CONFIG_IP_NF_NAT=y
+CONFIG_IP_NF_TARGET_MASQUERADE=y
+CONFIG_IP_NF_TARGET_NETMAP=y
+CONFIG_IP_NF_TARGET_REDIRECT=y
+CONFIG_IP_NF_MANGLE=y
+CONFIG_IP_NF_RAW=y
+CONFIG_IP_NF_SECURITY=y
+CONFIG_IP_NF_ARPTABLES=y
+CONFIG_IP_NF_ARPFILTER=y
+CONFIG_IP_NF_ARP_MANGLE=y
+CONFIG_NF_CONNTRACK_IPV6=y
+CONFIG_IP6_NF_IPTABLES=y
+CONFIG_IP6_NF_MATCH_RPFILTER=y
+CONFIG_IP6_NF_FILTER=y
+CONFIG_IP6_NF_TARGET_REJECT=y
+CONFIG_IP6_NF_MANGLE=y
+CONFIG_IP6_NF_RAW=y
+CONFIG_BRIDGE_NF_EBTABLES=y
+CONFIG_BRIDGE_EBT_BROUTE=y
+CONFIG_L2TP=y
+CONFIG_L2TP_DEBUGFS=y
+CONFIG_L2TP_V3=y
+CONFIG_L2TP_IP=y
+CONFIG_L2TP_ETH=y
+CONFIG_BRIDGE=y
+CONFIG_NET_SCHED=y
+CONFIG_NET_SCH_HTB=y
+CONFIG_NET_SCH_PRIO=y
+CONFIG_NET_SCH_MULTIQ=y
+CONFIG_NET_SCH_INGRESS=y
+CONFIG_NET_CLS_FW=y
+CONFIG_NET_CLS_U32=y
+CONFIG_CLS_U32_MARK=y
+CONFIG_NET_CLS_FLOW=y
+CONFIG_NET_EMATCH=y
+CONFIG_NET_EMATCH_CMP=y
+CONFIG_NET_EMATCH_NBYTE=y
+CONFIG_NET_EMATCH_U32=y
+CONFIG_NET_EMATCH_META=y
+CONFIG_NET_EMATCH_TEXT=y
+CONFIG_NET_CLS_ACT=y
+CONFIG_NET_ACT_GACT=y
+CONFIG_NET_ACT_MIRRED=y
+CONFIG_NET_ACT_SKBEDIT=y
+CONFIG_DNS_RESOLVER=y
+CONFIG_RMNET_DATA=y
+CONFIG_RMNET_DATA_FC=y
+CONFIG_RMNET_DATA_DEBUG_PKT=y
+CONFIG_BT=y
+CONFIG_MSM_BT_POWER=y
+CONFIG_CFG80211=y
+CONFIG_CFG80211_INTERNAL_REGDB=y
+# CONFIG_CFG80211_CRDA_SUPPORT is not set
+CONFIG_RFKILL=y
+CONFIG_NFC_NQ=y
+CONFIG_IPC_ROUTER=y
+CONFIG_IPC_ROUTER_SECURITY=y
+CONFIG_FW_LOADER_USER_HELPER_FALLBACK=y
+CONFIG_REGMAP_ALLOW_WRITE_DEBUGFS=y
+CONFIG_DMA_CMA=y
+CONFIG_ZRAM=y
+CONFIG_BLK_DEV_LOOP=y
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_HDCP_QSEECOM=y
+CONFIG_QSEECOM=y
+CONFIG_UID_SYS_STATS=y
+CONFIG_MEMORY_STATE_TIME=y
+CONFIG_SCSI=y
+CONFIG_BLK_DEV_SD=y
+CONFIG_CHR_DEV_SG=y
+CONFIG_CHR_DEV_SCH=y
+CONFIG_SCSI_CONSTANTS=y
+CONFIG_SCSI_LOGGING=y
+CONFIG_SCSI_SCAN_ASYNC=y
+CONFIG_SCSI_UFSHCD=y
+CONFIG_SCSI_UFSHCD_PLATFORM=y
+CONFIG_SCSI_UFS_QCOM=y
+CONFIG_SCSI_UFS_QCOM_ICE=y
+CONFIG_SCSI_UFSHCD_CMD_LOGGING=y
+CONFIG_MD=y
+CONFIG_BLK_DEV_DM=y
+CONFIG_DM_DEBUG=y
+CONFIG_DM_CRYPT=y
+CONFIG_DM_REQ_CRYPT=y
+CONFIG_DM_UEVENT=y
+CONFIG_DM_VERITY=y
+CONFIG_DM_VERITY_FEC=y
+CONFIG_NETDEVICES=y
+CONFIG_DUMMY=y
+CONFIG_TUN=y
+CONFIG_PPP=y
+CONFIG_PPP_BSDCOMP=y
+CONFIG_PPP_DEFLATE=y
+CONFIG_PPP_FILTER=y
+CONFIG_PPP_MPPE=y
+CONFIG_PPP_MULTILINK=y
+CONFIG_PPPOE=y
+CONFIG_PPPOL2TP=y
+CONFIG_PPPOLAC=y
+CONFIG_PPPOPNS=y
+CONFIG_PPP_ASYNC=y
+CONFIG_PPP_SYNC_TTY=y
+CONFIG_USB_USBNET=y
+CONFIG_WCNSS_MEM_PRE_ALLOC=y
+CONFIG_CLD_LL_CORE=y
+CONFIG_INPUT_EVDEV=y
+CONFIG_KEYBOARD_GPIO=y
+# CONFIG_INPUT_MOUSE is not set
+CONFIG_INPUT_JOYSTICK=y
+CONFIG_INPUT_TOUCHSCREEN=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
+# CONFIG_LEGACY_PTYS is not set
+# CONFIG_DEVMEM is not set
+# CONFIG_DEVKMEM is not set
+CONFIG_SERIAL_MSM=y
+CONFIG_SERIAL_MSM_CONSOLE=y
+CONFIG_SERIAL_MSM_HS=y
+CONFIG_SERIAL_MSM_SMD=y
+CONFIG_DIAG_CHAR=y
+CONFIG_DIAG_USES_SMD=y
+CONFIG_HW_RANDOM=y
+CONFIG_HW_RANDOM_MSM_LEGACY=y
+CONFIG_MSM_SMD_PKT=y
+CONFIG_MSM_ADSPRPC=y
+CONFIG_MSM_RDBG=m
+CONFIG_I2C_CHARDEV=y
+CONFIG_I2C_MSM_V2=y
+CONFIG_SPI=y
+CONFIG_SPI_QUP=y
+CONFIG_SPI_SPIDEV=y
+CONFIG_SLIMBUS_MSM_NGD=y
+CONFIG_SPMI=y
+CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
+CONFIG_PINCTRL_MSM8937=y
+CONFIG_PINCTRL_MSM8917=y
+CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
+CONFIG_GPIOLIB=y
+CONFIG_GPIO_SYSFS=y
+CONFIG_GPIO_QPNP_PIN=y
+CONFIG_GPIO_QPNP_PIN_DEBUG=y
+CONFIG_POWER_RESET_QCOM=y
+CONFIG_QCOM_DLOAD_MODE=y
+CONFIG_POWER_RESET_SYSCON=y
+CONFIG_QPNP_FG=y
+CONFIG_SMB135X_CHARGER=y
+CONFIG_SMB1351_USB_CHARGER=y
+CONFIG_QPNP_SMB5=y
+CONFIG_QPNP_SMBCHARGER=y
+CONFIG_QPNP_TYPEC=y
+CONFIG_QPNP_QG=y
+CONFIG_MSM_APM=y
+CONFIG_SENSORS_QPNP_ADC_VOLTAGE=y
+CONFIG_THERMAL=y
+CONFIG_THERMAL_WRITABLE_TRIPS=y
+CONFIG_THERMAL_GOV_USER_SPACE=y
+CONFIG_THERMAL_GOV_LOW_LIMITS=y
+CONFIG_CPU_THERMAL=y
+CONFIG_DEVFREQ_THERMAL=y
+CONFIG_THERMAL_QPNP=y
+CONFIG_THERMAL_QPNP_ADC_TM=y
+CONFIG_THERMAL_TSENS=y
+CONFIG_QTI_VIRTUAL_SENSOR=y
+CONFIG_QTI_QMI_COOLING_DEVICE=y
+CONFIG_REGULATOR_COOLING_DEVICE=y
+CONFIG_QTI_BCL_PMIC5=y
+CONFIG_QTI_BCL_SOC_DRIVER=y
+CONFIG_MFD_SPMI_PMIC=y
+CONFIG_REGULATOR=y
+CONFIG_REGULATOR_FIXED_VOLTAGE=y
+CONFIG_REGULATOR_CPR=y
+CONFIG_REGULATOR_CPR4_APSS=y
+CONFIG_REGULATOR_CPRH_KBSS=y
+CONFIG_REGULATOR_MEM_ACC=y
+CONFIG_REGULATOR_MSM_GFX_LDO=y
+CONFIG_REGULATOR_QPNP_LABIBB=y
+CONFIG_REGULATOR_QPNP_LCDB=y
+CONFIG_REGULATOR_QPNP=y
+CONFIG_REGULATOR_RPM_SMD=y
+CONFIG_REGULATOR_SPM=y
+CONFIG_REGULATOR_STUB=y
+CONFIG_MEDIA_SUPPORT=y
+CONFIG_MEDIA_CAMERA_SUPPORT=y
+CONFIG_MEDIA_CONTROLLER=y
+CONFIG_VIDEO_V4L2_SUBDEV_API=y
+CONFIG_V4L_PLATFORM_DRIVERS=y
+CONFIG_MSM_CAMERA=y
+CONFIG_MSM_CAMERA_DEBUG=y
+CONFIG_MSMB_CAMERA=y
+CONFIG_MSMB_CAMERA_DEBUG=y
+CONFIG_MSM_CAMERA_SENSOR=y
+CONFIG_MSM_CPP=y
+CONFIG_MSM_CCI=y
+CONFIG_MSM_CSI20_HEADER=y
+CONFIG_MSM_CSI22_HEADER=y
+CONFIG_MSM_CSI30_HEADER=y
+CONFIG_MSM_CSI31_HEADER=y
+CONFIG_MSM_CSIPHY=y
+CONFIG_MSM_CSID=y
+CONFIG_MSM_EEPROM=y
+CONFIG_MSM_ISPIF_V2=y
+CONFIG_IMX134=y
+CONFIG_IMX132=y
+CONFIG_OV9724=y
+CONFIG_OV5648=y
+CONFIG_GC0339=y
+CONFIG_OV8825=y
+CONFIG_OV8865=y
+CONFIG_s5k4e1=y
+CONFIG_OV12830=y
+CONFIG_MSM_V4L2_VIDEO_OVERLAY_DEVICE=y
+CONFIG_MSMB_JPEG=y
+CONFIG_MSM_FD=y
+CONFIG_MSM_JPEGDMA=y
+CONFIG_MSM_VIDC_3X_V4L2=y
+CONFIG_MSM_VIDC_3X_GOVERNORS=y
+CONFIG_MSM_SDE_ROTATOR=y
+CONFIG_MSM_SDE_ROTATOR_EVTLOG_DEBUG=y
+CONFIG_RADIO_IRIS=y
+CONFIG_RADIO_IRIS_TRANSPORT=y
+CONFIG_QCOM_KGSL=y
+CONFIG_FB=y
+CONFIG_FB_VIRTUAL=y
+CONFIG_FB_MSM=y
+CONFIG_FB_MSM_MDSS=y
+CONFIG_FB_MSM_MDSS_WRITEBACK=y
+CONFIG_FB_MSM_MDSS_DSI_CTRL_STATUS=y
+CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
+CONFIG_BACKLIGHT_LCD_SUPPORT=y
+CONFIG_BACKLIGHT_CLASS_DEVICE=y
+CONFIG_SOUND=y
+CONFIG_SND=y
+CONFIG_SND_DYNAMIC_MINORS=y
+CONFIG_SND_USB_AUDIO=y
+CONFIG_SND_SOC=y
+CONFIG_UHID=y
+CONFIG_HID_APPLE=y
+CONFIG_HID_ELECOM=y
+CONFIG_HID_MAGICMOUSE=y
+CONFIG_HID_MICROSOFT=y
+CONFIG_HID_MULTITOUCH=y
+CONFIG_USB_HIDDEV=y
+CONFIG_USB=y
+CONFIG_USB_ANNOUNCE_NEW_DEVICES=y
+CONFIG_USB_MON=y
+CONFIG_USB_XHCI_HCD=y
+CONFIG_USB_EHCI_HCD=y
+CONFIG_USB_EHCI_MSM=y
+CONFIG_USB_EHCI_HCD_PLATFORM=y
+CONFIG_USB_OHCI_HCD=y
+CONFIG_USB_OHCI_HCD_PLATFORM=y
+CONFIG_USB_ACM=y
+CONFIG_USB_STORAGE=y
+CONFIG_USB_STORAGE_DATAFAB=y
+CONFIG_USB_STORAGE_FREECOM=y
+CONFIG_USB_STORAGE_ISD200=y
+CONFIG_USB_STORAGE_USBAT=y
+CONFIG_USB_STORAGE_SDDR09=y
+CONFIG_USB_STORAGE_SDDR55=y
+CONFIG_USB_STORAGE_JUMPSHOT=y
+CONFIG_USB_STORAGE_ALAUDA=y
+CONFIG_USB_STORAGE_ONETOUCH=y
+CONFIG_USB_STORAGE_KARMA=y
+CONFIG_USB_STORAGE_CYPRESS_ATACB=y
+CONFIG_USB_DWC3=y
+CONFIG_USB_DWC3_MSM=y
+CONFIG_USB_SERIAL=y
+CONFIG_USB_EHSET_TEST_FIXTURE=y
+CONFIG_NOP_USB_XCEIV=y
+CONFIG_DUAL_ROLE_USB_INTF=y
+CONFIG_USB_MSM_SSPHY_QMP=y
+CONFIG_MSM_QUSB_PHY=y
+CONFIG_USB_GADGET=y
+CONFIG_USB_GADGET_DEBUG_FILES=y
+CONFIG_USB_GADGET_DEBUG_FS=y
+CONFIG_USB_GADGET_VBUS_DRAW=500
+CONFIG_USB_CI13XXX_MSM=y
+CONFIG_USB_CONFIGFS=y
+CONFIG_USB_CONFIGFS_SERIAL=y
+CONFIG_USB_CONFIGFS_NCM=y
+CONFIG_USB_CONFIGFS_QCRNDIS=y
+CONFIG_USB_CONFIGFS_RNDIS=y
+CONFIG_USB_CONFIGFS_RMNET_BAM=y
+CONFIG_USB_CONFIGFS_MASS_STORAGE=y
+CONFIG_USB_CONFIGFS_F_FS=y
+CONFIG_USB_CONFIGFS_F_MTP=y
+CONFIG_USB_CONFIGFS_F_PTP=y
+CONFIG_USB_CONFIGFS_F_ACC=y
+CONFIG_USB_CONFIGFS_F_AUDIO_SRC=y
+CONFIG_USB_CONFIGFS_UEVENT=y
+CONFIG_USB_CONFIGFS_F_MIDI=y
+CONFIG_USB_CONFIGFS_F_HID=y
+CONFIG_USB_CONFIGFS_F_DIAG=y
+CONFIG_USB_CONFIGFS_F_CDEV=y
+CONFIG_USB_CONFIGFS_F_CCID=y
+CONFIG_USB_CONFIGFS_F_QDSS=y
+CONFIG_MMC=y
+CONFIG_MMC_PERF_PROFILING=y
+CONFIG_MMC_RING_BUFFER=y
+CONFIG_MMC_PARANOID_SD_INIT=y
+CONFIG_MMC_CLKGATE=y
+CONFIG_MMC_BLOCK_MINORS=32
+CONFIG_MMC_BLOCK_DEFERRED_RESUME=y
+CONFIG_MMC_TEST=y
+CONFIG_MMC_SDHCI=y
+CONFIG_MMC_SDHCI_PLTFM=y
+CONFIG_MMC_SDHCI_MSM=y
+CONFIG_MMC_SDHCI_MSM_ICE=y
+CONFIG_MMC_CQ_HCI=y
+CONFIG_LEDS_QTI_TRI_LED=y
+CONFIG_LEDS_QPNP=y
+CONFIG_LEDS_QPNP_FLASH=y
+CONFIG_LEDS_QPNP_FLASH_V2=y
+CONFIG_LEDS_QPNP_WLED=y
+CONFIG_LEDS_QPNP_HAPTICS=y
+CONFIG_LEDS_QPNP_VIBRATOR_LDO=y
+CONFIG_LEDS_TRIGGERS=y
+CONFIG_LEDS_TRIGGER_TIMER=y
+CONFIG_EDAC=y
+CONFIG_EDAC_MM_EDAC=y
+CONFIG_RTC_CLASS=y
+CONFIG_RTC_DRV_QPNP=y
+CONFIG_DMADEVICES=y
+CONFIG_QCOM_SPS_DMA=y
+CONFIG_UIO=y
+CONFIG_UIO_MSM_SHAREDMEM=y
+CONFIG_STAGING=y
+CONFIG_ASHMEM=y
+CONFIG_ANDROID_LOW_MEMORY_KILLER=y
+CONFIG_ION=y
+CONFIG_ION_MSM=y
+CONFIG_IPA=y
+CONFIG_RMNET_IPA=y
+CONFIG_RNDIS_IPA=y
+CONFIG_SPS=y
+CONFIG_SPS_SUPPORT_NDP_BAM=y
+CONFIG_QPNP_COINCELL=y
+CONFIG_QPNP_REVID=y
+CONFIG_USB_BAM=y
+CONFIG_MSM_EXT_DISPLAY=y
+CONFIG_MSM_RMNET_BAM=y
+CONFIG_MSM_MDSS_PLL=y
+CONFIG_REMOTE_SPINLOCK_MSM=y
+CONFIG_MAILBOX=y
+CONFIG_ARM_SMMU=y
+CONFIG_QCOM_LAZY_MAPPING=y
+CONFIG_IOMMU_DEBUG=y
+CONFIG_IOMMU_DEBUG_TRACKING=y
+CONFIG_IOMMU_TESTS=y
+CONFIG_QCOM_CPUSS_DUMP=y
+CONFIG_QCOM_RUN_QUEUE_STATS=y
+CONFIG_MSM_SPM=y
+CONFIG_MSM_L2_SPM=y
+CONFIG_QCOM_SCM=y
+CONFIG_MSM_BOOT_STATS=y
+CONFIG_MSM_CORE_HANG_DETECT=y
+CONFIG_MSM_GLADIATOR_HANG_DETECT=y
+CONFIG_QCOM_WATCHDOG_V2=y
+CONFIG_QCOM_MEMORY_DUMP_V2=y
+CONFIG_MSM_DEBUG_LAR_UNLOCK=y
+CONFIG_MSM_RPM_SMD=y
+CONFIG_QCOM_BUS_SCALING=y
+CONFIG_QCOM_SECURE_BUFFER=y
+CONFIG_QCOM_EARLY_RANDOM=y
+CONFIG_MSM_SMEM=y
+CONFIG_MSM_SMD=y
+CONFIG_MSM_SMD_DEBUG=y
+CONFIG_MSM_TZ_SMMU=y
+CONFIG_TRACER_PKT=y
+CONFIG_MSM_SMP2P=y
+CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
+CONFIG_MSM_QMI_INTERFACE=y
+CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_PIL=y
+CONFIG_MSM_PIL_SSR_GENERIC=y
+CONFIG_MSM_PIL_MSS_QDSP6V5=y
+CONFIG_ICNSS=y
+CONFIG_MSM_PERFORMANCE=y
+CONFIG_MSM_EVENT_TIMER=y
+CONFIG_MSM_AVTIMER=y
+CONFIG_MSM_PM=y
+CONFIG_QCOM_DCC=y
+CONFIG_QTI_RPM_STATS_LOG=y
+CONFIG_QCOM_FORCE_WDOG_BITE_ON_PANIC=y
+CONFIG_MEM_SHARE_QMI_SERVICE=y
+CONFIG_MSM_BAM_DMUX=y
+CONFIG_WCNSS_CORE=y
+CONFIG_WCNSS_CORE_PRONTO=y
+CONFIG_WCNSS_REGISTER_DUMP_ON_BITE=y
+CONFIG_QCOM_BIMC_BWMON=y
+CONFIG_DEVFREQ_GOV_QCOM_BW_HWMON=y
+CONFIG_DEVFREQ_SIMPLE_DEV=y
+CONFIG_QCOM_DEVFREQ_DEVBW=y
+CONFIG_SPDM_SCM=y
+CONFIG_DEVFREQ_SPDM=y
+CONFIG_PWM=y
+CONFIG_PWM_QPNP=y
+CONFIG_PWM_QTI_LPG=y
+CONFIG_ARM_GIC_V3_ACL=y
+CONFIG_QTI_MPM=y
+CONFIG_ANDROID=y
+CONFIG_ANDROID_BINDER_IPC=y
+CONFIG_SENSORS_SSC=y
+CONFIG_MSM_TZ_LOG=y
+CONFIG_EXT2_FS=y
+CONFIG_EXT2_FS_XATTR=y
+CONFIG_EXT3_FS=y
+CONFIG_EXT4_FS_SECURITY=y
+CONFIG_QUOTA=y
+CONFIG_QUOTA_NETLINK_INTERFACE=y
+CONFIG_QFMT_V2=y
+CONFIG_FUSE_FS=y
+CONFIG_MSDOS_FS=y
+CONFIG_VFAT_FS=y
+CONFIG_TMPFS=y
+CONFIG_TMPFS_POSIX_ACL=y
+CONFIG_ECRYPT_FS=y
+CONFIG_ECRYPT_FS_MESSAGING=y
+# CONFIG_NETWORK_FILESYSTEMS is not set
+CONFIG_NLS_CODEPAGE_437=y
+CONFIG_NLS_ISO8859_1=y
+CONFIG_PRINTK_TIME=y
+CONFIG_DYNAMIC_DEBUG=y
+CONFIG_DEBUG_INFO=y
+CONFIG_PAGE_OWNER=y
+CONFIG_PAGE_OWNER_ENABLE_DEFAULT=y
+CONFIG_MAGIC_SYSRQ=y
+CONFIG_DEBUG_PAGEALLOC=y
+CONFIG_SLUB_DEBUG_PANIC_ON=y
+CONFIG_DEBUG_PAGEALLOC_ENABLE_DEFAULT=y
+CONFIG_PAGE_POISONING=y
+CONFIG_DEBUG_OBJECTS=y
+CONFIG_DEBUG_OBJECTS_FREE=y
+CONFIG_DEBUG_OBJECTS_TIMERS=y
+CONFIG_DEBUG_OBJECTS_WORK=y
+CONFIG_DEBUG_OBJECTS_RCU_HEAD=y
+CONFIG_DEBUG_OBJECTS_PERCPU_COUNTER=y
+CONFIG_SLUB_DEBUG_ON=y
+CONFIG_DEBUG_KMEMLEAK=y
+CONFIG_DEBUG_KMEMLEAK_EARLY_LOG_SIZE=4000
+CONFIG_DEBUG_KMEMLEAK_DEFAULT_OFF=y
+CONFIG_DEBUG_STACK_USAGE=y
+CONFIG_DEBUG_MEMORY_INIT=y
+CONFIG_LOCKUP_DETECTOR=y
+CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC=y
+CONFIG_WQ_WATCHDOG=y
+CONFIG_PANIC_TIMEOUT=5
+CONFIG_PANIC_ON_SCHED_BUG=y
+CONFIG_PANIC_ON_RT_THROTTLING=y
+CONFIG_SCHEDSTATS=y
+CONFIG_SCHED_STACK_END_CHECK=y
+# CONFIG_DEBUG_PREEMPT is not set
+CONFIG_DEBUG_SPINLOCK=y
+CONFIG_DEBUG_MUTEXES=y
+CONFIG_DEBUG_ATOMIC_SLEEP=y
+CONFIG_DEBUG_LIST=y
+CONFIG_FAULT_INJECTION=y
+CONFIG_FAIL_PAGE_ALLOC=y
+CONFIG_FAULT_INJECTION_DEBUG_FS=y
+CONFIG_FAULT_INJECTION_STACKTRACE_FILTER=y
+CONFIG_IPC_LOGGING=y
+CONFIG_QCOM_RTB=y
+CONFIG_QCOM_RTB_SEPARATE_CPUS=y
+CONFIG_FUNCTION_TRACER=y
+CONFIG_IRQSOFF_TRACER=y
+CONFIG_PREEMPT_TRACER=y
+CONFIG_BLK_DEV_IO_TRACE=y
+CONFIG_CPU_FREQ_SWITCH_PROFILER=y
+CONFIG_LKDTM=y
+CONFIG_MEMTEST=y
+CONFIG_PANIC_ON_DATA_CORRUPTION=y
+CONFIG_ARM64_PTDUMP=y
+CONFIG_PID_IN_CONTEXTIDR=y
+CONFIG_CORESIGHT=y
+CONFIG_CORESIGHT_LINK_AND_SINK_TMC=y
+CONFIG_CORESIGHT_SOURCE_ETM4X=y
+CONFIG_CORESIGHT_REMOTE_ETM=y
+CONFIG_CORESIGHT_REMOTE_ETM_DEFAULT_ENABLE=0
+CONFIG_CORESIGHT_QCOM_REPLICATOR=y
+CONFIG_CORESIGHT_DBGUI=y
+CONFIG_CORESIGHT_STM=y
+CONFIG_CORESIGHT_TPDA=y
+CONFIG_CORESIGHT_TPDM=y
+CONFIG_CORESIGHT_CTI=y
+CONFIG_CORESIGHT_EVENT=y
+CONFIG_CORESIGHT_HWEVENT=y
+CONFIG_SECURITY_PERF_EVENTS_RESTRICT=y
+CONFIG_SECURITY=y
+CONFIG_HARDENED_USERCOPY=y
+CONFIG_SECURITY_SELINUX=y
+CONFIG_SECURITY_SMACK=y
+CONFIG_CRYPTO_CTR=y
+CONFIG_CRYPTO_XCBC=y
+CONFIG_CRYPTO_MD4=y
+CONFIG_CRYPTO_TWOFISH=y
+CONFIG_CRYPTO_ANSI_CPRNG=y
+CONFIG_CRYPTO_DEV_QCOM_MSM_QCE=y
+CONFIG_CRYPTO_DEV_QCRYPTO=y
+CONFIG_CRYPTO_DEV_QCEDEV=y
+CONFIG_CRYPTO_DEV_QCOM_ICE=y
+CONFIG_ARM64_CRYPTO=y
+CONFIG_CRYPTO_SHA1_ARM64_CE=y
+CONFIG_CRYPTO_SHA2_ARM64_CE=y
+CONFIG_CRYPTO_GHASH_ARM64_CE=y
+CONFIG_CRYPTO_AES_ARM64_CE_CCM=y
+CONFIG_CRYPTO_AES_ARM64_CE_BLK=y
+CONFIG_CRYPTO_AES_ARM64_NEON_BLK=y
+CONFIG_CRYPTO_CRC32_ARM64=y
+CONFIG_QMI_ENCDEC=y
diff --git a/arch/arm64/configs/msm8953-perf_defconfig b/arch/arm64/configs/msm8953-perf_defconfig
index a77f39f..0fe026f 100644
--- a/arch/arm64/configs/msm8953-perf_defconfig
+++ b/arch/arm64/configs/msm8953-perf_defconfig
@@ -7,6 +7,9 @@
CONFIG_HIGH_RES_TIMERS=y
CONFIG_IRQ_TIME_ACCOUNTING=y
CONFIG_SCHED_WALT=y
+CONFIG_TASKSTATS=y
+CONFIG_TASK_XACCT=y
+CONFIG_TASK_IO_ACCOUNTING=y
CONFIG_RCU_EXPERT=y
CONFIG_RCU_FAST_NO_HZ=y
CONFIG_RCU_NOCB_CPU=y
@@ -28,6 +31,8 @@
CONFIG_SCHED_TUNE=y
CONFIG_DEFAULT_USE_ENERGY_AWARE=y
CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
# CONFIG_RD_XZ is not set
# CONFIG_RD_LZO is not set
# CONFIG_RD_LZ4 is not set
@@ -51,19 +56,15 @@
# CONFIG_IOSCHED_DEADLINE is not set
CONFIG_ARCH_QCOM=y
CONFIG_ARCH_MSM8953=y
-CONFIG_ARCH_MSM8937=y
-CONFIG_ARCH_MSM8917=y
CONFIG_ARCH_SDM450=y
CONFIG_ARCH_SDM632=y
-CONFIG_ARCH_SDM429=y
-CONFIG_ARCH_SDM439=y
+# CONFIG_ARM64_ERRATUM_1024718 is not set
CONFIG_SCHED_MC=y
CONFIG_NR_CPUS=8
CONFIG_PREEMPT=y
CONFIG_HZ_100=y
CONFIG_CMA=y
CONFIG_ZSMALLOC=y
-CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_SECCOMP=y
CONFIG_HARDEN_BRANCH_PREDICTOR=y
CONFIG_ARMV8_DEPRECATED=y
@@ -241,7 +242,9 @@
CONFIG_BLK_DEV_LOOP=y
CONFIG_BLK_DEV_RAM=y
CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_HDCP_QSEECOM=y
CONFIG_QSEECOM=y
+CONFIG_UID_SYS_STATS=y
CONFIG_MEMORY_STATE_TIME=y
CONFIG_SCSI=y
CONFIG_BLK_DEV_SD=y
@@ -313,8 +316,6 @@
CONFIG_SPMI=y
CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
CONFIG_PINCTRL_MSM8953=y
-CONFIG_PINCTRL_MSM8937=y
-CONFIG_PINCTRL_MSM8917=y
CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
CONFIG_GPIOLIB=y
CONFIG_GPIO_SYSFS=y
@@ -322,7 +323,6 @@
CONFIG_GPIO_QPNP_PIN_DEBUG=y
CONFIG_POWER_RESET_QCOM=y
CONFIG_QCOM_DLOAD_MODE=y
-CONFIG_POWER_RESET_XGENE=y
CONFIG_POWER_RESET_SYSCON=y
CONFIG_QPNP_FG=y
CONFIG_SMB135X_CHARGER=y
@@ -348,6 +348,7 @@
CONFIG_QTI_BCL_PMIC5=y
CONFIG_QTI_BCL_SOC_DRIVER=y
CONFIG_MFD_SPMI_PMIC=y
+CONFIG_REGULATOR=y
CONFIG_REGULATOR_FIXED_VOLTAGE=y
CONFIG_REGULATOR_CPR=y
CONFIG_REGULATOR_CPR4_APSS=y
@@ -400,9 +401,7 @@
CONFIG_RADIO_IRIS=y
CONFIG_RADIO_IRIS_TRANSPORT=y
CONFIG_QCOM_KGSL=y
-CONFIG_DRM=y
-CONFIG_DRM_SDE_EVTLOG_DEBUG=y
-CONFIG_DRM_SDE_RSC=y
+CONFIG_FB=y
CONFIG_FB_MSM=y
CONFIG_FB_MSM_MDSS=y
CONFIG_FB_MSM_MDSS_WRITEBACK=y
@@ -410,9 +409,6 @@
CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
CONFIG_BACKLIGHT_LCD_SUPPORT=y
CONFIG_BACKLIGHT_CLASS_DEVICE=y
-CONFIG_LOGO=y
-# CONFIG_LOGO_LINUX_MONO is not set
-# CONFIG_LOGO_LINUX_VGA16 is not set
CONFIG_SOUND=y
CONFIG_SND=y
CONFIG_SND_DYNAMIC_MINORS=y
@@ -521,6 +517,7 @@
CONFIG_QPNP_COINCELL=y
CONFIG_QPNP_REVID=y
CONFIG_USB_BAM=y
+CONFIG_MSM_EXT_DISPLAY=y
CONFIG_MSM_RMNET_BAM=y
CONFIG_MSM_MDSS_PLL=y
CONFIG_REMOTE_SPINLOCK_MSM=y
@@ -530,8 +527,8 @@
CONFIG_QCOM_RUN_QUEUE_STATS=y
CONFIG_MSM_SPM=y
CONFIG_MSM_L2_SPM=y
+CONFIG_QCOM_SCM=y
CONFIG_MSM_BOOT_STATS=y
-CONFIG_QCOM_EUD=y
CONFIG_QCOM_WATCHDOG_V2=y
CONFIG_QCOM_MEMORY_DUMP_V2=y
CONFIG_MSM_RPM_SMD=y
@@ -546,6 +543,7 @@
CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
CONFIG_MSM_QMI_INTERFACE=y
CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_SYSMON_COMM=y
CONFIG_MSM_PIL=y
CONFIG_MSM_PIL_SSR_GENERIC=y
CONFIG_MSM_PIL_MSS_QDSP6V5=y
@@ -585,6 +583,7 @@
CONFIG_QFMT_V2=y
CONFIG_FUSE_FS=y
CONFIG_VFAT_FS=y
+CONFIG_TMPFS=y
CONFIG_TMPFS_POSIX_ACL=y
CONFIG_ECRYPT_FS=y
CONFIG_ECRYPT_FS_MESSAGING=y
diff --git a/arch/arm64/configs/msm8953_defconfig b/arch/arm64/configs/msm8953_defconfig
index 569a69c..b15ef8a 100644
--- a/arch/arm64/configs/msm8953_defconfig
+++ b/arch/arm64/configs/msm8953_defconfig
@@ -32,6 +32,8 @@
CONFIG_SCHED_TUNE=y
CONFIG_DEFAULT_USE_ENERGY_AWARE=y
CONFIG_BLK_DEV_INITRD=y
+# CONFIG_RD_BZIP2 is not set
+# CONFIG_RD_LZMA is not set
# CONFIG_RD_XZ is not set
# CONFIG_RD_LZO is not set
# CONFIG_RD_LZ4 is not set
@@ -55,12 +57,9 @@
# CONFIG_IOSCHED_DEADLINE is not set
CONFIG_ARCH_QCOM=y
CONFIG_ARCH_MSM8953=y
-CONFIG_ARCH_MSM8937=y
-CONFIG_ARCH_MSM8917=y
CONFIG_ARCH_SDM450=y
CONFIG_ARCH_SDM632=y
-CONFIG_ARCH_SDM429=y
-CONFIG_ARCH_SDM439=y
+# CONFIG_ARM64_ERRATUM_1024718 is not set
CONFIG_SCHED_MC=y
CONFIG_NR_CPUS=8
CONFIG_PREEMPT=y
@@ -69,7 +68,6 @@
CONFIG_CMA=y
CONFIG_CMA_DEBUGFS=y
CONFIG_ZSMALLOC=y
-CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_SECCOMP=y
CONFIG_HARDEN_BRANCH_PREDICTOR=y
CONFIG_ARMV8_DEPRECATED=y
@@ -250,6 +248,7 @@
CONFIG_BLK_DEV_LOOP=y
CONFIG_BLK_DEV_RAM=y
CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_HDCP_QSEECOM=y
CONFIG_QSEECOM=y
CONFIG_UID_SYS_STATS=y
CONFIG_MEMORY_STATE_TIME=y
@@ -325,8 +324,6 @@
CONFIG_SPMI=y
CONFIG_SPMI_MSM_PMIC_ARB_DEBUG=y
CONFIG_PINCTRL_MSM8953=y
-CONFIG_PINCTRL_MSM8937=y
-CONFIG_PINCTRL_MSM8917=y
CONFIG_PINCTRL_QCOM_SPMI_PMIC=y
CONFIG_GPIOLIB=y
CONFIG_GPIO_SYSFS=y
@@ -334,7 +331,6 @@
CONFIG_GPIO_QPNP_PIN_DEBUG=y
CONFIG_POWER_RESET_QCOM=y
CONFIG_QCOM_DLOAD_MODE=y
-CONFIG_POWER_RESET_XGENE=y
CONFIG_POWER_RESET_SYSCON=y
CONFIG_QPNP_FG=y
CONFIG_SMB135X_CHARGER=y
@@ -360,6 +356,7 @@
CONFIG_QTI_BCL_PMIC5=y
CONFIG_QTI_BCL_SOC_DRIVER=y
CONFIG_MFD_SPMI_PMIC=y
+CONFIG_REGULATOR=y
CONFIG_REGULATOR_FIXED_VOLTAGE=y
CONFIG_REGULATOR_CPR=y
CONFIG_REGULATOR_CPR4_APSS=y
@@ -412,9 +409,7 @@
CONFIG_RADIO_IRIS=y
CONFIG_RADIO_IRIS_TRANSPORT=y
CONFIG_QCOM_KGSL=y
-CONFIG_DRM=y
-CONFIG_DRM_SDE_EVTLOG_DEBUG=y
-CONFIG_DRM_SDE_RSC=y
+CONFIG_FB=y
CONFIG_FB_VIRTUAL=y
CONFIG_FB_MSM=y
CONFIG_FB_MSM_MDSS=y
@@ -423,9 +418,6 @@
CONFIG_FB_MSM_MDSS_XLOG_DEBUG=y
CONFIG_BACKLIGHT_LCD_SUPPORT=y
CONFIG_BACKLIGHT_CLASS_DEVICE=y
-CONFIG_LOGO=y
-# CONFIG_LOGO_LINUX_MONO is not set
-# CONFIG_LOGO_LINUX_VGA16 is not set
CONFIG_SOUND=y
CONFIG_SND=y
CONFIG_SND_DYNAMIC_MINORS=y
@@ -535,6 +527,7 @@
CONFIG_QPNP_COINCELL=y
CONFIG_QPNP_REVID=y
CONFIG_USB_BAM=y
+CONFIG_MSM_EXT_DISPLAY=y
CONFIG_MSM_RMNET_BAM=y
CONFIG_MSM_MDSS_PLL=y
CONFIG_REMOTE_SPINLOCK_MSM=y
@@ -548,10 +541,10 @@
CONFIG_QCOM_RUN_QUEUE_STATS=y
CONFIG_MSM_SPM=y
CONFIG_MSM_L2_SPM=y
+CONFIG_QCOM_SCM=y
CONFIG_MSM_BOOT_STATS=y
CONFIG_MSM_CORE_HANG_DETECT=y
CONFIG_MSM_GLADIATOR_HANG_DETECT=y
-CONFIG_QCOM_EUD=y
CONFIG_QCOM_WATCHDOG_V2=y
CONFIG_QCOM_MEMORY_DUMP_V2=y
CONFIG_MSM_DEBUG_LAR_UNLOCK=y
@@ -568,6 +561,7 @@
CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
CONFIG_MSM_QMI_INTERFACE=y
CONFIG_MSM_SUBSYSTEM_RESTART=y
+CONFIG_MSM_SYSMON_COMM=y
CONFIG_MSM_PIL=y
CONFIG_MSM_PIL_SSR_GENERIC=y
CONFIG_MSM_PIL_MSS_QDSP6V5=y
@@ -609,6 +603,7 @@
CONFIG_FUSE_FS=y
CONFIG_MSDOS_FS=y
CONFIG_VFAT_FS=y
+CONFIG_TMPFS=y
CONFIG_TMPFS_POSIX_ACL=y
CONFIG_ECRYPT_FS=y
CONFIG_ECRYPT_FS_MESSAGING=y
diff --git a/arch/arm64/configs/sdm670-perf_defconfig b/arch/arm64/configs/sdm670-perf_defconfig
index 5297e3f..f82678e 100644
--- a/arch/arm64/configs/sdm670-perf_defconfig
+++ b/arch/arm64/configs/sdm670-perf_defconfig
@@ -66,6 +66,7 @@
CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_PROCESS_RECLAIM=y
CONFIG_SECCOMP=y
+CONFIG_HARDEN_BRANCH_PREDICTOR=y
CONFIG_ARMV8_DEPRECATED=y
CONFIG_SWP_EMULATION=y
CONFIG_CP15_BARRIER_EMULATION=y
@@ -442,6 +443,7 @@
CONFIG_MMC=y
CONFIG_MMC_PERF_PROFILING=y
CONFIG_MMC_PARANOID_SD_INIT=y
+CONFIG_MMC_CLKGATE=y
CONFIG_MMC_BLOCK_MINORS=32
CONFIG_MMC_BLOCK_DEFERRED_RESUME=y
CONFIG_MMC_TEST=y
diff --git a/arch/arm64/configs/sdm670_defconfig b/arch/arm64/configs/sdm670_defconfig
index ad75f53..09de6e8 100644
--- a/arch/arm64/configs/sdm670_defconfig
+++ b/arch/arm64/configs/sdm670_defconfig
@@ -71,6 +71,7 @@
CONFIG_BALANCE_ANON_FILE_RECLAIM=y
CONFIG_PROCESS_RECLAIM=y
CONFIG_SECCOMP=y
+CONFIG_HARDEN_BRANCH_PREDICTOR=y
CONFIG_ARMV8_DEPRECATED=y
CONFIG_SWP_EMULATION=y
CONFIG_CP15_BARRIER_EMULATION=y
@@ -243,6 +244,7 @@
CONFIG_IPC_ROUTER=y
CONFIG_IPC_ROUTER_SECURITY=y
CONFIG_FW_LOADER_USER_HELPER_FALLBACK=y
+CONFIG_AQT_REGMAP=y
CONFIG_REGMAP_ALLOW_WRITE_DEBUGFS=y
CONFIG_DMA_CMA=y
CONFIG_ZRAM=y
@@ -448,6 +450,7 @@
CONFIG_MMC_PERF_PROFILING=y
CONFIG_MMC_RING_BUFFER=y
CONFIG_MMC_PARANOID_SD_INIT=y
+CONFIG_MMC_CLKGATE=y
CONFIG_MMC_BLOCK_MINORS=32
CONFIG_MMC_BLOCK_DEFERRED_RESUME=y
CONFIG_MMC_TEST=y
diff --git a/arch/arm64/configs/sdm845_defconfig b/arch/arm64/configs/sdm845_defconfig
index d3ae4a5..ac25fb9 100644
--- a/arch/arm64/configs/sdm845_defconfig
+++ b/arch/arm64/configs/sdm845_defconfig
@@ -528,6 +528,7 @@
CONFIG_QCOM_WATCHDOG_V2=y
CONFIG_QCOM_WDOG_IPI_ENABLE=y
CONFIG_QCOM_MEMORY_DUMP_V2=y
+CONFIG_QCOM_MINIDUMP=y
CONFIG_QCOM_BUS_SCALING=y
CONFIG_QCOM_BUS_CONFIG_RPMH=y
CONFIG_QCOM_SECURE_BUFFER=y
diff --git a/arch/arm64/include/asm/dma-iommu.h b/arch/arm64/include/asm/dma-iommu.h
index cfd49b2..fefec0b 100644
--- a/arch/arm64/include/asm/dma-iommu.h
+++ b/arch/arm64/include/asm/dma-iommu.h
@@ -25,6 +25,7 @@
dma_addr_t base;
u32 min_iova_align;
struct page *guard_page;
+ u32 force_guard_page_len;
struct dma_fast_smmu_mapping *fast;
};
diff --git a/arch/arm64/mm/dma-mapping.c b/arch/arm64/mm/dma-mapping.c
index 31d4684..42dde2d 100644
--- a/arch/arm64/mm/dma-mapping.c
+++ b/arch/arm64/mm/dma-mapping.c
@@ -1183,7 +1183,8 @@
size = PAGE_ALIGN(size);
if (mapping->min_iova_align)
- guard_len = ALIGN(size, mapping->min_iova_align) - size;
+ guard_len = ALIGN(size + mapping->force_guard_page_len,
+ mapping->min_iova_align) - size;
else
guard_len = 0;
@@ -1231,12 +1232,14 @@
addr = addr & PAGE_MASK;
size = PAGE_ALIGN(size);
- if (mapping->min_iova_align) {
- guard_len = ALIGN(size, mapping->min_iova_align) - size;
- iommu_unmap(mapping->domain, addr + size, guard_len);
- } else {
+ if (mapping->min_iova_align)
+ guard_len = ALIGN(size + mapping->force_guard_page_len,
+ mapping->min_iova_align) - size;
+ else
guard_len = 0;
- }
+
+ if (guard_len)
+ iommu_unmap(mapping->domain, addr + size, guard_len);
start = (addr - mapping->base) >> PAGE_SHIFT;
count = (size + guard_len) >> PAGE_SHIFT;
@@ -1987,21 +1990,30 @@
unsigned int bitmap_size = BITS_TO_LONGS(mapping->bits) * sizeof(long);
int vmid = VMID_HLOS;
int min_iova_align = 0;
+ int force_iova_guard_page = 0;
iommu_domain_get_attr(mapping->domain,
DOMAIN_ATTR_MMU500_ERRATA_MIN_ALIGN,
&min_iova_align);
iommu_domain_get_attr(mapping->domain,
DOMAIN_ATTR_SECURE_VMID, &vmid);
+ iommu_domain_get_attr(mapping->domain,
+ DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE,
+ &force_iova_guard_page);
+
if (vmid >= VMID_LAST || vmid < 0)
vmid = VMID_HLOS;
- if (min_iova_align) {
- mapping->min_iova_align = ARM_SMMU_MIN_IOVA_ALIGN;
- mapping->guard_page = arm_smmu_errata_get_guard_page(vmid);
- if (!mapping->guard_page)
- return -ENOMEM;
- }
+ mapping->min_iova_align = (min_iova_align) ? ARM_SMMU_MIN_IOVA_ALIGN :
+ PAGE_SIZE;
+
+ if (force_iova_guard_page)
+ mapping->force_guard_page_len = PAGE_SIZE;
+
+ mapping->guard_page =
+ arm_smmu_errata_get_guard_page(vmid);
+ if (!mapping->guard_page)
+ return -ENOMEM;
mapping->bitmap = kzalloc(bitmap_size, GFP_KERNEL | __GFP_NOWARN |
__GFP_NORETRY);
diff --git a/drivers/base/regmap/Kconfig b/drivers/base/regmap/Kconfig
index 45fc564..9afd9a9 100644
--- a/drivers/base/regmap/Kconfig
+++ b/drivers/base/regmap/Kconfig
@@ -33,6 +33,17 @@
config REGMAP_SWR
tristate
+config AQT_REGMAP
+ depends on SND_SOC
+ bool "For regmap on AQT"
+ select REGMAP_IRQ
+ default n
+ help
+ Say 'y' here to enable regmap_irq for aqt1000 codec.
+ This config is intended for enabling REGMAP_IRQ for
+ AQT1000 codec. AQT codec uses pm_runtime and calls
+ regmap_irq as a part of init.
+
config REGMAP_ALLOW_WRITE_DEBUGFS
depends on REGMAP && DEBUG_FS
bool "Allow REGMAP debugfs write"
diff --git a/drivers/char/adsprpc.c b/drivers/char/adsprpc.c
index c9ceb48..44e0644 100644
--- a/drivers/char/adsprpc.c
+++ b/drivers/char/adsprpc.c
@@ -582,16 +582,20 @@
return -ENOTTY;
}
-static int dma_alloc_memory(dma_addr_t *region_phys, void **vaddr, size_t size)
+static int dma_alloc_memory(dma_addr_t *region_phys, size_t size)
{
struct fastrpc_apps *me = &gfa;
+ void *vaddr = NULL;
+ unsigned long dma_attrs = 0;
if (me->dev == NULL) {
pr_err("device adsprpc-mem is not initialized\n");
return -ENODEV;
}
- *vaddr = dma_alloc_coherent(me->dev, size, region_phys, GFP_KERNEL);
- if (!*vaddr) {
+ dma_attrs |= DMA_ATTR_SKIP_ZEROING | DMA_ATTR_NO_KERNEL_MAPPING;
+ vaddr = dma_alloc_attrs(me->dev, size, region_phys, GFP_KERNEL,
+ dma_attrs);
+ if (!vaddr) {
pr_err("ADSPRPC: Failed to allocate %x remote heap memory\n",
(unsigned int)size);
return -ENOMEM;
@@ -665,14 +669,17 @@
}
if (map->flags == ADSP_MMAP_HEAP_ADDR ||
map->flags == ADSP_MMAP_REMOTE_HEAP_ADDR) {
+ unsigned long dma_attrs = 0;
if (me->dev == NULL) {
pr_err("failed to free remote heap allocation\n");
return;
}
if (map->phys) {
- dma_free_coherent(me->dev, map->size,
- (void *)map->va, (dma_addr_t)map->phys);
+ dma_attrs |=
+ DMA_ATTR_SKIP_ZEROING | DMA_ATTR_NO_KERNEL_MAPPING;
+ dma_free_attrs(me->dev, map->size, (void *)map->va,
+ (dma_addr_t)map->phys, dma_attrs);
}
} else if (map->flags == FASTRPC_DMAHANDLE_NOMAP) {
if (!IS_ERR_OR_NULL(map->handle))
@@ -729,7 +736,6 @@
struct fastrpc_mmap *map = NULL;
unsigned long attrs;
dma_addr_t region_phys = 0;
- void *region_vaddr = NULL;
unsigned long flags;
int err = 0, vmid;
@@ -749,13 +755,12 @@
mflags == ADSP_MMAP_REMOTE_HEAP_ADDR) {
map->apps = me;
map->fl = NULL;
- VERIFY(err, !dma_alloc_memory(®ion_phys, ®ion_vaddr,
- len));
+ VERIFY(err, !dma_alloc_memory(®ion_phys, len));
if (err)
goto bail;
map->phys = (uintptr_t)region_phys;
map->size = len;
- map->va = (uintptr_t)region_vaddr;
+ map->va = (uintptr_t)map->phys;
} else if (mflags == FASTRPC_DMAHANDLE_NOMAP) {
ion_phys_addr_t iphys;
@@ -2663,7 +2668,7 @@
static int fastrpc_file_free(struct fastrpc_file *fl)
{
struct hlist_node *n = NULL;
- struct fastrpc_mmap *map = NULL;
+ struct fastrpc_mmap *map = NULL, *lmap = NULL;
struct fastrpc_perf *perf = NULL, *fperf = NULL;
int cid;
@@ -2687,9 +2692,15 @@
fastrpc_context_list_dtor(fl);
fastrpc_buf_list_free(fl);
mutex_lock(&fl->fl_map_mutex);
- hlist_for_each_entry_safe(map, n, &fl->maps, hn) {
- fastrpc_mmap_free(map, 1);
- }
+ do {
+ lmap = NULL;
+ hlist_for_each_entry_safe(map, n, &fl->maps, hn) {
+ hlist_del_init(&map->hn);
+ lmap = map;
+ break;
+ }
+ fastrpc_mmap_free(lmap, 1);
+ } while (lmap);
mutex_unlock(&fl->fl_map_mutex);
if (fl->refcount && (fl->ssrcount == fl->apps->channel[cid].ssrcount))
kref_put_mutex(&fl->apps->channel[cid].kref,
@@ -3505,7 +3516,6 @@
static int fastrpc_cb_legacy_probe(struct device *dev)
{
- struct fastrpc_apps *me = &gfa;
struct fastrpc_channel_ctx *chan;
struct fastrpc_session_ctx *first_sess = NULL, *sess = NULL;
const char *name;
@@ -3574,7 +3584,6 @@
sess->smmu.secure = false;
chan->sesscount++;
}
- me->legacy = 1;
bail:
kfree(sids);
return err;
@@ -3627,7 +3636,6 @@
int err = 0;
struct fastrpc_apps *me = &gfa;
struct device *dev = &pdev->dev;
- struct smq_phy_page range;
struct device_node *ion_node, *node;
struct platform_device *ion_pdev;
struct cma *cma;
@@ -3651,6 +3659,7 @@
if (of_device_is_compatible(dev->of_node,
"qcom,msm-fastrpc-legacy-compute")) {
me->glink = false;
+ me->legacy = 1;
}
if (of_device_is_compatible(dev->of_node,
@@ -3661,7 +3670,6 @@
if (of_device_is_compatible(dev->of_node,
"qcom,msm-adsprpc-mem-region")) {
me->dev = dev;
- range.addr = 0;
ion_node = of_find_compatible_node(NULL, NULL, "qcom,msm-ion");
if (ion_node) {
for_each_available_child_of_node(ion_node, node) {
@@ -3674,13 +3682,14 @@
break;
cma = dev_get_cma_area(&ion_pdev->dev);
if (cma) {
- range.addr = cma_get_base(cma);
- range.size = (size_t)cma_get_size(cma);
+ me->range.addr = cma_get_base(cma);
+ me->range.size =
+ (size_t)cma_get_size(cma);
}
break;
}
}
- if (range.addr && !of_property_read_bool(dev->of_node,
+ if (me->range.addr && !of_property_read_bool(dev->of_node,
"restrict-access")) {
int srcVM[1] = {VMID_HLOS};
int destVM[4] = {VMID_HLOS, VMID_MSS_MSA, VMID_SSC_Q6,
@@ -3691,12 +3700,11 @@
PERM_READ | PERM_WRITE | PERM_EXEC,
};
- VERIFY(err, !hyp_assign_phys(range.addr, range.size,
- srcVM, 1, destVM, destVMperm, 4));
+ VERIFY(err, !hyp_assign_phys(me->range.addr,
+ me->range.size, srcVM, 1,
+ destVM, destVMperm, 4));
if (err)
goto bail;
- me->range.addr = range.addr;
- me->range.size = range.size;
}
return 0;
}
diff --git a/drivers/char/adsprpc_compat.c b/drivers/char/adsprpc_compat.c
index 2868dd3..0f07483 100644
--- a/drivers/char/adsprpc_compat.c
+++ b/drivers/char/adsprpc_compat.c
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2014-2018, 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
@@ -77,13 +77,13 @@
struct compat_fastrpc_ioctl_mmap {
compat_int_t fd; /* ion fd */
compat_uint_t flags; /* flags for dsp to map with */
- compat_u64 vaddrin; /* optional virtual address */
+ compat_uptr_t vaddrin; /* optional virtual address */
compat_size_t size; /* size */
- compat_u64 vaddrout; /* dsps virtual address */
+ compat_uptr_t vaddrout; /* dsps virtual address */
};
struct compat_fastrpc_ioctl_munmap {
- compat_u64 vaddrout; /* address to unmap */
+ compat_uptr_t vaddrout; /* address to unmap */
compat_size_t size; /* size */
};
@@ -191,7 +191,7 @@
compat_uint_t u;
compat_int_t i;
compat_size_t s;
- compat_u64 p;
+ compat_uptr_t p;
int err;
err = get_user(i, &map32->fd);
@@ -199,7 +199,7 @@
err |= get_user(u, &map32->flags);
err |= put_user(u, &map->flags);
err |= get_user(p, &map32->vaddrin);
- err |= put_user(p, &map->vaddrin);
+ err |= put_user(p, (uintptr_t *)&map->vaddrin);
err |= get_user(s, &map32->size);
err |= put_user(s, &map->size);
@@ -210,7 +210,7 @@
struct compat_fastrpc_ioctl_mmap __user *map32,
struct fastrpc_ioctl_mmap __user *map)
{
- compat_u64 p;
+ compat_uptr_t p;
int err;
err = get_user(p, &map->vaddrout);
@@ -223,7 +223,7 @@
struct compat_fastrpc_ioctl_munmap __user *unmap32,
struct fastrpc_ioctl_munmap __user *unmap)
{
- compat_u64 p;
+ compat_uptr_t p;
compat_size_t s;
int err;
diff --git a/drivers/char/adsprpc_shared.h b/drivers/char/adsprpc_shared.h
index 37f3e63..bb7b654 100644
--- a/drivers/char/adsprpc_shared.h
+++ b/drivers/char/adsprpc_shared.h
@@ -199,16 +199,16 @@
};
struct fastrpc_ioctl_munmap {
- uint64_t vaddrout; /* address to unmap */
+ uintptr_t vaddrout; /* address to unmap */
size_t size; /* size */
};
struct fastrpc_ioctl_mmap {
int fd; /* ion fd */
uint32_t flags; /* flags for dsp to map with */
- uint64_t vaddrin; /* optional virtual address */
+ uintptr_t vaddrin; /* optional virtual address */
size_t size; /* size */
- uint64_t vaddrout; /* dsps virtual address */
+ uintptr_t vaddrout; /* dsps virtual address */
};
struct fastrpc_ioctl_munmap_fd {
diff --git a/drivers/char/diag/diag_masks.c b/drivers/char/diag/diag_masks.c
index 223bc03..b7d56a9 100644
--- a/drivers/char/diag/diag_masks.c
+++ b/drivers/char/diag/diag_masks.c
@@ -27,9 +27,6 @@
#define DIAG_SET_FEATURE_MASK(x) (feature_bytes[(x)/8] |= (1 << (x & 0x7)))
-#define diag_check_update(x) \
- (!info || (info && (info->peripheral_mask & MD_PERIPHERAL_MASK(x)))) \
-
struct diag_mask_info msg_mask;
struct diag_mask_info msg_bt_mask;
struct diag_mask_info log_mask;
@@ -64,6 +61,20 @@
{ .ssid_first = MSG_SSID_25, .ssid_last = MSG_SSID_25_LAST }
};
+static int diag_check_update(int md_peripheral, int pid)
+{
+ int ret;
+ struct diag_md_session_t *info = NULL;
+
+ mutex_lock(&driver->md_session_lock);
+ info = diag_md_session_get_pid(pid);
+ ret = (!info || (info &&
+ (info->peripheral_mask & MD_PERIPHERAL_MASK(md_peripheral))));
+ mutex_unlock(&driver->md_session_lock);
+
+ return ret;
+}
+
static int diag_apps_responds(void)
{
/*
@@ -825,7 +836,7 @@
mutex_unlock(&driver->msg_mask_lock);
mutex_unlock(&mask_info->lock);
mutex_unlock(&driver->md_session_lock);
- if (diag_check_update(APPS_DATA))
+ if (diag_check_update(APPS_DATA, pid))
diag_update_userspace_clients(MSG_MASKS_TYPE);
/*
@@ -849,7 +860,7 @@
for (i = 0; i < NUM_MD_SESSIONS; i++) {
if (i == APPS_DATA)
continue;
- if (!diag_check_update(i))
+ if (!diag_check_update(i, pid))
continue;
if (i > NUM_PERIPHERALS)
peripheral = diag_search_peripheral_by_pd(i);
@@ -919,7 +930,7 @@
mutex_unlock(&driver->msg_mask_lock);
mutex_unlock(&mask_info->lock);
mutex_unlock(&driver->md_session_lock);
- if (diag_check_update(APPS_DATA))
+ if (diag_check_update(APPS_DATA, pid))
diag_update_userspace_clients(MSG_MASKS_TYPE);
/*
@@ -937,7 +948,7 @@
for (i = 0; i < NUM_MD_SESSIONS; i++) {
if (i == APPS_DATA)
continue;
- if (!diag_check_update(i))
+ if (!diag_check_update(i, pid))
continue;
if (i > NUM_PERIPHERALS)
peripheral = diag_search_peripheral_by_pd(i);
@@ -1027,7 +1038,7 @@
mask_info->status = DIAG_CTRL_MASK_VALID;
mutex_unlock(&mask_info->lock);
mutex_unlock(&driver->md_session_lock);
- if (diag_check_update(APPS_DATA))
+ if (diag_check_update(APPS_DATA, pid))
diag_update_userspace_clients(EVENT_MASKS_TYPE);
/*
@@ -1046,7 +1057,7 @@
for (i = 0; i < NUM_MD_SESSIONS; i++) {
if (i == APPS_DATA)
continue;
- if (!diag_check_update(i))
+ if (!diag_check_update(i, pid))
continue;
if (i > NUM_PERIPHERALS)
peripheral = diag_search_peripheral_by_pd(i);
@@ -1098,7 +1109,7 @@
}
mutex_unlock(&mask_info->lock);
mutex_unlock(&driver->md_session_lock);
- if (diag_check_update(APPS_DATA))
+ if (diag_check_update(APPS_DATA, pid))
diag_update_userspace_clients(EVENT_MASKS_TYPE);
/*
@@ -1110,7 +1121,7 @@
for (i = 0; i < NUM_MD_SESSIONS; i++) {
if (i == APPS_DATA)
continue;
- if (!diag_check_update(i))
+ if (!diag_check_update(i, pid))
continue;
if (i > NUM_PERIPHERALS)
peripheral = diag_search_peripheral_by_pd(i);
@@ -1373,7 +1384,7 @@
}
mutex_unlock(&mask_info->lock);
mutex_unlock(&driver->md_session_lock);
- if (diag_check_update(APPS_DATA))
+ if (diag_check_update(APPS_DATA, pid))
diag_update_userspace_clients(LOG_MASKS_TYPE);
/*
@@ -1404,7 +1415,7 @@
for (i = 0; i < NUM_MD_SESSIONS; i++) {
if (i == APPS_DATA)
continue;
- if (!diag_check_update(i))
+ if (!diag_check_update(i, pid))
continue;
if (i > NUM_PERIPHERALS)
peripheral = diag_search_peripheral_by_pd(i);
@@ -1459,7 +1470,7 @@
}
mask_info->status = DIAG_CTRL_MASK_ALL_DISABLED;
mutex_unlock(&driver->md_session_lock);
- if (diag_check_update(APPS_DATA))
+ if (diag_check_update(APPS_DATA, pid))
diag_update_userspace_clients(LOG_MASKS_TYPE);
/*
@@ -1477,7 +1488,7 @@
for (i = 0; i < NUM_MD_SESSIONS; i++) {
if (i == APPS_DATA)
continue;
- if (!diag_check_update(i))
+ if (!diag_check_update(i, pid))
continue;
if (i > NUM_PERIPHERALS)
peripheral = diag_search_peripheral_by_pd(i);
@@ -2042,14 +2053,6 @@
__func__, mask_info->ptr, mask_info->update_buf);
return -EINVAL;
}
- mutex_lock(&driver->diag_maskclear_mutex);
- if (driver->mask_clear) {
- DIAG_LOG(DIAG_DEBUG_PERIPHERALS,
- "diag:%s: count = %zu\n", __func__, count);
- mutex_unlock(&driver->diag_maskclear_mutex);
- return -EIO;
- }
- mutex_unlock(&driver->diag_maskclear_mutex);
mutex_lock(&mask_info->lock);
mutex_lock(&driver->msg_mask_lock);
diff --git a/drivers/char/diag/diagchar.h b/drivers/char/diag/diagchar.h
index 9988291..fc18776 100644
--- a/drivers/char/diag/diagchar.h
+++ b/drivers/char/diag/diagchar.h
@@ -543,8 +543,6 @@
struct class *diagchar_class;
struct device *diag_dev;
int ref_count;
- int mask_clear;
- struct mutex diag_maskclear_mutex;
struct mutex diag_notifier_mutex;
struct mutex diagchar_mutex;
struct mutex diag_file_mutex;
diff --git a/drivers/char/diag/diagchar_core.c b/drivers/char/diag/diagchar_core.c
index d4bae2e..ba321b0 100644
--- a/drivers/char/diag/diagchar_core.c
+++ b/drivers/char/diag/diagchar_core.c
@@ -459,10 +459,6 @@
if (diag_mask_clear_param)
diag_clear_masks(pid);
- mutex_lock(&driver->diag_maskclear_mutex);
- driver->mask_clear = 1;
- mutex_unlock(&driver->diag_maskclear_mutex);
-
mutex_lock(&driver->diagchar_mutex);
p_mask =
diag_translate_kernel_to_user_mask(session_mask);
@@ -559,9 +555,7 @@
DIAG_LOG(DIAG_DEBUG_USERSPACE, "diag: process exit %s\n",
current->comm);
ret = diag_remove_client_entry(file);
- mutex_lock(&driver->diag_maskclear_mutex);
- driver->mask_clear = 0;
- mutex_unlock(&driver->diag_maskclear_mutex);
+
return ret;
}
@@ -1673,6 +1667,51 @@
return ret;
}
+static void diag_switch_logging_clear_mask(
+ struct diag_logging_mode_param_t *param, int pid)
+{
+ int new_mode;
+ struct diag_md_session_t *session_info = NULL;
+
+ mutex_lock(&driver->md_session_lock);
+ session_info = diag_md_session_get_pid(pid);
+ if (!session_info) {
+ DIAG_LOG(DIAG_DEBUG_USERSPACE, "Invalid pid: %d\n", pid);
+ mutex_unlock(&driver->md_session_lock);
+ return;
+ }
+ mutex_unlock(&driver->md_session_lock);
+
+ if (!param)
+ return;
+
+ if (!param->peripheral_mask) {
+ DIAG_LOG(DIAG_DEBUG_USERSPACE,
+ "asking for mode switch with no peripheral mask set\n");
+ return;
+ }
+
+ switch (param->req_mode) {
+ case CALLBACK_MODE:
+ case UART_MODE:
+ case SOCKET_MODE:
+ case MEMORY_DEVICE_MODE:
+ new_mode = DIAG_MEMORY_DEVICE_MODE;
+ break;
+ case USB_MODE:
+ new_mode = DIAG_USB_MODE;
+ break;
+ default:
+ DIAG_LOG(DIAG_DEBUG_USERSPACE,
+ "Request to switch to invalid mode: %d\n",
+ param->req_mode);
+ return;
+ }
+ if ((new_mode == DIAG_USB_MODE) && diag_mask_clear_param)
+ diag_clear_masks(pid);
+
+}
+
static int diag_switch_logging(struct diag_logging_mode_param_t *param)
{
int new_mode, i = 0;
@@ -2500,6 +2539,7 @@
if (copy_from_user((void *)&mode_param, (void __user *)ioarg,
sizeof(mode_param)))
return -EFAULT;
+ diag_switch_logging_clear_mask(&mode_param, current->tgid);
mutex_lock(&driver->diagchar_mutex);
result = diag_switch_logging(&mode_param);
mutex_unlock(&driver->diagchar_mutex);
@@ -2631,6 +2671,7 @@
if (copy_from_user((void *)&mode_param, (void __user *)ioarg,
sizeof(mode_param)))
return -EFAULT;
+ diag_switch_logging_clear_mask(&mode_param, current->tgid);
mutex_lock(&driver->diagchar_mutex);
result = diag_switch_logging(&mode_param);
mutex_unlock(&driver->diagchar_mutex);
@@ -3902,7 +3943,6 @@
non_hdlc_data.len = 0;
mutex_init(&driver->hdlc_disable_mutex);
mutex_init(&driver->diagchar_mutex);
- mutex_init(&driver->diag_maskclear_mutex);
mutex_init(&driver->diag_notifier_mutex);
mutex_init(&driver->diag_file_mutex);
mutex_init(&driver->delayed_rsp_mutex);
diff --git a/drivers/clk/msm/clock-cpu-8939.c b/drivers/clk/msm/clock-cpu-8939.c
index 68ea9a1..dd1745a 100644
--- a/drivers/clk/msm/clock-cpu-8939.c
+++ b/drivers/clk/msm/clock-cpu-8939.c
@@ -230,19 +230,31 @@
static struct clk *logical_cpu_to_clk(int cpu)
{
- struct device_node *cpu_node = of_get_cpu_node(cpu, NULL);
- u32 reg;
+ struct device_node *cpu_node;
+ const u32 *cell;
+ u64 hwid;
- /* CPU 0/1/2/3 --> a53_bc_clk and mask = 0x103
- * CPU 4/5/6/7 --> a53_lc_clk and mask = 0x3
- */
- if (cpu_node && !of_property_read_u32(cpu_node, "reg", ®)) {
- if ((reg | a53_bc_clk.cpu_reg_mask) == a53_bc_clk.cpu_reg_mask)
- return &a53_lc_clk.c;
- if ((reg | a53_lc_clk.cpu_reg_mask) == a53_lc_clk.cpu_reg_mask)
- return &a53_bc_clk.c;
+ cpu_node = of_get_cpu_node(cpu, NULL);
+ if (!cpu_node)
+ goto fail;
+
+ cell = of_get_property(cpu_node, "reg", NULL);
+ if (!cell) {
+ pr_err("%s: missing reg property\n", cpu_node->full_name);
+ goto fail;
}
+ /*
+ * CPU 0/1/2/3 --> a53_bc_clk and mask = 0x103
+ * CPU 4/5/6/7 --> a53_lc_clk and mask = 0x3
+ */
+ hwid = of_read_number(cell, of_n_addr_cells(cpu_node));
+ if ((hwid | a53_bc_clk.cpu_reg_mask) == a53_bc_clk.cpu_reg_mask)
+ return &a53_lc_clk.c;
+ if ((hwid | a53_lc_clk.cpu_reg_mask) == a53_lc_clk.cpu_reg_mask)
+ return &a53_bc_clk.c;
+
+fail:
return NULL;
}
@@ -477,6 +489,11 @@
struct dev_pm_opp *oppl;
int j = 1;
+ if (!cpudev) {
+ pr_warn("clock-cpu: NULL CPU device\n");
+ return -ENODEV;
+ }
+
rcu_read_lock();
/* Check if the regulator driver has already populated OPP tables */
oppl = dev_pm_opp_find_freq_exact(vregdev, 2, true);
diff --git a/drivers/clk/msm/clock-cpu-8953.c b/drivers/clk/msm/clock-cpu-8953.c
index c771755..4ba2543 100644
--- a/drivers/clk/msm/clock-cpu-8953.c
+++ b/drivers/clk/msm/clock-cpu-8953.c
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2015-2017, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2015-2018, 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
@@ -466,18 +466,27 @@
static struct clk *logical_cpu_to_clk(int cpu)
{
- struct device_node *cpu_node = of_get_cpu_node(cpu, NULL);
- u32 reg;
+ struct device_node *cpu_node;
+ const u32 *cell;
+ u64 hwid;
- if (cpu_node && !of_property_read_u32(cpu_node, "reg", ®)) {
- if ((reg | a53_pwr_clk.cpu_reg_mask) ==
- a53_pwr_clk.cpu_reg_mask)
- return &a53_pwr_clk.c;
- if ((reg | a53_perf_clk.cpu_reg_mask) ==
- a53_perf_clk.cpu_reg_mask)
- return &a53_perf_clk.c;
+ cpu_node = of_get_cpu_node(cpu, NULL);
+ if (!cpu_node)
+ goto fail;
+
+ cell = of_get_property(cpu_node, "reg", NULL);
+ if (!cell) {
+ pr_err("%s: missing reg property\n", cpu_node->full_name);
+ goto fail;
}
+ hwid = of_read_number(cell, of_n_addr_cells(cpu_node));
+ if ((hwid | a53_pwr_clk.cpu_reg_mask) == a53_pwr_clk.cpu_reg_mask)
+ return &a53_pwr_clk.c;
+ if ((hwid | a53_perf_clk.cpu_reg_mask) == a53_perf_clk.cpu_reg_mask)
+ return &a53_perf_clk.c;
+
+fail:
return NULL;
}
@@ -490,6 +499,11 @@
bool first = true;
int j = 1;
+ if (!dev) {
+ pr_warn("clock-cpu: NULL CPU device\n");
+ return -ENODEV;
+ }
+
while (1) {
rate = c->fmax[j++];
level = find_vdd_level(c, rate);
diff --git a/drivers/clk/msm/clock-cpu-sdm632.c b/drivers/clk/msm/clock-cpu-sdm632.c
index 357c49c..58a2520 100644
--- a/drivers/clk/msm/clock-cpu-sdm632.c
+++ b/drivers/clk/msm/clock-cpu-sdm632.c
@@ -528,18 +528,28 @@
static struct clk *logical_cpu_to_clk(int cpu)
{
- struct device_node *cpu_node = of_get_cpu_node(cpu, NULL);
- u32 reg;
+ struct device_node *cpu_node;
+ const u32 *cell;
+ u64 hwid;
- if (cpu_node && !of_property_read_u32(cpu_node, "reg", ®)) {
- if ((reg | pwr_clk.cpu_reg_mask) ==
- pwr_clk.cpu_reg_mask)
- return &pwr_clk.c;
- if ((reg | perf_clk.cpu_reg_mask) ==
- perf_clk.cpu_reg_mask)
- return &perf_clk.c;
+ cpu_node = of_get_cpu_node(cpu, NULL);
+ if (!cpu_node)
+ goto fail;
+
+ cell = of_get_property(cpu_node, "reg", NULL);
+ if (!cell) {
+ pr_err("%s: missing reg property\n", cpu_node->full_name);
+ goto fail;
}
+ hwid = of_read_number(cell, of_n_addr_cells(cpu_node));
+ if ((hwid | pwr_clk.cpu_reg_mask) == pwr_clk.cpu_reg_mask)
+ return &pwr_clk.c;
+
+ if ((hwid | perf_clk.cpu_reg_mask) == perf_clk.cpu_reg_mask)
+ return &perf_clk.c;
+
+fail:
return NULL;
}
@@ -676,6 +686,11 @@
long ret, uv, corner;
int j = 1;
+ if (!cpudev) {
+ pr_warn("clock-cpu: NULL CPU device\n");
+ return -ENODEV;
+ }
+
while (1) {
rate = c->fmax[j++];
diff --git a/drivers/clk/msm/clock-gcc-8952.c b/drivers/clk/msm/clock-gcc-8952.c
index 7da217c..3c9fc0e 100644
--- a/drivers/clk/msm/clock-gcc-8952.c
+++ b/drivers/clk/msm/clock-gcc-8952.c
@@ -4512,13 +4512,6 @@
clk_prepare_enable(&pnoc_keepalive_a_clk.c);
clk_prepare_enable(&xo_a_clk_src.c);
- clk_prepare_enable(&gcc_blsp1_ahb_clk.c);
- clk_prepare_enable(&gcc_blsp2_ahb_clk.c);
- clk_prepare_enable(&gcc_blsp1_uart2_apps_clk.c);
- clk_prepare_enable(&gcc_blsp1_uart1_apps_clk.c);
- clk_prepare_enable(&gcc_bimc_gpu_clk.c);
- clk_prepare_enable(&sysmmnoc_msmbus_a_clk.c);
- clk_prepare_enable(&sysmmnoc_a_clk.c);
if (!compat_bin && !compat_bin3) {
/* Configure Sleep and Wakeup cycles for GMEM clock */
diff --git a/drivers/clk/qcom/gcc-sdxpoorwills.c b/drivers/clk/qcom/gcc-sdxpoorwills.c
index 4050683..b52002f 100644
--- a/drivers/clk/qcom/gcc-sdxpoorwills.c
+++ b/drivers/clk/qcom/gcc-sdxpoorwills.c
@@ -40,6 +40,7 @@
#define F(f, s, h, m, n) { (f), (s), (2 * (h) - 1), (m), (n) }
static DEFINE_VDD_REGULATORS(vdd_cx, VDD_CX_NUM, 1, vdd_corner);
+static DEFINE_VDD_REGULATORS(vdd_cx_ao, VDD_CX_NUM, 1, vdd_corner);
enum {
P_BI_TCXO,
@@ -64,6 +65,13 @@
"core_bi_pll_test_se",
};
+static const char * const gcc_parent_names_ao_0[] = {
+ "bi_tcxo_ao",
+ "gpll0",
+ "gpll0_out_even",
+ "core_bi_pll_test_se",
+};
+
static const struct parent_map gcc_parent_map_1[] = {
{ P_BI_TCXO, 0 },
{ P_CORE_BI_PLL_TEST_SE, 7 },
@@ -219,7 +227,6 @@
.name = "gcc_blsp1_qup1_i2c_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP3(
MIN, 9600000,
@@ -250,7 +257,6 @@
.name = "gcc_blsp1_qup1_spi_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -270,7 +276,6 @@
.name = "gcc_blsp1_qup2_i2c_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP3(
MIN, 9600000,
@@ -289,7 +294,6 @@
.name = "gcc_blsp1_qup2_spi_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -309,7 +313,6 @@
.name = "gcc_blsp1_qup3_i2c_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP3(
MIN, 9600000,
@@ -328,7 +331,6 @@
.name = "gcc_blsp1_qup3_spi_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -348,7 +350,6 @@
.name = "gcc_blsp1_qup4_i2c_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP3(
MIN, 9600000,
@@ -367,7 +368,6 @@
.name = "gcc_blsp1_qup4_spi_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -418,7 +418,6 @@
.name = "gcc_blsp1_uart1_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -438,7 +437,6 @@
.name = "gcc_blsp1_uart2_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -458,7 +456,6 @@
.name = "gcc_blsp1_uart3_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -478,7 +475,6 @@
.name = "gcc_blsp1_uart4_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 9600000,
@@ -490,9 +486,6 @@
static const struct freq_tbl ftbl_gcc_cpuss_ahb_clk_src[] = {
F(19200000, P_BI_TCXO, 1, 0, 0),
- F(50000000, P_GPLL0_OUT_EVEN, 6, 0, 0),
- F(100000000, P_GPLL0_OUT_MAIN, 6, 0, 0),
- F(133333333, P_GPLL0_OUT_MAIN, 4.5, 0, 0),
{ }
};
@@ -504,21 +497,16 @@
.freq_tbl = ftbl_gcc_cpuss_ahb_clk_src,
.clkr.hw.init = &(struct clk_init_data){
.name = "gcc_cpuss_ahb_clk_src",
- .parent_names = gcc_parent_names_0,
+ .parent_names = gcc_parent_names_ao_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
- VDD_CX_FMAX_MAP4(
- MIN, 19200000,
- LOWER, 50000000,
- NOMINAL, 100000000,
- HIGH, 133333333),
+ VDD_CX_FMAX_MAP1_AO(
+ MIN, 19200000),
},
};
static const struct freq_tbl ftbl_gcc_cpuss_rbcpr_clk_src[] = {
F(19200000, P_BI_TCXO, 1, 0, 0),
- F(50000000, P_GPLL0_OUT_MAIN, 12, 0, 0),
{ }
};
@@ -530,13 +518,11 @@
.freq_tbl = ftbl_gcc_cpuss_rbcpr_clk_src,
.clkr.hw.init = &(struct clk_init_data){
.name = "gcc_cpuss_rbcpr_clk_src",
- .parent_names = gcc_parent_names_0,
+ .parent_names = gcc_parent_names_ao_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
- VDD_CX_FMAX_MAP2(
- MIN, 19200000,
- NOMINAL, 50000000),
+ VDD_CX_FMAX_MAP1_AO(
+ MIN, 19200000),
},
};
@@ -561,7 +547,6 @@
.name = "gcc_emac_clk_src",
.parent_names = gcc_parent_names_4,
.num_parents = 5,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 19200000,
@@ -571,17 +556,25 @@
},
};
+static const struct freq_tbl ftbl_gcc_emac_ptp_clk_src[] = {
+ F(19200000, P_BI_TCXO, 1, 0, 0),
+ F(25000000, P_GPLL0_OUT_EVEN, 12, 0, 0),
+ F(50000000, P_GPLL0_OUT_EVEN, 6, 0, 0),
+ F(125000000, P_GPLL4_OUT_EVEN, 4, 0, 0),
+ F(250000000, P_GPLL4_OUT_EVEN, 2, 0, 0),
+ { }
+};
+
static struct clk_rcg2 gcc_emac_ptp_clk_src = {
.cmd_rcgr = 0x47038,
.mnd_width = 0,
.hid_width = 5,
.parent_map = gcc_parent_map_4,
- .freq_tbl = ftbl_gcc_emac_clk_src,
+ .freq_tbl = ftbl_gcc_emac_ptp_clk_src,
.clkr.hw.init = &(struct clk_init_data){
.name = "gcc_emac_ptp_clk_src",
.parent_names = gcc_parent_names_4,
.num_parents = 5,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 19200000,
@@ -610,7 +603,6 @@
.name = "gcc_gp1_clk_src",
.parent_names = gcc_parent_names_2,
.num_parents = 5,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 19200000,
@@ -630,7 +622,6 @@
.name = "gcc_gp2_clk_src",
.parent_names = gcc_parent_names_2,
.num_parents = 5,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 19200000,
@@ -650,7 +641,6 @@
.name = "gcc_gp3_clk_src",
.parent_names = gcc_parent_names_2,
.num_parents = 5,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 19200000,
@@ -675,7 +665,6 @@
.name = "gcc_pcie_aux_phy_clk_src",
.parent_names = gcc_parent_names_3,
.num_parents = 3,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP1(
MIN, 19200000),
@@ -698,7 +687,6 @@
.name = "gcc_pcie_phy_refgen_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP2(
MIN, 19200000,
@@ -723,7 +711,6 @@
.name = "gcc_pdm2_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP3(
MIN, 9600000,
@@ -742,7 +729,6 @@
.name = "gcc_sdcc1_apps_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP4(
MIN, 19200000,
@@ -762,7 +748,6 @@
.name = "gcc_spmi_fetcher_clk_src",
.parent_names = gcc_parent_names_1,
.num_parents = 2,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP1(
MIN, 19200000),
@@ -788,7 +773,6 @@
.name = "gcc_usb30_master_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP5(
MIN, 50000000,
@@ -816,7 +800,6 @@
.name = "gcc_usb30_mock_utmi_clk_src",
.parent_names = gcc_parent_names_0,
.num_parents = 4,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP3(
MIN, 19200000,
@@ -841,7 +824,6 @@
.name = "gcc_usb3_phy_aux_clk_src",
.parent_names = gcc_parent_names_3,
.num_parents = 3,
- .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
VDD_CX_FMAX_MAP1(
MIN, 19200000),
@@ -1884,6 +1866,14 @@
return PTR_ERR(vdd_cx.regulator[0]);
}
+ vdd_cx_ao.regulator[0] = devm_regulator_get(&pdev->dev, "vdd_cx_ao");
+ if (IS_ERR(vdd_cx_ao.regulator[0])) {
+ if (!(PTR_ERR(vdd_cx_ao.regulator[0]) == -EPROBE_DEFER))
+ dev_err(&pdev->dev,
+ "Unable to get vdd_cx_ao regulator\n");
+ return PTR_ERR(vdd_cx_ao.regulator[0]);
+ }
+
/* Register the dummy measurement clocks */
for (i = 0; i < ARRAY_SIZE(gcc_sdxpoorwills_hws); i++) {
clk = devm_clk_register(&pdev->dev, gcc_sdxpoorwills_hws[i]);
@@ -1922,6 +1912,15 @@
}
module_exit(gcc_sdxpoorwills_exit);
+static int gcc_cpuss_ahb_clk_update_rate(void)
+{
+ clk_set_rate(gcc_cpuss_ahb_clk.clkr.hw.clk, 19200000);
+ clk_set_rate(gcc_sys_noc_cpuss_ahb_clk.clkr.hw.clk, 19200000);
+
+ return 0;
+}
+late_initcall(gcc_cpuss_ahb_clk_update_rate);
+
MODULE_DESCRIPTION("QTI GCC SDXPOORWILLS Driver");
MODULE_LICENSE("GPL v2");
MODULE_ALIAS("platform:gcc-sdxpoorwills");
diff --git a/drivers/cpuidle/lpm-levels-of.c b/drivers/cpuidle/lpm-levels-of.c
index 61c0ae8..ad0be45 100644
--- a/drivers/cpuidle/lpm-levels-of.c
+++ b/drivers/cpuidle/lpm-levels-of.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2018, 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
@@ -178,8 +178,8 @@
struct kernel_param kp;
struct lpm_level_avail *avail = get_avail_ptr(kobj, attr);
- if (!avail)
- pr_info("Error\n");
+ if (WARN_ON(!avail))
+ return -EINVAL;
kp.arg = &avail->latency_us;
@@ -197,8 +197,15 @@
{
int ret = 0;
struct kernel_param kp;
+ struct lpm_level_avail *avail = get_avail_ptr(kobj, attr);
- kp.arg = get_enabled_ptr(attr, get_avail_ptr(kobj, attr));
+ if (WARN_ON(!avail))
+ return -EINVAL;
+
+ kp.arg = get_enabled_ptr(attr, avail);
+ if (WARN_ON(!kp.arg))
+ return -EINVAL;
+
ret = param_get_bool(buf, &kp);
if (ret > 0) {
strlcat(buf, "\n", PAGE_SIZE);
@@ -453,6 +460,17 @@
if (ret)
goto fail;
+ key = "qcom,disable-prediction";
+ c->lpm_prediction = !(of_property_read_bool(node, key));
+
+ if (c->lpm_prediction) {
+ key = "qcom,clstr-tmr-add";
+ ret = of_property_read_u32(node, key, &c->tmr_add);
+ if (ret || c->tmr_add < TIMER_ADD_LOW ||
+ c->tmr_add > TIMER_ADD_HIGH)
+ c->tmr_add = DEFAULT_TIMER_ADD;
+ }
+
/* Set default_level to 0 as default */
c->default_level = 0;
@@ -713,8 +731,28 @@
if (ret)
goto failed_parse_params;
- key = "qcom,use-prediction";
- cpu->lpm_prediction = of_property_read_bool(node, key);
+ key = "qcom,disable-prediction";
+ cpu->lpm_prediction = !(of_property_read_bool(node, key));
+
+ if (cpu->lpm_prediction) {
+ key = "qcom,ref-stddev";
+ ret = of_property_read_u32(node, key, &cpu->ref_stddev);
+ if (ret || cpu->ref_stddev < STDDEV_LOW ||
+ cpu->ref_stddev > STDDEV_HIGH)
+ cpu->ref_stddev = DEFAULT_STDDEV;
+
+ key = "qcom,tmr-add";
+ ret = of_property_read_u32(node, key, &cpu->tmr_add);
+ if (ret || cpu->tmr_add < TIMER_ADD_LOW ||
+ cpu->tmr_add > TIMER_ADD_HIGH)
+ cpu->tmr_add = DEFAULT_TIMER_ADD;
+
+ key = "qcom,ref-premature-cnt";
+ ret = of_property_read_u32(node, key, &cpu->ref_premature_cnt);
+ if (ret || cpu->ref_premature_cnt < PREMATURE_CNT_LOW ||
+ cpu->ref_premature_cnt > PREMATURE_CNT_HIGH)
+ cpu->ref_premature_cnt = DEFAULT_PREMATURE_CNT;
+ }
key = "parse_cpu";
ret = parse_cpu(node, cpu);
diff --git a/drivers/cpuidle/lpm-levels.c b/drivers/cpuidle/lpm-levels.c
index 013b0c8..69ac505 100644
--- a/drivers/cpuidle/lpm-levels.c
+++ b/drivers/cpuidle/lpm-levels.c
@@ -92,15 +92,6 @@
static bool lpm_prediction = true;
module_param_named(lpm_prediction, lpm_prediction, bool, 0664);
-static uint32_t ref_stddev = 500;
-module_param_named(ref_stddev, ref_stddev, uint, 0664);
-
-static uint32_t tmr_add = 1000;
-module_param_named(tmr_add, tmr_add, uint, 0664);
-
-static uint32_t ref_premature_cnt = 1;
-module_param_named(ref_premature_cnt, ref_premature_cnt, uint, 0664);
-
static uint32_t bias_hyst;
module_param_named(bias_hyst, bias_hyst, uint, 0664);
@@ -496,7 +487,7 @@
* ignore one maximum sample and retry
*/
if (((avg > stddev * 6) && (divisor >= (MAXSAMPLES - 1)))
- || stddev <= ref_stddev) {
+ || stddev <= cpu->ref_stddev) {
history->stime = ktime_to_us(ktime_get()) + avg;
return avg;
} else if (divisor > (MAXSAMPLES - 1)) {
@@ -521,7 +512,7 @@
total += history->resi[i];
}
}
- if (failed >= ref_premature_cnt) {
+ if (failed >= cpu->ref_premature_cnt) {
*idx_restrict = j;
do_div(total, failed);
for (i = 0; i < j; i++) {
@@ -545,8 +536,9 @@
static inline void invalidate_predict_history(struct cpuidle_device *dev)
{
struct lpm_history *history = &per_cpu(hist, dev->cpu);
+ struct lpm_cpu *lpm_cpu = per_cpu(cpu_lpm, dev->cpu);
- if (!lpm_prediction)
+ if (!lpm_prediction || !lpm_cpu->lpm_prediction)
return;
if (history->hinvalid) {
@@ -561,8 +553,9 @@
struct lpm_history *history;
int i;
unsigned int cpu;
+ struct lpm_cpu *lpm_cpu = per_cpu(cpu_lpm, raw_smp_processor_id());
- if (!lpm_prediction)
+ if (!lpm_prediction || !lpm_cpu->lpm_prediction)
return;
for_each_possible_cpu(cpu) {
@@ -681,8 +674,8 @@
if ((predicted || (idx_restrict != (cpu->nlevels + 1)))
&& ((best_level >= 0)
&& (best_level < (cpu->nlevels-1)))) {
- htime = predicted + tmr_add;
- if (htime == tmr_add)
+ htime = predicted + cpu->tmr_add;
+ if (htime == cpu->tmr_add)
htime = idx_restrict_time;
else if (htime > max_residency[best_level])
htime = max_residency[best_level];
@@ -746,14 +739,14 @@
next_event.tv64 = next_event_c->tv64;
}
- if (from_idle && lpm_prediction) {
+ if (from_idle && lpm_prediction && cluster->lpm_prediction) {
history = &per_cpu(hist, cpu);
if (history->stime && (history->stime < prediction))
prediction = history->stime;
}
}
- if (from_idle && lpm_prediction) {
+ if (from_idle && lpm_prediction && cluster->lpm_prediction) {
if (prediction > ktime_to_us(ktime_get()))
*pred_time = prediction - ktime_to_us(ktime_get());
}
@@ -772,7 +765,7 @@
struct cluster_history *history = &cluster->history;
int64_t cur_time = ktime_to_us(ktime_get());
- if (!lpm_prediction)
+ if (!lpm_prediction || !cluster->lpm_prediction)
return 0;
if (history->hinvalid) {
@@ -847,7 +840,7 @@
struct lpm_cluster *cluster =
container_of(history, struct lpm_cluster, history);
- if (!lpm_prediction)
+ if (!lpm_prediction || !cluster->lpm_prediction)
return;
if ((history->entry_idx == -1) || (history->entry_idx == idx)) {
@@ -908,7 +901,7 @@
struct lpm_cluster *cluster = lpm_root_node;
struct list_head *list;
- if (!lpm_prediction)
+ if (!lpm_prediction || !cluster->lpm_prediction)
return;
clear_cl_history_each(&cluster->history);
@@ -955,17 +948,6 @@
latency_us = pm_qos_request_for_cpumask(PM_QOS_CPU_DMA_LATENCY,
&mask);
- /*
- * If atleast one of the core in the cluster is online, the cluster
- * low power modes should be determined by the idle characteristics
- * even if the last core enters the low power mode as a part of
- * hotplug.
- */
-
- if (!from_idle && num_online_cpus() > 1 &&
- cpumask_intersects(&cluster->child_cpus, cpu_online_mask))
- from_idle = true;
-
for (i = 0; i < cluster->nlevels; i++) {
struct lpm_cluster_level *level = &cluster->levels[i];
struct power_params *pwr_params = &level->pwr;
@@ -1045,14 +1027,24 @@
cluster->child_cpus.bits[0], from_idle);
lpm_stats_cluster_enter(cluster->stats, idx);
- if (from_idle && lpm_prediction)
+ if (from_idle && lpm_prediction && cluster->lpm_prediction)
update_cluster_history_time(&cluster->history, idx,
ktime_to_us(ktime_get()));
}
if (level->notify_rpm) {
+ /*
+ * Print the clocks which are enabled during system suspend
+ * This debug information is useful to know which are the
+ * clocks that are enabled and preventing the system level
+ * LPMs(XO and Vmin).
+ */
+ if (!from_idle)
+ clock_debug_print_enabled(true);
+
cpu = get_next_online_cpu(from_idle);
cpumask_copy(&cpumask, cpumask_of(cpu));
+
clear_predict_history();
clear_cl_predict_history();
if (sys_pm_ops && sys_pm_ops->enter)
@@ -1067,7 +1059,8 @@
if (predicted && (idx < (cluster->nlevels - 1))) {
struct power_params *pwr_params = &cluster->levels[idx].pwr;
- clusttimer_start(cluster, pwr_params->max_residency + tmr_add);
+ clusttimer_start(cluster, pwr_params->max_residency +
+ cluster->tmr_add);
}
return 0;
@@ -1121,7 +1114,8 @@
&cluster->levels[0].pwr;
clusttimer_start(cluster,
- pwr_params->max_residency + tmr_add);
+ pwr_params->max_residency +
+ cluster->tmr_add);
goto failed;
}
@@ -1336,8 +1330,9 @@
{
struct lpm_history *history = &per_cpu(hist, dev->cpu);
uint32_t tmr = 0;
+ struct lpm_cpu *lpm_cpu = per_cpu(cpu_lpm, dev->cpu);
- if (!lpm_prediction)
+ if (!lpm_prediction || !lpm_cpu->lpm_prediction)
return;
if (history->htmr_wkup) {
@@ -1395,13 +1390,37 @@
update_history(dev, idx);
trace_cpu_idle_exit(idx, success);
local_irq_enable();
- if (lpm_prediction) {
+ if (lpm_prediction && cpu->lpm_prediction) {
histtimer_cancel();
clusttimer_cancel();
}
return idx;
}
+static void lpm_cpuidle_freeze(struct cpuidle_device *dev,
+ struct cpuidle_driver *drv, int idx)
+{
+ struct lpm_cpu *cpu = per_cpu(cpu_lpm, dev->cpu);
+ const struct cpumask *cpumask = get_cpu_mask(dev->cpu);
+
+ for (; idx >= 0; idx--) {
+ if (lpm_cpu_mode_allow(dev->cpu, idx, false))
+ break;
+ }
+ if (idx < 0) {
+ pr_err("Failed suspend\n");
+ return;
+ }
+
+ cpu_prepare(cpu, idx, true);
+ cluster_prepare(cpu->parent, cpumask, idx, false, 0);
+
+ psci_enter_sleep(cpu, idx, false);
+
+ cluster_unprepare(cpu->parent, cpumask, idx, false, 0);
+ cpu_unprepare(cpu, idx, true);
+}
+
#ifdef CONFIG_CPU_IDLE_MULTIPLE_DRIVERS
static int cpuidle_register_cpu(struct cpuidle_driver *drv,
struct cpumask *mask)
@@ -1489,6 +1508,8 @@
st->power_usage = cpu_level->pwr.ss_power;
st->target_residency = 0;
st->enter = lpm_cpuidle_enter;
+ if (i == lpm_cpu->nlevels - 1)
+ st->enter_freeze = lpm_cpuidle_freeze;
}
lpm_cpu->drv->state_count = lpm_cpu->nlevels;
@@ -1623,14 +1644,6 @@
cpu_prepare(lpm_cpu, idx, false);
cluster_prepare(cluster, cpumask, idx, false, 0);
- /*
- * Print the clocks which are enabled during system suspend
- * This debug information is useful to know which are the
- * clocks that are enabled and preventing the system level
- * LPMs(XO and Vmin).
- */
- clock_debug_print_enabled(true);
-
psci_enter_sleep(lpm_cpu, idx, false);
cluster_unprepare(cluster, cpumask, idx, false, 0);
@@ -1645,6 +1658,11 @@
.wake = lpm_suspend_wake,
};
+static const struct platform_freeze_ops lpm_freeze_ops = {
+ .prepare = lpm_suspend_prepare,
+ .restore = lpm_suspend_wake,
+};
+
static int lpm_probe(struct platform_device *pdev)
{
int ret;
@@ -1671,6 +1689,7 @@
* how late lpm_levels gets initialized.
*/
suspend_set_ops(&lpm_suspend_ops);
+ freeze_set_ops(&lpm_freeze_ops);
hrtimer_init(&lpm_hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
hrtimer_init(&histtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
cluster_timer_init(lpm_root_node);
diff --git a/drivers/cpuidle/lpm-levels.h b/drivers/cpuidle/lpm-levels.h
index 1ff69c8..0b598c0 100644
--- a/drivers/cpuidle/lpm-levels.h
+++ b/drivers/cpuidle/lpm-levels.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2018, 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,6 +16,15 @@
#define NR_LPM_LEVELS 8
#define MAXSAMPLES 5
#define CLUST_SMPL_INVLD_TIME 40000
+#define DEFAULT_PREMATURE_CNT 3
+#define DEFAULT_STDDEV 100
+#define DEFAULT_TIMER_ADD 100
+#define TIMER_ADD_LOW 100
+#define TIMER_ADD_HIGH 1500
+#define STDDEV_LOW 100
+#define STDDEV_HIGH 1000
+#define PREMATURE_CNT_LOW 1
+#define PREMATURE_CNT_HIGH 5
struct power_params {
uint32_t latency_us; /* Enter + Exit latency */
@@ -43,6 +52,9 @@
int nlevels;
unsigned int psci_mode_shift;
unsigned int psci_mode_mask;
+ uint32_t ref_stddev;
+ uint32_t ref_premature_cnt;
+ uint32_t tmr_add;
bool lpm_prediction;
struct cpuidle_driver *drv;
struct lpm_cluster *parent;
@@ -97,6 +109,8 @@
int min_child_level;
int default_level;
int last_level;
+ uint32_t tmr_add;
+ bool lpm_prediction;
struct list_head cpu;
spinlock_t sync_lock;
struct cpumask child_cpus;
diff --git a/drivers/crypto/msm/ice.c b/drivers/crypto/msm/ice.c
index 6fa91ae..3aa75aa 100644
--- a/drivers/crypto/msm/ice.c
+++ b/drivers/crypto/msm/ice.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2018, 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
@@ -74,6 +74,9 @@
#define QCOM_ICE_MAX_BIST_CHECK_COUNT 100
#define QCOM_ICE_UFS 10
#define QCOM_ICE_SDCC 20
+#define QCOM_ICE_ENCRYPT 0x1
+#define QCOM_ICE_DECRYPT 0x2
+#define QCOM_SECT_LEN_IN_BYTE 512
struct ice_clk_info {
struct list_head list;
@@ -123,6 +126,11 @@
ktime_t ice_reset_complete_time;
};
+static int ice_fde_flag;
+static unsigned long userdata_start;
+static unsigned long userdata_end;
+static struct ice_crypto_setting ice_data;
+
static int qti_ice_setting_config(struct request *req,
struct platform_device *pdev,
struct ice_crypto_setting *crypto_data,
@@ -149,20 +157,50 @@
memcpy(&setting->crypto_data, crypto_data,
sizeof(setting->crypto_data));
- if (rq_data_dir(req) == WRITE)
+ if (rq_data_dir(req) == WRITE &&
+ (ice_fde_flag & QCOM_ICE_ENCRYPT))
setting->encr_bypass = false;
- else if (rq_data_dir(req) == READ)
+ else if (rq_data_dir(req) == READ &&
+ (ice_fde_flag & QCOM_ICE_DECRYPT))
setting->decr_bypass = false;
else {
/* Should I say BUG_ON */
setting->encr_bypass = true;
setting->decr_bypass = true;
+ pr_debug("%s direction unknown", __func__);
}
}
return 0;
}
+void qcom_ice_set_fde_flag(int flag)
+{
+ ice_fde_flag = flag;
+ pr_debug("%s read_write setting %d\n", __func__, ice_fde_flag);
+}
+EXPORT_SYMBOL(qcom_ice_set_fde_flag);
+
+int qcom_ice_set_fde_conf(sector_t s_sector, sector_t size,
+ int index, int mode)
+{
+ userdata_start = s_sector;
+ userdata_end = s_sector + size;
+ if (INT_MAX - s_sector < size) {
+ WARN_ON(1);
+ return -EINVAL;
+ }
+ ice_data.key_index = index;
+ ice_data.algo_mode = mode;
+ ice_data.key_size = ICE_CRYPTO_KEY_SIZE_256;
+ ice_data.key_mode = ICE_CRYPTO_USE_LUT_SW_KEY;
+
+ pr_debug("%s sector info set start %lu end %lu\n", __func__,
+ userdata_start, userdata_end);
+ return 0;
+}
+EXPORT_SYMBOL(qcom_ice_set_fde_conf);
+
static int qcom_ice_enable_clocks(struct ice_device *, bool);
#ifdef CONFIG_MSM_BUS_SCALING
@@ -1445,11 +1483,10 @@
struct request *req,
struct ice_data_setting *setting, bool async)
{
- struct ice_crypto_setting *crypto_data;
struct ice_crypto_setting pfk_crypto_data = {0};
- union map_info *info;
int ret = 0;
bool is_pfe = false;
+ sector_t data_size;
if (!pdev || !req || !setting) {
pr_err("%s: Invalid params passed\n", __func__);
@@ -1484,28 +1521,22 @@
&pfk_crypto_data, setting);
}
+ if (ice_fde_flag == 0)
+ return 0;
+
+ if ((req->__sector >= userdata_start) &&
+ (req->__sector < userdata_end)) {
/*
- * info field in req->end_io_data could be used by mulitple dm or
- * non-dm entities. To ensure that we are running operation on dm
- * based request, check BIO_DONT_FREE flag
+ * Ugly hack to address non-block-size aligned userdata end address in
+ * eMMC based devices.
*/
- if (bio_flagged(req->bio, BIO_INLINECRYPT)) {
- info = dm_get_rq_mapinfo(req);
- if (!info) {
- pr_debug("%s info not available in request\n",
- __func__);
+ data_size = req->__data_len/QCOM_SECT_LEN_IN_BYTE;
+
+ if ((req->__sector + data_size) > userdata_end)
return 0;
- }
-
- crypto_data = (struct ice_crypto_setting *)info->ptr;
- if (!crypto_data) {
- pr_err("%s crypto_data not available in request\n",
- __func__);
- return -EINVAL;
- }
-
- return qti_ice_setting_config(req, pdev,
- crypto_data, setting);
+ else
+ return qti_ice_setting_config(req, pdev,
+ &ice_data, setting);
}
/*
diff --git a/drivers/devfreq/devfreq.c b/drivers/devfreq/devfreq.c
index a7df9cb..3357aaf 100644
--- a/drivers/devfreq/devfreq.c
+++ b/drivers/devfreq/devfreq.c
@@ -520,6 +520,7 @@
devfreq->profile->exit(devfreq->dev.parent);
mutex_destroy(&devfreq->lock);
+ mutex_destroy(&devfreq->sysfs_lock);
kfree(devfreq);
}
@@ -576,6 +577,7 @@
}
mutex_init(&devfreq->lock);
+ mutex_init(&devfreq->sysfs_lock);
mutex_lock(&devfreq->lock);
devfreq->dev.parent = dev;
devfreq->dev.class = devfreq_class;
@@ -972,12 +974,13 @@
goto out;
}
+ mutex_lock(&df->sysfs_lock);
if (df->governor) {
ret = df->governor->event_handler(df, DEVFREQ_GOV_STOP, NULL);
if (ret) {
dev_warn(dev, "%s: Governor %s not stopped(%d)\n",
__func__, df->governor->name, ret);
- goto out;
+ goto gov_stop_out;
}
}
prev_gov = df->governor;
@@ -995,6 +998,9 @@
NULL);
}
}
+
+gov_stop_out:
+ mutex_unlock(&df->sysfs_lock);
out:
mutex_unlock(&devfreq_list_lock);
@@ -1089,8 +1095,10 @@
if (ret != 1)
return -EINVAL;
+ mutex_lock(&df->sysfs_lock);
df->governor->event_handler(df, DEVFREQ_GOV_INTERVAL, &value);
ret = count;
+ mutex_unlock(&df->sysfs_lock);
return ret;
}
@@ -1108,6 +1116,7 @@
if (ret != 1)
return -EINVAL;
+ mutex_lock(&df->sysfs_lock);
mutex_lock(&df->lock);
max = df->max_freq;
if (value && max && value > max) {
@@ -1120,6 +1129,7 @@
ret = count;
unlock:
mutex_unlock(&df->lock);
+ mutex_unlock(&df->sysfs_lock);
return ret;
}
@@ -1135,6 +1145,7 @@
if (ret != 1)
return -EINVAL;
+ mutex_lock(&df->sysfs_lock);
mutex_lock(&df->lock);
min = df->min_freq;
if (value && min && value < min) {
@@ -1147,6 +1158,7 @@
ret = count;
unlock:
mutex_unlock(&df->lock);
+ mutex_unlock(&df->sysfs_lock);
return ret;
}
diff --git a/drivers/gpu/drm/msm/dp/dp_aux.c b/drivers/gpu/drm/msm/dp/dp_aux.c
index 630b5fb..8952fc9 100644
--- a/drivers/gpu/drm/msm/dp/dp_aux.c
+++ b/drivers/gpu/drm/msm/dp/dp_aux.c
@@ -548,7 +548,7 @@
}
ret = dp_aux_cmd_fifo_tx(aux, msg);
- if ((ret < 0) && aux->native && !atomic_read(&aux->aborted)) {
+ if ((ret < 0) && !atomic_read(&aux->aborted)) {
aux->retry_cnt++;
if (!(aux->retry_cnt % retry_count))
aux->catalog->update_aux_cfg(aux->catalog,
diff --git a/drivers/gpu/drm/msm/dp/dp_catalog.c b/drivers/gpu/drm/msm/dp/dp_catalog.c
index 56a41b5..5e73dfa 100644
--- a/drivers/gpu/drm/msm/dp/dp_catalog.c
+++ b/drivers/gpu/drm/msm/dp/dp_catalog.c
@@ -54,17 +54,17 @@
}
static u8 const vm_pre_emphasis[4][4] = {
- {0x00, 0x0B, 0x12, 0xFF}, /* pe0, 0 db */
- {0x00, 0x0A, 0x12, 0xFF}, /* pe1, 3.5 db */
- {0x00, 0x0C, 0xFF, 0xFF}, /* pe2, 6.0 db */
+ {0x00, 0x0B, 0x14, 0xFF}, /* pe0, 0 db */
+ {0x00, 0x0B, 0x12, 0xFF}, /* pe1, 3.5 db */
+ {0x00, 0x0B, 0xFF, 0xFF}, /* pe2, 6.0 db */
{0xFF, 0xFF, 0xFF, 0xFF} /* pe3, 9.5 db */
};
/* voltage swing, 0.2v and 1.0v are not support */
static u8 const vm_voltage_swing[4][4] = {
- {0x07, 0x0F, 0x14, 0xFF}, /* sw0, 0.4v */
- {0x11, 0x1D, 0x1F, 0xFF}, /* sw1, 0.6 v */
- {0x18, 0x1F, 0xFF, 0xFF}, /* sw1, 0.8 v */
+ {0x07, 0x0F, 0x16, 0xFF}, /* sw0, 0.4v */
+ {0x11, 0x1E, 0x1F, 0xFF}, /* sw1, 0.6 v */
+ {0x19, 0x1F, 0xFF, 0xFF}, /* sw1, 0.8 v */
{0xFF, 0xFF, 0xFF, 0xFF} /* sw1, 1.2 v, optional */
};
diff --git a/drivers/gpu/drm/msm/dp/dp_ctrl.c b/drivers/gpu/drm/msm/dp/dp_ctrl.c
index 2e2887e..f2e9085 100644
--- a/drivers/gpu/drm/msm/dp/dp_ctrl.c
+++ b/drivers/gpu/drm/msm/dp/dp_ctrl.c
@@ -130,7 +130,7 @@
ctrl = container_of(dp_ctrl, struct dp_ctrl_private, dp_ctrl);
- if (!ctrl->power_on || atomic_read(&ctrl->aborted)) {
+ if (!ctrl->power_on) {
pr_err("CTRL off, return\n");
return;
}
diff --git a/drivers/gpu/drm/msm/dp/dp_display.c b/drivers/gpu/drm/msm/dp/dp_display.c
index bf903b9..3e5cdc6 100644
--- a/drivers/gpu/drm/msm/dp/dp_display.c
+++ b/drivers/gpu/drm/msm/dp/dp_display.c
@@ -610,6 +610,8 @@
goto end;
}
+ atomic_set(&dp->aborted, 0);
+
dp_display_host_init(dp);
/* check for hpd high and framework ready */
@@ -694,10 +696,10 @@
/* wait for idle state */
cancel_delayed_work(&dp->connect_work);
+ cancel_work(&dp->attention_work);
flush_workqueue(dp->wq);
dp_display_handle_disconnect(dp);
- atomic_set(&dp->aborted, 0);
end:
return rc;
}
@@ -801,6 +803,7 @@
/* wait for idle state */
cancel_delayed_work(&dp->connect_work);
+ cancel_work(&dp->attention_work);
flush_workqueue(dp->wq);
dp_display_handle_disconnect(dp);
diff --git a/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c b/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c
index 1ab1de6..93e364de 100644
--- a/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c
+++ b/drivers/gpu/drm/msm/dsi-staging/dsi_ctrl.c
@@ -275,12 +275,12 @@
switch (op) {
case DSI_CTRL_OP_POWER_STATE_CHANGE:
if (state->power_state == op_state) {
- pr_debug("[%d] No change in state, pwr_state=%d\n",
+ pr_err("[%d] No change in state, pwr_state=%d\n",
dsi_ctrl->cell_index, op_state);
rc = -EINVAL;
} else if (state->power_state == DSI_CTRL_POWER_VREG_ON) {
if (state->vid_engine_state == DSI_CTRL_ENGINE_ON) {
- pr_debug("[%d]State error: op=%d: %d\n",
+ pr_err("[%d]State error: op=%d: %d\n",
dsi_ctrl->cell_index,
op_state,
state->vid_engine_state);
@@ -290,12 +290,12 @@
break;
case DSI_CTRL_OP_CMD_ENGINE:
if (state->cmd_engine_state == op_state) {
- pr_debug("[%d] No change in state, cmd_state=%d\n",
+ pr_err("[%d] No change in state, cmd_state=%d\n",
dsi_ctrl->cell_index, op_state);
rc = -EINVAL;
} else if ((state->power_state != DSI_CTRL_POWER_VREG_ON) ||
(state->controller_state != DSI_CTRL_ENGINE_ON)) {
- pr_debug("[%d]State error: op=%d: %d, %d\n",
+ pr_err("[%d]State error: op=%d: %d, %d\n",
dsi_ctrl->cell_index,
op,
state->power_state,
@@ -305,12 +305,12 @@
break;
case DSI_CTRL_OP_VID_ENGINE:
if (state->vid_engine_state == op_state) {
- pr_debug("[%d] No change in state, cmd_state=%d\n",
+ pr_err("[%d] No change in state, cmd_state=%d\n",
dsi_ctrl->cell_index, op_state);
rc = -EINVAL;
} else if ((state->power_state != DSI_CTRL_POWER_VREG_ON) ||
(state->controller_state != DSI_CTRL_ENGINE_ON)) {
- pr_debug("[%d]State error: op=%d: %d, %d\n",
+ pr_err("[%d]State error: op=%d: %d, %d\n",
dsi_ctrl->cell_index,
op,
state->power_state,
@@ -320,11 +320,11 @@
break;
case DSI_CTRL_OP_HOST_ENGINE:
if (state->controller_state == op_state) {
- pr_debug("[%d] No change in state, ctrl_state=%d\n",
+ pr_err("[%d] No change in state, ctrl_state=%d\n",
dsi_ctrl->cell_index, op_state);
rc = -EINVAL;
} else if (state->power_state != DSI_CTRL_POWER_VREG_ON) {
- pr_debug("[%d]State error (link is off): op=%d:, %d\n",
+ pr_err("[%d]State error (link is off): op=%d:, %d\n",
dsi_ctrl->cell_index,
op_state,
state->power_state);
@@ -332,7 +332,7 @@
} else if ((op_state == DSI_CTRL_ENGINE_OFF) &&
((state->cmd_engine_state != DSI_CTRL_ENGINE_OFF) ||
(state->vid_engine_state != DSI_CTRL_ENGINE_OFF))) {
- pr_debug("[%d]State error (eng on): op=%d: %d, %d\n",
+ pr_err("[%d]State error (eng on): op=%d: %d, %d\n",
dsi_ctrl->cell_index,
op_state,
state->cmd_engine_state,
@@ -344,7 +344,7 @@
if ((state->power_state != DSI_CTRL_POWER_VREG_ON) ||
(state->host_initialized != true) ||
(state->cmd_engine_state != DSI_CTRL_ENGINE_ON)) {
- pr_debug("[%d]State error: op=%d: %d, %d, %d\n",
+ pr_err("[%d]State error: op=%d: %d, %d, %d\n",
dsi_ctrl->cell_index,
op,
state->power_state,
@@ -355,23 +355,23 @@
break;
case DSI_CTRL_OP_HOST_INIT:
if (state->host_initialized == op_state) {
- pr_debug("[%d] No change in state, host_init=%d\n",
+ pr_err("[%d] No change in state, host_init=%d\n",
dsi_ctrl->cell_index, op_state);
rc = -EINVAL;
} else if (state->power_state != DSI_CTRL_POWER_VREG_ON) {
- pr_debug("[%d]State error: op=%d: %d\n",
+ pr_err("[%d]State error: op=%d: %d\n",
dsi_ctrl->cell_index, op, state->power_state);
rc = -EINVAL;
}
break;
case DSI_CTRL_OP_TPG:
if (state->tpg_enabled == op_state) {
- pr_debug("[%d] No change in state, tpg_enabled=%d\n",
+ pr_err("[%d] No change in state, tpg_enabled=%d\n",
dsi_ctrl->cell_index, op_state);
rc = -EINVAL;
} else if ((state->power_state != DSI_CTRL_POWER_VREG_ON) ||
(state->controller_state != DSI_CTRL_ENGINE_ON)) {
- pr_debug("[%d]State error: op=%d: %d, %d\n",
+ pr_err("[%d]State error: op=%d: %d, %d\n",
dsi_ctrl->cell_index,
op,
state->power_state,
@@ -381,7 +381,7 @@
break;
case DSI_CTRL_OP_PHY_SW_RESET:
if (state->power_state != DSI_CTRL_POWER_VREG_ON) {
- pr_debug("[%d]State error: op=%d: %d\n",
+ pr_err("[%d]State error: op=%d: %d\n",
dsi_ctrl->cell_index, op, state->power_state);
rc = -EINVAL;
}
diff --git a/drivers/gpu/drm/msm/dsi-staging/dsi_display.c b/drivers/gpu/drm/msm/dsi-staging/dsi_display.c
index c79a72a..199833d 100644
--- a/drivers/gpu/drm/msm/dsi-staging/dsi_display.c
+++ b/drivers/gpu/drm/msm/dsi-staging/dsi_display.c
@@ -488,7 +488,6 @@
int i, j = 0;
int len = 0, *lenp;
int group = 0, count = 0;
- struct dsi_display_mode *mode;
struct drm_panel_esd_config *config;
if (!panel)
@@ -497,8 +496,7 @@
config = &(panel->esd_config);
lenp = config->status_valid_params ?: config->status_cmds_rlen;
- mode = panel->cur_mode;
- count = mode->priv_info->cmd_sets[DSI_CMD_SET_PANEL_STATUS].count;
+ count = config->status_cmd.count;
for (i = 0; i < count; i++)
len += lenp[i];
@@ -694,7 +692,7 @@
reinit_completion(&display->esd_te_gate);
if (!wait_for_completion_timeout(&display->esd_te_gate,
esd_te_timeout)) {
- pr_err("ESD check failed\n");
+ pr_err("TE check failed\n");
rc = -EINVAL;
}
@@ -703,7 +701,7 @@
return rc;
}
-int dsi_display_check_status(void *display)
+int dsi_display_check_status(void *display, bool te_check_override)
{
struct dsi_display *dsi_display = display;
struct dsi_panel *panel;
@@ -713,18 +711,20 @@
if (dsi_display == NULL)
return -EINVAL;
- panel = dsi_display->panel;
-
- status_mode = panel->esd_config.status_mode;
-
mutex_lock(&dsi_display->display_lock);
+ panel = dsi_display->panel;
if (!panel->panel_initialized) {
pr_debug("Panel not initialized\n");
mutex_unlock(&dsi_display->display_lock);
return rc;
}
+ if (te_check_override && gpio_is_valid(dsi_display->disp_te_gpio))
+ status_mode = ESD_MODE_PANEL_TE;
+ else
+ status_mode = panel->esd_config.status_mode;
+
dsi_display_clk_ctrl(dsi_display->dsi_clk_handle,
DSI_ALL_CLKS, DSI_CLK_ON);
@@ -2706,7 +2706,7 @@
const struct mipi_dsi_msg *msg)
{
struct dsi_display *display = to_dsi_display(host);
- int rc = 0;
+ int rc = 0, ret = 0;
if (!host || !msg) {
pr_err("Invalid params\n");
@@ -2764,13 +2764,17 @@
}
error_disable_cmd_engine:
- (void)dsi_display_cmd_engine_disable(display);
+ ret = dsi_display_cmd_engine_disable(display);
+ if (ret) {
+ pr_err("[%s]failed to disable DSI cmd engine, rc=%d\n",
+ display->name, ret);
+ }
error_disable_clks:
- rc = dsi_display_clk_ctrl(display->dsi_clk_handle,
+ ret = dsi_display_clk_ctrl(display->dsi_clk_handle,
DSI_ALL_CLKS, DSI_CLK_OFF);
- if (rc) {
+ if (ret) {
pr_err("[%s] failed to disable all DSI clocks, rc=%d\n",
- display->name, rc);
+ display->name, ret);
}
error:
return rc;
diff --git a/drivers/gpu/drm/msm/dsi-staging/dsi_display.h b/drivers/gpu/drm/msm/dsi-staging/dsi_display.h
index 85fd65c1..6b1c029 100644
--- a/drivers/gpu/drm/msm/dsi-staging/dsi_display.h
+++ b/drivers/gpu/drm/msm/dsi-staging/dsi_display.h
@@ -581,8 +581,9 @@
/**
* dsi_display_check_status() - check if panel is dead or alive
* @display: Handle to display.
+ * @te_check_override: Whether check for TE from panel or default check
*/
-int dsi_display_check_status(void *display);
+int dsi_display_check_status(void *display, bool te_check_override);
/**
* dsi_display_cmd_transfer() - transfer command to the panel
diff --git a/drivers/gpu/drm/msm/dsi-staging/dsi_panel.c b/drivers/gpu/drm/msm/dsi-staging/dsi_panel.c
index 31d6fd1..e62c65e 100644
--- a/drivers/gpu/drm/msm/dsi-staging/dsi_panel.c
+++ b/drivers/gpu/drm/msm/dsi-staging/dsi_panel.c
@@ -2054,9 +2054,8 @@
int final_value, final_scale;
int ratio_index;
- dsc->version = 0x11;
- dsc->scr_rev = 0;
dsc->rc_model_size = 8192;
+
if (dsc->version == 0x11 && dsc->scr_rev == 0x1)
dsc->first_line_bpg_offset = 15;
else
@@ -2248,6 +2247,36 @@
return 0;
}
+ rc = of_property_read_u32(of_node, "qcom,mdss-dsc-version", &data);
+ if (rc) {
+ priv_info->dsc.version = 0x11;
+ rc = 0;
+ } else {
+ priv_info->dsc.version = data & 0xff;
+ /* only support DSC 1.1 rev */
+ if (priv_info->dsc.version != 0x11) {
+ pr_err("%s: DSC version:%d not supported\n", __func__,
+ priv_info->dsc.version);
+ rc = -EINVAL;
+ goto error;
+ }
+ }
+
+ rc = of_property_read_u32(of_node, "qcom,mdss-dsc-scr-version", &data);
+ if (rc) {
+ priv_info->dsc.scr_rev = 0x0;
+ rc = 0;
+ } else {
+ priv_info->dsc.scr_rev = data & 0xff;
+ /* only one scr rev supported */
+ if (priv_info->dsc.scr_rev > 0x1) {
+ pr_err("%s: DSC scr version:%d not supported\n",
+ __func__, priv_info->dsc.scr_rev);
+ rc = -EINVAL;
+ goto error;
+ }
+ }
+
rc = of_property_read_u32(of_node, "qcom,mdss-dsc-slice-height", &data);
if (rc) {
pr_err("failed to parse qcom,mdss-dsc-slice-height\n");
diff --git a/drivers/gpu/drm/msm/msm_drv.h b/drivers/gpu/drm/msm/msm_drv.h
index 17a41d5..ce4197b 100644
--- a/drivers/gpu/drm/msm/msm_drv.h
+++ b/drivers/gpu/drm/msm/msm_drv.h
@@ -156,6 +156,8 @@
CRTC_PROP_IDLE_TIMEOUT,
CRTC_PROP_DEST_SCALER,
+ CRTC_PROP_ENABLE_SUI_ENHANCEMENT,
+
/* total # of properties */
CRTC_PROP_COUNT
};
diff --git a/drivers/gpu/drm/msm/sde/sde_color_processing.c b/drivers/gpu/drm/msm/sde/sde_color_processing.c
index 919ed97..0f55b19 100644
--- a/drivers/gpu/drm/msm/sde/sde_color_processing.c
+++ b/drivers/gpu/drm/msm/sde/sde_color_processing.c
@@ -1799,25 +1799,21 @@
goto exit;
}
- node = _sde_cp_get_intr_node(DRM_EVENT_AD_BACKLIGHT, crtc);
+ node = container_of(ad_irq, struct sde_crtc_irq_info, irq);
if (!en) {
- if (node) {
- spin_lock_irqsave(&node->state_lock, flags);
- if (node->state == IRQ_ENABLED) {
- ret = sde_core_irq_disable(kms, &irq_idx, 1);
- if (ret)
- DRM_ERROR("disable irq %d error %d\n",
- irq_idx, ret);
- else
- node->state = IRQ_NOINIT;
- } else {
+ spin_lock_irqsave(&node->state_lock, flags);
+ if (node->state == IRQ_ENABLED) {
+ ret = sde_core_irq_disable(kms, &irq_idx, 1);
+ if (ret)
+ DRM_ERROR("disable irq %d error %d\n",
+ irq_idx, ret);
+ else
node->state = IRQ_NOINIT;
- }
- spin_unlock_irqrestore(&node->state_lock, flags);
} else {
- DRM_ERROR("failed to get node from crtc event list\n");
+ node->state = IRQ_NOINIT;
}
+ spin_unlock_irqrestore(&node->state_lock, flags);
sde_core_irq_unregister_callback(kms, irq_idx, ad_irq);
ret = 0;
goto exit;
@@ -1831,32 +1827,18 @@
goto exit;
}
- if (node) {
- /* device resume or resume from IPC cases */
- spin_lock_irqsave(&node->state_lock, flags);
- if (node->state == IRQ_DISABLED || node->state == IRQ_NOINIT) {
- ret = sde_core_irq_enable(kms, &irq_idx, 1);
- if (ret) {
- DRM_ERROR("enable irq %d error %d\n",
- irq_idx, ret);
- sde_core_irq_unregister_callback(kms,
- irq_idx, ad_irq);
- } else {
- node->state = IRQ_ENABLED;
- }
- }
- spin_unlock_irqrestore(&node->state_lock, flags);
- } else {
- /* request from userspace to register the event
- * in this case, node has not been added into the event list
- */
+ spin_lock_irqsave(&node->state_lock, flags);
+ if (node->state == IRQ_DISABLED || node->state == IRQ_NOINIT) {
ret = sde_core_irq_enable(kms, &irq_idx, 1);
if (ret) {
- DRM_ERROR("failed to enable irq ret %d\n", ret);
- sde_core_irq_unregister_callback(kms,
- irq_idx, ad_irq);
+ DRM_ERROR("enable irq %d error %d\n", irq_idx, ret);
+ sde_core_irq_unregister_callback(kms, irq_idx, ad_irq);
+ } else {
+ node->state = IRQ_ENABLED;
}
}
+ spin_unlock_irqrestore(&node->state_lock, flags);
+
exit:
return ret;
}
@@ -1937,7 +1919,7 @@
spin_unlock_irqrestore(&crtc->spin_lock, flags);
if (!node) {
- DRM_ERROR("cannot find histogram event node in crtc\n");
+ DRM_DEBUG_DRIVER("cannot find histogram event node in crtc\n");
return;
}
@@ -2082,26 +2064,29 @@
goto exit;
}
- node = _sde_cp_get_intr_node(DRM_EVENT_HISTOGRAM, crtc);
+ node = container_of(hist_irq, struct sde_crtc_irq_info, irq);
/* deregister histogram irq */
if (!en) {
- if (node) {
- /* device suspend case or suspend to IPC cases */
+ spin_lock_irqsave(&node->state_lock, flags);
+ if (node->state == IRQ_ENABLED) {
+ node->state = IRQ_DISABLING;
+ spin_unlock_irqrestore(&node->state_lock, flags);
+ ret = sde_core_irq_disable(kms, &irq_idx, 1);
spin_lock_irqsave(&node->state_lock, flags);
- if (node->state == IRQ_ENABLED) {
- ret = sde_core_irq_disable(kms, &irq_idx, 1);
- if (ret)
- DRM_ERROR("disable irq %d error %d\n",
- irq_idx, ret);
- else
- node->state = IRQ_NOINIT;
+ if (ret) {
+ DRM_ERROR("disable irq %d error %d\n",
+ irq_idx, ret);
+ node->state = IRQ_ENABLED;
} else {
node->state = IRQ_NOINIT;
}
spin_unlock_irqrestore(&node->state_lock, flags);
+ } else if (node->state == IRQ_DISABLED) {
+ node->state = IRQ_NOINIT;
+ spin_unlock_irqrestore(&node->state_lock, flags);
} else {
- DRM_ERROR("failed to get node from crtc event list\n");
+ spin_unlock_irqrestore(&node->state_lock, flags);
}
sde_core_irq_unregister_callback(kms, irq_idx, hist_irq);
@@ -2117,32 +2102,19 @@
goto exit;
}
- if (node) {
- /* device resume or resume from IPC cases */
- spin_lock_irqsave(&node->state_lock, flags);
- if (node->state == IRQ_DISABLED || node->state == IRQ_NOINIT) {
- ret = sde_core_irq_enable(kms, &irq_idx, 1);
- if (ret) {
- DRM_ERROR("enable irq %d error %d\n",
- irq_idx, ret);
- sde_core_irq_unregister_callback(kms,
- irq_idx, hist_irq);
- } else {
- node->state = IRQ_ENABLED;
- }
- }
- spin_unlock_irqrestore(&node->state_lock, flags);
- } else {
- /* request from userspace to register the event
- * in this case, node has not been added into the event list
- */
+ spin_lock_irqsave(&node->state_lock, flags);
+ if (node->state == IRQ_DISABLED || node->state == IRQ_NOINIT) {
ret = sde_core_irq_enable(kms, &irq_idx, 1);
if (ret) {
- DRM_ERROR("failed to enable irq ret %d\n", ret);
+ DRM_ERROR("enable irq %d error %d\n", irq_idx, ret);
sde_core_irq_unregister_callback(kms,
irq_idx, hist_irq);
+ } else {
+ node->state = IRQ_ENABLED;
}
}
+ spin_unlock_irqrestore(&node->state_lock, flags);
+
exit:
return ret;
}
diff --git a/drivers/gpu/drm/msm/sde/sde_connector.c b/drivers/gpu/drm/msm/sde/sde_connector.c
index e59c5f0..d2f8d12 100644
--- a/drivers/gpu/drm/msm/sde/sde_connector.c
+++ b/drivers/gpu/drm/msm/sde/sde_connector.c
@@ -1731,12 +1731,59 @@
return c_conn->encoder;
}
+static void _sde_connector_report_panel_dead(struct sde_connector *conn)
+{
+ struct drm_event event;
+ bool panel_dead = true;
+
+ if (!conn)
+ return;
+
+ event.type = DRM_EVENT_PANEL_DEAD;
+ event.length = sizeof(bool);
+ msm_mode_object_event_notify(&conn->base.base,
+ conn->base.dev, &event, (u8 *)&panel_dead);
+ sde_encoder_display_failure_notification(conn->encoder);
+ SDE_EVT32(SDE_EVTLOG_ERROR);
+ SDE_ERROR("esd check failed report PANEL_DEAD conn_id: %d enc_id: %d\n",
+ conn->base.base.id, conn->encoder->base.id);
+}
+
+int sde_connector_esd_status(struct drm_connector *conn)
+{
+ struct sde_connector *sde_conn = NULL;
+ int ret = 0;
+
+ if (!conn)
+ return ret;
+
+ sde_conn = to_sde_connector(conn);
+ if (!sde_conn || !sde_conn->ops.check_status)
+ return ret;
+
+ /* protect this call with ESD status check call */
+ mutex_lock(&sde_conn->lock);
+ ret = sde_conn->ops.check_status(sde_conn->display, true);
+ mutex_unlock(&sde_conn->lock);
+
+ if (ret <= 0) {
+ /* cancel if any pending esd work */
+ sde_connector_schedule_status_work(conn, false);
+ _sde_connector_report_panel_dead(sde_conn);
+ ret = -ETIMEDOUT;
+ } else {
+ SDE_DEBUG("Successfully received TE from panel\n");
+ ret = 0;
+ }
+ SDE_EVT32(ret);
+
+ return ret;
+}
+
static void sde_connector_check_status_work(struct work_struct *work)
{
struct sde_connector *conn;
- struct drm_event event;
int rc = 0;
- bool panel_dead = false;
conn = container_of(to_delayed_work(work),
struct sde_connector, status_work);
@@ -1753,7 +1800,7 @@
return;
}
- rc = conn->ops.check_status(conn->display);
+ rc = conn->ops.check_status(conn->display, false);
mutex_unlock(&conn->lock);
if (conn->force_panel_dead) {
@@ -1777,15 +1824,7 @@
}
status_dead:
- SDE_EVT32(rc, SDE_EVTLOG_ERROR);
- SDE_ERROR("esd check failed report PANEL_DEAD conn_id: %d enc_id: %d\n",
- conn->base.base.id, conn->encoder->base.id);
- panel_dead = true;
- event.type = DRM_EVENT_PANEL_DEAD;
- event.length = sizeof(bool);
- msm_mode_object_event_notify(&conn->base.base,
- conn->base.dev, &event, (u8 *)&panel_dead);
- sde_encoder_display_failure_notification(conn->encoder);
+ _sde_connector_report_panel_dead(conn);
}
static const struct drm_connector_helper_funcs sde_connector_helper_ops = {
diff --git a/drivers/gpu/drm/msm/sde/sde_connector.h b/drivers/gpu/drm/msm/sde/sde_connector.h
index ef2385e..c6f348e 100644
--- a/drivers/gpu/drm/msm/sde/sde_connector.h
+++ b/drivers/gpu/drm/msm/sde/sde_connector.h
@@ -228,9 +228,10 @@
/**
* check_status - check status of connected display panel
* @display: Pointer to private display handle
+ * @te_check_override: Whether check TE from panel or default check
* Returns: positive value for success, negetive or zero for failure
*/
- int (*check_status)(void *display);
+ int (*check_status)(void *display, bool te_check_override);
/**
* cmd_transfer - Transfer command to the connected display panel
@@ -770,4 +771,11 @@
*/
int sde_connector_get_panel_vfp(struct drm_connector *connector,
struct drm_display_mode *mode);
+
+/**
+ * sde_connector_esd_status - helper function to check te status
+ * @connector: Pointer to DRM connector object
+ */
+int sde_connector_esd_status(struct drm_connector *connector);
+
#endif /* _SDE_CONNECTOR_H_ */
diff --git a/drivers/gpu/drm/msm/sde/sde_crtc.c b/drivers/gpu/drm/msm/sde/sde_crtc.c
index 7bc01c3..ce2997d 100644
--- a/drivers/gpu/drm/msm/sde/sde_crtc.c
+++ b/drivers/gpu/drm/msm/sde/sde_crtc.c
@@ -1851,7 +1851,8 @@
ops |= (SDE_KMS_OPS_WAIT_FOR_TX_DONE |
SDE_KMS_OPS_CLEANUP_PLANE_FB);
}
- if (catalog->sui_misr_supported)
+ if (catalog->sui_misr_supported &&
+ sde_crtc->enable_sui_enhancement)
smmu_state->sui_misr_state =
SUI_MISR_ENABLE_REQ;
/* secure camera usecase */
@@ -1881,7 +1882,8 @@
if (old_valid_fb)
ops |= (SDE_KMS_OPS_WAIT_FOR_TX_DONE |
SDE_KMS_OPS_CLEANUP_PLANE_FB);
- if (catalog->sui_misr_supported)
+ if (catalog->sui_misr_supported &&
+ sde_crtc->enable_sui_enhancement)
smmu_state->sui_misr_state =
SUI_MISR_DISABLE_REQ;
}
@@ -4398,6 +4400,7 @@
return -EINVAL;
}
+ sde_crtc = to_sde_crtc(crtc);
cstate = to_sde_crtc_state(state);
secure = sde_crtc_get_property(cstate, CRTC_PROP_SECURITY_LEVEL);
@@ -4434,7 +4437,8 @@
}
plane = pstates[i].drm_pstate->plane;
- if (!sde_plane_is_sec_ui_allowed(plane)) {
+ if (sde_crtc->enable_sui_enhancement &&
+ !sde_plane_is_sec_ui_allowed(plane)) {
SDE_ERROR("crtc%d: sec-ui not allowed in p%d\n",
crtc->base.id, plane->base.id);
return -EINVAL;
@@ -4475,7 +4479,6 @@
MSM_DISPLAY_CAP_VID_MODE);
}
- sde_crtc = to_sde_crtc(crtc);
smmu_state = &sde_kms->smmu_state;
/*
* In video mode check for null commit before transition
@@ -4987,6 +4990,10 @@
"idle_time", 0, 0, U64_MAX, 0,
CRTC_PROP_IDLE_TIMEOUT);
+ msm_property_install_range(&sde_crtc->property_info,
+ "enable_sui_enhancement", 0, 0, U64_MAX, 0,
+ CRTC_PROP_ENABLE_SUI_ENHANCEMENT);
+
msm_property_install_blob(&sde_crtc->property_info, "capabilities",
DRM_MODE_PROP_IMMUTABLE, CRTC_PROP_INFO);
@@ -5222,6 +5229,9 @@
cstate->bw_control = true;
cstate->bw_split_vote = true;
break;
+ case CRTC_PROP_ENABLE_SUI_ENHANCEMENT:
+ sde_crtc->enable_sui_enhancement = val ? true : false;
+ break;
case CRTC_PROP_OUTPUT_FENCE:
if (!val)
goto exit;
@@ -6032,10 +6042,10 @@
node = kzalloc(sizeof(*node), GFP_KERNEL);
if (!node)
return -ENOMEM;
- node->event = event;
INIT_LIST_HEAD(&node->list);
node->func = custom_events[i].func;
node->event = event;
+ node->state = IRQ_NOINIT;
spin_lock_init(&node->state_lock);
break;
}
@@ -6066,8 +6076,6 @@
if (!ret) {
spin_lock_irqsave(&crtc->spin_lock, flags);
- /* irq is regiestered and enabled and set the state */
- node->state = IRQ_ENABLED;
list_add_tail(&node->list, &crtc->user_event_list);
spin_unlock_irqrestore(&crtc->spin_lock, flags);
} else {
diff --git a/drivers/gpu/drm/msm/sde/sde_crtc.h b/drivers/gpu/drm/msm/sde/sde_crtc.h
index bc1614c..64f3821 100644
--- a/drivers/gpu/drm/msm/sde/sde_crtc.h
+++ b/drivers/gpu/drm/msm/sde/sde_crtc.h
@@ -171,6 +171,8 @@
* @misr_enable : boolean entry indicates misr enable/disable status.
* @misr_frame_count : misr frame count provided by client
* @misr_data : store misr data before turning off the clocks.
+ * @enable_sui_enhancement: indicate enable/disable of sui_enhancement feature
+ * which is set by user-mode.
* @sbuf_op_mode_old : inline rotator op mode for previous commit cycle
* @sbuf_flush_mask_old: inline rotator flush mask for previous commit
* @sbuf_flush_mask_all: inline rotator flush mask for all attached planes
@@ -242,6 +244,8 @@
u32 misr_frame_count;
u32 misr_data[CRTC_DUAL_MIXERS];
+ bool enable_sui_enhancement;
+
u32 sbuf_op_mode_old;
u32 sbuf_flush_mask_old;
u32 sbuf_flush_mask_all;
@@ -390,6 +394,7 @@
enum sde_crtc_irq_state {
IRQ_NOINIT,
IRQ_ENABLED,
+ IRQ_DISABLING,
IRQ_DISABLED,
};
@@ -690,6 +695,22 @@
}
/**
+ * sde_crtc_is_sui_enhancement_enabled - Checks if user-mode has enabled the
+ * sui enhancement feature
+ * @crtc: Pointer to crtc
+ */
+static inline bool sde_crtc_is_sui_enhancement_enabled(struct drm_crtc *crtc)
+{
+ struct sde_crtc *sde_crtc;
+
+ if (!crtc)
+ return false;
+ sde_crtc = to_sde_crtc(crtc);
+
+ return sde_crtc->enable_sui_enhancement;
+}
+
+/**
* sde_crtc_get_secure_transition - determines the operations to be
* performed before transitioning to secure state
* This function should be called after swapping the new state
diff --git a/drivers/gpu/drm/msm/sde/sde_encoder_phys_cmd.c b/drivers/gpu/drm/msm/sde/sde_encoder_phys_cmd.c
index 3edaed3..828d771 100644
--- a/drivers/gpu/drm/msm/sde/sde_encoder_phys_cmd.c
+++ b/drivers/gpu/drm/msm/sde/sde_encoder_phys_cmd.c
@@ -473,6 +473,10 @@
atomic_read(&phys_enc->pending_kickoff_cnt),
frame_event);
+ /* check if panel is still sending TE signal or not */
+ if (sde_connector_esd_status(phys_enc->connector))
+ goto exit;
+
if (cmd_enc->pp_timeout_report_cnt >= PP_TIMEOUT_MAX_TRIALS) {
cmd_enc->pp_timeout_report_cnt = PP_TIMEOUT_MAX_TRIALS;
frame_event |= SDE_ENCODER_FRAME_EVENT_PANEL_DEAD;
@@ -490,11 +494,12 @@
SDE_EVT32(DRMID(phys_enc->parent), SDE_EVTLOG_FATAL);
}
- atomic_add_unless(&phys_enc->pending_kickoff_cnt, -1, 0);
-
/* request a ctl reset before the next kickoff */
phys_enc->enable_state = SDE_ENC_ERR_NEEDS_HW_RESET;
+exit:
+ atomic_add_unless(&phys_enc->pending_kickoff_cnt, -1, 0);
+
if (phys_enc->parent_ops.handle_frame_done)
phys_enc->parent_ops.handle_frame_done(
phys_enc->parent, phys_enc, frame_event);
diff --git a/drivers/gpu/drm/msm/sde/sde_encoder_phys_vid.c b/drivers/gpu/drm/msm/sde/sde_encoder_phys_vid.c
index dd72665..862a8b3 100644
--- a/drivers/gpu/drm/msm/sde/sde_encoder_phys_vid.c
+++ b/drivers/gpu/drm/msm/sde/sde_encoder_phys_vid.c
@@ -846,7 +846,7 @@
if (phys_enc->parent_ops.handle_frame_done && event)
phys_enc->parent_ops.handle_frame_done(
phys_enc->parent, phys_enc,
- SDE_ENCODER_FRAME_EVENT_DONE);
+ event);
return ret;
}
diff --git a/drivers/gpu/drm/msm/sde/sde_hw_catalog.c b/drivers/gpu/drm/msm/sde/sde_hw_catalog.c
index 92c74d8..eacafe6 100644
--- a/drivers/gpu/drm/msm/sde/sde_hw_catalog.c
+++ b/drivers/gpu/drm/msm/sde/sde_hw_catalog.c
@@ -3245,12 +3245,20 @@
sde_cfg->perf.min_prefill_lines = 25;
sde_cfg->vbif_qos_nlvl = 4;
sde_cfg->ts_prefill_rev = 1;
- } else if (IS_SDM845_TARGET(hw_rev) || IS_SDM670_TARGET(hw_rev)) {
+ } else if (IS_SDM845_TARGET(hw_rev)) {
/* update sdm845 target here */
sde_cfg->has_wb_ubwc = true;
sde_cfg->perf.min_prefill_lines = 24;
sde_cfg->vbif_qos_nlvl = 8;
sde_cfg->ts_prefill_rev = 2;
+ sde_cfg->sui_misr_supported = true;
+ sde_cfg->sui_block_xin_mask = 0x3F71;
+ } else if (IS_SDM670_TARGET(hw_rev)) {
+ /* update sdm670 target here */
+ sde_cfg->has_wb_ubwc = true;
+ sde_cfg->perf.min_prefill_lines = 24;
+ sde_cfg->vbif_qos_nlvl = 8;
+ sde_cfg->ts_prefill_rev = 2;
} else {
SDE_ERROR("unsupported chipset id:%X\n", hw_rev);
sde_cfg->perf.min_prefill_lines = 0xffff;
diff --git a/drivers/gpu/drm/msm/sde/sde_kms.c b/drivers/gpu/drm/msm/sde/sde_kms.c
index 0412fc6..33bdec9 100644
--- a/drivers/gpu/drm/msm/sde/sde_kms.c
+++ b/drivers/gpu/drm/msm/sde/sde_kms.c
@@ -105,6 +105,32 @@
return sdecustom;
}
+bool sde_kms_is_vbif_operation_allowed(struct sde_kms *sde_kms)
+{
+ struct drm_device *dev;
+ struct drm_crtc *crtc;
+ bool sui_enhancement = false;
+
+ if (!sde_kms || !sde_kms->dev)
+ return false;
+ dev = sde_kms->dev;
+
+ if (!sde_kms->catalog->sui_misr_supported)
+ return true;
+
+ list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
+ if (!crtc->state || !crtc->state->active)
+ continue;
+
+ sui_enhancement |= sde_crtc_is_sui_enhancement_enabled(crtc);
+ }
+
+ if (!sui_enhancement)
+ return true;
+
+ return !sde_kms_is_secure_session_inprogress(sde_kms);
+}
+
#ifdef CONFIG_DEBUG_FS
static int _sde_danger_signal_status(struct seq_file *s,
bool danger_status)
diff --git a/drivers/gpu/drm/msm/sde/sde_kms.h b/drivers/gpu/drm/msm/sde/sde_kms.h
index ad6d279..450695d 100644
--- a/drivers/gpu/drm/msm/sde/sde_kms.h
+++ b/drivers/gpu/drm/msm/sde/sde_kms.h
@@ -305,6 +305,16 @@
bool sde_is_custom_client(void);
/**
+ * sde_kms_is_vbif_operation_allowed - resticts the VBIF programming
+ * during secure-ui, if the sec_ui_misr feature is enabled
+ *
+ * @sde_kms: Pointer to sde_kms
+ *
+ * return: false if secure-session is in progress; true otherwise
+ */
+bool sde_kms_is_vbif_operation_allowed(struct sde_kms *sde_kms);
+
+/**
* sde_kms_power_resource_is_enabled - whether or not power resource is enabled
* @dev: Pointer to drm device
* Return: true if power resource is enabled; false otherwise
@@ -372,25 +382,6 @@
}
/**
- * sde_kms_is_vbif_operation_allowed - resticts the VBIF programming
- * during secure-ui, if the sec_ui_misr feature is enabled
- *
- * @sde_kms: Pointer to sde_kms
- *
- * return: false if secure-session is in progress; true otherwise
- */
-static inline bool sde_kms_is_vbif_operation_allowed(struct sde_kms *sde_kms)
-{
- if (!sde_kms)
- return false;
-
- if (!sde_kms->catalog->sui_misr_supported)
- return true;
-
- return !sde_kms_is_secure_session_inprogress(sde_kms);
-}
-
-/**
* Debugfs functions - extra helper functions for debugfs support
*
* Main debugfs documentation is located at,
diff --git a/drivers/gpu/msm/adreno-gpulist.h b/drivers/gpu/msm/adreno-gpulist.h
index 1fb76dd..6b9d0e7 100644
--- a/drivers/gpu/msm/adreno-gpulist.h
+++ b/drivers/gpu/msm/adreno-gpulist.h
@@ -202,6 +202,20 @@
.regfw_name = "a530v3_seq.fw2",
},
{
+ .gpurev = ADRENO_REV_A504,
+ .core = 5,
+ .major = 0,
+ .minor = 4,
+ .patchid = ANY_ID,
+ .features = ADRENO_PREEMPTION | ADRENO_64BIT,
+ .pm4fw_name = "a530_pm4.fw",
+ .pfpfw_name = "a530_pfp.fw",
+ .gpudev = &adreno_a5xx_gpudev,
+ .gmem_size = (SZ_128K + SZ_8K),
+ .num_protected_regs = 0x20,
+ .busy_mask = 0xFFFFFFFE,
+ },
+ {
.gpurev = ADRENO_REV_A505,
.core = 5,
.major = 0,
diff --git a/drivers/gpu/msm/adreno.c b/drivers/gpu/msm/adreno.c
index 763dc18..cb916ae 100644
--- a/drivers/gpu/msm/adreno.c
+++ b/drivers/gpu/msm/adreno.c
@@ -643,7 +643,7 @@
if (fence_retries == FENCE_RETRY_MAX) {
KGSL_DRV_CRIT_RATELIMIT(device,
"AHB fence stuck in ISR\n");
- return ret;
+ goto done;
}
fence_retries++;
} while (fence != 0);
@@ -687,6 +687,7 @@
adreno_writereg(adreno_dev, ADRENO_REG_RBBM_INT_CLEAR_CMD,
int_bit);
+done:
/* Turn off the KEEPALIVE vote from earlier unless hard fault set */
if (gpudev->gpu_keepalive) {
/* If hard fault, then let snapshot turn off the keepalive */
@@ -1014,6 +1015,46 @@
return -ENODEV;
}
+static void
+l3_pwrlevel_probe(struct kgsl_device *device, struct device_node *node)
+{
+
+ struct device_node *pwrlevel_node, *child;
+
+ pwrlevel_node = of_find_node_by_name(node, "qcom,l3-pwrlevels");
+
+ if (pwrlevel_node == NULL)
+ return;
+
+ device->num_l3_pwrlevels = 0;
+
+ for_each_child_of_node(pwrlevel_node, child) {
+ unsigned int index;
+
+ if (of_property_read_u32(child, "reg", &index))
+ return;
+ if (index >= MAX_L3_LEVELS) {
+ dev_err(&device->pdev->dev, "L3 pwrlevel %d is out of range\n",
+ index);
+ continue;
+ }
+
+ if (index >= device->num_l3_pwrlevels)
+ device->num_l3_pwrlevels = index + 1;
+
+ if (of_property_read_u32(child, "qcom,l3-freq",
+ &device->l3_freq[index]))
+ return;
+ }
+
+ device->l3_clk = devm_clk_get(&device->pdev->dev, "l3_vote");
+
+ if (IS_ERR_OR_NULL(device->l3_clk)) {
+ dev_err(&device->pdev->dev, "Unable to get the l3_vote clock\n");
+ return;
+ }
+}
+
static inline struct adreno_device *adreno_get_dev(struct platform_device *pdev)
{
const struct of_device_id *of_id =
@@ -1060,6 +1101,8 @@
/* Get context aware DCVS properties */
adreno_of_get_ca_aware_properties(adreno_dev, node);
+ l3_pwrlevel_probe(device, node);
+
/* get pm-qos-active-latency, set it to default if not found */
if (of_property_read_u32(node, "qcom,pm-qos-active-latency",
&device->pwrctrl.pm_qos_active_latency))
diff --git a/drivers/gpu/msm/adreno.h b/drivers/gpu/msm/adreno.h
index 9ca22fd..686ed34 100644
--- a/drivers/gpu/msm/adreno.h
+++ b/drivers/gpu/msm/adreno.h
@@ -203,6 +203,7 @@
ADRENO_REV_A418 = 418,
ADRENO_REV_A420 = 420,
ADRENO_REV_A430 = 430,
+ ADRENO_REV_A504 = 504,
ADRENO_REV_A505 = 505,
ADRENO_REV_A506 = 506,
ADRENO_REV_A508 = 508,
@@ -1201,6 +1202,7 @@
ADRENO_GPUREV(adreno_dev) < 600;
}
+ADRENO_TARGET(a504, ADRENO_REV_A504)
ADRENO_TARGET(a505, ADRENO_REV_A505)
ADRENO_TARGET(a506, ADRENO_REV_A506)
ADRENO_TARGET(a508, ADRENO_REV_A508)
@@ -1227,9 +1229,9 @@
(ADRENO_CHIPID_PATCH(adreno_dev->chipid) == 2);
}
-static inline int adreno_is_a505_or_a506(struct adreno_device *adreno_dev)
+static inline int adreno_is_a504_to_a506(struct adreno_device *adreno_dev)
{
- return ADRENO_GPUREV(adreno_dev) >= 505 &&
+ return ADRENO_GPUREV(adreno_dev) >= 504 &&
ADRENO_GPUREV(adreno_dev) <= 506;
}
diff --git a/drivers/gpu/msm/adreno_a5xx.c b/drivers/gpu/msm/adreno_a5xx.c
index 4775c3e..6ef74de 100644
--- a/drivers/gpu/msm/adreno_a5xx.c
+++ b/drivers/gpu/msm/adreno_a5xx.c
@@ -56,6 +56,7 @@
{ adreno_is_a512, a540_vbif },
{ adreno_is_a510, a530_vbif },
{ adreno_is_a508, a530_vbif },
+ { adreno_is_a504, a530_vbif },
{ adreno_is_a505, a530_vbif },
{ adreno_is_a506, a530_vbif },
};
@@ -127,6 +128,7 @@
} a5xx_efuse_funcs[] = {
{ adreno_is_a530, a530_efuse_leakage },
{ adreno_is_a530, a530_efuse_speed_bin },
+ { adreno_is_a504, a530_efuse_speed_bin },
{ adreno_is_a505, a530_efuse_speed_bin },
{ adreno_is_a512, a530_efuse_speed_bin },
{ adreno_is_a508, a530_efuse_speed_bin },
@@ -152,7 +154,7 @@
uint64_t addr;
struct adreno_gpudev *gpudev = ADRENO_GPU_DEVICE(adreno_dev);
- if (adreno_is_a505_or_a506(adreno_dev) || adreno_is_a508(adreno_dev)) {
+ if (adreno_is_a504_to_a506(adreno_dev) || adreno_is_a508(adreno_dev)) {
gpudev->snapshot_data->sect_sizes->cp_meq = 32;
gpudev->snapshot_data->sect_sizes->cp_merciu = 1024;
gpudev->snapshot_data->sect_sizes->roq = 256;
@@ -1178,6 +1180,7 @@
{ adreno_is_a530, a530_hwcg_regs, ARRAY_SIZE(a530_hwcg_regs) },
{ adreno_is_a512, a512_hwcg_regs, ARRAY_SIZE(a512_hwcg_regs) },
{ adreno_is_a510, a510_hwcg_regs, ARRAY_SIZE(a510_hwcg_regs) },
+ { adreno_is_a504, a50x_hwcg_regs, ARRAY_SIZE(a50x_hwcg_regs) },
{ adreno_is_a505, a50x_hwcg_regs, ARRAY_SIZE(a50x_hwcg_regs) },
{ adreno_is_a506, a50x_hwcg_regs, ARRAY_SIZE(a50x_hwcg_regs) },
{ adreno_is_a508, a50x_hwcg_regs, ARRAY_SIZE(a50x_hwcg_regs) },
@@ -1924,7 +1927,7 @@
* Below CP registers are 0x0 by default, program init
* values based on a5xx flavor.
*/
- if (adreno_is_a505_or_a506(adreno_dev) || adreno_is_a508(adreno_dev)) {
+ if (adreno_is_a504_to_a506(adreno_dev) || adreno_is_a508(adreno_dev)) {
kgsl_regwrite(device, A5XX_CP_MEQ_THRESHOLDS, 0x20);
kgsl_regwrite(device, A5XX_CP_MERCIU_SIZE, 0x400);
kgsl_regwrite(device, A5XX_CP_ROQ_THRESHOLDS_2, 0x40000030);
@@ -1950,7 +1953,7 @@
* vtxFifo and primFifo thresholds default values
* are different.
*/
- if (adreno_is_a505_or_a506(adreno_dev) || adreno_is_a508(adreno_dev))
+ if (adreno_is_a504_to_a506(adreno_dev) || adreno_is_a508(adreno_dev))
kgsl_regwrite(device, A5XX_PC_DBG_ECO_CNTL,
(0x100 << 11 | 0x100 << 22));
else if (adreno_is_a510(adreno_dev) || adreno_is_a512(adreno_dev))
diff --git a/drivers/gpu/msm/adreno_ringbuffer.c b/drivers/gpu/msm/adreno_ringbuffer.c
index df93606..f7f01f5 100644
--- a/drivers/gpu/msm/adreno_ringbuffer.c
+++ b/drivers/gpu/msm/adreno_ringbuffer.c
@@ -762,54 +762,13 @@
sizedwords, 0, NULL);
}
-static int
-l3_pwrlevel_probe(struct kgsl_device *device, struct device_node *node)
-{
- struct device_node *pwrlevel_node, *child;
-
- pwrlevel_node = of_find_node_by_name(node, "qcom,l3-pwrlevels");
-
- if (pwrlevel_node == NULL) {
- dev_err_once(&device->pdev->dev, "Unable to find 'qcom,l3-pwrlevels'\n");
- return -EINVAL;
- }
-
- device->num_l3_pwrlevels = 0;
-
- for_each_child_of_node(pwrlevel_node, child) {
- unsigned int index;
-
- if (of_property_read_u32(child, "reg", &index))
- return -EINVAL;
- if (index >= MAX_L3_LEVELS) {
- dev_err(&device->pdev->dev, "L3 pwrlevel %d is out of range\n",
- index);
- continue;
- }
-
- if (index >= device->num_l3_pwrlevels)
- device->num_l3_pwrlevels = index + 1;
-
- if (of_property_read_u32(child, "qcom,l3-freq",
- &device->l3_freq[index]))
- return -EINVAL;
-
- }
-
- return 0;
-
-}
static void adreno_ringbuffer_set_constraint(struct kgsl_device *device,
struct kgsl_drawobj *drawobj)
{
struct kgsl_context *context = drawobj->context;
- struct device *dev = &device->pdev->dev;
unsigned long flags = drawobj->flags;
- struct device_node *node;
-
- node = device->pdev->dev.of_node;
/*
* Check if the context has a constraint and constraint flags are
@@ -821,22 +780,14 @@
kgsl_pwrctrl_set_constraint(device, &context->pwr_constraint,
context->id);
- if (IS_ERR_OR_NULL(device->l3_clk))
- device->l3_clk = devm_clk_get(dev, "l3_vote");
-
- if (IS_ERR_OR_NULL(device->l3_clk)) {
- KGSL_DEV_ERR_ONCE(device, "Unable to get the l3_vote clock. Cannot set the L3 constraint\n");
- return;
- }
-
if (context->l3_pwr_constraint.type &&
((context->flags & KGSL_CONTEXT_PWR_CONSTRAINT) ||
(flags & KGSL_CONTEXT_PWR_CONSTRAINT))) {
- int ret = l3_pwrlevel_probe(device, node);
-
- if (ret)
+ if (IS_ERR_OR_NULL(device->l3_clk)) {
+ KGSL_DEV_ERR_ONCE(device, "Cannot set L3 constraint\n");
return;
+ }
switch (context->l3_pwr_constraint.type) {
diff --git a/drivers/gpu/msm/kgsl.c b/drivers/gpu/msm/kgsl.c
index 913f9bf..2e617429 100644
--- a/drivers/gpu/msm/kgsl.c
+++ b/drivers/gpu/msm/kgsl.c
@@ -977,24 +977,6 @@
}
}
-static void process_release_sync_sources(struct kgsl_process_private *private)
-{
- struct kgsl_syncsource *syncsource;
- int next = 0;
-
- while (1) {
- spin_lock(&private->syncsource_lock);
- syncsource = idr_get_next(&private->syncsource_idr, &next);
- spin_unlock(&private->syncsource_lock);
-
- if (syncsource == NULL)
- break;
-
- kgsl_syncsource_cleanup(private, syncsource);
- next = next + 1;
- }
-}
-
static void kgsl_process_private_close(struct kgsl_device_private *dev_priv,
struct kgsl_process_private *private)
{
@@ -1013,7 +995,8 @@
kgsl_process_uninit_sysfs(private);
- process_release_sync_sources(private);
+ /* Release all syncsource objects from process private */
+ kgsl_syncsource_process_release_syncsources(private);
/* When using global pagetables, do not detach global pagetable */
if (private->pagetable->name != KGSL_MMU_GLOBAL_PT)
diff --git a/drivers/gpu/msm/kgsl_sync.c b/drivers/gpu/msm/kgsl_sync.c
index a4de6a0..d484894 100644
--- a/drivers/gpu/msm/kgsl_sync.c
+++ b/drivers/gpu/msm/kgsl_sync.c
@@ -623,18 +623,11 @@
kref_put(&syncsource->refcount, kgsl_syncsource_destroy);
}
-void kgsl_syncsource_cleanup(struct kgsl_process_private *private,
+static void kgsl_syncsource_cleanup(struct kgsl_process_private *private,
struct kgsl_syncsource *syncsource)
{
struct kgsl_syncsource_fence *sfence, *next;
- spin_lock(&private->syncsource_lock);
- if (syncsource->id != 0) {
- idr_remove(&private->syncsource_idr, syncsource->id);
- syncsource->id = 0;
- }
- spin_unlock(&private->syncsource_lock);
-
/* Signal all fences to release any callbacks */
spin_lock(&syncsource->lock);
@@ -659,10 +652,17 @@
spin_lock(&private->syncsource_lock);
syncsource = idr_find(&private->syncsource_idr, param->id);
- spin_unlock(&private->syncsource_lock);
- if (syncsource == NULL)
+ if (syncsource == NULL) {
+ spin_unlock(&private->syncsource_lock);
return -EINVAL;
+ }
+
+ if (syncsource->id != 0) {
+ idr_remove(&private->syncsource_idr, syncsource->id);
+ syncsource->id = 0;
+ }
+ spin_unlock(&private->syncsource_lock);
kgsl_syncsource_cleanup(private, syncsource);
return 0;
@@ -807,6 +807,32 @@
kfree(sfence);
}
+void kgsl_syncsource_process_release_syncsources(
+ struct kgsl_process_private *private)
+{
+ struct kgsl_syncsource *syncsource;
+ int next = 0;
+
+ while (1) {
+ spin_lock(&private->syncsource_lock);
+ syncsource = idr_get_next(&private->syncsource_idr, &next);
+
+ if (syncsource == NULL) {
+ spin_unlock(&private->syncsource_lock);
+ break;
+ }
+
+ if (syncsource->id != 0) {
+ idr_remove(&private->syncsource_idr, syncsource->id);
+ syncsource->id = 0;
+ }
+ spin_unlock(&private->syncsource_lock);
+
+ kgsl_syncsource_cleanup(private, syncsource);
+ next = next + 1;
+ }
+}
+
static const char *kgsl_syncsource_get_timeline_name(struct fence *fence)
{
struct kgsl_syncsource_fence *sfence =
diff --git a/drivers/gpu/msm/kgsl_sync.h b/drivers/gpu/msm/kgsl_sync.h
index 955401d..6998b40 100644
--- a/drivers/gpu/msm/kgsl_sync.h
+++ b/drivers/gpu/msm/kgsl_sync.h
@@ -108,8 +108,8 @@
void kgsl_syncsource_put(struct kgsl_syncsource *syncsource);
-void kgsl_syncsource_cleanup(struct kgsl_process_private *private,
- struct kgsl_syncsource *syncsource);
+void kgsl_syncsource_process_release_syncsources(
+ struct kgsl_process_private *private);
void kgsl_dump_fence(struct kgsl_drawobj_sync_event *event,
char *fence_str, int len);
@@ -182,8 +182,8 @@
}
-static inline void kgsl_syncsource_cleanup(struct kgsl_process_private *private,
- struct kgsl_syncsource *syncsource)
+static inline void kgsl_syncsource_process_release_syncsources(
+ struct kgsl_process_private *private)
{
}
diff --git a/drivers/hwtracing/coresight/coresight-tmc-etr.c b/drivers/hwtracing/coresight/coresight-tmc-etr.c
index bedb812..9d2ab01 100644
--- a/drivers/hwtracing/coresight/coresight-tmc-etr.c
+++ b/drivers/hwtracing/coresight/coresight-tmc-etr.c
@@ -839,9 +839,10 @@
if (drvdata->mode == CS_MODE_SYSFS)
goto out;
- if (drvdata->out_mode == TMC_ETR_OUT_MODE_MEM)
+ if (drvdata->out_mode == TMC_ETR_OUT_MODE_MEM) {
drvdata->mode = CS_MODE_SYSFS;
tmc_etr_enable_hw(drvdata);
+ }
drvdata->enable = true;
drvdata->sticky_enable = true;
diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig
index bcb861ec..b705f4a 100644
--- a/drivers/input/touchscreen/Kconfig
+++ b/drivers/input/touchscreen/Kconfig
@@ -1205,6 +1205,24 @@
To compile this driver as a module, choose M here: the
module will be called colibri_vf50_ts.
+config TOUCHSCREEN_FT5X06_PSENSOR
+ tristate "FocalTech proximity feature support"
+ depends on TOUCHSCREEN_FT5X06 && SENSORS
+ help
+ Say Y here if you want to support ft5x06's proximity
+ feature.
+
+ If unsure, say N.
+
+config TOUCHSCREEN_FT5X06_GESTURE
+ tristate "FocalTech gesture feature support"
+ depends on TOUCHSCREEN_FT5X06
+ help
+ Say Y here if you want to support ft5x06's gesture
+ feature.
+
+ If unsure, say N.
+
config TOUCHSCREEN_ROHM_BU21023
tristate "ROHM BU21023/24 Dual touch support resistive touchscreens"
depends on I2C
@@ -1227,4 +1245,27 @@
source "drivers/input/touchscreen/synaptics_dsx/Kconfig"
source "drivers/input/touchscreen/focaltech_touch/Kconfig"
+config TOUCHSCREEN_FT5X06
+ tristate "FocalTech touchscreens"
+ depends on I2C
+ help
+ Say Y here if you have a ft5X06 touchscreen.
+ Ft5x06 controllers are multi touch controllers which can
+ report 5 touches at a time.
+
+ If unsure, say N.
+
+ To compile this driver as a module, choose M here: the
+ module will be called ft5x06_ts.
+
+config FT_SECURE_TOUCH
+ bool "Secure Touch support for Focaltech Touchscreen"
+ depends on TOUCHSCREEN_FT5X06
+ help
+ Say Y here
+ -Focaltech touch driver is connected
+ -To enable secure touch for Focaltech touch driver
+
+ If unsure, say N.
+
endif
diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile
index f2749e4..b2f6911 100644
--- a/drivers/input/touchscreen/Makefile
+++ b/drivers/input/touchscreen/Makefile
@@ -37,6 +37,7 @@
obj-$(CONFIG_TOUCHSCREEN_ELO) += elo.o
obj-$(CONFIG_TOUCHSCREEN_EGALAX) += egalax_ts.o
obj-$(CONFIG_TOUCHSCREEN_EGALAX_SERIAL) += egalax_ts_serial.o
+obj-$(CONFIG_TOUCHSCREEN_FT5X06) += ft5x06_ts.o
obj-$(CONFIG_TOUCHSCREEN_FUJITSU) += fujitsu_ts.o
obj-$(CONFIG_TOUCHSCREEN_GOODIX) += goodix.o
obj-$(CONFIG_TOUCHSCREEN_ILI210X) += ili210x.o
diff --git a/drivers/input/touchscreen/ft5x06_ts.c b/drivers/input/touchscreen/ft5x06_ts.c
new file mode 100644
index 0000000..7f320b3
--- /dev/null
+++ b/drivers/input/touchscreen/ft5x06_ts.c
@@ -0,0 +1,2781 @@
+/*
+ *
+ * FocalTech ft5x06 TouchScreen driver.
+ *
+ * Copyright (c) 2010 Focal tech Ltd.
+ * Copyright (c) 2012-2016, 2018 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
+ * may be copied, distributed, and modified under those terms.
+ *
+ * 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 <linux/i2c.h>
+#include <linux/input.h>
+#include <linux/input/mt.h>
+#include <linux/slab.h>
+#include <linux/interrupt.h>
+#include <linux/delay.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/gpio.h>
+#include <linux/of_gpio.h>
+#include <linux/regulator/consumer.h>
+#include <linux/firmware.h>
+#include <linux/debugfs.h>
+#include <linux/input/ft5x06_ts.h>
+#include <linux/init.h>
+#include <linux/fs.h>
+#include <linux/uaccess.h>
+#include <linux/kobject.h>
+#include <linux/sysfs.h>
+
+
+#if defined(CONFIG_FB)
+#include <linux/notifier.h>
+#include <linux/fb.h>
+
+#elif defined(CONFIG_HAS_EARLYSUSPEND)
+#include <linux/earlysuspend.h>
+/* Early-suspend level */
+#define FT_SUSPEND_LEVEL 1
+#endif
+
+#if defined(CONFIG_FT_SECURE_TOUCH)
+#include <linux/completion.h>
+#include <linux/atomic.h>
+#include <linux/clk.h>
+#include <linux/pm_runtime.h>
+static irqreturn_t ft5x06_ts_interrupt(int irq, void *data);
+#endif
+
+#define FT_DRIVER_VERSION 0x02
+
+#define FT_META_REGS 3
+#define FT_ONE_TCH_LEN 6
+#define FT_TCH_LEN(x) (FT_META_REGS + FT_ONE_TCH_LEN * x)
+
+#define FT_PRESS 0x7F
+#define FT_MAX_ID 0x0F
+#define FT_TOUCH_X_H_POS 3
+#define FT_TOUCH_X_L_POS 4
+#define FT_TOUCH_Y_H_POS 5
+#define FT_TOUCH_Y_L_POS 6
+#define FT_TD_STATUS 2
+#define FT_TOUCH_EVENT_POS 3
+#define FT_TOUCH_ID_POS 5
+#define FT_TOUCH_DOWN 0
+#define FT_TOUCH_CONTACT 2
+
+/* register address*/
+#define FT_REG_DEV_MODE 0x00
+#define FT_DEV_MODE_REG_CAL 0x02
+#define FT_REG_ID 0xA3
+#define FT_REG_PMODE 0xA5
+#define FT_REG_FW_VER 0xA6
+#define FT_REG_FW_VENDOR_ID 0xA8
+#define FT_REG_POINT_RATE 0x88
+#define FT_REG_THGROUP 0x80
+#define FT_REG_ECC 0xCC
+#define FT_REG_RESET_FW 0x07
+#define FT_REG_FW_MIN_VER 0xB2
+#define FT_REG_FW_SUB_MIN_VER 0xB3
+
+/* gesture register address*/
+#define FT_REG_GESTURE_ENABLE 0xD0
+#define FT_REG_GESTURE_OUTPUT 0xD3
+
+/* gesture register bits*/
+#define FT_GESTURE_DOUBLECLICK_COORD_X 100
+#define FT_GESTURE_DOUBLECLICK_COORD_Y 100
+#define FT_GESTURE_WAKEUP_TIMEOUT 500
+#define FT_GESTURE_DEFAULT_TRACKING_ID 0x0A
+#define FT_GESTURE_DOUBLECLICK_ID 0x24
+#define FT_GESTURE_POINTER_NUM_MAX 128
+#define FT_GESTURE_POINTER_SIZEOF 4
+#define FT_GESTURE_ID_FLAG_SIZE 1
+#define FT_GESTURE_POINTER_NUM_FLAG_SIZE 1
+/* 6 bytes are taken to mark which gesture is supported in firmware */
+#define FT_GESTURE_SET_FLAG_SIZE 6
+#define I2C_TRANSFER_MAX_BYTE 255
+#define FT_GESTURE_DATA_HEADER (FT_GESTURE_ID_FLAG_SIZE + \
+ FT_GESTURE_POINTER_NUM_FLAG_SIZE + \
+ FT_GESTURE_SET_FLAG_SIZE)
+
+/* power register bits*/
+#define FT_PMODE_ACTIVE 0x00
+#define FT_PMODE_MONITOR 0x01
+#define FT_PMODE_STANDBY 0x02
+#define FT_PMODE_HIBERNATE 0x03
+#define FT_FACTORYMODE_VALUE 0x40
+#define FT_WORKMODE_VALUE 0x00
+#define FT_RST_CMD_REG1 0xFC
+#define FT_RST_CMD_REG2 0xBC
+#define FT_READ_ID_REG 0x90
+#define FT_ERASE_APP_REG 0x61
+#define FT_ERASE_PANEL_REG 0x63
+#define FT_FW_START_REG 0xBF
+
+#define FT_STATUS_NUM_TP_MASK 0x0F
+
+#define FT_VTG_MIN_UV 2600000
+#define FT_VTG_MAX_UV 3300000
+#define FT_I2C_VTG_MIN_UV 1800000
+#define FT_I2C_VTG_MAX_UV 1800000
+
+#define FT_COORDS_ARR_SIZE 4
+#define MAX_BUTTONS 4
+
+#define FT_8BIT_SHIFT 8
+#define FT_4BIT_SHIFT 4
+#define FT_FW_NAME_MAX_LEN 50
+
+#define FT5316_ID 0x0A
+#define FT5306I_ID 0x55
+#define FT6X06_ID 0x06
+#define FT6X36_ID 0x36
+
+#define FT_UPGRADE_AA 0xAA
+#define FT_UPGRADE_55 0x55
+
+#define FT_FW_MIN_SIZE 8
+#define FT_FW_MAX_SIZE 32768
+
+/* Firmware file is not supporting minor and sub minor so use 0 */
+#define FT_FW_FILE_MAJ_VER(x) ((x)->data[(x)->size - 2])
+#define FT_FW_FILE_MIN_VER(x) 0
+#define FT_FW_FILE_SUB_MIN_VER(x) 0
+#define FT_FW_FILE_VENDOR_ID(x) ((x)->data[(x)->size - 1])
+
+#define FT_FW_FILE_MAJ_VER_FT6X36(x) ((x)->data[0x10a])
+#define FT_FW_FILE_VENDOR_ID_FT6X36(x) ((x)->data[0x108])
+
+/**
+ * Application data verification will be run before upgrade flow.
+ * Firmware image stores some flags with negative and positive value
+ * in corresponding addresses, we need pick them out do some check to
+ * make sure the application data is valid.
+ */
+#define FT_FW_CHECK(x, ts_data) \
+ (ts_data->family_id == FT6X36_ID ? \
+ (((x)->data[0x104] ^ (x)->data[0x105]) == 0xFF \
+ && ((x)->data[0x106] ^ (x)->data[0x107]) == 0xFF) : \
+ (((x)->data[(x)->size - 8] ^ (x)->data[(x)->size - 6]) == 0xFF \
+ && ((x)->data[(x)->size - 7] ^ (x)->data[(x)->size - 5]) == 0xFF \
+ && ((x)->data[(x)->size - 3] ^ (x)->data[(x)->size - 4]) == 0xFF))
+
+#define FT_MAX_TRIES 5
+#define FT_RETRY_DLY 20
+
+#define FT_MAX_WR_BUF 10
+#define FT_MAX_RD_BUF 2
+#define FT_FW_PKT_LEN 128
+#define FT_FW_PKT_META_LEN 6
+#define FT_FW_PKT_DLY_MS 20
+#define FT_FW_LAST_PKT 0x6ffa
+#define FT_EARSE_DLY_MS 100
+#define FT_55_AA_DLY_NS 5000
+
+#define FT_UPGRADE_LOOP 30
+#define FT_CAL_START 0x04
+#define FT_CAL_FIN 0x00
+#define FT_CAL_STORE 0x05
+#define FT_CAL_RETRY 100
+#define FT_REG_CAL 0x00
+#define FT_CAL_MASK 0x70
+
+#define FT_INFO_MAX_LEN 512
+
+#define FT_BLOADER_SIZE_OFF 12
+#define FT_BLOADER_NEW_SIZE 30
+#define FT_DATA_LEN_OFF_OLD_FW 8
+#define FT_DATA_LEN_OFF_NEW_FW 14
+#define FT_FINISHING_PKT_LEN_OLD_FW 6
+#define FT_FINISHING_PKT_LEN_NEW_FW 12
+#define FT_MAGIC_BLOADER_Z7 0x7bfa
+#define FT_MAGIC_BLOADER_LZ4 0x6ffa
+#define FT_MAGIC_BLOADER_GZF_30 0x7ff4
+#define FT_MAGIC_BLOADER_GZF 0x7bf4
+
+#define PINCTRL_STATE_ACTIVE "pmx_ts_active"
+#define PINCTRL_STATE_SUSPEND "pmx_ts_suspend"
+#define PINCTRL_STATE_RELEASE "pmx_ts_release"
+
+static irqreturn_t ft5x06_ts_interrupt(int irq, void *data);
+
+enum {
+ FT_BLOADER_VERSION_LZ4 = 0,
+ FT_BLOADER_VERSION_Z7 = 1,
+ FT_BLOADER_VERSION_GZF = 2,
+};
+
+enum {
+ FT_FT5336_FAMILY_ID_0x11 = 0x11,
+ FT_FT5336_FAMILY_ID_0x12 = 0x12,
+ FT_FT5336_FAMILY_ID_0x13 = 0x13,
+ FT_FT5336_FAMILY_ID_0x14 = 0x14,
+};
+
+#define FT_STORE_TS_INFO(buf, id, fw_maj, fw_min, fw_sub_min) \
+ snprintf(buf, FT_INFO_MAX_LEN, \
+ "vendor name = Focaltech\n" \
+ "model = 0x%x\n" \
+ "fw_version = %d.%d.%d\n", \
+ id, fw_maj, fw_min, fw_sub_min)
+#define FT_TS_INFO_SYSFS_DIR_NAME "ts_info"
+static char *ts_info_buff;
+
+#define FT_STORE_TS_DBG_INFO(buf, id, name, max_tch, group_id, \
+ fw_vkey_support, fw_name, fw_maj, fw_min, fw_sub_min) \
+ snprintf(buf, FT_INFO_MAX_LEN, \
+ "controller\t= focaltech\n" \
+ "model\t\t= 0x%x\n" \
+ "name\t\t= %s\n" \
+ "max_touches\t= %d\n" \
+ "drv_ver\t\t= 0x%x\n" \
+ "group_id\t= 0x%x\n" \
+ "fw_vkey_support\t= %s\n" \
+ "fw_name\t\t= %s\n" \
+ "fw_ver\t\t= %d.%d.%d\n", id, name, \
+ max_tch, FT_DRIVER_VERSION, group_id, \
+ fw_vkey_support, fw_name, fw_maj, fw_min, \
+ fw_sub_min)
+
+#define FT_DEBUG_DIR_NAME "ts_debug"
+
+struct ft5x06_ts_data {
+ struct i2c_client *client;
+ struct input_dev *input_dev;
+ const struct ft5x06_ts_platform_data *pdata;
+ struct ft5x06_gesture_platform_data *gesture_pdata;
+ struct regulator *vdd;
+ struct regulator *vcc_i2c;
+ struct mutex ft_clk_io_ctrl_mutex;
+ char fw_name[FT_FW_NAME_MAX_LEN];
+ bool loading_fw;
+ u8 family_id;
+ struct dentry *dir;
+ u16 addr;
+ bool suspended;
+ char *ts_info;
+ u8 *tch_data;
+ u32 tch_data_len;
+ u8 fw_ver[3];
+ u8 fw_vendor_id;
+ struct kobject *ts_info_kobj;
+#if defined(CONFIG_FB)
+ struct work_struct fb_notify_work;
+ struct notifier_block fb_notif;
+#elif defined(CONFIG_HAS_EARLYSUSPEND)
+ struct early_suspend early_suspend;
+#endif
+ struct pinctrl *ts_pinctrl;
+ struct pinctrl_state *pinctrl_state_active;
+ struct pinctrl_state *pinctrl_state_suspend;
+ struct pinctrl_state *pinctrl_state_release;
+#if defined(CONFIG_FT_SECURE_TOUCH)
+ atomic_t st_enabled;
+ atomic_t st_pending_irqs;
+ struct completion st_powerdown;
+ struct completion st_irq_processed;
+ bool st_initialized;
+ struct clk *core_clk;
+ struct clk *iface_clk;
+#endif
+};
+
+static int ft5x06_ts_start(struct device *dev);
+static int ft5x06_ts_stop(struct device *dev);
+
+#if defined(CONFIG_FT_SECURE_TOUCH)
+static void ft5x06_secure_touch_init(struct ft5x06_ts_data *data)
+{
+ data->st_initialized = 0;
+
+ init_completion(&data->st_powerdown);
+ init_completion(&data->st_irq_processed);
+
+ /* Get clocks */
+ data->core_clk = devm_clk_get(&data->client->dev, "core_clk");
+ if (IS_ERR(data->core_clk)) {
+ data->core_clk = NULL;
+ dev_warn(&data->client->dev,
+ "%s: core_clk is not defined\n", __func__);
+ }
+
+ data->iface_clk = devm_clk_get(&data->client->dev, "iface_clk");
+ if (IS_ERR(data->iface_clk)) {
+ data->iface_clk = NULL;
+ dev_warn(&data->client->dev,
+ "%s: iface_clk is not defined", __func__);
+ }
+ data->st_initialized = 1;
+}
+
+static void ft5x06_secure_touch_notify(struct ft5x06_ts_data *data)
+{
+ sysfs_notify(&data->input_dev->dev.kobj, NULL, "secure_touch");
+}
+
+static irqreturn_t ft5x06_filter_interrupt(struct ft5x06_ts_data *data)
+{
+ if (atomic_read(&data->st_enabled)) {
+ if (atomic_cmpxchg(&data->st_pending_irqs, 0, 1) == 0) {
+ reinit_completion(&data->st_irq_processed);
+ ft5x06_secure_touch_notify(data);
+ wait_for_completion_interruptible(
+ &data->st_irq_processed);
+ }
+ return IRQ_HANDLED;
+ }
+ return IRQ_NONE;
+}
+
+/*
+ * 'blocking' variable will have value 'true' when we want to prevent the driver
+ * from accessing the xPU/SMMU protected HW resources while the session is
+ * active.
+ */
+static void ft5x06_secure_touch_stop(struct ft5x06_ts_data *data, bool blocking)
+{
+ if (atomic_read(&data->st_enabled)) {
+ atomic_set(&data->st_pending_irqs, -1);
+ ft5x06_secure_touch_notify(data);
+ if (blocking)
+ wait_for_completion_interruptible(
+ &data->st_powerdown);
+ }
+}
+
+static int ft5x06_clk_prepare_enable(struct ft5x06_ts_data *data)
+{
+ int ret;
+
+ ret = clk_prepare_enable(data->iface_clk);
+ if (ret) {
+ dev_err(&data->client->dev,
+ "error on clk_prepare_enable(iface_clk):%d\n", ret);
+ return ret;
+ }
+
+ ret = clk_prepare_enable(data->core_clk);
+ if (ret) {
+ clk_disable_unprepare(data->iface_clk);
+ dev_err(&data->client->dev,
+ "error clk_prepare_enable(core_clk):%d\n", ret);
+ }
+ return ret;
+}
+
+static void ft5x06_clk_disable_unprepare(struct ft5x06_ts_data *data)
+{
+ clk_disable_unprepare(data->core_clk);
+ clk_disable_unprepare(data->iface_clk);
+}
+
+static int ft5x06_bus_get(struct ft5x06_ts_data *data)
+{
+ int retval;
+
+ mutex_lock(&data->ft_clk_io_ctrl_mutex);
+ retval = pm_runtime_get_sync(data->client->adapter->dev.parent);
+ if (retval >= 0 && data->core_clk != NULL && data->iface_clk != NULL) {
+ retval = ft5x06_clk_prepare_enable(data);
+ if (retval)
+ pm_runtime_put_sync(data->client->adapter->dev.parent);
+ }
+ mutex_unlock(&data->ft_clk_io_ctrl_mutex);
+ return retval;
+}
+
+static void ft5x06_bus_put(struct ft5x06_ts_data *data)
+{
+ mutex_lock(&data->ft_clk_io_ctrl_mutex);
+ if (data->core_clk != NULL && data->iface_clk != NULL)
+ ft5x06_clk_disable_unprepare(data);
+ pm_runtime_put_sync(data->client->adapter->dev.parent);
+ mutex_unlock(&data->ft_clk_io_ctrl_mutex);
+}
+
+static ssize_t ft5x06_secure_touch_enable_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+
+ return scnprintf(buf, PAGE_SIZE, "%d", atomic_read(&data->st_enabled));
+}
+
+/*
+ * Accept only "0" and "1" valid values.
+ * "0" will reset the st_enabled flag, then wake up the reading process and
+ * the interrupt handler.
+ * The bus driver is notified via pm_runtime that it is not required to stay
+ * awake anymore.
+ * It will also make sure the queue of events is emptied in the controller,
+ * in case a touch happened in between the secure touch being disabled and
+ * the local ISR being ungated.
+ * "1" will set the st_enabled flag and clear the st_pending_irqs flag.
+ * The bus driver is requested via pm_runtime to stay awake.
+ */
+static ssize_t ft5x06_secure_touch_enable_store(struct device *dev,
+ struct device_attribute *attr, const char *buf, size_t count)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ unsigned long value;
+ int err = 0;
+
+ if (count > 2)
+ return -EINVAL;
+ err = kstrtoul(buf, 10, &value);
+ if (err != 0)
+ return err;
+
+ if (!data->st_initialized)
+ return -EIO;
+
+ err = count;
+ switch (value) {
+ case 0:
+ if (atomic_read(&data->st_enabled) == 0)
+ break;
+ ft5x06_bus_put(data);
+ atomic_set(&data->st_enabled, 0);
+ ft5x06_secure_touch_notify(data);
+ complete(&data->st_irq_processed);
+ ft5x06_ts_interrupt(data->client->irq, data);
+ complete(&data->st_powerdown);
+ break;
+
+ case 1:
+ if (atomic_read(&data->st_enabled)) {
+ err = -EBUSY;
+ break;
+ }
+ synchronize_irq(data->client->irq);
+ if (ft5x06_bus_get(data) < 0) {
+ dev_err(&data->client->dev, "ft5x06_bus_get failed\n");
+ err = -EIO;
+ break;
+ }
+ reinit_completion(&data->st_powerdown);
+ reinit_completion(&data->st_irq_processed);
+ atomic_set(&data->st_enabled, 1);
+ atomic_set(&data->st_pending_irqs, 0);
+ break;
+
+ default:
+ dev_err(&data->client->dev, "unsupported value: %lu\n", value);
+ err = -EINVAL;
+ break;
+ }
+ return err;
+}
+
+/*
+ * This function returns whether there are pending interrupts, or
+ * other error conditions that need to be signaled to the userspace library,
+ * according tot he following logic:
+ * - st_enabled is 0 if secure touch is not enabled, returning -EBADF
+ * - st_pending_irqs is -1 to signal that secure touch is in being stopped,
+ * returning -EINVAL
+ * - st_pending_irqs is 1 to signal that there is a pending irq, returning
+ * the value "1" to the sysfs read operation
+ * - st_pending_irqs is 0 (only remaining case left) if the pending interrupt
+ * has been processed, so the interrupt handler can be allowed to continue.
+ */
+static ssize_t ft5x06_secure_touch_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ int val = 0;
+
+ if (atomic_read(&data->st_enabled) == 0)
+ return -EBADF;
+ if (atomic_cmpxchg(&data->st_pending_irqs, -1, 0) == -1)
+ return -EINVAL;
+ if (atomic_cmpxchg(&data->st_pending_irqs, 1, 0) == 1)
+ val = 1;
+ else
+ complete(&data->st_irq_processed);
+ return scnprintf(buf, PAGE_SIZE, "%u", val);
+}
+#else
+static void ft5x06_secure_touch_init(struct ft5x06_ts_data *data)
+{
+}
+static irqreturn_t ft5x06_filter_interrupt(struct ft5x06_ts_data *data)
+{
+ return IRQ_NONE;
+}
+static void ft5x06_secure_touch_stop(struct ft5x06_ts_data *data, bool blocking)
+{
+}
+#endif
+
+static struct device_attribute attrs[] = {
+#if defined(CONFIG_FT_SECURE_TOUCH)
+ __ATTR(secure_touch_enable, (0664),
+ ft5x06_secure_touch_enable_show,
+ ft5x06_secure_touch_enable_store),
+ __ATTR(secure_touch, 0444,
+ ft5x06_secure_touch_show, NULL),
+#endif
+};
+
+static inline bool ft5x06_gesture_support_enabled(void)
+{
+ return IS_ENABLED(CONFIG_TOUCHSCREEN_FT5X06_GESTURE);
+}
+
+static int ft5x06_i2c_read(struct i2c_client *client, char *writebuf,
+ int writelen, char *readbuf, int readlen)
+{
+ int ret;
+
+ if (writelen > 0) {
+ struct i2c_msg msgs[] = {
+ {
+ .addr = client->addr,
+ .flags = 0,
+ .len = writelen,
+ .buf = writebuf,
+ },
+ {
+ .addr = client->addr,
+ .flags = I2C_M_RD,
+ .len = readlen,
+ .buf = readbuf,
+ },
+ };
+ ret = i2c_transfer(client->adapter, msgs, 2);
+ if (ret < 0)
+ dev_err(&client->dev, "%s: i2c read error.\n",
+ __func__);
+ } else {
+ struct i2c_msg msgs[] = {
+ {
+ .addr = client->addr,
+ .flags = I2C_M_RD,
+ .len = readlen,
+ .buf = readbuf,
+ },
+ };
+ ret = i2c_transfer(client->adapter, msgs, 1);
+ if (ret < 0)
+ dev_err(&client->dev, "%s:i2c read error.\n", __func__);
+ }
+ return ret;
+}
+
+static int ft5x06_i2c_write(struct i2c_client *client, char *writebuf,
+ int writelen)
+{
+ int ret;
+
+ struct i2c_msg msgs[] = {
+ {
+ .addr = client->addr,
+ .flags = 0,
+ .len = writelen,
+ .buf = writebuf,
+ },
+ };
+ ret = i2c_transfer(client->adapter, msgs, 1);
+ if (ret < 0)
+ dev_err(&client->dev, "%s: i2c write error.\n", __func__);
+
+ return ret;
+}
+
+static int ft5x0x_write_reg(struct i2c_client *client, u8 addr, const u8 val)
+{
+ u8 buf[2] = {0};
+
+ buf[0] = addr;
+ buf[1] = val;
+
+ return ft5x06_i2c_write(client, buf, sizeof(buf));
+}
+
+static int ft5x0x_read_reg(struct i2c_client *client, u8 addr, u8 *val)
+{
+ return ft5x06_i2c_read(client, &addr, 1, val, 1);
+}
+
+#ifdef CONFIG_TOUCHSCREEN_FT5X06_GESTURE
+static ssize_t ft5x06_gesture_enable_to_set_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+
+ return scnprintf(buf, PAGE_SIZE, "%d\n",
+ data->gesture_pdata->gesture_enable_to_set);
+}
+
+static ssize_t ft5x06_gesture_enable_to_set_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t size)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ unsigned long value = 0;
+ int ret;
+
+ if (data->suspended)
+ return -EINVAL;
+
+ ret = kstrtoul(buf, 16, &value);
+ if (ret < 0) {
+ dev_err(dev, "%s:kstrtoul failed, ret=0x%x\n",
+ __func__, ret);
+ return ret;
+ }
+
+ if (value == 1)
+ data->gesture_pdata->gesture_enable_to_set = 1;
+ else
+ data->gesture_pdata->gesture_enable_to_set = 0;
+ return size;
+}
+
+static DEVICE_ATTR(enable, 0664,
+ ft5x06_gesture_enable_to_set_show,
+ ft5x06_gesture_enable_to_set_store);
+
+static int ft5x06_entry_pocket(struct device *dev)
+{
+ return ft5x06_ts_stop(dev);
+}
+
+static int ft5x06_leave_pocket(struct device *dev)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ int err;
+
+ ft5x06_ts_start(dev);
+ ft5x0x_write_reg(data->client, FT_REG_GESTURE_ENABLE, 1);
+ err = enable_irq_wake(data->client->irq);
+ if (err)
+ dev_err(&data->client->dev,
+ "%s: set_irq_wake failed\n", __func__);
+ data->suspended = true;
+
+ return err;
+}
+
+static ssize_t gesture_in_pocket_mode_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+
+ return scnprintf(buf, PAGE_SIZE, "%d\n",
+ data->gesture_pdata->in_pocket);
+}
+
+static ssize_t gesture_in_pocket_mode_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t size)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ unsigned long value = 0;
+ int ret;
+
+ ret = kstrtoul(buf, 16, &value);
+ if (ret < 0) {
+ dev_err(dev, "%s:kstrtoul failed, ret=0x%x\n",
+ __func__, ret);
+ return ret;
+ }
+
+ if (value == 1 && data->gesture_pdata->in_pocket == 0) {
+ data->gesture_pdata->in_pocket = 1;
+ ft5x06_entry_pocket(dev);
+ } else if (value == 0 && data->gesture_pdata->in_pocket == 1) {
+ ft5x06_leave_pocket(dev);
+ data->gesture_pdata->in_pocket = 0;
+ }
+ return size;
+}
+
+static DEVICE_ATTR(pocket, 0664,
+ gesture_in_pocket_mode_show,
+ gesture_in_pocket_mode_store);
+
+static int ft5x06_report_gesture_doubleclick(struct input_dev *ip_dev)
+{
+ int i;
+
+ for (i = 0; i < 2; i++) {
+ input_mt_slot(ip_dev, FT_GESTURE_DEFAULT_TRACKING_ID);
+ input_mt_report_slot_state(ip_dev, MT_TOOL_FINGER, 1);
+ input_report_abs(ip_dev, ABS_MT_POSITION_X,
+ FT_GESTURE_DOUBLECLICK_COORD_X);
+ input_report_abs(ip_dev, ABS_MT_POSITION_Y,
+ FT_GESTURE_DOUBLECLICK_COORD_Y);
+ input_mt_report_pointer_emulation(ip_dev, false);
+ input_sync(ip_dev);
+ input_mt_slot(ip_dev, FT_GESTURE_DEFAULT_TRACKING_ID);
+ input_mt_report_slot_state(ip_dev, MT_TOOL_FINGER, 0);
+ input_mt_report_pointer_emulation(ip_dev, false);
+ input_sync(ip_dev);
+ }
+ return 0;
+}
+
+static int ft5x06_report_gesture(struct i2c_client *i2c_client,
+ struct input_dev *ip_dev)
+{
+ int i, temp, gesture_data_size;
+ int gesture_coord_x, gesture_coord_y;
+ int ret = -1;
+ short pointnum = 0;
+ unsigned char buf[FT_GESTURE_POINTER_NUM_MAX *
+ FT_GESTURE_POINTER_SIZEOF + FT_GESTURE_DATA_HEADER];
+
+ buf[0] = FT_REG_GESTURE_OUTPUT;
+ ret = ft5x06_i2c_read(i2c_client, buf, 1,
+ buf, FT_GESTURE_DATA_HEADER);
+ if (ret < 0) {
+ dev_err(&i2c_client->dev, "%s read touchdata failed.\n",
+ __func__);
+ return ret;
+ }
+
+ /* FW support doubleclick */
+ if (buf[0] == FT_GESTURE_DOUBLECLICK_ID) {
+ ft5x06_report_gesture_doubleclick(ip_dev);
+ return 0;
+ }
+
+ pointnum = (short)(buf[1]) & 0xff;
+ gesture_data_size = pointnum * FT_GESTURE_POINTER_SIZEOF +
+ FT_GESTURE_DATA_HEADER;
+ buf[0] = FT_REG_GESTURE_OUTPUT;
+ temp = gesture_data_size / I2C_TRANSFER_MAX_BYTE;
+ for (i = 0; i < temp; i++)
+ ret = ft5x06_i2c_read(i2c_client, buf, ((i == 0) ? 1 : 0),
+ buf + I2C_TRANSFER_MAX_BYTE * i, I2C_TRANSFER_MAX_BYTE);
+ ret = ft5x06_i2c_read(i2c_client, buf, ((temp == 0) ? 1 : 0),
+ buf + I2C_TRANSFER_MAX_BYTE * temp,
+ gesture_data_size - I2C_TRANSFER_MAX_BYTE * temp);
+ if (ret < 0) {
+ dev_err(&i2c_client->dev, "%s read touchdata failed.\n",
+ __func__);
+ return ret;
+ }
+
+ for (i = 0; i < pointnum; i++) {
+ gesture_coord_x = (((s16) buf[FT_GESTURE_DATA_HEADER +
+ (FT_GESTURE_POINTER_SIZEOF * i)]) & 0x0F) << 8 |
+ (((s16) buf[FT_GESTURE_DATA_HEADER + 1 +
+ (FT_GESTURE_POINTER_SIZEOF * i)]) & 0xFF);
+ gesture_coord_y = (((s16) buf[FT_GESTURE_DATA_HEADER + 2 +
+ (FT_GESTURE_POINTER_SIZEOF * i)]) & 0x0F) << 8 |
+ (((s16) buf[FT_GESTURE_DATA_HEADER + 3 +
+ (FT_GESTURE_POINTER_SIZEOF * i)]) & 0xFF);
+ input_mt_slot(ip_dev, FT_GESTURE_DEFAULT_TRACKING_ID);
+ input_mt_report_slot_state(ip_dev, MT_TOOL_FINGER, 1);
+ input_report_abs(ip_dev, ABS_MT_POSITION_X, gesture_coord_x);
+ input_report_abs(ip_dev, ABS_MT_POSITION_Y, gesture_coord_y);
+ input_mt_report_pointer_emulation(ip_dev, false);
+ input_sync(ip_dev);
+ }
+ input_mt_slot(ip_dev, FT_GESTURE_DEFAULT_TRACKING_ID);
+ input_mt_report_slot_state(ip_dev, MT_TOOL_FINGER, 0);
+ input_mt_report_pointer_emulation(ip_dev, false);
+ input_sync(ip_dev);
+
+ return 0;
+}
+#else
+static DEVICE_ATTR(pocket, 0664, NULL, NULL);
+static DEVICE_ATTR(enable, 0664, NULL, NULL);
+
+static int ft5x06_report_gesture(struct i2c_client *i2c_client,
+ struct input_dev *ip_dev)
+{
+ return 0;
+}
+#endif
+
+static void ft5x06_update_fw_vendor_id(struct ft5x06_ts_data *data)
+{
+ struct i2c_client *client = data->client;
+ u8 reg_addr;
+ int err;
+
+ reg_addr = FT_REG_FW_VENDOR_ID;
+ err = ft5x06_i2c_read(client, ®_addr, 1, &data->fw_vendor_id, 1);
+ if (err < 0)
+ dev_err(&client->dev, "fw vendor id read failed");
+}
+
+static void ft5x06_update_fw_ver(struct ft5x06_ts_data *data)
+{
+ struct i2c_client *client = data->client;
+ u8 reg_addr;
+ int err;
+
+ reg_addr = FT_REG_FW_VER;
+ err = ft5x06_i2c_read(client, ®_addr, 1, &data->fw_ver[0], 1);
+ if (err < 0)
+ dev_err(&client->dev, "fw major version read failed");
+
+ reg_addr = FT_REG_FW_MIN_VER;
+ err = ft5x06_i2c_read(client, ®_addr, 1, &data->fw_ver[1], 1);
+ if (err < 0)
+ dev_err(&client->dev, "fw minor version read failed");
+
+ reg_addr = FT_REG_FW_SUB_MIN_VER;
+ err = ft5x06_i2c_read(client, ®_addr, 1, &data->fw_ver[2], 1);
+ if (err < 0)
+ dev_err(&client->dev, "fw sub minor version read failed");
+
+ dev_info(&client->dev, "Firmware version = %d.%d.%d\n",
+ data->fw_ver[0], data->fw_ver[1], data->fw_ver[2]);
+}
+
+static irqreturn_t ft5x06_ts_interrupt(int irq, void *dev_id)
+{
+ struct ft5x06_ts_data *data = dev_id;
+ struct input_dev *ip_dev;
+ int rc, i;
+ u32 id, x, y, status, num_touches;
+ u8 reg, *buf, gesture_is_active;
+ bool update_input = false;
+
+ if (!data) {
+ pr_err("%s: Invalid data\n", __func__);
+ return IRQ_HANDLED;
+ }
+
+ if (ft5x06_filter_interrupt(data) == IRQ_HANDLED)
+ return IRQ_HANDLED;
+
+ ip_dev = data->input_dev;
+ buf = data->tch_data;
+
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support) {
+ ft5x0x_read_reg(data->client, FT_REG_GESTURE_ENABLE,
+ &gesture_is_active);
+ if (gesture_is_active) {
+ pm_wakeup_event(&(data->client->dev),
+ FT_GESTURE_WAKEUP_TIMEOUT);
+ ft5x06_report_gesture(data->client, ip_dev);
+ return IRQ_HANDLED;
+ }
+ }
+
+ /*
+ * Read touch data start from register FT_REG_DEV_MODE.
+ * The touch x/y value start from FT_TOUCH_X_H/L_POS and
+ * FT_TOUCH_Y_H/L_POS in buf.
+ */
+ reg = FT_REG_DEV_MODE;
+ rc = ft5x06_i2c_read(data->client, ®, 1, buf, data->tch_data_len);
+ if (rc < 0) {
+ dev_err(&data->client->dev, "%s: read data fail\n", __func__);
+ return IRQ_HANDLED;
+ }
+
+ for (i = 0; i < data->pdata->num_max_touches; i++) {
+ /*
+ * Getting the finger ID of the touch event incase of
+ * multiple touch events
+ */
+ id = (buf[FT_TOUCH_ID_POS + FT_ONE_TCH_LEN * i]) >> 4;
+ if (id >= FT_MAX_ID)
+ break;
+
+ update_input = true;
+
+ x = (buf[FT_TOUCH_X_H_POS + FT_ONE_TCH_LEN * i] & 0x0F) << 8 |
+ (buf[FT_TOUCH_X_L_POS + FT_ONE_TCH_LEN * i]);
+ y = (buf[FT_TOUCH_Y_H_POS + FT_ONE_TCH_LEN * i] & 0x0F) << 8 |
+ (buf[FT_TOUCH_Y_L_POS + FT_ONE_TCH_LEN * i]);
+
+ status = buf[FT_TOUCH_EVENT_POS + FT_ONE_TCH_LEN * i] >> 6;
+
+ num_touches = buf[FT_TD_STATUS] & FT_STATUS_NUM_TP_MASK;
+
+ /* invalid combination */
+ if (!num_touches && !status && !id)
+ break;
+
+ input_mt_slot(ip_dev, id);
+ if (status == FT_TOUCH_DOWN || status == FT_TOUCH_CONTACT) {
+ input_mt_report_slot_state(ip_dev, MT_TOOL_FINGER, 1);
+ input_report_abs(ip_dev, ABS_MT_POSITION_X, x);
+ input_report_abs(ip_dev, ABS_MT_POSITION_Y, y);
+ } else {
+ input_mt_report_slot_state(ip_dev, MT_TOOL_FINGER, 0);
+ }
+ }
+
+ if (update_input) {
+ input_mt_report_pointer_emulation(ip_dev, false);
+ input_sync(ip_dev);
+ }
+
+ return IRQ_HANDLED;
+}
+
+static int ft5x06_gpio_configure(struct ft5x06_ts_data *data, bool on)
+{
+ int err = 0;
+
+ if (on) {
+ if (gpio_is_valid(data->pdata->irq_gpio)) {
+ err = gpio_request(data->pdata->irq_gpio,
+ "ft5x06_irq_gpio");
+ if (err) {
+ dev_err(&data->client->dev,
+ "irq gpio request failed");
+ goto err_irq_gpio_req;
+ }
+
+ err = gpio_direction_input(data->pdata->irq_gpio);
+ if (err) {
+ dev_err(&data->client->dev,
+ "set_direction for irq gpio failed\n");
+ goto err_irq_gpio_dir;
+ }
+ }
+
+ if (gpio_is_valid(data->pdata->reset_gpio)) {
+ err = gpio_request(data->pdata->reset_gpio,
+ "ft5x06_reset_gpio");
+ if (err) {
+ dev_err(&data->client->dev,
+ "reset gpio request failed");
+ goto err_irq_gpio_dir;
+ }
+
+ err = gpio_direction_output(data->pdata->reset_gpio, 0);
+ if (err) {
+ dev_err(&data->client->dev,
+ "set_direction for reset gpio failed\n");
+ goto err_reset_gpio_dir;
+ }
+ msleep(data->pdata->hard_rst_dly);
+ gpio_set_value_cansleep(data->pdata->reset_gpio, 1);
+ }
+
+ return 0;
+ }
+ if (gpio_is_valid(data->pdata->irq_gpio))
+ gpio_free(data->pdata->irq_gpio);
+ if (gpio_is_valid(data->pdata->reset_gpio)) {
+ /*
+ * This is intended to save leakage current
+ * only. Even if the call(gpio_direction_input)
+ * fails, only leakage current will be more but
+ * functionality will not be affected.
+ */
+ err = gpio_direction_input(data->pdata->reset_gpio);
+ if (err) {
+ dev_err(&data->client->dev,
+ "unable to set direction for gpio [%d]\n",
+ data->pdata->irq_gpio);
+ }
+ gpio_free(data->pdata->reset_gpio);
+ }
+
+ return 0;
+
+err_reset_gpio_dir:
+ if (gpio_is_valid(data->pdata->reset_gpio))
+ gpio_free(data->pdata->reset_gpio);
+err_irq_gpio_dir:
+ if (gpio_is_valid(data->pdata->irq_gpio))
+ gpio_free(data->pdata->irq_gpio);
+err_irq_gpio_req:
+ return err;
+}
+
+static int ft5x06_power_on(struct ft5x06_ts_data *data, bool on)
+{
+ int rc;
+
+ if (!on)
+ goto power_off;
+
+ rc = regulator_enable(data->vdd);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator vdd enable failed rc=%d\n", rc);
+ return rc;
+ }
+
+ rc = regulator_enable(data->vcc_i2c);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator vcc_i2c enable failed rc=%d\n", rc);
+ regulator_disable(data->vdd);
+ }
+
+ return rc;
+
+power_off:
+ rc = regulator_disable(data->vdd);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator vdd disable failed rc=%d\n", rc);
+ return rc;
+ }
+
+ rc = regulator_disable(data->vcc_i2c);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator vcc_i2c disable failed rc=%d\n", rc);
+ rc = regulator_enable(data->vdd);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator vdd enable failed rc=%d\n", rc);
+ }
+ }
+
+ return rc;
+}
+
+static int ft5x06_power_init(struct ft5x06_ts_data *data, bool on)
+{
+ int rc;
+
+ if (!on)
+ goto pwr_deinit;
+
+ data->vdd = regulator_get(&data->client->dev, "vdd");
+ if (IS_ERR(data->vdd)) {
+ rc = PTR_ERR(data->vdd);
+ dev_err(&data->client->dev,
+ "Regulator get failed vdd rc=%d\n", rc);
+ return rc;
+ }
+
+ if (regulator_count_voltages(data->vdd) > 0) {
+ rc = regulator_set_voltage(data->vdd, FT_VTG_MIN_UV,
+ FT_VTG_MAX_UV);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator set_vtg failed vdd rc=%d\n", rc);
+ goto reg_vdd_put;
+ }
+ }
+
+ data->vcc_i2c = regulator_get(&data->client->dev, "vcc_i2c");
+ if (IS_ERR(data->vcc_i2c)) {
+ rc = PTR_ERR(data->vcc_i2c);
+ dev_err(&data->client->dev,
+ "Regulator get failed vcc_i2c rc=%d\n", rc);
+ goto reg_vdd_set_vtg;
+ }
+
+ if (regulator_count_voltages(data->vcc_i2c) > 0) {
+ rc = regulator_set_voltage(data->vcc_i2c, FT_I2C_VTG_MIN_UV,
+ FT_I2C_VTG_MAX_UV);
+ if (rc) {
+ dev_err(&data->client->dev,
+ "Regulator set_vtg failed vcc_i2c rc=%d\n", rc);
+ goto reg_vcc_i2c_put;
+ }
+ }
+
+ return 0;
+
+reg_vcc_i2c_put:
+ regulator_put(data->vcc_i2c);
+reg_vdd_set_vtg:
+ if (regulator_count_voltages(data->vdd) > 0)
+ regulator_set_voltage(data->vdd, 0, FT_VTG_MAX_UV);
+reg_vdd_put:
+ regulator_put(data->vdd);
+ return rc;
+
+pwr_deinit:
+ if (regulator_count_voltages(data->vdd) > 0)
+ regulator_set_voltage(data->vdd, 0, FT_VTG_MAX_UV);
+
+ regulator_put(data->vdd);
+
+ if (regulator_count_voltages(data->vcc_i2c) > 0)
+ regulator_set_voltage(data->vcc_i2c, 0, FT_I2C_VTG_MAX_UV);
+
+ regulator_put(data->vcc_i2c);
+ return 0;
+}
+
+static int ft5x06_ts_pinctrl_init(struct ft5x06_ts_data *ft5x06_data)
+{
+ int retval;
+
+ /* Get pinctrl if target uses pinctrl */
+ ft5x06_data->ts_pinctrl = devm_pinctrl_get(&(ft5x06_data->client->dev));
+ if (IS_ERR_OR_NULL(ft5x06_data->ts_pinctrl)) {
+ retval = PTR_ERR(ft5x06_data->ts_pinctrl);
+ dev_dbg(&ft5x06_data->client->dev,
+ "Target does not use pinctrl %d\n", retval);
+ goto err_pinctrl_get;
+ }
+
+ ft5x06_data->pinctrl_state_active
+ = pinctrl_lookup_state(ft5x06_data->ts_pinctrl,
+ PINCTRL_STATE_ACTIVE);
+ if (IS_ERR_OR_NULL(ft5x06_data->pinctrl_state_active)) {
+ retval = PTR_ERR(ft5x06_data->pinctrl_state_active);
+ dev_err(&ft5x06_data->client->dev,
+ "Can not lookup %s pinstate %d\n",
+ PINCTRL_STATE_ACTIVE, retval);
+ goto err_pinctrl_lookup;
+ }
+
+ ft5x06_data->pinctrl_state_suspend
+ = pinctrl_lookup_state(ft5x06_data->ts_pinctrl,
+ PINCTRL_STATE_SUSPEND);
+ if (IS_ERR_OR_NULL(ft5x06_data->pinctrl_state_suspend)) {
+ retval = PTR_ERR(ft5x06_data->pinctrl_state_suspend);
+ dev_err(&ft5x06_data->client->dev,
+ "Can not lookup %s pinstate %d\n",
+ PINCTRL_STATE_SUSPEND, retval);
+ goto err_pinctrl_lookup;
+ }
+
+ ft5x06_data->pinctrl_state_release
+ = pinctrl_lookup_state(ft5x06_data->ts_pinctrl,
+ PINCTRL_STATE_RELEASE);
+ if (IS_ERR_OR_NULL(ft5x06_data->pinctrl_state_release)) {
+ retval = PTR_ERR(ft5x06_data->pinctrl_state_release);
+ dev_dbg(&ft5x06_data->client->dev,
+ "Can not lookup %s pinstate %d\n",
+ PINCTRL_STATE_RELEASE, retval);
+ }
+
+ return 0;
+
+err_pinctrl_lookup:
+ devm_pinctrl_put(ft5x06_data->ts_pinctrl);
+err_pinctrl_get:
+ ft5x06_data->ts_pinctrl = NULL;
+ return retval;
+}
+
+#ifdef CONFIG_PM
+static int ft5x06_ts_start(struct device *dev)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ int err;
+
+ if (data->pdata->power_on) {
+ err = data->pdata->power_on(true);
+ if (err) {
+ dev_err(dev, "power on failed");
+ return err;
+ }
+ } else {
+ err = ft5x06_power_on(data, true);
+ if (err) {
+ dev_err(dev, "power on failed");
+ return err;
+ }
+ }
+
+ if (data->ts_pinctrl) {
+ err = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_active);
+ if (err < 0)
+ dev_err(dev, "Cannot get active pinctrl state\n");
+ }
+
+ err = ft5x06_gpio_configure(data, true);
+ if (err < 0) {
+ dev_err(&data->client->dev,
+ "failed to put gpios in resue state\n");
+ goto err_gpio_configuration;
+ }
+
+ if (gpio_is_valid(data->pdata->reset_gpio)) {
+ gpio_set_value_cansleep(data->pdata->reset_gpio, 0);
+ msleep(data->pdata->hard_rst_dly);
+ gpio_set_value_cansleep(data->pdata->reset_gpio, 1);
+ }
+
+ msleep(data->pdata->soft_rst_dly);
+
+ enable_irq(data->client->irq);
+ data->suspended = false;
+
+ return 0;
+
+err_gpio_configuration:
+ if (data->ts_pinctrl) {
+ err = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_suspend);
+ if (err < 0)
+ dev_err(dev, "Cannot get suspend pinctrl state\n");
+ }
+ if (data->pdata->power_on) {
+ err = data->pdata->power_on(false);
+ if (err)
+ dev_err(dev, "power off failed");
+ } else {
+ err = ft5x06_power_on(data, false);
+ if (err)
+ dev_err(dev, "power off failed");
+ }
+ return err;
+}
+
+static int ft5x06_ts_stop(struct device *dev)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ char txbuf[2];
+ int i, err;
+
+ disable_irq(data->client->irq);
+
+ /* release all touches */
+ for (i = 0; i < data->pdata->num_max_touches; i++) {
+ input_mt_slot(data->input_dev, i);
+ input_mt_report_slot_state(data->input_dev, MT_TOOL_FINGER, 0);
+ }
+ input_mt_report_pointer_emulation(data->input_dev, false);
+ input_sync(data->input_dev);
+
+ if (gpio_is_valid(data->pdata->reset_gpio)) {
+ txbuf[0] = FT_REG_PMODE;
+ txbuf[1] = FT_PMODE_HIBERNATE;
+ ft5x06_i2c_write(data->client, txbuf, sizeof(txbuf));
+ }
+
+ if (data->pdata->power_on) {
+ err = data->pdata->power_on(false);
+ if (err) {
+ dev_err(dev, "power off failed");
+ goto pwr_off_fail;
+ }
+ } else {
+ err = ft5x06_power_on(data, false);
+ if (err) {
+ dev_err(dev, "power off failed");
+ goto pwr_off_fail;
+ }
+ }
+
+ if (data->ts_pinctrl) {
+ err = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_suspend);
+ if (err < 0)
+ dev_err(dev, "Cannot get suspend pinctrl state\n");
+ }
+
+ err = ft5x06_gpio_configure(data, false);
+ if (err < 0) {
+ dev_err(&data->client->dev,
+ "failed to put gpios in suspend state\n");
+ goto gpio_configure_fail;
+ }
+
+ data->suspended = true;
+
+ return 0;
+
+gpio_configure_fail:
+ if (data->ts_pinctrl) {
+ err = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_active);
+ if (err < 0)
+ dev_err(dev, "Cannot get active pinctrl state\n");
+ }
+ if (data->pdata->power_on) {
+ err = data->pdata->power_on(true);
+ if (err)
+ dev_err(dev, "power on failed");
+ } else {
+ err = ft5x06_power_on(data, true);
+ if (err)
+ dev_err(dev, "power on failed");
+ }
+pwr_off_fail:
+ if (gpio_is_valid(data->pdata->reset_gpio)) {
+ gpio_set_value_cansleep(data->pdata->reset_gpio, 0);
+ msleep(data->pdata->hard_rst_dly);
+ gpio_set_value_cansleep(data->pdata->reset_gpio, 1);
+ }
+ enable_irq(data->client->irq);
+ return err;
+}
+
+static int ft5x06_ts_suspend(struct device *dev)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ int err;
+
+ if (data->loading_fw) {
+ dev_info(dev, "Firmware loading in process...\n");
+ return 0;
+ }
+
+ if (data->suspended) {
+ dev_info(dev, "Already in suspend state\n");
+ return 0;
+ }
+
+ ft5x06_secure_touch_stop(data, true);
+
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support &&
+ device_may_wakeup(dev) &&
+ data->gesture_pdata->gesture_enable_to_set) {
+
+ ft5x0x_write_reg(data->client, FT_REG_GESTURE_ENABLE, 1);
+ err = enable_irq_wake(data->client->irq);
+ if (err)
+ dev_err(&data->client->dev,
+ "%s: set_irq_wake failed\n", __func__);
+ data->suspended = true;
+ return err;
+ }
+
+ return ft5x06_ts_stop(dev);
+}
+
+static int ft5x06_ts_resume(struct device *dev)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ int err;
+
+ if (!data->suspended) {
+ dev_dbg(dev, "Already in awake state\n");
+ return 0;
+ }
+
+ ft5x06_secure_touch_stop(data, true);
+
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support &&
+ device_may_wakeup(dev) &&
+ !(data->gesture_pdata->in_pocket) &&
+ data->gesture_pdata->gesture_enable_to_set) {
+
+ ft5x0x_write_reg(data->client, FT_REG_GESTURE_ENABLE, 0);
+ err = disable_irq_wake(data->client->irq);
+ if (err)
+ dev_err(dev, "%s: disable_irq_wake failed\n",
+ __func__);
+ data->suspended = false;
+ return err;
+ }
+
+ err = ft5x06_ts_start(dev);
+ if (err < 0)
+ return err;
+
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support &&
+ device_may_wakeup(dev) &&
+ data->gesture_pdata->in_pocket &&
+ data->gesture_pdata->gesture_enable_to_set) {
+
+ ft5x0x_write_reg(data->client, FT_REG_GESTURE_ENABLE, 0);
+ err = disable_irq_wake(data->client->irq);
+ if (err)
+ dev_err(dev, "%s: disable_irq_wake failed\n",
+ __func__);
+ data->suspended = false;
+ data->gesture_pdata->in_pocket = 0;
+ }
+ return 0;
+}
+
+static const struct dev_pm_ops ft5x06_ts_pm_ops = {
+#if (!defined(CONFIG_FB) && !defined(CONFIG_HAS_EARLYSUSPEND))
+ .suspend = ft5x06_ts_suspend,
+ .resume = ft5x06_ts_resume,
+#endif
+};
+
+#else
+static int ft5x06_ts_suspend(struct device *dev)
+{
+ return 0;
+}
+
+static int ft5x06_ts_resume(struct device *dev)
+{
+ return 0;
+}
+
+#endif
+
+#if defined(CONFIG_FB)
+static void fb_notify_resume_work(struct work_struct *work)
+{
+ struct ft5x06_ts_data *ft5x06_data =
+ container_of(work, struct ft5x06_ts_data, fb_notify_work);
+ ft5x06_ts_resume(&ft5x06_data->client->dev);
+}
+
+static int fb_notifier_callback(struct notifier_block *self,
+ unsigned long event, void *data)
+{
+ struct fb_event *evdata = data;
+ int *blank;
+ struct ft5x06_ts_data *ft5x06_data =
+ container_of(self, struct ft5x06_ts_data, fb_notif);
+
+ if (evdata && evdata->data && ft5x06_data && ft5x06_data->client) {
+ blank = evdata->data;
+ if (ft5x06_data->pdata->resume_in_workqueue) {
+ if (event == FB_EARLY_EVENT_BLANK &&
+ *blank == FB_BLANK_UNBLANK)
+ schedule_work(&ft5x06_data->fb_notify_work);
+ else if (event == FB_EVENT_BLANK &&
+ *blank == FB_BLANK_POWERDOWN) {
+ flush_work(&ft5x06_data->fb_notify_work);
+ ft5x06_ts_suspend(&ft5x06_data->client->dev);
+ }
+ } else {
+ if (event == FB_EVENT_BLANK) {
+ if (*blank == FB_BLANK_UNBLANK)
+ ft5x06_ts_resume(
+ &ft5x06_data->client->dev);
+ else if (*blank == FB_BLANK_POWERDOWN)
+ ft5x06_ts_suspend(
+ &ft5x06_data->client->dev);
+ }
+ }
+ }
+
+ return 0;
+}
+#elif defined(CONFIG_HAS_EARLYSUSPEND)
+static void ft5x06_ts_early_suspend(struct early_suspend *handler)
+{
+ struct ft5x06_ts_data *data = container_of(handler,
+ struct ft5x06_ts_data,
+ early_suspend);
+
+ /*
+ * During early suspend/late resume, the driver doesn't access xPU/SMMU
+ * protected HW resources. So, there is no compelling need to block,
+ * but notifying the userspace that a power event has occurred is
+ * enough. Hence 'blocking' variable can be set to false.
+ */
+ ft5x06_secure_touch_stop(data, false);
+ ft5x06_ts_suspend(&data->client->dev);
+}
+
+static void ft5x06_ts_late_resume(struct early_suspend *handler)
+{
+ struct ft5x06_ts_data *data = container_of(handler,
+ struct ft5x06_ts_data,
+ early_suspend);
+
+ ft5x06_secure_touch_stop(data, false);
+ ft5x06_ts_resume(&data->client->dev);
+}
+#endif
+
+static int ft5x06_auto_cal(struct i2c_client *client)
+{
+ struct ft5x06_ts_data *data = i2c_get_clientdata(client);
+ u8 temp = 0, i;
+
+ /* set to factory mode */
+ msleep(2 * data->pdata->soft_rst_dly);
+ ft5x0x_write_reg(client, FT_REG_DEV_MODE, FT_FACTORYMODE_VALUE);
+ msleep(data->pdata->soft_rst_dly);
+
+ /* start calibration */
+ ft5x0x_write_reg(client, FT_DEV_MODE_REG_CAL, FT_CAL_START);
+ msleep(2 * data->pdata->soft_rst_dly);
+ for (i = 0; i < FT_CAL_RETRY; i++) {
+ ft5x0x_read_reg(client, FT_REG_CAL, &temp);
+ /* return to normal mode, calibration finish */
+ if (((temp & FT_CAL_MASK) >> FT_4BIT_SHIFT) == FT_CAL_FIN)
+ break;
+ }
+
+ /*calibration OK */
+ msleep(2 * data->pdata->soft_rst_dly);
+ ft5x0x_write_reg(client, FT_REG_DEV_MODE, FT_FACTORYMODE_VALUE);
+ msleep(data->pdata->soft_rst_dly);
+
+ /* store calibration data */
+ ft5x0x_write_reg(client, FT_DEV_MODE_REG_CAL, FT_CAL_STORE);
+ msleep(2 * data->pdata->soft_rst_dly);
+
+ /* set to normal mode */
+ ft5x0x_write_reg(client, FT_REG_DEV_MODE, FT_WORKMODE_VALUE);
+ msleep(2 * data->pdata->soft_rst_dly);
+
+ return 0;
+}
+
+static int ft5x06_fw_upgrade_start(struct i2c_client *client,
+ const u8 *data, u32 data_len)
+{
+ struct ft5x06_ts_data *ts_data = i2c_get_clientdata(client);
+ struct fw_upgrade_info info = ts_data->pdata->info;
+ u8 reset_reg;
+ u8 w_buf[FT_MAX_WR_BUF] = {0}, r_buf[FT_MAX_RD_BUF] = {0};
+ u8 pkt_buf[FT_FW_PKT_LEN + FT_FW_PKT_META_LEN];
+ int i, j, temp;
+ u32 pkt_num, pkt_len;
+ u8 is_5336_new_bootloader = false;
+ u8 is_5336_fwsize_30 = false;
+ u8 fw_ecc;
+
+ /* determine firmware size */
+ if (*(data + data_len - FT_BLOADER_SIZE_OFF) == FT_BLOADER_NEW_SIZE)
+ is_5336_fwsize_30 = true;
+ else
+ is_5336_fwsize_30 = false;
+
+ for (i = 0, j = 0; i < FT_UPGRADE_LOOP; i++) {
+ msleep(FT_EARSE_DLY_MS);
+ /* reset - write 0xaa and 0x55 to reset register */
+ if (ts_data->family_id == FT6X06_ID
+ || ts_data->family_id == FT6X36_ID)
+ reset_reg = FT_RST_CMD_REG2;
+ else
+ reset_reg = FT_RST_CMD_REG1;
+
+ ft5x0x_write_reg(client, reset_reg, FT_UPGRADE_AA);
+ msleep(info.delay_aa);
+
+ ft5x0x_write_reg(client, reset_reg, FT_UPGRADE_55);
+ if (i <= (FT_UPGRADE_LOOP / 2))
+ msleep(info.delay_55 + i * 3);
+ else
+ msleep(info.delay_55 - (i - (FT_UPGRADE_LOOP / 2)) * 2);
+
+ /* Enter upgrade mode */
+ w_buf[0] = FT_UPGRADE_55;
+ ft5x06_i2c_write(client, w_buf, 1);
+ usleep_range(FT_55_AA_DLY_NS, FT_55_AA_DLY_NS + 1);
+ w_buf[0] = FT_UPGRADE_AA;
+ ft5x06_i2c_write(client, w_buf, 1);
+
+ /* check READ_ID */
+ msleep(info.delay_readid);
+ w_buf[0] = FT_READ_ID_REG;
+ w_buf[1] = 0x00;
+ w_buf[2] = 0x00;
+ w_buf[3] = 0x00;
+
+ ft5x06_i2c_read(client, w_buf, 4, r_buf, 2);
+
+ if (r_buf[0] != info.upgrade_id_1
+ || r_buf[1] != info.upgrade_id_2) {
+ dev_err(&client->dev, "Upgrade ID mismatch(%d), IC=0x%x 0x%x, info=0x%x 0x%x\n",
+ i, r_buf[0], r_buf[1],
+ info.upgrade_id_1, info.upgrade_id_2);
+ } else
+ break;
+ }
+
+ if (i >= FT_UPGRADE_LOOP) {
+ dev_err(&client->dev, "Abort upgrade\n");
+ return -EIO;
+ }
+
+ w_buf[0] = 0xcd;
+ ft5x06_i2c_read(client, w_buf, 1, r_buf, 1);
+
+ if (r_buf[0] <= 4)
+ is_5336_new_bootloader = FT_BLOADER_VERSION_LZ4;
+ else if (r_buf[0] == 7)
+ is_5336_new_bootloader = FT_BLOADER_VERSION_Z7;
+ else if (r_buf[0] >= 0x0f &&
+ ((ts_data->family_id == FT_FT5336_FAMILY_ID_0x11) ||
+ (ts_data->family_id == FT_FT5336_FAMILY_ID_0x12) ||
+ (ts_data->family_id == FT_FT5336_FAMILY_ID_0x13) ||
+ (ts_data->family_id == FT_FT5336_FAMILY_ID_0x14)))
+ is_5336_new_bootloader = FT_BLOADER_VERSION_GZF;
+ else
+ is_5336_new_bootloader = FT_BLOADER_VERSION_LZ4;
+
+ dev_dbg(&client->dev, "bootloader type=%d, r_buf=0x%x, family_id=0x%x\n",
+ is_5336_new_bootloader, r_buf[0], ts_data->family_id);
+ /* is_5336_new_bootloader = FT_BLOADER_VERSION_GZF; */
+
+ /* erase app and panel paramenter area */
+ w_buf[0] = FT_ERASE_APP_REG;
+ ft5x06_i2c_write(client, w_buf, 1);
+ msleep(info.delay_erase_flash);
+
+ if (is_5336_fwsize_30) {
+ w_buf[0] = FT_ERASE_PANEL_REG;
+ ft5x06_i2c_write(client, w_buf, 1);
+ }
+ msleep(FT_EARSE_DLY_MS);
+
+ /* program firmware */
+ if (is_5336_new_bootloader == FT_BLOADER_VERSION_LZ4
+ || is_5336_new_bootloader == FT_BLOADER_VERSION_Z7)
+ data_len = data_len - FT_DATA_LEN_OFF_OLD_FW;
+ else
+ data_len = data_len - FT_DATA_LEN_OFF_NEW_FW;
+
+ pkt_num = (data_len) / FT_FW_PKT_LEN;
+ pkt_len = FT_FW_PKT_LEN;
+ pkt_buf[0] = FT_FW_START_REG;
+ pkt_buf[1] = 0x00;
+ fw_ecc = 0;
+
+ for (i = 0; i < pkt_num; i++) {
+ temp = i * FT_FW_PKT_LEN;
+ pkt_buf[2] = (u8) (temp >> FT_8BIT_SHIFT);
+ pkt_buf[3] = (u8) temp;
+ pkt_buf[4] = (u8) (pkt_len >> FT_8BIT_SHIFT);
+ pkt_buf[5] = (u8) pkt_len;
+
+ for (j = 0; j < FT_FW_PKT_LEN; j++) {
+ pkt_buf[6 + j] = data[i * FT_FW_PKT_LEN + j];
+ fw_ecc ^= pkt_buf[6 + j];
+ }
+
+ ft5x06_i2c_write(client, pkt_buf,
+ FT_FW_PKT_LEN + FT_FW_PKT_META_LEN);
+ msleep(FT_FW_PKT_DLY_MS);
+ }
+
+ /* send remaining bytes */
+ if ((data_len) % FT_FW_PKT_LEN > 0) {
+ temp = pkt_num * FT_FW_PKT_LEN;
+ pkt_buf[2] = (u8) (temp >> FT_8BIT_SHIFT);
+ pkt_buf[3] = (u8) temp;
+ temp = (data_len) % FT_FW_PKT_LEN;
+ pkt_buf[4] = (u8) (temp >> FT_8BIT_SHIFT);
+ pkt_buf[5] = (u8) temp;
+
+ for (i = 0; i < temp; i++) {
+ pkt_buf[6 + i] = data[pkt_num * FT_FW_PKT_LEN + i];
+ fw_ecc ^= pkt_buf[6 + i];
+ }
+
+ ft5x06_i2c_write(client, pkt_buf, temp + FT_FW_PKT_META_LEN);
+ msleep(FT_FW_PKT_DLY_MS);
+ }
+
+ /* send the finishing packet */
+ if (is_5336_new_bootloader == FT_BLOADER_VERSION_LZ4 ||
+ is_5336_new_bootloader == FT_BLOADER_VERSION_Z7) {
+ for (i = 0; i < FT_FINISHING_PKT_LEN_OLD_FW; i++) {
+ if (is_5336_new_bootloader == FT_BLOADER_VERSION_Z7)
+ temp = FT_MAGIC_BLOADER_Z7 + i;
+ else if (is_5336_new_bootloader ==
+ FT_BLOADER_VERSION_LZ4)
+ temp = FT_MAGIC_BLOADER_LZ4 + i;
+ pkt_buf[2] = (u8)(temp >> 8);
+ pkt_buf[3] = (u8)temp;
+ temp = 1;
+ pkt_buf[4] = (u8)(temp >> 8);
+ pkt_buf[5] = (u8)temp;
+ pkt_buf[6] = data[data_len + i];
+ fw_ecc ^= pkt_buf[6];
+
+ ft5x06_i2c_write(client,
+ pkt_buf, temp + FT_FW_PKT_META_LEN);
+ msleep(FT_FW_PKT_DLY_MS);
+ }
+ } else if (is_5336_new_bootloader == FT_BLOADER_VERSION_GZF) {
+ for (i = 0; i < FT_FINISHING_PKT_LEN_NEW_FW; i++) {
+ if (is_5336_fwsize_30)
+ temp = FT_MAGIC_BLOADER_GZF_30 + i;
+ else
+ temp = FT_MAGIC_BLOADER_GZF + i;
+ pkt_buf[2] = (u8)(temp >> 8);
+ pkt_buf[3] = (u8)temp;
+ temp = 1;
+ pkt_buf[4] = (u8)(temp >> 8);
+ pkt_buf[5] = (u8)temp;
+ pkt_buf[6] = data[data_len + i];
+ fw_ecc ^= pkt_buf[6];
+
+ ft5x06_i2c_write(client,
+ pkt_buf, temp + FT_FW_PKT_META_LEN);
+ msleep(FT_FW_PKT_DLY_MS);
+
+ }
+ }
+
+ /* verify checksum */
+ w_buf[0] = FT_REG_ECC;
+ ft5x06_i2c_read(client, w_buf, 1, r_buf, 1);
+ if (r_buf[0] != fw_ecc) {
+ dev_err(&client->dev, "ECC error! dev_ecc=%02x fw_ecc=%02x\n",
+ r_buf[0], fw_ecc);
+ return -EIO;
+ }
+
+ /* reset */
+ w_buf[0] = FT_REG_RESET_FW;
+ ft5x06_i2c_write(client, w_buf, 1);
+ msleep(ts_data->pdata->soft_rst_dly);
+
+ dev_info(&client->dev, "Firmware upgrade successful\n");
+
+ return 0;
+}
+
+static int ft5x06_fw_upgrade(struct device *dev, bool force)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ const struct firmware *fw = NULL;
+ int rc;
+ u8 fw_file_maj, fw_file_min, fw_file_sub_min, fw_file_vendor_id;
+ bool fw_upgrade = false;
+
+ if (data->suspended) {
+ dev_err(dev, "Device is in suspend state: Exit FW upgrade\n");
+ return -EBUSY;
+ }
+
+ rc = request_firmware(&fw, data->fw_name, dev);
+ if (rc < 0) {
+ dev_err(dev, "Request firmware failed - %s (%d)\n",
+ data->fw_name, rc);
+ return rc;
+ }
+
+ if (fw->size < FT_FW_MIN_SIZE || fw->size > FT_FW_MAX_SIZE) {
+ dev_err(dev, "Invalid firmware size (%zu)\n", fw->size);
+ rc = -EIO;
+ goto rel_fw;
+ }
+
+ if (data->family_id == FT6X36_ID) {
+ fw_file_maj = FT_FW_FILE_MAJ_VER_FT6X36(fw);
+ fw_file_vendor_id = FT_FW_FILE_VENDOR_ID_FT6X36(fw);
+ } else {
+ fw_file_maj = FT_FW_FILE_MAJ_VER(fw);
+ fw_file_vendor_id = FT_FW_FILE_VENDOR_ID(fw);
+ }
+ fw_file_min = FT_FW_FILE_MIN_VER(fw);
+ fw_file_sub_min = FT_FW_FILE_SUB_MIN_VER(fw);
+ fw_file_vendor_id = FT_FW_FILE_VENDOR_ID(fw);
+
+ dev_info(dev, "Current firmware: %d.%d.%d", data->fw_ver[0],
+ data->fw_ver[1], data->fw_ver[2]);
+ dev_info(dev, "New firmware: %d.%d.%d", fw_file_maj,
+ fw_file_min, fw_file_sub_min);
+
+ if (force)
+ fw_upgrade = true;
+ else if ((data->fw_ver[0] < fw_file_maj) &&
+ data->fw_vendor_id == fw_file_vendor_id)
+ fw_upgrade = true;
+
+ if (!fw_upgrade) {
+ dev_info(dev, "Exiting fw upgrade...\n");
+ rc = -EFAULT;
+ goto rel_fw;
+ }
+
+ /* start firmware upgrade */
+ if (FT_FW_CHECK(fw, data)) {
+ rc = ft5x06_fw_upgrade_start(data->client, fw->data, fw->size);
+ if (rc < 0)
+ dev_err(dev, "update failed (%d). try later...\n", rc);
+ else if (data->pdata->info.auto_cal)
+ ft5x06_auto_cal(data->client);
+ } else {
+ dev_err(dev, "FW format error\n");
+ rc = -EIO;
+ }
+
+ ft5x06_update_fw_ver(data);
+
+ FT_STORE_TS_DBG_INFO(data->ts_info, data->family_id, data->pdata->name,
+ data->pdata->num_max_touches, data->pdata->group_id,
+ data->pdata->fw_vkey_support ? "yes" : "no",
+ data->pdata->fw_name, data->fw_ver[0],
+ data->fw_ver[1], data->fw_ver[2]);
+ FT_STORE_TS_INFO(ts_info_buff, data->family_id, data->fw_ver[0],
+ data->fw_ver[1], data->fw_ver[2]);
+rel_fw:
+ release_firmware(fw);
+ return rc;
+}
+
+static ssize_t ft5x06_update_fw_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+
+ return snprintf(buf, 2, "%d\n", data->loading_fw);
+}
+
+static ssize_t ft5x06_update_fw_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t size)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ unsigned long val;
+ int rc;
+
+ if (size > 2)
+ return -EINVAL;
+
+ rc = kstrtoul(buf, 10, &val);
+ if (rc != 0)
+ return rc;
+
+ if (data->suspended) {
+ dev_info(dev, "In suspend state, try again later...\n");
+ return size;
+ }
+
+ mutex_lock(&data->input_dev->mutex);
+ if (!data->loading_fw && val) {
+ data->loading_fw = true;
+ ft5x06_fw_upgrade(dev, false);
+ data->loading_fw = false;
+ }
+ mutex_unlock(&data->input_dev->mutex);
+
+ return size;
+}
+
+static DEVICE_ATTR(update_fw, 0664, ft5x06_update_fw_show,
+ ft5x06_update_fw_store);
+
+static ssize_t ft5x06_force_update_fw_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t size)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+ unsigned long val;
+ int rc;
+
+ if (size > 2)
+ return -EINVAL;
+
+ rc = kstrtoul(buf, 10, &val);
+ if (rc != 0)
+ return rc;
+
+ mutex_lock(&data->input_dev->mutex);
+ if (!data->loading_fw && val) {
+ data->loading_fw = true;
+ ft5x06_fw_upgrade(dev, true);
+ data->loading_fw = false;
+ }
+ mutex_unlock(&data->input_dev->mutex);
+
+ return size;
+}
+
+static DEVICE_ATTR(force_update_fw, 0664, ft5x06_update_fw_show,
+ ft5x06_force_update_fw_store);
+
+static ssize_t ft5x06_fw_name_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+
+ return snprintf(buf, FT_FW_NAME_MAX_LEN - 1, "%s\n", data->fw_name);
+}
+
+static ssize_t ft5x06_fw_name_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t size)
+{
+ struct ft5x06_ts_data *data = dev_get_drvdata(dev);
+
+ if (size > FT_FW_NAME_MAX_LEN - 1)
+ return -EINVAL;
+
+ strlcpy(data->fw_name, buf, size);
+ if (data->fw_name[size-1] == '\n')
+ data->fw_name[size-1] = 0;
+
+ return size;
+}
+
+static DEVICE_ATTR(fw_name, 0664, ft5x06_fw_name_show, ft5x06_fw_name_store);
+
+static ssize_t ts_info_show(struct kobject *kobj,
+ struct kobj_attribute *attr, char *buf)
+{
+ strlcpy(buf, ts_info_buff, FT_INFO_MAX_LEN);
+ return strnlen(buf, FT_INFO_MAX_LEN);
+}
+static struct kobj_attribute ts_info_attr = __ATTR_RO(ts_info);
+
+static bool ft5x06_debug_addr_is_valid(int addr)
+{
+ if (addr < 0 || addr > 0xFF) {
+ pr_err("FT reg address is invalid: 0x%x\n", addr);
+ return false;
+ }
+
+ return true;
+}
+
+static int ft5x06_debug_data_set(void *_data, u64 val)
+{
+ struct ft5x06_ts_data *data = _data;
+
+ mutex_lock(&data->input_dev->mutex);
+
+ if (ft5x06_debug_addr_is_valid(data->addr))
+ dev_info(&data->client->dev,
+ "Writing into FT registers not supported\n");
+
+ mutex_unlock(&data->input_dev->mutex);
+
+ return 0;
+}
+
+static int ft5x06_debug_data_get(void *_data, u64 *val)
+{
+ struct ft5x06_ts_data *data = _data;
+ int rc;
+ u8 reg = 0;
+
+ mutex_lock(&data->input_dev->mutex);
+
+ if (ft5x06_debug_addr_is_valid(data->addr)) {
+ rc = ft5x0x_read_reg(data->client, data->addr, ®);
+ if (rc < 0)
+ dev_err(&data->client->dev,
+ "FT read register 0x%x failed (%d)\n",
+ data->addr, rc);
+ else
+ *val = reg;
+ }
+
+ mutex_unlock(&data->input_dev->mutex);
+
+ return 0;
+}
+
+DEFINE_SIMPLE_ATTRIBUTE(debug_data_fops, ft5x06_debug_data_get,
+ ft5x06_debug_data_set, "0x%02llX\n");
+
+static int ft5x06_debug_addr_set(void *_data, u64 val)
+{
+ struct ft5x06_ts_data *data = _data;
+
+ if (ft5x06_debug_addr_is_valid(val)) {
+ mutex_lock(&data->input_dev->mutex);
+ data->addr = val;
+ mutex_unlock(&data->input_dev->mutex);
+ }
+
+ return 0;
+}
+
+static int ft5x06_debug_addr_get(void *_data, u64 *val)
+{
+ struct ft5x06_ts_data *data = _data;
+
+ mutex_lock(&data->input_dev->mutex);
+
+ if (ft5x06_debug_addr_is_valid(data->addr))
+ *val = data->addr;
+
+ mutex_unlock(&data->input_dev->mutex);
+
+ return 0;
+}
+
+DEFINE_SIMPLE_ATTRIBUTE(debug_addr_fops, ft5x06_debug_addr_get,
+ ft5x06_debug_addr_set, "0x%02llX\n");
+
+static int ft5x06_debug_suspend_set(void *_data, u64 val)
+{
+ struct ft5x06_ts_data *data = _data;
+
+ mutex_lock(&data->input_dev->mutex);
+
+ if (val)
+ ft5x06_ts_suspend(&data->client->dev);
+ else
+ ft5x06_ts_resume(&data->client->dev);
+
+ mutex_unlock(&data->input_dev->mutex);
+
+ return 0;
+}
+
+static int ft5x06_debug_suspend_get(void *_data, u64 *val)
+{
+ struct ft5x06_ts_data *data = _data;
+
+ mutex_lock(&data->input_dev->mutex);
+ *val = data->suspended;
+ mutex_unlock(&data->input_dev->mutex);
+
+ return 0;
+}
+
+DEFINE_SIMPLE_ATTRIBUTE(debug_suspend_fops, ft5x06_debug_suspend_get,
+ ft5x06_debug_suspend_set, "%lld\n");
+
+static int ft5x06_debug_dump_info(struct seq_file *m, void *v)
+{
+ struct ft5x06_ts_data *data = m->private;
+
+ seq_printf(m, "%s\n", data->ts_info);
+
+ return 0;
+}
+
+static int debugfs_dump_info_open(struct inode *inode, struct file *file)
+{
+ return single_open(file, ft5x06_debug_dump_info, inode->i_private);
+}
+
+static const struct file_operations debug_dump_info_fops = {
+ .owner = THIS_MODULE,
+ .open = debugfs_dump_info_open,
+ .read = seq_read,
+ .release = single_release,
+};
+
+#ifdef CONFIG_OF
+static int ft5x06_get_dt_coords(struct device *dev, char *name,
+ struct ft5x06_ts_platform_data *pdata)
+{
+ u32 coords[FT_COORDS_ARR_SIZE];
+ struct property *prop;
+ struct device_node *np = dev->of_node;
+ int coords_size, rc;
+
+ prop = of_find_property(np, name, NULL);
+ if (!prop)
+ return -EINVAL;
+ if (!prop->value)
+ return -ENODATA;
+
+ coords_size = prop->length / sizeof(u32);
+ if (coords_size != FT_COORDS_ARR_SIZE) {
+ dev_err(dev, "invalid %s\n", name);
+ return -EINVAL;
+ }
+
+ rc = of_property_read_u32_array(np, name, coords, coords_size);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read %s\n", name);
+ return rc;
+ }
+
+ if (!strcmp(name, "focaltech,panel-coords")) {
+ pdata->panel_minx = coords[0];
+ pdata->panel_miny = coords[1];
+ pdata->panel_maxx = coords[2];
+ pdata->panel_maxy = coords[3];
+ } else if (!strcmp(name, "focaltech,display-coords")) {
+ pdata->x_min = coords[0];
+ pdata->y_min = coords[1];
+ pdata->x_max = coords[2];
+ pdata->y_max = coords[3];
+ } else {
+ dev_err(dev, "unsupported property %s\n", name);
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+static int ft5x06_parse_dt(struct device *dev,
+ struct ft5x06_ts_platform_data *pdata)
+{
+ int rc;
+ struct device_node *np = dev->of_node;
+ struct property *prop;
+ u32 temp_val, num_buttons;
+ u32 button_map[MAX_BUTTONS];
+
+ pdata->name = "focaltech";
+ rc = of_property_read_string(np, "focaltech,name", &pdata->name);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read name\n");
+ return rc;
+ }
+
+ rc = ft5x06_get_dt_coords(dev, "focaltech,panel-coords", pdata);
+ if (rc && (rc != -EINVAL))
+ return rc;
+
+ rc = ft5x06_get_dt_coords(dev, "focaltech,display-coords", pdata);
+ if (rc)
+ return rc;
+
+ pdata->i2c_pull_up = of_property_read_bool(np,
+ "focaltech,i2c-pull-up");
+
+ pdata->no_force_update = of_property_read_bool(np,
+ "focaltech,no-force-update");
+ /* reset, irq gpio info */
+ pdata->reset_gpio = of_get_named_gpio_flags(np, "focaltech,reset-gpio",
+ 0, &pdata->reset_gpio_flags);
+ if (pdata->reset_gpio < 0)
+ return pdata->reset_gpio;
+
+ pdata->irq_gpio = of_get_named_gpio_flags(np, "focaltech,irq-gpio",
+ 0, &pdata->irq_gpio_flags);
+ if (pdata->irq_gpio < 0)
+ return pdata->irq_gpio;
+
+ pdata->fw_name = "ft_fw.bin";
+ rc = of_property_read_string(np, "focaltech,fw-name", &pdata->fw_name);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw name\n");
+ return rc;
+ }
+
+ rc = of_property_read_u32(np, "focaltech,group-id", &temp_val);
+ if (!rc)
+ pdata->group_id = temp_val;
+ else
+ return rc;
+
+ rc = of_property_read_u32(np, "focaltech,hard-reset-delay-ms",
+ &temp_val);
+ if (!rc)
+ pdata->hard_rst_dly = temp_val;
+ else
+ return rc;
+
+ rc = of_property_read_u32(np, "focaltech,soft-reset-delay-ms",
+ &temp_val);
+ if (!rc)
+ pdata->soft_rst_dly = temp_val;
+ else
+ return rc;
+
+ rc = of_property_read_u32(np, "focaltech,num-max-touches", &temp_val);
+ if (!rc)
+ pdata->num_max_touches = temp_val;
+ else
+ return rc;
+
+ rc = of_property_read_u32(np, "focaltech,fw-delay-aa-ms", &temp_val);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw delay aa\n");
+ return rc;
+ } else if (rc != -EINVAL)
+ pdata->info.delay_aa = temp_val;
+
+ rc = of_property_read_u32(np, "focaltech,fw-delay-55-ms", &temp_val);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw delay 55\n");
+ return rc;
+ } else if (rc != -EINVAL)
+ pdata->info.delay_55 = temp_val;
+
+ rc = of_property_read_u32(np, "focaltech,fw-upgrade-id1", &temp_val);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw upgrade id1\n");
+ return rc;
+ } else if (rc != -EINVAL)
+ pdata->info.upgrade_id_1 = temp_val;
+
+ rc = of_property_read_u32(np, "focaltech,fw-upgrade-id2", &temp_val);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw upgrade id2\n");
+ return rc;
+ } else if (rc != -EINVAL)
+ pdata->info.upgrade_id_2 = temp_val;
+
+ rc = of_property_read_u32(np, "focaltech,fw-delay-readid-ms",
+ &temp_val);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw delay read id\n");
+ return rc;
+ } else if (rc != -EINVAL)
+ pdata->info.delay_readid = temp_val;
+
+ rc = of_property_read_u32(np, "focaltech,fw-delay-era-flsh-ms",
+ &temp_val);
+ if (rc && (rc != -EINVAL)) {
+ dev_err(dev, "Unable to read fw delay erase flash\n");
+ return rc;
+ } else if (rc != -EINVAL)
+ pdata->info.delay_erase_flash = temp_val;
+
+ pdata->info.auto_cal = of_property_read_bool(np,
+ "focaltech,fw-auto-cal");
+
+ pdata->fw_vkey_support = of_property_read_bool(np,
+ "focaltech,fw-vkey-support");
+
+ pdata->ignore_id_check = of_property_read_bool(np,
+ "focaltech,ignore-id-check");
+
+ pdata->gesture_support = of_property_read_bool(np,
+ "focaltech,gesture-support");
+
+ pdata->resume_in_workqueue = of_property_read_bool(np,
+ "focaltech,resume-in-workqueue");
+
+ rc = of_property_read_u32(np, "focaltech,family-id", &temp_val);
+ if (!rc)
+ pdata->family_id = temp_val;
+ else
+ return rc;
+
+ prop = of_find_property(np, "focaltech,button-map", NULL);
+ if (prop) {
+ num_buttons = prop->length / sizeof(temp_val);
+ if (num_buttons > MAX_BUTTONS)
+ return -EINVAL;
+
+ rc = of_property_read_u32_array(np,
+ "focaltech,button-map", button_map,
+ num_buttons);
+ if (rc) {
+ dev_err(dev, "Unable to read key codes\n");
+ return rc;
+ }
+ }
+
+ return 0;
+}
+#else
+static int ft5x06_parse_dt(struct device *dev,
+ struct ft5x06_ts_platform_data *pdata)
+{
+ return -ENODEV;
+}
+#endif
+
+static int ft5x06_ts_probe(struct i2c_client *client,
+ const struct i2c_device_id *id)
+{
+ struct ft5x06_ts_platform_data *pdata;
+ struct ft5x06_gesture_platform_data *gesture_pdata;
+ struct ft5x06_ts_data *data;
+ struct input_dev *input_dev;
+ struct dentry *temp;
+ u8 reg_value = 0;
+ u8 reg_addr;
+ int err, len, retval, attr_count;
+
+ if (client->dev.of_node) {
+ pdata = devm_kzalloc(&client->dev,
+ sizeof(struct ft5x06_ts_platform_data), GFP_KERNEL);
+ if (!pdata)
+ return -ENOMEM;
+
+ err = ft5x06_parse_dt(&client->dev, pdata);
+ if (err) {
+ dev_err(&client->dev, "DT parsing failed\n");
+ return err;
+ }
+ } else
+ pdata = client->dev.platform_data;
+
+ if (!pdata) {
+ dev_err(&client->dev, "Invalid pdata\n");
+ return -EINVAL;
+ }
+
+ if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
+ dev_err(&client->dev, "I2C not supported\n");
+ return -ENODEV;
+ }
+
+ data = devm_kzalloc(&client->dev,
+ sizeof(struct ft5x06_ts_data), GFP_KERNEL);
+ if (!data)
+ return -ENOMEM;
+
+ if (pdata->fw_name) {
+ len = strlen(pdata->fw_name);
+ if (len > FT_FW_NAME_MAX_LEN - 1) {
+ dev_err(&client->dev, "Invalid firmware name\n");
+ return -EINVAL;
+ }
+
+ strlcpy(data->fw_name, pdata->fw_name, len + 1);
+ }
+
+ data->tch_data_len = FT_TCH_LEN(pdata->num_max_touches);
+ data->tch_data = devm_kzalloc(&client->dev,
+ data->tch_data_len, GFP_KERNEL);
+ if (!data->tch_data)
+ return -ENOMEM;
+
+ input_dev = input_allocate_device();
+ if (!input_dev) {
+ dev_err(&client->dev, "failed to allocate input device\n");
+ return -ENOMEM;
+ }
+
+ data->input_dev = input_dev;
+ data->client = client;
+ data->pdata = pdata;
+
+ input_dev->name = "ft5x06_ts";
+ input_dev->id.bustype = BUS_I2C;
+ input_dev->dev.parent = &client->dev;
+
+ input_set_drvdata(input_dev, data);
+ i2c_set_clientdata(client, data);
+
+ __set_bit(EV_KEY, input_dev->evbit);
+ __set_bit(EV_ABS, input_dev->evbit);
+ __set_bit(BTN_TOUCH, input_dev->keybit);
+ __set_bit(INPUT_PROP_DIRECT, input_dev->propbit);
+
+ input_mt_init_slots(input_dev, pdata->num_max_touches, 0);
+ input_set_abs_params(input_dev, ABS_MT_POSITION_X, pdata->x_min,
+ pdata->x_max, 0, 0);
+ input_set_abs_params(input_dev, ABS_MT_POSITION_Y, pdata->y_min,
+ pdata->y_max, 0, 0);
+
+ err = input_register_device(input_dev);
+ if (err) {
+ dev_err(&client->dev, "Input device registration failed\n");
+ input_free_device(input_dev);
+ return err;
+ }
+
+ if (pdata->power_init) {
+ err = pdata->power_init(true);
+ if (err) {
+ dev_err(&client->dev, "power init failed");
+ goto unreg_inputdev;
+ }
+ } else {
+ err = ft5x06_power_init(data, true);
+ if (err) {
+ dev_err(&client->dev, "power init failed");
+ goto unreg_inputdev;
+ }
+ }
+
+ if (pdata->power_on) {
+ err = pdata->power_on(true);
+ if (err) {
+ dev_err(&client->dev, "power on failed");
+ goto pwr_deinit;
+ }
+ } else {
+ err = ft5x06_power_on(data, true);
+ if (err) {
+ dev_err(&client->dev, "power on failed");
+ goto pwr_deinit;
+ }
+ }
+
+ err = ft5x06_ts_pinctrl_init(data);
+ if (!err && data->ts_pinctrl) {
+ /*
+ * Pinctrl handle is optional. If pinctrl handle is found
+ * let pins to be configured in active state. If not
+ * found continue further without error.
+ */
+ err = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_active);
+ if (err < 0) {
+ dev_err(&client->dev,
+ "failed to select pin to active state");
+ }
+ }
+
+ err = ft5x06_gpio_configure(data, true);
+ if (err < 0) {
+ dev_err(&client->dev,
+ "Failed to configure the gpios\n");
+ goto err_gpio_req;
+ }
+
+ /* make sure CTP already finish startup process */
+ msleep(data->pdata->soft_rst_dly);
+
+ /* check the controller id */
+ reg_addr = FT_REG_ID;
+ err = ft5x06_i2c_read(client, ®_addr, 1, ®_value, 1);
+ if (err < 0) {
+ dev_err(&client->dev, "version read failed");
+ goto free_gpio;
+ }
+
+ dev_info(&client->dev, "Device ID = 0x%x\n", reg_value);
+
+ if ((pdata->family_id != reg_value) && (!pdata->ignore_id_check)) {
+ dev_err(&client->dev, "%s:Unsupported controller\n", __func__);
+ goto free_gpio;
+ }
+
+ data->family_id = pdata->family_id;
+
+ err = request_threaded_irq(client->irq, NULL,
+ ft5x06_ts_interrupt,
+ /*
+ * the interrupt trigger mode will be set in Device Tree with property
+ * "interrupts", so here we just need to set the flag IRQF_ONESHOT
+ */
+ IRQF_ONESHOT,
+ client->dev.driver->name, data);
+ if (err) {
+ dev_err(&client->dev, "request irq failed\n");
+ goto free_gpio;
+ }
+
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support) {
+ device_init_wakeup(&client->dev, 1);
+ gesture_pdata = devm_kzalloc(&client->dev,
+ sizeof(struct ft5x06_gesture_platform_data),
+ GFP_KERNEL);
+ if (!gesture_pdata) {
+ dev_err(&client->dev, "Failed to allocate memory\n");
+ goto free_gesture_dev;
+ }
+ data->gesture_pdata = gesture_pdata;
+ gesture_pdata->data = data;
+
+ gesture_pdata->gesture_class =
+ class_create(THIS_MODULE, "gesture");
+ if (IS_ERR(gesture_pdata->gesture_class)) {
+ err = PTR_ERR(gesture_pdata->gesture_class);
+ dev_err(&client->dev, "Failed to create class.\n");
+ goto free_gesture_pdata;
+ }
+
+ gesture_pdata->dev = device_create(gesture_pdata->gesture_class,
+ NULL, 0, NULL, "gesture_ft5x06");
+ if (IS_ERR(gesture_pdata->dev)) {
+ err = PTR_ERR(gesture_pdata->dev);
+ dev_err(&client->dev, "Failed to create device.\n");
+ goto free_gesture_class;
+ }
+
+ dev_set_drvdata(gesture_pdata->dev, data);
+ err = device_create_file(gesture_pdata->dev,
+ &dev_attr_enable);
+ if (err) {
+ dev_err(gesture_pdata->dev,
+ "sys file creation failed\n");
+ goto free_gesture_dev;
+ }
+ err = device_create_file(gesture_pdata->dev,
+ &dev_attr_pocket);
+ if (err) {
+ dev_err(gesture_pdata->dev,
+ "sys file creation failed\n");
+ goto free_enable_sys;
+ }
+ }
+
+ err = device_create_file(&client->dev, &dev_attr_fw_name);
+ if (err) {
+ dev_err(&client->dev, "sys file creation failed\n");
+ goto free_pocket_sys;
+ }
+
+ err = device_create_file(&client->dev, &dev_attr_update_fw);
+ if (err) {
+ dev_err(&client->dev, "sys file creation failed\n");
+ goto free_fw_name_sys;
+ }
+
+ err = device_create_file(&client->dev, &dev_attr_force_update_fw);
+ if (err) {
+ dev_err(&client->dev, "sys file creation failed\n");
+ goto free_update_fw_sys;
+ }
+
+ data->dir = debugfs_create_dir(FT_DEBUG_DIR_NAME, NULL);
+ if (data->dir == NULL || IS_ERR(data->dir)) {
+ pr_err("debugfs_create_dir failed(%ld)\n", PTR_ERR(data->dir));
+ err = PTR_ERR(data->dir);
+ goto free_force_update_fw_sys;
+ }
+
+ temp = debugfs_create_file("addr", 0600, data->dir, data,
+ &debug_addr_fops);
+ if (temp == NULL || IS_ERR(temp)) {
+ pr_err("debugfs_create_file failed: rc=%ld\n", PTR_ERR(temp));
+ err = PTR_ERR(temp);
+ goto free_debug_dir;
+ }
+
+ temp = debugfs_create_file("data", 0600, data->dir, data,
+ &debug_data_fops);
+ if (temp == NULL || IS_ERR(temp)) {
+ pr_err("debugfs_create_file failed: rc=%ld\n", PTR_ERR(temp));
+ err = PTR_ERR(temp);
+ goto free_debug_dir;
+ }
+
+ temp = debugfs_create_file("suspend", 0600, data->dir,
+ data, &debug_suspend_fops);
+ if (temp == NULL || IS_ERR(temp)) {
+ pr_err("debugfs_create_file failed: rc=%ld\n", PTR_ERR(temp));
+ err = PTR_ERR(temp);
+ goto free_debug_dir;
+ }
+
+ temp = debugfs_create_file("dump_info", 0600, data->dir,
+ data, &debug_dump_info_fops);
+ if (temp == NULL || IS_ERR(temp)) {
+ pr_err("debugfs_create_file failed: rc=%ld\n", PTR_ERR(temp));
+ err = PTR_ERR(temp);
+ goto free_debug_dir;
+ }
+
+ data->ts_info = devm_kzalloc(&client->dev,
+ FT_INFO_MAX_LEN, GFP_KERNEL);
+ if (!data->ts_info)
+ goto free_debug_dir;
+
+ /*get some register information */
+ reg_addr = FT_REG_POINT_RATE;
+ ft5x06_i2c_read(client, ®_addr, 1, ®_value, 1);
+ if (err < 0)
+ dev_err(&client->dev, "report rate read failed");
+
+ dev_info(&client->dev, "report rate = %dHz\n", reg_value * 10);
+
+ reg_addr = FT_REG_THGROUP;
+ err = ft5x06_i2c_read(client, ®_addr, 1, ®_value, 1);
+ if (err < 0)
+ dev_err(&client->dev, "threshold read failed");
+
+ dev_dbg(&client->dev, "touch threshold = %d\n", reg_value * 4);
+
+ /*creation touch panel info kobj*/
+ data->ts_info_kobj = kobject_create_and_add(FT_TS_INFO_SYSFS_DIR_NAME,
+ kernel_kobj);
+ if (!data->ts_info_kobj) {
+ dev_err(&client->dev, "kobject creation failed.\n");
+ } else {
+ err = sysfs_create_file(data->ts_info_kobj, &ts_info_attr.attr);
+ if (err) {
+ kobject_put(data->ts_info_kobj);
+ dev_err(&client->dev, "sysfs creation failed.\n");
+ } else {
+ ts_info_buff = devm_kzalloc(&client->dev,
+ FT_INFO_MAX_LEN, GFP_KERNEL);
+ if (!ts_info_buff)
+ goto free_debug_dir;
+ }
+ }
+
+ /*Initialize secure touch */
+ ft5x06_secure_touch_init(data);
+ ft5x06_secure_touch_stop(data, true);
+ mutex_init(&(data->ft_clk_io_ctrl_mutex));
+
+ /* Creation of secure touch sysfs files */
+ for (attr_count = 0; attr_count < ARRAY_SIZE(attrs); attr_count++) {
+ retval = sysfs_create_file(&data->input_dev->dev.kobj,
+ &attrs[attr_count].attr);
+ if (retval < 0) {
+ dev_err(&client->dev,
+ "%s: Failed to create sysfs attributes\n",
+ __func__);
+ goto free_secure_touch_sysfs;
+ }
+ }
+
+ ft5x06_update_fw_ver(data);
+ ft5x06_update_fw_vendor_id(data);
+
+ FT_STORE_TS_DBG_INFO(data->ts_info, data->family_id, data->pdata->name,
+ data->pdata->num_max_touches, data->pdata->group_id,
+ data->pdata->fw_vkey_support ? "yes" : "no",
+ data->pdata->fw_name, data->fw_ver[0],
+ data->fw_ver[1], data->fw_ver[2]);
+ FT_STORE_TS_INFO(ts_info_buff, data->family_id, data->fw_ver[0],
+ data->fw_ver[1], data->fw_ver[2]);
+#if defined(CONFIG_FB)
+ INIT_WORK(&data->fb_notify_work, fb_notify_resume_work);
+ data->fb_notif.notifier_call = fb_notifier_callback;
+
+ err = fb_register_client(&data->fb_notif);
+
+ if (err)
+ dev_err(&client->dev, "Unable to register fb_notifier: %d\n",
+ err);
+#elif defined(CONFIG_HAS_EARLYSUSPEND)
+ data->early_suspend.level = EARLY_SUSPEND_LEVEL_BLANK_SCREEN +
+ FT_SUSPEND_LEVEL;
+ data->early_suspend.suspend = ft5x06_ts_early_suspend;
+ data->early_suspend.resume = ft5x06_ts_late_resume;
+ register_early_suspend(&data->early_suspend);
+#endif
+ return 0;
+
+free_secure_touch_sysfs:
+ for (attr_count--; attr_count >= 0; attr_count--) {
+ sysfs_remove_file(&data->input_dev->dev.kobj,
+ &attrs[attr_count].attr);
+ }
+free_debug_dir:
+ debugfs_remove_recursive(data->dir);
+free_force_update_fw_sys:
+ device_remove_file(&client->dev, &dev_attr_force_update_fw);
+free_update_fw_sys:
+ device_remove_file(&client->dev, &dev_attr_update_fw);
+free_fw_name_sys:
+ device_remove_file(&client->dev, &dev_attr_fw_name);
+free_pocket_sys:
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support)
+ device_remove_file(&client->dev, &dev_attr_pocket);
+free_enable_sys:
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support)
+ device_remove_file(&client->dev, &dev_attr_enable);
+free_gesture_dev:
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support)
+ device_destroy(gesture_pdata->gesture_class, 0);
+free_gesture_class:
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support)
+ class_destroy(gesture_pdata->gesture_class);
+free_gesture_pdata:
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support) {
+ devm_kfree(&client->dev, gesture_pdata);
+ data->gesture_pdata = NULL;
+ }
+
+free_gpio:
+ if (gpio_is_valid(pdata->reset_gpio))
+ gpio_free(pdata->reset_gpio);
+ if (gpio_is_valid(pdata->irq_gpio))
+ gpio_free(pdata->irq_gpio);
+err_gpio_req:
+ if (data->ts_pinctrl) {
+ if (IS_ERR_OR_NULL(data->pinctrl_state_release)) {
+ devm_pinctrl_put(data->ts_pinctrl);
+ data->ts_pinctrl = NULL;
+ } else {
+ err = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_release);
+ if (err)
+ pr_err("failed to select relase pinctrl state\n");
+ }
+ }
+ if (pdata->power_on)
+ pdata->power_on(false);
+ else
+ ft5x06_power_on(data, false);
+pwr_deinit:
+ if (pdata->power_init)
+ pdata->power_init(false);
+ else
+ ft5x06_power_init(data, false);
+unreg_inputdev:
+ input_unregister_device(input_dev);
+ return err;
+}
+
+static int ft5x06_ts_remove(struct i2c_client *client)
+{
+ struct ft5x06_ts_data *data = i2c_get_clientdata(client);
+ int retval, attr_count;
+
+ if (ft5x06_gesture_support_enabled() && data->pdata->gesture_support) {
+ device_init_wakeup(&client->dev, 0);
+ device_remove_file(&client->dev, &dev_attr_pocket);
+ device_remove_file(&client->dev, &dev_attr_enable);
+ device_destroy(data->gesture_pdata->gesture_class, 0);
+ class_destroy(data->gesture_pdata->gesture_class);
+ devm_kfree(&client->dev, data->gesture_pdata);
+ data->gesture_pdata = NULL;
+ }
+
+ debugfs_remove_recursive(data->dir);
+ device_remove_file(&client->dev, &dev_attr_force_update_fw);
+ device_remove_file(&client->dev, &dev_attr_update_fw);
+ device_remove_file(&client->dev, &dev_attr_fw_name);
+
+#if defined(CONFIG_FB)
+ if (fb_unregister_client(&data->fb_notif))
+ dev_err(&client->dev, "Error occurred while unregistering fb_notifier.\n");
+#elif defined(CONFIG_HAS_EARLYSUSPEND)
+ unregister_early_suspend(&data->early_suspend);
+#endif
+ free_irq(client->irq, data);
+
+ if (gpio_is_valid(data->pdata->reset_gpio))
+ gpio_free(data->pdata->reset_gpio);
+
+ if (gpio_is_valid(data->pdata->irq_gpio))
+ gpio_free(data->pdata->irq_gpio);
+
+ if (data->ts_pinctrl) {
+ if (IS_ERR_OR_NULL(data->pinctrl_state_release)) {
+ devm_pinctrl_put(data->ts_pinctrl);
+ data->ts_pinctrl = NULL;
+ } else {
+ retval = pinctrl_select_state(data->ts_pinctrl,
+ data->pinctrl_state_release);
+ if (retval < 0)
+ pr_err("failed to select release pinctrl state\n");
+ }
+ }
+
+ for (attr_count = 0; attr_count < ARRAY_SIZE(attrs); attr_count++) {
+ sysfs_remove_file(&data->input_dev->dev.kobj,
+ &attrs[attr_count].attr);
+ }
+
+ if (data->pdata->power_on)
+ data->pdata->power_on(false);
+ else
+ ft5x06_power_on(data, false);
+
+ if (data->pdata->power_init)
+ data->pdata->power_init(false);
+ else
+ ft5x06_power_init(data, false);
+
+ input_unregister_device(data->input_dev);
+ kobject_put(data->ts_info_kobj);
+ return 0;
+}
+
+static const struct i2c_device_id ft5x06_ts_id[] = {
+ {"ft5x06_ts", 0},
+ {},
+};
+
+MODULE_DEVICE_TABLE(i2c, ft5x06_ts_id);
+
+#ifdef CONFIG_OF
+static const struct of_device_id ft5x06_match_table[] = {
+ { .compatible = "focaltech,5x06",},
+ { },
+};
+#else
+#define ft5x06_match_table NULL
+#endif
+
+static struct i2c_driver ft5x06_ts_driver = {
+ .probe = ft5x06_ts_probe,
+ .remove = ft5x06_ts_remove,
+ .driver = {
+ .name = "ft5x06_ts",
+ .owner = THIS_MODULE,
+ .of_match_table = ft5x06_match_table,
+#ifdef CONFIG_PM
+ .pm = &ft5x06_ts_pm_ops,
+#endif
+ },
+ .id_table = ft5x06_ts_id,
+};
+
+static int __init ft5x06_ts_init(void)
+{
+ return i2c_add_driver(&ft5x06_ts_driver);
+}
+module_init(ft5x06_ts_init);
+
+static void __exit ft5x06_ts_exit(void)
+{
+ i2c_del_driver(&ft5x06_ts_driver);
+}
+module_exit(ft5x06_ts_exit);
+
+MODULE_DESCRIPTION("FocalTech ft5x06 TouchScreen driver");
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.c b/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.c
index 7633767..21a9e8f 100644
--- a/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.c
+++ b/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.c
@@ -56,8 +56,6 @@
#define TYPE_B_PROTOCOL
#endif
-#define WAKEUP_GESTURE false
-
#define NO_0D_WHILE_2D
#define REPORT_2D_Z
#define REPORT_2D_W
@@ -1014,8 +1012,10 @@
input = input > 0 ? 1 : 0;
- if (rmi4_data->f11_wakeup_gesture || rmi4_data->f12_wakeup_gesture)
+ if (rmi4_data->f11_wakeup_gesture || rmi4_data->f12_wakeup_gesture) {
rmi4_data->enable_wakeup_gesture = input;
+ rmi4_data->wakeup_gesture_en = input;
+ }
return count;
}
@@ -1089,7 +1089,6 @@
input_sync(rmi4_data->input_dev);
input_report_key(rmi4_data->input_dev, KEY_WAKEUP, 0);
input_sync(rmi4_data->input_dev);
- rmi4_data->suspend = false;
}
return 0;
@@ -1250,7 +1249,6 @@
input_sync(rmi4_data->input_dev);
input_report_key(rmi4_data->input_dev, KEY_WAKEUP, 0);
input_sync(rmi4_data->input_dev);
- rmi4_data->suspend = false;
}
return 0;
@@ -3114,7 +3112,7 @@
}
if (rmi4_data->f11_wakeup_gesture || rmi4_data->f12_wakeup_gesture)
- rmi4_data->enable_wakeup_gesture = WAKEUP_GESTURE;
+ rmi4_data->enable_wakeup_gesture = rmi4_data->wakeup_gesture_en;
else
rmi4_data->enable_wakeup_gesture = false;
@@ -3954,6 +3952,7 @@
rmi4_data->suspend = false;
rmi4_data->irq_enabled = false;
rmi4_data->fingers_on_2d = false;
+ rmi4_data->wakeup_gesture_en = bdata->wakeup_gesture_en;
rmi4_data->reset_device = synaptics_rmi4_reset_device;
rmi4_data->irq_enable = synaptics_rmi4_irq_enable;
@@ -4423,7 +4422,8 @@
synaptics_secure_touch_stop(rmi4_data, false);
} else if (event == FB_EVENT_BLANK) {
transition = evdata->data;
- if (*transition == FB_BLANK_POWERDOWN) {
+ if (*transition == FB_BLANK_POWERDOWN ||
+ *transition == FB_BLANK_VSYNC_SUSPEND) {
flush_work(
&(rmi4_data->fb_notify_work));
synaptics_rmi4_suspend(
@@ -4564,8 +4564,10 @@
synaptics_secure_touch_stop(rmi4_data, true);
if (rmi4_data->enable_wakeup_gesture) {
- synaptics_rmi4_wakeup_gesture(rmi4_data, true);
- enable_irq_wake(rmi4_data->irq);
+ if (!rmi4_data->suspend) {
+ synaptics_rmi4_wakeup_gesture(rmi4_data, true);
+ enable_irq_wake(rmi4_data->irq);
+ }
goto exit;
}
@@ -4578,9 +4580,10 @@
if (rmi4_data->ts_pinctrl) {
retval = pinctrl_select_state(rmi4_data->ts_pinctrl,
rmi4_data->pinctrl_state_suspend);
- if (retval < 0)
+ if (retval < 0) {
dev_err(dev, "Cannot get idle pinctrl state\n");
goto err_pinctrl;
+ }
}
exit:
mutex_lock(&exp_data.mutex);
@@ -4591,10 +4594,9 @@
}
mutex_unlock(&exp_data.mutex);
- if (!rmi4_data->suspend) {
+ if (!rmi4_data->suspend && !rmi4_data->enable_wakeup_gesture)
synaptics_rmi4_enable_reg(rmi4_data, false);
- synaptics_rmi4_get_reg(rmi4_data, false);
- }
+
rmi4_data->suspend = true;
return 0;
@@ -4620,17 +4622,17 @@
synaptics_secure_touch_stop(rmi4_data, true);
if (rmi4_data->enable_wakeup_gesture) {
- synaptics_rmi4_wakeup_gesture(rmi4_data, false);
- disable_irq_wake(rmi4_data->irq);
+ if (rmi4_data->suspend) {
+ synaptics_rmi4_wakeup_gesture(rmi4_data, false);
+ disable_irq_wake(rmi4_data->irq);
+ }
goto exit;
}
rmi4_data->current_page = MASK_8BIT;
- if (rmi4_data->suspend) {
- synaptics_rmi4_get_reg(rmi4_data, true);
+ if (rmi4_data->suspend)
synaptics_rmi4_enable_reg(rmi4_data, true);
- }
synaptics_rmi4_sleep_enable(rmi4_data, false);
synaptics_rmi4_irq_enable(rmi4_data, true, false);
diff --git a/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.h b/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.h
index 39fec9a..f2fdaf1 100644
--- a/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.h
+++ b/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_core.h
@@ -372,6 +372,7 @@
bool fb_ready;
bool f11_wakeup_gesture;
bool f12_wakeup_gesture;
+ bool wakeup_gesture_en;
bool enable_wakeup_gesture;
bool wedge_sensor;
bool report_pressure;
diff --git a/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_i2c.c b/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_i2c.c
index df17a0b..f634f17 100644
--- a/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_i2c.c
+++ b/drivers/input/touchscreen/synaptics_dsx_2.6/synaptics_dsx_i2c.c
@@ -81,6 +81,9 @@
bdata->resume_in_workqueue = of_property_read_bool(np,
"synaptics,resume-in-workqueue");
+ bdata->wakeup_gesture_en = of_property_read_bool(np,
+ "synaptics,wakeup-gestures-en");
+
retval = of_property_read_string(np, "synaptics,pwr-reg-name", &name);
if (retval < 0)
bdata->pwr_reg_name = NULL;
diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index 40d4a2c..8005ab8 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -542,6 +542,7 @@
bool qsmmuv500_errata1_init;
bool qsmmuv500_errata1_client;
bool qsmmuv500_errata2_min_align;
+ bool is_force_guard_page;
};
static DEFINE_SPINLOCK(arm_smmu_devices_lock);
@@ -3245,6 +3246,12 @@
*((int *)data) = smmu_domain->qsmmuv500_errata2_min_align;
ret = 0;
break;
+ case DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE:
+ *((int *)data) = !!(smmu_domain->attributes
+ & (1 << DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE));
+ ret = 0;
+ break;
+
default:
ret = -ENODEV;
break;
@@ -3447,6 +3454,28 @@
1 << DOMAIN_ATTR_CB_STALL_DISABLE;
ret = 0;
break;
+
+ case DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE: {
+ int force_iova_guard_page = *((int *)data);
+
+ if (smmu_domain->smmu != NULL) {
+ dev_err(smmu_domain->smmu->dev,
+ "cannot change force guard page attribute while attached\n");
+ ret = -EBUSY;
+ break;
+ }
+
+ if (force_iova_guard_page)
+ smmu_domain->attributes |=
+ 1 << DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE;
+ else
+ smmu_domain->attributes &=
+ ~(1 << DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE);
+
+ ret = 0;
+ break;
+ }
+
default:
ret = -ENODEV;
}
@@ -5486,7 +5515,11 @@
pdev = container_of(dev, struct platform_device, dev);
res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "tcu-base");
- data->tcu_base = devm_ioremap_resource(dev, res);
+ if (!res) {
+ dev_err(dev, "Unable to get the tcu-base\n");
+ return -EINVAL;
+ }
+ data->tcu_base = devm_ioremap(dev, res->start, resource_size(res));
if (IS_ERR(data->tcu_base))
return PTR_ERR(data->tcu_base);
diff --git a/drivers/iommu/dma-iommu.c b/drivers/iommu/dma-iommu.c
index 57ae0dd..36c84df 100644
--- a/drivers/iommu/dma-iommu.c
+++ b/drivers/iommu/dma-iommu.c
@@ -45,6 +45,7 @@
spinlock_t msi_lock;
u32 min_iova_align;
struct page *guard_page;
+ u32 force_guard_page_len;
};
static inline struct iova_domain *cookie_iovad(struct iommu_domain *domain)
@@ -130,20 +131,31 @@
struct iommu_dma_cookie *cookie = domain->iova_cookie;
int vmid = VMID_HLOS;
int min_iova_align = 0;
+ int force_iova_guard_page = 0;
+
iommu_domain_get_attr(domain,
DOMAIN_ATTR_MMU500_ERRATA_MIN_ALIGN,
&min_iova_align);
iommu_domain_get_attr(domain, DOMAIN_ATTR_SECURE_VMID, &vmid);
+ iommu_domain_get_attr(domain,
+ DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE,
+ &force_iova_guard_page);
+
if (vmid >= VMID_LAST || vmid < 0)
vmid = VMID_HLOS;
- if (min_iova_align) {
- cookie->min_iova_align = ARM_SMMU_MIN_IOVA_ALIGN;
- cookie->guard_page = arm_smmu_errata_get_guard_page(vmid);
- if (!cookie->guard_page)
- return -ENOMEM;
- }
+ cookie->min_iova_align = (min_iova_align) ? ARM_SMMU_MIN_IOVA_ALIGN :
+ PAGE_SIZE;
+
+ if (force_iova_guard_page)
+ cookie->force_guard_page_len = PAGE_SIZE;
+
+ cookie->guard_page =
+ arm_smmu_errata_get_guard_page(vmid);
+ if (!cookie->guard_page)
+ return -ENOMEM;
+
return 0;
}
@@ -244,7 +256,8 @@
dma_addr_t ret_iova;
if (cookie->min_iova_align)
- guard_len = ALIGN(size, cookie->min_iova_align) - size;
+ guard_len = ALIGN(size + cookie->force_guard_page_len,
+ cookie->min_iova_align) - size;
else
guard_len = 0;
iova_len = (size + guard_len) >> shift;
@@ -290,12 +303,14 @@
unsigned long shift = iova_shift(iovad);
unsigned long guard_len;
- if (cookie->min_iova_align) {
- guard_len = ALIGN(size, cookie->min_iova_align) - size;
- iommu_unmap(domain, iova + size, guard_len);
- } else {
+ if (cookie->min_iova_align)
+ guard_len = ALIGN(size + cookie->force_guard_page_len,
+ cookie->min_iova_align) - size;
+ else
guard_len = 0;
- }
+
+ if (guard_len)
+ iommu_unmap(domain, iova + size, guard_len);
free_iova_fast(iovad, iova >> shift, (size + guard_len) >> shift);
}
diff --git a/drivers/iommu/dma-mapping-fast.c b/drivers/iommu/dma-mapping-fast.c
index eac7b41..7e6287c 100644
--- a/drivers/iommu/dma-mapping-fast.c
+++ b/drivers/iommu/dma-mapping-fast.c
@@ -163,7 +163,8 @@
dma_addr_t iova;
if (mapping->min_iova_align)
- guard_len = ALIGN(size, mapping->min_iova_align) - size;
+ guard_len = ALIGN(size + mapping->force_guard_page_len,
+ mapping->min_iova_align) - size;
else
guard_len = 0;
@@ -311,12 +312,15 @@
unsigned long nbits;
unsigned long guard_len;
- if (mapping->min_iova_align) {
- guard_len = ALIGN(size, mapping->min_iova_align) - size;
- iommu_unmap(mapping->domain, iova + size, guard_len);
- } else {
+ if (mapping->min_iova_align)
+ guard_len = ALIGN(size + mapping->force_guard_page_len,
+ mapping->min_iova_align) - size;
+ else
guard_len = 0;
- }
+
+ if (guard_len)
+ iommu_unmap(mapping->domain, iova + size, guard_len);
+
nbits = (size + guard_len) >> FAST_PAGE_SHIFT;
@@ -898,20 +902,30 @@
struct dma_fast_smmu_mapping *fast = mapping->fast;
int vmid = VMID_HLOS;
int min_iova_align = 0;
+ int force_iova_guard_page = 0;
iommu_domain_get_attr(mapping->domain,
- DOMAIN_ATTR_MMU500_ERRATA_MIN_ALIGN,
- &min_iova_align);
+ DOMAIN_ATTR_MMU500_ERRATA_MIN_ALIGN,
+ &min_iova_align);
iommu_domain_get_attr(mapping->domain, DOMAIN_ATTR_SECURE_VMID, &vmid);
+ iommu_domain_get_attr(mapping->domain,
+ DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE,
+ &force_iova_guard_page);
+
if (vmid >= VMID_LAST || vmid < 0)
vmid = VMID_HLOS;
- if (min_iova_align) {
- fast->min_iova_align = ARM_SMMU_MIN_IOVA_ALIGN;
- fast->guard_page = arm_smmu_errata_get_guard_page(vmid);
- if (!fast->guard_page)
- return -ENOMEM;
- }
+ fast->min_iova_align = (min_iova_align) ? ARM_SMMU_MIN_IOVA_ALIGN :
+ PAGE_SIZE;
+
+ if (force_iova_guard_page)
+ fast->force_guard_page_len = PAGE_SIZE;
+
+ fast->guard_page =
+ arm_smmu_errata_get_guard_page(vmid);
+ if (!fast->guard_page)
+ return -ENOMEM;
+
return 0;
}
diff --git a/drivers/irqchip/irq-gic-common.h b/drivers/irqchip/irq-gic-common.h
index 83b72f4..623e572 100644
--- a/drivers/irqchip/irq-gic-common.h
+++ b/drivers/irqchip/irq-gic-common.h
@@ -30,6 +30,12 @@
extern bool from_suspend;
extern struct irq_chip gic_arch_extn;
+#ifdef CONFIG_QCOM_SHOW_RESUME_IRQ
+extern int msm_show_resume_irq_mask;
+#else
+#define msm_show_resume_irq_mask 0
+#endif
+
int gic_configure_irq(unsigned int irq, unsigned int type,
void __iomem *base, void (*sync_access)(void));
void gic_dist_config(void __iomem *base, int gic_irqs,
diff --git a/drivers/irqchip/irq-gic-v3.c b/drivers/irqchip/irq-gic-v3.c
index c67e813..2519c92 100644
--- a/drivers/irqchip/irq-gic-v3.c
+++ b/drivers/irqchip/irq-gic-v3.c
@@ -40,6 +40,8 @@
#include <asm/smp_plat.h>
#include <asm/virt.h>
+#include <linux/syscore_ops.h>
+
#include "irq-gic-common.h"
struct redist_region {
@@ -370,6 +372,69 @@
return 0;
}
+#ifdef CONFIG_PM
+
+static int gic_suspend(void)
+{
+ return 0;
+}
+
+static void gic_show_resume_irq(struct gic_chip_data *gic)
+{
+ unsigned int i;
+ u32 enabled;
+ u32 pending[32];
+ void __iomem *base = gic_data.dist_base;
+
+ if (!msm_show_resume_irq_mask)
+ return;
+
+ for (i = 0; i * 32 < gic->irq_nr; i++) {
+ enabled = readl_relaxed(base + GICD_ICENABLER + i * 4);
+ pending[i] = readl_relaxed(base + GICD_ISPENDR + i * 4);
+ pending[i] &= enabled;
+ }
+
+ for (i = find_first_bit((unsigned long *)pending, gic->irq_nr);
+ i < gic->irq_nr;
+ i = find_next_bit((unsigned long *)pending, gic->irq_nr, i+1)) {
+ unsigned int irq = irq_find_mapping(gic->domain, i);
+ struct irq_desc *desc = irq_to_desc(irq);
+ const char *name = "null";
+
+ if (desc == NULL)
+ name = "stray irq";
+ else if (desc->action && desc->action->name)
+ name = desc->action->name;
+
+ pr_warn("%s: %d triggered %s\n", __func__, irq, name);
+ }
+}
+
+static void gic_resume_one(struct gic_chip_data *gic)
+{
+ gic_show_resume_irq(gic);
+}
+
+static void gic_resume(void)
+{
+ gic_resume_one(&gic_data);
+}
+
+static struct syscore_ops gic_syscore_ops = {
+ .suspend = gic_suspend,
+ .resume = gic_resume,
+};
+
+static int __init gic_init_sys(void)
+{
+ register_syscore_ops(&gic_syscore_ops);
+ return 0;
+}
+arch_initcall(gic_init_sys);
+
+#endif
+
static u64 gic_mpidr_to_affinity(unsigned long mpidr)
{
u64 aff;
diff --git a/drivers/irqchip/irq-gic.c b/drivers/irqchip/irq-gic.c
index 6c9446e..bd189a4 100644
--- a/drivers/irqchip/irq-gic.c
+++ b/drivers/irqchip/irq-gic.c
@@ -48,6 +48,7 @@
#include <asm/smp_plat.h>
#include <asm/virt.h>
+#include <linux/syscore_ops.h>
#include "irq-gic-common.h"
#ifdef CONFIG_ARM64
@@ -1232,6 +1233,70 @@
return ret;
}
+#ifdef CONFIG_PM
+static int gic_suspend(void)
+{
+ return 0;
+}
+
+static void gic_show_resume_irq(struct gic_chip_data *gic)
+{
+ unsigned int i;
+ u32 enabled;
+ u32 pending[32];
+ void __iomem *base = gic_data_dist_base(gic);
+
+ if (!msm_show_resume_irq_mask)
+ return;
+
+ for (i = 0; i * 32 < gic->gic_irqs; i++) {
+ enabled = readl_relaxed(base + GIC_DIST_ENABLE_CLEAR + i * 4);
+ pending[i] = readl_relaxed(base + GIC_DIST_PENDING_SET + i * 4);
+ pending[i] &= enabled;
+ }
+
+ for (i = find_first_bit((unsigned long *)pending, gic->gic_irqs);
+ i < gic->gic_irqs;
+ i = find_next_bit((unsigned long *)pending, gic->gic_irqs, i+1)) {
+ unsigned int irq = irq_find_mapping(gic->domain, i);
+ struct irq_desc *desc = irq_to_desc(irq);
+ const char *name = "null";
+
+ if (desc == NULL)
+ name = "stray irq";
+ else if (desc->action && desc->action->name)
+ name = desc->action->name;
+
+ pr_warn("%s: %d triggered %s\n", __func__, i, name);
+ }
+}
+
+static void gic_resume_one(struct gic_chip_data *gic)
+{
+ gic_show_resume_irq(gic);
+}
+
+static void gic_resume(void)
+{
+ int i;
+
+ for (i = 0; i < CONFIG_ARM_GIC_MAX_NR; i++)
+ gic_resume_one(&gic_data[i]);
+}
+
+static struct syscore_ops gic_syscore_ops = {
+ .suspend = gic_suspend,
+ .resume = gic_resume,
+};
+
+static int __init gic_init_sys(void)
+{
+ register_syscore_ops(&gic_syscore_ops);
+ return 0;
+}
+arch_initcall(gic_init_sys);
+#endif
+
void __init gic_init(unsigned int gic_nr, int irq_start,
void __iomem *dist_base, void __iomem *cpu_base)
{
diff --git a/drivers/irqchip/qcom/mpm.c b/drivers/irqchip/qcom/mpm.c
index a8b8b9b..2de64b6 100644
--- a/drivers/irqchip/qcom/mpm.c
+++ b/drivers/irqchip/qcom/mpm.c
@@ -466,6 +466,8 @@
}
msm_mpm_timer_write((uint32_t *)&wakeup);
+ trace_mpm_wakeup_time(from_idle, wakeup, arch_counter_get_cntvct());
+
return 0;
}
diff --git a/drivers/leds/leds-qti-tri-led.c b/drivers/leds/leds-qti-tri-led.c
index f638bc9..c303893 100644
--- a/drivers/leds/leds-qti-tri-led.c
+++ b/drivers/leds/leds-qti-tri-led.c
@@ -53,6 +53,7 @@
u32 off_ms;
enum led_brightness brightness;
bool blink;
+ bool breath;
};
struct qpnp_led_dev {
@@ -66,6 +67,7 @@
const char *default_trigger;
u8 id;
bool blinking;
+ bool breathing;
};
struct qpnp_tri_led_chip {
@@ -119,6 +121,10 @@
pstate.enabled = !!(pwm->duty_ns != 0);
pstate.period = pwm->period_ns;
pstate.duty_cycle = pwm->duty_ns;
+ pstate.output_type = led->led_setting.breath ?
+ PWM_OUTPUT_MODULATED : PWM_OUTPUT_FIXED;
+ /* Use default pattern in PWM device */
+ pstate.output_pattern = NULL;
rc = pwm_apply_state(led->pwm_dev, &pstate);
if (rc < 0)
@@ -183,7 +189,9 @@
/* Use initial period if no blinking is required */
period_ns = led->pwm_setting.pre_period_ns;
- if (period_ns > INT_MAX / brightness)
+ if (brightness == LED_OFF)
+ duty_ns = 0;
+ else if (period_ns > INT_MAX / brightness)
duty_ns = (period_ns / LED_FULL) * brightness;
else
duty_ns = (period_ns * brightness) / LED_FULL;
@@ -207,9 +215,15 @@
if (led->led_setting.blink) {
led->cdev.brightness = LED_FULL;
led->blinking = true;
+ led->breathing = false;
+ } else if (led->led_setting.breath) {
+ led->cdev.brightness = LED_FULL;
+ led->blinking = false;
+ led->breathing = true;
} else {
led->cdev.brightness = led->led_setting.brightness;
led->blinking = false;
+ led->breathing = false;
}
return rc;
@@ -227,7 +241,7 @@
brightness = LED_FULL;
if (brightness == led->led_setting.brightness &&
- !led->blinking) {
+ !led->blinking && !led->breathing) {
mutex_unlock(&led->lock);
return 0;
}
@@ -238,6 +252,7 @@
else
led->led_setting.on_ms = 0;
led->led_setting.blink = false;
+ led->led_setting.breath = false;
rc = qpnp_tri_led_set(led);
if (rc)
@@ -273,14 +288,17 @@
if (*on_ms == 0) {
led->led_setting.blink = false;
+ led->led_setting.breath = false;
led->led_setting.brightness = LED_OFF;
} else if (*off_ms == 0) {
led->led_setting.blink = false;
+ led->led_setting.breath = false;
led->led_setting.brightness = led->cdev.brightness;
} else {
led->led_setting.on_ms = *on_ms;
led->led_setting.off_ms = *off_ms;
led->led_setting.blink = true;
+ led->led_setting.breath = false;
}
rc = qpnp_tri_led_set(led);
@@ -292,6 +310,52 @@
return rc;
}
+static ssize_t breath_show(struct device *dev, struct device_attribute *attr,
+ char *buf)
+{
+ struct led_classdev *led_cdev = dev_get_drvdata(dev);
+ struct qpnp_led_dev *led =
+ container_of(led_cdev, struct qpnp_led_dev, cdev);
+
+ return snprintf(buf, PAGE_SIZE, "%d\n", led->led_setting.breath);
+}
+
+static ssize_t breath_store(struct device *dev, struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ int rc;
+ bool breath;
+ struct led_classdev *led_cdev = dev_get_drvdata(dev);
+ struct qpnp_led_dev *led =
+ container_of(led_cdev, struct qpnp_led_dev, cdev);
+
+ rc = kstrtobool(buf, &breath);
+ if (rc < 0)
+ return rc;
+
+ mutex_lock(&led->lock);
+ if (led->breathing == breath)
+ goto unlock;
+
+ led->led_setting.blink = false;
+ led->led_setting.breath = breath;
+ led->led_setting.brightness = breath ? LED_FULL : LED_OFF;
+ rc = qpnp_tri_led_set(led);
+ if (rc < 0)
+ dev_err(led->chip->dev, "Set led failed for %s, rc=%d\n",
+ led->label, rc);
+
+unlock:
+ mutex_unlock(&led->lock);
+ return (rc < 0) ? rc : count;
+}
+
+static DEVICE_ATTR(breath, 0644, breath_show, breath_store);
+static const struct attribute *breath_attrs[] = {
+ &dev_attr_breath.attr,
+ NULL
+};
+
static int qpnp_tri_led_register(struct qpnp_tri_led_chip *chip)
{
struct qpnp_led_dev *led;
@@ -313,15 +377,30 @@
if (rc < 0) {
dev_err(chip->dev, "%s led class device registering failed, rc=%d\n",
led->label, rc);
- goto destroy;
+ goto err_out;
+ }
+
+ if (pwm_get_output_type_supported(led->pwm_dev)
+ & PWM_OUTPUT_MODULATED) {
+ rc = sysfs_create_files(&led->cdev.dev->kobj,
+ breath_attrs);
+ if (rc < 0) {
+ dev_err(chip->dev, "Create breath file for %s led failed, rc=%d\n",
+ led->label, rc);
+ goto err_out;
+ }
}
}
return 0;
-destroy:
- for (j = 0; j <= i; j++)
- mutex_destroy(&chip->leds[i].lock);
+err_out:
+ for (j = 0; j <= i; j++) {
+ if (j < i)
+ sysfs_remove_files(&chip->leds[j].cdev.dev->kobj,
+ breath_attrs);
+ mutex_destroy(&chip->leds[j].lock);
+ }
return rc;
}
@@ -483,8 +562,10 @@
struct qpnp_tri_led_chip *chip = dev_get_drvdata(&pdev->dev);
mutex_destroy(&chip->bus_lock);
- for (i = 0; i < chip->num_leds; i++)
+ for (i = 0; i < chip->num_leds; i++) {
+ sysfs_remove_files(&chip->leds[i].cdev.dev->kobj, breath_attrs);
mutex_destroy(&chip->leds[i].lock);
+ }
dev_set_drvdata(chip->dev, NULL);
return 0;
}
diff --git a/drivers/media/platform/msm/camera/cam_cpas/cpas_top/cam_cpastop_hw.c b/drivers/media/platform/msm/camera/cam_cpas/cpas_top/cam_cpastop_hw.c
index 74f349a..158bbb9 100644
--- a/drivers/media/platform/msm/camera/cam_cpas/cpas_top/cam_cpastop_hw.c
+++ b/drivers/media/platform/msm/camera/cam_cpas/cpas_top/cam_cpastop_hw.c
@@ -374,7 +374,8 @@
if ((payload->irq_status & camnoc_info->irq_err[i].sbm_port) &&
(camnoc_info->irq_err[i].enable)) {
irq_type = camnoc_info->irq_err[i].irq_type;
- CAM_ERR(CAM_CPAS, "Error occurred, type=%d", irq_type);
+ CAM_ERR_RATE_LIMIT(CAM_CPAS,
+ "Error occurred, type=%d", irq_type);
memset(&irq_data, 0x0, sizeof(irq_data));
irq_data.irq_type = (enum cam_camnoc_irq_type)irq_type;
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_actuator/cam_actuator_core.c b/drivers/media/platform/msm/camera/cam_sensor_module/cam_actuator/cam_actuator_core.c
index 9f26635..56cb49a 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_actuator/cam_actuator_core.c
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_actuator/cam_actuator_core.c
@@ -488,6 +488,7 @@
i2c_reg_settings->request_id = 0;
i2c_reg_settings->is_settings_valid = 1;
rc = cam_sensor_i2c_command_parser(
+ &a_ctrl->io_master_info,
i2c_reg_settings,
&cmd_desc[i], 1);
if (rc < 0) {
@@ -544,7 +545,9 @@
offset = (uint32_t *)&csl_packet->payload;
offset += csl_packet->cmd_buf_offset / sizeof(uint32_t);
cmd_desc = (struct cam_cmd_buf_desc *)(offset);
- rc = cam_sensor_i2c_command_parser(i2c_reg_settings,
+ rc = cam_sensor_i2c_command_parser(
+ &a_ctrl->io_master_info,
+ i2c_reg_settings,
cmd_desc, 1);
if (rc < 0) {
CAM_ERR(CAM_ACTUATOR,
@@ -570,7 +573,9 @@
offset = (uint32_t *)&csl_packet->payload;
offset += csl_packet->cmd_buf_offset / sizeof(uint32_t);
cmd_desc = (struct cam_cmd_buf_desc *)(offset);
- rc = cam_sensor_i2c_command_parser(i2c_reg_settings,
+ rc = cam_sensor_i2c_command_parser(
+ &a_ctrl->io_master_info,
+ i2c_reg_settings,
cmd_desc, 1);
if (rc < 0) {
CAM_ERR(CAM_ACTUATOR,
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_eeprom/cam_eeprom_dev.c b/drivers/media/platform/msm/camera/cam_sensor_module/cam_eeprom/cam_eeprom_dev.c
index 68c5eea..b8c32d4 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_eeprom/cam_eeprom_dev.c
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_eeprom/cam_eeprom_dev.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2017-2018, 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
@@ -69,6 +69,9 @@
cci_client->retries = 3;
cci_client->id_map = 0;
cci_client->i2c_freq_mode = i2c_info->i2c_freq_mode;
+ } else if (e_ctrl->io_master_info.master_type == I2C_MASTER) {
+ e_ctrl->io_master_info.client->addr = i2c_info->slave_addr;
+ CAM_DBG(CAM_EEPROM, "Slave addr: 0x%x", i2c_info->slave_addr);
}
return 0;
}
@@ -188,6 +191,9 @@
e_ctrl->io_master_info.master_type = I2C_MASTER;
e_ctrl->io_master_info.client = client;
e_ctrl->eeprom_device_type = MSM_CAMERA_I2C_DEVICE;
+ e_ctrl->cal_data.mapdata = NULL;
+ e_ctrl->cal_data.map = NULL;
+ e_ctrl->userspace_probe = false;
rc = cam_eeprom_parse_dt(e_ctrl);
if (rc) {
@@ -205,10 +211,6 @@
if (rc)
goto free_soc;
- e_ctrl->cal_data.mapdata = NULL;
- e_ctrl->cal_data.map = NULL;
- e_ctrl->userspace_probe = false;
-
if (soc_private->i2c_info.slave_addr != 0)
e_ctrl->io_master_info.client->addr =
soc_private->i2c_info.slave_addr;
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_ois/cam_ois_core.c b/drivers/media/platform/msm/camera/cam_sensor_module/cam_ois/cam_ois_core.c
index fbdaee7..c792be4 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_ois/cam_ois_core.c
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_ois/cam_ois_core.c
@@ -517,6 +517,7 @@
i2c_reg_settings->is_settings_valid = 1;
i2c_reg_settings->request_id = 0;
rc = cam_sensor_i2c_command_parser(
+ &o_ctrl->io_master_info,
i2c_reg_settings,
&cmd_desc[i], 1);
if (rc < 0) {
@@ -533,6 +534,7 @@
i2c_reg_settings->is_settings_valid = 1;
i2c_reg_settings->request_id = 0;
rc = cam_sensor_i2c_command_parser(
+ &o_ctrl->io_master_info,
i2c_reg_settings,
&cmd_desc[i], 1);
if (rc < 0) {
@@ -604,7 +606,8 @@
i2c_reg_settings = &(o_ctrl->i2c_mode_data);
i2c_reg_settings->is_settings_valid = 1;
i2c_reg_settings->request_id = 0;
- rc = cam_sensor_i2c_command_parser(i2c_reg_settings,
+ rc = cam_sensor_i2c_command_parser(&o_ctrl->io_master_info,
+ i2c_reg_settings,
cmd_desc, 1);
if (rc < 0) {
CAM_ERR(CAM_OIS, "OIS pkt parsing failed: %d", rc);
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor/cam_sensor_core.c b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor/cam_sensor_core.c
index b3f3a35..e9dd1ad 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor/cam_sensor_core.c
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor/cam_sensor_core.c
@@ -230,7 +230,8 @@
offset += csl_packet->cmd_buf_offset / 4;
cmd_desc = (struct cam_cmd_buf_desc *)(offset);
- rc = cam_sensor_i2c_command_parser(i2c_reg_settings, cmd_desc, 1);
+ rc = cam_sensor_i2c_command_parser(&s_ctrl->io_master_info,
+ i2c_reg_settings, cmd_desc, 1);
if (rc < 0) {
CAM_ERR(CAM_SENSOR, "Fail parsing I2C Pkt: %d", rc);
return rc;
@@ -562,7 +563,6 @@
struct cam_sensor_power_setting *pd = NULL;
struct cam_sensor_power_ctrl_t *power_info =
&s_ctrl->sensordata->power_info;
-
if (!s_ctrl || !arg) {
CAM_ERR(CAM_SENSOR, "s_ctrl is NULL");
return -EINVAL;
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/Makefile b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/Makefile
index 98ee3ae..9f0843d 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/Makefile
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/Makefile
@@ -4,5 +4,6 @@
ccflags-y += -Idrivers/media/platform/msm/camera/cam_sensor_module/cam_cci
ccflags-y += -Idrivers/media/platform/msm/camera/cam_sensor_module/cam_res_mgr
ccflags-y += -Idrivers/media/platform/msm/camera/cam_smmu/
+ccflags-y += -Idrivers/media/platform/msm/camera/cam_cpas/include
obj-$(CONFIG_SPECTRA_CAMERA) += cam_sensor_util.o
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.c b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.c
index ac60dc8..a399963 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.c
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.c
@@ -242,6 +242,41 @@
return rc;
}
+static int cam_sensor_handle_slave_info(
+ struct camera_io_master *io_master,
+ uint32_t *cmd_buf)
+{
+ int rc = 0;
+ struct cam_cmd_i2c_info *i2c_info = (struct cam_cmd_i2c_info *)cmd_buf;
+
+ if (io_master == NULL || cmd_buf == NULL) {
+ CAM_ERR(CAM_SENSOR, "Invalid args");
+ return -EINVAL;
+ }
+
+ switch (io_master->master_type) {
+ case CCI_MASTER:
+ io_master->cci_client->sid = (i2c_info->slave_addr >> 1);
+ io_master->cci_client->i2c_freq_mode = i2c_info->i2c_freq_mode;
+ break;
+
+ case I2C_MASTER:
+ io_master->client->addr = i2c_info->slave_addr;
+ break;
+
+ case SPI_MASTER:
+ break;
+
+ default:
+ CAM_ERR(CAM_SENSOR, "Invalid master type: %d",
+ io_master->master_type);
+ rc = -EINVAL;
+ break;
+ }
+
+ return rc;
+}
+
/**
* Name : cam_sensor_i2c_command_parser
* Description : Parse CSL CCI packet and apply register settings
@@ -253,12 +288,16 @@
* WAIT + n x RND_WR with num_cmd_buf = 1. Do not exepect RD/WR
* with different cmd_type and op_code in one command buffer.
*/
-int cam_sensor_i2c_command_parser(struct i2c_settings_array *i2c_reg_settings,
- struct cam_cmd_buf_desc *cmd_desc, int32_t num_cmd_buffers)
+int cam_sensor_i2c_command_parser(
+ struct camera_io_master *io_master,
+ struct i2c_settings_array *i2c_reg_settings,
+ struct cam_cmd_buf_desc *cmd_desc,
+ int32_t num_cmd_buffers)
{
int16_t rc = 0, i = 0;
size_t len_of_buff = 0;
uint64_t generic_ptr;
+ uint16_t cmd_length_in_bytes = 0;
for (i = 0; i < num_cmd_buffers; i++) {
uint32_t *cmd_buf = NULL;
@@ -272,7 +311,6 @@
* It is not expected the same settings to
* be spread across multiple cmd buffers
*/
-
CAM_DBG(CAM_SENSOR, "Total cmd Buf in Bytes: %d",
cmd_desc[i].length);
@@ -373,6 +411,22 @@
}
break;
}
+ case CAMERA_SENSOR_CMD_TYPE_I2C_INFO: {
+ rc = cam_sensor_handle_slave_info(
+ io_master, cmd_buf);
+ if (rc) {
+ CAM_ERR(CAM_SENSOR,
+ "Handle slave info failed with rc: %d",
+ rc);
+ return rc;
+ }
+ cmd_length_in_bytes =
+ sizeof(struct cam_cmd_i2c_info);
+ cmd_buf +=
+ cmd_length_in_bytes / sizeof(uint32_t);
+ byte_cnt += cmd_length_in_bytes;
+ break;
+ }
default:
CAM_ERR(CAM_SENSOR, "Invalid Command Type:%d",
cmm_hdr->cmd_type);
diff --git a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.h b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.h
index d2079b0..c9ccc5c 100644
--- a/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.h
+++ b/drivers/media/platform/msm/camera/cam_sensor_module/cam_sensor_utils/cam_sensor_util.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2017-2018, 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
@@ -24,6 +24,7 @@
#include <cam_mem_mgr.h>
#include "cam_soc_util.h"
#include "cam_debug_util.h"
+#include "cam_sensor_io.h"
#define INVALID_VREG 100
@@ -34,7 +35,8 @@
int msm_camera_pinctrl_init
(struct msm_pinctrl_info *sensor_pctrl, struct device *dev);
-int cam_sensor_i2c_command_parser(struct i2c_settings_array *i2c_reg_settings,
+int cam_sensor_i2c_command_parser(struct camera_io_master *io_master,
+ struct i2c_settings_array *i2c_reg_settings,
struct cam_cmd_buf_desc *cmd_desc, int32_t num_cmd_buffers);
int32_t delete_request(struct i2c_settings_array *i2c_array);
diff --git a/drivers/media/platform/msm/camera/cam_smmu/cam_smmu_api.c b/drivers/media/platform/msm/camera/cam_smmu/cam_smmu_api.c
index 0d03df0..ecfc566 100644
--- a/drivers/media/platform/msm/camera/cam_smmu/cam_smmu_api.c
+++ b/drivers/media/platform/msm/camera/cam_smmu/cam_smmu_api.c
@@ -145,6 +145,7 @@
struct mutex payload_list_lock;
struct list_head payload_list;
u32 non_fatal_fault;
+ u32 enable_iova_guard;
};
static const struct of_device_id msm_cam_smmu_dt_match[] = {
@@ -3048,6 +3049,15 @@
"Error: failed to set non fatal fault attribute");
}
+ if (!strcmp(cb->name, "icp")) {
+ iommu_cb_set.enable_iova_guard = 1;
+ if (iommu_domain_set_attr(cb->mapping->domain,
+ DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE,
+ &iommu_cb_set.enable_iova_guard) < 0) {
+ CAM_ERR(CAM_SMMU,
+ "Failed to set iova guard pagei attr");
+ }
+ }
} else {
CAM_ERR(CAM_SMMU, "Context bank does not have IO region");
rc = -ENODEV;
diff --git a/drivers/media/platform/msm/camera_v2/common/cam_smmu_api.c b/drivers/media/platform/msm/camera_v2/common/cam_smmu_api.c
index 08c8575..1d74309 100644
--- a/drivers/media/platform/msm/camera_v2/common/cam_smmu_api.c
+++ b/drivers/media/platform/msm/camera_v2/common/cam_smmu_api.c
@@ -270,53 +270,6 @@
}
}
-
-static int cam_smmu_query_vaddr_in_range(int handle,
- unsigned long fault_addr, unsigned long *start_addr,
- unsigned long *end_addr, int *fd)
-{
- int idx, rc = -EINVAL;
- struct cam_dma_buff_info *mapping;
- unsigned long sa, ea;
-
- if (!start_addr || !end_addr || !fd) {
- pr_err("Invalid params\n");
- return -EINVAL;
- }
-
- idx = GET_SMMU_TABLE_IDX(handle);
- if (handle == HANDLE_INIT || idx < 0 || idx >= iommu_cb_set.cb_num) {
- pr_err("Error: handle or index invalid. idx = %d hdl = %x\n",
- idx, handle);
- return -EINVAL;
- }
-
- mutex_lock(&iommu_cb_set.cb_info[idx].lock);
- if (iommu_cb_set.cb_info[idx].handle != handle) {
- pr_err("Error: hdl is not valid, table_hdl = %x, hdl = %x\n",
- iommu_cb_set.cb_info[idx].handle, handle);
- mutex_unlock(&iommu_cb_set.cb_info[idx].lock);
- return -EINVAL;
- }
-
- list_for_each_entry(mapping,
- &iommu_cb_set.cb_info[idx].smmu_buf_list, list) {
- sa = (unsigned long)mapping->paddr;
- ea = (unsigned long)mapping->paddr + mapping->len;
-
- if (sa <= fault_addr && fault_addr < ea) {
- *start_addr = sa;
- *end_addr = ea;
- *fd = mapping->ion_fd;
- rc = 0;
- break;
- }
- }
- mutex_unlock(&iommu_cb_set.cb_info[idx].lock);
- return rc;
-}
-EXPORT_SYMBOL(cam_smmu_query_vaddr_in_range);
-
static void cam_smmu_check_vaddr_in_range(int idx, void *vaddr)
{
struct cam_dma_buff_info *mapping;
diff --git a/drivers/media/platform/msm/camera_v2/sensor/csiphy/include/msm_csiphy_10_0_0_hwreg.h b/drivers/media/platform/msm/camera_v2/sensor/csiphy/include/msm_csiphy_10_0_0_hwreg.h
new file mode 100644
index 0000000..87c759c
--- /dev/null
+++ b/drivers/media/platform/msm/camera_v2/sensor/csiphy/include/msm_csiphy_10_0_0_hwreg.h
@@ -0,0 +1,143 @@
+/* Copyright (c) 2018, 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.
+ */
+
+#ifndef MSM_CSIPHY_10_0_0_HWREG_H
+#define MSM_CSIPHY_10_0_0_HWREG_H
+
+#include <sensor/csiphy/msm_csiphy.h>
+
+#define LANE_MASK_AGGR_MODE 0x1F
+#define LANE_MASK_PHY_A 0x13
+#define LANE_MASK_PHY_B 0x2C
+#define mask_phy_enable_A 0x3
+#define mask_phy_enable_B 0xC
+#define mask_base_dir_A 0x1
+#define mask_base_dir_B 0x2
+#define mask_force_mode_A 0x3
+#define mask_force_mode_B 0xC
+#define mask_enable_clk_A 0x1
+#define mask_enable_clk_B 0x2
+#define mask_ctrl_1_A 0x5
+#define mask_ctrl_1_B 0xA
+#define mask_hs_freq_range 0x7F
+#define mask_osc_freq_2 0xFF
+#define mask_osc_freq_3 0xF00
+
+static struct csiphy_reg_parms_t csiphy_v10_0_0 = {
+ //ToDo: Fill these addresses from SWI
+ .mipi_csiphy_interrupt_status0_addr = 0x5B4,
+ .mipi_csiphy_interrupt_clear0_addr = 0x59C,
+ .mipi_csiphy_glbl_irq_cmd_addr = 0x588,
+ .mipi_csiphy_interrupt_clk_status0_addr = 0x5D8,
+ .mipi_csiphy_interrupt_clk_clear0_addr = 0x5D0,
+};
+
+static struct csiphy_reg_snps_parms_t csiphy_v10_0_0_snps = {
+ /*MIPI CSI PHY registers*/
+ {0x560, 0x9}, /* mipi_csiphy_sys_ctrl */
+ {0x5Ac, 0x9}, /* mipi_csiphy_sys_ctrl_1 */
+ {0x564, 0xF}, /* mipi_csiphy_ctrl_1 */
+ {0x568, 0x49}, /* mipi_csiphy_ctrl_2 */
+ {0x56C, 0x49}, /* mipi_csiphy_ctrl_3 */
+ {0x580, 0x7F}, /* mipi_csiphy_fifo_ctrl */
+ {0x570, 0x0}, /* mipi_csiphy_enable */
+ {0x578, 0x0}, /* mipi_csiphy_basedir */
+ {0x57C, 0x0}, /* mipi_csiphy_force_mode */
+ {0x574, 0x0}, /* mipi_csiphy_enable_clk */
+ {0x58C, 0xFF}, /* mipi_csiphy_irq_mask_ctrl_lane_0 */
+ {0x5C8, 0xFF}, /* mipi_csiphy_irq_mask_ctrl_lane_clk_0 */
+ {0x20, 0x0}, /* mipi_csiphy_rx_sys_7_00 */
+ {0x28, 0x43}, /* mipi_csiphy_rx_sys_9_00 */
+ {0x380, 0x0}, /* mipi_csiphy_rx_startup_ovr_0_00 */
+ {0x384, 0x0}, /* mipi_csiphy_rx_startup_ovr_1_00 */
+ {0x388, 0xCC}, /* mipi_csiphy_rx_startup_ovr_2_00 */
+ {0x38C, 0x1}, /* mipi_csiphy_rx_startup_ovr_3_00 */
+ {0x390, 0x1}, /* mipi_csiphy_rx_startup_ovr_4_00 */
+ {0x394, 0x1}, /* mipi_csiphy_rx_startup_ovr_5_00 */
+ {0x324, 0x0}, /* mipi_csiphy_rx_startup_obs_2_00 */
+ {0x6B0, 0x0}, /* mipi_csiphy_rx_cb_2_00 */
+ {0x4CC, 0x1}, /* mipi_csiphy_rx_dual_phy_0_00 */
+ {0xC0, 0x0}, /* mipi_csiphy_rx_clk_lane_3_00 */
+ {0xC4, 0xA}, /* mipi_csiphy_rx_clk_lane_4_00 */
+ {0xC8, 0x0}, /* mipi_csiphy_rx_clk_lane_6_00 */
+ {0x12c, 0x0}, /* mipi_csiphy_rx_lane_0_7_00 */
+ {0x220, 0x0}, /* mipi_csiphy_rx_lane_1_7_00 */
+ {0xCC, 0x0}, /* mipi_csiphy_rx_clk_lane_7_00 */
+};
+
+static struct snps_freq_value snps_v100_freq_values[] = {
+ {80, 0x0, 460 }, /* 80 - 97.125*/
+ {90, 0x10, 460 }, /* 80 - 107.625*/
+ {100, 0x20, 460 }, /* 83.125 - 118.125*/
+ {110, 0x30, 460 }, /* 92.625 - 128.625*/
+ {120, 0x1, 460 }, /* 102.125 - 139.125*/
+ {130, 0x11, 460 }, /* 111.625 - 149.625*/
+ {140, 0x21, 460 }, /* 121.125 - 160.125*/
+ {150, 0x31, 460 }, /* 130.625 - 170.625*/
+ {160, 0x2, 460 }, /* 140.125 - 181.125*/
+ {170, 0x12, 460 }, /* 149.625 - 191.625*/
+ {180, 0x22, 460 }, /* 159.125 - 202.125*/
+ {190, 0x32, 460 }, /* 168.625 - 212.625*/
+ {205, 0x3, 460 }, /* 182.875 - 228.375*/
+ {220, 0x13, 460 }, /* 197.125 - 244.125*/
+ {235, 0x23, 460 }, /* 211.375 - 259.875*/
+ {250, 0x33, 460 }, /* 225.625 - 275.625*/
+ {275, 0x4, 460 }, /* 249.375 - 301.875*/
+ {300, 0x14, 460 }, /* 273.125 - 328.125*/
+ {325, 0x25, 460 }, /* 296.875 - 354.375*/
+ {350, 0x35, 460 }, /* 320.625 - 380.625*/
+ {400, 0x5, 460 }, /* 368.125 - 433.125*/
+ {450, 0x16, 460 }, /* 415.625 - 485.625*/
+ {500, 0x26, 460 }, /* 463.125 - 538.125*/
+ {550, 0x37, 460 }, /* 510.625 - 590.625*/
+ {600, 0x7, 460 }, /* 558.125 - 643.125*/
+ {650, 0x18, 460 }, /* 605.625 - 695.625*/
+ {700, 0x28, 460 }, /* 653.125 - 748.125*/
+ {750, 0x39, 460 }, /* 700.625 - 800.625*/
+ {800, 0x9, 460 }, /* 748.125 - 853.125*/
+ {850, 0x19, 460 }, /* 795.625 - 905.625*/
+ {900, 0x29, 460 }, /* 843.125 - 958.125*/
+ {950, 0x3a, 460 }, /* 890.625 - 1010.625*/
+ {1000, 0xa, 460 }, /* 938.125 - 1063.125*/
+ {1050, 0x1a, 460 }, /* 985.625 - 1115.625*/
+ {1100, 0x2a, 460 }, /*1033.125 - 1168.125*/
+ {1150, 0x3b, 460 }, /*1080.625 - 1220.625*/
+ {1200, 0xb, 460 }, /*1128.125 - 1273.125*/
+ {1250, 0x1b, 460 }, /*1175.625 - 1325.625*/
+ {1300, 0x2b, 460 }, /*1223.125 - 1378.125*/
+ {1350, 0x3c, 460 }, /*1270.625 - 1430.625*/
+ {1400, 0xc, 460 }, /*1318.125 - 1483.125*/
+ {1450, 0x1c, 460}, /*1365.625 - 1535.625*/
+ {1500, 0x2c, 460 }, /*1413.125 - 1588.125*/
+ {1550, 0x3d, 285 }, /*1460.625 - 1640.625*/
+ {1600, 0xd, 295 }, /*1508.125 - 1693.125*/
+ {1650, 0x1d, 304 }, /*1555.625 - 1745.625*/
+ {1700, 0x2e, 313 }, /*1603.125 - 1798.125*/
+ {1750, 0x3e, 322 }, /*1650.625 - 1850.625*/
+ {1800, 0xe, 331 }, /*1698.125 - 1903.125*/
+ {1850, 0x1e, 341 }, /*1745.625 - 1955.625*/
+ {1900, 0x2f, 350 }, /*1793.125 - 2008.125*/
+ {1950, 0x3f, 359 }, /*1840.625 - 2060.625*/
+ {2000, 0xf, 368 }, /*1888.125 - 2113.125*/
+ {2050, 0x40, 377 }, /*1935.625 - 2165.625*/
+ {2100, 0x41, 387 }, /*1983.125 - 2218.125*/
+ {2150, 0x42, 396 }, /*2030.625 - 2270.625*/
+ {2200, 0x43, 405 }, /*2078.125 - 2323.125*/
+ {2250, 0x44, 414 }, /*2125.625 - 2375.625*/
+ {2300, 0x45, 423 }, /*2173.125 - 2428.125*/
+ {2350, 0x46, 432 }, /*2220.625 - 2480.625*/
+ {2400, 0x47, 442 }, /* 2268.125 - 2500*/
+ {2450, 0x48, 451 }, /* 2315.625 - 2500*/
+ {2500, 0x49, 460 }, /* 2363.125 - 2500*/
+};
+
+#endif
diff --git a/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.c b/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.c
index edf022e..58a4390 100644
--- a/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.c
+++ b/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.c
@@ -27,6 +27,8 @@
#include "include/msm_csiphy_3_5_hwreg.h"
#include "include/msm_csiphy_5_0_hwreg.h"
#include "include/msm_csiphy_5_0_1_hwreg.h"
+#include "include/msm_csiphy_10_0_0_hwreg.h"
+
#include "cam_hw_ops.h"
#define DBG_CSIPHY 0
@@ -43,6 +45,7 @@
#define CSIPHY_VERSION_V35 0x35
#define CSIPHY_VERSION_V50 0x500
#define CSIPHY_VERSION_V501 0x501
+#define CSIPHY_VERSION_V1000 0x1000
#define MSM_CSIPHY_DRV_NAME "msm_csiphy"
#define CLK_LANE_OFFSET 1
#define NUM_LANES_OFFSET 4
@@ -52,6 +55,9 @@
#define MAX_DPHY_DATA_LN 4
#define CLOCK_OFFSET 0x700
#define CSIPHY_SOF_DEBUG_COUNT 2
+#define MBPS 1000000
+#define SNPS_INTERPHY_OFFSET 0x800
+#define SET_THE_BIT(x) (0x1 << x)
#undef CDBG
#define CDBG(fmt, args...) pr_debug(fmt, ##args)
@@ -74,6 +80,42 @@
}
}
+static void snps_irq_config(
+ struct csiphy_device *csiphy_dev, bool enable)
+{
+ uint16_t offset = 0x4;
+ uint16_t data;
+ void __iomem *csiphybase;
+
+ csiphybase = csiphy_dev->base;
+
+ if (enable)
+ data = csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_0.data;
+ else
+ data = 0;
+
+ msm_camera_io_w(data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_0.addr);
+ msm_camera_io_w(data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_0.addr + offset);
+ msm_camera_io_w(data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_0.addr + 2 * offset);
+ msm_camera_io_w(data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_0.addr + 3 * offset);
+
+ msm_camera_io_w(data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_clk_0.addr);
+ msm_camera_io_w(data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_irq_mask_ctrl_lane_clk_0.addr + offset);
+}
+
static void msm_csiphy_cphy_irq_config(
struct csiphy_device *csiphy_dev,
struct msm_camera_csiphy_params *csiphy_params)
@@ -81,50 +123,459 @@
void __iomem *csiphybase;
csiphybase = csiphy_dev->base;
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl11.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl11.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl12.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl12.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl13.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl13.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl14.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl14.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl15.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl15.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl16.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl16.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl17.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl17.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl18.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl18.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl19.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl19.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl20.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl20.addr);
- msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl21.data,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl21.addr);
+ if (csiphy_dev->is_snps_phy) {
+ snps_irq_config(csiphy_dev, true);
+ } else {
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl11.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl11.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl12.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl12.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl13.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl13.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl14.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl14.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl15.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl15.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl16.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl16.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl17.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl17.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl18.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl18.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl19.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl19.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl20.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl20.addr);
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl21.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl21.addr);
+ }
+}
+
+static int msm_csiphy_snps_2_lane_config(
+ struct csiphy_device *csiphy_dev,
+ struct msm_camera_csiphy_params *csiphy_params,
+ enum snps_csiphy_mode mode, int num_lanes)
+
+{
+ uint32_t offset;
+ uint32_t value, i, diff, diff_i;
+ void __iomem *csiphybase;
+
+ csiphybase = csiphy_dev->base;
+
+ if (mode == TWO_LANE_PHY_A)
+ offset = 0x0;
+ else if (mode == TWO_LANE_PHY_B)
+ offset = SNPS_INTERPHY_OFFSET;
+ else
+ return -EINVAL;
+
+ diff = abs(snps_v100_freq_values[0].default_bit_rate -
+ ((csiphy_params->data_rate / num_lanes) / MBPS));
+ /* ToDo: Can be optimized to a O(1) search */
+ for (i = 1; i < sizeof(snps_v100_freq_values)/
+ sizeof(snps_v100_freq_values[0]); i++) {
+ diff_i = abs(snps_v100_freq_values[i].default_bit_rate -
+ ((csiphy_params->data_rate / num_lanes) / MBPS));
+ if (diff_i > diff) {
+ i--;
+ break;
+ }
+ diff = diff_i;
+ }
+
+ if (i == (sizeof(snps_v100_freq_values)/
+ sizeof(snps_v100_freq_values[0]))) {
+ if (((csiphy_params->data_rate / num_lanes) / MBPS) >
+ snps_v100_freq_values[--i].default_bit_rate) {
+ pr_err("unsupported data rate\n");
+ return -EINVAL;
+ }
+ }
+
+ if (mode == TWO_LANE_PHY_A) {
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_sys_ctrl.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_sys_ctrl.addr + offset);
+
+ msm_camera_io_w((snps_v100_freq_values[i].hs_freq &
+ mask_hs_freq_range),
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_ctrl_3.addr + offset);
+ } else {
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_sys_ctrl_1.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_sys_ctrl_1.addr);
+
+ msm_camera_io_w((snps_v100_freq_values[i].hs_freq &
+ mask_hs_freq_range),
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_ctrl_2.addr);
+ }
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_sys_7_00.addr + offset);
+ value |= SET_THE_BIT(5);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_sys_7_00.addr + offset);
+
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_sys_9_00.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_sys_9_00.addr + offset);
+
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_4_00.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_4_00.addr + offset);
+
+ msm_camera_io_w((snps_v100_freq_values[i].osc_freq &
+ mask_osc_freq_2),
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_2_00.addr + offset);
+
+ msm_camera_io_w((snps_v100_freq_values[i].osc_freq &
+ mask_osc_freq_3) >> 8,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_3_00.addr + offset);
+
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_5_00.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_5_00.addr + offset);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_cb_2_00.addr + offset);
+ value |= SET_THE_BIT(6);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_cb_2_00.addr + offset);
+
+ return 0;
+}
+
+static int msm_csiphy_snps_lane_config(
+ struct csiphy_device *csiphy_dev,
+ struct msm_camera_csiphy_params *csiphy_params)
+{
+ int ret;
+ uint16_t lane_mask = 0;
+ void __iomem *csiphybase;
+ enum snps_csiphy_mode mode = INVALID_MODE;
+ uint32_t value, num_tries, num_lanes, offset;
+
+ csiphybase = csiphy_dev->base;
+ /* lane mask usage
+ * BIT LANE
+ * 0(LSB) PHY A data 0
+ * 1 PHY A data 1
+ * 2 PHY B data 0
+ * 3 PHY B data 1
+ * 4 PHY A clk (clk 0)
+ * 5 PHY B clk (clk 1)
+ */
+
+ lane_mask = csiphy_params->lane_mask & 0x3f;
+ CDBG("%s:%d lane_maks: %d, cur_snps_state = %d\n",
+ __func__, __LINE__, lane_mask, csiphy_dev->snps_state);
+
+ if (lane_mask == LANE_MASK_AGGR_MODE) { /* Aggregate mdoe */
+ /* 4 lane config */
+ mode = AGGREGATE_MODE;
+ num_lanes = 4;
+ if (csiphy_dev->snps_state != NOT_CONFIGURED) {
+ pr_err("%s: invalid request\n", __func__);
+ return -EINVAL;
+ }
+ csiphy_dev->snps_state = CONFIGURED_AGGREGATE_MODE;
+ } else if (lane_mask == LANE_MASK_PHY_A) { /* PHY A */
+ /* 2 lane config */
+ num_lanes = 2;
+ if (csiphy_dev->snps_state != NOT_CONFIGURED) {
+ mode = TWO_LANE_PHY_A;
+ csiphy_dev->snps_state = CONFIGURED_TWO_LANE_PHY_A;
+ } else if (csiphy_dev->snps_state ==
+ CONFIGURED_TWO_LANE_PHY_B) {
+ /* 2 lane + 2 lane config */
+ mode = TWO_LANE_PHY_A;
+ csiphy_dev->snps_state = CONFIGURED_COMBO_MODE;
+ } else {
+ pr_err("%s: invalid request\n", __func__);
+ return -EINVAL;
+ }
+ } else if (lane_mask == LANE_MASK_PHY_B) { /* PHY B */
+ /* 2 lane config */
+ num_lanes = 2;
+ if (csiphy_dev->snps_state != NOT_CONFIGURED) {
+ mode = TWO_LANE_PHY_B;
+ csiphy_dev->snps_state = CONFIGURED_TWO_LANE_PHY_B;
+ } else if (csiphy_dev->snps_state ==
+ CONFIGURED_TWO_LANE_PHY_A) {
+ /* 2 lane + 2 lane config */
+ mode = TWO_LANE_PHY_B;
+ csiphy_dev->snps_state = CONFIGURED_COMBO_MODE;
+ } else {
+ pr_err("%s: invalid request\n", __func__);
+ return -EINVAL;
+ }
+ } else { /* None of available configurations */
+ pr_err("%s: invalid configuration requested\n", __func__);
+ return -EINVAL;
+ }
+
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A) {
+ ret = msm_csiphy_snps_2_lane_config(csiphy_dev,
+ csiphy_params, TWO_LANE_PHY_A, num_lanes);
+ if (ret < 0) {
+ pr_err("%s:%d: Error in setting lane configuration\n",
+ __func__, __LINE__);
+ return ret;
+ }
+ }
+
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_B) {
+ ret = msm_csiphy_snps_2_lane_config(csiphy_dev,
+ csiphy_params, TWO_LANE_PHY_B, num_lanes);
+ if (ret < 0) {
+ pr_err("%s:%d: Error in setting lane configuration\n",
+ __func__, __LINE__);
+ return ret;
+ }
+ }
+
+ snps_irq_config(csiphy_dev, csiphy_params);
+
+ value = 0x0;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A)
+ value |= mask_force_mode_A;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_B)
+ value |= mask_force_mode_B;
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_force_mode.addr);
+
+ if (mode == AGGREGATE_MODE) {
+ /* Programming PHY A as master and PHY B as slave */
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_dual_phy_0_00.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_dual_phy_0_00.addr);
+
+ msm_camera_io_w(!(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_dual_phy_0_00.data),
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_dual_phy_0_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_0_7_00.addr);
+ value |= SET_THE_BIT(5);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_0_7_00.addr);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_0_7_00.addr +
+ SNPS_INTERPHY_OFFSET);
+ value |= SET_THE_BIT(5);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_0_7_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_1_7_00.addr);
+ value |= SET_THE_BIT(5);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_1_7_00.addr);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_1_7_00.addr +
+ SNPS_INTERPHY_OFFSET);
+ value |= SET_THE_BIT(5);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_lane_1_7_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_7_00.data;
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_7_00.addr);
+ value |= SET_THE_BIT(3);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_7_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_0_00.addr +
+ SNPS_INTERPHY_OFFSET);
+ value |= SET_THE_BIT(0);
+ value |= SET_THE_BIT(1);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_0_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_1_00.addr +
+ SNPS_INTERPHY_OFFSET);
+ value &= ~(SET_THE_BIT(0));
+ value |= SET_THE_BIT(1);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_ovr_1_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_6_00.addr);
+ value |= SET_THE_BIT(2);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_6_00.addr);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_6_00.addr +
+ SNPS_INTERPHY_OFFSET);
+ value |= SET_THE_BIT(3);
+ value |= SET_THE_BIT(7);
+ value &= ~(SET_THE_BIT(2));
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_6_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_3_00.addr +
+ SNPS_INTERPHY_OFFSET);
+ value |= SET_THE_BIT(7);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_3_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_4_00.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_clk_lane_4_00.addr +
+ SNPS_INTERPHY_OFFSET);
+
+ value = csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_fifo_ctrl.data;
+ value &= ~(SET_THE_BIT(0));
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_fifo_ctrl.addr);
+ value |= SET_THE_BIT(0);
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_fifo_ctrl.addr);
+ }
+
+ value = 0x0;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A)
+ value |= mask_phy_enable_A;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_B)
+ value |= mask_phy_enable_B;
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_enable.addr);
+
+ value = 0x0;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A)
+ value |= mask_base_dir_A;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_B)
+ value |= mask_base_dir_B;
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_basedir.addr);
+
+ value = 0x0;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A)
+ value |= mask_enable_clk_A;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_B)
+ value |= mask_enable_clk_B;
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_enable_clk.addr);
+
+ value = 0x0;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A)
+ value |= mask_ctrl_1_A;
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_B)
+ value |= mask_ctrl_1_B;
+ msm_camera_io_w(value,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_ctrl_1.addr);
+
+ if (mode == AGGREGATE_MODE || mode == TWO_LANE_PHY_A)
+ offset = 0x0;
+ else
+ offset = SNPS_INTERPHY_OFFSET;
+
+ value = 0x0;
+ num_tries = 0;
+
+ do {
+ num_tries++;
+ value = msm_camera_io_r(csiphybase +
+ csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_rx_startup_obs_2_00.addr + offset);
+ if ((value | SET_THE_BIT(4)) == value)
+ break;
+ usleep_range(100, 150);
+ } while (num_tries < 6);
+
+ if ((value | SET_THE_BIT(4)) != value) {
+ pr_err("%s: SNPS phy config failed\n", __func__);
+ return -EINVAL;
+ }
+
+ msm_camera_io_w(csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_force_mode.data,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_snps_reg.
+ mipi_csiphy_force_mode.addr);
+
+ return 0;
}
static int msm_csiphy_3phase_lane_config(
@@ -782,14 +1233,26 @@
ratio = csiphy_dev->csiphy_max_clk/clk_rate;
csiphy_params->settle_cnt = csiphy_params->settle_cnt/ratio;
}
- CDBG("%s csiphy_params, mask = 0x%x cnt = %d\n",
+ CDBG("%s csiphy_params, mask = 0x%x cnt = %d, data rate = %lu\n",
__func__,
csiphy_params->lane_mask,
- csiphy_params->lane_cnt);
+ csiphy_params->lane_cnt, csiphy_params->data_rate);
CDBG("%s csiphy_params, settle cnt = 0x%x csid %d\n",
__func__, csiphy_params->settle_cnt,
csiphy_params->csid_core);
+ if (csiphy_dev->is_snps_phy) {
+ rc = msm_csiphy_snps_lane_config(csiphy_dev,
+ csiphy_params);
+ if (rc < 0) {
+ pr_err("%s:%d: Error in setting lane configuration\n",
+ __func__, __LINE__);
+ }
+ csiphy_dev->num_irq_registers = 4;
+ csiphy_dev->num_clk_irq_registers = 2;
+ return rc;
+ }
+
if (csiphy_dev->hw_version >= CSIPHY_VERSION_V30 &&
csiphy_dev->clk_mux_base != NULL &&
csiphy_dev->hw_version < CSIPHY_VERSION_V50) {
@@ -943,39 +1406,43 @@
void __iomem *csiphybase;
csiphybase = csiphy_dev->base;
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl11.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl12.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl13.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl14.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl15.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl16.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl17.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl18.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl19.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl20.addr);
- msm_camera_io_w(0,
- csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
- mipi_csiphy_3ph_cmn_ctrl21.addr);
+ if (csiphy_dev->is_snps_phy) {
+ snps_irq_config(csiphy_dev, false);
+ } else {
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl11.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl12.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl13.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl14.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl15.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl16.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl17.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl18.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl19.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl20.addr);
+ msm_camera_io_w(0,
+ csiphybase + csiphy_dev->ctrl_reg->csiphy_3ph_reg.
+ mipi_csiphy_3ph_cmn_ctrl21.addr);
+ }
}
static irqreturn_t msm_csiphy_irq(int irq_num, void *data)
@@ -1010,12 +1477,33 @@
csiphy_dev->ctrl_reg->csiphy_reg.
mipi_csiphy_interrupt_clear0_addr + 0x4*i);
}
+
+ if (csiphy_dev->is_snps_phy) {
+ for (i = 0; i < csiphy_dev->num_clk_irq_registers; i++) {
+ irq = msm_camera_io_r(
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_interrupt_clk_status0_addr + 0x4*i);
+ msm_camera_io_w(irq,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_interrupt_clk_clear0_addr + 0x4*i);
+ pr_err_ratelimited(
+ "%s CSIPHY%d_IRQ_CLK_STATUS_ADDR%d = 0x%x\n",
+ __func__, csiphy_dev->pdev->id, i, irq);
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_interrupt_clk_clear0_addr + 0x4*i);
+ }
+ }
msm_camera_io_w(0x1, csiphy_dev->base +
csiphy_dev->ctrl_reg->
csiphy_reg.mipi_csiphy_glbl_irq_cmd_addr);
msm_camera_io_w(0x0, csiphy_dev->base +
csiphy_dev->ctrl_reg->
csiphy_reg.mipi_csiphy_glbl_irq_cmd_addr);
+
return IRQ_HANDLED;
}
@@ -1039,6 +1527,23 @@
mipi_csiphy_3ph_cmn_ctrl0.addr);
}
+static void msm_csiphy_snps_reset(struct csiphy_device *csiphy_dev)
+{
+ //Need to toggle this register to enable IRQ
+ msm_camera_io_w(0x1, csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.mipi_csiphy_glbl_irq_cmd_addr);
+ usleep_range(5000, 8000);
+ msm_camera_io_w(0x0, csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.mipi_csiphy_glbl_irq_cmd_addr);
+}
+
+static void msm_csiphy_snps_release(struct csiphy_device *csiphy_dev)
+{
+ CDBG("Releasing SNPS phy\n");
+}
+
#if DBG_CSIPHY
static int msm_csiphy_init(struct csiphy_device *csiphy_dev)
{
@@ -1112,7 +1617,9 @@
if (rc < 0)
pr_err("%s: irq enable failed\n", __func__);
- if (csiphy_dev->csiphy_3phase == CSI_3PHASE_HW)
+ if (csiphy_dev->is_snps_phy)
+ msm_csiphy_snps_reset(csiphy_dev);
+ else if (csiphy_dev->csiphy_3phase == CSI_3PHASE_HW)
msm_csiphy_3ph_reset(csiphy_dev);
else
msm_csiphy_reset(csiphy_dev);
@@ -1130,6 +1637,7 @@
CDBG("%s:%d called csiphy_dev->hw_version 0x%x\n", __func__, __LINE__,
csiphy_dev->hw_version);
csiphy_dev->csiphy_state = CSIPHY_POWER_UP;
+ csiphy_dev->snps_state = NOT_CONFIGURED;
return 0;
csiphy_enable_clk_fail:
@@ -1214,7 +1722,9 @@
}
CDBG("%s:%d clk enable success\n", __func__, __LINE__);
- if (csiphy_dev->csiphy_3phase == CSI_3PHASE_HW)
+ if (csiphy_dev->is_snps_phy)
+ msm_csiphy_snps_reset(csiphy_dev);
+ else if (csiphy_dev->csiphy_3phase == CSI_3PHASE_HW)
msm_csiphy_3ph_reset(csiphy_dev);
else
msm_csiphy_reset(csiphy_dev);
@@ -1233,6 +1743,7 @@
CDBG("%s:%d called csiphy_dev->hw_version 0x%x\n", __func__, __LINE__,
csiphy_dev->hw_version);
csiphy_dev->csiphy_state = CSIPHY_POWER_UP;
+ csiphy_dev->snps_state = NOT_CONFIGURED;
return 0;
csiphy_enable_clk_fail:
@@ -1322,28 +1833,41 @@
csiphy_dev->lane_mask[csiphy_dev->pdev->id] &=
~(csi_lane_mask);
- i = 0;
- while (csi_lane_mask) {
- if (csi_lane_mask & 0x1) {
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnn_cfg2_addr + 0x40*i);
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnn_misc1_addr + 0x40*i);
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnn_test_imp + 0x40*i);
+ if (csiphy_dev->is_snps_phy) {
+ msm_csiphy_snps_release(csiphy_dev);
+ } else {
+ i = 0;
+ while (csi_lane_mask) {
+ if (csi_lane_mask & 0x1) {
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.
+ mipi_csiphy_lnn_cfg2_addr +
+ 0x40*i);
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.
+ mipi_csiphy_lnn_misc1_addr +
+ 0x40*i);
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.
+ mipi_csiphy_lnn_test_imp +
+ 0x40*i);
+ }
+ csi_lane_mask >>= 1;
+ i++;
}
- csi_lane_mask >>= 1;
- i++;
+ msm_camera_io_w(0x0, csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_lnck_cfg2_addr);
+ msm_camera_io_w(0x0, csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_glbl_pwr_cfg_addr);
}
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnck_cfg2_addr);
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_glbl_pwr_cfg_addr);
}
rc = msm_camera_enable_irq(csiphy_dev->irq, false);
@@ -1368,6 +1892,7 @@
NULL, 0, &csiphy_dev->csiphy_reg_ptr[0], 0);
csiphy_dev->csiphy_state = CSIPHY_POWER_DOWN;
+ csiphy_dev->snps_state = NOT_CONFIGURED;
if (cam_config_ahb_clk(NULL, 0, CAM_AHB_CLIENT_CSIPHY,
CAM_AHB_SUSPEND_VOTE) < 0)
@@ -1442,28 +1967,41 @@
csiphy_dev->lane_mask[csiphy_dev->pdev->id] &=
~(csi_lane_mask);
- i = 0;
- while (csi_lane_mask) {
- if (csi_lane_mask & 0x1) {
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnn_cfg2_addr + 0x40*i);
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnn_misc1_addr + 0x40*i);
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnn_test_imp + 0x40*i);
+ if (csiphy_dev->is_snps_phy) {
+ msm_csiphy_snps_release(csiphy_dev);
+ } else {
+ i = 0;
+ while (csi_lane_mask) {
+ if (csi_lane_mask & 0x1) {
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.
+ mipi_csiphy_lnn_cfg2_addr +
+ 0x40*i);
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.
+ mipi_csiphy_lnn_misc1_addr +
+ 0x40*i);
+ msm_camera_io_w(0x0,
+ csiphy_dev->base +
+ csiphy_dev->ctrl_reg->
+ csiphy_reg.
+ mipi_csiphy_lnn_test_imp +
+ 0x40*i);
+ }
+ csi_lane_mask >>= 1;
+ i++;
}
- csi_lane_mask >>= 1;
- i++;
+ msm_camera_io_w(0x0, csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_lnck_cfg2_addr);
+ msm_camera_io_w(0x0, csiphy_dev->base +
+ csiphy_dev->ctrl_reg->csiphy_reg.
+ mipi_csiphy_glbl_pwr_cfg_addr);
}
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_lnck_cfg2_addr);
- msm_camera_io_w(0x0, csiphy_dev->base +
- csiphy_dev->ctrl_reg->csiphy_reg.
- mipi_csiphy_glbl_pwr_cfg_addr);
}
if (csiphy_dev->csiphy_sof_debug == SOF_DEBUG_ENABLE)
rc = msm_camera_enable_irq(csiphy_dev->irq, false);
@@ -1486,6 +2024,7 @@
NULL, 0, &csiphy_dev->csiphy_reg_ptr[0], 0);
csiphy_dev->csiphy_state = CSIPHY_POWER_DOWN;
+ csiphy_dev->snps_state = NOT_CONFIGURED;
if (cam_config_ahb_clk(NULL, 0, CAM_AHB_CLIENT_CSIPHY,
CAM_AHB_SUSPEND_VOTE) < 0)
@@ -1803,6 +2342,12 @@
new_csiphy_dev->csiphy_3phase = CSI_3PHASE_HW;
new_csiphy_dev->ctrl_reg->csiphy_combo_mode_settings =
csiphy_combo_mode_v5_0_1;
+ } else if (of_device_is_compatible(new_csiphy_dev->pdev->dev.of_node,
+ "qcom,csiphy-v10.00")) {
+ new_csiphy_dev->ctrl_reg->csiphy_snps_reg = csiphy_v10_0_0_snps;
+ new_csiphy_dev->ctrl_reg->csiphy_reg = csiphy_v10_0_0;
+ new_csiphy_dev->hw_dts_version = CSIPHY_VERSION_V1000;
+ new_csiphy_dev->is_snps_phy = 1;
} else {
pr_err("%s:%d, invalid hw version : 0x%x\n", __func__, __LINE__,
new_csiphy_dev->hw_dts_version);
diff --git a/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.h b/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.h
index bc8f2d9..79baf3c 100644
--- a/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.h
+++ b/drivers/media/platform/msm/camera_v2/sensor/csiphy/msm_csiphy.h
@@ -64,6 +64,41 @@
uint32_t mipi_csiphy_t_wakeup_cfg0_addr;
uint32_t csiphy_version;
uint32_t combo_clk_mask;
+ uint32_t mipi_csiphy_interrupt_clk_status0_addr;
+ uint32_t mipi_csiphy_interrupt_clk_clear0_addr;
+};
+
+struct csiphy_reg_snps_parms_t {
+ /*MIPI CSI PHY registers*/
+ struct csiphy_reg_t mipi_csiphy_sys_ctrl;
+ struct csiphy_reg_t mipi_csiphy_sys_ctrl_1;
+ struct csiphy_reg_t mipi_csiphy_ctrl_1;
+ struct csiphy_reg_t mipi_csiphy_ctrl_2;
+ struct csiphy_reg_t mipi_csiphy_ctrl_3;
+ struct csiphy_reg_t mipi_csiphy_fifo_ctrl;
+ struct csiphy_reg_t mipi_csiphy_enable;
+ struct csiphy_reg_t mipi_csiphy_basedir;
+ struct csiphy_reg_t mipi_csiphy_force_mode;
+ struct csiphy_reg_t mipi_csiphy_enable_clk;
+ struct csiphy_reg_t mipi_csiphy_irq_mask_ctrl_lane_0;
+ struct csiphy_reg_t mipi_csiphy_irq_mask_ctrl_lane_clk_0;
+ struct csiphy_reg_t mipi_csiphy_rx_sys_7_00;
+ struct csiphy_reg_t mipi_csiphy_rx_sys_9_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_ovr_0_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_ovr_1_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_ovr_2_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_ovr_3_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_ovr_4_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_ovr_5_00;
+ struct csiphy_reg_t mipi_csiphy_rx_startup_obs_2_00;
+ struct csiphy_reg_t mipi_csiphy_rx_cb_2_00;
+ struct csiphy_reg_t mipi_csiphy_rx_dual_phy_0_00;
+ struct csiphy_reg_t mipi_csiphy_rx_clk_lane_3_00;
+ struct csiphy_reg_t mipi_csiphy_rx_clk_lane_4_00;
+ struct csiphy_reg_t mipi_csiphy_rx_clk_lane_6_00;
+ struct csiphy_reg_t mipi_csiphy_rx_lane_0_7_00;
+ struct csiphy_reg_t mipi_csiphy_rx_lane_1_7_00;
+ struct csiphy_reg_t mipi_csiphy_rx_clk_lane_7_00;
};
struct csiphy_reg_3ph_parms_t {
@@ -150,6 +185,7 @@
struct csiphy_reg_parms_t csiphy_reg;
struct csiphy_reg_3ph_parms_t csiphy_3ph_reg;
struct csiphy_settings_t csiphy_combo_mode_settings;
+ struct csiphy_reg_snps_parms_t csiphy_snps_reg;
};
enum msm_csiphy_state_t {
@@ -157,6 +193,27 @@
CSIPHY_POWER_DOWN,
};
+enum snps_csiphy_mode {
+ AGGREGATE_MODE,
+ TWO_LANE_PHY_A,
+ TWO_LANE_PHY_B,
+ INVALID_MODE,
+};
+
+enum snps_csiphy_state {
+ NOT_CONFIGURED,
+ CONFIGURED_AGGREGATE_MODE,
+ CONFIGURED_TWO_LANE_PHY_A,
+ CONFIGURED_TWO_LANE_PHY_B,
+ CONFIGURED_COMBO_MODE,
+};
+
+struct snps_freq_value {
+ uint32_t default_bit_rate;
+ uint8_t hs_freq;
+ uint16_t osc_freq;
+};
+
struct csiphy_device {
struct platform_device *pdev;
struct msm_sd_subdev msm_sd;
@@ -190,6 +247,9 @@
struct camera_vreg_t *csiphy_vreg;
struct regulator *csiphy_reg_ptr[MAX_REGULATOR];
int32_t regulator_count;
+ uint8_t is_snps_phy;
+ enum snps_csiphy_state snps_state;
+ uint8_t num_clk_irq_registers;
};
#define VIDIOC_MSM_CSIPHY_RELEASE \
diff --git a/drivers/misc/qseecom.c b/drivers/misc/qseecom.c
index 232b4ae..c0143db 100644
--- a/drivers/misc/qseecom.c
+++ b/drivers/misc/qseecom.c
@@ -4444,11 +4444,8 @@
data = kzalloc(sizeof(*data), GFP_KERNEL);
if (!data) {
- if (ret == 0) {
- kfree(*handle);
- *handle = NULL;
- }
- return -ENOMEM;
+ ret = -ENOMEM;
+ goto exit_handle_free;
}
data->abort = 0;
data->type = QSEECOM_CLIENT_APP;
@@ -4463,10 +4460,8 @@
ION_HEAP(ION_QSECOM_HEAP_ID), 0);
if (IS_ERR_OR_NULL(data->client.ihandle)) {
pr_err("Ion client could not retrieve the handle\n");
- kfree(data);
- kfree(*handle);
- *handle = NULL;
- return -EINVAL;
+ ret = -ENOMEM;
+ goto exit_data_free;
}
mutex_lock(&app_access_lock);
@@ -4474,7 +4469,7 @@
strlcpy(app_ireq.app_name, app_name, MAX_APP_NAME_SIZE);
ret = __qseecom_check_app_exists(app_ireq, &app_id);
if (ret)
- goto err;
+ goto exit_ion_free;
strlcpy(data->client.app_name, app_name, MAX_APP_NAME_SIZE);
if (app_id) {
@@ -4500,23 +4495,22 @@
qseecom.pdev->init_name);
ret = __qseecom_load_fw(data, app_name, &app_id);
if (ret < 0)
- goto err;
+ goto exit_ion_free;
}
data->client.app_id = app_id;
if (!found_app) {
entry = kmalloc(sizeof(*entry), GFP_KERNEL);
if (!entry) {
pr_err("kmalloc for app entry failed\n");
- ret = -ENOMEM;
- goto err;
+ ret = -ENOMEM;
+ goto exit_ion_free;
}
entry->app_id = app_id;
entry->ref_cnt = 1;
strlcpy(entry->app_name, app_name, MAX_APP_NAME_SIZE);
if (__qseecom_get_fw_size(app_name, &fw_size, &app_arch)) {
ret = -EIO;
- kfree(entry);
- goto err;
+ goto exit_entry_free;
}
entry->app_arch = app_arch;
entry->app_blocked = false;
@@ -4532,7 +4526,7 @@
if (ret) {
pr_err("Cannot get phys_addr for the Ion Client, ret = %d\n",
ret);
- goto err;
+ goto exit_entry_free;
}
/* Populate the structure for sending scm call to load image */
@@ -4541,7 +4535,7 @@
if (IS_ERR_OR_NULL(data->client.sb_virt)) {
pr_err("ION memory mapping for client shared buf failed\n");
ret = -ENOMEM;
- goto err;
+ goto exit_entry_free;
}
data->client.user_virt_sb_base = (uintptr_t)data->client.sb_virt;
data->client.sb_phys = (phys_addr_t)pa;
@@ -4552,7 +4546,7 @@
kclient_entry = kzalloc(sizeof(*kclient_entry), GFP_KERNEL);
if (!kclient_entry) {
ret = -ENOMEM;
- goto err;
+ goto exit_ion_unmap_kernel;
}
kclient_entry->handle = *handle;
@@ -4564,11 +4558,24 @@
mutex_unlock(&app_access_lock);
return 0;
-err:
- kfree(data);
- kfree(*handle);
- *handle = NULL;
+exit_ion_unmap_kernel:
+ if (!IS_ERR_OR_NULL(data->client.ihandle))
+ ion_unmap_kernel(qseecom.ion_clnt, data->client.ihandle);
+exit_entry_free:
+ kfree(entry);
+exit_ion_free:
mutex_unlock(&app_access_lock);
+ if (!IS_ERR_OR_NULL(data->client.ihandle)) {
+ ion_free(qseecom.ion_clnt, data->client.ihandle);
+ data->client.ihandle = NULL;
+ }
+exit_data_free:
+ kfree(data);
+exit_handle_free:
+ if (*handle) {
+ kfree(*handle);
+ *handle = NULL;
+ }
return ret;
}
EXPORT_SYMBOL(qseecom_start_app);
@@ -6959,6 +6966,31 @@
pr_err("failed qseecom_register_listener: %d\n", ret);
break;
}
+ case QSEECOM_IOCTL_SET_ICE_INFO: {
+ struct qseecom_ice_data_t ice_data;
+
+ ret = copy_from_user(&ice_data, argp, sizeof(ice_data));
+ if (ret) {
+ pr_err("copy_from_user failed\n");
+ return -EFAULT;
+ }
+ qcom_ice_set_fde_flag(ice_data.flag);
+ break;
+ }
+
+ case QSEECOM_IOCTL_SET_ENCDEC_INFO: {
+ struct qseecom_encdec_conf_t conf;
+
+ ret = copy_from_user(&conf, argp, sizeof(conf));
+ if (ret) {
+ pr_err("copy_from_user failed\n");
+ return -EFAULT;
+ }
+ ret = qcom_ice_set_fde_conf(conf.start_sector, conf.fs_size,
+ conf.index, conf.mode);
+ break;
+ }
+
case QSEECOM_IOCTL_UNREGISTER_LISTENER_REQ: {
if ((data->listener.id == 0) ||
(data->type != QSEECOM_LISTENER_SERVICE)) {
diff --git a/drivers/misc/uid_sys_stats.c b/drivers/misc/uid_sys_stats.c
index 42a513c..728c65a 100644
--- a/drivers/misc/uid_sys_stats.c
+++ b/drivers/misc/uid_sys_stats.c
@@ -345,13 +345,13 @@
uid_entry->active_utime = 0;
}
- read_lock(&tasklist_lock);
+ rcu_read_lock();
do_each_thread(temp, task) {
uid = from_kuid_munged(user_ns, task_uid(task));
if (!uid_entry || uid_entry->uid != uid)
uid_entry = find_or_register_uid(uid);
if (!uid_entry) {
- read_unlock(&tasklist_lock);
+ rcu_read_unlock();
rt_mutex_unlock(&uid_lock);
pr_err("%s: failed to find the uid_entry for uid %d\n",
__func__, uid);
@@ -361,7 +361,7 @@
uid_entry->active_utime += utime;
uid_entry->active_stime += stime;
} while_each_thread(temp, task);
- read_unlock(&tasklist_lock);
+ rcu_read_unlock();
hash_for_each(hash_table, bkt, uid_entry, hash) {
cputime_t total_utime = uid_entry->utime +
diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c
index e04e0f0..2405ae3 100644
--- a/drivers/mmc/card/block.c
+++ b/drivers/mmc/card/block.c
@@ -3196,11 +3196,11 @@
static void mmc_blk_cmdq_requeue_rw_rq(struct mmc_queue *mq,
struct request *req)
{
- struct mmc_card *card = mq->card;
- struct mmc_host *host = card->host;
+ struct request_queue *q = req->q;
- blk_requeue_request(req->q, req);
- mmc_put_card(host->card);
+ spin_lock_irq(q->queue_lock);
+ blk_requeue_request(q, req);
+ spin_unlock_irq(q->queue_lock);
}
static int mmc_blk_cmdq_issue_rw_rq(struct mmc_queue *mq, struct request *req)
@@ -4090,9 +4090,16 @@
* If issuing of the request fails with eitehr EBUSY or
* EAGAIN error, re-queue the request.
* This case would occur with ICE calls.
+ * For request which gets completed successfully or
+ * errored out, we release host lock in completion or
+ * error handling softirq context. But here the request
+ * is neither completed nor erred-out, so release the
+ * host lock explicitly.
*/
- if (ret == -EBUSY || ret == -EAGAIN)
+ if (ret == -EBUSY || ret == -EAGAIN) {
mmc_blk_cmdq_requeue_rw_rq(mq, req);
+ mmc_put_card(host->card);
+ }
}
}
diff --git a/drivers/mmc/core/core.c b/drivers/mmc/core/core.c
index da9cddb..1b961a9 100644
--- a/drivers/mmc/core/core.c
+++ b/drivers/mmc/core/core.c
@@ -470,7 +470,7 @@
mmc_host_clear_sdr104(host);
err = mmc_hw_reset(host);
host->card->sdr104_blocked = true;
- } else {
+ } else if (mmc_card_sd(host->card)) {
/* If sdr104_wa is not present, just return status */
err = host->bus_ops->alive(host);
}
@@ -1665,7 +1665,8 @@
mmc_card_removed(host->card)) {
if (cmd->error && !cmd->retries &&
cmd->opcode != MMC_SEND_STATUS &&
- cmd->opcode != MMC_SEND_TUNING_BLOCK)
+ cmd->opcode != MMC_SEND_TUNING_BLOCK &&
+ cmd->opcode != MMC_SEND_TUNING_BLOCK_HS200)
mmc_recovery_fallback_lower_speed(host);
break;
}
@@ -4591,7 +4592,9 @@
mmc_bus_put(host);
+ mmc_claim_host(host);
mmc_power_off(host);
+ mmc_release_host(host);
return ret;
}
@@ -4612,8 +4615,8 @@
return -EINVAL;
}
- mmc_power_up(host, host->card->ocr);
mmc_claim_host(host);
+ mmc_power_up(host, host->card->ocr);
ret = host->bus_ops->power_restore(host);
mmc_release_host(host);
diff --git a/drivers/mmc/host/sdhci-msm.c b/drivers/mmc/host/sdhci-msm.c
index 47094d5..d91eb67 100644
--- a/drivers/mmc/host/sdhci-msm.c
+++ b/drivers/mmc/host/sdhci-msm.c
@@ -175,6 +175,8 @@
#define MAX_DRV_TYPES_SUPPORTED_HS200 4
#define MSM_AUTOSUSPEND_DELAY_MS 100
+#define RCLK_TOGGLE 0x2
+
struct sdhci_msm_offset {
u32 CORE_MCI_DATA_CNT;
u32 CORE_MCI_STATUS;
@@ -3497,6 +3499,33 @@
| CORE_HC_SELECT_IN_EN), host->ioaddr +
msm_host_offset->CORE_VENDOR_SPEC);
}
+ /*
+ * After MCLK ugating, toggle the FIFO write clock to get
+ * the FIFO pointers and flags to valid state.
+ */
+ if (msm_host->tuning_done ||
+ (card && mmc_card_strobe(card) &&
+ msm_host->enhanced_strobe)) {
+ /*
+ * set HC_REG_DLL_CONFIG_3[1] to select MCLK as
+ * DLL input clock
+ */
+ writel_relaxed(((readl_relaxed(host->ioaddr +
+ msm_host_offset->CORE_DDR_CONFIG))
+ | RCLK_TOGGLE), host->ioaddr +
+ msm_host_offset->CORE_DDR_CONFIG);
+ /* ensure above write as toggling same bit quickly */
+ wmb();
+ udelay(2);
+ /*
+ * clear HC_REG_DLL_CONFIG_3[1] to select RCLK as
+ * DLL input clock
+ */
+ writel_relaxed(((readl_relaxed(host->ioaddr +
+ msm_host_offset->CORE_DDR_CONFIG))
+ & ~RCLK_TOGGLE), host->ioaddr +
+ msm_host_offset->CORE_DDR_CONFIG);
+ }
if (!host->mmc->ios.old_rate && !msm_host->use_cdclp533) {
/*
* Poll on DLL_LOCK and DDR_DLL_LOCK bits in
diff --git a/drivers/net/wireless/cnss2/debug.c b/drivers/net/wireless/cnss2/debug.c
index 5e2d44c..a3cf6c2 100644
--- a/drivers/net/wireless/cnss2/debug.c
+++ b/drivers/net/wireless/cnss2/debug.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2016-2018, 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
@@ -17,8 +17,6 @@
#include "debug.h"
#include "pci.h"
-#define CNSS_IPC_LOG_PAGES 32
-
void *cnss_ipc_log_context;
static int cnss_pin_connect_show(struct seq_file *s, void *data)
@@ -172,7 +170,7 @@
} else if (sysfs_streq(cmd, "shutdown")) {
ret = cnss_driver_event_post(plat_priv,
CNSS_DRIVER_EVENT_POWER_DOWN,
- CNSS_EVENT_SYNC, NULL);
+ 0, NULL);
clear_bit(CNSS_DRIVER_DEBUG, &plat_priv->driver_state);
} else {
cnss_pr_err("Device boot debugfs command is invalid\n");
diff --git a/drivers/net/wireless/cnss2/debug.h b/drivers/net/wireless/cnss2/debug.h
index decc84a..f31fdfe 100644
--- a/drivers/net/wireless/cnss2/debug.h
+++ b/drivers/net/wireless/cnss2/debug.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2016-2018, 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,6 +16,8 @@
#include <linux/ipc_logging.h>
#include <linux/printk.h>
+#define CNSS_IPC_LOG_PAGES 32
+
extern void *cnss_ipc_log_context;
#define cnss_ipc_log_string(_x...) do { \
diff --git a/drivers/net/wireless/cnss2/main.c b/drivers/net/wireless/cnss2/main.c
index bcea74a..9142758 100644
--- a/drivers/net/wireless/cnss2/main.c
+++ b/drivers/net/wireless/cnss2/main.c
@@ -571,7 +571,8 @@
goto out;
}
- if (test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state)) {
+ if (test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state) &&
+ test_bit(CNSS_DRIVER_PROBED, &plat_priv->driver_state)) {
ret = plat_priv->driver_ops->reinit(pci_priv->pci_dev,
pci_priv->pci_device_id);
if (ret) {
@@ -588,6 +589,7 @@
ret);
goto out;
}
+ clear_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state);
clear_bit(CNSS_DRIVER_LOADING, &plat_priv->driver_state);
set_bit(CNSS_DRIVER_PROBED, &plat_priv->driver_state);
}
@@ -614,7 +616,8 @@
return -EINVAL;
}
- if (test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state)) {
+ if (test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state) &&
+ test_bit(CNSS_DRIVER_PROBED, &plat_priv->driver_state)) {
plat_priv->driver_ops->shutdown(pci_priv->pci_dev);
} else if (test_bit(CNSS_DRIVER_UNLOADING, &plat_priv->driver_state)) {
plat_priv->driver_ops->remove(pci_priv->pci_dev);
@@ -652,7 +655,9 @@
complete(&plat_priv->power_up_complete);
}
- if (ret)
+ if (ret && test_bit(CNSS_DEV_ERR_NOTIFY, &plat_priv->driver_state))
+ goto out;
+ else if (ret)
goto shutdown;
return 0;
@@ -662,6 +667,10 @@
cnss_suspend_pci_link(plat_priv->bus_priv);
cnss_power_off_device(plat_priv);
+ clear_bit(CNSS_FW_READY, &plat_priv->driver_state);
+ clear_bit(CNSS_FW_MEM_READY, &plat_priv->driver_state);
+
+out:
return ret;
}
@@ -940,7 +949,7 @@
of_property_read_bool(dev->of_node,
"qcom,notify-modem-status");
- if (esoc_info->notify_modem_status)
+ if (!esoc_info->notify_modem_status)
goto out;
ret = of_property_read_string_index(dev->of_node, "esoc-names", 0,
@@ -1172,23 +1181,16 @@
static void cnss_qca6290_crash_shutdown(struct cnss_plat_data *plat_priv)
{
struct cnss_pci_data *pci_priv = plat_priv->bus_priv;
- int ret = 0;
cnss_pr_dbg("Crash shutdown with driver_state 0x%lx\n",
plat_priv->driver_state);
- if (test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state) ||
- test_bit(CNSS_DRIVER_LOADING, &plat_priv->driver_state) ||
- test_bit(CNSS_DRIVER_UNLOADING, &plat_priv->driver_state))
- return;
-
- ret = cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_RDDM_KERNEL_PANIC);
- if (ret) {
- cnss_pr_err("Fail to complete RDDM, err = %d\n", ret);
+ if (test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state)) {
+ cnss_pr_dbg("Ignore crash shutdown\n");
return;
}
- cnss_pci_collect_dump_info(pci_priv);
+ cnss_pci_collect_dump_info(pci_priv, true);
}
static int cnss_powerup(struct cnss_plat_data *plat_priv)
@@ -1443,7 +1445,6 @@
struct cnss_pci_data *pci_priv = plat_priv->bus_priv;
struct cnss_subsys_info *subsys_info =
&plat_priv->subsys_info;
- int ret = 0;
plat_priv->recovery_count++;
@@ -1467,12 +1468,7 @@
break;
case CNSS_REASON_RDDM:
clear_bit(CNSS_DEV_ERR_NOTIFY, &plat_priv->driver_state);
- ret = cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_RDDM);
- if (ret) {
- cnss_pr_err("Failed to complete RDDM, err = %d\n", ret);
- break;
- }
- cnss_pci_collect_dump_info(pci_priv);
+ cnss_pci_collect_dump_info(pci_priv, false);
break;
case CNSS_REASON_DEFAULT:
case CNSS_REASON_TIMEOUT:
@@ -1538,11 +1534,6 @@
if (!test_bit(CNSS_FW_READY, &plat_priv->driver_state)) {
set_bit(CNSS_FW_BOOT_RECOVERY,
&plat_priv->driver_state);
- } else if (test_bit(CNSS_DRIVER_LOADING,
- &plat_priv->driver_state)) {
- cnss_pr_err("Driver probe is in progress, ignore recovery\n");
- ret = -EINVAL;
- goto out;
}
break;
}
diff --git a/drivers/net/wireless/cnss2/main.h b/drivers/net/wireless/cnss2/main.h
index 81b5de8..c11b206 100644
--- a/drivers/net/wireless/cnss2/main.h
+++ b/drivers/net/wireless/cnss2/main.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2016-2018, 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
@@ -109,6 +109,12 @@
bool valid;
};
+enum cnss_fw_dump_type {
+ CNSS_FW_IMAGE,
+ CNSS_FW_RDDM,
+ CNSS_FW_REMOTE_HEAP,
+};
+
enum cnss_driver_event_type {
CNSS_DRIVER_EVENT_SERVER_ARRIVE,
CNSS_DRIVER_EVENT_SERVER_EXIT,
diff --git a/drivers/net/wireless/cnss2/pci.c b/drivers/net/wireless/cnss2/pci.c
index 795b905..098631e 100644
--- a/drivers/net/wireless/cnss2/pci.c
+++ b/drivers/net/wireless/cnss2/pci.c
@@ -16,6 +16,7 @@
#include <linux/msi.h>
#include <linux/of.h>
#include <linux/pm_runtime.h>
+#include <linux/memblock.h>
#include "main.h"
#include "debug.h"
@@ -33,13 +34,11 @@
#define PCI_BAR_NUM 0
-#ifdef CONFIG_ARM_LPAE
-#define PCI_DMA_MASK 64
-#else
-#define PCI_DMA_MASK 32
-#endif
+#define PCI_DMA_MASK_32_BIT 32
+#define PCI_DMA_MASK_64_BIT 64
#define MHI_NODE_NAME "qcom,mhi"
+#define MHI_MSI_NAME "MHI"
#define MAX_M3_FILE_NAME_LENGTH 13
#define DEFAULT_M3_FILE_NAME "m3.bin"
@@ -164,6 +163,14 @@
pci_priv->pci_link_state = PCI_LINK_UP;
+ if (pci_priv->pci_dev->device != QCA6174_DEVICE_ID) {
+ ret = pci_set_power_state(pci_priv->pci_dev, PCI_D0);
+ if (ret) {
+ cnss_pr_err("Failed to set D0, err = %d\n", ret);
+ goto out;
+ }
+ }
+
ret = cnss_set_pci_config_space(pci_priv, RESTORE_PCI_CONFIG_SPACE);
if (ret)
goto out;
@@ -209,7 +216,6 @@
cnss_pr_err("PCI link down is detected by host driver, schedule recovery!\n");
- cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_NOTIFY_LINK_ERROR);
cnss_schedule_recovery(dev, CNSS_REASON_LINK_DOWN);
return 0;
@@ -324,7 +330,6 @@
spin_unlock_irqrestore(&pci_link_down_lock, flags);
cnss_pr_err("PCI link down, schedule recovery!\n");
- cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_NOTIFY_LINK_ERROR);
if (pci_dev->device == QCA6174_DEVICE_ID)
disable_irq(pci_dev->irq);
cnss_schedule_recovery(&pci_dev->dev, CNSS_REASON_LINK_DOWN);
@@ -830,8 +835,8 @@
.total_vectors = 32,
.total_users = 4,
.users = (struct cnss_msi_user[]) {
- { .name = "MHI", .num_vectors = 2, .base_vector = 0 },
- { .name = "CE", .num_vectors = 11, .base_vector = 2 },
+ { .name = "MHI", .num_vectors = 3, .base_vector = 0 },
+ { .name = "CE", .num_vectors = 10, .base_vector = 3 },
{ .name = "WAKE", .num_vectors = 1, .base_vector = 13 },
{ .name = "DP", .num_vectors = 18, .base_vector = 14 },
},
@@ -975,6 +980,7 @@
int ret = 0;
struct pci_dev *pci_dev = pci_priv->pci_dev;
u16 device_id;
+ u32 pci_dma_mask = PCI_DMA_MASK_64_BIT;
pci_read_config_word(pci_dev, PCI_DEVICE_ID, &device_id);
if (device_id != pci_priv->pci_device_id->device) {
@@ -1002,17 +1008,20 @@
goto disable_device;
}
- ret = pci_set_dma_mask(pci_dev, DMA_BIT_MASK(PCI_DMA_MASK));
+ if (device_id == QCA6174_DEVICE_ID)
+ pci_dma_mask = PCI_DMA_MASK_32_BIT;
+
+ ret = pci_set_dma_mask(pci_dev, DMA_BIT_MASK(pci_dma_mask));
if (ret) {
cnss_pr_err("Failed to set PCI DMA mask (%d), err = %d\n",
- ret, PCI_DMA_MASK);
+ ret, pci_dma_mask);
goto release_region;
}
- ret = pci_set_consistent_dma_mask(pci_dev, DMA_BIT_MASK(PCI_DMA_MASK));
+ ret = pci_set_consistent_dma_mask(pci_dev, DMA_BIT_MASK(pci_dma_mask));
if (ret) {
cnss_pr_err("Failed to set PCI consistent DMA mask (%d), err = %d\n",
- ret, PCI_DMA_MASK);
+ ret, pci_dma_mask);
goto release_region;
}
@@ -1047,17 +1056,23 @@
pci_clear_master(pci_dev);
pci_release_region(pci_dev, PCI_BAR_NUM);
- pci_disable_device(pci_dev);
+ if (pci_is_enabled(pci_dev))
+ pci_disable_device(pci_dev);
}
-static int cnss_mhi_pm_runtime_get(struct pci_dev *pci_dev)
+static int cnss_mhi_pm_runtime_get(struct mhi_controller *mhi_ctrl, void *priv)
{
- return pm_runtime_get(&pci_dev->dev);
+ struct cnss_pci_data *pci_priv = priv;
+
+ return pm_runtime_get(&pci_priv->pci_dev->dev);
}
-static void cnss_mhi_pm_runtime_put_noidle(struct pci_dev *pci_dev)
+static void cnss_mhi_pm_runtime_put_noidle(struct mhi_controller *mhi_ctrl,
+ void *priv)
{
- pm_runtime_put_noidle(&pci_dev->dev);
+ struct cnss_pci_data *pci_priv = priv;
+
+ pm_runtime_put_noidle(&pci_priv->pci_dev->dev);
}
static char *cnss_mhi_state_to_str(enum cnss_mhi_state mhi_state)
@@ -1071,76 +1086,85 @@
return "POWER_ON";
case CNSS_MHI_POWER_OFF:
return "POWER_OFF";
+ case CNSS_MHI_FORCE_POWER_OFF:
+ return "FORCE_POWER_OFF";
case CNSS_MHI_SUSPEND:
return "SUSPEND";
case CNSS_MHI_RESUME:
return "RESUME";
case CNSS_MHI_TRIGGER_RDDM:
return "TRIGGER_RDDM";
- case CNSS_MHI_RDDM:
- return "RDDM";
- case CNSS_MHI_RDDM_KERNEL_PANIC:
- return "RDDM_KERNEL_PANIC";
- case CNSS_MHI_NOTIFY_LINK_ERROR:
- return "NOTIFY_LINK_ERROR";
default:
return "UNKNOWN";
}
};
-static void *cnss_pci_collect_dump_seg(struct cnss_pci_data *pci_priv,
- enum mhi_rddm_segment type,
- void *start_addr)
+void cnss_pci_collect_dump_info(struct cnss_pci_data *pci_priv, bool in_panic)
{
- int count;
- struct scatterlist *sg_list, *s;
- unsigned int i;
struct cnss_plat_data *plat_priv = pci_priv->plat_priv;
struct cnss_dump_data *dump_data =
&plat_priv->ramdump_info_v2.dump_data;
- struct cnss_dump_seg *dump_seg = start_addr;
+ struct cnss_dump_seg *dump_seg =
+ plat_priv->ramdump_info_v2.dump_data_vaddr;
+ struct image_info *fw_image, *rddm_image;
+ struct cnss_fw_mem *fw_mem = &plat_priv->fw_mem;
+ int ret, i;
- count = mhi_xfer_rddm(&pci_priv->mhi_dev, type, &sg_list);
- if (count <= 0 || !sg_list) {
- cnss_pr_err("Invalid dump_seg for type %u, count %u, sg_list %pK\n",
- type, count, sg_list);
- return start_addr;
+ ret = mhi_download_rddm_img(pci_priv->mhi_ctrl, in_panic);
+ if (ret) {
+ cnss_pr_err("Failed to download RDDM image, err = %d\n", ret);
+ return;
}
- cnss_pr_dbg("Collect dump seg: type %u, nentries %d\n", type, count);
+ fw_image = pci_priv->mhi_ctrl->fbc_image;
+ rddm_image = pci_priv->mhi_ctrl->rddm_image;
+ dump_data->nentries = 0;
- for_each_sg(sg_list, s, count, i) {
- dump_seg->address = sg_dma_address(s);
- dump_seg->v_address = sg_virt(s);
- dump_seg->size = s->length;
- dump_seg->type = type;
+ cnss_pr_dbg("Collect FW image dump segment, nentries %d\n",
+ fw_image->entries);
+
+ for (i = 0; i < fw_image->entries; i++) {
+ dump_seg->address = fw_image->mhi_buf[i].dma_addr;
+ dump_seg->v_address = fw_image->mhi_buf[i].buf;
+ dump_seg->size = fw_image->mhi_buf[i].len;
+ dump_seg->type = CNSS_FW_IMAGE;
cnss_pr_dbg("seg-%d: address 0x%lx, v_address %pK, size 0x%lx\n",
i, dump_seg->address,
dump_seg->v_address, dump_seg->size);
dump_seg++;
}
- dump_data->nentries += count;
+ dump_data->nentries += fw_image->entries;
- return dump_seg;
-}
+ cnss_pr_dbg("Collect RDDM image dump segment, nentries %d\n",
+ rddm_image->entries);
-void cnss_pci_collect_dump_info(struct cnss_pci_data *pci_priv)
-{
- struct cnss_plat_data *plat_priv = pci_priv->plat_priv;
- struct cnss_dump_data *dump_data =
- &plat_priv->ramdump_info_v2.dump_data;
- void *start_addr, *end_addr;
+ for (i = 0; i < rddm_image->entries; i++) {
+ dump_seg->address = rddm_image->mhi_buf[i].dma_addr;
+ dump_seg->v_address = rddm_image->mhi_buf[i].buf;
+ dump_seg->size = rddm_image->mhi_buf[i].len;
+ dump_seg->type = CNSS_FW_RDDM;
+ cnss_pr_dbg("seg-%d: address 0x%lx, v_address %pK, size 0x%lx\n",
+ i, dump_seg->address,
+ dump_seg->v_address, dump_seg->size);
+ dump_seg++;
+ }
- dump_data->nentries = 0;
+ dump_data->nentries += rddm_image->entries;
- start_addr = plat_priv->ramdump_info_v2.dump_data_vaddr;
- end_addr = cnss_pci_collect_dump_seg(pci_priv,
- MHI_RDDM_FW_SEGMENT, start_addr);
+ if (fw_mem->pa && fw_mem->va && fw_mem->size) {
+ cnss_pr_dbg("Collect remote heap dump segment, nentries 1\n");
- start_addr = end_addr;
- end_addr = cnss_pci_collect_dump_seg(pci_priv,
- MHI_RDDM_RD_SEGMENT, start_addr);
+ dump_seg->address = fw_mem->pa;
+ dump_seg->v_address = fw_mem->va;
+ dump_seg->size = fw_mem->size;
+ dump_seg->type = CNSS_FW_REMOTE_HEAP;
+ cnss_pr_dbg("seg-0: address 0x%lx, v_address %pK, size 0x%lx\n",
+ dump_seg->address, dump_seg->v_address,
+ dump_seg->size);
+ dump_seg++;
+ dump_data->nentries++;
+ }
if (dump_data->nentries > 0)
plat_priv->ramdump_info_v2.dump_data_valid = true;
@@ -1154,65 +1178,148 @@
plat_priv->ramdump_info_v2.dump_data_valid = false;
}
-static void cnss_mhi_notify_status(enum MHI_CB_REASON reason, void *priv)
+static int cnss_mhi_link_status(struct mhi_controller *mhi_ctrl, void *priv)
{
struct cnss_pci_data *pci_priv = priv;
- struct cnss_plat_data *plat_priv = pci_priv->plat_priv;
- enum cnss_recovery_reason cnss_reason = CNSS_REASON_RDDM;
+ u16 device_id;
- if (!pci_priv)
+ if (!pci_priv) {
+ cnss_pr_err("pci_priv is NULL\n");
+ return -EINVAL;
+ }
+
+ pci_read_config_word(pci_priv->pci_dev, PCI_DEVICE_ID, &device_id);
+ if (device_id != pci_priv->device_id) {
+ cnss_pr_err("PCI device ID mismatch, link possibly down, current read ID: 0x%x, record ID: 0x%x\n",
+ device_id, pci_priv->device_id);
+ return -EIO;
+ }
+
+ return 0;
+}
+
+static void cnss_mhi_notify_status(struct mhi_controller *mhi_ctrl, void *priv,
+ enum MHI_CB reason)
+{
+ struct cnss_pci_data *pci_priv = priv;
+ struct cnss_plat_data *plat_priv;
+ enum cnss_recovery_reason cnss_reason;
+
+ if (!pci_priv) {
+ cnss_pr_err("pci_priv is NULL");
return;
+ }
+
+ plat_priv = pci_priv->plat_priv;
cnss_pr_dbg("MHI status cb is called with reason %d\n", reason);
+ if (plat_priv->driver_ops && plat_priv->driver_ops->update_status)
+ plat_priv->driver_ops->update_status(pci_priv->pci_dev,
+ CNSS_FW_DOWN);
+
+ switch (reason) {
+ case MHI_CB_EE_RDDM:
+ cnss_reason = CNSS_REASON_RDDM;
+ break;
+ default:
+ cnss_pr_err("Unsupported MHI status cb reason: %d\n", reason);
+ return;
+ }
+
set_bit(CNSS_DEV_ERR_NOTIFY, &plat_priv->driver_state);
del_timer(&plat_priv->fw_boot_timer);
- if (reason == MHI_CB_SYS_ERROR)
- cnss_reason = CNSS_REASON_TIMEOUT;
-
cnss_schedule_recovery(&pci_priv->pci_dev->dev,
cnss_reason);
}
+static int cnss_pci_get_mhi_msi(struct cnss_pci_data *pci_priv)
+{
+ int ret, num_vectors, i;
+ u32 user_base_data, base_vector;
+ int *irq;
+
+ ret = cnss_get_user_msi_assignment(&pci_priv->pci_dev->dev,
+ MHI_MSI_NAME, &num_vectors,
+ &user_base_data, &base_vector);
+ if (ret)
+ return ret;
+
+ cnss_pr_dbg("Number of assigned MSI for MHI is %d, base vector is %d\n",
+ num_vectors, base_vector);
+
+ irq = kcalloc(num_vectors, sizeof(int), GFP_KERNEL);
+ if (!irq)
+ return -ENOMEM;
+
+ for (i = 0; i < num_vectors; i++)
+ irq[i] = cnss_get_msi_irq(&pci_priv->pci_dev->dev,
+ base_vector + i);
+
+ pci_priv->mhi_ctrl->irq = irq;
+ pci_priv->mhi_ctrl->msi_allocated = num_vectors;
+
+ return 0;
+}
+
static int cnss_pci_register_mhi(struct cnss_pci_data *pci_priv)
{
int ret = 0;
+ struct cnss_plat_data *plat_priv = pci_priv->plat_priv;
struct pci_dev *pci_dev = pci_priv->pci_dev;
- struct mhi_device *mhi_dev = &pci_priv->mhi_dev;
+ struct mhi_controller *mhi_ctrl;
- mhi_dev->dev = &pci_priv->plat_priv->plat_dev->dev;
- mhi_dev->pci_dev = pci_dev;
-
- mhi_dev->resources[0].start = (resource_size_t)pci_priv->bar;
- mhi_dev->resources[0].end = (resource_size_t)pci_priv->bar +
- pci_resource_len(pci_dev, PCI_BAR_NUM);
- mhi_dev->resources[0].flags =
- pci_resource_flags(pci_dev, PCI_BAR_NUM);
- mhi_dev->resources[0].name = "BAR";
- cnss_pr_dbg("BAR start is %pa, BAR end is %pa\n",
- &mhi_dev->resources[0].start, &mhi_dev->resources[0].end);
-
- if (!mhi_dev->resources[1].start) {
- mhi_dev->resources[1].start = pci_dev->irq;
- mhi_dev->resources[1].end = pci_dev->irq + 1;
- mhi_dev->resources[1].flags = IORESOURCE_IRQ;
- mhi_dev->resources[1].name = "IRQ";
+ mhi_ctrl = mhi_alloc_controller(0);
+ if (!mhi_ctrl) {
+ cnss_pr_err("Invalid MHI controller context\n");
+ return -EINVAL;
}
- cnss_pr_dbg("IRQ start is %pa, IRQ end is %pa\n",
- &mhi_dev->resources[1].start, &mhi_dev->resources[1].end);
- mhi_dev->pm_runtime_get = cnss_mhi_pm_runtime_get;
- mhi_dev->pm_runtime_put_noidle = cnss_mhi_pm_runtime_put_noidle;
+ pci_priv->mhi_ctrl = mhi_ctrl;
- mhi_dev->support_rddm = true;
- mhi_dev->rddm_size = pci_priv->plat_priv->ramdump_info_v2.ramdump_size;
- mhi_dev->status_cb = cnss_mhi_notify_status;
+ mhi_ctrl->priv_data = pci_priv;
+ mhi_ctrl->dev = &pci_dev->dev;
+ mhi_ctrl->of_node = (&plat_priv->plat_dev->dev)->of_node;
+ mhi_ctrl->dev_id = pci_priv->device_id;
+ mhi_ctrl->domain = pci_domain_nr(pci_dev->bus);
+ mhi_ctrl->bus = pci_dev->bus->number;
+ mhi_ctrl->slot = PCI_SLOT(pci_dev->devfn);
- ret = mhi_register_device(mhi_dev, MHI_NODE_NAME, pci_priv);
+ mhi_ctrl->regs = pci_priv->bar;
+ cnss_pr_dbg("BAR starts at %pa\n",
+ &pci_resource_start(pci_priv->pci_dev, PCI_BAR_NUM));
+
+ ret = cnss_pci_get_mhi_msi(pci_priv);
if (ret) {
- cnss_pr_err("Failed to register as MHI device, err = %d\n",
- ret);
+ cnss_pr_err("Failed to get MSI for MHI\n");
+ return ret;
+ }
+
+ if (pci_priv->smmu_s1_enable) {
+ mhi_ctrl->iova_start = pci_priv->smmu_iova_start;
+ mhi_ctrl->iova_stop = pci_priv->smmu_iova_start +
+ pci_priv->smmu_iova_len;
+ } else {
+ mhi_ctrl->iova_start = memblock_start_of_DRAM();
+ mhi_ctrl->iova_stop = memblock_end_of_DRAM();
+ }
+
+ mhi_ctrl->link_status = cnss_mhi_link_status;
+ mhi_ctrl->status_cb = cnss_mhi_notify_status;
+ mhi_ctrl->runtime_get = cnss_mhi_pm_runtime_get;
+ mhi_ctrl->runtime_put = cnss_mhi_pm_runtime_put_noidle;
+
+ mhi_ctrl->rddm_size = pci_priv->plat_priv->ramdump_info_v2.ramdump_size;
+
+ mhi_ctrl->log_buf = ipc_log_context_create(CNSS_IPC_LOG_PAGES,
+ "cnss-mhi", 0);
+ if (!mhi_ctrl->log_buf)
+ cnss_pr_err("Unable to create CNSS MHI IPC log context\n");
+
+ ret = of_register_mhi_controller(mhi_ctrl);
+ if (ret) {
+ cnss_pr_err("Failed to register to MHI bus, err = %d\n", ret);
return ret;
}
@@ -1221,35 +1328,11 @@
static void cnss_pci_unregister_mhi(struct cnss_pci_data *pci_priv)
{
-}
+ struct mhi_controller *mhi_ctrl = pci_priv->mhi_ctrl;
-static enum mhi_dev_ctrl cnss_to_mhi_dev_state(enum cnss_mhi_state state)
-{
- switch (state) {
- case CNSS_MHI_INIT:
- return MHI_DEV_CTRL_INIT;
- case CNSS_MHI_DEINIT:
- return MHI_DEV_CTRL_DE_INIT;
- case CNSS_MHI_POWER_ON:
- return MHI_DEV_CTRL_POWER_ON;
- case CNSS_MHI_POWER_OFF:
- return MHI_DEV_CTRL_POWER_OFF;
- case CNSS_MHI_SUSPEND:
- return MHI_DEV_CTRL_SUSPEND;
- case CNSS_MHI_RESUME:
- return MHI_DEV_CTRL_RESUME;
- case CNSS_MHI_TRIGGER_RDDM:
- return MHI_DEV_CTRL_TRIGGER_RDDM;
- case CNSS_MHI_RDDM:
- return MHI_DEV_CTRL_RDDM;
- case CNSS_MHI_RDDM_KERNEL_PANIC:
- return MHI_DEV_CTRL_RDDM_KERNEL_PANIC;
- case CNSS_MHI_NOTIFY_LINK_ERROR:
- return MHI_DEV_CTRL_NOTIFY_LINK_ERROR;
- default:
- cnss_pr_err("Unknown CNSS MHI state (%d)\n", state);
- return -EINVAL;
- }
+ mhi_unregister_mhi_controller(mhi_ctrl);
+ ipc_log_context_destroy(mhi_ctrl->log_buf);
+ kfree(mhi_ctrl->irq);
}
static int cnss_pci_check_mhi_state_bit(struct cnss_pci_data *pci_priv,
@@ -1266,6 +1349,10 @@
!test_bit(CNSS_MHI_POWER_ON, &pci_priv->mhi_state))
return 0;
break;
+ case CNSS_MHI_FORCE_POWER_OFF:
+ if (test_bit(CNSS_MHI_POWER_ON, &pci_priv->mhi_state))
+ return 0;
+ break;
case CNSS_MHI_POWER_OFF:
case CNSS_MHI_SUSPEND:
if (test_bit(CNSS_MHI_POWER_ON, &pci_priv->mhi_state) &&
@@ -1277,9 +1364,6 @@
return 0;
break;
case CNSS_MHI_TRIGGER_RDDM:
- case CNSS_MHI_RDDM:
- case CNSS_MHI_RDDM_KERNEL_PANIC:
- case CNSS_MHI_NOTIFY_LINK_ERROR:
return 0;
default:
cnss_pr_err("Unhandled MHI state: %s(%d)\n",
@@ -1307,6 +1391,7 @@
set_bit(CNSS_MHI_POWER_ON, &pci_priv->mhi_state);
break;
case CNSS_MHI_POWER_OFF:
+ case CNSS_MHI_FORCE_POWER_OFF:
clear_bit(CNSS_MHI_POWER_ON, &pci_priv->mhi_state);
break;
case CNSS_MHI_SUSPEND:
@@ -1316,9 +1401,6 @@
clear_bit(CNSS_MHI_SUSPEND, &pci_priv->mhi_state);
break;
case CNSS_MHI_TRIGGER_RDDM:
- case CNSS_MHI_RDDM:
- case CNSS_MHI_RDDM_KERNEL_PANIC:
- case CNSS_MHI_NOTIFY_LINK_ERROR:
break;
default:
cnss_pr_err("Unhandled MHI state (%d)\n", mhi_state);
@@ -1329,7 +1411,6 @@
enum cnss_mhi_state mhi_state)
{
int ret = 0;
- enum mhi_dev_ctrl mhi_dev_state = cnss_to_mhi_dev_state(mhi_state);
if (!pci_priv) {
cnss_pr_err("pci_priv is NULL!\n");
@@ -1339,8 +1420,8 @@
if (pci_priv->device_id == QCA6174_DEVICE_ID)
return 0;
- if (mhi_dev_state < 0) {
- cnss_pr_err("Invalid MHI DEV state (%d)\n", mhi_dev_state);
+ if (mhi_state < 0) {
+ cnss_pr_err("Invalid MHI state (%d)\n", mhi_state);
return -EINVAL;
}
@@ -1350,16 +1431,51 @@
cnss_pr_dbg("Setting MHI state: %s(%d)\n",
cnss_mhi_state_to_str(mhi_state), mhi_state);
- ret = mhi_pm_control_device(&pci_priv->mhi_dev, mhi_dev_state);
- if (ret) {
- cnss_pr_err("Failed to set MHI state: %s(%d)\n",
+
+ switch (mhi_state) {
+ case CNSS_MHI_INIT:
+ ret = mhi_prepare_for_power_up(pci_priv->mhi_ctrl);
+ break;
+ case CNSS_MHI_DEINIT:
+ mhi_unprepare_after_power_down(pci_priv->mhi_ctrl);
+ ret = 0;
+ break;
+ case CNSS_MHI_POWER_ON:
+ ret = mhi_sync_power_up(pci_priv->mhi_ctrl);
+ break;
+ case CNSS_MHI_POWER_OFF:
+ mhi_power_down(pci_priv->mhi_ctrl, true);
+ ret = 0;
+ break;
+ case CNSS_MHI_FORCE_POWER_OFF:
+ mhi_power_down(pci_priv->mhi_ctrl, false);
+ ret = 0;
+ break;
+ case CNSS_MHI_SUSPEND:
+ ret = mhi_pm_suspend(pci_priv->mhi_ctrl);
+ break;
+ case CNSS_MHI_RESUME:
+ ret = mhi_pm_resume(pci_priv->mhi_ctrl);
+ break;
+ case CNSS_MHI_TRIGGER_RDDM:
+ cnss_pr_dbg("Bypass MHI state: %s(%d)\n",
cnss_mhi_state_to_str(mhi_state), mhi_state);
- goto out;
+ break;
+ default:
+ cnss_pr_err("Unhandled MHI state (%d)\n", mhi_state);
+ ret = -EINVAL;
}
+ if (ret)
+ goto out;
+
cnss_pci_set_mhi_state_bit(pci_priv, mhi_state);
+ return 0;
+
out:
+ cnss_pr_err("Failed to set MHI state: %s(%d)\n",
+ cnss_mhi_state_to_str(mhi_state), mhi_state);
return ret;
}
@@ -1404,7 +1520,10 @@
plat_priv = pci_priv->plat_priv;
cnss_pci_set_mhi_state_bit(pci_priv, CNSS_MHI_RESUME);
- cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_POWER_OFF);
+ if (!pci_priv->pci_link_down_ind)
+ cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_POWER_OFF);
+ else
+ cnss_pci_set_mhi_state(pci_priv, CNSS_MHI_FORCE_POWER_OFF);
if (plat_priv->ramdump_info_v2.dump_data_valid ||
test_bit(CNSS_DRIVER_RECOVERY, &plat_priv->driver_state))
@@ -1424,20 +1543,6 @@
cnss_pr_dbg("PCI is probing, vendor ID: 0x%x, device ID: 0x%x\n",
id->vendor, pci_dev->device);
- switch (pci_dev->device) {
- case QCA6290_EMULATION_DEVICE_ID:
- case QCA6290_DEVICE_ID:
- if (!mhi_is_device_ready(&plat_priv->plat_dev->dev,
- MHI_NODE_NAME)) {
- cnss_pr_err("MHI driver is not ready, defer PCI probe!\n");
- ret = -EPROBE_DEFER;
- goto out;
- }
- break;
- default:
- break;
- }
-
pci_priv = devm_kzalloc(&pci_dev->dev, sizeof(*pci_priv),
GFP_KERNEL);
if (!pci_priv) {
diff --git a/drivers/net/wireless/cnss2/pci.h b/drivers/net/wireless/cnss2/pci.h
index 4a82998..4b2f6bc 100644
--- a/drivers/net/wireless/cnss2/pci.h
+++ b/drivers/net/wireless/cnss2/pci.h
@@ -15,7 +15,7 @@
#include <asm/dma-iommu.h>
#include <linux/iommu.h>
-#include <linux/msm_mhi.h>
+#include <linux/mhi.h>
#include <linux/msm_pcie.h>
#include <linux/pci.h>
@@ -34,14 +34,13 @@
enum cnss_mhi_state {
CNSS_MHI_INIT,
CNSS_MHI_DEINIT,
+ CNSS_MHI_POWER_ON,
+ CNSS_MHI_POWER_OFF,
+ CNSS_MHI_FORCE_POWER_OFF,
CNSS_MHI_SUSPEND,
CNSS_MHI_RESUME,
- CNSS_MHI_POWER_OFF,
- CNSS_MHI_POWER_ON,
CNSS_MHI_TRIGGER_RDDM,
CNSS_MHI_RDDM,
- CNSS_MHI_RDDM_KERNEL_PANIC,
- CNSS_MHI_NOTIFY_LINK_ERROR,
};
struct cnss_msi_user {
@@ -76,7 +75,7 @@
void __iomem *bar;
struct cnss_msi_config *msi_config;
u32 msi_ep_base_data;
- struct mhi_device mhi_dev;
+ struct mhi_controller *mhi_ctrl;
unsigned long mhi_state;
};
@@ -137,7 +136,7 @@
enum cnss_mhi_state state);
int cnss_pci_start_mhi(struct cnss_pci_data *pci_priv);
void cnss_pci_stop_mhi(struct cnss_pci_data *pci_priv);
-void cnss_pci_collect_dump_info(struct cnss_pci_data *pci_priv);
+void cnss_pci_collect_dump_info(struct cnss_pci_data *pci_priv, bool in_panic);
void cnss_pci_clear_dump_info(struct cnss_pci_data *pci_priv);
int cnss_pm_request_resume(struct cnss_pci_data *pci_priv);
diff --git a/drivers/pci/host/pci-msm.c b/drivers/pci/host/pci-msm.c
index 20d48a0..b67a94d 100644
--- a/drivers/pci/host/pci-msm.c
+++ b/drivers/pci/host/pci-msm.c
@@ -63,12 +63,12 @@
#define PCIE_N_SW_RESET(n) (PCS_PORT(n) + 0x00)
#define PCIE_N_POWER_DOWN_CONTROL(n) (PCS_PORT(n) + 0x04)
-#define PCIE_GEN3_COM_INTEGLOOP_GAIN1_MODE0 0x0154
-#define PCIE_GEN3_L0_DRVR_CTRL0 0x080c
-#define PCIE_GEN3_L0_RESET_GEN 0x0890
-#define PCIE_GEN3_L0_BIST_ERR_CNT1_STATUS 0x08a8
-#define PCIE_GEN3_L0_BIST_ERR_CNT2_STATUS 0x08ac
-#define PCIE_GEN3_L0_DEBUG_BUS_STATUS4 0x08bc
+#define PCIE_GEN3_SPCIE_CAP 0x0154
+#define PCIE_GEN3_GEN2_CTRL 0x080c
+#define PCIE_GEN3_RELATED 0x0890
+#define PCIE_GEN3_EQ_CONTROL 0x08a8
+#define PCIE_GEN3_EQ_FB_MODE_DIR_CHANGE 0x08ac
+#define PCIE_GEN3_MISC_CONTROL 0x08bc
#define PCIE20_PARF_SYS_CTRL 0x00
#define PCIE20_PARF_PM_CTRL 0x20
@@ -130,7 +130,6 @@
#define PCIE_IATU_UTAR(n) (PCIE_IATU_BASE(n) + 0x18)
#define PCIE20_PORT_LINK_CTRL_REG 0x710
-#define PCIE20_GEN3_RELATED_REG 0x890
#define PCIE20_PIPE_LOOPBACK_CONTROL 0x8b8
#define LOOPBACK_BASE_ADDR_OFFSET 0x8000
@@ -1552,6 +1551,13 @@
break;
}
+ if (((base_sel - 1) >= MSM_PCIE_MAX_RES) ||
+ (!dev->res[base_sel - 1].resource)) {
+ PCIE_DBG_FS(dev, "PCIe: RC%d Resource does not exist\n",
+ dev->rc_idx);
+ break;
+ }
+
PCIE_DBG_FS(dev,
"base: %s: 0x%pK\nwr_offset: 0x%x\nwr_mask: 0x%x\nwr_value: 0x%x\n",
dev->res[base_sel - 1].name,
@@ -1571,6 +1577,13 @@
break;
case MSM_PCIE_DUMP_PCIE_REGISTER_SPACE:
+ if (((base_sel - 1) >= MSM_PCIE_MAX_RES) ||
+ (!dev->res[base_sel - 1].resource)) {
+ PCIE_DBG_FS(dev, "PCIe: RC%d Resource does not exist\n",
+ dev->rc_idx);
+ break;
+ }
+
if (!base_sel) {
PCIE_DBG_FS(dev, "Invalid base_sel: 0x%x\n", base_sel);
break;
@@ -1685,13 +1698,13 @@
dev->rc_idx);
writel_relaxed(0x10000,
- dev->dm_core + PCIE20_GEN3_RELATED_REG);
+ dev->dm_core + PCIE_GEN3_RELATED);
PCIE_DBG_FS(dev,
"PCIe: RC%d: 0x%x: 0x%x\n",
dev->rc_idx,
- dbi_base_addr + PCIE20_GEN3_RELATED_REG,
+ dbi_base_addr + PCIE_GEN3_RELATED,
readl_relaxed(dev->dm_core +
- PCIE20_GEN3_RELATED_REG));
+ PCIE_GEN3_RELATED));
writel_relaxed(0x80000001,
dev->dm_core + PCIE20_PIPE_LOOPBACK_CONTROL);
@@ -3694,25 +3707,25 @@
PCIE_DBG(dev, "PCIe: RC%d: Setting up Gen3\n", dev->rc_idx);
msm_pcie_write_reg_field(dev->dm_core,
- PCIE_GEN3_L0_DRVR_CTRL0, 0x1ff00, BIT(0));
+ PCIE_GEN3_GEN2_CTRL, 0x1ff00, BIT(0));
msm_pcie_write_reg(dev->dm_core,
- PCIE_GEN3_L0_BIST_ERR_CNT2_STATUS,
+ PCIE_GEN3_EQ_FB_MODE_DIR_CHANGE,
(0x05 << 14) | (0x05 << 10) | (0x0d << 5));
- msm_pcie_write_mask(dev->dm_core +
- PCIE_GEN3_L0_BIST_ERR_CNT1_STATUS, BIT(4), 0);
+ msm_pcie_write_reg(dev->dm_core,
+ PCIE_GEN3_EQ_CONTROL, 0x20);
msm_pcie_write_mask(dev->dm_core +
- PCIE_GEN3_L0_RESET_GEN, BIT(0), 0);
+ PCIE_GEN3_RELATED, BIT(0), 0);
/* configure PCIe preset */
msm_pcie_write_reg(dev->dm_core,
- PCIE_GEN3_L0_DEBUG_BUS_STATUS4, 1);
+ PCIE_GEN3_MISC_CONTROL, 1);
msm_pcie_write_reg(dev->dm_core,
- PCIE_GEN3_COM_INTEGLOOP_GAIN1_MODE0, 0x77777777);
+ PCIE_GEN3_SPCIE_CAP, 0x77777777);
msm_pcie_write_reg(dev->dm_core,
- PCIE_GEN3_L0_DEBUG_BUS_STATUS4, 1);
+ PCIE_GEN3_MISC_CONTROL, 1);
msm_pcie_write_reg_field(dev->dm_core,
PCIE20_CAP + PCI_EXP_LNKCTL2,
diff --git a/drivers/pinctrl/qcom/pinctrl-msm.c b/drivers/pinctrl/qcom/pinctrl-msm.c
index 9e1c8d2..f51ab9e 100644
--- a/drivers/pinctrl/qcom/pinctrl-msm.c
+++ b/drivers/pinctrl/qcom/pinctrl-msm.c
@@ -30,6 +30,7 @@
#include <linux/gpio.h>
#include <linux/interrupt.h>
#include <linux/spinlock.h>
+#include <linux/syscore_ops.h>
#include <linux/reboot.h>
#include <linux/pm.h>
#include <linux/log2.h>
@@ -74,6 +75,8 @@
void __iomem *pdc_regs;
};
+static struct msm_pinctrl *msm_pinctrl_data;
+
static int msm_get_groups_count(struct pinctrl_dev *pctldev)
{
struct msm_pinctrl *pctrl = pinctrl_dev_get_drvdata(pctldev);
@@ -1520,6 +1523,52 @@
}
}
+#ifdef CONFIG_PM
+static int msm_pinctrl_suspend(void)
+{
+ return 0;
+}
+
+static void msm_pinctrl_resume(void)
+{
+ int i, irq;
+ u32 val;
+ unsigned long flags;
+ struct irq_desc *desc;
+ const struct msm_pingroup *g;
+ const char *name = "null";
+ struct msm_pinctrl *pctrl = msm_pinctrl_data;
+
+ if (!msm_show_resume_irq_mask)
+ return;
+
+ spin_lock_irqsave(&pctrl->lock, flags);
+ for_each_set_bit(i, pctrl->enabled_irqs, pctrl->chip.ngpio) {
+ g = &pctrl->soc->groups[i];
+ val = readl_relaxed(pctrl->regs + g->intr_status_reg);
+ if (val & BIT(g->intr_status_bit)) {
+ irq = irq_find_mapping(pctrl->chip.irqdomain, i);
+ desc = irq_to_desc(irq);
+ if (desc == NULL)
+ name = "stray irq";
+ else if (desc->action && desc->action->name)
+ name = desc->action->name;
+
+ pr_warn("%s: %d triggered %s\n", __func__, irq, name);
+ }
+ }
+ spin_unlock_irqrestore(&pctrl->lock, flags);
+}
+#else
+#define msm_pinctrl_suspend NULL
+#define msm_pinctrl_resume NULL
+#endif
+
+static struct syscore_ops msm_pinctrl_pm_ops = {
+ .suspend = msm_pinctrl_suspend,
+ .resume = msm_pinctrl_resume,
+};
+
int msm_pinctrl_probe(struct platform_device *pdev,
const struct msm_pinctrl_soc_data *soc_data)
{
@@ -1527,7 +1576,8 @@
struct resource *res;
int ret;
- pctrl = devm_kzalloc(&pdev->dev, sizeof(*pctrl), GFP_KERNEL);
+ msm_pinctrl_data = pctrl = devm_kzalloc(&pdev->dev,
+ sizeof(*pctrl), GFP_KERNEL);
if (!pctrl) {
dev_err(&pdev->dev, "Can't allocate msm_pinctrl\n");
return -ENOMEM;
@@ -1570,6 +1620,7 @@
platform_set_drvdata(pdev, pctrl);
+ register_syscore_ops(&msm_pinctrl_pm_ops);
dev_dbg(&pdev->dev, "Probed Qualcomm pinctrl driver\n");
return 0;
@@ -1583,6 +1634,7 @@
gpiochip_remove(&pctrl->chip);
unregister_restart_handler(&pctrl->restart_nb);
+ unregister_syscore_ops(&msm_pinctrl_pm_ops);
return 0;
}
diff --git a/drivers/pinctrl/qcom/pinctrl-msm.h b/drivers/pinctrl/qcom/pinctrl-msm.h
index 9fc6660..b8185ae 100644
--- a/drivers/pinctrl/qcom/pinctrl-msm.h
+++ b/drivers/pinctrl/qcom/pinctrl-msm.h
@@ -174,4 +174,10 @@
const struct msm_pinctrl_soc_data *soc_data);
int msm_pinctrl_remove(struct platform_device *pdev);
+#ifdef CONFIG_QCOM_SHOW_RESUME_IRQ
+extern int msm_show_resume_irq_mask;
+#else
+#define msm_show_resume_irq_mask 0
+#endif
+
#endif
diff --git a/drivers/pinctrl/qcom/pinctrl-sdm670.c b/drivers/pinctrl/qcom/pinctrl-sdm670.c
index 37a6199..196559c 100644
--- a/drivers/pinctrl/qcom/pinctrl-sdm670.c
+++ b/drivers/pinctrl/qcom/pinctrl-sdm670.c
@@ -1586,7 +1586,7 @@
[154] = SDC_QDSD_PINGROUP(sdc2_clk, 0x9a000, 14, 6),
[155] = SDC_QDSD_PINGROUP(sdc2_cmd, 0x9a000, 11, 3),
[156] = SDC_QDSD_PINGROUP(sdc2_data, 0x9a000, 9, 0),
- [157] = UFS_RESET(ufs_reset, 0x9f000),
+ [157] = UFS_RESET(ufs_reset, 0x99d000),
};
static struct msm_dir_conn sdm670_dir_conn[] = {
{1, 510},
diff --git a/drivers/platform/msm/ipa/ipa_clients/ecm_ipa.c b/drivers/platform/msm/ipa/ipa_clients/ecm_ipa.c
index 9f8bfbe..f7de806 100644
--- a/drivers/platform/msm/ipa/ipa_clients/ecm_ipa.c
+++ b/drivers/platform/msm/ipa/ipa_clients/ecm_ipa.c
@@ -1445,6 +1445,10 @@
usb_to_ipa_ep_cfg.route.rt_tbl_hdl = 0;
usb_to_ipa_ep_cfg.mode.dst = IPA_CLIENT_A5_LAN_WAN_CONS;
usb_to_ipa_ep_cfg.mode.mode = IPA_BASIC;
+
+ /* enable hdr_metadata_reg_valid */
+ usb_to_ipa_ep_cfg.hdr.hdr_metadata_reg_valid = true;
+
result = ipa_cfg_ep(usb_to_ipa_hdl, &usb_to_ipa_ep_cfg);
if (result) {
ECM_IPA_ERROR("failed to configure USB to IPA point\n");
diff --git a/drivers/platform/msm/ipa/ipa_clients/rndis_ipa.c b/drivers/platform/msm/ipa/ipa_clients/rndis_ipa.c
index 4980167..51890dd 100644
--- a/drivers/platform/msm/ipa/ipa_clients/rndis_ipa.c
+++ b/drivers/platform/msm/ipa/ipa_clients/rndis_ipa.c
@@ -363,7 +363,7 @@
sizeof(struct rndis_pkt_hdr),
.hdr_a5_mux = false,
.hdr_remove_additional = false,
- .hdr_metadata_reg_valid = false,
+ .hdr_metadata_reg_valid = true,
},
.hdr_ext = {
.hdr_pad_to_alignment = 0,
@@ -410,7 +410,7 @@
.hdr_ofst_pkt_size = 3 * sizeof(u32),
.hdr_a5_mux = false,
.hdr_remove_additional = false,
- .hdr_metadata_reg_valid = false,
+ .hdr_metadata_reg_valid = true,
},
.hdr_ext = {
.hdr_pad_to_alignment = 0,
@@ -2184,6 +2184,9 @@
ipa_to_usb_ep_cfg.aggr.aggr_time_limit,
ipa_to_usb_ep_cfg.aggr.aggr_pkt_limit);
+ /* enable hdr_metadata_reg_valid */
+ usb_to_ipa_ep_cfg->hdr.hdr_metadata_reg_valid = true;
+
result = ipa_cfg_ep(ipa_to_usb_hdl, &ipa_to_usb_ep_cfg);
if (result) {
pr_err("failed to configure IPA to USB end-point\n");
diff --git a/drivers/platform/msm/ipa/ipa_v3/ipa.c b/drivers/platform/msm/ipa/ipa_v3/ipa.c
index da60ff5..065f97f 100644
--- a/drivers/platform/msm/ipa/ipa_v3/ipa.c
+++ b/drivers/platform/msm/ipa/ipa_v3/ipa.c
@@ -373,7 +373,7 @@
{
ipa3_active_clients_log_print_table(active_clients_table_buf,
IPA3_ACTIVE_CLIENTS_TABLE_BUF_SIZE);
- IPAERR("%s", active_clients_table_buf);
+ IPAERR("%s\n", active_clients_table_buf);
return NOTIFY_DONE;
}
@@ -4280,6 +4280,9 @@
if (res)
IPAERR("uC panic handler failed %d\n", res);
+ if (atomic_read(&ipa3_ctx->ipa3_active_clients.cnt) != 0)
+ ipahal_print_all_regs();
+
return NOTIFY_DONE;
}
diff --git a/drivers/platform/msm/ipa/ipa_v3/ipa_debugfs.c b/drivers/platform/msm/ipa/ipa_v3/ipa_debugfs.c
index 07773eb..ee9c49c 100644
--- a/drivers/platform/msm/ipa/ipa_v3/ipa_debugfs.c
+++ b/drivers/platform/msm/ipa/ipa_v3/ipa_debugfs.c
@@ -1894,6 +1894,16 @@
return simple_read_from_buffer(ubuf, count, ppos, dbg_buff, cnt);
}
+static ssize_t ipa3_read_ipahal_regs(struct file *file, char __user *ubuf,
+ size_t count, loff_t *ppos)
+{
+ IPA_ACTIVE_CLIENTS_INC_SIMPLE();
+ ipahal_print_all_regs();
+ IPA_ACTIVE_CLIENTS_DEC_SIMPLE();
+
+ return 0;
+}
+
static void ipa_dump_status(struct ipahal_pkt_status *status)
{
IPA_DUMP_STATUS_FIELD(status_opcode);
@@ -2160,6 +2170,10 @@
"enable_low_prio_print", IPA_WRITE_ONLY_MODE, NULL, {
.write = ipa3_enable_ipc_low,
}
+ }, {
+ "ipa_dump_regs", IPA_READ_ONLY_MODE, NULL, {
+ .read = ipa3_read_ipahal_regs,
+ }
}
};
diff --git a/drivers/platform/msm/ipa/ipa_v3/ipa_i.h b/drivers/platform/msm/ipa/ipa_v3/ipa_i.h
index 386ad51..6f87ece 100644
--- a/drivers/platform/msm/ipa/ipa_v3/ipa_i.h
+++ b/drivers/platform/msm/ipa/ipa_v3/ipa_i.h
@@ -2116,6 +2116,7 @@
int __ipa3_release_hdr_proc_ctx(u32 proc_ctx_hdl);
int _ipa_read_ep_reg_v3_0(char *buf, int max_len, int pipe);
int _ipa_read_ep_reg_v4_0(char *buf, int max_len, int pipe);
+int _ipa_read_ipahal_regs(void);
void _ipa_enable_clks_v3_0(void);
void _ipa_disable_clks_v3_0(void);
struct device *ipa3_get_dma_dev(void);
diff --git a/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_i.h b/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_i.h
index 8f78d56..26b7f0f 100644
--- a/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_i.h
+++ b/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_i.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2016-2018, 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
@@ -46,6 +46,15 @@
IPAHAL_DRV_NAME " %s:%d " fmt, ## args); \
} while (0)
+#define IPAHAL_DBG_REG(fmt, args...) \
+ do { \
+ pr_err(fmt, ## args); \
+ IPA_IPC_LOGGING(ipa_get_ipc_logbuf(), \
+ " %s:%d " fmt, ## args); \
+ IPA_IPC_LOGGING(ipa_get_ipc_logbuf_low(), \
+ " %s:%d " fmt, ## args); \
+ } while (0)
+
#define IPAHAL_ERR_RL(fmt, args...) \
do { \
pr_err_ratelimited_ipa(IPAHAL_DRV_NAME " %s:%d " fmt, \
diff --git a/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.c b/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.c
index 66837d0..ce59488 100644
--- a/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.c
+++ b/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.c
@@ -18,6 +18,8 @@
#include "ipahal_reg.h"
#include "ipahal_reg_i.h"
+#define IPA_MAX_MSG_LEN 4096
+
static const char *ipareg_name_to_str[IPA_REG_MAX] = {
__stringify(IPA_ROUTE),
__stringify(IPA_IRQ_STTS_EE_n),
@@ -26,6 +28,9 @@
__stringify(IPA_IRQ_SUSPEND_INFO_EE_n),
__stringify(IPA_SUSPEND_IRQ_EN_EE_n),
__stringify(IPA_SUSPEND_IRQ_CLR_EE_n),
+ __stringify(IPA_HOLB_DROP_IRQ_INFO_EE_n),
+ __stringify(IPA_HOLB_DROP_IRQ_EN_EE_n),
+ __stringify(IPA_HOLB_DROP_IRQ_CLR_EE_n),
__stringify(IPA_BCR),
__stringify(IPA_ENABLED_PIPES),
__stringify(IPA_COMP_SW_RESET),
@@ -35,7 +40,20 @@
__stringify(IPA_SPARE_REG_1),
__stringify(IPA_SPARE_REG_2),
__stringify(IPA_COMP_CFG),
+ __stringify(IPA_STATE_TX_WRAPPER),
+ __stringify(IPA_STATE_TX1),
+ __stringify(IPA_STATE_FETCHER),
+ __stringify(IPA_STATE_FETCHER_MASK),
+ __stringify(IPA_STATE_DFETCHER),
+ __stringify(IPA_STATE_ACL),
+ __stringify(IPA_STATE),
+ __stringify(IPA_STATE_RX_ACTIVE),
+ __stringify(IPA_STATE_TX0),
__stringify(IPA_STATE_AGGR_ACTIVE),
+ __stringify(IPA_STATE_GSI_TLV),
+ __stringify(IPA_STATE_GSI_AOS),
+ __stringify(IPA_STATE_GSI_IF),
+ __stringify(IPA_STATE_GSI_SKIP),
__stringify(IPA_ENDP_INIT_HDR_n),
__stringify(IPA_ENDP_INIT_HDR_EXT_n),
__stringify(IPA_ENDP_INIT_AGGR_n),
@@ -46,6 +64,7 @@
__stringify(IPA_ENDP_INIT_CONN_TRACK_n),
__stringify(IPA_ENDP_INIT_CTRL_n),
__stringify(IPA_ENDP_INIT_CTRL_SCND_n),
+ __stringify(IPA_ENDP_INIT_CTRL_STATUS_n),
__stringify(IPA_ENDP_INIT_HOL_BLOCK_EN_n),
__stringify(IPA_ENDP_INIT_HOL_BLOCK_TIMER_n),
__stringify(IPA_ENDP_INIT_DEAGGR_n),
@@ -55,6 +74,7 @@
__stringify(IPA_IRQ_EE_UC_n),
__stringify(IPA_ENDP_INIT_HDR_METADATA_MASK_n),
__stringify(IPA_ENDP_INIT_HDR_METADATA_n),
+ __stringify(IPA_ENDP_INIT_PROD_CFG_n),
__stringify(IPA_ENDP_INIT_RSRC_GRP_n),
__stringify(IPA_SHARED_MEM_SIZE),
__stringify(IPA_SRAM_DIRECT_ACCESS_n),
@@ -66,6 +86,8 @@
__stringify(IPA_SYS_PKT_PROC_CNTXT_BASE),
__stringify(IPA_LOCAL_PKT_PROC_CNTXT_BASE),
__stringify(IPA_ENDP_STATUS_n),
+ __stringify(IPA_ENDP_WEIGHTS_n),
+ __stringify(IPA_ENDP_YELLOW_RED_MARKER),
__stringify(IPA_ENDP_FILTER_ROUTER_HSH_CFG_n),
__stringify(IPA_SRC_RSRC_GRP_01_RSRC_TYPE_n),
__stringify(IPA_SRC_RSRC_GRP_23_RSRC_TYPE_n),
@@ -105,6 +127,12 @@
__stringify(IPA_STAT_ROUTER_IPV6_END_ID),
__stringify(IPA_STAT_DROP_CNT_BASE_n),
__stringify(IPA_STAT_DROP_CNT_MASK_n),
+ __stringify(IPA_SNOC_FEC_EE_n),
+ __stringify(IPA_FEC_ADDR_EE_n),
+ __stringify(IPA_FEC_ADDR_MSB_EE_n),
+ __stringify(IPA_FEC_ATTR_EE_n),
+ __stringify(IPA_MBIM_DEAGGR_FEC_ATTR_EE_n),
+ __stringify(IPA_GEN_DEAGGR_FEC_ATTR_EE_n),
};
static void ipareg_construct_dummy(enum ipahal_reg_name reg,
@@ -1651,6 +1679,9 @@
* @parse - CB to parse register value to abstracted structure
* @offset - register offset relative to base address
* @n_ofst - N parameterized register sub-offset
+ * @n_start - starting n for n_registers
+ * @n_end - ending n for n_registers
+ * @en_print - enable this register to be printed when the device crashes
*/
struct ipahal_reg_obj {
void (*construct)(enum ipahal_reg_name reg, const void *fields,
@@ -1659,6 +1690,9 @@
u32 val);
u32 offset;
u32 n_ofst;
+ int n_start;
+ int n_end;
+ bool en_print;
};
/*
@@ -1676,365 +1710,543 @@
/* IPAv3 */
[IPA_HW_v3_0][IPA_ROUTE] = {
ipareg_construct_route, ipareg_parse_dummy,
- 0x00000048, 0},
+ 0x00000048, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_IRQ_STTS_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00003008, 0x1000},
+ 0x00003008, 0x1000, 0, 0, 0},
[IPA_HW_v3_0][IPA_IRQ_EN_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000300c, 0x1000},
+ 0x0000300c, 0x1000, 0, 0, 0},
[IPA_HW_v3_0][IPA_IRQ_CLR_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00003010, 0x1000},
+ 0x00003010, 0x1000, 0, 0, 0},
[IPA_HW_v3_0][IPA_IRQ_SUSPEND_INFO_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00003098, 0x1000},
+ 0x00003098, 0x1000, 0, 0, 0},
[IPA_HW_v3_0][IPA_BCR] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x000001D0, 0},
+ 0x000001D0, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENABLED_PIPES] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000038, 0},
+ 0x00000038, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_COMP_SW_RESET] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000040, 0},
+ 0x00000040, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_VERSION] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000034, 0},
+ 0x00000034, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_TAG_TIMER] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000060, 0 },
+ 0x00000060, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_COMP_HW_VERSION] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000030, 0},
+ 0x00000030, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_SPARE_REG_1] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00005090, 0},
+ 0x00005090, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_SPARE_REG_2] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00005094, 0},
+ 0x00005094, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_COMP_CFG] = {
ipareg_construct_comp_cfg, ipareg_parse_comp_cfg,
- 0x0000003C, 0},
+ 0x0000003C, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_STATE_AGGR_ACTIVE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000010C, 0},
+ 0x0000010C, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_HDR_n] = {
ipareg_construct_endp_init_hdr_n, ipareg_parse_dummy,
- 0x00000810, 0x70},
+ 0x00000810, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_HDR_EXT_n] = {
ipareg_construct_endp_init_hdr_ext_n, ipareg_parse_dummy,
- 0x00000814, 0x70},
+ 0x00000814, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_AGGR_n] = {
ipareg_construct_endp_init_aggr_n,
ipareg_parse_endp_init_aggr_n,
- 0x00000824, 0x70},
+ 0x00000824, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_AGGR_FORCE_CLOSE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x000001EC, 0},
+ 0x000001EC, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_ROUTE_n] = {
ipareg_construct_endp_init_route_n, ipareg_parse_dummy,
- 0x00000828, 0x70},
+ 0x00000828, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_MODE_n] = {
ipareg_construct_endp_init_mode_n, ipareg_parse_dummy,
- 0x00000820, 0x70},
+ 0x00000820, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_NAT_n] = {
ipareg_construct_endp_init_nat_n, ipareg_parse_dummy,
- 0x0000080C, 0x70},
+ 0x0000080C, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_CTRL_n] = {
ipareg_construct_endp_init_ctrl_n,
ipareg_parse_endp_init_ctrl_n,
- 0x00000800, 0x70},
+ 0x00000800, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_CTRL_SCND_n] = {
ipareg_construct_endp_init_ctrl_scnd_n, ipareg_parse_dummy,
- 0x00000804, 0x70 },
+ 0x00000804, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_HOL_BLOCK_EN_n] = {
ipareg_construct_endp_init_hol_block_en_n,
ipareg_parse_dummy,
- 0x0000082c, 0x70},
+ 0x0000082c, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_HOL_BLOCK_TIMER_n] = {
ipareg_construct_endp_init_hol_block_timer_n,
ipareg_parse_dummy,
- 0x00000830, 0x70},
+ 0x00000830, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_DEAGGR_n] = {
ipareg_construct_endp_init_deaggr_n,
ipareg_parse_dummy,
- 0x00000834, 0x70},
+ 0x00000834, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_SEQ_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000083C, 0x70},
+ 0x0000083C, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_DEBUG_CNT_REG_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000600, 0x4},
+ 0x00000600, 0x4, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_CFG_n] = {
ipareg_construct_endp_init_cfg_n, ipareg_parse_dummy,
- 0x00000808, 0x70},
+ 0x00000808, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_IRQ_EE_UC_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000301c, 0x1000},
+ 0x0000301c, 0x1000, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_HDR_METADATA_MASK_n] = {
ipareg_construct_endp_init_hdr_metadata_mask_n,
ipareg_parse_dummy,
- 0x00000818, 0x70},
+ 0x00000818, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_HDR_METADATA_n] = {
ipareg_construct_endp_init_hdr_metadata_n,
ipareg_parse_dummy,
- 0x0000081c, 0x70},
+ 0x0000081c, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_INIT_RSRC_GRP_n] = {
ipareg_construct_endp_init_rsrc_grp_n,
ipareg_parse_dummy,
- 0x00000838, 0x70},
+ 0x00000838, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_SHARED_MEM_SIZE] = {
ipareg_construct_dummy, ipareg_parse_shared_mem_size,
- 0x00000054, 0},
+ 0x00000054, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_SRAM_DIRECT_ACCESS_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00007000, 0x4},
+ 0x00007000, 0x4, 0, 0, 0},
[IPA_HW_v3_0][IPA_DEBUG_CNT_CTRL_n] = {
ipareg_construct_debug_cnt_ctrl_n, ipareg_parse_dummy,
- 0x00000640, 0x4},
+ 0x00000640, 0x4, 0, 0, 0},
[IPA_HW_v3_0][IPA_UC_MAILBOX_m_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00032000, 0x4},
+ 0x00032000, 0x4, 0, 0, 0},
[IPA_HW_v3_0][IPA_FILT_ROUT_HASH_FLUSH] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000090, 0},
+ 0x00000090, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_SINGLE_NDP_MODE] = {
ipareg_construct_single_ndp_mode, ipareg_parse_single_ndp_mode,
- 0x00000068, 0},
+ 0x00000068, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_QCNCM] = {
ipareg_construct_qcncm, ipareg_parse_qcncm,
- 0x00000064, 0},
+ 0x00000064, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_SYS_PKT_PROC_CNTXT_BASE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x000001e0, 0},
+ 0x000001e0, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_LOCAL_PKT_PROC_CNTXT_BASE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x000001e8, 0},
+ 0x000001e8, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_STATUS_n] = {
ipareg_construct_endp_status_n, ipareg_parse_dummy,
- 0x00000840, 0x70},
+ 0x00000840, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_ENDP_FILTER_ROUTER_HSH_CFG_n] = {
ipareg_construct_hash_cfg_n, ipareg_parse_hash_cfg_n,
- 0x0000085C, 0x70},
+ 0x0000085C, 0x70, 0, 0, 0},
[IPA_HW_v3_0][IPA_SRC_RSRC_GRP_01_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x00000400, 0x20},
+ 0x00000400, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_SRC_RSRC_GRP_23_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x00000404, 0x20},
+ 0x00000404, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_SRC_RSRC_GRP_45_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x00000408, 0x20},
+ 0x00000408, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_SRC_RSRC_GRP_67_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x0000040C, 0x20},
+ 0x0000040C, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_DST_RSRC_GRP_01_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x00000500, 0x20},
+ 0x00000500, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_DST_RSRC_GRP_23_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x00000504, 0x20},
+ 0x00000504, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_DST_RSRC_GRP_45_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x00000508, 0x20},
+ 0x00000508, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_DST_RSRC_GRP_67_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy, ipareg_parse_dummy,
- 0x0000050c, 0x20},
+ 0x0000050c, 0x20, 0, 0, 0},
[IPA_HW_v3_0][IPA_RX_HPS_CLIENTS_MIN_DEPTH_0] = {
ipareg_construct_rx_hps_clients_depth0, ipareg_parse_dummy,
- 0x000023C4, 0},
+ 0x000023C4, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_RX_HPS_CLIENTS_MIN_DEPTH_1] = {
ipareg_construct_rx_hps_clients_depth1, ipareg_parse_dummy,
- 0x000023C8, 0},
+ 0x000023C8, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_RX_HPS_CLIENTS_MAX_DEPTH_0] = {
ipareg_construct_rx_hps_clients_depth0, ipareg_parse_dummy,
- 0x000023CC, 0},
+ 0x000023CC, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_RX_HPS_CLIENTS_MAX_DEPTH_1] = {
ipareg_construct_rx_hps_clients_depth1, ipareg_parse_dummy,
- 0x000023D0, 0},
+ 0x000023D0, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_QSB_MAX_WRITES] = {
ipareg_construct_qsb_max_writes, ipareg_parse_dummy,
- 0x00000074, 0},
+ 0x00000074, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_QSB_MAX_READS] = {
ipareg_construct_qsb_max_reads, ipareg_parse_dummy,
- 0x00000078, 0},
+ 0x00000078, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_DPS_SEQUENCER_FIRST] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0001e000, 0},
+ 0x0001e000, 0, 0, 0, 0},
[IPA_HW_v3_0][IPA_HPS_SEQUENCER_FIRST] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0001e080, 0},
+ 0x0001e080, 0, 0, 0, 0},
/* IPAv3.1 */
[IPA_HW_v3_1][IPA_IRQ_SUSPEND_INFO_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00003030, 0x1000},
+ 0x00003030, 0x1000, 0, 0, 0},
[IPA_HW_v3_1][IPA_SUSPEND_IRQ_EN_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00003034, 0x1000},
+ 0x00003034, 0x1000, 0, 0, 0},
[IPA_HW_v3_1][IPA_SUSPEND_IRQ_CLR_EE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00003038, 0x1000},
+ 0x00003038, 0x1000, 0, 0, 0},
/* IPAv3.5 */
[IPA_HW_v3_5][IPA_TX_CFG] = {
ipareg_construct_tx_cfg, ipareg_parse_tx_cfg,
- 0x000001FC, 0},
+ 0x000001FC, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_SRC_RSRC_GRP_01_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy_v3_5, ipareg_parse_dummy,
- 0x00000400, 0x20},
+ 0x00000400, 0x20, 0, 0, 0},
[IPA_HW_v3_5][IPA_SRC_RSRC_GRP_23_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy_v3_5, ipareg_parse_dummy,
- 0x00000404, 0x20},
+ 0x00000404, 0x20, 0, 0, 0},
[IPA_HW_v3_5][IPA_SRC_RSRC_GRP_45_RSRC_TYPE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_SRC_RSRC_GRP_67_RSRC_TYPE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_DST_RSRC_GRP_01_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy_v3_5, ipareg_parse_dummy,
- 0x00000500, 0x20},
+ 0x00000500, 0x20, 0, 0, 0},
[IPA_HW_v3_5][IPA_DST_RSRC_GRP_23_RSRC_TYPE_n] = {
ipareg_construct_rsrg_grp_xy_v3_5, ipareg_parse_dummy,
- 0x00000504, 0x20},
+ 0x00000504, 0x20, 0, 0, 0},
[IPA_HW_v3_5][IPA_DST_RSRC_GRP_45_RSRC_TYPE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_DST_RSRC_GRP_67_RSRC_TYPE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_ENDP_INIT_RSRC_GRP_n] = {
ipareg_construct_endp_init_rsrc_grp_n_v3_5,
ipareg_parse_dummy,
- 0x00000838, 0x70},
+ 0x00000838, 0x70, 0, 0, 0},
[IPA_HW_v3_5][IPA_RX_HPS_CLIENTS_MIN_DEPTH_0] = {
ipareg_construct_rx_hps_clients_depth0_v3_5,
ipareg_parse_dummy,
- 0x000023C4, 0},
+ 0x000023C4, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_RX_HPS_CLIENTS_MIN_DEPTH_1] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_RX_HPS_CLIENTS_MAX_DEPTH_0] = {
ipareg_construct_rx_hps_clients_depth0_v3_5,
ipareg_parse_dummy,
- 0x000023CC, 0},
+ 0x000023CC, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_RX_HPS_CLIENTS_MAX_DEPTH_1] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_SPARE_REG_1] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00002780, 0},
+ 0x00002780, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_SPARE_REG_2] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00002784, 0},
+ 0x00002784, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_IDLE_INDICATION_CFG] = {
ipareg_construct_idle_indication_cfg, ipareg_parse_dummy,
- 0x00000220, 0},
+ 0x00000220, 0, 0, 0, 0},
[IPA_HW_v3_5][IPA_HPS_FTCH_ARB_QUEUE_WEIGHT] = {
ipareg_construct_hps_queue_weights,
- ipareg_parse_hps_queue_weights, 0x000005a4, 0},
+ ipareg_parse_hps_queue_weights, 0x000005a4, 0, 0, 0, 0},
/* IPAv4.0 */
+ [IPA_HW_v4_0][IPA_IRQ_SUSPEND_INFO_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003030, 0x1000, 0, 1, 1},
+ [IPA_HW_v4_0][IPA_SUSPEND_IRQ_EN_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003034, 0x1000, 0, 1, 1},
+ [IPA_HW_v4_0][IPA_SUSPEND_IRQ_CLR_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003038, 0x1000, 0, 1, 1},
+ [IPA_HW_v4_0][IPA_IRQ_EN_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x0000300c, 0x1000, 0, 1, 1},
+ [IPA_HW_v4_0][IPA_TAG_TIMER] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000060, 0, 0, 0, 1},
[IPA_HW_v4_0][IPA_ENDP_INIT_CTRL_n] = {
ipareg_construct_endp_init_ctrl_n_v4_0, ipareg_parse_dummy,
- 0x00000800, 0x70 },
+ 0x00000800, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_HDR_EXT_n] = {
+ ipareg_construct_endp_init_hdr_ext_n, ipareg_parse_dummy,
+ 0x00000814, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_AGGR_n] = {
+ ipareg_construct_endp_init_aggr_n,
+ ipareg_parse_endp_init_aggr_n,
+ 0x00000824, 0x70, 0, 23, 1},
[IPA_HW_v4_0][IPA_TX_CFG] = {
ipareg_construct_tx_cfg_v4_0, ipareg_parse_tx_cfg_v4_0,
- 0x000001FC, 0},
+ 0x000001FC, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_DEBUG_CNT_REG_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_DEBUG_CNT_CTRL_n] = {
ipareg_construct_debug_cnt_ctrl_n, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_QCNCM] = {
ipareg_construct_qcncm, ipareg_parse_qcncm,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_SINGLE_NDP_MODE] = {
ipareg_construct_single_ndp_mode, ipareg_parse_single_ndp_mode,
- -1, 0},
+ -1, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_QSB_MAX_READS] = {
ipareg_construct_qsb_max_reads_v4_0, ipareg_parse_dummy,
- 0x00000078, 0},
+ 0x00000078, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_FILT_ROUT_HASH_FLUSH] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000014c, 0},
- [IPA_HW_v4_0][IPA_STATE_AGGR_ACTIVE] = {
- ipareg_construct_dummy, ipareg_parse_dummy,
- 0x000000b4, 0},
+ 0x0000014c, 0, 0, 0, 0},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_HDR_n] = {
+ ipareg_construct_endp_init_hdr_n, ipareg_parse_dummy,
+ 0x00000810, 0x70, 0, 23, 1},
[IPA_HW_v4_0][IPA_ENDP_INIT_ROUTE_n] = {
ipareg_construct_endp_init_route_n, ipareg_parse_dummy,
- -1, 0},
+ -1, 0, 0, 0, 0},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_MODE_n] = {
+ ipareg_construct_endp_init_mode_n, ipareg_parse_dummy,
+ 0x00000820, 0x70, 0, 10, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_NAT_n] = {
+ ipareg_construct_endp_init_nat_n, ipareg_parse_dummy,
+ 0x0000080C, 0x70, 0, 10, 1},
[IPA_HW_v4_0][IPA_ENDP_STATUS_n] = {
ipareg_construct_endp_status_n_v4_0, ipareg_parse_dummy,
- 0x00000840, 0x70},
- [IPA_HW_v4_0][IPA_CLKON_CFG] = {
- ipareg_construct_clkon_cfg, ipareg_parse_clkon_cfg,
- 0x00000044, 0},
+ 0x00000840, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_FILTER_ROUTER_HSH_CFG_n] = {
+ ipareg_construct_hash_cfg_n, ipareg_parse_hash_cfg_n,
+ 0x0000085C, 0x70, 0, 32, 1},
[IPA_HW_v4_0][IPA_ENDP_INIT_CONN_TRACK_n] = {
ipareg_construct_endp_init_conn_track_n,
ipareg_parse_dummy,
- 0x00000850, 0x70},
+ 0x00000850, 0x70, 0, 10, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_CTRL_SCND_n] = {
+ ipareg_construct_endp_init_ctrl_scnd_n, ipareg_parse_dummy,
+ 0x00000804, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_HOL_BLOCK_EN_n] = {
+ ipareg_construct_endp_init_hol_block_en_n,
+ ipareg_parse_dummy,
+ 0x0000082c, 0x70, 10, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_HOL_BLOCK_TIMER_n] = {
+ ipareg_construct_endp_init_hol_block_timer_n,
+ ipareg_parse_dummy,
+ 0x00000830, 0x70, 10, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_DEAGGR_n] = {
+ ipareg_construct_endp_init_deaggr_n,
+ ipareg_parse_dummy,
+ 0x00000834, 0x70, 0, 10, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_SEQ_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x0000083C, 0x70, 0, 10, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_CFG_n] = {
+ ipareg_construct_endp_init_cfg_n, ipareg_parse_dummy,
+ 0x00000808, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_IRQ_EE_UC_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x0000301c, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_HDR_METADATA_MASK_n] = {
+ ipareg_construct_endp_init_hdr_metadata_mask_n,
+ ipareg_parse_dummy,
+ 0x00000818, 0x70, 10, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_HDR_METADATA_n] = {
+ ipareg_construct_endp_init_hdr_metadata_n,
+ ipareg_parse_dummy,
+ 0x0000081c, 0x70, 0, 10, 1},
+ [IPA_HW_v4_0][IPA_CLKON_CFG] = {
+ ipareg_construct_clkon_cfg, ipareg_parse_clkon_cfg,
+ 0x00000044, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_QUOTA_BASE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000700, 0x4 },
+ 0x00000700, 0x4, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_QUOTA_MASK_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000708, 0x4 },
+ 0x00000708, 0x4, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_TETHERING_BASE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000710, 0x4 },
+ 0x00000710, 0x4, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_TETHERING_MASK_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000718, 0x4 },
+ 0x00000718, 0x4, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_FILTER_IPV4_BASE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000720, 0x0 },
+ 0x00000720, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_FILTER_IPV6_BASE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000724, 0x0 },
+ 0x00000724, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_ROUTER_IPV4_BASE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000728, 0x0 },
+ 0x00000728, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_ROUTER_IPV6_BASE] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000072C, 0x0 },
+ 0x0000072C, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_FILTER_IPV4_START_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000730, 0x0 },
+ 0x00000730, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_FILTER_IPV6_START_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000734, 0x0 },
+ 0x00000734, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_ROUTER_IPV4_START_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000738, 0x0 },
+ 0x00000738, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_ROUTER_IPV6_START_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000073C, 0x0 },
+ 0x0000073C, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_FILTER_IPV4_END_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000740, 0x0 },
+ 0x00000740, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_FILTER_IPV6_END_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000744, 0x0 },
+ 0x00000744, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_ROUTER_IPV4_END_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000748, 0x0 },
+ 0x00000748, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_ROUTER_IPV6_END_ID] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x0000074C, 0x0 },
+ 0x0000074C, 0, 0, 0, 0},
[IPA_HW_v4_0][IPA_STAT_DROP_CNT_BASE_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000750, 0x4 },
+ 0x00000750, 0x4, 3, 1},
[IPA_HW_v4_0][IPA_STAT_DROP_CNT_MASK_n] = {
ipareg_construct_dummy, ipareg_parse_dummy,
- 0x00000758, 0x4 },
+ 0x00000758, 0x4, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_TX_WRAPPER] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000090, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_TX1] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000094, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_FETCHER] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000098, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_FETCHER_MASK] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x0000009C, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_DFETCHER] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000A0, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_ACL] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000A4, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000A8, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_RX_ACTIVE] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000AC, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_TX0] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000B0, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_AGGR_ACTIVE] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000B4, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_GSI_TLV] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000B8, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_GSI_AOS] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000B8, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_GSI_IF] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000C0, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_STATE_GSI_SKIP] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x000000C4, 0, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_SNOC_FEC_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003018, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_FEC_ADDR_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003020, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_FEC_ADDR_MSB_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003024, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_FEC_ATTR_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003028, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_MBIM_DEAGGR_FEC_ATTR_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003028, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_GEN_DEAGGR_FEC_ATTR_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003028, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_HOLB_DROP_IRQ_INFO_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x0000303C, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_HOLB_DROP_IRQ_EN_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003040, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_HOLB_DROP_IRQ_CLR_EE_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00003044, 0x1000, 0, 0, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_CTRL_STATUS_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000864, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_PROD_CFG_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000CC8, 0x70, 10, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_INIT_RSRC_GRP_n] = {
+ ipareg_construct_endp_init_rsrc_grp_n_v3_5,
+ ipareg_parse_dummy,
+ 0x00000838, 0x70, 0, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_WEIGHTS_n] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000CA4, 0x70, 10, 23, 1},
+ [IPA_HW_v4_0][IPA_ENDP_YELLOW_RED_MARKER] = {
+ ipareg_construct_dummy, ipareg_parse_dummy,
+ 0x00000CC0, 0x70, 10, 23, 1},
};
+int ipahal_print_all_regs(void)
+{
+ int i, j;
+
+ IPAHAL_DBG("Printing all registers for ipa_hw_type %d\n",
+ ipahal_ctx->hw_type);
+
+ if ((ipahal_ctx->hw_type < IPA_HW_v4_0) ||
+ (ipahal_ctx->hw_type >= IPA_HW_MAX)) {
+ IPAHAL_ERR("invalid IPA HW type (%d)\n", ipahal_ctx->hw_type);
+ return -EINVAL;
+ }
+
+ for (i = 0; i < IPA_REG_MAX ; i++) {
+ if (!ipahal_reg_objs[IPA_HW_v4_0][i].en_print)
+ continue;
+
+ j = ipahal_reg_objs[ipahal_ctx->hw_type][i].n_start;
+
+ if (j == ipahal_reg_objs[ipahal_ctx->hw_type][i].n_end)
+ IPAHAL_DBG_REG("%s=0x%x\n", ipahal_reg_name_str(i),
+ ipahal_read_reg_n(i, j));
+
+ for (; j < ipahal_reg_objs[ipahal_ctx->hw_type][i].n_end; j++)
+ IPAHAL_DBG_REG("%s_%u=0x%x\n", ipahal_reg_name_str(i),
+ j, ipahal_read_reg_n(i, j));
+ }
+ return 0;
+}
+
/*
* ipahal_reg_init() - Build the registers information table
* See ipahal_reg_objs[][] comments
diff --git a/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.h b/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.h
index 2675771..7e8e8ba 100644
--- a/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.h
+++ b/drivers/platform/msm/ipa/ipa_v3/ipahal/ipahal_reg.h
@@ -29,6 +29,9 @@
IPA_IRQ_SUSPEND_INFO_EE_n,
IPA_SUSPEND_IRQ_EN_EE_n,
IPA_SUSPEND_IRQ_CLR_EE_n,
+ IPA_HOLB_DROP_IRQ_INFO_EE_n,
+ IPA_HOLB_DROP_IRQ_EN_EE_n,
+ IPA_HOLB_DROP_IRQ_CLR_EE_n,
IPA_BCR,
IPA_ENABLED_PIPES,
IPA_COMP_SW_RESET,
@@ -38,7 +41,20 @@
IPA_SPARE_REG_1,
IPA_SPARE_REG_2,
IPA_COMP_CFG,
+ IPA_STATE_TX_WRAPPER,
+ IPA_STATE_TX1,
+ IPA_STATE_FETCHER,
+ IPA_STATE_FETCHER_MASK,
+ IPA_STATE_DFETCHER,
+ IPA_STATE_ACL,
+ IPA_STATE,
+ IPA_STATE_RX_ACTIVE,
+ IPA_STATE_TX0,
IPA_STATE_AGGR_ACTIVE,
+ IPA_STATE_GSI_TLV,
+ IPA_STATE_GSI_AOS,
+ IPA_STATE_GSI_IF,
+ IPA_STATE_GSI_SKIP,
IPA_ENDP_INIT_HDR_n,
IPA_ENDP_INIT_HDR_EXT_n,
IPA_ENDP_INIT_AGGR_n,
@@ -49,6 +65,7 @@
IPA_ENDP_INIT_CONN_TRACK_n,
IPA_ENDP_INIT_CTRL_n,
IPA_ENDP_INIT_CTRL_SCND_n,
+ IPA_ENDP_INIT_CTRL_STATUS_n,
IPA_ENDP_INIT_HOL_BLOCK_EN_n,
IPA_ENDP_INIT_HOL_BLOCK_TIMER_n,
IPA_ENDP_INIT_DEAGGR_n,
@@ -58,6 +75,7 @@
IPA_IRQ_EE_UC_n,
IPA_ENDP_INIT_HDR_METADATA_MASK_n,
IPA_ENDP_INIT_HDR_METADATA_n,
+ IPA_ENDP_INIT_PROD_CFG_n,
IPA_ENDP_INIT_RSRC_GRP_n,
IPA_SHARED_MEM_SIZE,
IPA_SRAM_DIRECT_ACCESS_n,
@@ -69,6 +87,8 @@
IPA_SYS_PKT_PROC_CNTXT_BASE,
IPA_LOCAL_PKT_PROC_CNTXT_BASE,
IPA_ENDP_STATUS_n,
+ IPA_ENDP_WEIGHTS_n,
+ IPA_ENDP_YELLOW_RED_MARKER,
IPA_ENDP_FILTER_ROUTER_HSH_CFG_n,
IPA_SRC_RSRC_GRP_01_RSRC_TYPE_n,
IPA_SRC_RSRC_GRP_23_RSRC_TYPE_n,
@@ -108,6 +128,12 @@
IPA_STAT_ROUTER_IPV6_END_ID,
IPA_STAT_DROP_CNT_BASE_n,
IPA_STAT_DROP_CNT_MASK_n,
+ IPA_SNOC_FEC_EE_n,
+ IPA_FEC_ADDR_EE_n,
+ IPA_FEC_ADDR_MSB_EE_n,
+ IPA_FEC_ATTR_EE_n,
+ IPA_MBIM_DEAGGR_FEC_ATTR_EE_n,
+ IPA_GEN_DEAGGR_FEC_ATTR_EE_n,
IPA_REG_MAX,
};
@@ -492,6 +518,9 @@
bool endp_delay;
};
+
+int ipahal_print_all_regs(void);
+
/*
* ipahal_reg_name_str() - returns string that represent the register
* @reg_name: [in] register name
diff --git a/drivers/platform/msm/mhi_dev/mhi.c b/drivers/platform/msm/mhi_dev/mhi.c
index 47d5292..1c16e5a 100644
--- a/drivers/platform/msm/mhi_dev/mhi.c
+++ b/drivers/platform/msm/mhi_dev/mhi.c
@@ -38,6 +38,7 @@
/* Wait time before suspend/resume is complete */
#define MHI_SUSPEND_MIN 100
#define MHI_SUSPEND_TIMEOUT 600
+#define MHI_WAKEUP_TIMEOUT_CNT 20
#define MHI_MASK_CH_EV_LEN 32
#define MHI_RING_CMD_ID 0
#define MHI_RING_PRIMARY_EVT_ID 1
@@ -1326,6 +1327,8 @@
struct mhi_dev_channel *ch;
struct mhi_dev_ring *ring;
int ch_id = 0, rc = 0;
+ char *disconnected_12[2] = { "MHI_CHANNEL_STATE_12=DISCONNECTED", NULL};
+ char *disconnected_14[2] = { "MHI_CHANNEL_STATE_14=DISCONNECTED", NULL};
/* Hard stop all the channels */
for (ch_id = 0; ch_id < mhi->cfg.channels; ch_id++) {
@@ -1341,6 +1344,17 @@
/* Update ctrl node */
mhi_update_state_info(MHI_DEV_UEVENT_CTRL, MHI_STATE_DISCONNECTED);
+ mhi_update_state_info(MHI_CLIENT_MBIM_OUT, MHI_STATE_DISCONNECTED);
+ mhi_update_state_info(MHI_CLIENT_QMI_OUT, MHI_STATE_DISCONNECTED);
+ rc = kobject_uevent_env(&mhi_ctx->dev->kobj,
+ KOBJ_CHANGE, disconnected_12);
+ if (rc)
+ pr_err("Error sending uevent:%d\n", rc);
+
+ rc = kobject_uevent_env(&mhi_ctx->dev->kobj,
+ KOBJ_CHANGE, disconnected_14);
+ if (rc)
+ pr_err("Error sending uevent:%d\n", rc);
flush_workqueue(mhi->ring_init_wq);
flush_workqueue(mhi->pending_ring_wq);
@@ -2175,11 +2189,19 @@
}
while (atomic_read(&mhi_ctx->is_suspended) &&
- suspend_wait_timeout < MHI_SUSPEND_TIMEOUT) {
+ suspend_wait_timeout < MHI_WAKEUP_TIMEOUT_CNT) {
/* wait for the suspend to finish */
msleep(MHI_SUSPEND_MIN);
suspend_wait_timeout++;
}
+
+ if (suspend_wait_timeout >= MHI_WAKEUP_TIMEOUT_CNT ||
+ mhi_ctx->ctrl_info != MHI_STATE_CONNECTED) {
+ pr_err("Failed to wake up core\n");
+ mutex_unlock(&mhi_ctx->mhi_write_test);
+ return -ENODEV;
+ }
+
handle_client = wreq->client;
ch = handle_client->channel;
ch->wr_request_active = true;
diff --git a/drivers/platform/msm/usb_bam.c b/drivers/platform/msm/usb_bam.c
index b4cd640..9374bc8 100644
--- a/drivers/platform/msm/usb_bam.c
+++ b/drivers/platform/msm/usb_bam.c
@@ -26,6 +26,7 @@
#include <linux/workqueue.h>
#include <linux/dma-mapping.h>
#include <linux/pm_runtime.h>
+#include <linux/usb/msm_hsusb.h>
#define USB_THRESHOLD 512
#define USB_BAM_MAX_STR_LEN 50
@@ -2969,9 +2970,6 @@
else
usb_bam_data->override_threshold = threshold;
- usb_bam_data->enable_hsusb_bam_on_boot = of_property_read_bool(node,
- "qcom,enable-hsusb-bam-on-boot");
-
for_each_child_of_node(pdev->dev.of_node, node)
max_connections++;
@@ -3095,48 +3093,42 @@
return NULL;
}
-static int usb_bam_init(struct platform_device *pdev)
+static void msm_usb_bam_update_props(struct sps_bam_props *props,
+ struct platform_device *pdev)
{
- int ret;
struct usb_bam_ctx_type *ctx = dev_get_drvdata(&pdev->dev);
enum usb_ctrl bam_type = ctx->usb_bam_data->bam_type;
- struct sps_bam_props props;
struct device *dev;
- memset(&props, 0, sizeof(props));
-
- pr_debug("%s: usb_bam_init - %s\n", __func__,
- bam_enable_strings[bam_type]);
-
- props.phys_addr = ctx->io_res->start;
- props.virt_size = resource_size(ctx->io_res);
- props.irq = ctx->irq;
- props.summing_threshold = ctx->usb_bam_data->override_threshold;
- props.event_threshold = ctx->usb_bam_data->override_threshold;
- props.num_pipes = ctx->usb_bam_data->usb_bam_num_pipes;
- props.callback = usb_bam_sps_events;
- props.user = bam_enable_strings[bam_type];
+ props->phys_addr = ctx->io_res->start;
+ props->virt_addr = NULL;
+ props->virt_size = resource_size(ctx->io_res);
+ props->irq = ctx->irq;
+ props->summing_threshold = ctx->usb_bam_data->override_threshold;
+ props->event_threshold = ctx->usb_bam_data->override_threshold;
+ props->num_pipes = ctx->usb_bam_data->usb_bam_num_pipes;
+ props->callback = usb_bam_sps_events;
+ props->user = bam_enable_strings[bam_type];
/*
* HSUSB and HSIC Cores don't support RESET ACK signal to BAMs
* Hence, let BAM to ignore acknowledge from USB while resetting PIPE
*/
if (ctx->usb_bam_data->ignore_core_reset_ack && bam_type != DWC3_CTRL)
- props.options = SPS_BAM_NO_EXT_P_RST;
+ props->options = SPS_BAM_NO_EXT_P_RST;
if (ctx->usb_bam_data->disable_clk_gating)
- props.options |= SPS_BAM_NO_LOCAL_CLK_GATING;
+ props->options |= SPS_BAM_NO_LOCAL_CLK_GATING;
/*
- * HSUSB BAM is not NDP BAM and it must be enabled early before
+ * HSUSB BAM is not NDP BAM and it must be enabled before
* starting peripheral controller to avoid switching USB core mode
* from legacy to BAM with ongoing data transfers.
*/
- if (ctx->usb_bam_data->enable_hsusb_bam_on_boot
- && bam_type == CI_CTRL) {
- pr_debug("Register and enable HSUSB BAM\n");
- props.options |= SPS_BAM_OPT_ENABLE_AT_BOOT;
- props.options |= SPS_BAM_FORCE_RESET;
+ if (bam_type == CI_CTRL) {
+ log_event_dbg("Register and enable HSUSB BAM\n");
+ props->options |= SPS_BAM_OPT_ENABLE_AT_BOOT;
+ props->options |= SPS_BAM_FORCE_RESET;
}
dev = &ctx->usb_bam_pdev->dev;
@@ -3145,9 +3137,29 @@
"qcom,smmu-s1-bypass")) {
pr_info("%s: setting SPS_BAM_SMMU_EN flag with (%s)\n",
__func__, dev_name(dev));
- props.options |= SPS_BAM_SMMU_EN;
+ props->options |= SPS_BAM_SMMU_EN;
}
+}
+static int usb_bam_init(struct platform_device *pdev)
+{
+ int ret;
+ struct usb_bam_ctx_type *ctx = dev_get_drvdata(&pdev->dev);
+ enum usb_ctrl bam_type = ctx->usb_bam_data->bam_type;
+ struct sps_bam_props props;
+
+ pr_debug("%s: usb_bam_init - %s\n", __func__,
+ bam_enable_strings[bam_type]);
+
+ /*
+ * CI USB2 BAM is registered before starting controller
+ * and only if bam2bam function is present in composition
+ */
+ if (bam_type == CI_CTRL)
+ return 0;
+
+ memset(&props, 0, sizeof(props));
+ msm_usb_bam_update_props(&props, pdev);
ret = sps_register_bam_device(&props, &ctx->h_bam);
if (ret < 0) {
log_event_err("%s: register bam error %d\n", __func__, ret);
@@ -3428,7 +3440,7 @@
return 0;
usb_bam_data = ctx->usb_bam_data;
- if ((bam != CI_CTRL) || !usb_bam_data->enable_hsusb_bam_on_boot)
+ if (bam != CI_CTRL)
return 0;
if (!ctx->pipes_enabled_per_bam || info[bam].pipes_suspended)
@@ -3532,18 +3544,45 @@
{
struct msm_usb_bam_data *usb_bam_data;
struct usb_bam_ctx_type *ctx = &msm_usb_bam[bam];
+ static bool bam_enabled;
+ int ret;
if (!ctx->usb_bam_pdev)
return 0;
usb_bam_data = ctx->usb_bam_data;
- if ((bam != CI_CTRL) || !(bam_enable ||
- usb_bam_data->enable_hsusb_bam_on_boot))
+ if (bam != CI_CTRL)
return 0;
- msm_hw_bam_disable(1);
- sps_device_reset(ctx->h_bam);
- msm_hw_bam_disable(0);
+ if (bam_enabled == bam_enable) {
+ log_event_dbg("%s: USB BAM is already %s\n", __func__,
+ bam_enable ? "Registered" : "De-registered");
+ return 0;
+ }
+
+ if (bam_enable) {
+ struct sps_bam_props props;
+
+ memset(&props, 0, sizeof(props));
+ msm_usb_bam_update_props(&props, ctx->usb_bam_pdev);
+ msm_hw_bam_disable(1);
+ ret = sps_register_bam_device(&props, &ctx->h_bam);
+ bam_enabled = true;
+ if (ret < 0) {
+ log_event_err("%s: register bam error %d\n",
+ __func__, ret);
+ return -EFAULT;
+ }
+ log_event_dbg("%s: USB BAM Registered\n", __func__);
+ msm_hw_bam_disable(0);
+ } else {
+ msm_hw_soft_reset();
+ msm_hw_bam_disable(1);
+ sps_device_reset(ctx->h_bam);
+ sps_deregister_bam_device(ctx->h_bam);
+ log_event_dbg("%s: USB BAM De-registered\n", __func__);
+ bam_enabled = false;
+ }
return 0;
}
diff --git a/drivers/power/supply/power_supply_sysfs.c b/drivers/power/supply/power_supply_sysfs.c
index 03bfd48..d675e46 100644
--- a/drivers/power/supply/power_supply_sysfs.c
+++ b/drivers/power/supply/power_supply_sysfs.c
@@ -329,6 +329,7 @@
POWER_SUPPLY_ATTR(recharge_soc),
POWER_SUPPLY_ATTR(toggle_stat),
POWER_SUPPLY_ATTR(allow_hvdcp3),
+ POWER_SUPPLY_ATTR(hvdcp_opti_allowed),
/* Local extensions of type int64_t */
POWER_SUPPLY_ATTR(charge_counter_ext),
/* Properties of type `const char *' */
diff --git a/drivers/power/supply/qcom/battery.c b/drivers/power/supply/qcom/battery.c
index 223af14..275b982 100644
--- a/drivers/power/supply/qcom/battery.c
+++ b/drivers/power/supply/qcom/battery.c
@@ -74,6 +74,7 @@
int total_settled_ua;
int pl_settled_ua;
int pl_fcc_max;
+ u32 wa_flags;
struct class qcom_batt_class;
struct wakeup_source *pl_ws;
struct notifier_block nb;
@@ -85,6 +86,10 @@
PR_PARALLEL = BIT(0),
};
+enum {
+ AICL_RERUN_WA_BIT = BIT(0),
+};
+
static int debug_mask;
module_param_named(debug_mask, debug_mask, int, 0600);
@@ -620,7 +625,7 @@
if (icl_ua > pval.intval)
rerun_aicl = true;
- if (rerun_aicl) {
+ if (rerun_aicl && (chip->wa_flags & AICL_RERUN_WA_BIT)) {
/* set a lower ICL */
pval.intval = max(pval.intval - ICL_STEP_UA, ICL_STEP_UA);
power_supply_set_property(chip->main_psy,
@@ -1190,8 +1195,20 @@
return 0;
}
+static void pl_config_init(struct pl_data *chip, int smb_version)
+{
+ switch (smb_version) {
+ case PMI8998_SUBTYPE:
+ case PM660_SUBTYPE:
+ chip->wa_flags = AICL_RERUN_WA_BIT;
+ break;
+ default:
+ break;
+ }
+}
+
#define DEFAULT_RESTRICTED_CURRENT_UA 1000000
-int qcom_batt_init(void)
+int qcom_batt_init(int smb_version)
{
struct pl_data *chip;
int rc = 0;
@@ -1206,6 +1223,7 @@
if (!chip)
return -ENOMEM;
chip->slave_pct = 50;
+ pl_config_init(chip, smb_version);
chip->restricted_current = DEFAULT_RESTRICTED_CURRENT_UA;
chip->pl_ws = wakeup_source_register("qcom-battery");
diff --git a/drivers/power/supply/qcom/battery.h b/drivers/power/supply/qcom/battery.h
index 38626e7..94e8800 100644
--- a/drivers/power/supply/qcom/battery.h
+++ b/drivers/power/supply/qcom/battery.h
@@ -12,6 +12,6 @@
#ifndef __BATTERY_H
#define __BATTERY_H
-int qcom_batt_init(void);
+int qcom_batt_init(int smb_version);
void qcom_batt_deinit(void);
#endif /* __BATTERY_H */
diff --git a/drivers/power/supply/qcom/qg-core.h b/drivers/power/supply/qcom/qg-core.h
index 5ea9b78..55dba4e 100644
--- a/drivers/power/supply/qcom/qg-core.h
+++ b/drivers/power/supply/qcom/qg-core.h
@@ -115,8 +115,10 @@
};
enum ocv_type {
- PON_OCV,
- GOOD_OCV,
+ S7_PON_OCV,
+ S3_GOOD_OCV,
+ S3_LAST_OCV,
+ SDAM_PON_OCV,
};
enum debug_mask {
diff --git a/drivers/power/supply/qcom/qg-defs.h b/drivers/power/supply/qcom/qg-defs.h
index bbbc7ee..6ae9aa2 100644
--- a/drivers/power/supply/qcom/qg-defs.h
+++ b/drivers/power/supply/qcom/qg-defs.h
@@ -37,6 +37,8 @@
#define V_RAW_TO_UV(V_RAW) div_u64(194637ULL * (u64)V_RAW, 1000)
#define I_RAW_TO_UA(I_RAW) div_s64(152588LL * (s64)I_RAW, 1000)
+#define FIFO_V_RESET_VAL 0x8000
+#define FIFO_I_RESET_VAL 0x8000
#define DEGC_SCALE 10
#define UV_TO_DECIUV(a) (a / 100)
diff --git a/drivers/power/supply/qcom/qg-reg.h b/drivers/power/supply/qcom/qg-reg.h
index 1f42a8c..96533d4 100644
--- a/drivers/power/supply/qcom/qg-reg.h
+++ b/drivers/power/supply/qcom/qg-reg.h
@@ -77,6 +77,8 @@
#define QG_LAST_ADC_V_DATA0_REG 0xC0
#define QG_LAST_ADC_I_DATA0_REG 0xC2
+#define QG_LAST_S3_SLEEP_V_DATA0_REG 0xCC
+
/* SDAM offsets */
#define QG_SDAM_VALID_OFFSET 0x46
#define QG_SDAM_SOC_OFFSET 0x47
@@ -85,5 +87,6 @@
#define QG_SDAM_OCV_OFFSET 0x4C
#define QG_SDAM_IBAT_OFFSET 0x50
#define QG_SDAM_TIME_OFFSET 0x54
+#define QG_SDAM_PON_OCV_OFFSET 0x7C
#endif
diff --git a/drivers/power/supply/qcom/qg-sdam.c b/drivers/power/supply/qcom/qg-sdam.c
index 65bebab..54eed16 100644
--- a/drivers/power/supply/qcom/qg-sdam.c
+++ b/drivers/power/supply/qcom/qg-sdam.c
@@ -63,6 +63,11 @@
.offset = QG_SDAM_TIME_OFFSET,
.length = 4,
},
+ [SDAM_PON_OCV_UV] = {
+ .name = "SDAM_PON_OCV",
+ .offset = QG_SDAM_PON_OCV_OFFSET,
+ .length = 2,
+ },
};
int qg_sdam_write(u8 param, u32 data)
diff --git a/drivers/power/supply/qcom/qg-sdam.h b/drivers/power/supply/qcom/qg-sdam.h
index a75ead9..51af04c 100644
--- a/drivers/power/supply/qcom/qg-sdam.h
+++ b/drivers/power/supply/qcom/qg-sdam.h
@@ -23,6 +23,7 @@
SDAM_OCV_UV,
SDAM_IBAT_UA,
SDAM_TIME_SEC,
+ SDAM_PON_OCV_UV,
SDAM_MAX,
};
diff --git a/drivers/power/supply/qcom/qpnp-qg.c b/drivers/power/supply/qcom/qpnp-qg.c
index 3f05a53..effb093 100644
--- a/drivers/power/supply/qcom/qpnp-qg.c
+++ b/drivers/power/supply/qcom/qpnp-qg.c
@@ -64,33 +64,52 @@
return false;
}
-static int qg_read_ocv(struct qpnp_qg *chip, u32 *ocv_uv, u8 type)
+static int qg_read_ocv(struct qpnp_qg *chip, u32 *ocv_uv, u32 *ocv_raw, u8 type)
{
int rc, addr;
u64 temp = 0;
+ char ocv_name[20];
switch (type) {
- case GOOD_OCV:
+ case S3_GOOD_OCV:
addr = QG_S3_GOOD_OCV_V_DATA0_REG;
+ strlcpy(ocv_name, "S3_GOOD_OCV", 20);
break;
- case PON_OCV:
+ case S7_PON_OCV:
addr = QG_S7_PON_OCV_V_DATA0_REG;
+ strlcpy(ocv_name, "S7_PON_OCV", 20);
+ break;
+ case S3_LAST_OCV:
+ addr = QG_LAST_S3_SLEEP_V_DATA0_REG;
+ strlcpy(ocv_name, "S3_LAST_OCV", 20);
+ break;
+ case SDAM_PON_OCV:
+ addr = QG_SDAM_PON_OCV_OFFSET;
+ strlcpy(ocv_name, "SDAM_PON_OCV", 20);
break;
default:
pr_err("Invalid OCV type %d\n", type);
return -EINVAL;
}
- rc = qg_read(chip, chip->qg_base + addr, (u8 *)&temp, 2);
- if (rc < 0) {
- pr_err("Failed to read ocv, rc=%d\n", rc);
- return rc;
+ if (type == SDAM_PON_OCV) {
+ rc = qg_sdam_read(SDAM_PON_OCV_UV, ocv_raw);
+ if (rc < 0) {
+ pr_err("Failed to read SDAM PON OCV rc=%d\n", rc);
+ return rc;
+ }
+ } else {
+ rc = qg_read(chip, chip->qg_base + addr, (u8 *)ocv_raw, 2);
+ if (rc < 0) {
+ pr_err("Failed to read ocv, rc=%d\n", rc);
+ return rc;
+ }
}
+ temp = *ocv_raw;
*ocv_uv = V_RAW_TO_UV(temp);
- pr_debug("%s: OCV=%duV\n",
- type == GOOD_OCV ? "GOOD_OCV" : "PON_OCV", *ocv_uv);
+ pr_debug("%s: OCV_RAW=%x OCV=%duV\n", ocv_name, *ocv_raw, *ocv_uv);
return rc;
}
@@ -276,6 +295,12 @@
fifo_v = v_fifo[i] | (v_fifo[i + 1] << 8);
fifo_i = i_fifo[i] | (i_fifo[i + 1] << 8);
+ if (fifo_v == FIFO_V_RESET_VAL || fifo_i == FIFO_I_RESET_VAL) {
+ pr_err("Invalid FIFO data V_RAW=%x I_RAW=%x - FIFO rejected\n",
+ fifo_v, fifo_i);
+ return -EINVAL;
+ }
+
temp = sign_extend32(fifo_i, 15);
chip->kdata.fifo[j].v = V_RAW_TO_UV(fifo_v);
@@ -669,7 +694,7 @@
{
int rc;
u8 status = 0;
- u32 ocv_uv;
+ u32 ocv_uv = 0, ocv_raw = 0;
struct qpnp_qg *chip = data;
qg_dbg(chip, QG_DEBUG_IRQ, "IRQ triggered\n");
@@ -685,7 +710,7 @@
if (!(status & GOOD_OCV_BIT))
goto done;
- rc = qg_read_ocv(chip, &ocv_uv, GOOD_OCV);
+ rc = qg_read_ocv(chip, &ocv_uv, &ocv_raw, S3_GOOD_OCV);
if (rc < 0) {
pr_err("Failed to read good_ocv, rc=%d\n", rc);
goto done;
@@ -1030,9 +1055,6 @@
union power_supply_propval prop = {0, };
int rc, recharge_soc, health;
- vote(chip->good_ocv_irq_disable_votable,
- QG_INIT_STATE_IRQ_DISABLE, !chip->charge_done, 0);
-
if (!chip->dt.hold_soc_while_full)
goto out;
@@ -1528,11 +1550,11 @@
static int qg_determine_pon_soc(struct qpnp_qg *chip)
{
- u8 status = 0, ocv_type = 0;
int rc = 0, batt_temp = 0;
- bool use_pon_ocv = true, use_shutdown_ocv = false;
+ bool use_pon_ocv = true;
unsigned long rtc_sec = 0;
- u32 ocv_uv = 0, soc = 0, shutdown[SDAM_MAX] = {0};
+ u32 ocv_uv = 0, ocv_raw = 0, soc = 0, shutdown[SDAM_MAX] = {0};
+ char ocv_type[20] = "NONE";
if (!chip->profile_loaded) {
qg_dbg(chip, QG_DEBUG_PON, "No Profile, skipping PON soc\n");
@@ -1566,9 +1588,9 @@
chip->dt.ignore_shutdown_soc_secs,
(rtc_sec - shutdown[SDAM_TIME_SEC]))) {
use_pon_ocv = false;
- use_shutdown_ocv = true;
ocv_uv = shutdown[SDAM_OCV_UV];
soc = shutdown[SDAM_SOC];
+ strlcpy(ocv_type, "SHUTDOWN_SOC", 20);
qg_dbg(chip, QG_DEBUG_PON, "Using SHUTDOWN_SOC @ PON\n");
}
@@ -1580,24 +1602,31 @@
goto done;
}
- rc = qg_read(chip, chip->qg_base + QG_STATUS2_REG, &status, 1);
- if (rc < 0) {
- pr_err("Failed to read status2 register rc=%d\n", rc);
+ /*
+ * Read S3_LAST_OCV, if S3_LAST_OCV is invalid,
+ * read the SDAM_PON_OCV
+ * if SDAM is not-set, use S7_PON_OCV.
+ */
+ strlcpy(ocv_type, "S3_LAST_SOC", 20);
+ rc = qg_read_ocv(chip, &ocv_uv, &ocv_raw, S3_LAST_OCV);
+ if (rc < 0)
goto done;
- }
- if (status & GOOD_OCV_BIT)
- ocv_type = GOOD_OCV;
- else
- ocv_type = PON_OCV;
+ if (ocv_raw == FIFO_V_RESET_VAL) {
+ /* S3_LAST_OCV is invalid */
+ strlcpy(ocv_type, "SDAM_PON_SOC", 20);
+ rc = qg_read_ocv(chip, &ocv_uv, &ocv_raw, SDAM_PON_OCV);
+ if (rc < 0)
+ goto done;
- qg_dbg(chip, QG_DEBUG_PON, "Using %s @ PON\n",
- ocv_type == GOOD_OCV ? "GOOD_OCV" : "PON_OCV");
-
- rc = qg_read_ocv(chip, &ocv_uv, ocv_type);
- if (rc < 0) {
- pr_err("Failed to read ocv rc=%d\n", rc);
- goto done;
+ if (!ocv_uv) {
+ /* SDAM_PON_OCV is not set */
+ strlcpy(ocv_type, "S7_PON_SOC", 20);
+ rc = qg_read_ocv(chip, &ocv_uv, &ocv_raw,
+ S7_PON_OCV);
+ if (rc < 0)
+ goto done;
+ }
}
rc = lookup_soc_ocv(&soc, ocv_uv, batt_temp, false);
@@ -1608,7 +1637,7 @@
}
done:
if (rc < 0) {
- pr_err("Failed to get SOC @ PON, rc=%d\n", rc);
+ pr_err("Failed to get %s @ PON, rc=%d\n", ocv_type, rc);
return rc;
}
@@ -1629,9 +1658,9 @@
if (rc < 0)
pr_err("Failed to update sdam params rc=%d\n", rc);
- pr_info("use_pon_ocv=%d use_good_ocv=%d use_shutdown_ocv=%d ocv_uv=%duV soc=%d\n",
- use_pon_ocv, !!(status & GOOD_OCV_BIT),
- use_shutdown_ocv, ocv_uv, chip->msoc);
+ pr_info("using %s @ PON ocv_uv=%duV soc=%d\n",
+ ocv_type, ocv_uv, chip->msoc);
+
return 0;
}
@@ -2061,7 +2090,7 @@
else
chip->dt.s3_entry_ibat_ua = temp;
- rc = of_property_read_u32(node, "qcom,s3-entry-ibat-ua", &temp);
+ rc = of_property_read_u32(node, "qcom,s3-exit-ibat-ua", &temp);
if (rc < 0)
chip->dt.s3_exit_ibat_ua = -EINVAL;
else
@@ -2134,6 +2163,10 @@
if (!chip->profile_loaded)
return 0;
+ /* disable GOOD_OCV IRQ in sleep */
+ vote(chip->good_ocv_irq_disable_votable,
+ QG_INIT_STATE_IRQ_DISABLE, true, 0);
+
chip->suspend_data = false;
/* ignore any suspend processing if we are charging */
@@ -2198,13 +2231,17 @@
static int process_resume(struct qpnp_qg *chip)
{
u8 status2 = 0, rt_status = 0;
- u32 ocv_uv = 0;
+ u32 ocv_uv = 0, ocv_raw = 0;
int rc, batt_temp = 0;
/* skip if profile is not loaded */
if (!chip->profile_loaded)
return 0;
+ /* enable GOOD_OCV IRQ when awake */
+ vote(chip->good_ocv_irq_disable_votable,
+ QG_INIT_STATE_IRQ_DISABLE, false, 0);
+
rc = qg_read(chip, chip->qg_base + QG_STATUS2_REG, &status2, 1);
if (rc < 0) {
pr_err("Failed to read status2 register, rc=%d\n", rc);
@@ -2212,7 +2249,7 @@
}
if (status2 & GOOD_OCV_BIT) {
- rc = qg_read_ocv(chip, &ocv_uv, GOOD_OCV);
+ rc = qg_read_ocv(chip, &ocv_uv, &ocv_raw, S3_GOOD_OCV);
if (rc < 0) {
pr_err("Failed to read good_ocv, rc=%d\n", rc);
return rc;
diff --git a/drivers/power/supply/qcom/smb-lib.c b/drivers/power/supply/qcom/smb-lib.c
index 7e1aa5d..36a3be7 100644
--- a/drivers/power/supply/qcom/smb-lib.c
+++ b/drivers/power/supply/qcom/smb-lib.c
@@ -5228,7 +5228,7 @@
switch (chg->mode) {
case PARALLEL_MASTER:
- rc = qcom_batt_init();
+ rc = qcom_batt_init(chg->smb_version);
if (rc < 0) {
smblib_err(chg, "Couldn't init qcom_batt_init rc=%d\n",
rc);
diff --git a/drivers/power/supply/qcom/smb1355-charger.c b/drivers/power/supply/qcom/smb1355-charger.c
index ffbced6..327ae63 100644
--- a/drivers/power/supply/qcom/smb1355-charger.c
+++ b/drivers/power/supply/qcom/smb1355-charger.c
@@ -28,6 +28,7 @@
#include <linux/power_supply.h>
#include <linux/workqueue.h>
#include <linux/pmic-voter.h>
+#include <linux/string.h>
/* SMB1355 registers, different than mentioned in smb-reg.h */
@@ -120,6 +121,7 @@
#define MISC_CUST_SDCDC_ILIMIT_CFG_REG (MISC_BASE + 0xA1)
#define LS_VALLEY_THRESH_PCT_BIT BIT(3)
+#define PCL_LIMIT_MASK GENMASK(1, 0)
#define SNARL_BARK_BITE_WD_CFG_REG (MISC_BASE + 0x53)
#define BITE_WDOG_DISABLE_CHARGING_CFG_BIT BIT(7)
@@ -1029,6 +1031,16 @@
return rc;
}
+ /* For SMB1354, set PCL to 8.6 A */
+ if (!strcmp(chip->name, "smb1354")) {
+ rc = smb1355_masked_write(chip, MISC_CUST_SDCDC_ILIMIT_CFG_REG,
+ PCL_LIMIT_MASK, PCL_LIMIT_MASK);
+ if (rc < 0) {
+ pr_err("Couldn't set PCL limit to 8.6A rc=%d\n", rc);
+ return rc;
+ }
+ }
+
rc = smb1355_tskin_sensor_config(chip);
if (rc < 0) {
pr_err("Couldn't configure tskin regs rc=%d\n", rc);
diff --git a/drivers/power/supply/qcom/smb5-lib.c b/drivers/power/supply/qcom/smb5-lib.c
index 5df7c9e..3152669 100644
--- a/drivers/power/supply/qcom/smb5-lib.c
+++ b/drivers/power/supply/qcom/smb5-lib.c
@@ -18,6 +18,7 @@
#include <linux/qpnp/qpnp-revid.h>
#include <linux/irq.h>
#include <linux/pmic-voter.h>
+#include <linux/of_batterydata.h>
#include "smb5-lib.h"
#include "smb5-reg.h"
#include "battery.h"
@@ -592,6 +593,8 @@
chg->bms_psy = psy;
if (ev == PSY_EVENT_PROP_CHANGED)
schedule_work(&chg->bms_update_work);
+ if (!chg->jeita_configured)
+ schedule_work(&chg->jeita_update_work);
}
if (!chg->pl.psy && !strcmp(psy->desc->name, "parallel")) {
@@ -651,6 +654,7 @@
return 0;
}
+#define USBIN_100MA 100000
static void smblib_uusb_removal(struct smb_charger *chg)
{
int rc;
@@ -694,6 +698,15 @@
chg->pulse_cnt = 0;
chg->uusb_apsd_rerun_done = false;
+ /* write back the default FLOAT charger configuration */
+ rc = smblib_masked_write(chg, USBIN_OPTIONS_2_CFG_REG,
+ (u8)FLOAT_OPTIONS_MASK, chg->float_cfg);
+ if (rc < 0)
+ smblib_err(chg, "Couldn't write float charger options rc=%d\n",
+ rc);
+
+ /* leave the ICL configured to 100mA for next insertion */
+ vote(chg->usb_icl_votable, DEFAULT_100MA_VOTER, true, USBIN_100MA);
/* clear USB ICL vote for USB_PSY_VOTER */
rc = vote(chg->usb_icl_votable, USB_PSY_VOTER, false, 0);
if (rc < 0)
@@ -759,7 +772,6 @@
}
#define USBIN_25MA 25000
-#define USBIN_100MA 100000
#define USBIN_150MA 150000
#define USBIN_500MA 500000
#define USBIN_900MA 900000
@@ -881,6 +893,9 @@
goto out;
}
+ /* Re-run AICL */
+ if (chg->real_charger_type != POWER_SUPPLY_TYPE_USB)
+ rc = smblib_rerun_aicl(chg);
out:
return rc;
}
@@ -2109,12 +2124,20 @@
* Valid FLOAT charger, report the current based
* of Rp
*/
- typec_mode = smblib_get_prop_typec_mode(chg);
- rp_ua = get_rp_based_dcp_current(chg, typec_mode);
- rc = vote(chg->usb_icl_votable, LEGACY_UNKNOWN_VOTER,
- true, rp_ua);
- if (rc < 0)
- return rc;
+ if (chg->connector_type ==
+ POWER_SUPPLY_CONNECTOR_TYPEC) {
+ typec_mode = smblib_get_prop_typec_mode(chg);
+ rp_ua = get_rp_based_dcp_current(chg,
+ typec_mode);
+ rc = vote(chg->usb_icl_votable,
+ DYNAMIC_RP_VOTER, true, rp_ua);
+ if (rc < 0) {
+ pr_err("Couldn't vote ICL DYNAMIC_RP_VOTER rc=%d\n",
+ rc);
+ return rc;
+ }
+ }
+ /* No specific handling required for micro-USB */
} else {
/*
* FLOAT charger detected as SDP by USB driver,
@@ -2123,20 +2146,30 @@
*/
chg->real_charger_type = POWER_SUPPLY_TYPE_USB;
rc = vote(chg->usb_icl_votable, USB_PSY_VOTER,
- true, usb_current);
- if (rc < 0)
+ true, usb_current);
+ if (rc < 0) {
+ pr_err("Couldn't vote ICL USB_PSY_VOTER rc=%d\n",
+ rc);
return rc;
- rc = vote(chg->usb_icl_votable, LEGACY_UNKNOWN_VOTER,
- false, 0);
- if (rc < 0)
- return rc;
+ }
}
} else {
rc = vote(chg->usb_icl_votable, USB_PSY_VOTER,
true, usb_current);
+ if (rc < 0) {
+ pr_err("Couldn't vote ICL USB_PSY_VOTER rc=%d\n", rc);
+ return rc;
+ }
+
}
- return rc;
+ rc = vote(chg->usb_icl_votable, DEFAULT_100MA_VOTER, false, 0);
+ if (rc < 0) {
+ pr_err("Couldn't unvote ICL DEFAULT_100MA_VOTER rc=%d\n", rc);
+ return rc;
+ }
+
+ return 0;
}
int smblib_set_prop_sdp_current_max(struct smb_charger *chg,
@@ -2273,9 +2306,6 @@
smblib_err(chg, "Couldn't vote for USB ICL rc=%d\n",
rc);
- /* since PD was found the cable must be non-legacy */
- vote(chg->usb_icl_votable, LEGACY_UNKNOWN_VOTER, false, 0);
-
/* clear USB ICL vote for DCP_VOTER */
rc = vote(chg->usb_icl_votable, DCP_VOTER, false, 0);
if (rc < 0)
@@ -2883,6 +2913,7 @@
switch (apsd_result->bit) {
case SDP_CHARGER_BIT:
case CDP_CHARGER_BIT:
+ case FLOAT_CHARGER_BIT:
/* if not DCP then no hvdcp timeout happens. Enable pd here */
vote(chg->pd_disallowed_votable_indirect, APSD_VOTER,
false, 0);
@@ -2891,12 +2922,13 @@
smblib_notify_device_mode(chg, true);
break;
case OCP_CHARGER_BIT:
- case FLOAT_CHARGER_BIT:
+ vote(chg->usb_icl_votable, DEFAULT_100MA_VOTER, false, 0);
/* if not DCP then no hvdcp timeout happens, Enable pd here. */
vote(chg->pd_disallowed_votable_indirect, APSD_VOTER,
false, 0);
break;
case DCP_CHARGER_BIT:
+ vote(chg->usb_icl_votable, DEFAULT_100MA_VOTER, false, 0);
break;
default:
break;
@@ -3008,7 +3040,7 @@
cancel_delayed_work_sync(&chg->pl_enable_work);
/* reset input current limit voters */
- vote(chg->usb_icl_votable, LEGACY_UNKNOWN_VOTER, true, 100000);
+ vote(chg->usb_icl_votable, DEFAULT_100MA_VOTER, true, USBIN_100MA);
vote(chg->usb_icl_votable, PD_VOTER, false, 0);
vote(chg->usb_icl_votable, USB_PSY_VOTER, false, 0);
vote(chg->usb_icl_votable, DCP_VOTER, false, 0);
@@ -3016,6 +3048,7 @@
vote(chg->usb_icl_votable, SW_QC3_VOTER, false, 0);
vote(chg->usb_icl_votable, OTG_VOTER, false, 0);
vote(chg->usb_icl_votable, CTM_VOTER, false, 0);
+ vote(chg->usb_icl_votable, DYNAMIC_RP_VOTER, false, 0);
/* reset power delivery voters */
vote(chg->pd_allowed_votable, PD_VOTER, false, 0);
@@ -3146,8 +3179,8 @@
* pre-existing valid vote.
*/
if (apsd->pst == POWER_SUPPLY_TYPE_USB_FLOAT &&
- get_client_vote(chg->usb_icl_votable,
- LEGACY_UNKNOWN_VOTER) <= 100000)
+ (get_client_vote(chg->usb_icl_votable, DEFAULT_100MA_VOTER)
+ <= USBIN_100MA))
return;
/*
@@ -3159,7 +3192,7 @@
chg->typec_mode, typec_mode);
rp_ua = get_rp_based_dcp_current(chg, typec_mode);
- vote(chg->usb_icl_votable, LEGACY_UNKNOWN_VOTER, true, rp_ua);
+ vote(chg->usb_icl_votable, DYNAMIC_RP_VOTER, true, rp_ua);
}
static void smblib_handle_typec_cc_state_change(struct smb_charger *chg)
@@ -3497,6 +3530,100 @@
vote(chg->awake_votable, PL_DELAY_VOTER, false, 0);
}
+#define JEITA_SOFT 0
+#define JEITA_HARD 1
+static int smblib_update_jeita(struct smb_charger *chg, u32 *thresholds,
+ int type)
+{
+ int rc;
+ u16 temp, base;
+
+ base = CHGR_JEITA_THRESHOLD_BASE_REG(type);
+
+ temp = thresholds[1] & 0xFFFF;
+ temp = ((temp & 0xFF00) >> 8) | ((temp & 0xFF) << 8);
+ rc = smblib_batch_write(chg, base, (u8 *)&temp, 2);
+ if (rc < 0) {
+ smblib_err(chg,
+ "Couldn't configure Jeita %s hot threshold rc=%d\n",
+ (type == JEITA_SOFT) ? "Soft" : "Hard", rc);
+ return rc;
+ }
+
+ temp = thresholds[0] & 0xFFFF;
+ temp = ((temp & 0xFF00) >> 8) | ((temp & 0xFF) << 8);
+ rc = smblib_batch_write(chg, base + 2, (u8 *)&temp, 2);
+ if (rc < 0) {
+ smblib_err(chg,
+ "Couldn't configure Jeita %s cold threshold rc=%d\n",
+ (type == JEITA_SOFT) ? "Soft" : "Hard", rc);
+ return rc;
+ }
+
+ smblib_dbg(chg, PR_MISC, "%s Jeita threshold configured\n",
+ (type == JEITA_SOFT) ? "Soft" : "Hard");
+
+ return 0;
+}
+
+static void jeita_update_work(struct work_struct *work)
+{
+ struct smb_charger *chg = container_of(work, struct smb_charger,
+ jeita_update_work);
+ struct device_node *node = chg->dev->of_node;
+ struct device_node *batt_node, *pnode;
+ union power_supply_propval val;
+ int rc;
+ u32 jeita_thresholds[2];
+
+ batt_node = of_find_node_by_name(node, "qcom,battery-data");
+ if (!batt_node) {
+ smblib_err(chg, "Batterydata not available\n");
+ goto out;
+ }
+
+ rc = power_supply_get_property(chg->bms_psy,
+ POWER_SUPPLY_PROP_RESISTANCE_ID, &val);
+ if (rc < 0) {
+ smblib_err(chg, "Failed to get batt-id rc=%d\n", rc);
+ goto out;
+ }
+
+ pnode = of_batterydata_get_best_profile(batt_node,
+ val.intval / 1000, NULL);
+ if (IS_ERR(pnode)) {
+ rc = PTR_ERR(pnode);
+ smblib_err(chg, "Failed to detect valid battery profile %d\n",
+ rc);
+ goto out;
+ }
+
+ rc = of_property_read_u32_array(pnode, "qcom,jeita-hard-thresholds",
+ jeita_thresholds, 2);
+ if (!rc) {
+ rc = smblib_update_jeita(chg, jeita_thresholds, JEITA_HARD);
+ if (rc < 0) {
+ smblib_err(chg, "Couldn't configure Hard Jeita rc=%d\n",
+ rc);
+ goto out;
+ }
+ }
+
+ rc = of_property_read_u32_array(pnode, "qcom,jeita-soft-thresholds",
+ jeita_thresholds, 2);
+ if (!rc) {
+ rc = smblib_update_jeita(chg, jeita_thresholds, JEITA_SOFT);
+ if (rc < 0) {
+ smblib_err(chg, "Couldn't configure Soft Jeita rc=%d\n",
+ rc);
+ goto out;
+ }
+ }
+
+out:
+ chg->jeita_configured = true;
+}
+
static int smblib_create_votables(struct smb_charger *chg)
{
int rc = 0;
@@ -3621,6 +3748,7 @@
mutex_init(&chg->otg_oc_lock);
INIT_WORK(&chg->bms_update_work, bms_update_work);
INIT_WORK(&chg->pl_update_work, pl_update_work);
+ INIT_WORK(&chg->jeita_update_work, jeita_update_work);
INIT_DELAYED_WORK(&chg->clear_hdc_work, clear_hdc_work);
INIT_DELAYED_WORK(&chg->icl_change_work, smblib_icl_change_work);
INIT_DELAYED_WORK(&chg->pl_enable_work, smblib_pl_enable_work);
@@ -3629,10 +3757,11 @@
chg->fake_capacity = -EINVAL;
chg->fake_input_current_limited = -EINVAL;
chg->fake_batt_status = -EINVAL;
+ chg->jeita_configured = false;
switch (chg->mode) {
case PARALLEL_MASTER:
- rc = qcom_batt_init();
+ rc = qcom_batt_init(chg->smb_version);
if (rc < 0) {
smblib_err(chg, "Couldn't init qcom_batt_init rc=%d\n",
rc);
@@ -3686,6 +3815,7 @@
switch (chg->mode) {
case PARALLEL_MASTER:
cancel_work_sync(&chg->bms_update_work);
+ cancel_work_sync(&chg->jeita_update_work);
cancel_work_sync(&chg->pl_update_work);
cancel_delayed_work_sync(&chg->clear_hdc_work);
cancel_delayed_work_sync(&chg->icl_change_work);
diff --git a/drivers/power/supply/qcom/smb5-lib.h b/drivers/power/supply/qcom/smb5-lib.h
index 39cc921..7ee4a3a 100644
--- a/drivers/power/supply/qcom/smb5-lib.h
+++ b/drivers/power/supply/qcom/smb5-lib.h
@@ -56,7 +56,6 @@
#define CTM_VOTER "CTM_VOTER"
#define SW_QC3_VOTER "SW_QC3_VOTER"
#define AICL_RERUN_VOTER "AICL_RERUN_VOTER"
-#define LEGACY_UNKNOWN_VOTER "LEGACY_UNKNOWN_VOTER"
#define QNOVO_VOTER "QNOVO_VOTER"
#define BATT_PROFILE_VOTER "BATT_PROFILE_VOTER"
#define OTG_DELAY_VOTER "OTG_DELAY_VOTER"
@@ -66,6 +65,8 @@
#define PL_FCC_LOW_VOTER "PL_FCC_LOW_VOTER"
#define WBC_VOTER "WBC_VOTER"
#define HW_LIMIT_VOTER "HW_LIMIT_VOTER"
+#define DYNAMIC_RP_VOTER "DYNAMIC_RP_VOTER"
+#define DEFAULT_100MA_VOTER "DEFAULT_100MA_VOTER"
#define BOOST_BACK_STORM_COUNT 3
#define WEAK_CHG_STORM_COUNT 8
@@ -304,6 +305,7 @@
/* work */
struct work_struct bms_update_work;
struct work_struct pl_update_work;
+ struct work_struct jeita_update_work;
struct delayed_work ps_change_timeout_work;
struct delayed_work clear_hdc_work;
struct delayed_work icl_change_work;
@@ -347,6 +349,7 @@
bool otg_present;
int hw_max_icl_ua;
int auto_recharge_soc;
+ bool jeita_configured;
/* workaround flag */
u32 wa_flags;
diff --git a/drivers/power/supply/qcom/smb5-reg.h b/drivers/power/supply/qcom/smb5-reg.h
index 3334f67..bb28423 100644
--- a/drivers/power/supply/qcom/smb5-reg.h
+++ b/drivers/power/supply/qcom/smb5-reg.h
@@ -101,6 +101,7 @@
#define JEITA_CCCOMP_CFG_HOT_REG (CHGR_BASE + 0x92)
#define JEITA_CCCOMP_CFG_COLD_REG (CHGR_BASE + 0x93)
+#define CHGR_JEITA_THRESHOLD_BASE_REG(i) (CHGR_BASE + 0x94 + (i * 4))
/********************************
* DCDC Peripheral Registers *
********************************/
diff --git a/drivers/pwm/core.c b/drivers/pwm/core.c
index 172ef82..17b808c 100644
--- a/drivers/pwm/core.c
+++ b/drivers/pwm/core.c
@@ -285,6 +285,7 @@
pwm->pwm = chip->base + i;
pwm->hwpwm = i;
pwm->state.polarity = polarity;
+ pwm->state.output_type = PWM_OUTPUT_FIXED;
if (chip->ops->get_state)
chip->ops->get_state(chip, pwm, &pwm->state);
@@ -498,6 +499,31 @@
pwm->state.polarity = state->polarity;
}
+ if (state->output_type != pwm->state.output_type) {
+ if (!pwm->chip->ops->set_output_type)
+ return -ENOTSUPP;
+
+ err = pwm->chip->ops->set_output_type(pwm->chip, pwm,
+ state->output_type);
+ if (err)
+ return err;
+
+ pwm->state.output_type = state->output_type;
+ }
+
+ if (state->output_pattern != pwm->state.output_pattern &&
+ state->output_pattern != NULL) {
+ if (!pwm->chip->ops->set_output_pattern)
+ return -ENOTSUPP;
+
+ err = pwm->chip->ops->set_output_pattern(pwm->chip,
+ pwm, state->output_pattern);
+ if (err)
+ return err;
+
+ pwm->state.output_pattern = state->output_pattern;
+ }
+
if (state->period != pwm->state.period ||
state->duty_cycle != pwm->state.duty_cycle) {
err = pwm->chip->ops->config(pwm->chip, pwm,
diff --git a/drivers/pwm/pwm-qti-lpg.c b/drivers/pwm/pwm-qti-lpg.c
index 85a5ea0..31f5204 100644
--- a/drivers/pwm/pwm-qti-lpg.c
+++ b/drivers/pwm/pwm-qti-lpg.c
@@ -24,11 +24,16 @@
#include <linux/platform_device.h>
#include <linux/pwm.h>
#include <linux/regmap.h>
+#include <linux/slab.h>
#include <linux/types.h>
#define REG_SIZE_PER_LPG 0x100
+#define LPG_BASE "lpg-base"
+#define LUT_BASE "lut-base"
+/* LPG module registers */
#define REG_LPG_PERPH_SUBTYPE 0x05
+#define REG_LPG_PATTERN_CONFIG 0x40
#define REG_LPG_PWM_SIZE_CLK 0x41
#define REG_LPG_PWM_FREQ_PREDIV_CLK 0x42
#define REG_LPG_PWM_TYPE_CONFIG 0x43
@@ -36,16 +41,29 @@
#define REG_LPG_PWM_VALUE_MSB 0x45
#define REG_LPG_ENABLE_CONTROL 0x46
#define REG_LPG_PWM_SYNC 0x47
+#define REG_LPG_RAMP_STEP_DURATION_LSB 0x50
+#define REG_LPG_RAMP_STEP_DURATION_MSB 0x51
+#define REG_LPG_PAUSE_HI_MULTIPLIER 0x52
+#define REG_LPG_PAUSE_LO_MULTIPLIER 0x54
+#define REG_LPG_HI_INDEX 0x56
+#define REG_LPG_LO_INDEX 0x57
+
+/* REG_LPG_PATTERN_CONFIG */
+#define LPG_PATTERN_EN_PAUSE_LO BIT(0)
+#define LPG_PATTERN_EN_PAUSE_HI BIT(1)
+#define LPG_PATTERN_RAMP_TOGGLE BIT(2)
+#define LPG_PATTERN_REPEAT BIT(3)
+#define LPG_PATTERN_RAMP_LO_TO_HI BIT(4)
/* REG_LPG_PERPH_SUBTYPE */
#define SUBTYPE_PWM 0x0b
#define SUBTYPE_LPG_LITE 0x11
/* REG_LPG_PWM_SIZE_CLK */
-#define LPG_PWM_SIZE_MASK_LPG BIT(4)
-#define LPG_PWM_SIZE_MASK_PWM BIT(2)
-#define LPG_PWM_SIZE_SHIFT_LPG 4
-#define LPG_PWM_SIZE_SHIFT_PWM 2
+#define LPG_PWM_SIZE_LPG_MASK BIT(4)
+#define LPG_PWM_SIZE_PWM_MASK BIT(2)
+#define LPG_PWM_SIZE_LPG_SHIFT 4
+#define LPG_PWM_SIZE_PWM_SHIFT 2
#define LPG_PWM_CLK_FREQ_SEL_MASK GENMASK(1, 0)
/* REG_LPG_PWM_FREQ_PREDIV_CLK */
@@ -64,6 +82,7 @@
/* REG_LPG_ENABLE_CONTROL */
#define LPG_EN_LPG_OUT_BIT BIT(7)
+#define LPG_EN_LPG_OUT_SHIFT 7
#define LPG_PWM_SRC_SELECT_MASK BIT(2)
#define LPG_PWM_SRC_SELECT_SHIFT 2
#define LPG_EN_RAMP_GEN_MASK BIT(1)
@@ -77,9 +96,18 @@
#define NUM_CLK_PREDIV 4
#define NUM_PWM_EXP 8
-enum {
+#define LPG_HI_LO_IDX_MASK GENMASK(5, 0)
+
+/* LUT module registers */
+#define REG_LPG_LUT_1_LSB 0x42
+#define REG_LPG_LUT_RAMP_CONTROL 0xc8
+
+#define LPG_LUT_VALUE_MSB_MASK BIT(0)
+#define LPG_LUT_COUNT_MAX 47
+
+enum lpg_src {
LUT_PATTERN = 0,
- PWM_OUTPUT,
+ PWM_VALUE,
};
static const int pwm_size[NUM_PWM_SIZE] = {6, 9};
@@ -87,6 +115,19 @@
static const int clk_prediv[NUM_CLK_PREDIV] = {1, 3, 5, 6};
static const int pwm_exponent[NUM_PWM_EXP] = {0, 1, 2, 3, 4, 5, 6, 7};
+struct lpg_ramp_config {
+ u16 step_ms;
+ u8 pause_hi_count;
+ u8 pause_lo_count;
+ u8 hi_idx;
+ u8 lo_idx;
+ bool ramp_dir_low_to_hi;
+ bool pattern_repeat;
+ bool toggle;
+ u32 *pattern;
+ u32 pattern_length;
+};
+
struct lpg_pwm_config {
u32 pwm_size;
u32 pwm_clk;
@@ -96,13 +137,23 @@
u32 best_period_ns;
};
+struct qpnp_lpg_lut {
+ struct qpnp_lpg_chip *chip;
+ struct mutex lock;
+ u32 reg_base;
+ u32 *pattern; /* patterns in percentage */
+};
+
struct qpnp_lpg_channel {
struct qpnp_lpg_chip *chip;
struct lpg_pwm_config pwm_config;
+ struct lpg_ramp_config ramp_config;
u32 lpg_idx;
u32 reg_base;
+ u32 max_pattern_length;
u8 src_sel;
u8 subtype;
+ bool lut_written;
int current_period_ns;
int current_duty_ns;
};
@@ -112,6 +163,7 @@
struct regmap *regmap;
struct device *dev;
struct qpnp_lpg_channel *lpgs;
+ struct qpnp_lpg_lut *lut;
struct mutex bus_lock;
u32 num_lpgs;
};
@@ -163,6 +215,36 @@
return rc;
}
+static int qpnp_lut_write(struct qpnp_lpg_lut *lut, u16 addr, u8 val)
+{
+ int rc;
+
+ mutex_lock(&lut->chip->bus_lock);
+ rc = regmap_write(lut->chip->regmap, lut->reg_base + addr, val);
+ if (rc < 0)
+ dev_err(lut->chip->dev, "Write addr 0x%x with value %d failed, rc=%d\n",
+ lut->reg_base + addr, val, rc);
+ mutex_unlock(&lut->chip->bus_lock);
+
+ return rc;
+}
+
+static int qpnp_lut_masked_write(struct qpnp_lpg_lut *lut,
+ u16 addr, u8 mask, u8 val)
+{
+ int rc;
+
+ mutex_lock(&lut->chip->bus_lock);
+ rc = regmap_update_bits(lut->chip->regmap, lut->reg_base + addr,
+ mask, val);
+ if (rc < 0)
+ dev_err(lut->chip->dev, "Update addr 0x%x to val 0x%x with mask 0x%x failed, rc=%d\n",
+ lut->reg_base + addr, val, mask, rc);
+ mutex_unlock(&lut->chip->bus_lock);
+
+ return rc;
+}
+
static struct qpnp_lpg_channel *pwm_dev_to_qpnp_lpg(struct pwm_chip *pwm_chip,
struct pwm_device *pwm) {
@@ -227,11 +309,11 @@
/* pwm_clk_idx is 1 bit lower than the register value */
pwm_clk_idx += 1;
if (lpg->subtype == SUBTYPE_PWM) {
- shift = LPG_PWM_SIZE_SHIFT_PWM;
- mask = LPG_PWM_SIZE_MASK_PWM;
+ shift = LPG_PWM_SIZE_PWM_SHIFT;
+ mask = LPG_PWM_SIZE_PWM_MASK;
} else {
- shift = LPG_PWM_SIZE_SHIFT_LPG;
- mask = LPG_PWM_SIZE_MASK_LPG;
+ shift = LPG_PWM_SIZE_LPG_SHIFT;
+ mask = LPG_PWM_SIZE_LPG_MASK;
}
val = pwm_size_idx << shift | pwm_clk_idx;
@@ -252,6 +334,9 @@
return rc;
}
+ if (lpg->src_sel == LUT_PATTERN)
+ return 0;
+
val = lpg->pwm_config.pwm_value & LPG_PWM_VALUE_LSB_MASK;
rc = qpnp_lpg_write(lpg, REG_LPG_PWM_VALUE_LSB, val);
if (rc < 0) {
@@ -280,6 +365,145 @@
return rc;
}
+static int qpnp_lpg_set_lut_pattern(struct qpnp_lpg_channel *lpg,
+ unsigned int *pattern, unsigned int length)
+{
+ struct qpnp_lpg_lut *lut = lpg->chip->lut;
+ int i, rc = 0;
+ u16 full_duty_value, pwm_values[LPG_LUT_COUNT_MAX + 1] = {0};
+ u8 lsb, msb, addr;
+
+ if (length > lpg->max_pattern_length) {
+ dev_err(lpg->chip->dev, "new pattern length (%d) larger than predefined (%d)\n",
+ length, lpg->max_pattern_length);
+ return -EINVAL;
+ }
+
+ /* Program LUT pattern */
+ mutex_lock(&lut->lock);
+ addr = REG_LPG_LUT_1_LSB + lpg->ramp_config.lo_idx * 2;
+ for (i = 0; i < length; i++) {
+ full_duty_value = 1 << lpg->pwm_config.pwm_size;
+ pwm_values[i] = pattern[i] * full_duty_value / 100;
+
+ if (unlikely(pwm_values[i] > full_duty_value)) {
+ dev_err(lpg->chip->dev, "PWM value %d exceed the max %d\n",
+ pwm_values[i], full_duty_value);
+ rc = -EINVAL;
+ goto unlock;
+ }
+
+ if (pwm_values[i] == full_duty_value)
+ pwm_values[i] = full_duty_value - 1;
+
+ lsb = pwm_values[i] & 0xff;
+ msb = pwm_values[i] >> 8;
+ rc = qpnp_lut_write(lut, addr++, lsb);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write NO.%d LUT pattern LSB (%d) failed, rc=%d",
+ i, lsb, rc);
+ goto unlock;
+ }
+
+ rc = qpnp_lut_masked_write(lut, addr++,
+ LPG_LUT_VALUE_MSB_MASK, msb);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write NO.%d LUT pattern MSB (%d) failed, rc=%d",
+ i, msb, rc);
+ goto unlock;
+ }
+ }
+ lpg->ramp_config.pattern_length = length;
+unlock:
+ mutex_unlock(&lut->lock);
+
+ return rc;
+}
+
+static int qpnp_lpg_set_ramp_config(struct qpnp_lpg_channel *lpg)
+{
+ struct lpg_ramp_config *ramp = &lpg->ramp_config;
+ u8 lsb, msb, addr, mask, val;
+ int rc = 0;
+
+ /* Set ramp step duration */
+ lsb = ramp->step_ms & 0xff;
+ msb = ramp->step_ms >> 8;
+ addr = REG_LPG_RAMP_STEP_DURATION_LSB;
+ rc = qpnp_lpg_write(lpg, addr, lsb);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write RAMP_STEP_DURATION_LSB failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+ rc = qpnp_lpg_write(lpg, addr + 1, msb);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write RAMP_STEP_DURATION_MSB failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ /* Set hi_idx and lo_idx */
+ rc = qpnp_lpg_masked_write(lpg, REG_LPG_HI_INDEX,
+ LPG_HI_LO_IDX_MASK, ramp->hi_idx);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write LPG_HI_IDX failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ rc = qpnp_lpg_masked_write(lpg, REG_LPG_LO_INDEX,
+ LPG_HI_LO_IDX_MASK, ramp->lo_idx);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write LPG_LO_IDX failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ /* Set pause_hi/lo_count */
+ rc = qpnp_lpg_write(lpg, REG_LPG_PAUSE_HI_MULTIPLIER,
+ ramp->pause_hi_count);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write LPG_PAUSE_HI_MULTIPLIER failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ rc = qpnp_lpg_write(lpg, REG_LPG_PAUSE_LO_MULTIPLIER,
+ ramp->pause_lo_count);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write LPG_PAUSE_LO_MULTIPLIER failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ /* Set LPG_PATTERN_CONFIG */
+ addr = REG_LPG_PATTERN_CONFIG;
+ mask = LPG_PATTERN_EN_PAUSE_LO | LPG_PATTERN_EN_PAUSE_HI
+ | LPG_PATTERN_RAMP_TOGGLE | LPG_PATTERN_REPEAT
+ | LPG_PATTERN_RAMP_LO_TO_HI;
+ val = 0;
+ if (ramp->pause_lo_count != 0)
+ val |= LPG_PATTERN_EN_PAUSE_LO;
+ if (ramp->pause_hi_count != 0)
+ val |= LPG_PATTERN_EN_PAUSE_HI;
+ if (ramp->ramp_dir_low_to_hi)
+ val |= LPG_PATTERN_RAMP_LO_TO_HI;
+ if (ramp->pattern_repeat)
+ val |= LPG_PATTERN_REPEAT;
+ if (ramp->toggle)
+ val |= LPG_PATTERN_RAMP_TOGGLE;
+
+ rc = qpnp_lpg_masked_write(lpg, addr, mask, val);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Write LPG_PATTERN_CONFIG failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ return rc;
+}
+
static void __qpnp_lpg_calc_pwm_period(int period_ns,
struct lpg_pwm_config *pwm_config)
{
@@ -396,17 +620,202 @@
return -EINVAL;
}
- if (period_ns != lpg->current_period_ns)
+ if (period_ns != lpg->current_period_ns) {
__qpnp_lpg_calc_pwm_period(period_ns, &lpg->pwm_config);
+ /* program LUT if PWM period is changed */
+ if (lpg->src_sel == LUT_PATTERN) {
+ rc = qpnp_lpg_set_lut_pattern(lpg,
+ lpg->ramp_config.pattern,
+ lpg->ramp_config.pattern_length);
+ if (rc < 0) {
+ dev_err(pwm_chip->dev, "set LUT pattern failed for LPG%d, rc=%d\n",
+ lpg->lpg_idx, rc);
+ return rc;
+ }
+ lpg->lut_written = true;
+ }
+ }
+
if (period_ns != lpg->current_period_ns ||
duty_ns != lpg->current_duty_ns)
__qpnp_lpg_calc_pwm_duty(period_ns, duty_ns, &lpg->pwm_config);
rc = qpnp_lpg_set_pwm_config(lpg);
- if (rc < 0)
+ if (rc < 0) {
dev_err(pwm_chip->dev, "Config PWM failed for channel %d, rc=%d\n",
lpg->lpg_idx, rc);
+ return rc;
+ }
+
+ lpg->current_period_ns = period_ns;
+ lpg->current_duty_ns = duty_ns;
+
+ return rc;
+}
+
+static int qpnp_lpg_pwm_src_enable(struct qpnp_lpg_channel *lpg, bool en)
+{
+ struct qpnp_lpg_chip *chip = lpg->chip;
+ struct qpnp_lpg_lut *lut = chip->lut;
+ u8 mask, val;
+ int rc;
+
+ mask = LPG_PWM_SRC_SELECT_MASK | LPG_EN_LPG_OUT_BIT |
+ LPG_EN_RAMP_GEN_MASK;
+ val = lpg->src_sel << LPG_PWM_SRC_SELECT_SHIFT;
+
+ if (lpg->src_sel == LUT_PATTERN)
+ val |= 1 << LPG_EN_RAMP_GEN_SHIFT;
+
+ if (en)
+ val |= 1 << LPG_EN_LPG_OUT_SHIFT;
+
+ rc = qpnp_lpg_masked_write(lpg, REG_LPG_ENABLE_CONTROL, mask, val);
+ if (rc < 0) {
+ dev_err(chip->dev, "Write LPG_ENABLE_CONTROL failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ if (lpg->src_sel == LUT_PATTERN && en) {
+ mutex_lock(&lut->lock);
+ val = 1 << lpg->lpg_idx;
+ rc = qpnp_lut_write(lut, REG_LPG_LUT_RAMP_CONTROL, val);
+ if (rc < 0)
+ dev_err(chip->dev, "Write LPG_LUT_RAMP_CONTROL failed, rc=%d\n",
+ rc);
+ mutex_unlock(&lut->lock);
+ }
+
+ return rc;
+}
+
+static int qpnp_lpg_pwm_set_output_type(struct pwm_chip *pwm_chip,
+ struct pwm_device *pwm, enum pwm_output_type output_type)
+{
+ struct qpnp_lpg_channel *lpg;
+ enum lpg_src src_sel;
+ int rc;
+
+ lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
+ if (lpg == NULL) {
+ dev_err(pwm_chip->dev, "lpg not found\n");
+ return -ENODEV;
+ }
+
+ if (lpg->chip->lut == NULL) {
+ pr_debug("lpg%d only support PWM mode\n", lpg->lpg_idx);
+ return 0;
+ }
+
+ src_sel = (output_type == PWM_OUTPUT_MODULATED) ?
+ LUT_PATTERN : PWM_VALUE;
+ if (src_sel == lpg->src_sel)
+ return 0;
+
+ if (src_sel == LUT_PATTERN) {
+ /* program LUT if it's never been programmed */
+ if (!lpg->lut_written) {
+ rc = qpnp_lpg_set_lut_pattern(lpg,
+ lpg->ramp_config.pattern,
+ lpg->ramp_config.pattern_length);
+ if (rc < 0) {
+ dev_err(pwm_chip->dev, "set LUT pattern failed for LPG%d, rc=%d\n",
+ lpg->lpg_idx, rc);
+ return rc;
+ }
+ lpg->lut_written = true;
+ }
+
+ rc = qpnp_lpg_set_ramp_config(lpg);
+ if (rc < 0) {
+ dev_err(pwm_chip->dev, "Config LPG%d ramping failed, rc=%d\n",
+ lpg->lpg_idx, rc);
+ return rc;
+ }
+ }
+
+ lpg->src_sel = src_sel;
+
+ if (pwm_is_enabled(pwm)) {
+ rc = qpnp_lpg_pwm_src_enable(lpg, true);
+ if (rc < 0) {
+ dev_err(pwm_chip->dev, "Enable PWM output failed for channel %d, rc=%d\n",
+ lpg->lpg_idx, rc);
+ return rc;
+ }
+ }
+
+ return 0;
+}
+
+static int qpnp_lpg_pwm_set_output_pattern(struct pwm_chip *pwm_chip,
+ struct pwm_device *pwm, struct pwm_output_pattern *output_pattern)
+{
+ struct qpnp_lpg_channel *lpg;
+ int rc = 0, i, period_ns, duty_ns;
+ u32 *percentages;
+
+ lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
+ if (lpg == NULL) {
+ dev_err(pwm_chip->dev, "lpg not found\n");
+ return -ENODEV;
+ }
+
+ if (output_pattern->num_entries > lpg->max_pattern_length) {
+ dev_err(lpg->chip->dev, "pattern length %d shouldn't exceed %d\n",
+ output_pattern->num_entries,
+ lpg->max_pattern_length);
+ return -EINVAL;
+ }
+
+ percentages = kcalloc(output_pattern->num_entries,
+ sizeof(u32), GFP_KERNEL);
+ if (!percentages)
+ return -ENOMEM;
+
+ period_ns = pwm_get_period(pwm);
+ for (i = 0; i < output_pattern->num_entries; i++) {
+ duty_ns = output_pattern->duty_pattern[i];
+ if (duty_ns > period_ns) {
+ dev_err(lpg->chip->dev, "duty %dns is larger than period %dns\n",
+ duty_ns, period_ns);
+ goto err;
+ }
+ /* Translate the pattern in duty_ns to percentage */
+ if ((INT_MAX / duty_ns) < 100)
+ percentages[i] = duty_ns / (period_ns / 100);
+ else
+ percentages[i] = (duty_ns * 100) / period_ns;
+ }
+
+ rc = qpnp_lpg_set_lut_pattern(lpg, percentages,
+ output_pattern->num_entries);
+ if (rc < 0) {
+ dev_err(lpg->chip->dev, "Set LUT pattern failed for LPG%d, rc=%d\n",
+ lpg->lpg_idx, rc);
+ goto err;
+ }
+
+ lpg->lut_written = true;
+ memcpy(lpg->ramp_config.pattern, percentages,
+ output_pattern->num_entries);
+ lpg->ramp_config.hi_idx = lpg->ramp_config.lo_idx +
+ output_pattern->num_entries - 1;
+ if ((INT_MAX / period_ns) > output_pattern->cycles_per_duty)
+ lpg->ramp_config.step_ms = output_pattern->cycles_per_duty *
+ period_ns / NSEC_PER_MSEC;
+ else
+ lpg->ramp_config.step_ms = (period_ns / NSEC_PER_MSEC) *
+ output_pattern->cycles_per_duty;
+
+ rc = qpnp_lpg_set_ramp_config(lpg);
+ if (rc < 0)
+ dev_err(pwm_chip->dev, "Config LPG%d ramping failed, rc=%d\n",
+ lpg->lpg_idx, rc);
+err:
+ kfree(percentages);
return rc;
}
@@ -416,7 +825,6 @@
{
struct qpnp_lpg_channel *lpg;
int rc = 0;
- u8 mask, val;
lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
if (lpg == NULL) {
@@ -431,10 +839,7 @@
return rc;
}
- mask = LPG_PWM_SRC_SELECT_MASK | LPG_EN_LPG_OUT_BIT;
- val = lpg->src_sel << LPG_PWM_SRC_SELECT_SHIFT | LPG_EN_LPG_OUT_BIT;
-
- rc = qpnp_lpg_masked_write(lpg, REG_LPG_ENABLE_CONTROL, mask, val);
+ rc = qpnp_lpg_pwm_src_enable(lpg, true);
if (rc < 0)
dev_err(pwm_chip->dev, "Enable PWM output failed for channel %d, rc=%d\n",
lpg->lpg_idx, rc);
@@ -447,7 +852,6 @@
{
struct qpnp_lpg_channel *lpg;
int rc;
- u8 mask, val;
lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
if (lpg == NULL) {
@@ -455,10 +859,7 @@
return;
}
- mask = LPG_PWM_SRC_SELECT_MASK | LPG_EN_LPG_OUT_BIT;
- val = lpg->src_sel << LPG_PWM_SRC_SELECT_SHIFT;
-
- rc = qpnp_lpg_masked_write(lpg, REG_LPG_ENABLE_CONTROL, mask, val);
+ rc = qpnp_lpg_pwm_src_enable(lpg, false);
if (rc < 0) {
dev_err(pwm_chip->dev, "Disable PWM output failed for channel %d, rc=%d\n",
lpg->lpg_idx, rc);
@@ -471,13 +872,32 @@
rc);
}
+static int qpnp_lpg_pwm_output_types_supported(struct pwm_chip *pwm_chip,
+ struct pwm_device *pwm)
+{
+ enum pwm_output_type type = PWM_OUTPUT_FIXED;
+ struct qpnp_lpg_channel *lpg;
+
+ lpg = pwm_dev_to_qpnp_lpg(pwm_chip, pwm);
+ if (lpg == NULL) {
+ dev_err(pwm_chip->dev, "lpg not found\n");
+ return type;
+ }
+
+ if (lpg->chip->lut != NULL)
+ type |= PWM_OUTPUT_MODULATED;
+
+ return type;
+}
+
#ifdef CONFIG_DEBUG_FS
static void qpnp_lpg_pwm_dbg_show(struct pwm_chip *pwm_chip, struct seq_file *s)
{
struct qpnp_lpg_channel *lpg;
struct lpg_pwm_config *cfg;
+ struct lpg_ramp_config *ramp;
struct pwm_device *pwm;
- int i;
+ int i, j;
for (i = 0; i < pwm_chip->npwm; i++) {
pwm = &pwm_chip->pwms[i];
@@ -512,12 +932,39 @@
seq_printf(s, " pwm_value = %d\n", cfg->pwm_value);
seq_printf(s, " Requested period: %dns, best period = %dns\n",
pwm_get_period(pwm), cfg->best_period_ns);
+
+ ramp = &lpg->ramp_config;
+ if (pwm_get_output_type(pwm) == PWM_OUTPUT_MODULATED) {
+ seq_puts(s, " ramping duty percentages:");
+ for (j = 0; j < ramp->pattern_length; j++)
+ seq_printf(s, " %d", ramp->pattern[j]);
+ seq_puts(s, "\n");
+ seq_printf(s, " ramping time per step: %dms\n",
+ ramp->step_ms);
+ seq_printf(s, " ramping low index: %d\n",
+ ramp->lo_idx);
+ seq_printf(s, " ramping high index: %d\n",
+ ramp->hi_idx);
+ seq_printf(s, " ramping from low to high: %d\n",
+ ramp->ramp_dir_low_to_hi);
+ seq_printf(s, " ramping pattern repeat: %d\n",
+ ramp->pattern_repeat);
+ seq_printf(s, " ramping toggle: %d\n",
+ ramp->toggle);
+ seq_printf(s, " ramping pause count at low index: %d\n",
+ ramp->pause_lo_count);
+ seq_printf(s, " ramping pause count at high index: %d\n",
+ ramp->pause_hi_count);
+ }
}
}
#endif
static const struct pwm_ops qpnp_lpg_pwm_ops = {
.config = qpnp_lpg_pwm_config,
+ .get_output_type_supported = qpnp_lpg_pwm_output_types_supported,
+ .set_output_type = qpnp_lpg_pwm_set_output_type,
+ .set_output_pattern = qpnp_lpg_pwm_set_output_pattern,
.enable = qpnp_lpg_pwm_enable,
.disable = qpnp_lpg_pwm_disable,
#ifdef CONFIG_DEBUG_FS
@@ -528,15 +975,19 @@
static int qpnp_lpg_parse_dt(struct qpnp_lpg_chip *chip)
{
+ struct device_node *child;
+ struct qpnp_lpg_channel *lpg;
+ struct lpg_ramp_config *ramp;
int rc = 0, i;
- u64 base, length;
+ u32 base, length, lpg_chan_id, tmp;
const __be32 *addr;
addr = of_get_address(chip->dev->of_node, 0, NULL, NULL);
if (!addr) {
- dev_err(chip->dev, "Getting address failed\n");
+ dev_err(chip->dev, "Get %s address failed\n", LPG_BASE);
return -EINVAL;
}
+
base = be32_to_cpu(addr[0]);
length = be32_to_cpu(addr[1]);
@@ -550,7 +1001,7 @@
chip->lpgs[i].chip = chip;
chip->lpgs[i].lpg_idx = i;
chip->lpgs[i].reg_base = base + i * REG_SIZE_PER_LPG;
- chip->lpgs[i].src_sel = PWM_OUTPUT;
+ chip->lpgs[i].src_sel = PWM_VALUE;
rc = qpnp_lpg_read(&chip->lpgs[i], REG_LPG_PERPH_SUBTYPE,
&chip->lpgs[i].subtype);
if (rc < 0) {
@@ -559,7 +1010,142 @@
}
}
- return rc;
+ addr = of_get_address(chip->dev->of_node, 1, NULL, NULL);
+ if (!addr) {
+ pr_debug("NO LUT address assigned\n");
+ return 0;
+ }
+
+ chip->lut = devm_kmalloc(chip->dev, sizeof(*chip->lut), GFP_KERNEL);
+ if (!chip->lut)
+ return -ENOMEM;
+
+ chip->lut->chip = chip;
+ chip->lut->reg_base = be32_to_cpu(*addr);
+ mutex_init(&chip->lut->lock);
+
+ rc = of_property_count_elems_of_size(chip->dev->of_node,
+ "qcom,lut-patterns", sizeof(u32));
+ if (rc < 0) {
+ dev_err(chip->dev, "Read qcom,lut-patterns failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ length = rc;
+ if (length > LPG_LUT_COUNT_MAX) {
+ dev_err(chip->dev, "qcom,lut-patterns length %d exceed max %d\n",
+ length, LPG_LUT_COUNT_MAX);
+ return -EINVAL;
+ }
+
+ chip->lut->pattern = devm_kcalloc(chip->dev, LPG_LUT_COUNT_MAX,
+ sizeof(*chip->lut->pattern), GFP_KERNEL);
+ if (!chip->lut->pattern)
+ return -ENOMEM;
+
+ rc = of_property_read_u32_array(chip->dev->of_node, "qcom,lut-patterns",
+ chip->lut->pattern, length);
+ if (rc < 0) {
+ dev_err(chip->dev, "Get qcom,lut-patterns failed, rc=%d\n",
+ rc);
+ return rc;
+ }
+
+ if (of_get_available_child_count(chip->dev->of_node) == 0) {
+ dev_err(chip->dev, "No ramp configuration for any LPG\n");
+ return -EINVAL;
+ }
+
+ for_each_available_child_of_node(chip->dev->of_node, child) {
+ rc = of_property_read_u32(child, "qcom,lpg-chan-id",
+ &lpg_chan_id);
+ if (rc < 0) {
+ dev_err(chip->dev, "Get qcom,lpg-chan-id failed for node %s, rc=%d\n",
+ child->name, rc);
+ return rc;
+ }
+
+ if (lpg_chan_id > chip->num_lpgs) {
+ dev_err(chip->dev, "lpg-chann-id %d is out of range 1~%d\n",
+ lpg_chan_id, chip->num_lpgs);
+ return -EINVAL;
+ }
+
+ /* lpg channel id is indexed from 1 in hardware */
+ lpg = &chip->lpgs[lpg_chan_id - 1];
+ ramp = &lpg->ramp_config;
+
+ rc = of_property_read_u32(child, "qcom,ramp-step-ms", &tmp);
+ if (rc < 0) {
+ dev_err(chip->dev, "get qcom,ramp-step-ms failed for lpg%d, rc=%d\n",
+ lpg_chan_id, rc);
+ return rc;
+ }
+ ramp->step_ms = (u16)tmp;
+
+ rc = of_property_read_u32(child, "qcom,ramp-low-index", &tmp);
+ if (rc < 0) {
+ dev_err(chip->dev, "get qcom,ramp-low-index failed for lpg%d, rc=%d\n",
+ lpg_chan_id, rc);
+ return rc;
+ }
+ ramp->lo_idx = (u8)tmp;
+ if (ramp->lo_idx >= LPG_LUT_COUNT_MAX) {
+ dev_err(chip->dev, "qcom,ramp-low-index should less than max %d\n",
+ LPG_LUT_COUNT_MAX);
+ return -EINVAL;
+ }
+
+ rc = of_property_read_u32(child, "qcom,ramp-high-index", &tmp);
+ if (rc < 0) {
+ dev_err(chip->dev, "get qcom,ramp-high-index failed for lpg%d, rc=%d\n",
+ lpg_chan_id, rc);
+ return rc;
+ }
+ ramp->hi_idx = (u8)tmp;
+
+ if (ramp->hi_idx > LPG_LUT_COUNT_MAX) {
+ dev_err(chip->dev, "qcom,ramp-high-index shouldn't exceed max %d\n",
+ LPG_LUT_COUNT_MAX);
+ return -EINVAL;
+ }
+
+ if (ramp->hi_idx <= ramp->lo_idx) {
+ dev_err(chip->dev, "high-index(%d) should be larger than low-index(%d)\n",
+ ramp->hi_idx, ramp->lo_idx);
+ return -EINVAL;
+ }
+
+ ramp->pattern_length = ramp->hi_idx - ramp->lo_idx + 1;
+ ramp->pattern = &chip->lut->pattern[ramp->lo_idx];
+ lpg->max_pattern_length = ramp->pattern_length;
+
+ rc = of_property_read_u32(child,
+ "qcom,ramp-pause-hi-count", &tmp);
+ if (rc < 0)
+ ramp->pause_hi_count = 0;
+ else
+ ramp->pause_hi_count = (u8)tmp;
+
+ rc = of_property_read_u32(child,
+ "qcom,ramp-pause-lo-count", &tmp);
+ if (rc < 0)
+ ramp->pause_lo_count = 0;
+ else
+ ramp->pause_lo_count = (u8)tmp;
+
+ ramp->ramp_dir_low_to_hi = of_property_read_bool(child,
+ "qcom,ramp-from-low-to-high");
+
+ ramp->pattern_repeat = of_property_read_bool(child,
+ "qcom,ramp-pattern-repeat");
+
+ ramp->toggle = of_property_read_bool(child,
+ "qcom,ramp-toggle");
+ }
+
+ return 0;
}
static int qpnp_lpg_probe(struct platform_device *pdev)
@@ -583,7 +1169,7 @@
if (rc < 0) {
dev_err(chip->dev, "Devicetree properties parsing failed, rc=%d\n",
rc);
- goto destroy;
+ goto err_out;
}
dev_set_drvdata(chip->dev, chip);
@@ -595,11 +1181,11 @@
rc = pwmchip_add(&chip->pwm_chip);
if (rc < 0) {
dev_err(chip->dev, "Add pwmchip failed, rc=%d\n", rc);
- goto destroy;
+ goto err_out;
}
return 0;
-destroy:
+err_out:
mutex_destroy(&chip->bus_lock);
return rc;
}
diff --git a/drivers/pwm/sysfs.c b/drivers/pwm/sysfs.c
index a813239..ea2b53d 100644
--- a/drivers/pwm/sysfs.c
+++ b/drivers/pwm/sysfs.c
@@ -223,11 +223,60 @@
return sprintf(buf, "%u %u\n", result.period, result.duty_cycle);
}
+static ssize_t output_type_show(struct device *child,
+ struct device_attribute *attr,
+ char *buf)
+{
+ const struct pwm_device *pwm = child_to_pwm_device(child);
+ const char *output_type = "unknown";
+ struct pwm_state state;
+
+ pwm_get_state(pwm, &state);
+ switch (state.output_type) {
+ case PWM_OUTPUT_FIXED:
+ output_type = "fixed";
+ break;
+ case PWM_OUTPUT_MODULATED:
+ output_type = "modulated";
+ break;
+ default:
+ break;
+ }
+
+ return snprintf(buf, PAGE_SIZE, "%s\n", output_type);
+}
+
+static ssize_t output_type_store(struct device *child,
+ struct device_attribute *attr,
+ const char *buf, size_t size)
+{
+ struct pwm_export *export = child_to_pwm_export(child);
+ struct pwm_device *pwm = export->pwm;
+ struct pwm_state state;
+ int ret = -EINVAL;
+
+ mutex_lock(&export->lock);
+ pwm_get_state(pwm, &state);
+ if (sysfs_streq(buf, "fixed"))
+ state.output_type = PWM_OUTPUT_FIXED;
+ else if (sysfs_streq(buf, "modulated"))
+ state.output_type = PWM_OUTPUT_MODULATED;
+ else
+ goto unlock;
+
+ ret = pwm_apply_state(pwm, &state);
+unlock:
+ mutex_unlock(&export->lock);
+
+ return ret ? : size;
+}
+
static DEVICE_ATTR_RW(period);
static DEVICE_ATTR_RW(duty_cycle);
static DEVICE_ATTR_RW(enable);
static DEVICE_ATTR_RW(polarity);
static DEVICE_ATTR_RO(capture);
+static DEVICE_ATTR_RW(output_type);
static struct attribute *pwm_attrs[] = {
&dev_attr_period.attr,
@@ -235,6 +284,7 @@
&dev_attr_enable.attr,
&dev_attr_polarity.attr,
&dev_attr_capture.attr,
+ &dev_attr_output_type.attr,
NULL
};
ATTRIBUTE_GROUPS(pwm);
diff --git a/drivers/regulator/qpnp-lcdb-regulator.c b/drivers/regulator/qpnp-lcdb-regulator.c
index 79d7cba..07a6198 100644
--- a/drivers/regulator/qpnp-lcdb-regulator.c
+++ b/drivers/regulator/qpnp-lcdb-regulator.c
@@ -991,7 +991,8 @@
}
#define MIN_BST_VOLTAGE_MV 4700
-#define MAX_BST_VOLTAGE_MV 6250
+#define PM660_MAX_BST_VOLTAGE_MV 6250
+#define MAX_BST_VOLTAGE_MV 6275
#define MIN_VOLTAGE_MV 4000
#define MAX_VOLTAGE_MV 6000
#define VOLTAGE_MIN_STEP_100_MV 4000
@@ -1017,8 +1018,14 @@
if (bst_voltage_mv < MIN_BST_VOLTAGE_MV)
bst_voltage_mv = MIN_BST_VOLTAGE_MV;
- else if (bst_voltage_mv > MAX_BST_VOLTAGE_MV)
- bst_voltage_mv = MAX_BST_VOLTAGE_MV;
+
+ if (pmic_subtype == PM660L_SUBTYPE) {
+ if (bst_voltage_mv > PM660_MAX_BST_VOLTAGE_MV)
+ bst_voltage_mv = PM660_MAX_BST_VOLTAGE_MV;
+ } else {
+ if (bst_voltage_mv > MAX_BST_VOLTAGE_MV)
+ bst_voltage_mv = MAX_BST_VOLTAGE_MV;
+ }
if (bst_voltage_mv != bst->voltage_mv) {
if (pmic_subtype == PM660L_SUBTYPE) {
@@ -1883,6 +1890,8 @@
return rc;
}
lcdb->bst.soft_start_us = (val & SOFT_START_MASK) * 200 + 200;
+ if (!lcdb->bst.headroom_mv)
+ lcdb->bst.headroom_mv = PM660_BST_HEADROOM_DEFAULT_MV;
} else {
rc = qpnp_lcdb_read(lcdb, lcdb->base +
LCDB_BST_SS_CTL_REG, &val, 1);
@@ -1891,6 +1900,8 @@
return rc;
}
lcdb->bst.soft_start_us = soft_start_us[val & SOFT_START_MASK];
+ if (!lcdb->bst.headroom_mv)
+ lcdb->bst.headroom_mv = BST_HEADROOM_DEFAULT_MV;
}
return 0;
diff --git a/drivers/scsi/ufs/ufs-qcom.c b/drivers/scsi/ufs/ufs-qcom.c
index 46c8268..39ab28a 100644
--- a/drivers/scsi/ufs/ufs-qcom.c
+++ b/drivers/scsi/ufs/ufs-qcom.c
@@ -2499,7 +2499,7 @@
int ufs_qcom_testbus_config(struct ufs_qcom_host *host)
{
int reg = 0;
- int offset, ret = 0, testbus_sel_offset = 19;
+ int offset = -1, ret = 0, testbus_sel_offset = 19;
u32 mask = TEST_BUS_SUB_SEL_MASK;
unsigned long flags;
struct ufs_hba *hba;
@@ -2564,6 +2564,12 @@
* is legal
*/
}
+ if (offset < 0) {
+ dev_err(hba->dev, "%s: Bad offset: %d\n", __func__, offset);
+ ret = -EINVAL;
+ spin_unlock_irqrestore(hba->host->host_lock, flags);
+ goto out;
+ }
mask <<= offset;
spin_unlock_irqrestore(hba->host->host_lock, flags);
diff --git a/drivers/soc/qcom/Kconfig b/drivers/soc/qcom/Kconfig
index 4e412497..5fafaca 100644
--- a/drivers/soc/qcom/Kconfig
+++ b/drivers/soc/qcom/Kconfig
@@ -386,8 +386,8 @@
configured separately.
config MSM_TZ_SMMU
- depends on ARCH_MSM8953 || ARCH_MSM8909
bool "Helper functions for SMMU configuration through TZ"
+ default n
help
Say 'Y' here for targets that need to call into TZ to configure
SMMUs for any reason (for example, for errata workarounds or
@@ -558,6 +558,14 @@
It also notifies userspace of transitions between these states via
sysfs.
+config MSM_SYSMON_COMM
+ bool "MSM System Monitor communication support"
+ depends on MSM_SMD && MSM_SUBSYSTEM_RESTART
+ help
+ This option adds support for MSM System Monitor library, which
+ provides an API that may be used for notifying subsystems within
+ the SoC about other subsystems' power-up/down state-changes.
+
config MSM_PIL
bool "Peripheral image loading"
select FW_LOADER
@@ -813,4 +821,50 @@
provides a means to support more logical channels
via muxing than BAM could without muxing.
+ config MSM_GLINK_BGCOM_XPRT
+ depends on MSM_GLINK
+ depends on MSM_BGCOM
+ tristate "Generic Link (G-Link) BGCOM Transport"
+ help
+ G-Link BGCOM Transport is a Transport plug-in developed over BGCOM.
+ This transport plug-in performs marshaling of G-Link
+ commands & data to the appropriate BGCOM format and
+ allows for G-Link communication with remote subsystems that are
+ external to the System-on-Chip.
+
+ config MSM_BGCOM_INTERFACE
+ bool "Driver support for Blackghost Communication"
+ depends on MSM_BGCOM
+ help
+ Create a bg_com_dev device node for user space communication.
+ Single user space client can open device node for communication
+ from hardware. Hardware will provide access to read
+ registers and read/write AHB memory in the device.
+
+ config MSM_BGRSB
+ bool "Provide support for rsb events on Blackghost chipset"
+ depends on MSM_GLINK
+ help
+ BGRSB communicates to BG over Glink for RSB configuration and
+ enable/disable on device power state change. It enables/disables
+ the regulator specific to RSB. Sends the side band events generated
+ by BG to input framework.
+
+ config MSM_PIL_SSR_BG
+ tristate "MSM Subsystem Blackghost(BG) Support"
+ depends on MSM_PIL && MSM_SUBSYSTEM_RESTART
+ help
+ Support for booting and shutting down Blackghost(BG) SOC which is
+ an external SOC. This driver communicates with Blackghost(BG) SOC
+ via pair of IPC GPIOs for inward and outward signals between MSM
+ and Blackghost(BG) SOC.
+
+ config MSM_BGCOM
+ bool "Provide APIs to communicate with Blackghost chipset"
+ help
+ BGCOM is a thin layer above SPI. It is used whithin a SoC for
+ communication between G-Link/bg_com_dev and BG processor over SPI.
+ This handle the interrupts raised by BG and notify the G-link with
+ interrupt event and event data.
+
source "drivers/soc/qcom/wcnss/Kconfig"
diff --git a/drivers/soc/qcom/Makefile b/drivers/soc/qcom/Makefile
index c7c7f62..5edf3b8 100644
--- a/drivers/soc/qcom/Makefile
+++ b/drivers/soc/qcom/Makefile
@@ -37,6 +37,7 @@
obj-$(CONFIG_MSM_GLINK) += glink.o glink_debugfs.o glink_ssr.o
obj-$(CONFIG_MSM_TZ_SMMU) += msm_tz_smmu.o
obj-$(CONFIG_MSM_GLINK_LOOPBACK_SERVER) += glink_loopback_server.o
+obj-$(CONFIG_MSM_GLINK_BGCOM_XPRT) += glink_bgcom_xprt.o
obj-$(CONFIG_MSM_GLINK_SMEM_NATIVE_XPRT) += glink_smem_native_xprt.o
obj-$(CONFIG_MSM_GLINK_SPI_XPRT) += glink_spi_xprt.o
obj-$(CONFIG_MSM_SPCOM) += spcom.o
@@ -67,7 +68,9 @@
obj-$(CONFIG_MEM_SHARE_QMI_SERVICE) += memshare/
obj-$(CONFIG_MSM_PIL) += peripheral-loader.o
obj-$(CONFIG_MSM_PIL_SSR_GENERIC) += subsys-pil-tz.o
+obj-$(CONFIG_MSM_PIL_SSR_BG) += subsys-pil-bg.o
obj-$(CONFIG_MSM_PIL_MSS_QDSP6V5) += pil-q6v5.o pil-msa.o pil-q6v5-mss.o
+obj-$(CONFIG_MSM_BGCOM) += bgcom_spi.o
obj-$(CONFIG_MSM_PERFORMANCE) += msm_performance.o
@@ -77,6 +80,9 @@
obj-y += ramdump.o
obj-y += microdump_collector.o
endif
+obj-$(CONFIG_MSM_SYSMON_COMM) += sysmon.o sysmon-qmi.o
+obj-$(CONFIG_MSM_BGRSB) += bg_rsb.o
+obj-$(CONFIG_MSM_BGCOM_INTERFACE) += bgcom_interface.o
obj-$(CONFIG_MSM_JTAGV8) += jtagv8.o jtagv8-etm.o
obj-$(CONFIG_QCOM_COMMAND_DB) += cmd-db.o
obj-$(CONFIG_MSM_QBT1000) += qbt1000.o
diff --git a/drivers/soc/qcom/bg_rsb.c b/drivers/soc/qcom/bg_rsb.c
new file mode 100644
index 0000000..fdfd7b7
--- /dev/null
+++ b/drivers/soc/qcom/bg_rsb.c
@@ -0,0 +1,1037 @@
+/* Copyright (c) 2017-2018, 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.
+ *
+ */
+
+#define pr_fmt(msg) "bgrsb: %s: " msg, __func__
+
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/device.h>
+#include <linux/mutex.h>
+#include <linux/platform_device.h>
+#include <soc/qcom/glink.h>
+#include <linux/input.h>
+#include <linux/delay.h>
+#include <linux/wait.h>
+#include <linux/sched.h>
+#include <linux/regulator/consumer.h>
+#include <soc/qcom/subsystem_restart.h>
+#include <soc/qcom/subsystem_notif.h>
+
+#include "bgrsb.h"
+
+#define BGRSB_GLINK_INTENT_SIZE 0x04
+#define BGRSB_MSG_SIZE 0x08
+#define TIMEOUT_MS 500
+
+#define BGRSB_LDO15_VTG_MIN_UV 3300000
+#define BGRSB_LDO15_VTG_MAX_UV 3300000
+
+#define BGRSB_LDO11_VTG_MIN_UV 1800000
+#define BGRSB_LDO11_VTG_MAX_UV 1800000
+
+#define BGRSB_BGWEAR_SUBSYS "bg-wear"
+
+#define BGRSB_BTTN_CONFIGURE 5
+#define BGRSB_POWER_CALIBRATION 2
+#define BGRSB_POWER_ENABLE 1
+#define BGRSB_POWER_DISABLE 0
+#define BGRSB_GLINK_POWER_ENABLE 6
+#define BGRSB_GLINK_POWER_DISABLE 7
+
+
+struct bgrsb_regulator {
+ struct regulator *regldo11;
+ struct regulator *regldo15;
+};
+
+enum ldo_task {
+ BGRSB_ENABLE_LDO11,
+ BGRSB_ENABLE_LDO15,
+ BGRSB_DISABLE_LDO11,
+ BGRSB_DISABLE_LDO15,
+ BGRSB_NO_ACTION
+};
+
+enum bgrsb_state {
+ BGRSB_STATE_UNKNOWN,
+ BGRSB_STATE_INIT,
+ BGRSB_STATE_LDO11_ENABLED,
+ BGRSB_STATE_RSB_CONFIGURED,
+ BGRSB_STATE_LDO15_ENABLED,
+ BGRSB_STATE_RSB_ENABLED
+};
+
+struct bgrsb_msg {
+ uint32_t cmd_id;
+ uint32_t data;
+};
+
+struct bgrsb_priv {
+ void *handle;
+ struct input_dev *input;
+ struct mutex glink_mutex;
+
+ enum bgrsb_state bgrsb_current_state;
+ enum glink_link_state link_state;
+
+ bool chnl_state;
+ void *lhndl;
+
+ struct work_struct bg_up_work;
+ struct work_struct bg_down_work;
+
+ struct work_struct rsb_up_work;
+ struct work_struct rsb_down_work;
+
+ struct work_struct rsb_glink_up_work;
+ struct work_struct rsb_glink_down_work;
+
+ struct work_struct rsb_calibration_work;
+ struct work_struct bttn_configr_work;
+
+ struct work_struct glink_work;
+
+ struct workqueue_struct *bgrsb_event_wq;
+ struct workqueue_struct *bgrsb_wq;
+
+ struct bg_glink_chnl chnl;
+ char rx_buf[BGRSB_GLINK_INTENT_SIZE];
+
+ struct bgrsb_regulator rgltr;
+
+ enum ldo_task ldo_action;
+
+ void *bgwear_subsys_handle;
+
+ struct completion bg_resp_cmplt;
+ struct completion wrk_cmplt;
+ struct completion bg_lnikup_cmplt;
+ struct completion tx_done;
+
+ struct device *ldev;
+
+ wait_queue_head_t link_state_wait;
+
+ uint32_t calbrtion_intrvl;
+ uint32_t calbrtion_cpi;
+
+ uint8_t bttn_configs;
+
+ bool calibration_needed;
+ bool is_calibrd;
+};
+
+static void *bgrsb_drv;
+static int bgrsb_enable(struct bgrsb_priv *dev, bool enable);
+
+int bgrsb_send_input(struct event *evnt)
+{
+ uint8_t press_code;
+ uint8_t value;
+
+ struct bgrsb_priv *dev =
+ container_of(bgrsb_drv, struct bgrsb_priv, lhndl);
+
+ if (!evnt)
+ return -EINVAL;
+
+ if (evnt->sub_id == 1) {
+ input_report_rel(dev->input, REL_WHEEL, evnt->evnt_data);
+ input_sync(dev->input);
+ } else if (evnt->sub_id == 2) {
+
+ press_code = (uint8_t) evnt->evnt_data;
+ value = (uint8_t) (evnt->evnt_data >> 8);
+
+ switch (press_code) {
+ case 0x1:
+ if (value == 0) {
+ input_report_key(dev->input, KEY_VOLUMEDOWN, 1);
+ input_sync(dev->input);
+ } else {
+ input_report_key(dev->input, KEY_VOLUMEDOWN, 0);
+ input_sync(dev->input);
+ }
+ break;
+ case 0x2:
+ if (value == 0) {
+ input_report_key(dev->input, KEY_VOLUMEUP, 1);
+ input_sync(dev->input);
+ } else {
+ input_report_key(dev->input, KEY_VOLUMEUP, 0);
+ input_sync(dev->input);
+ }
+ break;
+ case 0x3:
+ if (value == 0) {
+ input_report_key(dev->input, KEY_POWER, 1);
+ input_sync(dev->input);
+ } else {
+ input_report_key(dev->input, KEY_POWER, 0);
+ input_sync(dev->input);
+ }
+ break;
+ default:
+ pr_info("event: type[%d] , data: %d\n",
+ evnt->sub_id, evnt->evnt_data);
+ }
+ }
+ return 0;
+}
+EXPORT_SYMBOL(bgrsb_send_input);
+
+static void bgrsb_glink_notify_rx(void *handle, const void *priv,
+ const void *pkt_priv, const void *ptr, size_t size)
+{
+ struct bgrsb_priv *dev = (struct bgrsb_priv *)priv;
+
+ memcpy(dev->rx_buf, ptr, size);
+ glink_rx_done(dev->handle, ptr, false);
+ complete(&dev->bg_resp_cmplt);
+}
+
+static void bgrsb_glink_notify_state(void *handle, const void *priv,
+ unsigned int event)
+{
+ struct bgrsb_priv *dev = (struct bgrsb_priv *)priv;
+
+ switch (event) {
+ case GLINK_CONNECTED:
+ complete(&dev->bg_lnikup_cmplt);
+ break;
+ case GLINK_REMOTE_DISCONNECTED:
+ case GLINK_LOCAL_DISCONNECTED:
+ dev->chnl_state = false;
+ break;
+ }
+}
+
+static void bgrsb_glink_notify_tx_done(void *handle, const void *priv,
+ const void *pkt_priv, const void *ptr)
+{
+ struct bgrsb_priv *dev = (struct bgrsb_priv *)priv;
+
+ complete(&dev->tx_done);
+}
+
+static void bgrsb_glink_close_work(struct work_struct *work)
+{
+ struct bgrsb_priv *dev =
+ container_of(work, struct bgrsb_priv, glink_work);
+
+ if (dev->handle)
+ glink_close(dev->handle);
+ dev->handle = NULL;
+}
+
+static void bgrsb_glink_open_work(struct work_struct *work)
+{
+ struct glink_open_config open_cfg;
+ void *hndl = NULL;
+ int rc = 0;
+ struct bgrsb_priv *dev =
+ container_of(work, struct bgrsb_priv, glink_work);
+
+ if (dev->handle)
+ return;
+
+ memset(&open_cfg, 0, sizeof(struct glink_open_config));
+ open_cfg.priv = (void *)dev;
+ open_cfg.edge = dev->chnl.chnl_edge;
+ open_cfg.transport = dev->chnl.chnl_trnsprt;
+ open_cfg.name = dev->chnl.chnl_name;
+ open_cfg.notify_tx_done = bgrsb_glink_notify_tx_done;
+ open_cfg.notify_state = bgrsb_glink_notify_state;
+ open_cfg.notify_rx = bgrsb_glink_notify_rx;
+
+ init_completion(&dev->bg_lnikup_cmplt);
+ hndl = glink_open(&open_cfg);
+
+ if (IS_ERR_OR_NULL(hndl)) {
+ pr_err("Glink open failed[%s]\n",
+ dev->chnl.chnl_name);
+ dev->handle = NULL;
+ return;
+ }
+
+ rc = wait_for_completion_timeout(&dev->bg_lnikup_cmplt,
+ msecs_to_jiffies(TIMEOUT_MS));
+ if (!rc) {
+ pr_err("Channel open failed. Time out\n");
+ return;
+ }
+ dev->chnl_state = true;
+ dev->handle = hndl;
+}
+
+static void bgrsb_glink_state_cb(struct glink_link_state_cb_info *cb_info,
+ void *data)
+{
+ struct bgrsb_priv *dev = (struct bgrsb_priv *)data;
+
+ dev->link_state = cb_info->link_state;
+ switch (dev->link_state) {
+ case GLINK_LINK_STATE_UP:
+ INIT_WORK(&dev->glink_work, bgrsb_glink_open_work);
+ queue_work(dev->bgrsb_event_wq, &dev->glink_work);
+ break;
+ case GLINK_LINK_STATE_DOWN:
+ INIT_WORK(&dev->glink_work, bgrsb_glink_close_work);
+ queue_work(dev->bgrsb_event_wq, &dev->glink_work);
+ break;
+ }
+}
+
+static int bgrsb_init_link_inf(struct bgrsb_priv *dev)
+{
+ struct glink_link_info link_info;
+ void *hndl;
+
+ link_info.glink_link_state_notif_cb = bgrsb_glink_state_cb;
+ link_info.transport = dev->chnl.chnl_trnsprt;
+ link_info.edge = dev->chnl.chnl_edge;
+
+ hndl = glink_register_link_state_cb(&link_info, (void *)dev);
+ if (IS_ERR_OR_NULL(hndl)) {
+ pr_err("Unable to register link[%s]\n",
+ dev->chnl.chnl_name);
+ return -EFAULT;
+ }
+ return 0;
+}
+
+static int bgrsb_init_regulators(struct device *pdev)
+{
+ struct regulator *reg11;
+ struct regulator *reg15;
+ struct bgrsb_priv *dev = dev_get_drvdata(pdev);
+
+ reg11 = regulator_get(pdev, "vdd-ldo1");
+ if (IS_ERR_OR_NULL(reg11)) {
+ pr_err("Unable to get regulator for LDO-11\n");
+ return PTR_ERR(reg11);
+ }
+
+ reg15 = regulator_get(pdev, "vdd-ldo2");
+ if (IS_ERR_OR_NULL(reg15)) {
+ pr_err("Unable to get regulator for LDO-15\n");
+ return PTR_ERR(reg15);
+ }
+
+ dev->rgltr.regldo11 = reg11;
+ dev->rgltr.regldo15 = reg15;
+
+ return 0;
+}
+
+static int bgrsb_ldo_work(struct bgrsb_priv *dev, enum ldo_task ldo_action)
+{
+ int ret = 0;
+
+ switch (ldo_action) {
+ case BGRSB_ENABLE_LDO11:
+ ret = regulator_set_voltage(dev->rgltr.regldo11,
+ BGRSB_LDO11_VTG_MIN_UV, BGRSB_LDO11_VTG_MAX_UV);
+ if (ret) {
+ pr_err("Failed to request LDO-11 voltage.\n");
+ goto err_ret;
+ }
+ ret = regulator_enable(dev->rgltr.regldo11);
+ if (ret) {
+ pr_err("Failed to enable LDO-11 %d\n", ret);
+ goto err_ret;
+ }
+ break;
+
+ case BGRSB_ENABLE_LDO15:
+ ret = regulator_set_voltage(dev->rgltr.regldo15,
+ BGRSB_LDO15_VTG_MIN_UV, BGRSB_LDO15_VTG_MAX_UV);
+ if (ret) {
+ pr_err("Failed to request LDO-15 voltage.\n");
+ goto err_ret;
+ }
+ ret = regulator_enable(dev->rgltr.regldo15);
+ if (ret) {
+ pr_err("Failed to enable LDO-15 %d\n", ret);
+ goto err_ret;
+ }
+ break;
+ case BGRSB_DISABLE_LDO11:
+ ret = regulator_disable(dev->rgltr.regldo11);
+ if (ret) {
+ pr_err("Failed to disable LDO-11 %d\n", ret);
+ goto err_ret;
+ }
+ break;
+
+ case BGRSB_DISABLE_LDO15:
+ ret = regulator_disable(dev->rgltr.regldo15);
+ if (ret) {
+ pr_err("Failed to disable LDO-15 %d\n", ret);
+ goto err_ret;
+ }
+ regulator_set_load(dev->rgltr.regldo15, 0);
+ break;
+ default:
+ ret = -EINVAL;
+ }
+
+err_ret:
+ return ret;
+}
+
+static void bgrsb_bgdown_work(struct work_struct *work)
+{
+ struct bgrsb_priv *dev = container_of(work, struct bgrsb_priv,
+ bg_down_work);
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_ENABLED) {
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO15) == 0)
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ else
+ pr_err("Failed to unvote LDO-15 on BG down\n");
+ }
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_CONFIGURED) {
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO11) == 0)
+ dev->bgrsb_current_state = BGRSB_STATE_INIT;
+ else
+ pr_err("Failed to unvote LDO-11 on BG down\n");
+ }
+
+ pr_info("RSB current state is : %d\n", dev->bgrsb_current_state);
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_INIT) {
+ if (dev->is_calibrd)
+ dev->calibration_needed = true;
+ }
+}
+
+static void bgrsb_glink_bgdown_work(struct work_struct *work)
+{
+ int rc;
+ struct bgrsb_priv *dev = container_of(work, struct bgrsb_priv,
+ rsb_glink_down_work);
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_ENABLED) {
+
+ rc = bgrsb_enable(dev, false);
+ if (rc != 0) {
+ pr_err("Failed to send disable command to BG\n");
+ return;
+ }
+
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO15) != 0) {
+ pr_err("Failed to un-vote LDO-15\n");
+ return;
+ }
+
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ pr_info("RSB Disabled\n");
+ }
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_CONFIGURED) {
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO11) == 0)
+ dev->bgrsb_current_state = BGRSB_STATE_INIT;
+ else
+ pr_err("Failed to unvote LDO-11 on BG Glink down\n");
+ }
+ if (dev->handle)
+ glink_close(dev->handle);
+ dev->handle = NULL;
+ pr_debug("BG Glink Close connection\n");
+}
+
+static int bgrsb_tx_msg(struct bgrsb_priv *dev, void *msg, size_t len)
+{
+ int rc = 0;
+ uint8_t resp = 0;
+
+ if (!dev->chnl_state)
+ return -ENODEV;
+
+ mutex_lock(&dev->glink_mutex);
+ init_completion(&dev->tx_done);
+ init_completion(&dev->bg_resp_cmplt);
+
+ rc = glink_queue_rx_intent(dev->handle,
+ (void *)dev, BGRSB_GLINK_INTENT_SIZE);
+
+ if (rc) {
+ pr_err("Failed to queue intent\n");
+ goto err_ret;
+ }
+
+ rc = glink_tx(dev->handle, (void *)dev, msg,
+ len, GLINK_TX_REQ_INTENT);
+ if (rc) {
+ pr_err("Failed to send command\n");
+ goto err_ret;
+ }
+
+ rc = wait_for_completion_timeout(&dev->tx_done,
+ msecs_to_jiffies(TIMEOUT_MS));
+ if (!rc) {
+ pr_err("Timed out waiting for Command to send\n");
+ rc = -ETIMEDOUT;
+ goto err_ret;
+ }
+
+ rc = wait_for_completion_timeout(&dev->bg_resp_cmplt,
+ msecs_to_jiffies(TIMEOUT_MS));
+ if (!rc) {
+ pr_err("Timed out waiting for response\n");
+ rc = -ETIMEDOUT;
+ goto err_ret;
+ }
+
+ resp = *(uint8_t *)dev->rx_buf;
+ if (!(resp == 0x01)) {
+ pr_err("Bad RSB response\n");
+ rc = -EINVAL;
+ goto err_ret;
+ }
+ rc = 0;
+
+err_ret:
+ mutex_unlock(&dev->glink_mutex);
+ return rc;
+}
+
+static int bgrsb_enable(struct bgrsb_priv *dev, bool enable)
+{
+ int rc = 0;
+ struct bgrsb_msg req = {0};
+
+ req.cmd_id = 0x02;
+ req.data = enable ? 0x01 : 0x00;
+
+ rc = bgrsb_tx_msg(dev, &req, BGRSB_MSG_SIZE);
+ return rc;
+}
+
+static int bgrsb_configr_rsb(struct bgrsb_priv *dev, bool enable)
+{
+ int rc = 0;
+ struct bgrsb_msg req = {0};
+
+ req.cmd_id = 0x01;
+ req.data = enable ? 0x01 : 0x00;
+
+ rc = bgrsb_tx_msg(dev, &req, BGRSB_MSG_SIZE);
+ return rc;
+}
+
+static void bgrsb_bgup_work(struct work_struct *work)
+{
+ int rc = 0;
+ struct bgrsb_priv *dev = container_of(work, struct bgrsb_priv,
+ bg_up_work);
+
+ if (bgrsb_ldo_work(dev, BGRSB_ENABLE_LDO11) == 0) {
+
+ rc = wait_event_timeout(dev->link_state_wait,
+ (dev->chnl_state == true),
+ msecs_to_jiffies(TIMEOUT_MS*2));
+ if (rc == 0) {
+ pr_err("Glink channel connection time out\n");
+ return;
+ }
+ rc = bgrsb_configr_rsb(dev, true);
+ if (rc != 0) {
+ pr_err("BG failed to configure RSB %d\n", rc);
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO11) == 0)
+ dev->bgrsb_current_state = BGRSB_STATE_INIT;
+ return;
+ }
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ pr_debug("RSB Cofigured\n");
+ }
+}
+
+static void bgrsb_glink_bgup_work(struct work_struct *work)
+{
+ int rc = 0;
+ struct bgrsb_priv *dev = container_of(work, struct bgrsb_priv,
+ rsb_glink_up_work);
+
+ if (bgrsb_ldo_work(dev, BGRSB_ENABLE_LDO11) == 0) {
+
+ INIT_WORK(&dev->glink_work, bgrsb_glink_open_work);
+ queue_work(dev->bgrsb_event_wq, &dev->glink_work);
+
+ rc = wait_event_timeout(dev->link_state_wait,
+ (dev->chnl_state == true),
+ msecs_to_jiffies(TIMEOUT_MS*2));
+ if (rc == 0) {
+ pr_err("Glink channel connection time out\n");
+ return;
+ }
+ rc = bgrsb_configr_rsb(dev, true);
+ if (rc != 0) {
+ pr_err("BG Glink failed to configure RSB %d\n", rc);
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO11) == 0)
+ dev->bgrsb_current_state = BGRSB_STATE_INIT;
+ return;
+ }
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ pr_debug("Glink RSB Cofigured\n");
+ }
+}
+
+/**
+ *ssr_bg_cb(): callback function is called
+ *by ssr framework when BG goes down, up and during ramdump
+ *collection. It handles BG shutdown and power up events.
+ */
+static int ssr_bgrsb_cb(struct notifier_block *this,
+ unsigned long opcode, void *data)
+{
+ struct bgrsb_priv *dev = container_of(bgrsb_drv,
+ struct bgrsb_priv, lhndl);
+
+ switch (opcode) {
+ case SUBSYS_BEFORE_SHUTDOWN:
+ queue_work(dev->bgrsb_wq, &dev->bg_down_work);
+ break;
+ case SUBSYS_AFTER_POWERUP:
+ if (dev->bgrsb_current_state == BGRSB_STATE_INIT)
+ queue_work(dev->bgrsb_wq, &dev->bg_up_work);
+ break;
+ }
+ return NOTIFY_DONE;
+}
+
+static struct notifier_block ssr_bg_nb = {
+ .notifier_call = ssr_bgrsb_cb,
+ .priority = 0,
+};
+
+/**
+ * ssr_register checks that domain id should be in range and register
+ * SSR framework for value at domain id.
+ */
+static int bgrsb_ssr_register(struct bgrsb_priv *dev)
+{
+ struct notifier_block *nb;
+
+ if (!dev)
+ return -ENODEV;
+
+ nb = &ssr_bg_nb;
+ dev->bgwear_subsys_handle =
+ subsys_notif_register_notifier(BGRSB_BGWEAR_SUBSYS, nb);
+
+ if (!dev->bgwear_subsys_handle) {
+ dev->bgwear_subsys_handle = NULL;
+ return -EFAULT;
+ }
+ return 0;
+}
+
+static void bgrsb_enable_rsb(struct work_struct *work)
+{
+ int rc = 0;
+ struct bgrsb_priv *dev = container_of(work, struct bgrsb_priv,
+ rsb_up_work);
+
+ if (dev->bgrsb_current_state != BGRSB_STATE_RSB_CONFIGURED) {
+ pr_err("BG is not yet configured for RSB\n");
+ return;
+ }
+
+ if (bgrsb_ldo_work(dev, BGRSB_ENABLE_LDO15) == 0) {
+
+ rc = bgrsb_enable(dev, true);
+ if (rc != 0) {
+ pr_err("Failed to send enable command to BG\n");
+ bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO15);
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ return;
+ }
+ }
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_ENABLED;
+ pr_debug("RSB Enabled\n");
+
+ if (dev->calibration_needed) {
+ dev->calibration_needed = false;
+ queue_work(dev->bgrsb_wq, &dev->rsb_calibration_work);
+ }
+}
+
+static void bgrsb_disable_rsb(struct work_struct *work)
+{
+ int rc = 0;
+ struct bgrsb_priv *dev = container_of(work, struct bgrsb_priv,
+ rsb_down_work);
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_ENABLED) {
+
+ rc = bgrsb_enable(dev, false);
+ if (rc != 0) {
+ pr_err("Failed to send disable command to BG\n");
+ return;
+ }
+
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO15) != 0)
+ return;
+
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ pr_debug("RSB Disabled\n");
+ }
+}
+
+static void bgrsb_calibration(struct work_struct *work)
+{
+ int rc = 0;
+ struct bgrsb_msg req = {0};
+ struct bgrsb_priv *dev =
+ container_of(work, struct bgrsb_priv,
+ rsb_calibration_work);
+
+ req.cmd_id = 0x03;
+ req.data = dev->calbrtion_cpi;
+
+ rc = bgrsb_tx_msg(dev, &req, 5);
+ if (rc != 0) {
+ pr_err("Failed to send resolution value to BG\n");
+ return;
+ }
+
+ req.cmd_id = 0x04;
+ req.data = dev->calbrtion_intrvl;
+
+ rc = bgrsb_tx_msg(dev, &req, 5);
+ if (rc != 0) {
+ pr_err("Failed to send interval value to BG\n");
+ return;
+ }
+ dev->is_calibrd = true;
+ pr_debug("RSB Calibbered\n");
+}
+
+static void bgrsb_buttn_configration(struct work_struct *work)
+{
+ int rc = 0;
+ struct bgrsb_msg req = {0};
+ struct bgrsb_priv *dev =
+ container_of(work, struct bgrsb_priv,
+ bttn_configr_work);
+
+ req.cmd_id = 0x05;
+ req.data = dev->bttn_configs;
+
+ rc = bgrsb_tx_msg(dev, &req, 5);
+ if (rc != 0) {
+ pr_err("Failed to send button configuration cmnd to BG\n");
+ return;
+ }
+
+ dev->bttn_configs = 0;
+ pr_debug("Button configured\n");
+}
+
+static int split_bg_work(struct bgrsb_priv *dev, char *str)
+{
+ long val;
+ int ret;
+ char *tmp;
+
+ tmp = strsep(&str, ":");
+ if (!tmp)
+ return -EINVAL;
+
+ ret = kstrtol(tmp, 10, &val);
+ if (ret < 0)
+ return ret;
+
+ switch (val) {
+ case BGRSB_POWER_DISABLE:
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_CONFIGURED)
+ return 0;
+ queue_work(dev->bgrsb_wq, &dev->rsb_down_work);
+ break;
+ case BGRSB_POWER_ENABLE:
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_ENABLED)
+ return 0;
+ queue_work(dev->bgrsb_wq, &dev->rsb_up_work);
+ break;
+ case BGRSB_POWER_CALIBRATION:
+ tmp = strsep(&str, ":");
+ if (!tmp)
+ return -EINVAL;
+
+ ret = kstrtol(tmp, 10, &val);
+ if (ret < 0)
+ return ret;
+
+ dev->calbrtion_intrvl = (uint32_t)val;
+
+ tmp = strsep(&str, ":");
+ if (!tmp)
+ return -EINVAL;
+
+ ret = kstrtol(tmp, 10, &val);
+ if (ret < 0)
+ return ret;
+
+ dev->calbrtion_cpi = (uint32_t)val;
+
+ queue_work(dev->bgrsb_wq, &dev->rsb_calibration_work);
+ break;
+ case BGRSB_BTTN_CONFIGURE:
+ tmp = strsep(&str, ":");
+ if (!tmp)
+ return -EINVAL;
+
+ ret = kstrtol(tmp, 10, &val);
+ if (ret < 0)
+ return ret;
+
+ dev->bttn_configs = (uint8_t)val;
+ queue_work(dev->bgrsb_wq, &dev->bttn_configr_work);
+ break;
+ case BGRSB_GLINK_POWER_DISABLE:
+ queue_work(dev->bgrsb_wq, &dev->rsb_glink_down_work);
+ break;
+ case BGRSB_GLINK_POWER_ENABLE:
+ queue_work(dev->bgrsb_wq, &dev->rsb_glink_up_work);
+ break;
+ }
+ return 0;
+}
+
+static int store_enable(struct device *pdev, struct device_attribute *attr,
+ const char *buff, size_t count)
+{
+ int rc;
+ struct bgrsb_priv *dev = dev_get_drvdata(pdev);
+ char *arr = kstrdup(buff, GFP_KERNEL);
+
+ if (!arr)
+ goto err_ret;
+
+ rc = split_bg_work(dev, arr);
+ if (rc != 0)
+ pr_err("Not able to process request\n");
+
+err_ret:
+ return count;
+}
+
+static int show_enable(struct device *dev, struct device_attribute *attr,
+ char *buff)
+{
+ return 0;
+}
+
+static struct device_attribute dev_attr_rsb = {
+ .attr = {
+ .name = "enable",
+ .mode = 00660,
+ },
+ .show = show_enable,
+ .store = store_enable,
+};
+
+static int bgrsb_init(struct bgrsb_priv *dev)
+{
+ bgrsb_drv = &dev->lhndl;
+ dev->chnl.chnl_name = "RSB_CTRL";
+ dev->chnl.chnl_edge = "bg";
+ dev->chnl.chnl_trnsprt = "bgcom";
+ mutex_init(&dev->glink_mutex);
+ dev->link_state = GLINK_LINK_STATE_DOWN;
+
+ dev->ldo_action = BGRSB_NO_ACTION;
+
+ dev->bgrsb_event_wq =
+ create_singlethread_workqueue(dev->chnl.chnl_name);
+ if (!dev->bgrsb_event_wq) {
+ pr_err("Failed to init Glink work-queue\n");
+ goto err_ret;
+ }
+
+ dev->bgrsb_wq =
+ create_singlethread_workqueue("bg-work-queue");
+ if (!dev->bgrsb_wq) {
+ pr_err("Failed to init BG-RSB work-queue\n");
+ goto free_rsb_wq;
+ }
+
+ init_waitqueue_head(&dev->link_state_wait);
+
+ /* set default bgrsb state */
+ dev->bgrsb_current_state = BGRSB_STATE_INIT;
+
+ /* Init all works */
+ INIT_WORK(&dev->bg_up_work, bgrsb_bgup_work);
+ INIT_WORK(&dev->bg_down_work, bgrsb_bgdown_work);
+ INIT_WORK(&dev->rsb_up_work, bgrsb_enable_rsb);
+ INIT_WORK(&dev->rsb_down_work, bgrsb_disable_rsb);
+ INIT_WORK(&dev->rsb_calibration_work, bgrsb_calibration);
+ INIT_WORK(&dev->bttn_configr_work, bgrsb_buttn_configration);
+ INIT_WORK(&dev->rsb_glink_down_work, bgrsb_glink_bgdown_work);
+ INIT_WORK(&dev->rsb_glink_up_work, bgrsb_glink_bgup_work);
+
+ return 0;
+
+free_rsb_wq:
+ destroy_workqueue(dev->bgrsb_event_wq);
+err_ret:
+ return -EFAULT;
+}
+
+static int bg_rsb_probe(struct platform_device *pdev)
+{
+ struct bgrsb_priv *dev;
+ struct input_dev *input;
+ int rc;
+
+ dev = devm_kzalloc(&pdev->dev, sizeof(*dev), GFP_KERNEL);
+ if (!dev)
+ return -ENOMEM;
+
+ dev->bgrsb_current_state = BGRSB_STATE_UNKNOWN;
+ rc = bgrsb_init(dev);
+ if (rc)
+ goto err_ret_dev;
+
+ rc = bgrsb_init_link_inf(dev);
+ if (rc)
+ goto err_ret_dev;
+
+ /* Set up input device */
+ input = input_allocate_device();
+ if (!input)
+ goto err_ret_dev;
+
+ input_set_capability(input, EV_REL, REL_WHEEL);
+ input_set_capability(input, EV_KEY, KEY_VOLUMEUP);
+ input_set_capability(input, EV_KEY, KEY_VOLUMEDOWN);
+ input->name = "bg-spi";
+
+ rc = input_register_device(input);
+ if (rc) {
+ pr_err("Input device registration failed\n");
+ goto err_ret_inp;
+ }
+ dev->input = input;
+
+ /* register device for bg-wear ssr */
+ rc = bgrsb_ssr_register(dev);
+ if (rc) {
+ pr_err("Failed to register for bg ssr\n");
+ goto err_ret_inp;
+ }
+ rc = device_create_file(&pdev->dev, &dev_attr_rsb);
+ if (rc) {
+ pr_err("Not able to create the file bg-rsb/enable\n");
+ goto err_ret_inp;
+ }
+ dev_set_drvdata(&pdev->dev, dev);
+ rc = bgrsb_init_regulators(&pdev->dev);
+ if (rc) {
+ pr_err("Failed to set regulators\n");
+ goto err_ret_inp;
+ }
+ return 0;
+
+err_ret_inp:
+ input_free_device(input);
+
+err_ret_dev:
+ devm_kfree(&pdev->dev, dev);
+ return -ENODEV;
+}
+
+static int bg_rsb_remove(struct platform_device *pdev)
+{
+ struct bgrsb_priv *dev = platform_get_drvdata(pdev);
+
+ destroy_workqueue(dev->bgrsb_event_wq);
+ destroy_workqueue(dev->bgrsb_wq);
+ input_free_device(dev->input);
+
+ return 0;
+}
+
+static int bg_rsb_resume(struct platform_device *pdev)
+{
+ int rc;
+ struct bgrsb_priv *dev = platform_get_drvdata(pdev);
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_CONFIGURED)
+ return 0;
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_INIT) {
+ if (bgrsb_ldo_work(dev, BGRSB_ENABLE_LDO11) == 0) {
+ rc = bgrsb_configr_rsb(dev, true);
+ if (rc != 0) {
+ pr_err("BG failed to configure RSB %d\n", rc);
+ bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO11);
+ return rc;
+ }
+ dev->bgrsb_current_state = BGRSB_STATE_RSB_CONFIGURED;
+ pr_debug("RSB Cofigured\n");
+ return 0;
+ }
+ pr_err("RSB failed to resume\n");
+ }
+ return -EINVAL;
+}
+
+static int bg_rsb_suspend(struct platform_device *pdev, pm_message_t state)
+{
+ struct bgrsb_priv *dev = platform_get_drvdata(pdev);
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_INIT)
+ return 0;
+
+ if (dev->bgrsb_current_state == BGRSB_STATE_RSB_ENABLED) {
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO15) != 0)
+ goto ret_err;
+ }
+
+ if (bgrsb_ldo_work(dev, BGRSB_DISABLE_LDO11) == 0) {
+ dev->bgrsb_current_state = BGRSB_STATE_INIT;
+ pr_debug("RSB Init\n");
+ return 0;
+ }
+
+ret_err:
+ pr_err("RSB failed to suspend\n");
+ return -EINVAL;
+}
+
+static const struct of_device_id bg_rsb_of_match[] = {
+ { .compatible = "qcom,bg-rsb", },
+ { }
+};
+
+static struct platform_driver bg_rsb_driver = {
+ .driver = {
+ .name = "bg-rsb",
+ .of_match_table = bg_rsb_of_match,
+ },
+ .probe = bg_rsb_probe,
+ .remove = bg_rsb_remove,
+ .resume = bg_rsb_resume,
+ .suspend = bg_rsb_suspend,
+};
+
+module_platform_driver(bg_rsb_driver);
+MODULE_DESCRIPTION("SoC BG RSB driver");
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/soc/qcom/bgcom.h b/drivers/soc/qcom/bgcom.h
new file mode 100644
index 0000000..b389a91
--- /dev/null
+++ b/drivers/soc/qcom/bgcom.h
@@ -0,0 +1,214 @@
+/* Copyright (c) 2017-2018, 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.
+ *
+ */
+
+#ifndef BGCOM_H
+#define BGCOM_H
+
+#define BGCOM_REG_TZ_TO_MASTER_STATUS 0x01
+#define BGCOM_REG_TZ_TO_MASTER_DATA 0x03
+#define BGCOM_REG_SLAVE_STATUS 0x05
+#define BGCOM_REG_TIMESTAMP 0x07
+#define BGCOM_REG_SLAVE_STATUS_AUTO_CLEAR 0x09
+#define BGCOM_REG_FIFO_FILL 0x0B
+#define BGCOM_REG_FIFO_SIZE 0x0D
+#define BGCOM_REG_TZ_TO_SLAVE_COMMAND 0x0E
+#define BGCOM_REG_TZ_TO_SLAVE_DATA 0x10
+#define BGCOM_REG_MASTER_STATUS 0x12
+#define BGCOM_REG_MASTER_COMMAND 0x14
+#define BGCOM_REG_MSG_WR_REG_4 0x16
+#define BGCOM_REG_TO_SLAVE_FIFO 0x40
+#define BGCOM_REG_TO_MASTER_FIFO 0x41
+#define BGCOM_REG_TO_SLAVE_AHB 0x42
+#define BGCOM_REG_TO_MASTER_AHB 0x43
+
+/* Enum to define the bgcom SPI state */
+enum bgcom_spi_state {
+ BGCOM_SPI_FREE = 0,
+ BGCOM_SPI_BUSY,
+};
+
+/* Enums to identify Blackghost events */
+enum bgcom_event_type {
+ BGCOM_EVENT_NONE = 0,
+ BGCOM_EVENT_APPLICATION_RUNNING,
+ BGCOM_EVENT_TO_SLAVE_FIFO_READY,
+ BGCOM_EVENT_TO_MASTER_FIFO_READY,
+ BGCOM_EVENT_AHB_READY,
+ BGCOM_EVENT_TO_MASTER_FIFO_USED,
+ BGCOM_EVENT_TO_SLAVE_FIFO_FREE,
+ BGCOM_EVENT_TIMESTAMP_UPDATE,
+ BGCOM_EVENT_RESET_OCCURRED,
+
+ BGCOM_EVENT_ERROR_WRITE_FIFO_OVERRUN,
+ BGCOM_EVENT_ERROR_WRITE_FIFO_BUS_ERR,
+ BGCOM_EVENT_ERROR_WRITE_FIFO_ACCESS,
+ BGCOM_EVENT_ERROR_READ_FIFO_UNDERRUN,
+ BGCOM_EVENT_ERROR_READ_FIFO_BUS_ERR,
+ BGCOM_EVENT_ERROR_READ_FIFO_ACCESS,
+ BGCOM_EVENT_ERROR_TRUNCATED_READ,
+ BGCOM_EVENT_ERROR_TRUNCATED_WRITE,
+ BGCOM_EVENT_ERROR_AHB_ILLEGAL_ADDRESS,
+ BGCOM_EVENT_ERROR_AHB_BUS_ERR,
+ BGCOM_EVENT_ERROR_UNKNOWN,
+};
+
+/* Event specific data */
+union bgcom_event_data_type {
+ uint32_t unused;
+ bool application_running; /* BGCOM_EVENT_APPLICATION_RUNNING */
+ bool to_slave_fifo_ready; /* BGCOM_EVENT_TO_SLAVE_FIFO_READY */
+ bool to_master_fifo_ready; /* BGCOM_EVENT_TO_MASTER_FIFO_READY */
+ bool ahb_ready; /* BGCOM_EVENT_AHB_READY */
+ uint16_t to_slave_fifo_free; /* BGCOM_EVENT_TO_SLAVE_FIFO_FREE */
+ struct fifo_event_data {
+ uint16_t to_master_fifo_used;
+ void *data;
+ } fifo_data;
+};
+
+/* Client specific data */
+struct bgcom_open_config_type {
+ /** Private data pointer for client to maintain context.
+ * This data is passed back to client in the notification callbacks.
+ */
+ void *priv;
+
+ /* Notification callbacks to notify the BG events */
+ void (*bgcom_notification_cb)(void *handle, void *priv,
+ enum bgcom_event_type event,
+ union bgcom_event_data_type *event_data);
+};
+
+/**
+ * bgcom_open() - opens a channel to interact with Blackghost
+ * @open_config: pointer to the open configuration structure
+ *
+ * Open a new connection to blackghost
+ *
+ * Return a handle on success or NULL on error
+ */
+void *bgcom_open(struct bgcom_open_config_type *open_config);
+
+/**
+ * bgcom_close() - close the exsting with Blackghost
+ * @handle: pointer to the handle, provided by bgcom at
+ * bgcom_open
+ *
+ * Open a new connection to blackghost
+ *
+ * Return 0 on success or error on invalid handle
+ */
+int bgcom_close(void **handle);
+
+/**
+ * bgcom_reg_read() - Read from the one or more contiguous registers from BG
+ * @handle: BGCOM handle associated with the channel
+ * @reg_start_addr : 8 bit start address of the registers to read from
+ * @num_regs : Number of contiguous registers to read, starting
+ * from reg_start_addr.
+ * @read_buf : Buffer to read from the registers.
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_reg_read(void *handle, uint8_t reg_start_addr,
+ uint32_t num_regs, void *read_buf);
+
+/**
+ * Write into the one or more contiguous registers.
+ *
+ * @param[in] handle BGCOM handle associated with the channel.
+ * @param[in] reg_start_addr 8bit start address of the registers to write into.
+ * @param[in] num_regs Number of contiguous registers to write, starting
+ * from reg_start_addr.
+ * @param[in] write_buf Buffer to write into the registers.
+ *
+ * @return
+ * 0 if function is successful,
+ * Otherwise returns error code.
+ *
+ * @sideeffects Causes the Blackghost SPI slave to wakeup. Depending up on
+ * the operation, it may also wakeup the complete Blackghost.
+ */
+
+/**
+ * bgcom_reg_write() - Write to the one or more contiguous registers on BG
+ * @handle: BGCOM handle associated with the channel
+ * @reg_start_addr : 8 bit start address of the registers to read from
+ * @num_regs : Number of contiguous registers to write, starting
+ * from reg_start_addr.
+ * @write_buf : Buffer to be written to the registers.
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_reg_write(void *handle, uint8_t reg_start_addr,
+ uint8_t num_regs, void *write_buf);
+
+/**
+ * bgcom_fifo_read() - Read data from the TO_MASTER_FIFO.
+ * @handle: BGCOM handle associated with the channel
+ * @num_words : number of words to read from FIFO
+ * @read_buf : Buffer read from FIFO.
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_fifo_read(void *handle, uint32_t num_words,
+ void *read_buf);
+
+/**
+ * bgcom_fifo_write() - Write data to the TO_SLAVE_FIFO.
+ * @handle: BGCOM handle associated with the channel
+ * @num_words : number of words to write on FIFO
+ * @write_buf : Buffer written to FIFO.
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_fifo_write(void *handle, uint32_t num_words,
+ void *write_buf);
+
+/**
+ * bgcom_ahb_read() - Read data from the AHB memory.
+ * @handle: BGCOM handle associated with the channel
+ * @ahb_start_addr : Memory start address from where to read
+ * @num_words : number of words to read from AHB
+ * @read_buf : Buffer read from FIFO.
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_ahb_read(void *handle, uint32_t ahb_start_addr,
+ uint32_t num_words, void *read_buf);
+
+/**
+ * bgcom_ahb_write() - Write data to the AHB memory.
+ * @handle: BGCOM handle associated with the channel
+ * @ahb_start_addr : Memory start address from where to start write
+ * @num_words : number of words to read from AHB
+ * @write_buf : Buffer to write in AHB.
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_ahb_write(void *handle, uint32_t ahb_start_addr,
+ uint32_t num_words, void *write_buf);
+
+/**
+ * bgcom_suspend() - Suspends the channel.
+ * @handle: BGCOM handle associated with the channel
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_suspend(void *handle);
+
+/**
+ * bgcom_resume() - Resumes the channel.
+ * @handle: BGCOM handle associated with the channel
+ * Return 0 on success or -Ve on error
+ */
+int bgcom_resume(void *handle);
+
+int bgcom_set_spi_state(enum bgcom_spi_state state);
+
+void bgcom_bgdown_handler(void);
+
+#endif /* BGCOM_H */
diff --git a/drivers/soc/qcom/bgcom_interface.c b/drivers/soc/qcom/bgcom_interface.c
new file mode 100644
index 0000000..efef26d
--- /dev/null
+++ b/drivers/soc/qcom/bgcom_interface.c
@@ -0,0 +1,614 @@
+/* Copyright (c) 2017-2018, 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.
+ *
+ */
+#define pr_fmt(msg) "bgcom_dev:" msg
+
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/version.h>
+#include <linux/fs.h>
+#include <linux/cdev.h>
+#include <linux/device.h>
+#include <linux/errno.h>
+#include <linux/uaccess.h>
+#include <linux/slab.h>
+#include <linux/sysfs.h>
+#include <linux/kobject.h>
+#include <soc/qcom/subsystem_restart.h>
+#include <soc/qcom/subsystem_notif.h>
+#include "bgcom.h"
+#include "linux/bgcom_interface.h"
+#include "bgcom_interface.h"
+#include <linux/of.h>
+#include <linux/of_gpio.h>
+#include <linux/gpio.h>
+#include <linux/delay.h>
+#include <linux/platform_device.h>
+#include <linux/regulator/consumer.h>
+
+#define BGCOM "bg_com_dev"
+
+#define BGDAEMON_LDO09_LPM_VTG 0
+#define BGDAEMON_LDO09_NPM_VTG 10000
+
+#define BGDAEMON_LDO03_LPM_VTG 0
+#define BGDAEMON_LDO03_NPM_VTG 10000
+
+#define MPPS_DOWN_EVENT_TO_BG_TIMEOUT 100
+
+enum {
+ SSR_DOMAIN_BG,
+ SSR_DOMAIN_MODEM,
+ SSR_DOMAIN_MAX,
+};
+
+enum ldo_task {
+ ENABLE_LDO03,
+ ENABLE_LDO09,
+ DISABLE_LDO03,
+ DISABLE_LDO09
+};
+
+struct bgdaemon_regulator {
+ struct regulator *regldo03;
+ struct regulator *regldo09;
+};
+
+struct bgdaemon_priv {
+ struct bgdaemon_regulator rgltr;
+ enum ldo_task ldo_action;
+};
+
+struct bg_event {
+ enum bg_event_type e_type;
+};
+
+struct service_info {
+ const char name[32];
+ int domain_id;
+ void *handle;
+ struct notifier_block *nb;
+};
+
+static char *ssr_domains[] = {
+ "bg-wear",
+ "modem",
+};
+
+static struct bgdaemon_priv *dev;
+static unsigned int bgreset_gpio;
+static DEFINE_MUTEX(bg_char_mutex);
+static struct cdev bg_cdev;
+static struct class *bg_class;
+struct device *dev_ret;
+static dev_t bg_dev;
+static int device_open;
+static void *handle;
+static struct bgcom_open_config_type config_type;
+static DECLARE_COMPLETION(bg_modem_down_wait);
+
+/**
+ * send_uevent(): send events to user space
+ * pce : ssr event handle value
+ * Return: 0 on success, standard Linux error code on error
+ *
+ * It adds pce value to event and broadcasts to user space.
+ */
+static int send_uevent(struct bg_event *pce)
+{
+ char event_string[32];
+ char *envp[2] = { event_string, NULL };
+
+ snprintf(event_string, ARRAY_SIZE(event_string),
+ "BG_EVENT=%d", pce->e_type);
+ return kobject_uevent_env(&dev_ret->kobj, KOBJ_CHANGE, envp);
+}
+
+static int bgdaemon_configure_regulators(bool state)
+{
+ int retval;
+
+ if (state == true) {
+ retval = regulator_enable(dev->rgltr.regldo03);
+ if (retval)
+ pr_err("Failed to enable LDO-03 regulator:%d\n",
+ retval);
+ retval = regulator_enable(dev->rgltr.regldo09);
+ if (retval)
+ pr_err("Failed to enable LDO-09 regulator:%d\n",
+ retval);
+ }
+ if (state == false) {
+ retval = regulator_disable(dev->rgltr.regldo03);
+ if (retval)
+ pr_err("Failed to disable LDO-03 regulator:%d\n",
+ retval);
+ retval = regulator_disable(dev->rgltr.regldo09);
+ if (retval)
+ pr_err("Failed to disable LDO-09 regulator:%d\n",
+ retval);
+ }
+ return retval;
+}
+static int bgdaemon_init_regulators(struct device *pdev)
+{
+ int rc;
+ struct regulator *reg03;
+ struct regulator *reg09;
+
+ reg03 = regulator_get(pdev, "ssr-reg1");
+ if (IS_ERR_OR_NULL(reg03)) {
+ rc = PTR_ERR(reg03);
+ pr_err("Unable to get regulator for LDO-03\n");
+ goto err_ret;
+ }
+ reg09 = regulator_get(pdev, "ssr-reg2");
+ if (IS_ERR_OR_NULL(reg09)) {
+ rc = PTR_ERR(reg09);
+ pr_err("Unable to get regulator for LDO-09\n");
+ goto err_ret;
+ }
+ dev->rgltr.regldo03 = reg03;
+ dev->rgltr.regldo09 = reg09;
+ return 0;
+err_ret:
+ return rc;
+}
+
+static int bgdaemon_ldowork(enum ldo_task do_action)
+{
+ int ret;
+
+ switch (do_action) {
+ case ENABLE_LDO03:
+ ret = regulator_set_load(dev->rgltr.regldo03,
+ BGDAEMON_LDO03_NPM_VTG);
+ if (ret < 0) {
+ pr_err("Failed to request LDO-03 voltage:%d\n",
+ ret);
+ goto err_ret;
+ }
+ break;
+ case ENABLE_LDO09:
+ ret = regulator_set_load(dev->rgltr.regldo09,
+ BGDAEMON_LDO09_NPM_VTG);
+ if (ret < 0) {
+ pr_err("Failed to request LDO-09 voltage:%d\n",
+ ret);
+ goto err_ret;
+ }
+ break;
+ case DISABLE_LDO03:
+ ret = regulator_set_load(dev->rgltr.regldo03,
+ BGDAEMON_LDO03_LPM_VTG);
+ if (ret < 0) {
+ pr_err("Failed to disable LDO-03:%d\n", ret);
+ goto err_ret;
+ }
+ break;
+ case DISABLE_LDO09:
+ ret = regulator_set_load(dev->rgltr.regldo09,
+ BGDAEMON_LDO09_LPM_VTG);
+ if (ret < 0) {
+ pr_err("Failed to disable LDO-09:%d\n", ret);
+ goto err_ret;
+ }
+ break;
+ default:
+ ret = -EINVAL;
+ }
+
+err_ret:
+ return ret;
+}
+
+static int bgcom_char_open(struct inode *inode, struct file *file)
+{
+ int ret;
+
+ mutex_lock(&bg_char_mutex);
+ if (device_open == 1) {
+ pr_err("device is already open\n");
+ mutex_unlock(&bg_char_mutex);
+ return -EBUSY;
+ }
+ device_open++;
+ handle = bgcom_open(&config_type);
+ mutex_unlock(&bg_char_mutex);
+ if (IS_ERR(handle)) {
+ device_open = 0;
+ ret = PTR_ERR(handle);
+ handle = NULL;
+ return ret;
+ }
+ return 0;
+}
+
+static int bgchar_read_cmd(struct bg_ui_data *fui_obj_msg,
+ int type)
+{
+ void *read_buf;
+ int ret;
+ void __user *result = (void *)
+ (uintptr_t)fui_obj_msg->result;
+
+ read_buf = kmalloc_array(fui_obj_msg->num_of_words, sizeof(uint32_t),
+ GFP_KERNEL);
+ if (read_buf == NULL)
+ return -ENOMEM;
+ switch (type) {
+ case REG_READ:
+ ret = bgcom_reg_read(handle, fui_obj_msg->cmd,
+ fui_obj_msg->num_of_words,
+ read_buf);
+ break;
+ case AHB_READ:
+ ret = bgcom_ahb_read(handle,
+ fui_obj_msg->bg_address,
+ fui_obj_msg->num_of_words,
+ read_buf);
+ break;
+ }
+ if (!ret && copy_to_user(result, read_buf,
+ fui_obj_msg->num_of_words * sizeof(uint32_t))) {
+ pr_err("copy to user failed\n");
+ ret = -EFAULT;
+ }
+ kfree(read_buf);
+ return ret;
+}
+
+static int bgchar_write_cmd(struct bg_ui_data *fui_obj_msg, int type)
+{
+ void *write_buf;
+ int ret;
+ void __user *write = (void *)
+ (uintptr_t)fui_obj_msg->write;
+
+ write_buf = kmalloc_array(fui_obj_msg->num_of_words, sizeof(uint32_t),
+ GFP_KERNEL);
+ if (write_buf == NULL)
+ return -ENOMEM;
+ write_buf = memdup_user(write,
+ fui_obj_msg->num_of_words * sizeof(uint32_t));
+ if (IS_ERR(write_buf)) {
+ ret = PTR_ERR(write_buf);
+ kfree(write_buf);
+ return ret;
+ }
+ switch (type) {
+ case REG_WRITE:
+ ret = bgcom_reg_write(handle, fui_obj_msg->cmd,
+ fui_obj_msg->num_of_words,
+ write_buf);
+ break;
+ case AHB_WRITE:
+ ret = bgcom_ahb_write(handle,
+ fui_obj_msg->bg_address,
+ fui_obj_msg->num_of_words,
+ write_buf);
+ break;
+ }
+ kfree(write_buf);
+ return ret;
+}
+
+int bg_soft_reset(void)
+{
+ /*pull down reset gpio */
+ gpio_direction_output(bgreset_gpio, 0);
+ msleep(50);
+ gpio_set_value(bgreset_gpio, 1);
+ return 0;
+}
+EXPORT_SYMBOL(bg_soft_reset);
+
+static int modem_down2_bg(void)
+{
+ complete(&bg_modem_down_wait);
+ return 0;
+}
+
+static long bg_com_ioctl(struct file *filp,
+ unsigned int ui_bgcom_cmd, unsigned long arg)
+{
+ int ret;
+ struct bg_ui_data ui_obj_msg;
+
+ switch (ui_bgcom_cmd) {
+ case REG_READ:
+ case AHB_READ:
+ if (copy_from_user(&ui_obj_msg, (void __user *) arg,
+ sizeof(ui_obj_msg))) {
+ pr_err("The copy from user failed\n");
+ ret = -EFAULT;
+ }
+ ret = bgchar_read_cmd(&ui_obj_msg,
+ ui_bgcom_cmd);
+ if (ret < 0)
+ pr_err("bgchar_read_cmd failed\n");
+ break;
+ case AHB_WRITE:
+ case REG_WRITE:
+ if (copy_from_user(&ui_obj_msg, (void __user *) arg,
+ sizeof(ui_obj_msg))) {
+ pr_err("The copy from user failed\n");
+ ret = -EFAULT;
+ }
+ ret = bgchar_write_cmd(&ui_obj_msg, ui_bgcom_cmd);
+ if (ret < 0)
+ pr_err("bgchar_write_cmd failed\n");
+ break;
+ case SET_SPI_FREE:
+ ret = bgcom_set_spi_state(BGCOM_SPI_FREE);
+ break;
+ case SET_SPI_BUSY:
+ ret = bgcom_set_spi_state(BGCOM_SPI_BUSY);
+ break;
+ case BG_SOFT_RESET:
+ ret = bg_soft_reset();
+ break;
+ case BG_MODEM_DOWN2_BG_DONE:
+ ret = modem_down2_bg();
+ break;
+ default:
+ ret = -ENOIOCTLCMD;
+ }
+ return ret;
+}
+
+static int bgcom_char_close(struct inode *inode, struct file *file)
+{
+ int ret;
+
+ mutex_lock(&bg_char_mutex);
+ ret = bgcom_close(&handle);
+ device_open = 0;
+ mutex_unlock(&bg_char_mutex);
+ return ret;
+}
+
+static int bg_daemon_probe(struct platform_device *pdev)
+{
+ struct device_node *node;
+ unsigned int reset_gpio;
+ int ret;
+
+ node = pdev->dev.of_node;
+
+ dev = kzalloc(sizeof(struct bgdaemon_priv), GFP_KERNEL);
+ if (!dev)
+ return -ENOMEM;
+
+ reset_gpio = of_get_named_gpio(node, "qcom,bg-reset-gpio", 0);
+ if (!gpio_is_valid(reset_gpio)) {
+ pr_err("gpio %d found is not valid\n", reset_gpio);
+ goto err_ret;
+ }
+
+ if (gpio_request(reset_gpio, "bg_reset_gpio")) {
+ pr_err("gpio %d request failed\n", reset_gpio);
+ goto err_ret;
+ }
+
+ if (gpio_direction_output(reset_gpio, 1)) {
+ pr_err("gpio %d direction not set\n", reset_gpio);
+ goto err_ret;
+ }
+
+ pr_info("bg-soft-reset gpio successfully requested\n");
+ bgreset_gpio = reset_gpio;
+
+ ret = bgdaemon_init_regulators(&pdev->dev);
+ if (ret != 0) {
+ pr_err("Failed to init regulators:%d\n", ret);
+ goto err_device;
+ }
+ ret = bgdaemon_configure_regulators(true);
+ if (ret) {
+ pr_err("Failed to confifigure regulators:%d\n", ret);
+ bgdaemon_configure_regulators(false);
+ goto err_ret;
+ }
+
+err_device:
+ return -ENODEV;
+err_ret:
+ return 0;
+}
+
+static const struct of_device_id bg_daemon_of_match[] = {
+ { .compatible = "qcom,bg-daemon", },
+ { }
+};
+MODULE_DEVICE_TABLE(of, bg_daemon_of_match);
+
+static struct platform_driver bg_daemon_driver = {
+ .probe = bg_daemon_probe,
+ .driver = {
+ .name = "bg-daemon",
+ .of_match_table = bg_daemon_of_match,
+ },
+};
+
+static const struct file_operations fops = {
+ .owner = THIS_MODULE,
+ .open = bgcom_char_open,
+ .release = bgcom_char_close,
+ .unlocked_ioctl = bg_com_ioctl,
+};
+
+static int __init init_bg_com_dev(void)
+{
+ int ret;
+
+ ret = alloc_chrdev_region(&bg_dev, 0, 1, BGCOM);
+ if (ret < 0) {
+ pr_err("failed with error %d\n", ret);
+ return ret;
+ }
+ cdev_init(&bg_cdev, &fops);
+ ret = cdev_add(&bg_cdev, bg_dev, 1);
+ if (ret < 0) {
+ unregister_chrdev_region(bg_dev, 1);
+ pr_err("device registration failed\n");
+ return ret;
+ }
+ bg_class = class_create(THIS_MODULE, BGCOM);
+ if (IS_ERR_OR_NULL(bg_class)) {
+ cdev_del(&bg_cdev);
+ unregister_chrdev_region(bg_dev, 1);
+ pr_err("class creation failed\n");
+ return PTR_ERR(bg_class);
+ }
+
+ dev_ret = device_create(bg_class, NULL, bg_dev, NULL, BGCOM);
+ if (IS_ERR_OR_NULL(dev_ret)) {
+ class_destroy(bg_class);
+ cdev_del(&bg_cdev);
+ unregister_chrdev_region(bg_dev, 1);
+ pr_err("device create failed\n");
+ return PTR_ERR(dev_ret);
+ }
+
+ if (platform_driver_register(&bg_daemon_driver))
+ pr_err("%s: failed to register bg-daemon register\n", __func__);
+
+ return 0;
+}
+
+static void __exit exit_bg_com_dev(void)
+{
+ device_destroy(bg_class, bg_dev);
+ class_destroy(bg_class);
+ cdev_del(&bg_cdev);
+ unregister_chrdev_region(bg_dev, 1);
+ bgdaemon_configure_regulators(false);
+ platform_driver_unregister(&bg_daemon_driver);
+}
+
+/**
+ *ssr_bg_cb(): callback function is called
+ *by ssr framework when BG goes down, up and during ramdump
+ *collection. It handles BG shutdown and power up events.
+ */
+static int ssr_bg_cb(struct notifier_block *this,
+ unsigned long opcode, void *data)
+{
+ struct bg_event bge;
+
+ switch (opcode) {
+ case SUBSYS_BEFORE_SHUTDOWN:
+ bge.e_type = BG_BEFORE_POWER_DOWN;
+ bgdaemon_ldowork(ENABLE_LDO03);
+ bgdaemon_ldowork(ENABLE_LDO09);
+ bgcom_bgdown_handler();
+ bgcom_set_spi_state(BGCOM_SPI_BUSY);
+ send_uevent(&bge);
+ break;
+ case SUBSYS_AFTER_POWERUP:
+ bge.e_type = BG_AFTER_POWER_UP;
+ bgdaemon_ldowork(DISABLE_LDO03);
+ bgdaemon_ldowork(DISABLE_LDO09);
+ bgcom_set_spi_state(BGCOM_SPI_FREE);
+ send_uevent(&bge);
+ break;
+ }
+ return NOTIFY_DONE;
+}
+
+/**
+ *ssr_modem_cb(): callback function is called
+ *by ssr framework when modem goes down, up and during ramdump
+ *collection. It handles modem shutdown and power up events.
+ */
+static int ssr_modem_cb(struct notifier_block *this,
+ unsigned long opcode, void *data)
+{
+ struct bg_event modeme;
+ int ret;
+
+ switch (opcode) {
+ case SUBSYS_BEFORE_SHUTDOWN:
+ modeme.e_type = MODEM_BEFORE_POWER_DOWN;
+ reinit_completion(&bg_modem_down_wait);
+ send_uevent(&modeme);
+ ret = wait_for_completion_timeout(&bg_modem_down_wait,
+ msecs_to_jiffies(MPPS_DOWN_EVENT_TO_BG_TIMEOUT));
+ if (!ret)
+ pr_err("Time out on modem down event\n");
+ break;
+ case SUBSYS_AFTER_POWERUP:
+ modeme.e_type = MODEM_AFTER_POWER_UP;
+ send_uevent(&modeme);
+ break;
+ }
+ return NOTIFY_DONE;
+}
+
+static struct notifier_block ssr_modem_nb = {
+ .notifier_call = ssr_modem_cb,
+ .priority = 0,
+};
+
+static struct notifier_block ssr_bg_nb = {
+ .notifier_call = ssr_bg_cb,
+ .priority = 0,
+};
+
+static struct service_info service_data[2] = {
+ {
+ .name = "SSR_BG",
+ .domain_id = SSR_DOMAIN_BG,
+ .nb = &ssr_bg_nb,
+ .handle = NULL,
+ },
+ {
+ .name = "SSR_MODEM",
+ .domain_id = SSR_DOMAIN_MODEM,
+ .nb = &ssr_modem_nb,
+ .handle = NULL,
+ },
+};
+
+/**
+ * ssr_register checks that domain id should be in range and register
+ * SSR framework for value at domain id.
+ */
+static int __init ssr_register(void)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(service_data); i++) {
+ if ((service_data[i].domain_id < 0) ||
+ (service_data[i].domain_id >= SSR_DOMAIN_MAX)) {
+ pr_err("Invalid service ID = %d\n",
+ service_data[i].domain_id);
+ } else {
+ service_data[i].handle =
+ subsys_notif_register_notifier(
+ ssr_domains[service_data[i].domain_id],
+ service_data[i].nb);
+ if (IS_ERR_OR_NULL(service_data[i].handle)) {
+ pr_err("subsys register failed for id = %d",
+ service_data[i].domain_id);
+ service_data[i].handle = NULL;
+ }
+ }
+ }
+ return 0;
+}
+
+module_init(init_bg_com_dev);
+late_initcall(ssr_register);
+module_exit(exit_bg_com_dev);
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/soc/qcom/bgcom_interface.h b/drivers/soc/qcom/bgcom_interface.h
new file mode 100644
index 0000000..500ca6d
--- /dev/null
+++ b/drivers/soc/qcom/bgcom_interface.h
@@ -0,0 +1,22 @@
+/* Copyright (c) 2017-2018, 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.
+ *
+ */
+#ifndef BGCOM_INTERFACE_H
+#define BGCOM_INTERFACE_H
+
+/**
+ * bg_soft_reset() - soft reset Blackghost
+ * Return 0 on success or -Ve on error
+ */
+int bg_soft_reset(void);
+
+#endif /* BGCOM_INTERFACE_H */
diff --git a/drivers/soc/qcom/bgcom_spi.c b/drivers/soc/qcom/bgcom_spi.c
new file mode 100644
index 0000000..b8e3b84
--- /dev/null
+++ b/drivers/soc/qcom/bgcom_spi.c
@@ -0,0 +1,1010 @@
+/* Copyright (c) 2017-2018, 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.
+ *
+ */
+
+#define pr_fmt(msg) "bgcom: %s: " msg, __func__
+
+#include <linux/init.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/delay.h>
+#include <linux/spi/spi.h>
+#include <linux/ratelimit.h>
+#include <linux/interrupt.h>
+#include <linux/device.h>
+#include <linux/bitops.h>
+#include <linux/gpio.h>
+#include <linux/of_gpio.h>
+#include <linux/kthread.h>
+#include "bgcom.h"
+#include "bgrsb.h"
+#include "bgcom_interface.h"
+
+#define BG_SPI_WORD_SIZE (0x04)
+#define BG_SPI_READ_LEN (0x04)
+#define BG_SPI_WRITE_CMND_LEN (0x01)
+#define BG_SPI_FIFO_READ_CMD (0x41)
+#define BG_SPI_FIFO_WRITE_CMD (0x40)
+#define BG_SPI_AHB_READ_CMD (0x43)
+#define BG_SPI_AHB_WRITE_CMD (0x42)
+#define BG_SPI_AHB_CMD_LEN (0x05)
+#define BG_SPI_AHB_READ_CMD_LEN (0x08)
+#define BG_STATUS_REG (0x05)
+#define BG_CMND_REG (0x14)
+
+#define BG_SPI_MAX_WORDS (0x3FFFFFFD)
+#define BG_SPI_MAX_REGS (0x0A)
+#define SLEEP_IN_STATE_CHNG 2000
+#define HED_EVENT_ID_LEN (0x02)
+#define HED_EVENT_SIZE_LEN (0x02)
+#define HED_EVENT_DATA_STRT_LEN (0x05)
+
+#define MAX_RETRY 200
+
+enum bgcom_state {
+ /*BGCOM Staus ready*/
+ BGCOM_PROB_SUCCESS = 0,
+ BGCOM_PROB_WAIT = 1,
+ BGCOM_STATE_SUSPEND = 2,
+ BGCOM_STATE_ACTIVE = 3
+};
+
+enum bgcom_req_type {
+ /*BGCOM local requests*/
+ BGCOM_READ_REG = 0,
+ BGCOM_READ_FIFO = 1,
+ BGCOM_READ_AHB = 2,
+};
+
+struct bg_spi_priv {
+ struct spi_device *spi;
+ /* Transaction related */
+ struct mutex xfer_mutex;
+ void *lhandle;
+ /* Message for single transfer */
+ struct spi_message msg1;
+ struct spi_transfer xfer1;
+ int irq_lock;
+
+ enum bgcom_state bg_state;
+};
+
+struct cb_data {
+ void *priv;
+ void *handle;
+ void (*bgcom_notification_cb)(void *handle, void *priv,
+ enum bgcom_event_type event,
+ union bgcom_event_data_type *event_data);
+ struct list_head list;
+};
+
+struct bg_context {
+ struct bg_spi_priv *bg_spi;
+ enum bgcom_state state;
+ struct cb_data *cb;
+};
+
+struct event_list {
+ struct event *evnt;
+ struct list_head list;
+};
+static void *bg_com_drv;
+static uint32_t g_slav_status_reg;
+
+/* BGCOM client callbacks set-up */
+static void send_input_events(struct work_struct *work);
+static struct list_head cb_head = LIST_HEAD_INIT(cb_head);
+static struct list_head pr_lst_hd = LIST_HEAD_INIT(pr_lst_hd);
+static enum bgcom_spi_state spi_state;
+
+
+static struct workqueue_struct *wq;
+static DECLARE_WORK(input_work, send_input_events);
+
+static struct mutex bg_resume_mutex;
+
+static void augmnt_fifo(uint8_t *data, int pos)
+{
+ data[pos] = '\0';
+}
+
+static void send_input_events(struct work_struct *work)
+{
+ struct list_head *temp;
+ struct list_head *pos;
+ struct event_list *node;
+ struct event *evnt;
+
+ if (list_empty(&pr_lst_hd))
+ return;
+
+ list_for_each_safe(pos, temp, &pr_lst_hd) {
+ node = list_entry(pos, struct event_list, list);
+ evnt = node->evnt;
+ bgrsb_send_input(evnt);
+ kfree(evnt);
+ list_del(&node->list);
+ kfree(node);
+ }
+}
+
+int bgcom_set_spi_state(enum bgcom_spi_state state)
+{
+ struct bg_spi_priv *bg_spi = container_of(bg_com_drv,
+ struct bg_spi_priv, lhandle);
+ if (state < 0 || state > 1)
+ return -EINVAL;
+
+ if (state == spi_state)
+ return 0;
+
+ mutex_lock(&bg_spi->xfer_mutex);
+ spi_state = state;
+ if (spi_state == BGCOM_SPI_BUSY)
+ msleep(SLEEP_IN_STATE_CHNG);
+ mutex_unlock(&bg_spi->xfer_mutex);
+ return 0;
+}
+EXPORT_SYMBOL(bgcom_set_spi_state);
+
+static inline
+void add_to_irq_list(struct cb_data *data)
+{
+ list_add_tail(&data->list, &cb_head);
+}
+
+static bool is_bgcom_ready(void)
+{
+ return (bg_com_drv != NULL ? true : false);
+}
+
+static void bg_spi_reinit_xfer(struct spi_transfer *xfer)
+{
+ xfer->tx_buf = NULL;
+ xfer->rx_buf = NULL;
+ xfer->delay_usecs = 0;
+ xfer->len = 0;
+}
+
+static int read_bg_locl(enum bgcom_req_type req_type,
+ uint32_t no_of_words, void *buf)
+{
+
+ struct bg_context clnt_handle;
+ struct bg_spi_priv *spi =
+ container_of(bg_com_drv, struct bg_spi_priv, lhandle);
+ int ret = 0;
+
+ if (!buf)
+ return -EINVAL;
+
+ clnt_handle.bg_spi = spi;
+
+ switch (req_type) {
+ case BGCOM_READ_REG:
+ ret = bgcom_reg_read(&clnt_handle,
+ BG_STATUS_REG, no_of_words, buf);
+ break;
+ case BGCOM_READ_FIFO:
+ ret = bgcom_fifo_read(&clnt_handle, no_of_words, buf);
+ break;
+ case BGCOM_READ_AHB:
+ break;
+ }
+ return ret;
+}
+
+static int bgcom_transfer(void *handle, uint8_t *tx_buf,
+ uint8_t *rx_buf, uint32_t txn_len)
+{
+ struct spi_transfer *tx_xfer;
+ struct bg_spi_priv *bg_spi;
+ struct bg_context *cntx;
+ struct spi_device *spi;
+ int ret;
+
+ if (!handle || !tx_buf)
+ return -EINVAL;
+
+ cntx = (struct bg_context *)handle;
+
+ if (cntx->state == BGCOM_PROB_WAIT) {
+ if (!is_bgcom_ready())
+ return -ENODEV;
+ cntx->bg_spi = container_of(bg_com_drv,
+ struct bg_spi_priv, lhandle);
+ cntx->state = BGCOM_PROB_SUCCESS;
+ }
+ bg_spi = cntx->bg_spi;
+
+ if (!bg_spi)
+ return -ENODEV;
+
+ tx_xfer = &bg_spi->xfer1;
+ spi = bg_spi->spi;
+
+ mutex_lock(&bg_spi->xfer_mutex);
+ bg_spi_reinit_xfer(tx_xfer);
+ tx_xfer->tx_buf = tx_buf;
+ if (rx_buf)
+ tx_xfer->rx_buf = rx_buf;
+
+ tx_xfer->len = txn_len;
+ ret = spi_sync(spi, &bg_spi->msg1);
+ mutex_unlock(&bg_spi->xfer_mutex);
+
+ if (ret)
+ pr_err("SPI transaction failed: %d\n", ret);
+ return ret;
+}
+
+/* BG-COM Interrupt handling */
+static inline
+void send_event(enum bgcom_event_type event,
+ void *data)
+{
+ struct list_head *pos;
+ struct cb_data *cb;
+
+ /* send interrupt notification for each
+ * registered call-back
+ */
+ list_for_each(pos, &cb_head) {
+ cb = list_entry(pos, struct cb_data, list);
+ cb->bgcom_notification_cb(cb->handle,
+ cb->priv, event, data);
+ }
+}
+
+void bgcom_bgdown_handler(void)
+{
+ send_event(BGCOM_EVENT_RESET_OCCURRED, NULL);
+ g_slav_status_reg = 0;
+}
+EXPORT_SYMBOL(bgcom_bgdown_handler);
+
+static void parse_fifo(uint8_t *data, union bgcom_event_data_type *event_data)
+{
+ uint16_t p_len;
+ uint8_t sub_id;
+ uint32_t evnt_tm;
+ uint16_t event_id;
+ void *evnt_data;
+ struct event *evnt;
+ struct event_list *data_list;
+
+ while (*data != '\0') {
+
+ event_id = *((uint16_t *) data);
+ data = data + HED_EVENT_ID_LEN;
+ p_len = *((uint16_t *) data);
+ data = data + HED_EVENT_SIZE_LEN;
+
+ if (event_id == 0xFFFE) {
+
+ sub_id = *data;
+ evnt_tm = *((uint32_t *)(data+1));
+
+ evnt = kmalloc(sizeof(*evnt), GFP_KERNEL);
+ evnt->sub_id = sub_id;
+ evnt->evnt_tm = evnt_tm;
+ evnt->evnt_data =
+ *(int16_t *)(data + HED_EVENT_DATA_STRT_LEN);
+
+ data_list = kmalloc(sizeof(*data_list), GFP_KERNEL);
+ data_list->evnt = evnt;
+ list_add_tail(&data_list->list, &pr_lst_hd);
+
+ } else if (event_id == 0x0001) {
+ evnt_data = kmalloc(p_len, GFP_KERNEL);
+ if (evnt_data != NULL) {
+ memcpy(evnt_data, data, p_len);
+ event_data->fifo_data.to_master_fifo_used =
+ p_len/BG_SPI_WORD_SIZE;
+ event_data->fifo_data.data = evnt_data;
+ send_event(BGCOM_EVENT_TO_MASTER_FIFO_USED,
+ event_data);
+ }
+ }
+ data = data + p_len;
+ }
+ if (!list_empty(&pr_lst_hd))
+ queue_work(wq, &input_work);
+}
+
+static void send_back_notification(uint32_t slav_status_reg,
+ uint32_t slav_status_auto_clear_reg,
+ uint32_t fifo_fill_reg, uint32_t fifo_size_reg)
+{
+ uint16_t master_fifo_used;
+ uint16_t slave_fifo_free;
+ uint32_t *ptr;
+ int ret;
+ union bgcom_event_data_type event_data = { .fifo_data = {0} };
+
+ master_fifo_used = (uint16_t)fifo_fill_reg;
+ slave_fifo_free = (uint16_t)(fifo_fill_reg >> 16);
+
+ if (slav_status_auto_clear_reg & BIT(31))
+ send_event(BGCOM_EVENT_RESET_OCCURRED, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(30))
+ send_event(BGCOM_EVENT_ERROR_WRITE_FIFO_OVERRUN, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(29))
+ send_event(BGCOM_EVENT_ERROR_WRITE_FIFO_BUS_ERR, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(28))
+ send_event(BGCOM_EVENT_ERROR_WRITE_FIFO_ACCESS, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(27))
+ send_event(BGCOM_EVENT_ERROR_READ_FIFO_UNDERRUN, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(26))
+ send_event(BGCOM_EVENT_ERROR_READ_FIFO_BUS_ERR, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(25))
+ send_event(BGCOM_EVENT_ERROR_READ_FIFO_ACCESS, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(24))
+ send_event(BGCOM_EVENT_ERROR_TRUNCATED_READ, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(23))
+ send_event(BGCOM_EVENT_ERROR_TRUNCATED_WRITE, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(22))
+ send_event(BGCOM_EVENT_ERROR_AHB_ILLEGAL_ADDRESS, NULL);
+
+ if (slav_status_auto_clear_reg & BIT(21))
+ send_event(BGCOM_EVENT_ERROR_AHB_BUS_ERR, NULL);
+
+ /* check if BG status is changed */
+ if (g_slav_status_reg ^ slav_status_reg) {
+ if (slav_status_reg & BIT(30)) {
+ event_data.application_running = true;
+ send_event(BGCOM_EVENT_APPLICATION_RUNNING,
+ &event_data);
+ }
+
+ if (slav_status_reg & BIT(29)) {
+ event_data.to_slave_fifo_ready = true;
+ send_event(BGCOM_EVENT_TO_SLAVE_FIFO_READY,
+ &event_data);
+ }
+
+ if (slav_status_reg & BIT(28)) {
+ event_data.to_master_fifo_ready = true;
+ send_event(BGCOM_EVENT_TO_MASTER_FIFO_READY,
+ &event_data);
+ }
+
+ if (slav_status_reg & BIT(27)) {
+ event_data.ahb_ready = true;
+ send_event(BGCOM_EVENT_AHB_READY,
+ &event_data);
+ }
+ }
+
+ if (master_fifo_used > 0) {
+ ptr = kzalloc(master_fifo_used*BG_SPI_WORD_SIZE + 1,
+ GFP_KERNEL | GFP_ATOMIC);
+ if (ptr != NULL) {
+ ret = read_bg_locl(BGCOM_READ_FIFO,
+ master_fifo_used, ptr);
+ if (!ret) {
+ augmnt_fifo((uint8_t *)ptr,
+ master_fifo_used*BG_SPI_WORD_SIZE);
+ parse_fifo((uint8_t *)ptr, &event_data);
+ }
+ kfree(ptr);
+ }
+ }
+
+ event_data.to_slave_fifo_free = slave_fifo_free;
+ send_event(BGCOM_EVENT_TO_SLAVE_FIFO_FREE, &event_data);
+}
+
+static void bg_irq_tasklet_hndlr_l(void)
+{
+ uint32_t slave_status_reg;
+ uint32_t glink_isr_reg;
+ uint32_t slav_status_auto_clear_reg;
+ uint32_t fifo_fill_reg;
+ uint32_t fifo_size_reg;
+ int ret = 0;
+ uint32_t irq_buf[5] = {0};
+
+ ret = read_bg_locl(BGCOM_READ_REG, 5, &irq_buf[0]);
+ if (ret)
+ return;
+
+ /* save current state */
+ slave_status_reg = irq_buf[0];
+ glink_isr_reg = irq_buf[1];
+ slav_status_auto_clear_reg = irq_buf[2];
+ fifo_fill_reg = irq_buf[3];
+ fifo_size_reg = irq_buf[4];
+
+ send_back_notification(slave_status_reg,
+ slav_status_auto_clear_reg, fifo_fill_reg, fifo_size_reg);
+
+ g_slav_status_reg = slave_status_reg;
+}
+
+int bgcom_ahb_read(void *handle, uint32_t ahb_start_addr,
+ uint32_t num_words, void *read_buf)
+{
+ uint32_t txn_len;
+ uint8_t *tx_buf;
+ uint8_t *rx_buf;
+ uint32_t size;
+ int ret;
+ uint8_t cmnd = 0;
+ uint32_t ahb_addr = 0;
+
+ if (!handle || !read_buf || num_words == 0
+ || num_words > BG_SPI_MAX_WORDS) {
+ pr_err("Invalid param\n");
+ return -EINVAL;
+ }
+ if (!is_bgcom_ready())
+ return -ENODEV;
+
+ if (spi_state == BGCOM_SPI_BUSY) {
+ pr_err("Device busy\n");
+ return -EBUSY;
+ }
+
+ if (bgcom_resume(handle)) {
+ pr_err("Failed to resume\n");
+ return -EBUSY;
+ }
+
+ size = num_words*BG_SPI_WORD_SIZE;
+ txn_len = BG_SPI_AHB_READ_CMD_LEN + size;
+
+ tx_buf = kzalloc(txn_len, GFP_KERNEL);
+
+ if (!tx_buf)
+ return -ENOMEM;
+
+ rx_buf = kzalloc(txn_len, GFP_KERNEL);
+
+ if (!rx_buf) {
+ kfree(tx_buf);
+ return -ENOMEM;
+ }
+
+ cmnd |= BG_SPI_AHB_READ_CMD;
+ ahb_addr |= ahb_start_addr;
+
+ memcpy(tx_buf, &cmnd, sizeof(cmnd));
+ memcpy(tx_buf+sizeof(cmnd), &ahb_addr, sizeof(ahb_addr));
+
+ ret = bgcom_transfer(handle, tx_buf, rx_buf, txn_len);
+
+ if (!ret)
+ memcpy(read_buf, rx_buf+BG_SPI_AHB_READ_CMD_LEN, size);
+
+ kfree(tx_buf);
+ kfree(rx_buf);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_ahb_read);
+
+int bgcom_ahb_write(void *handle, uint32_t ahb_start_addr,
+ uint32_t num_words, void *write_buf)
+{
+ uint32_t txn_len;
+ uint8_t *tx_buf;
+ uint32_t size;
+ int ret;
+ uint8_t cmnd = 0;
+ uint32_t ahb_addr = 0;
+
+ if (!handle || !write_buf || num_words == 0
+ || num_words > BG_SPI_MAX_WORDS) {
+ pr_err("Invalid param\n");
+ return -EINVAL;
+ }
+
+ if (!is_bgcom_ready())
+ return -ENODEV;
+
+ if (spi_state == BGCOM_SPI_BUSY) {
+ pr_err("Device busy\n");
+ return -EBUSY;
+ }
+
+ if (bgcom_resume(handle)) {
+ pr_err("Failed to resume\n");
+ return -EBUSY;
+ }
+
+ size = num_words*BG_SPI_WORD_SIZE;
+ txn_len = BG_SPI_AHB_CMD_LEN + size;
+
+ tx_buf = kzalloc(txn_len, GFP_KERNEL);
+
+ if (!tx_buf)
+ return -ENOMEM;
+
+ cmnd |= BG_SPI_AHB_WRITE_CMD;
+ ahb_addr |= ahb_start_addr;
+
+ memcpy(tx_buf, &cmnd, sizeof(cmnd));
+ memcpy(tx_buf+sizeof(cmnd), &ahb_addr, sizeof(ahb_addr));
+ memcpy(tx_buf+BG_SPI_AHB_CMD_LEN, write_buf, size);
+
+ ret = bgcom_transfer(handle, tx_buf, NULL, txn_len);
+ kfree(tx_buf);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_ahb_write);
+
+int bgcom_fifo_write(void *handle, uint32_t num_words,
+ void *write_buf)
+{
+ uint32_t txn_len;
+ uint8_t *tx_buf;
+ uint32_t size;
+ int ret;
+ uint8_t cmnd = 0;
+
+ if (!handle || !write_buf || num_words == 0
+ || num_words > BG_SPI_MAX_WORDS) {
+ pr_err("Invalid param\n");
+ return -EINVAL;
+ }
+
+ if (!is_bgcom_ready())
+ return -ENODEV;
+
+ if (spi_state == BGCOM_SPI_BUSY) {
+ pr_err("Device busy\n");
+ return -EBUSY;
+ }
+
+ if (bgcom_resume(handle)) {
+ pr_err("Failed to resume\n");
+ return -EBUSY;
+ }
+
+ size = num_words*BG_SPI_WORD_SIZE;
+ txn_len = BG_SPI_WRITE_CMND_LEN + size;
+
+ tx_buf = kzalloc(txn_len, GFP_KERNEL | GFP_ATOMIC);
+
+ if (!tx_buf)
+ return -ENOMEM;
+
+ cmnd |= BG_SPI_FIFO_WRITE_CMD;
+ memcpy(tx_buf, &cmnd, sizeof(cmnd));
+ memcpy(tx_buf+sizeof(cmnd), write_buf, size);
+
+ ret = bgcom_transfer(handle, tx_buf, NULL, txn_len);
+ kfree(tx_buf);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_fifo_write);
+
+int bgcom_fifo_read(void *handle, uint32_t num_words,
+ void *read_buf)
+{
+ uint32_t txn_len;
+ uint8_t *tx_buf;
+ uint8_t *rx_buf;
+ uint32_t size;
+ uint8_t cmnd = 0;
+ int ret = 0;
+
+ if (!handle || !read_buf || num_words == 0
+ || num_words > BG_SPI_MAX_WORDS) {
+ pr_err("Invalid param\n");
+ return -EINVAL;
+ }
+
+ if (!is_bgcom_ready())
+ return -ENODEV;
+
+ if (spi_state == BGCOM_SPI_BUSY) {
+ pr_err("Device busy\n");
+ return -EBUSY;
+ }
+
+ size = num_words*BG_SPI_WORD_SIZE;
+ txn_len = BG_SPI_READ_LEN + size;
+ tx_buf = kzalloc(txn_len, GFP_KERNEL | GFP_ATOMIC);
+
+ if (!tx_buf)
+ return -ENOMEM;
+
+ rx_buf = kzalloc(txn_len, GFP_KERNEL | GFP_ATOMIC);
+
+ if (!rx_buf) {
+ kfree(tx_buf);
+ return -ENOMEM;
+ }
+
+ cmnd |= BG_SPI_FIFO_READ_CMD;
+ memcpy(tx_buf, &cmnd, sizeof(cmnd));
+
+ ret = bgcom_transfer(handle, tx_buf, rx_buf, txn_len);
+
+ if (!ret)
+ memcpy(read_buf, rx_buf+BG_SPI_READ_LEN, size);
+ kfree(tx_buf);
+ kfree(rx_buf);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_fifo_read);
+
+int bgcom_reg_write(void *handle, uint8_t reg_start_addr,
+ uint8_t num_regs, void *write_buf)
+{
+ uint32_t txn_len;
+ uint8_t *tx_buf;
+ uint32_t size;
+ uint8_t cmnd = 0;
+ int ret = 0;
+
+ if (!handle || !write_buf || num_regs == 0
+ || num_regs > BG_SPI_MAX_REGS) {
+ pr_err("Invalid param\n");
+ return -EINVAL;
+ }
+
+ if (!is_bgcom_ready())
+ return -ENODEV;
+
+ if (spi_state == BGCOM_SPI_BUSY) {
+ pr_err("Device busy\n");
+ return -EBUSY;
+ }
+
+ size = num_regs*BG_SPI_WORD_SIZE;
+ txn_len = BG_SPI_WRITE_CMND_LEN + size;
+
+ tx_buf = kzalloc(txn_len, GFP_KERNEL);
+
+ if (!tx_buf)
+ return -ENOMEM;
+
+ cmnd |= reg_start_addr;
+ memcpy(tx_buf, &cmnd, sizeof(cmnd));
+ memcpy(tx_buf+sizeof(cmnd), write_buf, size);
+
+ ret = bgcom_transfer(handle, tx_buf, NULL, txn_len);
+ kfree(tx_buf);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_reg_write);
+
+int bgcom_reg_read(void *handle, uint8_t reg_start_addr,
+ uint32_t num_regs, void *read_buf)
+{
+ uint32_t txn_len;
+ uint8_t *tx_buf;
+ uint8_t *rx_buf;
+ uint32_t size;
+ int ret;
+ uint8_t cmnd = 0;
+
+ if (!handle || !read_buf || num_regs == 0
+ || num_regs > BG_SPI_MAX_REGS) {
+ pr_err("Invalid param\n");
+ return -EINVAL;
+ }
+
+ if (!is_bgcom_ready())
+ return -ENODEV;
+
+ if (spi_state == BGCOM_SPI_BUSY) {
+ pr_err("Device busy\n");
+ return -EBUSY;
+ }
+
+ size = num_regs*BG_SPI_WORD_SIZE;
+ txn_len = BG_SPI_READ_LEN + size;
+
+ tx_buf = kzalloc(txn_len, GFP_KERNEL | GFP_ATOMIC);
+
+ if (!tx_buf)
+ return -ENOMEM;
+
+ rx_buf = kzalloc(txn_len, GFP_KERNEL | GFP_ATOMIC);
+
+ if (!rx_buf) {
+ kfree(tx_buf);
+ return -ENOMEM;
+ }
+
+ cmnd |= reg_start_addr;
+ memcpy(tx_buf, &cmnd, sizeof(cmnd));
+
+ ret = bgcom_transfer(handle, tx_buf, rx_buf, txn_len);
+
+ if (!ret)
+ memcpy(read_buf, rx_buf+BG_SPI_READ_LEN, size);
+ kfree(tx_buf);
+ kfree(rx_buf);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_reg_read);
+
+static int is_bg_resume(void *handle)
+{
+ uint32_t txn_len;
+ int ret;
+ uint8_t tx_buf[8] = {0};
+ uint8_t rx_buf[8] = {0};
+ uint32_t cmnd_reg = 0;
+
+ txn_len = 0x08;
+ tx_buf[0] = 0x05;
+ ret = bgcom_transfer(handle, tx_buf, rx_buf, txn_len);
+ if (!ret)
+ memcpy(&cmnd_reg, rx_buf+BG_SPI_READ_LEN, 0x04);
+ return cmnd_reg & BIT(31);
+}
+
+int bgcom_resume(void *handle)
+{
+ struct bg_spi_priv *bg_spi;
+ struct bg_context *cntx;
+ int retry = 0;
+
+ if (handle == NULL)
+ return -EINVAL;
+
+ cntx = (struct bg_context *)handle;
+ bg_spi = cntx->bg_spi;
+
+ mutex_lock(&bg_resume_mutex);
+ if (bg_spi->bg_state == BGCOM_STATE_ACTIVE)
+ goto unlock;
+ do {
+ if (is_bg_resume(handle)) {
+ bg_spi->bg_state = BGCOM_STATE_ACTIVE;
+ break;
+ }
+ udelay(10);
+ ++retry;
+ } while (retry < MAX_RETRY);
+
+unlock:
+ mutex_unlock(&bg_resume_mutex);
+ if (retry == MAX_RETRY) {
+ /* BG failed to resume. Trigger BG soft reset. */
+ pr_err("BG failed to resume\n");
+ bg_soft_reset();
+ return -ETIMEDOUT;
+ }
+ pr_info("BG retries for wake up : %d\n", retry);
+ return 0;
+}
+EXPORT_SYMBOL(bgcom_resume);
+
+int bgcom_suspend(void *handle)
+{
+ struct bg_spi_priv *bg_spi;
+ struct bg_context *cntx;
+ uint32_t cmnd_reg = 0;
+ int ret = 0;
+
+ if (handle == NULL)
+ return -EINVAL;
+
+ cntx = (struct bg_context *)handle;
+ bg_spi = cntx->bg_spi;
+ mutex_lock(&bg_resume_mutex);
+ if (bg_spi->bg_state == BGCOM_STATE_SUSPEND)
+ goto unlock;
+
+ cmnd_reg |= BIT(31);
+ ret = bgcom_reg_write(handle, BG_CMND_REG, 1, &cmnd_reg);
+ if (ret == 0)
+ bg_spi->bg_state = BGCOM_STATE_SUSPEND;
+
+unlock:
+ mutex_unlock(&bg_resume_mutex);
+ pr_info("suspended with : %d\n", ret);
+ return ret;
+}
+EXPORT_SYMBOL(bgcom_suspend);
+
+void *bgcom_open(struct bgcom_open_config_type *open_config)
+{
+ struct bg_spi_priv *spi;
+ struct cb_data *irq_notification;
+ struct bg_context *clnt_handle =
+ kzalloc(sizeof(*clnt_handle), GFP_KERNEL);
+
+ if (!clnt_handle)
+ return NULL;
+
+ /* Client handle Set-up */
+ if (!is_bgcom_ready()) {
+ clnt_handle->bg_spi = NULL;
+ clnt_handle->state = BGCOM_PROB_WAIT;
+ } else {
+ spi = container_of(bg_com_drv, struct bg_spi_priv, lhandle);
+ clnt_handle->bg_spi = spi;
+ clnt_handle->state = BGCOM_PROB_SUCCESS;
+ }
+ clnt_handle->cb = NULL;
+ /* Interrupt callback Set-up */
+ if (open_config && open_config->bgcom_notification_cb) {
+ irq_notification = kzalloc(sizeof(*irq_notification),
+ GFP_KERNEL);
+ if (!irq_notification)
+ goto error_ret;
+
+ /* set irq node */
+ irq_notification->handle = clnt_handle;
+ irq_notification->priv = open_config->priv;
+ irq_notification->bgcom_notification_cb =
+ open_config->bgcom_notification_cb;
+ add_to_irq_list(irq_notification);
+ clnt_handle->cb = irq_notification;
+ }
+ return clnt_handle;
+
+error_ret:
+ kfree(clnt_handle);
+ return NULL;
+}
+EXPORT_SYMBOL(bgcom_open);
+
+int bgcom_close(void **handle)
+{
+ struct bg_context *lhandle;
+ struct cb_data *cb = NULL;
+
+ if (*handle == NULL)
+ return -EINVAL;
+ lhandle = *handle;
+ cb = lhandle->cb;
+ if (cb)
+ list_del(&cb->list);
+
+ kfree(*handle);
+ *handle = NULL;
+ return 0;
+}
+EXPORT_SYMBOL(bgcom_close);
+
+static irqreturn_t bg_irq_tasklet_hndlr(int irq, void *device)
+{
+ struct bg_spi_priv *bg_spi = device;
+ /* check if call-back exists */
+ if (list_empty(&cb_head)) {
+ pr_debug("No callback registered\n");
+ return IRQ_HANDLED;
+ } else if (spi_state == BGCOM_SPI_BUSY) {
+ return IRQ_HANDLED;
+ } else if (!bg_spi->irq_lock) {
+ bg_spi->irq_lock = 1;
+ bg_irq_tasklet_hndlr_l();
+ bg_spi->irq_lock = 0;
+ }
+ return IRQ_HANDLED;
+}
+
+static void bg_spi_init(struct bg_spi_priv *bg_spi)
+{
+ if (!bg_spi) {
+ pr_err("device not found\n");
+ return;
+ }
+
+ /* BGCOM SPI set-up */
+ mutex_init(&bg_spi->xfer_mutex);
+ spi_message_init(&bg_spi->msg1);
+ spi_message_add_tail(&bg_spi->xfer1, &bg_spi->msg1);
+
+ /* BGCOM IRQ set-up */
+ bg_spi->irq_lock = 0;
+
+ spi_state = BGCOM_SPI_FREE;
+
+ wq = create_singlethread_workqueue("input_wq");
+
+ bg_spi->bg_state = BGCOM_STATE_ACTIVE;
+
+ bg_com_drv = &bg_spi->lhandle;
+
+ mutex_init(&bg_resume_mutex);
+}
+
+static int bg_spi_probe(struct spi_device *spi)
+{
+ struct bg_spi_priv *bg_spi;
+ struct device_node *node;
+ int irq_gpio = 0;
+ int bg_irq = 0;
+ int ret;
+
+ bg_spi = devm_kzalloc(&spi->dev, sizeof(*bg_spi),
+ GFP_KERNEL | GFP_ATOMIC);
+ if (!bg_spi)
+ return -ENOMEM;
+ bg_spi->spi = spi;
+ spi_set_drvdata(spi, bg_spi);
+ bg_spi_init(bg_spi);
+
+ /* BGCOM Interrupt probe */
+ node = spi->dev.of_node;
+ irq_gpio = of_get_named_gpio(node, "qcom,irq-gpio", 0);
+ if (!gpio_is_valid(irq_gpio)) {
+ pr_err("gpio %d found is not valid\n", irq_gpio);
+ goto err_ret;
+ }
+
+ ret = gpio_request(irq_gpio, "bgcom_gpio");
+ if (ret) {
+ pr_err("gpio %d request failed\n", irq_gpio);
+ goto err_ret;
+ }
+
+ ret = gpio_direction_input(irq_gpio);
+ if (ret) {
+ pr_err("gpio_direction_input not set: %d\n", ret);
+ goto err_ret;
+ }
+
+ bg_irq = gpio_to_irq(irq_gpio);
+ ret = request_threaded_irq(bg_irq, NULL, bg_irq_tasklet_hndlr,
+ IRQF_TRIGGER_HIGH | IRQF_ONESHOT, "qcom,bg_spi", bg_spi);
+
+ if (ret)
+ goto err_ret;
+
+ pr_info("Bgcom Probed successfully\n");
+ return ret;
+
+err_ret:
+ bg_com_drv = NULL;
+ mutex_destroy(&bg_spi->xfer_mutex);
+ spi_set_drvdata(spi, NULL);
+ return -ENODEV;
+}
+
+static int bg_spi_remove(struct spi_device *spi)
+{
+ struct bg_spi_priv *bg_spi = spi_get_drvdata(spi);
+
+ mutex_destroy(&bg_spi->xfer_mutex);
+ devm_kfree(&spi->dev, bg_spi);
+ spi_set_drvdata(spi, NULL);
+
+ return 0;
+}
+
+static const struct of_device_id bg_spi_of_match[] = {
+ { .compatible = "qcom,bg-spi", },
+ { }
+};
+MODULE_DEVICE_TABLE(of, bg_spi_of_match);
+
+static struct spi_driver bg_spi_driver = {
+ .driver = {
+ .name = "bg-spi",
+ .of_match_table = bg_spi_of_match,
+ },
+ .probe = bg_spi_probe,
+ .remove = bg_spi_remove,
+};
+
+module_spi_driver(bg_spi_driver);
+MODULE_DESCRIPTION("bg SPI driver");
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/soc/qcom/bgrsb.h b/drivers/soc/qcom/bgrsb.h
new file mode 100644
index 0000000..1ad23b7
--- /dev/null
+++ b/drivers/soc/qcom/bgrsb.h
@@ -0,0 +1,36 @@
+/* Copyright (c) 2017-2018, 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.
+ *
+ */
+
+#ifndef BGRSB_H
+#define BGRSB_H
+
+struct event {
+ uint8_t sub_id;
+ int16_t evnt_data;
+ uint32_t evnt_tm;
+};
+
+
+struct bg_glink_chnl {
+ char *chnl_name;
+ char *chnl_edge;
+ char *chnl_trnsprt;
+};
+
+/**
+ * bgrsb_send_input() - send the recived input to input framework
+ * @evnt: pointer to the event structure
+ */
+int bgrsb_send_input(struct event *evnt);
+
+#endif /* BGCOM_H */
diff --git a/drivers/soc/qcom/dcc_v2.c b/drivers/soc/qcom/dcc_v2.c
index 41a1a79..7c54073 100644
--- a/drivers/soc/qcom/dcc_v2.c
+++ b/drivers/soc/qcom/dcc_v2.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2015-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2015-2018, 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
@@ -1635,7 +1635,7 @@
}
static const struct of_device_id msm_dcc_match[] = {
- { .compatible = "qcom,dcc_v2"},
+ { .compatible = "qcom,dcc-v2"},
{}
};
diff --git a/drivers/soc/qcom/glink.c b/drivers/soc/qcom/glink.c
index 4892f50..b8deec1 100644
--- a/drivers/soc/qcom/glink.c
+++ b/drivers/soc/qcom/glink.c
@@ -457,6 +457,42 @@
rwref_put(&ctx->ch_state_lhb2);
}
+
+/**
+ * glink_subsys_up() - Inform transport about remote subsystem up.
+ * @subsystem: The name of the subsystem
+ *
+ * Call into the transport using the subsys_up(if_ptr) function to allow it to
+ * initialize any necessary structures.
+ *
+ * Return: Standard error codes.
+ */
+int glink_subsys_up(const char *subsystem)
+{
+ int ret = 0;
+ bool transport_found = false;
+ struct glink_core_xprt_ctx *xprt_ctx = NULL;
+
+ mutex_lock(&transport_list_lock_lha0);
+ list_for_each_entry(xprt_ctx, &transport_list, list_node) {
+ if (!strcmp(subsystem, xprt_ctx->edge) &&
+ !xprt_is_fully_opened(xprt_ctx)) {
+ GLINK_INFO_XPRT(xprt_ctx, "%s: %s Subsystem up\n",
+ __func__, subsystem);
+ if (xprt_ctx->ops->subsys_up)
+ xprt_ctx->ops->subsys_up(xprt_ctx->ops);
+ transport_found = true;
+ }
+ }
+ mutex_unlock(&transport_list_lock_lha0);
+
+ if (!transport_found)
+ ret = -ENODEV;
+
+ return ret;
+}
+EXPORT_SYMBOL(glink_subsys_up);
+
/**
* glink_ssr() - Clean up locally for SSR by simulating remote close
* @subsystem: The name of the subsystem being restarted
@@ -3792,6 +3828,10 @@
*/
int glink_xprt_name_to_id(const char *name, uint16_t *id)
{
+ if (!strcmp(name, "bgcom")) {
+ *id = SPIV2_XPRT_ID;
+ return 0;
+ }
if (!strcmp(name, "smem")) {
*id = SMEM_XPRT_ID;
return 0;
diff --git a/drivers/soc/qcom/glink_bgcom_xprt.c b/drivers/soc/qcom/glink_bgcom_xprt.c
new file mode 100644
index 0000000..3c3923c
--- /dev/null
+++ b/drivers/soc/qcom/glink_bgcom_xprt.c
@@ -0,0 +1,1754 @@
+/* Copyright (c) 2017-2018, 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 <linux/delay.h>
+#include <linux/err.h>
+#include <linux/gfp.h>
+#include <linux/kernel.h>
+#include <linux/kthread.h>
+#include <linux/list.h>
+#include <linux/module.h>
+#include <linux/mutex.h>
+#include <linux/of.h>
+#include <linux/platform_device.h>
+#include <linux/printk.h>
+#include <linux/sched.h>
+#include <linux/seq_file.h>
+#include <linux/slab.h>
+#include <linux/spinlock.h>
+#include <linux/srcu.h>
+#include <linux/wait.h>
+#include <linux/component.h>
+#include <soc/qcom/tracer_pkt.h>
+
+#include "glink_core_if.h"
+#include "glink_private.h"
+#include "glink_xprt_if.h"
+#include "bgcom.h"
+
+#define XPRT_NAME "bgcom"
+#define FIFO_ALIGNMENT 16
+#define TRACER_PKT_FEATURE BIT(2)
+
+#define ACTIVE_TX BIT(0)
+#define ACTIVE_RX BIT(1)
+
+#define ID_MASK 0xFFFFFF
+
+#define BGCOM_RESET 0x00000000
+#define BGCOM_APPLICATION_RUNNING 0x00000001
+#define BGCOM_TO_SLAVE_FIFO_READY 0x00000002
+#define BGCOM_TO_MASTER_FIFO_READY 0x00000004
+#define BGCOM_AHB_READY 0x00000008
+#define WORD_SIZE 4
+#define TX_BLOCKED_CMD_RESERVE 16
+#define FIFO_FULL_RESERVE (TX_BLOCKED_CMD_RESERVE/WORD_SIZE)
+#define BGCOM_LINKUP (BGCOM_APPLICATION_RUNNING \
+ | BGCOM_TO_SLAVE_FIFO_READY \
+ | BGCOM_TO_MASTER_FIFO_READY \
+ | BGCOM_AHB_READY)
+/**
+ * enum command_types - definition of the types of commands sent/received
+ * @VERSION_CMD: Version and feature set supported
+ * @VERSION_ACK_CMD: Response for @VERSION_CMD
+ * @OPEN_CMD: Open a channel
+ * @CLOSE_CMD: Close a channel
+ * @OPEN_ACK_CMD: Response to @OPEN_CMD
+ * @CLOSE_ACK_CMD: Response for @CLOSE_CMD
+ * @RX_INTENT_CMD: RX intent for a channel is queued
+ * @RX_DONE_CMD: Use of RX intent for a channel is complete
+ * @RX_DONE_W_REUSE_CMD: Same as @RX_DONE but also reuse the used intent
+ * @RX_INTENT_REQ_CMD: Request to have RX intent queued
+ * @RX_INTENT_REQ_ACK_CMD: Response for @RX_INTENT_REQ_CMD
+ * @TX_DATA_CMD: Start of a data transfer
+ * @TX_DATA_CONT_CMD: Continuation or end of a data transfer
+ * @READ_NOTIF_CMD: Request for a notification when this cmd is read
+ * @SIGNALS_CMD: Sideband signals
+ * @TRACER_PKT_CMD: Start of a Tracer Packet Command
+ * @TRACER_PKT_CONT_CMD: Continuation or end of a Tracer Packet Command
+ */
+enum command_types {
+ VERSION_CMD,
+ VERSION_ACK_CMD,
+ OPEN_CMD,
+ CLOSE_CMD,
+ OPEN_ACK_CMD,
+ CLOSE_ACK_CMD,
+ RX_INTENT_CMD,
+ RX_DONE_CMD,
+ RX_DONE_W_REUSE_CMD,
+ RX_INTENT_REQ_CMD,
+ RX_INTENT_REQ_ACK_CMD,
+ TX_DATA_CMD,
+ TX_DATA_CONT_CMD,
+ READ_NOTIF_CMD,
+ SIGNALS_CMD,
+ TRACER_PKT_CMD,
+ TRACER_PKT_CONT_CMD,
+};
+
+struct bgcom_fifo_size {
+ uint32_t to_master:16;
+ uint32_t to_slave:16;
+};
+
+struct bgcom_fifo_fill {
+ uint32_t rx_avail:16;
+ uint32_t tx_avail:16;
+};
+
+/**
+ * struct edge_info - local information for managing a single complete edge
+ * @list: List item to traverse in edge_info list
+ * @xprt_if: The transport interface registered with the
+ * glink core associated with this edge.
+ * @xprt_cfg: The transport configuration for the glink core
+ * assocaited with this edge.
+ * @subsys_name: Name of the remote subsystem in the edge.
+ * @bgcom_dev: Pointer to the connectingSPI Device.
+ * @fifo_size: Size of the FIFO at the remote end.
+ * @fifo_fill: Current available fifo size.
+ * @tx_avail_lock: Lock to serialize access to tx_avail.
+ * @kwork: Work to be executed when receiving data.
+ * @kworker: Handle to the entity processing @kwork.
+ * @task: Handle to the task context that runs @kworker.
+ * @use_ref: Active users of this transport grab a
+ * reference. Used for SSR synchronization.
+ * @in_ssr: Signals if this transport is in ssr.
+ * @water_mark_reached Signals if tx_avail need to read from fifo.
+ * @write_lock: Lock to serialize write/tx operation.
+ * @tx_blocked_queue: Queue of entities waiting for the remote side to
+ * signal the resumption of TX.
+ * @tx_resume_needed: A tx resume signal needs to be sent to the glink
+ * core.
+ * @tx_blocked_signal_sent: Flag to indicate the flush signal has already
+ * been sent, and a response is pending from the
+ * remote side. Protected by @write_lock.
+ * @num_pw_states: Size of @ramp_time_us.
+ * @ramp_time_us: Array of ramp times in microseconds where array
+ * index position represents a power state.
+ * @bgcom_status Maintains bgcom status based on events.
+ * @wakeup_work : Work item for waking up tx_thread
+ * @activity_flag: Flag indicating active TX and RX.
+ * @activity_lock: Lock to synchronize access to activity flag.
+ * @bgcom_config: Config to be given to bgcom driver.
+ * @bgcom_handle: Handle to use bgcom driver apis.
+ */
+struct edge_info {
+ struct list_head list;
+ struct glink_transport_if xprt_if;
+ struct glink_core_transport_cfg xprt_cfg;
+ char subsys_name[GLINK_NAME_SIZE];
+ struct bgcom_device *bgcom_dev;
+
+ struct bgcom_fifo_size fifo_size;
+ struct bgcom_fifo_fill fifo_fill;
+ struct mutex tx_avail_lock;
+
+ struct kthread_worker kworker;
+ struct task_struct *task;
+ struct srcu_struct use_ref;
+ bool in_ssr;
+ bool water_mark_reached;
+ struct mutex write_lock;
+ wait_queue_head_t tx_blocked_queue;
+ bool tx_resume_needed;
+ bool tx_blocked_signal_sent;
+
+ uint32_t num_pw_states;
+ unsigned long *ramp_time_us;
+ uint32_t bgcom_status;
+ struct work_struct wakeup_work;
+ uint32_t activity_flag;
+ spinlock_t activity_lock;
+ struct bgcom_open_config_type bgcom_config;
+ void *bgcom_handle;
+};
+
+struct rx_pkt {
+ void *rx_buf;
+ uint32_t rx_len;
+ struct edge_info *einfo;
+ struct kthread_work kwork;
+};
+
+
+static uint32_t negotiate_features_v1(struct glink_transport_if *if_ptr,
+ const struct glink_core_version *version,
+ uint32_t features);
+static DEFINE_SPINLOCK(edge_infos_lock);
+static LIST_HEAD(edge_infos);
+static struct glink_core_version versions[] = {
+ {1, TRACER_PKT_FEATURE, negotiate_features_v1},
+};
+
+/**
+ * negotiate_features_v1() - determine what features of a version can be used
+ * @if_ptr: The transport for which features are negotiated for.
+ * @version: The version negotiated.
+ * @features: The set of requested features.
+ *
+ * Return: What set of the requested features can be supported.
+ */
+static uint32_t negotiate_features_v1(struct glink_transport_if *if_ptr,
+ const struct glink_core_version *version,
+ uint32_t features)
+{
+ return features & version->features;
+}
+
+/**
+ * glink_bgcom_get_tx_avail() - Available Write Space in the remote side
+ * @einfo: Edge information corresponding to the remote side.
+ *
+ * Return: 0 on error, available write space on success.
+ */
+static int glink_bgcom_get_tx_avail(struct edge_info *einfo)
+{
+ uint32_t tx_avail;
+
+ mutex_lock(&einfo->tx_avail_lock);
+ tx_avail = einfo->fifo_fill.tx_avail;
+ if (tx_avail < FIFO_FULL_RESERVE)
+ tx_avail = 0;
+ else
+ tx_avail -= FIFO_FULL_RESERVE;
+
+ mutex_unlock(&einfo->tx_avail_lock);
+ return tx_avail;
+}
+
+
+/**
+ * glink_bgcom_update_tx_avail() - update available Write Space in fifo
+ * @einfo: Edge information corresponding to the remote side.
+ * @size: size to update.
+ *
+ * Return: 0 on error, available write space on success.
+ */
+static void glink_bgcom_update_tx_avail(struct edge_info *einfo, uint32_t size)
+{
+ mutex_lock(&einfo->tx_avail_lock);
+ einfo->fifo_fill.tx_avail -= size;
+ if (einfo->fifo_fill.tx_avail < einfo->fifo_size.to_slave/2)
+ einfo->water_mark_reached = true;
+ mutex_unlock(&einfo->tx_avail_lock);
+}
+
+/**
+ * glink_bgcom_xprt_tx_cmd_safe() - Transmit G-Link commands
+ * @einfo: Edge information corresponding to the remote subsystem.
+ * @src: Source buffer containing the G-Link command.
+ * @size: Size of the command to transmit.
+ *
+ * This function is used to transmit the G-Link commands. This function
+ * must be called with einfo->write_lock locked.
+ *
+ * Return: 0 on success, standard Linux error codes on error.
+ */
+static int glink_bgcom_xprt_tx_cmd_safe(struct edge_info *einfo, void *src,
+ uint32_t size)
+{
+ uint32_t tx_avail = glink_bgcom_get_tx_avail(einfo);
+ int ret;
+ uint32_t size_in_words = size/WORD_SIZE;
+
+ if (size_in_words > tx_avail) {
+ GLINK_ERR("%s: No Space in Fifo\n", __func__);
+ return -ENOSPC;
+ }
+
+ ret = bgcom_fifo_write(einfo->bgcom_handle, size_in_words, src);
+ if (ret < 0) {
+ GLINK_ERR("%s: Error %d writing data\n", __func__, ret);
+ return ret;
+ }
+ glink_bgcom_update_tx_avail(einfo, size_in_words);
+ return ret;
+}
+
+/**
+ * send_tx_blocked_signal() - Send flow control request message
+ * @einfo: Edge information corresponding to the remote subsystem.
+ *
+ * This function is used to send a message to the remote subsystem indicating
+ * that the local subsystem is waiting for the write space. The remote
+ * subsystem on receiving this message will send a resume tx message.
+ */
+static void send_tx_blocked_signal(struct edge_info *einfo)
+{
+ struct read_notif_request {
+ uint16_t cmd;
+ uint16_t reserved;
+ uint32_t reserved2;
+ uint64_t reserved3;
+ };
+ struct read_notif_request read_notif_req = {0};
+ int size_in_word = sizeof(read_notif_req)/WORD_SIZE;
+ void *src = &read_notif_req;
+ int ret;
+
+ read_notif_req.cmd = READ_NOTIF_CMD;
+ if (!einfo->tx_blocked_signal_sent) {
+ einfo->tx_blocked_signal_sent = true;
+ ret = bgcom_fifo_write(einfo->bgcom_handle, size_in_word, src);
+ if (ret < 0) {
+ GLINK_ERR("%s: Err %d send blocked\n", __func__, ret);
+ return;
+ }
+ glink_bgcom_update_tx_avail(einfo, size_in_word);
+ }
+}
+
+/**
+ * glink_bgcom_xprt_tx_cmd() - Transmit G-Link commands
+ * @einfo: Edge information corresponding to the remote subsystem.
+ * @src: Source buffer containing the G-Link command.
+ * @size: Size of the command to transmit.
+ *
+ * This function is used to transmit the G-Link commands. This function
+ * might sleep if the space is not available to transmit the command.
+ *
+ * Return: 0 on success, standard Linux error codes on error.
+ */
+static int glink_bgcom_xprt_tx_cmd(struct edge_info *einfo, void *src,
+ uint32_t size)
+{
+ int ret;
+ DEFINE_WAIT(wait);
+
+ mutex_lock(&einfo->write_lock);
+ while (glink_bgcom_get_tx_avail(einfo) < (size/WORD_SIZE)) {
+ send_tx_blocked_signal(einfo);
+ prepare_to_wait(&einfo->tx_blocked_queue, &wait,
+ TASK_UNINTERRUPTIBLE);
+ if (glink_bgcom_get_tx_avail(einfo) < (size/WORD_SIZE)
+ && !einfo->in_ssr) {
+ mutex_unlock(&einfo->write_lock);
+ schedule();
+ mutex_lock(&einfo->write_lock);
+ }
+ finish_wait(&einfo->tx_blocked_queue, &wait);
+ if (einfo->in_ssr) {
+ mutex_unlock(&einfo->write_lock);
+ return -EFAULT;
+ }
+ }
+ ret = glink_bgcom_xprt_tx_cmd_safe(einfo, src, size);
+ mutex_unlock(&einfo->write_lock);
+ return ret;
+}
+
+/**
+ * process_rx_data() - process received data from an edge
+ * @einfo: The edge the data is received on.
+ * @cmd_id: ID to specify the type of data.
+ * @rcid: The remote channel id associated with the data.
+ * @intend_id: The intent the data should be put in.
+ * @src: Address of the source buffer from which the data
+ * is read.
+ * @frag_size: Size of the data fragment to read.
+ * @size_remaining: Size of data left to be read in this packet.
+ */
+static void process_rx_data(struct edge_info *einfo, uint16_t cmd_id,
+ uint32_t rcid, uint32_t intent_id, void *src,
+ uint32_t frag_size, uint32_t size_remaining)
+{
+ struct glink_core_rx_intent *intent;
+ int rc = 0;
+
+ intent = einfo->xprt_if.glink_core_if_ptr->rx_get_pkt_ctx(
+ &einfo->xprt_if, rcid, intent_id);
+ if (intent == NULL) {
+ GLINK_ERR("%s: no intent for ch %d liid %d\n", __func__, rcid,
+ intent_id);
+ return;
+ } else if (intent->data == NULL) {
+ GLINK_ERR("%s: intent for ch %d liid %d has no data buff\n",
+ __func__, rcid, intent_id);
+ return;
+ } else if (intent->intent_size - intent->write_offset < frag_size ||
+ intent->write_offset + size_remaining > intent->intent_size) {
+ GLINK_ERR("%s: rx data size:%d and remaining:%d %s %d %s:%d\n",
+ __func__, frag_size, size_remaining,
+ "will overflow ch", rcid, "intent", intent_id);
+ return;
+ }
+
+ rc = bgcom_ahb_read(einfo->bgcom_handle, (uint32_t)(size_t)src,
+ ALIGN(frag_size, WORD_SIZE)/WORD_SIZE,
+ intent->data + intent->write_offset);
+
+ if (rc < 0) {
+ GLINK_ERR("%s: Error %d receiving data %d:%d:%d:%d\n",
+ __func__, rc, rcid, intent_id, frag_size,
+ size_remaining);
+ size_remaining += frag_size;
+ } else {
+ intent->write_offset += frag_size;
+ intent->pkt_size += frag_size;
+
+ if (unlikely((cmd_id == TRACER_PKT_CMD ||
+ cmd_id == TRACER_PKT_CONT_CMD) && !size_remaining)) {
+ tracer_pkt_log_event(intent->data, GLINK_XPRT_RX);
+ intent->tracer_pkt = true;
+ }
+ }
+ einfo->xprt_if.glink_core_if_ptr->rx_put_pkt_ctx(&einfo->xprt_if,
+ rcid, intent, size_remaining ? false : true);
+}
+
+/**
+ * process_rx_cmd() - Process incoming G-Link commands
+ * @einfo: Edge information corresponding to the remote subsystem.
+ * @rx_data: Buffer which contains the G-Link commands to be processed.
+ * @rx_size: Size of the buffer containing the series of G-Link commands.
+ *
+ * This function is used to parse and process a series of G-Link commands
+ * received in a buffer.
+ */
+static void process_rx_cmd(struct edge_info *einfo,
+ void *rx_data, int rx_size)
+{
+ struct command {
+ uint16_t id;
+ uint16_t param1;
+ uint32_t param2;
+ uint32_t param3;
+ uint32_t param4;
+ };
+ struct intent_desc {
+ uint32_t size;
+ uint32_t id;
+ uint64_t addr;
+ };
+ struct rx_desc {
+ uint32_t size;
+ uint32_t size_left;
+ uint64_t addr;
+ };
+ struct command *cmd;
+ struct intent_desc *intents;
+ struct rx_desc *rx_descp;
+ int offset = 0;
+ int rcu_id;
+ uint16_t rcid;
+ uint16_t name_len;
+ uint16_t prio;
+ char *name;
+ bool granted;
+ int i;
+
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+
+ while (offset < rx_size) {
+ cmd = (struct command *)(rx_data + offset);
+ offset += sizeof(*cmd);
+ switch (cmd->id) {
+ case VERSION_CMD:
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_version(
+ &einfo->xprt_if, cmd->param1, cmd->param2);
+ break;
+
+ case VERSION_ACK_CMD:
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_version_ack(
+ &einfo->xprt_if, cmd->param1, cmd->param2);
+ break;
+
+ case OPEN_CMD:
+ rcid = cmd->param1;
+ name_len = (uint16_t)(cmd->param2 & 0xFFFF);
+ prio = (uint16_t)((cmd->param2 & 0xFFFF0000) >> 16);
+ name = (char *)(rx_data + offset);
+ offset += ALIGN(name_len, FIFO_ALIGNMENT);
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_ch_remote_open(
+ &einfo->xprt_if, rcid, name, prio);
+ break;
+
+ case CLOSE_CMD:
+ einfo->xprt_if.glink_core_if_ptr->
+ rx_cmd_ch_remote_close(
+ &einfo->xprt_if, cmd->param1);
+ break;
+
+ case OPEN_ACK_CMD:
+ prio = (uint16_t)(cmd->param2 & 0xFFFF);
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_ch_open_ack(
+ &einfo->xprt_if, cmd->param1, prio);
+ break;
+
+ case CLOSE_ACK_CMD:
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_ch_close_ack(
+ &einfo->xprt_if, cmd->param1);
+ break;
+
+ case RX_INTENT_CMD:
+ for (i = 0; i < cmd->param2; i++) {
+ intents = (struct intent_desc *)
+ (rx_data + offset);
+ offset += sizeof(*intents);
+ einfo->xprt_if.glink_core_if_ptr->
+ rx_cmd_remote_rx_intent_put_cookie(
+ &einfo->xprt_if, cmd->param1,
+ intents->id, intents->size,
+ (void *)(uintptr_t)(intents->addr));
+ }
+ break;
+
+ case RX_DONE_CMD:
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_tx_done(
+ &einfo->xprt_if, cmd->param1, cmd->param2,
+ false);
+ break;
+
+ case RX_INTENT_REQ_CMD:
+ einfo->xprt_if.glink_core_if_ptr->
+ rx_cmd_remote_rx_intent_req(
+ &einfo->xprt_if, cmd->param1,
+ cmd->param2);
+ break;
+
+ case RX_INTENT_REQ_ACK_CMD:
+ granted = cmd->param2 == 1 ? true : false;
+ einfo->xprt_if.glink_core_if_ptr->
+ rx_cmd_rx_intent_req_ack(&einfo->xprt_if,
+ cmd->param1, granted);
+ break;
+
+ case TX_DATA_CMD:
+ case TX_DATA_CONT_CMD:
+ case TRACER_PKT_CMD:
+ case TRACER_PKT_CONT_CMD:
+ rx_descp = (struct rx_desc *)(rx_data + offset);
+ offset += sizeof(*rx_descp);
+ process_rx_data(einfo, cmd->id, cmd->param1,
+ cmd->param2,
+ (void *)(uintptr_t)(rx_descp->addr),
+ rx_descp->size, rx_descp->size_left);
+ break;
+
+ case READ_NOTIF_CMD:
+ break;
+
+ case SIGNALS_CMD:
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_remote_sigs(
+ &einfo->xprt_if, cmd->param1, cmd->param2);
+ break;
+
+ case RX_DONE_W_REUSE_CMD:
+ einfo->xprt_if.glink_core_if_ptr->rx_cmd_tx_done(
+ &einfo->xprt_if, cmd->param1,
+ cmd->param2, true);
+ break;
+
+ default:
+ GLINK_ERR("Unrecognized command: %d\n", cmd->id);
+ break;
+ }
+ }
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+
+/**
+ * tx_wakeup_worker() - worker function to wakeup tx blocked thread
+ * @work: kwork associated with the edge to process commands on.
+ */
+static void tx_wakeup_worker(struct edge_info *einfo)
+{
+ int rcu_id;
+ struct bgcom_fifo_fill fifo_fill;
+
+ mutex_lock(&einfo->tx_avail_lock);
+ bgcom_reg_read(einfo->bgcom_handle, BGCOM_REG_FIFO_FILL, 1,
+ &fifo_fill);
+ einfo->fifo_fill.tx_avail = fifo_fill.tx_avail;
+ if (einfo->fifo_fill.tx_avail > einfo->fifo_size.to_slave/2)
+ einfo->water_mark_reached = false;
+ mutex_unlock(&einfo->tx_avail_lock);
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+ if (einfo->tx_resume_needed &&
+ glink_bgcom_get_tx_avail(einfo)) {
+ einfo->tx_resume_needed = false;
+ einfo->xprt_if.glink_core_if_ptr->tx_resume(
+ &einfo->xprt_if);
+ }
+ mutex_lock(&einfo->write_lock);
+ if (einfo->tx_blocked_signal_sent) {
+ wake_up_all(&einfo->tx_blocked_queue);
+ einfo->tx_blocked_signal_sent = false;
+ }
+ mutex_unlock(&einfo->write_lock);
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * __rx_worker() - Receive commands on a specific edge
+ * @einfo: Edge to process commands on.
+ *
+ * This function checks the size of data to be received, allocates the
+ * buffer for that data and reads the data from the remote subsytem
+ * into that buffer. This function then calls the process_rx_cmd() to
+ * parse the received G-Link command sequence. This function will also
+ * poll for the data for a predefined duration for performance reasons.
+ */
+static void __rx_worker(struct rx_pkt *rx_pkt_info)
+{
+ int rcu_id;
+ struct edge_info *einfo = rx_pkt_info->einfo;
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+ process_rx_cmd(einfo, rx_pkt_info->rx_buf,
+ rx_pkt_info->rx_len*WORD_SIZE);
+ kfree(rx_pkt_info->rx_buf);
+ kfree(rx_pkt_info);
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * rx_worker() - Worker function to process received commands
+ * @work: kwork associated with the edge to process commands on.
+ */
+static void rx_worker(struct kthread_work *work)
+{
+ struct rx_pkt *rx_pkt_info;
+
+ rx_pkt_info = container_of(work, struct rx_pkt, kwork);
+ __rx_worker(rx_pkt_info);
+};
+
+/**
+ * tx_cmd_version() - Convert a version cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @version: The version number to encode.
+ * @features: The features information to encode.
+ */
+static void tx_cmd_version(struct glink_transport_if *if_ptr, uint32_t version,
+ uint32_t features)
+{
+ struct command {
+ uint16_t id;
+ uint16_t version;
+ uint32_t features;
+ uint32_t fifo_size;
+ uint32_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+
+ cmd.id = VERSION_CMD;
+ cmd.version = version;
+ cmd.features = features;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * tx_cmd_version_ack() - Convert a version ack cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @version: The version number to encode.
+ * @features: The features information to encode.
+ */
+static void tx_cmd_version_ack(struct glink_transport_if *if_ptr,
+ uint32_t version,
+ uint32_t features)
+{
+ struct command {
+ uint16_t id;
+ uint16_t version;
+ uint32_t features;
+ uint32_t fifo_size;
+ uint32_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+
+ cmd.id = VERSION_ACK_CMD;
+ cmd.version = version;
+ cmd.features = features;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * set_version() - Activate a negotiated version and feature set
+ * @if_ptr: The transport to configure.
+ * @version: The version to use.
+ * @features: The features to use.
+ *
+ * Return: The supported capabilities of the transport.
+ */
+static uint32_t set_version(struct glink_transport_if *if_ptr, uint32_t version,
+ uint32_t features)
+{
+ struct edge_info *einfo;
+ uint32_t ret;
+ int rcu_id;
+
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+ }
+
+ ret = GCAP_SIGNALS;
+ if (features & TRACER_PKT_FEATURE)
+ ret |= GCAP_TRACER_PKT;
+
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return ret;
+}
+
+/**
+ * tx_cmd_ch_open() - Convert a channel open cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @name: The channel name to encode.
+ * @req_xprt: The transport the core would like to migrate this channel to.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int tx_cmd_ch_open(struct glink_transport_if *if_ptr, uint32_t lcid,
+ const char *name, uint16_t req_xprt)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint16_t length;
+ uint16_t req_xprt;
+ uint64_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ uint32_t buf_size;
+ void *buf;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ cmd.id = OPEN_CMD;
+ cmd.lcid = lcid;
+ cmd.length = (uint16_t)(strlen(name) + 1);
+ cmd.req_xprt = req_xprt;
+
+ buf_size = ALIGN(sizeof(cmd) + cmd.length, FIFO_ALIGNMENT);
+
+ buf = kzalloc(buf_size, GFP_KERNEL);
+ if (!buf) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -ENOMEM;
+ }
+
+ memcpy(buf, &cmd, sizeof(cmd));
+ memcpy(buf + sizeof(cmd), name, cmd.length);
+
+ glink_bgcom_xprt_tx_cmd(einfo, buf, buf_size);
+
+ kfree(buf);
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+}
+
+/**
+ * tx_cmd_ch_close() - Convert a channel close cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int tx_cmd_ch_close(struct glink_transport_if *if_ptr, uint32_t lcid)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t reserved1;
+ uint64_t reserved2;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ cmd.id = CLOSE_CMD;
+ cmd.lcid = lcid;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+}
+
+/**
+ * tx_cmd_ch_remote_open_ack() - Convert a channel open ack cmd to wire format
+ * and transmit
+ * @if_ptr: The transport to transmit on.
+ * @rcid: The remote channel id to encode.
+ * @xprt_resp: The response to a transport migration request.
+ */
+static void tx_cmd_ch_remote_open_ack(struct glink_transport_if *if_ptr,
+ uint32_t rcid, uint16_t xprt_resp)
+{
+ struct command {
+ uint16_t id;
+ uint16_t rcid;
+ uint16_t reserved1;
+ uint16_t xprt_resp;
+ uint64_t reserved2;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+
+ cmd.id = OPEN_ACK_CMD;
+ cmd.rcid = rcid;
+ cmd.xprt_resp = xprt_resp;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * tx_cmd_ch_remote_close_ack() - Convert a channel close ack cmd to wire format
+ * and transmit
+ * @if_ptr: The transport to transmit on.
+ * @rcid: The remote channel id to encode.
+ */
+static void tx_cmd_ch_remote_close_ack(struct glink_transport_if *if_ptr,
+ uint32_t rcid)
+{
+ struct command {
+ uint16_t id;
+ uint16_t rcid;
+ uint32_t reserved1;
+ uint64_t reserved2;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+
+ cmd.id = CLOSE_ACK_CMD;
+ cmd.rcid = rcid;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * ssr() - Process a subsystem restart notification of a transport
+ * @if_ptr: The transport to restart
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int ssr(struct glink_transport_if *if_ptr)
+{
+ struct edge_info *einfo;
+
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ einfo->in_ssr = true;
+ wake_up_all(&einfo->tx_blocked_queue);
+
+ synchronize_srcu(&einfo->use_ref);
+ einfo->tx_resume_needed = false;
+ einfo->tx_blocked_signal_sent = false;
+ einfo->xprt_if.glink_core_if_ptr->link_down(&einfo->xprt_if);
+
+ return 0;
+}
+
+/**
+ * allocate_rx_intent() - Allocate/reserve space for RX Intent
+ * @if_ptr: The transport the intent is associated with.
+ * @size: size of intent.
+ * @intent: Pointer to the intent structure.
+ *
+ * Assign "data" with the buffer created, since the transport creates
+ * a linear buffer and "iovec" with the "intent" itself, so that
+ * the data can be passed to a client that receives only vector buffer.
+ * Note that returning NULL for the pointer is valid (it means that space has
+ * been reserved, but the actual pointer will be provided later).
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int allocate_rx_intent(struct glink_transport_if *if_ptr, size_t size,
+ struct glink_core_rx_intent *intent)
+{
+ void *t;
+
+ t = kzalloc(ALIGN(size, WORD_SIZE), GFP_KERNEL);
+ if (!t)
+ return -ENOMEM;
+
+ intent->data = t;
+ intent->iovec = (void *)intent;
+ intent->vprovider = rx_linear_vbuf_provider;
+ intent->pprovider = NULL;
+ return 0;
+}
+
+/**
+ * deallocate_rx_intent() - Deallocate space created for RX Intent
+ * @if_ptr: The transport the intent is associated with.
+ * @intent: Pointer to the intent structure.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int deallocate_rx_intent(struct glink_transport_if *if_ptr,
+ struct glink_core_rx_intent *intent)
+{
+ if (!intent || !intent->data)
+ return -EINVAL;
+
+ kfree(intent->data);
+ intent->data = NULL;
+ intent->iovec = NULL;
+ intent->vprovider = NULL;
+ return 0;
+}
+
+/**
+ * tx_cmd_local_rx_intent() - Convert an rx intent cmd to wire format and
+ * transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @size: The intent size to encode.
+ * @liid: The local intent id to encode.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int tx_cmd_local_rx_intent(struct glink_transport_if *if_ptr,
+ uint32_t lcid, size_t size, uint32_t liid)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t count;
+ uint64_t reserved;
+ uint32_t size;
+ uint32_t liid;
+ uint64_t addr;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ if (size > UINT_MAX) {
+ GLINK_ERR("%s: size %zu is too large to encode\n",
+ __func__, size);
+ return -EMSGSIZE;
+ }
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ cmd.id = RX_INTENT_CMD;
+ cmd.lcid = lcid;
+ cmd.count = 1;
+ cmd.size = size;
+ cmd.liid = liid;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+}
+
+/**
+ * tx_cmd_local_rx_done() - Convert an rx done cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @liid: The local intent id to encode.
+ * @reuse: Reuse the consumed intent.
+ */
+static void tx_cmd_local_rx_done(struct glink_transport_if *if_ptr,
+ uint32_t lcid, uint32_t liid, bool reuse)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t liid;
+ uint64_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return;
+ }
+
+ cmd.id = reuse ? RX_DONE_W_REUSE_CMD : RX_DONE_CMD;
+ cmd.lcid = lcid;
+ cmd.liid = liid;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+}
+
+/**
+ * tx_cmd_rx_intent_req() - Convert an rx intent request cmd to wire format and
+ * transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @size: The requested intent size to encode.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int tx_cmd_rx_intent_req(struct glink_transport_if *if_ptr,
+ uint32_t lcid, size_t size)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t size;
+ uint64_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ if (size > UINT_MAX) {
+ GLINK_ERR("%s: size %zu is too large to encode\n",
+ __func__, size);
+ return -EMSGSIZE;
+ }
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ cmd.id = RX_INTENT_REQ_CMD,
+ cmd.lcid = lcid;
+ cmd.size = ALIGN(size, WORD_SIZE);
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+}
+
+/**
+ * tx_cmd_rx_intent_req_ack() - Convert an rx intent request ack cmd to wire
+ * format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @granted: The request response to encode.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int tx_cmd_remote_rx_intent_req_ack(struct glink_transport_if *if_ptr,
+ uint32_t lcid, bool granted)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t response;
+ uint64_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ cmd.id = RX_INTENT_REQ_ACK_CMD,
+ cmd.lcid = lcid;
+ if (granted)
+ cmd.response = 1;
+ else
+ cmd.response = 0;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+}
+
+/**
+ * tx_cmd_set_sigs() - Convert a signals ack cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @sigs: The signals to encode.
+ *
+ * Return: 0 on success or standard Linux error code.
+ */
+static int tx_cmd_set_sigs(struct glink_transport_if *if_ptr, uint32_t lcid,
+ uint32_t sigs)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t sigs;
+ uint64_t reserved;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ int rcu_id;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ cmd.id = SIGNALS_CMD,
+ cmd.lcid = lcid;
+ cmd.sigs = sigs;
+
+ glink_bgcom_xprt_tx_cmd(einfo, &cmd, sizeof(cmd));
+
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return 0;
+}
+
+/**
+ * tx_data() - convert a data/tracer_pkt to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @cmd_id: The command ID to transmit.
+ * @lcid: The local channel id to encode.
+ * @pctx: The data to encode.
+ *
+ * Return: Number of bytes written or standard Linux error code.
+ */
+static int tx_data(struct glink_transport_if *if_ptr, uint16_t cmd_id,
+ uint32_t lcid, struct glink_core_tx_pkt *pctx)
+{
+ struct command {
+ uint16_t id;
+ uint16_t lcid;
+ uint32_t riid;
+ uint64_t reserved;
+ uint32_t size;
+ uint32_t size_left;
+ uint64_t addr;
+ };
+ struct command cmd;
+ struct edge_info *einfo;
+ void *data_start, *dst = NULL;
+ size_t tx_size = 0;
+ int rcu_id;
+
+ if (pctx->size < pctx->size_remaining) {
+ GLINK_ERR("%s: size remaining exceeds size. Resetting.\n",
+ __func__);
+ pctx->size_remaining = pctx->size;
+ }
+ if (!pctx->size_remaining)
+ return 0;
+
+ memset(&cmd, 0, sizeof(cmd));
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+
+ rcu_id = srcu_read_lock(&einfo->use_ref);
+ if (einfo->in_ssr) {
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EFAULT;
+ }
+
+ if (cmd_id == TX_DATA_CMD) {
+ if (pctx->size_remaining == pctx->size)
+ cmd.id = TX_DATA_CMD;
+ else
+ cmd.id = TX_DATA_CONT_CMD;
+ } else {
+ if (pctx->size_remaining == pctx->size)
+ cmd.id = TRACER_PKT_CMD;
+ else
+ cmd.id = TRACER_PKT_CONT_CMD;
+ }
+ cmd.lcid = lcid;
+ cmd.riid = pctx->riid;
+ data_start = get_tx_vaddr(pctx, pctx->size - pctx->size_remaining,
+ &tx_size);
+ if (unlikely(!data_start)) {
+ GLINK_ERR("%s: invalid data_start\n", __func__);
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return -EINVAL;
+ }
+ if (likely(pctx->cookie))
+ dst = pctx->cookie + (pctx->size - pctx->size_remaining);
+
+ mutex_lock(&einfo->write_lock);
+ /* Need enough space to write the command */
+ if (glink_bgcom_get_tx_avail(einfo) <= sizeof(cmd)/WORD_SIZE) {
+ einfo->tx_resume_needed = true;
+ send_tx_blocked_signal(einfo);
+ mutex_unlock(&einfo->write_lock);
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ GLINK_ERR("%s: No Space in Fifo\n", __func__);
+ return -EAGAIN;
+ }
+ cmd.addr = 0;
+ cmd.size = tx_size;
+ pctx->size_remaining -= tx_size;
+ cmd.size_left = pctx->size_remaining;
+ if (cmd.id == TRACER_PKT_CMD)
+ tracer_pkt_log_event((void *)(pctx->data), GLINK_XPRT_TX);
+
+ bgcom_resume(einfo->bgcom_handle);
+ bgcom_ahb_write(einfo->bgcom_handle, (uint32_t)(size_t)dst,
+ ALIGN(tx_size, WORD_SIZE)/WORD_SIZE,
+ data_start);
+ glink_bgcom_xprt_tx_cmd_safe(einfo, &cmd, sizeof(cmd));
+ GLINK_DBG("%s %s: lcid[%u] riid[%u] cmd %d, size[%d], size_left[%d]\n",
+ "<BGCOM>", __func__, cmd.lcid, cmd.riid, cmd.id, cmd.size,
+ cmd.size_left);
+ mutex_unlock(&einfo->write_lock);
+ srcu_read_unlock(&einfo->use_ref, rcu_id);
+ return cmd.size;
+}
+
+/**
+ * tx() - convert a data transmit cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @pctx: The data to encode.
+ *
+ * Return: Number of bytes written or standard Linux error code.
+ */
+static int tx(struct glink_transport_if *if_ptr, uint32_t lcid,
+ struct glink_core_tx_pkt *pctx)
+{
+ return tx_data(if_ptr, TX_DATA_CMD, lcid, pctx);
+}
+
+/**
+ * tx_cmd_tracer_pkt() - convert a tracer packet cmd to wire format and transmit
+ * @if_ptr: The transport to transmit on.
+ * @lcid: The local channel id to encode.
+ * @pctx: The data to encode.
+ *
+ * Return: Number of bytes written or standard Linux error code.
+ */
+static int tx_cmd_tracer_pkt(struct glink_transport_if *if_ptr, uint32_t lcid,
+ struct glink_core_tx_pkt *pctx)
+{
+ return tx_data(if_ptr, TRACER_PKT_CMD, lcid, pctx);
+}
+
+/**
+ * int wait_link_down() - Check status of read/write indices
+ * @if_ptr: The transport to check
+ *
+ * Return: 1 if indices are all zero, 0 otherwise
+ */
+static int wait_link_down(struct glink_transport_if *if_ptr)
+{
+ return 0;
+}
+
+/**
+ * get_power_vote_ramp_time() - Get the ramp time required for the power
+ * votes to be applied
+ * @if_ptr: The transport interface on which power voting is requested.
+ * @state: The power state for which ramp time is required.
+ *
+ * Return: The ramp time specific to the power state, standard error otherwise.
+ */
+static unsigned long get_power_vote_ramp_time(
+ struct glink_transport_if *if_ptr, uint32_t state)
+{
+ return 0;
+}
+
+/**
+ * power_vote() - Update the power votes to meet qos requirement
+ * @if_ptr: The transport interface on which power voting is requested.
+ * @state: The power state for which the voting should be done.
+ *
+ * Return: 0 on Success, standard error otherwise.
+ */
+static int power_vote(struct glink_transport_if *if_ptr, uint32_t state)
+{
+ unsigned long flags;
+ struct edge_info *einfo;
+
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+ spin_lock_irqsave(&einfo->activity_lock, flags);
+ einfo->activity_flag |= ACTIVE_TX;
+ spin_unlock_irqrestore(&einfo->activity_lock, flags);
+ return 0;
+}
+
+/**
+ * power_unvote() - Remove the all the power votes
+ * @if_ptr: The transport interface on which power voting is requested.
+ *
+ * Return: 0 on Success, standard error otherwise.
+ */
+static int power_unvote(struct glink_transport_if *if_ptr)
+{
+ unsigned long flags;
+ struct edge_info *einfo;
+
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+ spin_lock_irqsave(&einfo->activity_lock, flags);
+ einfo->activity_flag &= ~ACTIVE_TX;
+ spin_unlock_irqrestore(&einfo->activity_lock, flags);
+ return 0;
+}
+
+static void glink_bgcom_linkup(struct edge_info *einfo)
+{
+ if (einfo->bgcom_status != BGCOM_LINKUP)
+ return;
+ einfo->in_ssr = false;
+ synchronize_srcu(&einfo->use_ref);
+ bgcom_reg_read(einfo->bgcom_handle, BGCOM_REG_FIFO_SIZE, 1,
+ &einfo->fifo_size);
+ mutex_lock(&einfo->tx_avail_lock);
+ einfo->fifo_fill.tx_avail = einfo->fifo_size.to_master;
+ mutex_unlock(&einfo->tx_avail_lock);
+ einfo->xprt_if.glink_core_if_ptr->link_up(&einfo->xprt_if);
+}
+
+static void glink_bgcom_event_handler(void *handle,
+ void *priv_data, enum bgcom_event_type event,
+ union bgcom_event_data_type *data)
+{
+ struct edge_info *einfo = (struct edge_info *)priv_data;
+ struct rx_pkt *rx_pkt_info;
+
+ switch (event) {
+ case BGCOM_EVENT_APPLICATION_RUNNING:
+ if (data->application_running &&
+ einfo->bgcom_status != BGCOM_LINKUP) {
+ einfo->bgcom_status |= BGCOM_APPLICATION_RUNNING;
+ glink_bgcom_linkup(einfo);
+ }
+ break;
+ case BGCOM_EVENT_TO_SLAVE_FIFO_READY:
+ if (data->to_slave_fifo_ready &&
+ einfo->bgcom_status != BGCOM_LINKUP) {
+ einfo->bgcom_status |= BGCOM_TO_SLAVE_FIFO_READY;
+ glink_bgcom_linkup(einfo);
+ }
+ break;
+ case BGCOM_EVENT_TO_MASTER_FIFO_READY:
+ if (data->to_master_fifo_ready &&
+ einfo->bgcom_status != BGCOM_LINKUP) {
+ einfo->bgcom_status |= BGCOM_TO_MASTER_FIFO_READY;
+ glink_bgcom_linkup(einfo);
+ }
+ break;
+ case BGCOM_EVENT_AHB_READY:
+ if (data->ahb_ready &&
+ einfo->bgcom_status != BGCOM_LINKUP) {
+ einfo->bgcom_status |= BGCOM_AHB_READY;
+ glink_bgcom_linkup(einfo);
+ }
+ break;
+ case BGCOM_EVENT_TO_MASTER_FIFO_USED:
+ rx_pkt_info = kzalloc(sizeof(struct rx_pkt), GFP_KERNEL);
+ rx_pkt_info->rx_buf = data->fifo_data.data;
+ rx_pkt_info->rx_len = data->fifo_data.to_master_fifo_used;
+ rx_pkt_info->einfo = einfo;
+ kthread_init_work(&rx_pkt_info->kwork, rx_worker);
+ kthread_queue_work(&einfo->kworker, &rx_pkt_info->kwork);
+ break;
+ case BGCOM_EVENT_TO_SLAVE_FIFO_FREE:
+ if (einfo->water_mark_reached)
+ tx_wakeup_worker(einfo);
+ break;
+ case BGCOM_EVENT_RESET_OCCURRED:
+ einfo->bgcom_status = BGCOM_RESET;
+ ssr(&einfo->xprt_if);
+ break;
+ case BGCOM_EVENT_ERROR_WRITE_FIFO_OVERRUN:
+ case BGCOM_EVENT_ERROR_WRITE_FIFO_BUS_ERR:
+ case BGCOM_EVENT_ERROR_WRITE_FIFO_ACCESS:
+ case BGCOM_EVENT_ERROR_READ_FIFO_UNDERRUN:
+ case BGCOM_EVENT_ERROR_READ_FIFO_BUS_ERR:
+ case BGCOM_EVENT_ERROR_READ_FIFO_ACCESS:
+ case BGCOM_EVENT_ERROR_TRUNCATED_READ:
+ case BGCOM_EVENT_ERROR_TRUNCATED_WRITE:
+ case BGCOM_EVENT_ERROR_AHB_ILLEGAL_ADDRESS:
+ case BGCOM_EVENT_ERROR_AHB_BUS_ERR:
+ GLINK_ERR("%s: ERROR %d", __func__, event);
+ break;
+ default:
+ GLINK_ERR("%s: unhandled event %d", __func__, event);
+ break;
+ }
+}
+
+/**
+ * init_xprt_if() - Initialize the xprt_if for an edge
+ * @einfo: The edge to initialize.
+ */
+static void init_xprt_if(struct edge_info *einfo)
+{
+ einfo->xprt_if.tx_cmd_version = tx_cmd_version;
+ einfo->xprt_if.tx_cmd_version_ack = tx_cmd_version_ack;
+ einfo->xprt_if.set_version = set_version;
+ einfo->xprt_if.tx_cmd_ch_open = tx_cmd_ch_open;
+ einfo->xprt_if.tx_cmd_ch_close = tx_cmd_ch_close;
+ einfo->xprt_if.tx_cmd_ch_remote_open_ack = tx_cmd_ch_remote_open_ack;
+ einfo->xprt_if.tx_cmd_ch_remote_close_ack = tx_cmd_ch_remote_close_ack;
+ einfo->xprt_if.ssr = ssr;
+ einfo->xprt_if.allocate_rx_intent = allocate_rx_intent;
+ einfo->xprt_if.deallocate_rx_intent = deallocate_rx_intent;
+ einfo->xprt_if.tx_cmd_local_rx_intent = tx_cmd_local_rx_intent;
+ einfo->xprt_if.tx_cmd_local_rx_done = tx_cmd_local_rx_done;
+ einfo->xprt_if.tx = tx;
+ einfo->xprt_if.tx_cmd_rx_intent_req = tx_cmd_rx_intent_req;
+ einfo->xprt_if.tx_cmd_remote_rx_intent_req_ack =
+ tx_cmd_remote_rx_intent_req_ack;
+ einfo->xprt_if.tx_cmd_set_sigs = tx_cmd_set_sigs;
+ einfo->xprt_if.wait_link_down = wait_link_down;
+ einfo->xprt_if.tx_cmd_tracer_pkt = tx_cmd_tracer_pkt;
+ einfo->xprt_if.get_power_vote_ramp_time = get_power_vote_ramp_time;
+ einfo->xprt_if.power_vote = power_vote;
+ einfo->xprt_if.power_unvote = power_unvote;
+}
+
+/**
+ * init_xprt_cfg() - Initialize the xprt_cfg for an edge
+ * @einfo: The edge to initialize.
+ * @name: The name of the remote side this edge communicates to.
+ */
+static void init_xprt_cfg(struct edge_info *einfo, const char *name)
+{
+ einfo->xprt_cfg.name = XPRT_NAME;
+ einfo->xprt_cfg.edge = name;
+ einfo->xprt_cfg.versions = versions;
+ einfo->xprt_cfg.versions_entries = ARRAY_SIZE(versions);
+ einfo->xprt_cfg.max_cid = SZ_64K;
+ einfo->xprt_cfg.max_iid = SZ_2G;
+}
+
+/**
+ * parse_qos_dt_params() - Parse the power states from DT
+ * @dev: Reference to the platform device for a specific edge.
+ * @einfo: Edge information for the edge probe function is called.
+ *
+ * Return: 0 on success, standard error code otherwise.
+ */
+static int parse_qos_dt_params(struct device_node *node,
+ struct edge_info *einfo)
+{
+ int rc;
+ int i;
+ char *key;
+ uint32_t *arr32;
+ uint32_t num_states;
+
+ key = "qcom,ramp-time";
+ if (!of_find_property(node, key, &num_states))
+ return -ENODEV;
+
+ num_states /= sizeof(uint32_t);
+
+ einfo->num_pw_states = num_states;
+
+ arr32 = kmalloc_array(num_states, sizeof(uint32_t), GFP_KERNEL);
+ if (!arr32)
+ return -ENOMEM;
+
+ einfo->ramp_time_us = kmalloc_array(num_states, sizeof(unsigned long),
+ GFP_KERNEL);
+ if (!einfo->ramp_time_us) {
+ rc = -ENOMEM;
+ goto mem_alloc_fail;
+ }
+
+ rc = of_property_read_u32_array(node, key, arr32, num_states);
+ if (rc) {
+ rc = -ENODEV;
+ goto invalid_key;
+ }
+ for (i = 0; i < num_states; i++)
+ einfo->ramp_time_us[i] = arr32[i];
+
+ kfree(arr32);
+ return 0;
+
+invalid_key:
+ kfree(einfo->ramp_time_us);
+mem_alloc_fail:
+ kfree(arr32);
+ return rc;
+}
+
+static int glink_bgcom_probe(struct platform_device *pdev)
+{
+ struct device_node *node;
+ struct device_node *phandle_node;
+ struct edge_info *einfo;
+ int rc;
+ char *key;
+ const char *subsys_name;
+ unsigned long flags;
+
+ node = pdev->dev.of_node;
+
+ einfo = devm_kzalloc(&pdev->dev, sizeof(*einfo), GFP_KERNEL);
+ if (!einfo) {
+ rc = -ENOMEM;
+ goto edge_info_alloc_fail;
+ }
+
+ key = "label";
+ subsys_name = of_get_property(node, key, NULL);
+ if (!subsys_name) {
+ GLINK_ERR("%s: missing key %s\n", __func__, key);
+ rc = -ENODEV;
+ goto missing_key;
+ }
+ strlcpy(einfo->subsys_name, subsys_name, sizeof(einfo->subsys_name));
+
+ init_xprt_cfg(einfo, subsys_name);
+ init_xprt_if(einfo);
+
+ kthread_init_worker(&einfo->kworker);
+ init_srcu_struct(&einfo->use_ref);
+ mutex_init(&einfo->write_lock);
+ init_waitqueue_head(&einfo->tx_blocked_queue);
+ spin_lock_init(&einfo->activity_lock);
+ mutex_init(&einfo->tx_avail_lock);
+
+ spin_lock_irqsave(&edge_infos_lock, flags);
+ list_add_tail(&einfo->list, &edge_infos);
+ spin_unlock_irqrestore(&edge_infos_lock, flags);
+
+ einfo->task = kthread_run(kthread_worker_fn, &einfo->kworker,
+ "bgcom_%s", subsys_name);
+ if (IS_ERR(einfo->task)) {
+ rc = PTR_ERR(einfo->task);
+ GLINK_ERR("%s: kthread run failed %d\n", __func__, rc);
+ goto kthread_fail;
+ }
+
+ key = "qcom,qos-config";
+ phandle_node = of_parse_phandle(node, key, 0);
+ if (phandle_node && !(of_get_glink_core_qos_cfg(phandle_node,
+ &einfo->xprt_cfg)))
+ parse_qos_dt_params(node, einfo);
+
+ rc = glink_core_register_transport(&einfo->xprt_if, &einfo->xprt_cfg);
+ if (rc == -EPROBE_DEFER)
+ goto reg_xprt_fail;
+ if (rc) {
+ GLINK_ERR("%s: glink core register transport failed: %d\n",
+ __func__, rc);
+ goto reg_xprt_fail;
+ }
+
+ einfo->bgcom_config.priv = (void *)einfo;
+ einfo->bgcom_config.bgcom_notification_cb = glink_bgcom_event_handler;
+ einfo->bgcom_handle = NULL;
+ dev_set_drvdata(&pdev->dev, einfo);
+ if (!strcmp(einfo->xprt_cfg.edge, "bg")) {
+ einfo->bgcom_handle = bgcom_open(&einfo->bgcom_config);
+ if (!einfo->bgcom_handle) {
+ GLINK_ERR("%s: bgcom open failed\n", __func__);
+ rc = -ENODEV;
+ goto bgcom_open_fail;
+ }
+ }
+ return 0;
+
+bgcom_open_fail:
+ dev_set_drvdata(&pdev->dev, NULL);
+ glink_core_unregister_transport(&einfo->xprt_if);
+reg_xprt_fail:
+ kthread_flush_worker(&einfo->kworker);
+ kthread_stop(einfo->task);
+ einfo->task = NULL;
+kthread_fail:
+ spin_lock_irqsave(&edge_infos_lock, flags);
+ list_del(&einfo->list);
+ spin_unlock_irqrestore(&edge_infos_lock, flags);
+missing_key:
+ kfree(einfo);
+edge_info_alloc_fail:
+ return rc;
+}
+
+static int glink_bgcom_remove(struct platform_device *pdev)
+{
+ struct edge_info *einfo;
+ unsigned long flags;
+
+ einfo = (struct edge_info *)dev_get_drvdata(&pdev->dev);
+ bgcom_close(&einfo->bgcom_handle);
+ glink_core_unregister_transport(&einfo->xprt_if);
+ kthread_flush_worker(&einfo->kworker);
+ kthread_stop(einfo->task);
+ einfo->task = NULL;
+ spin_lock_irqsave(&edge_infos_lock, flags);
+ list_del(&einfo->list);
+ spin_unlock_irqrestore(&edge_infos_lock, flags);
+ return 0;
+}
+
+static int glink_bgcom_resume(struct platform_device *pdev)
+{
+ return 0;
+}
+
+static int glink_bgcom_suspend(struct platform_device *pdev,
+ pm_message_t state)
+{
+ unsigned long flags;
+ struct edge_info *einfo;
+ bool suspend;
+ int rc = -EBUSY;
+
+ einfo = (struct edge_info *)dev_get_drvdata(&pdev->dev);
+ if (strcmp(einfo->xprt_cfg.edge, "bg"))
+ return 0;
+
+ spin_lock_irqsave(&einfo->activity_lock, flags);
+ suspend = !(einfo->activity_flag);
+ spin_unlock_irqrestore(&einfo->activity_lock, flags);
+ if (suspend)
+ rc = bgcom_suspend(einfo->bgcom_handle);
+ if (rc < 0)
+ GLINK_ERR("%s: Could not suspend activity_flag %d, rc %d\n",
+ __func__, einfo->activity_flag, rc);
+ return rc;
+}
+
+static const struct of_device_id bgcom_match_table[] = {
+ { .compatible = "qcom,glink-bgcom-xprt" },
+ {},
+};
+
+static struct platform_driver glink_bgcom_driver = {
+ .probe = glink_bgcom_probe,
+ .remove = glink_bgcom_remove,
+ .resume = glink_bgcom_resume,
+ .suspend = glink_bgcom_suspend,
+ .driver = {
+ .name = "msm_glink_bgcom_xprt",
+ .owner = THIS_MODULE,
+ .of_match_table = bgcom_match_table,
+ },
+};
+
+static int __init glink_bgcom_xprt_init(void)
+{
+ int rc;
+
+ rc = platform_driver_register(&glink_bgcom_driver);
+ if (rc)
+ GLINK_ERR("%s: glink_bgcom register failed %d\n", __func__, rc);
+
+ return rc;
+}
+module_init(glink_bgcom_xprt_init);
+
+static void __exit glink_bgcom_xprt_exit(void)
+{
+ platform_driver_unregister(&glink_bgcom_driver);
+}
+module_exit(glink_bgcom_xprt_exit);
+
+MODULE_DESCRIPTION("MSM G-Link bgcom Transport");
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/soc/qcom/glink_private.h b/drivers/soc/qcom/glink_private.h
index 31c1721..c982cbd 100644
--- a/drivers/soc/qcom/glink_private.h
+++ b/drivers/soc/qcom/glink_private.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2018, 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
@@ -824,6 +824,14 @@
*/
int glink_ssr(const char *subsystem);
+/*
+ * glink_subsys_up() - SSR sub system up function.
+ * @subsystem: Constant string for name of remote subsystem.
+ *
+ * Return: Standard error code.
+ */
+int glink_subsys_up(const char *subsystem);
+
/**
* notify for subsystem() - Notify other subsystems that a subsystem is being
* restarted
diff --git a/drivers/soc/qcom/glink_smem_native_xprt.c b/drivers/soc/qcom/glink_smem_native_xprt.c
index baebb25..dda2178 100644
--- a/drivers/soc/qcom/glink_smem_native_xprt.c
+++ b/drivers/soc/qcom/glink_smem_native_xprt.c
@@ -947,15 +947,6 @@
rcu_id = srcu_read_lock(&einfo->use_ref);
- if (unlikely(!einfo->rx_fifo) && atomic_ctx) {
- if (!get_rx_fifo(einfo)) {
- srcu_read_unlock(&einfo->use_ref, rcu_id);
- return;
- }
- einfo->in_ssr = false;
- einfo->xprt_if.glink_core_if_ptr->link_up(&einfo->xprt_if);
- }
-
if (einfo->in_ssr) {
srcu_read_unlock(&einfo->use_ref, rcu_id);
return;
@@ -1569,6 +1560,24 @@
}
/**
+ * subsys_up() - process a subsystem up notification
+ * @if_ptr: The transport which is up
+ *
+ */
+static void subsys_up(struct glink_transport_if *if_ptr)
+{
+ struct edge_info *einfo;
+
+ einfo = container_of(if_ptr, struct edge_info, xprt_if);
+ if (!einfo->rx_fifo) {
+ if (!get_rx_fifo(einfo))
+ return;
+ einfo->in_ssr = false;
+ einfo->xprt_if.glink_core_if_ptr->link_up(&einfo->xprt_if);
+ }
+}
+
+/**
* ssr() - process a subsystem restart notification of a transport
* @if_ptr: The transport to restart
*
@@ -2261,6 +2270,7 @@
einfo->xprt_if.tx_cmd_ch_remote_open_ack = tx_cmd_ch_remote_open_ack;
einfo->xprt_if.tx_cmd_ch_remote_close_ack = tx_cmd_ch_remote_close_ack;
einfo->xprt_if.ssr = ssr;
+ einfo->xprt_if.subsys_up = subsys_up;
einfo->xprt_if.allocate_rx_intent = allocate_rx_intent;
einfo->xprt_if.deallocate_rx_intent = deallocate_rx_intent;
einfo->xprt_if.tx_cmd_local_rx_intent = tx_cmd_local_rx_intent;
@@ -2555,6 +2565,7 @@
rc);
goto request_irq_fail;
}
+ einfo->in_ssr = true;
rc = enable_irq_wake(irq_line);
if (rc < 0)
pr_err("%s: enable_irq_wake() failed on %d\n", __func__,
@@ -3102,6 +3113,7 @@
cfg_p_addr = smem_virt_to_phys(mbox_cfg);
writel_relaxed(lower_32_bits(cfg_p_addr), mbox_loc);
writel_relaxed(upper_32_bits(cfg_p_addr), mbox_loc + 4);
+ einfo->in_ssr = true;
send_irq(einfo);
iounmap(mbox_size);
iounmap(mbox_loc);
diff --git a/drivers/soc/qcom/glink_ssr.c b/drivers/soc/qcom/glink_ssr.c
index 7f97ab0..c16621a 100644
--- a/drivers/soc/qcom/glink_ssr.c
+++ b/drivers/soc/qcom/glink_ssr.c
@@ -266,18 +266,37 @@
__func__);
return;
}
- if (unlikely(!do_cleanup_data))
- goto missing_do_cleanup_data;
- if (unlikely(!cb_data))
- goto missing_cb_data;
- if (unlikely(!resp))
- goto missing_response;
- if (unlikely(resp->version != do_cleanup_data->version))
- goto version_mismatch;
- if (unlikely(resp->seq_num != do_cleanup_data->seq_num))
- goto invalid_seq_number;
- if (unlikely(resp->response != GLINK_SSR_CLEANUP_DONE))
- goto wrong_response;
+ if (unlikely(!do_cleanup_data)) {
+ GLINK_SSR_ERR("<SSR> %s: Missing do_cleanup data!\n", __func__);
+ goto no_clean_done;
+ }
+ if (unlikely(!cb_data)) {
+ GLINK_SSR_ERR("<SSR> %s: Missing cb_data!\n", __func__);
+ goto done;
+ }
+ if (unlikely(!resp)) {
+ GLINK_SSR_ERR("<SSR> %s: Missing response data\n", __func__);
+ goto done;
+ }
+ if (unlikely(resp->version != do_cleanup_data->version)) {
+ GLINK_SSR_ERR("<SSR> %s: Version mismatch. %s[%d], %s[%d]\n",
+ __func__, "do_cleanup version",
+ do_cleanup_data->version, "cleanup_done version",
+ resp->version);
+ goto done;
+ }
+ if (unlikely(resp->seq_num != do_cleanup_data->seq_num)) {
+ GLINK_SSR_ERR("<SSR> %s: Invalid seq. number %s[%d], %s[%d]\n",
+ __func__, "do_cleanup seq num",
+ do_cleanup_data->seq_num,
+ "cleanup_done seq_num", resp->seq_num);
+ goto done;
+ }
+ if (unlikely(resp->response != GLINK_SSR_CLEANUP_DONE)) {
+ GLINK_SSR_ERR("<SSR> %s: Not a cleaup_done message. %s[%d]\n",
+ __func__, "cleanup_done response", resp->response);
+ goto done;
+ }
cb_data->responded = true;
atomic_dec(&responses_remaining);
@@ -287,38 +306,15 @@
__func__, cb_data->edge, resp->response,
resp->version, resp->seq_num,
do_cleanup_data->name);
-
+done:
kfree(do_cleanup_data);
+no_clean_done:
rx_done_work->ptr = ptr;
rx_done_work->handle = handle;
INIT_WORK(&rx_done_work->work, rx_done_cb_worker);
queue_work(glink_ssr_wq, &rx_done_work->work);
wake_up(&waitqueue);
return;
-
-missing_cb_data:
- panic("%s: Missing cb_data!\n", __func__);
- return;
-missing_do_cleanup_data:
- panic("%s: Missing do_cleanup data!\n", __func__);
- return;
-missing_response:
- GLINK_SSR_ERR("<SSR> %s: Missing response data\n", __func__);
- return;
-version_mismatch:
- GLINK_SSR_ERR("<SSR> %s: Version mismatch. %s[%d], %s[%d]\n", __func__,
- "do_cleanup version", do_cleanup_data->version,
- "cleanup_done version", resp->version);
- return;
-invalid_seq_number:
- GLINK_SSR_ERR("<SSR> %s: Invalid seq. number. %s[%d], %s[%d]\n",
- __func__, "do_cleanup seq num",
- do_cleanup_data->seq_num,
- "cleanup_done seq_num", resp->seq_num);
- return;
-wrong_response:
- GLINK_SSR_ERR("<SSR> %s: Not a cleaup_done message. %s[%d]\n", __func__,
- "cleanup_done response", resp->response);
}
/**
@@ -492,6 +488,17 @@
"Subsystem notification failed", ret);
return ret;
}
+ } else if (code == SUBSYS_AFTER_POWERUP) {
+ GLINK_SSR_LOG("<SSR> %s: %s: subsystem restart for %s\n",
+ __func__, "SUBSYS_AFTER_POWERUP",
+ notifier->subsystem);
+ ss_info = get_info_for_subsystem(notifier->subsystem);
+ if (ss_info == NULL) {
+ GLINK_SSR_ERR("<SSR> %s: ss_info is NULL\n", __func__);
+ return -EINVAL;
+ }
+
+ glink_subsys_up(ss_info->edge);
}
return NOTIFY_DONE;
}
@@ -958,13 +965,6 @@
key = "qcom,notify-edges";
while (true) {
phandle_node = of_parse_phandle(node, key, phandle_index++);
- if (!phandle_node && phandle_index == 0) {
- GLINK_SSR_ERR(
- "<SSR> %s: qcom,notify-edges is not present",
- __func__);
- ret = -ENODEV;
- goto notify_edges_not_present;
- }
if (!phandle_node)
break;
@@ -976,7 +976,7 @@
"<SSR> %s: Could not allocate subsys_info_leaf\n",
__func__);
ret = -ENOMEM;
- goto notify_edges_not_present;
+ goto notify_edges_no_memory;
}
subsys_name = of_get_property(phandle_node, "label", NULL);
@@ -1019,7 +1019,7 @@
list_del(&ss_info->subsystem_list_node);
invalid_dt_node:
kfree(ss_info_leaf);
-notify_edges_not_present:
+notify_edges_no_memory:
subsys_notif_unregister_notifier(handle, &nb->nb);
delete_ss_info_notify_list(ss_info);
nb_registration_fail:
diff --git a/drivers/soc/qcom/glink_xprt_if.h b/drivers/soc/qcom/glink_xprt_if.h
index 47c1580..1902152 100644
--- a/drivers/soc/qcom/glink_xprt_if.h
+++ b/drivers/soc/qcom/glink_xprt_if.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2018, 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
@@ -105,6 +105,7 @@
void (*tx_cmd_ch_remote_close_ack)(struct glink_transport_if *if_ptr,
uint32_t rcid);
int (*ssr)(struct glink_transport_if *if_ptr);
+ void (*subsys_up)(struct glink_transport_if *if_ptr);
/* channel data */
int (*allocate_rx_intent)(struct glink_transport_if *if_ptr,
diff --git a/drivers/soc/qcom/memshare/msm_memshare.c b/drivers/soc/qcom/memshare/msm_memshare.c
index 77a76d2..696c043 100644
--- a/drivers/soc/qcom/memshare/msm_memshare.c
+++ b/drivers/soc/qcom/memshare/msm_memshare.c
@@ -352,7 +352,7 @@
static int modem_notifier_cb(struct notifier_block *this, unsigned long code,
void *_cmd)
{
- int i, ret;
+ int i, ret, size = 0;
u32 source_vmlist[1] = {VMID_MSS_MSA};
int dest_vmids[1] = {VMID_HLOS};
int dest_perms[1] = {PERM_READ|PERM_WRITE|PERM_EXEC};
@@ -393,6 +393,7 @@
case SUBSYS_AFTER_POWERUP:
pr_debug("memshare: Modem has booted up\n");
for (i = 0; i < MAX_CLIENTS; i++) {
+ size = memblock[i].size;
if (memblock[i].free_memory > 0 &&
bootup_request >= 2) {
memblock[i].free_memory -= 1;
@@ -430,9 +431,18 @@
memblock[i].hyp_mapping = 0;
}
}
+ if (memblock[i].client_id == 1) {
+ /*
+ * Check if the client id
+ * is of diag so that free
+ * the memory region of
+ * client's size + guard
+ * bytes of 4K.
+ */
+ size += MEMSHARE_GUARD_BYTES;
+ }
dma_free_attrs(memsh_drv->dev,
- memblock[i].size,
- memblock[i].virtual_addr,
+ size, memblock[i].virtual_addr,
memblock[i].phy_addr,
attrs);
free_client(i);
@@ -635,7 +645,7 @@
{
struct mem_free_generic_req_msg_v01 *free_req;
struct mem_free_generic_resp_msg_v01 free_resp;
- int rc, flag = 0, ret = 0;
+ int rc, flag = 0, ret = 0, size = 0;
uint32_t client_id;
u32 source_vmlist[1] = {VMID_MSS_MSA};
int dest_vmids[1] = {VMID_HLOS};
@@ -669,7 +679,18 @@
pr_err("memshare: %s, failed to unmap the region\n",
__func__);
}
- dma_free_attrs(memsh_drv->dev, memblock[client_id].size,
+ size = memblock[client_id].size;
+ if (memblock[client_id].client_id == 1) {
+ /*
+ * Check if the client id
+ * is of diag so that free
+ * the memory region of
+ * client's size + guard
+ * bytes of 4K.
+ */
+ size += MEMSHARE_GUARD_BYTES;
+ }
+ dma_free_attrs(memsh_drv->dev, size,
memblock[client_id].virtual_addr,
memblock[client_id].phy_addr,
attrs);
diff --git a/drivers/soc/qcom/pil_bg_intf.h b/drivers/soc/qcom/pil_bg_intf.h
new file mode 100644
index 0000000..722024b
--- /dev/null
+++ b/drivers/soc/qcom/pil_bg_intf.h
@@ -0,0 +1,43 @@
+/* Copyright (c) 2017-2018 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.
+ */
+
+#ifndef __BG_INTF_H_
+#define __BG_INTF_H_
+
+#define MAX_APP_NAME_SIZE 100
+#define RESULT_SUCCESS 0
+#define RESULT_FAILURE -1
+
+/* tzapp command list.*/
+enum bg_tz_commands {
+ BGPIL_RAMDUMP,
+ BGPIL_IMAGE_LOAD,
+ BGPIL_AUTH_MDT,
+ BGPIL_DLOAD_CONT,
+};
+
+/* tzapp bg request.*/
+__packed struct tzapp_bg_req {
+ uint8_t tzapp_bg_cmd;
+ phys_addr_t address_fw;
+ size_t size_fw;
+};
+
+/* tzapp bg response.*/
+__packed struct tzapp_bg_rsp {
+ uint32_t tzapp_bg_cmd;
+ uint32_t bg_info_len;
+ uint32_t status;
+ uint32_t bg_info[100];
+};
+
+#endif
diff --git a/drivers/soc/qcom/rpmh_master_stat.c b/drivers/soc/qcom/rpmh_master_stat.c
index e696d4d..3a77ed8 100644
--- a/drivers/soc/qcom/rpmh_master_stat.c
+++ b/drivers/soc/qcom/rpmh_master_stat.c
@@ -103,6 +103,7 @@
struct msm_rpmh_master_stats *record,
const char *name)
{
+ uint64_t temp_accumulated_duration = record->accumulated_duration;
/*
* If a master is in sleep when reading the sleep stats from SMEM
* adjust the accumulated sleep duration to show actual sleep time.
@@ -110,7 +111,7 @@
* the purpose of computing battery utilization.
*/
if (record->last_entered > record->last_exited)
- record->accumulated_duration +=
+ temp_accumulated_duration +=
(arch_counter_get_cntvct()
- record->last_entered);
@@ -121,7 +122,7 @@
"\tSleep Accumulated Duration:0x%llx\n\n",
name, record->version_id, record->counts,
record->last_entered, record->last_exited,
- record->accumulated_duration);
+ temp_accumulated_duration);
}
static ssize_t msm_rpmh_master_stats_show(struct kobject *kobj,
diff --git a/drivers/soc/qcom/socinfo.c b/drivers/soc/qcom/socinfo.c
index d8fcf5f..a82cb43 100644
--- a/drivers/soc/qcom/socinfo.c
+++ b/drivers/soc/qcom/socinfo.c
@@ -617,6 +617,8 @@
/* SDM429 and SDM439 ID*/
[353] = {MSM_CPU_SDM439, "SDM439"},
[354] = {MSM_CPU_SDM429, "SDM429"},
+ [363] = {MSM_CPU_SDA439, "SDA439"},
+ [364] = {MSM_CPU_SDA429, "SDA429"},
/* Uninitialized IDs are not known to run Linux.
* MSM_CPU_UNKNOWN is set to 0 to ensure these IDs are
@@ -1573,6 +1575,14 @@
dummy_socinfo.id = 354;
strlcpy(dummy_socinfo.build_id, "sdm429 - ",
sizeof(dummy_socinfo.build_id));
+ } else if (early_machine_is_sda439()) {
+ dummy_socinfo.id = 363;
+ strlcpy(dummy_socinfo.build_id, "sda439 - ",
+ sizeof(dummy_socinfo.build_id));
+ } else if (early_machine_is_sda429()) {
+ dummy_socinfo.id = 364;
+ strlcpy(dummy_socinfo.build_id, "sda429 - ",
+ sizeof(dummy_socinfo.build_id));
} else if (early_machine_is_mdm9607()) {
dummy_socinfo.id = 290;
strlcpy(dummy_socinfo.build_id, "mdm9607 - ",
diff --git a/drivers/soc/qcom/subsys-pil-bg.c b/drivers/soc/qcom/subsys-pil-bg.c
new file mode 100644
index 0000000..75c3666
--- /dev/null
+++ b/drivers/soc/qcom/subsys-pil-bg.c
@@ -0,0 +1,771 @@
+/* Copyright (c) 2017-2018, 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 <linux/kernel.h>
+#include <linux/err.h>
+#include <linux/io.h>
+#include <linux/module.h>
+#include <linux/platform_device.h>
+#include <linux/of.h>
+#include <linux/interrupt.h>
+#include <linux/of_gpio.h>
+#include <linux/delay.h>
+#include <linux/slab.h>
+#include <linux/dma-mapping.h>
+#include <linux/reboot.h>
+#include <soc/qcom/subsystem_restart.h>
+#include <soc/qcom/ramdump.h>
+#include <soc/qcom/subsystem_notif.h>
+#include <linux/highmem.h>
+
+#include "peripheral-loader.h"
+#include "../../misc/qseecom_kernel.h"
+#include "pil_bg_intf.h"
+
+#define INVALID_GPIO -1
+#define NUM_GPIOS 4
+#define SECURE_APP "bgapp"
+#define desc_to_data(d) container_of(d, struct pil_bg_data, desc)
+#define subsys_to_data(d) container_of(d, struct pil_bg_data, subsys_desc)
+#define BG_RAMDUMP_SZ 0x00102000
+#define BG_CRASH_IN_TWM 2
+/**
+ * struct pil_bg_data
+ * @qseecom_handle: handle of TZ app
+ * @bg_queue: private queue to schedule worker threads for bottom half
+ * @restart_work: work struct for executing ssr
+ * @reboot_blk: notification block for reboot event
+ * @subsys_desc: subsystem descriptor
+ * @subsys: subsystem device pointer
+ * @gpios: array to hold all gpio handle
+ * @desc: PIL descriptor
+ * @address_fw: address where firmware binaries loaded
+ * @ramdump_dev: ramdump device pointer
+ * @size_fw: size of bg firmware binaries
+ * @errfatal_irq: irq number to indicate bg crash or shutdown
+ * @status_irq: irq to indicate bg status
+ * @app_status: status of tz app loading
+ * @is_ready: Is BG chip up
+ * @err_ready: The error ready signal
+ */
+
+struct pil_bg_data {
+ struct qseecom_handle *qseecom_handle;
+ struct workqueue_struct *bg_queue;
+ struct work_struct restart_work;
+ struct notifier_block reboot_blk;
+ struct subsys_desc subsys_desc;
+ struct subsys_device *subsys;
+ unsigned int gpios[NUM_GPIOS];
+ int errfatal_irq;
+ int status_irq;
+ struct pil_desc desc;
+ phys_addr_t address_fw;
+ void *ramdump_dev;
+ u32 cmd_status;
+ size_t size_fw;
+ int app_status;
+ bool is_ready;
+ struct completion err_ready;
+};
+
+static irqreturn_t bg_status_change(int irq, void *dev_id);
+
+/**
+ * bg_app_shutdown_notify() - Toggle AP2BG err fatal gpio when
+ * called by SSR framework.
+ * @subsys: struct containing private BG data.
+ *
+ * Return: none.
+ */
+static void bg_app_shutdown_notify(const struct subsys_desc *subsys)
+{
+ struct pil_bg_data *bg_data = subsys_to_data(subsys);
+ /* Toggle AP2BG err fatal gpio here to inform apps err fatal event */
+ if (gpio_is_valid(bg_data->gpios[2]))
+ gpio_set_value(bg_data->gpios[2], 1);
+}
+
+/**
+ * bg_app_reboot_notify() - Toggle AP2BG err fatal gpio.
+ * @nb: struct containing private BG data.
+ *
+ * Return: NOTIFY_DONE indicating success.
+ */
+static int bg_app_reboot_notify(struct notifier_block *nb,
+ unsigned long code, void *unused)
+{
+ struct pil_bg_data *bg_data = container_of(nb,
+ struct pil_bg_data, reboot_blk);
+ /* Toggle AP2BG err fatal gpio here to inform apps err fatal event */
+ if (gpio_is_valid(bg_data->gpios[2]))
+ gpio_set_value(bg_data->gpios[2], 1);
+ return NOTIFY_DONE;
+}
+
+/**
+ * get_cmd_rsp_buffers() - Function sets cmd & rsp buffer pointers and
+ * aligns buffer lengths
+ * @hdl: index of qseecom_handle
+ * @cmd: req buffer - set to qseecom_handle.sbuf
+ * @cmd_len: ptr to req buffer len
+ * @rsp: rsp buffer - set to qseecom_handle.sbuf + offset
+ * @rsp_len: ptr to rsp buffer len
+ *
+ * Return: Success always .
+ */
+static int get_cmd_rsp_buffers(struct qseecom_handle *handle, void **cmd,
+ uint32_t *cmd_len, void **rsp, uint32_t *rsp_len)
+{
+ *cmd = handle->sbuf;
+ if (*cmd_len & QSEECOM_ALIGN_MASK)
+ *cmd_len = QSEECOM_ALIGN(*cmd_len);
+
+ *rsp = handle->sbuf + *cmd_len;
+ if (*rsp_len & QSEECOM_ALIGN_MASK)
+ *rsp_len = QSEECOM_ALIGN(*rsp_len);
+
+ return 0;
+}
+
+/**
+ * pil_load_bg_tzapp() - Called to load TZ app.
+ * @pbd: struct containing private BG data.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int pil_load_bg_tzapp(struct pil_bg_data *pbd)
+{
+ int rc;
+
+ /* return success if already loaded */
+ if (pbd->qseecom_handle && !pbd->app_status)
+ return 0;
+ /* Load the APP */
+ rc = qseecom_start_app(&pbd->qseecom_handle, SECURE_APP, SZ_4K);
+ if (rc < 0) {
+ dev_err(pbd->desc.dev, "BG TZ app load failure\n");
+ pbd->app_status = RESULT_FAILURE;
+ return -EIO;
+ }
+ pbd->app_status = RESULT_SUCCESS;
+ return 0;
+}
+
+/**
+ * bgpil_tzapp_comm() - Function called to communicate with TZ APP.
+ * @req: struct containing command and parameters.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static long bgpil_tzapp_comm(struct pil_bg_data *pbd,
+ struct tzapp_bg_req *req)
+{
+ struct tzapp_bg_req *bg_tz_req;
+ struct tzapp_bg_rsp *bg_tz_rsp;
+ int rc, req_len, rsp_len;
+
+ /* Fill command structure */
+ req_len = sizeof(struct tzapp_bg_req);
+ rsp_len = sizeof(struct tzapp_bg_rsp);
+ rc = get_cmd_rsp_buffers(pbd->qseecom_handle,
+ (void **)&bg_tz_req, &req_len,
+ (void **)&bg_tz_rsp, &rsp_len);
+ if (rc)
+ goto end;
+
+ bg_tz_req->tzapp_bg_cmd = req->tzapp_bg_cmd;
+ bg_tz_req->address_fw = req->address_fw;
+ bg_tz_req->size_fw = req->size_fw;
+ rc = qseecom_send_command(pbd->qseecom_handle,
+ (void *)bg_tz_req, req_len, (void *)bg_tz_rsp, rsp_len);
+ pr_debug("BG PIL qseecom returned with value 0x%x and status 0x%x\n",
+ rc, bg_tz_rsp->status);
+ if (rc || bg_tz_rsp->status)
+ pbd->cmd_status = bg_tz_rsp->status;
+ else
+ pbd->cmd_status = 0;
+end:
+ return rc;
+}
+
+/**
+ * wait_for_err_ready() - Called in power_up to wait for error ready.
+ * Signal waiting function.
+ * @bg_data: BG PIL private structure.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int wait_for_err_ready(struct pil_bg_data *bg_data)
+{
+ int ret;
+
+ if ((!bg_data->status_irq))
+ return 0;
+
+ ret = wait_for_completion_timeout(&bg_data->err_ready,
+ msecs_to_jiffies(10000));
+ if (!ret) {
+ pr_err("[%s]: Error ready timed out\n", bg_data->desc.name);
+ return -ETIMEDOUT;
+ }
+ return 0;
+}
+
+/**
+ * bg_powerup() - Called by SSR framework on userspace invocation.
+ * does load tz app and call peripheral loader.
+ * @subsys: struct containing private BG data.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int bg_powerup(const struct subsys_desc *subsys)
+{
+ struct pil_bg_data *bg_data = subsys_to_data(subsys);
+ int ret;
+
+ init_completion(&bg_data->err_ready);
+ if (!bg_data->qseecom_handle) {
+ ret = pil_load_bg_tzapp(bg_data);
+ if (ret) {
+ dev_err(bg_data->desc.dev,
+ "%s: BG TZ app load failure\n",
+ __func__);
+ return ret;
+ }
+ }
+ pr_debug("bgapp loaded\n");
+ bg_data->desc.fw_name = subsys->fw_name;
+
+ ret = devm_request_irq(bg_data->desc.dev, bg_data->status_irq,
+ bg_status_change,
+ IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING | IRQF_ONESHOT,
+ "bg2ap_status", bg_data);
+ if (ret < 0) {
+ dev_err(bg_data->desc.dev,
+ "%s: BG2AP_STATUS IRQ#%d re registration failed, err=%d",
+ __func__, bg_data->status_irq, ret);
+ return ret;
+ }
+ disable_irq(bg_data->status_irq);
+
+ /* Enable status and err fatal irqs */
+ ret = pil_boot(&bg_data->desc);
+ if (ret) {
+ dev_err(bg_data->desc.dev,
+ "%s: BG PIL Boot failed\n", __func__);
+ return ret;
+ }
+ enable_irq(bg_data->status_irq);
+ enable_irq(bg_data->errfatal_irq);
+ ret = wait_for_err_ready(bg_data);
+ if (ret) {
+ dev_err(bg_data->desc.dev,
+ "[%s:%d]: Timed out waiting for error ready: %s!\n",
+ current->comm, current->pid, bg_data->desc.name);
+ return ret;
+ }
+ return ret;
+}
+
+/**
+ * bg_shutdown() - Called by SSR framework on userspace invocation.
+ * disable status interrupt to avoid spurious signal during PRM exit.
+ * @subsys: struct containing private BG data.
+ * @force_stop: unused
+ *
+ * Return: always success
+ */
+static int bg_shutdown(const struct subsys_desc *subsys, bool force_stop)
+{
+ struct pil_bg_data *bg_data = subsys_to_data(subsys);
+
+ disable_irq(bg_data->status_irq);
+ devm_free_irq(bg_data->desc.dev, bg_data->status_irq, bg_data);
+ disable_irq(bg_data->errfatal_irq);
+ bg_data->is_ready = false;
+ return 0;
+}
+
+/**
+ * bg_auth_metadata() - Called by Peripheral loader framework
+ * send command to tz app for authentication of metadata.
+ * @pil: pil descriptor.
+ * @metadata: metadata load address
+ * @size: size of metadata
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int bg_auth_metadata(struct pil_desc *pil,
+ const u8 *metadata, size_t size,
+ phys_addr_t addr, void *sz)
+{
+ struct pil_bg_data *bg_data = desc_to_data(pil);
+ struct tzapp_bg_req bg_tz_req;
+ void *mdata_buf;
+ dma_addr_t mdata_phys;
+ unsigned long attrs = 0;
+ struct device dev = {0};
+ int ret;
+
+ arch_setup_dma_ops(&dev, 0, 0, NULL, 0);
+
+ dev.coherent_dma_mask = DMA_BIT_MASK(sizeof(dma_addr_t) * 8);
+ attrs |= DMA_ATTR_STRONGLY_ORDERED;
+ mdata_buf = dma_alloc_attrs(&dev, size,
+ &mdata_phys, GFP_KERNEL, attrs);
+
+ if (!mdata_buf) {
+ pr_err("BG_PIL: Allocation for metadata failed.\n");
+ return -ENOMEM;
+ }
+
+ /* Make sure there are no mappings in PKMAP and fixmap */
+ kmap_flush_unused();
+ kmap_atomic_flush_unused();
+
+ memcpy(mdata_buf, metadata, size);
+
+ bg_tz_req.tzapp_bg_cmd = BGPIL_AUTH_MDT;
+ bg_tz_req.address_fw = (phys_addr_t)mdata_phys;
+ bg_tz_req.size_fw = size;
+
+ ret = bgpil_tzapp_comm(bg_data, &bg_tz_req);
+ if (ret || bg_data->cmd_status) {
+ dev_err(pil->dev,
+ "%s: BGPIL_AUTH_MDT qseecom call failed\n",
+ __func__);
+ return bg_data->cmd_status;
+ }
+ dma_free_attrs(&dev, size, mdata_buf, mdata_phys, attrs);
+ pr_debug("BG MDT Authenticated\n");
+ return 0;
+}
+
+/**
+ * bg_get_firmware_addr() - Called by Peripheral loader framework
+ * to get address and size of bg firmware binaries.
+ * @pil: pil descriptor.
+ * @addr: fw load address
+ * @size: size of fw
+ *
+ * Return: 0 on success.
+ */
+static int bg_get_firmware_addr(struct pil_desc *pil,
+ phys_addr_t addr, size_t size)
+{
+ struct pil_bg_data *bg_data = desc_to_data(pil);
+
+ bg_data->address_fw = addr;
+ bg_data->size_fw = size;
+ pr_debug("BG PIL loads firmware blobs at 0x%x with size 0x%x\n",
+ addr, size);
+ return 0;
+}
+
+
+/**
+ * bg_auth_and_xfer() - Called by Peripheral loader framework
+ * to signal tz app to authenticate and boot bg chip.
+ * @pil: pil descriptor.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int bg_auth_and_xfer(struct pil_desc *pil)
+{
+ struct pil_bg_data *bg_data = desc_to_data(pil);
+ struct tzapp_bg_req bg_tz_req;
+ int ret;
+
+ bg_tz_req.tzapp_bg_cmd = BGPIL_IMAGE_LOAD;
+ bg_tz_req.address_fw = bg_data->address_fw;
+ bg_tz_req.size_fw = bg_data->size_fw;
+
+ ret = bgpil_tzapp_comm(bg_data, &bg_tz_req);
+ if (bg_data->cmd_status == BG_CRASH_IN_TWM) {
+ /* Do ramdump and resend boot cmd */
+ bg_data->subsys_desc.ramdump(true, &bg_data->subsys_desc);
+ bg_tz_req.tzapp_bg_cmd = BGPIL_DLOAD_CONT;
+ ret = bgpil_tzapp_comm(bg_data, &bg_tz_req);
+ }
+ if (ret || bg_data->cmd_status) {
+ dev_err(pil->dev,
+ "%s: BGPIL_IMAGE_LOAD qseecom call failed\n",
+ __func__);
+ pil_free_memory(&bg_data->desc);
+ return bg_data->cmd_status;
+ }
+ /* BG Transfer of image is complete, free up the memory */
+ pr_debug("BG Firmware authentication and transfer done\n");
+ pil_free_memory(&bg_data->desc);
+ return 0;
+}
+
+/**
+ * bg_ramdump() - Called by SSR framework to save dump of BG internal
+ * memory, BG PIL does allocate region from dynamic memory and pass this
+ * region to tz to dump memory content of BG.
+ * @subsys: subsystem descriptor.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int bg_ramdump(int enable, const struct subsys_desc *subsys)
+{
+ struct pil_bg_data *bg_data = subsys_to_data(subsys);
+ struct pil_desc desc = bg_data->desc;
+ struct ramdump_segment *ramdump_segments;
+ struct tzapp_bg_req bg_tz_req;
+ phys_addr_t start_addr;
+ void *region;
+ int ret;
+ struct device dev = {0};
+
+ arch_setup_dma_ops(&dev, 0, 0, NULL, 0);
+
+ desc.attrs = 0;
+ desc.attrs |= DMA_ATTR_SKIP_ZEROING;
+ desc.attrs |= DMA_ATTR_STRONGLY_ORDERED;
+
+ region = dma_alloc_attrs(desc.dev, BG_RAMDUMP_SZ,
+ &start_addr, GFP_KERNEL, desc.attrs);
+
+ if (region == NULL) {
+ dev_dbg(desc.dev,
+ "BG PIL failure to allocate ramdump region of size %zx\n",
+ BG_RAMDUMP_SZ);
+ return -ENOMEM;
+ }
+
+ ramdump_segments = kcalloc(1, sizeof(*ramdump_segments), GFP_KERNEL);
+ if (!ramdump_segments)
+ return -ENOMEM;
+
+ bg_tz_req.tzapp_bg_cmd = BGPIL_RAMDUMP;
+ bg_tz_req.address_fw = start_addr;
+ bg_tz_req.size_fw = BG_RAMDUMP_SZ;
+
+ ret = bgpil_tzapp_comm(bg_data, &bg_tz_req);
+ if (ret || bg_data->cmd_status) {
+ dev_dbg(desc.dev, "%s: BG PIL ramdump collection failed\n",
+ __func__);
+ return bg_data->cmd_status;
+ }
+
+ ramdump_segments->address = start_addr;
+ ramdump_segments->size = BG_RAMDUMP_SZ;
+
+ do_ramdump(bg_data->ramdump_dev, ramdump_segments, 1);
+ kfree(ramdump_segments);
+ dma_free_attrs(desc.dev, BG_RAMDUMP_SZ, region,
+ start_addr, desc.attrs);
+ return 0;
+}
+
+static struct pil_reset_ops pil_ops_trusted = {
+ .init_image = bg_auth_metadata,
+ .mem_setup = bg_get_firmware_addr,
+ .auth_and_reset = bg_auth_and_xfer,
+ .shutdown = NULL,
+ .proxy_vote = NULL,
+ .proxy_unvote = NULL,
+};
+
+/**
+ * bg_restart_work() - scheduled by interrupt handler to carry
+ * out ssr sequence
+ * @work: work struct.
+ *
+ * Return: none.
+ */
+static void bg_restart_work(struct work_struct *work)
+{
+ struct pil_bg_data *drvdata =
+ container_of(work, struct pil_bg_data, restart_work);
+ subsystem_restart_dev(drvdata->subsys);
+}
+
+static irqreturn_t bg_errfatal(int irq, void *dev_id)
+{
+ struct pil_bg_data *drvdata = (struct pil_bg_data *)dev_id;
+
+ if (!drvdata)
+ return IRQ_HANDLED;
+
+ dev_dbg(drvdata->desc.dev, "BG s/w err fatal\n");
+
+ queue_work(drvdata->bg_queue, &drvdata->restart_work);
+
+ return IRQ_HANDLED;
+}
+
+static irqreturn_t bg_status_change(int irq, void *dev_id)
+{
+ bool value;
+ struct pil_bg_data *drvdata = (struct pil_bg_data *)dev_id;
+
+ if (!drvdata)
+ return IRQ_HANDLED;
+
+ value = gpio_get_value(drvdata->gpios[0]);
+ if (value == true && !drvdata->is_ready) {
+ dev_info(drvdata->desc.dev,
+ "BG services are up and running: irq state changed 0->1\n");
+ drvdata->is_ready = true;
+ complete(&drvdata->err_ready);
+ } else if (value == false && drvdata->is_ready) {
+ dev_err(drvdata->desc.dev,
+ "BG got unexpected reset: irq state changed 1->0\n");
+ drvdata->is_ready = false;
+ queue_work(drvdata->bg_queue, &drvdata->restart_work);
+ } else {
+ dev_err(drvdata->desc.dev,
+ "BG status irq: unknown status\n");
+ }
+
+ return IRQ_HANDLED;
+}
+
+/**
+ * setup_bg_gpio_irq() - called in probe to configure input/
+ * output gpio.
+ * @drvdata: private data struct for BG.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int setup_bg_gpio_irq(struct platform_device *pdev,
+ struct pil_bg_data *drvdata)
+{
+ int ret = -1;
+ int irq, i;
+
+ if (gpio_request(drvdata->gpios[0], "BG2AP_STATUS")) {
+ dev_err(&pdev->dev,
+ "%s Failed to configure BG2AP_STATUS gpio\n",
+ __func__);
+ goto err;
+ }
+ if (gpio_request(drvdata->gpios[1], "BG2AP_ERRFATAL")) {
+ dev_err(&pdev->dev,
+ "%s Failed to configure BG2AP_ERRFATAL gpio\n",
+ __func__);
+ goto err;
+ }
+ gpio_direction_input(drvdata->gpios[0]);
+ gpio_direction_input(drvdata->gpios[1]);
+ /* BG2AP STATUS IRQ */
+ irq = gpio_to_irq(drvdata->gpios[0]);
+ if (irq < 0) {
+ dev_err(&pdev->dev,
+ "%s: bad BG2AP_STATUS IRQ resource, err = %d\n",
+ __func__, irq);
+ goto err;
+ }
+
+ drvdata->status_irq = irq;
+ /* BG2AP ERR_FATAL irq. */
+ irq = gpio_to_irq(drvdata->gpios[1]);
+ if (irq < 0) {
+ dev_err(&pdev->dev, "bad BG2AP_ERRFATAL IRQ resource\n");
+ goto err;
+ }
+ ret = request_irq(irq, bg_errfatal,
+ IRQF_TRIGGER_RISING | IRQF_ONESHOT, "bg2ap_errfatal", drvdata);
+ if (ret < 0) {
+ dev_err(&pdev->dev,
+ "%s: BG2AP_ERRFATAL IRQ#%d request failed,\n",
+ __func__, irq);
+ goto err;
+ }
+ drvdata->errfatal_irq = irq;
+ enable_irq(drvdata->errfatal_irq);
+ /* Configure outgoing GPIO's */
+ if (gpio_request(drvdata->gpios[2], "AP2BG_ERRFATAL")) {
+ dev_err(&pdev->dev,
+ "%s Failed to configure AP2BG_ERRFATAL gpio\n",
+ __func__);
+ goto err;
+ }
+ if (gpio_request(drvdata->gpios[3], "AP2BG_STATUS")) {
+ dev_err(&pdev->dev,
+ "%s Failed to configure AP2BG_STATUS gpio\n",
+ __func__);
+ goto err;
+ }
+ /*
+ * Put status gpio in default high state which will
+ * make transition to low on any sudden reset case of msm
+ */
+ gpio_direction_output(drvdata->gpios[2], 0);
+ gpio_direction_output(drvdata->gpios[3], 1);
+ /* Inform BG that AP is up */
+ gpio_set_value(drvdata->gpios[3], 1);
+ return 0;
+err:
+ for (i = 0; i < NUM_GPIOS; ++i) {
+ if (gpio_is_valid(drvdata->gpios[i]))
+ gpio_free(drvdata->gpios[i]);
+ }
+ return ret;
+}
+
+/**
+ * bg_dt_parse_gpio() - called in probe to parse gpio's
+ * @drvdata: private data struct for BG.
+ *
+ * Return: 0 on success. Error code on failure.
+ */
+static int bg_dt_parse_gpio(struct platform_device *pdev,
+ struct pil_bg_data *drvdata)
+{
+ int i, val;
+
+ for (i = 0; i < NUM_GPIOS; i++)
+ drvdata->gpios[i] = INVALID_GPIO;
+ val = of_get_named_gpio(pdev->dev.of_node,
+ "qcom,bg2ap-status-gpio", 0);
+ if (val >= 0)
+ drvdata->gpios[0] = val;
+ else {
+ pr_err("BG status gpio not found, error=%d\n", val);
+ return -EINVAL;
+ }
+ val = of_get_named_gpio(pdev->dev.of_node,
+ "qcom,bg2ap-errfatal-gpio", 0);
+ if (val >= 0)
+ drvdata->gpios[1] = val;
+ else {
+ pr_err("BG err-fatal gpio not found, error=%d\n", val);
+ return -EINVAL;
+ }
+ val = of_get_named_gpio(pdev->dev.of_node,
+ "qcom,ap2bg-errfatal-gpio", 0);
+ if (val >= 0)
+ drvdata->gpios[2] = val;
+ else {
+ pr_err("ap2bg err-fatal gpio not found, error=%d\n", val);
+ return -EINVAL;
+ }
+ val = of_get_named_gpio(pdev->dev.of_node,
+ "qcom,ap2bg-status-gpio", 0);
+ if (val >= 0)
+ drvdata->gpios[3] = val;
+ else {
+ pr_err("ap2bg status gpio not found, error=%d\n", val);
+ return -EINVAL;
+ }
+ return 0;
+}
+
+static int pil_bg_driver_probe(struct platform_device *pdev)
+{
+ struct pil_bg_data *bg_data;
+ int rc;
+
+ bg_data = devm_kzalloc(&pdev->dev, sizeof(*bg_data), GFP_KERNEL);
+ if (!bg_data)
+ return -ENOMEM;
+ platform_set_drvdata(pdev, bg_data);
+ rc = of_property_read_string(pdev->dev.of_node,
+ "qcom,firmware-name", &bg_data->desc.name);
+ if (rc)
+ return rc;
+ bg_data->desc.dev = &pdev->dev;
+ bg_data->desc.owner = THIS_MODULE;
+ bg_data->desc.ops = &pil_ops_trusted;
+ rc = pil_desc_init(&bg_data->desc);
+ if (rc)
+ return rc;
+ /* Read gpio configuration */
+ rc = bg_dt_parse_gpio(pdev, bg_data);
+ if (rc)
+ return rc;
+ rc = setup_bg_gpio_irq(pdev, bg_data);
+ if (rc < 0)
+ return rc;
+ bg_data->subsys_desc.name = bg_data->desc.name;
+ bg_data->subsys_desc.owner = THIS_MODULE;
+ bg_data->subsys_desc.dev = &pdev->dev;
+ bg_data->subsys_desc.shutdown = bg_shutdown;
+ bg_data->subsys_desc.powerup = bg_powerup;
+ bg_data->subsys_desc.ramdump = bg_ramdump;
+ bg_data->subsys_desc.free_memory = NULL;
+ bg_data->subsys_desc.crash_shutdown = bg_app_shutdown_notify;
+ bg_data->ramdump_dev =
+ create_ramdump_device(bg_data->subsys_desc.name, &pdev->dev);
+ if (!bg_data->ramdump_dev) {
+ rc = -ENOMEM;
+ goto err_ramdump;
+ }
+ bg_data->subsys = subsys_register(&bg_data->subsys_desc);
+ if (IS_ERR(bg_data->subsys)) {
+ rc = PTR_ERR(bg_data->subsys);
+ goto err_subsys;
+ }
+
+ bg_data->reboot_blk.notifier_call = bg_app_reboot_notify;
+ register_reboot_notifier(&bg_data->reboot_blk);
+
+ bg_data->bg_queue = alloc_workqueue("bg_queue", 0, 0);
+ if (!bg_data->bg_queue) {
+ dev_err(&pdev->dev, "could not create bg_queue\n");
+ subsys_unregister(bg_data->subsys);
+ goto err_subsys;
+ }
+ INIT_WORK(&bg_data->restart_work, bg_restart_work);
+ return 0;
+err_subsys:
+ destroy_ramdump_device(bg_data->ramdump_dev);
+err_ramdump:
+ pil_desc_release(&bg_data->desc);
+ return rc;
+}
+
+static int pil_bg_driver_exit(struct platform_device *pdev)
+{
+ struct pil_bg_data *bg_data = platform_get_drvdata(pdev);
+
+ subsys_unregister(bg_data->subsys);
+ destroy_ramdump_device(bg_data->ramdump_dev);
+ pil_desc_release(&bg_data->desc);
+
+ return 0;
+}
+
+const struct of_device_id pil_bg_match_table[] = {
+ {.compatible = "qcom,pil-blackghost"},
+ {}
+};
+
+static struct platform_driver pil_bg_driver = {
+ .probe = pil_bg_driver_probe,
+ .remove = pil_bg_driver_exit,
+ .driver = {
+ .name = "subsys-pil-bg",
+ .of_match_table = pil_bg_match_table,
+ .owner = THIS_MODULE,
+ },
+};
+
+static int __init pil_bg_init(void)
+{
+ return platform_driver_register(&pil_bg_driver);
+}
+module_init(pil_bg_init);
+
+static void __exit pil_bg_exit(void)
+{
+ platform_driver_unregister(&pil_bg_driver);
+}
+module_exit(pil_bg_exit);
+
+MODULE_DESCRIPTION("Support for booting QTI Blackghost SoC");
+MODULE_LICENSE("GPL v2");
diff --git a/drivers/usb/dwc3/dwc3-msm.c b/drivers/usb/dwc3/dwc3-msm.c
index 04bce36..3650b98 100644
--- a/drivers/usb/dwc3/dwc3-msm.c
+++ b/drivers/usb/dwc3/dwc3-msm.c
@@ -4100,6 +4100,10 @@
dbg_event(0xFF, "fw_restarthost", 0);
flush_delayed_work(&mdwc->sm_work);
+
+ if (!mdwc->in_host_mode)
+ goto err;
+
dbg_event(0xFF, "stop_host_mode", dwc->maximum_speed);
ret = dwc3_otg_start_host(mdwc, 0);
if (ret)
diff --git a/drivers/usb/dwc3/ep0.c b/drivers/usb/dwc3/ep0.c
index 381ad49..902d36e 100644
--- a/drivers/usb/dwc3/ep0.c
+++ b/drivers/usb/dwc3/ep0.c
@@ -1143,13 +1143,18 @@
__dwc3_ep0_do_control_status(dwc, dep);
}
-static void dwc3_ep0_end_control_data(struct dwc3 *dwc, struct dwc3_ep *dep)
+void dwc3_ep0_end_control_data(struct dwc3 *dwc, struct dwc3_ep *dep)
{
struct dwc3_gadget_ep_cmd_params params;
u32 cmd;
int ret;
- if (!dep->resource_index)
+ /*
+ * For status/DATA OUT stage, TRB will be queued on ep0 out
+ * endpoint for which resource index is zero. Hence allow
+ * queuing ENDXFER command for ep0 out endpoint.
+ */
+ if (!dep->resource_index && dep->number)
return;
cmd = DWC3_DEPCMD_ENDTRANSFER;
diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c
index 3c38ee1..243c078 100644
--- a/drivers/usb/dwc3/gadget.c
+++ b/drivers/usb/dwc3/gadget.c
@@ -3154,8 +3154,17 @@
* that EP0 is in setup phase by issuing a stall
* and restart if EP0 is not in setup phase.
*/
- if (dwc->ep0state != EP0_SETUP_PHASE)
+ if (dwc->ep0state != EP0_SETUP_PHASE) {
+ unsigned int dir;
+
+ dbg_event(0xFF, "CONTRPEND", dwc->ep0state);
+ dir = !!dwc->ep0_expect_in;
+ if (dwc->ep0state == EP0_DATA_PHASE)
+ dwc3_ep0_end_control_data(dwc, dwc->eps[dir]);
+ else
+ dwc3_ep0_end_control_data(dwc, dwc->eps[!dir]);
dwc3_ep0_stall_and_restart(dwc);
+ }
dwc3_stop_active_transfers(dwc);
dwc3_clear_stall_all_ep(dwc);
diff --git a/drivers/usb/dwc3/gadget.h b/drivers/usb/dwc3/gadget.h
index 8275e56..b3be233 100644
--- a/drivers/usb/dwc3/gadget.h
+++ b/drivers/usb/dwc3/gadget.h
@@ -98,6 +98,7 @@
void dwc3_ep0_interrupt(struct dwc3 *dwc,
const struct dwc3_event_depevt *event);
void dwc3_ep0_out_start(struct dwc3 *dwc);
+void dwc3_ep0_end_control_data(struct dwc3 *dwc, struct dwc3_ep *dep);
void dwc3_ep0_stall_and_restart(struct dwc3 *dwc);
int __dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value);
int dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value);
diff --git a/drivers/usb/gadget/ci13xxx_udc.c b/drivers/usb/gadget/ci13xxx_udc.c
index 75205bf..10d737f 100644
--- a/drivers/usb/gadget/ci13xxx_udc.c
+++ b/drivers/usb/gadget/ci13xxx_udc.c
@@ -3982,15 +3982,15 @@
return;
}
+#ifdef CONFIG_USB_GADGET_DEBUG_FILES
+ dbg_remove_files(&udc->gadget.dev);
+#endif
usb_del_gadget_udc(&udc->gadget);
if (udc->transceiver) {
otg_set_peripheral(udc->transceiver->otg, &udc->gadget);
usb_put_phy(udc->transceiver);
}
-#ifdef CONFIG_USB_GADGET_DEBUG_FILES
- dbg_remove_files(&udc->gadget.dev);
-#endif
destroy_eps(udc);
dma_pool_destroy(udc->td_pool);
dma_pool_destroy(udc->qh_pool);
diff --git a/drivers/usb/gadget/function/f_ccid.c b/drivers/usb/gadget/function/f_ccid.c
index 76b181a..631597e 100644
--- a/drivers/usb/gadget/function/f_ccid.c
+++ b/drivers/usb/gadget/function/f_ccid.c
@@ -1037,9 +1037,6 @@
pr_debug("ccid_bind_config\n");
ccid_dev->function.name = FUNCTION_NAME;
- ccid_dev->function.fs_descriptors = ccid_fs_descs;
- ccid_dev->function.hs_descriptors = ccid_hs_descs;
- ccid_dev->function.ss_descriptors = ccid_ss_descs;
ccid_dev->function.bind = ccid_function_bind;
ccid_dev->function.unbind = ccid_function_unbind;
ccid_dev->function.set_alt = ccid_function_set_alt;
diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c
index 47f1a8e..7897f68 100644
--- a/drivers/usb/gadget/function/f_fs.c
+++ b/drivers/usb/gadget/function/f_fs.c
@@ -1404,7 +1404,7 @@
*to = p->data;
}
- ffs_log("enter");
+ ffs_log("exit");
return res;
}
@@ -3633,6 +3633,8 @@
if (ffs->func) {
ffs_func_eps_disable(ffs->func);
ffs->func = NULL;
+ /* matching put to allow LPM on disconnect */
+ usb_gadget_autopm_put_async(ffs->gadget);
}
if (ffs->state == FFS_DEACTIVATED) {
@@ -3665,13 +3667,9 @@
static void ffs_func_disable(struct usb_function *f)
{
- struct ffs_function *func = ffs_func_from_usb(f);
- struct ffs_data *ffs = func->ffs;
-
ffs_log("enter");
ffs_func_set_alt(f, 0, (unsigned)-1);
- /* matching put to allow LPM on disconnect */
- usb_gadget_autopm_put_async(ffs->gadget);
+
ffs_log("exit");
}
diff --git a/drivers/usb/gadget/function/f_gsi.c b/drivers/usb/gadget/function/f_gsi.c
index 7d509db..5ffbf12 100644
--- a/drivers/usb/gadget/function/f_gsi.c
+++ b/drivers/usb/gadget/function/f_gsi.c
@@ -19,14 +19,35 @@
MODULE_PARM_DESC(qti_packet_debug, "Print QTI Packet's Raw Data");
static struct workqueue_struct *ipa_usb_wq;
-static struct gsi_inst_status {
- struct mutex gsi_lock;
- bool inst_exist;
- struct gsi_opts *opts;
-} inst_status[IPA_USB_MAX_TETH_PROT_SIZE];
+static struct f_gsi *__gsi[IPA_USB_MAX_TETH_PROT_SIZE];
+static void *ipc_log_ctxt;
+
+#define NUM_LOG_PAGES 15
+#define log_event_err(x, ...) do { \
+ if (gsi) { \
+ ipc_log_string(ipc_log_ctxt, "id%d:"x, gsi->prot_id, \
+ ##__VA_ARGS__); \
+ pr_err("id%d:"x, gsi->prot_id, ##__VA_ARGS__); \
+ } \
+} while (0)
+
+#define log_event_dbg(x, ...) do { \
+ if (gsi) { \
+ ipc_log_string(ipc_log_ctxt, "id%d:"x, gsi->prot_id, \
+ ##__VA_ARGS__); \
+ pr_debug("id%d:"x, gsi->prot_id, ##__VA_ARGS__); \
+ } \
+} while (0)
+
+#define log_event_info(x, ...) do { \
+ if (gsi) { \
+ ipc_log_string(ipc_log_ctxt, "id%d:"x, gsi->prot_id, \
+ ##__VA_ARGS__); \
+ pr_info("id%d:"x, gsi->prot_id, ##__VA_ARGS__); \
+ } \
+} while (0)
/* Deregister misc device and free instance structures */
-static void gsi_inst_clean(struct gsi_opts *opts);
static void gsi_rndis_ipa_reset_trigger(struct gsi_data_port *d_port);
static void ipa_disconnect_handler(struct gsi_data_port *d_port);
static int gsi_ctrl_send_notification(struct f_gsi *gsi);
@@ -921,68 +942,43 @@
struct gsi_ctrl_port,
ctrl_device);
struct f_gsi *gsi;
- struct gsi_inst_status *inst_cur;
if (!c_port) {
pr_err_ratelimited("%s: gsi ctrl port %pK", __func__, c_port);
return -ENODEV;
}
- gsi = container_of(c_port, struct f_gsi, c_port);
- inst_cur = &inst_status[gsi->prot_id];
+ gsi = c_port_to_gsi(c_port);
+
log_event_dbg("%s: open ctrl dev %s", __func__, c_port->name);
- mutex_lock(&inst_cur->gsi_lock);
-
- fp->private_data = &gsi->prot_id;
-
- if (!inst_cur->inst_exist) {
- mutex_unlock(&inst_cur->gsi_lock);
- log_event_err("%s: [prot_id = %d], GSI instance freed already\n",
- __func__, gsi->prot_id);
- return -ENODEV;
- }
-
if (c_port->is_open) {
- mutex_unlock(&inst_cur->gsi_lock);
log_event_err("%s: Already opened\n", __func__);
return -EBUSY;
}
c_port->is_open = true;
- mutex_unlock(&inst_cur->gsi_lock);
-
return 0;
}
static int gsi_ctrl_dev_release(struct inode *ip, struct file *fp)
{
- enum ipa_usb_teth_prot prot_id =
- *(enum ipa_usb_teth_prot *)(fp->private_data);
- struct gsi_inst_status *inst_cur = &inst_status[prot_id];
+ struct gsi_ctrl_port *c_port = container_of(fp->private_data,
+ struct gsi_ctrl_port,
+ ctrl_device);
struct f_gsi *gsi;
- mutex_lock(&inst_cur->gsi_lock);
-
- if (unlikely(inst_cur->inst_exist == false)) {
- if (inst_cur->opts) {
- /* GSI instance clean up */
- gsi_inst_clean(inst_cur->opts);
- inst_cur->opts = NULL;
- }
- mutex_unlock(&inst_cur->gsi_lock);
- pr_err_ratelimited("%s: prot_id:%d: delayed free memory\n",
- __func__, prot_id);
+ if (!c_port) {
+ pr_err_ratelimited("%s: gsi ctrl port NULL", __func__);
return -ENODEV;
}
- inst_cur->opts->gsi->c_port.is_open = false;
- gsi = inst_cur->opts->gsi;
- mutex_unlock(&inst_cur->gsi_lock);
+ gsi = c_port_to_gsi(c_port);
- log_event_dbg("close ctrl dev %s\n",
- inst_cur->opts->gsi->c_port.name);
+ log_event_dbg("close ctrl dev %s\n", c_port->name);
+
+ c_port->is_open = false;
return 0;
}
@@ -990,33 +986,23 @@
static ssize_t
gsi_ctrl_dev_read(struct file *fp, char __user *buf, size_t count, loff_t *pos)
{
- struct gsi_ctrl_port *c_port;
+ struct gsi_ctrl_port *c_port = container_of(fp->private_data,
+ struct gsi_ctrl_port,
+ ctrl_device);
struct gsi_ctrl_pkt *cpkt = NULL;
- enum ipa_usb_teth_prot prot_id =
- *(enum ipa_usb_teth_prot *)(fp->private_data);
- struct gsi_inst_status *inst_cur = &inst_status[prot_id];
- struct f_gsi *gsi;
unsigned long flags;
int ret = 0;
+ struct f_gsi *gsi;
- pr_debug("%s: Enter %zu", __func__, count);
-
- mutex_lock(&inst_cur->gsi_lock);
- if (unlikely(inst_cur->inst_exist == false)) {
- mutex_unlock(&inst_cur->gsi_lock);
- pr_err_ratelimited("%s: free_inst is called and being freed\n",
- __func__);
- return -ENODEV;
- }
- mutex_unlock(&inst_cur->gsi_lock);
-
- gsi = inst_cur->opts->gsi;
- c_port = &inst_cur->opts->gsi->c_port;
if (!c_port) {
- log_event_err("%s: gsi ctrl port %pK", __func__, c_port);
+ pr_err_ratelimited("%s: gsi ctrl port NULL", __func__);
return -ENODEV;
}
+ gsi = c_port_to_gsi(c_port);
+
+ log_event_dbg("%s: Enter %zu", __func__, count);
+
if (count > GSI_MAX_CTRL_PKT_SIZE) {
log_event_err("Large buff size %zu, should be %d",
count, GSI_MAX_CTRL_PKT_SIZE);
@@ -1079,34 +1065,32 @@
int ret = 0;
unsigned long flags;
struct gsi_ctrl_pkt *cpkt;
- struct gsi_ctrl_port *c_port;
- struct usb_request *req;
- enum ipa_usb_teth_prot prot_id =
- *(enum ipa_usb_teth_prot *)(fp->private_data);
- struct gsi_inst_status *inst_cur = &inst_status[prot_id];
struct f_gsi *gsi;
+ struct gsi_ctrl_port *c_port = container_of(fp->private_data,
+ struct gsi_ctrl_port,
+ ctrl_device);
- pr_debug("Enter %zu", count);
-
- mutex_lock(&inst_cur->gsi_lock);
- if (unlikely(inst_cur->inst_exist == false)) {
- mutex_unlock(&inst_cur->gsi_lock);
- pr_err_ratelimited("%s: free_inst is called and being freed\n",
- __func__);
+ if (!c_port) {
+ pr_err_ratelimited("%s: gsi ctrl port NULL", __func__);
return -ENODEV;
}
- mutex_unlock(&inst_cur->gsi_lock);
- gsi = inst_cur->opts->gsi;
- c_port = &gsi->c_port;
- req = c_port->notify_req;
-
- if (!c_port || !req || !req->buf) {
- log_event_err("%s: c_port %pK req %p req->buf %p",
- __func__, c_port, req, req ? req->buf : req);
+ if (!c_port->notify_req) {
+ pr_err_ratelimited("%s: gsi ctrl port notify_req NULL",
+ __func__);
return -ENODEV;
}
+ if (!c_port->notify_req->buf) {
+ pr_err_ratelimited("%s: gsi ctrl port notify_req->buf",
+ __func__);
+ return -ENODEV;
+ }
+
+ gsi = c_port_to_gsi(c_port);
+
+ log_event_dbg("%s: Enter %zu", __func__, count);
+
if (!count || count > GSI_MAX_CTRL_PKT_SIZE) {
log_event_err("error: ctrl pkt length %zu", count);
return -EINVAL;
@@ -1157,33 +1141,22 @@
static long gsi_ctrl_dev_ioctl(struct file *fp, unsigned int cmd,
unsigned long arg)
{
- struct gsi_ctrl_port *c_port;
+ struct gsi_ctrl_port *c_port = container_of(fp->private_data,
+ struct gsi_ctrl_port,
+ ctrl_device);
struct f_gsi *gsi;
struct gsi_ctrl_pkt *cpkt;
struct ep_info info;
- enum ipa_usb_teth_prot prot_id =
- *(enum ipa_usb_teth_prot *)(fp->private_data);
- struct gsi_inst_status *inst_cur = &inst_status[prot_id];
int val, ret = 0;
unsigned long flags;
- mutex_lock(&inst_cur->gsi_lock);
- if (unlikely(inst_cur->inst_exist == false)) {
- mutex_unlock(&inst_cur->gsi_lock);
- pr_err_ratelimited("%s: free_inst is called and being freed\n",
- __func__);
- return -ENODEV;
- }
- mutex_unlock(&inst_cur->gsi_lock);
-
- gsi = inst_cur->opts->gsi;
- c_port = &gsi->c_port;
-
if (!c_port) {
- log_event_err("%s: gsi ctrl port %pK", __func__, c_port);
+ pr_err_ratelimited("%s: gsi ctrl port NULL", __func__);
return -ENODEV;
}
+ gsi = c_port_to_gsi(c_port);
+
switch (cmd) {
case QTI_CTRL_MODEM_OFFLINE:
if (gsi->prot_id == IPA_USB_DIAG) {
@@ -1301,30 +1274,20 @@
static unsigned int gsi_ctrl_dev_poll(struct file *fp, poll_table *wait)
{
- struct gsi_ctrl_port *c_port;
- enum ipa_usb_teth_prot prot_id =
- *(enum ipa_usb_teth_prot *)(fp->private_data);
- struct gsi_inst_status *inst_cur = &inst_status[prot_id];
- struct f_gsi *gsi;
+ struct gsi_ctrl_port *c_port = container_of(fp->private_data,
+ struct gsi_ctrl_port,
+ ctrl_device);
unsigned long flags;
unsigned int mask = 0;
+ struct f_gsi *gsi;
- mutex_lock(&inst_cur->gsi_lock);
- if (unlikely(inst_cur->inst_exist == false)) {
- mutex_unlock(&inst_cur->gsi_lock);
- pr_err_ratelimited("%s: free_inst is called and being freed\n",
- __func__);
- return -ENODEV;
- }
- mutex_unlock(&inst_cur->gsi_lock);
-
- gsi = inst_cur->opts->gsi;
- c_port = &inst_cur->opts->gsi->c_port;
if (!c_port) {
- log_event_err("%s: gsi ctrl port %pK", __func__, c_port);
+ pr_err_ratelimited("%s: gsi ctrl port NULL", __func__);
return -ENODEV;
}
+ gsi = c_port_to_gsi(c_port);
+
poll_wait(fp, &c_port->read_wq, wait);
spin_lock_irqsave(&c_port->lock, flags);
@@ -1368,11 +1331,6 @@
int sz = GSI_CTRL_NAME_LEN;
bool ctrl_dev_create = true;
- if (!gsi) {
- log_event_err("%s: gsi prot ctx is NULL", __func__);
- return -EINVAL;
- }
-
INIT_LIST_HEAD(&gsi->c_port.cpkt_req_q);
INIT_LIST_HEAD(&gsi->c_port.cpkt_resp_q);
@@ -2917,7 +2875,9 @@
static void gsi_free_func(struct usb_function *f)
{
- pr_debug("%s\n", __func__);
+ struct f_gsi *gsi = func_to_gsi(f);
+
+ log_event_dbg("%s\n", __func__);
}
static int gsi_bind_config(struct f_gsi *gsi)
@@ -2970,21 +2930,15 @@
return status;
}
-static struct f_gsi *gsi_function_init(enum ipa_usb_teth_prot prot_id)
+static struct f_gsi *gsi_function_init(void)
{
struct f_gsi *gsi;
int ret = 0;
- if (prot_id >= IPA_USB_MAX_TETH_PROT_SIZE) {
- pr_err("%s: invalid prot id %d", __func__, prot_id);
- ret = -EINVAL;
- goto error;
- }
-
gsi = kzalloc(sizeof(*gsi), GFP_KERNEL);
if (!gsi) {
ret = -ENOMEM;
- goto error;
+ return ERR_PTR(ret);
}
spin_lock_init(&gsi->d_port.lock);
@@ -2994,19 +2948,9 @@
gsi->d_port.in_channel_handle = -EINVAL;
gsi->d_port.out_channel_handle = -EINVAL;
- gsi->prot_id = prot_id;
-
gsi->d_port.ipa_usb_wq = ipa_usb_wq;
- ret = gsi_function_ctrl_port_init(gsi);
- if (ret) {
- kfree(gsi);
- goto error;
- }
-
return gsi;
-error:
- return ERR_PTR(ret);
}
static void gsi_opts_release(struct config_item *item)
@@ -3217,23 +3161,12 @@
.ct_owner = THIS_MODULE,
};
-static void gsi_inst_clean(struct gsi_opts *opts)
-{
- if (opts->gsi->c_port.ctrl_device.fops)
- misc_deregister(&opts->gsi->c_port.ctrl_device);
-
- kfree(opts->gsi);
- kfree(opts);
-}
-
static int gsi_set_inst_name(struct usb_function_instance *fi,
const char *name)
{
- int prot_id, name_len;
+ int prot_id, name_len, ret = 0;
+ struct gsi_opts *opts;
struct f_gsi *gsi;
- char gsi_inst_name[MAX_INST_NAME_LEN + sizeof("gsi.") + 1];
- void *ipc_log_ctxt;
- struct gsi_opts *opts, *opts_prev;
opts = container_of(fi, struct gsi_opts, func_inst);
@@ -3248,73 +3181,27 @@
return -EINVAL;
}
- mutex_lock(&inst_status[prot_id].gsi_lock);
- opts_prev = inst_status[prot_id].opts;
- if (opts_prev) {
- mutex_unlock(&inst_status[prot_id].gsi_lock);
- pr_err("%s: prot_id = %d, prev inst do not freed yet\n",
- __func__, prot_id);
- return -EBUSY;
- }
- mutex_unlock(&inst_status[prot_id].gsi_lock);
-
if (prot_id == IPA_USB_RNDIS)
config_group_init_type_name(&opts->func_inst.group, "",
&gsi_func_rndis_type);
- gsi = gsi_function_init(prot_id);
- if (IS_ERR(gsi))
- return PTR_ERR(gsi);
-
- opts->gsi = gsi;
- /*
- * create instance name with prefixing "gsi." to differentiate
- * ipc log debugfs entry
- */
- snprintf(gsi_inst_name, sizeof(gsi_inst_name), "gsi.%s", name);
- ipc_log_ctxt = ipc_log_context_create(NUM_LOG_PAGES, gsi_inst_name, 0);
- if (!ipc_log_ctxt)
- pr_err("%s: Err allocating ipc_log_ctxt for prot:%s\n",
- __func__, gsi_inst_name);
- opts->gsi->ipc_log_ctxt = ipc_log_ctxt;
-
- /* Set instance status */
- mutex_lock(&inst_status[prot_id].gsi_lock);
- inst_status[prot_id].inst_exist = true;
- inst_status[prot_id].opts = opts;
- mutex_unlock(&inst_status[prot_id].gsi_lock);
-
- return 0;
+ gsi = opts->gsi = __gsi[prot_id];
+ opts->gsi->prot_id = prot_id;
+ ret = gsi_function_ctrl_port_init(opts->gsi);
+ if (ret)
+ log_event_err("%s:ctrl port init failed for %s instance\n",
+ __func__, name);
+ return ret;
}
static void gsi_free_inst(struct usb_function_instance *f)
{
struct gsi_opts *opts = container_of(f, struct gsi_opts, func_inst);
- enum ipa_usb_teth_prot prot_id;
- struct f_gsi *gsi;
- if (!opts->gsi)
- return;
+ if (opts && opts->gsi && opts->gsi->c_port.ctrl_device.fops)
+ misc_deregister(&opts->gsi->c_port.ctrl_device);
- prot_id = opts->gsi->prot_id;
- gsi = opts->gsi;
- mutex_lock(&inst_status[prot_id].gsi_lock);
- if (opts->gsi->c_port.is_open) {
- /* Mark instance exist as false */
- inst_status[prot_id].inst_exist = false;
- mutex_unlock(&inst_status[prot_id].gsi_lock);
- log_event_err(
- "%s: [prot_id = %d] Dev is open, free mem when dev close\n",
- __func__, prot_id);
- return;
- }
-
- ipc_log_context_destroy(opts->gsi->ipc_log_ctxt);
- /* Clear instance status */
- gsi_inst_clean(opts);
- inst_status[prot_id].inst_exist = false;
- inst_status[prot_id].opts = NULL;
- mutex_unlock(&inst_status[prot_id].gsi_lock);
+ kfree(opts);
}
static struct usb_function_instance *gsi_alloc_inst(void)
@@ -3362,8 +3249,15 @@
return -ENOMEM;
}
- for (i = 0; i < IPA_USB_MAX_TETH_PROT_SIZE; i++)
- mutex_init(&inst_status[i].gsi_lock);
+ for (i = 0; i < IPA_USB_MAX_TETH_PROT_SIZE; i++) {
+ __gsi[i] = gsi_function_init();
+ if (IS_ERR(__gsi[i]))
+ return PTR_ERR(__gsi[i]);
+ }
+
+ ipc_log_ctxt = ipc_log_context_create(NUM_LOG_PAGES, "usb_gsi", 0);
+ if (!ipc_log_ctxt)
+ pr_err("%s: Err allocating ipc_log_ctxt\n", __func__);
return usb_function_register(&gsiusb_func);
}
@@ -3371,8 +3265,16 @@
static void __exit fgsi_exit(void)
{
+ int i;
+
if (ipa_usb_wq)
destroy_workqueue(ipa_usb_wq);
+ if (ipc_log_ctxt)
+ ipc_log_context_destroy(ipc_log_ctxt);
+
+ for (i = 0; i < IPA_USB_MAX_TETH_PROT_SIZE; i++)
+ kfree(__gsi[i]);
+
usb_function_unregister(&gsiusb_func);
}
module_exit(fgsi_exit);
diff --git a/drivers/usb/gadget/function/f_gsi.h b/drivers/usb/gadget/function/f_gsi.h
index 71bea5e..c6e64fd 100644
--- a/drivers/usb/gadget/function/f_gsi.h
+++ b/drivers/usb/gadget/function/f_gsi.h
@@ -82,28 +82,6 @@
#define EVT_IPA_SUSPEND 9
#define EVT_RESUMED 10
-#define NUM_LOG_PAGES 10
-#define log_event_err(x, ...) do { \
- if (gsi) { \
- ipc_log_string(gsi->ipc_log_ctxt, x, ##__VA_ARGS__); \
- pr_err(x, ##__VA_ARGS__); \
- } \
-} while (0)
-
-#define log_event_dbg(x, ...) do { \
- if (gsi) { \
- ipc_log_string(gsi->ipc_log_ctxt, x, ##__VA_ARGS__); \
- pr_debug(x, ##__VA_ARGS__); \
- } \
-} while (0)
-
-#define log_event_info(x, ...) do { \
- if (gsi) { \
- ipc_log_string(gsi->ipc_log_ctxt, x, ##__VA_ARGS__); \
- pr_info(x, ##__VA_ARGS__); \
- } \
-} while (0)
-
enum connection_state {
STATE_UNINITIALIZED,
STATE_INITIALIZED,
@@ -275,7 +253,6 @@
struct gsi_data_port d_port;
struct gsi_ctrl_port c_port;
- void *ipc_log_ctxt;
bool rmnet_dtr_status;
};
@@ -313,15 +290,15 @@
if (!name)
goto error;
- if (!strncasecmp(name, "rndis", strlen("rndis")))
+ if (!strncasecmp(name, "rndis", MAX_INST_NAME_LEN))
return IPA_USB_RNDIS;
- if (!strncasecmp(name, "ecm", strlen("ecm")))
+ if (!strncasecmp(name, "ecm", MAX_INST_NAME_LEN))
return IPA_USB_ECM;
- if (!strncasecmp(name, "rmnet", strlen("rmnet")))
+ if (!strncasecmp(name, "rmnet", MAX_INST_NAME_LEN))
return IPA_USB_RMNET;
- if (!strncasecmp(name, "mbim", strlen("mbim")))
+ if (!strncasecmp(name, "mbim", MAX_INST_NAME_LEN))
return IPA_USB_MBIM;
- if (!strncasecmp(name, "dpl", strlen("dpl")))
+ if (!strncasecmp(name, "dpl", MAX_INST_NAME_LEN))
return IPA_USB_DIAG;
error:
@@ -879,6 +856,7 @@
.bEndpointAddress = USB_DIR_IN,
.bmAttributes = USB_ENDPOINT_XFER_BULK,
+ .wMaxPacketSize = 4*cpu_to_le16(NCM_STATUS_BYTECOUNT),
};
static struct usb_endpoint_descriptor mbim_gsi_fs_out_desc = {
@@ -887,6 +865,7 @@
.bEndpointAddress = USB_DIR_OUT,
.bmAttributes = USB_ENDPOINT_XFER_BULK,
+ .wMaxPacketSize = 4*cpu_to_le16(NCM_STATUS_BYTECOUNT),
};
static struct usb_descriptor_header *mbim_gsi_fs_function[] = {
@@ -1180,6 +1159,7 @@
.bEndpointAddress = USB_DIR_IN,
.bmAttributes = USB_ENDPOINT_XFER_BULK,
+ .wMaxPacketSize = cpu_to_le16(ECM_QC_STATUS_BYTECOUNT),
};
static struct usb_endpoint_descriptor ecm_gsi_fs_out_desc = {
@@ -1188,6 +1168,7 @@
.bEndpointAddress = USB_DIR_OUT,
.bmAttributes = USB_ENDPOINT_XFER_BULK,
+ .wMaxPacketSize = cpu_to_le16(ECM_QC_STATUS_BYTECOUNT),
};
static struct usb_descriptor_header *ecm_gsi_fs_function[] = {
diff --git a/drivers/usb/gadget/function/f_mtp.c b/drivers/usb/gadget/function/f_mtp.c
index 4cc7d94..651776d 100644
--- a/drivers/usb/gadget/function/f_mtp.c
+++ b/drivers/usb/gadget/function/f_mtp.c
@@ -1415,6 +1415,12 @@
dev->cdev = cdev;
DBG(cdev, "mtp_function_bind dev: %pK\n", dev);
+ /* ChipIdea controller supports 16K request length for IN endpoint */
+ if (cdev->gadget->is_chipidea && mtp_tx_req_len > 16384) {
+ DBG(cdev, "Truncating Tx Req length to 16K for ChipIdea\n");
+ mtp_tx_req_len = 16384;
+ }
+
/* allocate interface ID(s) */
id = usb_interface_id(c, f);
if (id < 0)
diff --git a/drivers/usb/gadget/function/f_qc_rndis.c b/drivers/usb/gadget/function/f_qc_rndis.c
index 908805a..df26403 100644
--- a/drivers/usb/gadget/function/f_qc_rndis.c
+++ b/drivers/usb/gadget/function/f_qc_rndis.c
@@ -1063,6 +1063,7 @@
* until we're activated via set_alt().
*/
+ c->cdev->gadget->bam2bam_func_enabled = true;
DBG(cdev, "RNDIS: %s speed IN/%s OUT/%s NOTIFY/%s\n",
gadget_is_superspeed(c->cdev->gadget) ? "super" :
gadget_is_dualspeed(c->cdev->gadget) ? "dual" : "full",
@@ -1116,6 +1117,7 @@
usb_free_descriptors(f->hs_descriptors);
usb_free_descriptors(f->fs_descriptors);
+ c->cdev->gadget->bam2bam_func_enabled = false;
kfree(rndis->notify_req->buf);
usb_ep_free_request(rndis->notify, rndis->notify_req);
diff --git a/drivers/usb/gadget/function/f_qdss.c b/drivers/usb/gadget/function/f_qdss.c
index 6ae2693..d1c3741 100644
--- a/drivers/usb/gadget/function/f_qdss.c
+++ b/drivers/usb/gadget/function/f_qdss.c
@@ -478,6 +478,7 @@
}
}
+ c->cdev->gadget->bam2bam_func_enabled = true;
return 0;
fail:
clear_eps(f);
@@ -494,7 +495,7 @@
pr_debug("qdss_unbind\n");
flush_workqueue(qdss->wq);
-
+ c->cdev->gadget->bam2bam_func_enabled = false;
clear_eps(f);
clear_desc(gadget, f);
}
diff --git a/drivers/usb/gadget/function/f_rmnet.c b/drivers/usb/gadget/function/f_rmnet.c
index ffc6897..bdb9762 100644
--- a/drivers/usb/gadget/function/f_rmnet.c
+++ b/drivers/usb/gadget/function/f_rmnet.c
@@ -480,6 +480,8 @@
if (dev->notify_req)
frmnet_free_req(dev->notify, dev->notify_req);
+
+ c->cdev->gadget->bam2bam_func_enabled = false;
}
static void frmnet_purge_responses(struct f_rmnet *dev)
@@ -1116,6 +1118,9 @@
return dev->ifc_id;
}
+ if (dev->xport_type == BAM2BAM_IPA)
+ c->cdev->gadget->bam2bam_func_enabled = true;
+
info.data_str_idx = 0;
if (dev->qti_port_type == QTI_PORT_RMNET) {
info.string_defs = rmnet_string_defs;
diff --git a/drivers/video/fbdev/msm/Makefile b/drivers/video/fbdev/msm/Makefile
index 4ee7f4a..81d4953 100644
--- a/drivers/video/fbdev/msm/Makefile
+++ b/drivers/video/fbdev/msm/Makefile
@@ -41,6 +41,7 @@
mdss-dsi-objs += mdss_dsi_panel.o
mdss-dsi-objs += msm_mdss_io_8974.o
mdss-dsi-objs += mdss_dsi_phy.o
+mdss-dsi-objs += mdss_dsi_phy_12nm.o
mdss-dsi-objs += mdss_dsi_clk.o
obj-$(CONFIG_FB_MSM_MDSS) += mdss-dsi.o
obj-$(CONFIG_FB_MSM_MDSS) += mdss_panel.o
diff --git a/drivers/video/fbdev/msm/mdss_dsi.c b/drivers/video/fbdev/msm/mdss_dsi.c
index 6bb0960..cad1387 100644
--- a/drivers/video/fbdev/msm/mdss_dsi.c
+++ b/drivers/video/fbdev/msm/mdss_dsi.c
@@ -2989,9 +2989,9 @@
info.core_clks.mmss_misc_ahb_clk =
ctrl_pdata->shared_data->mmss_misc_ahb_clk;
- info.link_clks.esc_clk = ctrl_pdata->esc_clk;
- info.link_clks.byte_clk = ctrl_pdata->byte_clk;
- info.link_clks.pixel_clk = ctrl_pdata->pixel_clk;
+ info.link_lp_clks.esc_clk = ctrl_pdata->esc_clk;
+ info.link_hs_clks.byte_clk = ctrl_pdata->byte_clk;
+ info.link_hs_clks.pixel_clk = ctrl_pdata->pixel_clk;
info.pre_clkoff_cb = mdss_dsi_pre_clkoff_cb;
info.post_clkon_cb = mdss_dsi_post_clkon_cb;
@@ -3976,13 +3976,12 @@
if (!data) {
pr_err("%s:%d, Unable to read Phy Strength ctrl settings\n",
__func__, __LINE__);
- return -EINVAL;
+ } else {
+ pinfo->mipi.dsi_phy_db.strength_len = len;
+ for (i = 0; i < len; i++)
+ pinfo->mipi.dsi_phy_db.strength[i] = data[i];
}
- pinfo->mipi.dsi_phy_db.strength_len = len;
- for (i = 0; i < len; i++)
- pinfo->mipi.dsi_phy_db.strength[i] = data[i];
-
pinfo->mipi.dsi_phy_db.reg_ldo_mode = of_property_read_bool(
ctrl_pdev->dev.of_node, "qcom,regulator-ldo-mode");
@@ -3991,13 +3990,12 @@
if (!data) {
pr_err("%s:%d, Unable to read Phy regulator settings\n",
__func__, __LINE__);
- return -EINVAL;
+ } else {
+ pinfo->mipi.dsi_phy_db.regulator_len = len;
+ for (i = 0; i < len; i++)
+ pinfo->mipi.dsi_phy_db.regulator[i] = data[i];
}
- pinfo->mipi.dsi_phy_db.regulator_len = len;
- for (i = 0; i < len; i++)
- pinfo->mipi.dsi_phy_db.regulator[i] = data[i];
-
data = of_get_property(ctrl_pdev->dev.of_node,
"qcom,platform-bist-ctrl", &len);
if ((!data) || (len != 6))
@@ -4012,13 +4010,12 @@
if (!data) {
pr_err("%s:%d, Unable to read Phy lane configure settings\n",
__func__, __LINE__);
- return -EINVAL;
+ } else {
+ pinfo->mipi.dsi_phy_db.lanecfg_len = len;
+ for (i = 0; i < len; i++)
+ pinfo->mipi.dsi_phy_db.lanecfg[i] = data[i];
}
- pinfo->mipi.dsi_phy_db.lanecfg_len = len;
- for (i = 0; i < len; i++)
- pinfo->mipi.dsi_phy_db.lanecfg[i] = data[i];
-
ctrl_pdata->timing_db_mode = of_property_read_bool(
ctrl_pdev->dev.of_node, "qcom,timing-db-mode");
diff --git a/drivers/video/fbdev/msm/mdss_dsi.h b/drivers/video/fbdev/msm/mdss_dsi.h
index 60bc455..058c27a 100644
--- a/drivers/video/fbdev/msm/mdss_dsi.h
+++ b/drivers/video/fbdev/msm/mdss_dsi.h
@@ -337,6 +337,7 @@
struct mdss_panel_timing timing;
uint32_t phy_timing[12];
uint32_t phy_timing_8996[40];
+ uint32_t phy_timing_12nm[8];
/* DSI_CLKOUT_TIMING_CTRL */
char t_clk_post;
char t_clk_pre;
@@ -616,15 +617,19 @@
struct mdss_dsi_ctrl_pdata *ctrl_pdata);
int mdss_dsi_pre_clkoff_cb(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state new_state);
int mdss_dsi_post_clkoff_cb(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state curr_state);
int mdss_dsi_post_clkon_cb(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state curr_state);
int mdss_dsi_pre_clkon_cb(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state new_state);
int mdss_dsi_panel_reset(struct mdss_panel_data *pdata, int enable);
void mdss_dsi_phy_disable(struct mdss_dsi_ctrl_pdata *ctrl);
diff --git a/drivers/video/fbdev/msm/mdss_dsi_clk.c b/drivers/video/fbdev/msm/mdss_dsi_clk.c
index 372c93e..779e847 100644
--- a/drivers/video/fbdev/msm/mdss_dsi_clk.c
+++ b/drivers/video/fbdev/msm/mdss_dsi_clk.c
@@ -27,11 +27,9 @@
};
struct dsi_link_clks {
- struct mdss_dsi_link_clk_info clks;
+ struct mdss_dsi_link_hs_clk_info hs_clks;
+ struct mdss_dsi_link_lp_clk_info lp_clks;
u32 current_clk_state;
- u32 byte_clk_rate;
- u32 pix_clk_rate;
- u32 esc_clk_rate;
};
struct mdss_dsi_clk_mngr {
@@ -73,28 +71,27 @@
rc = clk_prepare_enable(c_clks->clks.mdp_core_clk);
if (rc) {
- pr_err("%s: failed to enable mdp_core_clock. rc=%d\n",
- __func__, rc);
+ pr_err("failed to enable mdp_core_clock. rc=%d\n", rc);
goto error;
}
rc = clk_prepare_enable(c_clks->clks.ahb_clk);
if (rc) {
- pr_err("%s: failed to enable ahb clock. rc=%d\n", __func__, rc);
+ pr_err("failed to enable ahb clock. rc=%d\n", rc);
goto disable_core_clk;
}
rc = clk_prepare_enable(c_clks->clks.axi_clk);
if (rc) {
- pr_err("%s: failed to enable ahb clock. rc=%d\n", __func__, rc);
+ pr_err("failed to enable ahb clock. rc=%d\n", rc);
goto disable_ahb_clk;
}
if (c_clks->clks.mmss_misc_ahb_clk) {
rc = clk_prepare_enable(c_clks->clks.mmss_misc_ahb_clk);
if (rc) {
- pr_err("%s: failed to enable mmss misc ahb clk.rc=%d\n",
- __func__, rc);
+ pr_err("failed to enable mmss misc ahb clk.rc=%d\n",
+ rc);
goto disable_axi_clk;
}
}
@@ -140,12 +137,15 @@
return rc;
}
-static int dsi_link_clk_set_rate(struct dsi_link_clks *l_clks)
+static int dsi_link_hs_clk_set_rate(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks)
{
int rc = 0;
struct mdss_dsi_clk_mngr *mngr;
+ struct dsi_link_clks *l_clks;
struct mdss_dsi_ctrl_pdata *ctrl;
+ l_clks = container_of(link_hs_clks, struct dsi_link_clks, hs_clks);
mngr = container_of(l_clks, struct mdss_dsi_clk_mngr, link_clks);
/*
@@ -160,19 +160,13 @@
if (ctrl->panel_data.panel_info.cont_splash_enabled)
return 0;
- rc = clk_set_rate(l_clks->clks.esc_clk, l_clks->esc_clk_rate);
- if (rc) {
- pr_err("clk_set_rate failed for esc_clk rc = %d\n", rc);
- goto error;
- }
-
- rc = clk_set_rate(l_clks->clks.byte_clk, l_clks->byte_clk_rate);
+ rc = clk_set_rate(link_hs_clks->byte_clk, link_hs_clks->byte_clk_rate);
if (rc) {
pr_err("clk_set_rate failed for byte_clk rc = %d\n", rc);
goto error;
}
- rc = clk_set_rate(l_clks->clks.pixel_clk, l_clks->pix_clk_rate);
+ rc = clk_set_rate(link_hs_clks->pixel_clk, link_hs_clks->pix_clk_rate);
if (rc) {
pr_err("clk_set_rate failed for pixel_clk rc = %d\n", rc);
goto error;
@@ -182,141 +176,203 @@
return rc;
}
-static int dsi_link_clk_prepare(struct dsi_link_clks *l_clks)
+static int dsi_link_hs_clk_prepare(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks)
{
int rc = 0;
- rc = clk_prepare(l_clks->clks.esc_clk);
+ rc = clk_prepare(link_hs_clks->byte_clk);
if (rc) {
- pr_err("%s: Failed to prepare dsi esc clk\n", __func__);
- goto esc_clk_err;
- }
-
- rc = clk_prepare(l_clks->clks.byte_clk);
- if (rc) {
- pr_err("%s: Failed to prepare dsi byte clk\n", __func__);
+ pr_err("Failed to prepare dsi byte clk\n");
goto byte_clk_err;
}
- rc = clk_prepare(l_clks->clks.pixel_clk);
+ rc = clk_prepare(link_hs_clks->pixel_clk);
if (rc) {
- pr_err("%s: Failed to prepare dsi pixel clk\n", __func__);
+ pr_err("Failed to prepare dsi pixel_clk\n");
goto pixel_clk_err;
}
return rc;
pixel_clk_err:
- clk_unprepare(l_clks->clks.byte_clk);
+ clk_unprepare(link_hs_clks->byte_clk);
byte_clk_err:
- clk_unprepare(l_clks->clks.esc_clk);
-esc_clk_err:
return rc;
}
-static int dsi_link_clk_unprepare(struct dsi_link_clks *l_clks)
+static int dsi_link_hs_clk_unprepare(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks)
{
int rc = 0;
- clk_unprepare(l_clks->clks.pixel_clk);
- clk_unprepare(l_clks->clks.byte_clk);
- clk_unprepare(l_clks->clks.esc_clk);
+ clk_unprepare(link_hs_clks->pixel_clk);
+ clk_unprepare(link_hs_clks->byte_clk);
return rc;
}
-static int dsi_link_clk_enable(struct dsi_link_clks *l_clks)
+static int dsi_link_hs_clk_enable(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks)
{
int rc = 0;
- rc = clk_enable(l_clks->clks.esc_clk);
+ rc = clk_enable(link_hs_clks->byte_clk);
if (rc) {
- pr_err("%s: Failed to enable dsi esc clk\n", __func__);
- goto esc_clk_err;
- }
-
- rc = clk_enable(l_clks->clks.byte_clk);
- if (rc) {
- pr_err("%s: Failed to enable dsi byte clk\n", __func__);
+ pr_err("Failed to enable dsi byte clk\n");
goto byte_clk_err;
}
- rc = clk_enable(l_clks->clks.pixel_clk);
+ rc = clk_enable(link_hs_clks->pixel_clk);
if (rc) {
- pr_err("%s: Failed to enable dsi pixel clk\n", __func__);
+ pr_err("Failed to enable dsi pixel_clk\n");
goto pixel_clk_err;
}
return rc;
pixel_clk_err:
- clk_disable(l_clks->clks.byte_clk);
+ clk_disable(link_hs_clks->byte_clk);
byte_clk_err:
- clk_disable(l_clks->clks.esc_clk);
-esc_clk_err:
return rc;
}
-static int dsi_link_clk_disable(struct dsi_link_clks *l_clks)
+static int dsi_link_hs_clk_disable(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks)
{
int rc = 0;
- clk_disable(l_clks->clks.esc_clk);
- clk_disable(l_clks->clks.pixel_clk);
- clk_disable(l_clks->clks.byte_clk);
+ clk_disable(link_hs_clks->pixel_clk);
+ clk_disable(link_hs_clks->byte_clk);
return rc;
}
-static int dsi_link_clk_start(struct dsi_link_clks *l_clks)
+static int dsi_link_hs_clk_start(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks,
+ enum mdss_dsi_link_clk_op_type op_type)
{
int rc = 0;
+ struct dsi_link_clks *l_clks;
struct mdss_dsi_clk_mngr *mngr;
+ l_clks = container_of(link_hs_clks, struct dsi_link_clks, hs_clks);
mngr = container_of(l_clks, struct mdss_dsi_clk_mngr, link_clks);
- rc = dsi_link_clk_set_rate(l_clks);
- if (rc) {
- pr_err("failed to set clk rates, rc = %d\n", rc);
- goto error;
+ if (op_type & MDSS_DSI_LINK_CLK_SET_RATE) {
+ rc = dsi_link_hs_clk_set_rate(link_hs_clks);
+ if (rc) {
+ pr_err("failed to set HS clk rates, rc = %d\n", rc);
+ goto error;
+ }
}
- rc = dsi_link_clk_prepare(l_clks);
- if (rc) {
- pr_err("failed to prepare link clks, rc = %d\n", rc);
- goto error;
+ if (op_type & MDSS_DSI_LINK_CLK_PREPARE) {
+ rc = dsi_link_hs_clk_prepare(link_hs_clks);
+ if (rc) {
+ pr_err("failed to prepare link HS clks, rc = %d\n", rc);
+ goto error;
+ }
}
- rc = dsi_link_clk_enable(l_clks);
- if (rc) {
- pr_err("failed to enable link clks, rc = %d\n", rc);
- goto error_unprepare;
+ if (op_type & MDSS_DSI_LINK_CLK_ENABLE) {
+ rc = dsi_link_hs_clk_enable(link_hs_clks);
+ if (rc) {
+ pr_err("failed to enable link HS clks, rc = %d\n", rc);
+ goto error_unprepare;
+ }
}
- pr_debug("%s: LINK CLOCK IS ON\n", mngr->name);
+ pr_debug("%s: LINK HS CLOCK IS ON\n", mngr->name);
return rc;
error_unprepare:
- dsi_link_clk_unprepare(l_clks);
+ dsi_link_hs_clk_unprepare(link_hs_clks);
error:
return rc;
}
-static int dsi_link_clk_stop(struct dsi_link_clks *l_clks)
+static int dsi_link_lp_clk_start(
+ struct mdss_dsi_link_lp_clk_info *link_lp_clks)
{
int rc = 0;
struct mdss_dsi_clk_mngr *mngr;
+ struct dsi_link_clks *l_clks;
+ struct mdss_dsi_ctrl_pdata *ctrl;
+ l_clks = container_of(link_lp_clks, struct dsi_link_clks, lp_clks);
+ mngr = container_of(l_clks, struct mdss_dsi_clk_mngr, link_clks);
+ /*
+ * In an ideal world, cont_splash_enabled should not be required inside
+ * the clock manager. But, in the current driver cont_splash_enabled
+ * flag is set inside mdp driver and there is no interface event
+ * associated with this flag setting. Also, set rate for clock need not
+ * be called for every enable call. It should be done only once when
+ * coming out of suspend.
+ */
+ ctrl = mngr->priv_data;
+ if (ctrl->panel_data.panel_info.cont_splash_enabled)
+ goto prepare;
+
+ rc = clk_set_rate(link_lp_clks->esc_clk, link_lp_clks->esc_clk_rate);
+ if (rc) {
+ pr_err("clk_set_rate failed for esc_clk rc = %d\n", rc);
+ goto error;
+ }
+
+prepare:
+ rc = clk_prepare(link_lp_clks->esc_clk);
+ if (rc) {
+ pr_err("Failed to prepare dsi esc clk\n");
+ goto error;
+ }
+
+ rc = clk_enable(link_lp_clks->esc_clk);
+ if (rc) {
+ pr_err("Failed to enable dsi esc clk\n");
+ clk_unprepare(l_clks->lp_clks.esc_clk);
+ goto error;
+ }
+error:
+ pr_debug("%s: LINK LP CLOCK IS ON\n", mngr->name);
+ return rc;
+}
+
+static int dsi_link_hs_clk_stop(
+ struct mdss_dsi_link_hs_clk_info *link_hs_clks)
+{
+ int rc = 0;
+ struct dsi_link_clks *l_clks;
+ struct mdss_dsi_clk_mngr *mngr;
+
+ l_clks = container_of(link_hs_clks, struct dsi_link_clks, hs_clks);
mngr = container_of(l_clks, struct mdss_dsi_clk_mngr, link_clks);
- (void)dsi_link_clk_disable(l_clks);
+ (void)dsi_link_hs_clk_disable(link_hs_clks);
- (void)dsi_link_clk_unprepare(l_clks);
- pr_debug("%s: LINK CLOCK IS OFF\n", mngr->name);
+ (void)dsi_link_hs_clk_unprepare(link_hs_clks);
+ pr_debug("%s: LINK HS CLOCK IS OFF\n", mngr->name);
return rc;
}
+static int dsi_link_lp_clk_stop(
+ struct mdss_dsi_link_lp_clk_info *link_lp_clks)
+{
+ struct dsi_link_clks *l_clks;
+ struct mdss_dsi_clk_mngr *mngr;
+
+ l_clks = container_of(link_lp_clks, struct dsi_link_clks, lp_clks);
+ mngr = container_of(l_clks, struct mdss_dsi_clk_mngr, link_clks);
+
+ clk_disable(l_clks->lp_clks.esc_clk);
+ clk_unprepare(l_clks->lp_clks.esc_clk);
+
+ pr_debug("%s: LINK LP CLOCK IS OFF\n", mngr->name);
+ return 0;
+}
+
+
static int dsi_update_clk_state(struct dsi_core_clks *c_clks, u32 c_state,
struct dsi_link_clks *l_clks, u32 l_state)
{
@@ -347,8 +403,8 @@
if (c_clks && (c_state == MDSS_DSI_CLK_ON)) {
if (c_clks->current_clk_state == MDSS_DSI_CLK_OFF) {
rc = mngr->pre_clkon_cb(mngr->priv_data,
- MDSS_DSI_CORE_CLK,
- MDSS_DSI_CLK_ON);
+ MDSS_DSI_CORE_CLK, MDSS_DSI_LINK_NONE,
+ MDSS_DSI_CLK_ON);
if (rc) {
pr_err("failed to turn on MDP FS rc= %d\n", rc);
goto error;
@@ -362,8 +418,8 @@
if (mngr->post_clkon_cb) {
rc = mngr->post_clkon_cb(mngr->priv_data,
- MDSS_DSI_CORE_CLK,
- MDSS_DSI_CLK_ON);
+ MDSS_DSI_CORE_CLK, MDSS_DSI_LINK_NONE,
+ MDSS_DSI_CLK_ON);
if (rc)
pr_err("post clk on cb failed, rc = %d\n", rc);
}
@@ -375,21 +431,50 @@
if (l_state == MDSS_DSI_CLK_ON) {
if (mngr->pre_clkon_cb) {
rc = mngr->pre_clkon_cb(mngr->priv_data,
- MDSS_DSI_LINK_CLK, l_state);
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_LP_CLK,
+ l_state);
if (rc)
- pr_err("pre link clk on cb failed\n");
+ pr_err("pre link LP clk on cb failed\n");
}
- rc = dsi_link_clk_start(l_clks);
+ rc = dsi_link_lp_clk_start(&l_clks->lp_clks);
if (rc) {
- pr_err("failed to start link clk rc= %d\n", rc);
+ pr_err("failed to start LP link clk clk\n");
goto error;
}
if (mngr->post_clkon_cb) {
rc = mngr->post_clkon_cb(mngr->priv_data,
- MDSS_DSI_LINK_CLK,
- l_state);
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_LP_CLK,
+ l_state);
if (rc)
- pr_err("post link clk on cb failed\n");
+ pr_err("post LP clk on cb failed\n");
+ }
+
+ if (mngr->pre_clkon_cb) {
+ rc = mngr->pre_clkon_cb(mngr->priv_data,
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_HS_CLK,
+ l_state);
+ if (rc)
+ pr_err("pre HS clk on cb failed\n");
+ }
+ rc = dsi_link_hs_clk_start(&l_clks->hs_clks,
+ (MDSS_DSI_LINK_CLK_SET_RATE |
+ MDSS_DSI_LINK_CLK_PREPARE));
+ if (rc) {
+ pr_err("failed to prepare HS clk rc= %d\n", rc);
+ goto error;
+ }
+ if (mngr->post_clkon_cb) {
+ rc = mngr->post_clkon_cb(mngr->priv_data,
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_HS_CLK,
+ l_state);
+ if (rc)
+ pr_err("post HS clk on cb failed\n");
+ }
+ rc = dsi_link_hs_clk_start(&l_clks->hs_clks,
+ MDSS_DSI_LINK_CLK_ENABLE);
+ if (rc) {
+ pr_err("failed to enable HS clk rc= %d\n", rc);
+ goto error;
}
} else {
/*
@@ -418,9 +503,16 @@
goto error;
}
- rc = dsi_link_clk_start(l_clks);
+ rc = dsi_link_lp_clk_start(&l_clks->lp_clks);
if (rc) {
- pr_err("Link clks did not start\n");
+ pr_err("LP Link clks did not start\n");
+ goto error;
+ }
+
+ rc = dsi_link_hs_clk_start(&l_clks->hs_clks,
+ MDSS_DSI_LINK_CLK_START);
+ if (rc) {
+ pr_err("HS Link clks did not start\n");
goto error;
}
l_c_on = true;
@@ -429,24 +521,50 @@
if (mngr->pre_clkoff_cb) {
rc = mngr->pre_clkoff_cb(mngr->priv_data,
- MDSS_DSI_LINK_CLK, l_state);
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_HS_CLK,
+ l_state);
if (rc)
- pr_err("pre link clk off cb failed\n");
+ pr_err("pre HS clk off cb failed\n");
}
- rc = dsi_link_clk_stop(l_clks);
+ rc = dsi_link_hs_clk_stop(&l_clks->hs_clks);
if (rc) {
- pr_err("failed to stop link clk, rc = %d\n",
+ pr_err("failed to stop HS clk, rc = %d\n",
rc);
goto error;
}
if (mngr->post_clkoff_cb) {
rc = mngr->post_clkoff_cb(mngr->priv_data,
- MDSS_DSI_LINK_CLK, l_state);
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_HS_CLK,
+ l_state);
if (rc)
- pr_err("post link clk off cb failed\n");
+ pr_err("post HS clk off cb failed\n");
}
+
+ if (mngr->pre_clkoff_cb) {
+ rc = mngr->pre_clkoff_cb(mngr->priv_data,
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_LP_CLK,
+ l_state);
+ if (rc)
+ pr_err("pre LP clk off cb failed\n");
+ }
+
+ rc = dsi_link_lp_clk_stop(&l_clks->lp_clks);
+ if (rc) {
+ pr_err("failed to stop LP link clk, rc = %d\n",
+ rc);
+ goto error;
+ }
+
+ if (mngr->post_clkoff_cb) {
+ rc = mngr->post_clkoff_cb(mngr->priv_data,
+ MDSS_DSI_LINK_CLK, MDSS_DSI_LINK_LP_CLK,
+ l_state);
+ if (rc)
+ pr_err("post LP clk off cb failed\n");
+ }
+
/*
* This check is to save unnecessary clock state
* change when going from EARLY_GATE to OFF. In the
@@ -502,8 +620,8 @@
if (mngr->pre_clkoff_cb) {
rc = mngr->pre_clkoff_cb(mngr->priv_data,
- MDSS_DSI_CORE_CLK,
- c_state);
+ MDSS_DSI_CORE_CLK, MDSS_DSI_LINK_NONE,
+ c_state);
if (rc)
pr_err("pre core clk off cb failed\n");
}
@@ -517,7 +635,7 @@
if (c_state == MDSS_DSI_CLK_OFF) {
if (mngr->post_clkoff_cb) {
rc = mngr->post_clkoff_cb(mngr->priv_data,
- MDSS_DSI_CORE_CLK,
+ MDSS_DSI_CORE_CLK, MDSS_DSI_LINK_NONE,
MDSS_DSI_CLK_OFF);
if (rc)
pr_err("post clkoff cb fail, rc = %d\n",
@@ -610,27 +728,30 @@
MDSS_XLOG(clk, rate, flags);
switch (clk) {
case MDSS_DSI_LINK_ESC_CLK:
- mngr->link_clks.esc_clk_rate = rate;
+ mngr->link_clks.lp_clks.esc_clk_rate = rate;
if (!flags) {
- rc = clk_set_rate(mngr->link_clks.clks.esc_clk, rate);
+ rc = clk_set_rate(mngr->link_clks.lp_clks.esc_clk,
+ rate);
if (rc)
pr_err("set rate failed for esc clk rc=%d\n",
rc);
}
break;
case MDSS_DSI_LINK_BYTE_CLK:
- mngr->link_clks.byte_clk_rate = rate;
+ mngr->link_clks.hs_clks.byte_clk_rate = rate;
if (!flags) {
- rc = clk_set_rate(mngr->link_clks.clks.byte_clk, rate);
+ rc = clk_set_rate(mngr->link_clks.hs_clks.byte_clk,
+ rate);
if (rc)
pr_err("set rate failed for byte clk rc=%d\n",
rc);
}
break;
case MDSS_DSI_LINK_PIX_CLK:
- mngr->link_clks.pix_clk_rate = rate;
+ mngr->link_clks.hs_clks.pix_clk_rate = rate;
if (!flags) {
- rc = clk_set_rate(mngr->link_clks.clks.pixel_clk, rate);
+ rc = clk_set_rate(mngr->link_clks.hs_clks.pixel_clk,
+ rate);
if (rc)
pr_err("failed to set rate for pix clk rc=%d\n",
rc);
@@ -888,8 +1009,10 @@
mutex_init(&mngr->clk_mutex);
memcpy(&mngr->core_clks.clks, &info->core_clks, sizeof(struct
mdss_dsi_core_clk_info));
- memcpy(&mngr->link_clks.clks, &info->link_clks, sizeof(struct
- mdss_dsi_link_clk_info));
+ memcpy(&mngr->link_clks.hs_clks, &info->link_hs_clks, sizeof(struct
+ mdss_dsi_link_hs_clk_info));
+ memcpy(&mngr->link_clks.lp_clks, &info->link_lp_clks, sizeof(struct
+ mdss_dsi_link_lp_clk_info));
INIT_LIST_HEAD(&mngr->client_list);
mngr->pre_clkon_cb = info->pre_clkon_cb;
@@ -981,15 +1104,26 @@
if ((clk & MDSS_DSI_LINK_CLK) &&
(mngr->link_clks.current_clk_state == MDSS_DSI_CLK_ON)) {
- rc = dsi_link_clk_stop(&mngr->link_clks);
+ rc = dsi_link_hs_clk_stop(&mngr->link_clks.hs_clks);
if (rc) {
- pr_err("failed to stop link clks\n");
+ pr_err("failed to stop HS link clks\n");
goto error;
}
- rc = dsi_link_clk_start(&mngr->link_clks);
+ rc = dsi_link_lp_clk_stop(&mngr->link_clks.lp_clks);
+ if (rc) {
+ pr_err("failed to stop LP link clks\n");
+ goto error;
+ }
+
+ rc = dsi_link_lp_clk_start(&mngr->link_clks.lp_clks);
if (rc)
- pr_err("failed to start link clks\n");
+ pr_err("failed to start LP link clks\n");
+
+ rc = dsi_link_hs_clk_start(&mngr->link_clks.hs_clks,
+ MDSS_DSI_LINK_CLK_START);
+ if (rc)
+ pr_err("failed to start HS link clks\n");
} else if (clk & MDSS_DSI_LINK_CLK) {
pr_err("cannot reset, link clock is off\n");
diff --git a/drivers/video/fbdev/msm/mdss_dsi_clk.h b/drivers/video/fbdev/msm/mdss_dsi_clk.h
index 837f2f6..5f000f9 100644
--- a/drivers/video/fbdev/msm/mdss_dsi_clk.h
+++ b/drivers/video/fbdev/msm/mdss_dsi_clk.h
@@ -39,6 +39,13 @@
MDSS_DSI_LINK_CLK_MAX,
};
+enum mdss_dsi_link_clk_op_type {
+ MDSS_DSI_LINK_CLK_SET_RATE = BIT(0),
+ MDSS_DSI_LINK_CLK_PREPARE = BIT(1),
+ MDSS_DSI_LINK_CLK_ENABLE = BIT(2),
+ MDSS_DSI_LINK_CLK_START = BIT(0) | BIT(1) | BIT(2),
+};
+
enum mdss_dsi_clk_type {
MDSS_DSI_CORE_CLK = BIT(0),
MDSS_DSI_LINK_CLK = BIT(1),
@@ -46,53 +53,67 @@
MDSS_DSI_CLKS_MAX = BIT(2),
};
+enum mdss_dsi_lclk_type {
+ MDSS_DSI_LINK_NONE = 0,
+ MDSS_DSI_LINK_LP_CLK = BIT(0),
+ MDSS_DSI_LINK_HS_CLK = BIT(1),
+};
+
/**
* typedef *pre_clockoff_cb() - Callback before clock is turned off
* @priv: private data pointer.
* @clk_type: clock which is being turned off.
+ * @l_type: specifies if the clock is HS or LP type. Valid only for link clocks.
* @new_state: next state for the clock.
*
* @return: error code.
*/
typedef int (*pre_clockoff_cb)(void *priv,
- enum mdss_dsi_clk_type clk_type,
- enum mdss_dsi_clk_state new_state);
+ enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
+ enum mdss_dsi_clk_state new_state);
/**
* typedef *post_clockoff_cb() - Callback after clock is turned off
* @priv: private data pointer.
* @clk_type: clock which was turned off.
+ * @l_type: specifies if the clock is HS or LP type. Valid only for link clocks.
* @curr_state: current state for the clock.
*
* @return: error code.
*/
typedef int (*post_clockoff_cb)(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state curr_state);
/**
* typedef *post_clockon_cb() - Callback after clock is turned on
* @priv: private data pointer.
* @clk_type: clock which was turned on.
+ * @l_type: specifies if the clock is HS or LP type. Valid only for link clocks.
* @curr_state: current state for the clock.
*
* @return: error code.
*/
typedef int (*post_clockon_cb)(void *priv,
- enum mdss_dsi_clk_type clk_type,
- enum mdss_dsi_clk_state curr_state);
+ enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
+ enum mdss_dsi_clk_state curr_state);
/**
* typedef *pre_clockon_cb() - Callback before clock is turned on
* @priv: private data pointer.
* @clk_type: clock which is being turned on.
+ * @l_type: specifies if the clock is HS or LP type. Valid only for link clocks.
* @new_state: next state for the clock.
*
* @return: error code.
*/
typedef int (*pre_clockon_cb)(void *priv,
- enum mdss_dsi_clk_type clk_type,
- enum mdss_dsi_clk_state new_state);
+ enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
+ enum mdss_dsi_clk_state new_state);
struct mdss_dsi_core_clk_info {
struct clk *mdp_core_clk;
@@ -101,10 +122,16 @@
struct clk *mmss_misc_ahb_clk;
};
-struct mdss_dsi_link_clk_info {
- struct clk *esc_clk;
+struct mdss_dsi_link_hs_clk_info {
struct clk *byte_clk;
struct clk *pixel_clk;
+ u32 byte_clk_rate;
+ u32 pix_clk_rate;
+};
+
+struct mdss_dsi_link_lp_clk_info {
+ struct clk *esc_clk;
+ u32 esc_clk_rate;
};
struct dsi_panel_clk_ctrl {
@@ -126,7 +153,8 @@
struct mdss_dsi_clk_info {
char name[DSI_CLK_NAME_LEN];
struct mdss_dsi_core_clk_info core_clks;
- struct mdss_dsi_link_clk_info link_clks;
+ struct mdss_dsi_link_hs_clk_info link_hs_clks;
+ struct mdss_dsi_link_lp_clk_info link_lp_clks;
pre_clockoff_cb pre_clkoff_cb;
post_clockoff_cb post_clkoff_cb;
post_clockon_cb post_clkon_cb;
diff --git a/drivers/video/fbdev/msm/mdss_dsi_host.c b/drivers/video/fbdev/msm/mdss_dsi_host.c
index 988c7a9..d76be70 100644
--- a/drivers/video/fbdev/msm/mdss_dsi_host.c
+++ b/drivers/video/fbdev/msm/mdss_dsi_host.c
@@ -303,6 +303,20 @@
*/
reg_val = MIPI_INP(ctrl->phy_io.base + 0x20c);
reg_val = reg_val >> 4;
+ if (!reg_val) {
+ /*
+ * DSI_0_PHY_DSIPHY_REVISION_ID3 for 12nm PHY
+ * reset value = 0x20
+ * 7:4 Major
+ * 3:0 Minor
+ */
+ reg_val = MIPI_INP(ctrl->phy_io.base + 0x3dc);
+ reg_val = reg_val >> 4;
+ if (reg_val == 0x2) {
+ ctrl->shared_data->phy_rev = DSI_PHY_REV_12NM;
+ return;
+ }
+ }
}
if (reg_val == DSI_PHY_REV_20)
@@ -413,6 +427,9 @@
/* DSI_LAN_SWAP_CTRL */
MIPI_OUTP((ctrl_pdata->ctrl_base) + 0x00b0, ctrl_pdata->dlane_swap);
+ if (ctrl_pdata->shared_data->phy_rev == DSI_PHY_REV_12NM)
+ goto next;
+
/* clock out ctrl */
data = pinfo->t_clk_post & 0x3f; /* 6 bits */
data <<= 8;
@@ -420,6 +437,7 @@
/* DSI_CLKOUT_TIMING_CTRL */
MIPI_OUTP((ctrl_pdata->ctrl_base) + 0xc4, data);
+next:
data = 0;
if (pinfo->rx_eot_ignore)
data |= BIT(4);
diff --git a/drivers/video/fbdev/msm/mdss_dsi_panel.c b/drivers/video/fbdev/msm/mdss_dsi_panel.c
index 1cbaa44..2ef1695 100644
--- a/drivers/video/fbdev/msm/mdss_dsi_panel.c
+++ b/drivers/video/fbdev/msm/mdss_dsi_panel.c
@@ -2309,6 +2309,9 @@
for (i = 0; i < ARRAY_SIZE(pt->phy_timing_8996); i++)
pinfo->mipi.dsi_phy_db.timing_8996[i] = pt->phy_timing_8996[i];
+ for (i = 0; i < ARRAY_SIZE(pt->phy_timing_12nm); i++)
+ pinfo->mipi.dsi_phy_db.timing_12nm[i] = pt->phy_timing_12nm[i];
+
ctrl->on_cmds = pt->on_cmds;
ctrl->post_panel_on_cmds = pt->post_panel_on_cmds;
@@ -2421,6 +2424,18 @@
pt->phy_timing_8996[i] = data[i];
phy_timings_present = true;
}
+
+ data = of_get_property(np,
+ "qcom,mdss-dsi-panel-timings-phy-12nm", &len);
+ if ((!data) || (len != 8)) {
+ pr_debug("%s:%d, Unable to read 12nm Phy lane timing settings",
+ __func__, __LINE__);
+ } else {
+ for (i = 0; i < len; i++)
+ pt->phy_timing_12nm[i] = data[i];
+ phy_timings_present = true;
+ }
+
if (!phy_timings_present) {
pr_err("%s: phy timing settings not present\n", __func__);
return -EINVAL;
diff --git a/drivers/video/fbdev/msm/mdss_dsi_phy.h b/drivers/video/fbdev/msm/mdss_dsi_phy.h
index aea42e8..108e26e 100644
--- a/drivers/video/fbdev/msm/mdss_dsi_phy.h
+++ b/drivers/video/fbdev/msm/mdss_dsi_phy.h
@@ -16,11 +16,13 @@
#include <linux/types.h>
#include "mdss_panel.h"
+#include "mdss_dsi.h"
enum phy_rev {
DSI_PHY_REV_UNKNOWN = 0x00,
DSI_PHY_REV_10 = 0x01, /* REV 1.0 - 20nm, 28nm */
DSI_PHY_REV_20 = 0x02, /* REV 2.0 - 14nm */
+ DSI_PHY_REV_12NM = 0x03, /* 12nm PHY */
DSI_PHY_REV_MAX,
};
@@ -36,4 +38,53 @@
int mdss_dsi_phy_calc_timing_param(struct mdss_panel_info *pinfo, u32 phy_rev,
u32 frate_hz);
+/*
+ * mdss_dsi_12nm_phy_regulator_enable() - enable lane reg for DSI 12nm PHY
+ *
+ * @ctrl: pointer to DSI controller structure
+ */
+int mdss_dsi_12nm_phy_regulator_enable(struct mdss_dsi_ctrl_pdata *ctrl);
+
+/*
+ * mdss_dsi_12nm_phy_regulator_disable() - disable lane reg for DSI 12nm PHY
+ *
+ * @ctrl: pointer to DSI controller structure
+ */
+int mdss_dsi_12nm_phy_regulator_disable(struct mdss_dsi_ctrl_pdata *ctrl);
+
+/*
+ * mdss_dsi_12nm_phy_config() - initialization sequence for DSI 12nm PHY
+ *
+ * @ctrl: pointer to DSI controller structure
+ *
+ * This function performs a sequence of register writes to initialize DSI
+ * 12nm phy. This function assumes that the DSI bus clocks are turned on.
+ * This function should only be called prior to enabling the DSI link clocks.
+ */
+int mdss_dsi_12nm_phy_config(struct mdss_dsi_ctrl_pdata *ctrl);
+
+/*
+ * mdss_dsi_12nm_phy_shutdown() - shutdown sequence for DSI 12nm PHY
+ *
+ * @ctrl: pointer to DSI controller structure
+ *
+ * Perform a sequence of register writes to completely shut down DSI 12nm PHY.
+ * This function assumes that the DSI bus clocks are turned on.
+ */
+int mdss_dsi_12nm_phy_shutdown(struct mdss_dsi_ctrl_pdata *ctrl);
+
+/*
+ * mdss_dsi_12nm_phy_hstx_drv_ctrl() - enable/disable HSTX drivers
+ *
+ * @ctrl: pointer to DSI controller structure
+ * @enable: boolean to specify enable/disable the HSTX drivers
+ *
+ * Perform a sequence of register writes to enable/disable HSTX drivers.
+ * This function assumes that the DSI bus clocks are turned on.
+ */
+
+void mdss_dsi_12nm_phy_hstx_drv_ctrl(
+ struct mdss_dsi_ctrl_pdata *ctrl, bool enable);
+
+
#endif /* MDSS_DSI_PHY_H */
diff --git a/drivers/video/fbdev/msm/mdss_dsi_phy_12nm.c b/drivers/video/fbdev/msm/mdss_dsi_phy_12nm.c
new file mode 100644
index 0000000..7b9a536
--- /dev/null
+++ b/drivers/video/fbdev/msm/mdss_dsi_phy_12nm.c
@@ -0,0 +1,124 @@
+/* Copyright (c) 2018, 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 <linux/iopoll.h>
+#include "mdss_dsi_phy.h"
+
+#define T_TA_GO_TIM_COUNT 0x014
+#define T_TA_SURE_TIM_COUNT 0x018
+#define HSTX_DRIV_INDATA_CTRL_CLKLANE 0x0c0
+#define HSTX_DATAREV_CTRL_CLKLANE 0x0d4
+#define HSTX_DRIV_INDATA_CTRL_LANE0 0x100
+#define HSTX_READY_DLY_DATA_REV_CTRL_LANE0 0x114
+#define HSTX_DRIV_INDATA_CTRL_LANE1 0x140
+#define HSTX_READY_DLY_DATA_REV_CTRL_LANE1 0x154
+#define HSTX_CLKLANE_REQSTATE_TIM_CTRL 0x180
+#define HSTX_CLKLANE_HS0STATE_TIM_CTRL 0x188
+#define HSTX_CLKLANE_TRALSTATE_TIM_CTRL 0x18c
+#define HSTX_CLKLANE_CLKPOSTSTATE_TIM_CTRL 0x194
+#define HSTX_DATALANE_REQSTATE_TIM_CTRL 0x1c0
+#define HSTX_DATALANE_HS0STATE_TIM_CTRL 0x1c8
+#define HSTX_DATALANE_TRAILSTATE_TIM_CTRL 0x1cc
+#define HSTX_DATALANE_EXITSTATE_TIM_CTRL 0x1d0
+#define HSTX_DRIV_INDATA_CTRL_LANE2 0x200
+#define HSTX_READY_DLY_DATA_REV_CTRL_LANE2 0x214
+#define HSTX_READY_DLY_DATA_REV_CTRL_LANE3 0x254
+#define HSTX_DRIV_INDATA_CTRL_LANE3 0x240
+#define CTRL0 0x3e8
+#define SYS_CTRL 0x3f0
+#define REQ_DLY 0x3fc
+
+#define DSI_PHY_W32(b, off, val) MIPI_OUTP((b) + (off), (val))
+#define DSI_PHY_R32(b, off) MIPI_INP((b) + (off))
+
+int mdss_dsi_12nm_phy_regulator_enable(struct mdss_dsi_ctrl_pdata *ctrl)
+{
+ /* Nothing to be done for 12nm PHY */
+ return 0;
+}
+
+int mdss_dsi_12nm_phy_regulator_disable(struct mdss_dsi_ctrl_pdata *ctrl)
+{
+ /* Nothing to be done for 12nm PHY */
+ return 0;
+}
+
+int mdss_dsi_12nm_phy_config(struct mdss_dsi_ctrl_pdata *ctrl)
+{
+ struct mdss_dsi_phy_ctrl *pd =
+ &(((ctrl->panel_data).panel_info.mipi).dsi_phy_db);
+
+ /* CTRL0: CFG_CLK_EN */
+ DSI_PHY_W32(ctrl->phy_io.base, CTRL0, BIT(0));
+
+ /* DSI PHY clock lane timings */
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_CLKLANE_HS0STATE_TIM_CTRL,
+ (pd->timing_12nm[0] | BIT(7)));
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_CLKLANE_TRALSTATE_TIM_CTRL,
+ (pd->timing_12nm[1] | BIT(6)));
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_CLKLANE_CLKPOSTSTATE_TIM_CTRL,
+ (pd->timing_12nm[2] | BIT(6)));
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_CLKLANE_REQSTATE_TIM_CTRL,
+ pd->timing_12nm[3]);
+
+ /* DSI PHY data lane timings */
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DATALANE_HS0STATE_TIM_CTRL,
+ (pd->timing_12nm[4] | BIT(7)));
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DATALANE_TRAILSTATE_TIM_CTRL,
+ (pd->timing_12nm[5] | BIT(6)));
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DATALANE_REQSTATE_TIM_CTRL,
+ pd->timing_12nm[6]);
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DATALANE_EXITSTATE_TIM_CTRL,
+ (pd->timing_12nm[7] | BIT(6) | BIT(7)));
+
+ DSI_PHY_W32(ctrl->phy_io.base, T_TA_GO_TIM_COUNT, 0x03);
+ DSI_PHY_W32(ctrl->phy_io.base, T_TA_SURE_TIM_COUNT, 0x01);
+ DSI_PHY_W32(ctrl->phy_io.base, REQ_DLY, 0x85);
+
+ /* DSI lane control registers */
+ DSI_PHY_W32(ctrl->phy_io.base,
+ HSTX_READY_DLY_DATA_REV_CTRL_LANE0, 0x00);
+ DSI_PHY_W32(ctrl->phy_io.base,
+ HSTX_READY_DLY_DATA_REV_CTRL_LANE1, 0x00);
+ DSI_PHY_W32(ctrl->phy_io.base,
+ HSTX_READY_DLY_DATA_REV_CTRL_LANE2, 0x00);
+ DSI_PHY_W32(ctrl->phy_io.base,
+ HSTX_READY_DLY_DATA_REV_CTRL_LANE3, 0x00);
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DATAREV_CTRL_CLKLANE, 0x00);
+ wmb(); /* make sure DSI PHY registers are programmed */
+
+ return 0;
+}
+
+int mdss_dsi_12nm_phy_shutdown(struct mdss_dsi_ctrl_pdata *ctrl)
+{
+ DSI_PHY_W32(ctrl->phy_io.base, SYS_CTRL, BIT(0) | BIT(3));
+ wmb(); /* make sure DSI PHY is disabled */
+ return 0;
+}
+
+void mdss_dsi_12nm_phy_hstx_drv_ctrl(
+ struct mdss_dsi_ctrl_pdata *ctrl, bool enable)
+{
+ u32 data = 0;
+
+ if (enable)
+ data = BIT(2) | BIT(3);
+
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DRIV_INDATA_CTRL_CLKLANE, data);
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DRIV_INDATA_CTRL_LANE0, data);
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DRIV_INDATA_CTRL_LANE1, data);
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DRIV_INDATA_CTRL_LANE2, data);
+ DSI_PHY_W32(ctrl->phy_io.base, HSTX_DRIV_INDATA_CTRL_LANE3, data);
+ wmb(); /* make sure DSI PHY registers are programmed */
+}
diff --git a/drivers/video/fbdev/msm/mdss_mdp.c b/drivers/video/fbdev/msm/mdss_mdp.c
index 13a4bb6..d07650b 100644
--- a/drivers/video/fbdev/msm/mdss_mdp.c
+++ b/drivers/video/fbdev/msm/mdss_mdp.c
@@ -2098,10 +2098,9 @@
devm_kzalloc(&mdata->pdev->dev, sizeof(u32) *
mdata->scaler_off->ndest_scalers,
GFP_KERNEL);
- if (!mdata->scaler_off->dest_scaler_off) {
- kfree(mdata->scaler_off->dest_scaler_off);
+ if (!mdata->scaler_off->dest_scaler_off)
return -ENOMEM;
- }
+
ret = mdss_mdp_parse_dt_handler(mdata->pdev,
"qcom,mdss-dest-scaler-off",
mdata->scaler_off->dest_scaler_off,
@@ -2112,10 +2111,9 @@
devm_kzalloc(&mdata->pdev->dev, sizeof(u32) *
mdata->scaler_off->ndest_scalers,
GFP_KERNEL);
- if (!mdata->scaler_off->dest_scaler_lut_off) {
- kfree(mdata->scaler_off->dest_scaler_lut_off);
+ if (!mdata->scaler_off->dest_scaler_lut_off)
return -ENOMEM;
- }
+
ret = mdss_mdp_parse_dt_handler(mdata->pdev,
"qcom,mdss-dest-scalers-lut-off",
mdata->scaler_off->dest_scaler_lut_off,
diff --git a/drivers/video/fbdev/msm/mdss_panel.h b/drivers/video/fbdev/msm/mdss_panel.h
index 53db752..a3f9349 100644
--- a/drivers/video/fbdev/msm/mdss_panel.h
+++ b/drivers/video/fbdev/msm/mdss_panel.h
@@ -308,6 +308,7 @@
bool reg_ldo_mode;
char timing_8996[40];/* 8996, 8 * 5 */
+ char timing_12nm[14]; /* 12nm PHY */
char regulator_len;
char strength_len;
char lanecfg_len;
diff --git a/drivers/video/fbdev/msm/msm_mdss_io_8974.c b/drivers/video/fbdev/msm/msm_mdss_io_8974.c
index ec1ee60..f0e46f7 100644
--- a/drivers/video/fbdev/msm/msm_mdss_io_8974.c
+++ b/drivers/video/fbdev/msm/msm_mdss_io_8974.c
@@ -519,7 +519,8 @@
* is only done from the clock master. This will ensure that the PLL is
* off when PHY reset is called.
*/
- if (mdss_dsi_is_ctrl_clk_slave(ctrl))
+ if (mdss_dsi_is_ctrl_clk_slave(ctrl) ||
+ (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM))
return;
mdss_dsi_phy_sw_reset_sub(ctrl);
@@ -561,6 +562,9 @@
if (ctrl->shared_data->phy_rev == DSI_PHY_REV_20)
return;
+ if (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM)
+ return;
+
MIPI_OUTP(ctrl->phy_regulator_io.base + 0x018, 0x000);
}
@@ -575,6 +579,8 @@
MIPI_OUTP(ctrl->phy_io.base + DSIPHY_PLL_CLKBUFLR_EN, 0);
MIPI_OUTP(ctrl->phy_io.base + DSIPHY_CMN_GLBL_TEST_CTRL, 0);
MIPI_OUTP(ctrl->phy_io.base + DSIPHY_CMN_CTRL_0, 0);
+ } else if (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM) {
+ mdss_dsi_12nm_phy_shutdown(ctrl);
} else {
MIPI_OUTP(ctrl->phy_io.base + MDSS_DSI_DSIPHY_CTRL_0, 0x000);
}
@@ -596,7 +602,8 @@
return;
}
- if (ctrl->shared_data->phy_rev == DSI_PHY_REV_20)
+ if ((ctrl->shared_data->phy_rev == DSI_PHY_REV_20) ||
+ (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM))
return;
pd = &(((ctrl->panel_data).panel_info.mipi).dsi_phy_db);
@@ -1144,6 +1151,8 @@
if (enable) {
if (ctrl->shared_data->phy_rev == DSI_PHY_REV_20) {
mdss_dsi_8996_phy_regulator_enable(ctrl);
+ } else if (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM) {
+ mdss_dsi_12nm_phy_regulator_enable(ctrl);
} else {
switch (ctrl->shared_data->hw_rev) {
case MDSS_DSI_HW_REV_103:
@@ -1194,6 +1203,8 @@
if (ctrl->shared_data->phy_rev == DSI_PHY_REV_20) {
mdss_dsi_8996_phy_config(ctrl);
+ } else if (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM) {
+ mdss_dsi_12nm_phy_config(ctrl);
} else {
switch (ctrl->shared_data->hw_rev) {
case MDSS_DSI_HW_REV_103:
@@ -1269,6 +1280,13 @@
}
}
+static void mdss_dsi_phy_hstx_drv_ctrl(
+ struct mdss_dsi_ctrl_pdata *ctrl, bool enable)
+{
+ if (ctrl->shared_data->phy_rev == DSI_PHY_REV_12NM)
+ mdss_dsi_12nm_phy_hstx_drv_ctrl(ctrl, enable);
+}
+
void mdss_dsi_core_clk_deinit(struct device *dev, struct dsi_shared_data *sdata)
{
if (sdata->mmss_misc_ahb_clk)
@@ -1688,7 +1706,7 @@
}
static bool mdss_dsi_is_ulps_req_valid(struct mdss_dsi_ctrl_pdata *ctrl,
- int enable)
+ int enable, bool reconfig)
{
struct mdss_dsi_ctrl_pdata *octrl = NULL;
struct mdss_panel_data *pdata = &ctrl->panel_data;
@@ -1719,11 +1737,11 @@
* However, this should be allowed in following usecases:
* 1. If ULPS during suspend feature is enabled, where we
* configure the lanes in ULPS after turning off the panel.
- * 2. When coming out of idle PC with clamps enabled, where we
- * transition the controller HW state back to ULPS prior to
+ * 2. When coming out of idle PC with ULPS enabled, where we need to
+ * reconfigure the controller HW state again to ULPS prior to
* disabling ULPS.
*/
- if (enable && !ctrl->mmss_clamp &&
+ if (enable && !reconfig &&
!(ctrl->ctrl_state & CTRL_STATE_PANEL_INIT) &&
!pdata->panel_info.ulps_suspend_enabled) {
pr_debug("%s: panel not yet initialized\n", __func__);
@@ -1752,13 +1770,14 @@
* mdss_dsi_ulps_config() - Program DSI lanes to enter/exit ULPS mode
* @ctrl: pointer to DSI controller structure
* @enable: 1 to enter ULPS, 0 to exit ULPS
+ * @reconfig: boolean to specify if DSI controller is reconfigured to enter ULPS
*
* This function executes the necessary programming sequence to enter/exit
* DSI Ultra-Low Power State (ULPS). This function assumes that the link and
* core clocks are already on.
*/
static int mdss_dsi_ulps_config(struct mdss_dsi_ctrl_pdata *ctrl,
- int enable)
+ int enable, bool reconfig)
{
int ret = 0;
struct mdss_panel_data *pdata = NULL;
@@ -1780,7 +1799,7 @@
pinfo = &pdata->panel_info;
mipi = &pinfo->mipi;
- if (!mdss_dsi_is_ulps_req_valid(ctrl, enable)) {
+ if (!mdss_dsi_is_ulps_req_valid(ctrl, enable, reconfig)) {
pr_debug("%s: skiping ULPS config for ctrl%d, enable=%d\n",
__func__, ctrl->ndx, enable);
return 0;
@@ -1801,9 +1820,9 @@
if (mipi->data_lane3)
active_lanes |= BIT(3);
- pr_debug("%s: configuring ulps (%s) for ctrl%d, active lanes=0x%08x,clamps=%s\n",
+ pr_debug("%s: configuring ulps (%s) for ctrl%d, active lanes=0x%08x,reconfig=%s\n",
__func__, (enable ? "on" : "off"), ctrl->ndx,
- active_lanes, ctrl->mmss_clamp ? "enabled" : "disabled");
+ active_lanes, reconfig ? "true" : "false");
if (enable && !ctrl->ulps) {
/*
@@ -1816,7 +1835,7 @@
* power collapse and just restoring the controller state to
* ULPS with the clamps still in place.
*/
- if (!ctrl->mmss_clamp) {
+ if (!reconfig) {
ret = mdss_dsi_wait_for_lane_idle(ctrl);
if (ret) {
pr_warn("%s: lanes not idle, skip ulps\n",
@@ -2165,6 +2184,7 @@
int mdss_dsi_pre_clkoff_cb(void *priv,
enum mdss_dsi_clk_type clk,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state new_state)
{
int rc = 0;
@@ -2173,7 +2193,14 @@
pdata = &ctrl->panel_data;
- if ((clk & MDSS_DSI_LINK_CLK) && (new_state == MDSS_DSI_CLK_OFF)) {
+ if ((clk & MDSS_DSI_LINK_CLK) && (l_type == MDSS_DSI_LINK_HS_CLK) &&
+ (new_state == MDSS_DSI_CLK_OFF)) {
+ /* Disable HS TX driver in DSI PHY if applicable */
+ mdss_dsi_phy_hstx_drv_ctrl(ctrl, false);
+ }
+
+ if ((clk & MDSS_DSI_LINK_CLK) && (l_type == MDSS_DSI_LINK_LP_CLK) &&
+ (new_state == MDSS_DSI_CLK_OFF)) {
/*
* If ULPS feature is enabled, enter ULPS first.
* However, when blanking the panel, we should enter ULPS
@@ -2181,9 +2208,9 @@
*/
if (!(ctrl->ctrl_state & CTRL_STATE_PANEL_INIT)) {
if (pdata->panel_info.ulps_suspend_enabled)
- mdss_dsi_ulps_config(ctrl, 1);
+ mdss_dsi_ulps_config(ctrl, 1, false);
} else if (mdss_dsi_ulps_feature_enabled(pdata)) {
- rc = mdss_dsi_ulps_config(ctrl, 1);
+ rc = mdss_dsi_ulps_config(ctrl, 1, false);
}
if (rc) {
pr_err("%s: failed enable ulps, rc = %d\n",
@@ -2208,7 +2235,7 @@
* Make sure that controller is not in ULPS state when
* the DSI link is not active.
*/
- rc = mdss_dsi_ulps_config(ctrl, 0);
+ rc = mdss_dsi_ulps_config(ctrl, 0, false);
if (rc)
pr_err("%s: failed to disable ulps. rc=%d\n",
__func__, rc);
@@ -2220,6 +2247,7 @@
int mdss_dsi_post_clkon_cb(void *priv,
enum mdss_dsi_clk_type clk,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state curr_state)
{
int rc = 0;
@@ -2238,6 +2266,21 @@
if (mmss_clamp)
mdss_dsi_ctrl_setup(ctrl);
+ rc = mdss_dsi_clamp_ctrl(ctrl, 0);
+ if (rc) {
+ pr_err("%s: Failed to disable dsi clamps. rc=%d\n",
+ __func__, rc);
+ goto error;
+ }
+
+ /*
+ * Phy setup is needed if coming out of idle
+ * power collapse with clamps enabled.
+ */
+ if (ctrl->phy_power_off || mmss_clamp)
+ mdss_dsi_phy_power_on(ctrl, mmss_clamp);
+ }
+ if ((clk & MDSS_DSI_LINK_CLK) && (l_type == MDSS_DSI_LINK_HS_CLK)) {
if (ctrl->ulps) {
/*
* ULPS Entry Request. This is needed if the lanes were
@@ -2254,37 +2297,22 @@
* ULPS.
*/
ctrl->ulps = false;
- rc = mdss_dsi_ulps_config(ctrl, 1);
+ rc = mdss_dsi_ulps_config(ctrl, 1, true);
if (rc) {
pr_err("%s: Failed to enter ULPS. rc=%d\n",
__func__, rc);
goto error;
}
- }
- rc = mdss_dsi_clamp_ctrl(ctrl, 0);
- if (rc) {
- pr_err("%s: Failed to disable dsi clamps. rc=%d\n",
- __func__, rc);
- goto error;
- }
-
- /*
- * Phy setup is needed if coming out of idle
- * power collapse with clamps enabled.
- */
- if (ctrl->phy_power_off || mmss_clamp)
- mdss_dsi_phy_power_on(ctrl, mmss_clamp);
- }
- if (clk & MDSS_DSI_LINK_CLK) {
- if (ctrl->ulps) {
- rc = mdss_dsi_ulps_config(ctrl, 0);
+ rc = mdss_dsi_ulps_config(ctrl, 0, false);
if (rc) {
pr_err("%s: failed to disable ulps, rc= %d\n",
__func__, rc);
goto error;
}
}
+ /* Enable HS TX driver in DSI PHY if applicable */
+ mdss_dsi_phy_hstx_drv_ctrl(ctrl, true);
}
error:
return rc;
@@ -2292,6 +2320,7 @@
int mdss_dsi_post_clkoff_cb(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state curr_state)
{
int rc = 0;
@@ -2342,6 +2371,7 @@
int mdss_dsi_pre_clkon_cb(void *priv,
enum mdss_dsi_clk_type clk_type,
+ enum mdss_dsi_lclk_type l_type,
enum mdss_dsi_clk_state new_state)
{
int rc = 0;
diff --git a/fs/f2fs/super.c b/fs/f2fs/super.c
index 1692c26..78b763c 100644
--- a/fs/f2fs/super.c
+++ b/fs/f2fs/super.c
@@ -1456,7 +1456,7 @@
while (toread > 0) {
tocopy = min_t(unsigned long, sb->s_blocksize - offset, toread);
repeat:
- page = read_mapping_page(mapping, blkidx, NULL);
+ page = read_cache_page_gfp(mapping, blkidx, GFP_NOFS);
if (IS_ERR(page)) {
if (PTR_ERR(page) == -ENOMEM) {
congestion_wait(BLK_RW_ASYNC, HZ/50);
diff --git a/fs/sdcardfs/sdcardfs.h b/fs/sdcardfs/sdcardfs.h
index 610466a..826afb5 100644
--- a/fs/sdcardfs/sdcardfs.h
+++ b/fs/sdcardfs/sdcardfs.h
@@ -669,7 +669,7 @@
static inline bool qstr_case_eq(const struct qstr *q1, const struct qstr *q2)
{
- return q1->len == q2->len && str_case_eq(q1->name, q2->name);
+ return q1->len == q2->len && str_n_case_eq(q1->name, q2->name, q2->len);
}
#define QSTR_LITERAL(string) QSTR_INIT(string, sizeof(string)-1)
diff --git a/include/crypto/ice.h b/include/crypto/ice.h
index 558d136..b02a440 100644
--- a/include/crypto/ice.h
+++ b/include/crypto/ice.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2018, 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
@@ -53,6 +53,8 @@
struct qcom_ice_variant_ops *qcom_ice_get_variant_ops(struct device_node *node);
struct platform_device *qcom_ice_get_pdevice(struct device_node *node);
+void qcom_ice_set_fde_flag(int flag);
+int qcom_ice_set_fde_conf(sector_t strt, sector_t size, int idx, int mode);
#ifdef CONFIG_CRYPTO_DEV_QCOM_ICE
int qcom_ice_setup_ice_hw(const char *storage_type, int enable);
diff --git a/include/linux/devfreq.h b/include/linux/devfreq.h
index 8e849a6..eb84ce6 100644
--- a/include/linux/devfreq.h
+++ b/include/linux/devfreq.h
@@ -167,6 +167,7 @@
struct list_head node;
struct mutex lock;
+ struct mutex sysfs_lock;
struct device dev;
struct devfreq_dev_profile *profile;
const struct devfreq_governor *governor;
diff --git a/include/linux/dma-mapping-fast.h b/include/linux/dma-mapping-fast.h
index e9dabab..e370b43 100644
--- a/include/linux/dma-mapping-fast.h
+++ b/include/linux/dma-mapping-fast.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2016-2018, 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
@@ -27,6 +27,7 @@
u32 min_iova_align;
struct page *guard_page;
+ u32 force_guard_page_len;
unsigned int bitmap_size;
unsigned long *bitmap;
diff --git a/include/linux/input/ft5x06_ts.h b/include/linux/input/ft5x06_ts.h
new file mode 100644
index 0000000..2310989
--- /dev/null
+++ b/include/linux/input/ft5x06_ts.h
@@ -0,0 +1,77 @@
+/*
+ *
+ * FocalTech ft5x06 TouchScreen driver header file.
+ *
+ * Copyright (c) 2010 Focal tech Ltd.
+ * Copyright (c) 2012-2015, 2018 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
+ * may be copied, distributed, and modified under those terms.
+ *
+ * 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.
+ *
+ */
+#ifndef __LINUX_FT5X06_TS_H__
+#define __LINUX_FT5X06_TS_H__
+
+#define FT5X06_ID 0x55
+#define FT5X16_ID 0x0A
+#define FT5X36_ID 0x14
+#define FT6X06_ID 0x06
+#define FT6X36_ID 0x36
+
+struct fw_upgrade_info {
+ bool auto_cal;
+ u16 delay_aa;
+ u16 delay_55;
+ u8 upgrade_id_1;
+ u8 upgrade_id_2;
+ u16 delay_readid;
+ u16 delay_erase_flash;
+};
+
+struct ft5x06_gesture_platform_data {
+ int gesture_enable_to_set; /* enable/disable gesture */
+ int in_pocket; /* whether in pocket mode or not */
+ struct device *dev;
+ struct class *gesture_class;
+ struct ft5x06_ts_data *data;
+};
+
+struct ft5x06_ts_platform_data {
+ struct fw_upgrade_info info;
+ const char *name;
+ const char *fw_name;
+ u32 irqflags;
+ u32 irq_gpio;
+ u32 irq_gpio_flags;
+ u32 reset_gpio;
+ u32 reset_gpio_flags;
+ u32 family_id;
+ u32 x_max;
+ u32 y_max;
+ u32 x_min;
+ u32 y_min;
+ u32 panel_minx;
+ u32 panel_miny;
+ u32 panel_maxx;
+ u32 panel_maxy;
+ u32 group_id;
+ u32 hard_rst_dly;
+ u32 soft_rst_dly;
+ u32 num_max_touches;
+ bool fw_vkey_support;
+ bool no_force_update;
+ bool i2c_pull_up;
+ bool ignore_id_check;
+ bool gesture_support;
+ bool resume_in_workqueue;
+ int (*power_init)(bool);
+ int (*power_on)(bool);
+};
+
+#endif
diff --git a/include/linux/input/synaptics_dsx_v2_6.h b/include/linux/input/synaptics_dsx_v2_6.h
index 52241e5..5cd26bb 100644
--- a/include/linux/input/synaptics_dsx_v2_6.h
+++ b/include/linux/input/synaptics_dsx_v2_6.h
@@ -87,6 +87,7 @@
bool y_flip;
bool swap_axes;
bool resume_in_workqueue;
+ bool wakeup_gesture_en;
int irq_gpio;
int irq_on_state;
int power_gpio;
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index f25acfc..acbc605 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -148,6 +148,7 @@
DOMAIN_ATTR_CB_STALL_DISABLE,
DOMAIN_ATTR_UPSTREAM_IOVA_ALLOCATOR,
DOMAIN_ATTR_MMU500_ERRATA_MIN_ALIGN,
+ DOMAIN_ATTR_FORCE_IOVA_GUARD_PAGE,
DOMAIN_ATTR_MAX,
};
diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index 3513226..e1b845a 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -2169,13 +2169,10 @@
/* Used in GRE, set in fou/gue_gro_receive */
u8 is_fou:1;
- /* Used to determine if flush_id can be ignored */
- u8 is_atomic:1;
-
/* Number of gro_receive callbacks this packet already went through */
u8 recursion_counter:4;
- /* 1 bit hole */
+ /* 2 bit hole */
/* used to support CHECKSUM_COMPLETE for tunneling protocols */
__wsum csum;
diff --git a/include/linux/power_supply.h b/include/linux/power_supply.h
index 629907a..b59d548 100644
--- a/include/linux/power_supply.h
+++ b/include/linux/power_supply.h
@@ -280,6 +280,7 @@
POWER_SUPPLY_PROP_RECHARGE_SOC,
POWER_SUPPLY_PROP_TOGGLE_STAT,
POWER_SUPPLY_PROP_ALLOW_HVDCP3,
+ POWER_SUPPLY_PROP_HVDCP_OPTI_ALLOWED,
/* Local extensions of type int64_t */
POWER_SUPPLY_PROP_CHARGE_COUNTER_EXT,
/* Properties of type `const char *' */
diff --git a/include/linux/pwm.h b/include/linux/pwm.h
index 2c6c511..6c0168b 100644
--- a/include/linux/pwm.h
+++ b/include/linux/pwm.h
@@ -47,6 +47,29 @@
PWMF_EXPORTED = 1 << 1,
};
+/**
+ * enum pwm_output_type - output type of the PWM signal
+ * @PWM_OUTPUT_FIXED: PWM output is fixed until a change request
+ * @PWM_OUTPUT_MODULATED: PWM output is modulated in hardware
+ * autonomously with a predefined pattern
+ */
+enum pwm_output_type {
+ PWM_OUTPUT_FIXED = 1 << 0,
+ PWM_OUTPUT_MODULATED = 1 << 1,
+};
+
+/**
+ * struct pwm_output_pattern - PWM duty pattern for MODULATED duty type
+ * @duty_pattern: PWM duty cycles in the pattern for duty modulation
+ * @num_entries: number of entries in the pattern
+ * @cycles_per_duty: number of PWM period cycles an entry stays at
+ */
+struct pwm_output_pattern {
+ unsigned int *duty_pattern;
+ unsigned int num_entries;
+ unsigned int cycles_per_duty;
+};
+
/*
* struct pwm_state - state of a PWM channel
* @period: PWM period (in nanoseconds)
@@ -58,6 +81,8 @@
unsigned int period;
unsigned int duty_cycle;
enum pwm_polarity polarity;
+ enum pwm_output_type output_type;
+ struct pwm_output_pattern *output_pattern;
bool enabled;
};
@@ -143,6 +168,26 @@
return state.polarity;
}
+static inline enum pwm_output_type pwm_get_output_type(
+ const struct pwm_device *pwm)
+{
+ struct pwm_state state;
+
+ pwm_get_state(pwm, &state);
+
+ return state.output_type;
+}
+
+static inline struct pwm_output_pattern *pwm_get_output_pattern(
+ struct pwm_device *pwm)
+{
+ struct pwm_state state;
+
+ pwm_get_state(pwm, &state);
+
+ return pwm->state.output_pattern ?: NULL;
+}
+
static inline void pwm_get_args(const struct pwm_device *pwm,
struct pwm_args *args)
{
@@ -246,6 +291,9 @@
* @capture: capture and report PWM signal
* @enable: enable PWM output toggling
* @disable: disable PWM output toggling
+ * @get_output_type_supported: get the supported output type
+ * @set_output_type: set PWM output type
+ * @set_output_pattern: set the pattern for the modulated output
* @apply: atomically apply a new PWM config. The state argument
* should be adjusted with the real hardware config (if the
* approximate the period or duty_cycle value, state should
@@ -267,6 +315,13 @@
struct pwm_capture *result, unsigned long timeout);
int (*enable)(struct pwm_chip *chip, struct pwm_device *pwm);
void (*disable)(struct pwm_chip *chip, struct pwm_device *pwm);
+ int (*get_output_type_supported)(struct pwm_chip *chip,
+ struct pwm_device *pwm);
+ int (*set_output_type)(struct pwm_chip *chip, struct pwm_device *pwm,
+ enum pwm_output_type output_type);
+ int (*set_output_pattern)(struct pwm_chip *chip,
+ struct pwm_device *pwm,
+ struct pwm_output_pattern *output_pattern);
int (*apply)(struct pwm_chip *chip, struct pwm_device *pwm,
struct pwm_state *state);
void (*get_state)(struct pwm_chip *chip, struct pwm_device *pwm,
@@ -323,6 +378,21 @@
int pwm_adjust_config(struct pwm_device *pwm);
/**
+ * pwm_output_type_support()
+ * @pwm: PWM device
+ *
+ * Returns: output types supported by the PWM device
+ */
+static inline int pwm_get_output_type_supported(struct pwm_device *pwm)
+{
+ if (pwm->chip->ops->get_output_type_supported != NULL)
+ return pwm->chip->ops->
+ get_output_type_supported(pwm->chip, pwm);
+ else
+ return PWM_OUTPUT_FIXED;
+}
+
+/**
* pwm_config() - change a PWM device configuration
* @pwm: PWM device
* @duty_ns: "on" time (in nanoseconds)
diff --git a/include/linux/sched.h b/include/linux/sched.h
index 8933c9f..bae4f35 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -3971,6 +3971,7 @@
#define SCHED_CPUFREQ_WALT (1U << 4)
#define SCHED_CPUFREQ_PL (1U << 5)
#define SCHED_CPUFREQ_EARLY_DET (1U << 6)
+#define SCHED_CPUFREQ_FORCE_UPDATE (1U << 7)
#define SCHED_CPUFREQ_RT_DL (SCHED_CPUFREQ_RT | SCHED_CPUFREQ_DL)
diff --git a/include/linux/usb_bam.h b/include/linux/usb_bam.h
index fc0647a..3811e34 100644
--- a/include/linux/usb_bam.h
+++ b/include/linux/usb_bam.h
@@ -216,7 +216,6 @@
* can work at in bam2bam mode when connected to HS host.
* @max_mbps_superspeed: Maximum Mbits per seconds that the USB core
* can work at in bam2bam mode when connected to SS host.
- * @enable_hsusb_bam_on_boot: Enable HSUSB BAM (non-NDP) on bootup itself
*/
struct msm_usb_bam_data {
u8 max_connections;
@@ -229,7 +228,6 @@
u32 override_threshold;
u32 max_mbps_highspeed;
u32 max_mbps_superspeed;
- bool enable_hsusb_bam_on_boot;
enum usb_ctrl bam_type;
};
diff --git a/include/net/cnss2.h b/include/net/cnss2.h
index ca2de60..9dbf449 100644
--- a/include/net/cnss2.h
+++ b/include/net/cnss2.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2016-2018, 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 @@
CNSS_INITIALIZED,
CNSS_LOAD_UNLOAD,
CNSS_RECOVERY,
+ CNSS_FW_DOWN,
};
struct cnss_ce_tgt_pipe_cfg {
diff --git a/include/soc/qcom/hsic_sysmon.h b/include/soc/qcom/hsic_sysmon.h
new file mode 100644
index 0000000..5cbecab
--- /dev/null
+++ b/include/soc/qcom/hsic_sysmon.h
@@ -0,0 +1,58 @@
+/* Copyright (c) 2012-2013,2016,2018, 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.
+ */
+
+#ifndef __HSIC_SYSMON_H__
+#define __HSIC_SYSMON_H__
+
+/**
+ * enum hsic_sysmon_device_id - Supported HSIC subsystem devices
+ */
+enum hsic_sysmon_device_id {
+ HSIC_SYSMON_DEV_EXT_MODEM,
+ HSIC_SYSMON_DEV_EXT_MODEM_2,
+ NUM_HSIC_SYSMON_DEVS
+};
+
+#if IS_ENABLED(CONFIG_MSM_HSIC_SYSMON) || \
+ IS_ENABLED(CONFIG_MSM_HSIC_SYSMON_MODULE)
+
+extern int hsic_sysmon_open(enum hsic_sysmon_device_id id);
+extern void hsic_sysmon_close(enum hsic_sysmon_device_id id);
+extern int hsic_sysmon_read(enum hsic_sysmon_device_id id, char *data,
+ size_t len, size_t *actual_len, int timeout);
+extern int hsic_sysmon_write(enum hsic_sysmon_device_id id, const char *data,
+ size_t len, int timeout);
+
+#else /* CONFIG_MSM_HSIC_SYSMON || CONFIG_MSM_HSIC_SYSMON_MODULE */
+
+static inline int hsic_sysmon_open(enum hsic_sysmon_device_id id)
+{
+ return -ENODEV;
+}
+
+static inline void hsic_sysmon_close(enum hsic_sysmon_device_id id) { }
+
+static inline int hsic_sysmon_read(enum hsic_sysmon_device_id id, char *data,
+ size_t len, size_t *actual_len, int timeout)
+{
+ return -ENODEV;
+}
+
+static inline int hsic_sysmon_write(enum hsic_sysmon_device_id id,
+ const char *data, size_t len, int timeout)
+{
+ return -ENODEV;
+}
+
+#endif /* CONFIG_MSM_HSIC_SYSMON || CONFIG_MSM_HSIC_SYSMON_MODULE */
+
+#endif /* __HSIC_SYSMON_H__ */
diff --git a/include/soc/qcom/socinfo.h b/include/soc/qcom/socinfo.h
index b04052e..5f496a8 100644
--- a/include/soc/qcom/socinfo.h
+++ b/include/soc/qcom/socinfo.h
@@ -122,6 +122,10 @@
of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sdm439")
#define early_machine_is_sdm429() \
of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sdm429")
+#define early_machine_is_sda439() \
+ of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sda439")
+#define early_machine_is_sda429() \
+ of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,sda429")
#define early_machine_is_mdm9650() \
of_flat_dt_is_compatible(of_get_flat_dt_root(), "qcom,mdm9650")
#else
@@ -174,6 +178,8 @@
#define early_machine_is_sdm632() 0
#define early_machine_is_sdm439() 0
#define early_machine_is_sdm429() 0
+#define early_machine_is_sda439() 0
+#define early_machine_is_sda429() 0
#define early_machine_is_mdm9650() 0
#endif
@@ -248,6 +254,8 @@
MSM_CPU_9607,
MSM_CPU_SDM439,
MSM_CPU_SDM429,
+ MSM_CPU_SDA439,
+ MSM_CPU_SDA429,
MSM_CPU_9650,
};
diff --git a/include/soc/qcom/sysmon.h b/include/soc/qcom/sysmon.h
index 56860db..2ad3a5e 100644
--- a/include/soc/qcom/sysmon.h
+++ b/include/soc/qcom/sysmon.h
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2011-2016, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2011-2016,2018 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,10 +15,27 @@
#ifndef __MSM_SYSMON_H
#define __MSM_SYSMON_H
+#include <soc/qcom/smd.h>
#include <soc/qcom/subsystem_notif.h>
#include <soc/qcom/subsystem_restart.h>
/**
+ * enum subsys_id - Destination subsystems for events.
+ */
+enum subsys_id {
+ /* SMD subsystems */
+ SYSMON_SS_MODEM = SMD_APPS_MODEM,
+ SYSMON_SS_LPASS = SMD_APPS_QDSP,
+ SYSMON_SS_WCNSS = SMD_APPS_WCNSS,
+ SYSMON_SS_DSPS = SMD_APPS_DSPS,
+ SYSMON_SS_Q6FW = SMD_APPS_Q6FW,
+
+ /* Non-SMD subsystems */
+ SYSMON_SS_EXT_MODEM = SMD_NUM_TYPE,
+ SYSMON_NUM_SS
+};
+
+/**
* enum ssctl_ssr_event_enum_type - Subsystem notification type.
*/
enum ssctl_ssr_event_enum_type {
diff --git a/include/trace/events/mpm.h b/include/trace/events/mpm.h
index 433fdbf..6746377 100644
--- a/include/trace/events/mpm.h
+++ b/include/trace/events/mpm.h
@@ -57,6 +57,28 @@
TP_printk("index:%u wakeup_irqs:0x%x", __entry->index, __entry->irqs)
);
+TRACE_EVENT(mpm_wakeup_time,
+
+ TP_PROTO(bool from_idle, u64 wakeup, u64 current_ticks),
+
+ TP_ARGS(from_idle, wakeup, current_ticks),
+
+ TP_STRUCT__entry(
+ __field(bool, from_idle)
+ __field(u64, wakeup)
+ __field(u64, current_ticks)
+ ),
+
+ TP_fast_assign(
+ __entry->from_idle = from_idle;
+ __entry->wakeup = wakeup;
+ __entry->current_ticks = current_ticks;
+ ),
+
+ TP_printk("idle:%d wakeup:0x%llx current:0x%llx", __entry->from_idle,
+ __entry->wakeup, __entry->current_ticks)
+);
+
#endif
#define TRACE_INCLUDE_FILE mpm
#include <trace/define_trace.h>
diff --git a/include/trace/events/sched.h b/include/trace/events/sched.h
index 23a3b9a..4ad7cbd 100644
--- a/include/trace/events/sched.h
+++ b/include/trace/events/sched.h
@@ -714,10 +714,10 @@
TP_PROTO(struct task_struct *p, int next_cpu, int backup_cpu,
int target_cpu, bool sync, bool need_idle,
- bool placement_boost, int rtg_cpu),
+ bool placement_boost, int rtg_cpu, u64 start_t),
TP_ARGS(p, next_cpu, backup_cpu, target_cpu, sync, need_idle,
- placement_boost, rtg_cpu),
+ placement_boost, rtg_cpu, start_t),
TP_STRUCT__entry(
__field(int, pid )
@@ -746,9 +746,7 @@
__entry->need_idle = need_idle;
__entry->placement_boost = placement_boost;
__entry->rtg_cpu = rtg_cpu;
- __entry->latency = p->ravg.mark_start ?
- ktime_get_ns() -
- p->ravg.mark_start : 0;
+ __entry->latency = (sched_clock() - start_t);
),
TP_printk("pid=%d comm=%s util=%lu prev_cpu=%d next_cpu=%d backup_cpu=%d target_cpu=%d sync=%d need_idle=%d placement_boost=%d rtg_cpu=%d latency=%llu",
diff --git a/include/uapi/linux/Kbuild b/include/uapi/linux/Kbuild
index a17b435..75aa98ff 100644
--- a/include/uapi/linux/Kbuild
+++ b/include/uapi/linux/Kbuild
@@ -511,4 +511,5 @@
header-y += msm_dsps.h
header-y += msm-core-interface.h
header-y += msm_rotator.h
+header-y += bgcom_interface.h
header-y += nfc/
diff --git a/include/uapi/linux/bgcom_interface.h b/include/uapi/linux/bgcom_interface.h
new file mode 100644
index 0000000..f18280a
--- /dev/null
+++ b/include/uapi/linux/bgcom_interface.h
@@ -0,0 +1,63 @@
+/* Copyright (c) 2018, 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.
+ */
+#ifndef LINUX_BG_CHAR_H
+#define LINUX_BG_CHAR_H
+#define BGCOM_REG_READ 0
+#define BGCOM_AHB_READ 1
+#define BGCOM_AHB_WRITE 2
+#define BGCOM_SET_SPI_FREE 3
+#define BGCOM_SET_SPI_BUSY 4
+#define BGCOM_REG_WRITE 5
+#define BGCOM_SOFT_RESET 6
+#define BGCOM_MODEM_DOWN2_BG 7
+#define EXCHANGE_CODE 'V'
+
+struct bg_ui_data {
+ uint64_t __user write;
+ uint64_t __user result;
+ uint32_t bg_address;
+ uint32_t cmd;
+ uint32_t num_of_words;
+};
+
+enum bg_event_type {
+ BG_BEFORE_POWER_DOWN = 1,
+ BG_AFTER_POWER_UP,
+ MODEM_BEFORE_POWER_DOWN,
+ MODEM_AFTER_POWER_UP,
+};
+
+#define REG_READ \
+ _IOWR(EXCHANGE_CODE, BGCOM_REG_READ, \
+ struct bg_ui_data)
+#define AHB_READ \
+ _IOWR(EXCHANGE_CODE, BGCOM_AHB_READ, \
+ struct bg_ui_data)
+#define AHB_WRITE \
+ _IOW(EXCHANGE_CODE, BGCOM_AHB_WRITE, \
+ struct bg_ui_data)
+#define SET_SPI_FREE \
+ _IOR(EXCHANGE_CODE, BGCOM_SET_SPI_FREE, \
+ struct bg_ui_data)
+#define SET_SPI_BUSY \
+ _IOR(EXCHANGE_CODE, BGCOM_SET_SPI_BUSY, \
+ struct bg_ui_data)
+#define REG_WRITE \
+ _IOWR(EXCHANGE_CODE, BGCOM_REG_WRITE, \
+ struct bg_ui_data)
+#define BG_SOFT_RESET \
+ _IOWR(EXCHANGE_CODE, BGCOM_SOFT_RESET, \
+ struct bg_ui_data)
+#define BG_MODEM_DOWN2_BG_DONE \
+ _IOWR(EXCHANGE_CODE, BGCOM_MODEM_DOWN2_BG, \
+ struct bg_ui_data)
+#endif
diff --git a/include/uapi/linux/qseecom.h b/include/uapi/linux/qseecom.h
index 55c71dd..f0a26b2 100644
--- a/include/uapi/linux/qseecom.h
+++ b/include/uapi/linux/qseecom.h
@@ -277,6 +277,17 @@
struct qseecom_ce_pipe_entry ce_pipe_entry[MAX_CE_PIPE_PAIR_PER_UNIT];
};
+struct qseecom_ice_data_t {
+ int flag;
+};
+
+struct qseecom_encdec_conf_t {
+ __le64 start_sector;
+ size_t fs_size;
+ int index;
+ int mode;
+};
+
#define SG_ENTRY_SZ sizeof(struct qseecom_sg_entry)
#define SG_ENTRY_SZ_64BIT sizeof(struct qseecom_sg_entry_64bit)
@@ -385,5 +396,10 @@
#define QSEECOM_IOCTL_QUERY_CE_PIPE_INFO \
_IOWR(QSEECOM_IOC_MAGIC, 42, struct qseecom_ce_info_req)
+#define QSEECOM_IOCTL_SET_ICE_INFO \
+ _IOWR(QSEECOM_IOC_MAGIC, 43, struct qseecom_ice_data_t)
+
+#define QSEECOM_IOCTL_SET_ENCDEC_INFO \
+ _IOWR(QSEECOM_IOC_MAGIC, 44, struct qseecom_encdec_conf_t)
#endif /* _UAPI_QSEECOM_H_ */
diff --git a/include/uapi/media/msm_camera.h b/include/uapi/media/msm_camera.h
index 693fd21..c58a273 100644
--- a/include/uapi/media/msm_camera.h
+++ b/include/uapi/media/msm_camera.h
@@ -1392,6 +1392,7 @@
uint16_t lane_mask;
uint8_t combo_mode;
uint8_t csid_core;
+ unsigned long data_rate;
};
struct msm_camera_csi2_params {
diff --git a/include/uapi/media/msm_camsensor_sdk.h b/include/uapi/media/msm_camsensor_sdk.h
index 5266c02..2283933f 100644
--- a/include/uapi/media/msm_camsensor_sdk.h
+++ b/include/uapi/media/msm_camsensor_sdk.h
@@ -367,6 +367,7 @@
unsigned char csid_core;
unsigned int csiphy_clk;
unsigned char csi_3phase;
+ unsigned long data_rate;
};
struct msm_camera_i2c_seq_reg_array {
diff --git a/kernel/power/Kconfig b/kernel/power/Kconfig
index f4330a2..a29eaee 100644
--- a/kernel/power/Kconfig
+++ b/kernel/power/Kconfig
@@ -77,6 +77,23 @@
For more information take a look at <file:Documentation/power/swsusp.txt>.
+config HIBERNATION_IMAGE_REUSE
+ bool "Reuse hibernation image"
+ depends on HIBERNATION
+ ---help---
+ By default this hibernation image is erased after either a
+ successful or unsuccessful hibernation restore sequeunce. Since
+ filesystem contents on disk are not part of the hibernation
+ image, failure to create a new hibernation image every boot can
+ lead to filesystem corruption.
+
+ Conversely, if the usecase can guarantee that the filesystem is
+ not ever modified, the same hibernation image can be reused. This
+ prevents creating additional hibernation images unncesarily.
+
+ For more details, refer to the description of CONFIG_HIBERNATION
+ for booting without resuming.
+
config ARCH_SAVE_PAGE_KEYS
bool
diff --git a/kernel/power/swap.c b/kernel/power/swap.c
index a3b1e61..95db6b79 100644
--- a/kernel/power/swap.c
+++ b/kernel/power/swap.c
@@ -1542,10 +1542,12 @@
if (!memcmp(HIBERNATE_SIG, swsusp_header->sig, 10)) {
memcpy(swsusp_header->sig, swsusp_header->orig_sig, 10);
+#ifndef CONFIG_HIBERNATION_IMAGE_REUSE
/* Reset swap signature now */
error = hib_submit_io(REQ_OP_WRITE, WRITE_SYNC,
swsusp_resume_block,
swsusp_header, NULL);
+#endif
} else {
error = -EINVAL;
}
diff --git a/kernel/sched/fair.c b/kernel/sched/fair.c
index 744b535..c00e731 100644
--- a/kernel/sched/fair.c
+++ b/kernel/sched/fair.c
@@ -6814,12 +6814,33 @@
bool avoid_prev_cpu;
};
+#ifdef CONFIG_SCHED_WALT
+static unsigned long cpu_estimated_capacity(int cpu, struct task_struct *p)
+{
+ unsigned long tutil, estimated_capacity;
+
+ if (task_in_cum_window_demand(cpu_rq(cpu), p))
+ tutil = 0;
+ else
+ tutil = task_util(p);
+
+ estimated_capacity = cpu_util_cum(cpu, tutil);
+
+ return estimated_capacity;
+}
+#else
+static unsigned long cpu_estimated_capacity(int cpu, struct task_struct *p)
+{
+ return cpu_util_wake(cpu, p);
+}
+#endif
+
static bool is_packing_eligible(struct task_struct *p, int target_cpu,
struct find_best_target_env *fbt_env,
unsigned int target_cpus_count,
int best_idle_cstate)
{
- unsigned long tutil, estimated_capacity;
+ unsigned long estimated_capacity;
if (fbt_env->placement_boost || fbt_env->need_idle)
return false;
@@ -6830,12 +6851,7 @@
if (target_cpus_count != 1)
return true;
- if (task_in_cum_window_demand(cpu_rq(target_cpu), p))
- tutil = 0;
- else
- tutil = task_util(p);
-
- estimated_capacity = cpu_util_cum(target_cpu, tutil);
+ estimated_capacity = cpu_estimated_capacity(target_cpu, p);
estimated_capacity = add_capacity_margin(estimated_capacity,
target_cpu);
@@ -6874,6 +6890,7 @@
return walt_start_cpu(start_cpu);
}
+unsigned int sched_smp_overlap_capacity;
static inline int find_best_target(struct task_struct *p, int *backup_cpu,
bool boosted, bool prefer_idle,
struct find_best_target_env *fbt_env)
@@ -7113,6 +7130,12 @@
}
/*
+ * Consider only idle CPUs for active migration.
+ */
+ if (p->state == TASK_RUNNING)
+ continue;
+
+ /*
* Case C) Non latency sensitive tasks on ACTIVE CPUs.
*
* Pack tasks in the most energy efficient capacities.
@@ -7273,6 +7296,7 @@
task_fits_max(p, cpu);
}
+#ifdef CONFIG_SCHED_WALT
static inline struct cpumask *find_rtg_target(struct task_struct *p)
{
struct related_thread_group *grp;
@@ -7293,6 +7317,12 @@
return rtg_target;
}
+#else
+static inline struct cpumask *find_rtg_target(struct task_struct *p)
+{
+ return NULL;
+}
+#endif
static int select_energy_cpu_brute(struct task_struct *p, int prev_cpu, int sync)
{
@@ -7303,6 +7333,10 @@
int next_cpu = -1;
struct cpumask *rtg_target = find_rtg_target(p);
struct find_best_target_env fbt_env;
+ u64 start_t = 0;
+
+ if (trace_sched_task_util_enabled())
+ start_t = sched_clock();
schedstat_inc(p->se.statistics.nr_wakeups_secb_attempts);
schedstat_inc(this_rq()->eas_stats.secb_attempts);
@@ -7427,7 +7461,8 @@
unlock:
trace_sched_task_util(p, next_cpu, backup_cpu, target_cpu, sync,
fbt_env.need_idle, fbt_env.placement_boost,
- rtg_target ? cpumask_first(rtg_target) : -1);
+ rtg_target ? cpumask_first(rtg_target) : -1,
+ start_t);
rcu_read_unlock();
return target_cpu;
}
@@ -8754,9 +8789,11 @@
capacity = 1;
cpu_rq(cpu)->cpu_capacity = capacity;
- sdg->sgc->capacity = capacity;
- sdg->sgc->max_capacity = capacity;
- sdg->sgc->min_capacity = capacity;
+ if (!sd->child) {
+ sdg->sgc->capacity = capacity;
+ sdg->sgc->max_capacity = capacity;
+ sdg->sgc->min_capacity = capacity;
+ }
}
void update_group_capacity(struct sched_domain *sd, int cpu)
@@ -8770,9 +8807,16 @@
interval = clamp(interval, 1UL, max_load_balance_interval);
sdg->sgc->next_update = jiffies + interval;
- if (!child) {
+ /*
+ * When there is only 1 CPU in the sched group of a higher
+ * level sched domain (sd->child != NULL), the load balance
+ * does not happen for the last level sched domain. Check
+ * this condition and update the CPU capacity accordingly.
+ */
+ if (cpumask_weight(sched_group_cpus(sdg)) == 1) {
update_cpu_capacity(sd, cpu);
- return;
+ if (!child)
+ return;
}
capacity = 0;
@@ -10871,6 +10915,24 @@
#endif /* CONFIG_SMP */
+#ifdef CONFIG_SCHED_WALT
+static inline void
+walt_update_misfit_task(struct rq *rq, struct task_struct *curr)
+{
+ bool misfit = rq->misfit_task;
+
+ if (curr->misfit != misfit) {
+ walt_fixup_nr_big_tasks(rq, curr, 1, misfit);
+ curr->misfit = misfit;
+ }
+}
+#else
+static inline void
+walt_update_misfit_task(struct rq *rq, struct task_struct *curr)
+{
+}
+#endif
+
/*
* scheduler tick hitting a task of our scheduling class:
*/
@@ -10878,10 +10940,6 @@
{
struct cfs_rq *cfs_rq;
struct sched_entity *se = &curr->se;
-#ifdef CONFIG_SMP
- bool old_misfit = curr->misfit;
- bool misfit;
-#endif
for_each_sched_entity(se) {
cfs_rq = cfs_rq_of(se);
@@ -10897,15 +10955,9 @@
trace_sched_overutilized(true);
}
- misfit = !task_fits_max(curr, rq->cpu);
- rq->misfit_task = misfit;
-
- if (old_misfit != misfit) {
- walt_fixup_nr_big_tasks(rq, curr, 1, misfit);
- curr->misfit = misfit;
- }
+ rq->misfit_task = !task_fits_max(curr, rq->cpu);
#endif
-
+ walt_update_misfit_task(rq, curr);
}
/*
diff --git a/kernel/sched/sched.h b/kernel/sched/sched.h
index 8329e9c..3637d96 100644
--- a/kernel/sched/sched.h
+++ b/kernel/sched/sched.h
@@ -822,6 +822,7 @@
u8 curr_table;
int prev_top;
int curr_top;
+ bool notif_pending;
#endif
#ifdef CONFIG_IRQ_TIME_ACCOUNTING
@@ -1112,6 +1113,11 @@
SCHED_BOOST_ON_ALL,
};
+#define NO_BOOST 0
+#define FULL_THROTTLE_BOOST 1
+#define CONSERVATIVE_BOOST 2
+#define RESTRAINED_BOOST 3
+
/*
* Returns the rq capacity of any rq in a group. This does not play
* well with groups where rq capacity can change independently.
@@ -1910,6 +1916,9 @@
return cpu_util_freq_pelt(cpu);
}
+#define sched_ravg_window TICK_NSEC
+#define sysctl_sched_use_walt_cpu_util 0
+
#endif /* CONFIG_SCHED_WALT */
extern unsigned long
@@ -2258,7 +2267,8 @@
#ifdef CONFIG_SCHED_WALT
unsigned int exception_flags = SCHED_CPUFREQ_INTERCLUSTER_MIG |
- SCHED_CPUFREQ_PL | SCHED_CPUFREQ_EARLY_DET;
+ SCHED_CPUFREQ_PL | SCHED_CPUFREQ_EARLY_DET |
+ SCHED_CPUFREQ_FORCE_UPDATE;
/*
* Skip if we've already reported, but not if this is an inter-cluster
@@ -2367,11 +2377,6 @@
extern void add_new_task_to_grp(struct task_struct *new);
extern unsigned int update_freq_aggregate_threshold(unsigned int threshold);
-#define NO_BOOST 0
-#define FULL_THROTTLE_BOOST 1
-#define CONSERVATIVE_BOOST 2
-#define RESTRAINED_BOOST 3
-
static inline int cpu_capacity(int cpu)
{
return cpu_rq(cpu)->cluster->capacity;
@@ -2789,6 +2794,11 @@
static inline void clear_walt_request(int cpu) { }
+static inline int is_reserved(int cpu)
+{
+ return 0;
+}
+
static inline int got_boost_kick(void)
{
return 0;
diff --git a/kernel/sched/tune.c b/kernel/sched/tune.c
index bdcd174..192e8c7 100644
--- a/kernel/sched/tune.c
+++ b/kernel/sched/tune.c
@@ -753,6 +753,10 @@
sync_cgroup_colocation(task, colocate);
}
+#else
+static void schedtune_attach(struct cgroup_taskset *tset)
+{
+}
#endif
static int
diff --git a/kernel/sched/walt.c b/kernel/sched/walt.c
index b4d815c..e6a11c1 100644
--- a/kernel/sched/walt.c
+++ b/kernel/sched/walt.c
@@ -822,8 +822,11 @@
migrate_top_tasks(p, src_rq, dest_rq);
- if (!same_freq_domain(new_cpu, task_cpu(p)))
+ if (!same_freq_domain(new_cpu, task_cpu(p))) {
+ src_rq->notif_pending = true;
+ dest_rq->notif_pending = true;
irq_work_queue(&walt_migration_irq_work);
+ }
if (p == src_rq->ed_task) {
src_rq->ed_task = NULL;
@@ -2193,7 +2196,6 @@
int __read_mostly min_power_cpu;
-unsigned int sched_smp_overlap_capacity;
void walt_sched_energy_populated_callback(void)
{
struct sched_cluster *cluster;
@@ -3114,10 +3116,11 @@
int cpu;
u64 wc;
int flag = SCHED_CPUFREQ_WALT;
+ bool is_migration = false;
/* Am I the window rollover work or the migration work? */
if (irq_work == &walt_migration_irq_work)
- flag |= SCHED_CPUFREQ_INTERCLUSTER_MIG;
+ is_migration = true;
for_each_cpu(cpu, cpu_possible_mask)
raw_spin_lock(&cpu_rq(cpu)->lock);
@@ -3144,14 +3147,29 @@
raw_spin_unlock(&cluster->load_lock);
}
- for_each_sched_cluster(cluster)
- for_each_cpu(cpu, &cluster->cpus)
- cpufreq_update_util(cpu_rq(cpu), flag);
+ for_each_sched_cluster(cluster) {
+ for_each_cpu(cpu, &cluster->cpus) {
+ int nflag = flag;
+
+ rq = cpu_rq(cpu);
+
+ if (is_migration) {
+ if (rq->notif_pending) {
+ nflag |= SCHED_CPUFREQ_INTERCLUSTER_MIG;
+ rq->notif_pending = false;
+ } else {
+ nflag |= SCHED_CPUFREQ_FORCE_UPDATE;
+ }
+ }
+
+ cpufreq_update_util(rq, nflag);
+ }
+ }
for_each_cpu(cpu, cpu_possible_mask)
raw_spin_unlock(&cpu_rq(cpu)->lock);
- if (irq_work != &walt_migration_irq_work)
+ if (!is_migration)
core_ctl_check(this_rq()->window_start);
}
@@ -3247,6 +3265,7 @@
clear_top_tasks_bitmap(rq->top_tasks_bitmap[j]);
}
rq->cum_window_demand = 0;
+ rq->notif_pending = false;
walt_cpu_util_freq_divisor =
(sched_ravg_window >> SCHED_CAPACITY_SHIFT) * 100;
diff --git a/kernel/sched/walt.h b/kernel/sched/walt.h
index 414c4ae..be06e7d4 100644
--- a/kernel/sched/walt.h
+++ b/kernel/sched/walt.h
@@ -181,7 +181,6 @@
{
return sched_irqload(cpu) >= sysctl_sched_cpu_high_irqload;
}
-#define walt_cpu_high_irqload(cpu) sched_cpu_high_irqload(cpu)
static inline int exiting_task(struct task_struct *p)
{
@@ -378,6 +377,12 @@
return prev_cpu;
}
+static inline u64 sched_irqload(int cpu)
+{
+ return 0;
+}
#endif /* CONFIG_SCHED_WALT */
+#define walt_cpu_high_irqload(cpu) sched_cpu_high_irqload(cpu)
+
#endif
diff --git a/net/core/dev.c b/net/core/dev.c
index c2f62d2..72fb37c 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -4568,6 +4568,7 @@
unsigned long diffs;
NAPI_GRO_CB(p)->flush = 0;
+ NAPI_GRO_CB(p)->flush_id = 0;
if (hash != skb_get_hash_raw(p)) {
NAPI_GRO_CB(p)->same_flow = 0;
@@ -4659,7 +4660,6 @@
NAPI_GRO_CB(skb)->encap_mark = 0;
NAPI_GRO_CB(skb)->recursion_counter = 0;
NAPI_GRO_CB(skb)->is_fou = 0;
- NAPI_GRO_CB(skb)->is_atomic = 1;
NAPI_GRO_CB(skb)->gro_remcsum_start = 0;
/* Setup for GRO checksum validation */
diff --git a/net/core/neighbour.c b/net/core/neighbour.c
index 7d07d6b..eecad95 100644
--- a/net/core/neighbour.c
+++ b/net/core/neighbour.c
@@ -945,11 +945,15 @@
if (neigh_probe_enable) {
if (neigh->nud_state & (NUD_INCOMPLETE | NUD_PROBE | NUD_STALE))
neigh_probe(neigh);
- } else if (neigh->nud_state & (NUD_INCOMPLETE | NUD_PROBE)) {
- neigh_probe(neigh);
+ else
+ write_unlock(&neigh->lock);
} else {
+ if (neigh->nud_state & (NUD_INCOMPLETE | NUD_PROBE)) {
+ neigh_probe(neigh);
+ } else {
out:
- write_unlock(&neigh->lock);
+ write_unlock(&neigh->lock);
+ }
}
if (notify)
diff --git a/net/ipc_router/ipc_router_core.c b/net/ipc_router/ipc_router_core.c
index d38157d..f3c81c2 100644
--- a/net/ipc_router/ipc_router_core.c
+++ b/net/ipc_router/ipc_router_core.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011-2017, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2011-2018, 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
@@ -277,7 +277,7 @@
*/
static void skb_copy_to_log_buf(struct sk_buff_head *skb_head,
unsigned int pl_len, unsigned int hdr_offset,
- u64 *log_buf)
+ unsigned char *log_buf)
{
struct sk_buff *temp_skb;
unsigned int copied_len = 0, copy_len = 0;
@@ -356,7 +356,8 @@
else if (hdr->version == IPC_ROUTER_V2)
hdr_offset = sizeof(struct rr_header_v2);
}
- skb_copy_to_log_buf(skb_head, buf_len, hdr_offset, &pl_buf);
+ skb_copy_to_log_buf(skb_head, buf_len, hdr_offset,
+ (unsigned char *)&pl_buf);
if (port_ptr && rport_ptr && (port_ptr->type == CLIENT_PORT) &&
rport_ptr->server) {
diff --git a/net/ipv4/af_inet.c b/net/ipv4/af_inet.c
index f3bf1ba..90c91a7 100644
--- a/net/ipv4/af_inet.c
+++ b/net/ipv4/af_inet.c
@@ -1362,7 +1362,6 @@
for (p = *head; p; p = p->next) {
struct iphdr *iph2;
- u16 flush_id;
if (!NAPI_GRO_CB(p)->same_flow)
continue;
@@ -1388,34 +1387,23 @@
NAPI_GRO_CB(p)->flush |= flush;
- /* We need to store of the IP ID check to be included later
- * when we can verify that this packet does in fact belong
- * to a given flow.
+ /* For non-atomic datagrams we need to save the IP ID offset
+ * to be included later. If the frame has the DF bit set
+ * we must ignore the IP ID value as per RFC 6864.
*/
- flush_id = (u16)(id - ntohs(iph2->id));
+ if (iph2->frag_off & htons(IP_DF))
+ continue;
- /* This bit of code makes it much easier for us to identify
- * the cases where we are doing atomic vs non-atomic IP ID
- * checks. Specifically an atomic check can return IP ID
- * values 0 - 0xFFFF, while a non-atomic check can only
- * return 0 or 0xFFFF.
+ /* We must save the offset as it is possible to have multiple
+ * flows using the same protocol and address pairs so we
+ * need to wait until we can validate this is part of the
+ * same flow with a 5-tuple or better to avoid unnecessary
+ * collisions between flows.
*/
- if (!NAPI_GRO_CB(p)->is_atomic ||
- !(iph->frag_off & htons(IP_DF))) {
- flush_id ^= NAPI_GRO_CB(p)->count;
- flush_id = flush_id ? 0xFFFF : 0;
- }
-
- /* If the previous IP ID value was based on an atomic
- * datagram we can overwrite the value and ignore it.
- */
- if (NAPI_GRO_CB(skb)->is_atomic)
- NAPI_GRO_CB(p)->flush_id = flush_id;
- else
- NAPI_GRO_CB(p)->flush_id |= flush_id;
+ NAPI_GRO_CB(p)->flush_id |= ntohs(iph2->id) ^
+ (u16)(id - NAPI_GRO_CB(p)->count);
}
- NAPI_GRO_CB(skb)->is_atomic = !!(iph->frag_off & htons(IP_DF));
NAPI_GRO_CB(skb)->flush |= flush;
skb_set_network_header(skb, off);
/* The above will be needed by the transport layer if there is one
diff --git a/net/ipv4/tcp_offload.c b/net/ipv4/tcp_offload.c
index 366b1be..35637f1 100644
--- a/net/ipv4/tcp_offload.c
+++ b/net/ipv4/tcp_offload.c
@@ -230,7 +230,7 @@
found:
/* Include the IP ID check below from the inner most IP hdr */
- flush = NAPI_GRO_CB(p)->flush;
+ flush = NAPI_GRO_CB(p)->flush | NAPI_GRO_CB(p)->flush_id;
flush |= (__force int)(flags & TCP_FLAG_CWR);
flush |= (__force int)((flags ^ tcp_flag_word(th2)) &
~(TCP_FLAG_CWR | TCP_FLAG_FIN | TCP_FLAG_PSH));
@@ -239,17 +239,6 @@
flush |= *(u32 *)((u8 *)th + i) ^
*(u32 *)((u8 *)th2 + i);
- /* When we receive our second frame we can made a decision on if we
- * continue this flow as an atomic flow with a fixed ID or if we use
- * an incrementing ID.
- */
- if (NAPI_GRO_CB(p)->flush_id != 1 ||
- NAPI_GRO_CB(p)->count != 1 ||
- !NAPI_GRO_CB(p)->is_atomic)
- flush |= NAPI_GRO_CB(p)->flush_id;
- else
- NAPI_GRO_CB(p)->is_atomic = false;
-
mss = skb_shinfo(p)->gso_size;
flush |= (len - 1) >= mss;
@@ -318,9 +307,6 @@
iph->daddr, 0);
skb_shinfo(skb)->gso_type |= SKB_GSO_TCPV4;
- if (NAPI_GRO_CB(skb)->is_atomic)
- skb_shinfo(skb)->gso_type |= SKB_GSO_TCP_FIXEDID;
-
return tcp_gro_complete(skb);
}
diff --git a/net/ipv6/ip6_offload.c b/net/ipv6/ip6_offload.c
index 649f4d8..3cdf4dc 100644
--- a/net/ipv6/ip6_offload.c
+++ b/net/ipv6/ip6_offload.c
@@ -237,15 +237,8 @@
/* flush if Traffic Class fields are different */
NAPI_GRO_CB(p)->flush |= !!(first_word & htonl(0x0FF00000));
NAPI_GRO_CB(p)->flush |= flush;
-
- /* If the previous IP ID value was based on an atomic
- * datagram we can overwrite the value and ignore it.
- */
- if (NAPI_GRO_CB(skb)->is_atomic)
- NAPI_GRO_CB(p)->flush_id = 0;
}
- NAPI_GRO_CB(skb)->is_atomic = true;
NAPI_GRO_CB(skb)->flush |= flush;
skb_gro_postpull_rcsum(skb, iph, nlen);