⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 video_dec_buffer_manager.c

📁 最新MTK手机软件源码
💻 C
📖 第 1 页 / 共 2 页
字号:

    /* should call config first */
    if (g_video_dec_buffer_mgr_ptr->buffer_count == 0)
        EXT_ASSERT(0, (kal_uint32)g_video_dec_buffer_mgr_ptr->buffer_count, 0, 0);

    /* control parameter */
    g_video_dec_buffer_mgr_ptr->start_frame_no = start_frame_no;
    g_video_dec_buffer_mgr_ptr->end_frame_no = end_frame_no;

    g_video_dec_buffer_mgr_ptr->b_data_empty = KAL_FALSE;
    g_video_dec_buffer_mgr_ptr->write_buffer_id = 0;
    g_video_dec_buffer_mgr_ptr->read_buffer_id = 0;
    g_video_dec_buffer_mgr_ptr->cancel_put_buffer = KAL_FALSE;

    /* each buffer parameter */
    for (index = 0; index < g_video_dec_buffer_mgr_ptr->buffer_count; index++)
    {
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].total_frames_in_buffers = 0;
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].frame_read_index = 0;
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].frame_write_index = 0;
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].frame_start_id = 0;
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].prev_duration = 0;
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].is_write_done = KAL_FALSE;
        g_video_dec_buffer_mgr_ptr->DEC_BUFFER[index].size_usage = 0;
    }

    kal_give_mutex(g_video_dec_buffer_mutex);
}


/* get next frame address, and this function is called in ISR.
 * @param  addr frame memory addrsss
 * @param  length frame size(bytes)
 * @param  prev_frame_duration the duration of the previous frame(unit: auido interrupt count)
 * @return Media status, which is based MEDIA_STATUS_CODE structure.
 */
MEDIA_STATUS_CODE video_dec_get_next_frame(kal_uint8 **addr, kal_uint32 *length, kal_uint32 *prev_frame_duration)
{
    VIDEO_DEC_BUFFER_STRUCT *buffer_ptr = &g_video_dec_buffer_mgr_ptr->DEC_BUFFER[g_video_dec_buffer_mgr_ptr->read_buffer_id];

    if(g_video_dec_buffer_mgr_ptr->b_data_empty == KAL_TRUE)
    {
        /* send ilm to task, in order to prepare data */
        video_dbg_trace(MP4_DEC_HISR_SEND_ILM, video_get_current_time());

        if ((*g_video_dec_buffer_mgr_ptr->cb_info.callback) != NULL)
        {
            (*g_video_dec_buffer_mgr_ptr->cb_info.callback)(g_video_dec_buffer_mgr_ptr->cb_info.event_id);
        }

        g_video_dec_buffer_mgr_ptr->b_data_empty = KAL_FALSE;
        g_video_dec_buffer_mgr_ptr->send_ilm = KAL_FALSE;
    }           

    if (buffer_ptr->frame_read_index == buffer_ptr->frame_write_index)
    {
        if (buffer_ptr->is_write_done == KAL_TRUE)
        {
            /* buffer is read empty */
            buffer_ptr->is_write_done = KAL_FALSE;

            if ((g_video_dec_buffer_mgr_ptr->end_frame_no != g_video_dec_buffer_mgr_ptr->start_frame_no) && (g_video_dec_buffer_mgr_ptr->send_ilm == KAL_TRUE))
            {
                g_video_dec_buffer_mgr_ptr->b_data_empty = KAL_TRUE;
            }

            g_video_dec_buffer_mgr_ptr->read_buffer_id++;
            g_video_dec_buffer_mgr_ptr->read_buffer_id %= g_video_dec_buffer_mgr_ptr->buffer_count;
            buffer_ptr = &g_video_dec_buffer_mgr_ptr->DEC_BUFFER[g_video_dec_buffer_mgr_ptr->read_buffer_id];
        }
    /* If already false, it means all buufer empty. Do nothing */
    }
    else
    {
        if (buffer_ptr->is_write_done != KAL_TRUE)
        {
            ASSERT(0);
        }
    }

    if (buffer_ptr->is_write_done == KAL_FALSE)
    {
        /* All buffer are empty */
        /* No frame length information, only provide previous frame time information*/
        *prev_frame_duration = buffer_ptr->prev_duration;
        return VIDEO_ERROR;
    }

    /* Error check */
    if ((buffer_ptr->is_write_done == KAL_FALSE) || (g_video_dec_buffer_mgr_ptr->end_frame_no < g_video_dec_buffer_mgr_ptr->start_frame_no))
    {
        EXT_ASSERT(0, (kal_uint32)buffer_ptr->is_write_done, (kal_uint32)g_video_dec_buffer_mgr_ptr->end_frame_no,
                          (kal_uint32)g_video_dec_buffer_mgr_ptr->start_frame_no)
    }

    /* Get information*/
    *addr = (kal_uint8 *)buffer_ptr->frame_buffer_addr[buffer_ptr->frame_read_index];
    *length = buffer_ptr->frame_length[buffer_ptr->frame_read_index];
    *prev_frame_duration = buffer_ptr->prev_frame_duration[buffer_ptr->frame_read_index];
    buffer_ptr->prev_duration = buffer_ptr->prev_frame_duration[buffer_ptr->frame_read_index];
    buffer_ptr->frame_read_index++;

    return MEDIA_STATUS_OK;
}


