From f0d08f89ff27f7a600f21f443b6622132c9eb641 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:00:54 +0530 Subject: [PATCH 01/12] OMAPDSS: DISPC: Change return type of dispc_mgr_set_clock_div() dipsc_mgr_set_clock div has an int return type to report errors or success. The function doesn't really check for errors and always returns 0. Change the return type to void. Checking for the correct DISPC clock divider ranges will be done when a DSS2 user does a manager apply. This support will be added later. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/dispc.c | 4 +--- drivers/video/omap2/dss/dpi.c | 10 ++-------- drivers/video/omap2/dss/dsi.c | 6 +----- drivers/video/omap2/dss/dss.h | 2 +- drivers/video/omap2/dss/sdi.c | 5 +---- 5 files changed, 6 insertions(+), 21 deletions(-) diff --git a/drivers/video/omap2/dss/dispc.c b/drivers/video/omap2/dss/dispc.c index d1a7a0c90289..738ad779436f 100644 --- a/drivers/video/omap2/dss/dispc.c +++ b/drivers/video/omap2/dss/dispc.c @@ -3224,15 +3224,13 @@ int dispc_calc_clock_rates(unsigned long dispc_fclk_rate, return 0; } -int dispc_mgr_set_clock_div(enum omap_channel channel, +void dispc_mgr_set_clock_div(enum omap_channel channel, struct dispc_clock_info *cinfo) { DSSDBG("lck = %lu (%u)\n", cinfo->lck, cinfo->lck_div); DSSDBG("pck = %lu (%u)\n", cinfo->pck, cinfo->pck_div); dispc_mgr_set_lcd_divisor(channel, cinfo->lck_div, cinfo->pck_div); - - return 0; } int dispc_mgr_get_clock_div(enum omap_channel channel, diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c index a81b6d6deb57..bb0aad8e960a 100644 --- a/drivers/video/omap2/dss/dpi.c +++ b/drivers/video/omap2/dss/dpi.c @@ -83,11 +83,7 @@ static int dpi_set_dsi_clk(struct omap_dss_device *dssdev, dss_select_dispc_clk_source(dssdev->clocks.dispc.dispc_fclk_src); - r = dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); - if (r) { - dss_select_dispc_clk_source(OMAP_DSS_CLK_SRC_FCK); - return r; - } + dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); *fck = dsi_cinfo.dsi_pll_hsdiv_dispc_clk; *lck_div = dispc_cinfo.lck_div; @@ -112,9 +108,7 @@ static int dpi_set_dispc_clk(struct omap_dss_device *dssdev, if (r) return r; - r = dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); - if (r) - return r; + dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); *fck = dss_cinfo.fck; *lck_div = dispc_cinfo.lck_div; diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c index e0d43b275e3e..5db5147a6ff7 100644 --- a/drivers/video/omap2/dss/dsi.c +++ b/drivers/video/omap2/dss/dsi.c @@ -4451,11 +4451,7 @@ static int dsi_configure_dispc_clocks(struct omap_dss_device *dssdev) return r; } - r = dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); - if (r) { - DSSERR("Failed to set dispc clocks\n"); - return r; - } + dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); return 0; } diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h index 6c5ecf02759e..a638846559ce 100644 --- a/drivers/video/omap2/dss/dss.h +++ b/drivers/video/omap2/dss/dss.h @@ -425,7 +425,7 @@ void dispc_mgr_set_timings(enum omap_channel channel, unsigned long dispc_mgr_lclk_rate(enum omap_channel channel); unsigned long dispc_mgr_pclk_rate(enum omap_channel channel); unsigned long dispc_core_clk_rate(void); -int dispc_mgr_set_clock_div(enum omap_channel channel, +void dispc_mgr_set_clock_div(enum omap_channel channel, struct dispc_clock_info *cinfo); int dispc_mgr_get_clock_div(enum omap_channel channel, struct dispc_clock_info *cinfo); diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c index 0fcd4d7e202e..73f8357955ae 100644 --- a/drivers/video/omap2/dss/sdi.c +++ b/drivers/video/omap2/dss/sdi.c @@ -106,9 +106,7 @@ int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) if (r) goto err_set_dss_clock_div; - r = dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); - if (r) - goto err_set_dispc_clock_div; + dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); dss_sdi_init(dssdev->phy.sdi.datapairs); r = dss_sdi_enable(); @@ -125,7 +123,6 @@ int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) err_mgr_enable: dss_sdi_disable(); err_sdi_enable: -err_set_dispc_clock_div: err_set_dss_clock_div: err_calc_clock_div: dispc_runtime_put(); From c56fb3ef051c6cafca48c0ddcf52a570d6257574 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:03:48 +0530 Subject: [PATCH 02/12] OMAPDSS: Add struct to hold LCD overlay manager configuration Create a struct dss_lcd_mgr_config which holds LCD overlay manager related parameters. These are currently partially contained in the omap_dss_device connected to the manager, and the rest are in the interface driver. The parameters are directly written to the DISPC registers in the interface drivers. These should eventually be applied at the correct time using the shadow register programming model. This struct would help in grouping these parameters so that they can be applied together. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/dss.h | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h index a638846559ce..061c95e20d49 100644 --- a/drivers/video/omap2/dss/dss.h +++ b/drivers/video/omap2/dss/dss.h @@ -158,6 +158,19 @@ struct reg_field { u8 low; }; +struct dss_lcd_mgr_config { + enum dss_io_pad_mode io_pad_mode; + + bool stallmode; + bool fifohandcheck; + + struct dispc_clock_info clock_info; + + int video_port_width; + + int lcden_sig_polarity; +}; + struct seq_file; struct platform_device; From 5cf9a264115da9b69a2cdbe43ea0e741844bfef6 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:19:13 +0530 Subject: [PATCH 03/12] OMAPDSS: DPI: Configure dss_lcd_mgr_config struct with lcd manager parameters Create a dss_lcd_mgr_config struct instance in DPI. Fill up all the parameters of the struct with configurations held by the panel, and the configurations required by DPI. Use these to write to the DISPC registers. These direct register writes would be later replaced by a function which applies the configuration using the shadow register programming model. The DISPC_DIVISORo registers were written in the functions dpi_set_dispc_clk() and dpi_set_dsi_clk(), now they just fill up the dispc_clock_info parameter in mgr_config. They are written later in dpi_config_lcd_manager. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/dpi.c | 37 ++++++++++++++++++++++++++--------- 1 file changed, 28 insertions(+), 9 deletions(-) diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c index bb0aad8e960a..6664775c3e45 100644 --- a/drivers/video/omap2/dss/dpi.c +++ b/drivers/video/omap2/dss/dpi.c @@ -38,6 +38,8 @@ static struct { struct regulator *vdds_dsi_reg; struct platform_device *dsidev; + + struct dss_lcd_mgr_config mgr_config; } dpi; static struct platform_device *dpi_get_dsidev(enum omap_dss_clk_source clk) @@ -83,7 +85,7 @@ static int dpi_set_dsi_clk(struct omap_dss_device *dssdev, dss_select_dispc_clk_source(dssdev->clocks.dispc.dispc_fclk_src); - dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); + dpi.mgr_config.clock_info = dispc_cinfo; *fck = dsi_cinfo.dsi_pll_hsdiv_dispc_clk; *lck_div = dispc_cinfo.lck_div; @@ -108,7 +110,7 @@ static int dpi_set_dispc_clk(struct omap_dss_device *dssdev, if (r) return r; - dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); + dpi.mgr_config.clock_info = dispc_cinfo; *fck = dss_cinfo.fck; *lck_div = dispc_cinfo.lck_div; @@ -149,15 +151,32 @@ static int dpi_set_mode(struct omap_dss_device *dssdev) return 0; } -static void dpi_basic_init(struct omap_dss_device *dssdev) +static void dpi_config_lcd_manager(struct omap_dss_device *dssdev) { - dispc_mgr_set_io_pad_mode(DSS_IO_PAD_MODE_BYPASS); - dispc_mgr_enable_stallmode(dssdev->manager->id, false); + dpi.mgr_config.io_pad_mode = DSS_IO_PAD_MODE_BYPASS; - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); + dpi.mgr_config.stallmode = false; + dpi.mgr_config.fifohandcheck = false; + + dpi.mgr_config.video_port_width = dssdev->phy.dpi.data_lines; + + dpi.mgr_config.lcden_sig_polarity = 0; + + dispc_mgr_set_io_pad_mode(dpi.mgr_config.io_pad_mode); + dispc_mgr_enable_stallmode(dssdev->manager->id, + dpi.mgr_config.stallmode); + dispc_mgr_enable_fifohandcheck(dssdev->manager->id, + dpi.mgr_config.fifohandcheck); dispc_mgr_set_tft_data_lines(dssdev->manager->id, - dssdev->phy.dpi.data_lines); + dpi.mgr_config.video_port_width); + + dispc_mgr_set_clock_div(dssdev->manager->id, + &dpi.mgr_config.clock_info); + + dispc_lcd_enable_signal_polarity(dpi.mgr_config.lcden_sig_polarity); + + dispc_mgr_set_lcd_type_tft(dssdev->manager->id); } int omapdss_dpi_display_enable(struct omap_dss_device *dssdev) @@ -190,8 +209,6 @@ int omapdss_dpi_display_enable(struct omap_dss_device *dssdev) if (r) goto err_get_dispc; - dpi_basic_init(dssdev); - if (dpi_use_dsi_pll(dssdev)) { r = dsi_runtime_get(dpi.dsidev); if (r) @@ -206,6 +223,8 @@ int omapdss_dpi_display_enable(struct omap_dss_device *dssdev) if (r) goto err_set_mode; + dpi_config_lcd_manager(dssdev); + mdelay(2); r = dss_mgr_enable(dssdev->manager); From bc2e60a69fead72cfff97ddccb4cca5ce75164a8 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Mon, 25 Jun 2012 11:24:10 +0530 Subject: [PATCH 04/12] OMAPDSS: RFBI: Configure dss_lcd_mgr_config struct with lcd manager parameters Create a dss_lcd_mgr_config struct instance in RFBI. Fill up all the parameters of the struct with configurations held by the panel, and the configurations required by RFBI. Use these to write to the DISPC registers. These direct register writes would be later replaced by a function which applies the configuration using the shadow register programming model. Create function rfbi_config_lcd_manager() which fills up the mgr_config parameters and writes to the DISPC regs. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/rfbi.c | 34 ++++++++++++++++++++++++++++------ 1 file changed, 28 insertions(+), 6 deletions(-) diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c index 539d709c6c0e..0dc8dac1c07c 100644 --- a/drivers/video/omap2/dss/rfbi.c +++ b/drivers/video/omap2/dss/rfbi.c @@ -859,6 +859,33 @@ static void rfbi_dump_regs(struct seq_file *s) #undef DUMPREG } +static void rfbi_config_lcd_manager(struct omap_dss_device *dssdev) +{ + struct dss_lcd_mgr_config mgr_config; + + mgr_config.io_pad_mode = DSS_IO_PAD_MODE_RFBI; + + mgr_config.stallmode = true; + /* Do we need fifohandcheck for RFBI? */ + mgr_config.fifohandcheck = false; + + mgr_config.video_port_width = dssdev->ctrl.pixel_size; + mgr_config.lcden_sig_polarity = 0; + + dispc_mgr_set_io_pad_mode(mgr_config.io_pad_mode); + + dispc_mgr_enable_stallmode(dssdev->manager->id, mgr_config.stallmode); + dispc_mgr_enable_fifohandcheck(dssdev->manager->id, + mgr_config.fifohandcheck); + + dispc_mgr_set_tft_data_lines(dssdev->manager->id, + mgr_config.video_port_width); + + dispc_lcd_enable_signal_polarity(mgr_config.lcden_sig_polarity); + + dispc_mgr_set_lcd_type_tft(dssdev->manager->id); +} + int omapdss_rfbi_display_enable(struct omap_dss_device *dssdev) { int r; @@ -885,12 +912,7 @@ int omapdss_rfbi_display_enable(struct omap_dss_device *dssdev) goto err1; } - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); - - dispc_mgr_set_io_pad_mode(DSS_IO_PAD_MODE_RFBI); - dispc_mgr_enable_stallmode(dssdev->manager->id, true); - - dispc_mgr_set_tft_data_lines(dssdev->manager->id, dssdev->ctrl.pixel_size); + rfbi_config_lcd_manager(dssdev); rfbi_configure(dssdev->phy.rfbi.channel, dssdev->ctrl.pixel_size, From 7d2572f8b3df70c29527e5579b4b67a76ba8477d Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:31:07 +0530 Subject: [PATCH 05/12] OMAPDSS: DSI: Configure dss_lcd_mgr_config struct with lcd manager parameters Create a dss_lcd_mgr_config struct instance in DSI. Fill up all the parameters of the struct with configurations held by the panel, and the configurations required by DSI. Use these to write to the DISPC registers. These direct register writes would be later replaced by a function which applies the configuration using the shadow register programming model. The function dsi_configure_dispc_clocks() is now called in dsi_display_init_dispc(), this lets all the lcd manager related configurations happen in the same place. The DISPC_DIVISORo register was written in dsi_configure_dispc_clock(), now it just fills up the dispc_clock_info parameter in mgr_config. The clock_info is written later in dsi_display_init_dispc(). Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/dsi.c | 100 ++++++++++++++++++++++------------ 1 file changed, 64 insertions(+), 36 deletions(-) diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c index 5db5147a6ff7..f51df30d8c15 100644 --- a/drivers/video/omap2/dss/dsi.c +++ b/drivers/video/omap2/dss/dsi.c @@ -331,6 +331,8 @@ struct dsi_data { unsigned num_lanes_used; unsigned scp_clk_refcount; + + struct dss_lcd_mgr_config mgr_config; }; struct dsi_packet_sent_handler_data { @@ -4337,14 +4339,40 @@ EXPORT_SYMBOL(omap_dsi_update); /* Display funcs */ +static int dsi_configure_dispc_clocks(struct omap_dss_device *dssdev) +{ + struct platform_device *dsidev = dsi_get_dsidev_from_dssdev(dssdev); + struct dsi_data *dsi = dsi_get_dsidrv_data(dsidev); + struct dispc_clock_info dispc_cinfo; + int r; + unsigned long long fck; + + fck = dsi_get_pll_hsdiv_dispc_rate(dsidev); + + dispc_cinfo.lck_div = dssdev->clocks.dispc.channel.lck_div; + dispc_cinfo.pck_div = dssdev->clocks.dispc.channel.pck_div; + + r = dispc_calc_clock_rates(fck, &dispc_cinfo); + if (r) { + DSSERR("Failed to calc dispc clocks\n"); + return r; + } + + dsi->mgr_config.clock_info = dispc_cinfo; + + return 0; +} + static int dsi_display_init_dispc(struct omap_dss_device *dssdev) { - int r; + struct platform_device *dsidev = dsi_get_dsidev_from_dssdev(dssdev); + struct dsi_data *dsi = dsi_get_dsidrv_data(dsidev); struct omap_video_timings timings; + int r; + u32 irq = 0; if (dssdev->panel.dsi_mode == OMAP_DSS_DSI_CMD_MODE) { u16 dw, dh; - u32 irq; dssdev->driver->get_resolution(dssdev, &dw, &dh); @@ -4363,16 +4391,16 @@ static int dsi_display_init_dispc(struct omap_dss_device *dssdev) (void *) dssdev, irq); if (r) { DSSERR("can't get FRAMEDONE irq\n"); - return r; + goto err; } - dispc_mgr_enable_stallmode(dssdev->manager->id, true); - dispc_mgr_enable_fifohandcheck(dssdev->manager->id, 1); + dsi->mgr_config.stallmode = true; + dsi->mgr_config.fifohandcheck = true; } else { timings = dssdev->panel.timings; - dispc_mgr_enable_stallmode(dssdev->manager->id, false); - dispc_mgr_enable_fifohandcheck(dssdev->manager->id, 0); + dsi->mgr_config.stallmode = false; + dsi->mgr_config.fifohandcheck = false; } /* @@ -4388,12 +4416,39 @@ static int dsi_display_init_dispc(struct omap_dss_device *dssdev) dss_mgr_set_timings(dssdev->manager, &timings); - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); + r = dsi_configure_dispc_clocks(dssdev); + if (r) + goto err1; + + dsi->mgr_config.io_pad_mode = DSS_IO_PAD_MODE_BYPASS; + dsi->mgr_config.video_port_width = + dsi_get_pixel_size(dssdev->panel.dsi_pix_fmt); + dsi->mgr_config.lcden_sig_polarity = 0; + + dispc_mgr_set_io_pad_mode(dsi->mgr_config.io_pad_mode); + + dispc_mgr_enable_stallmode(dssdev->manager->id, + dsi->mgr_config.stallmode); + dispc_mgr_enable_fifohandcheck(dssdev->manager->id, + dsi->mgr_config.fifohandcheck); + + dispc_mgr_set_clock_div(dssdev->manager->id, + &dsi->mgr_config.clock_info); dispc_mgr_set_tft_data_lines(dssdev->manager->id, - dsi_get_pixel_size(dssdev->panel.dsi_pix_fmt)); + dsi->mgr_config.video_port_width); + + dispc_lcd_enable_signal_polarity(dsi->mgr_config.lcden_sig_polarity); + + dispc_mgr_set_lcd_type_tft(dssdev->manager->id); return 0; +err1: + if (dssdev->panel.dsi_mode == OMAP_DSS_DSI_CMD_MODE) + omap_dispc_unregister_isr(dsi_framedone_irq_callback, + (void *) dssdev, irq); +err: + return r; } static void dsi_display_uninit_dispc(struct omap_dss_device *dssdev) @@ -4433,29 +4488,6 @@ static int dsi_configure_dsi_clocks(struct omap_dss_device *dssdev) return 0; } -static int dsi_configure_dispc_clocks(struct omap_dss_device *dssdev) -{ - struct platform_device *dsidev = dsi_get_dsidev_from_dssdev(dssdev); - struct dispc_clock_info dispc_cinfo; - int r; - unsigned long long fck; - - fck = dsi_get_pll_hsdiv_dispc_rate(dsidev); - - dispc_cinfo.lck_div = dssdev->clocks.dispc.channel.lck_div; - dispc_cinfo.pck_div = dssdev->clocks.dispc.channel.pck_div; - - r = dispc_calc_clock_rates(fck, &dispc_cinfo); - if (r) { - DSSERR("Failed to calc dispc clocks\n"); - return r; - } - - dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); - - return 0; -} - static int dsi_display_init_dsi(struct omap_dss_device *dssdev) { struct platform_device *dsidev = dsi_get_dsidev_from_dssdev(dssdev); @@ -4477,10 +4509,6 @@ static int dsi_display_init_dsi(struct omap_dss_device *dssdev) DSSDBG("PLL OK\n"); - r = dsi_configure_dispc_clocks(dssdev); - if (r) - goto err2; - r = dsi_cio_init(dssdev); if (r) goto err2; From 37a579903efaf25b74fcf1fd645817af94d36152 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:33:18 +0530 Subject: [PATCH 06/12] OMAPDSS: SDI: Configure dss_lcd_mgr_config struct with lcd manager parameters Create a dss_lcd_mgr_config struct instance in SDI. Fill up all the parameters of the struct with configurations held by the panel, and the configurations required by SDI. Use these to write to the DISPC registers. These direct register writes would be later replaced by a function which applies the configuration using the shadow register programming model. Create function sdi_config_lcd_manager() which fills the mgr_config parameters and writes to the DISPC registers. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/sdi.c | 42 ++++++++++++++++++++++------------- 1 file changed, 26 insertions(+), 16 deletions(-) diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c index 73f8357955ae..f102eae6e2af 100644 --- a/drivers/video/omap2/dss/sdi.c +++ b/drivers/video/omap2/dss/sdi.c @@ -32,18 +32,34 @@ static struct { bool update_enabled; struct regulator *vdds_sdi_reg; + + struct dss_lcd_mgr_config mgr_config; } sdi; -static void sdi_basic_init(struct omap_dss_device *dssdev) - +static void sdi_config_lcd_manager(struct omap_dss_device *dssdev) { - dispc_mgr_set_io_pad_mode(DSS_IO_PAD_MODE_BYPASS); - dispc_mgr_enable_stallmode(dssdev->manager->id, false); + sdi.mgr_config.io_pad_mode = DSS_IO_PAD_MODE_BYPASS; + + sdi.mgr_config.stallmode = false; + sdi.mgr_config.fifohandcheck = false; + + sdi.mgr_config.video_port_width = 24; + sdi.mgr_config.lcden_sig_polarity = 1; + + dispc_mgr_set_io_pad_mode(sdi.mgr_config.io_pad_mode); + dispc_mgr_enable_stallmode(dssdev->manager->id, + sdi.mgr_config.stallmode); + dispc_mgr_enable_fifohandcheck(dssdev->manager->id, + sdi.mgr_config.fifohandcheck); + + dispc_mgr_set_clock_div(dssdev->manager->id, + &sdi.mgr_config.clock_info); + + dispc_mgr_set_tft_data_lines(dssdev->manager->id, + sdi.mgr_config.video_port_width); + dispc_lcd_enable_signal_polarity(sdi.mgr_config.lcden_sig_polarity); dispc_mgr_set_lcd_type_tft(dssdev->manager->id); - - dispc_mgr_set_tft_data_lines(dssdev->manager->id, 24); - dispc_lcd_enable_signal_polarity(1); } int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) @@ -51,8 +67,6 @@ int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) struct omap_video_timings *t = &dssdev->panel.timings; struct dss_clock_info dss_cinfo; struct dispc_clock_info dispc_cinfo; - u16 lck_div, pck_div; - unsigned long fck; unsigned long pck; int r; @@ -75,8 +89,6 @@ int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) if (r) goto err_get_dispc; - sdi_basic_init(dssdev); - /* 15.5.9.1.2 */ dssdev->panel.timings.data_pclk_edge = OMAPDSS_DRIVE_SIG_RISING_EDGE; dssdev->panel.timings.sync_pclk_edge = OMAPDSS_DRIVE_SIG_RISING_EDGE; @@ -85,11 +97,9 @@ int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) if (r) goto err_calc_clock_div; - fck = dss_cinfo.fck; - lck_div = dispc_cinfo.lck_div; - pck_div = dispc_cinfo.pck_div; + sdi.mgr_config.clock_info = dispc_cinfo; - pck = fck / lck_div / pck_div / 1000; + pck = dss_cinfo.fck / dispc_cinfo.lck_div / dispc_cinfo.pck_div / 1000; if (pck != t->pixel_clock) { DSSWARN("Could not find exact pixel clock. Requested %d kHz, " @@ -106,7 +116,7 @@ int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) if (r) goto err_set_dss_clock_div; - dispc_mgr_set_clock_div(dssdev->manager->id, &dispc_cinfo); + sdi_config_lcd_manager(dssdev); dss_sdi_init(dssdev->phy.sdi.datapairs); r = dss_sdi_enable(); From f476ae9dab3234532d41d36beb4ba7be838fa786 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:37:03 +0530 Subject: [PATCH 07/12] OMAPDSS: APPLY: Remove DISPC writes to manager's lcd parameters in interface drivers Replace the DISPC fuctions used to configure LCD channel related manager parameters with dss_mgr_set_lcd_config() in APPLY. This function ensures that the DISPC registers are written at the right time by using the shadow register programming model. The LCD manager configurations is stored as a private data of manager in APPLY. It is treated as an extra info as it's the panel drivers which trigger this apply via interface drivers, and not a DSS2 user like omapfb or omapdrm. Storing LCD manager related properties in APPLY also prevents the need to refer to the panel connected to the manager for information. This helps in making the DSS driver less dependent on panel. A helper function is added to check whether the manager is LCD or TV. The direct DISPC register writes are removed from the interface drivers. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/apply.c | 68 +++++++++++++++++++++++++++++++++ drivers/video/omap2/dss/dpi.c | 16 +------- drivers/video/omap2/dss/dsi.c | 17 +-------- drivers/video/omap2/dss/dss.h | 11 ++++++ drivers/video/omap2/dss/rfbi.c | 13 +------ drivers/video/omap2/dss/sdi.c | 15 +------- 6 files changed, 83 insertions(+), 57 deletions(-) diff --git a/drivers/video/omap2/dss/apply.c b/drivers/video/omap2/dss/apply.c index 3ce7a3ec6224..30915bdcb237 100644 --- a/drivers/video/omap2/dss/apply.c +++ b/drivers/video/omap2/dss/apply.c @@ -104,6 +104,7 @@ struct mgr_priv_data { bool shadow_extra_info_dirty; struct omap_video_timings timings; + struct dss_lcd_mgr_config lcd_config; }; static struct { @@ -137,6 +138,7 @@ static struct mgr_priv_data *get_mgr_priv(struct omap_overlay_manager *mgr) void dss_apply_init(void) { const int num_ovls = dss_feat_get_num_ovls(); + struct mgr_priv_data *mp; int i; spin_lock_init(&data_lock); @@ -168,6 +170,16 @@ void dss_apply_init(void) op->user_info = op->info; } + + /* + * Initialize some of the lcd_config fields for TV manager, this lets + * us prevent checking if the manager is LCD or TV at some places + */ + mp = &dss_data.mgr_priv_data_array[OMAP_DSS_CHANNEL_DIGIT]; + + mp->lcd_config.video_port_width = 24; + mp->lcd_config.clock_info.lck_div = 1; + mp->lcd_config.clock_info.pck_div = 1; } static bool ovl_manual_update(struct omap_overlay *ovl) @@ -633,6 +645,24 @@ static void dss_mgr_write_regs_extra(struct omap_overlay_manager *mgr) dispc_mgr_set_timings(mgr->id, &mp->timings); + /* lcd_config parameters */ + if (dss_mgr_is_lcd(mgr->id)) { + dispc_mgr_set_io_pad_mode(mp->lcd_config.io_pad_mode); + + dispc_mgr_enable_stallmode(mgr->id, mp->lcd_config.stallmode); + dispc_mgr_enable_fifohandcheck(mgr->id, + mp->lcd_config.fifohandcheck); + + dispc_mgr_set_clock_div(mgr->id, &mp->lcd_config.clock_info); + + dispc_mgr_set_tft_data_lines(mgr->id, + mp->lcd_config.video_port_width); + + dispc_lcd_enable_signal_polarity(mp->lcd_config.lcden_sig_polarity); + + dispc_mgr_set_lcd_type_tft(mgr->id); + } + mp->extra_info_dirty = false; if (mp->updating) mp->shadow_extra_info_dirty = true; @@ -1292,6 +1322,44 @@ void dss_mgr_set_timings(struct omap_overlay_manager *mgr, mutex_unlock(&apply_lock); } +static void dss_apply_mgr_lcd_config(struct omap_overlay_manager *mgr, + const struct dss_lcd_mgr_config *config) +{ + struct mgr_priv_data *mp = get_mgr_priv(mgr); + + mp->lcd_config = *config; + mp->extra_info_dirty = true; +} + +void dss_mgr_set_lcd_config(struct omap_overlay_manager *mgr, + const struct dss_lcd_mgr_config *config) +{ + unsigned long flags; + struct mgr_priv_data *mp = get_mgr_priv(mgr); + + mutex_lock(&apply_lock); + + if (mp->enabled) { + DSSERR("cannot apply lcd config for %s: manager needs to be disabled\n", + mgr->name); + goto out; + } + + spin_lock_irqsave(&data_lock, flags); + + dss_apply_mgr_lcd_config(mgr, config); + + dss_write_regs(); + dss_set_go_bits(); + + spin_unlock_irqrestore(&data_lock, flags); + + wait_pending_extra_info_updates(); + +out: + mutex_unlock(&apply_lock); +} + int dss_ovl_set_info(struct omap_overlay *ovl, struct omap_overlay_info *info) { diff --git a/drivers/video/omap2/dss/dpi.c b/drivers/video/omap2/dss/dpi.c index 6664775c3e45..3266be23fc0d 100644 --- a/drivers/video/omap2/dss/dpi.c +++ b/drivers/video/omap2/dss/dpi.c @@ -162,21 +162,7 @@ static void dpi_config_lcd_manager(struct omap_dss_device *dssdev) dpi.mgr_config.lcden_sig_polarity = 0; - dispc_mgr_set_io_pad_mode(dpi.mgr_config.io_pad_mode); - dispc_mgr_enable_stallmode(dssdev->manager->id, - dpi.mgr_config.stallmode); - dispc_mgr_enable_fifohandcheck(dssdev->manager->id, - dpi.mgr_config.fifohandcheck); - - dispc_mgr_set_tft_data_lines(dssdev->manager->id, - dpi.mgr_config.video_port_width); - - dispc_mgr_set_clock_div(dssdev->manager->id, - &dpi.mgr_config.clock_info); - - dispc_lcd_enable_signal_polarity(dpi.mgr_config.lcden_sig_polarity); - - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); + dss_mgr_set_lcd_config(dssdev->manager, &dpi.mgr_config); } int omapdss_dpi_display_enable(struct omap_dss_device *dssdev) diff --git a/drivers/video/omap2/dss/dsi.c b/drivers/video/omap2/dss/dsi.c index f51df30d8c15..b07e8864f82f 100644 --- a/drivers/video/omap2/dss/dsi.c +++ b/drivers/video/omap2/dss/dsi.c @@ -4425,22 +4425,7 @@ static int dsi_display_init_dispc(struct omap_dss_device *dssdev) dsi_get_pixel_size(dssdev->panel.dsi_pix_fmt); dsi->mgr_config.lcden_sig_polarity = 0; - dispc_mgr_set_io_pad_mode(dsi->mgr_config.io_pad_mode); - - dispc_mgr_enable_stallmode(dssdev->manager->id, - dsi->mgr_config.stallmode); - dispc_mgr_enable_fifohandcheck(dssdev->manager->id, - dsi->mgr_config.fifohandcheck); - - dispc_mgr_set_clock_div(dssdev->manager->id, - &dsi->mgr_config.clock_info); - - dispc_mgr_set_tft_data_lines(dssdev->manager->id, - dsi->mgr_config.video_port_width); - - dispc_lcd_enable_signal_polarity(dsi->mgr_config.lcden_sig_polarity); - - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); + dss_mgr_set_lcd_config(dssdev->manager, &dsi->mgr_config); return 0; err1: diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h index 061c95e20d49..80ed88f53c19 100644 --- a/drivers/video/omap2/dss/dss.h +++ b/drivers/video/omap2/dss/dss.h @@ -207,6 +207,8 @@ int dss_mgr_set_device(struct omap_overlay_manager *mgr, int dss_mgr_unset_device(struct omap_overlay_manager *mgr); void dss_mgr_set_timings(struct omap_overlay_manager *mgr, struct omap_video_timings *timings); +void dss_mgr_set_lcd_config(struct omap_overlay_manager *mgr, + const struct dss_lcd_mgr_config *config); const struct omap_video_timings *dss_mgr_get_timings(struct omap_overlay_manager *mgr); bool dss_ovl_is_enabled(struct omap_overlay *ovl); @@ -244,6 +246,15 @@ int dss_mgr_check(struct omap_overlay_manager *mgr, const struct omap_video_timings *mgr_timings, struct omap_overlay_info **overlay_infos); +static inline bool dss_mgr_is_lcd(enum omap_channel id) +{ + if (id == OMAP_DSS_CHANNEL_LCD || id == OMAP_DSS_CHANNEL_LCD2 || + id == OMAP_DSS_CHANNEL_LCD3) + return true; + else + return false; +} + /* overlay */ void dss_init_overlays(struct platform_device *pdev); void dss_uninit_overlays(struct platform_device *pdev); diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c index 0dc8dac1c07c..cc22426144cb 100644 --- a/drivers/video/omap2/dss/rfbi.c +++ b/drivers/video/omap2/dss/rfbi.c @@ -872,18 +872,7 @@ static void rfbi_config_lcd_manager(struct omap_dss_device *dssdev) mgr_config.video_port_width = dssdev->ctrl.pixel_size; mgr_config.lcden_sig_polarity = 0; - dispc_mgr_set_io_pad_mode(mgr_config.io_pad_mode); - - dispc_mgr_enable_stallmode(dssdev->manager->id, mgr_config.stallmode); - dispc_mgr_enable_fifohandcheck(dssdev->manager->id, - mgr_config.fifohandcheck); - - dispc_mgr_set_tft_data_lines(dssdev->manager->id, - mgr_config.video_port_width); - - dispc_lcd_enable_signal_polarity(mgr_config.lcden_sig_polarity); - - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); + dss_mgr_set_lcd_config(dssdev->manager, &mgr_config); } int omapdss_rfbi_display_enable(struct omap_dss_device *dssdev) diff --git a/drivers/video/omap2/dss/sdi.c b/drivers/video/omap2/dss/sdi.c index f102eae6e2af..5d31699fbd3c 100644 --- a/drivers/video/omap2/dss/sdi.c +++ b/drivers/video/omap2/dss/sdi.c @@ -46,20 +46,7 @@ static void sdi_config_lcd_manager(struct omap_dss_device *dssdev) sdi.mgr_config.video_port_width = 24; sdi.mgr_config.lcden_sig_polarity = 1; - dispc_mgr_set_io_pad_mode(sdi.mgr_config.io_pad_mode); - dispc_mgr_enable_stallmode(dssdev->manager->id, - sdi.mgr_config.stallmode); - dispc_mgr_enable_fifohandcheck(dssdev->manager->id, - sdi.mgr_config.fifohandcheck); - - dispc_mgr_set_clock_div(dssdev->manager->id, - &sdi.mgr_config.clock_info); - - dispc_mgr_set_tft_data_lines(dssdev->manager->id, - sdi.mgr_config.video_port_width); - dispc_lcd_enable_signal_polarity(sdi.mgr_config.lcden_sig_polarity); - - dispc_mgr_set_lcd_type_tft(dssdev->manager->id); + dss_mgr_set_lcd_config(dssdev->manager, &sdi.mgr_config); } int omapdss_sdi_display_enable(struct omap_dss_device *dssdev) From 6e5435958c6ee4fa2142d298d836dd78b8353f66 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Wed, 23 May 2012 17:01:35 +0530 Subject: [PATCH 08/12] OMAPDSS: MANAGER: Check LCD related overlay manager parameters The LCD related manager configurations are a part of the manager's private data in APPLY. Pass this to dss_lcd_mgr_config to dss_mgr_check and create a function to check the validity of some of the configurations. To check some of the configurations, we require information of interface to which the manager output is connected. These can be added once interfaces are represented as an entity. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/apply.c | 2 +- drivers/video/omap2/dss/dss.h | 1 + drivers/video/omap2/dss/manager.c | 35 +++++++++++++++++++++++++++++++ 3 files changed, 37 insertions(+), 1 deletion(-) diff --git a/drivers/video/omap2/dss/apply.c b/drivers/video/omap2/dss/apply.c index 30915bdcb237..8c94fbe21822 100644 --- a/drivers/video/omap2/dss/apply.c +++ b/drivers/video/omap2/dss/apply.c @@ -226,7 +226,7 @@ static int dss_check_settings_low(struct omap_overlay_manager *mgr, ois[ovl->id] = oi; } - return dss_mgr_check(mgr, mi, &mp->timings, ois); + return dss_mgr_check(mgr, mi, &mp->timings, &mp->lcd_config, ois); } /* diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h index 80ed88f53c19..f87a4318d564 100644 --- a/drivers/video/omap2/dss/dss.h +++ b/drivers/video/omap2/dss/dss.h @@ -244,6 +244,7 @@ int dss_mgr_check_timings(struct omap_overlay_manager *mgr, int dss_mgr_check(struct omap_overlay_manager *mgr, struct omap_overlay_manager_info *info, const struct omap_video_timings *mgr_timings, + const struct dss_lcd_mgr_config *config, struct omap_overlay_info **overlay_infos); static inline bool dss_mgr_is_lcd(enum omap_channel id) diff --git a/drivers/video/omap2/dss/manager.c b/drivers/video/omap2/dss/manager.c index a51eb060c142..53710fadc82d 100644 --- a/drivers/video/omap2/dss/manager.c +++ b/drivers/video/omap2/dss/manager.c @@ -665,9 +665,40 @@ int dss_mgr_check_timings(struct omap_overlay_manager *mgr, return 0; } +static int dss_mgr_check_lcd_config(struct omap_overlay_manager *mgr, + const struct dss_lcd_mgr_config *config) +{ + struct dispc_clock_info cinfo = config->clock_info; + int dl = config->video_port_width; + bool stallmode = config->stallmode; + bool fifohandcheck = config->fifohandcheck; + + if (cinfo.lck_div < 1 || cinfo.lck_div > 255) + return -EINVAL; + + if (cinfo.pck_div < 1 || cinfo.pck_div > 255) + return -EINVAL; + + if (dl != 12 && dl != 16 && dl != 18 && dl != 24) + return -EINVAL; + + /* fifohandcheck should be used only with stallmode */ + if (stallmode == false && fifohandcheck == true) + return -EINVAL; + + /* + * io pad mode can be only checked by using dssdev connected to the + * manager. Ignore checking these for now, add checks when manager + * is capable of holding information related to the connected interface + */ + + return 0; +} + int dss_mgr_check(struct omap_overlay_manager *mgr, struct omap_overlay_manager_info *info, const struct omap_video_timings *mgr_timings, + const struct dss_lcd_mgr_config *lcd_config, struct omap_overlay_info **overlay_infos) { struct omap_overlay *ovl; @@ -683,6 +714,10 @@ int dss_mgr_check(struct omap_overlay_manager *mgr, if (r) return r; + r = dss_mgr_check_lcd_config(mgr, lcd_config); + if (r) + return r; + list_for_each_entry(ovl, &mgr->overlays, list) { struct omap_overlay_info *oi; int r; From 75bac5d1a2776d61a64d75fd19092dff724016a0 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Thu, 24 May 2012 15:08:54 +0530 Subject: [PATCH 09/12] OMAPDSS: APPLY: Remove usage of omap_dss_device from manual/auto update checks APPLY needs to know at certain places whether an overlay manager is in manual or auto update mode. The caps of the connected omap_dss_device were used to check that. A LCD manager is in manual update if stallmode is enabled for that manager. TV managers for now always auto update. Return the value of stallmode parameter in the private data 'lcd_confg' in mgr_manual_update() and ovl_manual_update(), for TV managers stallmode field will be false by default. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/apply.c | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/drivers/video/omap2/dss/apply.c b/drivers/video/omap2/dss/apply.c index 8c94fbe21822..b237b575c70b 100644 --- a/drivers/video/omap2/dss/apply.c +++ b/drivers/video/omap2/dss/apply.c @@ -182,14 +182,23 @@ void dss_apply_init(void) mp->lcd_config.clock_info.pck_div = 1; } +/* + * A LCD manager's stallmode decides whether it is in manual or auto update. TV + * manager is always auto update, stallmode field for TV manager is false by + * default + */ static bool ovl_manual_update(struct omap_overlay *ovl) { - return ovl->manager->device->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE; + struct mgr_priv_data *mp = get_mgr_priv(ovl->manager); + + return mp->lcd_config.stallmode; } static bool mgr_manual_update(struct omap_overlay_manager *mgr) { - return mgr->device->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE; + struct mgr_priv_data *mp = get_mgr_priv(mgr); + + return mp->lcd_config.stallmode; } static int dss_check_settings_low(struct omap_overlay_manager *mgr, From dd88b7a67736db931041009886ba5204cdf3de16 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Fri, 29 Jun 2012 14:41:30 +0530 Subject: [PATCH 10/12] OMAPDSS: DISPC: Remove a redundant function dss_mgr_is_lcd() available in dss.h does the same thing as dispc_mgr_is_lcd() in dispc.c. Remove the function from dispc.c and replace it with the one in dss.h. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/dispc.c | 22 ++++++---------------- 1 file changed, 6 insertions(+), 16 deletions(-) diff --git a/drivers/video/omap2/dss/dispc.c b/drivers/video/omap2/dss/dispc.c index 738ad779436f..5b289c5f695b 100644 --- a/drivers/video/omap2/dss/dispc.c +++ b/drivers/video/omap2/dss/dispc.c @@ -498,16 +498,6 @@ void dispc_runtime_put(void) WARN_ON(r < 0 && r != -ENOSYS); } -static inline bool dispc_mgr_is_lcd(enum omap_channel channel) -{ - if (channel == OMAP_DSS_CHANNEL_LCD || - channel == OMAP_DSS_CHANNEL_LCD2 || - channel == OMAP_DSS_CHANNEL_LCD3) - return true; - else - return false; -} - u32 dispc_mgr_get_vsync_irq(enum omap_channel channel) { return mgr_desc[channel].vsync_irq; @@ -1010,7 +1000,7 @@ static void dispc_mgr_set_cpr_coef(enum omap_channel channel, { u32 coef_r, coef_g, coef_b; - if (!dispc_mgr_is_lcd(channel)) + if (!dss_mgr_is_lcd(channel)) return; coef_r = FLD_VAL(coefs->rr, 31, 22) | FLD_VAL(coefs->rg, 20, 11) | @@ -1869,7 +1859,7 @@ static int check_horiz_timing_omap3(enum omap_channel channel, nonactive = t->x_res + t->hfp + t->hsw + t->hbp - out_width; pclk = dispc_mgr_pclk_rate(channel); - if (dispc_mgr_is_lcd(channel)) + if (dss_mgr_is_lcd(channel)) lclk = dispc_mgr_lclk_rate(channel); else lclk = dispc_fclk_rate(); @@ -2452,7 +2442,7 @@ bool dispc_mgr_is_enabled(enum omap_channel channel) void dispc_mgr_enable(enum omap_channel channel, bool enable) { - if (dispc_mgr_is_lcd(channel)) + if (dss_mgr_is_lcd(channel)) dispc_mgr_enable_lcd_out(channel, enable); else if (channel == OMAP_DSS_CHANNEL_DIGIT) dispc_mgr_enable_digit_out(enable); @@ -2642,7 +2632,7 @@ bool dispc_mgr_timings_ok(enum omap_channel channel, timings_ok = _dispc_mgr_size_ok(timings->x_res, timings->y_res); - if (dispc_mgr_is_lcd(channel)) + if (dss_mgr_is_lcd(channel)) timings_ok = timings_ok && _dispc_lcd_timings_ok(timings->hsw, timings->hfp, timings->hbp, timings->vsw, timings->vfp, @@ -2734,7 +2724,7 @@ void dispc_mgr_set_timings(enum omap_channel channel, return; } - if (dispc_mgr_is_lcd(channel)) { + if (dss_mgr_is_lcd(channel)) { _dispc_mgr_set_lcd_timings(channel, t.hsw, t.hfp, t.hbp, t.vsw, t.vfp, t.vbp, t.vsync_level, t.hsync_level, t.data_pclk_edge, t.de_level, t.sync_pclk_edge); @@ -2840,7 +2830,7 @@ unsigned long dispc_mgr_pclk_rate(enum omap_channel channel) { unsigned long r; - if (dispc_mgr_is_lcd(channel)) { + if (dss_mgr_is_lcd(channel)) { int pcd; u32 l; From c47cdb3088581f9d744b03399e8b4e89a56a111b Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Tue, 29 May 2012 11:55:38 +0530 Subject: [PATCH 11/12] OMAPDSS: RFBI: Use dss_mgr_enable to enable the overlay manager The RFBI driver uses a direct DISPC register write to enable the overlay manager. Replace this with dss_mgr_enable() which checks if the connected overlay and managers are correctly configured, and configure DSS for fifomerge. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/rfbi.c | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/drivers/video/omap2/dss/rfbi.c b/drivers/video/omap2/dss/rfbi.c index cc22426144cb..7c087424b634 100644 --- a/drivers/video/omap2/dss/rfbi.c +++ b/drivers/video/omap2/dss/rfbi.c @@ -300,10 +300,11 @@ void omap_rfbi_write_pixels(const void __iomem *buf, int scr_width, } EXPORT_SYMBOL(omap_rfbi_write_pixels); -static void rfbi_transfer_area(struct omap_dss_device *dssdev, u16 width, +static int rfbi_transfer_area(struct omap_dss_device *dssdev, u16 width, u16 height, void (*callback)(void *data), void *data) { u32 l; + int r; struct omap_video_timings timings = { .hsw = 1, .hfp = 1, @@ -322,7 +323,9 @@ static void rfbi_transfer_area(struct omap_dss_device *dssdev, u16 width, dss_mgr_set_timings(dssdev->manager, &timings); - dispc_mgr_enable(dssdev->manager->id, true); + r = dss_mgr_enable(dssdev->manager); + if (r) + return r; rfbi.framedone_callback = callback; rfbi.framedone_callback_data = data; @@ -335,6 +338,8 @@ static void rfbi_transfer_area(struct omap_dss_device *dssdev, u16 width, l = FLD_MOD(l, 1, 4, 4); /* ITE */ rfbi_write_reg(RFBI_CONTROL, l); + + return 0; } static void framedone_callback(void *data, u32 mask) @@ -814,8 +819,11 @@ int omap_rfbi_update(struct omap_dss_device *dssdev, u16 x, u16 y, u16 w, u16 h, void (*callback)(void *), void *data) { - rfbi_transfer_area(dssdev, w, h, callback, data); - return 0; + int r; + + r = rfbi_transfer_area(dssdev, w, h, callback, data); + + return r; } EXPORT_SYMBOL(omap_rfbi_update); From 6c6f510afb86e3c77c351dfa20cbb8ca834abad9 Mon Sep 17 00:00:00 2001 From: Archit Taneja Date: Mon, 25 Jun 2012 14:58:48 +0530 Subject: [PATCH 12/12] OMAPDSS: OVERLAY: Clean up replication checking Replication logic for an overlay depends on the color mode in which it is configured and the video port width of the manager it is connected to. video port width now held in dss_lcd_mgr_config in the manager's private data in APPLY. Use this instead of referring to the omap_dss_device connected to the manager. Replication is enabled in the case of TV manager, the video_port_width is set to a default value of 24 for TV manager. Make the replication checking an overlay function since it's more of an overlay characteristic than a display characteristic. Signed-off-by: Archit Taneja --- drivers/video/omap2/dss/apply.c | 2 +- drivers/video/omap2/dss/display.c | 34 ------------------------------- drivers/video/omap2/dss/dss.h | 4 ++-- drivers/video/omap2/dss/overlay.c | 13 ++++++++++++ 4 files changed, 16 insertions(+), 37 deletions(-) diff --git a/drivers/video/omap2/dss/apply.c b/drivers/video/omap2/dss/apply.c index b237b575c70b..0fefc68372b9 100644 --- a/drivers/video/omap2/dss/apply.c +++ b/drivers/video/omap2/dss/apply.c @@ -571,7 +571,7 @@ static void dss_ovl_write_regs(struct omap_overlay *ovl) mp = get_mgr_priv(ovl->manager); - replication = dss_use_replication(ovl->manager->device, oi->color_mode); + replication = dss_ovl_use_replication(mp->lcd_config, oi->color_mode); r = dispc_ovl_setup(ovl->id, oi, replication, &mp->timings); if (r) { diff --git a/drivers/video/omap2/dss/display.c b/drivers/video/omap2/dss/display.c index 1a0c15f83d0d..5bd957e85505 100644 --- a/drivers/video/omap2/dss/display.c +++ b/drivers/video/omap2/dss/display.c @@ -316,40 +316,6 @@ void omapdss_default_get_timings(struct omap_dss_device *dssdev, } EXPORT_SYMBOL(omapdss_default_get_timings); -/* Checks if replication logic should be used. Only use for active matrix, - * when overlay is in RGB12U or RGB16 mode, and LCD interface is - * 18bpp or 24bpp */ -bool dss_use_replication(struct omap_dss_device *dssdev, - enum omap_color_mode mode) -{ - int bpp; - - if (mode != OMAP_DSS_COLOR_RGB12U && mode != OMAP_DSS_COLOR_RGB16) - return false; - - switch (dssdev->type) { - case OMAP_DISPLAY_TYPE_DPI: - bpp = dssdev->phy.dpi.data_lines; - break; - case OMAP_DISPLAY_TYPE_HDMI: - case OMAP_DISPLAY_TYPE_VENC: - case OMAP_DISPLAY_TYPE_SDI: - bpp = 24; - break; - case OMAP_DISPLAY_TYPE_DBI: - bpp = dssdev->ctrl.pixel_size; - break; - case OMAP_DISPLAY_TYPE_DSI: - bpp = dsi_get_pixel_size(dssdev->panel.dsi_pix_fmt); - break; - default: - BUG(); - return false; - } - - return bpp > 16; -} - void dss_init_device(struct platform_device *pdev, struct omap_dss_device *dssdev) { diff --git a/drivers/video/omap2/dss/dss.h b/drivers/video/omap2/dss/dss.h index f87a4318d564..f67afe76f217 100644 --- a/drivers/video/omap2/dss/dss.h +++ b/drivers/video/omap2/dss/dss.h @@ -231,8 +231,6 @@ void dss_init_device(struct platform_device *pdev, struct omap_dss_device *dssdev); void dss_uninit_device(struct platform_device *pdev, struct omap_dss_device *dssdev); -bool dss_use_replication(struct omap_dss_device *dssdev, - enum omap_color_mode mode); /* manager */ int dss_init_overlay_managers(struct platform_device *pdev); @@ -265,6 +263,8 @@ int dss_ovl_simple_check(struct omap_overlay *ovl, const struct omap_overlay_info *info); int dss_ovl_check(struct omap_overlay *ovl, struct omap_overlay_info *info, const struct omap_video_timings *mgr_timings); +bool dss_ovl_use_replication(struct dss_lcd_mgr_config config, + enum omap_color_mode mode); /* DSS */ int dss_init_platform_driver(void) __init; diff --git a/drivers/video/omap2/dss/overlay.c b/drivers/video/omap2/dss/overlay.c index ec69325a118a..952c6fad9a81 100644 --- a/drivers/video/omap2/dss/overlay.c +++ b/drivers/video/omap2/dss/overlay.c @@ -687,3 +687,16 @@ int dss_ovl_check(struct omap_overlay *ovl, struct omap_overlay_info *info, return 0; } + +/* + * Checks if replication logic should be used. Only use when overlay is in + * RGB12U or RGB16 mode, and video port width interface is 18bpp or 24bpp + */ +bool dss_ovl_use_replication(struct dss_lcd_mgr_config config, + enum omap_color_mode mode) +{ + if (mode != OMAP_DSS_COLOR_RGB12U && mode != OMAP_DSS_COLOR_RGB16) + return false; + + return config.video_port_width > 16; +}