vdin: hdmi 4k,garbage is seen at the bottom [1/1]
authorzhiwei.yuan <zhiwei.yuan@amlogic.com>
Fri, 27 Sep 2019 09:46:52 +0000 (17:46 +0800)
committerJianxin Pan <jianxin.pan@amlogic.com>
Mon, 30 Sep 2019 07:40:40 +0000 (00:40 -0700)
PD#SWPL-14760

Problem:
afbce write need more memory since block can not be separater

Solution:
increase memory size for each frame

Verify:
verified by t962x2_x301

Change-Id: I5a80d0d6f22ef72353bf8b9faa904ec4f4b7c7aa
Signed-off-by: zhiwei.yuan <zhiwei.yuan@amlogic.com>
14 files changed:
arch/arm/boot/dts/amlogic/tl1_t962x2_skt.dts
arch/arm/boot/dts/amlogic/tl1_t962x2_t309.dts
arch/arm/boot/dts/amlogic/tl1_t962x2_x301_1g.dts
arch/arm/boot/dts/amlogic/tl1_t962x2_x301_1g_drm.dts
arch/arm/boot/dts/amlogic/tl1_t962x2_x301_2g.dts
arch/arm/boot/dts/amlogic/tl1_t962x2_x301_2g_drm.dts
arch/arm64/boot/dts/amlogic/tl1_t962x2_t309.dts
arch/arm64/boot/dts/amlogic/tl1_t962x2_x301_1g.dts
arch/arm64/boot/dts/amlogic/tl1_t962x2_x301_1g_drm.dts
arch/arm64/boot/dts/amlogic/tl1_t962x2_x301_2g.dts
arch/arm64/boot/dts/amlogic/tl1_t962x2_x301_2g_drm.dts
drivers/amlogic/media/vin/tvin/vdin/vdin_afbce.c
drivers/amlogic/media/vin/tvin/vdin/vdin_canvas.c
drivers/amlogic/media/vin/tvin/vdin/vdin_drv.h

index ac7d102..769b910 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 */
                tv_bit_mode = <0x215>;
                /* afbce_bit_mode: (amlogic frame buff compression encoder)
-                * bit 0~3:
-                * 0 -- normal mode, not use afbce
-                * 1 -- use afbce non-mmu mode
-                * 2 -- use afbce mmu mode
-                * bit 4:
-                * 0 -- afbce compression-lossy disable
-                * 1 -- afbce compression-lossy enable
+                * bit0 -- enable afbce
+                * bit1 -- enable afbce compression-lossy
+                * bit4 -- afbce for 4k
+                * bit5 -- afbce for 1080p
+                * bit6 -- afbce for 720p
+                * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 79c90aa..b22f1b4 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 */
                tv_bit_mode = <0x215>;
                /* afbce_bit_mode: (amlogic frame buff compression encoder)
-                * bit 0~3:
-                * 0 -- normal mode, not use afbce
-                * 1 -- use afbce non-mmu mode
-                * 2 -- use afbce mmu mode
-                * bit 4:
-                * 0 -- afbce compression-lossy disable
-                * 1 -- afbce compression-lossy enable
+                * bit0 -- enable afbce
+                * bit1 -- enable afbce compression-lossy
+                * bit4 -- afbce for 4k
+                * bit5 -- afbce for 1080p
+                * bit6 -- afbce for 720p
+                * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index a917c3a..1fe3dcc 100644 (file)
@@ -90,7 +90,7 @@
                        compatible = "shared-dma-pool";
                        reusable;
                        /* ion_codec_mm max can alloc size 80M*/
-                       size = <0xd000000>;
+                       size = <0xdc00000>;
                        alignment = <0x400000>;
                        linux,contiguous-region;
                        alloc-ranges = <0x30000000 0x10000000>;
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 9fa4aea..d042d2f 100644 (file)
@@ -91,7 +91,7 @@
                        compatible = "shared-dma-pool";
                        reusable;
                        /* ion_codec_mm max can alloc size 80M*/
