1/*
2 * saa7111 - Philips SAA7111A video decoder driver version 0.0.3
3 *
4 * Copyright (C) 1998 Dave Perks <dperks@ibm.net>
5 *
6 * Slight changes for video timing and attachment output by
7 * Wolfgang Scherr <scherr@net4you.net>
8 *
9 * Changes by Ronald Bultje <rbultje@ronald.bitfreak.net>
10 *    - moved over to linux>=2.4.x i2c protocol (1/1/2003)
11 *
12 * Changes by Michael Hunold <michael@mihu.de>
13 *    - implemented DECODER_SET_GPIO, DECODER_INIT, DECODER_SET_VBI_BYPASS
14 *
15 * This program is free software; you can redistribute it and/or modify
16 * it under the terms of the GNU General Public License as published by
17 * the Free Software Foundation; either version 2 of the License, or
18 * (at your option) any later version.
19 *
20 * This program is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23 * GNU General Public License for more details.
24 *
25 * You should have received a copy of the GNU General Public License
26 * along with this program; if not, write to the Free Software
27 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
28 */
29
30#include <linux/module.h>
31#include <linux/init.h>
32#include <linux/delay.h>
33#include <linux/errno.h>
34#include <linux/fs.h>
35#include <linux/kernel.h>
36#include <linux/major.h>
37#include <linux/slab.h>
38#include <linux/mm.h>
39#include <linux/signal.h>
40#include <asm/io.h>
41#include <asm/pgtable.h>
42#include <asm/page.h>
43#include <linux/types.h>
44
45#include <linux/videodev.h>
46#include <asm/uaccess.h>
47
48MODULE_DESCRIPTION("Philips SAA7111 video decoder driver");
49MODULE_AUTHOR("Dave Perks");
50MODULE_LICENSE("GPL");
51
52#include <linux/i2c.h>
53
54#define I2C_NAME(s) (s)->name
55
56#include <linux/video_decoder.h>
57
58static int debug = 0;
59module_param(debug, int, 0644);
60MODULE_PARM_DESC(debug, "Debug level (0-1)");
61
62#define dprintk(num, format, args...) \
63	do { \
64		if (debug >= num) \
65			printk(format, ##args); \
66	} while (0)
67
68/* ----------------------------------------------------------------------- */
69
70#define SAA7111_NR_REG		0x18
71
72struct saa7111 {
73	unsigned char reg[SAA7111_NR_REG];
74
75	int norm;
76	int input;
77	int enable;
78};
79
80#define   I2C_SAA7111        0x48
81
82/* ----------------------------------------------------------------------- */
83
84static inline int
85saa7111_write (struct i2c_client *client,
86	       u8                 reg,
87	       u8                 value)
88{
89	struct saa7111 *decoder = i2c_get_clientdata(client);
90
91	decoder->reg[reg] = value;
92	return i2c_smbus_write_byte_data(client, reg, value);
93}
94
95static inline void
96saa7111_write_if_changed(struct i2c_client *client, u8 reg, u8 value)
97{
98	struct saa7111 *decoder = i2c_get_clientdata(client);
99
100	if (decoder->reg[reg] != value) {
101		decoder->reg[reg] = value;
102		i2c_smbus_write_byte_data(client, reg, value);
103	}
104}
105
106static int
107saa7111_write_block (struct i2c_client *client,
108		     const u8          *data,
109		     unsigned int       len)
110{
111	int ret = -1;
112	u8 reg;
113
114	/* the saa7111 has an autoincrement function, use it if
115	 * the adapter understands raw I2C */
116	if (i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
117		/* do raw I2C, not smbus compatible */
118		struct saa7111 *decoder = i2c_get_clientdata(client);
119		u8 block_data[32];
120		int block_len;
121
122		while (len >= 2) {
123			block_len = 0;
124			block_data[block_len++] = reg = data[0];
125			do {
126				block_data[block_len++] =
127				    decoder->reg[reg++] = data[1];
128				len -= 2;
129				data += 2;
130			} while (len >= 2 && data[0] == reg &&
131				 block_len < 32);
132			if ((ret = i2c_master_send(client, block_data,
133						   block_len)) < 0)
134				break;
135		}
136	} else {
137		/* do some slow I2C emulation kind of thing */
138		while (len >= 2) {
139			reg = *data++;
140			if ((ret = saa7111_write(client, reg,
141						 *data++)) < 0)
142				break;
143			len -= 2;
144		}
145	}
146
147	return ret;
148}
149
150static int
151saa7111_init_decoder (struct i2c_client *client,
152	      struct video_decoder_init *init)
153{
154	return saa7111_write_block(client, init->data, init->len);
155}
156
157static inline int
158saa7111_read (struct i2c_client *client,
159	      u8                 reg)
160{
161	return i2c_smbus_read_byte_data(client, reg);
162}
163
164/* ----------------------------------------------------------------------- */
165
166static const unsigned char saa7111_i2c_init[] = {
167	0x00, 0x00,		/* 00 - ID byte */
168	0x01, 0x00,		/* 01 - reserved */
169
170	/*front end */
171	0x02, 0xd0,		/* 02 - FUSE=3, GUDL=2, MODE=0 */
172	0x03, 0x23,		/* 03 - HLNRS=0, VBSL=1, WPOFF=0,
173				 * HOLDG=0, GAFIX=0, GAI1=256, GAI2=256 */
174	0x04, 0x00,		/* 04 - GAI1=256 */
175	0x05, 0x00,		/* 05 - GAI2=256 */
176
177	/* decoder */
178	0x06, 0xf3,		/* 06 - HSB at  13(50Hz) /  17(60Hz)
179				 * pixels after end of last line */
180	/*0x07, 0x13,     * 07 - HSS at 113(50Hz) / 117(60Hz) pixels
181				 * after end of last line */
182	0x07, 0xe8,		/* 07 - HSS seems to be needed to
183				 * work with NTSC, too */
184	0x08, 0xc8,		/* 08 - AUFD=1, FSEL=1, EXFIL=0,
185				 * VTRC=1, HPLL=0, VNOI=0 */
186	0x09, 0x01,		/* 09 - BYPS=0, PREF=0, BPSS=0,
187				 * VBLB=0, UPTCV=0, APER=1 */
188	0x0a, 0x80,		/* 0a - BRIG=128 */
189	0x0b, 0x47,		/* 0b - CONT=1.109 */
190	0x0c, 0x40,		/* 0c - SATN=1.0 */
191	0x0d, 0x00,		/* 0d - HUE=0 */
192	0x0e, 0x01,		/* 0e - CDTO=0, CSTD=0, DCCF=0,
193				 * FCTC=0, CHBW=1 */
194	0x0f, 0x00,		/* 0f - reserved */
195	0x10, 0x48,		/* 10 - OFTS=1, HDEL=0, VRLN=1, YDEL=0 */
196	0x11, 0x1c,		/* 11 - GPSW=0, CM99=0, FECO=0, COMPO=1,
197				 * OEYC=1, OEHV=1, VIPB=0, COLO=0 */
198	0x12, 0x00,		/* 12 - output control 2 */
199	0x13, 0x00,		/* 13 - output control 3 */
200	0x14, 0x00,		/* 14 - reserved */
201	0x15, 0x00,		/* 15 - VBI */
202	0x16, 0x00,		/* 16 - VBI */
203	0x17, 0x00,		/* 17 - VBI */
204};
205
206static int
207saa7111_command (struct i2c_client *client,
208		 unsigned int       cmd,
209		 void              *arg)
210{
211	struct saa7111 *decoder = i2c_get_clientdata(client);
212
213	switch (cmd) {
214
215	case 0:
216		break;
217	case DECODER_INIT:
218	{
219		struct video_decoder_init *init = arg;
220		if (NULL != init)
221			return saa7111_init_decoder(client, init);
222		else {
223			struct video_decoder_init vdi;
224			vdi.data = saa7111_i2c_init;
225			vdi.len = sizeof(saa7111_i2c_init);
226			return saa7111_init_decoder(client, &vdi);
227		}
228	}
229
230	case DECODER_DUMP:
231	{
232		int i;
233
234		for (i = 0; i < SAA7111_NR_REG; i += 16) {
235			int j;
236
237			printk(KERN_DEBUG "%s: %03x", I2C_NAME(client), i);
238			for (j = 0; j < 16 && i + j < SAA7111_NR_REG; ++j) {
239				printk(" %02x",
240				       saa7111_read(client, i + j));
241			}
242			printk("\n");
243		}
244	}
245		break;
246
247	case DECODER_GET_CAPABILITIES:
248	{
249		struct video_decoder_capability *cap = arg;
250
251		cap->flags = VIDEO_DECODER_PAL |
252			     VIDEO_DECODER_NTSC |
253			     VIDEO_DECODER_SECAM |
254			     VIDEO_DECODER_AUTO |
255			     VIDEO_DECODER_CCIR;
256		cap->inputs = 8;
257		cap->outputs = 1;
258	}
259		break;
260
261	case DECODER_GET_STATUS:
262	{
263		int *iarg = arg;
264		int status;
265		int res;
266
267		status = saa7111_read(client, 0x1f);
268		dprintk(1, KERN_DEBUG "%s status: 0x%02x\n", I2C_NAME(client),
269			status);
270		res = 0;
271		if ((status & (1 << 6)) == 0) {
272			res |= DECODER_STATUS_GOOD;
273		}
274		switch (decoder->norm) {
275		case VIDEO_MODE_NTSC:
276			res |= DECODER_STATUS_NTSC;
277			break;
278		case VIDEO_MODE_PAL:
279			res |= DECODER_STATUS_PAL;
280			break;
281		case VIDEO_MODE_SECAM:
282			res |= DECODER_STATUS_SECAM;
283			break;
284		default:
285		case VIDEO_MODE_AUTO:
286			if ((status & (1 << 5)) != 0) {
287				res |= DECODER_STATUS_NTSC;
288			} else {
289				res |= DECODER_STATUS_PAL;
290			}
291			break;
292		}
293		if ((status & (1 << 0)) != 0) {
294			res |= DECODER_STATUS_COLOR;
295		}
296		*iarg = res;
297	}
298		break;
299
300	case DECODER_SET_GPIO:
301	{
302		int *iarg = arg;
303		if (0 != *iarg) {
304			saa7111_write(client, 0x11,
305				(decoder->reg[0x11] | 0x80));
306		} else {
307			saa7111_write(client, 0x11,
308				(decoder->reg[0x11] & 0x7f));
309		}
310		break;
311	}
312
313	case DECODER_SET_VBI_BYPASS:
314	{
315		int *iarg = arg;
316		if (0 != *iarg) {
317			saa7111_write(client, 0x13,
318				(decoder->reg[0x13] & 0xf0) | 0x0a);
319		} else {
320			saa7111_write(client, 0x13,
321				(decoder->reg[0x13] & 0xf0));
322		}
323		break;
324	}
325
326	case DECODER_SET_NORM:
327	{
328		int *iarg = arg;
329
330		switch (*iarg) {
331
332		case VIDEO_MODE_NTSC:
333			saa7111_write(client, 0x08,
334				      (decoder->reg[0x08] & 0x3f) | 0x40);
335			saa7111_write(client, 0x0e,
336				      (decoder->reg[0x0e] & 0x8f));
337			break;
338
339		case VIDEO_MODE_PAL:
340			saa7111_write(client, 0x08,
341				      (decoder->reg[0x08] & 0x3f) | 0x00);
342			saa7111_write(client, 0x0e,
343				      (decoder->reg[0x0e] & 0x8f));
344			break;
345
346		case VIDEO_MODE_SECAM:
347			saa7111_write(client, 0x08,
348				      (decoder->reg[0x08] & 0x3f) | 0x00);
349			saa7111_write(client, 0x0e,
350				      (decoder->reg[0x0e] & 0x8f) | 0x50);
351			break;
352
353		case VIDEO_MODE_AUTO:
354			saa7111_write(client, 0x08,
355				      (decoder->reg[0x08] & 0x3f) | 0x80);
356			saa7111_write(client, 0x0e,
357				      (decoder->reg[0x0e] & 0x8f));
358			break;
359
360		default:
361			return -EINVAL;
362
363		}
364		decoder->norm = *iarg;
365	}
366		break;
367
368	case DECODER_SET_INPUT:
369	{
370		int *iarg = arg;
371
372		if (*iarg < 0 || *iarg > 7) {
373			return -EINVAL;
374		}
375
376		if (decoder->input != *iarg) {
377			decoder->input = *iarg;
378			/* select mode */
379			saa7111_write(client, 0x02,
380				      (decoder->
381				       reg[0x02] & 0xf8) | decoder->input);
382			/* bypass chrominance trap for modes 4..7 */
383			saa7111_write(client, 0x09,
384				      (decoder->
385				       reg[0x09] & 0x7f) | ((decoder->
386							     input >
387							     3) ? 0x80 :
388							    0));
389		}
390	}
391		break;
392
393	case DECODER_SET_OUTPUT:
394	{
395		int *iarg = arg;
396
397		/* not much choice of outputs */
398		if (*iarg != 0) {
399			return -EINVAL;
400		}
401	}
402		break;
403
404	case DECODER_ENABLE_OUTPUT:
405	{
406		int *iarg = arg;
407		int enable = (*iarg != 0);
408
409		if (decoder->enable != enable) {
410			decoder->enable = enable;
411
412			/* RJ: If output should be disabled (for
413			 * playing videos), we also need a open PLL.
414			 * The input is set to 0 (where no input
415			 * source is connected), although this
416			 * is not necessary.
417			 *
418			 * If output should be enabled, we have to
419			 * reverse the above.
420			 */
421
422			if (decoder->enable) {
423				saa7111_write(client, 0x02,
424					      (decoder->
425					       reg[0x02] & 0xf8) |
426					      decoder->input);
427				saa7111_write(client, 0x08,
428					      (decoder->reg[0x08] & 0xfb));
429				saa7111_write(client, 0x11,
430					      (decoder->
431					       reg[0x11] & 0xf3) | 0x0c);
432			} else {
433				saa7111_write(client, 0x02,
434					      (decoder->reg[0x02] & 0xf8));
435				saa7111_write(client, 0x08,
436					      (decoder->
437					       reg[0x08] & 0xfb) | 0x04);
438				saa7111_write(client, 0x11,
439					      (decoder->reg[0x11] & 0xf3));
440			}
441		}
442	}
443		break;
444
445	case DECODER_SET_PICTURE:
446	{
447		struct video_picture *pic = arg;
448
449		/* We want 0 to 255 we get 0-65535 */
450		saa7111_write_if_changed(client, 0x0a, pic->brightness >> 8);
451		/* We want 0 to 127 we get 0-65535 */
452		saa7111_write(client, 0x0b, pic->contrast >> 9);
453		/* We want 0 to 127 we get 0-65535 */
454		saa7111_write(client, 0x0c, pic->colour >> 9);
455		/* We want -128 to 127 we get 0-65535 */
456		saa7111_write(client, 0x0d, (pic->hue - 32768) >> 8);
457	}
458		break;
459
460	default:
461		return -EINVAL;
462	}
463
464	return 0;
465}
466
467/* ----------------------------------------------------------------------- */
468
469/*
470 * Generic i2c probe
471 * concerning the addresses: i2c wants 7 bit (without the r/w bit), so '>>1'
472 */
473static unsigned short normal_i2c[] = { I2C_SAA7111 >> 1, I2C_CLIENT_END };
474
475static unsigned short ignore = I2C_CLIENT_END;
476
477static struct i2c_client_address_data addr_data = {
478	.normal_i2c		= normal_i2c,
479	.probe			= &ignore,
480	.ignore			= &ignore,
481};
482
483static struct i2c_driver i2c_driver_saa7111;
484
485static int
486saa7111_detect_client (struct i2c_adapter *adapter,
487		       int                 address,
488		       int                 kind)
489{
490	int i;
491	struct i2c_client *client;
492	struct saa7111 *decoder;
493	struct video_decoder_init vdi;
494
495	dprintk(1,
496		KERN_INFO
497		"saa7111.c: detecting saa7111 client on address 0x%x\n",
498		address << 1);
499
500	/* Check if the adapter supports the needed features */
501	if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA))
502		return 0;
503
504	client = kzalloc(sizeof(struct i2c_client), GFP_KERNEL);
505	if (client == 0)
506		return -ENOMEM;
507	client->addr = address;
508	client->adapter = adapter;
509	client->driver = &i2c_driver_saa7111;
510	strlcpy(I2C_NAME(client), "saa7111", sizeof(I2C_NAME(client)));
511
512	decoder = kzalloc(sizeof(struct saa7111), GFP_KERNEL);
513	if (decoder == NULL) {
514		kfree(client);
515		return -ENOMEM;
516	}
517	decoder->norm = VIDEO_MODE_NTSC;
518	decoder->input = 0;
519	decoder->enable = 1;
520	i2c_set_clientdata(client, decoder);
521
522	i = i2c_attach_client(client);
523	if (i) {
524		kfree(client);
525		kfree(decoder);
526		return i;
527	}
528
529	vdi.data = saa7111_i2c_init;
530	vdi.len = sizeof(saa7111_i2c_init);
531	i = saa7111_init_decoder(client, &vdi);
532	if (i < 0) {
533		dprintk(1, KERN_ERR "%s_attach error: init status %d\n",
534			I2C_NAME(client), i);
535	} else {
536		dprintk(1,
537			KERN_INFO
538			"%s_attach: chip version %x at address 0x%x\n",
539			I2C_NAME(client), saa7111_read(client, 0x00) >> 4,
540			client->addr << 1);
541	}
542
543	return 0;
544}
545
546static int
547saa7111_attach_adapter (struct i2c_adapter *adapter)
548{
549	dprintk(1,
550		KERN_INFO
551		"saa7111.c: starting probe for adapter %s (0x%x)\n",
552		I2C_NAME(adapter), adapter->id);
553	return i2c_probe(adapter, &addr_data, &saa7111_detect_client);
554}
555
556static int
557saa7111_detach_client (struct i2c_client *client)
558{
559	struct saa7111 *decoder = i2c_get_clientdata(client);
560	int err;
561
562	err = i2c_detach_client(client);
563	if (err) {
564		return err;
565	}
566
567	kfree(decoder);
568	kfree(client);
569
570	return 0;
571}
572
573/* ----------------------------------------------------------------------- */
574
575static struct i2c_driver i2c_driver_saa7111 = {
576	.driver = {
577		.name = "saa7111",
578	},
579
580	.id = I2C_DRIVERID_SAA7111A,
581
582	.attach_adapter = saa7111_attach_adapter,
583	.detach_client = saa7111_detach_client,
584	.command = saa7111_command,
585};
586
587static int __init
588saa7111_init (void)
589{
590	return i2c_add_driver(&i2c_driver_saa7111);
591}
592
593static void __exit
594saa7111_exit (void)
595{
596	i2c_del_driver(&i2c_driver_saa7111);
597}
598
599module_init(saa7111_init);
600module_exit(saa7111_exit);
601