xref: /linux/drivers/media/platform/rockchip/rkvdec/rkvdec-vdpu381-h264.c (revision bf4afc53b77aeaa48b5409da5c8da6bb4eff7f43)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Rockchip VDPU381 Video Decoder H264 backend
4  *
5  * Copyright (C) 2024 Collabora, Ltd.
6  *  Detlev Casanova <detlev.casanova@collabora.com>
7  */
8 
9 #include <media/v4l2-h264.h>
10 #include <media/v4l2-mem2mem.h>
11 
12 #include "rkvdec.h"
13 #include "rkvdec-cabac.h"
14 #include "rkvdec-rcb.h"
15 #include "rkvdec-h264-common.h"
16 #include "rkvdec-vdpu381-regs.h"
17 
18 struct rkvdec_sps {
19 	u16 seq_parameter_set_id:			4;
20 	u16 profile_idc:				8;
21 	u16 constraint_set3_flag:			1;
22 	u16 chroma_format_idc:				2;
23 	u16 bit_depth_luma:				3;
24 	u16 bit_depth_chroma:				3;
25 	u16 qpprime_y_zero_transform_bypass_flag:	1;
26 	u16 log2_max_frame_num_minus4:			4;
27 	u16 max_num_ref_frames:				5;
28 	u16 pic_order_cnt_type:				2;
29 	u16 log2_max_pic_order_cnt_lsb_minus4:		4;
30 	u16 delta_pic_order_always_zero_flag:		1;
31 	u16 pic_width_in_mbs:				12;
32 	u16 pic_height_in_mbs:				12;
33 	u16 frame_mbs_only_flag:			1;
34 	u16 mb_adaptive_frame_field_flag:		1;
35 	u16 direct_8x8_inference_flag:			1;
36 	u16 mvc_extension_enable:			1;
37 	u16 num_views:					2;
38 
39 	u16 reserved_bits:				12;
40 	u16 reserved[11];
41 } __packed;
42 
43 struct rkvdec_pps {
44 	u16 pic_parameter_set_id:				8;
45 	u16 pps_seq_parameter_set_id:				5;
46 	u16 entropy_coding_mode_flag:				1;
47 	u16 bottom_field_pic_order_in_frame_present_flag:	1;
48 	u16 num_ref_idx_l0_default_active_minus1:		5;
49 	u16 num_ref_idx_l1_default_active_minus1:		5;
50 	u16 weighted_pred_flag:					1;
51 	u16 weighted_bipred_idc:				2;
52 	u16 pic_init_qp_minus26:				7;
53 	u16 pic_init_qs_minus26:				6;
54 	u16 chroma_qp_index_offset:				5;
55 	u16 deblocking_filter_control_present_flag:		1;
56 	u16 constrained_intra_pred_flag:			1;
57 	u16 redundant_pic_cnt_present:				1;
58 	u16 transform_8x8_mode_flag:				1;
59 	u16 second_chroma_qp_index_offset:			5;
60 	u16 scaling_list_enable_flag:				1;
61 	u32 scaling_list_address;
62 	u16 is_longterm;
63 
64 	u8 reserved[3];
65 } __packed;
66 
67 struct rkvdec_sps_pps {
68 	struct rkvdec_sps sps;
69 	struct rkvdec_pps pps;
70 } __packed;
71 
72 /* Data structure describing auxiliary buffer format. */
73 struct rkvdec_h264_priv_tbl {
74 	s8 cabac_table[4][464][2];
75 	struct rkvdec_h264_scaling_list scaling_list;
76 	struct rkvdec_sps_pps param_set[256];
77 	struct rkvdec_rps rps;
78 };
79 
80 struct rkvdec_h264_ctx {
81 	struct rkvdec_aux_buf priv_tbl;
82 	struct rkvdec_h264_reflists reflists;
83 	struct rkvdec_vdpu381_regs_h264 regs;
84 };
85 
assemble_hw_pps(struct rkvdec_ctx * ctx,struct rkvdec_h264_run * run)86 static void assemble_hw_pps(struct rkvdec_ctx *ctx,
87 			    struct rkvdec_h264_run *run)
88 {
89 	struct rkvdec_h264_ctx *h264_ctx = ctx->priv;
90 	const struct v4l2_ctrl_h264_sps *sps = run->sps;
91 	const struct v4l2_ctrl_h264_pps *pps = run->pps;
92 	const struct v4l2_ctrl_h264_decode_params *dec_params = run->decode_params;
93 	const struct v4l2_h264_dpb_entry *dpb = dec_params->dpb;
94 	struct rkvdec_h264_priv_tbl *priv_tbl = h264_ctx->priv_tbl.cpu;
95 	struct rkvdec_sps_pps *hw_ps;
96 	dma_addr_t scaling_list_address;
97 	u32 scaling_distance;
98 	u32 i;
99 
100 	/*
101 	 * HW read the SPS/PPS information from PPS packet index by PPS id.
102 	 * offset from the base can be calculated by PPS_id * 32 (size per PPS
103 	 * packet unit). so the driver copy SPS/PPS information to the exact PPS
104 	 * packet unit for HW accessing.
105 	 */
106 	hw_ps = &priv_tbl->param_set[pps->pic_parameter_set_id];
107 	memset(hw_ps, 0, sizeof(*hw_ps));
108 
109 	/* write sps */
110 	hw_ps->sps.seq_parameter_set_id = sps->seq_parameter_set_id;
111 	hw_ps->sps.profile_idc = sps->profile_idc;
112 	hw_ps->sps.constraint_set3_flag = !!(sps->constraint_set_flags & (1 << 3));
113 	hw_ps->sps.chroma_format_idc = sps->chroma_format_idc;
114 	hw_ps->sps.bit_depth_luma = sps->bit_depth_luma_minus8;
115 	hw_ps->sps.bit_depth_chroma = sps->bit_depth_chroma_minus8;
116 	hw_ps->sps.qpprime_y_zero_transform_bypass_flag =
117 		!!(sps->flags & V4L2_H264_SPS_FLAG_QPPRIME_Y_ZERO_TRANSFORM_BYPASS);
118 	hw_ps->sps.log2_max_frame_num_minus4 = sps->log2_max_frame_num_minus4;
119 	hw_ps->sps.max_num_ref_frames = sps->max_num_ref_frames;
120 	hw_ps->sps.pic_order_cnt_type = sps->pic_order_cnt_type;
121 	hw_ps->sps.log2_max_pic_order_cnt_lsb_minus4 =
122 		sps->log2_max_pic_order_cnt_lsb_minus4;
123 	hw_ps->sps.delta_pic_order_always_zero_flag =
124 		!!(sps->flags & V4L2_H264_SPS_FLAG_DELTA_PIC_ORDER_ALWAYS_ZERO);
125 	hw_ps->sps.mvc_extension_enable = 1;
126 	hw_ps->sps.num_views = 1;
127 
128 	/*
129 	 * Use the SPS values since they are already in macroblocks
130 	 * dimensions, height can be field height (halved) if
131 	 * V4L2_H264_SPS_FLAG_FRAME_MBS_ONLY is not set and also it allows
132 	 * decoding smaller images into larger allocation which can be used
133 	 * to implementing SVC spatial layer support.
134 	 */
135 	hw_ps->sps.pic_width_in_mbs = sps->pic_width_in_mbs_minus1 + 1;
136 	hw_ps->sps.pic_height_in_mbs = sps->pic_height_in_map_units_minus1 + 1;
137 	hw_ps->sps.frame_mbs_only_flag =
138 		!!(sps->flags & V4L2_H264_SPS_FLAG_FRAME_MBS_ONLY);
139 	hw_ps->sps.mb_adaptive_frame_field_flag =
140 		!!(sps->flags & V4L2_H264_SPS_FLAG_MB_ADAPTIVE_FRAME_FIELD);
141 	hw_ps->sps.direct_8x8_inference_flag =
142 		!!(sps->flags & V4L2_H264_SPS_FLAG_DIRECT_8X8_INFERENCE);
143 
144 	/* write pps */
145 	hw_ps->pps.pic_parameter_set_id = pps->pic_parameter_set_id;
146 	hw_ps->pps.pps_seq_parameter_set_id = pps->seq_parameter_set_id;
147 	hw_ps->pps.entropy_coding_mode_flag =
148 		!!(pps->flags & V4L2_H264_PPS_FLAG_ENTROPY_CODING_MODE);
149 	hw_ps->pps.bottom_field_pic_order_in_frame_present_flag =
150 		!!(pps->flags & V4L2_H264_PPS_FLAG_BOTTOM_FIELD_PIC_ORDER_IN_FRAME_PRESENT);
151 	hw_ps->pps.num_ref_idx_l0_default_active_minus1 =
152 		pps->num_ref_idx_l0_default_active_minus1;
153 	hw_ps->pps.num_ref_idx_l1_default_active_minus1 =
154 		pps->num_ref_idx_l1_default_active_minus1;
155 	hw_ps->pps.weighted_pred_flag =
156 		!!(pps->flags & V4L2_H264_PPS_FLAG_WEIGHTED_PRED);
157 	hw_ps->pps.weighted_bipred_idc = pps->weighted_bipred_idc;
158 	hw_ps->pps.pic_init_qp_minus26 = pps->pic_init_qp_minus26;
159 	hw_ps->pps.pic_init_qs_minus26 = pps->pic_init_qs_minus26;
160 	hw_ps->pps.chroma_qp_index_offset = pps->chroma_qp_index_offset;
161 	hw_ps->pps.deblocking_filter_control_present_flag =
162 		!!(pps->flags & V4L2_H264_PPS_FLAG_DEBLOCKING_FILTER_CONTROL_PRESENT);
163 	hw_ps->pps.constrained_intra_pred_flag =
164 		!!(pps->flags & V4L2_H264_PPS_FLAG_CONSTRAINED_INTRA_PRED);
165 	hw_ps->pps.redundant_pic_cnt_present =
166 		!!(pps->flags & V4L2_H264_PPS_FLAG_REDUNDANT_PIC_CNT_PRESENT);
167 	hw_ps->pps.transform_8x8_mode_flag =
168 		!!(pps->flags & V4L2_H264_PPS_FLAG_TRANSFORM_8X8_MODE);
169 	hw_ps->pps.second_chroma_qp_index_offset = pps->second_chroma_qp_index_offset;
170 	hw_ps->pps.scaling_list_enable_flag =
171 		!!(pps->flags & V4L2_H264_PPS_FLAG_SCALING_MATRIX_PRESENT);
172 
173 	/*
174 	 * To be on the safe side, program the scaling matrix address
175 	 */
176 	scaling_distance = offsetof(struct rkvdec_h264_priv_tbl, scaling_list);
177 	scaling_list_address = h264_ctx->priv_tbl.dma + scaling_distance;
178 	hw_ps->pps.scaling_list_address = scaling_list_address;
179 
180 	for (i = 0; i < ARRAY_SIZE(dec_params->dpb); i++) {
181 		if (dpb[i].flags & V4L2_H264_DPB_ENTRY_FLAG_LONG_TERM)
182 			hw_ps->pps.is_longterm |= (1 << i);
183 	}
184 }
185 
rkvdec_write_regs(struct rkvdec_ctx * ctx)186 static void rkvdec_write_regs(struct rkvdec_ctx *ctx)
187 {
188 	struct rkvdec_dev *rkvdec = ctx->dev;
189 	struct rkvdec_h264_ctx *h264_ctx = ctx->priv;
190 
191 	rkvdec_memcpy_toio(rkvdec->regs + OFFSET_COMMON_REGS,
192 			   &h264_ctx->regs.common,
193 			   sizeof(h264_ctx->regs.common));
194 	rkvdec_memcpy_toio(rkvdec->regs + OFFSET_CODEC_PARAMS_REGS,
195 			   &h264_ctx->regs.h264_param,
196 			   sizeof(h264_ctx->regs.h264_param));
197 	rkvdec_memcpy_toio(rkvdec->regs + OFFSET_COMMON_ADDR_REGS,
198 			   &h264_ctx->regs.common_addr,
199 			   sizeof(h264_ctx->regs.common_addr));
200 	rkvdec_memcpy_toio(rkvdec->regs + OFFSET_CODEC_ADDR_REGS,
201 			   &h264_ctx->regs.h264_addr,
202 			   sizeof(h264_ctx->regs.h264_addr));
203 	rkvdec_memcpy_toio(rkvdec->regs + OFFSET_POC_HIGHBIT_REGS,
204 			   &h264_ctx->regs.h264_highpoc,
205 			   sizeof(h264_ctx->regs.h264_highpoc));
206 }
207 
config_registers(struct rkvdec_ctx * ctx,struct rkvdec_h264_run * run)208 static void config_registers(struct rkvdec_ctx *ctx,
209 			     struct rkvdec_h264_run *run)
210 {
211 	const struct v4l2_ctrl_h264_decode_params *dec_params = run->decode_params;
212 	const struct v4l2_h264_dpb_entry *dpb = dec_params->dpb;
213 	struct rkvdec_h264_ctx *h264_ctx = ctx->priv;
214 	dma_addr_t priv_start_addr = h264_ctx->priv_tbl.dma;
215 	const struct v4l2_pix_format_mplane *dst_fmt;
216 	struct vb2_v4l2_buffer *src_buf = run->base.bufs.src;
217 	struct vb2_v4l2_buffer *dst_buf = run->base.bufs.dst;
218 	struct rkvdec_vdpu381_regs_h264 *regs = &h264_ctx->regs;
219 	const struct v4l2_format *f;
220 	dma_addr_t rlc_addr;
221 	dma_addr_t dst_addr;
222 	u32 hor_virstride;
223 	u32 ver_virstride;
224 	u32 y_virstride;
225 	u32 offset;
226 	u32 pixels;
227 	u32 i;
228 
229 	memset(regs, 0, sizeof(*regs));
230 
231 	/* Set H264 mode */
232 	regs->common.reg009_dec_mode.dec_mode = VDPU381_MODE_H264;
233 
234 	/* Set config */
235 	regs->common.reg011_important_en.buf_empty_en = 1;
236 	regs->common.reg011_important_en.dec_clkgate_e = 1;
237 	regs->common.reg011_important_en.dec_timeout_e = 1;
238 	regs->common.reg011_important_en.pix_range_det_e = 1;
239 
240 	/*
241 	 * Even though the scan list address can be set in RPS,
242 	 * with some frames, it will try to use the address set in the register.
243 	 */
244 	regs->common.reg012_secondary_en.scanlist_addr_valid_en = 1;
245 
246 	/* Set IDR flag */
247 	regs->common.reg013_en_mode_set.cur_pic_is_idr =
248 		!!(dec_params->flags & V4L2_H264_DECODE_PARAM_FLAG_IDR_PIC);
249 
250 	/* Set input stream length */
251 	regs->common.reg016_stream_len = vb2_get_plane_payload(&src_buf->vb2_buf, 0);
252 
253 	/* Set max slice number */
254 	regs->common.reg017_slice_number.slice_num = MAX_SLICE_NUMBER;
255 
256 	/* Set strides */
257 	f = &ctx->decoded_fmt;
258 	dst_fmt = &f->fmt.pix_mp;
259 	hor_virstride = dst_fmt->plane_fmt[0].bytesperline;
260 	ver_virstride = dst_fmt->height;
261 	y_virstride = hor_virstride * ver_virstride;
262 
263 	regs->common.reg018_y_hor_stride.y_hor_virstride = hor_virstride / 16;
264 	regs->common.reg019_uv_hor_stride.uv_hor_virstride = hor_virstride / 16;
265 	regs->common.reg020_y_stride.y_virstride = y_virstride / 16;
266 
267 	/* Activate block gating */
268 	regs->common.reg026_block_gating_en.inter_auto_gating_e = 1;
269 	regs->common.reg026_block_gating_en.filterd_auto_gating_e = 1;
270 	regs->common.reg026_block_gating_en.strmd_auto_gating_e = 1;
271 	regs->common.reg026_block_gating_en.mcp_auto_gating_e = 1;
272 	regs->common.reg026_block_gating_en.busifd_auto_gating_e = 0;
273 	regs->common.reg026_block_gating_en.dec_ctrl_auto_gating_e = 1;
274 	regs->common.reg026_block_gating_en.intra_auto_gating_e = 1;
275 	regs->common.reg026_block_gating_en.mc_auto_gating_e = 1;
276 	regs->common.reg026_block_gating_en.transd_auto_gating_e = 1;
277 	regs->common.reg026_block_gating_en.sram_auto_gating_e = 1;
278 	regs->common.reg026_block_gating_en.cru_auto_gating_e = 1;
279 	regs->common.reg026_block_gating_en.reg_cfg_gating_en = 1;
280 
281 	/* Set timeout threshold */
282 	pixels = dst_fmt->height * dst_fmt->width;
283 	if (pixels < RKVDEC_1080P_PIXELS)
284 		regs->common.reg032_timeout_threshold = RKVDEC_TIMEOUT_1080p;
285 	else if (pixels < RKVDEC_4K_PIXELS)
286 		regs->common.reg032_timeout_threshold = RKVDEC_TIMEOUT_4K;
287 	else if (pixels < RKVDEC_8K_PIXELS)
288 		regs->common.reg032_timeout_threshold = RKVDEC_TIMEOUT_8K;
289 	else
290 		regs->common.reg032_timeout_threshold = RKVDEC_TIMEOUT_MAX;
291 
292 	/* Set TOP and BOTTOM POCs */
293 	regs->h264_param.reg065_cur_top_poc = dec_params->top_field_order_cnt;
294 	regs->h264_param.reg066_cur_bot_poc = dec_params->bottom_field_order_cnt;
295 
296 	/* Set ref pic address & poc */
297 	for (i = 0; i < ARRAY_SIZE(dec_params->dpb); i++) {
298 		struct vb2_buffer *vb_buf = run->ref_buf[i];
299 		dma_addr_t buf_dma;
300 
301 		/*
302 		 * If a DPB entry is unused or invalid, address of current destination
303 		 * buffer is returned.
304 		 */
305 		if (!vb_buf)
306 			vb_buf = &dst_buf->vb2_buf;
307 
308 		buf_dma = vb2_dma_contig_plane_dma_addr(vb_buf, 0);
309 
310 		/* Set reference addresses */
311 		regs->h264_addr.reg164_180_ref_base[i] = buf_dma;
312 
313 		/* Set COLMV addresses */
314 		regs->h264_addr.reg182_198_colmv_base[i] = buf_dma + ctx->colmv_offset;
315 
316 		struct rkvdec_vdpu381_h264_ref_info *ref_info =
317 			&regs->h264_param.reg099_102_ref_info_regs[i / 4].ref_info[i % 4];
318 
319 		ref_info->ref_field =
320 			!!(dpb[i].flags & V4L2_H264_DPB_ENTRY_FLAG_FIELD);
321 		ref_info->ref_colmv_use_flag =
322 			!!(dpb[i].flags & V4L2_H264_DPB_ENTRY_FLAG_ACTIVE);
323 		ref_info->ref_topfield_used =
324 			!!(dpb[i].fields & V4L2_H264_TOP_FIELD_REF);
325 		ref_info->ref_botfield_used =
326 			!!(dpb[i].fields & V4L2_H264_BOTTOM_FIELD_REF);
327 
328 		regs->h264_param.reg067_098_ref_poc[i * 2] =
329 			dpb[i].top_field_order_cnt;
330 		regs->h264_param.reg067_098_ref_poc[i * 2 + 1] =
331 			dpb[i].bottom_field_order_cnt;
332 	}
333 
334 	/* Set rlc base address (input stream) */
335 	rlc_addr = vb2_dma_contig_plane_dma_addr(&src_buf->vb2_buf, 0);
336 	regs->common_addr.rlc_base = rlc_addr;
337 	regs->common_addr.rlcwrite_base = rlc_addr;
338 
339 	/* Set output base address */
340 	dst_addr = vb2_dma_contig_plane_dma_addr(&dst_buf->vb2_buf, 0);
341 	regs->common_addr.decout_base = dst_addr;
342 	regs->common_addr.error_ref_base = dst_addr;
343 
344 	/* Set colmv address */
345 	regs->common_addr.colmv_cur_base = dst_addr + ctx->colmv_offset;
346 
347 	/* Set RCB addresses */
348 	for (i = 0; i < rkvdec_rcb_buf_count(ctx); i++)
349 		regs->common_addr.rcb_base[i] = rkvdec_rcb_buf_dma_addr(ctx, i);
350 
351 	/* Set hw pps address */
352 	offset = offsetof(struct rkvdec_h264_priv_tbl, param_set);
353 	regs->h264_addr.reg161_pps_base = priv_start_addr + offset;
354 
355 	/* Set hw rps address */
356 	offset = offsetof(struct rkvdec_h264_priv_tbl, rps);
357 	regs->h264_addr.reg163_rps_base = priv_start_addr + offset;
358 
359 	/* Set cabac table */
360 	offset = offsetof(struct rkvdec_h264_priv_tbl, cabac_table);
361 	regs->h264_addr.reg199_cabactbl_base = priv_start_addr + offset;
362 
363 	offset = offsetof(struct rkvdec_h264_priv_tbl, scaling_list);
364 	regs->h264_addr.reg181_scanlist_addr = priv_start_addr + offset;
365 
366 	rkvdec_write_regs(ctx);
367 }
368 
rkvdec_h264_start(struct rkvdec_ctx * ctx)369 static int rkvdec_h264_start(struct rkvdec_ctx *ctx)
370 {
371 	struct rkvdec_dev *rkvdec = ctx->dev;
372 	struct rkvdec_h264_priv_tbl *priv_tbl;
373 	struct rkvdec_h264_ctx *h264_ctx;
374 	struct v4l2_ctrl *ctrl;
375 	int ret;
376 
377 	ctrl = v4l2_ctrl_find(&ctx->ctrl_hdl,
378 			      V4L2_CID_STATELESS_H264_SPS);
379 	if (!ctrl)
380 		return -EINVAL;
381 
382 	ret = rkvdec_h264_validate_sps(ctx, ctrl->p_new.p_h264_sps);
383 	if (ret)
384 		return ret;
385 
386 	h264_ctx = kzalloc_obj(*h264_ctx);
387 	if (!h264_ctx)
388 		return -ENOMEM;
389 
390 	priv_tbl = dma_alloc_coherent(rkvdec->dev, sizeof(*priv_tbl),
391 				      &h264_ctx->priv_tbl.dma, GFP_KERNEL);
392 	if (!priv_tbl) {
393 		ret = -ENOMEM;
394 		goto err_free_ctx;
395 	}
396 
397 	h264_ctx->priv_tbl.size = sizeof(*priv_tbl);
398 	h264_ctx->priv_tbl.cpu = priv_tbl;
399 	memcpy(priv_tbl->cabac_table, rkvdec_h264_cabac_table,
400 	       sizeof(rkvdec_h264_cabac_table));
401 
402 	ctx->priv = h264_ctx;
403 	return 0;
404 
405 err_free_ctx:
406 	kfree(h264_ctx);
407 	return ret;
408 }
409 
rkvdec_h264_stop(struct rkvdec_ctx * ctx)410 static void rkvdec_h264_stop(struct rkvdec_ctx *ctx)
411 {
412 	struct rkvdec_h264_ctx *h264_ctx = ctx->priv;
413 	struct rkvdec_dev *rkvdec = ctx->dev;
414 
415 	dma_free_coherent(rkvdec->dev, h264_ctx->priv_tbl.size,
416 			  h264_ctx->priv_tbl.cpu, h264_ctx->priv_tbl.dma);
417 	kfree(h264_ctx);
418 }
419 
rkvdec_h264_run(struct rkvdec_ctx * ctx)420 static int rkvdec_h264_run(struct rkvdec_ctx *ctx)
421 {
422 	struct v4l2_h264_reflist_builder reflist_builder;
423 	struct rkvdec_dev *rkvdec = ctx->dev;
424 	struct rkvdec_h264_ctx *h264_ctx = ctx->priv;
425 	struct rkvdec_h264_priv_tbl *tbl = h264_ctx->priv_tbl.cpu;
426 	struct rkvdec_h264_run run;
427 
428 	rkvdec_h264_run_preamble(ctx, &run);
429 
430 	/* Build the P/B{0,1} ref lists. */
431 	v4l2_h264_init_reflist_builder(&reflist_builder, run.decode_params,
432 				       run.sps, run.decode_params->dpb);
433 	v4l2_h264_build_p_ref_list(&reflist_builder, h264_ctx->reflists.p);
434 	v4l2_h264_build_b_ref_lists(&reflist_builder, h264_ctx->reflists.b0,
435 				    h264_ctx->reflists.b1);
436 
437 	assemble_hw_scaling_list(&run, &tbl->scaling_list);
438 	assemble_hw_pps(ctx, &run);
439 	lookup_ref_buf_idx(ctx, &run);
440 	assemble_hw_rps(&reflist_builder, &run, &h264_ctx->reflists, &tbl->rps);
441 
442 	config_registers(ctx, &run);
443 
444 	rkvdec_run_postamble(ctx, &run.base);
445 
446 	rkvdec_schedule_watchdog(rkvdec, h264_ctx->regs.common.reg032_timeout_threshold);
447 
448 	/* Start decoding! */
449 	writel(VDPU381_DEC_E_BIT, rkvdec->regs + VDPU381_REG_DEC_E);
450 
451 	return 0;
452 }
453 
rkvdec_h264_try_ctrl(struct rkvdec_ctx * ctx,struct v4l2_ctrl * ctrl)454 static int rkvdec_h264_try_ctrl(struct rkvdec_ctx *ctx, struct v4l2_ctrl *ctrl)
455 {
456 	if (ctrl->id == V4L2_CID_STATELESS_H264_SPS)
457 		return rkvdec_h264_validate_sps(ctx, ctrl->p_new.p_h264_sps);
458 
459 	return 0;
460 }
461 
462 const struct rkvdec_coded_fmt_ops rkvdec_vdpu381_h264_fmt_ops = {
463 	.adjust_fmt = rkvdec_h264_adjust_fmt,
464 	.get_image_fmt = rkvdec_h264_get_image_fmt,
465 	.start = rkvdec_h264_start,
466 	.stop = rkvdec_h264_stop,
467 	.run = rkvdec_h264_run,
468 	.try_ctrl = rkvdec_h264_try_ctrl,
469 };
470