-                       size = <0xd000000>;
+                       size = <0xdc00000>;
                        alignment = <0x400000>;
                        linux,contiguous-region;
                        alloc-ranges = <0x30000000 0x10000000>;
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 090af19..7a06605 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 3a9a387..02c3c78 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 2349a9e..9118312 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 */
                tv_bit_mode = <0x215>;
                /* afbce_bit_mode: (amlogic frame buff compression encoder)
-                * bit 0~3:
-                * 0 -- normal mode, not use afbce
-                * 1 -- use afbce non-mmu mode
-                * 2 -- use afbce mmu mode
-                * bit 4:
-                * 0 -- afbce compression-lossy disable
-                * 1 -- afbce compression-lossy enable
+                * bit0 -- enable afbce
+                * bit1 -- enable afbce compression-lossy
+                * bit4 -- afbce for 4k
+                * bit5 -- afbce for 1080p
+                * bit6 -- afbce for 720p
+                * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index beb85bd..3fe9871 100644 (file)
@@ -89,7 +89,7 @@
                        compatible = "shared-dma-pool";
                        reusable;
                        /* ion_codec_mm max can alloc size 80M*/
-                       size = <0x0 0xd000000>;
+                       size = <0x0 0xdc00000>;
                        alignment = <0x0 0x400000>;
                        linux,contiguous-region;
                        alloc-ranges = <0x0 0x30000000 0x0 0x10000000>;
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index bc8be40..c800f71 100644 (file)
@@ -89,7 +89,7 @@
                        compatible = "shared-dma-pool";
                        reusable;
                        /* ion_codec_mm max can alloc size 80M*/
-                       size = <0x0 0xd000000>;
+                       size = <0x0 0xdc00000>;
                        alignment = <0x0 0x400000>;
                        linux,contiguous-region;
                        alloc-ranges = <0x0 0x30000000 0x0 0x10000000>;
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 97303f8..5c8c58e 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 023f91e..4505f99 100644 (file)
                 *if support 4K2K-YUV422-10bit-wr:3840*2160*3*6 ~= 160M
                 *if support 4K2K-YUV422-8BIT-WR:3840*2160*2*4 ~= 64M
                 *if support 1080p-YUV422-8BIT-WR:1920*1080*2*4 ~= 16M
+                *worst case:(4096*2160*4 + 2M(afbce issue)) *6buf = 214.5M
                 */
-               cma_size = <200>;
+               cma_size = <215>;
                interrupts = <0 83 1>;
                rdma-irq = <2>;
                clocks = <&clkc CLKID_FCLK_DIV5>,
                 * bit6 -- afbce for 720p
                 * bit7 -- afbce for smaller resolution
                 */
-               afbce_bit_mode = <0x11>;
+               afbce_bit_mode = <0x31>;
        };
 
        vdin@1 {
index 6b04de4..ab385af 100644 (file)
@@ -350,6 +350,12 @@ void vdin_afbce_config(struct vdin_dev_s *devp)
 
        W_VCBUS_BIT(AFBCE_MMU_RMIF_CTRL4, devp->afbce_info->table_paddr, 0, 32);
        W_VCBUS_BIT(AFBCE_MMU_RMIF_SCOPE_X, cur_mmu_used, 0, 12);
+       /*for almost uncompressed pattern,garbage at bottom
+        *(h_active * v_active * bytes per pixel + 3M) / page_size - 1
+        *where 3M is the rest bytes of block,since every block must not be\
+        *separated by 2 pages
+        */
+       W_VCBUS_BIT(AFBCE_MMU_RMIF_SCOPE_X, 0x1c4f, 16, 13);
 
        W_VCBUS_BIT(AFBCE_ENABLE, 1, 12, 1); //set afbce pulse mode
        W_VCBUS_BIT(AFBCE_ENABLE, 0, 8, 1);//disable afbce
index bc204b3..2620009 100644 (file)
@@ -427,14 +427,10 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                CODEC_MM_FLAGS_DMA;
        unsigned int max_buffer_num = min_buf_num;
        unsigned int i, j;
-       /*head_size:3840*2160*3*9/32*/
-       unsigned int afbce_head_size_byte = PAGE_SIZE * 1712;
-       /*afbce map_table need 218700 byte at most*/
-       unsigned int afbce_table_size_byte = PAGE_SIZE * 60;/*0.3M*/
+       unsigned int afbce_head_total_bytes;
+       unsigned int afbce_table_total_bytes;
        unsigned long ref_paddr;
        unsigned int mem_used;
-       unsigned int frame_head_size;
-       unsigned int mmu_used;
 
        if (devp->rdma_enable)
                max_buffer_num++;
@@ -456,8 +452,11 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                        devp->cma_mem_alloc);
                return 0;
        }
