diff --git a/msm/dp/dp_aux.c b/msm/dp/dp_aux.c index f121c9a3ead7..12eddb50ae9a 100644 --- a/msm/dp/dp_aux.c +++ b/msm/dp/dp_aux.c @@ -495,35 +495,33 @@ static ssize_t dp_aux_transfer_debug(struct drm_dp_aux *drm_aux, } if (aux->native) { + mutex_lock(aux->dp_aux.access_lock); aux->dp_aux.reg = msg->address; aux->dp_aux.read = aux->read; aux->dp_aux.size = msg->size; + if (!aux->read) + memcpy(aux->dpcd + msg->address, + msg->buffer, msg->size); + reinit_completion(&aux->comp); + mutex_unlock(aux->dp_aux.access_lock); - if (aux->read) { - timeout = wait_for_completion_timeout(&aux->comp, HZ); - if (!timeout) { - DP_ERR("read timeout: 0x%x\n", msg->address); - atomic_set(&aux->aborted, 1); - ret = -ETIMEDOUT; - goto end; - } + timeout = wait_for_completion_timeout(&aux->comp, HZ * 2); + if (!timeout) { + DP_ERR("%s timeout: 0x%x\n", + aux->read ? "read" : "write", + msg->address); + atomic_set(&aux->aborted, 1); + ret = -ETIMEDOUT; + goto end; + } + mutex_lock(aux->dp_aux.access_lock); + if (aux->read) memcpy(msg->buffer, aux->dpcd + msg->address, msg->size); - } else { - memcpy(aux->dpcd + msg->address, msg->buffer, - msg->size); - - timeout = wait_for_completion_timeout(&aux->comp, HZ); - if (!timeout) { - DP_ERR("write timeout: 0x%x\n", msg->address); - atomic_set(&aux->aborted, 1); - ret = -ETIMEDOUT; - goto end; - } - } + mutex_unlock(aux->dp_aux.access_lock); aux->aux_error_num = DP_AUX_ERR_NONE; } else { @@ -725,6 +723,8 @@ static void dp_aux_dpcd_updated(struct dp_aux *dp_aux) aux = container_of(dp_aux, struct dp_aux_private, dp_aux); + /* make sure wait has started */ + usleep_range(20, 30); complete(&aux->comp); } diff --git a/msm/dp/dp_aux.h b/msm/dp/dp_aux.h index 42951d68a750..0f41b89a2575 100644 --- a/msm/dp/dp_aux.h +++ b/msm/dp/dp_aux.h @@ -40,6 +40,8 @@ struct dp_aux { bool read; + struct mutex *access_lock; + struct drm_dp_aux *drm_aux; int (*drm_aux_register)(struct dp_aux *aux); void (*drm_aux_deregister)(struct dp_aux *aux); diff --git a/msm/dp/dp_debug.c b/msm/dp/dp_debug.c index fa6bee7c3737..7cd9a571da1d 100644 --- a/msm/dp/dp_debug.c +++ b/msm/dp/dp_debug.c @@ -178,7 +178,6 @@ static ssize_t dp_debug_write_dpcd(struct file *file, ssize_t rc = count; char offset_ch[5]; u32 offset, data_len; - u32 extended_capability_bytes = 0; const u32 dp_receiver_cap_size = 16; if (!debug) @@ -252,25 +251,9 @@ static ssize_t dp_debug_write_dpcd(struct file *file, bail: kfree(buf); - /* - * If extension bit is set then increase the length - * of user input to account for the extra bytes - */ - if (dpcd && (dpcd_buf_index > DP_RECEIVER_CAP_SIZE) && - (dpcd[DP_TRAINING_AUX_RD_INTERVAL] & - DP_EXT_REC_CAP_FIELD)) - extended_capability_bytes = 4; - - /* - * Reset panel's dpcd in case of any failure. Also, set the - * panel's dpcd only if a full dpcd is provided with offset as 0. - */ - if (!dpcd || (!offset && - (data_len == (dp_receiver_cap_size + - extended_capability_bytes))) || - (offset == 0xffff)) { + if (!dpcd || (size / char_to_nib) >= dp_receiver_cap_size || + offset == 0xffff) { debug->panel->set_dpcd(debug->panel, dpcd); - /* * print dpcd status as this code is executed * only while running in debug mode which is manually @@ -280,10 +263,11 @@ bail: DP_INFO("[%s]\n", "CLEAR"); else DP_INFO("[%s]\n", "SET"); - } else - debug->aux->dpcd_updated(debug->aux); + } mutex_unlock(&debug->lock); + + debug->aux->dpcd_updated(debug->aux); return rc; } @@ -295,16 +279,18 @@ static ssize_t dp_debug_read_dpcd(struct file *file, int const buf_size = SZ_4K; u32 offset = 0; u32 len = 0; + bool notify = false; if (!debug || !debug->aux || !debug->dpcd) return -ENODEV; + mutex_lock(&debug->lock); if (*ppos) - return 0; + goto end; buf = kzalloc(buf_size, GFP_KERNEL); if (!buf) - return -ENOMEM; + goto end; len += snprintf(buf, buf_size, "0x%x", debug->aux->reg); @@ -318,8 +304,7 @@ static ssize_t dp_debug_read_dpcd(struct file *file, debug->dpcd[debug->aux->reg + offset++]); } - if (debug->dp_debug.sim_mode && debug->aux->dpcd_updated) - debug->aux->dpcd_updated(debug->aux); + notify = true; } len = min_t(size_t, count, len); @@ -327,6 +312,12 @@ static ssize_t dp_debug_read_dpcd(struct file *file, *ppos += len; kfree(buf); +end: + mutex_unlock(&debug->lock); + + if (notify) + debug->aux->dpcd_updated(debug->aux); + return len; } @@ -2274,6 +2265,7 @@ struct dp_debug *dp_debug_get(struct dp_debug_in *in) goto error; } + debug->aux->access_lock = &debug->lock; dp_debug->get_edid = dp_debug_get_edid; dp_debug->abort = dp_debug_abort;