diff options
-rw-r--r-- | drivers/video/Kconfig | 8 | ||||
-rw-r--r-- | drivers/video/Makefile | 2 | ||||
-rw-r--r-- | drivers/video/mipi_dsi_northwest.c | 133 | ||||
-rw-r--r-- | include/mipi_dsi_northwest.h | 71 | ||||
-rw-r--r-- | scripts/config_whitelist.txt | 1 |
5 files changed, 94 insertions, 121 deletions
diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig index ce0221f5d38..28b0697e245 100644 --- a/drivers/video/Kconfig +++ b/drivers/video/Kconfig @@ -548,6 +548,14 @@ config IMX_MIPI_DSI_BRIDGE help Enable MIPI DSI bridge interface for display controller. +config IMX_NORTHWEST_MIPI_DSI + bool "i.MX northwest's MIPI DSI" + default n + select IMX_MIPI_DSI_BRIDGE + depends on VIDEO && MX7ULP + help + Support for i.MX7ULP MIPI DSI controller. + config MXC_EPDC bool "i.MX EPDC support" depends on LCD && (MX7 || MX6) diff --git a/drivers/video/Makefile b/drivers/video/Makefile index 7c735ee7c50..e07b1dc2bcc 100644 --- a/drivers/video/Makefile +++ b/drivers/video/Makefile @@ -63,7 +63,7 @@ obj-$(CONFIG_VIDEO_VADC) += mxc_vadc.o obj-$(CONFIG_VIDEO_CSI) += mxc_csi.o obj-$(CONFIG_VIDEO_PXP) += mxc_pxp.o obj-$(CONFIG_VIDEO_GIS) += mxc_gis.o -obj-$(CONFIG_MXC_MIPI_DSI_NORTHWEST) += mipi_dsi_northwest.o +obj-$(CONFIG_IMX_NORTHWEST_MIPI_DSI) += mipi_dsi_northwest.o obj-$(CONFIG_IMX_MIPI_DSI_BRIDGE) += imx_mipi_dsi_bridge.o obj-$(CONFIG_HX8363) += hx8363_wvga.o diff --git a/drivers/video/mipi_dsi_northwest.c b/drivers/video/mipi_dsi_northwest.c index 30c8e28269a..dd118b377cd 100644 --- a/drivers/video/mipi_dsi_northwest.c +++ b/drivers/video/mipi_dsi_northwest.c @@ -17,6 +17,7 @@ #include "mipi_dsi_northwest_regs.h" #include <mipi_dsi_northwest.h> #include <mipi_display.h> +#include <imx_mipi_dsi_bridge.h> #define MIPI_LCD_SLEEP_MODE_DELAY (120) #define MIPI_FIFO_TIMEOUT 250000 /* 250ms */ @@ -34,6 +35,18 @@ enum mipi_dsi_payload { DSI_PAYLOAD_VIDEO, }; +/* + * mipi-dsi northwest driver information structure, holds useful data for the driver. + */ +struct mipi_dsi_northwest_info { + u32 mmio_base; + u32 sim_base; + int enabled; + struct mipi_dsi_client_dev *dsi_panel_dev; + struct mipi_dsi_client_driver *dsi_panel_drv; + struct fb_videomode mode; +}; + /** * board_mipi_panel_reset - give a reset cycle for mipi dsi panel * @@ -141,7 +154,7 @@ static int mipi_dsi_host_init(struct mipi_dsi_northwest_info *mipi_dsi) { uint32_t lane_num; - switch (mipi_dsi->dsi_panel_dev->data_lane_num) { + switch (mipi_dsi->dsi_panel_dev->lanes) { case 1: lane_num = 0x0; break; @@ -171,9 +184,11 @@ static int mipi_dsi_host_init(struct mipi_dsi_northwest_info *mipi_dsi) static int mipi_dsi_dpi_init(struct mipi_dsi_northwest_info *mipi_dsi) { uint32_t bpp, color_coding, pixel_fmt; - struct fb_videomode *mode = &(mipi_dsi->dsi_panel_dev->mode); + struct fb_videomode *mode = &(mipi_dsi->mode); - bpp = mipi_dsi->dsi_panel_dev->bpp; + bpp = mipi_dsi_pixel_format_to_bpp(mipi_dsi->dsi_panel_dev->format); + if (bpp < 0) + return -EINVAL; writel(mode->xres, mipi_dsi->mmio_base + DPI_PIXEL_PAYLOAD_SIZE); writel(mode->xres, mipi_dsi->mmio_base + DPI_PIXEL_FIFO_SEND_LEVEL); @@ -293,8 +308,8 @@ static int mipi_dsi_enable(struct mipi_dsi_northwest_info *mipi_dsi) mipi_dsi_init_interrupt(mipi_dsi); /* Call panel driver's setup */ - if (mipi_dsi->dsi_panel_drv->mipi_panel_setup) { - ret = mipi_dsi->dsi_panel_drv->mipi_panel_setup(mipi_dsi->dsi_panel_dev); + if (mipi_dsi->dsi_panel_drv->dsi_client_setup) { + ret = mipi_dsi->dsi_panel_drv->dsi_client_setup(mipi_dsi->dsi_panel_dev); if (ret < 0) { printf("failed to init mipi lcd.\n"); return ret; @@ -393,7 +408,7 @@ static int wait_for_pkt_done(struct mipi_dsi_northwest_info *mipi_dsi, unsigned } static int mipi_dsi_pkt_write(struct mipi_dsi_northwest_info *mipi_dsi, - u8 data_type, const u32 *buf, int len) + u8 data_type, const u8 *buf, int len) { int ret = 0; const uint8_t *data = (const uint8_t *)buf; @@ -437,7 +452,7 @@ static int mipi_dsi_dcs_cmd(struct mipi_dsi_northwest_info *mipi_dsi, buf[0] = cmd; buf[1] = 0x0; err = mipi_dsi_pkt_write(mipi_dsi, - MIPI_DSI_DCS_SHORT_WRITE, buf, 0); + MIPI_DSI_DCS_SHORT_WRITE, (u8 *)buf, 0); break; default: @@ -468,34 +483,11 @@ static void mipi_dsi_shutdown(struct mipi_dsi_northwest_info *mipi_dsi) clrbits_le32(mipi_dsi->sim_base + SIM_SOPT1CFG, DSI_RST_DPI_N); } -struct mipi_dsi_northwest_info *dsi_info = NULL; - -int mipi_dsi_northwest_setup(u32 base_addr, u32 sim_addr) +/* Attach a LCD panel device */ +int mipi_dsi_northwest_bridge_attach(struct mipi_dsi_bridge_driver *bridge_driver, struct mipi_dsi_client_dev *panel_dev) { - if (dsi_info != NULL) { - printf("mipi_dsi_northwest has been initialized.\n"); - return -EBUSY; - } + struct mipi_dsi_northwest_info *dsi_info = (struct mipi_dsi_northwest_info *)bridge_driver->driver_private; - dsi_info = (struct mipi_dsi_northwest_info *)malloc(sizeof(struct mipi_dsi_northwest_info)); - if (!dsi_info) { - printf("failed to allocate mipi_dsi_northwest_info object.\n"); - return -ENOMEM; - } - - dsi_info->mmio_base = base_addr; - dsi_info->sim_base = sim_addr; - dsi_info->mipi_dsi_pkt_write = &mipi_dsi_pkt_write; - dsi_info->dsi_panel_dev = NULL; - dsi_info->dsi_panel_drv = NULL; - dsi_info->enabled = 0; - - return 0; -} - -/* Register a LCD panel device */ -int mipi_dsi_northwest_register_panel_device(struct mipi_dsi_northwest_panel_device *panel_dev) -{ if (!panel_dev) { printf("mipi_dsi_northwest_panel_device is NULL.\n"); return -EFAULT; @@ -506,11 +498,6 @@ int mipi_dsi_northwest_register_panel_device(struct mipi_dsi_northwest_panel_dev return -EFAULT; } - if (!dsi_info) { - printf("mipi_dsi_northwest is not initialized\n"); - return -EFAULT; - } - if (dsi_info->dsi_panel_drv) { if (strcmp(panel_dev->name, dsi_info->dsi_panel_drv->name)) { printf("The panel device name %s is not for LCD driver %s\n", @@ -520,14 +507,17 @@ int mipi_dsi_northwest_register_panel_device(struct mipi_dsi_northwest_panel_dev } dsi_info->dsi_panel_dev = panel_dev; - panel_dev->host = dsi_info; return 0; } -/* Register a LCD panel driver, will search the panel device to bind with them */ -int mipi_dsi_northwest_register_panel_driver(struct mipi_dsi_northwest_panel_driver *panel_drv) + +/* Add a LCD panel driver, will search the panel device to bind with them */ +int mipi_dsi_northwest_bridge_add_client_driver(struct mipi_dsi_bridge_driver *bridge_driver, + struct mipi_dsi_client_driver *panel_drv) { + struct mipi_dsi_northwest_info *dsi_info = (struct mipi_dsi_northwest_info *)bridge_driver->driver_private; + if (!panel_drv) { printf("mipi_dsi_northwest_panel_driver is NULL.\n"); return -EFAULT; @@ -538,11 +528,6 @@ int mipi_dsi_northwest_register_panel_driver(struct mipi_dsi_northwest_panel_dri return -EFAULT; } - if (!dsi_info) { - printf("mipi_dsi_northwest is not initialized\n"); - return -EFAULT; - } - if (dsi_info->dsi_panel_dev) { if (strcmp(panel_drv->name, dsi_info->dsi_panel_dev->name)) { printf("The panel driver name %s is not for LCD device %s\n", @@ -557,8 +542,10 @@ int mipi_dsi_northwest_register_panel_driver(struct mipi_dsi_northwest_panel_dri } /* Enable the mipi dsi display */ -int mipi_dsi_northwest_enable(void) +static int mipi_dsi_northwest_bridge_enable(struct mipi_dsi_bridge_driver *bridge_driver) { + struct mipi_dsi_northwest_info *dsi_info = (struct mipi_dsi_northwest_info *)bridge_driver->driver_private; + if (!dsi_info->dsi_panel_dev || !dsi_info->dsi_panel_drv) return -ENODEV; @@ -570,8 +557,10 @@ int mipi_dsi_northwest_enable(void) } /* Disable and shutdown the mipi dsi display */ -int mipi_dsi_northwest_shutdown(void) +static int mipi_dsi_northwest_bridge_disable(struct mipi_dsi_bridge_driver *bridge_driver) { + struct mipi_dsi_northwest_info *dsi_info = (struct mipi_dsi_northwest_info *)bridge_driver->driver_private; + if (!dsi_info->enabled) return 0; @@ -582,3 +571,51 @@ int mipi_dsi_northwest_shutdown(void) return 0; } + +static int mipi_dsi_northwest_bridge_mode_set(struct mipi_dsi_bridge_driver *bridge_driver, + struct fb_videomode *fbmode) +{ + struct mipi_dsi_northwest_info *dsi_info = (struct mipi_dsi_northwest_info *)bridge_driver->driver_private; + + dsi_info->mode = *fbmode; + + return 0; +} + +static int mipi_dsi_northwest_bridge_pkt_write(struct mipi_dsi_bridge_driver *bridge_driver, + u8 data_type, const u8 *buf, int len) +{ + struct mipi_dsi_northwest_info *mipi_dsi = (struct mipi_dsi_northwest_info *)bridge_driver->driver_private; + + return mipi_dsi_pkt_write(mipi_dsi, data_type, buf, len); +} + +struct mipi_dsi_bridge_driver imx_northwest_dsi_driver = { + .attach = mipi_dsi_northwest_bridge_attach, + .enable = mipi_dsi_northwest_bridge_enable, + .disable = mipi_dsi_northwest_bridge_disable, + .mode_set = mipi_dsi_northwest_bridge_mode_set, + .pkt_write = mipi_dsi_northwest_bridge_pkt_write, + .add_client_driver = mipi_dsi_northwest_bridge_add_client_driver, + .name = "imx_northwest_mipi_dsi", +}; + +int mipi_dsi_northwest_setup(u32 base_addr, u32 sim_addr) +{ + struct mipi_dsi_northwest_info *dsi_info; + + dsi_info = (struct mipi_dsi_northwest_info *)malloc(sizeof(struct mipi_dsi_northwest_info)); + if (!dsi_info) { + printf("failed to allocate mipi_dsi_northwest_info object.\n"); + return -ENOMEM; + } + + dsi_info->mmio_base = base_addr; + dsi_info->sim_base = sim_addr; + dsi_info->dsi_panel_dev = NULL; + dsi_info->dsi_panel_drv = NULL; + dsi_info->enabled = 0; + + imx_northwest_dsi_driver.driver_private = dsi_info; + return imx_mipi_dsi_bridge_register_driver(&imx_northwest_dsi_driver); +} diff --git a/include/mipi_dsi_northwest.h b/include/mipi_dsi_northwest.h index 8795ede1efb..9be24984c74 100644 --- a/include/mipi_dsi_northwest.h +++ b/include/mipi_dsi_northwest.h @@ -11,78 +11,7 @@ #include <linux/fb.h> -#define DSI_CMD_BUF_MAXSIZE (128) - -/* - * device structure for mipi-dsi based lcd panel. - * - * @name: name of the device to use with this device, - * the name will be used for binding driver. - * @mode: video mode parameters for the panel. - * @bpp: bits per pixel. only 24 bits is supported. - * @virtual_ch_id: virtual channel id for this dsi device. - * @data_lane_num: the data lane number, max is 2. - * @host: pointer to the host driver instance, will be setup - * during register device. - */ -struct mipi_dsi_northwest_panel_device { - const char *name; - struct fb_videomode mode; - int bpp; - u32 virtual_ch_id; - u32 data_lane_num; - - struct mipi_dsi_northwest_info *host; -}; - - -/* - * driver structure for mipi-dsi based lcd panel. - * - * this structure should be registered by lcd panel driver. - * mipi-dsi driver seeks lcd panel registered through name field - * and calls these callback functions in appropriate time. - * - * @name: name of the driver to use with this device, or an - * alias for that name. - * @mipi_panel_setup: callback pointer for initializing lcd panel based on mipi - * dsi interface. - */ -struct mipi_dsi_northwest_panel_driver { - const char *name; - - int (*mipi_panel_setup)(struct mipi_dsi_northwest_panel_device *panel_dev); -}; - -/* - * mipi-dsi northwest driver information structure, holds useful data for the driver. - */ -struct mipi_dsi_northwest_info { - u32 mmio_base; - u32 sim_base; - int enabled; - struct mipi_dsi_northwest_panel_device *dsi_panel_dev; - struct mipi_dsi_northwest_panel_driver *dsi_panel_drv; - - int (*mipi_dsi_pkt_write)(struct mipi_dsi_northwest_info *mipi_dsi, - u8 data_type, const u32 *buf, int len); -}; - /* Setup mipi dsi host driver instance, with base address and SIM address provided */ int mipi_dsi_northwest_setup(u32 base_addr, u32 sim_addr); -/* Create a LCD panel device, will search the panel driver to bind with them */ -int mipi_dsi_northwest_register_panel_device(struct mipi_dsi_northwest_panel_device *panel_dev); - -/* Register a LCD panel driver, will search the panel device to bind with them */ -int mipi_dsi_northwest_register_panel_driver(struct mipi_dsi_northwest_panel_driver *panel_drv); - -/* Enable the mipi dsi display */ -int mipi_dsi_northwest_enable(void); - -/* Disable and shutdown the mipi dsi display */ -int mipi_dsi_northwest_shutdown(void); - -void hx8363_init(void); - #endif diff --git a/scripts/config_whitelist.txt b/scripts/config_whitelist.txt index 6879681ccb0..53f6ce46e1f 100644 --- a/scripts/config_whitelist.txt +++ b/scripts/config_whitelist.txt @@ -1403,7 +1403,6 @@ CONFIG_MXC_KPD CONFIG_MXC_KPD_COLMAX CONFIG_MXC_KPD_ROWMAX CONFIG_MXC_MCI_REGS_BASE -CONFIG_MXC_MIPI_DSI_NORTHWEST CONFIG_MXC_NAND_HWECC CONFIG_MXC_NAND_IP_REGS_BASE CONFIG_MXC_NAND_REGS_BASE |