/* Put bitstream data from file to double buffer, and this function should be  called in TASK.
 * @param None
 * @return Media status, which is based MEDIA_STATUS_CODE structure.
 */
MEDIA_STATUS_CODE video_dec_put_frame_to_buffer(void)
{
    kal_uint32 total_frames;
    MEDIA_STATUS_CODE result;
    VIDEO_DEC_BUFFER_STRUCT *buffer_ptr = &g_video_dec_buffer_mgr_ptr->DEC_BUFFER[g_video_dec_buffer_mgr_ptr->write_buffer_id];

    if (kal_if_hisr() == KAL_TRUE)
        EXT_ASSERT(0, 0, 0, 0);
    
    /* Only support these two scenario */
    if( (g_video_dec_buffer_mgr_ptr->cb_info.scenario != VIDEO_DEC_BUFFER_SCENARIO_FILE)
    	&& (g_video_dec_buffer_mgr_ptr->cb_info.scenario != VIDEO_DEC_BUFFER_SCENARIO_EDITOR))
    {
        EXT_ASSERT(0, (kal_uint32)g_video_dec_buffer_mgr_ptr->cb_info.scenario, 0, 0);
    }

    if ((buffer_ptr == NULL) || (buffer_ptr->buffer_length == 0))
        EXT_ASSERT(0, (kal_uint32)buffer_ptr, 0, 0);

    kal_take_mutex(g_video_dec_buffer_mutex);
    video_dbg_trace(MP4_DEC_TASK_IND_START, video_get_current_time());

    /* task is getting data, driver can send ilm again */
    g_video_dec_buffer_mgr_ptr->send_ilm = KAL_TRUE;

    while (buffer_ptr->is_write_done == KAL_FALSE)
    {
        if (g_video_dec_buffer_mgr_ptr->cancel_put_buffer == KAL_TRUE)
        {
            /* another task may want to re-start*/
            //g_video_dec_buffer_mgr_ptr->cancel_put_buffer = KAL_FALSE;

            kal_give_mutex(g_video_dec_buffer_mutex);
            return MEDIA_STATUS_OK;
        }

        /* Check illegal frame conditions */
        if ((g_video_dec_buffer_mgr_ptr->end_frame_no == 0) || (g_video_dec_buffer_mgr_ptr->start_frame_no > g_video_dec_buffer_mgr_ptr->end_frame_no))
        {
            VIDEO_ASSERT(0);

            g_video_dec_status.VIDEO_STATUS = VIDEO_DEC_FUNC_PARAMETER_ERROR;
            kal_give_mutex(g_video_dec_buffer_mutex);
            return VIDEO_ERROR;
        }

        /* All data are ready */
        if (g_video_dec_buffer_mgr_ptr->start_frame_no == g_video_dec_buffer_mgr_ptr->end_frame_no)
        {
            kal_give_mutex(g_video_dec_buffer_mutex);
            return MEDIA_STATUS_OK;
        }

        /* Determine total frame number that will be put in  this buffer */
        if ((g_video_dec_buffer_mgr_ptr->start_frame_no + DEC_MAX_FRMAE_IN_BUFFER) <= g_video_dec_buffer_mgr_ptr->end_frame_no)
            total_frames = DEC_MAX_FRMAE_IN_BUFFER;
        else
            total_frames = g_video_dec_buffer_mgr_ptr->end_frame_no - g_video_dec_buffer_mgr_ptr->start_frame_no;

        if (total_frames == 0)
        {
            VIDEO_ASSERT(0);

            g_video_dec_status.VIDEO_STATUS = VIDEO_DEC_FUNC_PARAMETER_ERROR;
            kal_give_mutex(g_video_dec_buffer_mutex);
            return VIDEO_ERROR;
        }

        buffer_ptr->frame_start_id = g_video_dec_buffer_mgr_ptr->start_frame_no;

        /* Get previous frame duration */
        if (buffer_ptr->frame_start_id == 0)
        {
            /* frame 0 dose not have previous frame duration */
            result = video_file_get_frametime(buffer_ptr->frame_start_id, (total_frames - 1), &buffer_ptr->prev_frame_duration[1]);
        }
        else
        {
            result = video_file_get_frametime(buffer_ptr->frame_start_id - 1, total_frames, &buffer_ptr->prev_frame_duration[0]);
        }

        if (result != MEDIA_STATUS_OK)
        {
            VIDEO_ASSERT(0);

            kal_give_mutex(g_video_dec_buffer_mutex);
            return result;
        }

        /* Get frame length and bitstream from file */
        
        buffer_ptr->file_read_info.result_frame_no = 0;
        buffer_ptr->file_read_info.start_frame_no = buffer_ptr->frame_start_id;
        buffer_ptr->file_read_info.total_frame_no = total_frames;
        buffer_ptr->file_read_info.max_size = buffer_ptr->buffer_length;
        buffer_ptr->frame_buffer_addr[0] = (kal_uint32)buffer_ptr->buffer;
        buffer_ptr->file_read_info.p_frame_buffer_addr = buffer_ptr->frame_buffer_addr;
        buffer_ptr->file_read_info.p_frame_length = buffer_ptr->frame_length;
        result = video_file_get_sample_data(&buffer_ptr->file_read_info);
        if (result != MEDIA_STATUS_OK)
        {
            VIDEO_ASSERT(0);
            kal_give_mutex(g_video_dec_buffer_mutex);
            return result;
        }

        /* update buffer parameter */
        buffer_ptr->total_frames_in_buffers = buffer_ptr->file_read_info.result_frame_no;
        buffer_ptr->frame_write_index = buffer_ptr->file_read_info.result_frame_no;
        g_video_dec_buffer_mgr_ptr->start_frame_no += buffer_ptr->file_read_info.result_frame_no;
        buffer_ptr->frame_read_index = 0;
        buffer_ptr->prev_duration = 0;
        buffer_ptr->size_usage = buffer_ptr->file_read_info.result_size;     

        if (g_video_dec_buffer_mgr_ptr->start_frame_no > g_video_dec_buffer_mgr_ptr->end_frame_no)
            EXT_ASSERT(0, (kal_uint32)g_video_dec_buffer_mgr_ptr->start_frame_no, (kal_uint32)g_video_dec_buffer_mgr_ptr->end_frame_no, 0);

        if(buffer_ptr->total_frames_in_buffers > 0)
        {
            /* get next buffer */
            buffer_ptr->is_write_done = KAL_TRUE;
            g_video_dec_buffer_mgr_ptr->write_buffer_id++;
            g_video_dec_buffer_mgr_ptr->write_buffer_id %= g_video_dec_buffer_mgr_ptr->buffer_count;
            buffer_ptr = &g_video_dec_buffer_mgr_ptr->DEC_BUFFER[g_video_dec_buffer_mgr_ptr->write_buffer_id];
        }
        else
        {
            break;	
        }

        /* berak if all data are available */
        if (g_video_dec_buffer_mgr_ptr->start_frame_no == g_video_dec_buffer_mgr_ptr->end_frame_no)
            break;
    }

    video_dbg_trace(MP4_DEC_TASK_IND_END, video_get_current_time());
    kal_give_mutex(g_video_dec_buffer_mutex);
    return MEDIA_STATUS_OK;
}
#endif /*MP4_CODEC*/

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -