• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *
3  * Copyright (C) 2016 Amlogic, Inc. All rights reserved.
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful, but WITHOUT
11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
13  * more details.
14  *
15 */
16 
17 #include "vdec_v4l2_buffer_ops.h"
18 #include <media/v4l2-mem2mem.h>
19 #include <linux/printk.h>
20 
vdec_v4l_get_buffer(struct aml_vcodec_ctx * ctx,struct vdec_v4l2_buffer ** out)21 int vdec_v4l_get_buffer(struct aml_vcodec_ctx *ctx,
22 	struct vdec_v4l2_buffer **out)
23 {
24 	int ret = -1;
25 
26 	if (ctx->drv_handle == 0)
27 		return -EIO;
28 
29 	ret = ctx->dec_if->get_param(ctx->drv_handle,
30 		GET_PARAM_FREE_FRAME_BUFFER, out);
31 
32 	return ret;
33 }
34 EXPORT_SYMBOL(vdec_v4l_get_buffer);
35 
vdec_v4l_get_pic_info(struct aml_vcodec_ctx * ctx,struct vdec_pic_info * pic)36 int vdec_v4l_get_pic_info(struct aml_vcodec_ctx *ctx,
37 	struct vdec_pic_info *pic)
38 {
39 	int ret = 0;
40 
41 	if (ctx->drv_handle == 0)
42 		return -EIO;
43 
44 	ret = ctx->dec_if->get_param(ctx->drv_handle,
45 		GET_PARAM_PIC_INFO, pic);
46 
47 	return ret;
48 }
49 EXPORT_SYMBOL(vdec_v4l_get_pic_info);
50 
vdec_v4l_set_ps_infos(struct aml_vcodec_ctx * ctx,struct aml_vdec_ps_infos * ps)51 int vdec_v4l_set_ps_infos(struct aml_vcodec_ctx *ctx,
52 	struct aml_vdec_ps_infos *ps)
53 {
54 	int ret = 0;
55 
56 	if (ctx->drv_handle == 0)
57 		return -EIO;
58 
59 	ret = ctx->dec_if->set_param(ctx->drv_handle,
60 		SET_PARAM_PS_INFO, ps);
61 
62 	return ret;
63 }
64 EXPORT_SYMBOL(vdec_v4l_set_ps_infos);
65 
vdec_v4l_set_hdr_infos(struct aml_vcodec_ctx * ctx,struct aml_vdec_hdr_infos * hdr)66 int vdec_v4l_set_hdr_infos(struct aml_vcodec_ctx *ctx,
67 	struct aml_vdec_hdr_infos *hdr)
68 {
69 	int ret = 0;
70 
71 	if (ctx->drv_handle == 0)
72 		return -EIO;
73 
74 	ret = ctx->dec_if->set_param(ctx->drv_handle,
75 		SET_PARAM_HDR_INFO, hdr);
76 
77 	return ret;
78 }
79 EXPORT_SYMBOL(vdec_v4l_set_hdr_infos);
80 
aml_wait_dpb_ready(struct aml_vcodec_ctx * ctx)81 static void aml_wait_dpb_ready(struct aml_vcodec_ctx *ctx)
82 {
83 	ulong expires;
84 
85 	expires = jiffies + msecs_to_jiffies(1000);
86 	while (!ctx->v4l_codec_dpb_ready) {
87 		u32 ready_num = 0;
88 
89 		if (time_after(jiffies, expires)) {
90 			pr_err("the DPB state has not ready.\n");
91 			break;
92 		}
93 
94 		ready_num = v4l2_m2m_num_dst_bufs_ready(ctx->m2m_ctx);
95 		if ((ready_num + ctx->buf_used_count) >= ctx->dpb_size)
96 			ctx->v4l_codec_dpb_ready = true;
97 	}
98 }
99 
aml_vdec_pic_info_update(struct aml_vcodec_ctx * ctx)100 void aml_vdec_pic_info_update(struct aml_vcodec_ctx *ctx)
101 {
102 	unsigned int dpbsize = 0;
103 	int ret;
104 
105 	if (ctx->dec_if->get_param(ctx->drv_handle, GET_PARAM_PIC_INFO, &ctx->last_decoded_picinfo)) {
106 		pr_err("Cannot get param : GET_PARAM_PICTURE_INFO ERR\n");
107 		return;
108 	}
109 
110 	if (ctx->last_decoded_picinfo.visible_width == 0 ||
111 		ctx->last_decoded_picinfo.visible_height == 0 ||
112 		ctx->last_decoded_picinfo.coded_width == 0 ||
113 		ctx->last_decoded_picinfo.coded_height == 0) {
114 		pr_err("Cannot get correct pic info\n");
115 		return;
116 	}
117 
118 	ret = ctx->dec_if->get_param(ctx->drv_handle, GET_PARAM_DPB_SIZE, &dpbsize);
119 	if (dpbsize == 0)
120 		pr_err("Incorrect dpb size, ret=%d\n", ret);
121 
122 	/* update picture information */
123 	ctx->dpb_size = dpbsize;
124 	ctx->picinfo = ctx->last_decoded_picinfo;
125 }
126 
vdec_v4l_post_evet(struct aml_vcodec_ctx * ctx,u32 event)127 int vdec_v4l_post_evet(struct aml_vcodec_ctx *ctx, u32 event)
128 {
129 	int ret = 0;
130 
131 	if (ctx->drv_handle == 0)
132 		return -EIO;
133 	if (event == 1)
134 		ctx->reset_flag = 2;
135 	ret = ctx->dec_if->set_param(ctx->drv_handle,
136 		SET_PARAM_POST_EVENT, &event);
137 
138 	return ret;
139 }
140 EXPORT_SYMBOL(vdec_v4l_post_evet);
141 
vdec_v4l_res_ch_event(struct aml_vcodec_ctx * ctx)142 int vdec_v4l_res_ch_event(struct aml_vcodec_ctx *ctx)
143 {
144 	int ret = 0;
145 	struct aml_vcodec_dev *dev = ctx->dev;
146 
147 	if (ctx->drv_handle == 0)
148 		return -EIO;
149 
150 	/* wait the DPB state to be ready. */
151 	aml_wait_dpb_ready(ctx);
152 
153 	aml_vdec_pic_info_update(ctx);
154 
155 	mutex_lock(&ctx->state_lock);
156 
157 	ctx->state = AML_STATE_FLUSHING;/*prepare flushing*/
158 
159 	pr_info("[%d]: vcodec state (AML_STATE_FLUSHING-RESCHG)\n", ctx->id);
160 
161 	mutex_unlock(&ctx->state_lock);
162 
163 	ctx->q_data[AML_Q_DATA_SRC].resolution_changed = true;
164 	v4l2_m2m_suspend(dev->m2m_dev_dec);
165 
166 	return ret;
167 }
168 EXPORT_SYMBOL(vdec_v4l_res_ch_event);
169 
170 
vdec_v4l_write_frame_sync(struct aml_vcodec_ctx * ctx)171 int vdec_v4l_write_frame_sync(struct aml_vcodec_ctx *ctx)
172 {
173 	int ret = 0;
174 
175 	if (ctx->drv_handle == 0)
176 		return -EIO;
177 
178 	ret = ctx->dec_if->set_param(ctx->drv_handle,
179 		SET_PARAM_WRITE_FRAME_SYNC, NULL);
180 
181 	return ret;
182 }
183 EXPORT_SYMBOL(vdec_v4l_write_frame_sync);
184 
185