xref: /freebsd/sys/dev/video/video_internal.h (revision 9c9428825f4c55e3cb37412c661bb9d385db4c68)
1*9c942882SAbdelkader Boudih /*
2*9c942882SAbdelkader Boudih  * Copyright (c) 2026 Abdelkader Boudih <freebsd@seuros.com>
3*9c942882SAbdelkader Boudih  *
4*9c942882SAbdelkader Boudih  * SPDX-License-Identifier: BSD-2-Clause
5*9c942882SAbdelkader Boudih  */
6*9c942882SAbdelkader Boudih 
7*9c942882SAbdelkader Boudih #ifndef _DEV_VIDEO_VIDEO_INTERNAL_H_
8*9c942882SAbdelkader Boudih #define _DEV_VIDEO_VIDEO_INTERNAL_H_
9*9c942882SAbdelkader Boudih 
10*9c942882SAbdelkader Boudih #include <sys/param.h>
11*9c942882SAbdelkader Boudih #include <sys/systm.h>
12*9c942882SAbdelkader Boudih #include <sys/bus.h>
13*9c942882SAbdelkader Boudih #include <sys/conf.h>
14*9c942882SAbdelkader Boudih #include <sys/kernel.h>
15*9c942882SAbdelkader Boudih #include <sys/lock.h>
16*9c942882SAbdelkader Boudih #include <sys/malloc.h>
17*9c942882SAbdelkader Boudih #include <sys/mutex.h>
18*9c942882SAbdelkader Boudih #include <sys/sx.h>
19*9c942882SAbdelkader Boudih #include <sys/queue.h>
20*9c942882SAbdelkader Boudih #include <sys/selinfo.h>
21*9c942882SAbdelkader Boudih 
22*9c942882SAbdelkader Boudih #include <vm/vm.h>
23*9c942882SAbdelkader Boudih #include <vm/vm_object.h>
24*9c942882SAbdelkader Boudih #include <vm/vm_page.h>
25*9c942882SAbdelkader Boudih #include <vm/vm_pager.h>
26*9c942882SAbdelkader Boudih 
27*9c942882SAbdelkader Boudih #include <dev/video/video.h>
28*9c942882SAbdelkader Boudih 
29*9c942882SAbdelkader Boudih MALLOC_DECLARE(M_VIDEO);
30*9c942882SAbdelkader Boudih 
31*9c942882SAbdelkader Boudih #define	VIDEO_MAX_BUFFERS	8
32*9c942882SAbdelkader Boudih #define	VIDEO_READ_BUFFERS	3
33*9c942882SAbdelkader Boudih 
34*9c942882SAbdelkader Boudih enum video_buf_state {
35*9c942882SAbdelkader Boudih 	VB_IDLE,
36*9c942882SAbdelkader Boudih 	VB_QUEUED,
37*9c942882SAbdelkader Boudih 	VB_ACTIVE,
38*9c942882SAbdelkader Boudih 	VB_DONE,
39*9c942882SAbdelkader Boudih 	VB_ERROR,
40*9c942882SAbdelkader Boudih };
41*9c942882SAbdelkader Boudih 
42*9c942882SAbdelkader Boudih struct video_buf {
43*9c942882SAbdelkader Boudih 	STAILQ_ENTRY(video_buf) entry;
44*9c942882SAbdelkader Boudih 	struct video_buf_pool	*pool;
45*9c942882SAbdelkader Boudih 	struct video_device	*vd;
46*9c942882SAbdelkader Boudih 
47*9c942882SAbdelkader Boudih 	uint32_t		index;
48*9c942882SAbdelkader Boudih 	enum video_buf_state	state;
49*9c942882SAbdelkader Boudih 
50*9c942882SAbdelkader Boudih 	void			*buf;
51*9c942882SAbdelkader Boudih 	size_t			length;
52*9c942882SAbdelkader Boudih 
53*9c942882SAbdelkader Boudih 	size_t			bytesused;
54*9c942882SAbdelkader Boudih 	uint32_t		sequence;
55*9c942882SAbdelkader Boudih 	struct timeval		timestamp;
56*9c942882SAbdelkader Boudih 	uint32_t		flags;
57*9c942882SAbdelkader Boudih };
58*9c942882SAbdelkader Boudih 
59*9c942882SAbdelkader Boudih STAILQ_HEAD(video_buf_list, video_buf);
60*9c942882SAbdelkader Boudih 
61*9c942882SAbdelkader Boudih /*
62*9c942882SAbdelkader Boudih  * All buffers must stay carved out of one OBJT_PHYS vm_object, mapped into
63*9c942882SAbdelkader Boudih  * the kernel map and handed to userspace mmap as that same object.  Giving
64*9c942882SAbdelkader Boudih  * each buffer its own object breaks the mmap path.
65*9c942882SAbdelkader Boudih  */
66*9c942882SAbdelkader Boudih struct video_buf_pool {
67*9c942882SAbdelkader Boudih 	vm_object_t		obj;
68*9c942882SAbdelkader Boudih 	vm_offset_t		kva;
69*9c942882SAbdelkader Boudih 
70*9c942882SAbdelkader Boudih 	u_int			nbufs;
71*9c942882SAbdelkader Boudih 	size_t			buf_size;
72*9c942882SAbdelkader Boudih 	size_t			map_size;
73*9c942882SAbdelkader Boudih 	struct video_buf	bufs[VIDEO_MAX_BUFFERS];
74*9c942882SAbdelkader Boudih };
75*9c942882SAbdelkader Boudih 
76*9c942882SAbdelkader Boudih struct video_file {
77*9c942882SAbdelkader Boudih 	struct video_device	*vd;
78*9c942882SAbdelkader Boudih 	bool			is_owner;
79*9c942882SAbdelkader Boudih 	bool			reading;	/* read(2) in progress */
80*9c942882SAbdelkader Boudih 	size_t			read_offset;
81*9c942882SAbdelkader Boudih 	struct video_buf	*read_buf;
82*9c942882SAbdelkader Boudih };
83*9c942882SAbdelkader Boudih 
84*9c942882SAbdelkader Boudih enum video_mode {
85*9c942882SAbdelkader Boudih 	VMODE_NONE,
86*9c942882SAbdelkader Boudih 	VMODE_READ,
87*9c942882SAbdelkader Boudih 	VMODE_MMAP,
88*9c942882SAbdelkader Boudih };
89*9c942882SAbdelkader Boudih 
90*9c942882SAbdelkader Boudih /* Lock order: cfg_sx -> mtx. */
91*9c942882SAbdelkader Boudih struct video_device {
92*9c942882SAbdelkader Boudih 	device_t		dev;
93*9c942882SAbdelkader Boudih 	struct cdev		*cdev;
94*9c942882SAbdelkader Boudih 	int			unit;
95*9c942882SAbdelkader Boudih 
96*9c942882SAbdelkader Boudih 	struct sx		cfg_sx;
97*9c942882SAbdelkader Boudih 	struct mtx		mtx;
98*9c942882SAbdelkader Boudih 
99*9c942882SAbdelkader Boudih 	bool			dying;
100*9c942882SAbdelkader Boudih 
101*9c942882SAbdelkader Boudih 	struct video_file	*owner;
102*9c942882SAbdelkader Boudih 	enum video_mode		mode;
103*9c942882SAbdelkader Boudih 	bool			streaming;
104*9c942882SAbdelkader Boudih 	bool			stopping;
105*9c942882SAbdelkader Boudih 
106*9c942882SAbdelkader Boudih 	struct video_format	format;
107*9c942882SAbdelkader Boudih 
108*9c942882SAbdelkader Boudih 	struct video_buf_pool	*pool;
109*9c942882SAbdelkader Boudih 	struct video_buf_list	queued;
110*9c942882SAbdelkader Boudih 	struct video_buf_list	done;
111*9c942882SAbdelkader Boudih 	u_int			readers;	/* copies in flight from pool */
112*9c942882SAbdelkader Boudih 
113*9c942882SAbdelkader Boudih 	struct selinfo		sel;
114*9c942882SAbdelkader Boudih };
115*9c942882SAbdelkader Boudih 
116*9c942882SAbdelkader Boudih 
117*9c942882SAbdelkader Boudih #endif /* _DEV_VIDEO_VIDEO_INTERNAL_H_ */
118