+
+       /*pixels*/
        h_size = devp->h_active;
        v_size = devp->v_active;
+
        if (devp->canvas_config_mode == 1) {
                h_size = max_buf_width;
                v_size = max_buf_height;
@@ -518,12 +517,20 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                                VDIN_YUV422_8BIT_PER_PIXEL_BYTE;
                }
        }
+
+       /*1 frame bytes*/
        mem_size = h_size * v_size;
+       /*for almost uncompressed pattern,garbage at bottom
+        *1024x1658 is the worst case,each page wast 2160x3x256byte for 4096
+        *since every block must not be separated by 2 pages
+        */
+       mem_size += 1024 * 1658;
+
        if ((devp->format_convert >= VDIN_FORMAT_CONVERT_YUV_NV12) &&
                (devp->format_convert <= VDIN_FORMAT_CONVERT_RGB_NV21))
                mem_size = (mem_size * 3)/2;
        devp->vfmem_size = PAGE_ALIGN(mem_size) + dolby_size_byte;
-       devp->vfmem_size = (devp->vfmem_size/PAGE_SIZE + 1)*PAGE_SIZE;
+       devp->vfmem_size = roundup(devp->vfmem_size, PAGE_SIZE);
 
        if (devp->set_canvas_manual == 1) {
                for (i = 0; i < VDIN_CANVAS_MAX_CNT; i++) {
@@ -539,10 +546,10 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                devp->vfmem_max_cnt = max_buffer_num;
        }
 
-
+       /*total frames bytes*/
        mem_size = PAGE_ALIGN(mem_size) * max_buffer_num +
                dolby_size_byte * max_buffer_num;
-       mem_size = (mem_size/PAGE_SIZE + 1)*PAGE_SIZE;
+       mem_size = roundup(mem_size, PAGE_SIZE);
 
        if (mem_size > devp->cma_mem_size) {
                mem_size = devp->cma_mem_size;
@@ -555,6 +562,24 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
        else if (devp->index == 1)
                strcpy(vdin_name, "vdin1");
 
+       /*allocate mem according to resolution
+        *each block contains 32 * 4 pixels
+        *one block associated to one header(4 bytes)
+        *dolby has one page size, & each vframe aligned to page size
+        *(((h(align 32 pixel) * v(4 pixel)) / (32 * 4)) * 4)  + dolby
+        *total max_buffer_num
+        */
+       afbce_head_total_bytes =  PAGE_ALIGN((roundup(devp->h_active, 32) *
+               roundup(devp->v_active, 4)) / 32 + dolby_size_byte);
+       afbce_head_total_bytes *= max_buffer_num;
+
+       /*((h * v * byte_per_pixel + dolby) / page_size) * 4(one address size)
+        * total max_buffer_num
+        */
+       afbce_table_total_bytes = PAGE_ALIGN
+               ((devp->vfmem_size * 4) / PAGE_SIZE);
+       afbce_table_total_bytes *= max_buffer_num;
+
        if (devp->cma_config_flag == 0x101) {
                /* canvas or afbce paddr */
                for (i = 0; i < max_buffer_num; i++) {
@@ -589,13 +614,12 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                                devp->index, i,
                                devp->vfmem_start[i], devp->vfmem_size);
                }
-               if (devp->afbce_info)
-                       devp->afbce_info->frame_body_size = devp->vfmem_size;
+
                devp->mem_size = mem_size;
 
                if (devp->afbce_info) {
                        devp->afbce_info->head_paddr = codec_mm_alloc_for_dma(
-                               vdin_name, afbce_head_size_byte/PAGE_SIZE,
+                               vdin_name, afbce_head_total_bytes / PAGE_SIZE,
                                0, flags);
                        if (devp->afbce_info->head_paddr == 0) {
                                pr_err("\nvdin%d header codec alloc fail!!!\n",
@@ -604,7 +628,7 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                                return 1;
                        }
                        devp->afbce_info->table_paddr = codec_mm_alloc_for_dma(
-                               vdin_name, afbce_table_size_byte/PAGE_SIZE,
+                               vdin_name, afbce_table_total_bytes / PAGE_SIZE,
                                0, flags);
                        if (devp->afbce_info->table_paddr == 0) {
                                pr_err("\nvdin%d table codec alloc fail!!!\n",
@@ -614,8 +638,9 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
                                devp->cma_mem_alloc = 0;
                                return 1;
                        }
-                       devp->afbce_info->head_size = afbce_head_size_byte;
-                       devp->afbce_info->table_size = afbce_table_size_byte;
+                       devp->afbce_info->frame_body_size = devp->vfmem_size;
+                       devp->afbce_info->head_size = afbce_head_total_bytes;
+                       devp->afbce_info->table_size = afbce_table_total_bytes;
 
                        pr_info("vdin%d head_start = 0x%lx, head_size = 0x%x\n",
                                devp->index, devp->afbce_info->head_paddr,
@@ -722,34 +747,31 @@ unsigned int vdin_cma_alloc(struct vdin_dev_s *devp)
 
        /* set afbce head paddr */
        if (devp->afbce_info) {
-               /* 1 block = 32 * 4 pixle = 128 pixel */
-               /* there is a header in one block, a header has 4 bytes */
-               frame_head_size = (int)roundup(devp->vfmem_size, 128);
-               /*h_active * v_active / 128 * 4 = frame_head_size*/
-               frame_head_size = PAGE_ALIGN(frame_head_size / 32);
+               /*h_active align to 32 pixel, v_active align to 4 pixel*/
+               devp->afbce_info->frame_head_size =
+                       PAGE_ALIGN((roundup(devp->h_active, 32) *
+                       roundup(devp->v_active, 4)) / 32 + dolby_size_byte);
 
-               devp->afbce_info->frame_head_size = frame_head_size;
 
                for (i = 0; i < max_buffer_num; i++) {
                        devp->afbce_info->fm_head_paddr[i] =
                                devp->afbce_info->head_paddr +
-                               (frame_head_size*i);
+                               (devp->afbce_info->frame_head_size * i);
 
                        pr_info("vdin%d fm_head_paddr[%d] = 0x%lx, frame_head_size = 0x%x\n",
                                devp->index, i,
                                devp->afbce_info->fm_head_paddr[i],
-                               frame_head_size);
+                               devp->afbce_info->frame_head_size);
                }
 
                /* set afbce table paddr */
-               mmu_used = devp->afbce_info->frame_body_size >> 12;
-               mmu_used = mmu_used * 4;
-               mmu_used = PAGE_ALIGN(mmu_used);
-               devp->afbce_info->frame_table_size = mmu_used;
+               devp->afbce_info->frame_table_size = PAGE_ALIGN
+                       ((devp->afbce_info->frame_body_size >> 12) * 4);
 
                for (i = 0; i < max_buffer_num; i++) {
                        devp->afbce_info->fm_table_paddr[i] =
-                               devp->afbce_info->table_paddr + (mmu_used*i);
+                               devp->afbce_info->table_paddr +
+                               (devp->afbce_info->frame_table_size * i);
 
                        pr_info("vdin%d fm_table_paddr[%d]=0x%lx, frame_table_size = 0x%x\n",
                                devp->index, i,
index a2cc960..136fb46 100644 (file)
@@ -48,7 +48,7 @@
 /* Ref.2019/04/25: tl1 vdin0 afbce dynamically switch support,
  *                 vpp also should support this function
  */
-#define VDIN_VER "Ref.2019/08/22:add vdin pixel probe feature"
+#define VDIN_VER "Ref.2019/09/30:afbce,optimize mem alloc & enable 1080p"
 
 /*the counter of vdin*/
 #define VDIN_MAX_DEVS                  2