video: driver: add support for timestamp reorder
Added support for timestamp reorder. It is default disabled. Change-Id: I51a6fc785860081b651fc67f443132cb2675b9fd Signed-off-by: Govindaraj Rajagopal <quic_grajagop@quicinc.com>
This commit is contained in:
@@ -381,6 +381,11 @@ static struct msm_platform_inst_capability instance_data_diwali_v0[] = {
|
||||
{0},
|
||||
NULL, msm_vidc_set_u32},
|
||||
|
||||
{TS_REORDER, DEC, H264|HEVC,
|
||||
V4L2_MPEG_MSM_VIDC_DISABLE, V4L2_MPEG_MSM_VIDC_ENABLE,
|
||||
1, V4L2_MPEG_MSM_VIDC_DISABLE,
|
||||
V4L2_CID_MPEG_VIDC_TS_REORDER},
|
||||
|
||||
{HFLIP, ENC, CODECS_ALL,
|
||||
V4L2_MPEG_MSM_VIDC_DISABLE,
|
||||
V4L2_MPEG_MSM_VIDC_ENABLE,
|
||||
|
@@ -262,6 +262,11 @@ static struct msm_platform_inst_capability instance_data_waipio[] = {
|
||||
{0},
|
||||
NULL, msm_vidc_set_u32},
|
||||
|
||||
{TS_REORDER, DEC, H264|HEVC,
|
||||
V4L2_MPEG_MSM_VIDC_DISABLE, V4L2_MPEG_MSM_VIDC_ENABLE,
|
||||
1, V4L2_MPEG_MSM_VIDC_DISABLE,
|
||||
V4L2_CID_MPEG_VIDC_TS_REORDER},
|
||||
|
||||
{HFLIP, ENC, CODECS_ALL,
|
||||
V4L2_MPEG_MSM_VIDC_DISABLE,
|
||||
V4L2_MPEG_MSM_VIDC_ENABLE,
|
||||
|
@@ -67,6 +67,12 @@ static inline is_output_meta_buffer(enum msm_vidc_buffer_type buffer_type)
|
||||
return buffer_type == MSM_VIDC_BUF_OUTPUT_META;
|
||||
}
|
||||
|
||||
static inline is_ts_reorder_allowed(struct msm_vidc_inst *inst)
|
||||
{
|
||||
return !!(inst->capabilities->cap[TS_REORDER].value &&
|
||||
is_decode_session(inst) && !is_image_session(inst));
|
||||
}
|
||||
|
||||
static inline is_scaling_enabled(struct msm_vidc_inst *inst)
|
||||
{
|
||||
return inst->crop.left != inst->compose.left ||
|
||||
@@ -428,6 +434,10 @@ int msm_vidc_update_timestamp(struct msm_vidc_inst *inst, u64 timestamp);
|
||||
int msm_vidc_set_auto_framerate(struct msm_vidc_inst *inst, u64 timestamp);
|
||||
int msm_vidc_calc_window_avg_framerate(struct msm_vidc_inst *inst);
|
||||
int msm_vidc_flush_ts(struct msm_vidc_inst *inst);
|
||||
int msm_vidc_ts_reorder_insert_timestamp(struct msm_vidc_inst *inst, u64 timestamp);
|
||||
int msm_vidc_ts_reorder_remove_timestamp(struct msm_vidc_inst *inst, u64 timestamp);
|
||||
int msm_vidc_ts_reorder_get_first_timestamp(struct msm_vidc_inst *inst, u64 *timestamp);
|
||||
int msm_vidc_ts_reorder_flush(struct msm_vidc_inst *inst);
|
||||
const char *buf_name(enum msm_vidc_buffer_type type);
|
||||
void msm_vidc_free_capabililty_list(struct msm_vidc_inst *inst,
|
||||
enum msm_vidc_ctrl_list_type list_type);
|
||||
|
@@ -118,6 +118,7 @@ struct msm_vidc_inst {
|
||||
struct msm_vidc_mappings_info mappings;
|
||||
struct msm_vidc_allocations_info allocations;
|
||||
struct msm_vidc_timestamps timestamps;
|
||||
struct msm_vidc_timestamps ts_reorder; /* list of struct msm_vidc_timestamp */
|
||||
bool subscribed_input_psc;
|
||||
bool subscribed_output_psc;
|
||||
bool subscribed_input_prop;
|
||||
|
@@ -363,6 +363,7 @@ enum msm_vidc_inst_capability_type {
|
||||
MB_CYCLES_FW,
|
||||
MB_CYCLES_FW_VPP,
|
||||
SECURE_MODE,
|
||||
TS_REORDER,
|
||||
HFLIP,
|
||||
VFLIP,
|
||||
ROTATION,
|
||||
|
@@ -1610,6 +1610,10 @@ int msm_vdec_streamon_input(struct msm_vidc_inst *inst)
|
||||
if (rc)
|
||||
goto error;
|
||||
|
||||
rc = msm_vidc_ts_reorder_flush(inst);
|
||||
if (rc)
|
||||
goto error;
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
|
@@ -840,6 +840,7 @@ void *msm_vidc_open(void *vidc_core, u32 session_type)
|
||||
}
|
||||
INIT_LIST_HEAD(&inst->response_works);
|
||||
INIT_LIST_HEAD(&inst->timestamps.list);
|
||||
INIT_LIST_HEAD(&inst->ts_reorder.list);
|
||||
INIT_LIST_HEAD(&inst->buffers.input.list);
|
||||
INIT_LIST_HEAD(&inst->buffers.input_meta.list);
|
||||
INIT_LIST_HEAD(&inst->buffers.output.list);
|
||||
|
@@ -81,6 +81,7 @@ static const struct msm_vidc_cap_name cap_name_arr[] = {
|
||||
{MB_CYCLES_FW, "MB_CYCLES_FW" },
|
||||
{MB_CYCLES_FW_VPP, "MB_CYCLES_FW_VPP" },
|
||||
{SECURE_MODE, "SECURE_MODE" },
|
||||
{TS_REORDER, "TS_REORDER" },
|
||||
{HFLIP, "HFLIP" },
|
||||
{VFLIP, "VFLIP" },
|
||||
{ROTATION, "ROTATION" },
|
||||
@@ -2404,6 +2405,102 @@ int msm_vidc_update_timestamp(struct msm_vidc_inst *inst, u64 timestamp)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int msm_vidc_ts_reorder_insert_timestamp(struct msm_vidc_inst *inst, u64 timestamp)
|
||||
{
|
||||
struct msm_vidc_timestamp *ts;
|
||||
|
||||
if (!inst) {
|
||||
d_vpr_e("%s: Invalid params\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* allocate ts from pool */
|
||||
ts = msm_memory_alloc(inst, MSM_MEM_POOL_TIMESTAMP);
|
||||
if (!ts) {
|
||||
i_vpr_e(inst, "%s: ts alloc failed\n", __func__);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
/* initialize ts node */
|
||||
INIT_LIST_HEAD(&ts->sort.list);
|
||||
ts->sort.val = timestamp;
|
||||
inst->ts_reorder.count++;
|
||||
list_add_tail(&ts->sort.list, &inst->ts_reorder.list);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int msm_vidc_ts_reorder_remove_timestamp(struct msm_vidc_inst *inst, u64 timestamp)
|
||||
{
|
||||
struct msm_vidc_timestamp *ts, *temp;
|
||||
|
||||
if (!inst) {
|
||||
d_vpr_e("%s: Invalid params\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* remove matching node */
|
||||
list_for_each_entry_safe(ts, temp, &inst->ts_reorder.list, sort.list) {
|
||||
if (ts->sort.val == timestamp) {
|
||||
list_del_init(&ts->sort.list);
|
||||
inst->ts_reorder.count--;
|
||||
msm_memory_free(inst, ts);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int msm_vidc_ts_reorder_get_first_timestamp(struct msm_vidc_inst *inst, u64 *timestamp)
|
||||
{
|
||||
struct msm_vidc_timestamp *ts;
|
||||
|
||||
if (!inst || !timestamp) {
|
||||
d_vpr_e("%s: Invalid params\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* check if list empty */
|
||||
if (list_empty(&inst->ts_reorder.list)) {
|
||||
i_vpr_e(inst, "%s: list empty. ts %lld\n", __func__, timestamp);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* get 1st node from reorder list */
|
||||
ts = list_first_entry(&inst->ts_reorder.list,
|
||||
struct msm_vidc_timestamp, sort.list);
|
||||
list_del_init(&ts->sort.list);
|
||||
|
||||
/* copy timestamp */
|
||||
*timestamp = ts->sort.val;
|
||||
|
||||
inst->ts_reorder.count--;
|
||||
msm_memory_free(inst, ts);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int msm_vidc_ts_reorder_flush(struct msm_vidc_inst *inst)
|
||||
{
|
||||
struct msm_vidc_timestamp *temp, *ts = NULL;
|
||||
|
||||
if (!inst) {
|
||||
d_vpr_e("%s: Invalid params\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* flush all entries */
|
||||
list_for_each_entry_safe(ts, temp, &inst->ts_reorder.list, sort.list) {
|
||||
i_vpr_l(inst, "%s: flushing ts: val %lld\n", __func__, ts->sort.val);
|
||||
list_del(&ts->sort.list);
|
||||
msm_memory_free(inst, ts);
|
||||
}
|
||||
inst->ts_reorder.count = 0;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int msm_vidc_get_delayed_unmap(struct msm_vidc_inst *inst, struct msm_vidc_map *map)
|
||||
{
|
||||
int rc = 0;
|
||||
@@ -3094,6 +3191,13 @@ static int msm_vidc_queue_buffer(struct msm_vidc_inst *inst, struct msm_vidc_buf
|
||||
meta->attr |= MSM_VIDC_ATTR_QUEUED;
|
||||
}
|
||||
|
||||
/* insert timestamp for ts_reorder enable case */
|
||||
if (is_ts_reorder_allowed(inst) && is_input_buffer(buf->type)) {
|
||||
rc = msm_vidc_ts_reorder_insert_timestamp(inst, buf->timestamp);
|
||||
if (rc)
|
||||
i_vpr_e(inst, "%s: insert timestamp failed\n", __func__);
|
||||
}
|
||||
|
||||
if (is_input_buffer(buf->type))
|
||||
inst->power.buffer_counter++;
|
||||
|
||||
@@ -5019,6 +5123,13 @@ void msm_vidc_destroy_buffers(struct msm_vidc_inst *inst)
|
||||
msm_memory_free(inst, ts);
|
||||
}
|
||||
|
||||
list_for_each_entry_safe(ts, dummy_ts, &inst->ts_reorder.list, sort.list) {
|
||||
i_vpr_e(inst, "%s: removing reorder ts: val %lld\n",
|
||||
__func__, ts->sort.val);
|
||||
list_del(&ts->sort.list);
|
||||
msm_memory_free(inst, ts);
|
||||
}
|
||||
|
||||
list_for_each_entry_safe(dbuf, dummy_dbuf, &inst->dmabuf_tracker, list) {
|
||||
i_vpr_e(inst, "%s: removing dma_buf %#x, refcount %u\n",
|
||||
__func__, dbuf->dmabuf, dbuf->refcount);
|
||||
|
@@ -755,6 +755,13 @@ static int handle_input_buffer(struct msm_vidc_inst *inst,
|
||||
buf->flags = 0;
|
||||
buf->flags = get_driver_buffer_flags(inst, buffer->flags);
|
||||
|
||||
/* handle ts_reorder for no_output prop attached input buffer */
|
||||
if (is_ts_reorder_allowed(inst) && inst->hfi_frame_info.no_output) {
|
||||
i_vpr_h(inst, "%s: received no_output buffer. remove timestamp %lld\n",
|
||||
__func__, buf->timestamp);
|
||||
msm_vidc_ts_reorder_remove_timestamp(inst, buf->timestamp);
|
||||
}
|
||||
|
||||
print_vidc_buffer(VIDC_HIGH, "high", "dqbuf", inst, buf);
|
||||
msm_vidc_update_stats(inst, buf, MSM_VIDC_DEBUGFS_EVENT_EBD);
|
||||
|
||||
@@ -886,6 +893,10 @@ static int handle_output_buffer(struct msm_vidc_inst *inst,
|
||||
if (!is_image_session(inst) && is_decode_session(inst) && buf->data_size)
|
||||
msm_vidc_update_timestamp(inst, buf->timestamp);
|
||||
|
||||
/* update output buffer timestamp, if ts_reorder is enabled */
|
||||
if (is_ts_reorder_allowed(inst) && buf->data_size)
|
||||
msm_vidc_ts_reorder_get_first_timestamp(inst, &buf->timestamp);
|
||||
|
||||
print_vidc_buffer(VIDC_HIGH, "high", "dqbuf", inst, buf);
|
||||
msm_vidc_update_stats(inst, buf, MSM_VIDC_DEBUGFS_EVENT_FBD);
|
||||
|
||||
|
@@ -189,6 +189,8 @@ enum v4l2_mpeg_video_av1_tier {
|
||||
V4L2_MPEG_VIDEO_AV1_TIER_MAIN = 0,
|
||||
V4L2_MPEG_VIDEO_AV1_TIER_HIGH = 1,
|
||||
};
|
||||
/* Decoder Timestamp Reorder control */
|
||||
#define V4L2_CID_MPEG_VIDC_TS_REORDER (V4L2_CID_MPEG_VIDC_BASE + 0x34)
|
||||
|
||||
/* Deprecate below controls once availble in gki and gsi bionic header */
|
||||
#ifndef V4L2_CID_MPEG_VIDEO_BASELAYER_PRIORITY_ID
|
||||
|
Reference in New Issue
Block a user