xref: /OK3568_Linux_fs/kernel/drivers/media/platform/sti/bdisp/bdisp.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0 */
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  * Copyright (C) STMicroelectronics SA 2014
4*4882a593Smuzhiyun  * Authors: Fabien Dessenne <fabien.dessenne@st.com> for STMicroelectronics.
5*4882a593Smuzhiyun  */
6*4882a593Smuzhiyun 
7*4882a593Smuzhiyun #include <linux/clk.h>
8*4882a593Smuzhiyun #include <linux/ktime.h>
9*4882a593Smuzhiyun #include <linux/platform_device.h>
10*4882a593Smuzhiyun #include <linux/spinlock.h>
11*4882a593Smuzhiyun 
12*4882a593Smuzhiyun #include <media/v4l2-ctrls.h>
13*4882a593Smuzhiyun #include <media/v4l2-device.h>
14*4882a593Smuzhiyun #include <media/v4l2-mem2mem.h>
15*4882a593Smuzhiyun 
16*4882a593Smuzhiyun #include <media/videobuf2-dma-contig.h>
17*4882a593Smuzhiyun 
18*4882a593Smuzhiyun #define BDISP_NAME              "bdisp"
19*4882a593Smuzhiyun 
20*4882a593Smuzhiyun /*
21*4882a593Smuzhiyun  *  Max nb of nodes in node-list:
22*4882a593Smuzhiyun  *   - 2 nodes to handle wide 4K pictures
23*4882a593Smuzhiyun  *   - 2 nodes to handle two planes (Y & CbCr) */
24*4882a593Smuzhiyun #define MAX_OUTPUT_PLANES       2
25*4882a593Smuzhiyun #define MAX_VERTICAL_STRIDES    2
26*4882a593Smuzhiyun #define MAX_NB_NODE             (MAX_OUTPUT_PLANES * MAX_VERTICAL_STRIDES)
27*4882a593Smuzhiyun 
28*4882a593Smuzhiyun /* struct bdisp_ctrls - bdisp control set
29*4882a593Smuzhiyun  * @hflip:      horizontal flip
30*4882a593Smuzhiyun  * @vflip:      vertical flip
31*4882a593Smuzhiyun  */
32*4882a593Smuzhiyun struct bdisp_ctrls {
33*4882a593Smuzhiyun 	struct v4l2_ctrl        *hflip;
34*4882a593Smuzhiyun 	struct v4l2_ctrl        *vflip;
35*4882a593Smuzhiyun };
36*4882a593Smuzhiyun 
37*4882a593Smuzhiyun /**
38*4882a593Smuzhiyun  * struct bdisp_fmt - driver's internal color format data
39*4882a593Smuzhiyun  * @pixelformat:fourcc code for this format
40*4882a593Smuzhiyun  * @nb_planes:  number of planes  (ex: [0]=RGB/Y - [1]=Cb/Cr, ...)
41*4882a593Smuzhiyun  * @bpp:        bits per pixel (general)
42*4882a593Smuzhiyun  * @bpp_plane0: byte per pixel for the 1st plane
43*4882a593Smuzhiyun  * @w_align:    width alignment in pixel (multiple of)
44*4882a593Smuzhiyun  * @h_align:    height alignment in pixel (multiple of)
45*4882a593Smuzhiyun  */
46*4882a593Smuzhiyun struct bdisp_fmt {
47*4882a593Smuzhiyun 	u32                     pixelformat;
48*4882a593Smuzhiyun 	u8                      nb_planes;
49*4882a593Smuzhiyun 	u8                      bpp;
50*4882a593Smuzhiyun 	u8                      bpp_plane0;
51*4882a593Smuzhiyun 	u8                      w_align;
52*4882a593Smuzhiyun 	u8                      h_align;
53*4882a593Smuzhiyun };
54*4882a593Smuzhiyun 
55*4882a593Smuzhiyun /**
56*4882a593Smuzhiyun  * struct bdisp_frame - frame properties
57*4882a593Smuzhiyun  *
58*4882a593Smuzhiyun  * @width:      frame width (including padding)
59*4882a593Smuzhiyun  * @height:     frame height (including padding)
60*4882a593Smuzhiyun  * @fmt:        pointer to frame format descriptor
61*4882a593Smuzhiyun  * @field:      frame / field type
62*4882a593Smuzhiyun  * @bytesperline: stride of the 1st plane
63*4882a593Smuzhiyun  * @sizeimage:  image size in bytes
64*4882a593Smuzhiyun  * @colorspace: colorspace
65*4882a593Smuzhiyun  * @crop:       crop area
66*4882a593Smuzhiyun  * @paddr:      image physical addresses per plane ([0]=RGB/Y - [1]=Cb/Cr, ...)
67*4882a593Smuzhiyun  */
68*4882a593Smuzhiyun struct bdisp_frame {
69*4882a593Smuzhiyun 	u32                     width;
70*4882a593Smuzhiyun 	u32                     height;
71*4882a593Smuzhiyun 	const struct bdisp_fmt  *fmt;
72*4882a593Smuzhiyun 	enum v4l2_field         field;
73*4882a593Smuzhiyun 	u32                     bytesperline;
74*4882a593Smuzhiyun 	u32                     sizeimage;
75*4882a593Smuzhiyun 	enum v4l2_colorspace    colorspace;
76*4882a593Smuzhiyun 	struct v4l2_rect        crop;
77*4882a593Smuzhiyun 	dma_addr_t              paddr[4];
78*4882a593Smuzhiyun };
79*4882a593Smuzhiyun 
80*4882a593Smuzhiyun /**
81*4882a593Smuzhiyun  * struct bdisp_request - bdisp request
82*4882a593Smuzhiyun  *
83*4882a593Smuzhiyun  * @src:        source frame properties
84*4882a593Smuzhiyun  * @dst:        destination frame properties
85*4882a593Smuzhiyun  * @hflip:      horizontal flip
86*4882a593Smuzhiyun  * @vflip:      vertical flip
87*4882a593Smuzhiyun  * @nb_req:     number of run request
88*4882a593Smuzhiyun  */
89*4882a593Smuzhiyun struct bdisp_request {
90*4882a593Smuzhiyun 	struct bdisp_frame      src;
91*4882a593Smuzhiyun 	struct bdisp_frame      dst;
92*4882a593Smuzhiyun 	unsigned int            hflip:1;
93*4882a593Smuzhiyun 	unsigned int            vflip:1;
94*4882a593Smuzhiyun 	int                     nb_req;
95*4882a593Smuzhiyun };
96*4882a593Smuzhiyun 
97*4882a593Smuzhiyun /**
98*4882a593Smuzhiyun  * struct bdisp_ctx - device context data
99*4882a593Smuzhiyun  *
100*4882a593Smuzhiyun  * @src:        source frame properties
101*4882a593Smuzhiyun  * @dst:        destination frame properties
102*4882a593Smuzhiyun  * @state:      flags to keep track of user configuration
103*4882a593Smuzhiyun  * @hflip:      horizontal flip
104*4882a593Smuzhiyun  * @vflip:      vertical flip
105*4882a593Smuzhiyun  * @bdisp_dev:  the device this context applies to
106*4882a593Smuzhiyun  * @node:       node array
107*4882a593Smuzhiyun  * @node_paddr: node physical address array
108*4882a593Smuzhiyun  * @fh:         v4l2 file handle
109*4882a593Smuzhiyun  * @ctrl_handler: v4l2 controls handler
110*4882a593Smuzhiyun  * @bdisp_ctrls: bdisp control set
111*4882a593Smuzhiyun  * @ctrls_rdy:  true if the control handler is initialized
112*4882a593Smuzhiyun  */
113*4882a593Smuzhiyun struct bdisp_ctx {
114*4882a593Smuzhiyun 	struct bdisp_frame      src;
115*4882a593Smuzhiyun 	struct bdisp_frame      dst;
116*4882a593Smuzhiyun 	u32                     state;
117*4882a593Smuzhiyun 	unsigned int            hflip:1;
118*4882a593Smuzhiyun 	unsigned int            vflip:1;
119*4882a593Smuzhiyun 	struct bdisp_dev        *bdisp_dev;
120*4882a593Smuzhiyun 	struct bdisp_node       *node[MAX_NB_NODE];
121*4882a593Smuzhiyun 	dma_addr_t              node_paddr[MAX_NB_NODE];
122*4882a593Smuzhiyun 	struct v4l2_fh          fh;
123*4882a593Smuzhiyun 	struct v4l2_ctrl_handler ctrl_handler;
124*4882a593Smuzhiyun 	struct bdisp_ctrls      bdisp_ctrls;
125*4882a593Smuzhiyun 	bool                    ctrls_rdy;
126*4882a593Smuzhiyun };
127*4882a593Smuzhiyun 
128*4882a593Smuzhiyun /**
129*4882a593Smuzhiyun  * struct bdisp_m2m_device - v4l2 memory-to-memory device data
130*4882a593Smuzhiyun  *
131*4882a593Smuzhiyun  * @vdev:       video device node for v4l2 m2m mode
132*4882a593Smuzhiyun  * @m2m_dev:    v4l2 m2m device data
133*4882a593Smuzhiyun  * @ctx:        hardware context data
134*4882a593Smuzhiyun  * @refcnt:     reference counter
135*4882a593Smuzhiyun  */
136*4882a593Smuzhiyun struct bdisp_m2m_device {
137*4882a593Smuzhiyun 	struct video_device     *vdev;
138*4882a593Smuzhiyun 	struct v4l2_m2m_dev     *m2m_dev;
139*4882a593Smuzhiyun 	struct bdisp_ctx        *ctx;
140*4882a593Smuzhiyun 	int                     refcnt;
141*4882a593Smuzhiyun };
142*4882a593Smuzhiyun 
143*4882a593Smuzhiyun /**
144*4882a593Smuzhiyun  * struct bdisp_dbg - debug info
145*4882a593Smuzhiyun  *
146*4882a593Smuzhiyun  * @debugfs_entry: debugfs
147*4882a593Smuzhiyun  * @copy_node:     array of last used nodes
148*4882a593Smuzhiyun  * @copy_request:  last bdisp request
149*4882a593Smuzhiyun  * @hw_start:      start time of last HW request
150*4882a593Smuzhiyun  * @last_duration: last HW processing duration in microsecs
151*4882a593Smuzhiyun  * @min_duration:  min HW processing duration in microsecs
152*4882a593Smuzhiyun  * @max_duration:  max HW processing duration in microsecs
153*4882a593Smuzhiyun  * @tot_duration:  total HW processing duration in microsecs
154*4882a593Smuzhiyun  */
155*4882a593Smuzhiyun struct bdisp_dbg {
156*4882a593Smuzhiyun 	struct dentry           *debugfs_entry;
157*4882a593Smuzhiyun 	struct bdisp_node       *copy_node[MAX_NB_NODE];
158*4882a593Smuzhiyun 	struct bdisp_request    copy_request;
159*4882a593Smuzhiyun 	ktime_t                 hw_start;
160*4882a593Smuzhiyun 	s64                     last_duration;
161*4882a593Smuzhiyun 	s64                     min_duration;
162*4882a593Smuzhiyun 	s64                     max_duration;
163*4882a593Smuzhiyun 	s64                     tot_duration;
164*4882a593Smuzhiyun };
165*4882a593Smuzhiyun 
166*4882a593Smuzhiyun /**
167*4882a593Smuzhiyun  * struct bdisp_dev - abstraction for bdisp entity
168*4882a593Smuzhiyun  *
169*4882a593Smuzhiyun  * @v4l2_dev:   v4l2 device
170*4882a593Smuzhiyun  * @vdev:       video device
171*4882a593Smuzhiyun  * @pdev:       platform device
172*4882a593Smuzhiyun  * @dev:        device
173*4882a593Smuzhiyun  * @lock:       mutex protecting this data structure
174*4882a593Smuzhiyun  * @slock:      spinlock protecting this data structure
175*4882a593Smuzhiyun  * @id:         device index
176*4882a593Smuzhiyun  * @m2m:        memory-to-memory V4L2 device information
177*4882a593Smuzhiyun  * @state:      flags used to synchronize m2m and capture mode operation
178*4882a593Smuzhiyun  * @clock:      IP clock
179*4882a593Smuzhiyun  * @regs:       registers
180*4882a593Smuzhiyun  * @irq_queue:  interrupt handler waitqueue
181*4882a593Smuzhiyun  * @work_queue: workqueue to handle timeouts
182*4882a593Smuzhiyun  * @timeout_work: IRQ timeout structure
183*4882a593Smuzhiyun  * @dbg:        debug info
184*4882a593Smuzhiyun  */
185*4882a593Smuzhiyun struct bdisp_dev {
186*4882a593Smuzhiyun 	struct v4l2_device      v4l2_dev;
187*4882a593Smuzhiyun 	struct video_device     vdev;
188*4882a593Smuzhiyun 	struct platform_device  *pdev;
189*4882a593Smuzhiyun 	struct device           *dev;
190*4882a593Smuzhiyun 	spinlock_t              slock;
191*4882a593Smuzhiyun 	struct mutex            lock;
192*4882a593Smuzhiyun 	u16                     id;
193*4882a593Smuzhiyun 	struct bdisp_m2m_device m2m;
194*4882a593Smuzhiyun 	unsigned long           state;
195*4882a593Smuzhiyun 	struct clk              *clock;
196*4882a593Smuzhiyun 	void __iomem            *regs;
197*4882a593Smuzhiyun 	wait_queue_head_t       irq_queue;
198*4882a593Smuzhiyun 	struct workqueue_struct *work_queue;
199*4882a593Smuzhiyun 	struct delayed_work     timeout_work;
200*4882a593Smuzhiyun 	struct bdisp_dbg        dbg;
201*4882a593Smuzhiyun };
202*4882a593Smuzhiyun 
203*4882a593Smuzhiyun void bdisp_hw_free_nodes(struct bdisp_ctx *ctx);
204*4882a593Smuzhiyun int bdisp_hw_alloc_nodes(struct bdisp_ctx *ctx);
205*4882a593Smuzhiyun void bdisp_hw_free_filters(struct device *dev);
206*4882a593Smuzhiyun int bdisp_hw_alloc_filters(struct device *dev);
207*4882a593Smuzhiyun int bdisp_hw_reset(struct bdisp_dev *bdisp);
208*4882a593Smuzhiyun int bdisp_hw_get_and_clear_irq(struct bdisp_dev *bdisp);
209*4882a593Smuzhiyun int bdisp_hw_update(struct bdisp_ctx *ctx);
210*4882a593Smuzhiyun 
211*4882a593Smuzhiyun void bdisp_debugfs_remove(struct bdisp_dev *bdisp);
212*4882a593Smuzhiyun void bdisp_debugfs_create(struct bdisp_dev *bdisp);
213*4882a593Smuzhiyun void bdisp_dbg_perf_begin(struct bdisp_dev *bdisp);
214*4882a593Smuzhiyun void bdisp_dbg_perf_end(struct bdisp_dev *bdisp);
215