diff options
22 files changed, 515 insertions, 105 deletions
diff --git a/Documentation/devicetree/bindings/pci/msm_pcie.txt b/Documentation/devicetree/bindings/pci/msm_pcie.txt index 4b5a6b4af789..8885f4ae80ad 100644 --- a/Documentation/devicetree/bindings/pci/msm_pcie.txt +++ b/Documentation/devicetree/bindings/pci/msm_pcie.txt @@ -110,6 +110,10 @@ Optional Properties: manager(scm) driver. scm driver uses this device id to restore PCIe controller related security configuration after coming out of the controller power collapse. + - resets: reset specifier pair consists of phandle for the reset controller + and reset lines used by this controller. + - reset-names: reset signal name strings sorted in the same order as the resets + property. Example: @@ -230,13 +234,21 @@ Example: <&clock_gcc clk_gcc_pcie_0_cfg_ahb_clk>, <&clock_gcc clk_gcc_pcie_0_mstr_axi_clk>, <&clock_gcc clk_gcc_pcie_0_slv_axi_clk>, - <&clock_gcc clk_pcie_0_phy_ldo>, - <&clock_gcc clk_gcc_pcie_phy_0_reset>; + <&clock_gcc clk_pcie_0_phy_ldo>; clock-names = "pcie_0_pipe_clk", "pcie_0_ref_clk_src", "pcie_0_aux_clk", "pcie_0_cfg_ahb_clk", "pcie_0_mstr_axi_clk", "pcie_0_slv_axi_clk", "pcie_0_ldo"; + + resets = <&clock_gcc GCC_PCIE_PHY_BCR>, + <&clock_gcc GCC_PCIE_PHY_COM_BCR>, + <&clock_gcc GCC_PCIE_PHY_NOCSR_COM_PHY_BCR>, + <&clock_gcc GCC_PCIE_0_PHY_BCR>; + + reset-names = "pcie_phy_reset", "pcie_phy_com_reset", + "pcie_phy_nocsr_com_phy_reset","pcie_0_phy_reset"; + max-clock-frequency-hz = <125000000>, <0>, <1000000>, <0>, <0>, <0>, <0>; qcom,l0s-supported; diff --git a/arch/arm/boot/dts/qcom/msm8996.dtsi b/arch/arm/boot/dts/qcom/msm8996.dtsi index 4b1b9796ebe6..dc1bbcd13c36 100644 --- a/arch/arm/boot/dts/qcom/msm8996.dtsi +++ b/arch/arm/boot/dts/qcom/msm8996.dtsi @@ -1394,18 +1394,20 @@ <&clock_gcc clk_gcc_pcie_clkref_clk>, <&clock_gcc clk_gcc_smmu_aggre0_axi_clk>, <&clock_gcc clk_gcc_pcie_phy_cfg_ahb_clk>, - <&clock_gcc clk_gcc_pcie_phy_aux_clk>, - <&clock_gcc clk_gcc_pcie_phy_reset>, - <&clock_gcc clk_gcc_pcie_phy_com_reset>, - <&clock_gcc clk_gcc_pcie_phy_nocsr_com_phy_reset>, - <&clock_gcc clk_gcc_pcie_0_phy_reset>; + <&clock_gcc clk_gcc_pcie_phy_aux_clk>; clock-names = "pcie_0_pipe_clk", "pcie_0_ref_clk_src", "pcie_0_aux_clk", "pcie_0_cfg_ahb_clk", "pcie_0_mstr_axi_clk", "pcie_0_slv_axi_clk", "pcie_0_ldo", "pcie_0_smmu_clk", - "pcie_phy_cfg_ahb_clk", "pcie_phy_aux_clk", "pcie_phy_reset", - "pcie_phy_com_reset", "pcie_phy_nocsr_com_phy_reset", - "pcie_0_phy_reset"; + "pcie_phy_cfg_ahb_clk", "pcie_phy_aux_clk"; + + resets = <&clock_gcc PCIE_PHY_BCR>, + <&clock_gcc PCIE_PHY_COM_BCR>, + <&clock_gcc PCIE_PHY_NOCSR_COM_PHY_BCR>, + <&clock_gcc PCIE_0_PHY_BCR>; + + reset-names = "pcie_phy_reset", "pcie_phy_com_reset", + "pcie_phy_nocsr_com_phy_reset","pcie_0_phy_reset"; max-clock-frequency-hz = <0>, <0>, <1010526>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>; @@ -1544,18 +1546,20 @@ <&clock_gcc clk_gcc_pcie_clkref_clk>, <&clock_gcc clk_gcc_smmu_aggre0_axi_clk>, <&clock_gcc clk_gcc_pcie_phy_cfg_ahb_clk>, - <&clock_gcc clk_gcc_pcie_phy_aux_clk>, - <&clock_gcc clk_gcc_pcie_phy_reset>, - <&clock_gcc clk_gcc_pcie_phy_com_reset>, - <&clock_gcc clk_gcc_pcie_phy_nocsr_com_phy_reset>, - <&clock_gcc clk_gcc_pcie_1_phy_reset>; + <&clock_gcc clk_gcc_pcie_phy_aux_clk>; clock-names = "pcie_1_pipe_clk", "pcie_1_ref_clk_src", "pcie_1_aux_clk", "pcie_1_cfg_ahb_clk", "pcie_1_mstr_axi_clk", "pcie_1_slv_axi_clk", "pcie_1_ldo", "pcie_1_smmu_clk", - "pcie_phy_cfg_ahb_clk", "pcie_phy_aux_clk", "pcie_phy_reset", - "pcie_phy_com_reset", "pcie_phy_nocsr_com_phy_reset", - "pcie_1_phy_reset"; + "pcie_phy_cfg_ahb_clk", "pcie_phy_aux_clk"; + + resets = <&clock_gcc PCIE_PHY_BCR>, + <&clock_gcc PCIE_PHY_COM_BCR>, + <&clock_gcc PCIE_PHY_NOCSR_COM_PHY_BCR>, + <&clock_gcc PCIE_1_PHY_BCR>; + + reset-names = "pcie_phy_reset", "pcie_phy_com_reset", + "pcie_phy_nocsr_com_phy_reset","pcie_1_phy_reset"; max-clock-frequency-hz = <0>, <0>, <1010526>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>; @@ -1698,18 +1702,20 @@ <&clock_gcc clk_gcc_pcie_clkref_clk>, <&clock_gcc clk_gcc_smmu_aggre0_axi_clk>, <&clock_gcc clk_gcc_pcie_phy_cfg_ahb_clk>, - <&clock_gcc clk_gcc_pcie_phy_aux_clk>, - <&clock_gcc clk_gcc_pcie_phy_reset>, - <&clock_gcc clk_gcc_pcie_phy_com_reset>, - <&clock_gcc clk_gcc_pcie_phy_nocsr_com_phy_reset>, - <&clock_gcc clk_gcc_pcie_2_phy_reset>; + <&clock_gcc clk_gcc_pcie_phy_aux_clk>; clock-names = "pcie_2_pipe_clk", "pcie_2_ref_clk_src", "pcie_2_aux_clk", "pcie_2_cfg_ahb_clk", "pcie_2_mstr_axi_clk", "pcie_2_slv_axi_clk", "pcie_2_ldo", "pcie_2_smmu_clk", - "pcie_phy_cfg_ahb_clk", "pcie_phy_aux_clk", "pcie_phy_reset", - "pcie_phy_com_reset", "pcie_phy_nocsr_com_phy_reset", - "pcie_2_phy_reset"; + "pcie_phy_cfg_ahb_clk", "pcie_phy_aux_clk"; + + resets = <&clock_gcc PCIE_PHY_BCR>, + <&clock_gcc PCIE_PHY_COM_BCR>, + <&clock_gcc PCIE_PHY_NOCSR_COM_PHY_BCR>, + <&clock_gcc PCIE_2_PHY_BCR>; + + reset-names = "pcie_phy_reset", "pcie_phy_com_reset", + "pcie_phy_nocsr_com_phy_reset","pcie_2_phy_reset"; max-clock-frequency-hz = <0>, <0>, <1010526>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>; diff --git a/arch/arm/boot/dts/qcom/msmcobalt-qrd-skuk.dtsi b/arch/arm/boot/dts/qcom/msmcobalt-qrd-skuk.dtsi index c028ea0eeab3..1ae0ab804eac 100644 --- a/arch/arm/boot/dts/qcom/msmcobalt-qrd-skuk.dtsi +++ b/arch/arm/boot/dts/qcom/msmcobalt-qrd-skuk.dtsi @@ -12,6 +12,7 @@ #include <dt-bindings/interrupt-controller/irq.h> #include "msmcobalt-pinctrl.dtsi" +#include "msmcobalt-audio.dtsi" &blsp1_uart3_hs { status = "ok"; @@ -99,4 +100,29 @@ debounce-interval = <15>; }; }; + + sound-tavil { + qcom,model = "msmcobalt-skuk-tavil-snd-card"; + + qcom,audio-routing = + "AIF4 VI", "MCLK", + "RX_BIAS", "MCLK", + "AMIC2", "MIC BIAS2", + "MIC BIAS2", "Headset Mic", + "DMIC0", "MIC BIAS1", + "MIC BIAS1", "Digital Mic0", + "DMIC1", "MIC BIAS1", + "MIC BIAS1", "Digital Mic1", + "DMIC2", "MIC BIAS3", + "MIC BIAS3", "Digital Mic2", + "DMIC4", "MIC BIAS4", + "MIC BIAS4", "Digital Mic4", + "SpkrLeft IN", "SPK1 OUT"; + + qcom,msm-mbhc-hphl-swh = <1>; + + qcom,wsa-max-devs = <1>; + qcom,wsa-devs = <&wsa881x_0211>, <&wsa881x_0213>; + qcom,wsa-aux-dev-prefix = "SpkrLeft", "SpkrLeft"; + }; }; diff --git a/arch/arm/boot/dts/qcom/msmcobalt.dtsi b/arch/arm/boot/dts/qcom/msmcobalt.dtsi index a16894dd4765..7f5f81eff9e5 100644 --- a/arch/arm/boot/dts/qcom/msmcobalt.dtsi +++ b/arch/arm/boot/dts/qcom/msmcobalt.dtsi @@ -1579,18 +1579,25 @@ <&clock_gcc clk_gcc_pcie_0_cfg_ahb_clk>, <&clock_gcc clk_gcc_pcie_0_mstr_axi_clk>, <&clock_gcc clk_gcc_pcie_0_slv_axi_clk>, - <&clock_gcc clk_gcc_pcie_clkref_clk>, - <&clock_gcc clk_gcc_pcie_phy_reset>; + <&clock_gcc clk_gcc_pcie_clkref_clk>; clock-names = "pcie_0_pipe_clk", "pcie_0_ref_clk_src", "pcie_0_aux_clk", "pcie_0_cfg_ahb_clk", "pcie_0_mstr_axi_clk", "pcie_0_slv_axi_clk", - "pcie_0_ldo", "pcie_0_phy_reset"; + "pcie_0_ldo"; max-clock-frequency-hz = <0>, <0>, <19200000>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>, <0>; + + resets = <&clock_gcc PCIE_PHY_BCR>, + <&clock_gcc PCIE_0_PHY_BCR>, + <&clock_gcc PCIE_0_PHY_BCR>; + + reset-names = "pcie_phy_reset", + "pcie_0_phy_reset", + "pcie_0_phy_pipe_reset"; }; qcom,ipc_router { diff --git a/drivers/media/platform/msm/sde/rotator/sde_rotator_core.c b/drivers/media/platform/msm/sde/rotator/sde_rotator_core.c index 3e5cbdecfba4..041a8219e145 100644 --- a/drivers/media/platform/msm/sde/rotator/sde_rotator_core.c +++ b/drivers/media/platform/msm/sde/rotator/sde_rotator_core.c @@ -278,6 +278,10 @@ static void sde_rotator_footswitch_ctrl(struct sde_rot_mgr *mgr, bool on) SDEROT_EVTLOG(on); SDEROT_DBG("%s: rotator regulators", on ? "Enable" : "Disable"); + + if (mgr->ops_hw_pre_pmevent) + mgr->ops_hw_pre_pmevent(mgr, on); + ret = sde_rot_enable_vreg(mgr->module_power.vreg_config, mgr->module_power.num_vreg, on); if (ret) { @@ -286,10 +290,13 @@ static void sde_rotator_footswitch_ctrl(struct sde_rot_mgr *mgr, bool on) return; } + if (mgr->ops_hw_post_pmevent) + mgr->ops_hw_post_pmevent(mgr, on); + mgr->regulator_enable = on; } -static int sde_rotator_clk_ctrl(struct sde_rot_mgr *mgr, int enable) +int sde_rotator_clk_ctrl(struct sde_rot_mgr *mgr, int enable) { struct clk *clk; int ret = 0; diff --git a/drivers/media/platform/msm/sde/rotator/sde_rotator_core.h b/drivers/media/platform/msm/sde/rotator/sde_rotator_core.h index 8659d361be07..aa17341de7c2 100644 --- a/drivers/media/platform/msm/sde/rotator/sde_rotator_core.h +++ b/drivers/media/platform/msm/sde/rotator/sde_rotator_core.h @@ -293,6 +293,8 @@ struct sde_rot_mgr { void (*ops_hw_free)(struct sde_rot_mgr *mgr, struct sde_rot_hw_resource *hw); int (*ops_hw_init)(struct sde_rot_mgr *mgr); + void (*ops_hw_pre_pmevent)(struct sde_rot_mgr *mgr, bool pmon); + void (*ops_hw_post_pmevent)(struct sde_rot_mgr *mgr, bool pmon); void (*ops_hw_destroy)(struct sde_rot_mgr *mgr); ssize_t (*ops_hw_show_caps)(struct sde_rot_mgr *mgr, struct device_attribute *attr, char *buf, ssize_t len); @@ -405,6 +407,8 @@ int sde_rotator_validate_request(struct sde_rot_mgr *rot_dev, struct sde_rot_file_private *ctx, struct sde_rot_entry_container *req); +int sde_rotator_clk_ctrl(struct sde_rot_mgr *mgr, int enable); + static inline void sde_rot_mgr_lock(struct sde_rot_mgr *mgr) { mutex_lock(&mgr->lock); diff --git a/drivers/media/platform/msm/sde/rotator/sde_rotator_r3.c b/drivers/media/platform/msm/sde/rotator/sde_rotator_r3.c index e9d2dd5ec972..d2bc76874c48 100644 --- a/drivers/media/platform/msm/sde/rotator/sde_rotator_r3.c +++ b/drivers/media/platform/msm/sde/rotator/sde_rotator_r3.c @@ -271,6 +271,7 @@ static int sde_hw_rotator_pending_swts(struct sde_hw_rotator *rot, SDEROT_DBG("ts:0x%x, queue_id:%d, swts:0x%x, pending:%d\n", ctx->timestamp, ctx->q_id, swts, pending); + SDEROT_EVTLOG(ctx->timestamp, swts, ctx->q_id, ts_diff); return pending; } @@ -1240,6 +1241,94 @@ static void sde_hw_rotator_swtc_destroy(struct sde_hw_rotator *rot) } /* + * sde_hw_rotator_pre_pmevent - SDE rotator core will call this before a + * PM event occurs + * @mgr: Pointer to rotator manager + * @pmon: Boolean indicate an on/off power event + */ +void sde_hw_rotator_pre_pmevent(struct sde_rot_mgr *mgr, bool pmon) +{ + struct sde_hw_rotator *rot; + u32 l_ts, h_ts, swts, hwts; + u32 rotsts, regdmasts; + + /* + * Check last HW timestamp with SW timestamp before power off event. + * If there is a mismatch, that will be quite possible the rotator HW + * is either hang or not finishing last submitted job. In that case, + * it is best to do a timeout eventlog to capture some good events + * log data for analysis. + */ + if (!pmon && mgr && mgr->hw_data) { + rot = mgr->hw_data; + h_ts = atomic_read(&rot->timestamp[ROT_QUEUE_HIGH_PRIORITY]); + l_ts = atomic_read(&rot->timestamp[ROT_QUEUE_LOW_PRIORITY]); + + /* contruct the combined timstamp */ + swts = (h_ts & SDE_REGDMA_SWTS_MASK) | + ((l_ts & SDE_REGDMA_SWTS_MASK) << + SDE_REGDMA_SWTS_SHIFT); + + /* Need to turn on clock to access rotator register */ + sde_rotator_clk_ctrl(mgr, true); + hwts = SDE_ROTREG_READ(rot->mdss_base, REGDMA_TIMESTAMP_REG); + regdmasts = SDE_ROTREG_READ(rot->mdss_base, + REGDMA_CSR_REGDMA_BLOCK_STATUS); + rotsts = SDE_ROTREG_READ(rot->mdss_base, ROTTOP_STATUS); + + SDEROT_DBG( + "swts:0x%x, hwts:0x%x, regdma-sts:0x%x, rottop-sts:0x%x\n", + swts, hwts, regdmasts, rotsts); + SDEROT_EVTLOG(swts, hwts, regdmasts, rotsts); + + if ((swts != hwts) && ((regdmasts & REGDMA_BUSY) || + (rotsts & ROT_STATUS_MASK))) { + SDEROT_ERR( + "Mismatch SWTS with HWTS: swts:0x%x, hwts:0x%x, regdma-sts:0x%x, rottop-sts:0x%x\n", + swts, hwts, regdmasts, rotsts); + SDEROT_EVTLOG_TOUT_HANDLER("rot", "vbif_dbg_bus", + "panic"); + } + + /* Turn off rotator clock after checking rotator registers */ + sde_rotator_clk_ctrl(mgr, false); + } +} + +/* + * sde_hw_rotator_post_pmevent - SDE rotator core will call this after a + * PM event occurs + * @mgr: Pointer to rotator manager + * @pmon: Boolean indicate an on/off power event + */ +void sde_hw_rotator_post_pmevent(struct sde_rot_mgr *mgr, bool pmon) +{ + struct sde_hw_rotator *rot; + u32 l_ts, h_ts, swts; + + /* + * After a power on event, the rotator HW is reset to default setting. + * It is necessary to synchronize the SW timestamp with the HW. + */ + if (pmon && mgr && mgr->hw_data) { + rot = mgr->hw_data; + h_ts = atomic_read(&rot->timestamp[ROT_QUEUE_HIGH_PRIORITY]); + l_ts = atomic_read(&rot->timestamp[ROT_QUEUE_LOW_PRIORITY]); + + /* contruct the combined timstamp */ + swts = (h_ts & SDE_REGDMA_SWTS_MASK) | + ((l_ts & SDE_REGDMA_SWTS_MASK) << + SDE_REGDMA_SWTS_SHIFT); + + SDEROT_DBG("swts:0x%x, h_ts:0x%x, l_ts;0x%x\n", + swts, h_ts, l_ts); + SDEROT_EVTLOG(swts, h_ts, l_ts); + rot->reset_hw_ts = true; + rot->last_hw_ts = swts; + } +} + +/* * sde_hw_rotator_destroy - Destroy hw rotator and free allocated resources * @mgr: Pointer to rotator manager */ @@ -1455,6 +1544,15 @@ static int sde_hw_rotator_config(struct sde_rot_hw_resource *hw, return -EINVAL; } + if (rot->reset_hw_ts) { + SDEROT_EVTLOG(rot->last_hw_ts); + SDE_ROTREG_WRITE(rot->mdss_base, REGDMA_TIMESTAMP_REG, + rot->last_hw_ts); + /* ensure write is issued to the rotator HW */ + wmb(); + rot->reset_hw_ts = false; + } + flags = (item->flags & SDE_ROTATION_FLIP_LR) ? SDE_ROT_FLAG_FLIP_LR : 0; flags |= (item->flags & SDE_ROTATION_FLIP_UD) ? @@ -1511,7 +1609,8 @@ static int sde_hw_rotator_config(struct sde_rot_hw_resource *hw, &entry->dst_buf); } - SDEROT_EVTLOG(flags, item->input.width, item->input.height, + SDEROT_EVTLOG(ctx->timestamp, flags, + item->input.width, item->input.height, item->output.width, item->output.height, entry->src_buf.p[0].addr, entry->dst_buf.p[0].addr); @@ -1715,6 +1814,7 @@ static int sde_rotator_hw_rev_init(struct sde_hw_rotator *rot) mdata->regdump = sde_rot_r3_regdump; mdata->regdump_size = ARRAY_SIZE(sde_rot_r3_regdump); + SDE_ROTREG_WRITE(rot->mdss_base, REGDMA_TIMESTAMP_REG, 0); return 0; } @@ -2174,6 +2274,8 @@ int sde_rotator_r3_init(struct sde_rot_mgr *mgr) mgr->ops_hw_create_debugfs = sde_rotator_r3_create_debugfs; mgr->ops_hw_get_pixfmt = sde_hw_rotator_get_pixfmt; mgr->ops_hw_is_valid_pixfmt = sde_hw_rotator_is_valid_pixfmt; + mgr->ops_hw_pre_pmevent = sde_hw_rotator_pre_pmevent; + mgr->ops_hw_post_pmevent = sde_hw_rotator_post_pmevent; ret = sde_hw_rotator_parse_dt(mgr->hw_data, mgr->pdev); if (ret) diff --git a/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_hwio.h b/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_hwio.h index 3267e4418b3a..a748b87a231a 100644 --- a/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_hwio.h +++ b/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_hwio.h @@ -250,9 +250,10 @@ /* General defines */ #define ROT_DONE_MASK 0x1 #define ROT_DONE_CLEAR 0x1 -#define ROT_BUSY_BIT BIT(1) +#define ROT_BUSY_BIT BIT(0) #define ROT_ERROR_BIT BIT(8) #define ROT_STATUS_MASK (ROT_BUSY_BIT | ROT_ERROR_BIT) +#define REGDMA_BUSY BIT(0) #define REGDMA_EN 0x1 #define REGDMA_SECURE_EN BIT(8) #define REGDMA_HALT BIT(16) diff --git a/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_internal.h b/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_internal.h index b95f838f463b..91ac3d0371fa 100644 --- a/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_internal.h +++ b/drivers/media/platform/msm/sde/rotator/sde_rotator_r3_internal.h @@ -270,6 +270,8 @@ struct sde_hw_rotator { spinlock_t rotisr_lock; bool dbgmem; + bool reset_hw_ts; + u32 last_hw_ts; }; /** diff --git a/drivers/mfd/wcd9xxx-core.c b/drivers/mfd/wcd9xxx-core.c index 981d372277ee..5bcd0db929b3 100644 --- a/drivers/mfd/wcd9xxx-core.c +++ b/drivers/mfd/wcd9xxx-core.c @@ -1219,6 +1219,11 @@ static int wcd9xxx_slim_probe(struct slim_device *slim) intf_type = wcd9xxx_get_intf_type(); + if (!slim) { + ret = -EINVAL; + goto err; + } + if (intf_type == WCD9XXX_INTERFACE_TYPE_I2C) { dev_dbg(&slim->dev, "%s:Codec is detected in I2C mode\n", __func__); diff --git a/drivers/pci/host/pci-msm.c b/drivers/pci/host/pci-msm.c index 2909443a62ca..87f4b641201c 100644 --- a/drivers/pci/host/pci-msm.c +++ b/drivers/pci/host/pci-msm.c @@ -31,6 +31,7 @@ #include <linux/types.h> #include <linux/of_gpio.h> #include <linux/clk/msm-clk.h> +#include <linux/reset.h> #include <linux/msm-bus.h> #include <linux/msm-bus-board.h> #include <linux/debugfs.h> @@ -298,7 +299,7 @@ #define MAX_PROP_SIZE 32 #define MAX_RC_NAME_LEN 15 #define MSM_PCIE_MAX_VREG 4 -#define MSM_PCIE_MAX_CLK 13 +#define MSM_PCIE_MAX_CLK 9 #define MSM_PCIE_MAX_PIPE_CLK 1 #define MAX_RC_NUM 3 #define MAX_DEVICE_NUM 20 @@ -312,6 +313,9 @@ #define PCIE_CLEAR 0xDEADBEEF #define PCIE_LINK_DOWN 0xFFFFFFFF +#define MSM_PCIE_MAX_RESET 4 +#define MSM_PCIE_MAX_PIPE_RESET 1 + #define MSM_PCIE_MSI_PHY 0xa0000000 #define PCIE20_MSI_CTRL_ADDR (0x820) #define PCIE20_MSI_CTRL_UPPER_ADDR (0x824) @@ -496,6 +500,13 @@ struct msm_pcie_vreg_info_t { bool required; }; +/* reset info structure */ +struct msm_pcie_reset_info_t { + struct reset_control *hdl; + char *name; + bool required; +}; + /* clock info structure */ struct msm_pcie_clk_info_t { struct clk *hdl; @@ -552,6 +563,8 @@ struct msm_pcie_dev_t { struct msm_pcie_res_info_t res[MSM_PCIE_MAX_RES]; struct msm_pcie_irq_info_t irq[MSM_PCIE_MAX_IRQ]; struct msm_pcie_irq_info_t msi[MSM_PCIE_MAX_MSI]; + struct msm_pcie_reset_info_t reset[MSM_PCIE_MAX_RESET]; + struct msm_pcie_reset_info_t pipe_reset[MSM_PCIE_MAX_PIPE_RESET]; void __iomem *parf; void __iomem *phy; @@ -707,6 +720,43 @@ static struct msm_pcie_gpio_info_t msm_pcie_gpio_info[MSM_PCIE_MAX_GPIO] = { {"qcom,ep-gpio", 0, 1, 1, 0, 0} }; +/* resets */ +static struct msm_pcie_reset_info_t +msm_pcie_reset_info[MAX_RC_NUM][MSM_PCIE_MAX_RESET] = { + { + {NULL, "pcie_phy_reset", false}, + {NULL, "pcie_phy_com_reset", false}, + {NULL, "pcie_phy_nocsr_com_phy_reset", false}, + {NULL, "pcie_0_phy_reset", false} + }, + { + {NULL, "pcie_phy_reset", false}, + {NULL, "pcie_phy_com_reset", false}, + {NULL, "pcie_phy_nocsr_com_phy_reset", false}, + {NULL, "pcie_1_phy_reset", false} + }, + { + {NULL, "pcie_phy_reset", false}, + {NULL, "pcie_phy_com_reset", false}, + {NULL, "pcie_phy_nocsr_com_phy_reset", false}, + {NULL, "pcie_2_phy_reset", false} + } +}; + +/* pipe reset */ +static struct msm_pcie_reset_info_t +msm_pcie_pipe_reset_info[MAX_RC_NUM][MSM_PCIE_MAX_PIPE_RESET] = { + { + {NULL, "pcie_0_phy_pipe_reset", false} + }, + { + {NULL, "pcie_1_phy_pipe_reset", false} + }, + { + {NULL, "pcie_2_phy_pipe_reset", false} + } +}; + /* clocks */ static struct msm_pcie_clk_info_t msm_pcie_clk_info[MAX_RC_NUM][MSM_PCIE_MAX_CLK] = { @@ -719,11 +769,7 @@ static struct msm_pcie_clk_info_t {NULL, "pcie_0_ldo", 0, false, true}, {NULL, "pcie_0_smmu_clk", 0, false, false}, {NULL, "pcie_phy_cfg_ahb_clk", 0, false, false}, - {NULL, "pcie_phy_aux_clk", 0, false, false}, - {NULL, "pcie_phy_reset", 0, false, false}, - {NULL, "pcie_phy_com_reset", 0, false, false}, - {NULL, "pcie_phy_nocsr_com_phy_reset", 0, false, false}, - {NULL, "pcie_0_phy_reset", 0, false, true} + {NULL, "pcie_phy_aux_clk", 0, false, false} }, { {NULL, "pcie_1_ref_clk_src", 0, false, false}, @@ -734,11 +780,7 @@ static struct msm_pcie_clk_info_t {NULL, "pcie_1_ldo", 0, false, true}, {NULL, "pcie_1_smmu_clk", 0, false, false}, {NULL, "pcie_phy_cfg_ahb_clk", 0, false, false}, - {NULL, "pcie_phy_aux_clk", 0, false, false}, - {NULL, "pcie_phy_reset", 0, false, false}, - {NULL, "pcie_phy_com_reset", 0, false, false}, - {NULL, "pcie_phy_nocsr_com_phy_reset", 0, false, false}, - {NULL, "pcie_1_phy_reset", 0, false, true} + {NULL, "pcie_phy_aux_clk", 0, false, false} }, { {NULL, "pcie_2_ref_clk_src", 0, false, false}, @@ -749,11 +791,7 @@ static struct msm_pcie_clk_info_t {NULL, "pcie_2_ldo", 0, false, true}, {NULL, "pcie_2_smmu_clk", 0, false, false}, {NULL, "pcie_phy_cfg_ahb_clk", 0, false, false}, - {NULL, "pcie_phy_aux_clk", 0, false, false}, - {NULL, "pcie_phy_reset", 0, false, false}, - {NULL, "pcie_phy_com_reset", 0, false, false}, - {NULL, "pcie_phy_nocsr_com_phy_reset", 0, false, false}, - {NULL, "pcie_2_phy_reset", 0, false, true} + {NULL, "pcie_phy_aux_clk", 0, false, false} } }; @@ -3431,6 +3469,7 @@ static int msm_pcie_clk_init(struct msm_pcie_dev_t *dev) { int i, rc = 0; struct msm_pcie_clk_info_t *info; + struct msm_pcie_reset_info_t *reset_info; PCIE_DBG(dev, "RC%d: entry\n", dev->rc_idx); @@ -3474,9 +3513,6 @@ static int msm_pcie_clk_init(struct msm_pcie_dev_t *dev) if (!info->hdl) continue; - if (i >= MSM_PCIE_MAX_CLK - (dev->common_phy ? 4 : 1)) - clk_reset(info->hdl, CLK_RESET_DEASSERT); - if (info->config_mem) msm_pcie_config_clock_mem(dev, info); @@ -3519,6 +3555,21 @@ static int msm_pcie_clk_init(struct msm_pcie_dev_t *dev) regulator_disable(dev->gdsc); } + for (i = 0; i < MSM_PCIE_MAX_RESET; i++) { + reset_info = &dev->reset[i]; + if (reset_info->hdl) { + rc = reset_control_deassert(reset_info->hdl); + if (rc) + PCIE_ERR(dev, + "PCIe: RC%d failed to deassert reset for %s.\n", + dev->rc_idx, reset_info->name); + else + PCIE_DBG2(dev, + "PCIe: RC%d successfully deasserted reset for %s.\n", + dev->rc_idx, reset_info->name); + } + } + PCIE_DBG(dev, "RC%d: exit\n", dev->rc_idx); return rc; @@ -3562,6 +3613,7 @@ static int msm_pcie_pipe_clk_init(struct msm_pcie_dev_t *dev) { int i, rc = 0; struct msm_pcie_clk_info_t *info; + struct msm_pcie_reset_info_t *pipe_reset_info; PCIE_DBG(dev, "RC%d: entry\n", dev->rc_idx); @@ -3571,7 +3623,6 @@ static int msm_pcie_pipe_clk_init(struct msm_pcie_dev_t *dev) if (!info->hdl) continue; - clk_reset(info->hdl, CLK_RESET_DEASSERT); if (info->config_mem) msm_pcie_config_clock_mem(dev, info); @@ -3608,6 +3659,22 @@ static int msm_pcie_pipe_clk_init(struct msm_pcie_dev_t *dev) clk_disable_unprepare(dev->pipeclk[i].hdl); } + for (i = 0; i < MSM_PCIE_MAX_PIPE_RESET; i++) { + pipe_reset_info = &dev->pipe_reset[i]; + if (pipe_reset_info->hdl) { + rc = reset_control_deassert( + pipe_reset_info->hdl); + if (rc) + PCIE_ERR(dev, + "PCIe: RC%d failed to deassert pipe reset for %s.\n", + dev->rc_idx, pipe_reset_info->name); + else + PCIE_DBG2(dev, + "PCIe: RC%d successfully deasserted pipe reset for %s.\n", + dev->rc_idx, pipe_reset_info->name); + } + } + PCIE_DBG(dev, "RC%d: exit\n", dev->rc_idx); return rc; @@ -3945,6 +4012,8 @@ static int msm_pcie_get_resources(struct msm_pcie_dev_t *dev, struct msm_pcie_res_info_t *res_info; struct msm_pcie_irq_info_t *irq_info; struct msm_pcie_irq_info_t *msi_info; + struct msm_pcie_reset_info_t *reset_info; + struct msm_pcie_reset_info_t *pipe_reset_info; char prop_name[MAX_PROP_SIZE]; const __be32 *prop; u32 *clkfreq = NULL; @@ -4161,6 +4230,54 @@ static int msm_pcie_get_resources(struct msm_pcie_dev_t *dev, } } + for (i = 0; i < MSM_PCIE_MAX_RESET; i++) { + reset_info = &dev->reset[i]; + + reset_info->hdl = devm_reset_control_get(&pdev->dev, + reset_info->name); + + if (IS_ERR(reset_info->hdl)) { + if (reset_info->required) { + PCIE_DBG(dev, + "Reset %s isn't available:%ld\n", + reset_info->name, + PTR_ERR(reset_info->hdl)); + + ret = PTR_ERR(reset_info->hdl); + reset_info->hdl = NULL; + goto out; + } else { + PCIE_DBG(dev, "Ignoring Reset %s\n", + reset_info->name); + reset_info->hdl = NULL; + } + } + } + + for (i = 0; i < MSM_PCIE_MAX_PIPE_RESET; i++) { + pipe_reset_info = &dev->pipe_reset[i]; + + pipe_reset_info->hdl = devm_reset_control_get(&pdev->dev, + pipe_reset_info->name); + + if (IS_ERR(pipe_reset_info->hdl)) { + if (pipe_reset_info->required) { + PCIE_DBG(dev, + "Pipe Reset %s isn't available:%ld\n", + pipe_reset_info->name, + PTR_ERR(pipe_reset_info->hdl)); + + ret = PTR_ERR(pipe_reset_info->hdl); + pipe_reset_info->hdl = NULL; + goto out; + } else { + PCIE_DBG(dev, "Ignoring Pipe Reset %s\n", + pipe_reset_info->name); + pipe_reset_info->hdl = NULL; + } + } + } + dev->bus_scale_table = msm_bus_cl_get_pdata(pdev); if (!dev->bus_scale_table) { PCIE_DBG(dev, "PCIe: No bus scale table for RC%d (%s)\n", @@ -6052,6 +6169,11 @@ static int msm_pcie_probe(struct platform_device *pdev) sizeof(msm_pcie_irq_info)); memcpy(msm_pcie_dev[rc_idx].msi, msm_pcie_msi_info, sizeof(msm_pcie_msi_info)); + memcpy(msm_pcie_dev[rc_idx].reset, msm_pcie_reset_info[rc_idx], + sizeof(msm_pcie_reset_info[rc_idx])); + memcpy(msm_pcie_dev[rc_idx].pipe_reset, + msm_pcie_pipe_reset_info[rc_idx], + sizeof(msm_pcie_pipe_reset_info[rc_idx])); msm_pcie_dev[rc_idx].shadow_en = true; for (i = 0; i < PCIE_CONF_SPACE_DW; i++) msm_pcie_dev[rc_idx].rc_shadow[i] = PCIE_CLEAR; diff --git a/drivers/soc/qcom/subsystem_restart.c b/drivers/soc/qcom/subsystem_restart.c index 6cfb8f7c836c..015e60ac622c 100644 --- a/drivers/soc/qcom/subsystem_restart.c +++ b/drivers/soc/qcom/subsystem_restart.c @@ -572,25 +572,6 @@ static void disable_all_irqs(struct subsys_device *dev) } } -int wait_for_shutdown_ack(struct subsys_desc *desc) -{ - int count; - - if (desc && !desc->shutdown_ack_gpio) - return 0; - - for (count = SHUTDOWN_ACK_MAX_LOOPS; count > 0; count--) { - if (gpio_get_value(desc->shutdown_ack_gpio)) - return count; - msleep(SHUTDOWN_ACK_DELAY_MS); - } - - pr_err("[%s]: Timed out waiting for shutdown ack\n", desc->name); - - return -ETIMEDOUT; -} -EXPORT_SYMBOL(wait_for_shutdown_ack); - static int wait_for_err_ready(struct subsys_device *subsys) { int ret; @@ -768,6 +749,31 @@ int subsystem_set_fwname(const char *name, const char *fw_name) } EXPORT_SYMBOL(subsystem_set_fwname); +int wait_for_shutdown_ack(struct subsys_desc *desc) +{ + int count; + struct subsys_device *dev; + + if (!desc || !desc->shutdown_ack_gpio) + return 0; + + dev = find_subsys(desc->name); + if (!dev) + return 0; + + for (count = SHUTDOWN_ACK_MAX_LOOPS; count > 0; count--) { + if (gpio_get_value(desc->shutdown_ack_gpio)) + return count; + else if (subsys_get_crash_status(dev)) + break; + msleep(SHUTDOWN_ACK_DELAY_MS); + } + + pr_err("[%s]: Timed out waiting for shutdown ack\n", desc->name); + return -ETIMEDOUT; +} +EXPORT_SYMBOL(wait_for_shutdown_ack); + void *__subsystem_get(const char *name, const char *fw_name) { struct subsys_device *subsys; diff --git a/drivers/usb/dwc3/core.c b/drivers/usb/dwc3/core.c index 7585c603cb3d..9fb05bbf3e74 100644 --- a/drivers/usb/dwc3/core.c +++ b/drivers/usb/dwc3/core.c @@ -155,6 +155,7 @@ static int dwc3_init_usb_phys(struct dwc3 *dwc) static int dwc3_core_reset(struct dwc3 *dwc) { int ret; + u32 reg; /* Reset PHYs */ usb_phy_reset(dwc->usb2_phy); @@ -168,6 +169,10 @@ static int dwc3_core_reset(struct dwc3 *dwc) return ret; } + reg = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0)); + reg &= ~DWC3_GUSB3PIPECTL_DELAYP1TRANS; + dwc3_writel(dwc->regs, DWC3_GUSB3PIPECTL(0), reg); + dwc3_notify_event(dwc, DWC3_CONTROLLER_RESET_EVENT); dwc3_notify_event(dwc, DWC3_CONTROLLER_POST_RESET_EVENT); diff --git a/drivers/usb/gadget/composite.c b/drivers/usb/gadget/composite.c index a99405261306..a480b0a9a238 100644 --- a/drivers/usb/gadget/composite.c +++ b/drivers/usb/gadget/composite.c @@ -35,9 +35,10 @@ (speed == USB_SPEED_SUPER ?\ SSUSB_GADGET_VBUS_DRAW : CONFIG_USB_GADGET_VBUS_DRAW) -static bool enable_l1_for_hs; -module_param(enable_l1_for_hs, bool, S_IRUGO | S_IWUSR); -MODULE_PARM_DESC(enable_l1_for_hs, "Enable support for L1 LPM for HS devices"); +static bool disable_l1_for_hs; +module_param(disable_l1_for_hs, bool, S_IRUGO | S_IWUSR); +MODULE_PARM_DESC(disable_l1_for_hs, + "Disable support for L1 LPM for HS devices"); /** * struct usb_os_string - represents OS String to be reported by a gadget @@ -1637,13 +1638,12 @@ composite_setup(struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl) if (gadget->speed >= USB_SPEED_SUPER) { cdev->desc.bcdUSB = cpu_to_le16(0x0310); cdev->desc.bMaxPacketSize0 = 9; - } else if (gadget->l1_supported || - enable_l1_for_hs) { + } else if (!disable_l1_for_hs) { cdev->desc.bcdUSB = cpu_to_le16(0x0210); DBG(cdev, "Config HS device with LPM(L1)\n"); } - } else if (gadget->l1_supported) { + } else if (!disable_l1_for_hs) { cdev->desc.bcdUSB = cpu_to_le16(0x0210); DBG(cdev, "Config HS device with LPM(L1)\n"); } @@ -1678,7 +1678,7 @@ composite_setup(struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl) case USB_DT_BOS: if ((gadget_is_superspeed(gadget) && (gadget->speed >= USB_SPEED_SUPER)) - || gadget->l1_supported) { + || !disable_l1_for_hs) { value = bos_desc(cdev); value = min(w_length, (u16) value); } @@ -1963,6 +1963,8 @@ unknown: break; case USB_RECIP_ENDPOINT: + if (!cdev->config) + break; endp = ((w_index & 0x80) >> 3) | (w_index & 0x0f); list_for_each_entry(f, &cdev->config->functions, list) { if (test_bit(endp, f->endpoints)) diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c index c5fd3ce3ed9a..fd2157c8e8c2 100644 --- a/drivers/usb/gadget/function/f_fs.c +++ b/drivers/usb/gadget/function/f_fs.c @@ -2275,7 +2275,7 @@ static int __ffs_do_os_desc_header(enum ffs_os_desc_type *next_type, return -EINVAL; } - ffs_log("exit: size of desc %lu", sizeof(*desc)); + ffs_log("exit: size of desc %zu", sizeof(*desc)); return sizeof(*desc); } diff --git a/drivers/usb/gadget/function/f_gsi.h b/drivers/usb/gadget/function/f_gsi.h index d56012779c78..d489e453594a 100644 --- a/drivers/usb/gadget/function/f_gsi.h +++ b/drivers/usb/gadget/function/f_gsi.h @@ -35,9 +35,9 @@ #define GSI_CTRL_DTR (1 << 0) -#define GSI_NUM_IN_BUFFERS 7 +#define GSI_NUM_IN_BUFFERS 15 #define GSI_IN_BUFF_SIZE 2048 -#define GSI_NUM_OUT_BUFFERS 7 +#define GSI_NUM_OUT_BUFFERS 15 #define GSI_ECM_NUM_OUT_BUFFERS 31 #define GSI_OUT_AGGR_SIZE 24576 diff --git a/drivers/usb/pd/policy_engine.c b/drivers/usb/pd/policy_engine.c index 1bb7082be8e6..82ae0b4fe135 100644 --- a/drivers/usb/pd/policy_engine.c +++ b/drivers/usb/pd/policy_engine.c @@ -925,7 +925,8 @@ int usbpd_send_vdm(struct usbpd *pd, u32 vdm_hdr, const u32 *vdos, int num_vdos) return -ENOMEM; vdm_tx->data[0] = vdm_hdr; - memcpy(&vdm_tx->data[1], vdos, num_vdos * sizeof(u32)); + if (vdos && num_vdos) + memcpy(&vdm_tx->data[1], vdos, num_vdos * sizeof(u32)); vdm_tx->size = num_vdos + 1; /* include the header */ /* VDM will get sent in PE_SRC/SNK_READY state handling */ diff --git a/drivers/usb/pd/qpnp-pdphy.c b/drivers/usb/pd/qpnp-pdphy.c index 8cf294306efd..5b5e6210a1bb 100644 --- a/drivers/usb/pd/qpnp-pdphy.c +++ b/drivers/usb/pd/qpnp-pdphy.c @@ -445,8 +445,10 @@ int pd_phy_write(u16 hdr, const u8 *data, size_t data_len, dev_dbg(pdphy->dev, "%s: hdr %x frame type %d timeout %u\n", __func__, hdr, type, timeout_ms); - print_hex_dump_debug("tx data obj:", DUMP_PREFIX_NONE, 32, 4, - data, data_len, false); + + if (data && data_len) + print_hex_dump_debug("tx data obj:", DUMP_PREFIX_NONE, 32, 4, + data, data_len, false); if (!pdphy) { pr_err("%s: pdphy not found\n", __func__); @@ -472,7 +474,7 @@ int pd_phy_write(u16 hdr, const u8 *data, size_t data_len, if (ret) return ret; - if (data_len) { + if (data && data_len) { /* write data objects of SOP message */ ret = pdphy_bulk_reg_write(pdphy, USB_PDPHY_TX_BUFFER_DATA, data, data_len); diff --git a/drivers/usb/phy/phy-msm-qusb-v2.c b/drivers/usb/phy/phy-msm-qusb-v2.c index 4ecdc350fbd4..5a768ee4d061 100644 --- a/drivers/usb/phy/phy-msm-qusb-v2.c +++ b/drivers/usb/phy/phy-msm-qusb-v2.c @@ -63,6 +63,7 @@ #define LINESTATE_DM BIT(1) #define QUSB2PHY_PLL_ANALOG_CONTROLS_ONE 0x0 +#define QUSB2PHY_PLL_ANALOG_CONTROLS_TWO 0x4 unsigned int phy_tune1; module_param(phy_tune1, uint, S_IRUGO | S_IWUSR); @@ -541,6 +542,7 @@ static int qusb_phy_set_suspend(struct usb_phy *phy, int suspend) { struct qusb_phy *qphy = container_of(phy, struct qusb_phy, phy); u32 linestate = 0, intr_mask = 0; + static u8 analog_ctrl_two; int ret; if (qphy->suspended && suspend) { @@ -554,6 +556,14 @@ static int qusb_phy_set_suspend(struct usb_phy *phy, int suspend) if (qphy->cable_connected || (qphy->phy.flags & PHY_HOST_MODE)) { + /* store clock settings like cmos/cml */ + analog_ctrl_two = + readl_relaxed(qphy->base + + QUSB2PHY_PLL_ANALOG_CONTROLS_TWO); + + writel_relaxed(0x1b, + qphy->base + QUSB2PHY_PLL_ANALOG_CONTROLS_TWO); + /* enable clock bypass */ writel_relaxed(0x90, qphy->base + QUSB2PHY_PLL_ANALOG_CONTROLS_ONE); @@ -599,6 +609,9 @@ static int qusb_phy_set_suspend(struct usb_phy *phy, int suspend) dev_err(phy->dev, "%s: phy_reset deassert failed\n", __func__); + writel_relaxed(0x1b, + qphy->base + QUSB2PHY_PLL_ANALOG_CONTROLS_TWO); + /* enable clock bypass */ writel_relaxed(0x90, qphy->base + QUSB2PHY_PLL_ANALOG_CONTROLS_ONE); @@ -620,6 +633,10 @@ static int qusb_phy_set_suspend(struct usb_phy *phy, int suspend) (qphy->phy.flags & PHY_HOST_MODE)) { qusb_phy_enable_clocks(qphy, true); + /* restore the default clock settings */ + writel_relaxed(analog_ctrl_two, + qphy->base + QUSB2PHY_PLL_ANALOG_CONTROLS_TWO); + /* disable clock bypass */ writel_relaxed(0x80, qphy->base + QUSB2PHY_PLL_ANALOG_CONTROLS_ONE); @@ -639,12 +656,17 @@ static int qusb_phy_set_suspend(struct usb_phy *phy, int suspend) */ wmb(); + qusb_phy_enable_power(qphy, true, true); + ret = reset_control_assert(qphy->phy_reset); + if (ret) + dev_err(phy->dev, "%s: phy_reset assert failed\n", + __func__); + usleep_range(100, 150); ret = reset_control_deassert(qphy->phy_reset); if (ret) dev_err(phy->dev, "%s: phy_reset deassert failed\n", __func__); - qusb_phy_enable_power(qphy, true, true); qusb_phy_enable_clocks(qphy, true); } qphy->suspended = false; diff --git a/drivers/video/fbdev/msm/mdss_mdp_ctl.c b/drivers/video/fbdev/msm/mdss_mdp_ctl.c index abc048866313..5b43453cc002 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_ctl.c +++ b/drivers/video/fbdev/msm/mdss_mdp_ctl.c @@ -2040,12 +2040,11 @@ static u64 mdss_mdp_ctl_calc_client_vote(struct mdss_data_type *mdata, return bw_sum_of_intfs; } -static void mdss_mdp_ctl_update_client_vote(struct mdss_data_type *mdata, +/* apply any adjustments to the ib quota */ +static inline u64 __calc_bus_ib_quota(struct mdss_data_type *mdata, struct mdss_mdp_perf_params *perf, bool nrt_client, u64 bw_vote) { - u64 bus_ab_quota, bus_ib_quota; - - bus_ab_quota = max(bw_vote, mdata->perf_tune.min_bus_vote); + u64 bus_ib_quota; if (test_bit(MDSS_QOS_PER_PIPE_IB, mdata->mdss_qos_map)) { if (!nrt_client) @@ -2071,6 +2070,18 @@ static void mdss_mdp_ctl_update_client_vote(struct mdss_data_type *mdata, bus_ib_quota = apply_fudge_factor(bus_ib_quota, &mdata->per_pipe_ib_factor); + return bus_ib_quota; +} + +static void mdss_mdp_ctl_update_client_vote(struct mdss_data_type *mdata, + struct mdss_mdp_perf_params *perf, bool nrt_client, u64 bw_vote) +{ + u64 bus_ab_quota, bus_ib_quota; + + bus_ab_quota = max(bw_vote, mdata->perf_tune.min_bus_vote); + bus_ib_quota = __calc_bus_ib_quota(mdata, perf, nrt_client, bw_vote); + + bus_ab_quota = apply_fudge_factor(bus_ab_quota, &mdss_res->ab_factor); ATRACE_INT("bus_quota", bus_ib_quota); @@ -2232,6 +2243,46 @@ static bool is_traffic_shaper_enabled(struct mdss_data_type *mdata) return false; } +static bool __mdss_mdp_compare_bw( + struct mdss_mdp_ctl *ctl, + struct mdss_mdp_perf_params *new_perf, + struct mdss_mdp_perf_params *old_perf, + bool params_changed, + bool stop_req) +{ + struct mdss_data_type *mdata = ctl->mdata; + bool is_nrt = mdss_mdp_is_nrt_ctl_path(ctl); + u64 new_ib = + __calc_bus_ib_quota(mdata, new_perf, is_nrt, new_perf->bw_ctl); + u64 old_ib = + __calc_bus_ib_quota(mdata, old_perf, is_nrt, old_perf->bw_ctl); + u64 max_new_bw = max(new_perf->bw_ctl, new_ib); + u64 max_old_bw = max(old_perf->bw_ctl, old_ib); + bool update_bw = false; + + /* + * three cases for bus bandwidth update. + * 1. new bandwidth vote (ab or ib) or writeback output vote + * are higher than current vote for update request. + * 2. new bandwidth vote or writeback output vote are + * lower than current vote at end of commit or stop. + * 3. end of writeback/rotator session - last chance to + * non-realtime remove vote. + */ + if ((params_changed && ((max_new_bw > max_old_bw) || /* ab and ib bw */ + (new_perf->bw_writeback > old_perf->bw_writeback))) || + (!params_changed && ((max_new_bw < max_old_bw) || + (new_perf->bw_writeback < old_perf->bw_writeback))) || + (stop_req && is_nrt)) + update_bw = true; + + trace_mdp_compare_bw(new_perf->bw_ctl, new_ib, new_perf->bw_writeback, + max_new_bw, old_perf->bw_ctl, old_ib, old_perf->bw_writeback, + max_old_bw, params_changed, update_bw); + + return update_bw; +} + static void mdss_mdp_ctl_perf_update(struct mdss_mdp_ctl *ctl, int params_changed, bool stop_req) { @@ -2267,20 +2318,8 @@ static void mdss_mdp_ctl_perf_update(struct mdss_mdp_ctl *ctl, else if (is_bw_released || params_changed) mdss_mdp_perf_calc_ctl(ctl, new); - /* - * three cases for bus bandwidth update. - * 1. new bandwidth vote or writeback output vote - * are higher than current vote for update request. - * 2. new bandwidth vote or writeback output vote are - * lower than current vote at end of commit or stop. - * 3. end of writeback/rotator session - last chance to - * non-realtime remove vote. - */ - if ((params_changed && ((new->bw_ctl > old->bw_ctl) || - (new->bw_writeback > old->bw_writeback))) || - (!params_changed && ((new->bw_ctl < old->bw_ctl) || - (new->bw_writeback < old->bw_writeback))) || - (stop_req && mdss_mdp_is_nrt_ctl_path(ctl))) { + if (__mdss_mdp_compare_bw(ctl, new, old, params_changed, + stop_req)) { pr_debug("c=%d p=%d new_bw=%llu,old_bw=%llu\n", ctl->num, params_changed, new->bw_ctl, diff --git a/drivers/video/fbdev/msm/mdss_mdp_trace.h b/drivers/video/fbdev/msm/mdss_mdp_trace.h index 85829fbba075..648e4fcd1cd2 100644 --- a/drivers/video/fbdev/msm/mdss_mdp_trace.h +++ b/drivers/video/fbdev/msm/mdss_mdp_trace.h @@ -295,6 +295,46 @@ TRACE_EVENT(mdp_perf_update_bus, __entry->ib_quota) ); +TRACE_EVENT(mdp_compare_bw, + TP_PROTO(unsigned long long new_ab, unsigned long long new_ib, + unsigned long long new_wb, unsigned long long new_max, + unsigned long long old_ab, unsigned long long old_ib, + unsigned long long old_wb, unsigned long long old_max, + u32 params_changed, bool update_bw), + TP_ARGS(new_ab, new_ib, new_wb, new_max, + old_ab, old_ib, old_wb, old_max, + params_changed, update_bw), + TP_STRUCT__entry( + __field(u64, new_ab) + __field(u64, new_ib) + __field(u64, new_wb) + __field(u64, new_max) + __field(u64, old_ab) + __field(u64, old_ib) + __field(u64, old_wb) + __field(u64, old_max) + __field(u32, params_changed) + __field(bool, update_bw) + ), + TP_fast_assign( + __entry->new_ab = new_ab; + __entry->new_ib = new_ib; + __entry->new_wb = new_wb; + __entry->new_max = new_max; + __entry->old_ab = old_ab; + __entry->old_ib = old_ib; + __entry->old_wb = old_wb; + __entry->old_max = old_max; + __entry->params_changed = params_changed; + __entry->update_bw = update_bw; + ), + TP_printk("[ab,ib,wb,max] new[%llu, %llu, %llu, %llu] old[%llu, %llu, %llu, %llu] parm:%d ret:%d", + __entry->new_ab, __entry->new_ib, __entry->new_wb, + __entry->new_max, __entry->old_ab, __entry->old_ib, + __entry->old_wb, __entry->old_max, __entry->params_changed, + __entry->update_bw) +); + TRACE_EVENT(mdp_misr_crc, TP_PROTO(u32 block_id, u32 vsync_cnt, u32 crc), TP_ARGS(block_id, vsync_cnt, crc), diff --git a/include/linux/usb/gadget.h b/include/linux/usb/gadget.h index 2c64620254eb..143e556f141d 100644 --- a/include/linux/usb/gadget.h +++ b/include/linux/usb/gadget.h @@ -752,7 +752,6 @@ struct usb_gadget { unsigned is_selfpowered:1; unsigned deactivated:1; unsigned connected:1; - bool l1_supported; bool remote_wakeup; }; #define work_to_gadget(w) (container_of((w), struct usb_gadget, work)) |
