blob: ca61708e82df1b139b9e7ccc93b4eb9cc46d91f1 [file] [log] [blame]
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -08001/* Copyright (c) 2012-2017, The Linux Foundation. All rights reserved.
2 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License version 2 and
5 * only version 2 as published by the Free Software Foundation.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
11 *
12 */
13
14#ifndef _MSM_VIDC_INTERNAL_H_
15#define _MSM_VIDC_INTERNAL_H_
16
17#include <linux/atomic.h>
18#include <linux/list.h>
19#include <linux/time.h>
20#include <linux/types.h>
21#include <linux/completion.h>
22#include <linux/wait.h>
23#include <linux/workqueue.h>
24#include <linux/msm-bus.h>
25#include <linux/msm-bus-board.h>
26#include <linux/kref.h>
27#include <media/v4l2-dev.h>
28#include <media/v4l2-device.h>
29#include <media/v4l2-ioctl.h>
30#include <media/v4l2-event.h>
31#include <media/v4l2-ctrls.h>
32#include <media/videobuf2-core.h>
33#include <media/videobuf2-v4l2.h>
34#include <media/msm_vidc.h>
35#include <media/msm_media_info.h>
36
37#include "vidc_hfi_api.h"
38
39#define MSM_VIDC_DRV_NAME "msm_vidc_driver"
40#define MSM_VIDC_VERSION KERNEL_VERSION(0, 0, 1)
41#define MAX_DEBUGFS_NAME 50
42#define DEFAULT_TIMEOUT 3
43#define DEFAULT_HEIGHT 1088
44#define DEFAULT_WIDTH 1920
45#define MIN_SUPPORTED_WIDTH 32
46#define MIN_SUPPORTED_HEIGHT 32
47#define DEFAULT_FPS 15
Praneeth Paladugudefea4e2017-02-09 23:44:08 -080048#define MIN_NUM_OUTPUT_BUFFERS 1
49#define MIN_NUM_CAPTURE_BUFFERS 1
50#define MAX_NUM_OUTPUT_BUFFERS VIDEO_MAX_FRAME // same as VB2_MAX_FRAME
51#define MAX_NUM_CAPTURE_BUFFERS VIDEO_MAX_FRAME // same as VB2_MAX_FRAME
52
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -080053
54/* Maintains the number of FTB's between each FBD over a window */
Praneeth Paladugue5fd0872017-04-19 11:24:28 -070055#define DCVS_FTB_WINDOW 16
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -080056
57#define V4L2_EVENT_VIDC_BASE 10
58
59#define SYS_MSG_START HAL_SYS_INIT_DONE
60#define SYS_MSG_END HAL_SYS_ERROR
61#define SESSION_MSG_START HAL_SESSION_EVENT_CHANGE
62#define SESSION_MSG_END HAL_SESSION_ERROR
63#define SYS_MSG_INDEX(__msg) (__msg - SYS_MSG_START)
64#define SESSION_MSG_INDEX(__msg) (__msg - SESSION_MSG_START)
65
66
67#define MAX_NAME_LENGTH 64
68
69#define EXTRADATA_IDX(__num_planes) ((__num_planes) ? (__num_planes) - 1 : 0)
70
71#define NUM_MBS_PER_SEC(__height, __width, __fps) \
72 (NUM_MBS_PER_FRAME(__height, __width) * __fps)
73
74#define NUM_MBS_PER_FRAME(__height, __width) \
75 ((ALIGN(__height, 16) / 16) * (ALIGN(__width, 16) / 16))
76
77enum vidc_ports {
78 OUTPUT_PORT,
79 CAPTURE_PORT,
80 MAX_PORT_NUM
81};
82
83enum vidc_core_state {
84 VIDC_CORE_UNINIT = 0,
85 VIDC_CORE_INIT,
86 VIDC_CORE_INIT_DONE,
87 VIDC_CORE_INVALID
88};
89
90/*
91 * Do not change the enum values unless
92 * you know what you are doing
93 */
94enum instance_state {
95 MSM_VIDC_CORE_UNINIT_DONE = 0x0001,
96 MSM_VIDC_CORE_INIT,
97 MSM_VIDC_CORE_INIT_DONE,
98 MSM_VIDC_OPEN,
99 MSM_VIDC_OPEN_DONE,
100 MSM_VIDC_LOAD_RESOURCES,
101 MSM_VIDC_LOAD_RESOURCES_DONE,
102 MSM_VIDC_START,
103 MSM_VIDC_START_DONE,
104 MSM_VIDC_STOP,
105 MSM_VIDC_STOP_DONE,
106 MSM_VIDC_RELEASE_RESOURCES,
107 MSM_VIDC_RELEASE_RESOURCES_DONE,
108 MSM_VIDC_CLOSE,
109 MSM_VIDC_CLOSE_DONE,
110 MSM_VIDC_CORE_UNINIT,
111 MSM_VIDC_CORE_INVALID
112};
113
114struct buf_info {
115 struct list_head list;
116 struct vb2_buffer *buf;
117};
118
119struct msm_vidc_list {
120 struct list_head list;
121 struct mutex lock;
122};
123
124static inline void INIT_MSM_VIDC_LIST(struct msm_vidc_list *mlist)
125{
126 mutex_init(&mlist->lock);
127 INIT_LIST_HEAD(&mlist->list);
128}
129
130static inline void DEINIT_MSM_VIDC_LIST(struct msm_vidc_list *mlist)
131{
132 mutex_destroy(&mlist->lock);
133}
134
135enum buffer_owner {
136 DRIVER,
137 FIRMWARE,
138 CLIENT,
139 MAX_OWNER
140};
141
Praneeth Paladugub71968b2015-08-19 20:47:57 -0700142struct vidc_freq_data {
143 struct list_head list;
144 ion_phys_addr_t device_addr;
145 unsigned long freq;
146};
147
Praneeth Paladugu319e7922017-03-16 11:09:06 -0700148struct recon_buf {
149 struct list_head list;
150 u32 buffer_index;
151 u32 CR;
152 u32 CF;
153};
154
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800155struct internal_buf {
156 struct list_head list;
157 enum hal_buffer buffer_type;
158 struct msm_smem *handle;
159 enum buffer_owner buffer_ownership;
160};
161
Praneeth Paladugud5bf7bc2017-05-29 23:41:04 -0700162struct msm_vidc_common_data {
163 char key[128];
164 int value;
165};
166
167struct msm_vidc_codec_data {
168 u32 fourcc;
169 enum session_type session_type;
170 int vpp_cycles;
171 int vsp_cycles;
172 int low_power_cycles;
173};
174
175struct msm_vidc_platform_data {
176 struct msm_vidc_common_data *common_data;
177 unsigned int common_data_length;
178 struct msm_vidc_codec_data *codec_data;
179 unsigned int codec_data_length;
180};
181
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800182struct msm_vidc_format {
183 char name[MAX_NAME_LENGTH];
184 u8 description[32];
185 u32 fourcc;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800186 int type;
187 u32 (*get_frame_size)(int plane, u32 height, u32 width);
Vaibhav Deshu Venkatesh8c9b6db2017-02-08 11:22:36 -0800188 bool defer_outputs;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800189};
190
191struct msm_vidc_drv {
192 struct mutex lock;
193 struct list_head cores;
194 int num_cores;
195 struct dentry *debugfs_root;
196 int thermal_level;
197 u32 platform_version;
198};
199
200struct msm_video_device {
201 int type;
202 struct video_device vdev;
203};
204
Praneeth Paladugu520e9b22017-05-31 13:25:18 -0700205struct session_crop {
206 u32 left;
207 u32 top;
208 u32 width;
209 u32 height;
210};
211
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800212struct session_prop {
213 u32 width[MAX_PORT_NUM];
214 u32 height[MAX_PORT_NUM];
Praneeth Paladugu520e9b22017-05-31 13:25:18 -0700215 struct session_crop crop_info;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800216 u32 fps;
217 u32 bitrate;
218};
219
220struct buf_queue {
221 struct vb2_queue vb2_bufq;
222 struct mutex lock;
Praneeth Paladugudefea4e2017-02-09 23:44:08 -0800223 unsigned int plane_sizes[VB2_MAX_PLANES];
224 int num_planes;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800225};
226
227enum profiling_points {
228 SYS_INIT = 0,
229 SESSION_INIT,
230 LOAD_RESOURCES,
231 FRAME_PROCESSING,
232 FW_IDLE,
233 MAX_PROFILING_POINTS,
234};
235
236struct buf_count {
237 int etb;
238 int ftb;
239 int fbd;
240 int ebd;
241};
242
Praneeth Paladugue5fd0872017-04-19 11:24:28 -0700243struct clock_data {
Praneeth Paladugu75cf18e2016-12-08 16:12:11 -0800244 int buffer_counter;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800245 int load;
246 int load_low;
247 int load_high;
248 int min_threshold;
249 int max_threshold;
Praneeth Paladugu1f9d1d92017-04-11 10:36:16 -0700250 unsigned int extra_capture_buffer_count;
251 unsigned int extra_output_buffer_count;
Praneeth Paladugu75cf18e2016-12-08 16:12:11 -0800252 enum hal_buffer buffer_type;
Praneeth Paladugue5fd0872017-04-19 11:24:28 -0700253 bool dcvs_mode;
254 unsigned long bitrate;
255 unsigned long min_freq;
256 unsigned long curr_freq;
257 u32 operating_rate;
Praneeth Paladugud5bf7bc2017-05-29 23:41:04 -0700258 struct msm_vidc_codec_data *entry;
Praneeth Paladugue5fd0872017-04-19 11:24:28 -0700259 u32 core_id;
Praneeth Paladugu319e7922017-03-16 11:09:06 -0700260 u32 dpb_fourcc;
261 u32 opb_fourcc;
Praneeth Paladugue5fd0872017-04-19 11:24:28 -0700262 enum hal_work_mode work_mode;
263 bool low_latency_mode;
Praneeth Paladugud5bf7bc2017-05-29 23:41:04 -0700264 bool use_sys_cache;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800265};
266
267struct profile_data {
268 int start;
269 int stop;
270 int cumulative;
271 char name[64];
272 int sampling;
273 int average;
274};
275
276struct msm_vidc_debug {
277 struct profile_data pdata[MAX_PROFILING_POINTS];
278 int profile;
279 int samples;
280};
281
282enum msm_vidc_modes {
283 VIDC_SECURE = BIT(0),
284 VIDC_TURBO = BIT(1),
285 VIDC_THUMBNAIL = BIT(2),
286 VIDC_LOW_POWER = BIT(3),
287 VIDC_REALTIME = BIT(4),
288};
289
290struct msm_vidc_core {
291 struct list_head list;
292 struct mutex lock;
293 int id;
294 struct hfi_device *device;
Praneeth Paladugud5bf7bc2017-05-29 23:41:04 -0700295 struct msm_vidc_platform_data *platform_data;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800296 struct msm_video_device vdev[MSM_VIDC_MAX_DEVICES];
297 struct v4l2_device v4l2_dev;
298 struct list_head instances;
299 struct dentry *debugfs_root;
300 enum vidc_core_state state;
301 struct completion completions[SYS_MSG_END - SYS_MSG_START + 1];
302 enum msm_vidc_hfi_type hfi_type;
303 struct msm_vidc_platform_resources resources;
304 u32 enc_codec_supported;
305 u32 dec_codec_supported;
306 u32 codec_count;
307 struct msm_vidc_capability *capabilities;
308 struct delayed_work fw_unload_work;
309 bool smmu_fault_handled;
Praneeth Paladugue5fd0872017-04-19 11:24:28 -0700310 unsigned long min_freq;
311 unsigned long curr_freq;
Praneeth Paladugu319e7922017-03-16 11:09:06 -0700312 struct vidc_bus_vote_data *vote_data;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800313};
314
315struct msm_vidc_inst {
316 struct list_head list;
317 struct mutex sync_lock, lock;
318 struct msm_vidc_core *core;
319 enum session_type session_type;
320 void *session;
321 struct session_prop prop;
322 enum instance_state state;
323 struct msm_vidc_format fmts[MAX_PORT_NUM];
324 struct buf_queue bufq[MAX_PORT_NUM];
325 struct msm_vidc_list pendingq;
Praneeth Paladugub71968b2015-08-19 20:47:57 -0700326 struct msm_vidc_list freqs;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800327 struct msm_vidc_list scratchbufs;
328 struct msm_vidc_list persistbufs;
329 struct msm_vidc_list pending_getpropq;
330 struct msm_vidc_list outputbufs;
Praneeth Paladugu319e7922017-03-16 11:09:06 -0700331 struct msm_vidc_list reconbufs;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800332 struct msm_vidc_list registeredbufs;
333 struct buffer_requirements buff_req;
334 void *mem_client;
335 struct v4l2_ctrl_handler ctrl_handler;
336 struct completion completions[SESSION_MSG_END - SESSION_MSG_START + 1];
337 struct v4l2_ctrl **cluster;
338 struct v4l2_fh event_handler;
339 struct msm_smem *extradata_handle;
340 bool in_reconfig;
341 u32 reconfig_width;
342 u32 reconfig_height;
343 struct dentry *debugfs_root;
344 void *priv;
345 struct msm_vidc_debug debug;
346 struct buf_count count;
Praneeth Paladugue5fd0872017-04-19 11:24:28 -0700347 struct clock_data clk_data;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800348 enum msm_vidc_modes flags;
349 struct msm_vidc_capability capability;
350 u32 buffer_size_limit;
351 enum buffer_mode_type buffer_mode_set[MAX_PORT_NUM];
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800352 struct v4l2_ctrl **ctrls;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800353 enum msm_vidc_pixel_depth bit_depth;
354 struct kref kref;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800355 u32 buffers_held_in_driver;
356 atomic_t in_flush;
357 u32 pic_struct;
358 u32 colour_space;
Chinmay Sawarkarb3c6ccb2017-02-23 18:01:32 -0800359 u32 profile;
360 u32 level;
361 u32 entropy_mode;
Praneeth Paladugud5bf7bc2017-05-29 23:41:04 -0700362 struct msm_vidc_codec_data *codec_data;
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800363};
364
365extern struct msm_vidc_drv *vidc_driver;
366
367struct msm_vidc_ctrl_cluster {
368 struct v4l2_ctrl **cluster;
369 struct list_head list;
370};
371
372struct msm_vidc_ctrl {
373 u32 id;
374 char name[MAX_NAME_LENGTH];
375 enum v4l2_ctrl_type type;
376 s32 minimum;
377 s32 maximum;
378 s32 default_value;
379 u32 step;
380 u32 menu_skip_mask;
381 u32 flags;
382 const char * const *qmenu;
383};
384
385void handle_cmd_response(enum hal_command_response cmd, void *data);
386int msm_vidc_trigger_ssr(struct msm_vidc_core *core,
387 enum hal_ssr_trigger_type type);
388int msm_vidc_check_session_supported(struct msm_vidc_inst *inst);
389int msm_vidc_check_scaling_supported(struct msm_vidc_inst *inst);
390void msm_vidc_queue_v4l2_event(struct msm_vidc_inst *inst, int event_type);
391
392struct buffer_info {
393 struct list_head list;
394 int type;
395 int num_planes;
396 int fd[VIDEO_MAX_PLANES];
397 int buff_off[VIDEO_MAX_PLANES];
398 int size[VIDEO_MAX_PLANES];
399 unsigned long uvaddr[VIDEO_MAX_PLANES];
400 ion_phys_addr_t device_addr[VIDEO_MAX_PLANES];
401 struct msm_smem *handle[VIDEO_MAX_PLANES];
402 enum v4l2_memory memory;
403 u32 v4l2_index;
404 bool pending_deletion;
405 atomic_t ref_count;
406 bool dequeued;
407 bool inactive;
408 bool mapped[VIDEO_MAX_PLANES];
409 int same_fd_ref[VIDEO_MAX_PLANES];
410 struct timeval timestamp;
411};
412
413struct buffer_info *device_to_uvaddr(struct msm_vidc_list *buf_list,
414 ion_phys_addr_t device_addr);
415int buf_ref_get(struct msm_vidc_inst *inst, struct buffer_info *binfo);
416int buf_ref_put(struct msm_vidc_inst *inst, struct buffer_info *binfo);
417int output_buffer_cache_invalidate(struct msm_vidc_inst *inst,
418 struct buffer_info *binfo);
419int qbuf_dynamic_buf(struct msm_vidc_inst *inst,
420 struct buffer_info *binfo);
421int unmap_and_deregister_buf(struct msm_vidc_inst *inst,
422 struct buffer_info *binfo);
423
424void msm_comm_handle_thermal_event(void);
425void *msm_smem_new_client(enum smem_type mtype,
426 void *platform_resources, enum session_type stype);
427struct msm_smem *msm_smem_alloc(void *clt, size_t size, u32 align, u32 flags,
428 enum hal_buffer buffer_type, int map_kernel);
429void msm_smem_free(void *clt, struct msm_smem *mem);
430void msm_smem_delete_client(void *clt);
431int msm_smem_cache_operations(void *clt, struct msm_smem *mem,
432 enum smem_cache_ops);
433struct msm_smem *msm_smem_user_to_kernel(void *clt, int fd, u32 offset,
434 enum hal_buffer buffer_type);
435struct context_bank_info *msm_smem_get_context_bank(void *clt,
436 bool is_secure, enum hal_buffer buffer_type);
437void msm_vidc_fw_unload_handler(struct work_struct *work);
438bool msm_smem_compare_buffers(void *clt, int fd, void *priv);
439/*
440 * XXX: normally should be in msm_vidc.h, but that's meant for public APIs,
441 * whereas this is private
442 */
443int msm_vidc_destroy(struct msm_vidc_inst *inst);
Praneeth Paladugud5bf7bc2017-05-29 23:41:04 -0700444void *vidc_get_drv_data(struct device *dev);
Praneeth Paladugu6e6fbdb2017-01-16 15:43:01 -0800445#endif