瀏覽代碼

msm: vidc: Fix priority level determination

Priority level was not determined at few sequences.
Determine the priority level and set to firmware, if
there is a change in driver and firmware priority.

Change-Id: I97861fd4ce8cfb7cf828a8da9a5ce8ba900280ef
Signed-off-by: Vikash Garodia <[email protected]>
Vikash Garodia 4 年之前
父節點
當前提交
e923948da6

+ 7 - 2
driver/variant/iris2/src/msm_vidc_power_iris2.c

@@ -50,9 +50,14 @@ u64 msm_vidc_calc_freq_iris2(struct msm_vidc_inst *inst, u32 data_size)
 
 	buf_timetamps_fps = msm_vidc_calc_framerate(inst);
 
-	/* use buffer detected fps instead of client set value */
-	if (fps < buf_timetamps_fps)
+	/*
+	 * when buffer detected fps is more than client set value by 10%,
+	 * utilize buffer detected fps to scale clock.
+	 */
+	if (div_u64(fps * 11, 10) < buf_timetamps_fps) {
 		fps = buf_timetamps_fps;
+		inst->priority_level = MSM_VIDC_PRIORITY_LOW;
+	}
 
 	mbs_per_second = mbpf * fps;
 

+ 1 - 0
driver/vidc/inc/msm_vidc_inst.h

@@ -146,6 +146,7 @@ struct msm_vidc_inst {
 	struct msm_vidc_inst_capability   *capabilities;
 	struct completion                  completions[MAX_SIGNAL];
 	enum priority_level                priority_level;
+	u32                                firmware_priority;
 	bool                               active;
 	u64                                last_qbuf_time_ns;
 	bool                               vb2q_init;

+ 7 - 2
driver/vidc/src/msm_vdec.c

@@ -1981,6 +1981,10 @@ int msm_vdec_qbuf(struct msm_vidc_inst *inst, struct vb2_buffer *vb2)
 		}
 	}
 
+	if (inst->firmware_priority != (inst->priority_level +
+					inst->capabilities->cap[PRIORITY].value * 2))
+		msm_vidc_set_session_priority(inst, PRIORITY);
+
 	/* batch decoder output & meta buffer only */
 	if (inst->decode_batch.enable && vb2->type == OUTPUT_MPLANE)
 		rc = msm_vdec_qbuf_batch(inst, vb2);
@@ -2369,8 +2373,7 @@ set_default:
 		}
 	}
 
-	if (!is_realtime_session(inst))
-		inst->priority_level = MSM_VIDC_PRIORITY_HIGH;
+	inst->priority_level = MSM_VIDC_PRIORITY_HIGH;
 
 	if (is_frame_rate)
 		capability->cap[FRAME_RATE].flags |= CAP_FLAG_CLIENT_SET;
@@ -2599,6 +2602,8 @@ int msm_vdec_inst_init(struct msm_vidc_inst *inst)
 	inst->buffers.output_meta.actual_count = 0;
 	inst->buffers.output_meta.size = 0;
 
+	inst->priority_level = MSM_VIDC_PRIORITY_LOW;
+
 	rc = msm_vdec_codec_change(inst,
 			inst->fmts[INPUT_PORT].fmt.pix_mp.pixelformat);
 

+ 12 - 2
driver/vidc/src/msm_venc.c

@@ -858,6 +858,15 @@ int msm_venc_qbuf(struct msm_vidc_inst *inst, struct vb2_buffer *vb2)
 {
 	int rc = 0;
 
+	if (!inst || !inst->capabilities) {
+		d_vpr_e("%s: invalid params\n", __func__);
+		return -EINVAL;
+	}
+
+	if (inst->firmware_priority != (inst->priority_level +
+		inst->capabilities->cap[PRIORITY].value * 2))
+		msm_vidc_set_session_priority(inst, PRIORITY);
+
 	rc = msm_vidc_queue_buffer_single(inst, vb2);
 	if (rc)
 		return rc;
@@ -1587,8 +1596,7 @@ set_default:
 		}
 	}
 
-	if (!is_realtime_session(inst))
-		inst->priority_level = MSM_VIDC_PRIORITY_HIGH;
+	inst->priority_level = MSM_VIDC_PRIORITY_HIGH;
 
 	if (is_frame_rate)
 		capability->cap[FRAME_RATE].flags |= CAP_FLAG_CLIENT_SET;
@@ -1810,6 +1818,8 @@ int msm_venc_inst_init(struct msm_vidc_inst *inst)
 	inst->buffers.input_meta.actual_count = 0;
 	inst->buffers.input_meta.size = 0;
 
+	inst->priority_level = MSM_VIDC_PRIORITY_LOW;
+
 	inst->hfi_rc_type = HFI_RC_VBR_CFR;
 	inst->hfi_layer_type = HFI_HIER_P_SLIDING_WINDOW;
 

+ 11 - 8
driver/vidc/src/msm_vidc_control.c

@@ -1901,7 +1901,7 @@ int msm_vidc_adjust_session_priority(void *instance, struct v4l2_ctrl *ctrl)
 {
 	int rc = 0;
 	int adjusted_value;
-	bool rate_by_client = false;
+	bool rate_by_client;
 	struct msm_vidc_inst_capability *capability;
 	struct msm_vidc_inst *inst = (struct msm_vidc_inst *)instance;
 
@@ -1914,8 +1914,13 @@ int msm_vidc_adjust_session_priority(void *instance, struct v4l2_ctrl *ctrl)
 		capability->cap[PRIORITY].value;
 
 	if (capability->cap[FRAME_RATE].flags & CAP_FLAG_CLIENT_SET ||
-		capability->cap[OPERATING_RATE].flags & CAP_FLAG_CLIENT_SET)
+		capability->cap[OPERATING_RATE].flags & CAP_FLAG_CLIENT_SET) {
 		rate_by_client = true;
+		inst->priority_level = MSM_VIDC_PRIORITY_HIGH;
+	} else {
+		rate_by_client = false;
+		inst->priority_level = MSM_VIDC_PRIORITY_LOW;
+	}
 
 	/*
 	 * For RT, check for resource feasability if rate is set by client.
@@ -1930,13 +1935,9 @@ int msm_vidc_adjust_session_priority(void *instance, struct v4l2_ctrl *ctrl)
 			return rc;
 		}
 	}
-	if (adjusted_value == 0 && !rate_by_client) {
-		adjusted_value = 1;
-		inst->priority_level = MSM_VIDC_PRIORITY_LOW;
-	}
 
-	if (adjusted_value > 0 && rate_by_client)
-		inst->priority_level = MSM_VIDC_PRIORITY_HIGH;
+	if (adjusted_value == 0 && !rate_by_client)
+		adjusted_value = 1;
 
 	msm_vidc_update_cap_value(inst, PRIORITY, adjusted_value, __func__);
 
@@ -2762,6 +2763,8 @@ int msm_vidc_set_session_priority(void *instance,
 	if (rc)
 		return rc;
 
+	inst->firmware_priority = hfi_value;
+
 	return rc;
 }