Commit 57f065fee2a421085621a34097ccbc45fc18aad5

Authored by Anatolij Gustschin
Committed by Stefano Babic
1 parent 01b7e8f6d4

video: ipuv3: add DM_VIDEO support

Extend the driver to build with DM_VIDEO enabled. DTS files
must additionally include 'u-boot,dm-pre-reloc' property in
soc and ipu nodes to enable driver binding to ipu device.

Signed-off-by: Anatolij Gustschin <agust@denx.de>

Showing 4 changed files with 113 additions and 14 deletions Side-by-side Diff

arch/arm/include/asm/mach-imx/video.h
... ... @@ -26,5 +26,6 @@
26 26 #endif
27 27  
28 28 int ipu_set_ldb_clock(int rate);
  29 +int ipu_displays_init(void);
29 30 #endif
arch/arm/mach-imx/video.c
... ... @@ -4,6 +4,17 @@
4 4 #include <linux/errno.h>
5 5 #include <asm/mach-imx/video.h>
6 6  
  7 +#ifdef CONFIG_IMX_HDMI
  8 +#include <asm/arch/mxc_hdmi.h>
  9 +#include <asm/io.h>
  10 +
  11 +int detect_hdmi(struct display_info_t const *dev)
  12 +{
  13 + struct hdmi_regs *hdmi = (struct hdmi_regs *)HDMI_ARB_BASE_ADDR;
  14 + return readb(&hdmi->phy_stat0) & HDMI_DVI_STAT;
  15 +}
  16 +#endif
  17 +
7 18 int board_video_skip(void)
8 19 {
9 20 int i;
... ... @@ -42,6 +53,11 @@
42 53 displays[i].mode.name,
43 54 displays[i].mode.xres,
44 55 displays[i].mode.yres);
  56 +
  57 +#ifdef CONFIG_IMX_HDMI
  58 + if (!strcmp(displays[i].mode.name, "HDMI"))
  59 + imx_enable_hdmi_phy();
  60 +#endif
45 61 } else
46 62 printf("LCD %s cannot be configured: %d\n",
47 63 displays[i].mode.name, ret);
48 64  
49 65  
... ... @@ -53,13 +69,8 @@
53 69 return ret;
54 70 }
55 71  
56   -#ifdef CONFIG_IMX_HDMI
57   -#include <asm/arch/mxc_hdmi.h>
58   -#include <asm/io.h>
59   -int detect_hdmi(struct display_info_t const *dev)
  72 +int ipu_displays_init(void)
60 73 {
61   - struct hdmi_regs *hdmi = (struct hdmi_regs *)HDMI_ARB_BASE_ADDR;
62   - return readb(&hdmi->phy_stat0) & HDMI_DVI_STAT;
  74 + return board_video_skip();
63 75 }
64   -#endif
drivers/video/Kconfig
... ... @@ -538,6 +538,13 @@
538 538  
539 539 source "drivers/video/bridge/Kconfig"
540 540  
  541 +config VIDEO_IPUV3
  542 + bool "i.MX IPUv3 Core video support"
  543 + depends on (VIDEO || DM_VIDEO) && (MX5 || MX6)
  544 + help
  545 + This enables framebuffer driver for i.MX processors working
  546 + on the IPUv3(Image Processing Unit) internal graphic processor.
  547 +
541 548 config VIDEO
542 549 bool "Enable legacy video support"
543 550 depends on !DM_VIDEO
... ... @@ -546,13 +553,6 @@
546 553 drivers use this because they are not yet converted to driver
547 554 model. Video drivers typically provide a colour text console and
548 555 cursor.
549   -
550   -config VIDEO_IPUV3
551   - bool "i.MX IPUv3 Core video support"
552   - depends on VIDEO && MX6
553   - help
554   - This enables framebuffer driver for i.MX processors working
555   - on the IPUv3(Image Processing Unit) internal graphic processor.
556 556  
557 557 config CFB_CONSOLE
558 558 bool "Enable colour frame buffer console"
drivers/video/mxc_ipuv3_fb.c
... ... @@ -17,6 +17,7 @@
17 17 #include <linux/list.h>
18 18 #include <linux/fb.h>
19 19 #include <asm/io.h>
  20 +#include <asm/mach-imx/video.h>
20 21 #include <malloc.h>
21 22 #include <video_fb.h>
22 23 #include "videomodes.h"
... ... @@ -24,6 +25,9 @@
24 25 #include "mxcfb.h"
25 26 #include "ipu_regs.h"
26 27  
  28 +#include <dm.h>
  29 +#include <video.h>
  30 +
