ARM: Davinci: FB driver 480P resolution support

parent 1be21cdc
......@@ -150,6 +150,147 @@ static int ths8200_detect_client(struct i2c_adapter *adapter,
return 0;
}
int ths8200_set_480p_mode(void)
{
/* place ths8200 in reset state */
ths8200_write_value(CHIP_CTL_REG, CHIP_SOFTWARE_RESET);
/* take ths8200 out of reset and in normal operation mode */
ths8200_write_value(CHIP_CTL_REG, CHIP_SOFTWARE_OUT_OF_RESET |
CHIP_LOW_FREQUENCY);
/* place color space conversion control in reset state */
ths8200_write_value(CSC_R11_REG, 0x00);
ths8200_write_value(CSC_R21_REG, 0x00);
ths8200_write_value(CSC_R31_REG, 0x00);
ths8200_write_value(CSC_G11_REG, 0x00);
ths8200_write_value(CSC_G21_REG, 0x00);
ths8200_write_value(CSC_G31_REG, 0x00);
ths8200_write_value(CSC_B11_REG, 0x00);
ths8200_write_value(CSC_B21_REG, 0x00);
ths8200_write_value(CSC_B31_REG, 0x00);
ths8200_write_value(CSC_OFFS1_REG, 0x00);
ths8200_write_value(CSC_OFFS12_REG, 0x00);
ths8200_write_value(CSC_OFFS23_REG, 0x00);
ths8200_write_value(CSC_OFFS3_REG,
CSC_BYPASSED |
CSC_PROTECTION_ON);
/* set YCx20 External Sync */
ths8200_write_value(DTG2_CNTL_REG, HS_IN_POSITIVE_POLARITY |
VS_IN_POSITIVE_POLARITY |
HS_OUT_POSITIVE_POLARITY |
VS_OUT_POSITIVE_POLARITY);
/* select the format for the input data manager */
ths8200_write_value(DATA_CNTL_REG, DATA_20BIT_YCBCR_MODE);
/* set the amplitude of the blanking level for the Y channel */
ths8200_write_value(DTG1_Y_SYNC1_LSB_REG, 0xFF);
/* set the amplitude of the negative sync and
equalization/serration/broad pulses for the Y channel */
ths8200_write_value(DTG1_Y_SYNC2_LSB_REG, 0x49);
/* set the amplitude of the positive sync for the Y channel */
ths8200_write_value(DTG1_Y_SYNC3_LSB_REG, 0xFF);
/* set msb for sync1 sync2 and sync3 */
ths8200_write_value(DTG1_Y_SYNC_MSB_REG, 0x13);
/* set the amplitude of the blanking level for the Cb and Cr channels */
ths8200_write_value(DTG1_CBCR_SYNC1_LSB_REG, 0xFF);
/* set the amplitude of the negative sync and
equalization/serration/broad pulses for the
Cb and Cr channels */
ths8200_write_value(DTG1_CBCR_SYNC2_LSB_REG, 0xFF);
/* set the amplitude of the positive sync for the Cb and Cr channels */
ths8200_write_value(DTG1_CBCR_SYNC3_LSB_REG, 0xFF);
/* set msb for sync1 sync2 and sync3 */
ths8200_write_value(DTG1_CBCR_SYNC_MSB_REG, 0x15);
/* set negative hsync width (half of total width) */
ths8200_write_value(DTG1_SPEC_A_REG, 0x28);
/* set end of active video to start of negative sync */
ths8200_write_value(DTG1_SPEC_B_REG, 0x10);
/* set positive hsync width (half of total width) */
ths8200_write_value(DTG1_SPEC_C_REG, 0x28);
/* set LSBs of sync to broad pulse */
ths8200_write_value(DTG1_SPEC_D_LSB_REG, 0x7A);
/* set LSBs of sync to active video */
ths8200_write_value(DTG1_SPEC_E_LSB_REG, 0x7A);
/* set MSB bit of sync to active video width[6]/sync to broad pulse [7] */
ths8200_write_value(DTG1_SPEC_DEH_MSB_REG, 0x00);
/* set broad pulse duration for SDTV (NA) */
ths8200_write_value(DTG1_SPEC_H_LSB_REG, 0x00);
/* set end of active video to sync LSBs [7:0] */
ths8200_write_value(DTG1_SPEC_K_LSB_REG, 0x10);
/* set end of active video to sync MSBs [2:0] */
ths8200_write_value(DTG1_SPEC_K_MSB_REG, 0x00);
/* set MSB bit of total number of pixels per line */
ths8200_write_value(DTG1_TOTAL_PIXELS_MSB_REG, 0x03);
/* set LSB bit of total number of pixels per line */
ths8200_write_value(DTG1_TOTAL_PIXELS_LSB_REG, 0x5A);
/* set MSB and LSB bit of the starting line number
for the DTG when Vsync input or V-bit is
asserted(vertical display control) */
ths8200_write_value(DTG1_FIELDFLIP_LINECNT_MSB_REG, 0x00);
ths8200_write_value(DTG1_FIELDFLIP_LINECNT_LSB_REG, 0x01);
/* set DTG on and set DTG operation mode to
ATSC mode 720P(SMPTE296M progressive)*/
ths8200_write_value(DTG1_MODE_REG, DTG_ON | ATSC_MODE_480P);
/* set MSB bit of number of lines per frame and
number of lines in field 1when in generic mode */
ths8200_write_value(DTG1_FRAME_FILED_SIZE_MSB_REG, 0x27);
/* set LSB bit of number of lines per frame when in generic mode */
ths8200_write_value(DTG1_FRAMESIZE_LSB_REG, 0x0D);
/* set LSB bit of number of lines in field 1 when in generic mode */
ths8200_write_value(DTG1_FIELDSIZE_LSB_REG, 0xFF);
/* set MSB and LSB bit of the number of pixels that the DTG
startup is horizontally delayed with respect to HS input for
dedicated timing modes or EAV input for embedded
timing modes. */
ths8200_write_value(DTG2_HS_IN_DLY_MSB_REG, 0x00);
ths8200_write_value(DTG2_HS_IN_DLY_LSB_REG, 0x40);
/* set MSB and LSB bit of the number of lines that the DTG
startup is vertically delayed with respect to VS input for
dedicated timing modes or the line counter value for
embedded timing.*/
ths8200_write_value(DTG2_VS_IN_DLY_MSB_REG, 0x00);
ths8200_write_value(DTG2_VS_IN_DLY_LSB_REG, 0x00);
/* place ths8200 in reset state */
ths8200_write_value(CHIP_CTL_REG, CHIP_SOFTWARE_RESET);
/* take ths8200 out of reset and in normal operation mode */
ths8200_write_value(CHIP_CTL_REG, CHIP_SOFTWARE_OUT_OF_RESET |
CHIP_LOW_FREQUENCY);
printk(KERN_INFO "THS8200 set video mode as 480p\n");
return 0;
}
int ths8200_set_720p_mode(void)
{
FN_IN;
......@@ -515,6 +656,7 @@ module_exit(ths8200_exit);
EXPORT_SYMBOL(ths8200_set_720p_mode);
EXPORT_SYMBOL(ths8200_set_1080i_mode);
EXPORT_SYMBOL(ths8200_set_480p_mode);
MODULE_DESCRIPTION("THS8200 Video DAC Convert Driver");
MODULE_AUTHOR("Neuros Technology International LLC");
......
......@@ -135,6 +135,11 @@ static struct fb_ops davincifb_ops;
#define DISP_YRES 480
#define DISP_MEMY 576
#define BASEX480P 0x50
#define BASEY480P 0x5
#define DISP_XRES480P 720
#define DISP_YRES480P 480
#define BASEX720P 0x50
#define BASEY720P 0x5
......@@ -1050,11 +1055,15 @@ int __init davincifb_setup(char *options)
} else if (!strncmp(this_opt + 7, "1080i", 5)) {
dmparams.output = HD1080I;
dmparams.format = COMPONENT;
} else if (!strncmp(this_opt + 7, "480p", 4)) {
dmparams.output = HD480P;
dmparams.format = COMPONENT;
}
} else if (!strncmp(this_opt, "format=", 7)) {
if (dmparams.output == LCD ||
dmparams.output == HD720P ||
dmparams.output == HD1080I)
dmparams.output == HD1080I ||
dmparams.output == HD480P)
continue;
if (!strncmp(this_opt + 7, "composite", 9))
dmparams.format = COMPOSITE;
......@@ -1115,6 +1124,7 @@ int __init davincifb_setup(char *options)
(dmparams.output == LCD) ? "LCD" :
(dmparams.output == HD720P) ? "HD720P":
(dmparams.output == HD1080I) ? "HD1080I":
(dmparams.output == HD480P) ? "HD480P":
(dmparams.output == NTSC) ? "NTSC" :
(dmparams.output == PAL) ? "PAL" : "unknown device!",
(dmparams.format == 0) ? "" :
......@@ -1136,6 +1146,9 @@ int __init davincifb_setup(char *options)
} else if (dmparams.output == HD1080I) {
format_xres = DISP_XRES1080I;
format_yres = DISP_YRES1080I;
} else if (dmparams.output == HD480P) {
format_xres = DISP_XRES480P;
format_yres = DISP_YRES480P;
} else {
printk(KERN_INFO
"DaVinci:invalid format..defaulting width to 480\n");
......@@ -1481,6 +1494,106 @@ static void enable_digital_output(bool on)
}
}
/* slow down the VCLK to 27MHZ from
* 74MHZ */
static inline void slow_down_vclk(void)
{
/* set DCLKPTN works as the clock enable for ENC
* clock. */
outl(VENC_DCKCTL_DCKEC, VENC_DCLKCTL);
/* DCLK pattern. The specified bit pattern is output in
* resolution of ENC clock units.*/
outl(0x01, VENC_DCLKPTN0);
/* select MXI mode. Use 27 MHz (from MXI27)
* (DAC clock = 27 MHz).VPBE/Video encoder clock
* is enabled*/
outl(VPSS_CLKCTL_ENABLE_VPBE_CLK,
VPSS_CLKCTL);
}
static void davincifb_480p_component_config(int on)
{
#ifdef CONFIG_THS8200
/* Enable THS8200 DAC output mode as 480P */
ths8200_set_480p_mode();
#endif/* CONFIG_THS8200 */
dispc_reg_out(VENC_VMOD, 0);
/* Set new baseX and baseY */
dispc_reg_out(OSD_BASEPX, BASEX480P);
dispc_reg_out(OSD_BASEPY, BASEY480P);
/* Enable the digtal output */
enable_digital_output(true);
/* slow down the vclk as 27MHZ */
slow_down_vclk();
dispc_reg_merge(PINMUX0, 0, PINMUX0_LFLDEN);
/* Enable OSD0 Window */
dispc_reg_out(OSD_OSDWIN0MD, 0x00002001);
/* Enable OSD1 Window */
dispc_reg_out(OSD_OSDWIN1MD, 0x00008000);
/* Set Timing parameters for 480P frame
(must match what THS8200 expects) */
dispc_reg_out(VENC_HSPLS, BASEX480P);
dispc_reg_out(VENC_VSPLS, BASEY480P);
dispc_reg_out(VENC_HINT, 858 - 1);
dispc_reg_out(VENC_HSTART, 122);
dispc_reg_out(VENC_HVALID, DISP_XRES480P);
dispc_reg_out(VENC_VINT, 525 - 1);
dispc_reg_out(VENC_VSTART, 36);
dispc_reg_out(VENC_VVALID, DISP_YRES480P);
dispc_reg_out(VENC_HSDLY, 0);
dispc_reg_out(VENC_VSDLY, 0);
dispc_reg_out(VENC_YCCCTL, 0);
dispc_reg_out(VENC_VSTARTA, 0);
/* Set VID0 window origin and size */
dispc_reg_out(OSD_VIDWIN0XP, 20);
dispc_reg_out(OSD_VIDWIN0YP, 25);
dispc_reg_out(OSD_VIDWIN0XL, DISP_XRES480P);
dispc_reg_out(OSD_VIDWIN0YL, DISP_YRES480P);
/* Set VID1 window origin and size */
dispc_reg_out(OSD_VIDWIN1XP, 20);
dispc_reg_out(OSD_VIDWIN1YP, 25);
dispc_reg_out(OSD_VIDWIN1XL, DISP_XRES480P);
dispc_reg_out(OSD_VIDWIN1YL, DISP_YRES480P);
/* Set OSD0 window origin and size */
dispc_reg_out(OSD_OSDWIN0XP, 20);
dispc_reg_out(OSD_OSDWIN0YP, 25);
dispc_reg_out(OSD_OSDWIN0XL, DISP_XRES480P);
dispc_reg_out(OSD_OSDWIN0YL, DISP_YRES480P);
/* Set OSD1 window origin and size */
dispc_reg_out(OSD_OSDWIN1XP, 20);
dispc_reg_out(OSD_OSDWIN1YP, 25);
dispc_reg_out(OSD_OSDWIN1XL, DISP_XRES480P);
dispc_reg_out(OSD_OSDWIN1YL, DISP_YRES480P);
/* Set OSD1 window origin and size */
dispc_reg_out(OSD_CURXP, 20);
dispc_reg_out(OSD_CURYP, 25);
dispc_reg_out(OSD_CURXL, DISP_XRES480P);
dispc_reg_out(OSD_CURYL, DISP_YRES480P);
/* Enable all VENC, non-standard timing mode,
master timing, HD, progressive */
dispc_reg_out(VENC_VMOD,
(VENC_VMOD_VENC | VENC_VMOD_VMD | VENC_VMOD_HDMD));
printk(KERN_INFO "Davinci set video mode as 480p\n");
}
static void davincifb_1080i_component_config(int on)
{
if (on) {
......@@ -1895,6 +2008,8 @@ static int davincifb_probe(struct platform_device *pdev)
dm->output_device_config = davincifb_720p_component_config;
else if ((dmparams.output == HD1080I) && (dmparams.format == COMPONENT))
dm->output_device_config = davincifb_1080i_component_config;
else if ((dmparams.output == HD480P) && (dmparams.format == COMPONENT))
dm->output_device_config = davincifb_480p_component_config;
/* Add support for other displays here */
else {
printk(KERN_WARNING "Unsupported output device!\n");
......
......@@ -158,4 +158,11 @@ int ths8200_set_720p_mode(void);
*/
int ths8200_set_1080i_mode(void);
/**
* set THS8200 DAC mode as 480p
*
* @return int
* 0: success, other error.
*/
int ths8200_set_480p_mode(void);
#endif /* End of DAVINCI_THS8200 */
......@@ -216,6 +216,7 @@
#define VENC_SYNCCTL_SYEV (1 << 1)
#define VENC_SYNCCTL_SYEH (1 << 0)
#define VENC_DCKCTL_DCKEC (1 << 11)
#define VPSS_CLKCTL_ENABLE_VPBE_CLK (1 << 3)
/* other VENC registers' bit positions not defined yet */
#define OSD_MODE_CS (1 << 15)
......@@ -436,6 +437,7 @@
#define PAL 2
#define HD720P 3
#define HD1080I 4
#define HD480P 5
#define COMPOSITE 1
#define SVIDEO 2
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment