diff options
author | Sankeerth Billakanti <sbillaka@codeaurora.org> | 2020-02-10 16:26:02 +0530 |
---|---|---|
committer | Sankeerth Billakanti <sbillaka@codeaurora.org> | 2020-02-18 15:08:53 +0530 |
commit | 3d076a474cc99e7ac6d687078bc3306729595103 (patch) | |
tree | e0f324b4afa5b58aa9b3cac279edd3d17ad15124 | |
parent | 174e74c85c2e168a4b9d30ac0bcd41a0e74eb9a1 (diff) | |
download | display-drivers-3d076a474cc99e7ac6d687078bc3306729595103.tar.gz |
disp: msm: dp: execute host_init on restoring session teardown
Ensure host_init is executed when the DP display driver is resuming
form a video session teardown. The host_deinit is executed when DP
video session teardown is initiated by the userspace while DP cable
is connected. If the DP display is disconnected from dongle while
the video session is in teardown, the host_init is not executed
when the session is restored. All subsequent display connections
will fail because the core clocks are not on and aux abort is not
reset.
This change will ensure host_init is executed whenever the
host_deinit is executed during DP video session teardown by userspace.
Change-Id: If1ae3eb731a96bd929cd023733c098b513436a1c
Signed-off-by: Sankeerth Billakanti <sbillaka@codeaurora.org>
-rw-r--r-- | msm/dp/dp_display.c | 43 |
1 files changed, 41 insertions, 2 deletions
diff --git a/msm/dp/dp_display.c b/msm/dp/dp_display.c index 33ba7b0b..ad30e03b 100644 --- a/msm/dp/dp_display.c +++ b/msm/dp/dp_display.c @@ -62,6 +62,7 @@ enum dp_display_states { DP_STATE_SUSPENDED = BIT(7), DP_STATE_ABORTED = BIT(8), DP_STATE_HDCP_ABORTED = BIT(9), + DP_STATE_SRC_PWRDN = BIT(10), }; static char *dp_display_state_name(enum dp_display_states state) @@ -111,6 +112,10 @@ static char *dp_display_state_name(enum dp_display_states state) len += scnprintf(buf + len, sizeof(buf) - len, "|%s|", "HDCP_ABORTED"); + if (state & DP_STATE_SRC_PWRDN) + len += scnprintf(buf + len, sizeof(buf) - len, "|%s|", + "SRC_PWRDN"); + if (!strlen(buf)) return "DISCONNECTED"; @@ -952,6 +957,26 @@ static int dp_display_process_hpd_high(struct dp_display_private *dp) dp->dp_display.max_pclk_khz = min(dp->parser->max_pclk_khz, dp->debug->max_pclk_khz); + + /* + * If dp video session is not restored from a previous session teardown + * by userspace, ensure the host_init is executed, in such a scenario, + * so that all the required DP resources are enabled. + * + * Below is one of the sequences of events which describe the above + * scenario: + * a. Source initiated power down resulting in host_deinit. + * b. Sink issues hpd low attention without physical cable disconnect. + * c. Source initiated power up sequence returns early because hpd is + * not high. + * d. Sink issues a hpd high attention event. + */ + if (dp_display_state_is(DP_STATE_SRC_PWRDN) && + dp_display_state_is(DP_STATE_CONFIGURED)) { + dp_display_host_init(dp); + dp_display_state_remove(DP_STATE_SRC_PWRDN); + } + dp_display_host_ready(dp); dp->link->psm_config(dp->link, &dp->panel->link_info, false); @@ -1227,7 +1252,6 @@ static int dp_display_usbpd_disconnect_cb(struct device *dev) SDE_EVT32_EXTERNAL(SDE_EVTLOG_FUNC_ENTRY, dp->state, dp->debug->psm_enabled); - dp_display_state_remove(DP_STATE_CONFIGURED); if (dp->debug->psm_enabled && dp_display_state_is(DP_STATE_READY)) dp->link->psm_config(dp->link, &dp->panel->link_info, true); @@ -1236,6 +1260,7 @@ static int dp_display_usbpd_disconnect_cb(struct device *dev) mutex_lock(&dp->session_lock); dp_display_host_deinit(dp); + dp_display_state_remove(DP_STATE_CONFIGURED); mutex_unlock(&dp->session_lock); if (!dp->debug->sim_mode && !dp->parser->no_aux_switch @@ -1784,6 +1809,20 @@ static int dp_display_prepare(struct dp_display *dp_display, void *panel) mutex_lock(&dp->session_lock); /* + * If DP video session is restored by the userspace after display + * disconnect notification from dongle i.e. typeC cable connected to + * source but disconnected at the display side, the DP controller is + * not restored to the desired configured state. So, ensure host_init + * is executed in such a scenario so that all the DP controller + * resources are enabled for the next connection event. + */ + if (dp_display_state_is(DP_STATE_SRC_PWRDN) && + dp_display_state_is(DP_STATE_CONFIGURED)) { + dp_display_host_init(dp); + dp_display_state_remove(DP_STATE_SRC_PWRDN); + } + + /* * If the physical connection to the sink is already lost by the time * we try to set up the connection, we can just skip all the steps * here safely. @@ -1808,7 +1847,6 @@ static int dp_display_prepare(struct dp_display *dp_display, void *panel) } /* For supporting DP_PANEL_SRC_INITIATED_POWER_DOWN case */ - dp_display_host_init(dp); dp_display_host_ready(dp); if (dp->debug->psm_enabled) { @@ -2223,6 +2261,7 @@ static int dp_display_unprepare(struct dp_display *dp_display, void *panel) dp->ctrl->off(dp->ctrl); dp_display_host_unready(dp); dp_display_host_deinit(dp); + dp_display_state_add(DP_STATE_SRC_PWRDN); } dp_display_state_remove(DP_STATE_ENABLED); |