summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVenkata Prahlad Valluru <vvalluru@codeaurora.org>2020-03-06 19:12:30 +0530
committerVenkata Prahlad Valluru <vvalluru@codeaurora.org>2020-03-06 19:14:00 +0530
commitfd06f35834d58041efd3b804ba33767dd808f188 (patch)
tree186ee84e658292d38bd977765cfef40d50d0ef5c
parentffd87dde76f6c9b6a134c981c877c2e25c350ea2 (diff)
mdss: msm: hdmi: fix CEC broadcast loopback issue
A new logical address is searched and allocated when HDMI hotplug interrupt happens. But there might be pending broadcast messages which are being handled with the old logical address, then the messages are received back again causing loopback issue. To fix this, abort CEC message sending if the message is broadcasting and the sender's logical address is different than the current logical address. Change-Id: I26c487bac8749c9de81b176d611f1263eab0d9ad Signed-off-by: Venkata Prahlad Valluru <vvalluru@codeaurora.org>
-rw-r--r--drivers/video/fbdev/msm/mdss_hdmi_cec.c20
1 files changed, 18 insertions, 2 deletions
diff --git a/drivers/video/fbdev/msm/mdss_hdmi_cec.c b/drivers/video/fbdev/msm/mdss_hdmi_cec.c
index 872e3594715f..3eda29edff4d 100644
--- a/drivers/video/fbdev/msm/mdss_hdmi_cec.c
+++ b/drivers/video/fbdev/msm/mdss_hdmi_cec.c
@@ -42,7 +42,7 @@ struct hdmi_cec_ctrl {
bool cec_wakeup_en;
bool cec_device_suspend;
bool cec_clear_logical_addr;
-
+ u32 cec_logical_addr;
u32 cec_msg_wr_status;
struct cec_msg recv_msg[CEC_RECV_Q_SIZE];
u32 head;
@@ -68,6 +68,20 @@ static int hdmi_cec_msg_send(void *data, struct cec_msg *msg)
return -EINVAL;
}
+ if (msg->sender_id != cec_ctrl->cec_logical_addr &&
+ msg->recvr_id == 0xF) {
+ /*
+ * If the current logical address is not the
+ * same as the sender_id and if the message is
+ * broadcasting, the message is looping back.
+ * Abort the message sending in that case
+ */
+ DEV_ERR("%s: abort potential MAL msg %d:%d logical %d\n",
+ __func__, msg->sender_id, msg->recvr_id,
+ cec_ctrl->cec_logical_addr);
+ return -EINVAL;
+ }
+
io = cec_ctrl->init_data.io;
reinit_completion(&cec_ctrl->cec_msg_wr_done);
@@ -414,8 +428,10 @@ static void hdmi_cec_write_logical_addr(void *input, u8 addr)
return;
}
- if (cec_ctrl->cec_enabled)
+ if (cec_ctrl->cec_enabled) {
DSS_REG_W(cec_ctrl->init_data.io, HDMI_CEC_ADDR, addr & 0xF);
+ cec_ctrl->cec_logical_addr = addr & 0xF;
+ }
}
static void hdmi_cec_clear_logical_addr(void *input, bool clear_flag)