aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGuodong Xu <guodong.xu@linaro.org>2013-04-27 09:24:02 +0800
committerGuodong Xu <guodong.xu@linaro.org>2013-04-27 09:24:02 +0800
commitc9fe8ae84a2dfc27bac57ec936e99bcd0a238d65 (patch)
tree72965e45a21e5f2a33fd9c4e512431fec8d976df
parent79340190bf465bc3990a80ee32d2f380c892c930 (diff)
parentca101c9493d7d30ed9881777a0501d983bf14222 (diff)
Merge remote-tracking branch 'origin/fb_4.26' into integration-linux-mainline
-rw-r--r--arch/arm/boot/dts/hi3620.dtsi2
-rw-r--r--arch/arm/boot/dts/hi4511.dts2
-rw-r--r--arch/arm/mach-hs/ipps2.c2
-rw-r--r--drivers/video/hisilicon/hi3620_fb.c97
4 files changed, 85 insertions, 18 deletions
diff --git a/arch/arm/boot/dts/hi3620.dtsi b/arch/arm/boot/dts/hi3620.dtsi
index ecd07da65e55..d4b33bf83826 100644
--- a/arch/arm/boot/dts/hi3620.dtsi
+++ b/arch/arm/boot/dts/hi3620.dtsi
@@ -238,7 +238,7 @@
#clock-cells = <0>;
clocks = <&osc26m>;
clock-output-names = "rclk_tcxo";
- hisilicon,fixed-factor = <1 4>;
+ hisilicon,fixed-factor = <1 1>;
};
refclk_timer0: refclk@12 {
compatible = "hisilicon,hi3620-clk-mux";
diff --git a/arch/arm/boot/dts/hi4511.dts b/arch/arm/boot/dts/hi4511.dts
index 39431d8689c7..96346e5535f5 100644
--- a/arch/arm/boot/dts/hi4511.dts
+++ b/arch/arm/boot/dts/hi4511.dts
@@ -1442,7 +1442,7 @@
status = "ok";
};
edc0: edc@fa202000 {
- hisilicon,pixel-format = "RGBA8888";
+ hisilicon,pixel-format = "RGB565";
hisilicon,color-mode = <5>;
hisilicon,dsi-clock-frequency = <241000000>; /* 241MHz, not 300MHz */
hisilicon,mipi-mode = "video";
diff --git a/arch/arm/mach-hs/ipps2.c b/arch/arm/mach-hs/ipps2.c
index a961a6032f63..4a3fd7f84dec 100644
--- a/arch/arm/mach-hs/ipps2.c
+++ b/arch/arm/mach-hs/ipps2.c
@@ -1152,8 +1152,8 @@ static struct platform_driver ipps2_driver = {
.of_match_table = of_match_ptr(mcu_match),
#ifdef CONFIG_PM_SLEEP
.pm = &ipps2_pm_ops,
-#endif
.shutdown = (void(*)(struct device *dev))(ipps2_suspend),
+#endif
},
};
diff --git a/drivers/video/hisilicon/hi3620_fb.c b/drivers/video/hisilicon/hi3620_fb.c
index e0d9d13082cf..981951a98805 100644
--- a/drivers/video/hisilicon/hi3620_fb.c
+++ b/drivers/video/hisilicon/hi3620_fb.c
@@ -283,17 +283,23 @@ static void set_screen_dimensions(struct fb_info *fb)
writel_relaxed(timing, info->reg_base + DSI_VTIMING_CFG);
}
-static void set_graphics_start(struct fb_info *fb, int xoffset, int yoffset)
+static void set_graphics_start(struct fb_info *fb, int xoffs, int yoffs)
{
struct hi3620fb_info *info = fb->par;
+ struct fb_var_screeninfo *var = &fb->var;
void __iomem *base = info->reg_base;
- u32 data;
+ u32 addr, data;
- data = yoffset & 0xfff;
- data |= (xoffset & 0xfff) << 16;
+ if (yoffs >= var->yres)
+ data = (yoffs - var->yres) & 0xfff;
+ else
+ data = yoffs & 0xfff;
+ data |= (xoffs & 0xfff) << 16;
writel_relaxed(data, base + EDC_VIDEO_CHAN_XY);
/* setup dma address */
- writel_relaxed(fb->fix.smem_start, base + EDC_VIDEO_CHAN_ADDR);
+ addr = (yoffs * var->xres_virtual + xoffs) * var->bits_per_pixel / 8;
+ addr = ALIGN(addr + fb->fix.smem_start, 64);
+ writel_relaxed(addr, base + EDC_VIDEO_CHAN_ADDR);
}
static void set_dma_control(struct fb_info *fb)
@@ -305,15 +311,13 @@ static void set_dma_control(struct fb_info *fb)
writel_relaxed(fb->fix.line_length, base + EDC_VIDEO_CHAN_STRIDE);
}
-static int hi3620fb_set_par(struct fb_info *fb)
+static void set_color(struct fb_info *fb)
{
struct fb_var_screeninfo *var = &fb->var;
struct hi3620fb_info *info = fb->par;
void __iomem *base = info->reg_base;
unsigned int ctrl = 0;
- fb->fix.ypanstep = var->yres;
-
ctrl = readl_relaxed(base + EDC_VIDEO_CHAN_CTRL);
if (var->blue.offset)
ctrl |= EDC_CHAN_CTRL_BGR; /* BGR format */
@@ -332,14 +336,62 @@ static int hi3620fb_set_par(struct fb_info *fb)
ctrl |= 3 << 16;
break;
}
+ writel_relaxed(ctrl, base + EDC_VIDEO_CHAN_CTRL);
+ ctrl = readl_relaxed(base + EDC_DISP_CTL);
+ ctrl &= ~(3 << 6);
+ switch (info->pix_fmt) {
+ case IMG_PIXEL_FORMAT_ARGB1555:
+ case IMG_PIXEL_FORMAT_RGB555:
+ case IMG_PIXEL_FORMAT_RGB565:
+ break;
+ case IMG_PIXEL_FORMAT_RGB888:
+ case IMG_PIXEL_FORMAT_ARGB8888:
+ ctrl |= 2 << 6;
+ break;
+ }
+ writel_relaxed(ctrl, base + EDC_DISP_CTL);
+ ctrl = readl_relaxed(base + LDI_CTRL);
+ ctrl &= ~(3 << 3);
+ switch (info->pix_fmt) {
+ case IMG_PIXEL_FORMAT_ARGB1555:
+ case IMG_PIXEL_FORMAT_RGB555:
+ case IMG_PIXEL_FORMAT_RGB565:
+ break;
+ case IMG_PIXEL_FORMAT_RGB888:
+ case IMG_PIXEL_FORMAT_ARGB8888:
+ ctrl |= 2 << 3;
+ break;
+ }
+ writel_relaxed(ctrl, base + LDI_CTRL);
+ ctrl = readl_relaxed(base + DSI_DPI_CFG);
+ ctrl &= ~(7 << 2);
+ switch (info->pix_fmt) {
+ case IMG_PIXEL_FORMAT_ARGB1555:
+ case IMG_PIXEL_FORMAT_RGB555:
+ case IMG_PIXEL_FORMAT_RGB565:
+ break;
+ case IMG_PIXEL_FORMAT_RGB888:
+ case IMG_PIXEL_FORMAT_ARGB8888:
+ ctrl |= 5 << 2;
+ break;
+ }
+ writel_relaxed(ctrl, base + DSI_DPI_CFG);
+}
+
+static int hi3620fb_set_par(struct fb_info *fb)
+{
+ struct fb_var_screeninfo *var = &fb->var;
+ struct hi3620fb_info *info = fb->par;
+ void __iomem *base = info->reg_base;
+ unsigned int ctrl = 0;
+
+ fb->fix.ypanstep = var->yres;
+
+ ctrl = readl_relaxed(base + EDC_VIDEO_CHAN_CTRL);
ctrl |= EDC_VIDEO_CHAN_CTRL_EN;
- /* color key & rotate is always disabled, linear format */
-// ctrl |= 1 << 24; /* enable channel */
-// ctrl &= ~0xfff;
-// ctrl |= 0xa;
-// ctrl |= var->yres - 1; /* debug. add for interrupt */
writel_relaxed(ctrl, base + EDC_VIDEO_CHAN_CTRL);
+ set_color(fb);
set_panel_control(fb);
set_screen_dimensions(fb);
set_dma_control(fb);
@@ -350,6 +402,16 @@ static int hi3620fb_set_par(struct fb_info *fb)
static int hi3620fb_pan_display(struct fb_var_screeninfo *var,
struct fb_info *fb)
{
+ struct hi3620fb_info *info = fb->par;
+ void __iomem *base = info->reg_base;
+
+ set_graphics_start(fb, var->xoffset, var->yoffset);
+ update_edc(base);
+ return 0;
+}
+
+static int hi3620fb_blank(int blank_mode, struct fb_info *info)
+{
return 0;
}
@@ -391,6 +453,7 @@ static struct fb_ops hi3620fb_ops = {
.fb_check_var = hi3620fb_check_var,
.fb_set_par = hi3620fb_set_par,
.fb_pan_display = hi3620fb_pan_display,
+ .fb_blank = hi3620fb_blank,
.fb_ioctl = hi3620fb_ioctl,
.fb_compat_ioctl = hi3620fb_ioctl,
};
@@ -462,7 +525,7 @@ static int hi3620_init_mode(struct device_node *np, struct fb_info *fb)
set_pix_fmt(info, pix_fmt);
fb_videomode_to_var(var, fb_vm);
var->xres_virtual = fb_vm->xres;
- var->yres_virtual = fb_vm->yres;
+ var->yres_virtual = fb_vm->yres * 2; /* double buffering */
var->grayscale = 0;
var->accel_flags = FB_ACCEL_NONE;
/* Now assume that video mode is only 1 in DTS. */
@@ -481,7 +544,7 @@ static int hi3620_init_mode(struct device_node *np, struct fb_info *fb)
fix->accel = FB_ACCEL_NONE; /* No hardware accelerator */
length = var->xres_virtual * var->bits_per_pixel / 8;
- fb->fix.line_length = ALIGN(length, 64);
+ fb->fix.line_length = length;
fb->fix.smem_len = ALIGN(fb->fix.line_length * fb->var.yres_virtual,
PAGE_SIZE);
hi3620_parse_dt(np, info);
@@ -614,6 +677,10 @@ static int hi3620_fb_probe(struct platform_device *pdev)
fb->screen_base = dma_alloc_coherent(fb->dev, fb->fix.smem_len,
&info->fb_start_dma,
GFP_KERNEL);
+ if (!fb->screen_base) {
+ dev_err(dev, "failed to allocate memory\n");
+ return -ENOMEM;
+ }
fb->screen_size = fb->fix.smem_len;
fb->fix.smem_start = info->fb_start_dma;
#else