diff options
| author | Ujwal Patel <ujwalp@codeaurora.org> | 2012-11-15 18:06:56 -0800 |
|---|---|---|
| committer | David Keitel <dkeitel@codeaurora.org> | 2016-03-23 20:13:34 -0700 |
| commit | 8f5a83a24ef557772da9c0772a36ef561e9876ca (patch) | |
| tree | a416fe16240a85e8cc9a95e6a1f14d82aa177330 | |
| parent | 8d57ffc14a23c3bd3810df181f18ea39c569a7fb (diff) | |
msm: mdss: hdmi: Add support for new resolutions
Add support for following new resolutions.
* 2560x1600 @ 60Hz (DVI)
* 3840x2160 @ 30Hz (HDMI)
* 3840x2160 @ 25Hz (HDMI)
* 3840x2160 @ 24Hz (HDMI)
* 4096x2160 @ 24Hz (HDMI)
Change-Id: I14262448fea80615c6c77b4638b0a9815efc3297
Signed-off-by: Ujwal Patel <ujwalp@codeaurora.org>
| -rw-r--r-- | drivers/video/fbdev/msm/mdss_hdmi_edid.c | 70 | ||||
| -rw-r--r-- | drivers/video/fbdev/msm/mdss_hdmi_tx.c | 185 | ||||
| -rw-r--r-- | drivers/video/fbdev/msm/mdss_hdmi_util.c | 93 | ||||
| -rw-r--r-- | drivers/video/fbdev/msm/mdss_hdmi_util.h | 32 |
4 files changed, 268 insertions, 112 deletions
diff --git a/drivers/video/fbdev/msm/mdss_hdmi_edid.c b/drivers/video/fbdev/msm/mdss_hdmi_edid.c index 4eafcf7362a2..281a5124d9a4 100644 --- a/drivers/video/fbdev/msm/mdss_hdmi_edid.c +++ b/drivers/video/fbdev/msm/mdss_hdmi_edid.c @@ -16,7 +16,7 @@ #include "mdss_hdmi_edid.h" #define DBC_START_OFFSET 4 -#define HDMI_VSDB_3D_DATA_OFFSET(vsd) \ +#define HDMI_VSDB_3D_EVF_DATA_OFFSET(vsd) \ (!((vsd)[8] & BIT(7)) ? 9 : (!((vsd)[8] & BIT(6)) ? 11 : 13)) struct hdmi_edid_sink_data { @@ -180,6 +180,10 @@ static struct hdmi_edid_video_mode_property_type {HDMI_VFRMT_1920x1080i120_16_9, 1920, 1080, true, 2200, 280, 1125, 22, 67500, 120000, 148500, 120000, false}, + /* All 2560 H Active */ + {HDMI_VFRMT_2560x1600p60_16_9, 2560, 1600, false, 2720, 160, 1646, + 46, 98700, 60000, 268500, 60000, false}, + /* All 2880 H Active */ {HDMI_VFRMT_2880x576i50_4_3, 2880, 576, true, 3456, 576, 625, 24, 15625, 50000, 54000, 50000, true}, @@ -437,7 +441,7 @@ static const u8 *hdmi_edid_find_block(const u8 *in_buf, u32 start_offset, u8 block_len = in_buf[offset] & 0x1F; if ((in_buf[offset] >> 5) == type) { *len = block_len; - DEV_DBG("%s: EDID: block=%d found @ %d w/ length=%d\n", + DEV_DBG("%s: EDID: block=%d found @ 0x%x w/ len=%d\n", __func__, type, offset, block_len); return in_buf + offset; @@ -533,8 +537,8 @@ static void hdmi_edid_extract_3d_present(struct hdmi_edid_ctrl *edid_ctrl, return; } - offset = HDMI_VSDB_3D_DATA_OFFSET(vsd); - DEV_DBG("%s: EDID: 3D present @ %d = %02x\n", __func__, + offset = HDMI_VSDB_3D_EVF_DATA_OFFSET(vsd); + DEV_DBG("%s: EDID: 3D present @ 0x%x = %02x\n", __func__, offset, vsd[offset]); if (vsd[offset] >> 7) { /* 3D format indication present */ @@ -835,7 +839,7 @@ static void hdmi_edid_get_display_vsd_3d_mode(const u8 *data_buf, 3, &len) : NULL; int i; - offset = HDMI_VSDB_3D_DATA_OFFSET(vsd); + offset = HDMI_VSDB_3D_EVF_DATA_OFFSET(vsd); present_multi_3d = (vsd[offset] & 0x60) >> 5; offset += 1; @@ -897,17 +901,16 @@ static void hdmi_edid_get_display_vsd_3d_mode(const u8 *data_buf, i = 0; while (hdmi_3d_len > 0) { - DEV_DBG("%s: EDID[3D]: 3D_Structure_%d @ %d: %02x\n", __func__, - i + 1, offset, vsd[offset]); + DEV_DBG("%s: EDID: 3D_Structure_%d @ 0x%x: %02x\n", + __func__, i + 1, offset, vsd[offset]); if ((vsd[offset] >> 4) >= sink_data->disp_multi_3d_mode_list_cnt) { if ((vsd[offset] & 0x0F) >= 8) { offset += 1; hdmi_3d_len -= 1; - DEV_DBG("%s:EDID[3D]:3D_Detail_%d @ %d: %02x\n", - __func__, i + 1, offset, - vsd[offset]); + DEV_DBG("%s:EDID:3D_Detail_%d @ 0x%x: %02x\n", + __func__, i + 1, offset, vsd[offset]); } i += 1; offset += 1; @@ -941,7 +944,7 @@ static void hdmi_edid_get_display_vsd_3d_mode(const u8 *data_buf, if ((vsd[offset] & 0x0F) >= 8) { offset += 1; hdmi_3d_len -= 1; - DEV_DBG("%s: EDID[3D]: 3D_Detail_%d @ %d: %02x\n", + DEV_DBG("%s: EDID[3D]: 3D_Detail_%d @ 0x%x: %02x\n", __func__, i + 1, offset, vsd[offset]); } @@ -951,6 +954,49 @@ static void hdmi_edid_get_display_vsd_3d_mode(const u8 *data_buf, } } /* hdmi_edid_get_display_vsd_3d_mode */ +static void hdmi_edid_get_extended_video_formats( + struct hdmi_edid_ctrl *edid_ctrl, const u8 *in_buf) +{ + u8 db_len, offset, i; + u8 hdmi_vic_len; + u32 video_format; + const u8 *vsd = NULL; + + if (!edid_ctrl) { + DEV_ERR("%s: invalid input\n", __func__); + return; + } + + vsd = hdmi_edid_find_block(in_buf, DBC_START_OFFSET, 3, &db_len); + + if (vsd == NULL || db_len < 9) { + DEV_DBG("%s: blk-id 3 not found or not long enough\n", + __func__); + return; + } + + /* check if HDMI_Video_present flag is set or not */ + if (!(vsd[8] & BIT(5))) { + DEV_DBG("%s: extended vfmts are not supported by the sink.\n", + __func__); + return; + } + + offset = HDMI_VSDB_3D_EVF_DATA_OFFSET(vsd); + + hdmi_vic_len = vsd[offset + 1] >> 5; + if (hdmi_vic_len) { + DEV_DBG("%s: EDID: EVFRMT @ 0x%x of block 3, len = %02x\n", + __func__, offset, hdmi_vic_len); + + for (i = 0; i < hdmi_vic_len; i++) { + video_format = HDMI_VFRMT_END + vsd[offset + 2 + i]; + hdmi_edid_add_sink_video_format(&edid_ctrl->sink_data, + video_format); + } + } +} /* hdmi_edid_get_extended_video_formats */ + static void hdmi_edid_get_display_mode(struct hdmi_edid_ctrl *edid_ctrl, const u8 *data_buf, u32 num_of_cea_blocks) { @@ -1113,6 +1159,8 @@ static void hdmi_edid_get_display_mode(struct hdmi_edid_ctrl *edid_ctrl, } } + hdmi_edid_get_extended_video_formats(edid_ctrl, data_buf+0x80); + /* mandaroty 3d format */ if (edid_ctrl->present_3d) { if (has60hz_mode) { diff --git a/drivers/video/fbdev/msm/mdss_hdmi_tx.c b/drivers/video/fbdev/msm/mdss_hdmi_tx.c index d9ce757aff7c..1a63f0b402cb 100644 --- a/drivers/video/fbdev/msm/mdss_hdmi_tx.c +++ b/drivers/video/fbdev/msm/mdss_hdmi_tx.c @@ -32,7 +32,7 @@ #define DRV_NAME "hdmi-tx" #define COMPATIBLE_NAME "qcom,hdmi-tx" -#define DEFAULT_VIDEO_RESOLUTION HDMI_VFRMT_1920x1080p60_16_9; +#define DEFAULT_VIDEO_RESOLUTION HDMI_VFRMT_1920x1080p60_16_9 /* HDMI PHY/PLL bit field macros */ #define SW_RESET BIT(2) @@ -91,35 +91,46 @@ const char *hdmi_pm_name(enum hdmi_tx_power_module_type module) } } /* hdmi_pm_name */ -static u8 hdmi_tx_avi_iframe_lut[][16] = { -/* 480p60 480i60 576p50 576i50 720p60 720p50 1080p60 1080i60 1080p50 - 1080i50 1080p24 1080p30 1080p25 640x480p 480p60_16_9 576p50_4_3 */ - {0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, - 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10}, /*00*/ - {0x18, 0x18, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, - 0x28, 0x28, 0x28, 0x28, 0x18, 0x28, 0x18}, /*01*/ - {0x00, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, - 0x04, 0x04, 0x04, 0x04, 0x88, 0x00, 0x04}, /*02*/ - {0x02, 0x06, 0x11, 0x15, 0x04, 0x13, 0x10, 0x05, 0x1F, - 0x14, 0x20, 0x22, 0x21, 0x01, 0x03, 0x11}, /*03*/ - {0x00, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, /*04*/ - {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, /*05*/ - {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, /*06*/ - {0xE1, 0xE1, 0x41, 0x41, 0xD1, 0xd1, 0x39, 0x39, 0x39, - 0x39, 0x39, 0x39, 0x39, 0xe1, 0xE1, 0x41}, /*07*/ - {0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 0x04, 0x04, 0x04, - 0x04, 0x04, 0x04, 0x04, 0x01, 0x01, 0x02}, /*08*/ - {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, /*09*/ - {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, /*10*/ - {0xD1, 0xD1, 0xD1, 0xD1, 0x01, 0x01, 0x81, 0x81, 0x81, - 0x81, 0x81, 0x81, 0x81, 0x81, 0xD1, 0xD1}, /*11*/ - {0x02, 0x02, 0x02, 0x02, 0x05, 0x05, 0x07, 0x07, 0x07, - 0x07, 0x07, 0x07, 0x07, 0x02, 0x02, 0x02} /*12*/ +static u8 hdmi_tx_avi_iframe_lut[][20] = { + {0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, + 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, + 0x10, 0x10}, /*00*/ + {0x18, 0x18, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, + 0x28, 0x28, 0x28, 0x28, 0x18, 0x28, 0x18, 0x28, 0x28, + 0x28, 0x28}, /*01*/ + {0x00, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, + 0x04, 0x04, 0x04, 0x04, 0x88, 0x00, 0x04, 0x04, 0x04, + 0x04, 0x04}, /*02*/ + {0x02, 0x06, 0x11, 0x15, 0x04, 0x13, 0x10, 0x05, 0x1F, + 0x14, 0x20, 0x22, 0x21, 0x01, 0x03, 0x11, 0x00, 0x00, + 0x00, 0x00}, /*03*/ + {0x00, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00}, /*04*/ + {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00}, /*05*/ + {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00}, /*06*/ + {0xE1, 0xE1, 0x41, 0x41, 0xD1, 0xd1, 0x39, 0x39, 0x39, + 0x39, 0x39, 0x39, 0x39, 0xe1, 0xE1, 0x41, 0x71, 0x71, + 0x71, 0x71}, /*07*/ + {0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 0x04, 0x04, 0x04, + 0x04, 0x04, 0x04, 0x04, 0x01, 0x01, 0x02, 0x08, 0x08, + 0x08, 0x08}, /*08*/ + {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00}, /*09*/ + {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00}, /*10*/ + {0xD1, 0xD1, 0xD1, 0xD1, 0x01, 0x01, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0xD1, 0xD1, 0x01, 0x01, + 0x01, 0x01}, /*11*/ + {0x02, 0x02, 0x02, 0x02, 0x05, 0x05, 0x07, 0x07, 0x07, + 0x07, 0x07, 0x07, 0x07, 0x02, 0x02, 0x02, 0x0F, 0x0F, + 0x0F, 0x10} /*12*/ }; /* Audio constants lookup table for hdmi_tx_audio_acr_setup */ @@ -141,6 +152,10 @@ static const struct hdmi_tx_audio_acr_arry hdmi_tx_audio_acr_lut[] = { {148500, {{4096, 148500}, {6272, 165000}, {6144, 148500}, {12544, 165000}, {12288, 148500}, {25088, 165000}, {24576, 148500} } }, + /* 297.000MHz */ + {297000, {{3072, 222750}, {4704, 247500}, {5120, 247500}, + {9408, 247500}, {10240, 247500}, {18816, 247500}, + {20480, 247500} } }, }; const char *hdmi_tx_pm_name(enum hdmi_tx_power_module_type module) @@ -482,9 +497,11 @@ static int hdmi_tx_init_panel_info(uint32_t resolution, } /* hdmi_tx_init_panel_info */ /* Table indicating the video format supported by the HDMI TX Core */ -/* Valid Pixel-Clock rates: 25.2MHz, 27MHz, 27.03MHz, 74.25MHz, 148.5MHz */ +/* Valid pclk rates (Mhz): 25.2, 27, 27.03, 74.25, 148.5, 268.5, 297 */ static void hdmi_tx_setup_video_mode_lut(void) { + hdmi_init_supported_video_timings(); + hdmi_set_supported_mode(HDMI_VFRMT_640x480p60_4_3); hdmi_set_supported_mode(HDMI_VFRMT_720x480p60_4_3); hdmi_set_supported_mode(HDMI_VFRMT_720x480p60_16_9); @@ -502,6 +519,11 @@ static void hdmi_tx_setup_video_mode_lut(void) hdmi_set_supported_mode(HDMI_VFRMT_1920x1080p50_16_9); hdmi_set_supported_mode(HDMI_VFRMT_1920x1080i60_16_9); hdmi_set_supported_mode(HDMI_VFRMT_1920x1080p60_16_9); + hdmi_set_supported_mode(HDMI_VFRMT_2560x1600p60_16_9); + hdmi_set_supported_mode(HDMI_VFRMT_3840x2160p30_16_9); + hdmi_set_supported_mode(HDMI_VFRMT_3840x2160p25_16_9); + hdmi_set_supported_mode(HDMI_VFRMT_3840x2160p24_16_9); + hdmi_set_supported_mode(HDMI_VFRMT_4096x2160p24_16_9); } /* hdmi_tx_setup_video_mode_lut */ static int hdmi_tx_read_sink_info(struct hdmi_tx_ctrl *hdmi_ctrl) @@ -780,6 +802,18 @@ static void hdmi_tx_set_avi_infoframe(struct hdmi_tx_ctrl *hdmi_ctrl) case HDMI_VFRMT_720x576p50_4_3: mode = 15; break; + case HDMI_VFRMT_3840x2160p30_16_9: + mode = 16; + break; + case HDMI_VFRMT_3840x2160p25_16_9: + mode = 17; + break; + case HDMI_VFRMT_3840x2160p24_16_9: + mode = 18; + break; + case HDMI_VFRMT_4096x2160p24_16_9: + mode = 19; + break; default: DEV_INFO("%s: mode %d not supported\n", __func__, hdmi_ctrl->video_resolution); @@ -854,12 +888,87 @@ static void hdmi_tx_set_avi_infoframe(struct hdmi_tx_ctrl *hdmi_ctrl) regVal = regVal << 8 | avi_iframe[14]; DSS_REG_W(io, HDMI_AVI_INFO3, regVal); - /* 0x3 for AVI InfFrame enable (every frame) */ + /* AVI InfFrame enable (every frame) */ DSS_REG_W(io, HDMI_INFOFRAME_CTRL0, - DSS_REG_R(io, HDMI_INFOFRAME_CTRL0) | - 0x00000003L); + DSS_REG_R(io, HDMI_INFOFRAME_CTRL0) | BIT(1) | BIT(0)); } /* hdmi_tx_set_avi_infoframe */ +/* todo: add 3D support */ +static void hdmi_tx_set_vendor_specific_infoframe( + struct hdmi_tx_ctrl *hdmi_ctrl) +{ + int i; + u8 vs_iframe[9]; /* two header + length + 6 data */ + u32 sum, reg_val; + u32 hdmi_vic, hdmi_video_format; + struct dss_io_data *io = NULL; + + if (!hdmi_ctrl) { + DEV_ERR("%s: invalid input\n", __func__); + return; + } + + io = &hdmi_ctrl->pdata.io[HDMI_TX_CORE_IO]; + if (!io->base) { + DEV_ERR("%s: Core io is not initialized\n", __func__); + return; + } + + /* HDMI Spec 1.4a Table 8-10 */ + vs_iframe[0] = 0x81; /* type */ + vs_iframe[1] = 0x1; /* version */ + vs_iframe[2] = 0x8; /* length */ + + vs_iframe[3] = 0x0; /* PB0: checksum */ + + /* PB1..PB3: 24 Bit IEEE Registration Code 00_0C_03 */ + vs_iframe[4] = 0x03; + vs_iframe[5] = 0x0C; + vs_iframe[6] = 0x00; + + hdmi_video_format = 0x1; + switch (hdmi_ctrl->video_resolution) { + case HDMI_VFRMT_3840x2160p30_16_9: + hdmi_vic = 0x1; + break; + case HDMI_VFRMT_3840x2160p25_16_9: + hdmi_vic = 0x2; + break; + case HDMI_VFRMT_3840x2160p24_16_9: + hdmi_vic = 0x3; + break; + case HDMI_VFRMT_4096x2160p24_16_9: + hdmi_vic = 0x4; + break; + default: + hdmi_video_format = 0x0; + hdmi_vic = 0x0; + } + + /* PB4: HDMI Video Format[7:5], Reserved[4:0] */ + vs_iframe[7] = (hdmi_video_format << 5) & 0xE0; + + /* PB5: HDMI_VIC or 3D_Structure[7:4], Reserved[3:0] */ + vs_iframe[8] = hdmi_vic; + + /* compute checksum */ + sum = 0; + for (i = 0; i < 9; i++) + sum += vs_iframe[i]; + + sum &= 0xFF; + sum = 256 - sum; + vs_iframe[3] = (u8)sum; + + reg_val = (hdmi_vic << 16) | (vs_iframe[3] << 8) | + (hdmi_video_format << 5) | vs_iframe[2]; + DSS_REG_W(io, HDMI_VENSPEC_INFO0, reg_val); + + /* vendor specific info-frame enable (every frame) */ + DSS_REG_W(io, HDMI_INFOFRAME_CTRL0, + DSS_REG_R(io, HDMI_INFOFRAME_CTRL0) | BIT(13) | BIT(12)); +} /* hdmi_tx_set_vendor_specific_infoframe */ + static void hdmi_tx_set_spd_infoframe(struct hdmi_tx_ctrl *hdmi_ctrl) { u32 packet_header = 0; @@ -1638,11 +1747,11 @@ static int hdmi_tx_start(struct hdmi_tx_ctrl *hdmi_ctrl) switch_set_state(&hdmi_ctrl->audio_sdev, 1); DEV_INFO("%s: hdmi_audio state switch to %d\n", __func__, hdmi_ctrl->audio_sdev.state); - } - hdmi_tx_set_avi_infoframe(hdmi_ctrl); - /* todo: CONFIG_FB_MSM_HDMI_3D */ - hdmi_tx_set_spd_infoframe(hdmi_ctrl); + hdmi_tx_set_avi_infoframe(hdmi_ctrl); + hdmi_tx_set_vendor_specific_infoframe(hdmi_ctrl); + hdmi_tx_set_spd_infoframe(hdmi_ctrl); + } /* todo: HDCP/CEC */ diff --git a/drivers/video/fbdev/msm/mdss_hdmi_util.c b/drivers/video/fbdev/msm/mdss_hdmi_util.c index d1f756c3d17e..81281a42a0c7 100644 --- a/drivers/video/fbdev/msm/mdss_hdmi_util.c +++ b/drivers/video/fbdev/msm/mdss_hdmi_util.c @@ -16,73 +16,24 @@ #include "mdss_hdmi_util.h" static struct hdmi_disp_mode_timing_type - hdmi_supported_video_mode_lut[HDMI_VFRMT_MAX] = { - HDMI_SETTINGS_640x480p60_4_3, - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x480p60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x480p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1280x720p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080i60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480i60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480i60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x240p60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x240p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x480i60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x480i60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x240p60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x240p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480p60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x576p50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x576p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1280x720p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080i50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576i50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576i50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x288p50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x288p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x576i50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x576i50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x288p50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x288p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576p50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080p24_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080p25_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080p30_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x480p60_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x480p60_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x576p50_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_2880x576p50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1250i50_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080i100_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1280x720p100_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x576p100_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x576p100_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576i100_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576i100_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1920x1080i120_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1280x720p120_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x480p120_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x480p120_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480i120_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480i120_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x576p200_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x576p200_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576i200_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x576i200_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x480p240_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_720x480p240_16_9), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480i240_4_3), - VFRMT_NOT_SUPPORTED(HDMI_VFRMT_1440x480i240_16_9), -}; /* hdmi_supported_video_mode_lut */ + hdmi_supported_video_mode_lut[HDMI_VFRMT_MAX]; #define HDMI_SETUP_LUT(MODE) do { \ struct hdmi_disp_mode_timing_type mode = HDMI_SETTINGS_##MODE; \ hdmi_supported_video_mode_lut[mode.video_format] = mode; \ } while (0) +void hdmi_init_supported_video_timings(void) +{ + int i; + + for (i = 0; i < HDMI_VFRMT_MAX; i++) { + struct hdmi_disp_mode_timing_type mode = VFRMT_NOT_SUPPORTED(i); + + hdmi_supported_video_mode_lut[i] = mode; + } +} /* hdmi_init_supported_video_timings */ + const struct hdmi_disp_mode_timing_type *hdmi_get_supported_mode(u32 mode) { const struct hdmi_disp_mode_timing_type *ret = NULL; @@ -203,6 +154,21 @@ void hdmi_set_supported_mode(u32 mode) case HDMI_VFRMT_1920x1080p60_16_9: HDMI_SETUP_LUT(1920x1080p60_16_9); break; + case HDMI_VFRMT_2560x1600p60_16_9: + HDMI_SETUP_LUT(2560x1600p60_16_9); + break; + case HDMI_VFRMT_3840x2160p30_16_9: + HDMI_SETUP_LUT(3840x2160p30_16_9); + break; + case HDMI_VFRMT_3840x2160p25_16_9: + HDMI_SETUP_LUT(3840x2160p25_16_9); + break; + case HDMI_VFRMT_3840x2160p24_16_9: + HDMI_SETUP_LUT(3840x2160p24_16_9); + break; + case HDMI_VFRMT_4096x2160p24_16_9: + HDMI_SETUP_LUT(4096x2160p24_16_9); + break; default: DEV_ERR("%s: unsupported mode=%d\n", __func__, mode); } @@ -270,6 +236,11 @@ const char *hdmi_get_video_fmt_2string(u32 format) case HDMI_VFRMT_720x480p240_16_9: return " 720x 480 p240 16/9"; case HDMI_VFRMT_1440x480i240_4_3: return "1440x 480 i240 4/3"; case HDMI_VFRMT_1440x480i240_16_9: return "1440x 480 i240 16/9"; + case HDMI_VFRMT_2560x1600p60_16_9: return "2560x1600 p60 16/9"; + case HDMI_VFRMT_3840x2160p30_16_9: return "3840x2160 p30 16/9"; + case HDMI_VFRMT_3840x2160p25_16_9: return "3840x2160 p25 16/9"; + case HDMI_VFRMT_3840x2160p24_16_9: return "3840x2160 p24 16/9"; + case HDMI_VFRMT_4096x2160p24_16_9: return "4096x2160 p24 16/9"; default: return "???"; } } /* hdmi_get_video_fmt_2string */ diff --git a/drivers/video/fbdev/msm/mdss_hdmi_util.h b/drivers/video/fbdev/msm/mdss_hdmi_util.h index 07e3bf9ccd6e..45729d3c3b1b 100644 --- a/drivers/video/fbdev/msm/mdss_hdmi_util.h +++ b/drivers/video/fbdev/msm/mdss_hdmi_util.h @@ -216,7 +216,7 @@ #define QFPROM_RAW_FEAT_CONFIG_ROW0_LSB (0x000000F8) #define QFPROM_RAW_FEAT_CONFIG_ROW0_MSB (0x000000FC) -/* all video formats defined by EIA CEA 861D */ +/* all video formats defined by EIA CEA-861-E */ #define HDMI_VFRMT_640x480p60_4_3 0 #define HDMI_VFRMT_720x480p60_4_3 1 #define HDMI_VFRMT_720x480p60_16_9 2 @@ -292,7 +292,18 @@ #define HDMI_VFRMT_1440x480i240_4_3 HDMI_VFRMT_720x480i240_4_3 #define HDMI_VFRMT_720x480i240_16_9 58 #define HDMI_VFRMT_1440x480i240_16_9 HDMI_VFRMT_720x480i240_16_9 -#define HDMI_VFRMT_MAX 59 +/* Video Identification Codes from 65-127 are reserved for the future */ +#define HDMI_VFRMT_END 127 +/* extended video formats */ +#define HDMI_VFRMT_3840x2160p30_16_9 (HDMI_VFRMT_END + 1) +#define HDMI_VFRMT_3840x2160p25_16_9 (HDMI_VFRMT_END + 2) +#define HDMI_VFRMT_3840x2160p24_16_9 (HDMI_VFRMT_END + 3) +#define HDMI_VFRMT_4096x2160p24_16_9 (HDMI_VFRMT_END + 4) +#define HDMI_EVFRMT_END HDMI_VFRMT_4096x2160p24_16_9 +/* DVI only resolutions */ +#define HDMI_VFRMT_2560x1600p60_16_9 (HDMI_EVFRMT_END + 1) +#define DVI_VFRMT_END HDMI_VFRMT_2560x1600p60_16_9 +#define HDMI_VFRMT_MAX (DVI_VFRMT_END + 1) #define HDMI_VFRMT_FORCE_32BIT 0x7FFFFFFF #define VFRMT_NOT_SUPPORTED(VFRMT) \ @@ -349,6 +360,21 @@ #define HDMI_SETTINGS_1920x1080p30_16_9 \ {HDMI_VFRMT_1920x1080p30_16_9, 1920, 88, 44, 148, false, \ 1080, 4, 5, 36, false, 74250, 30000, false, true} +#define HDMI_SETTINGS_2560x1600p60_16_9 \ + {HDMI_VFRMT_2560x1600p60_16_9, 2560, 48, 32, 80, false, \ + 1600, 3, 6, 37, false, 268500, 60000, false, true} +#define HDMI_SETTINGS_3840x2160p30_16_9 \ + {HDMI_VFRMT_3840x2160p30_16_9, 3840, 176, 88, 296, false, \ + 2160, 8, 10, 72, false, 297000, 30000, false, true} +#define HDMI_SETTINGS_3840x2160p25_16_9 \ + {HDMI_VFRMT_3840x2160p25_16_9, 3840, 1056, 88, 296, false, \ + 2160, 8, 10, 72, false, 297000, 25000, false, true} +#define HDMI_SETTINGS_3840x2160p24_16_9 \ + {HDMI_VFRMT_3840x2160p24_16_9, 3840, 1276, 88, 296, false, \ + 2160, 8, 10, 72, false, 297000, 24000, false, true} +#define HDMI_SETTINGS_4096x2160p24_16_9 \ + {HDMI_VFRMT_4096x2160p24_16_9, 4096, 1020, 88, 296, false, \ + 2160, 8, 10, 72, false, 297000, 24000, false, true} #define TOP_AND_BOTTOM 0x10 #define FRAME_PACKING 0x20 @@ -397,6 +423,8 @@ struct hdmi_tx_ddc_data { int retry; }; +/* video timing related utility routines */ +void hdmi_init_supported_video_timings(void); int hdmi_get_video_id_code(struct hdmi_disp_mode_timing_type *timing_in); const struct hdmi_disp_mode_timing_type *hdmi_get_supported_mode(u32 mode); void hdmi_set_supported_mode(u32 mode); |
