blob: b5d228d91b06416fad4aa0cfe222aa103212cf09 [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*
2 * Zoran zr36057/zr36067 PCI controller driver, for the
3 * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux
4 * Media Labs LML33/LML33R10.
5 *
6 * This part handles card-specific data and detection
Mauro Carvalho Chehabd56410e2006-03-25 09:19:53 -03007 *
Linus Torvalds1da177e2005-04-16 15:20:36 -07008 * Copyright (C) 2000 Serguei Miridonov <mirsev@cicese.mx>
9 *
10 * Currently maintained by:
11 * Ronald Bultje <rbultje@ronald.bitfreak.net>
12 * Laurent Pinchart <laurent.pinchart@skynet.be>
13 * Mailinglist <mjpeg-users@lists.sf.net>
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
Martin Samuelssonfbe60da2006-04-27 10:17:00 -030030#include <linux/delay.h>
31
Linus Torvalds1da177e2005-04-16 15:20:36 -070032#include <linux/types.h>
33#include <linux/kernel.h>
34#include <linux/module.h>
35#include <linux/init.h>
36#include <linux/vmalloc.h>
37
38#include <linux/proc_fs.h>
39#include <linux/i2c.h>
40#include <linux/i2c-algo-bit.h>
Hans Verkuil7f6adea2009-02-19 17:31:17 -030041#include <linux/videodev2.h>
Mauro Carvalho Chehab5e87efa2006-06-05 10:26:32 -030042#include <media/v4l2-common.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070043#include <linux/spinlock.h>
44#include <linux/sem.h>
45#include <linux/kmod.h>
46#include <linux/wait.h>
47
48#include <linux/pci.h>
49#include <linux/interrupt.h>
Ingo Molnar384c3682006-03-22 03:54:16 -030050#include <linux/mutex.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070051
52#include <asm/io.h>
53
54#include "videocodec.h"
55#include "zoran.h"
56#include "zoran_card.h"
57#include "zoran_device.h"
58#include "zoran_procfs.h"
59
Linus Torvalds1da177e2005-04-16 15:20:36 -070060extern const struct zoran_format zoran_formats[];
61
Trent Piepho45bdcef2009-01-12 13:09:46 -030062static int card[BUZ_MAX] = { [0 ... (BUZ_MAX-1)] = -1 };
Trent Piepho60e3cac2007-07-17 18:29:42 -030063module_param_array(card, int, NULL, 0444);
Trent Piepho45bdcef2009-01-12 13:09:46 -030064MODULE_PARM_DESC(card, "Card type");
Linus Torvalds1da177e2005-04-16 15:20:36 -070065
Trent Piepho45bdcef2009-01-12 13:09:46 -030066static int encoder[BUZ_MAX] = { [0 ... (BUZ_MAX-1)] = -1 };
Trent Piepho60e3cac2007-07-17 18:29:42 -030067module_param_array(encoder, int, NULL, 0444);
Trent Piepho45bdcef2009-01-12 13:09:46 -030068MODULE_PARM_DESC(encoder, "Video encoder chip");
Linus Torvalds1da177e2005-04-16 15:20:36 -070069
Trent Piepho45bdcef2009-01-12 13:09:46 -030070static int decoder[BUZ_MAX] = { [0 ... (BUZ_MAX-1)] = -1 };
Trent Piepho60e3cac2007-07-17 18:29:42 -030071module_param_array(decoder, int, NULL, 0444);
Trent Piepho45bdcef2009-01-12 13:09:46 -030072MODULE_PARM_DESC(decoder, "Video decoder chip");
Linus Torvalds1da177e2005-04-16 15:20:36 -070073
74/*
75 The video mem address of the video card.
76 The driver has a little database for some videocards
77 to determine it from there. If your video card is not in there
78 you have either to give it to the driver as a parameter
79 or set in in a VIDIOCSFBUF ioctl
80 */
81
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -030082static unsigned long vidmem; /* default = 0 - Video memory base address */
Trent Piepho60e3cac2007-07-17 18:29:42 -030083module_param(vidmem, ulong, 0444);
84MODULE_PARM_DESC(vidmem, "Default video memory base address");
Linus Torvalds1da177e2005-04-16 15:20:36 -070085
86/*
87 Default input and video norm at startup of the driver.
88*/
89
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -030090static unsigned int default_input; /* default 0 = Composite, 1 = S-Video */
Trent Piepho60e3cac2007-07-17 18:29:42 -030091module_param(default_input, uint, 0444);
Linus Torvalds1da177e2005-04-16 15:20:36 -070092MODULE_PARM_DESC(default_input,
93 "Default input (0=Composite, 1=S-Video, 2=Internal)");
94
Martin Samuelssonfbe60da2006-04-27 10:17:00 -030095static int default_mux = 1; /* 6 Eyes input selection */
Trent Piepho60e3cac2007-07-17 18:29:42 -030096module_param(default_mux, int, 0644);
Martin Samuelssonfbe60da2006-04-27 10:17:00 -030097MODULE_PARM_DESC(default_mux,
98 "Default 6 Eyes mux setting (Input selection)");
99
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -0300100static int default_norm; /* default 0 = PAL, 1 = NTSC 2 = SECAM */
Trent Piepho60e3cac2007-07-17 18:29:42 -0300101module_param(default_norm, int, 0444);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700102MODULE_PARM_DESC(default_norm, "Default norm (0=PAL, 1=NTSC, 2=SECAM)");
103
Trent Piepho60e3cac2007-07-17 18:29:42 -0300104/* /dev/videoN, -1 for autodetect */
Trent Piepho45bdcef2009-01-12 13:09:46 -0300105static int video_nr[BUZ_MAX] = { [0 ... (BUZ_MAX-1)] = -1 };
Trent Piepho60e3cac2007-07-17 18:29:42 -0300106module_param_array(video_nr, int, NULL, 0444);
Trent Piepho45bdcef2009-01-12 13:09:46 -0300107MODULE_PARM_DESC(video_nr, "Video device number (-1=Auto)");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700108
Hans Verkuil497d7d02009-02-18 18:33:35 -0300109int v4l_nbufs = 4;
Hans Verkuile686e732009-02-20 15:06:59 -0300110int v4l_bufsize = 864; /* Everybody should be able to work with this setting */
Trent Piepho60e3cac2007-07-17 18:29:42 -0300111module_param(v4l_nbufs, int, 0644);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700112MODULE_PARM_DESC(v4l_nbufs, "Maximum number of V4L buffers to use");
Trent Piepho60e3cac2007-07-17 18:29:42 -0300113module_param(v4l_bufsize, int, 0644);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700114MODULE_PARM_DESC(v4l_bufsize, "Maximum size per V4L buffer (in kB)");
115
116int jpg_nbufs = 32;
117int jpg_bufsize = 512; /* max size for 100% quality full-PAL frame */
Trent Piepho60e3cac2007-07-17 18:29:42 -0300118module_param(jpg_nbufs, int, 0644);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700119MODULE_PARM_DESC(jpg_nbufs, "Maximum number of JPG buffers to use");
Trent Piepho60e3cac2007-07-17 18:29:42 -0300120module_param(jpg_bufsize, int, 0644);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700121MODULE_PARM_DESC(jpg_bufsize, "Maximum size per JPG buffer (in kB)");
122
123int pass_through = 0; /* 1=Pass through TV signal when device is not used */
124 /* 0=Show color bar when device is not used (LML33: only if lml33dpath=1) */
Trent Piepho60e3cac2007-07-17 18:29:42 -0300125module_param(pass_through, int, 0644);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700126MODULE_PARM_DESC(pass_through,
127 "Pass TV signal through to TV-out when idling");
128
Jean Delvare18b548c2007-07-17 18:29:41 -0300129int zr36067_debug = 1;
130module_param_named(debug, zr36067_debug, int, 0644);
131MODULE_PARM_DESC(debug, "Debug level (0-5)");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700132
133MODULE_DESCRIPTION("Zoran-36057/36067 JPEG codec driver");
134MODULE_AUTHOR("Serguei Miridonov");
135MODULE_LICENSE("GPL");
136
Trent Piepho17faeb22009-01-12 13:09:46 -0300137#define ZR_DEVICE(subven, subdev, data) { \
138 .vendor = PCI_VENDOR_ID_ZORAN, .device = PCI_DEVICE_ID_ZORAN_36057, \
139 .subvendor = (subven), .subdevice = (subdev), .driver_data = (data) }
140
Mauro Carvalho Chehabdbdf03b2009-01-08 23:27:32 -0300141static struct pci_device_id zr36067_pci_tbl[] = {
Trent Piepho17faeb22009-01-12 13:09:46 -0300142 ZR_DEVICE(PCI_VENDOR_ID_MIRO, PCI_DEVICE_ID_MIRO_DC10PLUS, DC10plus),
143 ZR_DEVICE(PCI_VENDOR_ID_MIRO, PCI_DEVICE_ID_MIRO_DC30PLUS, DC30plus),
144 ZR_DEVICE(PCI_VENDOR_ID_ELECTRONICDESIGNGMBH, PCI_DEVICE_ID_LML_33R10, LML33R10),
145 ZR_DEVICE(PCI_VENDOR_ID_IOMEGA, PCI_DEVICE_ID_IOMEGA_BUZ, BUZ),
146 ZR_DEVICE(PCI_ANY_ID, PCI_ANY_ID, NUM_CARDS),
Mauro Carvalho Chehabdbdf03b2009-01-08 23:27:32 -0300147 {0}
148};
149MODULE_DEVICE_TABLE(pci, zr36067_pci_tbl);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700150
Trent Piepho601139e2009-01-12 13:09:46 -0300151static unsigned int zoran_num; /* number of cards found */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700152
153/* videocodec bus functions ZR36060 */
154static u32
155zr36060_read (struct videocodec *codec,
156 u16 reg)
157{
158 struct zoran *zr = (struct zoran *) codec->master_data->data;
159 __u32 data;
160
161 if (post_office_wait(zr)
162 || post_office_write(zr, 0, 1, reg >> 8)
163 || post_office_write(zr, 0, 2, reg & 0xff)) {
164 return -1;
165 }
166
167 data = post_office_read(zr, 0, 3) & 0xff;
168 return data;
169}
170
171static void
172zr36060_write (struct videocodec *codec,
173 u16 reg,
174 u32 val)
175{
176 struct zoran *zr = (struct zoran *) codec->master_data->data;
177
178 if (post_office_wait(zr)
179 || post_office_write(zr, 0, 1, reg >> 8)
180 || post_office_write(zr, 0, 2, reg & 0xff)) {
181 return;
182 }
183
184 post_office_write(zr, 0, 3, val & 0xff);
185}
186
187/* videocodec bus functions ZR36050 */
188static u32
189zr36050_read (struct videocodec *codec,
190 u16 reg)
191{
192 struct zoran *zr = (struct zoran *) codec->master_data->data;
193 __u32 data;
194
195 if (post_office_wait(zr)
196 || post_office_write(zr, 1, 0, reg >> 2)) { // reg. HIGHBYTES
197 return -1;
198 }
199
200 data = post_office_read(zr, 0, reg & 0x03) & 0xff; // reg. LOWBYTES + read
201 return data;
202}
203
204static void
205zr36050_write (struct videocodec *codec,
206 u16 reg,
207 u32 val)
208{
209 struct zoran *zr = (struct zoran *) codec->master_data->data;
210
211 if (post_office_wait(zr)
212 || post_office_write(zr, 1, 0, reg >> 2)) { // reg. HIGHBYTES
213 return;
214 }
215
216 post_office_write(zr, 0, reg & 0x03, val & 0xff); // reg. LOWBYTES + wr. data
217}
218
219/* videocodec bus functions ZR36016 */
220static u32
221zr36016_read (struct videocodec *codec,
222 u16 reg)
223{
224 struct zoran *zr = (struct zoran *) codec->master_data->data;
225 __u32 data;
226
227 if (post_office_wait(zr)) {
228 return -1;
229 }
230
231 data = post_office_read(zr, 2, reg & 0x03) & 0xff; // read
232 return data;
233}
234
235/* hack for in zoran_device.c */
236void
237zr36016_write (struct videocodec *codec,
238 u16 reg,
239 u32 val)
240{
241 struct zoran *zr = (struct zoran *) codec->master_data->data;
242
243 if (post_office_wait(zr)) {
244 return;
245 }
246
247 post_office_write(zr, 2, reg & 0x03, val & 0x0ff); // wr. data
248}
249
250/*
251 * Board specific information
252 */
253
254static void
255dc10_init (struct zoran *zr)
256{
Trent Piephoc61402b2009-03-10 23:28:33 -0300257 dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700258
259 /* Pixel clock selection */
260 GPIO(zr, 4, 0);
261 GPIO(zr, 5, 1);
262 /* Enable the video bus sync signals */
263 GPIO(zr, 7, 0);
264}
265
266static void
267dc10plus_init (struct zoran *zr)
268{
Trent Piephoc61402b2009-03-10 23:28:33 -0300269 dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700270}
271
272static void
273buz_init (struct zoran *zr)
274{
Trent Piephoc61402b2009-03-10 23:28:33 -0300275 dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700276
277 /* some stuff from Iomega */
278 pci_write_config_dword(zr->pci_dev, 0xfc, 0x90680f15);
279 pci_write_config_dword(zr->pci_dev, 0x0c, 0x00012020);
280 pci_write_config_dword(zr->pci_dev, 0xe8, 0xc0200000);
281}
282
283static void
284lml33_init (struct zoran *zr)
285{
Trent Piephoc61402b2009-03-10 23:28:33 -0300286 dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700287
288 GPIO(zr, 2, 1); // Set Composite input/output
289}
290
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300291static void
292avs6eyes_init (struct zoran *zr)
293{
294 // AverMedia 6-Eyes original driver by Christer Weinigel
295
296 // Lifted straight from Christer's old driver and
297 // modified slightly by Martin Samuelsson.
298
299 int mux = default_mux; /* 1 = BT866, 7 = VID1 */
300
301 GPIO(zr, 4, 1); /* Bt866 SLEEP on */
302 udelay(2);
303
304 GPIO(zr, 0, 1); /* ZR36060 /RESET on */
305 GPIO(zr, 1, 0); /* ZR36060 /SLEEP on */
306 GPIO(zr, 2, mux & 1); /* MUX S0 */
307 GPIO(zr, 3, 0); /* /FRAME on */
308 GPIO(zr, 4, 0); /* Bt866 SLEEP off */
309 GPIO(zr, 5, mux & 2); /* MUX S1 */
310 GPIO(zr, 6, 0); /* ? */
311 GPIO(zr, 7, mux & 4); /* MUX S2 */
312
313}
314
Linus Torvalds1da177e2005-04-16 15:20:36 -0700315static char *
Linus Torvalds1da177e2005-04-16 15:20:36 -0700316codecid_to_modulename (u16 codecid)
317{
318 char *name = NULL;
319
320 switch (codecid) {
321 case CODEC_TYPE_ZR36060:
322 name = "zr36060";
323 break;
324 case CODEC_TYPE_ZR36050:
325 name = "zr36050";
326 break;
327 case CODEC_TYPE_ZR36016:
328 name = "zr36016";
329 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700330 }
331
332 return name;
333}
334
335// struct tvnorm {
336// u16 Wt, Wa, HStart, HSyncStart, Ht, Ha, VStart;
337// };
338
339static struct tvnorm f50sqpixel = { 944, 768, 83, 880, 625, 576, 16 };
340static struct tvnorm f60sqpixel = { 780, 640, 51, 716, 525, 480, 12 };
341static struct tvnorm f50ccir601 = { 864, 720, 75, 804, 625, 576, 18 };
342static struct tvnorm f60ccir601 = { 858, 720, 57, 788, 525, 480, 16 };
343
344static struct tvnorm f50ccir601_lml33 = { 864, 720, 75+34, 804, 625, 576, 18 };
345static struct tvnorm f60ccir601_lml33 = { 858, 720, 57+34, 788, 525, 480, 16 };
346
347/* The DC10 (57/16/50) uses VActive as HSync, so HStart must be 0 */
348static struct tvnorm f50sqpixel_dc10 = { 944, 768, 0, 880, 625, 576, 0 };
349static struct tvnorm f60sqpixel_dc10 = { 780, 640, 0, 716, 525, 480, 12 };
350
351/* FIXME: I cannot swap U and V in saa7114, so i do one
352 * pixel left shift in zoran (75 -> 74)
353 * (Maxim Yevtyushkin <max@linuxmedialabs.com>) */
354static struct tvnorm f50ccir601_lm33r10 = { 864, 720, 74+54, 804, 625, 576, 18 };
355static struct tvnorm f60ccir601_lm33r10 = { 858, 720, 56+54, 788, 525, 480, 16 };
356
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300357/* FIXME: The ks0127 seem incapable of swapping U and V, too, which is why I
358 * copy Maxim's left shift hack for the 6 Eyes.
359 *
360 * Christer's driver used the unshifted norms, though...
361 * /Sam */
362static struct tvnorm f50ccir601_avs6eyes = { 864, 720, 74, 804, 625, 576, 18 };
363static struct tvnorm f60ccir601_avs6eyes = { 858, 720, 56, 788, 525, 480, 16 };
364
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300365static const unsigned short vpx3220_addrs[] = { 0x43, 0x47, I2C_CLIENT_END };
366static const unsigned short saa7110_addrs[] = { 0x4e, 0x4f, I2C_CLIENT_END };
367static const unsigned short saa7111_addrs[] = { 0x25, 0x24, I2C_CLIENT_END };
368static const unsigned short saa7114_addrs[] = { 0x21, 0x20, I2C_CLIENT_END };
369static const unsigned short adv717x_addrs[] = { 0x6a, 0x6b, 0x2a, 0x2b, I2C_CLIENT_END };
370static const unsigned short ks0127_addrs[] = { 0x6c, 0x6d, I2C_CLIENT_END };
371static const unsigned short saa7185_addrs[] = { 0x44, I2C_CLIENT_END };
372static const unsigned short bt819_addrs[] = { 0x45, I2C_CLIENT_END };
373static const unsigned short bt856_addrs[] = { 0x44, I2C_CLIENT_END };
374static const unsigned short bt866_addrs[] = { 0x44, I2C_CLIENT_END };
375
Linus Torvalds1da177e2005-04-16 15:20:36 -0700376static struct card_info zoran_cards[NUM_CARDS] __devinitdata = {
377 {
378 .type = DC10_old,
379 .name = "DC10(old)",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300380 .i2c_decoder = "vpx3220a",
381 .mod_decoder = "vpx3220",
382 .addrs_decoder = vpx3220_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700383 .video_codec = CODEC_TYPE_ZR36050,
384 .video_vfe = CODEC_TYPE_ZR36016,
385
386 .inputs = 3,
387 .input = {
388 { 1, "Composite" },
389 { 2, "S-Video" },
390 { 0, "Internal/comp" }
391 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300392 .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700393 .tvn = {
394 &f50sqpixel_dc10,
395 &f60sqpixel_dc10,
396 &f50sqpixel_dc10
397 },
398 .jpeg_int = 0,
399 .vsync_int = ZR36057_ISR_GIRQ1,
400 .gpio = { 2, 1, -1, 3, 7, 0, 4, 5 },
401 .gpio_pol = { 0, 0, 0, 1, 0, 0, 0, 0 },
402 .gpcs = { -1, 0 },
403 .vfe_pol = { 0, 0, 0, 0, 0, 0, 0, 0 },
404 .gws_not_connected = 0,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300405 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700406 .init = &dc10_init,
407 }, {
408 .type = DC10_new,
409 .name = "DC10(new)",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300410 .i2c_decoder = "saa7110",
411 .mod_decoder = "saa7110",
412 .addrs_decoder = saa7110_addrs,
413 .i2c_encoder = "adv7175",
414 .mod_encoder = "adv7175",
415 .addrs_encoder = adv717x_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700416 .video_codec = CODEC_TYPE_ZR36060,
417
418 .inputs = 3,
419 .input = {
420 { 0, "Composite" },
421 { 7, "S-Video" },
422 { 5, "Internal/comp" }
423 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300424 .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700425 .tvn = {
426 &f50sqpixel,
427 &f60sqpixel,
428 &f50sqpixel},
429 .jpeg_int = ZR36057_ISR_GIRQ0,
430 .vsync_int = ZR36057_ISR_GIRQ1,
431 .gpio = { 3, 0, 6, 1, 2, -1, 4, 5 },
432 .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 },
433 .gpcs = { -1, 1},
434 .vfe_pol = { 1, 1, 1, 1, 0, 0, 0, 0 },
435 .gws_not_connected = 0,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300436 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700437 .init = &dc10plus_init,
438 }, {
439 .type = DC10plus,
440 .name = "DC10plus",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300441 .i2c_decoder = "saa7110",
442 .mod_decoder = "saa7110",
443 .addrs_decoder = saa7110_addrs,
444 .i2c_encoder = "adv7175",
445 .mod_encoder = "adv7175",
446 .addrs_encoder = adv717x_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700447 .video_codec = CODEC_TYPE_ZR36060,
448
449 .inputs = 3,
450 .input = {
451 { 0, "Composite" },
452 { 7, "S-Video" },
453 { 5, "Internal/comp" }
454 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300455 .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700456 .tvn = {
457 &f50sqpixel,
458 &f60sqpixel,
459 &f50sqpixel
460 },
461 .jpeg_int = ZR36057_ISR_GIRQ0,
462 .vsync_int = ZR36057_ISR_GIRQ1,
463 .gpio = { 3, 0, 6, 1, 2, -1, 4, 5 },
464 .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 },
465 .gpcs = { -1, 1 },
466 .vfe_pol = { 1, 1, 1, 1, 0, 0, 0, 0 },
467 .gws_not_connected = 0,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300468 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700469 .init = &dc10plus_init,
470 }, {
471 .type = DC30,
472 .name = "DC30",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300473 .i2c_decoder = "vpx3220a",
474 .mod_decoder = "vpx3220",
475 .addrs_decoder = vpx3220_addrs,
476 .i2c_encoder = "adv7175",
477 .mod_encoder = "adv7175",
478 .addrs_encoder = adv717x_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700479 .video_codec = CODEC_TYPE_ZR36050,
480 .video_vfe = CODEC_TYPE_ZR36016,
481
482 .inputs = 3,
483 .input = {
484 { 1, "Composite" },
485 { 2, "S-Video" },
486 { 0, "Internal/comp" }
487 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300488 .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700489 .tvn = {
490 &f50sqpixel_dc10,
491 &f60sqpixel_dc10,
492 &f50sqpixel_dc10
493 },
494 .jpeg_int = 0,
495 .vsync_int = ZR36057_ISR_GIRQ1,
496 .gpio = { 2, 1, -1, 3, 7, 0, 4, 5 },
497 .gpio_pol = { 0, 0, 0, 1, 0, 0, 0, 0 },
498 .gpcs = { -1, 0 },
499 .vfe_pol = { 0, 0, 0, 0, 0, 0, 0, 0 },
500 .gws_not_connected = 0,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300501 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700502 .init = &dc10_init,
503 }, {
504 .type = DC30plus,
505 .name = "DC30plus",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300506 .i2c_decoder = "vpx3220a",
507 .mod_decoder = "vpx3220",
508 .addrs_decoder = vpx3220_addrs,
509 .i2c_encoder = "adv7175",
510 .mod_encoder = "adv7175",
511 .addrs_encoder = adv717x_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700512 .video_codec = CODEC_TYPE_ZR36050,
513 .video_vfe = CODEC_TYPE_ZR36016,
514
515 .inputs = 3,
516 .input = {
517 { 1, "Composite" },
518 { 2, "S-Video" },
519 { 0, "Internal/comp" }
520 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300521 .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700522 .tvn = {
523 &f50sqpixel_dc10,
524 &f60sqpixel_dc10,
525 &f50sqpixel_dc10
526 },
527 .jpeg_int = 0,
528 .vsync_int = ZR36057_ISR_GIRQ1,
529 .gpio = { 2, 1, -1, 3, 7, 0, 4, 5 },
530 .gpio_pol = { 0, 0, 0, 1, 0, 0, 0, 0 },
531 .gpcs = { -1, 0 },
532 .vfe_pol = { 0, 0, 0, 0, 0, 0, 0, 0 },
533 .gws_not_connected = 0,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300534 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700535 .init = &dc10_init,
536 }, {
537 .type = LML33,
538 .name = "LML33",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300539 .i2c_decoder = "bt819a",
540 .mod_decoder = "bt819",
541 .addrs_decoder = bt819_addrs,
542 .i2c_encoder = "bt856",
543 .mod_encoder = "bt856",
544 .addrs_encoder = bt856_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700545 .video_codec = CODEC_TYPE_ZR36060,
546
547 .inputs = 2,
548 .input = {
549 { 0, "Composite" },
550 { 7, "S-Video" }
551 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300552 .norms = V4L2_STD_NTSC|V4L2_STD_PAL,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700553 .tvn = {
554 &f50ccir601_lml33,
555 &f60ccir601_lml33,
556 NULL
557 },
558 .jpeg_int = ZR36057_ISR_GIRQ1,
559 .vsync_int = ZR36057_ISR_GIRQ0,
560 .gpio = { 1, -1, 3, 5, 7, -1, -1, -1 },
561 .gpio_pol = { 0, 0, 0, 0, 1, 0, 0, 0 },
562 .gpcs = { 3, 1 },
563 .vfe_pol = { 1, 1, 0, 0, 0, 1, 0, 0 },
564 .gws_not_connected = 1,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300565 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700566 .init = &lml33_init,
567 }, {
568 .type = LML33R10,
569 .name = "LML33R10",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300570 .i2c_decoder = "saa7114",
571 .mod_decoder = "saa7115",
572 .addrs_decoder = saa7114_addrs,
573 .i2c_encoder = "adv7170",
574 .mod_encoder = "adv7170",
575 .addrs_encoder = adv717x_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700576 .video_codec = CODEC_TYPE_ZR36060,
577
578 .inputs = 2,
579 .input = {
580 { 0, "Composite" },
581 { 7, "S-Video" }
582 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300583 .norms = V4L2_STD_NTSC|V4L2_STD_PAL,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700584 .tvn = {
585 &f50ccir601_lm33r10,
586 &f60ccir601_lm33r10,
587 NULL
588 },
589 .jpeg_int = ZR36057_ISR_GIRQ1,
590 .vsync_int = ZR36057_ISR_GIRQ0,
591 .gpio = { 1, -1, 3, 5, 7, -1, -1, -1 },
592 .gpio_pol = { 0, 0, 0, 0, 1, 0, 0, 0 },
593 .gpcs = { 3, 1 },
594 .vfe_pol = { 1, 1, 0, 0, 0, 1, 0, 0 },
595 .gws_not_connected = 1,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300596 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700597 .init = &lml33_init,
598 }, {
599 .type = BUZ,
600 .name = "Buz",
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300601 .i2c_decoder = "saa7111",
602 .mod_decoder = "saa7115",
603 .addrs_decoder = saa7111_addrs,
604 .i2c_encoder = "saa7185",
605 .mod_encoder = "saa7185",
606 .addrs_encoder = saa7185_addrs,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700607 .video_codec = CODEC_TYPE_ZR36060,
608
609 .inputs = 2,
610 .input = {
611 { 3, "Composite" },
612 { 7, "S-Video" }
613 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300614 .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700615 .tvn = {
616 &f50ccir601,
617 &f60ccir601,
618 &f50ccir601
619 },
620 .jpeg_int = ZR36057_ISR_GIRQ1,
621 .vsync_int = ZR36057_ISR_GIRQ0,
622 .gpio = { 1, -1, 3, -1, -1, -1, -1, -1 },
623 .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 },
624 .gpcs = { 3, 1 },
625 .vfe_pol = { 1, 1, 0, 0, 0, 1, 0, 0 },
626 .gws_not_connected = 1,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300627 .input_mux = 0,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700628 .init = &buz_init,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300629 }, {
630 .type = AVS6EYES,
631 .name = "6-Eyes",
632 /* AverMedia chose not to brand the 6-Eyes. Thus it
633 can't be autodetected, and requires card=x. */
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300634 .i2c_decoder = "ks0127",
635 .mod_decoder = "ks0127",
636 .addrs_decoder = ks0127_addrs,
637 .i2c_encoder = "bt866",
638 .mod_encoder = "bt866",
639 .addrs_encoder = bt866_addrs,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300640 .video_codec = CODEC_TYPE_ZR36060,
641
642 .inputs = 10,
643 .input = {
644 { 0, "Composite 1" },
645 { 1, "Composite 2" },
646 { 2, "Composite 3" },
647 { 4, "Composite 4" },
648 { 5, "Composite 5" },
649 { 6, "Composite 6" },
650 { 8, "S-Video 1" },
651 { 9, "S-Video 2" },
652 {10, "S-Video 3" },
653 {15, "YCbCr" }
654 },
Hans Verkuil107063c2009-02-18 17:26:06 -0300655 .norms = V4L2_STD_NTSC|V4L2_STD_PAL,
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300656 .tvn = {
657 &f50ccir601_avs6eyes,
658 &f60ccir601_avs6eyes,
659 NULL
660 },
661 .jpeg_int = ZR36057_ISR_GIRQ1,
662 .vsync_int = ZR36057_ISR_GIRQ0,
663 .gpio = { 1, 0, 3, -1, -1, -1, -1, -1 },// Validity unknown /Sam
664 .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, // Validity unknown /Sam
665 .gpcs = { 3, 1 }, // Validity unknown /Sam
666 .vfe_pol = { 1, 0, 0, 0, 0, 1, 0, 0 }, // Validity unknown /Sam
667 .gws_not_connected = 1,
668 .input_mux = 1,
669 .init = &avs6eyes_init,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700670 }
Martin Samuelssonfbe60da2006-04-27 10:17:00 -0300671
Linus Torvalds1da177e2005-04-16 15:20:36 -0700672};
673
674/*
675 * I2C functions
676 */
677/* software I2C functions */
678static int
679zoran_i2c_getsda (void *data)
680{
681 struct zoran *zr = (struct zoran *) data;
682
683 return (btread(ZR36057_I2CBR) >> 1) & 1;
684}
685
686static int
687zoran_i2c_getscl (void *data)
688{
689 struct zoran *zr = (struct zoran *) data;
690
691 return btread(ZR36057_I2CBR) & 1;
692}
693
694static void
695zoran_i2c_setsda (void *data,
696 int state)
697{
698 struct zoran *zr = (struct zoran *) data;
699
700 if (state)
701 zr->i2cbr |= 2;
702 else
703 zr->i2cbr &= ~2;
704 btwrite(zr->i2cbr, ZR36057_I2CBR);
705}
706
707static void
708zoran_i2c_setscl (void *data,
709 int state)
710{
711 struct zoran *zr = (struct zoran *) data;
712
713 if (state)
714 zr->i2cbr |= 1;
715 else
716 zr->i2cbr &= ~1;
717 btwrite(zr->i2cbr, ZR36057_I2CBR);
718}
719
Jean Delvare62751632008-06-12 13:20:46 -0300720static const struct i2c_algo_bit_data zoran_i2c_bit_data_template = {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700721 .setsda = zoran_i2c_setsda,
722 .setscl = zoran_i2c_setscl,
723 .getsda = zoran_i2c_getsda,
724 .getscl = zoran_i2c_getscl,
725 .udelay = 10,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700726 .timeout = 100,
727};
728
Linus Torvalds1da177e2005-04-16 15:20:36 -0700729static int
730zoran_register_i2c (struct zoran *zr)
731{
732 memcpy(&zr->i2c_algo, &zoran_i2c_bit_data_template,
733 sizeof(struct i2c_algo_bit_data));
734 zr->i2c_algo.data = zr;
Jean Delvare62751632008-06-12 13:20:46 -0300735 zr->i2c_adapter.id = I2C_HW_B_ZR36067;
Jean Delvare62751632008-06-12 13:20:46 -0300736 strlcpy(zr->i2c_adapter.name, ZR_DEVNAME(zr),
737 sizeof(zr->i2c_adapter.name));
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -0300738 i2c_set_adapdata(&zr->i2c_adapter, &zr->v4l2_dev);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700739 zr->i2c_adapter.algo_data = &zr->i2c_algo;
Jean Delvare12a917f2007-02-13 22:09:03 +0100740 zr->i2c_adapter.dev.parent = &zr->pci_dev->dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700741 return i2c_bit_add_bus(&zr->i2c_adapter);
742}
743
744static void
745zoran_unregister_i2c (struct zoran *zr)
746{
Jean Delvare32697112006-12-10 21:21:33 +0100747 i2c_del_adapter(&zr->i2c_adapter);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700748}
749
750/* Check a zoran_params struct for correctness, insert default params */
751
752int
753zoran_check_jpg_settings (struct zoran *zr,
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300754 struct zoran_jpg_settings *settings,
755 int try)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700756{
757 int err = 0, err0 = 0;
758
759 dprintk(4,
760 KERN_DEBUG
Trent Piephoc61402b2009-03-10 23:28:33 -0300761 "%s: %s - dec: %d, Hdcm: %d, Vdcm: %d, Tdcm: %d\n",
762 ZR_DEVNAME(zr), __func__, settings->decimation, settings->HorDcm,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700763 settings->VerDcm, settings->TmpDcm);
764 dprintk(4,
765 KERN_DEBUG
Trent Piephoc61402b2009-03-10 23:28:33 -0300766 "%s: %s - x: %d, y: %d, w: %d, y: %d\n",
767 ZR_DEVNAME(zr), __func__, settings->img_x, settings->img_y,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700768 settings->img_width, settings->img_height);
769 /* Check decimation, set default values for decimation = 1, 2, 4 */
770 switch (settings->decimation) {
771 case 1:
772
773 settings->HorDcm = 1;
774 settings->VerDcm = 1;
775 settings->TmpDcm = 1;
776 settings->field_per_buff = 2;
777 settings->img_x = 0;
778 settings->img_y = 0;
779 settings->img_width = BUZ_MAX_WIDTH;
780 settings->img_height = BUZ_MAX_HEIGHT / 2;
781 break;
782 case 2:
783
784 settings->HorDcm = 2;
785 settings->VerDcm = 1;
786 settings->TmpDcm = 2;
787 settings->field_per_buff = 1;
788 settings->img_x = (BUZ_MAX_WIDTH == 720) ? 8 : 0;
789 settings->img_y = 0;
790 settings->img_width =
791 (BUZ_MAX_WIDTH == 720) ? 704 : BUZ_MAX_WIDTH;
792 settings->img_height = BUZ_MAX_HEIGHT / 2;
793 break;
794 case 4:
795
796 if (zr->card.type == DC10_new) {
797 dprintk(1,
798 KERN_DEBUG
Trent Piephoc61402b2009-03-10 23:28:33 -0300799 "%s: %s - HDec by 4 is not supported on the DC10\n",
800 ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700801 err0++;
802 break;
803 }
804
805 settings->HorDcm = 4;
806 settings->VerDcm = 2;
807 settings->TmpDcm = 2;
808 settings->field_per_buff = 1;
809 settings->img_x = (BUZ_MAX_WIDTH == 720) ? 8 : 0;
810 settings->img_y = 0;
811 settings->img_width =
812 (BUZ_MAX_WIDTH == 720) ? 704 : BUZ_MAX_WIDTH;
813 settings->img_height = BUZ_MAX_HEIGHT / 2;
814 break;
815 case 0:
816
817 /* We have to check the data the user has set */
818
819 if (settings->HorDcm != 1 && settings->HorDcm != 2 &&
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300820 (zr->card.type == DC10_new || settings->HorDcm != 4)) {
821 settings->HorDcm = clamp(settings->HorDcm, 1, 2);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700822 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300823 }
824 if (settings->VerDcm != 1 && settings->VerDcm != 2) {
825 settings->VerDcm = clamp(settings->VerDcm, 1, 2);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700826 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300827 }
828 if (settings->TmpDcm != 1 && settings->TmpDcm != 2) {
829 settings->TmpDcm = clamp(settings->TmpDcm, 1, 2);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700830 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300831 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700832 if (settings->field_per_buff != 1 &&
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300833 settings->field_per_buff != 2) {
834 settings->field_per_buff = clamp(settings->field_per_buff, 1, 2);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700835 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300836 }
837 if (settings->img_x < 0) {
838 settings->img_x = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700839 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300840 }
841 if (settings->img_y < 0) {
842 settings->img_y = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700843 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300844 }
845 if (settings->img_width < 0 || settings->img_width > BUZ_MAX_WIDTH) {
846 settings->img_width = clamp(settings->img_width, 0, (int)BUZ_MAX_WIDTH);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700847 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300848 }
849 if (settings->img_height < 0 || settings->img_height > BUZ_MAX_HEIGHT / 2) {
850 settings->img_height = clamp(settings->img_height, 0, BUZ_MAX_HEIGHT / 2);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700851 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300852 }
853 if (settings->img_x + settings->img_width > BUZ_MAX_WIDTH) {
854 settings->img_x = BUZ_MAX_WIDTH - settings->img_width;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700855 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300856 }
857 if (settings->img_y + settings->img_height > BUZ_MAX_HEIGHT / 2) {
858 settings->img_y = BUZ_MAX_HEIGHT / 2 - settings->img_height;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700859 err0++;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300860 }
861 if (settings->img_width % (16 * settings->HorDcm) != 0) {
862 settings->img_width -= settings->img_width % (16 * settings->HorDcm);
863 if (settings->img_width == 0)
864 settings->img_width = 16 * settings->HorDcm;
865 err0++;
866 }
867 if (settings->img_height % (8 * settings->VerDcm) != 0) {
868 settings->img_height -= settings->img_height % (8 * settings->VerDcm);
869 if (settings->img_height == 0)
870 settings->img_height = 8 * settings->VerDcm;
871 err0++;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700872 }
873
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300874 if (!try && err0) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700875 dprintk(1,
876 KERN_ERR
Trent Piephoc61402b2009-03-10 23:28:33 -0300877 "%s: %s - error in params for decimation = 0\n",
878 ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700879 err++;
880 }
881 break;
882 default:
883 dprintk(1,
884 KERN_ERR
Trent Piephoc61402b2009-03-10 23:28:33 -0300885 "%s: %s - decimation = %d, must be 0, 1, 2 or 4\n",
886 ZR_DEVNAME(zr), __func__, settings->decimation);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700887 err++;
888 break;
889 }
890
891 if (settings->jpg_comp.quality > 100)
892 settings->jpg_comp.quality = 100;
893 if (settings->jpg_comp.quality < 5)
894 settings->jpg_comp.quality = 5;
895 if (settings->jpg_comp.APPn < 0)
896 settings->jpg_comp.APPn = 0;
897 if (settings->jpg_comp.APPn > 15)
898 settings->jpg_comp.APPn = 15;
899 if (settings->jpg_comp.APP_len < 0)
900 settings->jpg_comp.APP_len = 0;
901 if (settings->jpg_comp.APP_len > 60)
902 settings->jpg_comp.APP_len = 60;
903 if (settings->jpg_comp.COM_len < 0)
904 settings->jpg_comp.COM_len = 0;
905 if (settings->jpg_comp.COM_len > 60)
906 settings->jpg_comp.COM_len = 60;
907 if (err)
908 return -EINVAL;
909 return 0;
910}
911
912void
913zoran_open_init_params (struct zoran *zr)
914{
915 int i;
916
917 /* User must explicitly set a window */
918 zr->overlay_settings.is_set = 0;
919 zr->overlay_mask = NULL;
920 zr->overlay_active = ZORAN_FREE;
921
922 zr->v4l_memgrab_active = 0;
923 zr->v4l_overlay_active = 0;
924 zr->v4l_grab_frame = NO_GRAB_ACTIVE;
925 zr->v4l_grab_seq = 0;
926 zr->v4l_settings.width = 192;
927 zr->v4l_settings.height = 144;
Jean Delvarec014ec92008-09-07 05:21:34 -0300928 zr->v4l_settings.format = &zoran_formats[7]; /* YUY2 - YUV-4:2:2 packed */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700929 zr->v4l_settings.bytesperline =
930 zr->v4l_settings.width *
931 ((zr->v4l_settings.format->depth + 7) / 8);
932
933 /* DMA ring stuff for V4L */
934 zr->v4l_pend_tail = 0;
935 zr->v4l_pend_head = 0;
936 zr->v4l_sync_tail = 0;
937 zr->v4l_buffers.active = ZORAN_FREE;
938 for (i = 0; i < VIDEO_MAX_FRAME; i++) {
939 zr->v4l_buffers.buffer[i].state = BUZ_STATE_USER; /* nothing going on */
940 }
941 zr->v4l_buffers.allocated = 0;
942
943 for (i = 0; i < BUZ_MAX_FRAME; i++) {
944 zr->jpg_buffers.buffer[i].state = BUZ_STATE_USER; /* nothing going on */
945 }
946 zr->jpg_buffers.active = ZORAN_FREE;
947 zr->jpg_buffers.allocated = 0;
948 /* Set necessary params and call zoran_check_jpg_settings to set the defaults */
949 zr->jpg_settings.decimation = 1;
950 zr->jpg_settings.jpg_comp.quality = 50; /* default compression factor 8 */
951 if (zr->card.type != BUZ)
952 zr->jpg_settings.odd_even = 1;
953 else
954 zr->jpg_settings.odd_even = 0;
955 zr->jpg_settings.jpg_comp.APPn = 0;
956 zr->jpg_settings.jpg_comp.APP_len = 0; /* No APPn marker */
957 memset(zr->jpg_settings.jpg_comp.APP_data, 0,
958 sizeof(zr->jpg_settings.jpg_comp.APP_data));
959 zr->jpg_settings.jpg_comp.COM_len = 0; /* No COM marker */
960 memset(zr->jpg_settings.jpg_comp.COM_data, 0,
961 sizeof(zr->jpg_settings.jpg_comp.COM_data));
962 zr->jpg_settings.jpg_comp.jpeg_markers =
963 JPEG_MARKER_DHT | JPEG_MARKER_DQT;
Hans Verkuil0ba514d2009-02-18 17:11:17 -0300964 i = zoran_check_jpg_settings(zr, &zr->jpg_settings, 0);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700965 if (i)
Trent Piephoc61402b2009-03-10 23:28:33 -0300966 dprintk(1, KERN_ERR "%s: %s internal error\n",
967 ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700968
969 clear_interrupt_counters(zr);
970 zr->testing = 0;
971}
972
973static void __devinit
974test_interrupts (struct zoran *zr)
975{
976 DEFINE_WAIT(wait);
977 int timeout, icr;
978
979 clear_interrupt_counters(zr);
980
981 zr->testing = 1;
982 icr = btread(ZR36057_ICR);
983 btwrite(0x78000000 | ZR36057_ICR_IntPinEn, ZR36057_ICR);
984 prepare_to_wait(&zr->test_q, &wait, TASK_INTERRUPTIBLE);
985 timeout = schedule_timeout(HZ);
986 finish_wait(&zr->test_q, &wait);
987 btwrite(0, ZR36057_ICR);
988 btwrite(0x78000000, ZR36057_ISR);
989 zr->testing = 0;
990 dprintk(5, KERN_INFO "%s: Testing interrupts...\n", ZR_DEVNAME(zr));
991 if (timeout) {
992 dprintk(1, ": time spent: %d\n", 1 * HZ - timeout);
993 }
Jean Delvare18b548c2007-07-17 18:29:41 -0300994 if (zr36067_debug > 1)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700995 print_interrupts(zr);
996 btwrite(icr, ZR36057_ICR);
997}
998
999static int __devinit
1000zr36057_init (struct zoran *zr)
1001{
Jean Delvaredaf72f42006-03-22 03:48:37 -03001002 int j, err;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001003
1004 dprintk(1,
1005 KERN_INFO
Trent Piephoc61402b2009-03-10 23:28:33 -03001006 "%s: %s - initializing card[%d], zr=%p\n",
1007 ZR_DEVNAME(zr), __func__, zr->id, zr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001008
1009 /* default setup of all parameters which will persist between opens */
1010 zr->user = 0;
1011
1012 init_waitqueue_head(&zr->v4l_capq);
1013 init_waitqueue_head(&zr->jpg_capq);
1014 init_waitqueue_head(&zr->test_q);
1015 zr->jpg_buffers.allocated = 0;
1016 zr->v4l_buffers.allocated = 0;
1017
Hans Verkuil7f6adea2009-02-19 17:31:17 -03001018 zr->vbuf_base = (void *) vidmem;
1019 zr->vbuf_width = 0;
1020 zr->vbuf_height = 0;
1021 zr->vbuf_depth = 0;
1022 zr->vbuf_bytesperline = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001023
1024 /* Avoid nonsense settings from user for default input/norm */
Hans Verkuil7f6adea2009-02-19 17:31:17 -03001025 if (default_norm < 0 && default_norm > 2)
1026 default_norm = 0;
1027 if (default_norm == 0) {
Hans Verkuil107063c2009-02-18 17:26:06 -03001028 zr->norm = V4L2_STD_PAL;
1029 zr->timing = zr->card.tvn[0];
Hans Verkuil7f6adea2009-02-19 17:31:17 -03001030 } else if (default_norm == 1) {
Hans Verkuil107063c2009-02-18 17:26:06 -03001031 zr->norm = V4L2_STD_NTSC;
1032 zr->timing = zr->card.tvn[1];
1033 } else {
1034 zr->norm = V4L2_STD_SECAM;
1035 zr->timing = zr->card.tvn[2];
1036 }
1037 if (zr->timing == NULL) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001038 dprintk(1,
1039 KERN_WARNING
Trent Piephoc61402b2009-03-10 23:28:33 -03001040 "%s: %s - default TV standard not supported by hardware. PAL will be used.\n",
1041 ZR_DEVNAME(zr), __func__);
Hans Verkuil107063c2009-02-18 17:26:06 -03001042 zr->norm = V4L2_STD_PAL;
1043 zr->timing = zr->card.tvn[0];
Linus Torvalds1da177e2005-04-16 15:20:36 -07001044 }
1045
Trent Piepho60e3cac2007-07-17 18:29:42 -03001046 if (default_input > zr->card.inputs-1) {
1047 dprintk(1,
1048 KERN_WARNING
1049 "%s: default_input value %d out of range (0-%d)\n",
1050 ZR_DEVNAME(zr), default_input, zr->card.inputs-1);
1051 default_input = 0;
1052 }
1053 zr->input = default_input;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001054
Linus Torvalds1da177e2005-04-16 15:20:36 -07001055 /* default setup (will be repeated at every open) */
1056 zoran_open_init_params(zr);
1057
1058 /* allocate memory *before* doing anything to the hardware
1059 * in case allocation fails */
Jean Delvaredaf72f42006-03-22 03:48:37 -03001060 zr->stat_com = kzalloc(BUZ_NUM_STAT_COM * 4, GFP_KERNEL);
1061 zr->video_dev = kmalloc(sizeof(struct video_device), GFP_KERNEL);
1062 if (!zr->stat_com || !zr->video_dev) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001063 dprintk(1,
1064 KERN_ERR
Trent Piephoc61402b2009-03-10 23:28:33 -03001065 "%s: %s - kmalloc (STAT_COM) failed\n",
1066 ZR_DEVNAME(zr), __func__);
Jean Delvaredaf72f42006-03-22 03:48:37 -03001067 err = -ENOMEM;
1068 goto exit_free;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001069 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001070 for (j = 0; j < BUZ_NUM_STAT_COM; j++) {
Al Viro9c169df2008-06-22 14:19:49 -03001071 zr->stat_com[j] = cpu_to_le32(1); /* mark as unavailable to zr36057 */
Linus Torvalds1da177e2005-04-16 15:20:36 -07001072 }
1073
1074 /*
1075 * Now add the template and register the device unit.
1076 */
Linus Torvalds1da177e2005-04-16 15:20:36 -07001077 memcpy(zr->video_dev, &zoran_template, sizeof(zoran_template));
Hans Verkuilaff88bc2009-02-18 13:52:24 -03001078 zr->video_dev->parent = &zr->pci_dev->dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001079 strcpy(zr->video_dev->name, ZR_DEVNAME(zr));
Trent Piepho60e3cac2007-07-17 18:29:42 -03001080 err = video_register_device(zr->video_dev, VFL_TYPE_GRABBER, video_nr[zr->id]);
Jean Delvaredaf72f42006-03-22 03:48:37 -03001081 if (err < 0)
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001082 goto exit_free;
Trent Piepho601139e2009-01-12 13:09:46 -03001083 video_set_drvdata(zr->video_dev, zr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001084
1085 zoran_init_hardware(zr);
Jean Delvare18b548c2007-07-17 18:29:41 -03001086 if (zr36067_debug > 2)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001087 detect_guest_activity(zr);
1088 test_interrupts(zr);
1089 if (!pass_through) {
Hans Verkuil107063c2009-02-18 17:26:06 -03001090 struct v4l2_routing route = { 2, 0 };
1091
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001092 decoder_call(zr, video, s_stream, 0);
1093 encoder_call(zr, video, s_routing, &route);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001094 }
1095
1096 zr->zoran_proc = NULL;
1097 zr->initialized = 1;
1098 return 0;
Jean Delvaredaf72f42006-03-22 03:48:37 -03001099
Jean Delvaredaf72f42006-03-22 03:48:37 -03001100exit_free:
1101 kfree(zr->stat_com);
1102 kfree(zr->video_dev);
1103 return err;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001104}
1105
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001106static void __devexit zoran_remove(struct pci_dev *pdev)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001107{
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001108 struct v4l2_device *v4l2_dev = dev_get_drvdata(&pdev->dev);
1109 struct zoran *zr = to_zoran(v4l2_dev);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001110
Linus Torvalds1da177e2005-04-16 15:20:36 -07001111 if (!zr->initialized)
Jean Delvare85b9b8a2008-07-14 09:51:03 -03001112 goto exit_free;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001113
Linus Torvalds1da177e2005-04-16 15:20:36 -07001114 /* unregister videocodec bus */
1115 if (zr->codec) {
1116 struct videocodec_master *master = zr->codec->master_data;
Jesper Juhl2ea75332005-11-07 01:01:31 -08001117
Linus Torvalds1da177e2005-04-16 15:20:36 -07001118 videocodec_detach(zr->codec);
Jesper Juhl2ea75332005-11-07 01:01:31 -08001119 kfree(master);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001120 }
1121 if (zr->vfe) {
1122 struct videocodec_master *master = zr->vfe->master_data;
Jesper Juhl2ea75332005-11-07 01:01:31 -08001123
Linus Torvalds1da177e2005-04-16 15:20:36 -07001124 videocodec_detach(zr->vfe);
Jesper Juhl2ea75332005-11-07 01:01:31 -08001125 kfree(master);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001126 }
1127
1128 /* unregister i2c bus */
1129 zoran_unregister_i2c(zr);
1130 /* disable PCI bus-mastering */
1131 zoran_set_pci_master(zr, 0);
1132 /* put chip into reset */
1133 btwrite(0, ZR36057_SPGPPCR);
1134 free_irq(zr->pci_dev->irq, zr);
1135 /* unmap and free memory */
Jean Delvaredaf72f42006-03-22 03:48:37 -03001136 kfree(zr->stat_com);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001137 zoran_proc_cleanup(zr);
1138 iounmap(zr->zr36057_mem);
1139 pci_disable_device(zr->pci_dev);
1140 video_unregister_device(zr->video_dev);
Jean Delvare85b9b8a2008-07-14 09:51:03 -03001141exit_free:
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001142 v4l2_device_unregister(&zr->v4l2_dev);
Jean Delvare85b9b8a2008-07-14 09:51:03 -03001143 kfree(zr);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001144}
1145
1146void
1147zoran_vdev_release (struct video_device *vdev)
1148{
1149 kfree(vdev);
1150}
1151
1152static struct videocodec_master * __devinit
1153zoran_setup_videocodec (struct zoran *zr,
1154 int type)
1155{
1156 struct videocodec_master *m = NULL;
1157
1158 m = kmalloc(sizeof(struct videocodec_master), GFP_KERNEL);
1159 if (!m) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001160 dprintk(1, KERN_ERR "%s: %s - no memory\n",
1161 ZR_DEVNAME(zr), __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001162 return m;
1163 }
1164
Mauro Carvalho Chehab22c4a4e2007-10-15 12:09:17 -03001165 /* magic and type are unused for master struct. Makes sense only at
1166 codec structs.
1167 In the past, .type were initialized to the old V4L1 .hardware
1168 value, as VID_HARDWARE_ZR36067
1169 */
1170 m->magic = 0L;
1171 m->type = 0;
1172
Linus Torvalds1da177e2005-04-16 15:20:36 -07001173 m->flags = CODEC_FLAG_ENCODER | CODEC_FLAG_DECODER;
1174 strncpy(m->name, ZR_DEVNAME(zr), sizeof(m->name));
1175 m->data = zr;
1176
1177 switch (type)
1178 {
1179 case CODEC_TYPE_ZR36060:
1180 m->readreg = zr36060_read;
1181 m->writereg = zr36060_write;
1182 m->flags |= CODEC_FLAG_JPEG | CODEC_FLAG_VFE;
1183 break;
1184 case CODEC_TYPE_ZR36050:
1185 m->readreg = zr36050_read;
1186 m->writereg = zr36050_write;
1187 m->flags |= CODEC_FLAG_JPEG;
1188 break;
1189 case CODEC_TYPE_ZR36016:
1190 m->readreg = zr36016_read;
1191 m->writereg = zr36016_write;
1192 m->flags |= CODEC_FLAG_VFE;
1193 break;
1194 }
1195
1196 return m;
1197}
1198
1199/*
Joe Perchesc84e6032008-02-03 17:18:59 +02001200 * Scan for a Buz card (actually for the PCI controller ZR36057),
Linus Torvalds1da177e2005-04-16 15:20:36 -07001201 * request the irq and map the io memory
1202 */
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001203static int __devinit zoran_probe(struct pci_dev *pdev,
1204 const struct pci_device_id *ent)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001205{
1206 unsigned char latency, need_latency;
1207 struct zoran *zr;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001208 int result;
1209 struct videocodec_master *master_vfe = NULL;
1210 struct videocodec_master *master_codec = NULL;
1211 int card_num;
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001212 char *codec_name, *vfe_name;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001213 unsigned int nr;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001214
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001215
Trent Piepho601139e2009-01-12 13:09:46 -03001216 nr = zoran_num++;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001217 if (nr >= BUZ_MAX) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001218 dprintk(1, KERN_ERR "%s: driver limited to %d card(s) maximum\n",
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001219 ZORAN_NAME, BUZ_MAX);
1220 return -ENOENT;
1221 }
1222
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001223 zr = kzalloc(sizeof(struct zoran), GFP_KERNEL);
1224 if (!zr) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001225 dprintk(1, KERN_ERR "%s: %s - kzalloc failed\n",
1226 ZORAN_NAME, __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001227 return -ENOMEM;
1228 }
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001229 if (v4l2_device_register(&pdev->dev, &zr->v4l2_dev))
1230 goto zr_free_mem;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001231 zr->pci_dev = pdev;
1232 zr->id = nr;
1233 snprintf(ZR_DEVNAME(zr), sizeof(ZR_DEVNAME(zr)), "MJPEG[%u]", zr->id);
1234 spin_lock_init(&zr->spinlock);
1235 mutex_init(&zr->resource_lock);
1236 if (pci_enable_device(pdev))
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001237 goto zr_unreg;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001238 pci_read_config_byte(zr->pci_dev, PCI_CLASS_REVISION, &zr->revision);
Trent Piepho17faeb22009-01-12 13:09:46 -03001239
1240 dprintk(1,
1241 KERN_INFO
Trent Piepho5e098b62009-01-12 13:09:46 -03001242 "%s: Zoran ZR360%c7 (rev %d), irq: %d, memory: 0x%08llx\n",
Trent Piepho17faeb22009-01-12 13:09:46 -03001243 ZR_DEVNAME(zr), zr->revision < 2 ? '5' : '6', zr->revision,
Trent Piepho5e098b62009-01-12 13:09:46 -03001244 zr->pci_dev->irq, (uint64_t)pci_resource_start(zr->pci_dev, 0));
Trent Piepho17faeb22009-01-12 13:09:46 -03001245 if (zr->revision >= 2) {
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001246 dprintk(1,
1247 KERN_INFO
Trent Piepho17faeb22009-01-12 13:09:46 -03001248 "%s: Subsystem vendor=0x%04x id=0x%04x\n",
1249 ZR_DEVNAME(zr), zr->pci_dev->subsystem_vendor,
1250 zr->pci_dev->subsystem_device);
1251 }
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001252
Trent Piepho17faeb22009-01-12 13:09:46 -03001253 /* Use auto-detected card type? */
1254 if (card[nr] == -1) {
1255 if (zr->revision < 2) {
Jean Delvare85b9b8a2008-07-14 09:51:03 -03001256 dprintk(1,
1257 KERN_ERR
Trent Piepho17faeb22009-01-12 13:09:46 -03001258 "%s: No card type specified, please use the card=X module parameter\n",
1259 ZR_DEVNAME(zr));
1260 dprintk(1,
1261 KERN_ERR
1262 "%s: It is not possible to auto-detect ZR36057 based cards\n",
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001263 ZR_DEVNAME(zr));
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001264 goto zr_unreg;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001265 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001266
Trent Piepho17faeb22009-01-12 13:09:46 -03001267 card_num = ent->driver_data;
1268 if (card_num >= NUM_CARDS) {
1269 dprintk(1,
1270 KERN_ERR
1271 "%s: Unknown card, try specifying card=X module parameter\n",
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001272 ZR_DEVNAME(zr));
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001273 goto zr_unreg;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001274 }
Trent Piepho17faeb22009-01-12 13:09:46 -03001275 dprintk(3,
1276 KERN_DEBUG
1277 "%s: %s() - card %s detected\n",
1278 ZR_DEVNAME(zr), __func__, zoran_cards[card_num].name);
1279 } else {
1280 card_num = card[nr];
1281 if (card_num >= NUM_CARDS || card_num < 0) {
1282 dprintk(1,
1283 KERN_ERR
1284 "%s: User specified card type %d out of range (0 .. %d)\n",
1285 ZR_DEVNAME(zr), card_num, NUM_CARDS - 1);
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001286 goto zr_unreg;
Trent Piepho17faeb22009-01-12 13:09:46 -03001287 }
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001288 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001289
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001290 /* even though we make this a non pointer and thus
1291 * theoretically allow for making changes to this struct
1292 * on a per-individual card basis at runtime, this is
1293 * strongly discouraged. This structure is intended to
1294 * keep general card information, no settings or anything */
1295 zr->card = zoran_cards[card_num];
1296 snprintf(ZR_DEVNAME(zr), sizeof(ZR_DEVNAME(zr)),
1297 "%s[%u]", zr->card.name, zr->id);
1298
Trent Piepho5e098b62009-01-12 13:09:46 -03001299 zr->zr36057_mem = pci_ioremap_bar(zr->pci_dev, 0);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001300 if (!zr->zr36057_mem) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001301 dprintk(1, KERN_ERR "%s: %s() - ioremap failed\n",
Trent Piepho5e098b62009-01-12 13:09:46 -03001302 ZR_DEVNAME(zr), __func__);
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001303 goto zr_unreg;
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001304 }
1305
1306 result = request_irq(zr->pci_dev->irq, zoran_irq,
1307 IRQF_SHARED | IRQF_DISABLED, ZR_DEVNAME(zr), zr);
1308 if (result < 0) {
1309 if (result == -EINVAL) {
1310 dprintk(1,
1311 KERN_ERR
Trent Piephoc61402b2009-03-10 23:28:33 -03001312 "%s: %s - bad irq number or handler\n",
1313 ZR_DEVNAME(zr), __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001314 } else if (result == -EBUSY) {
1315 dprintk(1,
1316 KERN_ERR
Trent Piephoc61402b2009-03-10 23:28:33 -03001317 "%s: %s - IRQ %d busy, change your PnP config in BIOS\n",
1318 ZR_DEVNAME(zr), __func__, zr->pci_dev->irq);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001319 } else {
1320 dprintk(1,
1321 KERN_ERR
Trent Piephoc61402b2009-03-10 23:28:33 -03001322 "%s: %s - can't assign irq, error code %d\n",
1323 ZR_DEVNAME(zr), __func__, result);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001324 }
1325 goto zr_unmap;
1326 }
1327
1328 /* set PCI latency timer */
1329 pci_read_config_byte(zr->pci_dev, PCI_LATENCY_TIMER,
1330 &latency);
1331 need_latency = zr->revision > 1 ? 32 : 48;
1332 if (latency != need_latency) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001333 dprintk(2, KERN_INFO "%s: Changing PCI latency from %d to %d\n",
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001334 ZR_DEVNAME(zr), latency, need_latency);
1335 pci_write_config_byte(zr->pci_dev, PCI_LATENCY_TIMER,
1336 need_latency);
1337 }
1338
1339 zr36057_restart(zr);
1340 /* i2c */
1341 dprintk(2, KERN_INFO "%s: Initializing i2c bus...\n",
1342 ZR_DEVNAME(zr));
1343
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001344 if (zoran_register_i2c(zr) < 0) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001345 dprintk(1, KERN_ERR "%s: %s - can't initialize i2c bus\n",
1346 ZR_DEVNAME(zr), __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001347 goto zr_free_irq;
1348 }
1349
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001350 zr->decoder = v4l2_i2c_new_probed_subdev(&zr->i2c_adapter,
1351 zr->card.mod_decoder, zr->card.i2c_decoder, zr->card.addrs_decoder);
1352
1353 if (zr->card.mod_encoder)
1354 zr->encoder = v4l2_i2c_new_probed_subdev(&zr->i2c_adapter,
1355 zr->card.mod_encoder, zr->card.i2c_encoder,
1356 zr->card.addrs_encoder);
1357
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001358 dprintk(2,
1359 KERN_INFO "%s: Initializing videocodec bus...\n",
1360 ZR_DEVNAME(zr));
1361
1362 if (zr->card.video_codec) {
1363 codec_name = codecid_to_modulename(zr->card.video_codec);
1364 if (codec_name) {
1365 result = request_module(codec_name);
1366 if (result) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001367 dprintk(1,
1368 KERN_ERR
1369 "%s: failed to load modules %s: %d\n",
1370 ZR_DEVNAME(zr), codec_name, result);
1371 }
1372 }
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001373 }
1374 if (zr->card.video_vfe) {
1375 vfe_name = codecid_to_modulename(zr->card.video_vfe);
1376 if (vfe_name) {
1377 result = request_module(vfe_name);
1378 if (result < 0) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001379 dprintk(1,
1380 KERN_ERR
1381 "%s: failed to load modules %s: %d\n",
1382 ZR_DEVNAME(zr), vfe_name, result);
1383 }
1384 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001385 }
Alan Coxe491cbc2006-10-03 20:44:12 -03001386
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001387 /* reset JPEG codec */
1388 jpeg_codec_sleep(zr, 1);
1389 jpeg_codec_reset(zr);
1390 /* video bus enabled */
1391 /* display codec revision */
1392 if (zr->card.video_codec != 0) {
1393 master_codec = zoran_setup_videocodec(zr, zr->card.video_codec);
1394 if (!master_codec)
1395 goto zr_unreg_i2c;
1396 zr->codec = videocodec_attach(master_codec);
1397 if (!zr->codec) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001398 dprintk(1, KERN_ERR "%s: %s - no codec found\n",
1399 ZR_DEVNAME(zr), __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001400 goto zr_free_codec;
1401 }
1402 if (zr->codec->type != zr->card.video_codec) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001403 dprintk(1, KERN_ERR "%s: %s - wrong codec\n",
1404 ZR_DEVNAME(zr), __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001405 goto zr_detach_codec;
1406 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001407 }
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001408 if (zr->card.video_vfe != 0) {
1409 master_vfe = zoran_setup_videocodec(zr, zr->card.video_vfe);
1410 if (!master_vfe)
1411 goto zr_detach_codec;
1412 zr->vfe = videocodec_attach(master_vfe);
1413 if (!zr->vfe) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001414 dprintk(1, KERN_ERR "%s: %s - no VFE found\n",
1415 ZR_DEVNAME(zr), __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001416 goto zr_free_vfe;
1417 }
1418 if (zr->vfe->type != zr->card.video_vfe) {
Trent Piephoc61402b2009-03-10 23:28:33 -03001419 dprintk(1, KERN_ERR "%s: %s = wrong VFE\n",
1420 ZR_DEVNAME(zr), __func__);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001421 goto zr_detach_vfe;
1422 }
1423 }
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001424
1425 /* take care of Natoma chipset and a revision 1 zr36057 */
1426 if ((pci_pci_problems & PCIPCI_NATOMA) && zr->revision <= 1) {
1427 zr->jpg_buffers.need_contiguous = 1;
Trent Piephoc61402b2009-03-10 23:28:33 -03001428 dprintk(1, KERN_INFO
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001429 "%s: ZR36057/Natoma bug, max. buffer size is 128K\n",
1430 ZR_DEVNAME(zr));
1431 }
1432
1433 if (zr36057_init(zr) < 0)
1434 goto zr_detach_vfe;
1435
1436 zoran_proc_init(zr);
1437
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001438 return 0;
1439
1440zr_detach_vfe:
1441 videocodec_detach(zr->vfe);
1442zr_free_vfe:
1443 kfree(master_vfe);
1444zr_detach_codec:
1445 videocodec_detach(zr->codec);
1446zr_free_codec:
1447 kfree(master_codec);
1448zr_unreg_i2c:
1449 zoran_unregister_i2c(zr);
1450zr_free_irq:
1451 btwrite(0, ZR36057_SPGPPCR);
1452 free_irq(zr->pci_dev->irq, zr);
1453zr_unmap:
1454 iounmap(zr->zr36057_mem);
Hans Verkuil0ab6e1c2009-02-19 16:18:23 -03001455zr_unreg:
1456 v4l2_device_unregister(&zr->v4l2_dev);
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001457zr_free_mem:
1458 kfree(zr);
1459
1460 return -ENODEV;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001461}
1462
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001463static struct pci_driver zoran_driver = {
1464 .name = "zr36067",
1465 .id_table = zr36067_pci_tbl,
1466 .probe = zoran_probe,
1467 .remove = zoran_remove,
1468};
1469
1470static int __init zoran_init(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001471{
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001472 int res;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001473
Linus Torvalds1da177e2005-04-16 15:20:36 -07001474 printk(KERN_INFO "Zoran MJPEG board driver version %d.%d.%d\n",
1475 MAJOR_VERSION, MINOR_VERSION, RELEASE_VERSION);
1476
Linus Torvalds1da177e2005-04-16 15:20:36 -07001477 /* check the parameters we have been given, adjust if necessary */
1478 if (v4l_nbufs < 2)
1479 v4l_nbufs = 2;
1480 if (v4l_nbufs > VIDEO_MAX_FRAME)
1481 v4l_nbufs = VIDEO_MAX_FRAME;
1482 /* The user specfies the in KB, we want them in byte
1483 * (and page aligned) */
1484 v4l_bufsize = PAGE_ALIGN(v4l_bufsize * 1024);
1485 if (v4l_bufsize < 32768)
1486 v4l_bufsize = 32768;
1487 /* 2 MB is arbitrary but sufficient for the maximum possible images */
1488 if (v4l_bufsize > 2048 * 1024)
1489 v4l_bufsize = 2048 * 1024;
1490 if (jpg_nbufs < 4)
1491 jpg_nbufs = 4;
1492 if (jpg_nbufs > BUZ_MAX_FRAME)
1493 jpg_nbufs = BUZ_MAX_FRAME;
1494 jpg_bufsize = PAGE_ALIGN(jpg_bufsize * 1024);
1495 if (jpg_bufsize < 8192)
1496 jpg_bufsize = 8192;
1497 if (jpg_bufsize > (512 * 1024))
1498 jpg_bufsize = 512 * 1024;
1499 /* Use parameter for vidmem or try to find a video card */
1500 if (vidmem) {
1501 dprintk(1,
1502 KERN_INFO
1503 "%s: Using supplied video memory base address @ 0x%lx\n",
1504 ZORAN_NAME, vidmem);
1505 }
1506
Linus Torvalds1da177e2005-04-16 15:20:36 -07001507 /* some mainboards might not do PCI-PCI data transfer well */
Alan Coxe3558802006-09-14 11:47:55 -03001508 if (pci_pci_problems & (PCIPCI_FAIL|PCIAGP_FAIL|PCIPCI_ALIMAGIK)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001509 dprintk(1,
1510 KERN_WARNING
Alan Coxe3558802006-09-14 11:47:55 -03001511 "%s: chipset does not support reliable PCI-PCI DMA\n",
Linus Torvalds1da177e2005-04-16 15:20:36 -07001512 ZORAN_NAME);
1513 }
1514
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001515 res = pci_register_driver(&zoran_driver);
1516 if (res) {
1517 dprintk(1,
1518 KERN_ERR
1519 "%s: Unable to register ZR36057 driver\n",
1520 ZORAN_NAME);
1521 return res;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001522 }
1523
1524 return 0;
1525}
1526
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001527static void __exit zoran_exit(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001528{
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001529 pci_unregister_driver(&zoran_driver);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001530}
1531
Trent Piepho66aa66ea32009-01-11 12:02:54 -03001532module_init(zoran_init);
1533module_exit(zoran_exit);