From a4fe416f2bd9d26c03ac162d3afaa7726382499f Mon Sep 17 00:00:00 2001 From: Zongdong Jiao Date: Tue, 20 Nov 2018 12:37:30 +0800 Subject: [PATCH] hdmitx: add rx latency info [1/4] PD#SWPL-2456 Problem: Lack the latency info of RX Solution: Add the latency info of RX Verify: T962E/R321 Change-Id: I480398466753dd93ca6e908d39157acadff6879f Signed-off-by: Zongdong Jiao --- .../media/vout/hdmitx/hdmi_tx_20/hdmi_tx_edid.c | 109 ++++++++++++++++++++- .../media/vout/hdmitx/hdmi_tx_20/hdmi_tx_main.c | 31 +++--- .../amlogic/media/vout/hdmi_tx/hdmi_tx_module.h | 8 +- include/linux/amlogic/media/vout/vinfo.h | 10 ++ 4 files changed, 138 insertions(+), 20 deletions(-) diff --git a/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_edid.c b/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_edid.c index e6d6c33..9aa4d39 100644 --- a/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_edid.c +++ b/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_edid.c @@ -1403,6 +1403,40 @@ static void hdmitx_edid_4k2k_parse(struct rx_cap *pRXCap, unsigned char *dat, } } +static void get_latency(struct rx_cap *pRXCap, unsigned char *val) +{ + if (val[0] == 0) + pRXCap->vLatency = LATENCY_INVALID_UNKNOWN; + else if (val[0] == 0xFF) + pRXCap->vLatency = LATENCY_NOT_SUPPORT; + else + pRXCap->vLatency = (val[0] - 1) * 2; + + if (val[1] == 0) + pRXCap->aLatency = LATENCY_INVALID_UNKNOWN; + else if (val[1] == 0xFF) + pRXCap->aLatency = LATENCY_NOT_SUPPORT; + else + pRXCap->aLatency = (val[1] - 1) * 2; +} + +static void get_ilatency(struct rx_cap *pRXCap, unsigned char *val) +{ + if (val[0] == 0) + pRXCap->i_vLatency = LATENCY_INVALID_UNKNOWN; + else if (val[0] == 0xFF) + pRXCap->i_vLatency = LATENCY_NOT_SUPPORT; + else + pRXCap->i_vLatency = val[0] * 2 - 1; + + if (val[1] == 0) + pRXCap->i_aLatency = LATENCY_INVALID_UNKNOWN; + else if (val[1] == 0xFF) + pRXCap->i_aLatency = LATENCY_NOT_SUPPORT; + else + pRXCap->i_aLatency = val[1] * 2 - 1; +} + static int hdmitx_edid_block_parse(struct hdmitx_dev *hdmitx_device, unsigned char *BlockBuf) { @@ -1477,10 +1511,22 @@ static int hdmitx_edid_block_parse(struct hdmitx_dev *hdmitx_device, if (count > 7) { tmp = BlockBuf[offset+7]; idx = offset + 8; - if (tmp & (1<<6)) + if (tmp & (1<<6)) { + unsigned char val[2]; + + val[0] = BlockBuf[idx]; + val[1] = BlockBuf[idx + 1]; + get_latency(pRXCap, val); idx += 2; - if (tmp & (1<<7)) + } + if (tmp & (1<<7)) { + unsigned char val[2]; + + val[0] = BlockBuf[idx]; + val[1] = BlockBuf[idx + 1]; + get_ilatency(pRXCap, val); idx += 2; + } if (tmp & (1<<5)) { idx += 1; /* valid 4k */ @@ -1916,6 +1962,7 @@ next: } else dump_dtd_info(t); } + static void hdrinfo_to_vinfo(struct vinfo_s *info, struct rx_cap *pRXCap) { unsigned int k, l; @@ -1956,6 +2003,15 @@ static void hdrinfo_to_vinfo(struct vinfo_s *info, struct rx_cap *pRXCap) info->hdr_info.hdr_support); } +static void rxlatency_to_vinfo(struct vinfo_s *info, struct rx_cap *rx) +{ + if (!info || !rx) + return; + info->rx_latency.vLatency = rx->vLatency; + info->rx_latency.aLatency = rx->aLatency; + info->rx_latency.i_vLatency = rx->i_vLatency; + info->rx_latency.i_aLatency = rx->i_aLatency; +} int hdmitx_edid_parse(struct hdmitx_dev *hdmitx_device) { @@ -2153,8 +2209,10 @@ int hdmitx_edid_parse(struct hdmitx_dev *hdmitx_device) if (info) { if (!((strncmp(info->name, "480cvbs", 7) == 0) || (strncmp(info->name, "576cvbs", 7) == 0) || - (strncmp(info->name, "null", 4) == 0))) + (strncmp(info->name, "null", 4) == 0))) { hdrinfo_to_vinfo(info, pRXCap); + rxlatency_to_vinfo(info, pRXCap); + } } return 0; @@ -2652,6 +2710,51 @@ int hdmitx_edid_dump(struct hdmitx_dev *hdmitx_device, char *buffer, pos += snprintf(buffer+pos, buffer_len-pos, "MaxTMDSClock2 %d MHz\n", pRXCap->Max_TMDS_Clock2 * 5); } + + pos += snprintf(buffer+pos, buffer_len-pos, "vLatency: "); + if (pRXCap->vLatency == LATENCY_INVALID_UNKNOWN) + pos += snprintf(buffer+pos, buffer_len-pos, + " Invalid/Unknown\n"); + else if (pRXCap->vLatency == LATENCY_NOT_SUPPORT) + pos += snprintf(buffer+pos, buffer_len-pos, + " UnSupported\n"); + else + pos += snprintf(buffer+pos, buffer_len-pos, + " %d\n", pRXCap->vLatency); + + pos += snprintf(buffer+pos, buffer_len-pos, "aLatency: "); + if (pRXCap->aLatency == LATENCY_INVALID_UNKNOWN) + pos += snprintf(buffer+pos, buffer_len-pos, + " Invalid/Unknown\n"); + else if (pRXCap->aLatency == LATENCY_NOT_SUPPORT) + pos += snprintf(buffer+pos, buffer_len-pos, + " UnSupported\n"); + else + pos += snprintf(buffer+pos, buffer_len-pos, " %d\n", + pRXCap->aLatency); + + pos += snprintf(buffer+pos, buffer_len-pos, "i_vLatency: "); + if (pRXCap->i_vLatency == LATENCY_INVALID_UNKNOWN) + pos += snprintf(buffer+pos, buffer_len-pos, + " Invalid/Unknown\n"); + else if (pRXCap->i_vLatency == LATENCY_NOT_SUPPORT) + pos += snprintf(buffer+pos, buffer_len-pos, + " UnSupported\n"); + else + pos += snprintf(buffer+pos, buffer_len-pos, " %d\n", + pRXCap->i_vLatency); + + pos += snprintf(buffer+pos, buffer_len-pos, "i_aLatency: "); + if (pRXCap->i_aLatency == LATENCY_INVALID_UNKNOWN) + pos += snprintf(buffer+pos, buffer_len-pos, + " Invalid/Unknown\n"); + else if (pRXCap->i_aLatency == LATENCY_NOT_SUPPORT) + pos += snprintf(buffer+pos, buffer_len-pos, + " UnSupported\n"); + else + pos += snprintf(buffer+pos, buffer_len-pos, " %d\n", + pRXCap->i_aLatency); + if (pRXCap->colorimetry_data) pos += snprintf(buffer+pos, buffer_len-pos, "ColorMetry: 0x%x\n", pRXCap->colorimetry_data); diff --git a/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_main.c b/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_main.c index 7f663af..b14955d 100644 --- a/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_main.c +++ b/drivers/amlogic/media/vout/hdmitx/hdmi_tx_20/hdmi_tx_main.c @@ -421,6 +421,16 @@ static void hdrinfo_to_vinfo(struct vinfo_s *info, struct hdmitx_dev *hdev) info->hdr_info.hdr_support); } +static void rxlatency_to_vinfo(struct vinfo_s *info, struct rx_cap *rx) +{ + if (!info || !rx) + return; + info->rx_latency.vLatency = rx->vLatency; + info->rx_latency.aLatency = rx->aLatency; + info->rx_latency.i_vLatency = rx->i_vLatency; + info->rx_latency.i_aLatency = rx->i_aLatency; +} + static int set_disp_mode_auto(void) { int ret = -1; @@ -446,8 +456,10 @@ static int set_disp_mode_auto(void) if (!((strncmp(info->name, "480cvbs", 7) == 0) || (strncmp(info->name, "576cvbs", 7) == 0) || - (strncmp(info->name, "null", 4) == 0))) + (strncmp(info->name, "null", 4) == 0))) { hdrinfo_to_vinfo(info, hdev); + rxlatency_to_vinfo(info, &hdev->RXCap); + } hdmi_physcial_size_update(hdev); @@ -468,6 +480,7 @@ static int set_disp_mode_auto(void) return -1; } strncpy(mode, info->name, sizeof(mode)); + mode[31] = '\0'; if (strstr(mode, "fp")) { int i = 0; @@ -3771,21 +3784,13 @@ static void hdmitx_hpd_plugin_handler(struct work_struct *work) mutex_unlock(&setclk_mutex); } -static void clear_hdr_info(struct hdmitx_dev *hdev) +static void clear_rx_vinfo(struct hdmitx_dev *hdev) { struct vinfo_s *info = hdmitx_get_current_vinfo(); - unsigned int i; if (info) { - info->hdr_info.hdr_support = 0; - for (i = 0; i < 4; i++) - memset(&(info->hdr_info.dynamic_info[i]), - 0, sizeof(struct hdr_dynamic)); - info->hdr_info.colorimetry_support = 0; - info->hdr_info.lumi_max = 0; - info->hdr_info.lumi_avg = 0; - info->hdr_info.lumi_min = 0; - pr_info(SYS "clear RX hdr info\n"); + memset(&info->hdr_info, 0, sizeof(info->hdr_info)); + memset(&info->rx_latency, 0, sizeof(info->rx_latency)); } } @@ -3821,7 +3826,7 @@ static void hdmitx_hpd_plugout_handler(struct work_struct *work) hdev->HWOp.CntlMisc(hdev, MISC_TMDS_PHY_OP, TMDS_PHY_DISABLE); hdev->hdmitx_event &= ~HDMI_TX_HPD_PLUGOUT; hdev->HWOp.CntlMisc(hdev, MISC_ESM_RESET, 0); - clear_hdr_info(hdev); + clear_rx_vinfo(hdev); rx_edid_physical_addr(0, 0, 0, 0); hdmitx_edid_clear(hdev); hdmi_physcial_size_update(hdev); diff --git a/include/linux/amlogic/media/vout/hdmi_tx/hdmi_tx_module.h b/include/linux/amlogic/media/vout/hdmi_tx/hdmi_tx_module.h index aed86d5..757f403 100644 --- a/include/linux/amlogic/media/vout/hdmi_tx/hdmi_tx_module.h +++ b/include/linux/amlogic/media/vout/hdmi_tx/hdmi_tx_module.h @@ -130,10 +130,10 @@ struct rx_cap { unsigned char edid_version; unsigned char edid_revision; unsigned char ColorDeepSupport; - unsigned int Video_Latency; - unsigned int Audio_Latency; - unsigned int Interlaced_Video_Latency; - unsigned int Interlaced_Audio_Latency; + unsigned int vLatency; + unsigned int aLatency; + unsigned int i_vLatency; + unsigned int i_aLatency; unsigned int threeD_present; unsigned int threeD_Multi_present; unsigned int hdmi_vic_LEN; diff --git a/include/linux/amlogic/media/vout/vinfo.h b/include/linux/amlogic/media/vout/vinfo.h index dfafcaf..8a5720f 100644 --- a/include/linux/amlogic/media/vout/vinfo.h +++ b/include/linux/amlogic/media/vout/vinfo.h @@ -233,6 +233,15 @@ struct vinfo_base_s { enum color_fmt_e viu_color_fmt; }; +#define LATENCY_INVALID_UNKNOWN 0 +#define LATENCY_NOT_SUPPORT 0xffff +struct rx_av_latency { + unsigned int vLatency; + unsigned int aLatency; + unsigned int i_vLatency; + unsigned int i_aLatency; +}; + struct vinfo_s { char *name; enum vmode_e mode; @@ -254,6 +263,7 @@ struct vinfo_s { enum viu_mux_e viu_mux; struct master_display_info_s master_display_info; struct hdr_info hdr_info; + struct rx_av_latency rx_latency; struct vout_device_s *vout_device; }; -- 2.7.4