[PATCH 12/12] Provide more driver specific data in a videomode
Juergen Beisert
jbe at pengutronix.de
Tue Oct 26 07:31:48 EDT 2010
In order to support more than one videomode in a binary barebox, some drivers
need more specific data to setup the requested video mode in a correct manner.
This patch adds the 'priv' field to the generic videomode description to give
any platform a chance to forward some video hardware specific information on
a per videomode base.
This is currently i.MX21/i.MX25/i.MX27 specific.
BTW: At least the 'pcr' value could be generated at runtime from the 'sync'
field in 'struct fb_videomode'.
Signed-off-by: Juergen Beisert <jbe at pengutronix.de>
---
arch/arm/boards/eukrea_cpuimx25/eukrea_cpuimx25.c | 22 +++++------
arch/arm/boards/eukrea_cpuimx27/eukrea_cpuimx27.c | 21 +++++-----
arch/arm/boards/guf-neso/board.c | 45 +++++++++++----------
arch/arm/boards/imx21ads/imx21ads.c | 24 ++++++------
arch/arm/boards/pcm038/pcm038.c | 40 +++++++++---------
arch/arm/mach-imx/include/mach/imxfb.h | 20 +++++----
drivers/video/imx.c | 19 +++++----
include/fb.h | 2 +
8 files changed, 99 insertions(+), 94 deletions(-)
diff --git a/arch/arm/boards/eukrea_cpuimx25/eukrea_cpuimx25.c b/arch/arm/boards/eukrea_cpuimx25/eukrea_cpuimx25.c
index 032897a..9a9021a 100644
--- a/arch/arm/boards/eukrea_cpuimx25/eukrea_cpuimx25.c
+++ b/arch/arm/boards/eukrea_cpuimx25/eukrea_cpuimx25.c
@@ -120,7 +120,14 @@ static struct device_d nand_dev = {
.platform_data = &nand_info,
};
-static struct fb_videomode cmo_display = {
+static const struct imx_fb_driver_data driver_data = {
+ .pwmr = 0x00A903FF,
+ .lscr1 = 0x00120300,
+ .dmacr = 0x80040060,
+ .pcr = 0xCAD08B80,
+};
+
+static const struct fb_videomode cmo_display = {
.name = "CMO-QVGA",
.refresh = 60,
.xres = 320,
@@ -134,20 +141,11 @@ static struct fb_videomode cmo_display = {
.lower_margin = 4,
};
-static struct imx_fb_videomode imxfb_mode = {
- .mode = &cmo_display,
- .pcr = 0xCAD08B80,
- .bpp = 16,
-};
-
static struct imx_fb_platform_data eukrea_cpuimx25_fb_data = {
- .mode = &imxfb_mode,
- .pwmr = 0x00A903FF,
- .lscr1 = 0x00120300,
- .dmacr = 0x80040060,
+ .mode = &cmo_display,
+ .mode_cnt = 1,
};
-
static struct device_d imxfb_dev = {
.id = -1,
.name = "imxfb",
diff --git a/arch/arm/boards/eukrea_cpuimx27/eukrea_cpuimx27.c b/arch/arm/boards/eukrea_cpuimx27/eukrea_cpuimx27.c
index 3ea2466..3696105 100644
--- a/arch/arm/boards/eukrea_cpuimx27/eukrea_cpuimx27.c
+++ b/arch/arm/boards/eukrea_cpuimx27/eukrea_cpuimx27.c
@@ -186,7 +186,14 @@ static void eukrea_cpuimx27_mmu_init(void)
#endif
#ifdef CONFIG_DRIVER_VIDEO_IMX
-static struct fb_videomode cmo_display = {
+static const struct imx_fb_driver_data driver_data = {
+ .pwmr = 0x00A903FF,
+ .lscr1 = 0x00120300,
+ .dmacr = 0x00020010,
+ .pcr = 0xFAD08B80,
+};
+
+static const struct fb_videomode cmo_display = {
.name = "CMO-QVGA",
.refresh = 60,
.xres = 320,
@@ -198,18 +205,12 @@ static struct fb_videomode cmo_display = {
.vsync_len = 3,
.upper_margin = 15,
.lower_margin = 4,
+ .priv = &driver_data,
};
-static struct imx_fb_videomode imxfb_mode = {
- .mode = &cmo_display,
- .pcr = 0xFAD08B80,
- .bpp = 16,};
-
static struct imx_fb_platform_data eukrea_cpuimx27_fb_data = {
- .mode = &imxfb_mode,
- .pwmr = 0x00A903FF,
- .lscr1 = 0x00120300,
- .dmacr = 0x00020010,
+ .mode = &cmo_display,
+ .mode_cnt = 1,
};
static struct device_d imxfb_dev = {
diff --git a/arch/arm/boards/guf-neso/board.c b/arch/arm/boards/guf-neso/board.c
index 6949675..a4d246f 100644
--- a/arch/arm/boards/guf-neso/board.c
+++ b/arch/arm/boards/guf-neso/board.c
@@ -91,22 +91,11 @@ static struct device_d nand_dev = {
.platform_data = &nand_info,
};
-static struct fb_videomode cpt_display = {
- .name = "CPT CLAA070LC0JCT",
- .refresh = 60,
- .xres = 800,
- .yres = 480,
- .pixclock = KHZ2PICOS(27000),
- .hsync_len = 1, /* DE only sync */
- .left_margin = 50,
- .right_margin = 50,
- .vsync_len = 1, /* DE only sync */
- .upper_margin = 10,
- .lower_margin = 10,
-};
-
-static struct imx_fb_videomode imxfb_mode = {
- .mode = &cpt_display,
+static const struct imx_fb_driver_data driver_data = {
+ .pwmr = 0x00000000, /* doesn't matter */
+ .lscr1 = 0x00120300, /* doesn't matter */
+ /* dynamic mode -> using the reset values (as recommended in the datasheet) */
+ .dmacr = (0 << 31) | (4 << 16) | 96,
/*
* - TFT style panel
* - clk enabled while idle
@@ -122,7 +111,21 @@ static struct imx_fb_videomode imxfb_mode = {
PCR_SCLK_SEL |
PCR_LPPOL |
PCR_FLMPOL,
- .bpp = 16, /* TODO 32 bit does not work: The 'green' component is lacking in this mode */
+};
+
+static struct fb_videomode cpt_display = {
+ .name = "CPT CLAA070LC0JCT",
+ .refresh = 60,
+ .xres = 800,
+ .yres = 480,
+ .pixclock = KHZ2PICOS(27000),
+ .hsync_len = 1, /* DE only sync */
+ .left_margin = 50,
+ .right_margin = 50,
+ .vsync_len = 1, /* DE only sync */
+ .upper_margin = 10,
+ .lower_margin = 10,
+ .priv = &driver_data,
};
static void neso_fb_enable(int enable)
@@ -132,12 +135,10 @@ static void neso_fb_enable(int enable)
}
static struct imx_fb_platform_data neso_fb_data = {
- .mode = &imxfb_mode,
- .pwmr = 0x00000000, /* doesn't matter */
- .lscr1 = 0x00120300, /* doesn't matter */
- /* dynamic mode -> using the reset values (as recommended in the datasheet) */
- .dmacr = (0 << 31) | (4 << 16) | 96,
+ .mode = &cpt_display,
+ .mode_cnt = 1,
.enable = neso_fb_enable,
+ .bpp = 16, /* TODO 32 bit does not work: The 'green' component is lacking in this mode */
.framebuffer_ovl = (void *)0xa7f00000,
};
diff --git a/arch/arm/boards/imx21ads/imx21ads.c b/arch/arm/boards/imx21ads/imx21ads.c
index 81006de..3b654ec 100644
--- a/arch/arm/boards/imx21ads/imx21ads.c
+++ b/arch/arm/boards/imx21ads/imx21ads.c
@@ -79,7 +79,14 @@ static struct device_d cs8900_dev = {
// IRQ is connected to UART3_RTS
};
-static struct fb_videomode sharp_display = {
+static const struct imx_fb_driver_data driver_data = {
+ .pwmr = 0x00a903ff,
+ .lscr1 = 0x00120300,
+ .dmacr = 0x00020008,
+ .pcr = 0xfb108bc7,
+};
+
+static const struct fb_videomode sharp_display = {
.name = "Sharp-LQ035Q7",
.refresh = 60,
.xres = 240,
@@ -94,23 +101,16 @@ static struct fb_videomode sharp_display = {
.sync = 0,
.vmode = FB_VMODE_NONINTERLACED,
.flag = 0,
-};
-
-/* Sharp LQ035Q7DB02 QVGA display */
-static struct imx_fb_videomode imx_fb_modedata = {
- .mode = &sharp_display,
- .pcr = 0xfb108bc7,
- .bpp = 16,
+ .priv = &driver_data,
};
static struct imx_fb_platform_data imx_fb_data = {
- .mode = &imx_fb_modedata,
+/* Sharp LQ035Q7DB02 QVGA display */
+ .mode = &sharp_display,
+ .mode_cnt = 1,
.cmap_greyscale = 0,
.cmap_inverse = 0,
.cmap_static = 0,
- .pwmr = 0x00a903ff,
- .lscr1 = 0x00120300,
- .dmacr = 0x00020008,
};
static struct device_d imxfb_dev = {
diff --git a/arch/arm/boards/pcm038/pcm038.c b/arch/arm/boards/pcm038/pcm038.c
index 026e9c0..6a5d938 100644
--- a/arch/arm/boards/pcm038/pcm038.c
+++ b/arch/arm/boards/pcm038/pcm038.c
@@ -127,7 +127,23 @@ static struct device_d nand_dev = {
.platform_data = &nand_info,
};
-static struct fb_videomode sharp_display = {
+static const struct imx_fb_driver_data driver_data = {
+ /*
+ * - HSYNC active high
+ * - VSYNC active high
+ * - clk notenabled while idle
+ * - clock not inverted
+ * - data not inverted
+ * - data enable low active
+ * - enable sharp mode
+ */
+ .pwmr = 0x00A903FF,
+ .lscr1 = 0x00120300,
+ .dmacr = 0x00020010,
+ .pcr = 0xF00080C0,
+};
+
+static const struct fb_videomode sharp_display = {
.name = "Sharp-LQ035Q7",
.refresh = 60,
.xres = 240,
@@ -139,28 +155,12 @@ static struct fb_videomode sharp_display = {
.vsync_len = 1,
.upper_margin = 7,
.lower_margin = 9,
-};
-
-static struct imx_fb_videomode imxfb_mode = {
- .mode = &sharp_display,
- /*
- * - HSYNC active high
- * - VSYNC active high
- * - clk notenabled while idle
- * - clock not inverted
- * - data not inverted
- * - data enable low active
- * - enable sharp mode
- */
- .pcr = 0xF00080C0,
- .bpp = 16,
+ .priv = &driver_data,
};
static struct imx_fb_platform_data pcm038_fb_data = {
- .mode = &imxfb_mode,
- .pwmr = 0x00A903FF,
- .lscr1 = 0x00120300,
- .dmacr = 0x00020010,
+ .mode = &sharp_display,
+ .mode_cnt = 1,
};
static struct device_d imxfb_dev = {
diff --git a/arch/arm/mach-imx/include/mach/imxfb.h b/arch/arm/mach-imx/include/mach/imxfb.h
index c536119..dbd7c93 100644
--- a/arch/arm/mach-imx/include/mach/imxfb.h
+++ b/arch/arm/mach-imx/include/mach/imxfb.h
@@ -49,28 +49,30 @@
#define DMACR_HM(x) (((x) & 0xf) << 16)
#define DMACR_TM(x) ((x) & 0xf)
-struct imx_fb_videomode {
- struct fb_videomode *mode;
- u32 pcr;
- unsigned char bpp;
+/**
+ * Videomode dependent, but driver specific data
+ */
+struct imx_fb_driver_data {
+ uint32_t pwmr; /**< refer datasheet: LPCCR register */
+ uint32_t lscr1; /**< refer datasheet: LSCR register */
+ uint32_t dmacr; /**< refer datasheet: LDCR register */
+ uint32_t pcr; /**< refer datasheet: LPCR register */
};
/**
* Define relevant framebuffer information
*/
struct imx_fb_platform_data {
- struct imx_fb_videomode *mode;
+ const struct fb_videomode *mode;
unsigned mode_cnt; /**< number of entries in 'mode' */
+ unsigned char bpp; /**< preferred colour depth for this device */
+
u_int cmap_greyscale:1,
cmap_inverse:1,
cmap_static:1,
unused:29;
- u_int pwmr;
- u_int lscr1;
- u_int dmacr;
-
/** force a memory area to be used, else NULL for dynamic allocation */
void *framebuffer;
/** force a memory area to be used, else NULL for dynamic allocation */
diff --git a/drivers/video/imx.c b/drivers/video/imx.c
index 07438e5..d935149 100644
--- a/drivers/video/imx.c
+++ b/drivers/video/imx.c
@@ -300,6 +300,7 @@ static int imxfb_initialize_mode(struct fb_info *info, const struct fb_videomode
unsigned long lcd_clk;
unsigned long long tmp;
struct imxfb_info *fbi = fb_info_to_imxfb_info(info);
+ const struct imx_fb_driver_data *drv_data = mode->priv;
u32 pcr;
unsigned size;
@@ -324,6 +325,11 @@ static int imxfb_initialize_mode(struct fb_info *info, const struct fb_videomode
if (info->fb_dev->map_base == 0U /* FIXME should be 'NULL'*/)
info->fb_dev->map_base = (unsigned long)xzalloc(info->fb_dev->size);
+ fbi->pcr = drv_data->pcr;
+ fbi->pwmr = drv_data->pwmr;
+ fbi->lscr1 = drv_data->lscr1;
+ fbi->dmacr = drv_data->dmacr;
+
/* physical screen start address */
writel(VPW_VPW(mode->xres * info->bits_per_pixel / 8 / 4),
fbi->regs + LCDC_VPW);
@@ -535,7 +541,7 @@ static int imxfb_register_overlay(struct imxfb_info *fbi, struct device_d *hw_de
overlay->fb_setcolreg = imxfb_overlay_setcolreg;
/* add runtime video info */
- overlay->mode = pdata->mode->mode;
+ overlay->mode = pdata->mode;
overlay->mode_cnt = 1; /* no choice */
overlay_dev = register_framebuffer(overlay, pdata->framebuffer_ovl, 0);
@@ -585,17 +591,12 @@ static int imxfb_probe(struct device_d *dev)
fbi->fb_host.fb_setcolreg = imxfb_setcolreg;
fbi->regs = (void*)dev->map_base;
- fbi->pcr = pdata->mode->pcr;
- fbi->pwmr = pdata->pwmr;
- fbi->lscr1 = pdata->lscr1;
- fbi->dmacr = pdata->dmacr;
fbi->enable = pdata->enable;
/* add runtime video info */
- fbi->fb_host.mode = pdata->mode->mode;
- /* to be backward compatible */
- fbi->fb_host.mode_cnt = pdata->mode_cnt == 0 ? 1 : pdata->mode_cnt;
- fbi->fb_host.bits_per_pixel = 16; /* RGB565, the default */
+ fbi->fb_host.mode = pdata->mode;
+ fbi->fb_host.mode_cnt = pdata->mode_cnt;
+ fbi->fb_host.bits_per_pixel = pdata->bpp;
fb_dev = register_framebuffer(&fbi->fb_host, pdata->framebuffer, 0);
if (dev == NULL) {
diff --git a/include/fb.h b/include/fb.h
index 223b301..8ba4e5a 100644
--- a/include/fb.h
+++ b/include/fb.h
@@ -69,6 +69,8 @@ struct fb_videomode {
unsigned sync; /**< sync information, refer FB_SYNC_* macros */
unsigned vmode; /**< video mode information, refer FB_VMODE_* macros */
unsigned flag;
+
+ const void *priv; /**< video driver related information */
};
/* Interpretation of offset for color fields: All offsets are from the right,
--
1.7.2.3
More information about the barebox
mailing list