media_module: can't get the correct width and height information [1/1]
[GitHub/LineageOS/G12/android_hardware_amlogic_kernel-modules_media.git] / drivers / frame_provider / decoder / vp9 / vvp9.c
index d08def04b1483670c2f75bf9e56c46beb7dbda72..5d59c42f62e31356554a7ca5ed3517a01fdf9913 100644 (file)
@@ -601,6 +601,10 @@ struct PIC_BUFFER_CONFIG_s {
 
        /* vdec sync. */
        struct fence *fence;
+
+       /* hdr10 plus data */
+       u32 hdr10p_data_size;
+       char *hdr10p_data_buf;
 } PIC_BUFFER_CONFIG;
 
 enum BITSTREAM_PROFILE {
@@ -1211,7 +1215,7 @@ struct VP9Decoder_s {
        u32 mem_map_mode;
        u32 dynamic_buf_num_margin;
        struct vframe_s vframe_dummy;
-       unsigned int res_ch_flag;
+       u32 res_ch_flag;
        /*struct VP9Decoder_s vp9_decoder;*/
        union param_u vp9_param;
        int sidebind_type;
@@ -1222,6 +1226,8 @@ struct VP9Decoder_s {
        u64 frame_mode_pts64_save[FRAME_BUFFERS];
        int run_ready_min_buf_num;
        int one_package_frame_cnt;
+       u32 error_frame_width;
+       u32 error_frame_height;
 };
 
 static int vp9_print(struct VP9Decoder_s *pbi,
@@ -1318,9 +1324,13 @@ static int setup_frame_size(
        width = params->p.width;
        height = params->p.height;
        if (is_oversize(width, height)) {
+               pbi->error_frame_width = width;
+               pbi->error_frame_height = height;
                vp9_print(pbi, 0, "%s, Error: Invalid frame size\n", __func__);
                return -1;
        }
+       pbi->error_frame_width = 0;
+       pbi->error_frame_height = 0;
 
        /*vp9_read_frame_size(rb, &width, &height);*/
        if (print_header_info)
@@ -1445,9 +1455,13 @@ static int setup_frame_size_with_refs(
        }
 
        if (is_oversize(width, height)) {
+               pbi->error_frame_width = width;
+               pbi->error_frame_height = height;
                vp9_print(pbi, 0, "%s, Error: Invalid frame size\n", __func__);
                return -1;
        }
+       pbi->error_frame_width = 0;
+       pbi->error_frame_height = 0;
 
        params->p.width = width;
        params->p.height = height;
@@ -6877,6 +6891,41 @@ static void set_frame_info(struct VP9Decoder_s *pbi, struct vframe_s *vf)
                vdec_v4l_set_hdr_infos(ctx, &hdr);
        }
 
+       if ((pbi->chunk != NULL) && (pbi->chunk->hdr10p_data_buf != NULL)
+               && (pbi->chunk->hdr10p_data_size != 0)) {
+               char *new_buf;
+               int i = 0;
+               new_buf = vzalloc(pbi->chunk->hdr10p_data_size);
+
+               if (new_buf) {
+                       memcpy(new_buf, pbi->chunk->hdr10p_data_buf, pbi->chunk->hdr10p_data_size);
+                       if (debug & VP9_DEBUG_BUFMGR_MORE) {
+                               vp9_print(pbi, VP9_DEBUG_BUFMGR_MORE,
+                                       "hdr10p data: (size %d)\n",
+                                       pbi->chunk->hdr10p_data_size);
+                               for (i = 0; i < pbi->chunk->hdr10p_data_size; i++) {
+                                       vp9_print(pbi, VP9_DEBUG_BUFMGR_MORE,
+                                               "%02x ", pbi->chunk->hdr10p_data_buf[i]);
+                                       if (((i + 1) & 0xf) == 0)
+                                               vp9_print(pbi, VP9_DEBUG_BUFMGR_MORE, "\n");
+                               }
+                               vp9_print(pbi, VP9_DEBUG_BUFMGR_MORE, "\n");
+                       }
+
+                       vf->hdr10p_data_size = pbi->chunk->hdr10p_data_size;
+                       vf->hdr10p_data_buf = new_buf;
+               } else {
+                       vp9_print(pbi, 0, "%s:hdr10p data vzalloc size(%d) fail\n",
+                               __func__, pbi->chunk->hdr10p_data_size);
+                       vf->hdr10p_data_size = pbi->chunk->hdr10p_data_size;
+                       vf->hdr10p_data_buf = new_buf;
+               }
+
+               vfree(pbi->chunk->hdr10p_data_buf);
+               pbi->chunk->hdr10p_data_buf = NULL;
+               pbi->chunk->hdr10p_data_size = 0;
+       }
+
        vf->sidebind_type = pbi->sidebind_type;
        vf->sidebind_channel_id = pbi->sidebind_channel_id;
 }
@@ -6953,16 +7002,27 @@ static struct vframe_s *vvp9_vf_get(void *op_arg)
 static void vvp9_vf_put(struct vframe_s *vf, void *op_arg)
 {
        struct VP9Decoder_s *pbi = (struct VP9Decoder_s *)op_arg;
-       uint8_t index = vf->index & 0xff;
+       uint8_t index;
 
        if (vf == (&pbi->vframe_dummy))
                return;
 
+       if (!vf)
+               return;
+
+       index = vf->index & 0xff;
+
        if (pbi->enable_fence && vf->fence) {
                vdec_fence_put(vf->fence);
                vf->fence = NULL;
        }
 
+       if (vf->hdr10p_data_buf) {
+               vfree(vf->hdr10p_data_buf);
+               vf->hdr10p_data_buf = NULL;
+               vf->hdr10p_data_size = 0;
+       }
+
        kfifo_put(&pbi->newframe_q, (const struct vframe_s *)vf);
        pbi->vf_put_count++;
        if (index < pbi->used_buf_num) {
@@ -6994,6 +7054,8 @@ static void vvp9_vf_put(struct vframe_s *vf, void *op_arg)
 
 static int vvp9_event_cb(int type, void *data, void *private_data)
 {
+       struct VP9Decoder_s *pbi = (struct VP9Decoder_s *)private_data;
+
        if (type & VFRAME_EVENT_RECEIVER_RESET) {
 #if 0
                unsigned long flags;
@@ -7011,6 +7073,13 @@ static int vvp9_event_cb(int type, void *data, void *private_data)
 #endif
                amhevc_start();
 #endif
+       } else if (type & VFRAME_EVENT_RECEIVER_REQ_STATE) {
+               struct provider_state_req_s *req =
+                       (struct provider_state_req_s *)data;
+               if (req->req_type == REQ_STATE_SECURE)
+                       req->req_result[0] = vdec_secure(hw_to_vdec(pbi));
+               else
+                       req->req_result[0] = 0xffffffff;
        }
 
        return 0;
@@ -7444,6 +7513,7 @@ static int prepare_display_buf(struct VP9Decoder_s *pbi,
                        struct vdec_info tmp4x;
 
                        inc_vf_ref(pbi, pic_config->index);
+                       decoder_do_frame_check(pvdec, vf);
                        vdec_vframe_ready(pvdec, vf);
                        kfifo_put(&pbi->display_q, (const struct vframe_s *)vf);
                        ATRACE_COUNTER(MODULE_NAME, vf->pts);
@@ -7516,6 +7586,7 @@ static int notify_v4l_eos(struct vdec_s *vdec)
                vf->v4l_mem_handle      = (index == INVALID_IDX) ? (ulong)fb :
                                        hw->m_BUF[index].v4l_ref_buf_addr;
 
+               vdec_vframe_ready(vdec, vf);
                kfifo_put(&hw->display_q, (const struct vframe_s *)vf);
                vf_notify_receiver(vdec->vf_provider_name,
                        VFRAME_EVENT_PROVIDER_VFRAME_READY, NULL);
@@ -7656,7 +7727,8 @@ void vp9_recycle_mmu_work(struct work_struct *work)
        struct VP9Decoder_s *pbi = container_of(work,
                struct VP9Decoder_s, recycle_mmu_work);
 
-       vp9_recycle_mmu_buf(pbi);
+       if (pbi)
+               vp9_recycle_mmu_buf(pbi);
 }
 #endif
 
@@ -7691,6 +7763,7 @@ int continue_decoding(struct VP9Decoder_s *pbi)
 
        if (pbi->is_used_v4l && ctx->param_sets_from_ucode)
                pbi->res_ch_flag = 0;
+
        bit_depth_luma = pbi->vp9_param.p.bit_depth;
        bit_depth_chroma = pbi->vp9_param.p.bit_depth;
 
@@ -7951,7 +8024,7 @@ static void get_picture_qos_info(struct VP9Decoder_s *pbi)
                frame->min_mv = a[0];
 
                vp9_print(pbi, VP9_DEBUG_QOS_INFO,
-                       "mv data %x  a[0]= %x a[1]= %x a[2]= %x\n",
+                       "mv data %lx  a[0]= %x a[1]= %x a[2]= %x\n",
                        data, a[0], a[1], a[2]);
 
                data = READ_VREG(HEVC_QP_INFO);
@@ -7978,7 +8051,7 @@ static void get_picture_qos_info(struct VP9Decoder_s *pbi)
                frame->min_qp = a[0];
 
                vp9_print(pbi, VP9_DEBUG_QOS_INFO,
-                       "qp data %x  a[0]= %x a[1]= %x a[2]= %x\n",
+                       "qp data %lx  a[0]= %x a[1]= %x a[2]= %x\n",
                        data, a[0], a[1], a[2]);
 
                data = READ_VREG(HEVC_SKIP_INFO);
@@ -8005,7 +8078,7 @@ static void get_picture_qos_info(struct VP9Decoder_s *pbi)
                frame->min_skip = a[0];
 
                vp9_print(pbi, VP9_DEBUG_QOS_INFO,
-                       "skip data %x  a[0]= %x a[1]= %x a[2]= %x\n",
+                       "skip data %lx  a[0]= %x a[1]= %x a[2]= %x\n",
                        data, a[0], a[1], a[2]);
        } else {
                uint32_t blk88_y_count;
@@ -8360,6 +8433,7 @@ static int v4l_res_change(struct VP9Decoder_s *pbi)
                        vdec_v4l_res_ch_event(ctx);
                        pbi->v4l_params_parsed = false;
                        pbi->res_ch_flag = 1;
+                       ctx->v4l_resolution_change = 1;
                        pbi->eos = 1;
                        vp9_bufmgr_postproc(pbi);
                        //del_timer_sync(&pbi->timer);
@@ -9020,6 +9094,12 @@ int vvp9_dec_status(struct vdec_s *vdec, struct vdec_info *vstatus)
 
        vstatus->frame_width = frame_width;
        vstatus->frame_height = frame_height;
+       if (vp9->error_frame_width &&
+               vp9->error_frame_height) {
+               vstatus->frame_width = vp9->error_frame_width;
+               vstatus->frame_height = vp9->error_frame_height;
+       }
+
        if (vp9->frame_dur != 0)
                vstatus->frame_rate = ((96000 * 10 / vp9->frame_dur) % 10) < 5 ?
                                96000 / vp9->frame_dur : (96000 / vp9->frame_dur +1);
@@ -10162,9 +10242,7 @@ static unsigned long run_ready(struct vdec_s *vdec, unsigned long mask)
                                pbi->run_ready_min_buf_num)
                                        ret = 0;
                        } else {
-                               if ((pbi->res_ch_flag == 1) &&
-                               ((ctx->state <= AML_STATE_INIT) ||
-                               (ctx->state >= AML_STATE_FLUSHING)))
+                               if (ctx->v4l_resolution_change)
                                        ret = 0;
                        }
                } else if (ctx->cap_pool.in < ctx->dpb_size) {
@@ -10579,10 +10657,11 @@ static void vp9_dump_state(struct vdec_s *vdec)
        vp9_print(pbi, 0, "====== %s\n", __func__);
 
        vp9_print(pbi, 0,
-               "width/height (%d/%d), used_buf_num %d\n",
+               "width/height (%d/%d), used_buf_num %d video_signal_type 0x%x\n",
                cm->width,
                cm->height,
-               pbi->used_buf_num
+               pbi->used_buf_num,
+               pbi->video_signal_type
                );
 
        vp9_print(pbi, 0,
@@ -10628,7 +10707,7 @@ static void vp9_dump_state(struct vdec_s *vdec)
 
        for (i = 0; i < MAX_BUF_NUM; i++) {
                vp9_print(pbi, 0,
-                       "mv_Buf(%d) start_adr 0x%x size 0x%x used %d\n",
+                       "mv_Buf(%d) start_adr 0x%lx size 0x%x used %d\n",
                        i,
                        pbi->m_mv_BUF[i].start_adr,
                        pbi->m_mv_BUF[i].size,
@@ -10720,6 +10799,7 @@ static int ammvdec_vp9_probe(struct platform_device *pdev)
        struct vdec_s *pdata = *(struct vdec_s **)pdev->dev.platform_data;
        int ret;
        int config_val;
+       int transfer_val;
        struct vframe_content_light_level_s content_light_level;
        struct vframe_master_display_colour_s vf_dp;
 
@@ -10867,6 +10947,11 @@ static int ammvdec_vp9_probe(struct platform_device *pdev)
                        "parm_fence_usage",
                        &config_val) == 0)
                        pbi->fence_usage = config_val;
+
+               if (get_config_int(pdata->config,
+                       "parm_v4l_low_latency_mode",
+                       &config_val) == 0)
+                       pbi->low_latency_flag = config_val;
 #endif
                if (get_config_int(pdata->config, "HDRStaticInfo",
                                &vf_dp.present_flag) == 0
@@ -10896,13 +10981,22 @@ static int ammvdec_vp9_probe(struct platform_device *pdev)
                                        &content_light_level.max_content);
                        get_config_int(pdata->config, "mMaxFALL",
                                        &content_light_level.max_pic_average);
+
+                       get_config_int(pdata->config, "mTransfer",
+                                       &transfer_val);
+
+                       if (transfer_val == 0)
+                               transfer_val = 16;
+
+                       vp9_print(pbi, 0, "transfer_val=%d\n",transfer_val);
+
                        vf_dp.content_light_level = content_light_level;
                        pbi->video_signal_type = (1 << 29)
                                        | (5 << 26)     /* unspecified */
                                        | (0 << 25)     /* limit */
                                        | (1 << 24)     /* color available */
                                        | (9 << 16)     /* 2020 */
-                                       | (16 << 8)     /* 2084 */
+                                       | (transfer_val << 8)   /* 2084 */
                                        | (9 << 0);     /* 2020 */
                }
                pbi->vf_dp = vf_dp;
@@ -10960,8 +11054,8 @@ static int ammvdec_vp9_probe(struct platform_device *pdev)
                pbi->vvp9_amstream_dec_info.height = 0;
                pbi->vvp9_amstream_dec_info.rate = 30;
        }
-       pbi->low_latency_flag = 1;
 
+       pbi->low_latency_flag = 1;
        vp9_print(pbi, 0,
                        "no_head %d  low_latency %d\n",
                        pbi->no_head, pbi->low_latency_flag);
@@ -11187,22 +11281,12 @@ static int __init amvdec_vp9_driver_init_module(void)
        } else if (get_cpu_major_id() >= AM_MESON_CPU_MAJOR_ID_GXL
                /*&& get_cpu_major_id() != MESON_CPU_MAJOR_ID_GXLX*/
                && get_cpu_major_id() != AM_MESON_CPU_MAJOR_ID_TXL) {
-                       if (get_cpu_major_id() < AM_MESON_CPU_MAJOR_ID_TXLX) {
-                               if (vdec_is_support_4k())
-                                       amvdec_vp9_profile.profile =
-                                               "4k, 10bit, dwrite, compressed, fence";
-                               else
-                                       amvdec_vp9_profile.profile =
-                                               "10bit, dwrite, compressed, fence";
-                       } else {
-                               if (vdec_is_support_4k())
-                                       amvdec_vp9_profile.profile =
-                                               "4k, 10bit, dwrite, compressed, fence";
-                               else
-                                       amvdec_vp9_profile.profile =
-                                               "10bit, dwrite, compressed, fence";
-                       }
-
+                       if (vdec_is_support_4k())
+                               amvdec_vp9_profile.profile =
+                                       "4k, 10bit, dwrite, compressed, fence";
+                       else
+                               amvdec_vp9_profile.profile =
+                                       "10bit, dwrite, compressed, fence";
        } else {
                amvdec_vp9_profile.name = "vp9_unsupport";
        }