From: Mark Yao Date: Mon, 20 Apr 2015 08:46:05 +0000 (+0800) Subject: video: rockchip: logo: copy loader to framebuffer X-Git-Tag: firefly_0821_release~4158^2~178 X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=a9085919caeb58941c216e63a2bdef458d549f4d;p=firefly-linux-kernel-4.4.55.git video: rockchip: logo: copy loader to framebuffer Signed-off-by: Mark Yao --- diff --git a/drivers/video/rockchip/bmp_helper.c b/drivers/video/rockchip/bmp_helper.c index a50fd58729ea..3d0f9bf24cac 100755 --- a/drivers/video/rockchip/bmp_helper.c +++ b/drivers/video/rockchip/bmp_helper.c @@ -296,7 +296,42 @@ static void decode_rle8_bitmap(uint8_t *psrc, uint8_t *pdst, uint16_t *cmap, } } -int bmpdecoder(void *bmp_addr, void *pdst, int *width, int *height, int *bits) +/* + * get bmpdecoder needed size; + */ +int bmp_getsize(void *bmp_addr) +{ + BITMAPHEADER header; + BITMAPINFOHEADER infoheader; + char *src = bmp_addr; + int bits; + + memcpy(&header, bmp_addr, sizeof(header)); + src += sizeof(header); + + if (header.type != 0x4d42) { + pr_err("not bmp file type[%x], can't support\n", header.type); + return -EINVAL; + } + memcpy(&infoheader, src, sizeof(infoheader)); + + switch (infoheader.bitcount) { + case 8: + bits = 16; + break; + case 24: + bits = 24; + break; + case 16: + case 32: + pr_err("unsupport bit=%d now\n", infoheader.bitcount); + return -EINVAL; + } + + return infoheader.width * infoheader.height * bits >> 3; +} + +int bmpdecoder(void *bmp_addr, void *pdst, u16 *width, u16 *height, u16 *bits) { BITMAPHEADER header; BITMAPINFOHEADER infoheader; @@ -369,7 +404,6 @@ int bmpdecoder(void *bmp_addr, void *pdst, int *width, int *height, int *bits) if (flip) src -= *width * 3 * 2; } - *bits = 24; break; case 32: diff --git a/drivers/video/rockchip/bmp_helper.h b/drivers/video/rockchip/bmp_helper.h index fd1ad43f6d71..cefb30cbffb4 100644 --- a/drivers/video/rockchip/bmp_helper.h +++ b/drivers/video/rockchip/bmp_helper.h @@ -48,7 +48,8 @@ typedef struct bmpinfoheader { #define range(x, min, max) ((x) < (min)) ? (min) : (((x) > (max)) ? (max) : (x)) +int bmp_getsize(void *bmp_addr); int bmpencoder(void *__iomem *vaddr,int width, int height, u8 data_format, void *data, void (*fn)(void *, void *, int)); -int bmpdecoder(void *bmp_addr, void *dst, int *width, int *height, int *bits); +int bmpdecoder(void *bmp_addr, void *dst, u16 *width, u16 *height, u16 *bits); #endif /* _BMP_HELPER_H_ */ diff --git a/drivers/video/rockchip/rk_fb.c b/drivers/video/rockchip/rk_fb.c index 40782386d699..179f8c736048 100755 --- a/drivers/video/rockchip/rk_fb.c +++ b/drivers/video/rockchip/rk_fb.c @@ -884,11 +884,15 @@ static int rk_fb_close(struct fb_info *info, int user) */ info->var.xres_virtual = info->var.xres; info->var.yres_virtual = info->var.yres; + if (support_uboot_display()) { + info->var.bits_per_pixel = 32; + } else { #if defined(CONFIG_LOGO_LINUX_BMP) - info->var.bits_per_pixel = 32; + info->var.bits_per_pixel = 32; #else - info->var.bits_per_pixel = 16; + info->var.bits_per_pixel = 16; #endif + } info->fix.line_length = (info->var.xres_virtual) * (info->var.bits_per_pixel >> 3); info->var.width = dev_drv->screen0->width; @@ -906,6 +910,103 @@ static int rk_fb_close(struct fb_info *info, int user) return 0; } +#if defined(CONFIG_ROCKCHIP_RGA) || defined(CONFIG_ROCKCHIP_RGA2) +static int get_rga_format(int fmt) +{ + int rga_fmt = 0; + + switch (fmt) { + case XBGR888: + rga_fmt = RK_FORMAT_RGBX_8888; + break; + case ABGR888: + rga_fmt = RK_FORMAT_RGBA_8888; + break; + case ARGB888: + rga_fmt = RK_FORMAT_BGRA_8888; + break; + case RGB888: + rga_fmt = RK_FORMAT_RGB_888; + break; + case RGB565: + rga_fmt = RK_FORMAT_RGB_565; + break; + case YUV422: + rga_fmt = RK_FORMAT_YCbCr_422_SP; + break; + case YUV420: + rga_fmt = RK_FORMAT_YCbCr_420_SP; + break; + default: + rga_fmt = RK_FORMAT_RGBA_8888; + break; + } + + return rga_fmt; +} + +int rga_copy_common(phys_addr_t src, phys_addr_t dst, int src_fd, int dst_fd, + u16 src_width, u16 src_height, u16 src_stride, u16 src_virh, + u16 src_xpos, u16 src_ypos, int src_format, u16 dst_width, + u16 dst_height, u16 dst_stride, u16 dst_virh, u16 dst_xpos, + u16 dst_ypos, int dst_format, int iommu_en) +{ + struct rga_req Rga_Request; + long ret = 0; + + memset(&Rga_Request, 0, sizeof(Rga_Request)); + + Rga_Request.rotate_mode = 0; + Rga_Request.scale_mode = 0; + Rga_Request.src.act_w = src_width; + Rga_Request.src.act_h = src_height; + Rga_Request.src.vir_w = src_stride; + Rga_Request.src.vir_h = src_virh; + Rga_Request.src.format = get_rga_format(src_format); + Rga_Request.src.x_offset = src_xpos; + Rga_Request.src.y_offset = src_ypos; + + Rga_Request.dst.act_w = dst_width; + Rga_Request.dst.act_h = dst_height; + Rga_Request.dst.vir_w = dst_stride; + Rga_Request.dst.vir_h = dst_virh; + Rga_Request.dst.format = get_rga_format(dst_format); + Rga_Request.dst.x_offset = dst_xpos; + Rga_Request.dst.y_offset = dst_ypos; + + Rga_Request.src.yrgb_addr = src_fd; + Rga_Request.src.uv_addr = src; + Rga_Request.src.v_addr = 0; + + Rga_Request.dst.yrgb_addr = dst_fd; + Rga_Request.dst.uv_addr = dst; + Rga_Request.dst.v_addr = 0; + + Rga_Request.clip.xmin = 0; + Rga_Request.clip.xmax = 4096; + Rga_Request.clip.ymin = 0; + Rga_Request.clip.ymax = 4096; +#if defined(CONFIG_ROCKCHIP_IOMMU) + if (iommu_en) { + Rga_Request.mmu_info.mmu_en = 1; + Rga_Request.mmu_info.mmu_flag = 1; + if (src && dst_fd) + Rga_Request.mmu_info.mmu_flag |= (1 << 31) | (1 << 10); + } else { + Rga_Request.mmu_info.mmu_en = 0; + Rga_Request.mmu_info.mmu_flag = 0; + } +#else + Rga_Request.mmu_info.mmu_en = 0; + Rga_Request.mmu_info.mmu_flag = 0; +#endif + + ret = rga_ioctl_kernel(&Rga_Request); + if (ret) + pr_err(">>%s rga ioctl error\n", __func__); + return ret; +} +#endif #if defined(FB_ROATE_BY_KERNEL) #if defined(CONFIG_RK29_IPP) @@ -1034,40 +1135,6 @@ static void fb_copy_by_ipp(struct fb_info *dst_info, #endif #if defined(CONFIG_ROCKCHIP_RGA) || defined(CONFIG_ROCKCHIP_RGA2) -static int get_rga_format(int fmt) -{ - int rga_fmt = 0; - - switch (fmt) { - case XBGR888: - rga_fmt = RK_FORMAT_RGBX_8888; - break; - case ABGR888: - rga_fmt = RK_FORMAT_RGBA_8888; - break; - case ARGB888: - rga_fmt = RK_FORMAT_BGRA_8888; - break; - case RGB888: - rga_fmt = RK_FORMAT_RGB_888; - break; - case RGB565: - rga_fmt = RK_FORMAT_RGB_565; - break; - case YUV422: - rga_fmt = RK_FORMAT_YCbCr_422_SP; - break; - case YUV420: - rga_fmt = RK_FORMAT_YCbCr_420_SP; - break; - default: - rga_fmt = RK_FORMAT_RGBA_8888; - break; - } - - return rga_fmt; -} - static void rga_win_check(struct rk_lcdc_win *dst_win, struct rk_lcdc_win *src_win) { @@ -1101,6 +1168,7 @@ static void rga_win_check(struct rk_lcdc_win *dst_win, dst_win->area[0].yvir = dst_win->area[0].yact; } + static void win_copy_by_rga(struct rk_lcdc_win *dst_win, struct rk_lcdc_win *src_win, u16 orientation, int iommu_en) @@ -1411,36 +1479,181 @@ void rk_fd_fence_wait(struct rk_lcdc_driver *dev_drv, struct sync_fence *fence) if (err < 0) printk("error waiting on fence\n"); } -#if 0 -static int rk_fb_copy_from_loader(struct fb_info *info) + +static int rk_fb_copy_from_loader(struct fb_info *info, + phys_addr_t uboot_logo_base, + phys_addr_t uboot_logo_offset, + phys_addr_t uboot_logo_size) { - struct rk_fb_par *fb_par = (struct rk_fb_par *)info->par; + struct rk_fb_par *fb_par = info->par; struct rk_lcdc_driver *dev_drv = fb_par->lcdc_drv; - void *dst = info->screen_base; - u32 dsp_addr[4]; - u32 src; - u32 i,size; - int win_id; - struct rk_lcdc_win *win; + struct rk_fb *rk_fb = platform_get_drvdata(fb_pdev); + u16 width, height, bits; + int format; + int dst_format = info->var.nonstd & 0xff; + int dst_xpos, dst_ypos, dst_width, dst_height; + phys_addr_t start = uboot_logo_base + uboot_logo_offset; + unsigned int size = uboot_logo_size - uboot_logo_offset; + phys_addr_t src = 0; + phys_addr_t dst = 0; + int src_fd = 0; + char *vaddr = NULL, *bmp_buffer = NULL; + unsigned int nr_pages; + struct page **pages = NULL; + int fb_fd, tmp_fd = 0, bmp_fd = 0; + struct ion_handle *bmp_handle = NULL; +#if defined(CONFIG_ROCKCHIP_IOMMU) + unsigned int heap_id = dev_drv->iommu_enabled ? + ION_HEAP(ION_VMALLOC_HEAP_ID) : ION_HEAP(ION_CMA_HEAP_ID); + int rga_mmu_en = dev_drv->iommu_enabled ? 1 : 0; +#else + int rga_mmu_en = 0; + unsigned int heap_id = ION_HEAP(ION_CMA_HEAP_ID); +#endif + int logo_len; + int disp_mode = 0; + int ret, i=0; + + if (!uboot_logo_base || !uboot_logo_size) { + pr_err("can't found uboot logo address, failed\n"); + return -EINVAL; + } + /* + * rga driver can't handle fd = 0 case, + * so get a unused fd incase rga_fd=0. + */ + tmp_fd = get_unused_fd_flags(O_CLOEXEC); + if (tmp_fd < 0) + return tmp_fd; + + fb_fd = ion_share_dma_buf_fd(rk_fb->ion_client, fb_par->ion_hdl); + if (fb_fd < 0) { + dev_err(info->dev, "ion_share_dma_buf_fd failed\n"); + ret = fb_fd; + goto free_tmp_fd; + } + + dst_format = rk_fb_data_fmt(0, info->var.bits_per_pixel); + disp_mode = rk_fb->kernel_logo_mode; + + if (!uboot_logo_offset) { + dev_drv->ops->get_dspbuf_info(dev_drv, &width, &height, &format, + (u32 *)&start); + disp_mode = rk_fb->uboot_logo_mode; + src = start; + + goto start_copy; + } + size = roundup(size, PAGE_SIZE); - win_id = dev_drv->ops->fb_get_win_id(dev_drv, info->fix.id); - win = dev_drv->win[win_id]; - size = (win->area[0].xact) * (win->area[0].yact) << 2; - dev_drv->ops->get_dsp_addr(dev_drv, dsp_addr); - src = dsp_addr[win_id]; - dev_info(info->dev, "copy fb data %d x %d from dst_addr:%08x\n", - win->area[0].xact, win->area[0].yact, src); - for (i = 0; i < size; i += PAGE_SIZE) { - void *page = phys_to_page(i + src); - void *from_virt = kmap(page); - void *to_virt = dst + i; - memcpy(to_virt, from_virt, PAGE_SIZE); - } - dev_drv->ops->direct_set_addr(dev_drv, win_id, - info->fix.smem_start); - return 0; -} + nr_pages = size >> PAGE_SHIFT; + pages = kzalloc(sizeof(struct page) * nr_pages, GFP_KERNEL); + while (i < nr_pages) { + pages[i] = phys_to_page(start); + start += PAGE_SIZE; + i++; + } + vaddr = vmap(pages, nr_pages, VM_MAP, + pgprot_writecombine(PAGE_KERNEL)); + if (!vaddr) { + pr_err("failed to vmap phy addr 0x%lx\n", + (long)(uboot_logo_base + uboot_logo_offset)); + ret = -ENXIO; + goto free_pages; + } + + logo_len = bmp_getsize(vaddr); + if (logo_len < 0) { + ret = -EINVAL; + goto free_vmap; + } + /* + * alloc a tmp buffer for logo parse. + */ + bmp_handle = ion_alloc(rk_fb->ion_client, logo_len, 0, heap_id, 0); + if (IS_ERR(bmp_handle)) { + ret = -ENOMEM; + goto free_vmap; + } + bmp_fd = ion_share_dma_buf_fd(rk_fb->ion_client, bmp_handle); + if (bmp_fd < 0) { + dev_err(info->dev, "ion_share_dma_buf_fd failed\n"); + ret = -ENXIO; + goto free_bmp_handle; + } + bmp_buffer = ion_map_kernel(rk_fb->ion_client, bmp_handle); + if (IS_ERR(bmp_buffer)) { + ret = PTR_ERR(bmp_buffer); + goto free_bmp_fd; + } + + if (uboot_logo_offset) { + if(bmpdecoder(vaddr, bmp_buffer, &width, &height, &bits)) { + ret = -EINVAL; + goto ummap_bmp_buffer; + } + format = rk_fb_data_fmt(0, bits); + } else { + memcpy(bmp_buffer, vaddr, logo_len); + } + + src_fd = bmp_fd; + +start_copy: + if (width > info->var.xres || height > info->var.yres) { + pr_err("Error: Please Don't do that thing:\n"); + pr_err("\tLogo size[%dx%d] > Fb size[%dx%d]\n", width, height, + info->var.xres, info->var.yres); + pr_err("convert bmp size is Easy by many Pc tools\n"); + BUG(); + } + + if (disp_mode == DISP_CENTER) { + dst_xpos = (info->var.xres - width) >> 1; + dst_ypos = (info->var.yres - height) >> 1; + dst_width = width; + dst_height = height; + } else { + dst_xpos = 0; + dst_ypos = 0; + dst_width = info->var.xres; + dst_height = info->var.yres; + } + +#if defined(CONFIG_ROCKCHIP_RGA) || defined(CONFIG_ROCKCHIP_RGA2) + rga_copy_common(src, dst, src_fd, fb_fd, width, height, + width, height, 0, 0, format, dst_width, + dst_height, info->var.xres, info->var.yres, dst_xpos, + dst_ypos, dst_format, rga_mmu_en); +#else + /* + * Todo, if rga is not support, just return to kernel display + */ + return -EINVAL; #endif +free_bmp_fd: + /* + * Todo: + * Now can't find a suitable to free fd, close is userspace api, not + * kernel api. + */ +// if (bmp_fd) +// close(bmp_fd); +ummap_bmp_buffer: + if (bmp_handle) + ion_unmap_kernel(rk_fb->ion_client, bmp_handle); +free_bmp_handle: + if (bmp_handle) + ion_free(rk_fb->ion_client, bmp_handle); +free_vmap: + vunmap(vaddr); +free_pages: + kfree(pages); +// close(fb_fd); +free_tmp_fd: + put_unused_fd(tmp_fd); + return ret; +} #ifdef CONFIG_ROCKCHIP_IOMMU static int g_last_addr[4][4]; int g_last_timeout; @@ -3053,6 +3266,18 @@ static struct fb_ops fb_ops = { .fb_imageblit = cfb_imageblit, }; +static struct fb_var_screeninfo uboot_logo_var = { + .red = {16, 8, 0}, + .green = {8, 8, 0}, + .blue = {0, 8, 0}, + .transp = {0, 0, 0}, + .nonstd = HAL_PIXEL_FORMAT_BGRA_8888, + .grayscale = 0, /* (ysize<<20+xsize<<8) */ + .activate = FB_ACTIVATE_NOW, + .accel_flags = 0, + .vmode = FB_VMODE_NONINTERLACED, +}; + static struct fb_var_screeninfo def_var = { #if defined(CONFIG_LOGO_LINUX_BMP) .red = {16, 8, 0}, @@ -3229,8 +3454,8 @@ int rk_fb_switch_screen(struct rk_screen *screen, int enable, int lcdc_id) (rk_fb->disp_policy != DISPLAY_POLICY_BOX) && (rk_fb->disp_policy != DISPLAY_POLICY_BOX_TEMP)) dev_drv->ops->backlight_close(dev_drv, 1); - if (dev_drv->ops->dsp_black) - dev_drv->ops->dsp_black(dev_drv, 1); +// if (dev_drv->ops->dsp_black) +// dev_drv->ops->dsp_black(dev_drv, 1); if ((dev_drv->ops->set_screen_scaler) && (rk_fb->disp_mode == ONE_DUAL)) dev_drv->ops->set_screen_scaler(dev_drv, @@ -3729,17 +3954,23 @@ int rk_fb_register(struct rk_lcdc_driver *dev_drv, fb_par->id = rk_fb->num_fb; fb_par->lcdc_drv = dev_drv; fbi->par = (void *)fb_par; - fbi->var = def_var; + if (support_uboot_display()) { + fbi->var = uboot_logo_var; + fbi->var.bits_per_pixel = 32; + } else { + fbi->var = def_var; +#if defined(CONFIG_LOGO_LINUX_BMP) + fbi->var.bits_per_pixel = 32; +#else + fbi->var.bits_per_pixel = 16; +#endif + } fbi->fix = def_fix; sprintf(fbi->fix.id, "fb%d", rk_fb->num_fb); fb_videomode_to_var(&fbi->var, &dev_drv->cur_screen->mode); fbi->var.grayscale |= (fbi->var.xres << 8) + (fbi->var.yres << 20); -#if defined(CONFIG_LOGO_LINUX_BMP) - fbi->var.bits_per_pixel = 32; -#else - fbi->var.bits_per_pixel = 16; -#endif + fbi->fix.line_length = (fbi->var.xres_virtual) * (fbi->var.bits_per_pixel >> 3); fbi->var.width = dev_drv->cur_screen->width; @@ -3807,9 +4038,6 @@ int rk_fb_register(struct rk_lcdc_driver *dev_drv, /* show logo for primary display device */ #if !defined(CONFIG_FRAMEBUFFER_CONSOLE) if (dev_drv->prop == PRMRY) { - u16 xact, yact; - int format; - u32 dsp_addr; struct fb_info *main_fbi = rk_fb->fb[0]; main_fbi->fbops->fb_open(main_fbi, 1); main_fbi->var.pixclock = dev_drv->pixclock; @@ -3825,136 +4053,35 @@ int rk_fb_register(struct rk_lcdc_driver *dev_drv, dev_drv->uboot_logo = support_uboot_display(); if (dev_drv->uboot_logo && - uboot_logo_offset && uboot_logo_base) { - int width, height, bits; - phys_addr_t start = uboot_logo_base + uboot_logo_offset; - unsigned int size = uboot_logo_size - uboot_logo_offset; - unsigned int nr_pages; - struct page **pages; - char *vaddr; - int i = 0; - - if (dev_drv->ops->get_dspbuf_info) - dev_drv->ops->get_dspbuf_info(dev_drv, &xact, - &yact, &format, &dsp_addr); - nr_pages = size >> PAGE_SHIFT; - pages = kzalloc(sizeof(struct page) * nr_pages, - GFP_KERNEL); - while (i < nr_pages) { - pages[i] = phys_to_page(start); - start += PAGE_SIZE; - i++; - } - vaddr = vmap(pages, nr_pages, VM_MAP, - pgprot_writecombine(PAGE_KERNEL)); - if (!vaddr) { - pr_err("failed to vmap phy addr 0x%lx\n", - (long)(uboot_logo_base + - uboot_logo_offset)); - return -1; - } - - if(bmpdecoder(vaddr, main_fbi->screen_base, &width, - &height, &bits)) { - kfree(pages); - vunmap(vaddr); - return 0; - } - kfree(pages); - vunmap(vaddr); - if (dev_drv->uboot_logo && - (width != xact || height != yact)) { - pr_err("can't support uboot kernel logo use different size [%dx%d] != [%dx%d]\n", - xact, yact, width, height); - return 0; - } - - if (dev_drv->ops->post_dspbuf) { - dev_drv->ops->post_dspbuf(dev_drv, - main_fbi->fix.smem_start, - rk_fb_data_fmt(0, bits), - width, height, width * bits >> 5); - } - if (dev_drv->iommu_enabled) { - rk_fb_poll_wait_frame_complete(); - if (dev_drv->ops->mmu_en) - dev_drv->ops->mmu_en(dev_drv); - freed_index = 0; - } - - return 0; - } else if (dev_drv->uboot_logo && uboot_logo_base) { - u32 start = uboot_logo_base; - u32 start_base = start; - int logo_len, i=0; - unsigned int nr_pages; - struct page **pages; - char *vaddr; - - dev_drv->ops->get_dspbuf_info(dev_drv, &xact, - &yact, &format, - &start); - logo_len = rk_fb_pixel_width(format) * xact * yact >> 3; - if (logo_len > uboot_logo_size || - logo_len > main_fbi->fix.smem_len) { - pr_err("logo size > uboot reserve buffer size\n"); - return -1; - } - - nr_pages = uboot_logo_size >> PAGE_SHIFT; - pages = kzalloc(sizeof(struct page) * nr_pages, - GFP_KERNEL); - while (i < nr_pages) { - pages[i] = phys_to_page(start); - start += PAGE_SIZE; - i++; - } - vaddr = vmap(pages, nr_pages, VM_MAP, - pgprot_writecombine(PAGE_KERNEL)); - if (!vaddr) { - pr_err("failed to vmap phy addr 0x%x\n", - start_base); - return -1; - } - - memcpy(main_fbi->screen_base, vaddr, logo_len); - - kfree(pages); - vunmap(vaddr); - - dev_drv->ops->post_dspbuf(dev_drv, - main_fbi->fix.smem_start, - format, xact, yact, - xact * rk_fb_pixel_width(format) >> 5); - if (dev_drv->iommu_enabled) { - rk_fb_poll_wait_frame_complete(); - if (dev_drv->ops->mmu_en) - dev_drv->ops->mmu_en(dev_drv); - freed_index = 0; - } - return 0; + !rk_fb_copy_from_loader(main_fbi, uboot_logo_base, + uboot_logo_offset, + uboot_logo_size)) { + pr_info("success display uboot logo\n"); } else { - if (dev_drv->iommu_enabled) { - if (dev_drv->ops->mmu_en) - dev_drv->ops->mmu_en(dev_drv); - freed_index = 0; + #if defined(CONFIG_LOGO) + #if defined(CONFIG_LOGO_LINUX_BMP) + if (fb_prewine_bmp_logo(main_fbi, FB_ROTATE_UR)) { + fb_set_cmap(&main_fbi->cmap, main_fbi); + fb_show_bmp_logo(main_fbi, FB_ROTATE_UR); + } + #else + if (fb_prepare_logo(main_fbi, FB_ROTATE_UR)) { + fb_set_cmap(&main_fbi->cmap, main_fbi); + fb_show_logo(main_fbi, FB_ROTATE_UR); } + #endif + #endif } -#if defined(CONFIG_LOGO) + main_fbi->fbops->fb_set_par(main_fbi); -#if defined(CONFIG_LOGO_LINUX_BMP) - if (fb_prewine_bmp_logo(main_fbi, FB_ROTATE_UR)) { - fb_set_cmap(&main_fbi->cmap, main_fbi); - fb_show_bmp_logo(main_fbi, FB_ROTATE_UR); - } -#else - if (fb_prepare_logo(main_fbi, FB_ROTATE_UR)) { - fb_set_cmap(&main_fbi->cmap, main_fbi); - fb_show_logo(main_fbi, FB_ROTATE_UR); - } -#endif main_fbi->fbops->fb_pan_display(&main_fbi->var, main_fbi); -#endif + #if defined(CONFIG_ROCKCHIP_IOMMU) + if (dev_drv->iommu_enabled) { + rk_fb_poll_wait_frame_complete(); + if (dev_drv->ops->mmu_en) + dev_drv->ops->mmu_en(dev_drv); + } + #endif } else { struct fb_info *extend_fbi = rk_fb->fb[rk_fb->num_fb >> 1]; extend_fbi->var.pixclock = rk_fb->fb[0]->var.pixclock; @@ -4026,6 +4153,11 @@ static int rk_fb_probe(struct platform_device *pdev) if (!of_property_read_u32(np, "rockchip,uboot-logo-on", &uboot_logo_on)) printk(KERN_DEBUG "uboot-logo-on:%d\n", uboot_logo_on); + if (!of_property_read_u32(np, "rockchip,uboot-logo-mode", &mode)) + rk_fb->uboot_logo_mode = mode; + if (!of_property_read_u32(np, "rockchip,kernel-logo-mode", &mode)) + rk_fb->kernel_logo_mode = mode; + dev_set_name(&pdev->dev, "rockchip-fb"); #if defined(CONFIG_ION_ROCKCHIP) rk_fb->ion_client = rockchip_ion_client_create("rk_fb"); diff --git a/include/dt-bindings/rkfb/rk_fb.h b/include/dt-bindings/rkfb/rk_fb.h index e1daff3c1c69..a9d38c46808a 100755 --- a/include/dt-bindings/rkfb/rk_fb.h +++ b/include/dt-bindings/rkfb/rk_fb.h @@ -54,6 +54,9 @@ #define ROTATE_180 8 #define ROTATE_270 12 +#define DISP_CENTER 0 +#define DISP_FULLSCREEN 1 + #define COLOR_RGB 0 #define COLOR_YCBCR 1 diff --git a/include/linux/rk_fb.h b/include/linux/rk_fb.h index 99edb171a84d..003ba824bc2f 100755 --- a/include/linux/rk_fb.h +++ b/include/linux/rk_fb.h @@ -93,6 +93,8 @@ */ #define ROTATE_270 12 /* clockwise rotate 270 degrees */ +#define DISP_CENTER 0 +#define DISP_FULLSCREEN 1 /** * pixel align value for gpu,align as 64 bytes in an odd number of times @@ -680,6 +682,8 @@ struct rk_fb_par { struct rk_fb { int disp_mode; int disp_policy; + int uboot_logo_mode; + int kernel_logo_mode; struct rk29fb_info *mach_info; struct fb_info *fb[RK_MAX_FB_SUPPORT*2]; int num_fb;