xref: /freebsd/sys/dev/firewire/fwcam.h (revision 40e05479718460820cd24c22e59519a4f13eba3d)
1*40e05479SAbdelkader Boudih /*
2*40e05479SAbdelkader Boudih  * Copyright (c) 2026 Abdelkader Boudih <freebsd@seuros.com>
3*40e05479SAbdelkader Boudih  *
4*40e05479SAbdelkader Boudih  * SPDX-License-Identifier: BSD-2-Clause
5*40e05479SAbdelkader Boudih  */
6*40e05479SAbdelkader Boudih 
7*40e05479SAbdelkader Boudih #ifndef _DEV_FIREWIRE_FWCAM_H_
8*40e05479SAbdelkader Boudih #define _DEV_FIREWIRE_FWCAM_H_
9*40e05479SAbdelkader Boudih 
10*40e05479SAbdelkader Boudih /*
11*40e05479SAbdelkader Boudih  * IIDC 1394-based Digital Camera Specification v1.30
12*40e05479SAbdelkader Boudih  * Register offsets relative to command_regs_base
13*40e05479SAbdelkader Boudih  */
14*40e05479SAbdelkader Boudih 
15*40e05479SAbdelkader Boudih /* Section 1.1 - Camera initialize register */
16*40e05479SAbdelkader Boudih #define IIDC_INITIALIZE		0x000
17*40e05479SAbdelkader Boudih 
18*40e05479SAbdelkader Boudih /* Section 1.2 - Inquiry registers for video format/mode/frame rate */
19*40e05479SAbdelkader Boudih #define IIDC_V_FORMAT_INQ	0x100
20*40e05479SAbdelkader Boudih #define IIDC_V_MODE_INQ(f)	(0x180 + (f) * 4)
21*40e05479SAbdelkader Boudih #define IIDC_V_RATE_INQ(f, m)	(0x200 + (f) * 0x20 + (m) * 4)
22*40e05479SAbdelkader Boudih 
23*40e05479SAbdelkader Boudih /* Section 1.3 - Inquiry register for basic function */
24*40e05479SAbdelkader Boudih #define IIDC_BASIC_FUNC_INQ	0x400
25*40e05479SAbdelkader Boudih 
26*40e05479SAbdelkader Boudih /* Section 1.4 - Inquiry registers for feature presence */
27*40e05479SAbdelkader Boudih #define IIDC_FEATURE_HI_INQ	0x404
28*40e05479SAbdelkader Boudih #define IIDC_FEATURE_LO_INQ	0x408
29*40e05479SAbdelkader Boudih 
30*40e05479SAbdelkader Boudih /* Section 1.5 - Inquiry registers for feature elements (per feature) */
31*40e05479SAbdelkader Boudih #define IIDC_BRIGHTNESS_INQ	0x500
32*40e05479SAbdelkader Boudih #define IIDC_AUTO_EXPOSURE_INQ	0x504
33*40e05479SAbdelkader Boudih #define IIDC_SHARPNESS_INQ	0x508
34*40e05479SAbdelkader Boudih #define IIDC_WHITE_BAL_INQ	0x50C
35*40e05479SAbdelkader Boudih #define IIDC_HUE_INQ		0x510
36*40e05479SAbdelkader Boudih #define IIDC_SATURATION_INQ	0x514
37*40e05479SAbdelkader Boudih #define IIDC_GAMMA_INQ		0x518
38*40e05479SAbdelkader Boudih #define IIDC_SHUTTER_INQ	0x51C
39*40e05479SAbdelkader Boudih #define IIDC_GAIN_INQ		0x520
40*40e05479SAbdelkader Boudih #define IIDC_IRIS_INQ		0x524
41*40e05479SAbdelkader Boudih #define IIDC_FOCUS_INQ		0x528
42*40e05479SAbdelkader Boudih #define IIDC_TEMPERATURE_INQ	0x52C
43*40e05479SAbdelkader Boudih #define IIDC_TRIGGER_INQ	0x530
44*40e05479SAbdelkader Boudih 
45*40e05479SAbdelkader Boudih /* Section 1.6 - Status and control registers for camera */
46*40e05479SAbdelkader Boudih #define IIDC_CUR_V_FRM_RATE	0x600
47*40e05479SAbdelkader Boudih #define IIDC_CUR_V_MODE		0x604
48*40e05479SAbdelkader Boudih #define IIDC_CUR_V_FORMAT	0x608
49*40e05479SAbdelkader Boudih #define IIDC_ISO_CHANNEL	0x60C
50*40e05479SAbdelkader Boudih #define IIDC_CAMERA_POWER	0x610
51*40e05479SAbdelkader Boudih #define IIDC_ISO_EN		0x614
52*40e05479SAbdelkader Boudih #define IIDC_MEMORY_SAVE	0x618
53*40e05479SAbdelkader Boudih #define IIDC_ONE_SHOT		0x61C
54*40e05479SAbdelkader Boudih #define IIDC_MEM_SAVE_CH	0x620
55*40e05479SAbdelkader Boudih #define IIDC_CUR_MEM_CH		0x624
56*40e05479SAbdelkader Boudih 
57*40e05479SAbdelkader Boudih /* Section 1.7 - Status and control register for features */
58*40e05479SAbdelkader Boudih #define IIDC_BRIGHTNESS		0x800
59*40e05479SAbdelkader Boudih #define IIDC_AUTO_EXPOSURE	0x804
60*40e05479SAbdelkader Boudih #define IIDC_SHARPNESS		0x808
61*40e05479SAbdelkader Boudih #define IIDC_WHITE_BALANCE	0x80C
62*40e05479SAbdelkader Boudih #define IIDC_HUE		0x810
63*40e05479SAbdelkader Boudih #define IIDC_SATURATION		0x814
64*40e05479SAbdelkader Boudih #define IIDC_GAMMA		0x818
65*40e05479SAbdelkader Boudih #define IIDC_SHUTTER		0x81C
66*40e05479SAbdelkader Boudih #define IIDC_GAIN		0x820
67*40e05479SAbdelkader Boudih #define IIDC_IRIS		0x824
68*40e05479SAbdelkader Boudih #define IIDC_FOCUS		0x828
69*40e05479SAbdelkader Boudih #define IIDC_TEMPERATURE	0x82C
70*40e05479SAbdelkader Boudih #define IIDC_TRIGGER_MODE	0x830
71*40e05479SAbdelkader Boudih #define IIDC_ZOOM		0x880
72*40e05479SAbdelkader Boudih #define IIDC_PAN		0x884
73*40e05479SAbdelkader Boudih #define IIDC_TILT		0x888
74*40e05479SAbdelkader Boudih 
75*40e05479SAbdelkader Boudih /* Video format indices (CUR_V_FORMAT register) */
76*40e05479SAbdelkader Boudih #define IIDC_FMT_VGA		0	/* Format_0: VGA non-compressed */
77*40e05479SAbdelkader Boudih #define IIDC_FMT_SVGA1		1	/* Format_1: Super VGA (1) */
78*40e05479SAbdelkader Boudih #define IIDC_FMT_SVGA2		2	/* Format_2: Super VGA (2) */
79*40e05479SAbdelkader Boudih #define IIDC_FMT_STILL		6	/* Format_6: Still image */
80*40e05479SAbdelkader Boudih #define IIDC_FMT_PARTIAL	7	/* Format_7: Partial/scalable */
81*40e05479SAbdelkader Boudih 
82*40e05479SAbdelkader Boudih /* V_FORMAT_INQ bits */
83*40e05479SAbdelkader Boudih #define IIDC_FORMAT_VGA		(1 << 31)	/* Format_0: VGA */
84*40e05479SAbdelkader Boudih #define IIDC_FORMAT_SVGA1	(1 << 30)	/* Format_1: Super VGA (1) */
85*40e05479SAbdelkader Boudih #define IIDC_FORMAT_SVGA2	(1 << 29)	/* Format_2: Super VGA (2) */
86*40e05479SAbdelkader Boudih #define IIDC_FORMAT_STILL	(1 << 25)	/* Format_6: Still image */
87*40e05479SAbdelkader Boudih #define IIDC_FORMAT_PARTIAL	(1 << 24)	/* Format_7: Partial image */
88*40e05479SAbdelkader Boudih 
89*40e05479SAbdelkader Boudih /* ISO_CHANNEL register fields */
90*40e05479SAbdelkader Boudih #define IIDC_ISO_CH_MASK	0xf0000000	/* bits [0..3] */
91*40e05479SAbdelkader Boudih #define IIDC_ISO_CH_SHIFT	28
92*40e05479SAbdelkader Boudih #define IIDC_ISO_SPEED_MASK	0x03000000	/* bits [6..7] */
93*40e05479SAbdelkader Boudih #define IIDC_ISO_SPEED_SHIFT	24
94*40e05479SAbdelkader Boudih 
95*40e05479SAbdelkader Boudih /* CAMERA_POWER register */
96*40e05479SAbdelkader Boudih #define IIDC_POWER_ON		(1 << 31)	/* bit [0] */
97*40e05479SAbdelkader Boudih 
98*40e05479SAbdelkader Boudih /* ISO_EN register */
99*40e05479SAbdelkader Boudih #define IIDC_ISO_EN_ON		(1 << 31)	/* bit [0] */
100*40e05479SAbdelkader Boudih 
101*40e05479SAbdelkader Boudih /* BASIC_FUNC_INQ bits */
102*40e05479SAbdelkader Boudih #define IIDC_ADV_FEATURE_INQ	(1 << 31)	/* bit [0] */
103*40e05479SAbdelkader Boudih #define IIDC_CAM_POWER_CTRL	(1 << 15)	/* bit [16] */
104*40e05479SAbdelkader Boudih #define IIDC_ONE_SHOT_INQ	(1 << 12)	/* bit [19] */
105*40e05479SAbdelkader Boudih #define IIDC_MULTI_SHOT_INQ	(1 << 11)	/* bit [20] */
106*40e05479SAbdelkader Boudih 
107*40e05479SAbdelkader Boudih /* FEATURE_HI_INQ bits (feature presence, section 1.4) */
108*40e05479SAbdelkader Boudih #define IIDC_HAS_BRIGHTNESS	(1 << 31)
109*40e05479SAbdelkader Boudih #define IIDC_HAS_AUTO_EXPOSURE	(1 << 30)
110*40e05479SAbdelkader Boudih #define IIDC_HAS_SHARPNESS	(1 << 29)
111*40e05479SAbdelkader Boudih #define IIDC_HAS_WHITE_BALANCE	(1 << 28)
112*40e05479SAbdelkader Boudih #define IIDC_HAS_HUE		(1 << 27)
113*40e05479SAbdelkader Boudih #define IIDC_HAS_SATURATION	(1 << 26)
114*40e05479SAbdelkader Boudih #define IIDC_HAS_GAMMA		(1 << 25)
115*40e05479SAbdelkader Boudih #define IIDC_HAS_SHUTTER	(1 << 24)
116*40e05479SAbdelkader Boudih #define IIDC_HAS_GAIN		(1 << 23)
117*40e05479SAbdelkader Boudih #define IIDC_HAS_IRIS		(1 << 22)
118*40e05479SAbdelkader Boudih #define IIDC_HAS_FOCUS		(1 << 21)
119*40e05479SAbdelkader Boudih #define IIDC_HAS_TEMPERATURE	(1 << 20)
120*40e05479SAbdelkader Boudih #define IIDC_HAS_TRIGGER	(1 << 19)
121*40e05479SAbdelkader Boudih 
122*40e05479SAbdelkader Boudih /* Config ROM: IIDC unit-dependent directory command_regs_base key */
123*40e05479SAbdelkader Boudih #define IIDC_CROM_CMD_BASE	(CSRTYPE_C | 0x00)	/* 0x40 */
124*40e05479SAbdelkader Boudih 
125*40e05479SAbdelkader Boudih /*
126*40e05479SAbdelkader Boudih  * Frame size limits for Format_0 (VGA non-compressed):
127*40e05479SAbdelkader Boudih  * Mode_1: 320x240 YUV422 = 153,600 bytes
128*40e05479SAbdelkader Boudih  * Mode_2: 640x480 YUV411 = 460,800 bytes
129*40e05479SAbdelkader Boudih  * Mode_3: 640x480 YUV422 = 614,400 bytes
130*40e05479SAbdelkader Boudih  */
131*40e05479SAbdelkader Boudih /*
132*40e05479SAbdelkader Boudih  * ioctl interface
133*40e05479SAbdelkader Boudih  */
134*40e05479SAbdelkader Boudih struct fwcam_mode {
135*40e05479SAbdelkader Boudih 	uint8_t		format;		/* IIDC video format (0-7) */
136*40e05479SAbdelkader Boudih 	uint8_t		mode;		/* IIDC video mode (0-7) */
137*40e05479SAbdelkader Boudih 	uint8_t		framerate;	/* IIDC frame rate (0-7) */
138*40e05479SAbdelkader Boudih 	uint8_t		_pad;
139*40e05479SAbdelkader Boudih 	uint32_t	frame_size;	/* computed frame size in bytes (read-only) */
140*40e05479SAbdelkader Boudih };
141*40e05479SAbdelkader Boudih 
142*40e05479SAbdelkader Boudih struct fwcam_feature {
143*40e05479SAbdelkader Boudih 	uint32_t	id;		/* FWCAM_FEAT_* */
144*40e05479SAbdelkader Boudih 	uint32_t	flags;		/* FWCAM_FEATF_* (from INQ, read-only) */
145*40e05479SAbdelkader Boudih 	uint32_t	min;		/* minimum value (from INQ, read-only) */
146*40e05479SAbdelkader Boudih 	uint32_t	max;		/* maximum value (from INQ, read-only) */
147*40e05479SAbdelkader Boudih 	uint32_t	value;		/* current value / value to set */
148*40e05479SAbdelkader Boudih 	uint32_t	value2;		/* second value (white balance V) */
149*40e05479SAbdelkader Boudih };
150*40e05479SAbdelkader Boudih 
151*40e05479SAbdelkader Boudih /* Feature IDs (index into IIDC feature register space) */
152*40e05479SAbdelkader Boudih #define FWCAM_FEAT_BRIGHTNESS	0
153*40e05479SAbdelkader Boudih #define FWCAM_FEAT_AUTO_EXPOSURE 1
154*40e05479SAbdelkader Boudih #define FWCAM_FEAT_SHARPNESS	2
155*40e05479SAbdelkader Boudih #define FWCAM_FEAT_WHITE_BALANCE 3
156*40e05479SAbdelkader Boudih #define FWCAM_FEAT_HUE		4
157*40e05479SAbdelkader Boudih #define FWCAM_FEAT_SATURATION	5
158*40e05479SAbdelkader Boudih #define FWCAM_FEAT_GAMMA	6
159*40e05479SAbdelkader Boudih #define FWCAM_FEAT_SHUTTER	7
160*40e05479SAbdelkader Boudih #define FWCAM_FEAT_GAIN		8
161*40e05479SAbdelkader Boudih #define FWCAM_FEAT_IRIS		9
162*40e05479SAbdelkader Boudih #define FWCAM_FEAT_FOCUS	10
163*40e05479SAbdelkader Boudih #define FWCAM_FEAT_TEMPERATURE	11
164*40e05479SAbdelkader Boudih #define FWCAM_FEAT_TRIGGER	12
165*40e05479SAbdelkader Boudih #define FWCAM_FEAT_ZOOM		13
166*40e05479SAbdelkader Boudih #define FWCAM_FEAT_PAN		14
167*40e05479SAbdelkader Boudih #define FWCAM_FEAT_TILT		15
168*40e05479SAbdelkader Boudih #define FWCAM_FEAT_MAX		16
169*40e05479SAbdelkader Boudih 
170*40e05479SAbdelkader Boudih /* Feature flags (from INQ register bits) */
171*40e05479SAbdelkader Boudih #define FWCAM_FEATF_PRESENT	(1 << 0)  /* feature is present */
172*40e05479SAbdelkader Boudih #define FWCAM_FEATF_ONOFF	(1 << 1)  /* supports on/off */
173*40e05479SAbdelkader Boudih #define FWCAM_FEATF_AUTO	(1 << 2)  /* supports auto mode */
174*40e05479SAbdelkader Boudih #define FWCAM_FEATF_MANUAL	(1 << 3)  /* supports manual mode */
175*40e05479SAbdelkader Boudih 
176*40e05479SAbdelkader Boudih struct fwcam_info {
177*40e05479SAbdelkader Boudih 	uint32_t	formats;	/* V_FORMAT_INQ bitmask */
178*40e05479SAbdelkader Boudih 	uint32_t	basic_func;	/* BASIC_FUNC_INQ */
179*40e05479SAbdelkader Boudih 	uint32_t	features_hi;	/* FEATURE_HI_INQ */
180*40e05479SAbdelkader Boudih 	uint32_t	features_lo;	/* FEATURE_LO_INQ */
181*40e05479SAbdelkader Boudih 	uint8_t		cur_format;
182*40e05479SAbdelkader Boudih 	uint8_t		cur_mode;
183*40e05479SAbdelkader Boudih 	uint8_t		cur_framerate;
184*40e05479SAbdelkader Boudih 	uint8_t		state;		/* FWCAM_STATE_* */
185*40e05479SAbdelkader Boudih 	uint32_t	frame_size;
186*40e05479SAbdelkader Boudih 	uint32_t	frame_dropped;
187*40e05479SAbdelkader Boudih 	uint8_t		iso_channel;	/* active ISO receive channel */
188*40e05479SAbdelkader Boudih 	uint8_t		_pad[3];
189*40e05479SAbdelkader Boudih };
190*40e05479SAbdelkader Boudih 
191*40e05479SAbdelkader Boudih #define FWCAM_GMODE	_IOR('C', 1, struct fwcam_mode)
192*40e05479SAbdelkader Boudih #define FWCAM_SMODE	_IOWR('C', 2, struct fwcam_mode)
193*40e05479SAbdelkader Boudih #define FWCAM_GFEAT	_IOWR('C', 3, struct fwcam_feature)
194*40e05479SAbdelkader Boudih #define FWCAM_SFEAT	_IOW('C', 4, struct fwcam_feature)
195*40e05479SAbdelkader Boudih #define FWCAM_GINFO	_IOR('C', 5, struct fwcam_info)
196*40e05479SAbdelkader Boudih 
197*40e05479SAbdelkader Boudih /* fwcam state values (visible to userland via fwcam_info.state) */
198*40e05479SAbdelkader Boudih #define FWCAM_STATE_IDLE	0
199*40e05479SAbdelkader Boudih #define FWCAM_STATE_PROBED	1
200*40e05479SAbdelkader Boudih #define FWCAM_STATE_STREAMING	2
201*40e05479SAbdelkader Boudih #define FWCAM_STATE_DETACHING	3
202*40e05479SAbdelkader Boudih 
203*40e05479SAbdelkader Boudih /*
204*40e05479SAbdelkader Boudih  * Internal constants
205*40e05479SAbdelkader Boudih  */
206*40e05479SAbdelkader Boudih #define FWCAM_MAX_FRAME_SIZE	(640 * 480 * 3)	/* 921,600 (RGB24) */
207*40e05479SAbdelkader Boudih #define FWCAM_ISO_NCHUNK	256	/* receive DMA chunks */
208*40e05479SAbdelkader Boudih #define FWCAM_ISO_PKTSIZE	2048	/* max iso packet size (MCLBYTES) */
209*40e05479SAbdelkader Boudih 
210*40e05479SAbdelkader Boudih #ifdef _KERNEL
211*40e05479SAbdelkader Boudih struct fwcam_softc {
212*40e05479SAbdelkader Boudih 	struct firewire_dev_comm fd;	/* must be first */
213*40e05479SAbdelkader Boudih 	struct mtx		mtx;
214*40e05479SAbdelkader Boudih 	struct cdev		*cdev;
215*40e05479SAbdelkader Boudih 
216*40e05479SAbdelkader Boudih 	/* Remote camera node */
217*40e05479SAbdelkader Boudih 	struct fw_device	*fwdev;
218*40e05479SAbdelkader Boudih 
219*40e05479SAbdelkader Boudih 	/* IIDC command register addressing */
220*40e05479SAbdelkader Boudih 	uint16_t		cmd_hi;		/* always 0xffff */
221*40e05479SAbdelkader Boudih 	uint32_t		cmd_lo;		/* 0xf0000000 | (base << 2) */
222*40e05479SAbdelkader Boudih 
223*40e05479SAbdelkader Boudih 	/* Capabilities from INQ registers */
224*40e05479SAbdelkader Boudih 	uint32_t		formats;	/* V_FORMAT_INQ */
225*40e05479SAbdelkader Boudih 	uint32_t		basic_func;	/* BASIC_FUNC_INQ */
226*40e05479SAbdelkader Boudih 	uint32_t		features_hi;	/* FEATURE_HI_INQ */
227*40e05479SAbdelkader Boudih 	uint32_t		features_lo;	/* FEATURE_LO_INQ */
228*40e05479SAbdelkader Boudih 
229*40e05479SAbdelkader Boudih 	/* Current settings */
230*40e05479SAbdelkader Boudih 	uint8_t			cur_format;
231*40e05479SAbdelkader Boudih 	uint8_t			cur_mode;
232*40e05479SAbdelkader Boudih 	uint8_t			cur_framerate;
233*40e05479SAbdelkader Boudih 	uint8_t			iso_channel;
234*40e05479SAbdelkader Boudih 	uint8_t			iso_speed;
235*40e05479SAbdelkader Boudih 
236*40e05479SAbdelkader Boudih 	/* Deferred probe task */
237*40e05479SAbdelkader Boudih 	struct task		probe_task;
238*40e05479SAbdelkader Boudih 
239*40e05479SAbdelkader Boudih 	/* Isochronous receive */
240*40e05479SAbdelkader Boudih 	int			dma_ch;		/* IR DMA channel, -1 if none */
241*40e05479SAbdelkader Boudih 	int			iso_active;	/* iso_input running */
242*40e05479SAbdelkader Boudih 
243*40e05479SAbdelkader Boudih 	/* Frame assembly (double buffer) */
244*40e05479SAbdelkader Boudih 	uint8_t			*frame_buf;	/* frame being assembled */
245*40e05479SAbdelkader Boudih 	uint8_t			*read_buf;	/* completed frame for read() */
246*40e05479SAbdelkader Boudih 	uint32_t		frame_size;	/* expected frame size (bytes) */
247*40e05479SAbdelkader Boudih 	uint32_t		frame_offset;	/* write position in frame_buf */
248*40e05479SAbdelkader Boudih 	int			frame_ready;	/* read_buf has valid frame */
249*40e05479SAbdelkader Boudih 	int			read_in_progress; /* uiomove active on read_buf */
250*40e05479SAbdelkader Boudih 	int			frame_dropped;	/* dropped frame count */
251*40e05479SAbdelkader Boudih 	int			open_count;	/* cdev open count */
252*40e05479SAbdelkader Boudih 	struct selinfo		rsel;		/* poll/select/kqueue */
253*40e05479SAbdelkader Boudih 
254*40e05479SAbdelkader Boudih 	/* State: one of FWCAM_STATE_* */
255*40e05479SAbdelkader Boudih 	int			state;
256*40e05479SAbdelkader Boudih };
257*40e05479SAbdelkader Boudih 
258*40e05479SAbdelkader Boudih #define FWCAM_LOCK(sc)		mtx_lock(&(sc)->mtx)
259*40e05479SAbdelkader Boudih #define FWCAM_UNLOCK(sc)	mtx_unlock(&(sc)->mtx)
260*40e05479SAbdelkader Boudih 
261*40e05479SAbdelkader Boudih #endif /* _KERNEL */
262*40e05479SAbdelkader Boudih 
263*40e05479SAbdelkader Boudih #endif /* _DEV_FIREWIRE_FWCAM_H_ */
264