disp: msm: sde: modify in_clone_mode after wb_reset is done
Add changes to modify the phys_enc->in_clone_mode variable post wb_reset_state since this is a shared variable used during atomic_check and atomic_commit. In current issue case, wb_atomic_check has set in_clone_mode to true in commit N, and in commit N-1 CWB is being disabled and re-sets the in_clone_mode variable to false causing pp_done timeouts in primary in commit N. Change-Id: I8159bbdb5622a351d76bdc4dba75d48df20f4365 Signed-off-by: Jayaprakash Madisetty <jmadiset@codeaurora.org> Signed-off-by: Samantha Tran <samtran@codeaurora.org>
This commit is contained in:

committed by
Samantha Tran

parent
7d0890d337
commit
436efb403c
@@ -549,7 +549,7 @@ static bool sde_crtc_mode_fixup(struct drm_crtc *crtc,
|
||||
|
||||
drm_for_each_encoder_mask(encoder, c_state->crtc->dev,
|
||||
c_state->encoder_mask) {
|
||||
if (!sde_encoder_in_clone_mode(encoder)) {
|
||||
if (!sde_crtc_state_in_clone_mode(encoder, c_state)) {
|
||||
encoder_valid = true;
|
||||
break;
|
||||
}
|
||||
@@ -868,7 +868,7 @@ static int _sde_crtc_set_crtc_roi(struct drm_crtc *crtc,
|
||||
* This restriction should be relaxed when Connector ROI scaling is
|
||||
* supported and while in clone mode.
|
||||
*/
|
||||
if (!sde_encoder_in_clone_mode(sde_conn->encoder) &&
|
||||
if (!sde_crtc_state_in_clone_mode(sde_conn->encoder, state) &&
|
||||
is_conn_roi_dirty != is_crtc_roi_dirty) {
|
||||
SDE_ERROR("connector/crtc rois not updated together\n");
|
||||
return -EINVAL;
|
||||
@@ -2549,7 +2549,7 @@ void sde_crtc_prepare_commit(struct drm_crtc *crtc,
|
||||
dev = crtc->dev;
|
||||
sde_crtc = to_sde_crtc(crtc);
|
||||
cstate = to_sde_crtc_state(crtc->state);
|
||||
SDE_EVT32_VERBOSE(DRMID(crtc));
|
||||
SDE_EVT32_VERBOSE(DRMID(crtc), cstate->cwb_enc_mask);
|
||||
|
||||
SDE_ATRACE_BEGIN("sde_crtc_prepare_commit");
|
||||
|
||||
@@ -2569,6 +2569,7 @@ void sde_crtc_prepare_commit(struct drm_crtc *crtc,
|
||||
|
||||
cstate->connectors[cstate->num_connectors++] = conn;
|
||||
sde_connector_prepare_fence(conn);
|
||||
sde_encoder_set_clone_mode(encoder, crtc->state);
|
||||
}
|
||||
drm_connector_list_iter_end(&conn_iter);
|
||||
|
||||
@@ -2631,7 +2632,7 @@ enum sde_intf_mode sde_crtc_get_intf_mode(struct drm_crtc *crtc,
|
||||
drm_for_each_encoder_mask(encoder, crtc->dev,
|
||||
cstate->encoder_mask) {
|
||||
/* continue if copy encoder is encountered */
|
||||
if (sde_encoder_in_clone_mode(encoder))
|
||||
if (sde_crtc_state_in_clone_mode(encoder, cstate))
|
||||
continue;
|
||||
|
||||
return sde_encoder_get_intf_mode(encoder);
|
||||
|
@@ -466,6 +466,7 @@ enum sde_crtc_dirty_flags {
|
||||
* @property_values: Current crtc property values
|
||||
* @input_fence_timeout_ns : Cached input fence timeout, in ns
|
||||
* @num_dim_layers: Number of dim layers
|
||||
* @cwb_enc_mask : encoder mask populated during atomic_check if CWB is enabled
|
||||
* @dim_layer: Dim layer configs
|
||||
* @num_ds: Number of destination scalers to be configured
|
||||
* @num_ds_enabled: Number of destination scalers enabled
|
||||
@@ -501,6 +502,7 @@ struct sde_crtc_state {
|
||||
DECLARE_BITMAP(dirty, SDE_CRTC_DIRTY_MAX);
|
||||
uint64_t input_fence_timeout_ns;
|
||||
uint32_t num_dim_layers;
|
||||
uint32_t cwb_enc_mask;
|
||||
struct sde_hw_dim_layer dim_layer[SDE_MAX_DIM_LAYERS];
|
||||
uint32_t num_ds;
|
||||
uint32_t num_ds_enabled;
|
||||
@@ -880,6 +882,22 @@ static inline bool sde_crtc_atomic_check_has_modeset(
|
||||
return (crtc_state && drm_atomic_crtc_needs_modeset(crtc_state));
|
||||
}
|
||||
|
||||
static inline bool sde_crtc_state_in_clone_mode(struct drm_encoder *encoder,
|
||||
struct drm_crtc_state *state)
|
||||
{
|
||||
struct sde_crtc_state *cstate;
|
||||
|
||||
if (!state || !encoder)
|
||||
return false;
|
||||
|
||||
cstate = to_sde_crtc_state(state);
|
||||
if (sde_encoder_in_clone_mode(encoder) ||
|
||||
(cstate->cwb_enc_mask & drm_encoder_mask(encoder)))
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* sde_crtc_get_secure_transition - determines the operations to be
|
||||
* performed before transitioning to secure state
|
||||
|
@@ -849,6 +849,36 @@ bool sde_encoder_is_cwb_disabling(struct drm_encoder *drm_enc,
|
||||
return false;
|
||||
}
|
||||
|
||||
void sde_encoder_set_clone_mode(struct drm_encoder *drm_enc,
|
||||
struct drm_crtc_state *crtc_state)
|
||||
{
|
||||
struct sde_encoder_virt *sde_enc;
|
||||
struct sde_crtc_state *sde_crtc_state;
|
||||
int i = 0;
|
||||
|
||||
if (!drm_enc || !crtc_state) {
|
||||
SDE_DEBUG("invalid params\n");
|
||||
return;
|
||||
}
|
||||
sde_enc = to_sde_encoder_virt(drm_enc);
|
||||
sde_crtc_state = to_sde_crtc_state(crtc_state);
|
||||
|
||||
if ((sde_enc->disp_info.intf_type != DRM_MODE_CONNECTOR_VIRTUAL) ||
|
||||
(!(sde_crtc_state->cwb_enc_mask & drm_encoder_mask(drm_enc))))
|
||||
return;
|
||||
|
||||
for (i = 0; i < sde_enc->num_phys_encs; i++) {
|
||||
struct sde_encoder_phys *phys = sde_enc->phys_encs[i];
|
||||
|
||||
if (phys) {
|
||||
phys->in_clone_mode = true;
|
||||
SDE_DEBUG("enc:%d phys state:%d\n", DRMID(drm_enc), phys->enable_state);
|
||||
}
|
||||
}
|
||||
|
||||
sde_crtc_state->cwb_enc_mask = 0;
|
||||
}
|
||||
|
||||
static int _sde_encoder_atomic_check_phys_enc(struct sde_encoder_virt *sde_enc,
|
||||
struct drm_crtc_state *crtc_state,
|
||||
struct drm_connector_state *conn_state)
|
||||
|
@@ -491,6 +491,14 @@ void sde_encoder_enable_recovery_event(struct drm_encoder *encoder);
|
||||
*/
|
||||
bool sde_encoder_in_clone_mode(struct drm_encoder *enc);
|
||||
|
||||
/**
|
||||
* sde_encoder_set_clone_mode - cwb in wb phys enc is enabled.
|
||||
* drm_enc: Pointer to drm encoder structure
|
||||
* drm_crtc_state: Pointer to drm_crtc_state
|
||||
*/
|
||||
void sde_encoder_set_clone_mode(struct drm_encoder *drm_enc,
|
||||
struct drm_crtc_state *crtc_state);
|
||||
|
||||
/*
|
||||
* sde_encoder_is_cwb_disabling - check if cwb encoder disable is pending
|
||||
* @drm_enc: Pointer to drm encoder structure
|
||||
|
@@ -653,6 +653,7 @@ static void _sde_enc_phys_wb_detect_cwb(struct sde_encoder_phys *phys_enc,
|
||||
struct drm_crtc_state *crtc_state)
|
||||
{
|
||||
struct sde_encoder_phys_wb *wb_enc = to_sde_encoder_phys_wb(phys_enc);
|
||||
struct sde_crtc_state *cstate = to_sde_crtc_state(crtc_state);
|
||||
const struct sde_wb_cfg *wb_cfg = wb_enc->hw_wb->caps;
|
||||
u32 encoder_mask = 0;
|
||||
|
||||
@@ -662,9 +663,11 @@ static void _sde_enc_phys_wb_detect_cwb(struct sde_encoder_phys *phys_enc,
|
||||
encoder_mask = crtc_state->encoder_mask;
|
||||
encoder_mask &= ~drm_encoder_mask(phys_enc->parent);
|
||||
}
|
||||
phys_enc->in_clone_mode = encoder_mask ? true : false;
|
||||
|
||||
SDE_DEBUG("detect CWB(OR)DCWB - status:%d\n", phys_enc->in_clone_mode);
|
||||
cstate->cwb_enc_mask = encoder_mask ? drm_encoder_mask(phys_enc->parent) : 0;
|
||||
|
||||
SDE_DEBUG("detect CWB - status:%d, phys state:%d in_clone_mode:%d\n",
|
||||
cstate->cwb_enc_mask, phys_enc->enable_state, phys_enc->in_clone_mode);
|
||||
}
|
||||
|
||||
static int _sde_enc_phys_wb_validate_cwb(struct sde_encoder_phys *phys_enc,
|
||||
@@ -816,6 +819,7 @@ static int sde_encoder_phys_wb_atomic_check(
|
||||
struct drm_connector_state *conn_state)
|
||||
{
|
||||
struct sde_encoder_phys_wb *wb_enc = to_sde_encoder_phys_wb(phys_enc);
|
||||
struct sde_crtc_state *cstate = to_sde_crtc_state(crtc_state);
|
||||
struct sde_hw_wb *hw_wb = wb_enc->hw_wb;
|
||||
const struct sde_wb_cfg *wb_cfg = hw_wb->caps;
|
||||
struct drm_framebuffer *fb;
|
||||
@@ -843,7 +847,7 @@ static int sde_encoder_phys_wb_atomic_check(
|
||||
|
||||
_sde_enc_phys_wb_detect_cwb(phys_enc, crtc_state);
|
||||
|
||||
if (clone_mode_curr && !phys_enc->in_clone_mode) {
|
||||
if (clone_mode_curr && !cstate->cwb_enc_mask) {
|
||||
SDE_ERROR("WB commit before CWB disable\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -902,7 +906,7 @@ static int sde_encoder_phys_wb_atomic_check(
|
||||
crtc_state->mode_changed = true;
|
||||
|
||||
/* if in clone mode, return after cwb validation */
|
||||
if (phys_enc->in_clone_mode) {
|
||||
if (cstate->cwb_enc_mask) {
|
||||
rc = _sde_enc_phys_wb_validate_cwb(phys_enc, crtc_state,
|
||||
conn_state);
|
||||
if (rc)
|
||||
|
@@ -2135,7 +2135,7 @@ static int _sde_rm_populate_requirements(
|
||||
* found enabled.
|
||||
*/
|
||||
if ((!RM_RQ_CWB(reqs) || !RM_RQ_DCWB(reqs))
|
||||
&& sde_encoder_in_clone_mode(enc)) {
|
||||
&& sde_crtc_state_in_clone_mode(enc, crtc_state)) {
|
||||
if (cfg->has_dedicated_cwb_support)
|
||||
reqs->top_ctrl |= BIT(SDE_RM_TOPCTL_DCWB);
|
||||
else
|
||||
|
Reference in New Issue
Block a user