1 /* SPDX-License-Identifier: GPL-2.0+ */
2 /*
3 * Copyright (C) 2018 BayLibre, SAS
4 * Author: Maxime Jourdan <mjourdan@baylibre.com>
5 */
6
7 #ifndef __MESON_VDEC_CORE_H_
8 #define __MESON_VDEC_CORE_H_
9
10 #include <linux/irqreturn.h>
11 #include <linux/regmap.h>
12 #include <linux/list.h>
13 #include <media/videobuf2-v4l2.h>
14 #include <media/v4l2-ctrls.h>
15 #include <media/v4l2-device.h>
16 #include <linux/soc/amlogic/meson-canvas.h>
17
18 #include "vdec_platform.h"
19
20 /* 32 buffers in 3-plane YUV420 */
21 #define MAX_CANVAS (32 * 3)
22
23 struct amvdec_buffer {
24 struct list_head list;
25 struct vb2_buffer *vb;
26 };
27
28 /**
29 * struct amvdec_timestamp - stores a src timestamp along with a VIFIFO offset
30 *
31 * @list: used to make lists out of this struct
32 * @ts: timestamp
33 * @offset: offset in the VIFIFO where the associated packet was written
34 */
35 struct amvdec_timestamp {
36 struct list_head list;
37 u64 ts;
38 u32 offset;
39 };
40
41 struct amvdec_session;
42
43 /**
44 * struct amvdec_core - device parameters, singleton
45 *
46 * @dos_base: DOS memory base address
47 * @esparser_base: PARSER memory base address
48 * @regmap_ao: regmap for the AO bus
49 * @dev: core device
50 * @dev_dec: decoder device
51 * @platform: platform-specific data
52 * @canvas: canvas provider reference
53 * @dos_parser_clk: DOS_PARSER clock
54 * @dos_clk: DOS clock
55 * @vdec_1_clk: VDEC_1 clock
56 * @vdec_hevc_clk: VDEC_HEVC clock
57 * @esparser_reset: RESET for the PARSER
58 * @vdec_dec: video device for the decoder
59 * @v4l2_dev: v4l2 device
60 * @cur_sess: current decoding session
61 */
62 struct amvdec_core {
63 void __iomem *dos_base;
64 void __iomem *esparser_base;
65 struct regmap *regmap_ao;
66
67 struct device *dev;
68 struct device *dev_dec;
69 const struct vdec_platform *platform;
70
71 struct meson_canvas *canvas;
72
73 struct clk *dos_parser_clk;
74 struct clk *dos_clk;
75 struct clk *vdec_1_clk;
76 struct clk *vdec_hevc_clk;
77
78 struct reset_control *esparser_reset;
79
80 struct video_device *vdev_dec;
81 struct v4l2_device v4l2_dev;
82
83 struct amvdec_session *cur_sess;
84 struct mutex lock; /* video device lock */
85 };
86
87 /**
88 * struct amvdec_ops - vdec operations
89 *
90 * @start: mandatory call when the vdec needs to initialize
91 * @stop: mandatory call when the vdec needs to stop
92 * @conf_esparser: mandatory call to let the vdec configure the ESPARSER
93 * @vififo_level: mandatory call to get the current amount of data
94 * in the VIFIFO
95 * @use_offsets: mandatory call. Returns 1 if the VDEC supports vififo offsets
96 */
97 struct amvdec_ops {
98 int (*start)(struct amvdec_session *sess);
99 int (*stop)(struct amvdec_session *sess);
100 void (*conf_esparser)(struct amvdec_session *sess);
101 u32 (*vififo_level)(struct amvdec_session *sess);
102 };
103
104 /**
105 * struct amvdec_codec_ops - codec operations
106 *
107 * @start: mandatory call when the codec needs to initialize
108 * @stop: mandatory call when the codec needs to stop
109 * @load_extended_firmware: optional call to load additional firmware bits
110 * @num_pending_bufs: optional call to get the number of dst buffers on hold
111 * @can_recycle: optional call to know if the codec is ready to recycle
112 * a dst buffer
113 * @recycle: optional call to tell the codec to recycle a dst buffer. Must go
114 * in pair with @can_recycle
115 * @drain: optional call if the codec has a custom way of draining
116 * @eos_sequence: optional call to get an end sequence to send to esparser
117 * for flush. Mutually exclusive with @drain.
118 * @isr: mandatory call when the ISR triggers
119 * @threaded_isr: mandatory call for the threaded ISR
120 */
121 struct amvdec_codec_ops {
122 int (*start)(struct amvdec_session *sess);
123 int (*stop)(struct amvdec_session *sess);
124 int (*load_extended_firmware)(struct amvdec_session *sess,
125 const u8 *data, u32 len);
126 u32 (*num_pending_bufs)(struct amvdec_session *sess);
127 int (*can_recycle)(struct amvdec_core *core);
128 void (*recycle)(struct amvdec_core *core, u32 buf_idx);
129 void (*drain)(struct amvdec_session *sess);
130 void (*resume)(struct amvdec_session *sess);
131 const u8 * (*eos_sequence)(u32 *len);
132 irqreturn_t (*isr)(struct amvdec_session *sess);
133 irqreturn_t (*threaded_isr)(struct amvdec_session *sess);
134 };
135
136 /**
137 * struct amvdec_format - describes one of the OUTPUT (src) format supported
138 *
139 * @pixfmt: V4L2 pixel format
140 * @min_buffers: minimum amount of CAPTURE (dst) buffers
141 * @max_buffers: maximum amount of CAPTURE (dst) buffers
142 * @max_width: maximum picture width supported
143 * @max_height: maximum picture height supported
144 * @flags: enum flags associated with this pixfmt
145 * @vdec_ops: the VDEC operations that support this format
146 * @codec_ops: the codec operations that support this format
147 * @firmware_path: Path to the firmware that supports this format
148 * @pixfmts_cap: list of CAPTURE pixel formats available with pixfmt
149 */
150 struct amvdec_format {
151 u32 pixfmt;
152 u32 min_buffers;
153 u32 max_buffers;
154 u32 max_width;
155 u32 max_height;
156 u32 flags;
157
158 struct amvdec_ops *vdec_ops;
159 struct amvdec_codec_ops *codec_ops;
160
161 char *firmware_path;
162 u32 pixfmts_cap[4];
163 };
164
165 enum amvdec_status {
166 STATUS_STOPPED,
167 STATUS_RUNNING,
168 STATUS_NEEDS_RESUME,
169 };
170
171 /**
172 * struct amvdec_session - decoding session parameters
173 *
174 * @core: reference to the vdec core struct
175 * @fh: v4l2 file handle
176 * @m2m_dev: v4l2 m2m device
177 * @m2m_ctx: v4l2 m2m context
178 * @ctrl_handler: V4L2 control handler
179 * @ctrl_min_buf_capture: V4L2 control V4L2_CID_MIN_BUFFERS_FOR_CAPTURE
180 * @fmt_out: vdec pixel format for the OUTPUT queue
181 * @pixfmt_cap: V4L2 pixel format for the CAPTURE queue
182 * @width: current picture width
183 * @height: current picture height
184 * @colorspace: current colorspace
185 * @ycbcr_enc: current ycbcr_enc
186 * @quantization: current quantization
187 * @xfer_func: current transfer function
188 * @pixelaspect: Pixel Aspect Ratio reported by the decoder
189 * @esparser_queued_bufs: number of buffers currently queued into ESPARSER
190 * @esparser_queue_work: work struct for the ESPARSER to process src buffers
191 * @streamon_cap: stream on flag for capture queue
192 * @streamon_out: stream on flag for output queue
193 * @sequence_cap: capture sequence counter
194 * @should_stop: flag set if userspace signaled EOS via command
195 * or empty buffer
196 * @keyframe_found: flag set once a keyframe has been parsed
197 * @canvas_alloc: array of all the canvas IDs allocated
198 * @canvas_num: number of canvas IDs allocated
199 * @vififo_vaddr: virtual address for the VIFIFO
200 * @vififo_paddr: physical address for the VIFIFO
201 * @vififo_size: size of the VIFIFO dma alloc
202 * @bufs_recycle: list of buffers that need to be recycled
203 * @bufs_recycle_lock: lock for the bufs_recycle list
204 * @recycle_thread: task struct for the recycling thread
205 * @timestamps: chronological list of src timestamps
206 * @ts_spinlock: spinlock for the timestamps list
207 * @last_irq_jiffies: tracks last time the vdec triggered an IRQ
208 * @status: current decoding status
209 * @priv: codec private data
210 */
211 struct amvdec_session {
212 struct amvdec_core *core;
213
214 struct v4l2_fh fh;
215 struct v4l2_m2m_dev *m2m_dev;
216 struct v4l2_m2m_ctx *m2m_ctx;
217 struct v4l2_ctrl_handler ctrl_handler;
218 struct v4l2_ctrl *ctrl_min_buf_capture;
219 struct mutex lock; /* cap & out queues lock */
220
221 const struct amvdec_format *fmt_out;
222 u32 pixfmt_cap;
223
224 u32 width;
225 u32 height;
226 u32 colorspace;
227 u8 ycbcr_enc;
228 u8 quantization;
229 u8 xfer_func;
230
231 struct v4l2_fract pixelaspect;
232
233 atomic_t esparser_queued_bufs;
234 struct work_struct esparser_queue_work;
235
236 unsigned int streamon_cap, streamon_out;
237 unsigned int sequence_cap;
238 unsigned int should_stop;
239 unsigned int keyframe_found;
240 unsigned int num_dst_bufs;
241
242 u8 canvas_alloc[MAX_CANVAS];
243 u32 canvas_num;
244
245 void *vififo_vaddr;
246 dma_addr_t vififo_paddr;
247 u32 vififo_size;
248
249 struct list_head bufs_recycle;
250 struct mutex bufs_recycle_lock; /* bufs_recycle list lock */
251 struct task_struct *recycle_thread;
252
253 struct list_head timestamps;
254 spinlock_t ts_spinlock; /* timestamp list lock */
255
256 u64 last_irq_jiffies;
257 u32 last_offset;
258 u32 wrap_count;
259 u32 fw_idx_to_vb2_idx[32];
260
261 enum amvdec_status status;
262 void *priv;
263 };
264
265 u32 amvdec_get_output_size(struct amvdec_session *sess);
266
267 #endif