Merge "msm: venc: Modify vbvdelay logic"
This commit is contained in:
commit
2829ba22c6
@ -2390,11 +2390,10 @@ int msm_venc_set_rate_control(struct msm_vidc_inst *inst)
|
|||||||
int msm_venc_set_vbv_delay(struct msm_vidc_inst *inst)
|
int msm_venc_set_vbv_delay(struct msm_vidc_inst *inst)
|
||||||
{
|
{
|
||||||
int rc = 0;
|
int rc = 0;
|
||||||
|
bool is_legacy_cbr;
|
||||||
struct hfi_device *hdev;
|
struct hfi_device *hdev;
|
||||||
struct v4l2_ctrl *ctrl;
|
struct v4l2_ctrl *ctrl;
|
||||||
u32 codec;
|
u32 codec, height, width, buf_size;
|
||||||
u32 height, width, fps, mbpf, mbps;
|
|
||||||
u32 max_fps = 15;
|
|
||||||
struct hfi_vbv_hrd_buf_size hrd_buf_size;
|
struct hfi_vbv_hrd_buf_size hrd_buf_size;
|
||||||
struct v4l2_format *f;
|
struct v4l2_format *f;
|
||||||
|
|
||||||
@ -2408,10 +2407,6 @@ int msm_venc_set_vbv_delay(struct msm_vidc_inst *inst)
|
|||||||
codec = get_v4l2_codec(inst);
|
codec = get_v4l2_codec(inst);
|
||||||
height = f->fmt.pix_mp.height;
|
height = f->fmt.pix_mp.height;
|
||||||
width = f->fmt.pix_mp.width;
|
width = f->fmt.pix_mp.width;
|
||||||
mbpf = NUM_MBS_PER_FRAME(height, width);
|
|
||||||
fps = inst->clk_data.frame_rate >> 16;
|
|
||||||
mbpf = NUM_MBS_PER_FRAME(height, width);
|
|
||||||
mbps = NUM_MBS_PER_SEC(height, width, fps);
|
|
||||||
|
|
||||||
/* vbv delay is required for CBR_CFR and CBR_VFR only */
|
/* vbv delay is required for CBR_CFR and CBR_VFR only */
|
||||||
if (inst->rc_type != V4L2_MPEG_VIDEO_BITRATE_MODE_CBR &&
|
if (inst->rc_type != V4L2_MPEG_VIDEO_BITRATE_MODE_CBR &&
|
||||||
@ -2422,34 +2417,39 @@ int msm_venc_set_vbv_delay(struct msm_vidc_inst *inst)
|
|||||||
if (codec == V4L2_PIX_FMT_VP8)
|
if (codec == V4L2_PIX_FMT_VP8)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
/* default behavior */
|
/* Default behavior */
|
||||||
inst->clk_data.is_legacy_cbr = false;
|
is_legacy_cbr = false;
|
||||||
hrd_buf_size.vbv_hrd_buf_size = CBR_PLUS_BUF_SIZE;
|
buf_size = CBR_PLUS_BUF_SIZE;
|
||||||
|
|
||||||
/* if resolution greater than MAX_CBR (720p), default behavior */
|
/*
|
||||||
if (res_is_greater_than(width, height, MAX_CBR_W, MAX_CBR_H))
|
* Client can set vbv delay only when
|
||||||
goto set_vbv_delay;
|
* resolution is between VGA and 720p
|
||||||
|
*/
|
||||||
/* enable legacy cbr if resolution less than MIN_CBRPLUS (VGA) */
|
if (res_is_greater_than_or_equal_to(width, height, MIN_CBRPLUS_W,
|
||||||
if (res_is_less_than(width, height, MIN_CBRPLUS_W, MIN_CBRPLUS_H) &&
|
MIN_CBRPLUS_H) && res_is_less_than_or_equal_to(width, height,
|
||||||
mbps <= NUM_MBS_PER_SEC(MIN_CBRPLUS_H, MIN_CBRPLUS_W,
|
MAX_CBR_W, MAX_CBR_H)) {
|
||||||
max_fps)) {
|
|
||||||
inst->clk_data.is_legacy_cbr = true;
|
|
||||||
hrd_buf_size.vbv_hrd_buf_size = LEGACY_CBR_BUF_SIZE;
|
|
||||||
goto set_vbv_delay;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* enable legacy cbr if rate control is CBR_VFR and VBV delay is 500 */
|
|
||||||
if (inst->rc_type == V4L2_MPEG_VIDEO_BITRATE_MODE_CBR_VFR) {
|
|
||||||
ctrl = get_ctrl(inst, V4L2_CID_MPEG_VIDEO_VBV_DELAY);
|
ctrl = get_ctrl(inst, V4L2_CID_MPEG_VIDEO_VBV_DELAY);
|
||||||
if (ctrl->val == LEGACY_CBR_BUF_SIZE) {
|
if (ctrl->val == LEGACY_CBR_BUF_SIZE) {
|
||||||
inst->clk_data.is_legacy_cbr = true;
|
is_legacy_cbr = true;
|
||||||
hrd_buf_size.vbv_hrd_buf_size = LEGACY_CBR_BUF_SIZE;
|
buf_size = LEGACY_CBR_BUF_SIZE;
|
||||||
goto set_vbv_delay;
|
goto set_vbv_delay;
|
||||||
|
} else if (ctrl->val == CBR_PLUS_BUF_SIZE) {
|
||||||
|
is_legacy_cbr = false;
|
||||||
|
buf_size = CBR_PLUS_BUF_SIZE;
|
||||||
|
goto set_vbv_delay;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Enable legacy cbr if resolution < MIN_CBRPLUS (720p) */
|
||||||
|
if (res_is_less_than(width, height, MAX_CBR_W, MAX_CBR_H)) {
|
||||||
|
is_legacy_cbr = true;
|
||||||
|
buf_size = LEGACY_CBR_BUF_SIZE;
|
||||||
|
goto set_vbv_delay;
|
||||||
|
}
|
||||||
|
|
||||||
set_vbv_delay:
|
set_vbv_delay:
|
||||||
|
inst->clk_data.is_legacy_cbr = is_legacy_cbr;
|
||||||
|
hrd_buf_size.vbv_hrd_buf_size = buf_size;
|
||||||
dprintk(VIDC_HIGH, "Set hrd_buf_size %d",
|
dprintk(VIDC_HIGH, "Set hrd_buf_size %d",
|
||||||
hrd_buf_size.vbv_hrd_buf_size);
|
hrd_buf_size.vbv_hrd_buf_size);
|
||||||
rc = call_hfi_op(hdev, session_set_property,
|
rc = call_hfi_op(hdev, session_set_property,
|
||||||
|
@ -116,6 +116,34 @@ bool res_is_greater_than(u32 width, u32 height,
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool res_is_greater_than_or_equal_to(u32 width, u32 height,
|
||||||
|
u32 ref_width, u32 ref_height)
|
||||||
|
{
|
||||||
|
u32 num_mbs = NUM_MBS_PER_FRAME(height, width);
|
||||||
|
u32 max_side = max(ref_width, ref_height);
|
||||||
|
|
||||||
|
if (num_mbs >= NUM_MBS_PER_FRAME(ref_height, ref_width) ||
|
||||||
|
width >= max_side ||
|
||||||
|
height >= max_side)
|
||||||
|
return true;
|
||||||
|
else
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool res_is_less_than_or_equal_to(u32 width, u32 height,
|
||||||
|
u32 ref_width, u32 ref_height)
|
||||||
|
{
|
||||||
|
u32 num_mbs = NUM_MBS_PER_FRAME(height, width);
|
||||||
|
u32 max_side = max(ref_width, ref_height);
|
||||||
|
|
||||||
|
if (num_mbs <= NUM_MBS_PER_FRAME(ref_height, ref_width) ||
|
||||||
|
width <= max_side ||
|
||||||
|
height <= max_side)
|
||||||
|
return true;
|
||||||
|
else
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
int msm_vidc_get_mbs_per_frame(struct msm_vidc_inst *inst)
|
int msm_vidc_get_mbs_per_frame(struct msm_vidc_inst *inst)
|
||||||
{
|
{
|
||||||
int height, width;
|
int height, width;
|
||||||
|
@ -13,6 +13,10 @@ int msm_comm_vote_bus(struct msm_vidc_core *core);
|
|||||||
int msm_dcvs_try_enable(struct msm_vidc_inst *inst);
|
int msm_dcvs_try_enable(struct msm_vidc_inst *inst);
|
||||||
bool res_is_less_than(u32 width, u32 height, u32 ref_width, u32 ref_height);
|
bool res_is_less_than(u32 width, u32 height, u32 ref_width, u32 ref_height);
|
||||||
bool res_is_greater_than(u32 width, u32 height, u32 ref_width, u32 ref_height);
|
bool res_is_greater_than(u32 width, u32 height, u32 ref_width, u32 ref_height);
|
||||||
|
bool res_is_less_than_or_equal_to(u32 width, u32 height,
|
||||||
|
u32 ref_width, u32 ref_height);
|
||||||
|
bool res_is_greater_than_or_equal_to(u32 width, u32 height,
|
||||||
|
u32 ref_width, u32 ref_height);
|
||||||
int msm_vidc_get_mbs_per_frame(struct msm_vidc_inst *inst);
|
int msm_vidc_get_mbs_per_frame(struct msm_vidc_inst *inst);
|
||||||
int msm_comm_scale_clocks_and_bus(struct msm_vidc_inst *inst);
|
int msm_comm_scale_clocks_and_bus(struct msm_vidc_inst *inst);
|
||||||
int msm_comm_init_clocks_and_bus_data(struct msm_vidc_inst *inst);
|
int msm_comm_init_clocks_and_bus_data(struct msm_vidc_inst *inst);
|
||||||
|
Loading…
Reference in New Issue
Block a user