media_modules: mh264: keep last frame while reset decoder [1/2]

PD#OTT-71

Problem:
google cast display green lump when seek.
bufmgr reset after seek opration.

Solution:
keep the normal pic before reset and free buffer;

Verify:
U212, Atom

Change-Id: I0b1d21fb73ed8e7b2bf9815b53e0832444f1e41a
Signed-off-by: shihong.zheng <shihong.zheng@amlogic.com>
This commit is contained in:
shihong.zheng
2018-10-30 12:07:28 +08:00
committed by Dongjin Kim
parent e29ec06326
commit 1bba286120
2 changed files with 42 additions and 14 deletions

View File

@@ -7044,6 +7044,7 @@ static void h264_clear_dpb(struct vdec_h264_hw_s *hw)
static void h264_reset_bufmgr(struct vdec_s *vdec)
{
int i;
ulong timeout;
struct vdec_h264_hw_s *hw = (struct vdec_h264_hw_s *)vdec->private;
#if 0
struct h264_dpb_stru *p_H264_Dpb = &hw->dpb;
@@ -7101,6 +7102,13 @@ static void h264_reset_bufmgr(struct vdec_s *vdec)
__func__, hw->decode_pic_count+1,
hw->skip_frame_count);
timeout = jiffies + HZ;
while (kfifo_len(&hw->display_q) > 0) {
if (time_after(jiffies, timeout))
break;
schedule();
}
for (i = 0; i < VF_POOL_SIZE; i++)
hw->vfpool[hw->cur_pool][i].index = -1; /* VF_BUF_NUM; */

View File

@@ -32,6 +32,7 @@
#include <linux/amlogic/media/video_sink/video_keeper.h>
#include "decoder_bmmu_box.h"
#include <linux/amlogic/media/codec_mm/codec_mm.h>
#include <linux/amlogic/media/codec_mm/codec_mm_keeper.h>
struct decoder_bmmu_box {
int max_mm_num;
@@ -133,19 +134,28 @@ int decoder_bmmu_box_alloc_idx(void *handle, int idx, int size, int aligned_2n,
mm = box->mm_list[idx];
if (mm) {
int invalid = 0;
int keeped = 0;
if (mm->page_count * PAGE_SIZE < size) {
/*size is small. */
invalid = 1;
} else if (box->change_size_on_need_smaller &&
(mm->buffer_size > (size << 1))) {
/*size is too large. */
invalid = 2;
} else if (mm->phy_addr & ((1 << align) - 1)) {
/*addr is not align */
invalid = 4;
}
if (invalid) {
keeped = is_codec_mm_keeped(mm);
if (!keeped) {
if (mm->page_count * PAGE_SIZE < size) {
/*size is small. */
invalid = 1;
} else if (box->change_size_on_need_smaller &&
(mm->buffer_size > (size << 1))) {
/*size is too large. */
invalid = 2;
} else if (mm->phy_addr & ((1 << align) - 1)) {
/*addr is not align */
invalid = 4;
}
if (invalid) {
box->total_size -= mm->buffer_size;
codec_mm_release(mm, box->name);
box->mm_list[idx] = NULL;
mm = NULL;
}
} else {
box->total_size -= mm->buffer_size;
codec_mm_release(mm, box->name);
box->mm_list[idx] = NULL;
@@ -289,9 +299,19 @@ int decoder_bmmu_box_alloc_idx_wait(
{
int have_space;
int ret = -1;
int keeped = 0;
if (decoder_bmmu_box_get_mem_size(handle, idx) >= size)
return 0;/*have alloced memery before.*/
if (decoder_bmmu_box_get_mem_size(handle, idx) >= size) {
struct decoder_bmmu_box *box = handle;
struct codec_mm_s *mm;
mutex_lock(&box->mutex);
mm = box->mm_list[idx];
keeped = is_codec_mm_keeped(mm);
mutex_unlock(&box->mutex);
if (!keeped)
return 0;/*have alloced memery before.*/
}
have_space = decoder_bmmu_box_check_and_wait_size(
size,
wait_flags);