GNU Linux-libre 4.14.290-gnu1
[releases.git] / drivers / media / pci / cx88 / cx88-cards.c
1 /*
2  * device driver for Conexant 2388x based TV cards
3  * card-specific stuff.
4  *
5  * (c) 2003 Gerd Knorr <kraxel@bytesex.org> [SuSE Labs]
6  *
7  *  This program is free software; you can redistribute it and/or modify
8  *  it under the terms of the GNU General Public License as published by
9  *  the Free Software Foundation; either version 2 of the License, or
10  *  (at your option) any later version.
11  *
12  *  This program is distributed in the hope that it will be useful,
13  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *  GNU General Public License for more details.
16  */
17
18 #include "cx88.h"
19 #include "tea5767.h"
20 #include "xc4000.h"
21
22 #include <linux/init.h>
23 #include <linux/module.h>
24 #include <linux/pci.h>
25 #include <linux/delay.h>
26 #include <linux/slab.h>
27
28 static unsigned int tuner[] = {[0 ... (CX88_MAXBOARDS - 1)] = UNSET };
29 static unsigned int radio[] = {[0 ... (CX88_MAXBOARDS - 1)] = UNSET };
30 static unsigned int card[]  = {[0 ... (CX88_MAXBOARDS - 1)] = UNSET };
31
32 module_param_array(tuner, int, NULL, 0444);
33 module_param_array(radio, int, NULL, 0444);
34 module_param_array(card,  int, NULL, 0444);
35
36 MODULE_PARM_DESC(tuner, "tuner type");
37 MODULE_PARM_DESC(radio, "radio tuner type");
38 MODULE_PARM_DESC(card, "card type");
39
40 static unsigned int latency = UNSET;
41 module_param(latency, int, 0444);
42 MODULE_PARM_DESC(latency, "pci latency timer");
43
44 static int disable_ir;
45 module_param(disable_ir, int, 0444);
46 MODULE_PARM_DESC(disable_ir, "Disable IR support");
47
48 #define dprintk(level, fmt, arg...)     do {                            \
49         if (cx88_core_debug >= level)                                   \
50                 printk(KERN_DEBUG pr_fmt("%s: core:" fmt),              \
51                         __func__, ##arg);                               \
52 } while (0)
53
54 /* ------------------------------------------------------------------ */
55 /* board config info                                                  */
56
57 /* If radio_type !=UNSET, radio_addr should be specified
58  */
59
60 static const struct cx88_board cx88_boards[] = {
61         [CX88_BOARD_UNKNOWN] = {
62                 .name           = "UNKNOWN/GENERIC",
63                 .tuner_type     = UNSET,
64                 .radio_type     = UNSET,
65                 .tuner_addr     = ADDR_UNSET,
66                 .radio_addr     = ADDR_UNSET,
67                 .input          = { {
68                         .type   = CX88_VMUX_COMPOSITE1,
69                         .vmux   = 0,
70                 }, {
71                         .type   = CX88_VMUX_COMPOSITE2,
72                         .vmux   = 1,
73                 }, {
74                         .type   = CX88_VMUX_COMPOSITE3,
75                         .vmux   = 2,
76                 }, {
77                         .type   = CX88_VMUX_COMPOSITE4,
78                         .vmux   = 3,
79                 } },
80         },
81         [CX88_BOARD_HAUPPAUGE] = {
82                 .name           = "Hauppauge WinTV 34xxx models",
83                 .tuner_type     = UNSET,
84                 .radio_type     = UNSET,
85                 .tuner_addr     = ADDR_UNSET,
86                 .radio_addr     = ADDR_UNSET,
87                 .tda9887_conf   = TDA9887_PRESENT,
88                 .input          = { {
89                         .type   = CX88_VMUX_TELEVISION,
90                         .vmux   = 0,
91                         .gpio0  = 0xff00,  // internal decoder
92                 }, {
93                         .type   = CX88_VMUX_DEBUG,
94                         .vmux   = 0,
95                         .gpio0  = 0xff01,  // mono from tuner chip
96                 }, {
97                         .type   = CX88_VMUX_COMPOSITE1,
98                         .vmux   = 1,
99                         .gpio0  = 0xff02,
100                 }, {
101                         .type   = CX88_VMUX_SVIDEO,
102                         .vmux   = 2,
103                         .gpio0  = 0xff02,
104                 } },
105                 .radio = {
106                         .type   = CX88_RADIO,
107                         .gpio0  = 0xff01,
108                 },
109         },
110         [CX88_BOARD_GDI] = {
111                 .name           = "GDI Black Gold",
112                 .tuner_type     = UNSET,
113                 .radio_type     = UNSET,
114                 .tuner_addr     = ADDR_UNSET,
115                 .radio_addr     = ADDR_UNSET,
116                 .input          = { {
117                         .type   = CX88_VMUX_TELEVISION,
118                         .vmux   = 0,
119                 }, {
120                         .type   = CX88_VMUX_SVIDEO,
121                         .vmux   = 2,
122                 } },
123         },
124         [CX88_BOARD_PIXELVIEW] = {
125                 .name           = "PixelView",
126                 .tuner_type     = TUNER_PHILIPS_PAL,
127                 .radio_type     = UNSET,
128                 .tuner_addr     = ADDR_UNSET,
129                 .radio_addr     = ADDR_UNSET,
130                 .input          = { {
131                         .type   = CX88_VMUX_TELEVISION,
132                         .vmux   = 0,
133                         .gpio0  = 0xff00,  // internal decoder
134                 }, {
135                         .type   = CX88_VMUX_COMPOSITE1,
136                         .vmux   = 1,
137                 }, {
138                         .type   = CX88_VMUX_SVIDEO,
139                         .vmux   = 2,
140                 } },
141                 .radio = {
142                          .type  = CX88_RADIO,
143                          .gpio0 = 0xff10,
144                 },
145         },
146         [CX88_BOARD_ATI_WONDER_PRO] = {
147                 .name           = "ATI TV Wonder Pro",
148                 .tuner_type     = TUNER_PHILIPS_4IN1,
149                 .radio_type     = UNSET,
150                 .tuner_addr     = ADDR_UNSET,
151                 .radio_addr     = ADDR_UNSET,
152                 .tda9887_conf   = TDA9887_PRESENT | TDA9887_INTERCARRIER,
153                 .input          = { {
154                         .type   = CX88_VMUX_TELEVISION,
155                         .vmux   = 0,
156                         .gpio0  = 0x03ff,
157                 }, {
158                         .type   = CX88_VMUX_COMPOSITE1,
159                         .vmux   = 1,
160                         .gpio0  = 0x03fe,
161                 }, {
162                         .type   = CX88_VMUX_SVIDEO,
163                         .vmux   = 2,
164                         .gpio0  = 0x03fe,
165                 } },
166         },
167         [CX88_BOARD_WINFAST2000XP_EXPERT] = {
168                 .name           = "Leadtek Winfast 2000XP Expert",
169                 .tuner_type     = TUNER_PHILIPS_4IN1,
170                 .radio_type     = UNSET,
171                 .tuner_addr     = ADDR_UNSET,
172                 .radio_addr     = ADDR_UNSET,
173                 .tda9887_conf   = TDA9887_PRESENT,
174                 .input          = { {
175                         .type   = CX88_VMUX_TELEVISION,
176                         .vmux   = 0,
177                         .gpio0  = 0x00F5e700,
178                         .gpio1  = 0x00003004,
179                         .gpio2  = 0x00F5e700,
180                         .gpio3  = 0x02000000,
181                 }, {
182                         .type   = CX88_VMUX_COMPOSITE1,
183                         .vmux   = 1,
184                         .gpio0  = 0x00F5c700,
185                         .gpio1  = 0x00003004,
186                         .gpio2  = 0x00F5c700,
187                         .gpio3  = 0x02000000,
188                 }, {
189                         .type   = CX88_VMUX_SVIDEO,
190                         .vmux   = 2,
191                         .gpio0  = 0x00F5c700,
192                         .gpio1  = 0x00003004,
193                         .gpio2  = 0x00F5c700,
194                         .gpio3  = 0x02000000,
195                 } },
196                 .radio = {
197                         .type   = CX88_RADIO,
198                         .gpio0  = 0x00F5d700,
199                         .gpio1  = 0x00003004,
200                         .gpio2  = 0x00F5d700,
201                         .gpio3  = 0x02000000,
202                 },
203         },
204         [CX88_BOARD_AVERTV_STUDIO_303] = {
205                 .name           = "AverTV Studio 303 (M126)",
206                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
207                 .radio_type     = UNSET,
208                 .tuner_addr     = ADDR_UNSET,
209                 .radio_addr     = ADDR_UNSET,
210                 .tda9887_conf   = TDA9887_PRESENT,
211                 .input          = { {
212                         .type   = CX88_VMUX_TELEVISION,
213                         .vmux   = 0,
214                         .gpio1  = 0xe09f,
215                 }, {
216                         .type   = CX88_VMUX_COMPOSITE1,
217                         .vmux   = 1,
218                         .gpio1  = 0xe05f,
219                 }, {
220                         .type   = CX88_VMUX_SVIDEO,
221                         .vmux   = 2,
222                         .gpio1  = 0xe05f,
223                 } },
224                 .radio = {
225                         .gpio1  = 0xe0df,
226                         .type   = CX88_RADIO,
227                 },
228         },
229         [CX88_BOARD_MSI_TVANYWHERE_MASTER] = {
230                 // added gpio values thanks to Michal
231                 // values for PAL from DScaler
232                 .name           = "MSI TV-@nywhere Master",
233                 .tuner_type     = TUNER_MT2032,
234                 .radio_type     = UNSET,
235                 .tuner_addr     = ADDR_UNSET,
236                 .radio_addr     = ADDR_UNSET,
237                 .tda9887_conf   = TDA9887_PRESENT | TDA9887_INTERCARRIER_NTSC,
238                 .input          = { {
239                         .type   = CX88_VMUX_TELEVISION,
240                         .vmux   = 0,
241                         .gpio0  = 0x000040bf,
242                         .gpio1  = 0x000080c0,
243                         .gpio2  = 0x0000ff40,
244                 }, {
245                         .type   = CX88_VMUX_COMPOSITE1,
246                         .vmux   = 1,
247                         .gpio0  = 0x000040bf,
248                         .gpio1  = 0x000080c0,
249                         .gpio2  = 0x0000ff40,
250                 }, {
251                         .type   = CX88_VMUX_SVIDEO,
252                         .vmux   = 2,
253                         .gpio0  = 0x000040bf,
254                         .gpio1  = 0x000080c0,
255                         .gpio2  = 0x0000ff40,
256                 } },
257                 .radio = {
258                          .type   = CX88_RADIO,
259                          .vmux   = 3,
260                          .gpio0  = 0x000040bf,
261                          .gpio1  = 0x000080c0,
262                          .gpio2  = 0x0000ff20,
263                 },
264         },
265         [CX88_BOARD_WINFAST_DV2000] = {
266                 .name           = "Leadtek Winfast DV2000",
267                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
268                 .radio_type     = UNSET,
269                 .tuner_addr     = ADDR_UNSET,
270                 .radio_addr     = ADDR_UNSET,
271                 .tda9887_conf   = TDA9887_PRESENT,
272                 .input          = { {
273                         .type   = CX88_VMUX_TELEVISION,
274                         .vmux   = 0,
275                         .gpio0  = 0x0035e700,
276                         .gpio1  = 0x00003004,
277                         .gpio2  = 0x0035e700,
278                         .gpio3  = 0x02000000,
279                 }, {
280                         .type   = CX88_VMUX_COMPOSITE1,
281                         .vmux   = 1,
282                         .gpio0  = 0x0035c700,
283                         .gpio1  = 0x00003004,
284                         .gpio2  = 0x0035c700,
285                         .gpio3  = 0x02000000,
286                 }, {
287                         .type   = CX88_VMUX_SVIDEO,
288                         .vmux   = 2,
289                         .gpio0  = 0x0035c700,
290                         .gpio1  = 0x0035c700,
291                         .gpio2  = 0x02000000,
292                         .gpio3  = 0x02000000,
293                 } },
294                 .radio = {
295                         .type   = CX88_RADIO,
296                         .gpio0  = 0x0035d700,
297                         .gpio1  = 0x00007004,
298                         .gpio2  = 0x0035d700,
299                         .gpio3  = 0x02000000,
300                 },
301         },
302         [CX88_BOARD_LEADTEK_PVR2000] = {
303                 // gpio values for PAL version from regspy by DScaler
304                 .name           = "Leadtek PVR 2000",
305                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
306                 .radio_type     = UNSET,
307                 .tuner_addr     = ADDR_UNSET,
308                 .radio_addr     = ADDR_UNSET,
309                 .tda9887_conf   = TDA9887_PRESENT,
310                 .input          = { {
311                         .type   = CX88_VMUX_TELEVISION,
312                         .vmux   = 0,
313                         .gpio0  = 0x0000bde2,
314                         .audioroute = 1,
315                 }, {
316                         .type   = CX88_VMUX_COMPOSITE1,
317                         .vmux   = 1,
318                         .gpio0  = 0x0000bde6,
319                         .audioroute = 1,
320                 }, {
321                         .type   = CX88_VMUX_SVIDEO,
322                         .vmux   = 2,
323                         .gpio0  = 0x0000bde6,
324                         .audioroute = 1,
325                 } },
326                 .radio = {
327                         .type   = CX88_RADIO,
328                         .gpio0  = 0x0000bd62,
329                         .audioroute = 1,
330                 },
331                 .mpeg           = CX88_MPEG_BLACKBIRD,
332         },
333         [CX88_BOARD_IODATA_GVVCP3PCI] = {
334                 .name           = "IODATA GV-VCP3/PCI",
335                 .tuner_type     = UNSET,
336                 .radio_type     = UNSET,
337                 .tuner_addr     = ADDR_UNSET,
338                 .radio_addr     = ADDR_UNSET,
339                 .input          = { {
340                         .type   = CX88_VMUX_COMPOSITE1,
341                         .vmux   = 0,
342                 }, {
343                         .type   = CX88_VMUX_COMPOSITE2,
344                         .vmux   = 1,
345                 }, {
346                         .type   = CX88_VMUX_SVIDEO,
347                         .vmux   = 2,
348                 } },
349         },
350         [CX88_BOARD_PROLINK_PLAYTVPVR] = {
351                 .name           = "Prolink PlayTV PVR",
352                 .tuner_type     = TUNER_PHILIPS_FM1236_MK3,
353                 .radio_type     = UNSET,
354                 .tuner_addr     = ADDR_UNSET,
355                 .radio_addr     = ADDR_UNSET,
356                 .tda9887_conf   = TDA9887_PRESENT,
357                 .input          = { {
358                         .type   = CX88_VMUX_TELEVISION,
359                         .vmux   = 0,
360                         .gpio0  = 0xbff0,
361                 }, {
362                         .type   = CX88_VMUX_COMPOSITE1,
363                         .vmux   = 1,
364                         .gpio0  = 0xbff3,
365                 }, {
366                         .type   = CX88_VMUX_SVIDEO,
367                         .vmux   = 2,
368                         .gpio0  = 0xbff3,
369                 } },
370                 .radio = {
371                         .type   = CX88_RADIO,
372                         .gpio0  = 0xbff0,
373                 },
374         },
375         [CX88_BOARD_ASUS_PVR_416] = {
376                 .name           = "ASUS PVR-416",
377                 .tuner_type     = TUNER_PHILIPS_FM1236_MK3,
378                 .radio_type     = UNSET,
379                 .tuner_addr     = ADDR_UNSET,
380                 .radio_addr     = ADDR_UNSET,
381                 .tda9887_conf   = TDA9887_PRESENT,
382                 .input          = { {
383                         .type   = CX88_VMUX_TELEVISION,
384                         .vmux   = 0,
385                         .gpio0  = 0x0000fde6,
386                 }, {
387                         .type   = CX88_VMUX_SVIDEO,
388                         .vmux   = 2,
389                         .gpio0  = 0x0000fde6, // 0x0000fda6 L,R RCA audio in?
390                         .audioroute = 1,
391                 } },
392                 .radio = {
393                         .type   = CX88_RADIO,
394                         .gpio0  = 0x0000fde2,
395                 },
396                 .mpeg           = CX88_MPEG_BLACKBIRD,
397         },
398         [CX88_BOARD_MSI_TVANYWHERE] = {
399                 .name           = "MSI TV-@nywhere",
400                 .tuner_type     = TUNER_MT2032,
401                 .radio_type     = UNSET,
402                 .tuner_addr     = ADDR_UNSET,
403                 .radio_addr     = ADDR_UNSET,
404                 .tda9887_conf   = TDA9887_PRESENT,
405                 .input          = { {
406                         .type   = CX88_VMUX_TELEVISION,
407                         .vmux   = 0,
408                         .gpio0  = 0x00000fbf,
409                         .gpio2  = 0x0000fc08,
410                 }, {
411                         .type   = CX88_VMUX_COMPOSITE1,
412                         .vmux   = 1,
413                         .gpio0  = 0x00000fbf,
414                         .gpio2  = 0x0000fc68,
415                 }, {
416                         .type   = CX88_VMUX_SVIDEO,
417                         .vmux   = 2,
418                         .gpio0  = 0x00000fbf,
419                         .gpio2  = 0x0000fc68,
420                 } },
421         },
422         [CX88_BOARD_KWORLD_DVB_T] = {
423                 .name           = "KWorld/VStream XPert DVB-T",
424                 .tuner_type     = UNSET,
425                 .radio_type     = UNSET,
426                 .tuner_addr     = ADDR_UNSET,
427                 .radio_addr     = ADDR_UNSET,
428                 .input          = { {
429                         .type   = CX88_VMUX_COMPOSITE1,
430                         .vmux   = 1,
431                         .gpio0  = 0x0700,
432                         .gpio2  = 0x0101,
433                 }, {
434                         .type   = CX88_VMUX_SVIDEO,
435                         .vmux   = 2,
436                         .gpio0  = 0x0700,
437                         .gpio2  = 0x0101,
438                 } },
439                 .mpeg           = CX88_MPEG_DVB,
440         },
441         [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T1] = {
442                 .name           = "DViCO FusionHDTV DVB-T1",
443                 .tuner_type     = UNSET, /* No analog tuner */
444                 .radio_type     = UNSET,
445                 .tuner_addr     = ADDR_UNSET,
446                 .radio_addr     = ADDR_UNSET,
447                 .input          = { {
448                         .type   = CX88_VMUX_COMPOSITE1,
449                         .vmux   = 1,
450                         .gpio0  = 0x000027df,
451                 }, {
452                         .type   = CX88_VMUX_SVIDEO,
453                         .vmux   = 2,
454                         .gpio0  = 0x000027df,
455                 } },
456                 .mpeg           = CX88_MPEG_DVB,
457         },
458         [CX88_BOARD_KWORLD_LTV883] = {
459                 .name           = "KWorld LTV883RF",
460                 .tuner_type     = TUNER_TNF_8831BGFF,
461                 .radio_type     = UNSET,
462                 .tuner_addr     = ADDR_UNSET,
463                 .radio_addr     = ADDR_UNSET,
464                 .input          = { {
465                         .type   = CX88_VMUX_TELEVISION,
466                         .vmux   = 0,
467                         .gpio0  = 0x07f8,
468                 }, {
469                         .type   = CX88_VMUX_DEBUG,
470                         .vmux   = 0,
471                         .gpio0  = 0x07f9,  // mono from tuner chip
472                 }, {
473                         .type   = CX88_VMUX_COMPOSITE1,
474                         .vmux   = 1,
475                         .gpio0  = 0x000007fa,
476                 }, {
477                         .type   = CX88_VMUX_SVIDEO,
478                         .vmux   = 2,
479                         .gpio0  = 0x000007fa,
480                 } },
481                 .radio = {
482                         .type   = CX88_RADIO,
483                         .gpio0  = 0x000007f8,
484                 },
485         },
486         [CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q] = {
487                 .name           = "DViCO FusionHDTV 3 Gold-Q",
488                 .tuner_type     = TUNER_MICROTUNE_4042FI5,
489                 .radio_type     = UNSET,
490                 .tuner_addr     = ADDR_UNSET,
491                 .radio_addr     = ADDR_UNSET,
492                 /*
493                  * GPIO[0] resets DT3302 DTV receiver
494                  *     0 - reset asserted
495                  *     1 - normal operation
496                  * GPIO[1] mutes analog audio output connector
497                  *     0 - enable selected source
498                  *     1 - mute
499                  * GPIO[2] selects source for analog audio output connector
500                  *     0 - analog audio input connector on tab
501                  *     1 - analog DAC output from CX23881 chip
502                  * GPIO[3] selects RF input connector on tuner module
503                  *     0 - RF connector labeled CABLE
504                  *     1 - RF connector labeled ANT
505                  * GPIO[4] selects high RF for QAM256 mode
506                  *     0 - normal RF
507                  *     1 - high RF
508                  */
509                 .input          = { {
510                         .type   = CX88_VMUX_TELEVISION,
511                         .vmux   = 0,
512                         .gpio0  = 0x0f0d,
513                 }, {
514                         .type   = CX88_VMUX_CABLE,
515                         .vmux   = 0,
516                         .gpio0  = 0x0f05,
517                 }, {
518                         .type   = CX88_VMUX_COMPOSITE1,
519                         .vmux   = 1,
520                         .gpio0  = 0x0f00,
521                 }, {
522                         .type   = CX88_VMUX_SVIDEO,
523                         .vmux   = 2,
524                         .gpio0  = 0x0f00,
525                 } },
526                 .mpeg           = CX88_MPEG_DVB,
527         },
528         [CX88_BOARD_HAUPPAUGE_DVB_T1] = {
529                 .name           = "Hauppauge Nova-T DVB-T",
530                 .tuner_type     = UNSET,
531                 .radio_type     = UNSET,
532                 .tuner_addr     = ADDR_UNSET,
533                 .radio_addr     = ADDR_UNSET,
534                 .input          = { {
535                         .type   = CX88_VMUX_DVB,
536                         .vmux   = 0,
537                 } },
538                 .mpeg           = CX88_MPEG_DVB,
539         },
540         [CX88_BOARD_CONEXANT_DVB_T1] = {
541                 .name           = "Conexant DVB-T reference design",
542                 .tuner_type     = UNSET,
543                 .radio_type     = UNSET,
544                 .tuner_addr     = ADDR_UNSET,
545                 .radio_addr     = ADDR_UNSET,
546                 .input          = { {
547                         .type   = CX88_VMUX_DVB,
548                         .vmux   = 0,
549                 } },
550                 .mpeg           = CX88_MPEG_DVB,
551         },
552         [CX88_BOARD_PROVIDEO_PV259] = {
553                 .name           = "Provideo PV259",
554                 .tuner_type     = TUNER_PHILIPS_FQ1216ME,
555                 .radio_type     = UNSET,
556                 .tuner_addr     = ADDR_UNSET,
557                 .radio_addr     = ADDR_UNSET,
558                 .input          = { {
559                         .type   = CX88_VMUX_TELEVISION,
560                         .vmux   = 0,
561                         .audioroute = 1,
562                 } },
563                 .mpeg           = CX88_MPEG_BLACKBIRD,
564         },
565         [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS] = {
566                 .name           = "DViCO FusionHDTV DVB-T Plus",
567                 .tuner_type     = UNSET, /* No analog tuner */
568                 .radio_type     = UNSET,
569                 .tuner_addr     = ADDR_UNSET,
570                 .radio_addr     = ADDR_UNSET,
571                 .input          = { {
572                         .type   = CX88_VMUX_COMPOSITE1,
573                         .vmux   = 1,
574                         .gpio0  = 0x000027df,
575                 }, {
576                         .type   = CX88_VMUX_SVIDEO,
577                         .vmux   = 2,
578                         .gpio0  = 0x000027df,
579                 } },
580                 .mpeg           = CX88_MPEG_DVB,
581         },
582         [CX88_BOARD_DNTV_LIVE_DVB_T] = {
583                 .name           = "digitalnow DNTV Live! DVB-T",
584                 .tuner_type     = UNSET,
585                 .radio_type     = UNSET,
586                 .tuner_addr     = ADDR_UNSET,
587                 .radio_addr     = ADDR_UNSET,
588                 .input          = { {
589                         .type   = CX88_VMUX_COMPOSITE1,
590                         .vmux   = 1,
591                         .gpio0  = 0x00000700,
592                         .gpio2  = 0x00000101,
593                 }, {
594                         .type   = CX88_VMUX_SVIDEO,
595                         .vmux   = 2,
596                         .gpio0  = 0x00000700,
597                         .gpio2  = 0x00000101,
598                 } },
599                 .mpeg           = CX88_MPEG_DVB,
600         },
601         [CX88_BOARD_PCHDTV_HD3000] = {
602                 .name           = "pcHDTV HD3000 HDTV",
603                 .tuner_type     = TUNER_THOMSON_DTT761X,
604                 .radio_type     = UNSET,
605                 .tuner_addr     = ADDR_UNSET,
606                 .radio_addr     = ADDR_UNSET,
607                 .tda9887_conf   = TDA9887_PRESENT,
608                 /* GPIO[2] = audio source for analog audio out connector
609                  *  0 = analog audio input connector
610                  *  1 = CX88 audio DACs
611                  *
612                  * GPIO[7] = input to CX88's audio/chroma ADC
613                  *  0 = FM 10.7 MHz IF
614                  *  1 = Sound 4.5 MHz IF
615                  *
616                  * GPIO[1,5,6] = Oren 51132 pins 27,35,28 respectively
617                  *
618                  * GPIO[16] = Remote control input
619                  */
620                 .input          = { {
621                         .type   = CX88_VMUX_TELEVISION,
622                         .vmux   = 0,
623                         .gpio0  = 0x00008484,
624                 }, {
625                         .type   = CX88_VMUX_COMPOSITE1,
626                         .vmux   = 1,
627                         .gpio0  = 0x00008400,
628                 }, {
629                         .type   = CX88_VMUX_SVIDEO,
630                         .vmux   = 2,
631                         .gpio0  = 0x00008400,
632                 } },
633                 .radio = {
634                         .type   = CX88_RADIO,
635                         .gpio0  = 0x00008404,
636                 },
637                 .mpeg           = CX88_MPEG_DVB,
638         },
639         [CX88_BOARD_HAUPPAUGE_ROSLYN] = {
640                 // entry added by Kaustubh D. Bhalerao <bhalerao.1@osu.edu>
641                 // GPIO values obtained from regspy, courtesy Sean Covel
642                 .name           = "Hauppauge WinTV 28xxx (Roslyn) models",
643                 .tuner_type     = UNSET,
644                 .radio_type     = UNSET,
645                 .tuner_addr     = ADDR_UNSET,
646                 .radio_addr     = ADDR_UNSET,
647                 .input          = { {
648                         .type   = CX88_VMUX_TELEVISION,
649                         .vmux   = 0,
650                         .gpio0  = 0xed1a,
651                         .gpio2  = 0x00ff,
652                 }, {
653                         .type   = CX88_VMUX_DEBUG,
654                         .vmux   = 0,
655                         .gpio0  = 0xff01,
656                 }, {
657                         .type   = CX88_VMUX_COMPOSITE1,
658                         .vmux   = 1,
659                         .gpio0  = 0xff02,
660                 }, {
661                         .type   = CX88_VMUX_SVIDEO,
662                         .vmux   = 2,
663                         .gpio0  = 0xed92,
664                         .gpio2  = 0x00ff,
665                 } },
666                 .radio = {
667                          .type   = CX88_RADIO,
668                          .gpio0  = 0xed96,
669                          .gpio2  = 0x00ff,
670                  },
671                 .mpeg           = CX88_MPEG_BLACKBIRD,
672         },
673         [CX88_BOARD_DIGITALLOGIC_MEC] = {
674                 .name           = "Digital-Logic MICROSPACE Entertainment Center (MEC)",
675                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
676                 .radio_type     = UNSET,
677                 .tuner_addr     = ADDR_UNSET,
678                 .radio_addr     = ADDR_UNSET,
679                 .tda9887_conf   = TDA9887_PRESENT,
680                 .input          = { {
681                         .type   = CX88_VMUX_TELEVISION,
682                         .vmux   = 0,
683                         .gpio0  = 0x00009d80,
684                         .audioroute = 1,
685                 }, {
686                         .type   = CX88_VMUX_COMPOSITE1,
687                         .vmux   = 1,
688                         .gpio0  = 0x00009d76,
689                         .audioroute = 1,
690                 }, {
691                         .type   = CX88_VMUX_SVIDEO,
692                         .vmux   = 2,
693                         .gpio0  = 0x00009d76,
694                         .audioroute = 1,
695                 } },
696                 .radio = {
697                         .type   = CX88_RADIO,
698                         .gpio0  = 0x00009d00,
699                         .audioroute = 1,
700                 },
701                 .mpeg           = CX88_MPEG_BLACKBIRD,
702         },
703         [CX88_BOARD_IODATA_GVBCTV7E] = {
704                 .name           = "IODATA GV/BCTV7E",
705                 .tuner_type     = TUNER_PHILIPS_FQ1286,
706                 .radio_type     = UNSET,
707                 .tuner_addr     = ADDR_UNSET,
708                 .radio_addr     = ADDR_UNSET,
709                 .tda9887_conf   = TDA9887_PRESENT,
710                 .input          = { {
711                         .type   = CX88_VMUX_TELEVISION,
712                         .vmux   = 1,
713                         .gpio1  = 0x0000e03f,
714                 }, {
715                         .type   = CX88_VMUX_COMPOSITE1,
716                         .vmux   = 2,
717                         .gpio1  = 0x0000e07f,
718                 }, {
719                         .type   = CX88_VMUX_SVIDEO,
720                         .vmux   = 3,
721                         .gpio1  = 0x0000e07f,
722                 } }
723         },
724         [CX88_BOARD_PIXELVIEW_PLAYTV_ULTRA_PRO] = {
725                 .name           = "PixelView PlayTV Ultra Pro (Stereo)",
726                 /* May be also TUNER_YMEC_TVF_5533MF for NTSC/M or PAL/M */
727                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
728                 .radio_type     = UNSET,
729                 .tuner_addr     = ADDR_UNSET,
730                 .radio_addr     = ADDR_UNSET,
731                 /*
732                  * Some variants use a tda9874 and so need the
733                  * tvaudio module.
734                  */
735                 .audio_chip     = CX88_AUDIO_TVAUDIO,
736                 .input          = { {
737                         .type   = CX88_VMUX_TELEVISION,
738                         .vmux   = 0,
739                         .gpio0  = 0xbf61,  /* internal decoder */
740                 }, {
741                         .type   = CX88_VMUX_COMPOSITE1,
742                         .vmux   = 1,
743                         .gpio0  = 0xbf63,
744                 }, {
745                         .type   = CX88_VMUX_SVIDEO,
746                         .vmux   = 2,
747                         .gpio0  = 0xbf63,
748                 } },
749                 .radio = {
750                          .type  = CX88_RADIO,
751                          .gpio0 = 0xbf60,
752                  },
753         },
754         [CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_T] = {
755                 .name           = "DViCO FusionHDTV 3 Gold-T",
756                 .tuner_type     = TUNER_THOMSON_DTT761X,
757                 .radio_type     = UNSET,
758                 .tuner_addr     = ADDR_UNSET,
759                 .radio_addr     = ADDR_UNSET,
760                 .tda9887_conf   = TDA9887_PRESENT,
761                 .input          = { {
762                         .type   = CX88_VMUX_TELEVISION,
763                         .vmux   = 0,
764                         .gpio0  = 0x97ed,
765                 }, {
766                         .type   = CX88_VMUX_COMPOSITE1,
767                         .vmux   = 1,
768                         .gpio0  = 0x97e9,
769                 }, {
770                         .type   = CX88_VMUX_SVIDEO,
771                         .vmux   = 2,
772                         .gpio0  = 0x97e9,
773                 } },
774                 .mpeg           = CX88_MPEG_DVB,
775         },
776         [CX88_BOARD_ADSTECH_DVB_T_PCI] = {
777                 .name           = "ADS Tech Instant TV DVB-T PCI",
778                 .tuner_type     = UNSET,
779                 .radio_type     = UNSET,
780                 .tuner_addr     = ADDR_UNSET,
781                 .radio_addr     = ADDR_UNSET,
782                 .input          = { {
783                         .type   = CX88_VMUX_COMPOSITE1,
784                         .vmux   = 1,
785                         .gpio0  = 0x0700,
786                         .gpio2  = 0x0101,
787                 }, {
788                         .type   = CX88_VMUX_SVIDEO,
789                         .vmux   = 2,
790                         .gpio0  = 0x0700,
791                         .gpio2  = 0x0101,
792                 } },
793                 .mpeg           = CX88_MPEG_DVB,
794         },
795         [CX88_BOARD_TERRATEC_CINERGY_1400_DVB_T1] = {
796                 .name           = "TerraTec Cinergy 1400 DVB-T",
797                 .tuner_type     = UNSET,
798                 .input          = { {
799                         .type   = CX88_VMUX_DVB,
800                         .vmux   = 0,
801                 }, {
802                         .type   = CX88_VMUX_COMPOSITE1,
803                         .vmux   = 2,
804                 }, {
805                         .type   = CX88_VMUX_SVIDEO,
806                         .vmux   = 2,
807                 } },
808                 .mpeg           = CX88_MPEG_DVB,
809         },
810         [CX88_BOARD_DVICO_FUSIONHDTV_5_GOLD] = {
811                 .name           = "DViCO FusionHDTV 5 Gold",
812                 .tuner_type     = TUNER_LG_TDVS_H06XF, /* TDVS-H062F */
813                 .radio_type     = UNSET,
814                 .tuner_addr     = ADDR_UNSET,
815                 .radio_addr     = ADDR_UNSET,
816                 .tda9887_conf   = TDA9887_PRESENT,
817                 .input          = { {
818                         .type   = CX88_VMUX_TELEVISION,
819                         .vmux   = 0,
820                         .gpio0  = 0x87fd,
821                 }, {
822                         .type   = CX88_VMUX_COMPOSITE1,
823                         .vmux   = 1,
824                         .gpio0  = 0x87f9,
825                 }, {
826                         .type   = CX88_VMUX_SVIDEO,
827                         .vmux   = 2,
828                         .gpio0  = 0x87f9,
829                 } },
830                 .mpeg           = CX88_MPEG_DVB,
831         },
832         [CX88_BOARD_AVERMEDIA_ULTRATV_MC_550] = {
833                 .name           = "AverMedia UltraTV Media Center PCI 550",
834                 .tuner_type     = TUNER_PHILIPS_FM1236_MK3,
835                 .radio_type     = UNSET,
836                 .tuner_addr     = ADDR_UNSET,
837                 .radio_addr     = ADDR_UNSET,
838                 .tda9887_conf   = TDA9887_PRESENT,
839                 .input          = { {
840                         .type   = CX88_VMUX_COMPOSITE1,
841                         .vmux   = 0,
842                         .gpio0  = 0x0000cd73,
843                         .audioroute = 1,
844                 }, {
845                         .type   = CX88_VMUX_SVIDEO,
846                         .vmux   = 1,
847                         .gpio0  = 0x0000cd73,
848                         .audioroute = 1,
849                 }, {
850                         .type   = CX88_VMUX_TELEVISION,
851                         .vmux   = 3,
852                         .gpio0  = 0x0000cdb3,
853                         .audioroute = 1,
854                 } },
855                 .radio = {
856                         .type   = CX88_RADIO,
857                         .vmux   = 2,
858                         .gpio0  = 0x0000cdf3,
859                         .audioroute = 1,
860                 },
861                 .mpeg           = CX88_MPEG_BLACKBIRD,
862         },
863         [CX88_BOARD_KWORLD_VSTREAM_EXPERT_DVD] = {
864                  /* Alexander Wold <awold@bigfoot.com> */
865                  .name           = "Kworld V-Stream Xpert DVD",
866                  .tuner_type     = UNSET,
867                  .input          = { {
868                          .type   = CX88_VMUX_COMPOSITE1,
869                          .vmux   = 1,
870                          .gpio0  = 0x03000000,
871                          .gpio1  = 0x01000000,
872                          .gpio2  = 0x02000000,
873                          .gpio3  = 0x00100000,
874                  }, {
875                          .type   = CX88_VMUX_SVIDEO,
876                          .vmux   = 2,
877                          .gpio0  = 0x03000000,
878                          .gpio1  = 0x01000000,
879                          .gpio2  = 0x02000000,
880                          .gpio3  = 0x00100000,
881                  } },
882         },
883         [CX88_BOARD_ATI_HDTVWONDER] = {
884                 .name           = "ATI HDTV Wonder",
885                 .tuner_type     = TUNER_PHILIPS_TUV1236D,
886                 .radio_type     = UNSET,
887                 .tuner_addr     = ADDR_UNSET,
888                 .radio_addr     = ADDR_UNSET,
889                 .input          = { {
890                         .type   = CX88_VMUX_TELEVISION,
891                         .vmux   = 0,
892                         .gpio0  = 0x00000ff7,
893                         .gpio1  = 0x000000ff,
894                         .gpio2  = 0x00000001,
895                         .gpio3  = 0x00000000,
896                 }, {
897                         .type   = CX88_VMUX_COMPOSITE1,
898                         .vmux   = 1,
899                         .gpio0  = 0x00000ffe,
900                         .gpio1  = 0x000000ff,
901                         .gpio2  = 0x00000001,
902                         .gpio3  = 0x00000000,
903                 }, {
904                         .type   = CX88_VMUX_SVIDEO,
905                         .vmux   = 2,
906                         .gpio0  = 0x00000ffe,
907                         .gpio1  = 0x000000ff,
908                         .gpio2  = 0x00000001,
909                         .gpio3  = 0x00000000,
910                 } },
911                 .mpeg           = CX88_MPEG_DVB,
912         },
913         [CX88_BOARD_WINFAST_DTV1000] = {
914                 .name           = "WinFast DTV1000-T",
915                 .tuner_type     = UNSET,
916                 .radio_type     = UNSET,
917                 .tuner_addr     = ADDR_UNSET,
918                 .radio_addr     = ADDR_UNSET,
919                 .input          = { {
920                         .type   = CX88_VMUX_DVB,
921                         .vmux   = 0,
922                 }, {
923                         .type   = CX88_VMUX_COMPOSITE1,
924                         .vmux   = 1,
925                 }, {
926                         .type   = CX88_VMUX_SVIDEO,
927                         .vmux   = 2,
928                 } },
929                 .mpeg           = CX88_MPEG_DVB,
930         },
931         [CX88_BOARD_AVERTV_303] = {
932                 .name           = "AVerTV 303 (M126)",
933                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
934                 .radio_type     = UNSET,
935                 .tuner_addr     = ADDR_UNSET,
936                 .radio_addr     = ADDR_UNSET,
937                 .tda9887_conf   = TDA9887_PRESENT,
938                 .input          = { {
939                         .type   = CX88_VMUX_TELEVISION,
940                         .vmux   = 0,
941                         .gpio0  = 0x00ff,
942                         .gpio1  = 0xe09f,
943                         .gpio2  = 0x0010,
944                         .gpio3  = 0x0000,
945                 }, {
946                         .type   = CX88_VMUX_COMPOSITE1,
947                         .vmux   = 1,
948                         .gpio0  = 0x00ff,
949                         .gpio1  = 0xe05f,
950                         .gpio2  = 0x0010,
951                         .gpio3  = 0x0000,
952                 }, {
953                         .type   = CX88_VMUX_SVIDEO,
954                         .vmux   = 2,
955                         .gpio0  = 0x00ff,
956                         .gpio1  = 0xe05f,
957                         .gpio2  = 0x0010,
958                         .gpio3  = 0x0000,
959                 } },
960         },
961         [CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1] = {
962                 .name           = "Hauppauge Nova-S-Plus DVB-S",
963                 .tuner_type     = UNSET,
964                 .radio_type     = UNSET,
965                 .tuner_addr     = ADDR_UNSET,
966                 .radio_addr     = ADDR_UNSET,
967                 .audio_chip     = CX88_AUDIO_WM8775,
968                 .i2sinputcntl   = 2,
969                 .input          = { {
970                         .type   = CX88_VMUX_DVB,
971                         .vmux   = 0,
972                         /* 2: Line-In */
973                         .audioroute = 2,
974                 }, {
975                         .type   = CX88_VMUX_COMPOSITE1,
976                         .vmux   = 1,
977                         /* 2: Line-In */
978                         .audioroute = 2,
979                 }, {
980                         .type   = CX88_VMUX_SVIDEO,
981                         .vmux   = 2,
982                         /* 2: Line-In */
983                         .audioroute = 2,
984                 } },
985                 .mpeg           = CX88_MPEG_DVB,
986         },
987         [CX88_BOARD_HAUPPAUGE_NOVASE2_S1] = {
988                 .name           = "Hauppauge Nova-SE2 DVB-S",
989                 .tuner_type     = UNSET,
990                 .radio_type     = UNSET,
991                 .tuner_addr     = ADDR_UNSET,
992                 .radio_addr     = ADDR_UNSET,
993                 .input          = { {
994                         .type   = CX88_VMUX_DVB,
995                         .vmux   = 0,
996                 } },
997                 .mpeg           = CX88_MPEG_DVB,
998         },
999         [CX88_BOARD_KWORLD_DVBS_100] = {
1000                 .name           = "KWorld DVB-S 100",
1001                 .tuner_type     = UNSET,
1002                 .radio_type     = UNSET,
1003                 .tuner_addr     = ADDR_UNSET,
1004                 .radio_addr     = ADDR_UNSET,
1005                 .audio_chip = CX88_AUDIO_WM8775,
1006                 .input          = { {
1007                         .type   = CX88_VMUX_DVB,
1008                         .vmux   = 0,
1009                         /* 2: Line-In */
1010                         .audioroute = 2,
1011                 }, {
1012                         .type   = CX88_VMUX_COMPOSITE1,
1013                         .vmux   = 1,
1014                         /* 2: Line-In */
1015                         .audioroute = 2,
1016                 }, {
1017                         .type   = CX88_VMUX_SVIDEO,
1018                         .vmux   = 2,
1019                         /* 2: Line-In */
1020                         .audioroute = 2,
1021                 } },
1022                 .mpeg           = CX88_MPEG_DVB,
1023         },
1024         [CX88_BOARD_HAUPPAUGE_HVR1100] = {
1025                 .name           = "Hauppauge WinTV-HVR1100 DVB-T/Hybrid",
1026                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1027                 .radio_type     = UNSET,
1028                 .tuner_addr     = ADDR_UNSET,
1029                 .radio_addr     = ADDR_UNSET,
1030                 .tda9887_conf   = TDA9887_PRESENT,
1031                 .input          = { {
1032                         .type   = CX88_VMUX_TELEVISION,
1033                         .vmux   = 0,
1034                 }, {
1035                         .type   = CX88_VMUX_COMPOSITE1,
1036                         .vmux   = 1,
1037                 }, {
1038                         .type   = CX88_VMUX_SVIDEO,
1039                         .vmux   = 2,
1040                 } },
1041                 /* fixme: Add radio support */
1042                 .mpeg           = CX88_MPEG_DVB,
1043         },
1044         [CX88_BOARD_HAUPPAUGE_HVR1100LP] = {
1045                 .name           = "Hauppauge WinTV-HVR1100 DVB-T/Hybrid (Low Profile)",
1046                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1047                 .radio_type     = UNSET,
1048                 .tuner_addr     = ADDR_UNSET,
1049                 .radio_addr     = ADDR_UNSET,
1050                 .tda9887_conf   = TDA9887_PRESENT,
1051                 .input          = { {
1052                         .type   = CX88_VMUX_TELEVISION,
1053                         .vmux   = 0,
1054                 }, {
1055                         .type   = CX88_VMUX_COMPOSITE1,
1056                         .vmux   = 1,
1057                 } },
1058                 /* fixme: Add radio support */
1059                 .mpeg           = CX88_MPEG_DVB,
1060         },
1061         [CX88_BOARD_DNTV_LIVE_DVB_T_PRO] = {
1062                 .name           = "digitalnow DNTV Live! DVB-T Pro",
1063                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1064                 .radio_type     = UNSET,
1065                 .tuner_addr     = ADDR_UNSET,
1066                 .radio_addr     = ADDR_UNSET,
1067                 .tda9887_conf   = TDA9887_PRESENT | TDA9887_PORT1_ACTIVE |
1068                                   TDA9887_PORT2_ACTIVE,
1069                 .input          = { {
1070                         .type   = CX88_VMUX_TELEVISION,
1071                         .vmux   = 0,
1072                         .gpio0  = 0xf80808,
1073                 }, {
1074                         .type   = CX88_VMUX_COMPOSITE1,
1075                         .vmux   = 1,
1076                         .gpio0  = 0xf80808,
1077                 }, {
1078                         .type   = CX88_VMUX_SVIDEO,
1079                         .vmux   = 2,
1080                         .gpio0  = 0xf80808,
1081                 } },
1082                 .radio = {
1083                          .type  = CX88_RADIO,
1084                          .gpio0 = 0xf80808,
1085                 },
1086                 .mpeg           = CX88_MPEG_DVB,
1087         },
1088         [CX88_BOARD_KWORLD_DVB_T_CX22702] = {
1089                 /* Kworld V-stream Xpert DVB-T with Thomson tuner */
1090                 /* DTT 7579 Conexant CX22702-19 Conexant CX2388x  */
1091                 /* Manenti Marco <marco_manenti@colman.it> */
1092                 .name           = "KWorld/VStream XPert DVB-T with cx22702",
1093                 .tuner_type     = UNSET,
1094                 .radio_type     = UNSET,
1095                 .tuner_addr     = ADDR_UNSET,
1096                 .radio_addr     = ADDR_UNSET,
1097                 .input          = { {
1098                         .type   = CX88_VMUX_COMPOSITE1,
1099                         .vmux   = 1,
1100                         .gpio0  = 0x0700,
1101                         .gpio2  = 0x0101,
1102                 }, {
1103                         .type   = CX88_VMUX_SVIDEO,
1104                         .vmux   = 2,
1105                         .gpio0  = 0x0700,
1106                         .gpio2  = 0x0101,
1107                 } },
1108                 .mpeg           = CX88_MPEG_DVB,
1109         },
1110         [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL] = {
1111                 .name           = "DViCO FusionHDTV DVB-T Dual Digital",
1112                 .tuner_type     = UNSET, /* No analog tuner */
1113                 .radio_type     = UNSET,
1114                 .tuner_addr     = ADDR_UNSET,
1115                 .radio_addr     = ADDR_UNSET,
1116                 .input          = { {
1117                         .type   = CX88_VMUX_COMPOSITE1,
1118                         .vmux   = 1,
1119                         .gpio0  = 0x000067df,
1120                  }, {
1121                         .type   = CX88_VMUX_SVIDEO,
1122                         .vmux   = 2,
1123                         .gpio0  = 0x000067df,
1124                 } },
1125                 .mpeg           = CX88_MPEG_DVB,
1126         },
1127         [CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT] = {
1128                 .name           = "KWorld HardwareMpegTV XPert",
1129                 .tuner_type     = TUNER_PHILIPS_TDA8290,
1130                 .radio_type     = UNSET,
1131                 .tuner_addr     = ADDR_UNSET,
1132                 .radio_addr     = ADDR_UNSET,
1133                 .input          = { {
1134                         .type   = CX88_VMUX_TELEVISION,
1135                         .vmux   = 0,
1136                         .gpio0  = 0x3de2,
1137                         .gpio2  = 0x00ff,
1138                 }, {
1139                         .type   = CX88_VMUX_COMPOSITE1,
1140                         .vmux   = 1,
1141                         .gpio0  = 0x3de6,
1142                         .audioroute = 1,
1143                 }, {
1144                         .type   = CX88_VMUX_SVIDEO,
1145                         .vmux   = 2,
1146                         .gpio0  = 0x3de6,
1147                         .audioroute = 1,
1148                 } },
1149                 .radio = {
1150                         .type   = CX88_RADIO,
1151                         .gpio0  = 0x3de6,
1152                         .gpio2  = 0x00ff,
1153                 },
1154                 .mpeg           = CX88_MPEG_BLACKBIRD,
1155         },
1156         [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID] = {
1157                 .name           = "DViCO FusionHDTV DVB-T Hybrid",
1158                 .tuner_type     = TUNER_THOMSON_FE6600,
1159                 .radio_type     = UNSET,
1160                 .tuner_addr     = ADDR_UNSET,
1161                 .radio_addr     = ADDR_UNSET,
1162                 .input          = { {
1163                         .type   = CX88_VMUX_TELEVISION,
1164                         .vmux   = 0,
1165                         .gpio0  = 0x0000a75f,
1166                 }, {
1167                         .type   = CX88_VMUX_COMPOSITE1,
1168                         .vmux   = 1,
1169                         .gpio0  = 0x0000a75b,
1170                 }, {
1171                         .type   = CX88_VMUX_SVIDEO,
1172                         .vmux   = 2,
1173                         .gpio0  = 0x0000a75b,
1174                 } },
1175                 .mpeg           = CX88_MPEG_DVB,
1176         },
1177         [CX88_BOARD_PCHDTV_HD5500] = {
1178                 .name           = "pcHDTV HD5500 HDTV",
1179                 .tuner_type     = TUNER_LG_TDVS_H06XF, /* TDVS-H064F */
1180                 .radio_type     = UNSET,
1181                 .tuner_addr     = ADDR_UNSET,
1182                 .radio_addr     = ADDR_UNSET,
1183                 .tda9887_conf   = TDA9887_PRESENT,
1184                 .input          = { {
1185                         .type   = CX88_VMUX_TELEVISION,
1186                         .vmux   = 0,
1187                         .gpio0  = 0x87fd,
1188                 }, {
1189                         .type   = CX88_VMUX_COMPOSITE1,
1190                         .vmux   = 1,
1191                         .gpio0  = 0x87f9,
1192                 }, {
1193                         .type   = CX88_VMUX_SVIDEO,
1194                         .vmux   = 2,
1195                         .gpio0  = 0x87f9,
1196                 } },
1197                 .mpeg           = CX88_MPEG_DVB,
1198         },
1199         [CX88_BOARD_KWORLD_MCE200_DELUXE] = {
1200                 /*
1201                  * FIXME: tested TV input only, disabled composite,
1202                  * svideo and radio until they can be tested also.
1203                  */
1204                 .name           = "Kworld MCE 200 Deluxe",
1205                 .tuner_type     = TUNER_TENA_9533_DI,
1206                 .radio_type     = UNSET,
1207                 .tda9887_conf   = TDA9887_PRESENT,
1208                 .tuner_addr     = ADDR_UNSET,
1209                 .radio_addr     = ADDR_UNSET,
1210                 .input          = { {
1211                         .type   = CX88_VMUX_TELEVISION,
1212                         .vmux   = 0,
1213                         .gpio0  = 0x0000BDE6
1214                 } },
1215                 .mpeg           = CX88_MPEG_BLACKBIRD,
1216         },
1217         [CX88_BOARD_PIXELVIEW_PLAYTV_P7000] = {
1218                 /* FIXME: SVideo, Composite and FM inputs are untested */
1219                 .name           = "PixelView PlayTV P7000",
1220                 .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
1221                 .radio_type     = UNSET,
1222                 .tuner_addr     = ADDR_UNSET,
1223                 .radio_addr     = ADDR_UNSET,
1224                 .tda9887_conf   = TDA9887_PRESENT | TDA9887_PORT1_ACTIVE |
1225                                   TDA9887_PORT2_ACTIVE,
1226                 .input          = { {
1227                         .type   = CX88_VMUX_TELEVISION,
1228                         .vmux   = 0,
1229                         .gpio0  = 0x5da6,
1230                 } },
1231                 .mpeg           = CX88_MPEG_BLACKBIRD,
1232         },
1233         [CX88_BOARD_NPGTECH_REALTV_TOP10FM] = {
1234                 .name           = "NPG Tech Real TV FM Top 10",
1235                 .tuner_type     = TUNER_TNF_5335MF, /* Actually a TNF9535 */
1236                 .radio_type     = UNSET,
1237                 .tuner_addr     = ADDR_UNSET,
1238                 .radio_addr     = ADDR_UNSET,
1239                 .input          = { {
1240                         .type   = CX88_VMUX_TELEVISION,
1241                         .vmux   = 0,
1242                         .gpio0  = 0x0788,
1243                 }, {
1244                         .type   = CX88_VMUX_COMPOSITE1,
1245                         .vmux   = 1,
1246                         .gpio0  = 0x078b,
1247                 }, {
1248                         .type   = CX88_VMUX_SVIDEO,
1249                         .vmux   = 2,
1250                         .gpio0  = 0x078b,
1251                 } },
1252                 .radio = {
1253                          .type  = CX88_RADIO,
1254                          .gpio0 = 0x074a,
1255                 },
1256         },
1257         [CX88_BOARD_WINFAST_DTV2000H] = {
1258                 .name           = "WinFast DTV2000 H",
1259                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1260                 .radio_type     = UNSET,
1261                 .tuner_addr     = ADDR_UNSET,
1262                 .radio_addr     = ADDR_UNSET,
1263                 .tda9887_conf   = TDA9887_PRESENT,
1264                 .input          = { {
1265                         .type   = CX88_VMUX_TELEVISION,
1266                         .vmux   = 0,
1267                         .gpio0  = 0x00017304,
1268                         .gpio1  = 0x00008203,
1269                         .gpio2  = 0x00017304,
1270                         .gpio3  = 0x02000000,
1271                 }, {
1272                         .type   = CX88_VMUX_COMPOSITE1,
1273                         .vmux   = 1,
1274                         .gpio0  = 0x0001d701,
1275                         .gpio1  = 0x0000b207,
1276                         .gpio2  = 0x0001d701,
1277                         .gpio3  = 0x02000000,
1278                 }, {
1279                         .type   = CX88_VMUX_COMPOSITE2,
1280                         .vmux   = 2,
1281                         .gpio0  = 0x0001d503,
1282                         .gpio1  = 0x0000b207,
1283                         .gpio2  = 0x0001d503,
1284                         .gpio3  = 0x02000000,
1285                 }, {
1286                         .type   = CX88_VMUX_SVIDEO,
1287                         .vmux   = 3,
1288                         .gpio0  = 0x0001d701,
1289                         .gpio1  = 0x0000b207,
1290                         .gpio2  = 0x0001d701,
1291                         .gpio3  = 0x02000000,
1292                 } },
1293                 .radio = {
1294                          .type  = CX88_RADIO,
1295                          .gpio0 = 0x00015702,
1296                          .gpio1 = 0x0000f207,
1297                          .gpio2 = 0x00015702,
1298                          .gpio3 = 0x02000000,
1299                 },
1300                 .mpeg           = CX88_MPEG_DVB,
1301         },
1302         [CX88_BOARD_WINFAST_DTV2000H_J] = {
1303                 .name           = "WinFast DTV2000 H rev. J",
1304                 .tuner_type     = TUNER_PHILIPS_FMD1216MEX_MK3,
1305                 .radio_type     = UNSET,
1306                 .tuner_addr     = ADDR_UNSET,
1307                 .radio_addr     = ADDR_UNSET,
1308                 .tda9887_conf   = TDA9887_PRESENT,
1309                 .input          = { {
1310                         .type   = CX88_VMUX_TELEVISION,
1311                         .vmux   = 0,
1312                         .gpio0  = 0x00017300,
1313                         .gpio1  = 0x00008207,
1314                         .gpio2  = 0x00000000,
1315                         .gpio3  = 0x02000000,
1316                 }, {
1317                         .type   = CX88_VMUX_TELEVISION,
1318                         .vmux   = 0,
1319                         .gpio0  = 0x00018300,
1320                         .gpio1  = 0x0000f207,
1321                         .gpio2  = 0x00017304,
1322                         .gpio3  = 0x02000000,
1323                 }, {
1324                         .type   = CX88_VMUX_COMPOSITE1,
1325                         .vmux   = 1,
1326                         .gpio0  = 0x00018301,
1327                         .gpio1  = 0x0000f207,
1328                         .gpio2  = 0x00017304,
1329                         .gpio3  = 0x02000000,
1330                 }, {
1331                         .type   = CX88_VMUX_SVIDEO,
1332                         .vmux   = 2,
1333                         .gpio0  = 0x00018301,
1334                         .gpio1  = 0x0000f207,
1335                         .gpio2  = 0x00017304,
1336                         .gpio3  = 0x02000000,
1337                 } },
1338                 .radio = {
1339                          .type  = CX88_RADIO,
1340                          .gpio0 = 0x00015702,
1341                          .gpio1 = 0x0000f207,
1342                          .gpio2 = 0x00015702,
1343                          .gpio3 = 0x02000000,
1344                 },
1345                 .mpeg           = CX88_MPEG_DVB,
1346         },
1347         [CX88_BOARD_GENIATECH_DVBS] = {
1348                 .name          = "Geniatech DVB-S",
1349                 .tuner_type    = UNSET,
1350                 .radio_type    = UNSET,
1351                 .tuner_addr    = ADDR_UNSET,
1352                 .radio_addr    = ADDR_UNSET,
1353                 .input  = { {
1354                         .type  = CX88_VMUX_DVB,
1355                         .vmux  = 0,
1356                 }, {
1357                         .type  = CX88_VMUX_COMPOSITE1,
1358                         .vmux  = 1,
1359                 } },
1360                 .mpeg           = CX88_MPEG_DVB,
1361         },
1362         [CX88_BOARD_HAUPPAUGE_HVR3000] = {
1363                 .name           = "Hauppauge WinTV-HVR3000 TriMode Analog/DVB-S/DVB-T",
1364                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1365                 .radio_type     = UNSET,
1366                 .tuner_addr     = ADDR_UNSET,
1367                 .radio_addr     = ADDR_UNSET,
1368                 .tda9887_conf   = TDA9887_PRESENT,
1369                 .audio_chip     = CX88_AUDIO_WM8775,
1370                 .input          = { {
1371                         .type   = CX88_VMUX_TELEVISION,
1372                         .vmux   = 0,
1373                         .gpio0  = 0x84bf,
1374                         /* 1: TV Audio / FM Mono */
1375                         .audioroute = 1,
1376                 }, {
1377                         .type   = CX88_VMUX_COMPOSITE1,
1378                         .vmux   = 1,
1379                         .gpio0  = 0x84bf,
1380                         /* 2: Line-In */
1381                         .audioroute = 2,
1382                 }, {
1383                         .type   = CX88_VMUX_SVIDEO,
1384                         .vmux   = 2,
1385                         .gpio0  = 0x84bf,
1386                         /* 2: Line-In */
1387                         .audioroute = 2,
1388                 } },
1389                 .radio = {
1390                         .type   = CX88_RADIO,
1391                         .gpio0  = 0x84bf,
1392                         /* 4: FM Stereo (untested) */
1393                         .audioroute = 8,
1394                 },
1395                 .mpeg           = CX88_MPEG_DVB,
1396                 .num_frontends  = 2,
1397         },
1398         [CX88_BOARD_NORWOOD_MICRO] = {
1399                 .name           = "Norwood Micro TV Tuner",
1400                 .tuner_type     = TUNER_TNF_5335MF,
1401                 .radio_type     = UNSET,
1402                 .tuner_addr     = ADDR_UNSET,
1403                 .radio_addr     = ADDR_UNSET,
1404                 .input          = { {
1405                         .type   = CX88_VMUX_TELEVISION,
1406                         .vmux   = 0,
1407                         .gpio0  = 0x0709,
1408                 }, {
1409                         .type   = CX88_VMUX_COMPOSITE1,
1410                         .vmux   = 1,
1411                         .gpio0  = 0x070b,
1412                 }, {
1413                         .type   = CX88_VMUX_SVIDEO,
1414                         .vmux   = 2,
1415                         .gpio0  = 0x070b,
1416                 } },
1417         },
1418         [CX88_BOARD_TE_DTV_250_OEM_SWANN] = {
1419                 .name           = "Shenzhen Tungsten Ages Tech TE-DTV-250 / Swann OEM",
1420                 .tuner_type     = TUNER_LG_PAL_NEW_TAPC,
1421                 .radio_type     = UNSET,
1422                 .tuner_addr     = ADDR_UNSET,
1423                 .radio_addr     = ADDR_UNSET,
1424                 .input          = { {
1425                         .type   = CX88_VMUX_TELEVISION,
1426                         .vmux   = 0,
1427                         .gpio0  = 0x003fffff,
1428                         .gpio1  = 0x00e00000,
1429                         .gpio2  = 0x003fffff,
1430                         .gpio3  = 0x02000000,
1431                 }, {
1432                         .type   = CX88_VMUX_COMPOSITE1,
1433                         .vmux   = 1,
1434                         .gpio0  = 0x003fffff,
1435                         .gpio1  = 0x00e00000,
1436                         .gpio2  = 0x003fffff,
1437                         .gpio3  = 0x02000000,
1438                 }, {
1439                         .type   = CX88_VMUX_SVIDEO,
1440                         .vmux   = 2,
1441                         .gpio0  = 0x003fffff,
1442                         .gpio1  = 0x00e00000,
1443                         .gpio2  = 0x003fffff,
1444                         .gpio3  = 0x02000000,
1445                 } },
1446         },
1447         [CX88_BOARD_HAUPPAUGE_HVR1300] = {
1448                 .name           = "Hauppauge WinTV-HVR1300 DVB-T/Hybrid MPEG Encoder",
1449                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1450                 .radio_type     = UNSET,
1451                 .tuner_addr     = ADDR_UNSET,
1452                 .radio_addr     = ADDR_UNSET,
1453                 .tda9887_conf   = TDA9887_PRESENT,
1454                 .audio_chip     = CX88_AUDIO_WM8775,
1455                 /*
1456                  * gpio0 as reported by Mike Crash <mike AT mikecrash.com>
1457                  */
1458                 .input          = { {
1459                         .type   = CX88_VMUX_TELEVISION,
1460                         .vmux   = 0,
1461                         .gpio0  = 0xef88,
1462                         /* 1: TV Audio / FM Mono */
1463                         .audioroute = 1,
1464                 }, {
1465                         .type   = CX88_VMUX_COMPOSITE1,
1466                         .vmux   = 1,
1467                         .gpio0  = 0xef88,
1468                         /* 2: Line-In */
1469                         .audioroute = 2,
1470                 }, {
1471                         .type   = CX88_VMUX_SVIDEO,
1472                         .vmux   = 2,
1473                         .gpio0  = 0xef88,
1474                         /* 2: Line-In */
1475                         .audioroute = 2,
1476                 } },
1477                 .mpeg           = CX88_MPEG_DVB | CX88_MPEG_BLACKBIRD,
1478                 .radio = {
1479                         .type   = CX88_RADIO,
1480                         .gpio0  = 0xef88,
1481                         /* 4: FM Stereo (untested) */
1482                         .audioroute = 8,
1483                 },
1484         },
1485         [CX88_BOARD_SAMSUNG_SMT_7020] = {
1486                 .name           = "Samsung SMT 7020 DVB-S",
1487                 .tuner_type     = UNSET,
1488                 .radio_type     = UNSET,
1489                 .tuner_addr     = ADDR_UNSET,
1490                 .radio_addr     = ADDR_UNSET,
1491                 .input          = { {
1492                         .type   = CX88_VMUX_DVB,
1493                         .vmux   = 0,
1494                 } },
1495                 .mpeg           = CX88_MPEG_DVB,
1496         },
1497         [CX88_BOARD_ADSTECH_PTV_390] = {
1498                 .name           = "ADS Tech Instant Video PCI",
1499                 .tuner_type     = UNSET,
1500                 .radio_type     = UNSET,
1501                 .tuner_addr     = ADDR_UNSET,
1502                 .radio_addr     = ADDR_UNSET,
1503                 .input          = { {
1504                         .type   = CX88_VMUX_DEBUG,
1505                         .vmux   = 3,
1506                         .gpio0  = 0x04ff,
1507                 }, {
1508                         .type   = CX88_VMUX_COMPOSITE1,
1509                         .vmux   = 1,
1510                         .gpio0  = 0x07fa,
1511                 }, {
1512                         .type   = CX88_VMUX_SVIDEO,
1513                         .vmux   = 2,
1514                         .gpio0  = 0x07fa,
1515                 } },
1516         },
1517         [CX88_BOARD_PINNACLE_PCTV_HD_800i] = {
1518                 .name           = "Pinnacle PCTV HD 800i",
1519                 .tuner_type     = TUNER_XC5000,
1520                 .radio_type     = UNSET,
1521                 .tuner_addr     = ADDR_UNSET,
1522                 .radio_addr     = ADDR_UNSET,
1523                 .input          = { {
1524                         .type   = CX88_VMUX_TELEVISION,
1525                         .vmux   = 0,
1526                         .gpio0  = 0x04fb,
1527                         .gpio1  = 0x10ff,
1528                 }, {
1529                         .type   = CX88_VMUX_COMPOSITE1,
1530                         .vmux   = 1,
1531                         .gpio0  = 0x04fb,
1532                         .gpio1  = 0x10ef,
1533                         .audioroute = 1,
1534                 }, {
1535                         .type   = CX88_VMUX_SVIDEO,
1536                         .vmux   = 2,
1537                         .gpio0  = 0x04fb,
1538                         .gpio1  = 0x10ef,
1539                         .audioroute = 1,
1540                 } },
1541                 .mpeg           = CX88_MPEG_DVB,
1542         },
1543         [CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO] = {
1544                 .name           = "DViCO FusionHDTV 5 PCI nano",
1545                 /* xc3008 tuner, digital only for now */
1546                 .tuner_type     = UNSET,
1547                 .radio_type     = UNSET,
1548                 .tuner_addr     = ADDR_UNSET,
1549                 .radio_addr     = ADDR_UNSET,
1550                 .input          = { {
1551                         .type   = CX88_VMUX_TELEVISION,
1552                         .vmux   = 0,
1553                         .gpio0  = 0x000027df, /* Unconfirmed */
1554                 }, {
1555                         .type   = CX88_VMUX_COMPOSITE1,
1556                         .vmux   = 1,
1557                         .gpio0  = 0x000027df, /* Unconfirmed */
1558                         .audioroute = 1,
1559                 }, {
1560                         .type   = CX88_VMUX_SVIDEO,
1561                         .vmux   = 2,
1562                         .gpio0  = 0x000027df, /* Unconfirmed */
1563                         .audioroute = 1,
1564                 } },
1565                 .mpeg           = CX88_MPEG_DVB,
1566         },
1567         [CX88_BOARD_PINNACLE_HYBRID_PCTV] = {
1568                 .name           = "Pinnacle Hybrid PCTV",
1569                 .tuner_type     = TUNER_XC2028,
1570                 .tuner_addr     = 0x61,
1571                 .radio_type     = UNSET,
1572                 .radio_addr     = ADDR_UNSET,
1573                 .input          = { {
1574                         .type   = CX88_VMUX_TELEVISION,
1575                         .vmux   = 0,
1576                         .gpio0  = 0x004ff,
1577                         .gpio1  = 0x010ff,
1578                         .gpio2  = 0x00001,
1579                 }, {
1580                         .type   = CX88_VMUX_COMPOSITE1,
1581                         .vmux   = 1,
1582                         .gpio0  = 0x004fb,
1583                         .gpio1  = 0x010ef,
1584                         .audioroute = 1,
1585                 }, {
1586                         .type   = CX88_VMUX_SVIDEO,
1587                         .vmux   = 2,
1588                         .gpio0  = 0x004fb,
1589                         .gpio1  = 0x010ef,
1590                         .audioroute = 1,
1591                 } },
1592                 .radio = {
1593                         .type   = CX88_RADIO,
1594                         .gpio0  = 0x004ff,
1595                         .gpio1  = 0x010ff,
1596                         .gpio2  = 0x0ff,
1597                 },
1598                 .mpeg           = CX88_MPEG_DVB,
1599         },
1600         /* Terry Wu <terrywu2009@gmail.com> */
1601         /* TV Audio :      set GPIO 2, 18, 19 value to 0, 1, 0 */
1602         /* FM Audio :      set GPIO 2, 18, 19 value to 0, 0, 0 */
1603         /* Line-in Audio : set GPIO 2, 18, 19 value to 0, 1, 1 */
1604         /* Mute Audio :    set GPIO 2 value to 1               */
1605         [CX88_BOARD_WINFAST_TV2000_XP_GLOBAL] = {
1606                 .name           = "Leadtek TV2000 XP Global",
1607                 .tuner_type     = TUNER_XC2028,
1608                 .tuner_addr     = 0x61,
1609                 .radio_type     = UNSET,
1610                 .radio_addr     = ADDR_UNSET,
1611                 .input          = { {
1612                         .type   = CX88_VMUX_TELEVISION,
1613                         .vmux   = 0,
1614                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1615                         .gpio1  = 0x0000,
1616                         .gpio2  = 0x0C04,       /* pin 18 = 1, pin 19 = 0 */
1617                         .gpio3  = 0x0000,
1618                 }, {
1619                         .type   = CX88_VMUX_COMPOSITE1,
1620                         .vmux   = 1,
1621                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1622                         .gpio1  = 0x0000,
1623                         .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1624                         .gpio3  = 0x0000,
1625                 }, {
1626                         .type   = CX88_VMUX_SVIDEO,
1627                         .vmux   = 2,
1628                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1629                         .gpio1  = 0x0000,
1630                         .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1631                         .gpio3  = 0x0000,
1632                 } },
1633                 .radio = {
1634                         .type   = CX88_RADIO,
1635                         .gpio0  = 0x0400,        /* pin 2 = 0 */
1636                         .gpio1  = 0x0000,
1637                         .gpio2  = 0x0C00,       /* pin 18 = 0, pin 19 = 0 */
1638                         .gpio3  = 0x0000,
1639                 },
1640         },
1641         [CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36] = {
1642                 .name           = "Leadtek TV2000 XP Global (SC4100)",
1643                 .tuner_type     = TUNER_XC4000,
1644                 .tuner_addr     = 0x61,
1645                 .radio_type     = UNSET,
1646                 .radio_addr     = ADDR_UNSET,
1647                 .input          = { {
1648                         .type   = CX88_VMUX_TELEVISION,
1649                         .vmux   = 0,
1650                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1651                         .gpio1  = 0x0000,
1652                         .gpio2  = 0x0C04,       /* pin 18 = 1, pin 19 = 0 */
1653                         .gpio3  = 0x0000,
1654                 }, {
1655                         .type   = CX88_VMUX_COMPOSITE1,
1656                         .vmux   = 1,
1657                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1658                         .gpio1  = 0x0000,
1659                         .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1660                         .gpio3  = 0x0000,
1661                 }, {
1662                         .type   = CX88_VMUX_SVIDEO,
1663                         .vmux   = 2,
1664                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1665                         .gpio1  = 0x0000,
1666                         .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1667                         .gpio3  = 0x0000,
1668                 } },
1669                 .radio = {
1670                         .type   = CX88_RADIO,
1671                         .gpio0  = 0x0400,        /* pin 2 = 0 */
1672                         .gpio1  = 0x0000,
1673                         .gpio2  = 0x0C00,       /* pin 18 = 0, pin 19 = 0 */
1674                         .gpio3  = 0x0000,
1675                 },
1676         },
1677         [CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43] = {
1678                 .name           = "Leadtek TV2000 XP Global (XC4100)",
1679                 .tuner_type     = TUNER_XC4000,
1680                 .tuner_addr     = 0x61,
1681                 .radio_type     = UNSET,
1682                 .radio_addr     = ADDR_UNSET,
1683                 .input          = { {
1684                         .type   = CX88_VMUX_TELEVISION,
1685                         .vmux   = 0,
1686                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1687                         .gpio1  = 0x6040,       /* pin 14 = 1, pin 13 = 0 */
1688                         .gpio2  = 0x0000,
1689                         .gpio3  = 0x0000,
1690                 }, {
1691                         .type   = CX88_VMUX_COMPOSITE1,
1692                         .vmux   = 1,
1693                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1694                         .gpio1  = 0x6060,       /* pin 14 = 1, pin 13 = 1 */
1695                         .gpio2  = 0x0000,
1696                         .gpio3  = 0x0000,
1697                 }, {
1698                         .type   = CX88_VMUX_SVIDEO,
1699                         .vmux   = 2,
1700                         .gpio0  = 0x0400,       /* pin 2 = 0 */
1701                         .gpio1  = 0x6060,       /* pin 14 = 1, pin 13 = 1 */
1702                         .gpio2  = 0x0000,
1703                         .gpio3  = 0x0000,
1704                 } },
1705                 .radio = {
1706                         .type   = CX88_RADIO,
1707                         .gpio0  = 0x0400,        /* pin 2 = 0 */
1708                         .gpio1  = 0x6000,        /* pin 14 = 1, pin 13 = 0 */
1709                         .gpio2  = 0x0000,
1710                         .gpio3  = 0x0000,
1711                 },
1712         },
1713         [CX88_BOARD_POWERCOLOR_REAL_ANGEL] = {
1714                 /* Long names may confuse LIRC. */
1715                 .name           = "PowerColor RA330",
1716                 .tuner_type     = TUNER_XC2028,
1717                 .tuner_addr     = 0x61,
1718                 .input          = { {
1719                         /*
1720                          * Due to the way the cx88 driver is written,
1721                          * there is no way to deactivate audio pass-
1722                          * through without this entry. Furthermore, if
1723                          * the TV mux entry is first, you get audio
1724                          * from the tuner on boot for a little while.
1725                          */
1726                         .type   = CX88_VMUX_DEBUG,
1727                         .vmux   = 3,
1728                         .gpio0 = 0x00ff,
1729                         .gpio1 = 0xf39d,
1730                         .gpio3 = 0x0000,
1731                 }, {
1732                         .type   = CX88_VMUX_TELEVISION,
1733                         .vmux   = 0,
1734                         .gpio0 = 0x00ff,
1735                         .gpio1 = 0xf35d,
1736                         .gpio3 = 0x0000,
1737                 }, {
1738                         .type   = CX88_VMUX_COMPOSITE1,
1739                         .vmux   = 1,
1740                         .gpio0 = 0x00ff,
1741                         .gpio1 = 0xf37d,
1742                         .gpio3 = 0x0000,
1743                 }, {
1744                         .type   = CX88_VMUX_SVIDEO,
1745                         .vmux   = 2,
1746                         .gpio0  = 0x000ff,
1747                         .gpio1  = 0x0f37d,
1748                         .gpio3  = 0x00000,
1749                 } },
1750                 .radio = {
1751                         .type   = CX88_RADIO,
1752                         .gpio0  = 0x000ff,
1753                         .gpio1  = 0x0f35d,
1754                         .gpio3  = 0x00000,
1755                 },
1756         },
1757         [CX88_BOARD_GENIATECH_X8000_MT] = {
1758                 /* Also PowerColor Real Angel 330 and Geniatech X800 OEM */
1759                 .name           = "Geniatech X8000-MT DVBT",
1760                 .tuner_type     = TUNER_XC2028,
1761                 .tuner_addr     = 0x61,
1762                 .input          = { {
1763                         .type   = CX88_VMUX_TELEVISION,
1764                         .vmux   = 0,
1765                         .gpio0  = 0x00000000,
1766                         .gpio1  = 0x00e3e341,
1767                         .gpio2  = 0x00000000,
1768                         .gpio3  = 0x00000000,
1769                 }, {
1770                         .type   = CX88_VMUX_COMPOSITE1,
1771                         .vmux   = 1,
1772                         .gpio0  = 0x00000000,
1773                         .gpio1  = 0x00e3e361,
1774                         .gpio2  = 0x00000000,
1775                         .gpio3  = 0x00000000,
1776                 }, {
1777                         .type   = CX88_VMUX_SVIDEO,
1778                         .vmux   = 2,
1779                         .gpio0  = 0x00000000,
1780                         .gpio1  = 0x00e3e361,
1781                         .gpio2  = 0x00000000,
1782                         .gpio3  = 0x00000000,
1783                 } },
1784                 .radio = {
1785                         .type   = CX88_RADIO,
1786                         .gpio0  = 0x00000000,
1787                         .gpio1  = 0x00e3e341,
1788                         .gpio2  = 0x00000000,
1789                         .gpio3  = 0x00000000,
1790                 },
1791                 .mpeg           = CX88_MPEG_DVB,
1792         },
1793         [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO] = {
1794                 .name           = "DViCO FusionHDTV DVB-T PRO",
1795                 .tuner_type     = TUNER_XC2028,
1796                 .tuner_addr     = 0x61,
1797                 .radio_type     = UNSET,
1798                 .radio_addr     = ADDR_UNSET,
1799                 .input          = { {
1800                         .type   = CX88_VMUX_COMPOSITE1,
1801                         .vmux   = 1,
1802                         .gpio0  = 0x000067df,
1803                 }, {
1804                         .type   = CX88_VMUX_SVIDEO,
1805                         .vmux   = 2,
1806                         .gpio0  = 0x000067df,
1807                 } },
1808                 .mpeg           = CX88_MPEG_DVB,
1809         },
1810         [CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD] = {
1811                 .name           = "DViCO FusionHDTV 7 Gold",
1812                 .tuner_type     = TUNER_XC5000,
1813                 .radio_type     = UNSET,
1814                 .tuner_addr     = ADDR_UNSET,
1815                 .radio_addr     = ADDR_UNSET,
1816                 .input          = { {
1817                         .type   = CX88_VMUX_TELEVISION,
1818                         .vmux   = 0,
1819                         .gpio0  = 0x10df,
1820                 }, {
1821                         .type   = CX88_VMUX_COMPOSITE1,
1822                         .vmux   = 1,
1823                         .gpio0  = 0x16d9,
1824                 }, {
1825                         .type   = CX88_VMUX_SVIDEO,
1826                         .vmux   = 2,
1827                         .gpio0  = 0x16d9,
1828                 } },
1829                 .mpeg           = CX88_MPEG_DVB,
1830         },
1831         [CX88_BOARD_PROLINK_PV_8000GT] = {
1832                 .name           = "Prolink Pixelview MPEG 8000GT",
1833                 .tuner_type     = TUNER_XC2028,
1834                 .tuner_addr     = 0x61,
1835                 .input          = { {
1836                         .type   = CX88_VMUX_TELEVISION,
1837                         .vmux   = 0,
1838                         .gpio0 = 0x0ff,
1839                         .gpio2 = 0x0cfb,
1840                 }, {
1841                         .type   = CX88_VMUX_COMPOSITE1,
1842                         .vmux   = 1,
1843                         .gpio2 = 0x0cfb,
1844                 }, {
1845                         .type   = CX88_VMUX_SVIDEO,
1846                         .vmux   = 2,
1847                         .gpio2 = 0x0cfb,
1848                 } },
1849                 .radio = {
1850                         .type   = CX88_RADIO,
1851                         .gpio2 = 0x0cfb,
1852                 },
1853         },
1854         [CX88_BOARD_PROLINK_PV_GLOBAL_XTREME] = {
1855                 .name           = "Prolink Pixelview Global Extreme",
1856                 .tuner_type     = TUNER_XC2028,
1857                 .tuner_addr     = 0x61,
1858                 .input          = { {
1859                         .type   = CX88_VMUX_TELEVISION,
1860                         .vmux   = 0,
1861                         .gpio0 = 0x04fb,
1862                         .gpio1 = 0x04080,
1863                         .gpio2 = 0x0cf7,
1864                 }, {
1865                         .type   = CX88_VMUX_COMPOSITE1,
1866                         .vmux   = 1,
1867                         .gpio0 = 0x04fb,
1868                         .gpio1 = 0x04080,
1869                         .gpio2 = 0x0cfb,
1870                 }, {
1871                         .type   = CX88_VMUX_SVIDEO,
1872                         .vmux   = 2,
1873                         .gpio0 = 0x04fb,
1874                         .gpio1 = 0x04080,
1875                         .gpio2 = 0x0cfb,
1876                 } },
1877                 .radio = {
1878                         .type   = CX88_RADIO,
1879                         .gpio0 = 0x04ff,
1880                         .gpio1 = 0x04080,
1881                         .gpio2 = 0x0cf7,
1882                 },
1883         },
1884         /*
1885          * Both radio, analog and ATSC work with this board.
1886          * However, for analog to work, s5h1409 gate should be open,
1887          * otherwise, tuner-xc3028 won't be detected.
1888          * A proper fix require using the newer i2c methods to add
1889          * tuner-xc3028 without doing an i2c probe.
1890          */
1891         [CX88_BOARD_KWORLD_ATSC_120] = {
1892                 .name           = "Kworld PlusTV HD PCI 120 (ATSC 120)",
1893                 .tuner_type     = TUNER_XC2028,
1894                 .radio_type     = UNSET,
1895                 .tuner_addr     = ADDR_UNSET,
1896                 .radio_addr     = ADDR_UNSET,
1897                 .input          = { {
1898                         .type   = CX88_VMUX_TELEVISION,
1899                         .vmux   = 0,
1900                         .gpio0  = 0x000000ff,
1901                         .gpio1  = 0x0000f35d,
1902                         .gpio2  = 0x00000000,
1903                 }, {
1904                         .type   = CX88_VMUX_COMPOSITE1,
1905                         .vmux   = 1,
1906                         .gpio0  = 0x000000ff,
1907                         .gpio1  = 0x0000f37e,
1908                         .gpio2  = 0x00000000,
1909                 }, {
1910                         .type   = CX88_VMUX_SVIDEO,
1911                         .vmux   = 2,
1912                         .gpio0  = 0x000000ff,
1913                         .gpio1  = 0x0000f37e,
1914                         .gpio2  = 0x00000000,
1915                 } },
1916                 .radio = {
1917                         .type   = CX88_RADIO,
1918                         .gpio0  = 0x000000ff,
1919                         .gpio1  = 0x0000f35d,
1920                         .gpio2  = 0x00000000,
1921                 },
1922                 .mpeg           = CX88_MPEG_DVB,
1923         },
1924         [CX88_BOARD_HAUPPAUGE_HVR4000] = {
1925                 .name           = "Hauppauge WinTV-HVR4000 DVB-S/S2/T/Hybrid",
1926                 .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1927                 .radio_type     = UNSET,
1928                 .tuner_addr     = ADDR_UNSET,
1929                 .radio_addr     = ADDR_UNSET,
1930                 .tda9887_conf   = TDA9887_PRESENT,
1931                 .audio_chip     = CX88_AUDIO_WM8775,
1932                 /*
1933                  * GPIO0 (WINTV2000)
1934                  *
1935                  * Analogue     SAT     DVB-T
1936                  * Antenna      0xc4bf  0xc4bb
1937                  * Composite    0xc4bf  0xc4bb
1938                  * S-Video      0xc4bf  0xc4bb
1939                  * Composite1   0xc4ff  0xc4fb
1940                  * S-Video1     0xc4ff  0xc4fb
1941                  *
1942                  * BIT  VALUE   FUNCTION GP{x}_IO
1943                  * 0    1       I:?
1944                  * 1    1       I:?
1945                  * 2    1       O:MPEG PORT 0=DVB-T 1=DVB-S
1946                  * 3    1       I:?
1947                  * 4    1       I:?
1948                  * 5    1       I:?
1949                  * 6    0       O:INPUT SELECTOR 0=INTERNAL 1=EXPANSION
1950                  * 7    1       O:DVB-T DEMOD RESET LOW
1951                  *
1952                  * BIT  VALUE   FUNCTION GP{x}_OE
1953                  * 8    0       I
1954                  * 9    0       I
1955                  * a    1       O
1956                  * b    0       I
1957                  * c    0       I
1958                  * d    0       I
1959                  * e    1       O
1960                  * f    1       O
1961                  *
1962                  * WM8775 ADC
1963                  *
1964                  * 1: TV Audio / FM Mono
1965                  * 2: Line-In
1966                  * 3: Line-In Expansion
1967                  * 4: FM Stereo
1968                  */
1969                 .input          = { {
1970                         .type   = CX88_VMUX_TELEVISION,
1971                         .vmux   = 0,
1972                         .gpio0  = 0xc4bf,
1973                         /* 1: TV Audio / FM Mono */
1974                         .audioroute = 1,
1975                 }, {
1976                         .type   = CX88_VMUX_COMPOSITE1,
1977                         .vmux   = 1,
1978                         .gpio0  = 0xc4bf,
1979                         /* 2: Line-In */
1980                         .audioroute = 2,
1981                 }, {
1982                         .type   = CX88_VMUX_SVIDEO,
1983                         .vmux   = 2,
1984                         .gpio0  = 0xc4bf,
1985                         /* 2: Line-In */
1986                         .audioroute = 2,
1987                 } },
1988                 .radio = {
1989                         .type   = CX88_RADIO,
1990                         .gpio0  = 0xc4bf,
1991                         /* 4: FM Stereo */
1992                         .audioroute = 8,
1993                 },
1994                 .mpeg           = CX88_MPEG_DVB,
1995                 .num_frontends  = 2,
1996         },
1997         [CX88_BOARD_HAUPPAUGE_HVR4000LITE] = {
1998                 .name           = "Hauppauge WinTV-HVR4000(Lite) DVB-S/S2",
1999                 .tuner_type     = UNSET,
2000                 .radio_type     = UNSET,
2001                 .tuner_addr     = ADDR_UNSET,
2002                 .radio_addr     = ADDR_UNSET,
2003                 .input          = { {
2004                         .type   = CX88_VMUX_DVB,
2005                         .vmux   = 0,
2006                 } },
2007                 .mpeg           = CX88_MPEG_DVB,
2008         },
2009         [CX88_BOARD_TEVII_S420] = {
2010                 .name           = "TeVii S420 DVB-S",
2011                 .tuner_type     = UNSET,
2012                 .radio_type     = UNSET,
2013                 .tuner_addr     = ADDR_UNSET,
2014                 .radio_addr     = ADDR_UNSET,
2015                 .input          = { {
2016                         .type   = CX88_VMUX_DVB,
2017                         .vmux   = 0,
2018                 } },
2019                 .mpeg           = CX88_MPEG_DVB,
2020         },
2021         [CX88_BOARD_TEVII_S460] = {
2022                 .name           = "TeVii S460 DVB-S/S2",
2023                 .tuner_type     = UNSET,
2024                 .radio_type     = UNSET,
2025                 .tuner_addr     = ADDR_UNSET,
2026                 .radio_addr     = ADDR_UNSET,
2027                 .input          = { {
2028                         .type   = CX88_VMUX_DVB,
2029                         .vmux   = 0,
2030                 } },
2031                 .mpeg           = CX88_MPEG_DVB,
2032         },
2033         [CX88_BOARD_TEVII_S464] = {
2034                 .name           = "TeVii S464 DVB-S/S2",
2035                 .tuner_type     = UNSET,
2036                 .radio_type     = UNSET,
2037                 .tuner_addr     = ADDR_UNSET,
2038                 .radio_addr     = ADDR_UNSET,
2039                 .input          = { {
2040                         .type   = CX88_VMUX_DVB,
2041                         .vmux   = 0,
2042                 } },
2043                 .mpeg           = CX88_MPEG_DVB,
2044         },
2045         [CX88_BOARD_OMICOM_SS4_PCI] = {
2046                 .name           = "Omicom SS4 DVB-S/S2 PCI",
2047                 .tuner_type     = UNSET,
2048                 .radio_type     = UNSET,
2049                 .tuner_addr     = ADDR_UNSET,
2050                 .radio_addr     = ADDR_UNSET,
2051                 .input          = { {
2052                         .type   = CX88_VMUX_DVB,
2053                         .vmux   = 0,
2054                 } },
2055                 .mpeg           = CX88_MPEG_DVB,
2056         },
2057         [CX88_BOARD_TBS_8910] = {
2058                 .name           = "TBS 8910 DVB-S",
2059                 .tuner_type     = UNSET,
2060                 .radio_type     = UNSET,
2061                 .tuner_addr     = ADDR_UNSET,
2062                 .radio_addr     = ADDR_UNSET,
2063                 .input          = { {
2064                         .type   = CX88_VMUX_DVB,
2065                         .vmux   = 0,
2066                 } },
2067                 .mpeg           = CX88_MPEG_DVB,
2068         },
2069         [CX88_BOARD_TBS_8920] = {
2070                 .name           = "TBS 8920 DVB-S/S2",
2071                 .tuner_type     = UNSET,
2072                 .radio_type     = UNSET,
2073                 .tuner_addr     = ADDR_UNSET,
2074                 .radio_addr     = ADDR_UNSET,
2075                 .input          = { {
2076                         .type   = CX88_VMUX_DVB,
2077                         .vmux   = 0,
2078                         .gpio0  = 0x8080,
2079                 } },
2080                 .mpeg           = CX88_MPEG_DVB,
2081         },
2082         [CX88_BOARD_PROF_6200] = {
2083                 .name           = "Prof 6200 DVB-S",
2084                 .tuner_type     = UNSET,
2085                 .radio_type     = UNSET,
2086                 .tuner_addr     = ADDR_UNSET,
2087                 .radio_addr     = ADDR_UNSET,
2088                 .input          = { {
2089                         .type   = CX88_VMUX_DVB,
2090                         .vmux   = 0,
2091                 } },
2092                 .mpeg           = CX88_MPEG_DVB,
2093         },
2094         [CX88_BOARD_PROF_7300] = {
2095                 .name           = "PROF 7300 DVB-S/S2",
2096                 .tuner_type     = UNSET,
2097                 .radio_type     = UNSET,
2098                 .tuner_addr     = ADDR_UNSET,
2099                 .radio_addr     = ADDR_UNSET,
2100                 .input          = { {
2101                         .type   = CX88_VMUX_DVB,
2102                         .vmux   = 0,
2103                 } },
2104                 .mpeg           = CX88_MPEG_DVB,
2105         },
2106         [CX88_BOARD_SATTRADE_ST4200] = {
2107                 .name           = "SATTRADE ST4200 DVB-S/S2",
2108                 .tuner_type     = UNSET,
2109                 .radio_type     = UNSET,
2110                 .tuner_addr     = ADDR_UNSET,
2111                 .radio_addr     = ADDR_UNSET,
2112                 .input          = { {
2113                         .type   = CX88_VMUX_DVB,
2114                         .vmux   = 0,
2115                 } },
2116                 .mpeg           = CX88_MPEG_DVB,
2117         },
2118         [CX88_BOARD_TERRATEC_CINERGY_HT_PCI_MKII] = {
2119                 .name           = "Terratec Cinergy HT PCI MKII",
2120                 .tuner_type     = TUNER_XC2028,
2121                 .tuner_addr     = 0x61,
2122                 .radio_type     = UNSET,
2123                 .radio_addr     = ADDR_UNSET,
2124                 .input          = { {
2125                         .type   = CX88_VMUX_TELEVISION,
2126                         .vmux   = 0,
2127                         .gpio0  = 0x004ff,
2128                         .gpio1  = 0x010ff,
2129                         .gpio2  = 0x00001,
2130                 }, {
2131                         .type   = CX88_VMUX_COMPOSITE1,
2132                         .vmux   = 1,
2133                         .gpio0  = 0x004fb,
2134                         .gpio1  = 0x010ef,
2135                         .audioroute = 1,
2136                 }, {
2137                         .type   = CX88_VMUX_SVIDEO,
2138                         .vmux   = 2,
2139                         .gpio0  = 0x004fb,
2140                         .gpio1  = 0x010ef,
2141                         .audioroute = 1,
2142                 } },
2143                 .radio = {
2144                         .type   = CX88_RADIO,
2145                         .gpio0  = 0x004ff,
2146                         .gpio1  = 0x010ff,
2147                         .gpio2  = 0x0ff,
2148                 },
2149                 .mpeg           = CX88_MPEG_DVB,
2150         },
2151         [CX88_BOARD_HAUPPAUGE_IRONLY] = {
2152                 .name           = "Hauppauge WinTV-IR Only",
2153                 .tuner_type     = UNSET,
2154                 .radio_type     = UNSET,
2155                 .tuner_addr     = ADDR_UNSET,
2156                 .radio_addr     = ADDR_UNSET,
2157         },
2158         [CX88_BOARD_WINFAST_DTV1800H] = {
2159                 .name           = "Leadtek WinFast DTV1800 Hybrid",
2160                 .tuner_type     = TUNER_XC2028,
2161                 .radio_type     = UNSET,
2162                 .tuner_addr     = 0x61,
2163                 .radio_addr     = ADDR_UNSET,
2164                 /*
2165                  * GPIO setting
2166                  *
2167                  *  2: mute (0=off,1=on)
2168                  * 12: tuner reset pin
2169                  * 13: audio source (0=tuner audio,1=line in)
2170                  * 14: FM (0=on,1=off ???)
2171                  */
2172                 .input          = { {
2173                         .type   = CX88_VMUX_TELEVISION,
2174                         .vmux   = 0,
2175                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2176                         .gpio1  = 0x6040,       /* pin 13 = 0, pin 14 = 1 */
2177                         .gpio2  = 0x0000,
2178                 }, {
2179                         .type   = CX88_VMUX_COMPOSITE1,
2180                         .vmux   = 1,
2181                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2182                         .gpio1  = 0x6060,       /* pin 13 = 1, pin 14 = 1 */
2183                         .gpio2  = 0x0000,
2184                 }, {
2185                         .type   = CX88_VMUX_SVIDEO,
2186                         .vmux   = 2,
2187                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2188                         .gpio1  = 0x6060,       /* pin 13 = 1, pin 14 = 1 */
2189                         .gpio2  = 0x0000,
2190                 } },
2191                 .radio = {
2192                         .type   = CX88_RADIO,
2193                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2194                         .gpio1  = 0x6000,       /* pin 13 = 0, pin 14 = 0 */
2195                         .gpio2  = 0x0000,
2196                 },
2197                 .mpeg           = CX88_MPEG_DVB,
2198         },
2199         [CX88_BOARD_WINFAST_DTV1800H_XC4000] = {
2200                 .name           = "Leadtek WinFast DTV1800 H (XC4000)",
2201                 .tuner_type     = TUNER_XC4000,
2202                 .radio_type     = UNSET,
2203                 .tuner_addr     = 0x61,
2204                 .radio_addr     = ADDR_UNSET,
2205                 /*
2206                  * GPIO setting
2207                  *
2208                  *  2: mute (0=off,1=on)
2209                  * 12: tuner reset pin
2210                  * 13: audio source (0=tuner audio,1=line in)
2211                  * 14: FM (0=on,1=off ???)
2212                  */
2213                 .input          = { {
2214                         .type   = CX88_VMUX_TELEVISION,
2215                         .vmux   = 0,
2216                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2217                         .gpio1  = 0x6040,       /* pin 13 = 0, pin 14 = 1 */
2218                         .gpio2  = 0x0000,
2219                 }, {
2220                         .type   = CX88_VMUX_COMPOSITE1,
2221                         .vmux   = 1,
2222                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2223                         .gpio1  = 0x6060,       /* pin 13 = 1, pin 14 = 1 */
2224                         .gpio2  = 0x0000,
2225                 }, {
2226                         .type   = CX88_VMUX_SVIDEO,
2227                         .vmux   = 2,
2228                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2229                         .gpio1  = 0x6060,       /* pin 13 = 1, pin 14 = 1 */
2230                         .gpio2  = 0x0000,
2231                 } },
2232                 .radio = {
2233                         .type   = CX88_RADIO,
2234                         .gpio0  = 0x0400,       /* pin 2 = 0 */
2235                         .gpio1  = 0x6000,       /* pin 13 = 0, pin 14 = 0 */
2236                         .gpio2  = 0x0000,
2237                 },
2238                 .mpeg           = CX88_MPEG_DVB,
2239         },
2240         [CX88_BOARD_WINFAST_DTV2000H_PLUS] = {
2241                 .name           = "Leadtek WinFast DTV2000 H PLUS",
2242                 .tuner_type     = TUNER_XC4000,
2243                 .radio_type     = UNSET,
2244                 .tuner_addr     = 0x61,
2245                 .radio_addr     = ADDR_UNSET,
2246                 /*
2247                  * GPIO
2248                  *   2: 1: mute audio
2249                  *  12: 0: reset XC4000
2250                  *  13: 1: audio input is line in (0: tuner)
2251                  *  14: 0: FM radio
2252                  *  16: 0: RF input is cable
2253                  */
2254                 .input          = { {
2255                         .type   = CX88_VMUX_TELEVISION,
2256                         .vmux   = 0,
2257                         .gpio0  = 0x0403,
2258                         .gpio1  = 0xF0D7,
2259                         .gpio2  = 0x0101,
2260                         .gpio3  = 0x0000,
2261                 }, {
2262                         .type   = CX88_VMUX_CABLE,
2263                         .vmux   = 0,
2264                         .gpio0  = 0x0403,
2265                         .gpio1  = 0xF0D7,
2266                         .gpio2  = 0x0100,
2267                         .gpio3  = 0x0000,
2268                 }, {
2269                         .type   = CX88_VMUX_COMPOSITE1,
2270                         .vmux   = 1,
2271                         .gpio0  = 0x0403,       /* was 0x0407 */
2272                         .gpio1  = 0xF0F7,
2273                         .gpio2  = 0x0101,
2274                         .gpio3  = 0x0000,
2275                 }, {
2276                         .type   = CX88_VMUX_SVIDEO,
2277                         .vmux   = 2,
2278                         .gpio0  = 0x0403,       /* was 0x0407 */
2279                         .gpio1  = 0xF0F7,
2280                         .gpio2  = 0x0101,
2281                         .gpio3  = 0x0000,
2282                 } },
2283                 .radio = {
2284                         .type   = CX88_RADIO,
2285                         .gpio0  = 0x0403,
2286                         .gpio1  = 0xF097,
2287                         .gpio2  = 0x0100,
2288                         .gpio3  = 0x0000,
2289                 },
2290                 .mpeg           = CX88_MPEG_DVB,
2291         },
2292         [CX88_BOARD_PROF_7301] = {
2293                 .name           = "Prof 7301 DVB-S/S2",
2294                 .tuner_type     = UNSET,
2295                 .radio_type     = UNSET,
2296                 .tuner_addr     = ADDR_UNSET,
2297                 .radio_addr     = ADDR_UNSET,
2298                 .input          = { {
2299                         .type   = CX88_VMUX_DVB,
2300                         .vmux   = 0,
2301                 } },
2302                 .mpeg           = CX88_MPEG_DVB,
2303         },
2304         [CX88_BOARD_TWINHAN_VP1027_DVBS] = {
2305                 .name           = "Twinhan VP-1027 DVB-S",
2306                 .tuner_type     = UNSET,
2307                 .radio_type     = UNSET,
2308                 .tuner_addr     = ADDR_UNSET,
2309                 .radio_addr     = ADDR_UNSET,
2310                 .input          = { {
2311                        .type   = CX88_VMUX_DVB,
2312                        .vmux   = 0,
2313                 } },
2314                 .mpeg           = CX88_MPEG_DVB,
2315         },
2316 };
2317
2318 /* ------------------------------------------------------------------ */
2319 /* PCI subsystem IDs                                                  */
2320
2321 static const struct cx88_subid cx88_subids[] = {
2322         {
2323                 .subvendor = 0x0070,
2324                 .subdevice = 0x3400,
2325                 .card      = CX88_BOARD_HAUPPAUGE,
2326         }, {
2327                 .subvendor = 0x0070,
2328                 .subdevice = 0x3401,
2329                 .card      = CX88_BOARD_HAUPPAUGE,
2330         }, {
2331                 .subvendor = 0x14c7,
2332                 .subdevice = 0x0106,
2333                 .card      = CX88_BOARD_GDI,
2334         }, {
2335                 .subvendor = 0x14c7,
2336                 .subdevice = 0x0107, /* with mpeg encoder */
2337                 .card      = CX88_BOARD_GDI,
2338         }, {
2339                 .subvendor = PCI_VENDOR_ID_ATI,
2340                 .subdevice = 0x00f8,
2341                 .card      = CX88_BOARD_ATI_WONDER_PRO,
2342         }, {
2343                 .subvendor = PCI_VENDOR_ID_ATI,
2344                 .subdevice = 0x00f9,
2345                 .card      = CX88_BOARD_ATI_WONDER_PRO,
2346         }, {
2347                 .subvendor = 0x107d,
2348                 .subdevice = 0x6611,
2349                 .card      = CX88_BOARD_WINFAST2000XP_EXPERT,
2350         }, {
2351                 .subvendor = 0x107d,
2352                 .subdevice = 0x6613,    /* NTSC */
2353                 .card      = CX88_BOARD_WINFAST2000XP_EXPERT,
2354         }, {
2355                 .subvendor = 0x107d,
2356                 .subdevice = 0x6620,
2357                 .card      = CX88_BOARD_WINFAST_DV2000,
2358         }, {
2359                 .subvendor = 0x107d,
2360                 .subdevice = 0x663b,
2361                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2362         }, {
2363                 .subvendor = 0x107d,
2364                 .subdevice = 0x663c,
2365                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2366         }, {
2367                 .subvendor = 0x1461,
2368                 .subdevice = 0x000b,
2369                 .card      = CX88_BOARD_AVERTV_STUDIO_303,
2370         }, {
2371                 .subvendor = 0x1462,
2372                 .subdevice = 0x8606,
2373                 .card      = CX88_BOARD_MSI_TVANYWHERE_MASTER,
2374         }, {
2375                 .subvendor = 0x10fc,
2376                 .subdevice = 0xd003,
2377                 .card      = CX88_BOARD_IODATA_GVVCP3PCI,
2378         }, {
2379                 .subvendor = 0x1043,
2380                 .subdevice = 0x4823,  /* with mpeg encoder */
2381                 .card      = CX88_BOARD_ASUS_PVR_416,
2382         }, {
2383                 .subvendor = 0x17de,
2384                 .subdevice = 0x08a6,
2385                 .card      = CX88_BOARD_KWORLD_DVB_T,
2386         }, {
2387                 .subvendor = 0x18ac,
2388                 .subdevice = 0xd810,
2389                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q,
2390         }, {
2391                 .subvendor = 0x18ac,
2392                 .subdevice = 0xd820,
2393                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_T,
2394         }, {
2395                 .subvendor = 0x18ac,
2396                 .subdevice = 0xdb00,
2397                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T1,
2398         }, {
2399                 .subvendor = 0x0070,
2400                 .subdevice = 0x9002,
2401                 .card      = CX88_BOARD_HAUPPAUGE_DVB_T1,
2402         }, {
2403                 .subvendor = 0x14f1,
2404                 .subdevice = 0x0187,
2405                 .card      = CX88_BOARD_CONEXANT_DVB_T1,
2406         }, {
2407                 .subvendor = 0x1540,
2408                 .subdevice = 0x2580,
2409                 .card      = CX88_BOARD_PROVIDEO_PV259,
2410         }, {
2411                 .subvendor = 0x18ac,
2412                 .subdevice = 0xdb10,
2413                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS,
2414         }, {
2415                 .subvendor = 0x1554,
2416                 .subdevice = 0x4811,
2417                 .card      = CX88_BOARD_PIXELVIEW,
2418         }, {
2419                 .subvendor = 0x7063,
2420                 .subdevice = 0x3000, /* HD-3000 card */
2421                 .card      = CX88_BOARD_PCHDTV_HD3000,
2422         }, {
2423                 .subvendor = 0x17de,
2424                 .subdevice = 0xa8a6,
2425                 .card      = CX88_BOARD_DNTV_LIVE_DVB_T,
2426         }, {
2427                 .subvendor = 0x0070,
2428                 .subdevice = 0x2801,
2429                 .card      = CX88_BOARD_HAUPPAUGE_ROSLYN,
2430         }, {
2431                 .subvendor = 0x14f1,
2432                 .subdevice = 0x0342,
2433                 .card      = CX88_BOARD_DIGITALLOGIC_MEC,
2434         }, {
2435                 .subvendor = 0x10fc,
2436                 .subdevice = 0xd035,
2437                 .card      = CX88_BOARD_IODATA_GVBCTV7E,
2438         }, {
2439                 .subvendor = 0x1421,
2440                 .subdevice = 0x0334,
2441                 .card      = CX88_BOARD_ADSTECH_DVB_T_PCI,
2442         }, {
2443                 .subvendor = 0x153b,
2444                 .subdevice = 0x1166,
2445                 .card      = CX88_BOARD_TERRATEC_CINERGY_1400_DVB_T1,
2446         }, {
2447                 .subvendor = 0x18ac,
2448                 .subdevice = 0xd500,
2449                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_5_GOLD,
2450         }, {
2451                 .subvendor = 0x1461,
2452                 .subdevice = 0x8011,
2453                 .card      = CX88_BOARD_AVERMEDIA_ULTRATV_MC_550,
2454         }, {
2455                 .subvendor = PCI_VENDOR_ID_ATI,
2456                 .subdevice = 0xa101,
2457                 .card      = CX88_BOARD_ATI_HDTVWONDER,
2458         }, {
2459                 .subvendor = 0x107d,
2460                 .subdevice = 0x665f,
2461                 .card      = CX88_BOARD_WINFAST_DTV1000,
2462         }, {
2463                 .subvendor = 0x1461,
2464                 .subdevice = 0x000a,
2465                 .card      = CX88_BOARD_AVERTV_303,
2466         }, {
2467                 .subvendor = 0x0070,
2468                 .subdevice = 0x9200,
2469                 .card      = CX88_BOARD_HAUPPAUGE_NOVASE2_S1,
2470         }, {
2471                 .subvendor = 0x0070,
2472                 .subdevice = 0x9201,
2473                 .card      = CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1,
2474         }, {
2475                 .subvendor = 0x0070,
2476                 .subdevice = 0x9202,
2477                 .card      = CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1,
2478         }, {
2479                 .subvendor = 0x17de,
2480                 .subdevice = 0x08b2,
2481                 .card      = CX88_BOARD_KWORLD_DVBS_100,
2482         }, {
2483                 .subvendor = 0x0070,
2484                 .subdevice = 0x9400,
2485                 .card      = CX88_BOARD_HAUPPAUGE_HVR1100,
2486         }, {
2487                 .subvendor = 0x0070,
2488                 .subdevice = 0x9402,
2489                 .card      = CX88_BOARD_HAUPPAUGE_HVR1100,
2490         }, {
2491                 .subvendor = 0x0070,
2492                 .subdevice = 0x9800,
2493                 .card      = CX88_BOARD_HAUPPAUGE_HVR1100LP,
2494         }, {
2495                 .subvendor = 0x0070,
2496                 .subdevice = 0x9802,
2497                 .card      = CX88_BOARD_HAUPPAUGE_HVR1100LP,
2498         }, {
2499                 .subvendor = 0x0070,
2500                 .subdevice = 0x9001,
2501                 .card      = CX88_BOARD_HAUPPAUGE_DVB_T1,
2502         }, {
2503                 .subvendor = 0x1822,
2504                 .subdevice = 0x0025,
2505                 .card      = CX88_BOARD_DNTV_LIVE_DVB_T_PRO,
2506         }, {
2507                 .subvendor = 0x17de,
2508                 .subdevice = 0x08a1,
2509                 .card      = CX88_BOARD_KWORLD_DVB_T_CX22702,
2510         }, {
2511                 .subvendor = 0x18ac,
2512                 .subdevice = 0xdb50,
2513                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL,
2514         }, {
2515                 .subvendor = 0x18ac,
2516                 .subdevice = 0xdb54,
2517                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL,
2518                 /* Re-branded DViCO: DigitalNow DVB-T Dual */
2519         }, {
2520                 .subvendor = 0x18ac,
2521                 .subdevice = 0xdb11,
2522                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS,
2523                 /* Re-branded DViCO: UltraView DVB-T Plus */
2524         }, {
2525                 .subvendor = 0x18ac,
2526                 .subdevice = 0xdb30,
2527                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO,
2528         }, {
2529                 .subvendor = 0x17de,
2530                 .subdevice = 0x0840,
2531                 .card      = CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT,
2532         }, {
2533                 .subvendor = 0x1421,
2534                 .subdevice = 0x0305,
2535                 .card      = CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT,
2536         }, {
2537                 .subvendor = 0x18ac,
2538                 .subdevice = 0xdb40,
2539                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID,
2540         }, {
2541                 .subvendor = 0x18ac,
2542                 .subdevice = 0xdb44,
2543                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID,
2544         }, {
2545                 .subvendor = 0x7063,
2546                 .subdevice = 0x5500,
2547                 .card      = CX88_BOARD_PCHDTV_HD5500,
2548         }, {
2549                 .subvendor = 0x17de,
2550                 .subdevice = 0x0841,
2551                 .card      = CX88_BOARD_KWORLD_MCE200_DELUXE,
2552         }, {
2553                 .subvendor = 0x1822,
2554                 .subdevice = 0x0019,
2555                 .card      = CX88_BOARD_DNTV_LIVE_DVB_T_PRO,
2556         }, {
2557                 .subvendor = 0x1554,
2558                 .subdevice = 0x4813,
2559                 .card      = CX88_BOARD_PIXELVIEW_PLAYTV_P7000,
2560         }, {
2561                 .subvendor = 0x14f1,
2562                 .subdevice = 0x0842,
2563                 .card      = CX88_BOARD_NPGTECH_REALTV_TOP10FM,
2564         }, {
2565                 .subvendor = 0x107d,
2566                 .subdevice = 0x665e,
2567                 .card      = CX88_BOARD_WINFAST_DTV2000H,
2568         }, {
2569                 .subvendor = 0x107d,
2570                 .subdevice = 0x6f2b,
2571                 .card      = CX88_BOARD_WINFAST_DTV2000H_J,
2572         }, {
2573                 .subvendor = 0x18ac,
2574                 .subdevice = 0xd800, /* FusionHDTV 3 Gold (original revision) */
2575                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q,
2576         }, {
2577                 .subvendor = 0x14f1,
2578                 .subdevice = 0x0084,
2579                 .card      = CX88_BOARD_GENIATECH_DVBS,
2580         }, {
2581                 .subvendor = 0x0070,
2582                 .subdevice = 0x1404,
2583                 .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2584         }, {
2585                 .subvendor = 0x18ac,
2586                 .subdevice = 0xdc00,
2587                 .card      = CX88_BOARD_SAMSUNG_SMT_7020,
2588         }, {
2589                 .subvendor = 0x18ac,
2590                 .subdevice = 0xdccd,
2591                 .card      = CX88_BOARD_SAMSUNG_SMT_7020,
2592         }, {
2593                 .subvendor = 0x1461,
2594                 .subdevice = 0xc111, /* AverMedia M150-D */
2595                 /* This board is known to work with the ASUS PVR416 config */
2596                 .card      = CX88_BOARD_ASUS_PVR_416,
2597         }, {
2598                 .subvendor = 0xc180,
2599                 .subdevice = 0xc980,
2600                 .card      = CX88_BOARD_TE_DTV_250_OEM_SWANN,
2601         }, {
2602                 .subvendor = 0x0070,
2603                 .subdevice = 0x9600,
2604                 .card      = CX88_BOARD_HAUPPAUGE_HVR1300,
2605         }, {
2606                 .subvendor = 0x0070,
2607                 .subdevice = 0x9601,
2608                 .card      = CX88_BOARD_HAUPPAUGE_HVR1300,
2609         }, {
2610                 .subvendor = 0x0070,
2611                 .subdevice = 0x9602,
2612                 .card      = CX88_BOARD_HAUPPAUGE_HVR1300,
2613         }, {
2614                 .subvendor = 0x107d,
2615                 .subdevice = 0x6632,
2616                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2617         }, {
2618                 .subvendor = 0x12ab,
2619                 .subdevice = 0x2300, /* Club3D Zap TV2100 */
2620                 .card      = CX88_BOARD_KWORLD_DVB_T_CX22702,
2621         }, {
2622                 .subvendor = 0x0070,
2623                 .subdevice = 0x9000,
2624                 .card      = CX88_BOARD_HAUPPAUGE_DVB_T1,
2625         }, {
2626                 .subvendor = 0x0070,
2627                 .subdevice = 0x1400,
2628                 .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2629         }, {
2630                 .subvendor = 0x0070,
2631                 .subdevice = 0x1401,
2632                 .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2633         }, {
2634                 .subvendor = 0x0070,
2635                 .subdevice = 0x1402,
2636                 .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2637         }, {
2638                 .subvendor = 0x1421,
2639                 .subdevice = 0x0341, /* ADS Tech InstantTV DVB-S */
2640                 .card      = CX88_BOARD_KWORLD_DVBS_100,
2641         }, {
2642                 .subvendor = 0x1421,
2643                 .subdevice = 0x0390,
2644                 .card      = CX88_BOARD_ADSTECH_PTV_390,
2645         }, {
2646                 .subvendor = 0x11bd,
2647                 .subdevice = 0x0051,
2648                 .card      = CX88_BOARD_PINNACLE_PCTV_HD_800i,
2649         }, {
2650                 .subvendor = 0x18ac,
2651                 .subdevice = 0xd530,
2652                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO,
2653         }, {
2654                 .subvendor = 0x12ab,
2655                 .subdevice = 0x1788,
2656                 .card      = CX88_BOARD_PINNACLE_HYBRID_PCTV,
2657         }, {
2658                 .subvendor = 0x14f1,
2659                 .subdevice = 0xea3d,
2660                 .card      = CX88_BOARD_POWERCOLOR_REAL_ANGEL,
2661         }, {
2662                 .subvendor = 0x107d,
2663                 .subdevice = 0x6f18,
2664                 .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL,
2665         }, {
2666                 .subvendor = 0x14f1,
2667                 .subdevice = 0x8852,
2668                 .card      = CX88_BOARD_GENIATECH_X8000_MT,
2669         }, {
2670                 .subvendor = 0x18ac,
2671                 .subdevice = 0xd610,
2672                 .card      = CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD,
2673         }, {
2674                 .subvendor = 0x1554,
2675                 .subdevice = 0x4935,
2676                 .card      = CX88_BOARD_PROLINK_PV_8000GT,
2677         }, {
2678                 .subvendor = 0x1554,
2679                 .subdevice = 0x4976,
2680                 .card      = CX88_BOARD_PROLINK_PV_GLOBAL_XTREME,
2681         }, {
2682                 .subvendor = 0x17de,
2683                 .subdevice = 0x08c1,
2684                 .card      = CX88_BOARD_KWORLD_ATSC_120,
2685         }, {
2686                 .subvendor = 0x0070,
2687                 .subdevice = 0x6900,
2688                 .card      = CX88_BOARD_HAUPPAUGE_HVR4000,
2689         }, {
2690                 .subvendor = 0x0070,
2691                 .subdevice = 0x6904,
2692                 .card      = CX88_BOARD_HAUPPAUGE_HVR4000,
2693         }, {
2694                 .subvendor = 0x0070,
2695                 .subdevice = 0x6902,
2696                 .card      = CX88_BOARD_HAUPPAUGE_HVR4000,
2697         }, {
2698                 .subvendor = 0x0070,
2699                 .subdevice = 0x6905,
2700                 .card      = CX88_BOARD_HAUPPAUGE_HVR4000LITE,
2701         }, {
2702                 .subvendor = 0x0070,
2703                 .subdevice = 0x6906,
2704                 .card      = CX88_BOARD_HAUPPAUGE_HVR4000LITE,
2705         }, {
2706                 .subvendor = 0xd420,
2707                 .subdevice = 0x9022,
2708                 .card      = CX88_BOARD_TEVII_S420,
2709         }, {
2710                 .subvendor = 0xd460,
2711                 .subdevice = 0x9022,
2712                 .card      = CX88_BOARD_TEVII_S460,
2713         }, {
2714                 .subvendor = 0xd464,
2715                 .subdevice = 0x9022,
2716                 .card      = CX88_BOARD_TEVII_S464,
2717         }, {
2718                 .subvendor = 0xA044,
2719                 .subdevice = 0x2011,
2720                 .card      = CX88_BOARD_OMICOM_SS4_PCI,
2721         }, {
2722                 .subvendor = 0x8910,
2723                 .subdevice = 0x8888,
2724                 .card      = CX88_BOARD_TBS_8910,
2725         }, {
2726                 .subvendor = 0x8920,
2727                 .subdevice = 0x8888,
2728                 .card      = CX88_BOARD_TBS_8920,
2729         }, {
2730                 .subvendor = 0xb022,
2731                 .subdevice = 0x3022,
2732                 .card      = CX88_BOARD_PROF_6200,
2733         }, {
2734                 .subvendor = 0xB033,
2735                 .subdevice = 0x3033,
2736                 .card      = CX88_BOARD_PROF_7300,
2737         }, {
2738                 .subvendor = 0xb200,
2739                 .subdevice = 0x4200,
2740                 .card      = CX88_BOARD_SATTRADE_ST4200,
2741         }, {
2742                 .subvendor = 0x153b,
2743                 .subdevice = 0x1177,
2744                 .card      = CX88_BOARD_TERRATEC_CINERGY_HT_PCI_MKII,
2745         }, {
2746                 .subvendor = 0x0070,
2747                 .subdevice = 0x9290,
2748                 .card      = CX88_BOARD_HAUPPAUGE_IRONLY,
2749         }, {
2750                 .subvendor = 0x107d,
2751                 .subdevice = 0x6654,
2752                 .card      = CX88_BOARD_WINFAST_DTV1800H,
2753         }, {
2754                 /* WinFast DTV1800 H with XC4000 tuner */
2755                 .subvendor = 0x107d,
2756                 .subdevice = 0x6f38,
2757                 .card      = CX88_BOARD_WINFAST_DTV1800H_XC4000,
2758         }, {
2759                 .subvendor = 0x107d,
2760                 .subdevice = 0x6f42,
2761                 .card      = CX88_BOARD_WINFAST_DTV2000H_PLUS,
2762         }, {
2763                 /* PVR2000 PAL Model [107d:6630] */
2764                 .subvendor = 0x107d,
2765                 .subdevice = 0x6630,
2766                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2767         }, {
2768                 /* PVR2000 PAL Model [107d:6638] */
2769                 .subvendor = 0x107d,
2770                 .subdevice = 0x6638,
2771                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2772         }, {
2773                 /* PVR2000 NTSC Model [107d:6631] */
2774                 .subvendor = 0x107d,
2775                 .subdevice = 0x6631,
2776                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2777         }, {
2778                 /* PVR2000 NTSC Model [107d:6637] */
2779                 .subvendor = 0x107d,
2780                 .subdevice = 0x6637,
2781                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2782         }, {
2783                 /* PVR2000 NTSC Model [107d:663d] */
2784                 .subvendor = 0x107d,
2785                 .subdevice = 0x663d,
2786                 .card      = CX88_BOARD_LEADTEK_PVR2000,
2787         }, {
2788                 /* DV2000 NTSC Model [107d:6621] */
2789                 .subvendor = 0x107d,
2790                 .subdevice = 0x6621,
2791                 .card      = CX88_BOARD_WINFAST_DV2000,
2792         }, {
2793                 /* TV2000 XP Global [107d:6618]  */
2794                 .subvendor = 0x107d,
2795                 .subdevice = 0x6618,
2796                 .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL,
2797         }, {
2798                 /* TV2000 XP Global [107d:6618] */
2799                 .subvendor = 0x107d,
2800                 .subdevice = 0x6619,
2801                 .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL,
2802         }, {
2803                 /* WinFast TV2000 XP Global with XC4000 tuner */
2804                 .subvendor = 0x107d,
2805                 .subdevice = 0x6f36,
2806                 .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36,
2807         }, {
2808                 /* WinFast TV2000 XP Global with XC4000 tuner and different GPIOs */
2809                 .subvendor = 0x107d,
2810                 .subdevice = 0x6f43,
2811                 .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43,
2812         }, {
2813                 .subvendor = 0xb034,
2814                 .subdevice = 0x3034,
2815                 .card      = CX88_BOARD_PROF_7301,
2816         }, {
2817                 .subvendor = 0x1822,
2818                 .subdevice = 0x0023,
2819                 .card      = CX88_BOARD_TWINHAN_VP1027_DVBS,
2820         },
2821 };
2822
2823 /*
2824  * some leadtek specific stuff
2825  */
2826 static void leadtek_eeprom(struct cx88_core *core, u8 *eeprom_data)
2827 {
2828         if (eeprom_data[4] != 0x7d ||
2829             eeprom_data[5] != 0x10 ||
2830             eeprom_data[7] != 0x66) {
2831                 pr_warn("Leadtek eeprom invalid.\n");
2832                 return;
2833         }
2834
2835         /* Terry Wu <terrywu2009@gmail.com> */
2836         switch (eeprom_data[6]) {
2837         case 0x13: /* SSID 6613 for TV2000 XP Expert NTSC Model */
2838         case 0x21: /* SSID 6621 for DV2000 NTSC Model */
2839         case 0x31: /* SSID 6631 for PVR2000 NTSC Model */
2840         case 0x37: /* SSID 6637 for PVR2000 NTSC Model */
2841         case 0x3d: /* SSID 6637 for PVR2000 NTSC Model */
2842                 core->board.tuner_type = TUNER_PHILIPS_FM1236_MK3;
2843                 break;
2844         default:
2845                 core->board.tuner_type = TUNER_PHILIPS_FM1216ME_MK3;
2846                 break;
2847         }
2848
2849         pr_info("Leadtek Winfast 2000XP Expert config: tuner=%d, eeprom[0]=0x%02x\n",
2850                 core->board.tuner_type, eeprom_data[0]);
2851 }
2852
2853 static void hauppauge_eeprom(struct cx88_core *core, u8 *eeprom_data)
2854 {
2855         struct tveeprom tv;
2856
2857         tveeprom_hauppauge_analog(&tv, eeprom_data);
2858         core->board.tuner_type = tv.tuner_type;
2859         core->tuner_formats = tv.tuner_formats;
2860         core->board.radio.type = tv.has_radio ? CX88_RADIO : 0;
2861         core->model = tv.model;
2862
2863         /* Make sure we support the board model */
2864         switch (tv.model) {
2865         case 14009: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in) */
2866         case 14019: /* WinTV-HVR3000 (Retail, IR Blaster, b/panel video, 3.5mm audio in) */
2867         case 14029: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in - 880 bridge) */
2868         case 14109: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in - low profile) */
2869         case 14129: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in - 880 bridge - LP) */
2870         case 14559: /* WinTV-HVR3000 (OEM, no IR, b/panel video, 3.5mm audio in) */
2871         case 14569: /* WinTV-HVR3000 (OEM, no IR, no back panel video) */
2872         case 14659: /* WinTV-HVR3000 (OEM, no IR, b/panel video, RCA audio in - Low profile) */
2873         case 14669: /* WinTV-HVR3000 (OEM, no IR, no b/panel video - Low profile) */
2874         case 28552: /* WinTV-PVR 'Roslyn' (No IR) */
2875         case 34519: /* WinTV-PCI-FM */
2876         case 69009:
2877                 /* WinTV-HVR4000 (DVBS/S2/T, Video and IR, back panel inputs) */
2878         case 69100: /* WinTV-HVR4000LITE (DVBS/S2, IR) */
2879         case 69500: /* WinTV-HVR4000LITE (DVBS/S2, No IR) */
2880         case 69559:
2881                 /* WinTV-HVR4000 (DVBS/S2/T, Video no IR, back panel inputs) */
2882         case 69569: /* WinTV-HVR4000 (DVBS/S2/T, Video no IR) */
2883         case 90002: /* Nova-T-PCI (9002) */
2884         case 92001: /* Nova-S-Plus (Video and IR) */
2885         case 92002: /* Nova-S-Plus (Video and IR) */
2886         case 90003: /* Nova-T-PCI (9002 No RF out) */
2887         case 90500: /* Nova-T-PCI (oem) */
2888         case 90501: /* Nova-T-PCI (oem/IR) */
2889         case 92000: /* Nova-SE2 (OEM, No Video or IR) */
2890         case 92900: /* WinTV-IROnly (No analog or digital Video inputs) */
2891         case 94009: /* WinTV-HVR1100 (Video and IR Retail) */
2892         case 94501: /* WinTV-HVR1100 (Video and IR OEM) */
2893         case 96009: /* WinTV-HVR1300 (PAL Video, MPEG Video and IR RX) */
2894         case 96019: /* WinTV-HVR1300 (PAL Video, MPEG Video and IR RX/TX) */
2895         case 96559: /* WinTV-HVR1300 (PAL Video, MPEG Video no IR) */
2896         case 96569: /* WinTV-HVR1300 () */
2897         case 96659: /* WinTV-HVR1300 () */
2898         case 98559: /* WinTV-HVR1100LP (Video no IR, Retail - Low Profile) */
2899                 /* known */
2900                 break;
2901         case CX88_BOARD_SAMSUNG_SMT_7020:
2902                 cx_set(MO_GP0_IO, 0x008989FF);
2903                 break;
2904         default:
2905                 pr_warn("warning: unknown hauppauge model #%d\n", tv.model);
2906                 break;
2907         }
2908
2909         pr_info("hauppauge eeprom: model=%d\n", tv.model);
2910 }
2911
2912 /*
2913  * some GDI (was: Modular Technology) specific stuff
2914  */
2915
2916 static const struct {
2917         int  id;
2918         int  fm;
2919         const char *name;
2920 } gdi_tuner[] = {
2921         [0x01] = { .id   = UNSET,
2922                    .name = "NTSC_M" },
2923         [0x02] = { .id   = UNSET,
2924                    .name = "PAL_B" },
2925         [0x03] = { .id   = UNSET,
2926                    .name = "PAL_I" },
2927         [0x04] = { .id   = UNSET,
2928                    .name = "PAL_D" },
2929         [0x05] = { .id   = UNSET,
2930                    .name = "SECAM" },
2931
2932         [0x10] = { .id   = UNSET,
2933                    .fm   = 1,
2934                    .name = "TEMIC_4049" },
2935         [0x11] = { .id   = TUNER_TEMIC_4136FY5,
2936                    .name = "TEMIC_4136" },
2937         [0x12] = { .id   = UNSET,
2938                    .name = "TEMIC_4146" },
2939
2940         [0x20] = { .id   = TUNER_PHILIPS_FQ1216ME,
2941                    .fm   = 1,
2942                    .name = "PHILIPS_FQ1216_MK3" },
2943         [0x21] = { .id   = UNSET, .fm = 1,
2944                    .name = "PHILIPS_FQ1236_MK3" },
2945         [0x22] = { .id   = UNSET,
2946                    .name = "PHILIPS_FI1236_MK3" },
2947         [0x23] = { .id   = UNSET,
2948                    .name = "PHILIPS_FI1216_MK3" },
2949 };
2950
2951 static void gdi_eeprom(struct cx88_core *core, u8 *eeprom_data)
2952 {
2953         const char *name = (eeprom_data[0x0d] < ARRAY_SIZE(gdi_tuner))
2954                 ? gdi_tuner[eeprom_data[0x0d]].name : NULL;
2955
2956         pr_info("GDI: tuner=%s\n", name ? name : "unknown");
2957         if (!name)
2958                 return;
2959         core->board.tuner_type = gdi_tuner[eeprom_data[0x0d]].id;
2960         core->board.radio.type = gdi_tuner[eeprom_data[0x0d]].fm ?
2961                 CX88_RADIO : 0;
2962 }
2963
2964 /*
2965  * some Divco specific stuff
2966  */
2967 static int cx88_dvico_xc2028_callback(struct cx88_core *core,
2968                                       int command, int arg)
2969 {
2970         switch (command) {
2971         case XC2028_TUNER_RESET:
2972                 switch (core->boardnr) {
2973                 case CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO:
2974                         /* GPIO-4 xc3028 tuner */
2975
2976                         cx_set(MO_GP0_IO, 0x00001000);
2977                         cx_clear(MO_GP0_IO, 0x00000010);
2978                         msleep(100);
2979                         cx_set(MO_GP0_IO, 0x00000010);
2980                         msleep(100);
2981                         break;
2982                 default:
2983                         cx_write(MO_GP0_IO, 0x101000);
2984                         mdelay(5);
2985                         cx_set(MO_GP0_IO, 0x101010);
2986                 }
2987                 break;
2988         default:
2989                 return -EINVAL;
2990         }
2991
2992         return 0;
2993 }
2994
2995 /*
2996  * some Geniatech specific stuff
2997  */
2998
2999 static int cx88_xc3028_geniatech_tuner_callback(struct cx88_core *core,
3000                                                 int command, int mode)
3001 {
3002         switch (command) {
3003         case XC2028_TUNER_RESET:
3004                 switch (INPUT(core->input).type) {
3005                 case CX88_RADIO:
3006                         break;
3007                 case CX88_VMUX_DVB:
3008                         cx_write(MO_GP1_IO, 0x030302);
3009                         mdelay(50);
3010                         break;
3011                 default:
3012                         cx_write(MO_GP1_IO, 0x030301);
3013                         mdelay(50);
3014                 }
3015                 cx_write(MO_GP1_IO, 0x101010);
3016                 mdelay(50);
3017                 cx_write(MO_GP1_IO, 0x101000);
3018                 mdelay(50);
3019                 cx_write(MO_GP1_IO, 0x101010);
3020                 mdelay(50);
3021                 return 0;
3022         }
3023         return -EINVAL;
3024 }
3025
3026 static int cx88_xc3028_winfast1800h_callback(struct cx88_core *core,
3027                                              int command, int arg)
3028 {
3029         switch (command) {
3030         case XC2028_TUNER_RESET:
3031                 /* GPIO 12 (xc3028 tuner reset) */
3032                 cx_set(MO_GP1_IO, 0x1010);
3033                 mdelay(50);
3034                 cx_clear(MO_GP1_IO, 0x10);
3035                 mdelay(75);
3036                 cx_set(MO_GP1_IO, 0x10);
3037                 mdelay(75);
3038                 return 0;
3039         }
3040         return -EINVAL;
3041 }
3042
3043 static int cx88_xc4000_winfast2000h_plus_callback(struct cx88_core *core,
3044                                                   int command, int arg)
3045 {
3046         switch (command) {
3047         case XC4000_TUNER_RESET:
3048                 /* GPIO 12 (xc4000 tuner reset) */
3049                 cx_set(MO_GP1_IO, 0x1010);
3050                 mdelay(50);
3051                 cx_clear(MO_GP1_IO, 0x10);
3052                 mdelay(75);
3053                 cx_set(MO_GP1_IO, 0x10);
3054                 mdelay(75);
3055                 return 0;
3056         }
3057         return -EINVAL;
3058 }
3059
3060 /*
3061  * some Divco specific stuff
3062  */
3063 static int cx88_pv_8000gt_callback(struct cx88_core *core,
3064                                    int command, int arg)
3065 {
3066         switch (command) {
3067         case XC2028_TUNER_RESET:
3068                 cx_write(MO_GP2_IO, 0xcf7);
3069                 mdelay(50);
3070                 cx_write(MO_GP2_IO, 0xef5);
3071                 mdelay(50);
3072                 cx_write(MO_GP2_IO, 0xcf7);
3073                 break;
3074         default:
3075                 return -EINVAL;
3076         }
3077
3078         return 0;
3079 }
3080
3081 /*
3082  * some DViCO specific stuff
3083  */
3084
3085 static void dvico_fusionhdtv_hybrid_init(struct cx88_core *core)
3086 {
3087         struct i2c_msg msg = { .addr = 0x45, .flags = 0 };
3088         int i, err;
3089         static u8 init_bufs[13][5] = {
3090                 { 0x10, 0x00, 0x20, 0x01, 0x03 },
3091                 { 0x10, 0x10, 0x01, 0x00, 0x21 },
3092                 { 0x10, 0x10, 0x10, 0x00, 0xCA },
3093                 { 0x10, 0x10, 0x12, 0x00, 0x08 },
3094                 { 0x10, 0x10, 0x13, 0x00, 0x0A },
3095                 { 0x10, 0x10, 0x16, 0x01, 0xC0 },
3096                 { 0x10, 0x10, 0x22, 0x01, 0x3D },
3097                 { 0x10, 0x10, 0x73, 0x01, 0x2E },
3098                 { 0x10, 0x10, 0x72, 0x00, 0xC5 },
3099                 { 0x10, 0x10, 0x71, 0x01, 0x97 },
3100                 { 0x10, 0x10, 0x70, 0x00, 0x0F },
3101                 { 0x10, 0x10, 0xB0, 0x00, 0x01 },
3102                 { 0x03, 0x0C },
3103         };
3104
3105         for (i = 0; i < ARRAY_SIZE(init_bufs); i++) {
3106                 msg.buf = init_bufs[i];
3107                 msg.len = (i != 12 ? 5 : 2);
3108                 err = i2c_transfer(&core->i2c_adap, &msg, 1);
3109                 if (err != 1) {
3110                         pr_warn("dvico_fusionhdtv_hybrid_init buf %d failed (err = %d)!\n",
3111                                 i, err);
3112                         return;
3113                 }
3114         }
3115 }
3116
3117 static int cx88_xc2028_tuner_callback(struct cx88_core *core,
3118                                       int command, int arg)
3119 {
3120         /* Board-specific callbacks */
3121         switch (core->boardnr) {
3122         case CX88_BOARD_POWERCOLOR_REAL_ANGEL:
3123         case CX88_BOARD_GENIATECH_X8000_MT:
3124         case CX88_BOARD_KWORLD_ATSC_120:
3125                 return cx88_xc3028_geniatech_tuner_callback(core,
3126                                                         command, arg);
3127         case CX88_BOARD_PROLINK_PV_8000GT:
3128         case CX88_BOARD_PROLINK_PV_GLOBAL_XTREME:
3129                 return cx88_pv_8000gt_callback(core, command, arg);
3130         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO:
3131         case CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO:
3132                 return cx88_dvico_xc2028_callback(core, command, arg);
3133         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL:
3134         case CX88_BOARD_WINFAST_DTV1800H:
3135                 return cx88_xc3028_winfast1800h_callback(core, command, arg);
3136         }
3137
3138         switch (command) {
3139         case XC2028_TUNER_RESET:
3140                 switch (INPUT(core->input).type) {
3141                 case CX88_RADIO:
3142                         dprintk(1, "setting GPIO to radio!\n");
3143                         cx_write(MO_GP0_IO, 0x4ff);
3144                         mdelay(250);
3145                         cx_write(MO_GP2_IO, 0xff);
3146                         mdelay(250);
3147                         break;
3148                 case CX88_VMUX_DVB:     /* Digital TV*/
3149                 default:                /* Analog TV */
3150                         dprintk(1, "setting GPIO to TV!\n");
3151                         break;
3152                 }
3153                 cx_write(MO_GP1_IO, 0x101010);
3154                 mdelay(250);
3155                 cx_write(MO_GP1_IO, 0x101000);
3156                 mdelay(250);
3157                 cx_write(MO_GP1_IO, 0x101010);
3158                 mdelay(250);
3159                 return 0;
3160         }
3161         return -EINVAL;
3162 }
3163
3164 static int cx88_xc4000_tuner_callback(struct cx88_core *core,
3165                                       int command, int arg)
3166 {
3167         /* Board-specific callbacks */
3168         switch (core->boardnr) {
3169         case CX88_BOARD_WINFAST_DTV1800H_XC4000:
3170         case CX88_BOARD_WINFAST_DTV2000H_PLUS:
3171         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36:
3172         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43:
3173                 return cx88_xc4000_winfast2000h_plus_callback(core,
3174                                                               command, arg);
3175         }
3176         return -EINVAL;
3177 }
3178
3179 /*
3180  * Tuner callback function. Currently only needed for the Pinnacle
3181  * PCTV HD 800i with an xc5000 sillicon tuner. This is used for both
3182  * analog tuner attach (tuner-core.c) and dvb tuner attach (cx88-dvb.c)
3183  */
3184 static int cx88_xc5000_tuner_callback(struct cx88_core *core,
3185                                       int command, int arg)
3186 {
3187         switch (core->boardnr) {
3188         case CX88_BOARD_PINNACLE_PCTV_HD_800i:
3189                 if (command == 0) { /* This is the reset command from xc5000 */
3190
3191                         /*
3192                          * djh - According to the engineer at PCTV Systems,
3193                          * the xc5000 reset pin is supposed to be on GPIO12.
3194                          * However, despite three nights of effort, pulling
3195                          * that GPIO low didn't reset the xc5000.  While
3196                          * pulling MO_SRST_IO low does reset the xc5000, this
3197                          * also resets in the s5h1409 being reset as well.
3198                          * This causes tuning to always fail since the internal
3199                          * state of the s5h1409 does not match the driver's
3200                          * state.  Given that the only two conditions in which
3201                          * the driver performs a reset is during firmware load
3202                          * and powering down the chip, I am taking out the
3203                          * reset.  We know that the chip is being reset
3204                          * when the cx88 comes online, and not being able to
3205                          * do power management for this board is worse than
3206                          * not having any tuning at all.
3207                          */
3208                         return 0;
3209                 }
3210
3211                 dprintk(1, "xc5000: unknown tuner callback command.\n");
3212                 return -EINVAL;
3213         case CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD:
3214                 if (command == 0) { /* This is the reset command from xc5000 */
3215                         cx_clear(MO_GP0_IO, 0x00000010);
3216                         usleep_range(10000, 20000);
3217                         cx_set(MO_GP0_IO, 0x00000010);
3218                         return 0;
3219                 }
3220
3221                 dprintk(1, "xc5000: unknown tuner callback command.\n");
3222                 return -EINVAL;
3223         }
3224         return 0; /* Should never be here */
3225 }
3226
3227 int cx88_tuner_callback(void *priv, int component, int command, int arg)
3228 {
3229         struct i2c_algo_bit_data *i2c_algo = priv;
3230         struct cx88_core *core;
3231
3232         if (!i2c_algo) {
3233                 pr_err("Error - i2c private data undefined.\n");
3234                 return -EINVAL;
3235         }
3236
3237         core = i2c_algo->data;
3238
3239         if (!core) {
3240                 pr_err("Error - device struct undefined.\n");
3241                 return -EINVAL;
3242         }
3243
3244         if (component != DVB_FRONTEND_COMPONENT_TUNER)
3245                 return -EINVAL;
3246
3247         switch (core->board.tuner_type) {
3248         case TUNER_XC2028:
3249                 dprintk(1, "Calling XC2028/3028 callback\n");
3250                 return cx88_xc2028_tuner_callback(core, command, arg);
3251         case TUNER_XC4000:
3252                 dprintk(1, "Calling XC4000 callback\n");
3253                 return cx88_xc4000_tuner_callback(core, command, arg);
3254         case TUNER_XC5000:
3255                 dprintk(1, "Calling XC5000 callback\n");
3256                 return cx88_xc5000_tuner_callback(core, command, arg);
3257         }
3258         pr_err("Error: Calling callback for tuner %d\n",
3259                core->board.tuner_type);
3260         return -EINVAL;
3261 }
3262 EXPORT_SYMBOL(cx88_tuner_callback);
3263
3264 /* ----------------------------------------------------------------------- */
3265
3266 static void cx88_card_list(struct cx88_core *core, struct pci_dev *pci)
3267 {
3268         int i;
3269
3270         if (!pci->subsystem_vendor && !pci->subsystem_device) {
3271                 pr_err("Your board has no valid PCI Subsystem ID and thus can't\n");
3272                 pr_err("be autodetected.  Please pass card=<n> insmod option to\n");
3273                 pr_err("workaround that.  Redirect complaints to the vendor of\n");
3274                 pr_err("the TV card\n");
3275         } else {
3276                 pr_err("Your board isn't known (yet) to the driver.  You can\n");
3277                 pr_err("try to pick one of the existing card configs via\n");
3278                 pr_err("card=<n> insmod option.  Updating to the latest\n");
3279                 pr_err("version might help as well.\n");
3280         }
3281         pr_err("Here is a list of valid choices for the card=<n> insmod option:\n");
3282         for (i = 0; i < ARRAY_SIZE(cx88_boards); i++)
3283                 pr_err("    card=%d -> %s\n", i, cx88_boards[i].name);
3284 }
3285
3286 static void cx88_card_setup_pre_i2c(struct cx88_core *core)
3287 {
3288         switch (core->boardnr) {
3289         case CX88_BOARD_HAUPPAUGE_HVR1300:
3290                 /*
3291                  * Bring the 702 demod up before i2c scanning/attach or
3292                  * devices are hidden.
3293                  *
3294                  * We leave here with the 702 on the bus
3295                  *
3296                  * "reset the IR receiver on GPIO[3]"
3297                  * Reported by Mike Crash <mike AT mikecrash.com>
3298                  */
3299                 cx_write(MO_GP0_IO, 0x0000ef88);
3300                 udelay(1000);
3301                 cx_clear(MO_GP0_IO, 0x00000088);
3302                 udelay(50);
3303                 cx_set(MO_GP0_IO, 0x00000088); /* 702 out of reset */
3304                 udelay(1000);
3305                 break;
3306
3307         case CX88_BOARD_PROLINK_PV_GLOBAL_XTREME:
3308         case CX88_BOARD_PROLINK_PV_8000GT:
3309                 cx_write(MO_GP2_IO, 0xcf7);
3310                 mdelay(50);
3311                 cx_write(MO_GP2_IO, 0xef5);
3312                 mdelay(50);
3313                 cx_write(MO_GP2_IO, 0xcf7);
3314                 usleep_range(10000, 20000);
3315                 break;
3316
3317         case CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD:
3318                 /* Enable the xc5000 tuner */
3319                 cx_set(MO_GP0_IO, 0x00001010);
3320                 break;
3321
3322         case CX88_BOARD_WINFAST_DTV2000H_J:
3323         case CX88_BOARD_HAUPPAUGE_HVR3000:
3324         case CX88_BOARD_HAUPPAUGE_HVR4000:
3325                 /* Init GPIO */
3326                 cx_write(MO_GP0_IO, core->board.input[0].gpio0);
3327                 udelay(1000);
3328                 cx_clear(MO_GP0_IO, 0x00000080);
3329                 udelay(50);
3330                 cx_set(MO_GP0_IO, 0x00000080); /* 702 out of reset */
3331                 udelay(1000);
3332                 break;
3333
3334         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL:
3335         case CX88_BOARD_WINFAST_DTV1800H:
3336                 cx88_xc3028_winfast1800h_callback(core, XC2028_TUNER_RESET, 0);
3337                 break;
3338
3339         case CX88_BOARD_WINFAST_DTV1800H_XC4000:
3340         case CX88_BOARD_WINFAST_DTV2000H_PLUS:
3341         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36:
3342         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43:
3343                 cx88_xc4000_winfast2000h_plus_callback(core,
3344                                                        XC4000_TUNER_RESET, 0);
3345                 break;
3346
3347         case CX88_BOARD_TWINHAN_VP1027_DVBS:
3348                 cx_write(MO_GP0_IO, 0x00003230);
3349                 cx_write(MO_GP0_IO, 0x00003210);
3350                 usleep_range(10000, 20000);
3351                 cx_write(MO_GP0_IO, 0x00001230);
3352                 break;
3353         }
3354 }
3355
3356 /*
3357  * Sets board-dependent xc3028 configuration
3358  */
3359 void cx88_setup_xc3028(struct cx88_core *core, struct xc2028_ctrl *ctl)
3360 {
3361         memset(ctl, 0, sizeof(*ctl));
3362
3363         ctl->fname   = "/*(DEBLOBBED)*/";
3364         ctl->max_len = 64;
3365
3366         switch (core->boardnr) {
3367         case CX88_BOARD_POWERCOLOR_REAL_ANGEL:
3368                 /* Now works with firmware version 2.7 */
3369                 if (core->i2c_algo.udelay < 16)
3370                         core->i2c_algo.udelay = 16;
3371                 break;
3372         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO:
3373         case CX88_BOARD_WINFAST_DTV1800H:
3374                 ctl->demod = XC3028_FE_ZARLINK456;
3375                 break;
3376         case CX88_BOARD_KWORLD_ATSC_120:
3377         case CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO:
3378                 ctl->demod = XC3028_FE_OREN538;
3379                 break;
3380         case CX88_BOARD_GENIATECH_X8000_MT:
3381                 /*
3382                  * FIXME: For this board, the xc3028 never recovers after being
3383                  * powered down (the reset GPIO probably is not set properly).
3384                  * We don't have access to the hardware so we cannot determine
3385                  * which GPIO is used for xc3028, so just disable power xc3028
3386                  * power management for now
3387                  */
3388                 ctl->disable_power_mgmt = 1;
3389                 break;
3390         case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL:
3391         case CX88_BOARD_PROLINK_PV_GLOBAL_XTREME:
3392         case CX88_BOARD_PROLINK_PV_8000GT:
3393                 /*
3394                  * Those boards uses non-MTS firmware
3395                  */
3396                 break;
3397         case CX88_BOARD_PINNACLE_HYBRID_PCTV:
3398         case CX88_BOARD_TERRATEC_CINERGY_HT_PCI_MKII:
3399                 ctl->demod = XC3028_FE_ZARLINK456;
3400                 ctl->mts = 1;
3401                 break;
3402         default:
3403                 ctl->demod = XC3028_FE_OREN538;
3404                 ctl->mts = 1;
3405         }
3406 }
3407 EXPORT_SYMBOL_GPL(cx88_setup_xc3028);
3408
3409 static void cx88_card_setup(struct cx88_core *core)
3410 {
3411         static u8 eeprom[256];
3412         struct tuner_setup tun_setup;
3413         unsigned int mode_mask = T_RADIO | T_ANALOG_TV;
3414
3415         memset(&tun_setup, 0, sizeof(tun_setup));
3416
3417         if (!core->i2c_rc) {
3418                 core->i2c_client.addr = 0xa0 >> 1;
3419                 tveeprom_read(&core->i2c_client, eeprom, sizeof(eeprom));
3420         }
3421
3422         switch (core->boardnr) {
3423         case CX88_BOARD_HAUPPAUGE:
3424         case CX88_BOARD_HAUPPAUGE_ROSLYN:
3425                 if (!core->i2c_rc)
3426                         hauppauge_eeprom(core, eeprom + 8);
3427                 break;
3428         case CX88_BOARD_GDI:
3429                 if (!core->i2c_rc)
3430                         gdi_eeprom(core, eeprom);
3431                 break;
3432         case CX88_BOARD_LEADTEK_PVR2000:
3433         case CX88_BOARD_WINFAST_DV2000:
3434         case CX88_BOARD_WINFAST2000XP_EXPERT:
3435                 if (!core->i2c_rc)
3436                         leadtek_eeprom(core, eeprom);
3437                 break;
3438         case CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1:
3439         case CX88_BOARD_HAUPPAUGE_NOVASE2_S1:
3440         case CX88_BOARD_HAUPPAUGE_DVB_T1:
3441         case CX88_BOARD_HAUPPAUGE_HVR1100:
3442         case CX88_BOARD_HAUPPAUGE_HVR1100LP:
3443         case CX88_BOARD_HAUPPAUGE_HVR3000:
3444         case CX88_BOARD_HAUPPAUGE_HVR1300:
3445         case CX88_BOARD_HAUPPAUGE_HVR4000:
3446         case CX88_BOARD_HAUPPAUGE_HVR4000LITE:
3447         case CX88_BOARD_HAUPPAUGE_IRONLY:
3448                 if (!core->i2c_rc)
3449                         hauppauge_eeprom(core, eeprom);
3450                 break;
3451         case CX88_BOARD_KWORLD_DVBS_100:
3452                 cx_write(MO_GP0_IO, 0x000007f8);
3453                 cx_write(MO_GP1_IO, 0x00000001);
3454                 break;
3455         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO:
3456                 /* GPIO0:0 is hooked to demod reset */
3457                 /* GPIO0:4 is hooked to xc3028 reset */
3458                 cx_write(MO_GP0_IO, 0x00111100);
3459                 usleep_range(10000, 20000);
3460                 cx_write(MO_GP0_IO, 0x00111111);
3461                 break;
3462         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL:
3463                 /* GPIO0:6 is hooked to FX2 reset pin */
3464                 cx_set(MO_GP0_IO, 0x00004040);
3465                 cx_clear(MO_GP0_IO, 0x00000040);
3466                 msleep(1000);
3467                 cx_set(MO_GP0_IO, 0x00004040);
3468                 /* FALLTHROUGH */
3469         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T1:
3470         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS:
3471         case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID:
3472                 /* GPIO0:0 is hooked to mt352 reset pin */
3473                 cx_set(MO_GP0_IO, 0x00000101);
3474                 cx_clear(MO_GP0_IO, 0x00000001);
3475                 usleep_range(10000, 20000);
3476                 cx_set(MO_GP0_IO, 0x00000101);
3477                 if (!core->i2c_rc &&
3478                     core->boardnr == CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID)
3479                         dvico_fusionhdtv_hybrid_init(core);
3480                 break;
3481         case CX88_BOARD_KWORLD_DVB_T:
3482         case CX88_BOARD_DNTV_LIVE_DVB_T:
3483                 cx_set(MO_GP0_IO, 0x00000707);
3484                 cx_set(MO_GP2_IO, 0x00000101);
3485                 cx_clear(MO_GP2_IO, 0x00000001);
3486                 usleep_range(10000, 20000);
3487                 cx_clear(MO_GP0_IO, 0x00000007);
3488                 cx_set(MO_GP2_IO, 0x00000101);
3489                 break;
3490         case CX88_BOARD_DNTV_LIVE_DVB_T_PRO:
3491                 cx_write(MO_GP0_IO, 0x00080808);
3492                 break;
3493         case CX88_BOARD_ATI_HDTVWONDER:
3494                 if (!core->i2c_rc) {
3495                         /* enable tuner */
3496                         int i;
3497                         static const u8 buffer[][2] = {
3498                                 {0x10, 0x12},
3499                                 {0x13, 0x04},
3500                                 {0x16, 0x00},
3501                                 {0x14, 0x04},
3502                                 {0x17, 0x00}
3503                         };
3504                         core->i2c_client.addr = 0x0a;
3505
3506                         for (i = 0; i < ARRAY_SIZE(buffer); i++)
3507                                 if (i2c_master_send(&core->i2c_client,
3508                                                     buffer[i], 2) != 2)
3509                                         pr_warn("Unable to enable tuner(%i).\n",
3510                                                 i);
3511                 }
3512                 break;
3513         case CX88_BOARD_MSI_TVANYWHERE_MASTER:
3514         {
3515                 struct v4l2_priv_tun_config tea5767_cfg;
3516                 struct tea5767_ctrl ctl;
3517
3518                 memset(&ctl, 0, sizeof(ctl));
3519
3520                 ctl.high_cut  = 1;
3521                 ctl.st_noise  = 1;
3522                 ctl.deemph_75 = 1;
3523                 ctl.xtal_freq = TEA5767_HIGH_LO_13MHz;
3524
3525                 tea5767_cfg.tuner = TUNER_TEA5767;
3526                 tea5767_cfg.priv  = &ctl;
3527
3528                 call_all(core, tuner, s_config, &tea5767_cfg);
3529                 break;
3530         }
3531         case  CX88_BOARD_TEVII_S420:
3532         case  CX88_BOARD_TEVII_S460:
3533         case  CX88_BOARD_TEVII_S464:
3534         case  CX88_BOARD_OMICOM_SS4_PCI:
3535         case  CX88_BOARD_TBS_8910:
3536         case  CX88_BOARD_TBS_8920:
3537         case  CX88_BOARD_PROF_6200:
3538         case  CX88_BOARD_PROF_7300:
3539         case  CX88_BOARD_PROF_7301:
3540         case  CX88_BOARD_SATTRADE_ST4200:
3541                 cx_write(MO_GP0_IO, 0x8000);
3542                 msleep(100);
3543                 cx_write(MO_SRST_IO, 0);
3544                 usleep_range(10000, 20000);
3545                 cx_write(MO_GP0_IO, 0x8080);
3546                 msleep(100);
3547                 cx_write(MO_SRST_IO, 1);
3548                 msleep(100);
3549                 break;
3550         } /*end switch() */
3551
3552         /* Setup tuners */
3553         if (core->board.radio_type != UNSET) {
3554                 tun_setup.mode_mask      = T_RADIO;
3555                 tun_setup.type           = core->board.radio_type;
3556                 tun_setup.addr           = core->board.radio_addr;
3557                 tun_setup.tuner_callback = cx88_tuner_callback;
3558                 call_all(core, tuner, s_type_addr, &tun_setup);
3559                 mode_mask &= ~T_RADIO;
3560         }
3561
3562         if (core->board.tuner_type != UNSET) {
3563                 tun_setup.mode_mask      = mode_mask;
3564                 tun_setup.type           = core->board.tuner_type;
3565                 tun_setup.addr           = core->board.tuner_addr;
3566                 tun_setup.tuner_callback = cx88_tuner_callback;
3567
3568                 call_all(core, tuner, s_type_addr, &tun_setup);
3569         }
3570
3571         if (core->board.tda9887_conf) {
3572                 struct v4l2_priv_tun_config tda9887_cfg;
3573
3574                 tda9887_cfg.tuner = TUNER_TDA9887;
3575                 tda9887_cfg.priv  = &core->board.tda9887_conf;
3576
3577                 call_all(core, tuner, s_config, &tda9887_cfg);
3578         }
3579
3580         if (core->board.tuner_type == TUNER_XC2028) {
3581                 struct v4l2_priv_tun_config  xc2028_cfg;
3582                 struct xc2028_ctrl           ctl;
3583
3584                 /* Fills device-dependent initialization parameters */
3585                 cx88_setup_xc3028(core, &ctl);
3586
3587                 /* Sends parameters to xc2028/3028 tuner */
3588                 memset(&xc2028_cfg, 0, sizeof(xc2028_cfg));
3589                 xc2028_cfg.tuner = TUNER_XC2028;
3590                 xc2028_cfg.priv  = &ctl;
3591                 dprintk(1, "Asking xc2028/3028 to load firmware %s\n",
3592                         ctl.fname);
3593                 call_all(core, tuner, s_config, &xc2028_cfg);
3594         }
3595         call_all(core, core, s_power, 0);
3596 }
3597
3598 /* ------------------------------------------------------------------ */
3599
3600 static int cx88_pci_quirks(const char *name, struct pci_dev *pci)
3601 {
3602         unsigned int lat = UNSET;
3603         u8 ctrl = 0;
3604         u8 value;
3605
3606         /* check pci quirks */
3607         if (pci_pci_problems & PCIPCI_TRITON) {
3608                 pr_info("quirk: PCIPCI_TRITON -- set TBFX\n");
3609                 ctrl |= CX88X_EN_TBFX;
3610         }
3611         if (pci_pci_problems & PCIPCI_NATOMA) {
3612                 pr_info("quirk: PCIPCI_NATOMA -- set TBFX\n");
3613                 ctrl |= CX88X_EN_TBFX;
3614         }
3615         if (pci_pci_problems & PCIPCI_VIAETBF) {
3616                 pr_info("quirk: PCIPCI_VIAETBF -- set TBFX\n");
3617                 ctrl |= CX88X_EN_TBFX;
3618         }
3619         if (pci_pci_problems & PCIPCI_VSFX) {
3620                 pr_info("quirk: PCIPCI_VSFX -- set VSFX\n");
3621                 ctrl |= CX88X_EN_VSFX;
3622         }
3623 #ifdef PCIPCI_ALIMAGIK
3624         if (pci_pci_problems & PCIPCI_ALIMAGIK) {
3625                 pr_info("quirk: PCIPCI_ALIMAGIK -- latency fixup\n");
3626                 lat = 0x0A;
3627         }
3628 #endif
3629
3630         /* check insmod options */
3631         if (latency != UNSET)
3632                 lat = latency;
3633
3634         /* apply stuff */
3635         if (ctrl) {
3636                 pci_read_config_byte(pci, CX88X_DEVCTRL, &value);
3637                 value |= ctrl;
3638                 pci_write_config_byte(pci, CX88X_DEVCTRL, value);
3639         }
3640         if (lat != UNSET) {
3641                 pr_info("setting pci latency timer to %d\n", latency);
3642                 pci_write_config_byte(pci, PCI_LATENCY_TIMER, latency);
3643         }
3644         return 0;
3645 }
3646
3647 int cx88_get_resources(const struct cx88_core *core, struct pci_dev *pci)
3648 {
3649         if (request_mem_region(pci_resource_start(pci, 0),
3650                                pci_resource_len(pci, 0),
3651                                core->name))
3652                 return 0;
3653         pr_err("func %d: Can't get MMIO memory @ 0x%llx, subsystem: %04x:%04x\n",
3654                PCI_FUNC(pci->devfn),
3655                (unsigned long long)pci_resource_start(pci, 0),
3656                pci->subsystem_vendor, pci->subsystem_device);
3657         return -EBUSY;
3658 }
3659
3660 /*
3661  * Allocate and initialize the cx88 core struct.  One should hold the
3662  * devlist mutex before calling this.
3663  */
3664 struct cx88_core *cx88_core_create(struct pci_dev *pci, int nr)
3665 {
3666         struct cx88_core *core;
3667         int i;
3668
3669         core = kzalloc(sizeof(*core), GFP_KERNEL);
3670         if (!core)
3671                 return NULL;
3672
3673         refcount_set(&core->refcount, 1);
3674         core->pci_bus  = pci->bus->number;
3675         core->pci_slot = PCI_SLOT(pci->devfn);
3676         core->pci_irqmask = PCI_INT_RISC_RD_BERRINT | PCI_INT_RISC_WR_BERRINT |
3677                             PCI_INT_BRDG_BERRINT | PCI_INT_SRC_DMA_BERRINT |
3678                             PCI_INT_DST_DMA_BERRINT | PCI_INT_IPB_DMA_BERRINT;
3679         mutex_init(&core->lock);
3680
3681         core->nr = nr;
3682         sprintf(core->name, "cx88[%d]", core->nr);
3683
3684         /*
3685          * Note: Setting initial standard here would cause first call to
3686          * cx88_set_tvnorm() to return without programming any registers.  Leave
3687          * it blank for at this point and it will get set later in
3688          * cx8800_initdev()
3689          */
3690         core->tvnorm  = 0;
3691
3692         core->width   = 320;
3693         core->height  = 240;
3694         core->field   = V4L2_FIELD_INTERLACED;
3695
3696         strcpy(core->v4l2_dev.name, core->name);
3697         if (v4l2_device_register(NULL, &core->v4l2_dev)) {
3698                 kfree(core);
3699                 return NULL;
3700         }
3701
3702         if (v4l2_ctrl_handler_init(&core->video_hdl, 13)) {
3703                 v4l2_device_unregister(&core->v4l2_dev);
3704                 kfree(core);
3705                 return NULL;
3706         }
3707
3708         if (v4l2_ctrl_handler_init(&core->audio_hdl, 13)) {
3709                 v4l2_ctrl_handler_free(&core->video_hdl);
3710                 v4l2_device_unregister(&core->v4l2_dev);
3711                 kfree(core);
3712                 return NULL;
3713         }
3714
3715         if (cx88_get_resources(core, pci) != 0) {
3716                 v4l2_ctrl_handler_free(&core->video_hdl);
3717                 v4l2_ctrl_handler_free(&core->audio_hdl);
3718                 v4l2_device_unregister(&core->v4l2_dev);
3719                 kfree(core);
3720                 return NULL;
3721         }
3722
3723         /* PCI stuff */
3724         cx88_pci_quirks(core->name, pci);
3725         core->lmmio = ioremap(pci_resource_start(pci, 0),
3726                               pci_resource_len(pci, 0));
3727         core->bmmio = (u8 __iomem *)core->lmmio;
3728
3729         if (!core->lmmio) {
3730                 release_mem_region(pci_resource_start(pci, 0),
3731                                    pci_resource_len(pci, 0));
3732                 v4l2_ctrl_handler_free(&core->video_hdl);
3733                 v4l2_ctrl_handler_free(&core->audio_hdl);
3734                 v4l2_device_unregister(&core->v4l2_dev);
3735                 kfree(core);
3736                 return NULL;
3737         }
3738
3739         /* board config */
3740         core->boardnr = UNSET;
3741         if (card[core->nr] < ARRAY_SIZE(cx88_boards))
3742                 core->boardnr = card[core->nr];
3743         for (i = 0; core->boardnr == UNSET && i < ARRAY_SIZE(cx88_subids); i++)
3744                 if (pci->subsystem_vendor == cx88_subids[i].subvendor &&
3745                     pci->subsystem_device == cx88_subids[i].subdevice)
3746                         core->boardnr = cx88_subids[i].card;
3747         if (core->boardnr == UNSET) {
3748                 core->boardnr = CX88_BOARD_UNKNOWN;
3749                 cx88_card_list(core, pci);
3750         }
3751
3752         core->board = cx88_boards[core->boardnr];
3753
3754         if (!core->board.num_frontends && (core->board.mpeg & CX88_MPEG_DVB))
3755                 core->board.num_frontends = 1;
3756
3757         pr_info("subsystem: %04x:%04x, board: %s [card=%d,%s], frontend(s): %d\n",
3758                 pci->subsystem_vendor, pci->subsystem_device, core->board.name,
3759                 core->boardnr, card[core->nr] == core->boardnr ?
3760                 "insmod option" : "autodetected",
3761                 core->board.num_frontends);
3762
3763         if (tuner[core->nr] != UNSET)
3764                 core->board.tuner_type = tuner[core->nr];
3765         if (radio[core->nr] != UNSET)
3766                 core->board.radio_type = radio[core->nr];
3767
3768         dprintk(1, "TV tuner type %d, Radio tuner type %d\n",
3769                 core->board.tuner_type, core->board.radio_type);
3770
3771         /* init hardware */
3772         cx88_reset(core);
3773         cx88_card_setup_pre_i2c(core);
3774         cx88_i2c_init(core, pci);
3775
3776         /* load tuner module, if needed */
3777         if (core->board.tuner_type != UNSET) {
3778                 /*
3779                  * Ignore 0x6b and 0x6f on cx88 boards.
3780                  * FusionHDTV5 RT Gold has an ir receiver at 0x6b
3781                  * and an RTC at 0x6f which can get corrupted if probed.
3782                  */
3783                 static const unsigned short tv_addrs[] = {
3784                         0x42, 0x43, 0x4a, 0x4b,         /* tda8290 */
3785                         0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
3786                         0x68, 0x69, 0x6a, 0x6c, 0x6d, 0x6e,
3787                         I2C_CLIENT_END
3788                 };
3789                 int has_demod = (core->board.tda9887_conf & TDA9887_PRESENT);
3790
3791                 /*
3792                  * I don't trust the radio_type as is stored in the card
3793                  * definitions, so we just probe for it.
3794                  * The radio_type is sometimes missing, or set to UNSET but
3795                  * later code configures a tea5767.
3796                  */
3797                 v4l2_i2c_new_subdev(&core->v4l2_dev, &core->i2c_adap,
3798                                     "tuner", 0,
3799                                     v4l2_i2c_tuner_addrs(ADDRS_RADIO));
3800                 if (has_demod)
3801                         v4l2_i2c_new_subdev(&core->v4l2_dev,
3802                                             &core->i2c_adap, "tuner",
3803                                 0, v4l2_i2c_tuner_addrs(ADDRS_DEMOD));
3804                 if (core->board.tuner_addr == ADDR_UNSET) {
3805                         v4l2_i2c_new_subdev(&core->v4l2_dev,
3806                                             &core->i2c_adap, "tuner",
3807                                 0, has_demod ? tv_addrs + 4 : tv_addrs);
3808                 } else {
3809                         v4l2_i2c_new_subdev(&core->v4l2_dev, &core->i2c_adap,
3810                                             "tuner", core->board.tuner_addr,
3811                                             NULL);
3812                 }
3813         }
3814
3815         cx88_card_setup(core);
3816         if (!disable_ir) {
3817                 cx88_i2c_init_ir(core);
3818                 cx88_ir_init(core, pci);
3819         }
3820
3821         return core;
3822 }