Committer: Michael Beasley <mike@snafu.setup>
[mikesnafu-overlay.git] / drivers / media / video / bt866.c
blob96b415576f0deb8f5330eda6f758deb3cb76a73d
1 /*
2 bt866 - BT866 Digital Video Encoder (Rockwell Part)
4 Copyright (C) 1999 Mike Bernson <mike@mlb.org>
5 Copyright (C) 1998 Dave Perks <dperks@ibm.net>
7 Modifications for LML33/DC10plus unified driver
8 Copyright (C) 2000 Serguei Miridonov <mirsev@cicese.mx>
10 This code was modify/ported from the saa7111 driver written
11 by Dave Perks.
13 This code was adapted for the bt866 by Christer Weinigel and ported
14 to 2.6 by Martin Samuelsson.
16 This program is free software; you can redistribute it and/or modify
17 it under the terms of the GNU General Public License as published by
18 the Free Software Foundation; either version 2 of the License, or
19 (at your option) any later version.
21 This program is distributed in the hope that it will be useful,
22 but WITHOUT ANY WARRANTY; without even the implied warranty of
23 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 GNU General Public License for more details.
26 You should have received a copy of the GNU General Public License
27 along with this program; if not, write to the Free Software
28 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
31 #include <linux/module.h>
32 #include <linux/init.h>
33 #include <linux/delay.h>
34 #include <linux/errno.h>
35 #include <linux/fs.h>
36 #include <linux/kernel.h>
37 #include <linux/major.h>
38 #include <linux/slab.h>
39 #include <linux/mm.h>
40 #include <linux/signal.h>
41 #include <asm/io.h>
42 #include <asm/pgtable.h>
43 #include <asm/page.h>
44 #include <linux/sched.h>
45 #include <linux/types.h>
46 #include <linux/i2c.h>
48 #include <linux/videodev.h>
49 #include <asm/uaccess.h>
51 #include <linux/video_encoder.h>
53 MODULE_LICENSE("GPL");
55 #define BT866_DEVNAME "bt866"
56 #define I2C_BT866 0x88
58 MODULE_LICENSE("GPL");
60 #define DEBUG(x) /* Debug driver */
62 /* ----------------------------------------------------------------------- */
64 struct bt866 {
65 struct i2c_client *i2c;
66 int addr;
67 unsigned char reg[256];
69 int norm;
70 int enable;
71 int bright;
72 int contrast;
73 int hue;
74 int sat;
77 static int bt866_write(struct bt866 *dev,
78 unsigned char subaddr, unsigned char data);
80 static int bt866_do_command(struct bt866 *encoder,
81 unsigned int cmd, void *arg)
83 switch (cmd) {
84 case ENCODER_GET_CAPABILITIES:
86 struct video_encoder_capability *cap = arg;
88 DEBUG(printk
89 (KERN_INFO "%s: get capabilities\n",
90 encoder->i2c->name));
92 cap->flags
93 = VIDEO_ENCODER_PAL
94 | VIDEO_ENCODER_NTSC
95 | VIDEO_ENCODER_CCIR;
96 cap->inputs = 2;
97 cap->outputs = 1;
99 break;
101 case ENCODER_SET_NORM:
103 int *iarg = arg;
105 DEBUG(printk(KERN_INFO "%s: set norm %d\n",
106 encoder->i2c->name, *iarg));
108 switch (*iarg) {
110 case VIDEO_MODE_NTSC:
111 break;
113 case VIDEO_MODE_PAL:
114 break;
116 default:
117 return -EINVAL;
120 encoder->norm = *iarg;
122 break;
124 case ENCODER_SET_INPUT:
126 int *iarg = arg;
127 static const __u8 init[] = {
128 0xc8, 0xcc, /* CRSCALE */
129 0xca, 0x91, /* CBSCALE */
130 0xcc, 0x24, /* YC16 | OSDNUM */
131 0xda, 0x00, /* */
132 0xdc, 0x24, /* SETMODE | PAL */
133 0xde, 0x02, /* EACTIVE */
135 /* overlay colors */
136 0x70, 0xEB, 0x90, 0x80, 0xB0, 0x80, /* white */
137 0x72, 0xA2, 0x92, 0x8E, 0xB2, 0x2C, /* yellow */
138 0x74, 0x83, 0x94, 0x2C, 0xB4, 0x9C, /* cyan */
139 0x76, 0x70, 0x96, 0x3A, 0xB6, 0x48, /* green */
140 0x78, 0x54, 0x98, 0xC6, 0xB8, 0xB8, /* magenta */
141 0x7A, 0x41, 0x9A, 0xD4, 0xBA, 0x64, /* red */
142 0x7C, 0x23, 0x9C, 0x72, 0xBC, 0xD4, /* blue */
143 0x7E, 0x10, 0x9E, 0x80, 0xBE, 0x80, /* black */
145 0x60, 0xEB, 0x80, 0x80, 0xc0, 0x80, /* white */
146 0x62, 0xA2, 0x82, 0x8E, 0xc2, 0x2C, /* yellow */
147 0x64, 0x83, 0x84, 0x2C, 0xc4, 0x9C, /* cyan */
148 0x66, 0x70, 0x86, 0x3A, 0xc6, 0x48, /* green */
149 0x68, 0x54, 0x88, 0xC6, 0xc8, 0xB8, /* magenta */
150 0x6A, 0x41, 0x8A, 0xD4, 0xcA, 0x64, /* red */
151 0x6C, 0x23, 0x8C, 0x72, 0xcC, 0xD4, /* blue */
152 0x6E, 0x10, 0x8E, 0x80, 0xcE, 0x80, /* black */
154 int i;
155 u8 val;
157 for (i = 0; i < ARRAY_SIZE(init) / 2; i += 2)
158 bt866_write(encoder, init[i], init[i+1]);
160 val = encoder->reg[0xdc];
162 if (*iarg == 0)
163 val |= 0x40; /* CBSWAP */
164 else
165 val &= ~0x40; /* !CBSWAP */
167 bt866_write(encoder, 0xdc, val);
169 val = encoder->reg[0xcc];
170 if (*iarg == 2)
171 val |= 0x01; /* OSDBAR */
172 else
173 val &= ~0x01; /* !OSDBAR */
174 bt866_write(encoder, 0xcc, val);
176 DEBUG(printk(KERN_INFO "%s: set input %d\n",
177 encoder->i2c->name, *iarg));
179 switch (*iarg) {
180 case 0:
181 break;
182 case 1:
183 break;
184 default:
185 return -EINVAL;
189 break;
191 case ENCODER_SET_OUTPUT:
193 int *iarg = arg;
195 DEBUG(printk(KERN_INFO "%s: set output %d\n",
196 encoder->i2c->name, *iarg));
198 /* not much choice of outputs */
199 if (*iarg != 0)
200 return -EINVAL;
202 break;
204 case ENCODER_ENABLE_OUTPUT:
206 int *iarg = arg;
207 encoder->enable = !!*iarg;
209 DEBUG(printk
210 (KERN_INFO "%s: enable output %d\n",
211 encoder->i2c->name, encoder->enable));
213 break;
215 case 4711:
217 int *iarg = arg;
218 __u8 val;
220 printk("bt866: square = %d\n", *iarg);
222 val = encoder->reg[0xdc];
223 if (*iarg)
224 val |= 1; /* SQUARE */
225 else
226 val &= ~1; /* !SQUARE */
227 bt866_write(encoder, 0xdc, val);
228 break;
231 default:
232 return -EINVAL;
235 return 0;
238 static int bt866_write(struct bt866 *encoder,
239 unsigned char subaddr, unsigned char data)
241 unsigned char buffer[2];
242 int err;
244 buffer[0] = subaddr;
245 buffer[1] = data;
247 encoder->reg[subaddr] = data;
249 DEBUG(printk
250 ("%s: write 0x%02X = 0x%02X\n",
251 encoder->i2c->name, subaddr, data));
253 for (err = 0; err < 3;) {
254 if (i2c_master_send(encoder->i2c, buffer, 2) == 2)
255 break;
256 err++;
257 printk(KERN_WARNING "%s: I/O error #%d "
258 "(write 0x%02x/0x%02x)\n",
259 encoder->i2c->name, err, encoder->addr, subaddr);
260 schedule_timeout_interruptible(msecs_to_jiffies(100));
262 if (err == 3) {
263 printk(KERN_WARNING "%s: giving up\n",
264 encoder->i2c->name);
265 return -1;
268 return 0;
271 static int bt866_attach(struct i2c_adapter *adapter);
272 static int bt866_detach(struct i2c_client *client);
273 static int bt866_command(struct i2c_client *client,
274 unsigned int cmd, void *arg);
277 /* Addresses to scan */
278 static unsigned short normal_i2c[] = {I2C_BT866>>1, I2C_CLIENT_END};
279 static unsigned short probe[2] = {I2C_CLIENT_END, I2C_CLIENT_END};
280 static unsigned short ignore[2] = {I2C_CLIENT_END, I2C_CLIENT_END};
282 static struct i2c_client_address_data addr_data = {
283 normal_i2c,
284 probe,
285 ignore,
288 static struct i2c_driver i2c_driver_bt866 = {
289 .driver.name = BT866_DEVNAME,
290 .id = I2C_DRIVERID_BT866,
291 .attach_adapter = bt866_attach,
292 .detach_client = bt866_detach,
293 .command = bt866_command
297 static struct i2c_client bt866_client_tmpl =
299 .name = "(nil)",
300 .addr = 0,
301 .adapter = NULL,
302 .driver = &i2c_driver_bt866,
305 static int bt866_found_proc(struct i2c_adapter *adapter,
306 int addr, int kind)
308 struct bt866 *encoder;
309 struct i2c_client *client;
311 client = kzalloc(sizeof(*client), GFP_KERNEL);
312 if (client == NULL)
313 return -ENOMEM;
314 memcpy(client, &bt866_client_tmpl, sizeof(*client));
316 encoder = kzalloc(sizeof(*encoder), GFP_KERNEL);
317 if (encoder == NULL) {
318 kfree(client);
319 return -ENOMEM;
322 i2c_set_clientdata(client, encoder);
323 client->adapter = adapter;
324 client->addr = addr;
325 sprintf(client->name, "%s-%02x", BT866_DEVNAME, adapter->id);
327 encoder->i2c = client;
328 encoder->addr = addr;
329 //encoder->encoder_type = ENCODER_TYPE_UNKNOWN;
331 /* initialize */
333 i2c_attach_client(client);
335 return 0;
338 static int bt866_attach(struct i2c_adapter *adapter)
340 if (adapter->id == I2C_HW_B_ZR36067)
341 return i2c_probe(adapter, &addr_data, bt866_found_proc);
342 return 0;
345 static int bt866_detach(struct i2c_client *client)
347 struct bt866 *encoder = i2c_get_clientdata(client);
349 i2c_detach_client(client);
350 kfree(encoder);
351 kfree(client);
353 return 0;
356 static int bt866_command(struct i2c_client *client,
357 unsigned int cmd, void *arg)
359 struct bt866 *encoder = i2c_get_clientdata(client);
360 return bt866_do_command(encoder, cmd, arg);
363 static int __devinit bt866_init(void)
365 i2c_add_driver(&i2c_driver_bt866);
366 return 0;
369 static void __devexit bt866_exit(void)
371 i2c_del_driver(&i2c_driver_bt866);
374 module_init(bt866_init);
375 module_exit(bt866_exit);