Merge "ARM/dts: Set ref clock to 24MHz for msm8974"
diff --git a/arch/arm/boot/dts/msm8226.dtsi b/arch/arm/boot/dts/msm8226.dtsi
index 993da79..2599c46 100644
--- a/arch/arm/boot/dts/msm8226.dtsi
+++ b/arch/arm/boot/dts/msm8226.dtsi
@@ -1061,7 +1061,7 @@
< 300000 1525 >,
< 384000 1525 >,
< 600000 1525 >,
- < 787200 3051 >,
+ < 787200 1525 >,
< 998400 4066 >,
< 1094400 4066 >,
< 1190400 4066 >,
diff --git a/arch/arm/boot/dts/msm8926-v2.dtsi b/arch/arm/boot/dts/msm8926-v2.dtsi
index 1322573..c443ba6 100644
--- a/arch/arm/boot/dts/msm8926-v2.dtsi
+++ b/arch/arm/boot/dts/msm8926-v2.dtsi
@@ -66,6 +66,22 @@
};
};
+&soc {
+ mem_acc_vreg_corner: regulator@fd4aa044 {
+ compatible = "qcom,mem-acc-regulator";
+ reg = <0xfd4aa048 0x4>, <0xfd4aa044 0x4>, <0xfd4af000 0x4>;
+ reg-names = "acc-en", "acc-sel-l1", "acc-sel-l2";
+ regulator-name = "mem_acc_corner";
+ regulator-min-microvolt = <1>;
+ regulator-max-microvolt = <3>;
+
+ qcom,acc-en-bit-pos = <0>;
+ qcom,acc-sel-l1-bit-pos = <0>;
+ qcom,acc-sel-l2-bit-pos = <0>;
+ qcom,corner-acc-map = <0 1 3>;
+ };
+};
+
&pm8226_l3 {
regulator-max-microvolt = <1287500>;
};
@@ -90,4 +106,5 @@
qcom,vdd-mx-vmax = <1287500>;
qcom,vdd-mx-vmin-method = <4>;
qcom,vdd-mx-corner-map = <1050000 1150000 1280000>;
+ mem-acc-supply = <&mem_acc_vreg_corner>;
};
diff --git a/arch/arm/boot/dts/msm8974pro-ac-pma8084-pm8941.dtsi b/arch/arm/boot/dts/msm8974pro-ac-pma8084-pm8941.dtsi
index d745524..d679880 100644
--- a/arch/arm/boot/dts/msm8974pro-ac-pma8084-pm8941.dtsi
+++ b/arch/arm/boot/dts/msm8974pro-ac-pma8084-pm8941.dtsi
@@ -241,6 +241,11 @@
vadc@3100 {
interrupts = <0x2 0x31 0x0>;
interrupt-names = "eoc-int-en-set";
+ /delete-node/ chan@b3;
+ /delete-node/ chan@b4;
+ /delete-node/ chan@b5;
+ /delete-node/ chan@b7;
+ /delete-node/ chan@b8;
};
iadc@3600 {
@@ -255,5 +260,9 @@
interrupt-names = "eoc-int-en-set",
"high-thr-en-set",
"low-thr-en-set";
+ /delete-node/ chan@b3;
+ /delete-node/ chan@b4;
+ /delete-node/ chan@b5;
+ /delete-node/ chan@b7;
};
};
diff --git a/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c b/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c
index 3976436..0ea4a9a 100644
--- a/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c
+++ b/drivers/media/platform/msm/camera_v2/isp/msm_isp_axi_util.c
@@ -1086,8 +1086,8 @@
if (num_pix_streams > 0)
total_pix_bandwidth = total_pix_bandwidth /
num_pix_streams * (num_pix_streams - 1) +
- axi_data->src_info[VFE_PIX_0].pixel_clock *
- ISP_DEFAULT_FORMAT_FACTOR / ISP_Q2;
+ ((unsigned long)axi_data->src_info[VFE_PIX_0].
+ pixel_clock) * ISP_DEFAULT_FORMAT_FACTOR / ISP_Q2;
total_bandwidth = total_pix_bandwidth + total_rdi_bandwidth;
rc = msm_isp_update_bandwidth(ISP_VFE0 + vfe_dev->pdev->id,
diff --git a/drivers/mmc/core/cd-gpio.c b/drivers/mmc/core/cd-gpio.c
index 45ec5c2..9d813e9 100644
--- a/drivers/mmc/core/cd-gpio.c
+++ b/drivers/mmc/core/cd-gpio.c
@@ -19,8 +19,8 @@
struct mmc_cd_gpio {
unsigned int gpio;
- char label[0];
bool status;
+ char label[0];
};
static int mmc_cd_get_status(struct mmc_host *host)
diff --git a/drivers/video/msm/mdss/mdss_mdp.h b/drivers/video/msm/mdss/mdss_mdp.h
index 025713d..1613757 100644
--- a/drivers/video/msm/mdss/mdss_mdp.h
+++ b/drivers/video/msm/mdss/mdss_mdp.h
@@ -75,6 +75,13 @@
#define MDSS_MDP_REG_WRITE(addr, val) MDSS_REG_WRITE((u32)(addr), (u32)(val))
#define MDSS_MDP_REG_READ(addr) MDSS_REG_READ((u32)(addr))
#endif
+#define PERF_STATUS_DONE 0
+#define PERF_STATUS_BUSY 1
+
+enum mdss_mdp_perf_state_type {
+ PERF_SW_COMMIT_STATE = 0,
+ PERF_HW_MDP_STATE,
+};
enum mdss_mdp_block_power_state {
MDP_BLOCK_POWER_OFF = 0,
@@ -180,7 +187,7 @@
int force_screen_state;
struct mdss_mdp_perf_params cur_perf;
struct mdss_mdp_perf_params new_perf;
- int perf_status;
+ u32 perf_transaction_status;
struct mdss_data_type *mdata;
struct msm_fb_data_type *mfd;
@@ -565,8 +572,8 @@
int mdss_mdp_scan_pipes(void);
-void mdss_mdp_ctl_perf_taken(struct mdss_mdp_ctl *ctl);
-void mdss_mdp_ctl_perf_done(struct mdss_mdp_ctl *ctl);
+void mdss_mdp_ctl_perf_set_transaction_status(struct mdss_mdp_ctl *ctl,
+ enum mdss_mdp_perf_state_type component, bool new_status);
void mdss_mdp_ctl_perf_release_bw(struct mdss_mdp_ctl *ctl);
struct mdss_mdp_mixer *mdss_mdp_wb_mixer_alloc(int rotator);
diff --git a/drivers/video/msm/mdss/mdss_mdp_ctl.c b/drivers/video/msm/mdss/mdss_mdp_ctl.c
index 92c787b..ecea64e 100644
--- a/drivers/video/msm/mdss/mdss_mdp_ctl.c
+++ b/drivers/video/msm/mdss/mdss_mdp_ctl.c
@@ -704,79 +704,103 @@
perf->bw_overlap, perf->bw_prefill, perf->prefill_bytes);
}
-static bool mdss_mdp_ctl_perf_bw_released(struct mdss_mdp_ctl *ctl)
+static void set_status(u32 *value, bool status, u32 bit_num)
{
- unsigned long flags;
- bool released = false;
-
- if (!ctl || !ctl->panel_data ||
- (ctl->panel_data->panel_info.type != MIPI_CMD_PANEL))
- return released;
-
- spin_lock_irqsave(&ctl->spin_lock, flags);
- if (ctl->perf_status == 0) {
- released = true;
- ctl->perf_status++;
- } else if (ctl->perf_status <= 2) {
- ctl->perf_status++;
- } else {
- pr_err("pervious commit was not done\n");
- }
-
- pr_debug("perf_status=%d\n", ctl->perf_status);
- spin_unlock_irqrestore(&ctl->spin_lock, flags);
-
- return released;
+ if (status)
+ *value |= BIT(bit_num);
+ else
+ *value &= ~BIT(bit_num);
}
/**
- * @mdss_mdp_ctl_perf_taken() - indicates a committed buffer is taken
- * by h/w
- * @ctl - pointer to ctl data structure
- *
- * A committed buffer to be displayed is taken at a vsync or reader
- * pointer interrupt by h/w. This function must be called in vsync
- * interrupt context to indicate the buf status is changed.
- */
-void mdss_mdp_ctl_perf_taken(struct mdss_mdp_ctl *ctl)
-{
- if (!ctl || !ctl->panel_data ||
- (ctl->panel_data->panel_info.type != MIPI_CMD_PANEL))
- return;
-
- spin_lock(&ctl->spin_lock);
- if (ctl->perf_status)
- ctl->perf_status++;
- pr_debug("perf_status=%d\n", ctl->perf_status);
- spin_unlock(&ctl->spin_lock);
-}
-
-/**
- * @mdss_mdp_ctl_perf_done() - indicates a committed buffer is
- * displayed, so resources such as
- * bandwidth that are associated to this
- * buffer can be released.
+ * @ mdss_mdp_ctl_perf_set_transaction_status() -
+ * Set the status of the on-going operations
+ * for the command mode panels.
* @ctl - pointer to a ctl
*
- * When pingping done interrupt is trigged, mdp finishes displaying a
- * buffer which was committed by user and taken by h/w and calling
- * this function to clear those two states. This function must be
- * called in pinppong done interrupt context.
+ * This function is called to set the status bit in the perf_transaction_status
+ * according to the operation that it is on-going for the command mode
+ * panels, where:
+ *
+ * PERF_SW_COMMIT_STATE:
+ * 1 - If SW operation has been commited and bw
+ * has been requested (HW transaction have not started yet).
+ * 0 - If there is no SW operation pending
+ * PERF_HW_MDP_STATE:
+ * 1 - If HW transaction is on-going
+ * 0 - If there is no HW transaction on going (ping-pong interrupt
+ * has finished)
+ * Only if both states are zero there are no pending operations and
+ * BW could be released.
+ * State can be queried calling "mdss_mdp_ctl_perf_get_transaction_status"
*/
-void mdss_mdp_ctl_perf_done(struct mdss_mdp_ctl *ctl)
+void mdss_mdp_ctl_perf_set_transaction_status(struct mdss_mdp_ctl *ctl,
+ enum mdss_mdp_perf_state_type component, bool new_status)
{
+ u32 previous_transaction;
+ bool previous_status;
+ unsigned long flags;
+
if (!ctl || !ctl->panel_data ||
(ctl->panel_data->panel_info.type != MIPI_CMD_PANEL))
return;
- spin_lock(&ctl->spin_lock);
- if (ctl->perf_status) {
- ctl->perf_status--;
- if (ctl->perf_status)
- ctl->perf_status--;
+ spin_lock_irqsave(&ctl->spin_lock, flags);
+
+ previous_transaction = ctl->perf_transaction_status;
+ previous_status = previous_transaction & BIT(component) ?
+ PERF_STATUS_BUSY : PERF_STATUS_DONE;
+
+ /*
+ * If we set "done" state when previous state was not "busy",
+ * we want to print a warning since maybe there is a state
+ * that we are not considering
+ */
+ WARN((PERF_STATUS_DONE == new_status) &&
+ (PERF_STATUS_BUSY != previous_status),
+ "unexpected previous state for component: %d\n", component);
+
+ set_status(&ctl->perf_transaction_status, new_status,
+ (u32)component);
+
+ pr_debug("component:%d previous_transaction:%d transaction_status:%d\n",
+ component, previous_transaction, ctl->perf_transaction_status);
+ pr_debug("new_status:%d prev_status:%d\n",
+ new_status, previous_status);
+
+ spin_unlock_irqrestore(&ctl->spin_lock, flags);
+}
+
+/**
+ * @ mdss_mdp_ctl_perf_get_transaction_status() -
+ * Get the status of the on-going operations
+ * for the command mode panels.
+ * @ctl - pointer to a ctl
+ *
+ * Return:
+ * The status of the transactions for the command mode panels,
+ * note that the bandwidth can be released only if all transaction
+ * status bits are zero.
+ */
+u32 mdss_mdp_ctl_perf_get_transaction_status(struct mdss_mdp_ctl *ctl)
+{
+ unsigned long flags;
+ u32 transaction_status;
+
+ /*
+ * If Video Mode or not valid data to determine the status, return busy
+ * status, so the bandwidth cannot be freed by the caller
+ */
+ if (!ctl || !ctl->panel_data ||
+ (ctl->panel_data->panel_info.type != MIPI_CMD_PANEL)) {
+ return PERF_STATUS_BUSY;
}
- pr_debug("perf_status=%d\n", ctl->perf_status);
- spin_unlock(&ctl->spin_lock);
+
+ spin_lock_irqsave(&ctl->spin_lock, flags);
+ transaction_status = ctl->perf_transaction_status;
+ spin_unlock_irqrestore(&ctl->spin_lock, flags);
+
+ return transaction_status;
}
static inline void mdss_mdp_ctl_perf_update_bus(struct mdss_mdp_ctl *ctl)
@@ -810,13 +834,12 @@
* @ctl - pointer to a ctl
*
* Function checks a state variable for the ctl, if all pending commit
- * requests are done, meanning no more bandwidth is needed, release
+ * requests are done, meaning no more bandwidth is needed, release
* bandwidth request.
*/
void mdss_mdp_ctl_perf_release_bw(struct mdss_mdp_ctl *ctl)
{
- unsigned long flags;
- int need_release = 0;
+ int transaction_status;
struct mdss_data_type *mdata;
int i;
@@ -834,23 +857,21 @@
for (i = 0; i < mdata->nctl; i++) {
struct mdss_mdp_ctl *ctl = mdata->ctl_off + i;
- if (ctl->power_on && ctl->is_video_mode) {
- mutex_unlock(&mdss_mdp_ctl_lock);
- return;
- }
+ if (ctl->power_on && ctl->is_video_mode)
+ goto exit;
}
- spin_lock_irqsave(&ctl->spin_lock, flags);
- if (!ctl->perf_status)
- need_release = 1;
- pr_debug("need release=%d\n", need_release);
- spin_unlock_irqrestore(&ctl->spin_lock, flags);
+ transaction_status = mdss_mdp_ctl_perf_get_transaction_status(ctl);
+ pr_debug("transaction_status=0x%x\n", transaction_status);
- if (need_release) {
+ /*Release the bandwidth only if there are no transactions pending*/
+ if (!transaction_status) {
ctl->cur_perf.bw_ctl = 0;
ctl->new_perf.bw_ctl = 0;
+ pr_debug("Release BW ctl=%d\n", ctl->num);
mdss_mdp_ctl_perf_update_bus(ctl);
}
+exit:
mutex_unlock(&mdss_mdp_ctl_lock);
}
@@ -860,6 +881,7 @@
struct mdss_mdp_perf_params *new, *old;
int update_bus = 0, update_clk = 0;
struct mdss_data_type *mdata;
+ bool is_bw_released;
if (!ctl || !ctl->mdata)
return;
@@ -870,8 +892,14 @@
old = &ctl->cur_perf;
new = &ctl->new_perf;
+ /*
+ * We could have released the bandwidth if there were no transactions
+ * pending, so we want to re-calculate the bandwidth in this situation
+ */
+ is_bw_released = !mdss_mdp_ctl_perf_get_transaction_status(ctl);
+
if (ctl->power_on) {
- if (params_changed || mdss_mdp_ctl_perf_bw_released(ctl))
+ if (is_bw_released || params_changed)
mdss_mdp_perf_calc_ctl(ctl, new);
/*
* if params have just changed delay the update until
@@ -1623,11 +1651,13 @@
{
u32 temp;
+ mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_ON, false);
temp = readl_relaxed(ctl->mdata->mdp_base +
MDSS_MDP_REG_DISP_INTF_SEL);
temp |= (ctl->intf_type << ((ctl->intf_num - MDSS_MDP_INTF0) * 8));
writel_relaxed(temp, ctl->mdata->mdp_base +
MDSS_MDP_REG_DISP_INTF_SEL);
+ mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_OFF, false);
}
static int mdss_mdp_ctl_start_sub(struct mdss_mdp_ctl *ctl, bool handoff)
@@ -2450,6 +2480,7 @@
struct mdss_mdp_ctl *sctl = NULL;
int mixer1_changed, mixer2_changed;
int ret = 0;
+ bool is_bw_released;
if (!ctl) {
pr_err("display function not set\n");
@@ -2471,7 +2502,15 @@
mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_ON, false);
- if (mixer1_changed || mixer2_changed
+ /*
+ * We could have released the bandwidth if there were no transactions
+ * pending, so we want to re-calculate the bandwidth in this situation
+ */
+ is_bw_released = !mdss_mdp_ctl_perf_get_transaction_status(ctl);
+ mdss_mdp_ctl_perf_set_transaction_status(ctl, PERF_SW_COMMIT_STATE,
+ PERF_STATUS_BUSY);
+
+ if (is_bw_released || mixer1_changed || mixer2_changed
|| ctl->force_screen_state) {
if (ctl->prepare_fnc)
ret = ctl->prepare_fnc(ctl, arg);
diff --git a/drivers/video/msm/mdss/mdss_mdp_intf_cmd.c b/drivers/video/msm/mdss/mdss_mdp_intf_cmd.c
index 58e8762..0d1bae8 100644
--- a/drivers/video/msm/mdss/mdss_mdp_intf_cmd.c
+++ b/drivers/video/msm/mdss/mdss_mdp_intf_cmd.c
@@ -274,8 +274,6 @@
return;
}
- mdss_mdp_ctl_perf_taken(ctl);
-
vsync_time = ktime_get();
ctl->vsync_cnt++;
MDSS_XLOG(ctl->num, ctx->koff_cnt, ctx->clk_enabled,
@@ -343,7 +341,8 @@
return;
}
- mdss_mdp_ctl_perf_done(ctl);
+ mdss_mdp_ctl_perf_set_transaction_status(ctl,
+ PERF_HW_MDP_STATE, PERF_STATUS_DONE);
spin_lock(&ctx->clk_lock);
list_for_each_entry(tmp, &ctx->vsync_handlers, list) {
@@ -591,6 +590,9 @@
return -ENODEV;
}
+ mdss_mdp_ctl_perf_set_transaction_status(ctl,
+ PERF_HW_MDP_STATE, PERF_STATUS_BUSY);
+
if (ctx->panel_on == 0) {
rc = mdss_mdp_ctl_intf_event(ctl, MDSS_EVENT_UNBLANK, NULL);
WARN(rc, "intf %d unblank error (%d)\n", ctl->intf_num, rc);
@@ -620,6 +622,8 @@
INIT_COMPLETION(ctx->pp_comp);
mdss_mdp_irq_enable(MDSS_MDP_IRQ_PING_PONG_COMP, ctx->pp_num);
mdss_mdp_ctl_write(ctl, MDSS_MDP_REG_CTL_START, 1);
+ mdss_mdp_ctl_perf_set_transaction_status(ctl,
+ PERF_SW_COMMIT_STATE, PERF_STATUS_DONE);
mb();
MDSS_XLOG(ctl->num, ctx->koff_cnt, ctx->clk_enabled,
ctx->rdptr_enabled);
diff --git a/sound/soc/codecs/wcd9xxx-mbhc.c b/sound/soc/codecs/wcd9xxx-mbhc.c
index 0abd123..b2ec347 100644
--- a/sound/soc/codecs/wcd9xxx-mbhc.c
+++ b/sound/soc/codecs/wcd9xxx-mbhc.c
@@ -3441,7 +3441,8 @@
* wcd9xxx_update_rel_threshold : update mbhc release upper bound threshold
* to ceilmv + buffer
*/
-static int wcd9xxx_update_rel_threshold(struct wcd9xxx_mbhc *mbhc, int ceilmv)
+static int wcd9xxx_update_rel_threshold(struct wcd9xxx_mbhc *mbhc, int ceilmv,
+ bool vddio)
{
u16 v_brh, v_b1_hu;
int mv;
@@ -3451,6 +3452,8 @@
btn_det = WCD9XXX_MBHC_CAL_BTN_DET_PTR(calibration);
mv = ceilmv + btn_det->v_btn_press_delta_cic;
+ if (vddio)
+ mv = scale_v_micb_vddio(mbhc, mv, true);
pr_debug("%s: reprogram vb1hu/vbrh to %dmv\n", __func__, mv);
if (mbhc->mbhc_state != MBHC_STATE_POTENTIAL_RECOVERY) {
@@ -3651,7 +3654,7 @@
MBHC_BTN_DET_V_BTN_HIGH);
WARN_ON(btn >= btn_det->num_btn);
/* reprogram release threshold to catch voltage ramp up early */
- wcd9xxx_update_rel_threshold(mbhc, v_btn_high[btn]);
+ wcd9xxx_update_rel_threshold(mbhc, v_btn_high[btn], vddio);
mask = wcd9xxx_get_button_mask(btn);
mbhc->buttons_pressed |= mask;