1 /*
2  * Copyright (C) 2010 Bluecherry, LLC www.bluecherrydvr.com
3  * Copyright (C) 2010 Ben Collins <bcollins@bluecherry.net>
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18  */
19 
20 #include <linux/kernel.h>
21 #include <linux/module.h>
22 #include <linux/kthread.h>
23 #include <linux/freezer.h>
24 #include <media/v4l2-ioctl.h>
25 #include <media/v4l2-common.h>
26 #include <media/videobuf-dma-sg.h>
27 #include "solo6x10.h"
28 #include "tw28.h"
29 #include "solo6x10-jpeg.h"
30 
31 #define MIN_VID_BUFFERS		4
32 #define FRAME_BUF_SIZE		(128 * 1024)
33 #define MP4_QS			16
34 
35 static int solo_enc_thread(void *data);
36 
37 extern unsigned video_nr;
38 
39 struct solo_enc_fh {
40 	struct			solo_enc_dev *enc;
41 	u32			fmt;
42 	u16			rd_idx;
43 	u8			enc_on;
44 	enum solo_enc_types	type;
45 	struct videobuf_queue	vidq;
46 	struct list_head	vidq_active;
47 	struct task_struct	*kthread;
48 	struct p2m_desc		desc[SOLO_NR_P2M_DESC];
49 };
50 
51 static const u32 solo_user_ctrls[] = {
52 	V4L2_CID_BRIGHTNESS,
53 	V4L2_CID_CONTRAST,
54 	V4L2_CID_SATURATION,
55 	V4L2_CID_HUE,
56 	V4L2_CID_SHARPNESS,
57 	0
58 };
59 
60 static const u32 solo_mpeg_ctrls[] = {
61 	V4L2_CID_MPEG_VIDEO_ENCODING,
62 	V4L2_CID_MPEG_VIDEO_GOP_SIZE,
63 	0
64 };
65 
66 static const u32 solo_private_ctrls[] = {
67 	V4L2_CID_MOTION_ENABLE,
68 	V4L2_CID_MOTION_THRESHOLD,
69 	0
70 };
71 
72 static const u32 solo_fmtx_ctrls[] = {
73 	V4L2_CID_RDS_TX_RADIO_TEXT,
74 	0
75 };
76 
77 static const u32 *solo_ctrl_classes[] = {
78 	solo_user_ctrls,
79 	solo_mpeg_ctrls,
80 	solo_fmtx_ctrls,
81 	solo_private_ctrls,
82 	NULL
83 };
84 
solo_is_motion_on(struct solo_enc_dev * solo_enc)85 static int solo_is_motion_on(struct solo_enc_dev *solo_enc)
86 {
87 	struct solo_dev *solo_dev = solo_enc->solo_dev;
88 	u8 ch = solo_enc->ch;
89 
90 	if (solo_dev->motion_mask & (1 << ch))
91 		return 1;
92 	return 0;
93 }
94 
solo_motion_toggle(struct solo_enc_dev * solo_enc,int on)95 static void solo_motion_toggle(struct solo_enc_dev *solo_enc, int on)
96 {
97 	struct solo_dev *solo_dev = solo_enc->solo_dev;
98 	u8 ch = solo_enc->ch;
99 
100 	spin_lock(&solo_enc->lock);
101 
102 	if (on)
103 		solo_dev->motion_mask |= (1 << ch);
104 	else
105 		solo_dev->motion_mask &= ~(1 << ch);
106 
107 	/* Do this regardless of if we are turning on or off */
108 	solo_reg_write(solo_enc->solo_dev, SOLO_VI_MOT_CLEAR,
109 		       1 << solo_enc->ch);
110 	solo_enc->motion_detected = 0;
111 
112 	solo_reg_write(solo_dev, SOLO_VI_MOT_ADR,
113 		       SOLO_VI_MOTION_EN(solo_dev->motion_mask) |
114 		       (SOLO_MOTION_EXT_ADDR(solo_dev) >> 16));
115 
116 	if (solo_dev->motion_mask)
117 		solo_irq_on(solo_dev, SOLO_IRQ_MOTION);
118 	else
119 		solo_irq_off(solo_dev, SOLO_IRQ_MOTION);
120 
121 	spin_unlock(&solo_enc->lock);
122 }
123 
124 /* Should be called with solo_enc->lock held */
solo_update_mode(struct solo_enc_dev * solo_enc)125 static void solo_update_mode(struct solo_enc_dev *solo_enc)
126 {
127 	struct solo_dev *solo_dev = solo_enc->solo_dev;
128 
129 	assert_spin_locked(&solo_enc->lock);
130 
131 	solo_enc->interlaced = (solo_enc->mode & 0x08) ? 1 : 0;
132 	solo_enc->bw_weight = max(solo_dev->fps / solo_enc->interval, 1);
133 
134 	switch (solo_enc->mode) {
135 	case SOLO_ENC_MODE_CIF:
136 		solo_enc->width = solo_dev->video_hsize >> 1;
137 		solo_enc->height = solo_dev->video_vsize;
138 		break;
139 	case SOLO_ENC_MODE_D1:
140 		solo_enc->width = solo_dev->video_hsize;
141 		solo_enc->height = solo_dev->video_vsize << 1;
142 		solo_enc->bw_weight <<= 2;
143 		break;
144 	default:
145 		WARN(1, "mode is unknown\n");
146 	}
147 }
148 
149 /* Should be called with solo_enc->lock held */
solo_enc_on(struct solo_enc_fh * fh)150 static int solo_enc_on(struct solo_enc_fh *fh)
151 {
152 	struct solo_enc_dev *solo_enc = fh->enc;
153 	u8 ch = solo_enc->ch;
154 	struct solo_dev *solo_dev = solo_enc->solo_dev;
155 	u8 interval;
156 
157 	assert_spin_locked(&solo_enc->lock);
158 
159 	if (fh->enc_on)
160 		return 0;
161 
162 	solo_update_mode(solo_enc);
163 
164 	/* Make sure to bw check on first reader */
165 	if (!atomic_read(&solo_enc->readers)) {
166 		if (solo_enc->bw_weight > solo_dev->enc_bw_remain)
167 			return -EBUSY;
168 		else
169 			solo_dev->enc_bw_remain -= solo_enc->bw_weight;
170 	}
171 
172 	fh->enc_on = 1;
173 	fh->rd_idx = solo_enc->solo_dev->enc_wr_idx;
174 
175 	if (fh->type == SOLO_ENC_TYPE_EXT)
176 		solo_reg_write(solo_dev, SOLO_CAP_CH_COMP_ENA_E(ch), 1);
177 
178 	if (atomic_inc_return(&solo_enc->readers) > 1)
179 		return 0;
180 
181 	/* Disable all encoding for this channel */
182 	solo_reg_write(solo_dev, SOLO_CAP_CH_SCALE(ch), 0);
183 
184 	/* Common for both std and ext encoding */
185 	solo_reg_write(solo_dev, SOLO_VE_CH_INTL(ch),
186 		       solo_enc->interlaced ? 1 : 0);
187 
188 	if (solo_enc->interlaced)
189 		interval = solo_enc->interval - 1;
190 	else
191 		interval = solo_enc->interval;
192 
193 	/* Standard encoding only */
194 	solo_reg_write(solo_dev, SOLO_VE_CH_GOP(ch), solo_enc->gop);
195 	solo_reg_write(solo_dev, SOLO_VE_CH_QP(ch), solo_enc->qp);
196 	solo_reg_write(solo_dev, SOLO_CAP_CH_INTV(ch), interval);
197 
198 	/* Extended encoding only */
199 	solo_reg_write(solo_dev, SOLO_VE_CH_GOP_E(ch), solo_enc->gop);
200 	solo_reg_write(solo_dev, SOLO_VE_CH_QP_E(ch), solo_enc->qp);
201 	solo_reg_write(solo_dev, SOLO_CAP_CH_INTV_E(ch), interval);
202 
203 	/* Enables the standard encoder */
204 	solo_reg_write(solo_dev, SOLO_CAP_CH_SCALE(ch), solo_enc->mode);
205 
206 	/* Settle down Beavis... */
207 	mdelay(10);
208 
209 	return 0;
210 }
211 
solo_enc_off(struct solo_enc_fh * fh)212 static void solo_enc_off(struct solo_enc_fh *fh)
213 {
214 	struct solo_enc_dev *solo_enc = fh->enc;
215 	struct solo_dev *solo_dev = solo_enc->solo_dev;
216 
217 	if (!fh->enc_on)
218 		return;
219 
220 	if (fh->kthread) {
221 		kthread_stop(fh->kthread);
222 		fh->kthread = NULL;
223 	}
224 
225 	solo_dev->enc_bw_remain += solo_enc->bw_weight;
226 	fh->enc_on = 0;
227 
228 	if (atomic_dec_return(&solo_enc->readers) > 0)
229 		return;
230 
231 	solo_reg_write(solo_dev, SOLO_CAP_CH_SCALE(solo_enc->ch), 0);
232 	solo_reg_write(solo_dev, SOLO_CAP_CH_COMP_ENA_E(solo_enc->ch), 0);
233 }
234 
solo_start_fh_thread(struct solo_enc_fh * fh)235 static int solo_start_fh_thread(struct solo_enc_fh *fh)
236 {
237 	struct solo_enc_dev *solo_enc = fh->enc;
238 
239 	fh->kthread = kthread_run(solo_enc_thread, fh, SOLO6X10_NAME "_enc");
240 
241 	/* Oops, we had a problem */
242 	if (IS_ERR(fh->kthread)) {
243 		spin_lock(&solo_enc->lock);
244 		solo_enc_off(fh);
245 		spin_unlock(&solo_enc->lock);
246 
247 		return PTR_ERR(fh->kthread);
248 	}
249 
250 	return 0;
251 }
252 
enc_reset_gop(struct solo_dev * solo_dev,u8 ch)253 static void enc_reset_gop(struct solo_dev *solo_dev, u8 ch)
254 {
255 	BUG_ON(ch >= solo_dev->nr_chans);
256 	solo_reg_write(solo_dev, SOLO_VE_CH_GOP(ch), 1);
257 	solo_dev->v4l2_enc[ch]->reset_gop = 1;
258 }
259 
enc_gop_reset(struct solo_dev * solo_dev,u8 ch,u8 vop)260 static int enc_gop_reset(struct solo_dev *solo_dev, u8 ch, u8 vop)
261 {
262 	BUG_ON(ch >= solo_dev->nr_chans);
263 	if (!solo_dev->v4l2_enc[ch]->reset_gop)
264 		return 0;
265 	if (vop)
266 		return 1;
267 	solo_dev->v4l2_enc[ch]->reset_gop = 0;
268 	solo_reg_write(solo_dev, SOLO_VE_CH_GOP(ch),
269 		       solo_dev->v4l2_enc[ch]->gop);
270 	return 0;
271 }
272 
enc_write_sg(struct scatterlist * sglist,void * buf,int size)273 static void enc_write_sg(struct scatterlist *sglist, void *buf, int size)
274 {
275 	struct scatterlist *sg;
276 	u8 *src = buf;
277 
278 	for (sg = sglist; sg && size > 0; sg = sg_next(sg)) {
279 		u8 *p = sg_virt(sg);
280 		size_t len = sg_dma_len(sg);
281 		int i;
282 
283 		for (i = 0; i < len && size; i++)
284 			p[i] = *(src++);
285 	}
286 }
287 
enc_get_mpeg_dma_sg(struct solo_dev * solo_dev,struct p2m_desc * desc,struct scatterlist * sglist,int skip,unsigned int off,unsigned int size)288 static int enc_get_mpeg_dma_sg(struct solo_dev *solo_dev,
289 			       struct p2m_desc *desc,
290 			       struct scatterlist *sglist, int skip,
291 			       unsigned int off, unsigned int size)
292 {
293 	int ret;
294 
295 	if (off > SOLO_MP4E_EXT_SIZE(solo_dev))
296 		return -EINVAL;
297 
298 	if (off + size <= SOLO_MP4E_EXT_SIZE(solo_dev)) {
299 		return solo_p2m_dma_sg(solo_dev, SOLO_P2M_DMA_ID_MP4E,
300 				       desc, 0, sglist, skip,
301 				       SOLO_MP4E_EXT_ADDR(solo_dev) + off, size);
302 	}
303 
304 	/* Buffer wrap */
305 	ret = solo_p2m_dma_sg(solo_dev, SOLO_P2M_DMA_ID_MP4E, desc, 0,
306 			      sglist, skip, SOLO_MP4E_EXT_ADDR(solo_dev) + off,
307 			      SOLO_MP4E_EXT_SIZE(solo_dev) - off);
308 
309 	ret |= solo_p2m_dma_sg(solo_dev, SOLO_P2M_DMA_ID_MP4E, desc, 0,
310 			       sglist, skip + SOLO_MP4E_EXT_SIZE(solo_dev) - off,
311 			       SOLO_MP4E_EXT_ADDR(solo_dev),
312 			       size + off - SOLO_MP4E_EXT_SIZE(solo_dev));
313 
314 	return ret;
315 }
316 
enc_get_mpeg_dma_t(struct solo_dev * solo_dev,dma_addr_t buf,unsigned int off,unsigned int size)317 static int enc_get_mpeg_dma_t(struct solo_dev *solo_dev,
318 			      dma_addr_t buf, unsigned int off,
319 			      unsigned int size)
320 {
321 	int ret;
322 
323 	if (off > SOLO_MP4E_EXT_SIZE(solo_dev))
324 		return -EINVAL;
325 
326 	if (off + size <= SOLO_MP4E_EXT_SIZE(solo_dev)) {
327 		return solo_p2m_dma_t(solo_dev, SOLO_P2M_DMA_ID_MP4E, 0, buf,
328 				      SOLO_MP4E_EXT_ADDR(solo_dev) + off, size);
329 	}
330 
331 	/* Buffer wrap */
332 	ret = solo_p2m_dma_t(solo_dev, SOLO_P2M_DMA_ID_MP4E, 0, buf,
333 			     SOLO_MP4E_EXT_ADDR(solo_dev) + off,
334 			     SOLO_MP4E_EXT_SIZE(solo_dev) - off);
335 
336 	ret |= solo_p2m_dma_t(solo_dev, SOLO_P2M_DMA_ID_MP4E, 0,
337 			      buf + SOLO_MP4E_EXT_SIZE(solo_dev) - off,
338 			      SOLO_MP4E_EXT_ADDR(solo_dev),
339 			      size + off - SOLO_MP4E_EXT_SIZE(solo_dev));
340 
341 	return ret;
342 }
343 
enc_get_mpeg_dma(struct solo_dev * solo_dev,void * buf,unsigned int off,unsigned int size)344 static int enc_get_mpeg_dma(struct solo_dev *solo_dev, void *buf,
345 			    unsigned int off, unsigned int size)
346 {
347 	int ret;
348 
349 	dma_addr_t dma_addr = pci_map_single(solo_dev->pdev, buf, size,
350 					     PCI_DMA_FROMDEVICE);
351 	ret = enc_get_mpeg_dma_t(solo_dev, dma_addr, off, size);
352 	pci_unmap_single(solo_dev->pdev, dma_addr, size, PCI_DMA_FROMDEVICE);
353 
354 	return ret;
355 }
356 
enc_get_jpeg_dma_sg(struct solo_dev * solo_dev,struct p2m_desc * desc,struct scatterlist * sglist,int skip,unsigned int off,unsigned int size)357 static int enc_get_jpeg_dma_sg(struct solo_dev *solo_dev,
358 			       struct p2m_desc *desc,
359 			       struct scatterlist *sglist, int skip,
360 			       unsigned int off, unsigned int size)
361 {
362 	int ret;
363 
364 	if (off > SOLO_JPEG_EXT_SIZE(solo_dev))
365 		return -EINVAL;
366 
367 	if (off + size <= SOLO_JPEG_EXT_SIZE(solo_dev)) {
368 		return solo_p2m_dma_sg(solo_dev, SOLO_P2M_DMA_ID_JPEG,
369 				       desc, 0, sglist, skip,
370 				       SOLO_JPEG_EXT_ADDR(solo_dev) + off, size);
371 	}
372 
373 	/* Buffer wrap */
374 	ret = solo_p2m_dma_sg(solo_dev, SOLO_P2M_DMA_ID_JPEG, desc, 0,
375 			      sglist, skip, SOLO_JPEG_EXT_ADDR(solo_dev) + off,
376 			      SOLO_JPEG_EXT_SIZE(solo_dev) - off);
377 
378 	ret |= solo_p2m_dma_sg(solo_dev, SOLO_P2M_DMA_ID_JPEG, desc, 0,
379 			       sglist, skip + SOLO_JPEG_EXT_SIZE(solo_dev) - off,
380 			       SOLO_JPEG_EXT_ADDR(solo_dev),
381 			       size + off - SOLO_JPEG_EXT_SIZE(solo_dev));
382 
383 	return ret;
384 }
385 
386 /* Returns true of __chk is within the first __range bytes of __off */
387 #define OFF_IN_RANGE(__off, __range, __chk) \
388 	((__off <= __chk) && ((__off + __range) >= __chk))
389 
solo_jpeg_header(struct solo_enc_dev * solo_enc,struct videobuf_dmabuf * vbuf)390 static void solo_jpeg_header(struct solo_enc_dev *solo_enc,
391 			     struct videobuf_dmabuf *vbuf)
392 {
393 	struct scatterlist *sg;
394 	void *src = jpeg_header;
395 	size_t copied = 0;
396 	size_t to_copy = sizeof(jpeg_header);
397 
398 	for (sg = vbuf->sglist; sg && copied < to_copy; sg = sg_next(sg)) {
399 		size_t this_copy = min(sg_dma_len(sg),
400 				       (unsigned int)(to_copy - copied));
401 		u8 *p = sg_virt(sg);
402 
403 		memcpy(p, src + copied, this_copy);
404 
405 		if (OFF_IN_RANGE(copied, this_copy, SOF0_START + 5))
406 			p[(SOF0_START + 5) - copied] =
407 				0xff & (solo_enc->height >> 8);
408 		if (OFF_IN_RANGE(copied, this_copy, SOF0_START + 6))
409 			p[(SOF0_START + 6) - copied] = 0xff & solo_enc->height;
410 		if (OFF_IN_RANGE(copied, this_copy, SOF0_START + 7))
411 			p[(SOF0_START + 7) - copied] =
412 				0xff & (solo_enc->width >> 8);
413 		if (OFF_IN_RANGE(copied, this_copy, SOF0_START + 8))
414 			p[(SOF0_START + 8) - copied] = 0xff & solo_enc->width;
415 
416 		copied += this_copy;
417 	}
418 }
419 
solo_fill_jpeg(struct solo_enc_fh * fh,struct solo_enc_buf * enc_buf,struct videobuf_buffer * vb,struct videobuf_dmabuf * vbuf)420 static int solo_fill_jpeg(struct solo_enc_fh *fh, struct solo_enc_buf *enc_buf,
421 			  struct videobuf_buffer *vb,
422 			  struct videobuf_dmabuf *vbuf)
423 {
424 	struct solo_dev *solo_dev = fh->enc->solo_dev;
425 	int size = enc_buf->jpeg_size;
426 
427 	/* Copy the header first (direct write) */
428 	solo_jpeg_header(fh->enc, vbuf);
429 
430 	vb->size = size + sizeof(jpeg_header);
431 
432 	/* Grab the jpeg frame */
433 	return enc_get_jpeg_dma_sg(solo_dev, fh->desc, vbuf->sglist,
434 				   sizeof(jpeg_header),
435 				   enc_buf->jpeg_off, size);
436 }
437 
vop_interlaced(__le32 * vh)438 static inline int vop_interlaced(__le32 *vh)
439 {
440 	return (__le32_to_cpu(vh[0]) >> 30) & 1;
441 }
442 
vop_size(__le32 * vh)443 static inline u32 vop_size(__le32 *vh)
444 {
445 	return __le32_to_cpu(vh[0]) & 0xFFFFF;
446 }
447 
vop_hsize(__le32 * vh)448 static inline u8 vop_hsize(__le32 *vh)
449 {
450 	return (__le32_to_cpu(vh[1]) >> 8) & 0xFF;
451 }
452 
vop_vsize(__le32 * vh)453 static inline u8 vop_vsize(__le32 *vh)
454 {
455 	return __le32_to_cpu(vh[1]) & 0xFF;
456 }
457 
458 /* must be called with *bits % 8 = 0 */
write_bytes(u8 ** out,unsigned * bits,const u8 * src,unsigned count)459 static void write_bytes(u8 **out, unsigned *bits, const u8 *src, unsigned count)
460 {
461 	memcpy(*out, src, count);
462 	*out += count;
463 	*bits += count * 8;
464 }
465 
write_bits(u8 ** out,unsigned * bits,u32 value,unsigned count)466 static void write_bits(u8 **out, unsigned *bits, u32 value, unsigned count)
467 {
468 
469 	value <<= 32 - count; // shift to the right
470 
471 	while (count--) {
472 		**out <<= 1;
473 		**out |= !!(value & (1 << 31)); /* MSB */
474 		value <<= 1;
475 		if (++(*bits) % 8 == 0)
476 			(*out)++;
477 	}
478 }
479 
write_ue(u8 ** out,unsigned * bits,unsigned value)480 static void write_ue(u8 **out, unsigned *bits, unsigned value) /* H.264 only */
481 {
482 	uint32_t max = 0, cnt = 0;
483 
484 	while (value > max) {
485 		max = (max + 2) * 2 - 2;
486 		cnt++;
487 	}
488 	write_bits(out, bits, 1, cnt + 1);
489 	write_bits(out, bits, ~(max - value), cnt);
490 }
491 
write_se(u8 ** out,unsigned * bits,int value)492 static void write_se(u8 **out, unsigned *bits, int value) /* H.264 only */
493 {
494 	if (value <= 0)
495 		write_ue(out, bits, -value * 2);
496 	else
497 		write_ue(out, bits, value * 2 - 1);
498 }
499 
write_mpeg4_end(u8 ** out,unsigned * bits)500 static void write_mpeg4_end(u8 **out, unsigned *bits)
501 {
502 	write_bits(out, bits, 0, 1);
503 	/* align on 32-bit boundary */
504 	if (*bits % 32)
505 		write_bits(out, bits, 0xFFFFFFFF, 32 - *bits % 32);
506 }
507 
write_h264_end(u8 ** out,unsigned * bits,int align)508 static void write_h264_end(u8 **out, unsigned *bits, int align)
509 {
510 	write_bits(out, bits, 1, 1);
511 	while ((*bits) % 8)
512 		write_bits(out, bits, 0, 1);
513 	if (align)
514 		while ((*bits) % 32)
515 			write_bits(out, bits, 0, 1);
516 }
517 
mpeg4_write_vol(u8 ** out,struct solo_dev * solo_dev,__le32 * vh,unsigned fps,unsigned interval)518 static void mpeg4_write_vol(u8 **out, struct solo_dev *solo_dev,
519 			    __le32 *vh, unsigned fps, unsigned interval)
520 {
521 	static const u8 hdr[] = {
522 		0, 0, 1, 0x00 /* video_object_start_code */,
523 		0, 0, 1, 0x20 /* video_object_layer_start_code */
524 	};
525 	unsigned bits = 0;
526 	unsigned width = vop_hsize(vh) << 4;
527 	unsigned height = vop_vsize(vh) << 4;
528 	unsigned interlaced = vop_interlaced(vh);
529 
530 	write_bytes(out, &bits, hdr, sizeof(hdr));
531 	write_bits(out, &bits,    0,  1); /* random_accessible_vol */
532 	write_bits(out, &bits, 0x04,  8); /* video_object_type_indication: main */
533 	write_bits(out, &bits,    1,  1); /* is_object_layer_identifier */
534 	write_bits(out, &bits,    2,  4); /* video_object_layer_verid: table V2-39 */
535 	write_bits(out, &bits,    0,  3); /* video_object_layer_priority */
536 	if (solo_dev->video_type == SOLO_VO_FMT_TYPE_NTSC)
537 		write_bits(out, &bits,  3,  4); /* aspect_ratio_info, assuming 4:3 */
538 	else
539 		write_bits(out, &bits,  2,  4);
540 	write_bits(out, &bits,    1,  1); /* vol_control_parameters */
541 	write_bits(out, &bits,    1,  2); /* chroma_format: 4:2:0 */
542 	write_bits(out, &bits,    1,  1); /* low_delay */
543 	write_bits(out, &bits,    0,  1); /* vbv_parameters */
544 	write_bits(out, &bits,    0,  2); /* video_object_layer_shape: rectangular */
545 	write_bits(out, &bits,    1,  1); /* marker_bit */
546 	write_bits(out, &bits,  fps, 16); /* vop_time_increment_resolution */
547 	write_bits(out, &bits,    1,  1); /* marker_bit */
548 	write_bits(out, &bits,    1,  1); /* fixed_vop_rate */
549 	write_bits(out, &bits, interval, 15); /* fixed_vop_time_increment */
550 	write_bits(out, &bits,    1,  1); /* marker_bit */
551 	write_bits(out, &bits, width, 13); /* video_object_layer_width */
552 	write_bits(out, &bits,    1,  1); /* marker_bit */
553 	write_bits(out, &bits, height, 13); /* video_object_layer_height */
554 	write_bits(out, &bits,    1,  1); /* marker_bit */
555 	write_bits(out, &bits, interlaced, 1); /* interlaced */
556 	write_bits(out, &bits,    1,  1); /* obmc_disable */
557 	write_bits(out, &bits,    0,  2); /* sprite_enable */
558 	write_bits(out, &bits,    0,  1); /* not_8_bit */
559 	write_bits(out, &bits,    1,  0); /* quant_type */
560 	write_bits(out, &bits,    0,  1); /* load_intra_quant_mat */
561 	write_bits(out, &bits,    0,  1); /* load_nonintra_quant_mat */
562 	write_bits(out, &bits,    0,  1); /* quarter_sample */
563 	write_bits(out, &bits,    1,  1); /* complexity_estimation_disable */
564 	write_bits(out, &bits,    1,  1); /* resync_marker_disable */
565 	write_bits(out, &bits,    0,  1); /* data_partitioned */
566 	write_bits(out, &bits,    0,  1); /* newpred_enable */
567 	write_bits(out, &bits,    0,  1); /* reduced_resolution_vop_enable */
568 	write_bits(out, &bits,    0,  1); /* scalability */
569 	write_mpeg4_end(out, &bits);
570 }
571 
h264_write_vol(u8 ** out,struct solo_dev * solo_dev,__le32 * vh)572 static void h264_write_vol(u8 **out, struct solo_dev *solo_dev, __le32 *vh)
573 {
574 	static const u8 sps[] = {
575 		0, 0, 0, 1 /* start code */, 0x67, 66 /* profile_idc */,
576 		0 /* constraints */, 30 /* level_idc */
577 	};
578 	static const u8 pps[] = {
579 		0, 0, 0, 1 /* start code */, 0x68
580 	};
581 
582 	unsigned bits = 0;
583 	unsigned mbs_w = vop_hsize(vh);
584 	unsigned mbs_h = vop_vsize(vh);
585 
586 	write_bytes(out, &bits, sps, sizeof(sps));
587 	write_ue(out, &bits,   0);	/* seq_parameter_set_id */
588 	write_ue(out, &bits,   5);	/* log2_max_frame_num_minus4 */
589 	write_ue(out, &bits,   0);	/* pic_order_cnt_type */
590 	write_ue(out, &bits,   6);	/* log2_max_pic_order_cnt_lsb_minus4 */
591 	write_ue(out, &bits,   1);	/* max_num_ref_frames */
592 	write_bits(out, &bits, 0, 1);	/* gaps_in_frame_num_value_allowed_flag */
593 	write_ue(out, &bits, mbs_w - 1);	/* pic_width_in_mbs_minus1 */
594 	write_ue(out, &bits, mbs_h - 1);	/* pic_height_in_map_units_minus1 */
595 	write_bits(out, &bits, 1, 1);	/* frame_mbs_only_flag */
596 	write_bits(out, &bits, 1, 1);	/* direct_8x8_frame_field_flag */
597 	write_bits(out, &bits, 0, 1);	/* frame_cropping_flag */
598 	write_bits(out, &bits, 0, 1);	/* vui_parameters_present_flag */
599 	write_h264_end(out, &bits, 0);
600 
601 	write_bytes(out, &bits, pps, sizeof(pps));
602 	write_ue(out, &bits,   0);	/* pic_parameter_set_id */
603 	write_ue(out, &bits,   0);	/* seq_parameter_set_id */
604 	write_bits(out, &bits, 0, 1);	/* entropy_coding_mode_flag */
605 	write_bits(out, &bits, 0, 1);	/* bottom_field_pic_order_in_frame_present_flag */
606 	write_ue(out, &bits,   0);	/* num_slice_groups_minus1 */
607 	write_ue(out, &bits,   0);	/* num_ref_idx_l0_default_active_minus1 */
608 	write_ue(out, &bits,   0);	/* num_ref_idx_l1_default_active_minus1 */
609 	write_bits(out, &bits, 0, 1);	/* weighted_pred_flag */
610 	write_bits(out, &bits, 0, 2);	/* weighted_bipred_idc */
611 	write_se(out, &bits,   0);	/* pic_init_qp_minus26 */
612 	write_se(out, &bits,   0);	/* pic_init_qs_minus26 */
613 	write_se(out, &bits,   2);	/* chroma_qp_index_offset */
614 	write_bits(out, &bits, 0, 1);	/* deblocking_filter_control_present_flag */
615 	write_bits(out, &bits, 1, 1);	/* constrained_intra_pred_flag */
616 	write_bits(out, &bits, 0, 1);	/* redundant_pic_cnt_present_flag */
617 	write_h264_end(out, &bits, 1);
618 }
619 
solo_fill_mpeg(struct solo_enc_fh * fh,struct solo_enc_buf * enc_buf,struct videobuf_buffer * vb,struct videobuf_dmabuf * vbuf)620 static int solo_fill_mpeg(struct solo_enc_fh *fh, struct solo_enc_buf *enc_buf,
621 			  struct videobuf_buffer *vb,
622 			  struct videobuf_dmabuf *vbuf)
623 {
624 	struct solo_enc_dev *solo_enc = fh->enc;
625 	struct solo_dev *solo_dev = solo_enc->solo_dev;
626 
627 #define VH_WORDS 16
628 #define MAX_VOL_HEADER_LENGTH 64
629 
630 	__le32 vh[VH_WORDS];
631 	int ret;
632 	int frame_size, frame_off;
633 	int skip = 0;
634 
635 	if (WARN_ON_ONCE(enc_buf->size <= sizeof(vh)))
636 		return -EINVAL;
637 
638 	/* First get the hardware vop header (not real mpeg) */
639 	ret = enc_get_mpeg_dma(solo_dev, vh, enc_buf->off, sizeof(vh));
640 	if (WARN_ON_ONCE(ret))
641 		return ret;
642 
643 	if (WARN_ON_ONCE(vop_size(vh) > enc_buf->size))
644 		return -EINVAL;
645 
646 	vb->width = vop_hsize(vh) << 4;
647 	vb->height = vop_vsize(vh) << 4;
648 	vb->size = vop_size(vh);
649 
650 	/* If this is a key frame, add extra m4v header */
651 	if (!enc_buf->vop) {
652 		u8 header[MAX_VOL_HEADER_LENGTH], *out = header;
653 
654 		if (solo_dev->flags & FLAGS_6110)
655 			h264_write_vol(&out, solo_dev, vh);
656 		else
657 			mpeg4_write_vol(&out, solo_dev, vh,
658 					solo_dev->fps * 1000,
659 					solo_enc->interval * 1000);
660 		skip = out - header;
661 		enc_write_sg(vbuf->sglist, header, skip);
662 		/* Adjust the dma buffer past this header */
663 		vb->size += skip;
664 	}
665 
666 	/* Now get the actual mpeg payload */
667 	frame_off = (enc_buf->off + sizeof(vh)) % SOLO_MP4E_EXT_SIZE(solo_dev);
668 	frame_size = enc_buf->size - sizeof(vh);
669 
670 	ret = enc_get_mpeg_dma_sg(solo_dev, fh->desc, vbuf->sglist,
671 				  skip, frame_off, frame_size);
672 	WARN_ON_ONCE(ret);
673 
674 	return ret;
675 }
676 
solo_enc_fillbuf(struct solo_enc_fh * fh,struct videobuf_buffer * vb)677 static void solo_enc_fillbuf(struct solo_enc_fh *fh,
678 			    struct videobuf_buffer *vb)
679 {
680 	struct solo_enc_dev *solo_enc = fh->enc;
681 	struct solo_dev *solo_dev = solo_enc->solo_dev;
682 	struct solo_enc_buf *enc_buf = NULL;
683 	struct videobuf_dmabuf *vbuf;
684 	int ret;
685 	int error = 1;
686 	u16 idx = fh->rd_idx;
687 
688 	while (idx != solo_dev->enc_wr_idx) {
689 		struct solo_enc_buf *ebuf = &solo_dev->enc_buf[idx];
690 
691 		idx = (idx + 1) % SOLO_NR_RING_BUFS;
692 
693 		if (ebuf->ch != solo_enc->ch)
694 			continue;
695 
696 		if (fh->fmt == V4L2_PIX_FMT_MPEG) {
697 			if (fh->type == ebuf->type) {
698 				enc_buf = ebuf;
699 				break;
700 			}
701 		} else {
702 			/* For mjpeg, keep reading to the newest frame */
703 			enc_buf = ebuf;
704 		}
705 	}
706 
707 	fh->rd_idx = idx;
708 
709 	if (WARN_ON_ONCE(!enc_buf))
710 		goto buf_err;
711 
712 	if ((fh->fmt == V4L2_PIX_FMT_MPEG &&
713 	     vb->bsize < enc_buf->size) ||
714 	    (fh->fmt == V4L2_PIX_FMT_MJPEG &&
715 	     vb->bsize < (enc_buf->jpeg_size + sizeof(jpeg_header)))) {
716 		WARN_ON_ONCE(1);
717 		goto buf_err;
718 	}
719 
720 	vbuf = videobuf_to_dma(vb);
721 	if (WARN_ON_ONCE(!vbuf))
722 		goto buf_err;
723 
724 	if (fh->fmt == V4L2_PIX_FMT_MPEG)
725 		ret = solo_fill_mpeg(fh, enc_buf, vb, vbuf);
726 	else
727 		ret = solo_fill_jpeg(fh, enc_buf, vb, vbuf);
728 
729 	if (!ret)
730 		error = 0;
731 
732 buf_err:
733 	if (error) {
734 		vb->state = VIDEOBUF_ERROR;
735 	} else {
736 		vb->field_count++;
737 		vb->ts = enc_buf->ts;
738 		vb->state = VIDEOBUF_DONE;
739 	}
740 
741 	wake_up(&vb->done);
742 
743 	return;
744 }
745 
solo_enc_thread_try(struct solo_enc_fh * fh)746 static void solo_enc_thread_try(struct solo_enc_fh *fh)
747 {
748 	struct solo_enc_dev *solo_enc = fh->enc;
749 	struct solo_dev *solo_dev = solo_enc->solo_dev;
750 	struct videobuf_buffer *vb;
751 
752 	for (;;) {
753 		spin_lock(&solo_enc->lock);
754 
755 		if (fh->rd_idx == solo_dev->enc_wr_idx)
756 			break;
757 
758 		if (list_empty(&fh->vidq_active))
759 			break;
760 
761 		vb = list_first_entry(&fh->vidq_active,
762 				      struct videobuf_buffer, queue);
763 
764 		if (!waitqueue_active(&vb->done))
765 			break;
766 
767 		list_del(&vb->queue);
768 
769 		spin_unlock(&solo_enc->lock);
770 
771 		solo_enc_fillbuf(fh, vb);
772 	}
773 
774 	assert_spin_locked(&solo_enc->lock);
775 	spin_unlock(&solo_enc->lock);
776 }
777 
solo_enc_thread(void * data)778 static int solo_enc_thread(void *data)
779 {
780 	struct solo_enc_fh *fh = data;
781 	struct solo_enc_dev *solo_enc = fh->enc;
782 	DECLARE_WAITQUEUE(wait, current);
783 
784 	set_freezable();
785 	add_wait_queue(&solo_enc->thread_wait, &wait);
786 
787 	for (;;) {
788 		long timeout = schedule_timeout_interruptible(HZ);
789 		if (timeout == -ERESTARTSYS || kthread_should_stop())
790 			break;
791 		solo_enc_thread_try(fh);
792 		try_to_freeze();
793 	}
794 
795 	remove_wait_queue(&solo_enc->thread_wait, &wait);
796 
797 	return 0;
798 }
799 
solo_motion_isr(struct solo_dev * solo_dev)800 void solo_motion_isr(struct solo_dev *solo_dev)
801 {
802 	u32 status;
803 	int i;
804 
805 	solo_reg_write(solo_dev, SOLO_IRQ_STAT, SOLO_IRQ_MOTION);
806 
807 	status = solo_reg_read(solo_dev, SOLO_VI_MOT_STATUS);
808 
809 	for (i = 0; i < solo_dev->nr_chans; i++) {
810 		struct solo_enc_dev *solo_enc = solo_dev->v4l2_enc[i];
811 
812 		BUG_ON(solo_enc == NULL);
813 
814 		if (solo_enc->motion_detected)
815 			continue;
816 		if (!(status & (1 << i)))
817 			continue;
818 
819 		solo_enc->motion_detected = 1;
820 	}
821 }
822 
solo_enc_v4l2_isr(struct solo_dev * solo_dev)823 void solo_enc_v4l2_isr(struct solo_dev *solo_dev)
824 {
825 	struct solo_enc_buf *enc_buf;
826 	u32 mpeg_current, mpeg_next, mpeg_size;
827 	u32 jpeg_current, jpeg_next, jpeg_size;
828 	u32 reg_mpeg_size;
829 	u8 cur_q, vop_type;
830 	u8 ch;
831 	enum solo_enc_types enc_type;
832 
833 	solo_reg_write(solo_dev, SOLO_IRQ_STAT, SOLO_IRQ_ENCODER);
834 
835 	cur_q = ((solo_reg_read(solo_dev, SOLO_VE_STATE(11)) & 0xF) + 1) % MP4_QS;
836 
837 	reg_mpeg_size = ((solo_reg_read(solo_dev, SOLO_VE_STATE(0)) & 0xFFFFF) + 64 + 8) & ~7;
838 
839 	while (solo_dev->enc_idx != cur_q) {
840 		mpeg_current = solo_reg_read(solo_dev,
841 					SOLO_VE_MPEG4_QUE(solo_dev->enc_idx));
842 		jpeg_current = solo_reg_read(solo_dev,
843 					SOLO_VE_JPEG_QUE(solo_dev->enc_idx));
844 		solo_dev->enc_idx = (solo_dev->enc_idx + 1) % MP4_QS;
845 		mpeg_next = solo_reg_read(solo_dev,
846 					SOLO_VE_MPEG4_QUE(solo_dev->enc_idx));
847 		jpeg_next = solo_reg_read(solo_dev,
848 					SOLO_VE_JPEG_QUE(solo_dev->enc_idx));
849 
850 		ch = (mpeg_current >> 24) & 0x1f;
851 		if (ch >= SOLO_MAX_CHANNELS) {
852 			ch -= SOLO_MAX_CHANNELS;
853 			enc_type = SOLO_ENC_TYPE_EXT;
854 		} else
855 			enc_type = SOLO_ENC_TYPE_STD;
856 
857 		vop_type = (mpeg_current >> 29) & 3;
858 
859 		mpeg_current &= 0x00ffffff;
860 		mpeg_next    &= 0x00ffffff;
861 		jpeg_current &= 0x00ffffff;
862 		jpeg_next    &= 0x00ffffff;
863 
864 		mpeg_size = (SOLO_MP4E_EXT_SIZE(solo_dev) +
865 			     mpeg_next - mpeg_current) %
866 			    SOLO_MP4E_EXT_SIZE(solo_dev);
867 
868 		jpeg_size = (SOLO_JPEG_EXT_SIZE(solo_dev) +
869 			     jpeg_next - jpeg_current) %
870 			    SOLO_JPEG_EXT_SIZE(solo_dev);
871 
872 		/* XXX I think this means we had a ring overflow? */
873 		if (mpeg_current > mpeg_next && mpeg_size != reg_mpeg_size) {
874 			enc_reset_gop(solo_dev, ch);
875 			continue;
876 		}
877 
878 		/* When resetting the GOP, skip frames until I-frame */
879 		if (enc_gop_reset(solo_dev, ch, vop_type))
880 			continue;
881 
882 		enc_buf = &solo_dev->enc_buf[solo_dev->enc_wr_idx];
883 
884 		enc_buf->vop = vop_type;
885 		enc_buf->ch = ch;
886 		enc_buf->off = mpeg_current;
887 		enc_buf->size = mpeg_size;
888 		enc_buf->jpeg_off = jpeg_current;
889 		enc_buf->jpeg_size = jpeg_size;
890 		enc_buf->type = enc_type;
891 
892 		do_gettimeofday(&enc_buf->ts);
893 
894 		solo_dev->enc_wr_idx = (solo_dev->enc_wr_idx + 1) %
895 					SOLO_NR_RING_BUFS;
896 
897 		wake_up_interruptible(&solo_dev->v4l2_enc[ch]->thread_wait);
898 	}
899 
900 	return;
901 }
902 
solo_enc_buf_setup(struct videobuf_queue * vq,unsigned int * count,unsigned int * size)903 static int solo_enc_buf_setup(struct videobuf_queue *vq, unsigned int *count,
904 			      unsigned int *size)
905 {
906 	*size = FRAME_BUF_SIZE;
907 
908 	if (*count < MIN_VID_BUFFERS)
909 		*count = MIN_VID_BUFFERS;
910 
911 	return 0;
912 }
913 
solo_enc_buf_prepare(struct videobuf_queue * vq,struct videobuf_buffer * vb,enum v4l2_field field)914 static int solo_enc_buf_prepare(struct videobuf_queue *vq,
915 				struct videobuf_buffer *vb,
916 				enum v4l2_field field)
917 {
918 	struct solo_enc_fh *fh = vq->priv_data;
919 	struct solo_enc_dev *solo_enc = fh->enc;
920 
921 	vb->size = FRAME_BUF_SIZE;
922 	if (vb->baddr != 0 && vb->bsize < vb->size)
923 		return -EINVAL;
924 
925 	/* These properties only change when queue is idle */
926 	vb->width = solo_enc->width;
927 	vb->height = solo_enc->height;
928 	vb->field  = field;
929 
930 	if (vb->state == VIDEOBUF_NEEDS_INIT) {
931 		int rc = videobuf_iolock(vq, vb, NULL);
932 		if (rc < 0) {
933 			struct videobuf_dmabuf *dma = videobuf_to_dma(vb);
934 			videobuf_dma_unmap(vq->dev, dma);
935 			videobuf_dma_free(dma);
936 			vb->state = VIDEOBUF_NEEDS_INIT;
937 			return rc;
938 		}
939 	}
940 	vb->state = VIDEOBUF_PREPARED;
941 
942 	return 0;
943 }
944 
solo_enc_buf_queue(struct videobuf_queue * vq,struct videobuf_buffer * vb)945 static void solo_enc_buf_queue(struct videobuf_queue *vq,
946 			       struct videobuf_buffer *vb)
947 {
948 	struct solo_enc_fh *fh = vq->priv_data;
949 
950 	vb->state = VIDEOBUF_QUEUED;
951 	list_add_tail(&vb->queue, &fh->vidq_active);
952 	wake_up_interruptible(&fh->enc->thread_wait);
953 }
954 
solo_enc_buf_release(struct videobuf_queue * vq,struct videobuf_buffer * vb)955 static void solo_enc_buf_release(struct videobuf_queue *vq,
956 				 struct videobuf_buffer *vb)
957 {
958 	struct videobuf_dmabuf *dma = videobuf_to_dma(vb);
959 
960 	videobuf_dma_unmap(vq->dev, dma);
961 	videobuf_dma_free(dma);
962 	vb->state = VIDEOBUF_NEEDS_INIT;
963 }
964 
965 static struct videobuf_queue_ops solo_enc_video_qops = {
966 	.buf_setup	= solo_enc_buf_setup,
967 	.buf_prepare	= solo_enc_buf_prepare,
968 	.buf_queue	= solo_enc_buf_queue,
969 	.buf_release	= solo_enc_buf_release,
970 };
971 
solo_enc_poll(struct file * file,struct poll_table_struct * wait)972 static unsigned int solo_enc_poll(struct file *file,
973 				  struct poll_table_struct *wait)
974 {
975 	struct solo_enc_fh *fh = file->private_data;
976 
977 	return videobuf_poll_stream(file, &fh->vidq, wait);
978 }
979 
solo_enc_mmap(struct file * file,struct vm_area_struct * vma)980 static int solo_enc_mmap(struct file *file, struct vm_area_struct *vma)
981 {
982 	struct solo_enc_fh *fh = file->private_data;
983 
984 	return videobuf_mmap_mapper(&fh->vidq, vma);
985 }
986 
solo_enc_open(struct file * file)987 static int solo_enc_open(struct file *file)
988 {
989 	struct solo_enc_dev *solo_enc = video_drvdata(file);
990 	struct solo_enc_fh *fh;
991 
992 	fh = kzalloc(sizeof(*fh), GFP_KERNEL);
993 	if (fh == NULL)
994 		return -ENOMEM;
995 
996 	fh->enc = solo_enc;
997 	file->private_data = fh;
998 	INIT_LIST_HEAD(&fh->vidq_active);
999 	fh->fmt = V4L2_PIX_FMT_MPEG;
1000 	fh->type = SOLO_ENC_TYPE_STD;
1001 
1002 	videobuf_queue_sg_init(&fh->vidq, &solo_enc_video_qops,
1003 			       &solo_enc->solo_dev->pdev->dev,
1004 			       &solo_enc->lock,
1005 			       V4L2_BUF_TYPE_VIDEO_CAPTURE,
1006 			       V4L2_FIELD_INTERLACED,
1007 			       sizeof(struct videobuf_buffer), fh, NULL);
1008 
1009 	return 0;
1010 }
1011 
solo_enc_read(struct file * file,char __user * data,size_t count,loff_t * ppos)1012 static ssize_t solo_enc_read(struct file *file, char __user *data,
1013 			     size_t count, loff_t *ppos)
1014 {
1015 	struct solo_enc_fh *fh = file->private_data;
1016 	struct solo_enc_dev *solo_enc = fh->enc;
1017 
1018 	/* Make sure the encoder is on */
1019 	if (!fh->enc_on) {
1020 		int ret;
1021 
1022 		spin_lock(&solo_enc->lock);
1023 		ret = solo_enc_on(fh);
1024 		spin_unlock(&solo_enc->lock);
1025 		if (ret)
1026 			return ret;
1027 
1028 		ret = solo_start_fh_thread(fh);
1029 		if (ret)
1030 			return ret;
1031 	}
1032 
1033 	return videobuf_read_stream(&fh->vidq, data, count, ppos, 0,
1034 				    file->f_flags & O_NONBLOCK);
1035 }
1036 
solo_enc_release(struct file * file)1037 static int solo_enc_release(struct file *file)
1038 {
1039 	struct solo_enc_fh *fh = file->private_data;
1040 	struct solo_enc_dev *solo_enc = fh->enc;
1041 
1042 	videobuf_stop(&fh->vidq);
1043 	videobuf_mmap_free(&fh->vidq);
1044 
1045 	spin_lock(&solo_enc->lock);
1046 	solo_enc_off(fh);
1047 	spin_unlock(&solo_enc->lock);
1048 
1049 	kfree(fh);
1050 
1051 	return 0;
1052 }
1053 
solo_enc_querycap(struct file * file,void * priv,struct v4l2_capability * cap)1054 static int solo_enc_querycap(struct file *file, void  *priv,
1055 			     struct v4l2_capability *cap)
1056 {
1057 	struct solo_enc_fh *fh = priv;
1058 	struct solo_enc_dev *solo_enc = fh->enc;
1059 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1060 
1061 	strcpy(cap->driver, SOLO6X10_NAME);
1062 	snprintf(cap->card, sizeof(cap->card), "Softlogic 6x10 Enc %d",
1063 		 solo_enc->ch);
1064 	snprintf(cap->bus_info, sizeof(cap->bus_info), "PCI %s",
1065 		 pci_name(solo_dev->pdev));
1066 	cap->version = SOLO6X10_VER_NUM;
1067 	cap->capabilities =     V4L2_CAP_VIDEO_CAPTURE |
1068 				V4L2_CAP_READWRITE |
1069 				V4L2_CAP_STREAMING;
1070 	return 0;
1071 }
1072 
solo_enc_enum_input(struct file * file,void * priv,struct v4l2_input * input)1073 static int solo_enc_enum_input(struct file *file, void *priv,
1074 			       struct v4l2_input *input)
1075 {
1076 	struct solo_enc_fh *fh = priv;
1077 	struct solo_enc_dev *solo_enc = fh->enc;
1078 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1079 
1080 	if (input->index)
1081 		return -EINVAL;
1082 
1083 	snprintf(input->name, sizeof(input->name), "Encoder %d",
1084 		 solo_enc->ch + 1);
1085 	input->type = V4L2_INPUT_TYPE_CAMERA;
1086 
1087 	if (solo_dev->video_type == SOLO_VO_FMT_TYPE_NTSC)
1088 		input->std = V4L2_STD_NTSC_M;
1089 	else
1090 		input->std = V4L2_STD_PAL_B;
1091 
1092 	if (!tw28_get_video_status(solo_dev, solo_enc->ch))
1093 		input->status = V4L2_IN_ST_NO_SIGNAL;
1094 
1095 	return 0;
1096 }
1097 
solo_enc_set_input(struct file * file,void * priv,unsigned int index)1098 static int solo_enc_set_input(struct file *file, void *priv, unsigned int index)
1099 {
1100 	if (index)
1101 		return -EINVAL;
1102 
1103 	return 0;
1104 }
1105 
solo_enc_get_input(struct file * file,void * priv,unsigned int * index)1106 static int solo_enc_get_input(struct file *file, void *priv,
1107 			      unsigned int *index)
1108 {
1109 	*index = 0;
1110 
1111 	return 0;
1112 }
1113 
solo_enc_enum_fmt_cap(struct file * file,void * priv,struct v4l2_fmtdesc * f)1114 static int solo_enc_enum_fmt_cap(struct file *file, void *priv,
1115 				 struct v4l2_fmtdesc *f)
1116 {
1117 	switch (f->index) {
1118 	case 0:
1119 		f->pixelformat = V4L2_PIX_FMT_MPEG;
1120 		strcpy(f->description, "MPEG-4 AVC");
1121 		break;
1122 	case 1:
1123 		f->pixelformat = V4L2_PIX_FMT_MJPEG;
1124 		strcpy(f->description, "MJPEG");
1125 		break;
1126 	default:
1127 		return -EINVAL;
1128 	}
1129 
1130 	f->flags = V4L2_FMT_FLAG_COMPRESSED;
1131 
1132 	return 0;
1133 }
1134 
solo_enc_try_fmt_cap(struct file * file,void * priv,struct v4l2_format * f)1135 static int solo_enc_try_fmt_cap(struct file *file, void *priv,
1136 			    struct v4l2_format *f)
1137 {
1138 	struct solo_enc_fh *fh = priv;
1139 	struct solo_enc_dev *solo_enc = fh->enc;
1140 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1141 	struct v4l2_pix_format *pix = &f->fmt.pix;
1142 
1143 	if (pix->pixelformat != V4L2_PIX_FMT_MPEG &&
1144 	    pix->pixelformat != V4L2_PIX_FMT_MJPEG)
1145 		return -EINVAL;
1146 
1147 	/* We cannot change width/height in mid read */
1148 	if (atomic_read(&solo_enc->readers) > 0) {
1149 		if (pix->width != solo_enc->width ||
1150 		    pix->height != solo_enc->height)
1151 			return -EBUSY;
1152 	}
1153 
1154 	if (pix->width < solo_dev->video_hsize ||
1155 	    pix->height < solo_dev->video_vsize << 1) {
1156 		/* Default to CIF 1/2 size */
1157 		pix->width = solo_dev->video_hsize >> 1;
1158 		pix->height = solo_dev->video_vsize;
1159 	} else {
1160 		/* Full frame */
1161 		pix->width = solo_dev->video_hsize;
1162 		pix->height = solo_dev->video_vsize << 1;
1163 	}
1164 
1165 	if (pix->field == V4L2_FIELD_ANY)
1166 		pix->field = V4L2_FIELD_INTERLACED;
1167 	else if (pix->field != V4L2_FIELD_INTERLACED)
1168 		pix->field = V4L2_FIELD_INTERLACED;
1169 
1170 	/* Just set these */
1171 	pix->colorspace = V4L2_COLORSPACE_SMPTE170M;
1172 	pix->sizeimage = FRAME_BUF_SIZE;
1173 
1174 	return 0;
1175 }
1176 
solo_enc_set_fmt_cap(struct file * file,void * priv,struct v4l2_format * f)1177 static int solo_enc_set_fmt_cap(struct file *file, void *priv,
1178 				struct v4l2_format *f)
1179 {
1180 	struct solo_enc_fh *fh = priv;
1181 	struct solo_enc_dev *solo_enc = fh->enc;
1182 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1183 	struct v4l2_pix_format *pix = &f->fmt.pix;
1184 	int ret;
1185 
1186 	spin_lock(&solo_enc->lock);
1187 
1188 	ret = solo_enc_try_fmt_cap(file, priv, f);
1189 	if (ret) {
1190 		spin_unlock(&solo_enc->lock);
1191 		return ret;
1192 	}
1193 
1194 	if (pix->width == solo_dev->video_hsize)
1195 		solo_enc->mode = SOLO_ENC_MODE_D1;
1196 	else
1197 		solo_enc->mode = SOLO_ENC_MODE_CIF;
1198 
1199 	/* This does not change the encoder at all */
1200 	fh->fmt = pix->pixelformat;
1201 
1202 	if (pix->priv)
1203 		fh->type = SOLO_ENC_TYPE_EXT;
1204 	ret = solo_enc_on(fh);
1205 
1206 	spin_unlock(&solo_enc->lock);
1207 
1208 	if (ret)
1209 		return ret;
1210 
1211 	return solo_start_fh_thread(fh);
1212 }
1213 
solo_enc_get_fmt_cap(struct file * file,void * priv,struct v4l2_format * f)1214 static int solo_enc_get_fmt_cap(struct file *file, void *priv,
1215 				struct v4l2_format *f)
1216 {
1217 	struct solo_enc_fh *fh = priv;
1218 	struct solo_enc_dev *solo_enc = fh->enc;
1219 	struct v4l2_pix_format *pix = &f->fmt.pix;
1220 
1221 	pix->width = solo_enc->width;
1222 	pix->height = solo_enc->height;
1223 	pix->pixelformat = fh->fmt;
1224 	pix->field = solo_enc->interlaced ? V4L2_FIELD_INTERLACED :
1225 		     V4L2_FIELD_NONE;
1226 	pix->sizeimage = FRAME_BUF_SIZE;
1227 	pix->colorspace = V4L2_COLORSPACE_SMPTE170M;
1228 
1229 	return 0;
1230 }
1231 
solo_enc_reqbufs(struct file * file,void * priv,struct v4l2_requestbuffers * req)1232 static int solo_enc_reqbufs(struct file *file, void *priv,
1233 			    struct v4l2_requestbuffers *req)
1234 {
1235 	struct solo_enc_fh *fh = priv;
1236 
1237 	return videobuf_reqbufs(&fh->vidq, req);
1238 }
1239 
solo_enc_querybuf(struct file * file,void * priv,struct v4l2_buffer * buf)1240 static int solo_enc_querybuf(struct file *file, void *priv,
1241 			     struct v4l2_buffer *buf)
1242 {
1243 	struct solo_enc_fh *fh = priv;
1244 
1245 	return videobuf_querybuf(&fh->vidq, buf);
1246 }
1247 
solo_enc_qbuf(struct file * file,void * priv,struct v4l2_buffer * buf)1248 static int solo_enc_qbuf(struct file *file, void *priv, struct v4l2_buffer *buf)
1249 {
1250 	struct solo_enc_fh *fh = priv;
1251 
1252 	return videobuf_qbuf(&fh->vidq, buf);
1253 }
1254 
solo_enc_dqbuf(struct file * file,void * priv,struct v4l2_buffer * buf)1255 static int solo_enc_dqbuf(struct file *file, void *priv,
1256 			  struct v4l2_buffer *buf)
1257 {
1258 	struct solo_enc_fh *fh = priv;
1259 	struct solo_enc_dev *solo_enc = fh->enc;
1260 	int ret;
1261 
1262 	/* Make sure the encoder is on */
1263 	if (!fh->enc_on) {
1264 		spin_lock(&solo_enc->lock);
1265 		ret = solo_enc_on(fh);
1266 		spin_unlock(&solo_enc->lock);
1267 		if (ret)
1268 			return ret;
1269 
1270 		ret = solo_start_fh_thread(fh);
1271 		if (ret)
1272 			return ret;
1273 	}
1274 
1275 	ret = videobuf_dqbuf(&fh->vidq, buf, file->f_flags & O_NONBLOCK);
1276 	if (ret)
1277 		return ret;
1278 
1279 	/* Signal motion detection */
1280 	if (solo_is_motion_on(solo_enc)) {
1281 		buf->flags |= V4L2_BUF_FLAG_MOTION_ON;
1282 		if (solo_enc->motion_detected) {
1283 			buf->flags |= V4L2_BUF_FLAG_MOTION_DETECTED;
1284 			solo_reg_write(solo_enc->solo_dev, SOLO_VI_MOT_CLEAR,
1285 				       1 << solo_enc->ch);
1286 			solo_enc->motion_detected = 0;
1287 		}
1288 	}
1289 
1290 	/* Check for key frame on mpeg data */
1291 	if (fh->fmt == V4L2_PIX_FMT_MPEG) {
1292 		struct videobuf_dmabuf *vbuf =
1293 				videobuf_to_dma(fh->vidq.bufs[buf->index]);
1294 
1295 		if (vbuf) {
1296 			u8 *p = sg_virt(vbuf->sglist);
1297 			if (p[3] == 0x00)
1298 				buf->flags |= V4L2_BUF_FLAG_KEYFRAME;
1299 			else
1300 				buf->flags |= V4L2_BUF_FLAG_PFRAME;
1301 		}
1302 	}
1303 
1304 	return 0;
1305 }
1306 
solo_enc_streamon(struct file * file,void * priv,enum v4l2_buf_type i)1307 static int solo_enc_streamon(struct file *file, void *priv,
1308 			     enum v4l2_buf_type i)
1309 {
1310 	struct solo_enc_fh *fh = priv;
1311 
1312 	if (i != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1313 		return -EINVAL;
1314 
1315 	return videobuf_streamon(&fh->vidq);
1316 }
1317 
solo_enc_streamoff(struct file * file,void * priv,enum v4l2_buf_type i)1318 static int solo_enc_streamoff(struct file *file, void *priv,
1319 			      enum v4l2_buf_type i)
1320 {
1321 	struct solo_enc_fh *fh = priv;
1322 
1323 	if (i != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1324 		return -EINVAL;
1325 
1326 	return videobuf_streamoff(&fh->vidq);
1327 }
1328 
solo_enc_s_std(struct file * file,void * priv,v4l2_std_id * i)1329 static int solo_enc_s_std(struct file *file, void *priv, v4l2_std_id *i)
1330 {
1331 	return 0;
1332 }
1333 
solo_enum_framesizes(struct file * file,void * priv,struct v4l2_frmsizeenum * fsize)1334 static int solo_enum_framesizes(struct file *file, void *priv,
1335 				struct v4l2_frmsizeenum *fsize)
1336 {
1337 	struct solo_enc_fh *fh = priv;
1338 	struct solo_dev *solo_dev = fh->enc->solo_dev;
1339 
1340 	if (fsize->pixel_format != V4L2_PIX_FMT_MPEG)
1341 		return -EINVAL;
1342 
1343 	switch (fsize->index) {
1344 	case 0:
1345 		fsize->discrete.width = solo_dev->video_hsize >> 1;
1346 		fsize->discrete.height = solo_dev->video_vsize;
1347 		break;
1348 	case 1:
1349 		fsize->discrete.width = solo_dev->video_hsize;
1350 		fsize->discrete.height = solo_dev->video_vsize << 1;
1351 		break;
1352 	default:
1353 		return -EINVAL;
1354 	}
1355 
1356 	fsize->type = V4L2_FRMSIZE_TYPE_DISCRETE;
1357 
1358 	return 0;
1359 }
1360 
solo_enum_frameintervals(struct file * file,void * priv,struct v4l2_frmivalenum * fintv)1361 static int solo_enum_frameintervals(struct file *file, void *priv,
1362 				    struct v4l2_frmivalenum *fintv)
1363 {
1364 	struct solo_enc_fh *fh = priv;
1365 	struct solo_dev *solo_dev = fh->enc->solo_dev;
1366 
1367 	if (fintv->pixel_format != V4L2_PIX_FMT_MPEG || fintv->index)
1368 		return -EINVAL;
1369 
1370 	fintv->type = V4L2_FRMIVAL_TYPE_STEPWISE;
1371 
1372 	fintv->stepwise.min.numerator = solo_dev->fps;
1373 	fintv->stepwise.min.denominator = 1;
1374 
1375 	fintv->stepwise.max.numerator = solo_dev->fps;
1376 	fintv->stepwise.max.denominator = 15;
1377 
1378 	fintv->stepwise.step.numerator = 1;
1379 	fintv->stepwise.step.denominator = 1;
1380 
1381 	return 0;
1382 }
1383 
solo_g_parm(struct file * file,void * priv,struct v4l2_streamparm * sp)1384 static int solo_g_parm(struct file *file, void *priv,
1385 		       struct v4l2_streamparm *sp)
1386 {
1387 	struct solo_enc_fh *fh = priv;
1388 	struct solo_enc_dev *solo_enc = fh->enc;
1389 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1390 	struct v4l2_captureparm *cp = &sp->parm.capture;
1391 
1392 	cp->capability = V4L2_CAP_TIMEPERFRAME;
1393 	cp->timeperframe.numerator = solo_enc->interval;
1394 	cp->timeperframe.denominator = solo_dev->fps;
1395 	cp->capturemode = 0;
1396 	/* XXX: Shouldn't we be able to get/set this from videobuf? */
1397 	cp->readbuffers = 2;
1398 
1399 	return 0;
1400 }
1401 
solo_s_parm(struct file * file,void * priv,struct v4l2_streamparm * sp)1402 static int solo_s_parm(struct file *file, void *priv,
1403 		       struct v4l2_streamparm *sp)
1404 {
1405 	struct solo_enc_fh *fh = priv;
1406 	struct solo_enc_dev *solo_enc = fh->enc;
1407 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1408 	struct v4l2_captureparm *cp = &sp->parm.capture;
1409 
1410 	spin_lock(&solo_enc->lock);
1411 
1412 	if (atomic_read(&solo_enc->readers) > 0) {
1413 		spin_unlock(&solo_enc->lock);
1414 		return -EBUSY;
1415 	}
1416 
1417 	if ((cp->timeperframe.numerator == 0) ||
1418 	    (cp->timeperframe.denominator == 0)) {
1419 		/* reset framerate */
1420 		cp->timeperframe.numerator = 1;
1421 		cp->timeperframe.denominator = solo_dev->fps;
1422 	}
1423 
1424 	if (cp->timeperframe.denominator != solo_dev->fps)
1425 		cp->timeperframe.denominator = solo_dev->fps;
1426 
1427 	if (cp->timeperframe.numerator > 15)
1428 		cp->timeperframe.numerator = 15;
1429 
1430 	solo_enc->interval = cp->timeperframe.numerator;
1431 
1432 	cp->capability = V4L2_CAP_TIMEPERFRAME;
1433 
1434 	solo_enc->gop = max(solo_dev->fps / solo_enc->interval, 1);
1435 	solo_update_mode(solo_enc);
1436 
1437 	spin_unlock(&solo_enc->lock);
1438 
1439 	return 0;
1440 }
1441 
solo_queryctrl(struct file * file,void * priv,struct v4l2_queryctrl * qc)1442 static int solo_queryctrl(struct file *file, void *priv,
1443 			  struct v4l2_queryctrl *qc)
1444 {
1445 	struct solo_enc_fh *fh = priv;
1446 	struct solo_enc_dev *solo_enc = fh->enc;
1447 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1448 
1449 	qc->id = v4l2_ctrl_next(solo_ctrl_classes, qc->id);
1450 	if (!qc->id)
1451 		return -EINVAL;
1452 
1453 	switch (qc->id) {
1454 	case V4L2_CID_BRIGHTNESS:
1455 	case V4L2_CID_CONTRAST:
1456 	case V4L2_CID_SATURATION:
1457 	case V4L2_CID_HUE:
1458 		return v4l2_ctrl_query_fill(qc, 0x00, 0xff, 1, 0x80);
1459 	case V4L2_CID_SHARPNESS:
1460 		return v4l2_ctrl_query_fill(qc, 0x00, 0x0f, 1, 0x00);
1461 	case V4L2_CID_MPEG_VIDEO_ENCODING:
1462 		return v4l2_ctrl_query_fill(
1463 			qc, V4L2_MPEG_VIDEO_ENCODING_MPEG_1,
1464 			V4L2_MPEG_VIDEO_ENCODING_MPEG_4_AVC, 1,
1465 			V4L2_MPEG_VIDEO_ENCODING_MPEG_4_AVC);
1466 	case V4L2_CID_MPEG_VIDEO_GOP_SIZE:
1467 		return v4l2_ctrl_query_fill(qc, 1, 255, 1, solo_dev->fps);
1468 #ifdef PRIVATE_CIDS
1469 	case V4L2_CID_MOTION_THRESHOLD:
1470 		qc->flags |= V4L2_CTRL_FLAG_SLIDER;
1471 		qc->type = V4L2_CTRL_TYPE_INTEGER;
1472 		qc->minimum = 0;
1473 		qc->maximum = 0xffff;
1474 		qc->step = 1;
1475 		qc->default_value = SOLO_DEF_MOT_THRESH;
1476 		strlcpy(qc->name, "Motion Detection Threshold",
1477 			sizeof(qc->name));
1478 		return 0;
1479 	case V4L2_CID_MOTION_ENABLE:
1480 		qc->type = V4L2_CTRL_TYPE_BOOLEAN;
1481 		qc->minimum = 0;
1482 		qc->maximum = qc->step = 1;
1483 		qc->default_value = 0;
1484 		strlcpy(qc->name, "Motion Detection Enable", sizeof(qc->name));
1485 		return 0;
1486 #else
1487 	case V4L2_CID_MOTION_THRESHOLD:
1488 		return v4l2_ctrl_query_fill(qc, 0, 0xffff, 1,
1489 					    SOLO_DEF_MOT_THRESH);
1490 	case V4L2_CID_MOTION_ENABLE:
1491 		return v4l2_ctrl_query_fill(qc, 0, 1, 1, 0);
1492 #endif
1493 	case V4L2_CID_RDS_TX_RADIO_TEXT:
1494 		qc->type = V4L2_CTRL_TYPE_STRING;
1495 		qc->minimum = 0;
1496 		qc->maximum = OSD_TEXT_MAX;
1497 		qc->step = 1;
1498 		qc->default_value = 0;
1499 		strlcpy(qc->name, "OSD Text", sizeof(qc->name));
1500 		return 0;
1501 	}
1502 
1503 	return -EINVAL;
1504 }
1505 
solo_querymenu(struct file * file,void * priv,struct v4l2_querymenu * qmenu)1506 static int solo_querymenu(struct file *file, void *priv,
1507 			  struct v4l2_querymenu *qmenu)
1508 {
1509 	struct v4l2_queryctrl qctrl;
1510 	int err;
1511 
1512 	qctrl.id = qmenu->id;
1513 	err = solo_queryctrl(file, priv, &qctrl);
1514 	if (err)
1515 		return err;
1516 
1517 	return v4l2_ctrl_query_menu(qmenu, &qctrl, NULL);
1518 }
1519 
solo_g_ctrl(struct file * file,void * priv,struct v4l2_control * ctrl)1520 static int solo_g_ctrl(struct file *file, void *priv,
1521 		       struct v4l2_control *ctrl)
1522 {
1523 	struct solo_enc_fh *fh = priv;
1524 	struct solo_enc_dev *solo_enc = fh->enc;
1525 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1526 
1527 	switch (ctrl->id) {
1528 	case V4L2_CID_BRIGHTNESS:
1529 	case V4L2_CID_CONTRAST:
1530 	case V4L2_CID_SATURATION:
1531 	case V4L2_CID_HUE:
1532 	case V4L2_CID_SHARPNESS:
1533 		return tw28_get_ctrl_val(solo_dev, ctrl->id, solo_enc->ch,
1534 					 &ctrl->value);
1535 	case V4L2_CID_MPEG_VIDEO_ENCODING:
1536 		ctrl->value = V4L2_MPEG_VIDEO_ENCODING_MPEG_4_AVC;
1537 		break;
1538 	case V4L2_CID_MPEG_VIDEO_GOP_SIZE:
1539 		ctrl->value = solo_enc->gop;
1540 		break;
1541 	case V4L2_CID_MOTION_THRESHOLD:
1542 		ctrl->value = solo_enc->motion_thresh;
1543 		break;
1544 	case V4L2_CID_MOTION_ENABLE:
1545 		ctrl->value = solo_is_motion_on(solo_enc);
1546 		break;
1547 	default:
1548 		return -EINVAL;
1549 	}
1550 
1551 	return 0;
1552 }
1553 
solo_s_ctrl(struct file * file,void * priv,struct v4l2_control * ctrl)1554 static int solo_s_ctrl(struct file *file, void *priv,
1555 		       struct v4l2_control *ctrl)
1556 {
1557 	struct solo_enc_fh *fh = priv;
1558 	struct solo_enc_dev *solo_enc = fh->enc;
1559 	struct solo_dev *solo_dev = solo_enc->solo_dev;
1560 
1561 	switch (ctrl->id) {
1562 	case V4L2_CID_BRIGHTNESS:
1563 	case V4L2_CID_CONTRAST:
1564 	case V4L2_CID_SATURATION:
1565 	case V4L2_CID_HUE:
1566 	case V4L2_CID_SHARPNESS:
1567 		return tw28_set_ctrl_val(solo_dev, ctrl->id, solo_enc->ch,
1568 					 ctrl->value);
1569 	case V4L2_CID_MPEG_VIDEO_ENCODING:
1570 		if (ctrl->value != V4L2_MPEG_VIDEO_ENCODING_MPEG_4_AVC)
1571 			return -ERANGE;
1572 		break;
1573 	case V4L2_CID_MPEG_VIDEO_GOP_SIZE:
1574 		if (ctrl->value < 1 || ctrl->value > 255)
1575 			return -ERANGE;
1576 		solo_enc->gop = ctrl->value;
1577 		solo_reg_write(solo_dev, SOLO_VE_CH_GOP(solo_enc->ch),
1578 			       solo_enc->gop);
1579 		solo_reg_write(solo_dev, SOLO_VE_CH_GOP_E(solo_enc->ch),
1580 			       solo_enc->gop);
1581 		break;
1582 	case V4L2_CID_MOTION_THRESHOLD:
1583 		/* TODO accept value on lower 16-bits and use high
1584 		 * 16-bits to assign the value to a specific block */
1585 		if (ctrl->value < 0 || ctrl->value > 0xffff)
1586 			return -ERANGE;
1587 		solo_enc->motion_thresh = ctrl->value;
1588 		solo_set_motion_threshold(solo_dev, solo_enc->ch, ctrl->value);
1589 		break;
1590 	case V4L2_CID_MOTION_ENABLE:
1591 		solo_motion_toggle(solo_enc, ctrl->value);
1592 		break;
1593 	default:
1594 		return -EINVAL;
1595 	}
1596 
1597 	return 0;
1598 }
1599 
solo_s_ext_ctrls(struct file * file,void * priv,struct v4l2_ext_controls * ctrls)1600 static int solo_s_ext_ctrls(struct file *file, void *priv,
1601 			    struct v4l2_ext_controls *ctrls)
1602 {
1603 	struct solo_enc_fh *fh = priv;
1604 	struct solo_enc_dev *solo_enc = fh->enc;
1605 	int i;
1606 
1607 	for (i = 0; i < ctrls->count; i++) {
1608 		struct v4l2_ext_control *ctrl = (ctrls->controls + i);
1609 		int err;
1610 
1611 		switch (ctrl->id) {
1612 		case V4L2_CID_RDS_TX_RADIO_TEXT:
1613 			if (ctrl->size - 1 > OSD_TEXT_MAX)
1614 				err = -ERANGE;
1615 			else {
1616 				err = copy_from_user(solo_enc->osd_text,
1617 						     ctrl->string,
1618 						     OSD_TEXT_MAX);
1619 				solo_enc->osd_text[OSD_TEXT_MAX] = '\0';
1620 				if (!err)
1621 					err = solo_osd_print(solo_enc);
1622 			}
1623 			break;
1624 		default:
1625 			err = -EINVAL;
1626 		}
1627 
1628 		if (err < 0) {
1629 			ctrls->error_idx = i;
1630 			return err;
1631 		}
1632 	}
1633 
1634 	return 0;
1635 }
1636 
solo_g_ext_ctrls(struct file * file,void * priv,struct v4l2_ext_controls * ctrls)1637 static int solo_g_ext_ctrls(struct file *file, void *priv,
1638 			    struct v4l2_ext_controls *ctrls)
1639 {
1640 	struct solo_enc_fh *fh = priv;
1641 	struct solo_enc_dev *solo_enc = fh->enc;
1642 	int i;
1643 
1644 	for (i = 0; i < ctrls->count; i++) {
1645 		struct v4l2_ext_control *ctrl = (ctrls->controls + i);
1646 		int err;
1647 
1648 		switch (ctrl->id) {
1649 		case V4L2_CID_RDS_TX_RADIO_TEXT:
1650 			if (ctrl->size < OSD_TEXT_MAX) {
1651 				ctrl->size = OSD_TEXT_MAX;
1652 				err = -ENOSPC;
1653 			} else {
1654 				err = copy_to_user(ctrl->string,
1655 						   solo_enc->osd_text,
1656 						   OSD_TEXT_MAX);
1657 			}
1658 			break;
1659 		default:
1660 			err = -EINVAL;
1661 		}
1662 
1663 		if (err < 0) {
1664 			ctrls->error_idx = i;
1665 			return err;
1666 		}
1667 	}
1668 
1669 	return 0;
1670 }
1671 
1672 static const struct v4l2_file_operations solo_enc_fops = {
1673 	.owner			= THIS_MODULE,
1674 	.open			= solo_enc_open,
1675 	.release		= solo_enc_release,
1676 	.read			= solo_enc_read,
1677 	.poll			= solo_enc_poll,
1678 	.mmap			= solo_enc_mmap,
1679 	.ioctl			= video_ioctl2,
1680 };
1681 
1682 static const struct v4l2_ioctl_ops solo_enc_ioctl_ops = {
1683 	.vidioc_querycap		= solo_enc_querycap,
1684 	.vidioc_s_std			= solo_enc_s_std,
1685 	/* Input callbacks */
1686 	.vidioc_enum_input		= solo_enc_enum_input,
1687 	.vidioc_s_input			= solo_enc_set_input,
1688 	.vidioc_g_input			= solo_enc_get_input,
1689 	/* Video capture format callbacks */
1690 	.vidioc_enum_fmt_vid_cap	= solo_enc_enum_fmt_cap,
1691 	.vidioc_try_fmt_vid_cap		= solo_enc_try_fmt_cap,
1692 	.vidioc_s_fmt_vid_cap		= solo_enc_set_fmt_cap,
1693 	.vidioc_g_fmt_vid_cap		= solo_enc_get_fmt_cap,
1694 	/* Streaming I/O */
1695 	.vidioc_reqbufs			= solo_enc_reqbufs,
1696 	.vidioc_querybuf		= solo_enc_querybuf,
1697 	.vidioc_qbuf			= solo_enc_qbuf,
1698 	.vidioc_dqbuf			= solo_enc_dqbuf,
1699 	.vidioc_streamon		= solo_enc_streamon,
1700 	.vidioc_streamoff		= solo_enc_streamoff,
1701 	/* Frame size and interval */
1702 	.vidioc_enum_framesizes		= solo_enum_framesizes,
1703 	.vidioc_enum_frameintervals	= solo_enum_frameintervals,
1704 	/* Video capture parameters */
1705 	.vidioc_s_parm			= solo_s_parm,
1706 	.vidioc_g_parm			= solo_g_parm,
1707 	/* Controls */
1708 	.vidioc_queryctrl		= solo_queryctrl,
1709 	.vidioc_querymenu		= solo_querymenu,
1710 	.vidioc_g_ctrl			= solo_g_ctrl,
1711 	.vidioc_s_ctrl			= solo_s_ctrl,
1712 	.vidioc_g_ext_ctrls		= solo_g_ext_ctrls,
1713 	.vidioc_s_ext_ctrls		= solo_s_ext_ctrls,
1714 };
1715 
1716 static struct video_device solo_enc_template = {
1717 	.name			= SOLO6X10_NAME,
1718 	.fops			= &solo_enc_fops,
1719 	.ioctl_ops		= &solo_enc_ioctl_ops,
1720 	.minor			= -1,
1721 	.release		= video_device_release,
1722 
1723 	.tvnorms		= V4L2_STD_NTSC_M | V4L2_STD_PAL_B,
1724 	.current_norm		= V4L2_STD_NTSC_M,
1725 };
1726 
solo_enc_alloc(struct solo_dev * solo_dev,u8 ch)1727 static struct solo_enc_dev *solo_enc_alloc(struct solo_dev *solo_dev, u8 ch)
1728 {
1729 	struct solo_enc_dev *solo_enc;
1730 	int ret;
1731 
1732 	solo_enc = kzalloc(sizeof(*solo_enc), GFP_KERNEL);
1733 	if (!solo_enc)
1734 		return ERR_PTR(-ENOMEM);
1735 
1736 	solo_enc->vfd = video_device_alloc();
1737 	if (!solo_enc->vfd) {
1738 		kfree(solo_enc);
1739 		return ERR_PTR(-ENOMEM);
1740 	}
1741 
1742 	solo_enc->solo_dev = solo_dev;
1743 	solo_enc->ch = ch;
1744 
1745 	*solo_enc->vfd = solo_enc_template;
1746 	solo_enc->vfd->parent = &solo_dev->pdev->dev;
1747 	ret = video_register_device(solo_enc->vfd, VFL_TYPE_GRABBER,
1748 				    video_nr);
1749 	if (ret < 0) {
1750 		video_device_release(solo_enc->vfd);
1751 		kfree(solo_enc);
1752 		return ERR_PTR(ret);
1753 	}
1754 
1755 	video_set_drvdata(solo_enc->vfd, solo_enc);
1756 
1757 	snprintf(solo_enc->vfd->name, sizeof(solo_enc->vfd->name),
1758 		 "%s-enc (%i/%i)", SOLO6X10_NAME, solo_dev->vfd->num,
1759 		 solo_enc->vfd->num);
1760 
1761 	if (video_nr != -1)
1762 		video_nr++;
1763 
1764 	spin_lock_init(&solo_enc->lock);
1765 	init_waitqueue_head(&solo_enc->thread_wait);
1766 	atomic_set(&solo_enc->readers, 0);
1767 
1768 	solo_enc->qp = SOLO_DEFAULT_QP;
1769 	solo_enc->gop = solo_dev->fps;
1770 	solo_enc->interval = 1;
1771 	solo_enc->mode = SOLO_ENC_MODE_CIF;
1772 	solo_enc->motion_thresh = SOLO_DEF_MOT_THRESH;
1773 
1774 	spin_lock(&solo_enc->lock);
1775 	solo_update_mode(solo_enc);
1776 	spin_unlock(&solo_enc->lock);
1777 
1778 	return solo_enc;
1779 }
1780 
solo_enc_free(struct solo_enc_dev * solo_enc)1781 static void solo_enc_free(struct solo_enc_dev *solo_enc)
1782 {
1783 	if (solo_enc == NULL)
1784 		return;
1785 
1786 	video_unregister_device(solo_enc->vfd);
1787 	kfree(solo_enc);
1788 }
1789 
solo_enc_v4l2_init(struct solo_dev * solo_dev)1790 int solo_enc_v4l2_init(struct solo_dev *solo_dev)
1791 {
1792 	int i;
1793 
1794 	for (i = 0; i < solo_dev->nr_chans; i++) {
1795 		solo_dev->v4l2_enc[i] = solo_enc_alloc(solo_dev, i);
1796 		if (IS_ERR(solo_dev->v4l2_enc[i]))
1797 			break;
1798 	}
1799 
1800 	if (i != solo_dev->nr_chans) {
1801 		int ret = PTR_ERR(solo_dev->v4l2_enc[i]);
1802 		while (i--)
1803 			solo_enc_free(solo_dev->v4l2_enc[i]);
1804 		return ret;
1805 	}
1806 
1807 	/* D1@MAX-FPS * 4 */
1808 	solo_dev->enc_bw_remain = solo_dev->fps * 4 * 4;
1809 
1810 	dev_info(&solo_dev->pdev->dev, "Encoders as /dev/video%d-%d\n",
1811 		 solo_dev->v4l2_enc[0]->vfd->num,
1812 		 solo_dev->v4l2_enc[solo_dev->nr_chans - 1]->vfd->num);
1813 
1814 	return 0;
1815 }
1816 
solo_enc_v4l2_exit(struct solo_dev * solo_dev)1817 void solo_enc_v4l2_exit(struct solo_dev *solo_dev)
1818 {
1819 	int i;
1820 
1821 	solo_irq_off(solo_dev, SOLO_IRQ_MOTION);
1822 
1823 	for (i = 0; i < solo_dev->nr_chans; i++)
1824 		solo_enc_free(solo_dev->v4l2_enc[i]);
1825 }
1826