27 31 DECLARE_GLOBAL_DATA_PTR;
28 32  
29 33 static int mxcfb_map_video_memory(struct fb_info *fbi);
30 34  
... ... @@ -401,8 +405,14 @@
401 405 fbi->fix.line_length;
402 406 }
403 407 fbi->fix.smem_len = roundup(fbi->fix.smem_len, ARCH_DMA_MINALIGN);
  408 +
  409 +#if CONFIG_IS_ENABLED(DM_VIDEO)
  410 + fbi->screen_base = (char *)gd->video_bottom;
  411 +#else
404 412 fbi->screen_base = (char *)memalign(ARCH_DMA_MINALIGN,
405 413 fbi->fix.smem_len);
  414 +#endif
  415 +
406 416 fbi->fix.smem_start = (unsigned long)fbi->screen_base;
407 417 if (fbi->screen_base == 0) {
408 418 puts("Unable to allocate framebuffer memory\n");
409 419  
... ... @@ -416,7 +426,9 @@
416 426  
417 427 fbi->screen_size = fbi->fix.smem_len;
418 428  
  429 +#if CONFIG_IS_ENABLED(VIDEO)
419 430 gd->fb_base = fbi->fix.smem_start;
  431 +#endif
420 432  
421 433 /* Clear the screen */
422 434 memset((char *)fbi->screen_base, 0, fbi->fix.smem_len);
... ... @@ -611,4 +623,79 @@
611 623  
612 624 return 0;
613 625 }
  626 +
  627 +#if CONFIG_IS_ENABLED(DM_VIDEO)
  628 +enum {
  629 + /* Maximum display size we support */
  630 + LCD_MAX_WIDTH = 1920,
  631 + LCD_MAX_HEIGHT = 1080,
  632 + LCD_MAX_LOG2_BPP = VIDEO_BPP16,
  633 +};
  634 +
  635 +static int ipuv3_video_probe(struct udevice *dev)
  636 +{
  637 + struct video_uc_platdata *plat = dev_get_uclass_platdata(dev);
  638 + struct video_priv *uc_priv = dev_get_uclass_priv(dev);
  639 + u32 fb_start, fb_end;
  640 + int ret;
  641 +
  642 + debug("%s() plat: base 0x%lx, size 0x%x\n",
  643 + __func__, plat->base, plat->size);
  644 +
  645 + ret = ipu_probe();
  646 + if (ret)
  647 + return ret;
  648 +
  649 + ret = ipu_displays_init();
  650 + if (ret < 0)
  651 + return ret;
  652 +
  653 + ret = mxcfb_probe(gpixfmt, gdisp, gmode);
  654 + if (ret < 0)
  655 + return ret;
  656 +
  657 + uc_priv->xsize = gmode->xres;
  658 + uc_priv->ysize = gmode->yres;
  659 + uc_priv->bpix = LCD_MAX_LOG2_BPP;
  660 +
  661 + /* Enable dcache for the frame buffer */
  662 + fb_start = plat->base & ~(MMU_SECTION_SIZE - 1);
  663 + fb_end = plat->base + plat->size;
  664 + fb_end = ALIGN(fb_end, 1 << MMU_SECTION_SHIFT);
  665 + mmu_set_region_dcache_behaviour(fb_start, fb_end - fb_start,
  666 + DCACHE_WRITEBACK);
  667 + video_set_flush_dcache(dev, true);
  668 +
  669 + return 0;
  670 +}
  671 +
  672 +struct ipuv3_video_priv {
  673 + ulong regs;
  674 +};
  675 +
  676 +static int ipuv3_video_bind(struct udevice *dev)
  677 +{
  678 + struct video_uc_platdata *plat = dev_get_uclass_platdata(dev);
  679 +
  680 + plat->size = LCD_MAX_WIDTH * LCD_MAX_HEIGHT *
  681 + (1 << LCD_MAX_LOG2_BPP) / 8;
  682 +
  683 + return 0;
  684 +}
  685 +
  686 +static const struct udevice_id ipuv3_video_ids[] = {
  687 + { .compatible = "fsl,imx6q-ipu" },
  688 + { }
  689 +};
  690 +
  691 +U_BOOT_DRIVER(ipuv3_video) = {
  692 + .name = "ipuv3_video",
  693 + .id = UCLASS_VIDEO,
  694 + .of_match = ipuv3_video_ids,
  695 + .bind = ipuv3_video_bind,
  696 + .probe = ipuv3_video_probe,
  697 + .priv_auto_alloc_size = sizeof(struct ipuv3_video_priv),
  698 + .flags = DM_FLAG_PRE_RELOC,
  699 +};
  700 +#endif /* CONFIG_DM_VIDEO */