Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*
0003  * device driver for Conexant 2388x based TV cards
0004  * card-specific stuff.
0005  *
0006  * (c) 2003 Gerd Knorr <kraxel@bytesex.org> [SuSE Labs]
0007  */
0008 
0009 #include "cx88.h"
0010 #include "tea5767.h"
0011 #include "xc4000.h"
0012 
0013 #include <linux/init.h>
0014 #include <linux/module.h>
0015 #include <linux/pci.h>
0016 #include <linux/delay.h>
0017 #include <linux/slab.h>
0018 
0019 static unsigned int tuner[] = {[0 ... (CX88_MAXBOARDS - 1)] = UNSET };
0020 static unsigned int radio[] = {[0 ... (CX88_MAXBOARDS - 1)] = UNSET };
0021 static unsigned int card[]  = {[0 ... (CX88_MAXBOARDS - 1)] = UNSET };
0022 
0023 module_param_array(tuner, int, NULL, 0444);
0024 module_param_array(radio, int, NULL, 0444);
0025 module_param_array(card,  int, NULL, 0444);
0026 
0027 MODULE_PARM_DESC(tuner, "tuner type");
0028 MODULE_PARM_DESC(radio, "radio tuner type");
0029 MODULE_PARM_DESC(card, "card type");
0030 
0031 static unsigned int latency = UNSET;
0032 module_param(latency, int, 0444);
0033 MODULE_PARM_DESC(latency, "pci latency timer");
0034 
0035 static int disable_ir;
0036 module_param(disable_ir, int, 0444);
0037 MODULE_PARM_DESC(disable_ir, "Disable IR support");
0038 
0039 #define dprintk(level, fmt, arg...) do {                \
0040     if (cx88_core_debug >= level)                   \
0041         printk(KERN_DEBUG pr_fmt("%s: core:" fmt),      \
0042             __func__, ##arg);               \
0043 } while (0)
0044 
0045 /* ------------------------------------------------------------------ */
0046 /* board config info                                                  */
0047 
0048 /* If radio_type !=UNSET, radio_addr should be specified
0049  */
0050 
0051 static const struct cx88_board cx88_boards[] = {
0052     [CX88_BOARD_UNKNOWN] = {
0053         .name       = "UNKNOWN/GENERIC",
0054         .tuner_type     = UNSET,
0055         .radio_type     = UNSET,
0056         .tuner_addr = ADDR_UNSET,
0057         .radio_addr = ADDR_UNSET,
0058         .input          = { {
0059             .type   = CX88_VMUX_COMPOSITE1,
0060             .vmux   = 0,
0061         }, {
0062             .type   = CX88_VMUX_COMPOSITE2,
0063             .vmux   = 1,
0064         }, {
0065             .type   = CX88_VMUX_COMPOSITE3,
0066             .vmux   = 2,
0067         }, {
0068             .type   = CX88_VMUX_COMPOSITE4,
0069             .vmux   = 3,
0070         } },
0071     },
0072     [CX88_BOARD_HAUPPAUGE] = {
0073         .name       = "Hauppauge WinTV 34xxx models",
0074         .tuner_type     = UNSET,
0075         .radio_type     = UNSET,
0076         .tuner_addr = ADDR_UNSET,
0077         .radio_addr = ADDR_UNSET,
0078         .tda9887_conf   = TDA9887_PRESENT,
0079         .input          = { {
0080             .type   = CX88_VMUX_TELEVISION,
0081             .vmux   = 0,
0082             .gpio0  = 0xff00,  // internal decoder
0083         }, {
0084             .type   = CX88_VMUX_DEBUG,
0085             .vmux   = 0,
0086             .gpio0  = 0xff01,  // mono from tuner chip
0087         }, {
0088             .type   = CX88_VMUX_COMPOSITE1,
0089             .vmux   = 1,
0090             .gpio0  = 0xff02,
0091         }, {
0092             .type   = CX88_VMUX_SVIDEO,
0093             .vmux   = 2,
0094             .gpio0  = 0xff02,
0095         } },
0096         .radio = {
0097             .type   = CX88_RADIO,
0098             .gpio0  = 0xff01,
0099         },
0100     },
0101     [CX88_BOARD_GDI] = {
0102         .name       = "GDI Black Gold",
0103         .tuner_type     = UNSET,
0104         .radio_type     = UNSET,
0105         .tuner_addr = ADDR_UNSET,
0106         .radio_addr = ADDR_UNSET,
0107         .input          = { {
0108             .type   = CX88_VMUX_TELEVISION,
0109             .vmux   = 0,
0110         }, {
0111             .type   = CX88_VMUX_SVIDEO,
0112             .vmux   = 2,
0113         } },
0114     },
0115     [CX88_BOARD_PIXELVIEW] = {
0116         .name           = "PixelView",
0117         .tuner_type     = TUNER_PHILIPS_PAL,
0118         .radio_type     = UNSET,
0119         .tuner_addr = ADDR_UNSET,
0120         .radio_addr = ADDR_UNSET,
0121         .input          = { {
0122             .type   = CX88_VMUX_TELEVISION,
0123             .vmux   = 0,
0124             .gpio0  = 0xff00,  // internal decoder
0125         }, {
0126             .type   = CX88_VMUX_COMPOSITE1,
0127             .vmux   = 1,
0128         }, {
0129             .type   = CX88_VMUX_SVIDEO,
0130             .vmux   = 2,
0131         } },
0132         .radio = {
0133              .type  = CX88_RADIO,
0134              .gpio0 = 0xff10,
0135         },
0136     },
0137     [CX88_BOARD_ATI_WONDER_PRO] = {
0138         .name           = "ATI TV Wonder Pro",
0139         .tuner_type     = TUNER_PHILIPS_4IN1,
0140         .radio_type     = UNSET,
0141         .tuner_addr = ADDR_UNSET,
0142         .radio_addr = ADDR_UNSET,
0143         .tda9887_conf   = TDA9887_PRESENT | TDA9887_INTERCARRIER,
0144         .input          = { {
0145             .type   = CX88_VMUX_TELEVISION,
0146             .vmux   = 0,
0147             .gpio0  = 0x03ff,
0148         }, {
0149             .type   = CX88_VMUX_COMPOSITE1,
0150             .vmux   = 1,
0151             .gpio0  = 0x03fe,
0152         }, {
0153             .type   = CX88_VMUX_SVIDEO,
0154             .vmux   = 2,
0155             .gpio0  = 0x03fe,
0156         } },
0157     },
0158     [CX88_BOARD_WINFAST2000XP_EXPERT] = {
0159         .name           = "Leadtek Winfast 2000XP Expert",
0160         .tuner_type     = TUNER_PHILIPS_4IN1,
0161         .radio_type     = UNSET,
0162         .tuner_addr = ADDR_UNSET,
0163         .radio_addr = ADDR_UNSET,
0164         .tda9887_conf   = TDA9887_PRESENT,
0165         .input          = { {
0166             .type   = CX88_VMUX_TELEVISION,
0167             .vmux   = 0,
0168             .gpio0  = 0x00F5e700,
0169             .gpio1  = 0x00003004,
0170             .gpio2  = 0x00F5e700,
0171             .gpio3  = 0x02000000,
0172         }, {
0173             .type   = CX88_VMUX_COMPOSITE1,
0174             .vmux   = 1,
0175             .gpio0  = 0x00F5c700,
0176             .gpio1  = 0x00003004,
0177             .gpio2  = 0x00F5c700,
0178             .gpio3  = 0x02000000,
0179         }, {
0180             .type   = CX88_VMUX_SVIDEO,
0181             .vmux   = 2,
0182             .gpio0  = 0x00F5c700,
0183             .gpio1  = 0x00003004,
0184             .gpio2  = 0x00F5c700,
0185             .gpio3  = 0x02000000,
0186         } },
0187         .radio = {
0188             .type   = CX88_RADIO,
0189             .gpio0  = 0x00F5d700,
0190             .gpio1  = 0x00003004,
0191             .gpio2  = 0x00F5d700,
0192             .gpio3  = 0x02000000,
0193         },
0194     },
0195     [CX88_BOARD_AVERTV_STUDIO_303] = {
0196         .name           = "AverTV Studio 303 (M126)",
0197         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
0198         .radio_type     = UNSET,
0199         .tuner_addr = ADDR_UNSET,
0200         .radio_addr = ADDR_UNSET,
0201         .tda9887_conf   = TDA9887_PRESENT,
0202         .input          = { {
0203             .type   = CX88_VMUX_TELEVISION,
0204             .vmux   = 0,
0205             .gpio1  = 0xe09f,
0206         }, {
0207             .type   = CX88_VMUX_COMPOSITE1,
0208             .vmux   = 1,
0209             .gpio1  = 0xe05f,
0210         }, {
0211             .type   = CX88_VMUX_SVIDEO,
0212             .vmux   = 2,
0213             .gpio1  = 0xe05f,
0214         } },
0215         .radio = {
0216             .gpio1  = 0xe0df,
0217             .type   = CX88_RADIO,
0218         },
0219     },
0220     [CX88_BOARD_MSI_TVANYWHERE_MASTER] = {
0221         // added gpio values thanks to Michal
0222         // values for PAL from DScaler
0223         .name           = "MSI TV-@nywhere Master",
0224         .tuner_type     = TUNER_MT2032,
0225         .radio_type     = UNSET,
0226         .tuner_addr = ADDR_UNSET,
0227         .radio_addr = ADDR_UNSET,
0228         .tda9887_conf   = TDA9887_PRESENT | TDA9887_INTERCARRIER_NTSC,
0229         .input          = { {
0230             .type   = CX88_VMUX_TELEVISION,
0231             .vmux   = 0,
0232             .gpio0  = 0x000040bf,
0233             .gpio1  = 0x000080c0,
0234             .gpio2  = 0x0000ff40,
0235         }, {
0236             .type   = CX88_VMUX_COMPOSITE1,
0237             .vmux   = 1,
0238             .gpio0  = 0x000040bf,
0239             .gpio1  = 0x000080c0,
0240             .gpio2  = 0x0000ff40,
0241         }, {
0242             .type   = CX88_VMUX_SVIDEO,
0243             .vmux   = 2,
0244             .gpio0  = 0x000040bf,
0245             .gpio1  = 0x000080c0,
0246             .gpio2  = 0x0000ff40,
0247         } },
0248         .radio = {
0249              .type   = CX88_RADIO,
0250              .vmux   = 3,
0251              .gpio0  = 0x000040bf,
0252              .gpio1  = 0x000080c0,
0253              .gpio2  = 0x0000ff20,
0254         },
0255     },
0256     [CX88_BOARD_WINFAST_DV2000] = {
0257         .name           = "Leadtek Winfast DV2000",
0258         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
0259         .radio_type     = UNSET,
0260         .tuner_addr = ADDR_UNSET,
0261         .radio_addr = ADDR_UNSET,
0262         .tda9887_conf   = TDA9887_PRESENT,
0263         .input          = { {
0264             .type   = CX88_VMUX_TELEVISION,
0265             .vmux   = 0,
0266             .gpio0  = 0x0035e700,
0267             .gpio1  = 0x00003004,
0268             .gpio2  = 0x0035e700,
0269             .gpio3  = 0x02000000,
0270         }, {
0271             .type   = CX88_VMUX_COMPOSITE1,
0272             .vmux   = 1,
0273             .gpio0  = 0x0035c700,
0274             .gpio1  = 0x00003004,
0275             .gpio2  = 0x0035c700,
0276             .gpio3  = 0x02000000,
0277         }, {
0278             .type   = CX88_VMUX_SVIDEO,
0279             .vmux   = 2,
0280             .gpio0  = 0x0035c700,
0281             .gpio1  = 0x0035c700,
0282             .gpio2  = 0x02000000,
0283             .gpio3  = 0x02000000,
0284         } },
0285         .radio = {
0286             .type   = CX88_RADIO,
0287             .gpio0  = 0x0035d700,
0288             .gpio1  = 0x00007004,
0289             .gpio2  = 0x0035d700,
0290             .gpio3  = 0x02000000,
0291         },
0292     },
0293     [CX88_BOARD_LEADTEK_PVR2000] = {
0294         // gpio values for PAL version from regspy by DScaler
0295         .name           = "Leadtek PVR 2000",
0296         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
0297         .radio_type     = UNSET,
0298         .tuner_addr = ADDR_UNSET,
0299         .radio_addr = ADDR_UNSET,
0300         .tda9887_conf   = TDA9887_PRESENT,
0301         .input          = { {
0302             .type   = CX88_VMUX_TELEVISION,
0303             .vmux   = 0,
0304             .gpio0  = 0x0000bde2,
0305             .audioroute = 1,
0306         }, {
0307             .type   = CX88_VMUX_COMPOSITE1,
0308             .vmux   = 1,
0309             .gpio0  = 0x0000bde6,
0310             .audioroute = 1,
0311         }, {
0312             .type   = CX88_VMUX_SVIDEO,
0313             .vmux   = 2,
0314             .gpio0  = 0x0000bde6,
0315             .audioroute = 1,
0316         } },
0317         .radio = {
0318             .type   = CX88_RADIO,
0319             .gpio0  = 0x0000bd62,
0320             .audioroute = 1,
0321         },
0322         .mpeg           = CX88_MPEG_BLACKBIRD,
0323     },
0324     [CX88_BOARD_IODATA_GVVCP3PCI] = {
0325         .name       = "IODATA GV-VCP3/PCI",
0326         .tuner_type     = UNSET,
0327         .radio_type     = UNSET,
0328         .tuner_addr = ADDR_UNSET,
0329         .radio_addr = ADDR_UNSET,
0330         .input          = { {
0331             .type   = CX88_VMUX_COMPOSITE1,
0332             .vmux   = 0,
0333         }, {
0334             .type   = CX88_VMUX_COMPOSITE2,
0335             .vmux   = 1,
0336         }, {
0337             .type   = CX88_VMUX_SVIDEO,
0338             .vmux   = 2,
0339         } },
0340     },
0341     [CX88_BOARD_PROLINK_PLAYTVPVR] = {
0342         .name           = "Prolink PlayTV PVR",
0343         .tuner_type     = TUNER_PHILIPS_FM1236_MK3,
0344         .radio_type     = UNSET,
0345         .tuner_addr = ADDR_UNSET,
0346         .radio_addr = ADDR_UNSET,
0347         .tda9887_conf   = TDA9887_PRESENT,
0348         .input          = { {
0349             .type   = CX88_VMUX_TELEVISION,
0350             .vmux   = 0,
0351             .gpio0  = 0xbff0,
0352         }, {
0353             .type   = CX88_VMUX_COMPOSITE1,
0354             .vmux   = 1,
0355             .gpio0  = 0xbff3,
0356         }, {
0357             .type   = CX88_VMUX_SVIDEO,
0358             .vmux   = 2,
0359             .gpio0  = 0xbff3,
0360         } },
0361         .radio = {
0362             .type   = CX88_RADIO,
0363             .gpio0  = 0xbff0,
0364         },
0365     },
0366     [CX88_BOARD_ASUS_PVR_416] = {
0367         .name       = "ASUS PVR-416",
0368         .tuner_type     = TUNER_PHILIPS_FM1236_MK3,
0369         .radio_type     = UNSET,
0370         .tuner_addr = ADDR_UNSET,
0371         .radio_addr = ADDR_UNSET,
0372         .tda9887_conf   = TDA9887_PRESENT,
0373         .input          = { {
0374             .type   = CX88_VMUX_TELEVISION,
0375             .vmux   = 0,
0376             .gpio0  = 0x0000fde6,
0377         }, {
0378             .type   = CX88_VMUX_SVIDEO,
0379             .vmux   = 2,
0380             .gpio0  = 0x0000fde6, // 0x0000fda6 L,R RCA audio in?
0381             .audioroute = 1,
0382         } },
0383         .radio = {
0384             .type   = CX88_RADIO,
0385             .gpio0  = 0x0000fde2,
0386         },
0387         .mpeg           = CX88_MPEG_BLACKBIRD,
0388     },
0389     [CX88_BOARD_MSI_TVANYWHERE] = {
0390         .name           = "MSI TV-@nywhere",
0391         .tuner_type     = TUNER_MT2032,
0392         .radio_type     = UNSET,
0393         .tuner_addr = ADDR_UNSET,
0394         .radio_addr = ADDR_UNSET,
0395         .tda9887_conf   = TDA9887_PRESENT,
0396         .input          = { {
0397             .type   = CX88_VMUX_TELEVISION,
0398             .vmux   = 0,
0399             .gpio0  = 0x00000fbf,
0400             .gpio2  = 0x0000fc08,
0401         }, {
0402             .type   = CX88_VMUX_COMPOSITE1,
0403             .vmux   = 1,
0404             .gpio0  = 0x00000fbf,
0405             .gpio2  = 0x0000fc68,
0406         }, {
0407             .type   = CX88_VMUX_SVIDEO,
0408             .vmux   = 2,
0409             .gpio0  = 0x00000fbf,
0410             .gpio2  = 0x0000fc68,
0411         } },
0412     },
0413     [CX88_BOARD_KWORLD_DVB_T] = {
0414         .name           = "KWorld/VStream XPert DVB-T",
0415         .tuner_type     = UNSET,
0416         .radio_type     = UNSET,
0417         .tuner_addr = ADDR_UNSET,
0418         .radio_addr = ADDR_UNSET,
0419         .input          = { {
0420             .type   = CX88_VMUX_COMPOSITE1,
0421             .vmux   = 1,
0422             .gpio0  = 0x0700,
0423             .gpio2  = 0x0101,
0424         }, {
0425             .type   = CX88_VMUX_SVIDEO,
0426             .vmux   = 2,
0427             .gpio0  = 0x0700,
0428             .gpio2  = 0x0101,
0429         } },
0430         .mpeg           = CX88_MPEG_DVB,
0431     },
0432     [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T1] = {
0433         .name           = "DViCO FusionHDTV DVB-T1",
0434         .tuner_type     = UNSET, /* No analog tuner */
0435         .radio_type     = UNSET,
0436         .tuner_addr = ADDR_UNSET,
0437         .radio_addr = ADDR_UNSET,
0438         .input          = { {
0439             .type   = CX88_VMUX_COMPOSITE1,
0440             .vmux   = 1,
0441             .gpio0  = 0x000027df,
0442         }, {
0443             .type   = CX88_VMUX_SVIDEO,
0444             .vmux   = 2,
0445             .gpio0  = 0x000027df,
0446         } },
0447         .mpeg           = CX88_MPEG_DVB,
0448     },
0449     [CX88_BOARD_KWORLD_LTV883] = {
0450         .name           = "KWorld LTV883RF",
0451         .tuner_type     = TUNER_TNF_8831BGFF,
0452         .radio_type     = UNSET,
0453         .tuner_addr = ADDR_UNSET,
0454         .radio_addr = ADDR_UNSET,
0455         .input          = { {
0456             .type   = CX88_VMUX_TELEVISION,
0457             .vmux   = 0,
0458             .gpio0  = 0x07f8,
0459         }, {
0460             .type   = CX88_VMUX_DEBUG,
0461             .vmux   = 0,
0462             .gpio0  = 0x07f9,  // mono from tuner chip
0463         }, {
0464             .type   = CX88_VMUX_COMPOSITE1,
0465             .vmux   = 1,
0466             .gpio0  = 0x000007fa,
0467         }, {
0468             .type   = CX88_VMUX_SVIDEO,
0469             .vmux   = 2,
0470             .gpio0  = 0x000007fa,
0471         } },
0472         .radio = {
0473             .type   = CX88_RADIO,
0474             .gpio0  = 0x000007f8,
0475         },
0476     },
0477     [CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q] = {
0478         .name       = "DViCO FusionHDTV 3 Gold-Q",
0479         .tuner_type     = TUNER_MICROTUNE_4042FI5,
0480         .radio_type     = UNSET,
0481         .tuner_addr = ADDR_UNSET,
0482         .radio_addr = ADDR_UNSET,
0483         /*
0484          * GPIO[0] resets DT3302 DTV receiver
0485          *     0 - reset asserted
0486          *     1 - normal operation
0487          * GPIO[1] mutes analog audio output connector
0488          *     0 - enable selected source
0489          *     1 - mute
0490          * GPIO[2] selects source for analog audio output connector
0491          *     0 - analog audio input connector on tab
0492          *     1 - analog DAC output from CX23881 chip
0493          * GPIO[3] selects RF input connector on tuner module
0494          *     0 - RF connector labeled CABLE
0495          *     1 - RF connector labeled ANT
0496          * GPIO[4] selects high RF for QAM256 mode
0497          *     0 - normal RF
0498          *     1 - high RF
0499          */
0500         .input          = { {
0501             .type   = CX88_VMUX_TELEVISION,
0502             .vmux   = 0,
0503             .gpio0  = 0x0f0d,
0504         }, {
0505             .type   = CX88_VMUX_CABLE,
0506             .vmux   = 0,
0507             .gpio0  = 0x0f05,
0508         }, {
0509             .type   = CX88_VMUX_COMPOSITE1,
0510             .vmux   = 1,
0511             .gpio0  = 0x0f00,
0512         }, {
0513             .type   = CX88_VMUX_SVIDEO,
0514             .vmux   = 2,
0515             .gpio0  = 0x0f00,
0516         } },
0517         .mpeg           = CX88_MPEG_DVB,
0518     },
0519     [CX88_BOARD_HAUPPAUGE_DVB_T1] = {
0520         .name           = "Hauppauge Nova-T DVB-T",
0521         .tuner_type     = UNSET,
0522         .radio_type     = UNSET,
0523         .tuner_addr = ADDR_UNSET,
0524         .radio_addr = ADDR_UNSET,
0525         .input          = { {
0526             .type   = CX88_VMUX_DVB,
0527             .vmux   = 0,
0528         } },
0529         .mpeg           = CX88_MPEG_DVB,
0530     },
0531     [CX88_BOARD_CONEXANT_DVB_T1] = {
0532         .name           = "Conexant DVB-T reference design",
0533         .tuner_type     = UNSET,
0534         .radio_type     = UNSET,
0535         .tuner_addr = ADDR_UNSET,
0536         .radio_addr = ADDR_UNSET,
0537         .input          = { {
0538             .type   = CX88_VMUX_DVB,
0539             .vmux   = 0,
0540         } },
0541         .mpeg           = CX88_MPEG_DVB,
0542     },
0543     [CX88_BOARD_PROVIDEO_PV259] = {
0544         .name       = "Provideo PV259",
0545         .tuner_type     = TUNER_PHILIPS_FQ1216ME,
0546         .radio_type     = UNSET,
0547         .tuner_addr = ADDR_UNSET,
0548         .radio_addr = ADDR_UNSET,
0549         .input          = { {
0550             .type   = CX88_VMUX_TELEVISION,
0551             .vmux   = 0,
0552             .audioroute = 1,
0553         } },
0554         .mpeg           = CX88_MPEG_BLACKBIRD,
0555     },
0556     [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS] = {
0557         .name           = "DViCO FusionHDTV DVB-T Plus",
0558         .tuner_type     = UNSET, /* No analog tuner */
0559         .radio_type     = UNSET,
0560         .tuner_addr = ADDR_UNSET,
0561         .radio_addr = ADDR_UNSET,
0562         .input          = { {
0563             .type   = CX88_VMUX_COMPOSITE1,
0564             .vmux   = 1,
0565             .gpio0  = 0x000027df,
0566         }, {
0567             .type   = CX88_VMUX_SVIDEO,
0568             .vmux   = 2,
0569             .gpio0  = 0x000027df,
0570         } },
0571         .mpeg           = CX88_MPEG_DVB,
0572     },
0573     [CX88_BOARD_DNTV_LIVE_DVB_T] = {
0574         .name       = "digitalnow DNTV Live! DVB-T",
0575         .tuner_type     = UNSET,
0576         .radio_type     = UNSET,
0577         .tuner_addr = ADDR_UNSET,
0578         .radio_addr = ADDR_UNSET,
0579         .input      = { {
0580             .type   = CX88_VMUX_COMPOSITE1,
0581             .vmux   = 1,
0582             .gpio0  = 0x00000700,
0583             .gpio2  = 0x00000101,
0584         }, {
0585             .type   = CX88_VMUX_SVIDEO,
0586             .vmux   = 2,
0587             .gpio0  = 0x00000700,
0588             .gpio2  = 0x00000101,
0589         } },
0590         .mpeg           = CX88_MPEG_DVB,
0591     },
0592     [CX88_BOARD_PCHDTV_HD3000] = {
0593         .name           = "pcHDTV HD3000 HDTV",
0594         .tuner_type     = TUNER_THOMSON_DTT761X,
0595         .radio_type     = UNSET,
0596         .tuner_addr = ADDR_UNSET,
0597         .radio_addr = ADDR_UNSET,
0598         .tda9887_conf   = TDA9887_PRESENT,
0599         /* GPIO[2] = audio source for analog audio out connector
0600          *  0 = analog audio input connector
0601          *  1 = CX88 audio DACs
0602          *
0603          * GPIO[7] = input to CX88's audio/chroma ADC
0604          *  0 = FM 10.7 MHz IF
0605          *  1 = Sound 4.5 MHz IF
0606          *
0607          * GPIO[1,5,6] = Oren 51132 pins 27,35,28 respectively
0608          *
0609          * GPIO[16] = Remote control input
0610          */
0611         .input          = { {
0612             .type   = CX88_VMUX_TELEVISION,
0613             .vmux   = 0,
0614             .gpio0  = 0x00008484,
0615         }, {
0616             .type   = CX88_VMUX_COMPOSITE1,
0617             .vmux   = 1,
0618             .gpio0  = 0x00008400,
0619         }, {
0620             .type   = CX88_VMUX_SVIDEO,
0621             .vmux   = 2,
0622             .gpio0  = 0x00008400,
0623         } },
0624         .radio = {
0625             .type   = CX88_RADIO,
0626             .gpio0  = 0x00008404,
0627         },
0628         .mpeg           = CX88_MPEG_DVB,
0629     },
0630     [CX88_BOARD_HAUPPAUGE_ROSLYN] = {
0631         // entry added by Kaustubh D. Bhalerao <bhalerao.1@osu.edu>
0632         // GPIO values obtained from regspy, courtesy Sean Covel
0633         .name           = "Hauppauge WinTV 28xxx (Roslyn) models",
0634         .tuner_type     = UNSET,
0635         .radio_type     = UNSET,
0636         .tuner_addr = ADDR_UNSET,
0637         .radio_addr = ADDR_UNSET,
0638         .input          = { {
0639             .type   = CX88_VMUX_TELEVISION,
0640             .vmux   = 0,
0641             .gpio0  = 0xed1a,
0642             .gpio2  = 0x00ff,
0643         }, {
0644             .type   = CX88_VMUX_DEBUG,
0645             .vmux   = 0,
0646             .gpio0  = 0xff01,
0647         }, {
0648             .type   = CX88_VMUX_COMPOSITE1,
0649             .vmux   = 1,
0650             .gpio0  = 0xff02,
0651         }, {
0652             .type   = CX88_VMUX_SVIDEO,
0653             .vmux   = 2,
0654             .gpio0  = 0xed92,
0655             .gpio2  = 0x00ff,
0656         } },
0657         .radio = {
0658              .type   = CX88_RADIO,
0659              .gpio0  = 0xed96,
0660              .gpio2  = 0x00ff,
0661          },
0662         .mpeg           = CX88_MPEG_BLACKBIRD,
0663     },
0664     [CX88_BOARD_DIGITALLOGIC_MEC] = {
0665         .name           = "Digital-Logic MICROSPACE Entertainment Center (MEC)",
0666         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
0667         .radio_type     = UNSET,
0668         .tuner_addr = ADDR_UNSET,
0669         .radio_addr = ADDR_UNSET,
0670         .tda9887_conf   = TDA9887_PRESENT,
0671         .input          = { {
0672             .type   = CX88_VMUX_TELEVISION,
0673             .vmux   = 0,
0674             .gpio0  = 0x00009d80,
0675             .audioroute = 1,
0676         }, {
0677             .type   = CX88_VMUX_COMPOSITE1,
0678             .vmux   = 1,
0679             .gpio0  = 0x00009d76,
0680             .audioroute = 1,
0681         }, {
0682             .type   = CX88_VMUX_SVIDEO,
0683             .vmux   = 2,
0684             .gpio0  = 0x00009d76,
0685             .audioroute = 1,
0686         } },
0687         .radio = {
0688             .type   = CX88_RADIO,
0689             .gpio0  = 0x00009d00,
0690             .audioroute = 1,
0691         },
0692         .mpeg           = CX88_MPEG_BLACKBIRD,
0693     },
0694     [CX88_BOARD_IODATA_GVBCTV7E] = {
0695         .name           = "IODATA GV/BCTV7E",
0696         .tuner_type     = TUNER_PHILIPS_FQ1286,
0697         .radio_type     = UNSET,
0698         .tuner_addr = ADDR_UNSET,
0699         .radio_addr = ADDR_UNSET,
0700         .tda9887_conf   = TDA9887_PRESENT,
0701         .input          = { {
0702             .type   = CX88_VMUX_TELEVISION,
0703             .vmux   = 1,
0704             .gpio1  = 0x0000e03f,
0705         }, {
0706             .type   = CX88_VMUX_COMPOSITE1,
0707             .vmux   = 2,
0708             .gpio1  = 0x0000e07f,
0709         }, {
0710             .type   = CX88_VMUX_SVIDEO,
0711             .vmux   = 3,
0712             .gpio1  = 0x0000e07f,
0713         } }
0714     },
0715     [CX88_BOARD_PIXELVIEW_PLAYTV_ULTRA_PRO] = {
0716         .name           = "PixelView PlayTV Ultra Pro (Stereo)",
0717         /* May be also TUNER_YMEC_TVF_5533MF for NTSC/M or PAL/M */
0718         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
0719         .radio_type     = UNSET,
0720         .tuner_addr = ADDR_UNSET,
0721         .radio_addr = ADDR_UNSET,
0722         /*
0723          * Some variants use a tda9874 and so need the
0724          * tvaudio module.
0725          */
0726         .audio_chip     = CX88_AUDIO_TVAUDIO,
0727         .input          = { {
0728             .type   = CX88_VMUX_TELEVISION,
0729             .vmux   = 0,
0730             .gpio0  = 0xbf61,  /* internal decoder */
0731         }, {
0732             .type   = CX88_VMUX_COMPOSITE1,
0733             .vmux   = 1,
0734             .gpio0  = 0xbf63,
0735         }, {
0736             .type   = CX88_VMUX_SVIDEO,
0737             .vmux   = 2,
0738             .gpio0  = 0xbf63,
0739         } },
0740         .radio = {
0741              .type  = CX88_RADIO,
0742              .gpio0 = 0xbf60,
0743          },
0744     },
0745     [CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_T] = {
0746         .name           = "DViCO FusionHDTV 3 Gold-T",
0747         .tuner_type     = TUNER_THOMSON_DTT761X,
0748         .radio_type     = UNSET,
0749         .tuner_addr = ADDR_UNSET,
0750         .radio_addr = ADDR_UNSET,
0751         .tda9887_conf   = TDA9887_PRESENT,
0752         .input          = { {
0753             .type   = CX88_VMUX_TELEVISION,
0754             .vmux   = 0,
0755             .gpio0  = 0x97ed,
0756         }, {
0757             .type   = CX88_VMUX_COMPOSITE1,
0758             .vmux   = 1,
0759             .gpio0  = 0x97e9,
0760         }, {
0761             .type   = CX88_VMUX_SVIDEO,
0762             .vmux   = 2,
0763             .gpio0  = 0x97e9,
0764         } },
0765         .mpeg           = CX88_MPEG_DVB,
0766     },
0767     [CX88_BOARD_ADSTECH_DVB_T_PCI] = {
0768         .name           = "ADS Tech Instant TV DVB-T PCI",
0769         .tuner_type     = UNSET,
0770         .radio_type     = UNSET,
0771         .tuner_addr = ADDR_UNSET,
0772         .radio_addr = ADDR_UNSET,
0773         .input          = { {
0774             .type   = CX88_VMUX_COMPOSITE1,
0775             .vmux   = 1,
0776             .gpio0  = 0x0700,
0777             .gpio2  = 0x0101,
0778         }, {
0779             .type   = CX88_VMUX_SVIDEO,
0780             .vmux   = 2,
0781             .gpio0  = 0x0700,
0782             .gpio2  = 0x0101,
0783         } },
0784         .mpeg           = CX88_MPEG_DVB,
0785     },
0786     [CX88_BOARD_TERRATEC_CINERGY_1400_DVB_T1] = {
0787         .name           = "TerraTec Cinergy 1400 DVB-T",
0788         .tuner_type     = UNSET,
0789         .input          = { {
0790             .type   = CX88_VMUX_DVB,
0791             .vmux   = 0,
0792         }, {
0793             .type   = CX88_VMUX_COMPOSITE1,
0794             .vmux   = 2,
0795         }, {
0796             .type   = CX88_VMUX_SVIDEO,
0797             .vmux   = 2,
0798         } },
0799         .mpeg           = CX88_MPEG_DVB,
0800     },
0801     [CX88_BOARD_DVICO_FUSIONHDTV_5_GOLD] = {
0802         .name           = "DViCO FusionHDTV 5 Gold",
0803         .tuner_type     = TUNER_LG_TDVS_H06XF, /* TDVS-H062F */
0804         .radio_type     = UNSET,
0805         .tuner_addr = ADDR_UNSET,
0806         .radio_addr = ADDR_UNSET,
0807         .tda9887_conf   = TDA9887_PRESENT,
0808         .input          = { {
0809             .type   = CX88_VMUX_TELEVISION,
0810             .vmux   = 0,
0811             .gpio0  = 0x87fd,
0812         }, {
0813             .type   = CX88_VMUX_COMPOSITE1,
0814             .vmux   = 1,
0815             .gpio0  = 0x87f9,
0816         }, {
0817             .type   = CX88_VMUX_SVIDEO,
0818             .vmux   = 2,
0819             .gpio0  = 0x87f9,
0820         } },
0821         .mpeg           = CX88_MPEG_DVB,
0822     },
0823     [CX88_BOARD_AVERMEDIA_ULTRATV_MC_550] = {
0824         .name           = "AverMedia UltraTV Media Center PCI 550",
0825         .tuner_type     = TUNER_PHILIPS_FM1236_MK3,
0826         .radio_type     = UNSET,
0827         .tuner_addr     = ADDR_UNSET,
0828         .radio_addr     = ADDR_UNSET,
0829         .tda9887_conf   = TDA9887_PRESENT,
0830         .input          = { {
0831             .type   = CX88_VMUX_COMPOSITE1,
0832             .vmux   = 0,
0833             .gpio0  = 0x0000cd73,
0834             .audioroute = 1,
0835         }, {
0836             .type   = CX88_VMUX_SVIDEO,
0837             .vmux   = 1,
0838             .gpio0  = 0x0000cd73,
0839             .audioroute = 1,
0840         }, {
0841             .type   = CX88_VMUX_TELEVISION,
0842             .vmux   = 3,
0843             .gpio0  = 0x0000cdb3,
0844             .audioroute = 1,
0845         } },
0846         .radio = {
0847             .type   = CX88_RADIO,
0848             .vmux   = 2,
0849             .gpio0  = 0x0000cdf3,
0850             .audioroute = 1,
0851         },
0852         .mpeg           = CX88_MPEG_BLACKBIRD,
0853     },
0854     [CX88_BOARD_KWORLD_VSTREAM_EXPERT_DVD] = {
0855          /* Alexander Wold <awold@bigfoot.com> */
0856          .name           = "Kworld V-Stream Xpert DVD",
0857          .tuner_type     = UNSET,
0858          .input          = { {
0859              .type   = CX88_VMUX_COMPOSITE1,
0860              .vmux   = 1,
0861              .gpio0  = 0x03000000,
0862              .gpio1  = 0x01000000,
0863              .gpio2  = 0x02000000,
0864              .gpio3  = 0x00100000,
0865          }, {
0866              .type   = CX88_VMUX_SVIDEO,
0867              .vmux   = 2,
0868              .gpio0  = 0x03000000,
0869              .gpio1  = 0x01000000,
0870              .gpio2  = 0x02000000,
0871              .gpio3  = 0x00100000,
0872          } },
0873     },
0874     [CX88_BOARD_ATI_HDTVWONDER] = {
0875         .name           = "ATI HDTV Wonder",
0876         .tuner_type     = TUNER_PHILIPS_TUV1236D,
0877         .radio_type     = UNSET,
0878         .tuner_addr = ADDR_UNSET,
0879         .radio_addr = ADDR_UNSET,
0880         .input          = { {
0881             .type   = CX88_VMUX_TELEVISION,
0882             .vmux   = 0,
0883             .gpio0  = 0x00000ff7,
0884             .gpio1  = 0x000000ff,
0885             .gpio2  = 0x00000001,
0886             .gpio3  = 0x00000000,
0887         }, {
0888             .type   = CX88_VMUX_COMPOSITE1,
0889             .vmux   = 1,
0890             .gpio0  = 0x00000ffe,
0891             .gpio1  = 0x000000ff,
0892             .gpio2  = 0x00000001,
0893             .gpio3  = 0x00000000,
0894         }, {
0895             .type   = CX88_VMUX_SVIDEO,
0896             .vmux   = 2,
0897             .gpio0  = 0x00000ffe,
0898             .gpio1  = 0x000000ff,
0899             .gpio2  = 0x00000001,
0900             .gpio3  = 0x00000000,
0901         } },
0902         .mpeg           = CX88_MPEG_DVB,
0903     },
0904     [CX88_BOARD_WINFAST_DTV1000] = {
0905         .name           = "WinFast DTV1000-T",
0906         .tuner_type     = UNSET,
0907         .radio_type     = UNSET,
0908         .tuner_addr = ADDR_UNSET,
0909         .radio_addr = ADDR_UNSET,
0910         .input          = { {
0911             .type   = CX88_VMUX_DVB,
0912             .vmux   = 0,
0913         }, {
0914             .type   = CX88_VMUX_COMPOSITE1,
0915             .vmux   = 1,
0916         }, {
0917             .type   = CX88_VMUX_SVIDEO,
0918             .vmux   = 2,
0919         } },
0920         .mpeg           = CX88_MPEG_DVB,
0921     },
0922     [CX88_BOARD_AVERTV_303] = {
0923         .name           = "AVerTV 303 (M126)",
0924         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
0925         .radio_type     = UNSET,
0926         .tuner_addr = ADDR_UNSET,
0927         .radio_addr = ADDR_UNSET,
0928         .tda9887_conf   = TDA9887_PRESENT,
0929         .input          = { {
0930             .type   = CX88_VMUX_TELEVISION,
0931             .vmux   = 0,
0932             .gpio0  = 0x00ff,
0933             .gpio1  = 0xe09f,
0934             .gpio2  = 0x0010,
0935             .gpio3  = 0x0000,
0936         }, {
0937             .type   = CX88_VMUX_COMPOSITE1,
0938             .vmux   = 1,
0939             .gpio0  = 0x00ff,
0940             .gpio1  = 0xe05f,
0941             .gpio2  = 0x0010,
0942             .gpio3  = 0x0000,
0943         }, {
0944             .type   = CX88_VMUX_SVIDEO,
0945             .vmux   = 2,
0946             .gpio0  = 0x00ff,
0947             .gpio1  = 0xe05f,
0948             .gpio2  = 0x0010,
0949             .gpio3  = 0x0000,
0950         } },
0951     },
0952     [CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1] = {
0953         .name       = "Hauppauge Nova-S-Plus DVB-S",
0954         .tuner_type = UNSET,
0955         .radio_type = UNSET,
0956         .tuner_addr = ADDR_UNSET,
0957         .radio_addr = ADDR_UNSET,
0958         .audio_chip = CX88_AUDIO_WM8775,
0959         .i2sinputcntl   = 2,
0960         .input      = { {
0961             .type   = CX88_VMUX_DVB,
0962             .vmux   = 0,
0963             /* 2: Line-In */
0964             .audioroute = 2,
0965         }, {
0966             .type   = CX88_VMUX_COMPOSITE1,
0967             .vmux   = 1,
0968             /* 2: Line-In */
0969             .audioroute = 2,
0970         }, {
0971             .type   = CX88_VMUX_SVIDEO,
0972             .vmux   = 2,
0973             /* 2: Line-In */
0974             .audioroute = 2,
0975         } },
0976         .mpeg           = CX88_MPEG_DVB,
0977     },
0978     [CX88_BOARD_HAUPPAUGE_NOVASE2_S1] = {
0979         .name       = "Hauppauge Nova-SE2 DVB-S",
0980         .tuner_type = UNSET,
0981         .radio_type = UNSET,
0982         .tuner_addr = ADDR_UNSET,
0983         .radio_addr = ADDR_UNSET,
0984         .input      = { {
0985             .type   = CX88_VMUX_DVB,
0986             .vmux   = 0,
0987         } },
0988         .mpeg           = CX88_MPEG_DVB,
0989     },
0990     [CX88_BOARD_KWORLD_DVBS_100] = {
0991         .name       = "KWorld DVB-S 100",
0992         .tuner_type = UNSET,
0993         .radio_type = UNSET,
0994         .tuner_addr = ADDR_UNSET,
0995         .radio_addr = ADDR_UNSET,
0996         .audio_chip = CX88_AUDIO_WM8775,
0997         .input      = { {
0998             .type   = CX88_VMUX_DVB,
0999             .vmux   = 0,
1000             /* 2: Line-In */
1001             .audioroute = 2,
1002         }, {
1003             .type   = CX88_VMUX_COMPOSITE1,
1004             .vmux   = 1,
1005             /* 2: Line-In */
1006             .audioroute = 2,
1007         }, {
1008             .type   = CX88_VMUX_SVIDEO,
1009             .vmux   = 2,
1010             /* 2: Line-In */
1011             .audioroute = 2,
1012         } },
1013         .mpeg           = CX88_MPEG_DVB,
1014     },
1015     [CX88_BOARD_HAUPPAUGE_HVR1100] = {
1016         .name       = "Hauppauge WinTV-HVR1100 DVB-T/Hybrid",
1017         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1018         .radio_type = UNSET,
1019         .tuner_addr = ADDR_UNSET,
1020         .radio_addr = ADDR_UNSET,
1021         .tda9887_conf   = TDA9887_PRESENT,
1022         .input      = { {
1023             .type   = CX88_VMUX_TELEVISION,
1024             .vmux   = 0,
1025         }, {
1026             .type   = CX88_VMUX_COMPOSITE1,
1027             .vmux   = 1,
1028         }, {
1029             .type   = CX88_VMUX_SVIDEO,
1030             .vmux   = 2,
1031         } },
1032         /* fixme: Add radio support */
1033         .mpeg           = CX88_MPEG_DVB,
1034     },
1035     [CX88_BOARD_HAUPPAUGE_HVR1100LP] = {
1036         .name       = "Hauppauge WinTV-HVR1100 DVB-T/Hybrid (Low Profile)",
1037         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1038         .radio_type = UNSET,
1039         .tuner_addr = ADDR_UNSET,
1040         .radio_addr = ADDR_UNSET,
1041         .tda9887_conf   = TDA9887_PRESENT,
1042         .input      = { {
1043             .type   = CX88_VMUX_TELEVISION,
1044             .vmux   = 0,
1045         }, {
1046             .type   = CX88_VMUX_COMPOSITE1,
1047             .vmux   = 1,
1048         } },
1049         /* fixme: Add radio support */
1050         .mpeg           = CX88_MPEG_DVB,
1051     },
1052     [CX88_BOARD_DNTV_LIVE_DVB_T_PRO] = {
1053         .name           = "digitalnow DNTV Live! DVB-T Pro",
1054         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1055         .radio_type     = UNSET,
1056         .tuner_addr = ADDR_UNSET,
1057         .radio_addr = ADDR_UNSET,
1058         .tda9887_conf   = TDA9887_PRESENT | TDA9887_PORT1_ACTIVE |
1059                   TDA9887_PORT2_ACTIVE,
1060         .input          = { {
1061             .type   = CX88_VMUX_TELEVISION,
1062             .vmux   = 0,
1063             .gpio0  = 0xf80808,
1064         }, {
1065             .type   = CX88_VMUX_COMPOSITE1,
1066             .vmux   = 1,
1067             .gpio0  = 0xf80808,
1068         }, {
1069             .type   = CX88_VMUX_SVIDEO,
1070             .vmux   = 2,
1071             .gpio0  = 0xf80808,
1072         } },
1073         .radio = {
1074              .type  = CX88_RADIO,
1075              .gpio0 = 0xf80808,
1076         },
1077         .mpeg           = CX88_MPEG_DVB,
1078     },
1079     [CX88_BOARD_KWORLD_DVB_T_CX22702] = {
1080         /* Kworld V-stream Xpert DVB-T with Thomson tuner */
1081         /* DTT 7579 Conexant CX22702-19 Conexant CX2388x  */
1082         /* Manenti Marco <marco_manenti@colman.it> */
1083         .name           = "KWorld/VStream XPert DVB-T with cx22702",
1084         .tuner_type     = UNSET,
1085         .radio_type     = UNSET,
1086         .tuner_addr = ADDR_UNSET,
1087         .radio_addr = ADDR_UNSET,
1088         .input          = { {
1089             .type   = CX88_VMUX_COMPOSITE1,
1090             .vmux   = 1,
1091             .gpio0  = 0x0700,
1092             .gpio2  = 0x0101,
1093         }, {
1094             .type   = CX88_VMUX_SVIDEO,
1095             .vmux   = 2,
1096             .gpio0  = 0x0700,
1097             .gpio2  = 0x0101,
1098         } },
1099         .mpeg           = CX88_MPEG_DVB,
1100     },
1101     [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL] = {
1102         .name           = "DViCO FusionHDTV DVB-T Dual Digital",
1103         .tuner_type     = UNSET, /* No analog tuner */
1104         .radio_type     = UNSET,
1105         .tuner_addr = ADDR_UNSET,
1106         .radio_addr = ADDR_UNSET,
1107         .input          = { {
1108             .type   = CX88_VMUX_COMPOSITE1,
1109             .vmux   = 1,
1110             .gpio0  = 0x000067df,
1111          }, {
1112             .type   = CX88_VMUX_SVIDEO,
1113             .vmux   = 2,
1114             .gpio0  = 0x000067df,
1115         } },
1116         .mpeg           = CX88_MPEG_DVB,
1117     },
1118     [CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT] = {
1119         .name           = "KWorld HardwareMpegTV XPert",
1120         .tuner_type     = TUNER_PHILIPS_TDA8290,
1121         .radio_type     = UNSET,
1122         .tuner_addr = ADDR_UNSET,
1123         .radio_addr = ADDR_UNSET,
1124         .input          = { {
1125             .type   = CX88_VMUX_TELEVISION,
1126             .vmux   = 0,
1127             .gpio0  = 0x3de2,
1128             .gpio2  = 0x00ff,
1129         }, {
1130             .type   = CX88_VMUX_COMPOSITE1,
1131             .vmux   = 1,
1132             .gpio0  = 0x3de6,
1133             .audioroute = 1,
1134         }, {
1135             .type   = CX88_VMUX_SVIDEO,
1136             .vmux   = 2,
1137             .gpio0  = 0x3de6,
1138             .audioroute = 1,
1139         } },
1140         .radio = {
1141             .type   = CX88_RADIO,
1142             .gpio0  = 0x3de6,
1143             .gpio2  = 0x00ff,
1144         },
1145         .mpeg           = CX88_MPEG_BLACKBIRD,
1146     },
1147     [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID] = {
1148         .name           = "DViCO FusionHDTV DVB-T Hybrid",
1149         .tuner_type     = TUNER_THOMSON_FE6600,
1150         .radio_type     = UNSET,
1151         .tuner_addr = ADDR_UNSET,
1152         .radio_addr = ADDR_UNSET,
1153         .input          = { {
1154             .type   = CX88_VMUX_TELEVISION,
1155             .vmux   = 0,
1156             .gpio0  = 0x0000a75f,
1157         }, {
1158             .type   = CX88_VMUX_COMPOSITE1,
1159             .vmux   = 1,
1160             .gpio0  = 0x0000a75b,
1161         }, {
1162             .type   = CX88_VMUX_SVIDEO,
1163             .vmux   = 2,
1164             .gpio0  = 0x0000a75b,
1165         } },
1166         .mpeg           = CX88_MPEG_DVB,
1167     },
1168     [CX88_BOARD_PCHDTV_HD5500] = {
1169         .name           = "pcHDTV HD5500 HDTV",
1170         .tuner_type     = TUNER_LG_TDVS_H06XF, /* TDVS-H064F */
1171         .radio_type     = UNSET,
1172         .tuner_addr = ADDR_UNSET,
1173         .radio_addr = ADDR_UNSET,
1174         .tda9887_conf   = TDA9887_PRESENT,
1175         .input          = { {
1176             .type   = CX88_VMUX_TELEVISION,
1177             .vmux   = 0,
1178             .gpio0  = 0x87fd,
1179         }, {
1180             .type   = CX88_VMUX_COMPOSITE1,
1181             .vmux   = 1,
1182             .gpio0  = 0x87f9,
1183         }, {
1184             .type   = CX88_VMUX_SVIDEO,
1185             .vmux   = 2,
1186             .gpio0  = 0x87f9,
1187         } },
1188         .mpeg           = CX88_MPEG_DVB,
1189     },
1190     [CX88_BOARD_KWORLD_MCE200_DELUXE] = {
1191         /*
1192          * FIXME: tested TV input only, disabled composite,
1193          * svideo and radio until they can be tested also.
1194          */
1195         .name           = "Kworld MCE 200 Deluxe",
1196         .tuner_type     = TUNER_TENA_9533_DI,
1197         .radio_type     = UNSET,
1198         .tda9887_conf   = TDA9887_PRESENT,
1199         .tuner_addr     = ADDR_UNSET,
1200         .radio_addr     = ADDR_UNSET,
1201         .input          = { {
1202             .type   = CX88_VMUX_TELEVISION,
1203             .vmux   = 0,
1204             .gpio0  = 0x0000BDE6
1205         } },
1206         .mpeg           = CX88_MPEG_BLACKBIRD,
1207     },
1208     [CX88_BOARD_PIXELVIEW_PLAYTV_P7000] = {
1209         /* FIXME: SVideo, Composite and FM inputs are untested */
1210         .name           = "PixelView PlayTV P7000",
1211         .tuner_type     = TUNER_PHILIPS_FM1216ME_MK3,
1212         .radio_type     = UNSET,
1213         .tuner_addr = ADDR_UNSET,
1214         .radio_addr = ADDR_UNSET,
1215         .tda9887_conf   = TDA9887_PRESENT | TDA9887_PORT1_ACTIVE |
1216                   TDA9887_PORT2_ACTIVE,
1217         .input          = { {
1218             .type   = CX88_VMUX_TELEVISION,
1219             .vmux   = 0,
1220             .gpio0  = 0x5da6,
1221         } },
1222         .mpeg           = CX88_MPEG_BLACKBIRD,
1223     },
1224     [CX88_BOARD_NPGTECH_REALTV_TOP10FM] = {
1225         .name           = "NPG Tech Real TV FM Top 10",
1226         .tuner_type     = TUNER_TNF_5335MF, /* Actually a TNF9535 */
1227         .radio_type     = UNSET,
1228         .tuner_addr = ADDR_UNSET,
1229         .radio_addr = ADDR_UNSET,
1230         .input          = { {
1231             .type   = CX88_VMUX_TELEVISION,
1232             .vmux   = 0,
1233             .gpio0  = 0x0788,
1234         }, {
1235             .type   = CX88_VMUX_COMPOSITE1,
1236             .vmux   = 1,
1237             .gpio0  = 0x078b,
1238         }, {
1239             .type   = CX88_VMUX_SVIDEO,
1240             .vmux   = 2,
1241             .gpio0  = 0x078b,
1242         } },
1243         .radio = {
1244              .type  = CX88_RADIO,
1245              .gpio0 = 0x074a,
1246         },
1247     },
1248     [CX88_BOARD_WINFAST_DTV2000H] = {
1249         .name           = "WinFast DTV2000 H",
1250         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1251         .radio_type     = UNSET,
1252         .tuner_addr     = ADDR_UNSET,
1253         .radio_addr     = ADDR_UNSET,
1254         .tda9887_conf   = TDA9887_PRESENT,
1255         .input          = { {
1256             .type   = CX88_VMUX_TELEVISION,
1257             .vmux   = 0,
1258             .gpio0  = 0x00017304,
1259             .gpio1  = 0x00008203,
1260             .gpio2  = 0x00017304,
1261             .gpio3  = 0x02000000,
1262         }, {
1263             .type   = CX88_VMUX_COMPOSITE1,
1264             .vmux   = 1,
1265             .gpio0  = 0x0001d701,
1266             .gpio1  = 0x0000b207,
1267             .gpio2  = 0x0001d701,
1268             .gpio3  = 0x02000000,
1269         }, {
1270             .type   = CX88_VMUX_COMPOSITE2,
1271             .vmux   = 2,
1272             .gpio0  = 0x0001d503,
1273             .gpio1  = 0x0000b207,
1274             .gpio2  = 0x0001d503,
1275             .gpio3  = 0x02000000,
1276         }, {
1277             .type   = CX88_VMUX_SVIDEO,
1278             .vmux   = 3,
1279             .gpio0  = 0x0001d701,
1280             .gpio1  = 0x0000b207,
1281             .gpio2  = 0x0001d701,
1282             .gpio3  = 0x02000000,
1283         } },
1284         .radio = {
1285              .type  = CX88_RADIO,
1286              .gpio0 = 0x00015702,
1287              .gpio1 = 0x0000f207,
1288              .gpio2 = 0x00015702,
1289              .gpio3 = 0x02000000,
1290         },
1291         .mpeg           = CX88_MPEG_DVB,
1292     },
1293     [CX88_BOARD_WINFAST_DTV2000H_J] = {
1294         .name           = "WinFast DTV2000 H rev. J",
1295         .tuner_type     = TUNER_PHILIPS_FMD1216MEX_MK3,
1296         .radio_type     = UNSET,
1297         .tuner_addr     = ADDR_UNSET,
1298         .radio_addr     = ADDR_UNSET,
1299         .tda9887_conf   = TDA9887_PRESENT,
1300         .input          = { {
1301             .type   = CX88_VMUX_TELEVISION,
1302             .vmux   = 0,
1303             .gpio0  = 0x00017300,
1304             .gpio1  = 0x00008207,
1305             .gpio2  = 0x00000000,
1306             .gpio3  = 0x02000000,
1307         }, {
1308             .type   = CX88_VMUX_TELEVISION,
1309             .vmux   = 0,
1310             .gpio0  = 0x00018300,
1311             .gpio1  = 0x0000f207,
1312             .gpio2  = 0x00017304,
1313             .gpio3  = 0x02000000,
1314         }, {
1315             .type   = CX88_VMUX_COMPOSITE1,
1316             .vmux   = 1,
1317             .gpio0  = 0x00018301,
1318             .gpio1  = 0x0000f207,
1319             .gpio2  = 0x00017304,
1320             .gpio3  = 0x02000000,
1321         }, {
1322             .type   = CX88_VMUX_SVIDEO,
1323             .vmux   = 2,
1324             .gpio0  = 0x00018301,
1325             .gpio1  = 0x0000f207,
1326             .gpio2  = 0x00017304,
1327             .gpio3  = 0x02000000,
1328         } },
1329         .radio = {
1330              .type  = CX88_RADIO,
1331              .gpio0 = 0x00015702,
1332              .gpio1 = 0x0000f207,
1333              .gpio2 = 0x00015702,
1334              .gpio3 = 0x02000000,
1335         },
1336         .mpeg           = CX88_MPEG_DVB,
1337     },
1338     [CX88_BOARD_GENIATECH_DVBS] = {
1339         .name          = "Geniatech DVB-S",
1340         .tuner_type    = UNSET,
1341         .radio_type    = UNSET,
1342         .tuner_addr    = ADDR_UNSET,
1343         .radio_addr    = ADDR_UNSET,
1344         .input  = { {
1345             .type  = CX88_VMUX_DVB,
1346             .vmux  = 0,
1347         }, {
1348             .type  = CX88_VMUX_COMPOSITE1,
1349             .vmux  = 1,
1350         } },
1351         .mpeg           = CX88_MPEG_DVB,
1352     },
1353     [CX88_BOARD_HAUPPAUGE_HVR3000] = {
1354         .name           = "Hauppauge WinTV-HVR3000 TriMode Analog/DVB-S/DVB-T",
1355         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1356         .radio_type     = UNSET,
1357         .tuner_addr     = ADDR_UNSET,
1358         .radio_addr     = ADDR_UNSET,
1359         .tda9887_conf   = TDA9887_PRESENT,
1360         .audio_chip     = CX88_AUDIO_WM8775,
1361         .input          = { {
1362             .type   = CX88_VMUX_TELEVISION,
1363             .vmux   = 0,
1364             .gpio0  = 0x84bf,
1365             /* 1: TV Audio / FM Mono */
1366             .audioroute = 1,
1367         }, {
1368             .type   = CX88_VMUX_COMPOSITE1,
1369             .vmux   = 1,
1370             .gpio0  = 0x84bf,
1371             /* 2: Line-In */
1372             .audioroute = 2,
1373         }, {
1374             .type   = CX88_VMUX_SVIDEO,
1375             .vmux   = 2,
1376             .gpio0  = 0x84bf,
1377             /* 2: Line-In */
1378             .audioroute = 2,
1379         } },
1380         .radio = {
1381             .type   = CX88_RADIO,
1382             .gpio0  = 0x84bf,
1383             /* 4: FM Stereo (untested) */
1384             .audioroute = 8,
1385         },
1386         .mpeg           = CX88_MPEG_DVB,
1387         .num_frontends  = 2,
1388     },
1389     [CX88_BOARD_NORWOOD_MICRO] = {
1390         .name           = "Norwood Micro TV Tuner",
1391         .tuner_type     = TUNER_TNF_5335MF,
1392         .radio_type     = UNSET,
1393         .tuner_addr     = ADDR_UNSET,
1394         .radio_addr     = ADDR_UNSET,
1395         .input          = { {
1396             .type   = CX88_VMUX_TELEVISION,
1397             .vmux   = 0,
1398             .gpio0  = 0x0709,
1399         }, {
1400             .type   = CX88_VMUX_COMPOSITE1,
1401             .vmux   = 1,
1402             .gpio0  = 0x070b,
1403         }, {
1404             .type   = CX88_VMUX_SVIDEO,
1405             .vmux   = 2,
1406             .gpio0  = 0x070b,
1407         } },
1408     },
1409     [CX88_BOARD_TE_DTV_250_OEM_SWANN] = {
1410         .name           = "Shenzhen Tungsten Ages Tech TE-DTV-250 / Swann OEM",
1411         .tuner_type     = TUNER_LG_PAL_NEW_TAPC,
1412         .radio_type     = UNSET,
1413         .tuner_addr     = ADDR_UNSET,
1414         .radio_addr     = ADDR_UNSET,
1415         .input          = { {
1416             .type   = CX88_VMUX_TELEVISION,
1417             .vmux   = 0,
1418             .gpio0  = 0x003fffff,
1419             .gpio1  = 0x00e00000,
1420             .gpio2  = 0x003fffff,
1421             .gpio3  = 0x02000000,
1422         }, {
1423             .type   = CX88_VMUX_COMPOSITE1,
1424             .vmux   = 1,
1425             .gpio0  = 0x003fffff,
1426             .gpio1  = 0x00e00000,
1427             .gpio2  = 0x003fffff,
1428             .gpio3  = 0x02000000,
1429         }, {
1430             .type   = CX88_VMUX_SVIDEO,
1431             .vmux   = 2,
1432             .gpio0  = 0x003fffff,
1433             .gpio1  = 0x00e00000,
1434             .gpio2  = 0x003fffff,
1435             .gpio3  = 0x02000000,
1436         } },
1437     },
1438     [CX88_BOARD_HAUPPAUGE_HVR1300] = {
1439         .name       = "Hauppauge WinTV-HVR1300 DVB-T/Hybrid MPEG Encoder",
1440         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1441         .radio_type = UNSET,
1442         .tuner_addr = ADDR_UNSET,
1443         .radio_addr = ADDR_UNSET,
1444         .tda9887_conf   = TDA9887_PRESENT,
1445         .audio_chip     = CX88_AUDIO_WM8775,
1446         /*
1447          * gpio0 as reported by Mike Crash <mike AT mikecrash.com>
1448          */
1449         .input      = { {
1450             .type   = CX88_VMUX_TELEVISION,
1451             .vmux   = 0,
1452             .gpio0  = 0xef88,
1453             /* 1: TV Audio / FM Mono */
1454             .audioroute = 1,
1455         }, {
1456             .type   = CX88_VMUX_COMPOSITE1,
1457             .vmux   = 1,
1458             .gpio0  = 0xef88,
1459             /* 2: Line-In */
1460             .audioroute = 2,
1461         }, {
1462             .type   = CX88_VMUX_SVIDEO,
1463             .vmux   = 2,
1464             .gpio0  = 0xef88,
1465             /* 2: Line-In */
1466             .audioroute = 2,
1467         } },
1468         .mpeg           = CX88_MPEG_DVB | CX88_MPEG_BLACKBIRD,
1469         .radio = {
1470             .type   = CX88_RADIO,
1471             .gpio0  = 0xef88,
1472             /* 4: FM Stereo (untested) */
1473             .audioroute = 8,
1474         },
1475     },
1476     [CX88_BOARD_SAMSUNG_SMT_7020] = {
1477         .name       = "Samsung SMT 7020 DVB-S",
1478         .tuner_type = UNSET,
1479         .radio_type = UNSET,
1480         .tuner_addr = ADDR_UNSET,
1481         .radio_addr = ADDR_UNSET,
1482         .input      = { {
1483             .type   = CX88_VMUX_DVB,
1484             .vmux   = 0,
1485         } },
1486         .mpeg           = CX88_MPEG_DVB,
1487     },
1488     [CX88_BOARD_ADSTECH_PTV_390] = {
1489         .name           = "ADS Tech Instant Video PCI",
1490         .tuner_type     = UNSET,
1491         .radio_type     = UNSET,
1492         .tuner_addr     = ADDR_UNSET,
1493         .radio_addr     = ADDR_UNSET,
1494         .input          = { {
1495             .type   = CX88_VMUX_DEBUG,
1496             .vmux   = 3,
1497             .gpio0  = 0x04ff,
1498         }, {
1499             .type   = CX88_VMUX_COMPOSITE1,
1500             .vmux   = 1,
1501             .gpio0  = 0x07fa,
1502         }, {
1503             .type   = CX88_VMUX_SVIDEO,
1504             .vmux   = 2,
1505             .gpio0  = 0x07fa,
1506         } },
1507     },
1508     [CX88_BOARD_PINNACLE_PCTV_HD_800i] = {
1509         .name           = "Pinnacle PCTV HD 800i",
1510         .tuner_type     = TUNER_XC5000,
1511         .radio_type     = UNSET,
1512         .tuner_addr = ADDR_UNSET,
1513         .radio_addr = ADDR_UNSET,
1514         .input          = { {
1515             .type   = CX88_VMUX_TELEVISION,
1516             .vmux   = 0,
1517             .gpio0  = 0x04fb,
1518             .gpio1  = 0x10ff,
1519         }, {
1520             .type   = CX88_VMUX_COMPOSITE1,
1521             .vmux   = 1,
1522             .gpio0  = 0x04fb,
1523             .gpio1  = 0x10ef,
1524             .audioroute = 1,
1525         }, {
1526             .type   = CX88_VMUX_SVIDEO,
1527             .vmux   = 2,
1528             .gpio0  = 0x04fb,
1529             .gpio1  = 0x10ef,
1530             .audioroute = 1,
1531         } },
1532         .mpeg           = CX88_MPEG_DVB,
1533     },
1534     [CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO] = {
1535         .name           = "DViCO FusionHDTV 5 PCI nano",
1536         /* xc3008 tuner, digital only for now */
1537         .tuner_type     = UNSET,
1538         .radio_type     = UNSET,
1539         .tuner_addr = ADDR_UNSET,
1540         .radio_addr = ADDR_UNSET,
1541         .input          = { {
1542             .type   = CX88_VMUX_TELEVISION,
1543             .vmux   = 0,
1544             .gpio0  = 0x000027df, /* Unconfirmed */
1545         }, {
1546             .type   = CX88_VMUX_COMPOSITE1,
1547             .vmux   = 1,
1548             .gpio0  = 0x000027df, /* Unconfirmed */
1549             .audioroute = 1,
1550         }, {
1551             .type   = CX88_VMUX_SVIDEO,
1552             .vmux   = 2,
1553             .gpio0  = 0x000027df, /* Unconfirmed */
1554             .audioroute = 1,
1555         } },
1556         .mpeg           = CX88_MPEG_DVB,
1557     },
1558     [CX88_BOARD_PINNACLE_HYBRID_PCTV] = {
1559         .name           = "Pinnacle Hybrid PCTV",
1560         .tuner_type     = TUNER_XC2028,
1561         .tuner_addr     = 0x61,
1562         .radio_type     = UNSET,
1563         .radio_addr     = ADDR_UNSET,
1564         .input          = { {
1565             .type   = CX88_VMUX_TELEVISION,
1566             .vmux   = 0,
1567             .gpio0  = 0x004ff,
1568             .gpio1  = 0x010ff,
1569             .gpio2  = 0x00001,
1570         }, {
1571             .type   = CX88_VMUX_COMPOSITE1,
1572             .vmux   = 1,
1573             .gpio0  = 0x004fb,
1574             .gpio1  = 0x010ef,
1575             .audioroute = 1,
1576         }, {
1577             .type   = CX88_VMUX_SVIDEO,
1578             .vmux   = 2,
1579             .gpio0  = 0x004fb,
1580             .gpio1  = 0x010ef,
1581             .audioroute = 1,
1582         } },
1583         .radio = {
1584             .type   = CX88_RADIO,
1585             .gpio0  = 0x004ff,
1586             .gpio1  = 0x010ff,
1587             .gpio2  = 0x0ff,
1588         },
1589         .mpeg           = CX88_MPEG_DVB,
1590     },
1591     /* Terry Wu <terrywu2009@gmail.com> */
1592     /* TV Audio :      set GPIO 2, 18, 19 value to 0, 1, 0 */
1593     /* FM Audio :      set GPIO 2, 18, 19 value to 0, 0, 0 */
1594     /* Line-in Audio : set GPIO 2, 18, 19 value to 0, 1, 1 */
1595     /* Mute Audio :    set GPIO 2 value to 1               */
1596     [CX88_BOARD_WINFAST_TV2000_XP_GLOBAL] = {
1597         .name           = "Leadtek TV2000 XP Global",
1598         .tuner_type     = TUNER_XC2028,
1599         .tuner_addr     = 0x61,
1600         .radio_type     = UNSET,
1601         .radio_addr     = ADDR_UNSET,
1602         .input          = { {
1603             .type   = CX88_VMUX_TELEVISION,
1604             .vmux   = 0,
1605             .gpio0  = 0x0400,       /* pin 2 = 0 */
1606             .gpio1  = 0x0000,
1607             .gpio2  = 0x0C04,       /* pin 18 = 1, pin 19 = 0 */
1608             .gpio3  = 0x0000,
1609         }, {
1610             .type   = CX88_VMUX_COMPOSITE1,
1611             .vmux   = 1,
1612             .gpio0  = 0x0400,       /* pin 2 = 0 */
1613             .gpio1  = 0x0000,
1614             .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1615             .gpio3  = 0x0000,
1616         }, {
1617             .type   = CX88_VMUX_SVIDEO,
1618             .vmux   = 2,
1619             .gpio0  = 0x0400,       /* pin 2 = 0 */
1620             .gpio1  = 0x0000,
1621             .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1622             .gpio3  = 0x0000,
1623         } },
1624         .radio = {
1625             .type   = CX88_RADIO,
1626             .gpio0  = 0x0400,        /* pin 2 = 0 */
1627             .gpio1  = 0x0000,
1628             .gpio2  = 0x0C00,       /* pin 18 = 0, pin 19 = 0 */
1629             .gpio3  = 0x0000,
1630         },
1631     },
1632     [CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36] = {
1633         .name           = "Leadtek TV2000 XP Global (SC4100)",
1634         .tuner_type     = TUNER_XC4000,
1635         .tuner_addr     = 0x61,
1636         .radio_type     = UNSET,
1637         .radio_addr     = ADDR_UNSET,
1638         .input          = { {
1639             .type   = CX88_VMUX_TELEVISION,
1640             .vmux   = 0,
1641             .gpio0  = 0x0400,       /* pin 2 = 0 */
1642             .gpio1  = 0x0000,
1643             .gpio2  = 0x0C04,       /* pin 18 = 1, pin 19 = 0 */
1644             .gpio3  = 0x0000,
1645         }, {
1646             .type   = CX88_VMUX_COMPOSITE1,
1647             .vmux   = 1,
1648             .gpio0  = 0x0400,       /* pin 2 = 0 */
1649             .gpio1  = 0x0000,
1650             .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1651             .gpio3  = 0x0000,
1652         }, {
1653             .type   = CX88_VMUX_SVIDEO,
1654             .vmux   = 2,
1655             .gpio0  = 0x0400,       /* pin 2 = 0 */
1656             .gpio1  = 0x0000,
1657             .gpio2  = 0x0C0C,       /* pin 18 = 1, pin 19 = 1 */
1658             .gpio3  = 0x0000,
1659         } },
1660         .radio = {
1661             .type   = CX88_RADIO,
1662             .gpio0  = 0x0400,        /* pin 2 = 0 */
1663             .gpio1  = 0x0000,
1664             .gpio2  = 0x0C00,       /* pin 18 = 0, pin 19 = 0 */
1665             .gpio3  = 0x0000,
1666         },
1667     },
1668     [CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43] = {
1669         .name           = "Leadtek TV2000 XP Global (XC4100)",
1670         .tuner_type     = TUNER_XC4000,
1671         .tuner_addr     = 0x61,
1672         .radio_type     = UNSET,
1673         .radio_addr     = ADDR_UNSET,
1674         .input          = { {
1675             .type   = CX88_VMUX_TELEVISION,
1676             .vmux   = 0,
1677             .gpio0  = 0x0400,       /* pin 2 = 0 */
1678             .gpio1  = 0x6040,       /* pin 14 = 1, pin 13 = 0 */
1679             .gpio2  = 0x0000,
1680             .gpio3  = 0x0000,
1681         }, {
1682             .type   = CX88_VMUX_COMPOSITE1,
1683             .vmux   = 1,
1684             .gpio0  = 0x0400,       /* pin 2 = 0 */
1685             .gpio1  = 0x6060,       /* pin 14 = 1, pin 13 = 1 */
1686             .gpio2  = 0x0000,
1687             .gpio3  = 0x0000,
1688         }, {
1689             .type   = CX88_VMUX_SVIDEO,
1690             .vmux   = 2,
1691             .gpio0  = 0x0400,       /* pin 2 = 0 */
1692             .gpio1  = 0x6060,       /* pin 14 = 1, pin 13 = 1 */
1693             .gpio2  = 0x0000,
1694             .gpio3  = 0x0000,
1695         } },
1696         .radio = {
1697             .type   = CX88_RADIO,
1698             .gpio0  = 0x0400,        /* pin 2 = 0 */
1699             .gpio1  = 0x6000,        /* pin 14 = 1, pin 13 = 0 */
1700             .gpio2  = 0x0000,
1701             .gpio3  = 0x0000,
1702         },
1703     },
1704     [CX88_BOARD_POWERCOLOR_REAL_ANGEL] = {
1705         /* Long names may confuse LIRC. */
1706         .name           = "PowerColor RA330",
1707         .tuner_type     = TUNER_XC2028,
1708         .tuner_addr     = 0x61,
1709         .input          = { {
1710             /*
1711              * Due to the way the cx88 driver is written,
1712              * there is no way to deactivate audio pass-
1713              * through without this entry. Furthermore, if
1714              * the TV mux entry is first, you get audio
1715              * from the tuner on boot for a little while.
1716              */
1717             .type   = CX88_VMUX_DEBUG,
1718             .vmux   = 3,
1719             .gpio0 = 0x00ff,
1720             .gpio1 = 0xf39d,
1721             .gpio3 = 0x0000,
1722         }, {
1723             .type   = CX88_VMUX_TELEVISION,
1724             .vmux   = 0,
1725             .gpio0 = 0x00ff,
1726             .gpio1 = 0xf35d,
1727             .gpio3 = 0x0000,
1728         }, {
1729             .type   = CX88_VMUX_COMPOSITE1,
1730             .vmux   = 1,
1731             .gpio0 = 0x00ff,
1732             .gpio1 = 0xf37d,
1733             .gpio3 = 0x0000,
1734         }, {
1735             .type   = CX88_VMUX_SVIDEO,
1736             .vmux   = 2,
1737             .gpio0  = 0x000ff,
1738             .gpio1  = 0x0f37d,
1739             .gpio3  = 0x00000,
1740         } },
1741         .radio = {
1742             .type   = CX88_RADIO,
1743             .gpio0  = 0x000ff,
1744             .gpio1  = 0x0f35d,
1745             .gpio3  = 0x00000,
1746         },
1747     },
1748     [CX88_BOARD_GENIATECH_X8000_MT] = {
1749         /* Also PowerColor Real Angel 330 and Geniatech X800 OEM */
1750         .name           = "Geniatech X8000-MT DVBT",
1751         .tuner_type     = TUNER_XC2028,
1752         .tuner_addr     = 0x61,
1753         .input          = { {
1754             .type   = CX88_VMUX_TELEVISION,
1755             .vmux   = 0,
1756             .gpio0  = 0x00000000,
1757             .gpio1  = 0x00e3e341,
1758             .gpio2  = 0x00000000,
1759             .gpio3  = 0x00000000,
1760         }, {
1761             .type   = CX88_VMUX_COMPOSITE1,
1762             .vmux   = 1,
1763             .gpio0  = 0x00000000,
1764             .gpio1  = 0x00e3e361,
1765             .gpio2  = 0x00000000,
1766             .gpio3  = 0x00000000,
1767         }, {
1768             .type   = CX88_VMUX_SVIDEO,
1769             .vmux   = 2,
1770             .gpio0  = 0x00000000,
1771             .gpio1  = 0x00e3e361,
1772             .gpio2  = 0x00000000,
1773             .gpio3  = 0x00000000,
1774         } },
1775         .radio = {
1776             .type   = CX88_RADIO,
1777             .gpio0  = 0x00000000,
1778             .gpio1  = 0x00e3e341,
1779             .gpio2  = 0x00000000,
1780             .gpio3  = 0x00000000,
1781         },
1782         .mpeg           = CX88_MPEG_DVB,
1783     },
1784     [CX88_BOARD_NOTONLYTV_LV3H] = {
1785         .name           = "NotOnlyTV LV3H",
1786         .tuner_type     = TUNER_XC2028,
1787         .radio_type     = UNSET,
1788         .tuner_addr     = 0x61,
1789         .radio_addr     = ADDR_UNSET,
1790         /* if gpio1:bit9 is enabled, DVB-T won't work */
1791 
1792         .input          = { {
1793             .type   = CX88_VMUX_TELEVISION,
1794             .vmux   = 0,
1795             .gpio0  = 0x0000,
1796             .gpio1  = 0xa141,
1797             .gpio2  = 0x0000,
1798         }, {
1799             .type   = CX88_VMUX_COMPOSITE1,
1800             .vmux   = 1,
1801             .gpio0  = 0x0000,
1802             .gpio1  = 0xa161,
1803             .gpio2  = 0x0000,
1804         }, {
1805             .type   = CX88_VMUX_SVIDEO,
1806             .vmux   = 2,
1807             .gpio0  = 0x0000,
1808             .gpio1  = 0xa161,
1809             .gpio2  = 0x0000,
1810         } },
1811         .radio = {
1812             .type   = CX88_RADIO,
1813             .gpio0  = 0x0000,
1814             .gpio1  = 0xa141,
1815             .gpio2  = 0x0000,
1816         },
1817         .mpeg           = CX88_MPEG_DVB,
1818     },
1819     [CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO] = {
1820         .name           = "DViCO FusionHDTV DVB-T PRO",
1821         .tuner_type     = TUNER_XC2028,
1822         .tuner_addr     = 0x61,
1823         .radio_type     = UNSET,
1824         .radio_addr     = ADDR_UNSET,
1825         .input          = { {
1826             .type   = CX88_VMUX_COMPOSITE1,
1827             .vmux   = 1,
1828             .gpio0  = 0x000067df,
1829         }, {
1830             .type   = CX88_VMUX_SVIDEO,
1831             .vmux   = 2,
1832             .gpio0  = 0x000067df,
1833         } },
1834         .mpeg           = CX88_MPEG_DVB,
1835     },
1836     [CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD] = {
1837         .name           = "DViCO FusionHDTV 7 Gold",
1838         .tuner_type     = TUNER_XC5000,
1839         .radio_type     = UNSET,
1840         .tuner_addr = ADDR_UNSET,
1841         .radio_addr = ADDR_UNSET,
1842         .input          = { {
1843             .type   = CX88_VMUX_TELEVISION,
1844             .vmux   = 0,
1845             .gpio0  = 0x10df,
1846         }, {
1847             .type   = CX88_VMUX_COMPOSITE1,
1848             .vmux   = 1,
1849             .gpio0  = 0x16d9,
1850         }, {
1851             .type   = CX88_VMUX_SVIDEO,
1852             .vmux   = 2,
1853             .gpio0  = 0x16d9,
1854         } },
1855         .mpeg           = CX88_MPEG_DVB,
1856     },
1857     [CX88_BOARD_PROLINK_PV_8000GT] = {
1858         .name           = "Prolink Pixelview MPEG 8000GT",
1859         .tuner_type     = TUNER_XC2028,
1860         .tuner_addr     = 0x61,
1861         .input          = { {
1862             .type   = CX88_VMUX_TELEVISION,
1863             .vmux   = 0,
1864             .gpio0 = 0x0ff,
1865             .gpio2 = 0x0cfb,
1866         }, {
1867             .type   = CX88_VMUX_COMPOSITE1,
1868             .vmux   = 1,
1869             .gpio2 = 0x0cfb,
1870         }, {
1871             .type   = CX88_VMUX_SVIDEO,
1872             .vmux   = 2,
1873             .gpio2 = 0x0cfb,
1874         } },
1875         .radio = {
1876             .type   = CX88_RADIO,
1877             .gpio2 = 0x0cfb,
1878         },
1879     },
1880     [CX88_BOARD_PROLINK_PV_GLOBAL_XTREME] = {
1881         .name           = "Prolink Pixelview Global Extreme",
1882         .tuner_type     = TUNER_XC2028,
1883         .tuner_addr     = 0x61,
1884         .input          = { {
1885             .type   = CX88_VMUX_TELEVISION,
1886             .vmux   = 0,
1887             .gpio0 = 0x04fb,
1888             .gpio1 = 0x04080,
1889             .gpio2 = 0x0cf7,
1890         }, {
1891             .type   = CX88_VMUX_COMPOSITE1,
1892             .vmux   = 1,
1893             .gpio0 = 0x04fb,
1894             .gpio1 = 0x04080,
1895             .gpio2 = 0x0cfb,
1896         }, {
1897             .type   = CX88_VMUX_SVIDEO,
1898             .vmux   = 2,
1899             .gpio0 = 0x04fb,
1900             .gpio1 = 0x04080,
1901             .gpio2 = 0x0cfb,
1902         } },
1903         .radio = {
1904             .type   = CX88_RADIO,
1905             .gpio0 = 0x04ff,
1906             .gpio1 = 0x04080,
1907             .gpio2 = 0x0cf7,
1908         },
1909     },
1910     /*
1911      * Both radio, analog and ATSC work with this board.
1912      * However, for analog to work, s5h1409 gate should be open,
1913      * otherwise, tuner-xc3028 won't be detected.
1914      * A proper fix require using the newer i2c methods to add
1915      * tuner-xc3028 without doing an i2c probe.
1916      */
1917     [CX88_BOARD_KWORLD_ATSC_120] = {
1918         .name           = "Kworld PlusTV HD PCI 120 (ATSC 120)",
1919         .tuner_type     = TUNER_XC2028,
1920         .radio_type     = UNSET,
1921         .tuner_addr = ADDR_UNSET,
1922         .radio_addr = ADDR_UNSET,
1923         .input          = { {
1924             .type   = CX88_VMUX_TELEVISION,
1925             .vmux   = 0,
1926             .gpio0  = 0x000000ff,
1927             .gpio1  = 0x0000f35d,
1928             .gpio2  = 0x00000000,
1929         }, {
1930             .type   = CX88_VMUX_COMPOSITE1,
1931             .vmux   = 1,
1932             .gpio0  = 0x000000ff,
1933             .gpio1  = 0x0000f37e,
1934             .gpio2  = 0x00000000,
1935         }, {
1936             .type   = CX88_VMUX_SVIDEO,
1937             .vmux   = 2,
1938             .gpio0  = 0x000000ff,
1939             .gpio1  = 0x0000f37e,
1940             .gpio2  = 0x00000000,
1941         } },
1942         .radio = {
1943             .type   = CX88_RADIO,
1944             .gpio0  = 0x000000ff,
1945             .gpio1  = 0x0000f35d,
1946             .gpio2  = 0x00000000,
1947         },
1948         .mpeg           = CX88_MPEG_DVB,
1949     },
1950     [CX88_BOARD_HAUPPAUGE_HVR4000] = {
1951         .name           = "Hauppauge WinTV-HVR4000 DVB-S/S2/T/Hybrid",
1952         .tuner_type     = TUNER_PHILIPS_FMD1216ME_MK3,
1953         .radio_type     = UNSET,
1954         .tuner_addr     = ADDR_UNSET,
1955         .radio_addr     = ADDR_UNSET,
1956         .tda9887_conf   = TDA9887_PRESENT,
1957         .audio_chip     = CX88_AUDIO_WM8775,
1958         /*
1959          * GPIO0 (WINTV2000)
1960          *
1961          * Analogue     SAT     DVB-T
1962          * Antenna      0xc4bf  0xc4bb
1963          * Composite    0xc4bf  0xc4bb
1964          * S-Video      0xc4bf  0xc4bb
1965          * Composite1   0xc4ff  0xc4fb
1966          * S-Video1     0xc4ff  0xc4fb
1967          *
1968          * BIT  VALUE   FUNCTION GP{x}_IO
1969          * 0    1       I:?
1970          * 1    1       I:?
1971          * 2    1       O:MPEG PORT 0=DVB-T 1=DVB-S
1972          * 3    1       I:?
1973          * 4    1       I:?
1974          * 5    1       I:?
1975          * 6    0       O:INPUT SELECTOR 0=INTERNAL 1=EXPANSION
1976          * 7    1       O:DVB-T DEMOD RESET LOW
1977          *
1978          * BIT  VALUE   FUNCTION GP{x}_OE
1979          * 8    0       I
1980          * 9    0       I
1981          * a    1       O
1982          * b    0       I
1983          * c    0       I
1984          * d    0       I
1985          * e    1       O
1986          * f    1       O
1987          *
1988          * WM8775 ADC
1989          *
1990          * 1: TV Audio / FM Mono
1991          * 2: Line-In
1992          * 3: Line-In Expansion
1993          * 4: FM Stereo
1994          */
1995         .input          = { {
1996             .type   = CX88_VMUX_TELEVISION,
1997             .vmux   = 0,
1998             .gpio0  = 0xc4bf,
1999             /* 1: TV Audio / FM Mono */
2000             .audioroute = 1,
2001         }, {
2002             .type   = CX88_VMUX_COMPOSITE1,
2003             .vmux   = 1,
2004             .gpio0  = 0xc4bf,
2005             /* 2: Line-In */
2006             .audioroute = 2,
2007         }, {
2008             .type   = CX88_VMUX_SVIDEO,
2009             .vmux   = 2,
2010             .gpio0  = 0xc4bf,
2011             /* 2: Line-In */
2012             .audioroute = 2,
2013         } },
2014         .radio = {
2015             .type   = CX88_RADIO,
2016             .gpio0  = 0xc4bf,
2017             /* 4: FM Stereo */
2018             .audioroute = 8,
2019         },
2020         .mpeg           = CX88_MPEG_DVB,
2021         .num_frontends  = 2,
2022     },
2023     [CX88_BOARD_HAUPPAUGE_HVR4000LITE] = {
2024         .name           = "Hauppauge WinTV-HVR4000(Lite) DVB-S/S2",
2025         .tuner_type     = UNSET,
2026         .radio_type     = UNSET,
2027         .tuner_addr     = ADDR_UNSET,
2028         .radio_addr     = ADDR_UNSET,
2029         .input          = { {
2030             .type   = CX88_VMUX_DVB,
2031             .vmux   = 0,
2032         } },
2033         .mpeg           = CX88_MPEG_DVB,
2034     },
2035     [CX88_BOARD_TEVII_S420] = {
2036         .name           = "TeVii S420 DVB-S",
2037         .tuner_type     = UNSET,
2038         .radio_type     = UNSET,
2039         .tuner_addr     = ADDR_UNSET,
2040         .radio_addr     = ADDR_UNSET,
2041         .input          = { {
2042             .type   = CX88_VMUX_DVB,
2043             .vmux   = 0,
2044         } },
2045         .mpeg           = CX88_MPEG_DVB,
2046     },
2047     [CX88_BOARD_TEVII_S460] = {
2048         .name           = "TeVii S460 DVB-S/S2",
2049         .tuner_type     = UNSET,
2050         .radio_type     = UNSET,
2051         .tuner_addr     = ADDR_UNSET,
2052         .radio_addr     = ADDR_UNSET,
2053         .input          = { {
2054             .type   = CX88_VMUX_DVB,
2055             .vmux   = 0,
2056         } },
2057         .mpeg           = CX88_MPEG_DVB,
2058     },
2059     [CX88_BOARD_TEVII_S464] = {
2060         .name           = "TeVii S464 DVB-S/S2",
2061         .tuner_type     = UNSET,
2062         .radio_type     = UNSET,
2063         .tuner_addr     = ADDR_UNSET,
2064         .radio_addr     = ADDR_UNSET,
2065         .input          = { {
2066             .type   = CX88_VMUX_DVB,
2067             .vmux   = 0,
2068         } },
2069         .mpeg           = CX88_MPEG_DVB,
2070     },
2071     [CX88_BOARD_OMICOM_SS4_PCI] = {
2072         .name           = "Omicom SS4 DVB-S/S2 PCI",
2073         .tuner_type     = UNSET,
2074         .radio_type     = UNSET,
2075         .tuner_addr     = ADDR_UNSET,
2076         .radio_addr     = ADDR_UNSET,
2077         .input          = { {
2078             .type   = CX88_VMUX_DVB,
2079             .vmux   = 0,
2080         } },
2081         .mpeg           = CX88_MPEG_DVB,
2082     },
2083     [CX88_BOARD_TBS_8910] = {
2084         .name           = "TBS 8910 DVB-S",
2085         .tuner_type     = UNSET,
2086         .radio_type     = UNSET,
2087         .tuner_addr     = ADDR_UNSET,
2088         .radio_addr     = ADDR_UNSET,
2089         .input          = { {
2090             .type   = CX88_VMUX_DVB,
2091             .vmux   = 0,
2092         } },
2093         .mpeg           = CX88_MPEG_DVB,
2094     },
2095     [CX88_BOARD_TBS_8920] = {
2096         .name           = "TBS 8920 DVB-S/S2",
2097         .tuner_type     = UNSET,
2098         .radio_type     = UNSET,
2099         .tuner_addr     = ADDR_UNSET,
2100         .radio_addr     = ADDR_UNSET,
2101         .input          = { {
2102             .type   = CX88_VMUX_DVB,
2103             .vmux   = 0,
2104             .gpio0  = 0x8080,
2105         } },
2106         .mpeg           = CX88_MPEG_DVB,
2107     },
2108     [CX88_BOARD_PROF_6200] = {
2109         .name           = "Prof 6200 DVB-S",
2110         .tuner_type     = UNSET,
2111         .radio_type     = UNSET,
2112         .tuner_addr     = ADDR_UNSET,
2113         .radio_addr     = ADDR_UNSET,
2114         .input          = { {
2115             .type   = CX88_VMUX_DVB,
2116             .vmux   = 0,
2117         } },
2118         .mpeg           = CX88_MPEG_DVB,
2119     },
2120     [CX88_BOARD_PROF_7300] = {
2121         .name           = "PROF 7300 DVB-S/S2",
2122         .tuner_type     = UNSET,
2123         .radio_type     = UNSET,
2124         .tuner_addr     = ADDR_UNSET,
2125         .radio_addr     = ADDR_UNSET,
2126         .input          = { {
2127             .type   = CX88_VMUX_DVB,
2128             .vmux   = 0,
2129         } },
2130         .mpeg           = CX88_MPEG_DVB,
2131     },
2132     [CX88_BOARD_SATTRADE_ST4200] = {
2133         .name           = "SATTRADE ST4200 DVB-S/S2",
2134         .tuner_type     = UNSET,
2135         .radio_type     = UNSET,
2136         .tuner_addr     = ADDR_UNSET,
2137         .radio_addr     = ADDR_UNSET,
2138         .input          = { {
2139             .type   = CX88_VMUX_DVB,
2140             .vmux   = 0,
2141         } },
2142         .mpeg           = CX88_MPEG_DVB,
2143     },
2144     [CX88_BOARD_TERRATEC_CINERGY_HT_PCI_MKII] = {
2145         .name           = "Terratec Cinergy HT PCI MKII",
2146         .tuner_type     = TUNER_XC2028,
2147         .tuner_addr     = 0x61,
2148         .radio_type     = UNSET,
2149         .radio_addr     = ADDR_UNSET,
2150         .input          = { {
2151             .type   = CX88_VMUX_TELEVISION,
2152             .vmux   = 0,
2153             .gpio0  = 0x004ff,
2154             .gpio1  = 0x010ff,
2155             .gpio2  = 0x00001,
2156         }, {
2157             .type   = CX88_VMUX_COMPOSITE1,
2158             .vmux   = 1,
2159             .gpio0  = 0x004fb,
2160             .gpio1  = 0x010ef,
2161             .audioroute = 1,
2162         }, {
2163             .type   = CX88_VMUX_SVIDEO,
2164             .vmux   = 2,
2165             .gpio0  = 0x004fb,
2166             .gpio1  = 0x010ef,
2167             .audioroute = 1,
2168         } },
2169         .radio = {
2170             .type   = CX88_RADIO,
2171             .gpio0  = 0x004ff,
2172             .gpio1  = 0x010ff,
2173             .gpio2  = 0x0ff,
2174         },
2175         .mpeg           = CX88_MPEG_DVB,
2176     },
2177     [CX88_BOARD_HAUPPAUGE_IRONLY] = {
2178         .name           = "Hauppauge WinTV-IR Only",
2179         .tuner_type     = UNSET,
2180         .radio_type     = UNSET,
2181         .tuner_addr = ADDR_UNSET,
2182         .radio_addr = ADDR_UNSET,
2183     },
2184     [CX88_BOARD_WINFAST_DTV1800H] = {
2185         .name           = "Leadtek WinFast DTV1800 Hybrid",
2186         .tuner_type     = TUNER_XC2028,
2187         .radio_type     = UNSET,
2188         .tuner_addr     = 0x61,
2189         .radio_addr     = ADDR_UNSET,
2190         /*
2191          * GPIO setting
2192          *
2193          *  2: mute (0=off,1=on)
2194          * 12: tuner reset pin
2195          * 13: audio source (0=tuner audio,1=line in)
2196          * 14: FM (0=on,1=off ???)
2197          */
2198         .input          = { {
2199             .type   = CX88_VMUX_TELEVISION,
2200             .vmux   = 0,
2201             .gpio0  = 0x0400,       /* pin 2 = 0 */
2202             .gpio1  = 0x6040,       /* pin 13 = 0, pin 14 = 1 */
2203             .gpio2  = 0x0000,
2204         }, {
2205             .type   = CX88_VMUX_COMPOSITE1,
2206             .vmux   = 1,
2207             .gpio0  = 0x0400,       /* pin 2 = 0 */
2208             .gpio1  = 0x6060,       /* pin 13 = 1, pin 14 = 1 */
2209             .gpio2  = 0x0000,
2210         }, {
2211             .type   = CX88_VMUX_SVIDEO,
2212             .vmux   = 2,
2213             .gpio0  = 0x0400,       /* pin 2 = 0 */
2214             .gpio1  = 0x6060,       /* pin 13 = 1, pin 14 = 1 */
2215             .gpio2  = 0x0000,
2216         } },
2217         .radio = {
2218             .type   = CX88_RADIO,
2219             .gpio0  = 0x0400,       /* pin 2 = 0 */
2220             .gpio1  = 0x6000,       /* pin 13 = 0, pin 14 = 0 */
2221             .gpio2  = 0x0000,
2222         },
2223         .mpeg           = CX88_MPEG_DVB,
2224     },
2225     [CX88_BOARD_WINFAST_DTV1800H_XC4000] = {
2226         .name       = "Leadtek WinFast DTV1800 H (XC4000)",
2227         .tuner_type = TUNER_XC4000,
2228         .radio_type = UNSET,
2229         .tuner_addr = 0x61,
2230         .radio_addr = ADDR_UNSET,
2231         /*
2232          * GPIO setting
2233          *
2234          *  2: mute (0=off,1=on)
2235          * 12: tuner reset pin
2236          * 13: audio source (0=tuner audio,1=line in)
2237          * 14: FM (0=on,1=off ???)
2238          */
2239         .input      = { {
2240             .type   = CX88_VMUX_TELEVISION,
2241             .vmux   = 0,
2242             .gpio0  = 0x0400,   /* pin 2 = 0 */
2243             .gpio1  = 0x6040,   /* pin 13 = 0, pin 14 = 1 */
2244             .gpio2  = 0x0000,
2245         }, {
2246             .type   = CX88_VMUX_COMPOSITE1,
2247             .vmux   = 1,
2248             .gpio0  = 0x0400,   /* pin 2 = 0 */
2249             .gpio1  = 0x6060,   /* pin 13 = 1, pin 14 = 1 */
2250             .gpio2  = 0x0000,
2251         }, {
2252             .type   = CX88_VMUX_SVIDEO,
2253             .vmux   = 2,
2254             .gpio0  = 0x0400,   /* pin 2 = 0 */
2255             .gpio1  = 0x6060,   /* pin 13 = 1, pin 14 = 1 */
2256             .gpio2  = 0x0000,
2257         } },
2258         .radio = {
2259             .type   = CX88_RADIO,
2260             .gpio0  = 0x0400,   /* pin 2 = 0 */
2261             .gpio1  = 0x6000,   /* pin 13 = 0, pin 14 = 0 */
2262             .gpio2  = 0x0000,
2263         },
2264         .mpeg       = CX88_MPEG_DVB,
2265     },
2266     [CX88_BOARD_WINFAST_DTV2000H_PLUS] = {
2267         .name       = "Leadtek WinFast DTV2000 H PLUS",
2268         .tuner_type = TUNER_XC4000,
2269         .radio_type = UNSET,
2270         .tuner_addr = 0x61,
2271         .radio_addr = ADDR_UNSET,
2272         /*
2273          * GPIO
2274          *   2: 1: mute audio
2275          *  12: 0: reset XC4000
2276          *  13: 1: audio input is line in (0: tuner)
2277          *  14: 0: FM radio
2278          *  16: 0: RF input is cable
2279          */
2280         .input      = { {
2281             .type   = CX88_VMUX_TELEVISION,
2282             .vmux   = 0,
2283             .gpio0  = 0x0403,
2284             .gpio1  = 0xF0D7,
2285             .gpio2  = 0x0101,
2286             .gpio3  = 0x0000,
2287         }, {
2288             .type   = CX88_VMUX_CABLE,
2289             .vmux   = 0,
2290             .gpio0  = 0x0403,
2291             .gpio1  = 0xF0D7,
2292             .gpio2  = 0x0100,
2293             .gpio3  = 0x0000,
2294         }, {
2295             .type   = CX88_VMUX_COMPOSITE1,
2296             .vmux   = 1,
2297             .gpio0  = 0x0403,   /* was 0x0407 */
2298             .gpio1  = 0xF0F7,
2299             .gpio2  = 0x0101,
2300             .gpio3  = 0x0000,
2301         }, {
2302             .type   = CX88_VMUX_SVIDEO,
2303             .vmux   = 2,
2304             .gpio0  = 0x0403,   /* was 0x0407 */
2305             .gpio1  = 0xF0F7,
2306             .gpio2  = 0x0101,
2307             .gpio3  = 0x0000,
2308         } },
2309         .radio = {
2310             .type   = CX88_RADIO,
2311             .gpio0  = 0x0403,
2312             .gpio1  = 0xF097,
2313             .gpio2  = 0x0100,
2314             .gpio3  = 0x0000,
2315         },
2316         .mpeg       = CX88_MPEG_DVB,
2317     },
2318     [CX88_BOARD_PROF_7301] = {
2319         .name           = "Prof 7301 DVB-S/S2",
2320         .tuner_type     = UNSET,
2321         .radio_type     = UNSET,
2322         .tuner_addr     = ADDR_UNSET,
2323         .radio_addr     = ADDR_UNSET,
2324         .input          = { {
2325             .type   = CX88_VMUX_DVB,
2326             .vmux   = 0,
2327         } },
2328         .mpeg           = CX88_MPEG_DVB,
2329     },
2330     [CX88_BOARD_TWINHAN_VP1027_DVBS] = {
2331         .name       = "Twinhan VP-1027 DVB-S",
2332         .tuner_type     = UNSET,
2333         .radio_type     = UNSET,
2334         .tuner_addr     = ADDR_UNSET,
2335         .radio_addr     = ADDR_UNSET,
2336         .input          = { {
2337                .type   = CX88_VMUX_DVB,
2338                .vmux   = 0,
2339         } },
2340         .mpeg           = CX88_MPEG_DVB,
2341     },
2342 };
2343 
2344 /* ------------------------------------------------------------------ */
2345 /* PCI subsystem IDs                                                  */
2346 
2347 static const struct cx88_subid cx88_subids[] = {
2348     {
2349         .subvendor = 0x0070,
2350         .subdevice = 0x3400,
2351         .card      = CX88_BOARD_HAUPPAUGE,
2352     }, {
2353         .subvendor = 0x0070,
2354         .subdevice = 0x3401,
2355         .card      = CX88_BOARD_HAUPPAUGE,
2356     }, {
2357         .subvendor = 0x14c7,
2358         .subdevice = 0x0106,
2359         .card      = CX88_BOARD_GDI,
2360     }, {
2361         .subvendor = 0x14c7,
2362         .subdevice = 0x0107, /* with mpeg encoder */
2363         .card      = CX88_BOARD_GDI,
2364     }, {
2365         .subvendor = PCI_VENDOR_ID_ATI,
2366         .subdevice = 0x00f8,
2367         .card      = CX88_BOARD_ATI_WONDER_PRO,
2368     }, {
2369         .subvendor = PCI_VENDOR_ID_ATI,
2370         .subdevice = 0x00f9,
2371         .card      = CX88_BOARD_ATI_WONDER_PRO,
2372     }, {
2373         .subvendor = 0x107d,
2374         .subdevice = 0x6611,
2375         .card      = CX88_BOARD_WINFAST2000XP_EXPERT,
2376     }, {
2377         .subvendor = 0x107d,
2378         .subdevice = 0x6613,    /* NTSC */
2379         .card      = CX88_BOARD_WINFAST2000XP_EXPERT,
2380     }, {
2381         .subvendor = 0x107d,
2382         .subdevice = 0x6620,
2383         .card      = CX88_BOARD_WINFAST_DV2000,
2384     }, {
2385         .subvendor = 0x107d,
2386         .subdevice = 0x663b,
2387         .card      = CX88_BOARD_LEADTEK_PVR2000,
2388     }, {
2389         .subvendor = 0x107d,
2390         .subdevice = 0x663c,
2391         .card      = CX88_BOARD_LEADTEK_PVR2000,
2392     }, {
2393         .subvendor = 0x1461,
2394         .subdevice = 0x000b,
2395         .card      = CX88_BOARD_AVERTV_STUDIO_303,
2396     }, {
2397         .subvendor = 0x1462,
2398         .subdevice = 0x8606,
2399         .card      = CX88_BOARD_MSI_TVANYWHERE_MASTER,
2400     }, {
2401         .subvendor = 0x10fc,
2402         .subdevice = 0xd003,
2403         .card      = CX88_BOARD_IODATA_GVVCP3PCI,
2404     }, {
2405         .subvendor = 0x1043,
2406         .subdevice = 0x4823,  /* with mpeg encoder */
2407         .card      = CX88_BOARD_ASUS_PVR_416,
2408     }, {
2409         .subvendor = 0x17de,
2410         .subdevice = 0x08a6,
2411         .card      = CX88_BOARD_KWORLD_DVB_T,
2412     }, {
2413         .subvendor = 0x18ac,
2414         .subdevice = 0xd810,
2415         .card      = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q,
2416     }, {
2417         .subvendor = 0x18ac,
2418         .subdevice = 0xd820,
2419         .card      = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_T,
2420     }, {
2421         .subvendor = 0x18ac,
2422         .subdevice = 0xdb00,
2423         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T1,
2424     }, {
2425         .subvendor = 0x0070,
2426         .subdevice = 0x9002,
2427         .card      = CX88_BOARD_HAUPPAUGE_DVB_T1,
2428     }, {
2429         .subvendor = 0x14f1,
2430         .subdevice = 0x0187,
2431         .card      = CX88_BOARD_CONEXANT_DVB_T1,
2432     }, {
2433         .subvendor = 0x1540,
2434         .subdevice = 0x2580,
2435         .card      = CX88_BOARD_PROVIDEO_PV259,
2436     }, {
2437         .subvendor = 0x18ac,
2438         .subdevice = 0xdb10,
2439         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS,
2440     }, {
2441         .subvendor = 0x1554,
2442         .subdevice = 0x4811,
2443         .card      = CX88_BOARD_PIXELVIEW,
2444     }, {
2445         .subvendor = 0x7063,
2446         .subdevice = 0x3000, /* HD-3000 card */
2447         .card      = CX88_BOARD_PCHDTV_HD3000,
2448     }, {
2449         .subvendor = 0x17de,
2450         .subdevice = 0xa8a6,
2451         .card      = CX88_BOARD_DNTV_LIVE_DVB_T,
2452     }, {
2453         .subvendor = 0x0070,
2454         .subdevice = 0x2801,
2455         .card      = CX88_BOARD_HAUPPAUGE_ROSLYN,
2456     }, {
2457         .subvendor = 0x14f1,
2458         .subdevice = 0x0342,
2459         .card      = CX88_BOARD_DIGITALLOGIC_MEC,
2460     }, {
2461         .subvendor = 0x10fc,
2462         .subdevice = 0xd035,
2463         .card      = CX88_BOARD_IODATA_GVBCTV7E,
2464     }, {
2465         .subvendor = 0x1421,
2466         .subdevice = 0x0334,
2467         .card      = CX88_BOARD_ADSTECH_DVB_T_PCI,
2468     }, {
2469         .subvendor = 0x153b,
2470         .subdevice = 0x1166,
2471         .card      = CX88_BOARD_TERRATEC_CINERGY_1400_DVB_T1,
2472     }, {
2473         .subvendor = 0x18ac,
2474         .subdevice = 0xd500,
2475         .card      = CX88_BOARD_DVICO_FUSIONHDTV_5_GOLD,
2476     }, {
2477         .subvendor = 0x1461,
2478         .subdevice = 0x8011,
2479         .card      = CX88_BOARD_AVERMEDIA_ULTRATV_MC_550,
2480     }, {
2481         .subvendor = PCI_VENDOR_ID_ATI,
2482         .subdevice = 0xa101,
2483         .card      = CX88_BOARD_ATI_HDTVWONDER,
2484     }, {
2485         .subvendor = 0x107d,
2486         .subdevice = 0x665f,
2487         .card      = CX88_BOARD_WINFAST_DTV1000,
2488     }, {
2489         .subvendor = 0x1461,
2490         .subdevice = 0x000a,
2491         .card      = CX88_BOARD_AVERTV_303,
2492     }, {
2493         .subvendor = 0x0070,
2494         .subdevice = 0x9200,
2495         .card      = CX88_BOARD_HAUPPAUGE_NOVASE2_S1,
2496     }, {
2497         .subvendor = 0x0070,
2498         .subdevice = 0x9201,
2499         .card      = CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1,
2500     }, {
2501         .subvendor = 0x0070,
2502         .subdevice = 0x9202,
2503         .card      = CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1,
2504     }, {
2505         .subvendor = 0x17de,
2506         .subdevice = 0x08b2,
2507         .card      = CX88_BOARD_KWORLD_DVBS_100,
2508     }, {
2509         .subvendor = 0x0070,
2510         .subdevice = 0x9400,
2511         .card      = CX88_BOARD_HAUPPAUGE_HVR1100,
2512     }, {
2513         .subvendor = 0x0070,
2514         .subdevice = 0x9402,
2515         .card      = CX88_BOARD_HAUPPAUGE_HVR1100,
2516     }, {
2517         .subvendor = 0x0070,
2518         .subdevice = 0x9800,
2519         .card      = CX88_BOARD_HAUPPAUGE_HVR1100LP,
2520     }, {
2521         .subvendor = 0x0070,
2522         .subdevice = 0x9802,
2523         .card      = CX88_BOARD_HAUPPAUGE_HVR1100LP,
2524     }, {
2525         .subvendor = 0x0070,
2526         .subdevice = 0x9001,
2527         .card      = CX88_BOARD_HAUPPAUGE_DVB_T1,
2528     }, {
2529         .subvendor = 0x1822,
2530         .subdevice = 0x0025,
2531         .card      = CX88_BOARD_DNTV_LIVE_DVB_T_PRO,
2532     }, {
2533         .subvendor = 0x17de,
2534         .subdevice = 0x08a1,
2535         .card      = CX88_BOARD_KWORLD_DVB_T_CX22702,
2536     }, {
2537         .subvendor = 0x18ac,
2538         .subdevice = 0xdb50,
2539         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL,
2540     }, {
2541         .subvendor = 0x18ac,
2542         .subdevice = 0xdb54,
2543         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL,
2544         /* Re-branded DViCO: DigitalNow DVB-T Dual */
2545     }, {
2546         .subvendor = 0x18ac,
2547         .subdevice = 0xdb11,
2548         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS,
2549         /* Re-branded DViCO: UltraView DVB-T Plus */
2550     }, {
2551         .subvendor = 0x18ac,
2552         .subdevice = 0xdb30,
2553         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO,
2554     }, {
2555         .subvendor = 0x17de,
2556         .subdevice = 0x0840,
2557         .card      = CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT,
2558     }, {
2559         .subvendor = 0x1421,
2560         .subdevice = 0x0305,
2561         .card      = CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT,
2562     }, {
2563         .subvendor = 0x18ac,
2564         .subdevice = 0xdb40,
2565         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID,
2566     }, {
2567         .subvendor = 0x18ac,
2568         .subdevice = 0xdb44,
2569         .card      = CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID,
2570     }, {
2571         .subvendor = 0x7063,
2572         .subdevice = 0x5500,
2573         .card      = CX88_BOARD_PCHDTV_HD5500,
2574     }, {
2575         .subvendor = 0x17de,
2576         .subdevice = 0x0841,
2577         .card      = CX88_BOARD_KWORLD_MCE200_DELUXE,
2578     }, {
2579         .subvendor = 0x1822,
2580         .subdevice = 0x0019,
2581         .card      = CX88_BOARD_DNTV_LIVE_DVB_T_PRO,
2582     }, {
2583         .subvendor = 0x1554,
2584         .subdevice = 0x4813,
2585         .card      = CX88_BOARD_PIXELVIEW_PLAYTV_P7000,
2586     }, {
2587         .subvendor = 0x14f1,
2588         .subdevice = 0x0842,
2589         .card      = CX88_BOARD_NPGTECH_REALTV_TOP10FM,
2590     }, {
2591         .subvendor = 0x107d,
2592         .subdevice = 0x665e,
2593         .card      = CX88_BOARD_WINFAST_DTV2000H,
2594     }, {
2595         .subvendor = 0x107d,
2596         .subdevice = 0x6f2b,
2597         .card      = CX88_BOARD_WINFAST_DTV2000H_J,
2598     }, {
2599         .subvendor = 0x18ac,
2600         .subdevice = 0xd800, /* FusionHDTV 3 Gold (original revision) */
2601         .card      = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q,
2602     }, {
2603         .subvendor = 0x14f1,
2604         .subdevice = 0x0084,
2605         .card      = CX88_BOARD_GENIATECH_DVBS,
2606     }, {
2607         .subvendor = 0x0070,
2608         .subdevice = 0x1404,
2609         .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2610     }, {
2611         .subvendor = 0x18ac,
2612         .subdevice = 0xdc00,
2613         .card      = CX88_BOARD_SAMSUNG_SMT_7020,
2614     }, {
2615         .subvendor = 0x18ac,
2616         .subdevice = 0xdccd,
2617         .card      = CX88_BOARD_SAMSUNG_SMT_7020,
2618     }, {
2619         .subvendor = 0x1461,
2620         .subdevice = 0xc111, /* AverMedia M150-D */
2621         /* This board is known to work with the ASUS PVR416 config */
2622         .card      = CX88_BOARD_ASUS_PVR_416,
2623     }, {
2624         .subvendor = 0xc180,
2625         .subdevice = 0xc980,
2626         .card      = CX88_BOARD_TE_DTV_250_OEM_SWANN,
2627     }, {
2628         .subvendor = 0x0070,
2629         .subdevice = 0x9600,
2630         .card      = CX88_BOARD_HAUPPAUGE_HVR1300,
2631     }, {
2632         .subvendor = 0x0070,
2633         .subdevice = 0x9601,
2634         .card      = CX88_BOARD_HAUPPAUGE_HVR1300,
2635     }, {
2636         .subvendor = 0x0070,
2637         .subdevice = 0x9602,
2638         .card      = CX88_BOARD_HAUPPAUGE_HVR1300,
2639     }, {
2640         .subvendor = 0x107d,
2641         .subdevice = 0x6632,
2642         .card      = CX88_BOARD_LEADTEK_PVR2000,
2643     }, {
2644         .subvendor = 0x12ab,
2645         .subdevice = 0x2300, /* Club3D Zap TV2100 */
2646         .card      = CX88_BOARD_KWORLD_DVB_T_CX22702,
2647     }, {
2648         .subvendor = 0x0070,
2649         .subdevice = 0x9000,
2650         .card      = CX88_BOARD_HAUPPAUGE_DVB_T1,
2651     }, {
2652         .subvendor = 0x0070,
2653         .subdevice = 0x1400,
2654         .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2655     }, {
2656         .subvendor = 0x0070,
2657         .subdevice = 0x1401,
2658         .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2659     }, {
2660         .subvendor = 0x0070,
2661         .subdevice = 0x1402,
2662         .card      = CX88_BOARD_HAUPPAUGE_HVR3000,
2663     }, {
2664         .subvendor = 0x1421,
2665         .subdevice = 0x0341, /* ADS Tech InstantTV DVB-S */
2666         .card      = CX88_BOARD_KWORLD_DVBS_100,
2667     }, {
2668         .subvendor = 0x1421,
2669         .subdevice = 0x0390,
2670         .card      = CX88_BOARD_ADSTECH_PTV_390,
2671     }, {
2672         .subvendor = 0x11bd,
2673         .subdevice = 0x0051,
2674         .card      = CX88_BOARD_PINNACLE_PCTV_HD_800i,
2675     }, {
2676         .subvendor = 0x18ac,
2677         .subdevice = 0xd530,
2678         .card      = CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO,
2679     }, {
2680         .subvendor = 0x12ab,
2681         .subdevice = 0x1788,
2682         .card      = CX88_BOARD_PINNACLE_HYBRID_PCTV,
2683     }, {
2684         .subvendor = 0x14f1,
2685         .subdevice = 0xea3d,
2686         .card      = CX88_BOARD_POWERCOLOR_REAL_ANGEL,
2687     }, {
2688         .subvendor = 0x107d,
2689         .subdevice = 0x6f18,
2690         .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL,
2691     }, {
2692         /* Also NotOnlyTV LV3H (version 1.11 is silkscreened on the board) */
2693         .subvendor = 0x14f1,
2694         .subdevice = 0x8852,
2695         .card      = CX88_BOARD_GENIATECH_X8000_MT,
2696     }, {
2697         .subvendor = 0x18ac,
2698         .subdevice = 0xd610,
2699         .card      = CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD,
2700     }, {
2701         .subvendor = 0x1554,
2702         .subdevice = 0x4935,
2703         .card      = CX88_BOARD_PROLINK_PV_8000GT,
2704     }, {
2705         .subvendor = 0x1554,
2706         .subdevice = 0x4976,
2707         .card      = CX88_BOARD_PROLINK_PV_GLOBAL_XTREME,
2708     }, {
2709         .subvendor = 0x17de,
2710         .subdevice = 0x08c1,
2711         .card      = CX88_BOARD_KWORLD_ATSC_120,
2712     }, {
2713         .subvendor = 0x0070,
2714         .subdevice = 0x6900,
2715         .card      = CX88_BOARD_HAUPPAUGE_HVR4000,
2716     }, {
2717         .subvendor = 0x0070,
2718         .subdevice = 0x6904,
2719         .card      = CX88_BOARD_HAUPPAUGE_HVR4000,
2720     }, {
2721         .subvendor = 0x0070,
2722         .subdevice = 0x6902,
2723         .card      = CX88_BOARD_HAUPPAUGE_HVR4000,
2724     }, {
2725         .subvendor = 0x0070,
2726         .subdevice = 0x6905,
2727         .card      = CX88_BOARD_HAUPPAUGE_HVR4000LITE,
2728     }, {
2729         .subvendor = 0x0070,
2730         .subdevice = 0x6906,
2731         .card      = CX88_BOARD_HAUPPAUGE_HVR4000LITE,
2732     }, {
2733         .subvendor = 0xd420,
2734         .subdevice = 0x9022,
2735         .card      = CX88_BOARD_TEVII_S420,
2736     }, {
2737         .subvendor = 0xd460,
2738         .subdevice = 0x9022,
2739         .card      = CX88_BOARD_TEVII_S460,
2740     }, {
2741         .subvendor = 0xd464,
2742         .subdevice = 0x9022,
2743         .card      = CX88_BOARD_TEVII_S464,
2744     }, {
2745         .subvendor = 0xA044,
2746         .subdevice = 0x2011,
2747         .card      = CX88_BOARD_OMICOM_SS4_PCI,
2748     }, {
2749         .subvendor = 0x8910,
2750         .subdevice = 0x8888,
2751         .card      = CX88_BOARD_TBS_8910,
2752     }, {
2753         .subvendor = 0x8920,
2754         .subdevice = 0x8888,
2755         .card      = CX88_BOARD_TBS_8920,
2756     }, {
2757         .subvendor = 0xb022,
2758         .subdevice = 0x3022,
2759         .card      = CX88_BOARD_PROF_6200,
2760     }, {
2761         .subvendor = 0xB033,
2762         .subdevice = 0x3033,
2763         .card      = CX88_BOARD_PROF_7300,
2764     }, {
2765         .subvendor = 0xb200,
2766         .subdevice = 0x4200,
2767         .card      = CX88_BOARD_SATTRADE_ST4200,
2768     }, {
2769         .subvendor = 0x153b,
2770         .subdevice = 0x1177,
2771         .card      = CX88_BOARD_TERRATEC_CINERGY_HT_PCI_MKII,
2772     }, {
2773         .subvendor = 0x0070,
2774         .subdevice = 0x9290,
2775         .card      = CX88_BOARD_HAUPPAUGE_IRONLY,
2776     }, {
2777         .subvendor = 0x107d,
2778         .subdevice = 0x6654,
2779         .card      = CX88_BOARD_WINFAST_DTV1800H,
2780     }, {
2781         /* WinFast DTV1800 H with XC4000 tuner */
2782         .subvendor = 0x107d,
2783         .subdevice = 0x6f38,
2784         .card      = CX88_BOARD_WINFAST_DTV1800H_XC4000,
2785     }, {
2786         .subvendor = 0x107d,
2787         .subdevice = 0x6f42,
2788         .card      = CX88_BOARD_WINFAST_DTV2000H_PLUS,
2789     }, {
2790         /* PVR2000 PAL Model [107d:6630] */
2791         .subvendor = 0x107d,
2792         .subdevice = 0x6630,
2793         .card      = CX88_BOARD_LEADTEK_PVR2000,
2794     }, {
2795         /* PVR2000 PAL Model [107d:6638] */
2796         .subvendor = 0x107d,
2797         .subdevice = 0x6638,
2798         .card      = CX88_BOARD_LEADTEK_PVR2000,
2799     }, {
2800         /* PVR2000 NTSC Model [107d:6631] */
2801         .subvendor = 0x107d,
2802         .subdevice = 0x6631,
2803         .card      = CX88_BOARD_LEADTEK_PVR2000,
2804     }, {
2805         /* PVR2000 NTSC Model [107d:6637] */
2806         .subvendor = 0x107d,
2807         .subdevice = 0x6637,
2808         .card      = CX88_BOARD_LEADTEK_PVR2000,
2809     }, {
2810         /* PVR2000 NTSC Model [107d:663d] */
2811         .subvendor = 0x107d,
2812         .subdevice = 0x663d,
2813         .card      = CX88_BOARD_LEADTEK_PVR2000,
2814     }, {
2815         /* DV2000 NTSC Model [107d:6621] */
2816         .subvendor = 0x107d,
2817         .subdevice = 0x6621,
2818         .card      = CX88_BOARD_WINFAST_DV2000,
2819     }, {
2820         /* TV2000 XP Global [107d:6618]  */
2821         .subvendor = 0x107d,
2822         .subdevice = 0x6618,
2823         .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL,
2824     }, {
2825         /* TV2000 XP Global [107d:6618] */
2826         .subvendor = 0x107d,
2827         .subdevice = 0x6619,
2828         .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL,
2829     }, {
2830         /* WinFast TV2000 XP Global with XC4000 tuner */
2831         .subvendor = 0x107d,
2832         .subdevice = 0x6f36,
2833         .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36,
2834     }, {
2835         /* WinFast TV2000 XP Global with XC4000 tuner and different GPIOs */
2836         .subvendor = 0x107d,
2837         .subdevice = 0x6f43,
2838         .card      = CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43,
2839     }, {
2840         .subvendor = 0xb034,
2841         .subdevice = 0x3034,
2842         .card      = CX88_BOARD_PROF_7301,
2843     }, {
2844         .subvendor = 0x1822,
2845         .subdevice = 0x0023,
2846         .card      = CX88_BOARD_TWINHAN_VP1027_DVBS,
2847     },
2848 };
2849 
2850 /*
2851  * some leadtek specific stuff
2852  */
2853 static void leadtek_eeprom(struct cx88_core *core, u8 *eeprom_data)
2854 {
2855     if (eeprom_data[4] != 0x7d ||
2856         eeprom_data[5] != 0x10 ||
2857         eeprom_data[7] != 0x66) {
2858         pr_warn("Leadtek eeprom invalid.\n");
2859         return;
2860     }
2861 
2862     /* Terry Wu <terrywu2009@gmail.com> */
2863     switch (eeprom_data[6]) {
2864     case 0x13: /* SSID 6613 for TV2000 XP Expert NTSC Model */
2865     case 0x21: /* SSID 6621 for DV2000 NTSC Model */
2866     case 0x31: /* SSID 6631 for PVR2000 NTSC Model */
2867     case 0x37: /* SSID 6637 for PVR2000 NTSC Model */
2868     case 0x3d: /* SSID 6637 for PVR2000 NTSC Model */
2869         core->board.tuner_type = TUNER_PHILIPS_FM1236_MK3;
2870         break;
2871     default:
2872         core->board.tuner_type = TUNER_PHILIPS_FM1216ME_MK3;
2873         break;
2874     }
2875 
2876     pr_info("Leadtek Winfast 2000XP Expert config: tuner=%d, eeprom[0]=0x%02x\n",
2877         core->board.tuner_type, eeprom_data[0]);
2878 }
2879 
2880 static void hauppauge_eeprom(struct cx88_core *core, u8 *eeprom_data)
2881 {
2882     struct tveeprom tv;
2883 
2884     tveeprom_hauppauge_analog(&tv, eeprom_data);
2885     core->board.tuner_type = tv.tuner_type;
2886     core->tuner_formats = tv.tuner_formats;
2887     core->board.radio.type = tv.has_radio ? CX88_RADIO : 0;
2888     core->model = tv.model;
2889 
2890     /* Make sure we support the board model */
2891     switch (tv.model) {
2892     case 14009: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in) */
2893     case 14019: /* WinTV-HVR3000 (Retail, IR Blaster, b/panel video, 3.5mm audio in) */
2894     case 14029: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in - 880 bridge) */
2895     case 14109: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in - low profile) */
2896     case 14129: /* WinTV-HVR3000 (Retail, IR, b/panel video, 3.5mm audio in - 880 bridge - LP) */
2897     case 14559: /* WinTV-HVR3000 (OEM, no IR, b/panel video, 3.5mm audio in) */
2898     case 14569: /* WinTV-HVR3000 (OEM, no IR, no back panel video) */
2899     case 14659: /* WinTV-HVR3000 (OEM, no IR, b/panel video, RCA audio in - Low profile) */
2900     case 14669: /* WinTV-HVR3000 (OEM, no IR, no b/panel video - Low profile) */
2901     case 28552: /* WinTV-PVR 'Roslyn' (No IR) */
2902     case 34519: /* WinTV-PCI-FM */
2903     case 69009:
2904         /* WinTV-HVR4000 (DVBS/S2/T, Video and IR, back panel inputs) */
2905     case 69100: /* WinTV-HVR4000LITE (DVBS/S2, IR) */
2906     case 69500: /* WinTV-HVR4000LITE (DVBS/S2, No IR) */
2907     case 69559:
2908         /* WinTV-HVR4000 (DVBS/S2/T, Video no IR, back panel inputs) */
2909     case 69569: /* WinTV-HVR4000 (DVBS/S2/T, Video no IR) */
2910     case 90002: /* Nova-T-PCI (9002) */
2911     case 92001: /* Nova-S-Plus (Video and IR) */
2912     case 92002: /* Nova-S-Plus (Video and IR) */
2913     case 90003: /* Nova-T-PCI (9002 No RF out) */
2914     case 90500: /* Nova-T-PCI (oem) */
2915     case 90501: /* Nova-T-PCI (oem/IR) */
2916     case 92000: /* Nova-SE2 (OEM, No Video or IR) */
2917     case 92900: /* WinTV-IROnly (No analog or digital Video inputs) */
2918     case 94009: /* WinTV-HVR1100 (Video and IR Retail) */
2919     case 94501: /* WinTV-HVR1100 (Video and IR OEM) */
2920     case 96009: /* WinTV-HVR1300 (PAL Video, MPEG Video and IR RX) */
2921     case 96019: /* WinTV-HVR1300 (PAL Video, MPEG Video and IR RX/TX) */
2922     case 96559: /* WinTV-HVR1300 (PAL Video, MPEG Video no IR) */
2923     case 96569: /* WinTV-HVR1300 () */
2924     case 96659: /* WinTV-HVR1300 () */
2925     case 98559: /* WinTV-HVR1100LP (Video no IR, Retail - Low Profile) */
2926         /* known */
2927         break;
2928     case CX88_BOARD_SAMSUNG_SMT_7020:
2929         cx_set(MO_GP0_IO, 0x008989FF);
2930         break;
2931     default:
2932         pr_warn("warning: unknown hauppauge model #%d\n", tv.model);
2933         break;
2934     }
2935 
2936     pr_info("hauppauge eeprom: model=%d\n", tv.model);
2937 }
2938 
2939 /*
2940  * some GDI (was: Modular Technology) specific stuff
2941  */
2942 
2943 static const struct {
2944     int  id;
2945     int  fm;
2946     const char *name;
2947 } gdi_tuner[] = {
2948     [0x01] = { .id   = UNSET,
2949            .name = "NTSC_M" },
2950     [0x02] = { .id   = UNSET,
2951            .name = "PAL_B" },
2952     [0x03] = { .id   = UNSET,
2953            .name = "PAL_I" },
2954     [0x04] = { .id   = UNSET,
2955            .name = "PAL_D" },
2956     [0x05] = { .id   = UNSET,
2957            .name = "SECAM" },
2958 
2959     [0x10] = { .id   = UNSET,
2960            .fm   = 1,
2961            .name = "TEMIC_4049" },
2962     [0x11] = { .id   = TUNER_TEMIC_4136FY5,
2963            .name = "TEMIC_4136" },
2964     [0x12] = { .id   = UNSET,
2965            .name = "TEMIC_4146" },
2966 
2967     [0x20] = { .id   = TUNER_PHILIPS_FQ1216ME,
2968            .fm   = 1,
2969            .name = "PHILIPS_FQ1216_MK3" },
2970     [0x21] = { .id   = UNSET, .fm = 1,
2971            .name = "PHILIPS_FQ1236_MK3" },
2972     [0x22] = { .id   = UNSET,
2973            .name = "PHILIPS_FI1236_MK3" },
2974     [0x23] = { .id   = UNSET,
2975            .name = "PHILIPS_FI1216_MK3" },
2976 };
2977 
2978 static void gdi_eeprom(struct cx88_core *core, u8 *eeprom_data)
2979 {
2980     const char *name = (eeprom_data[0x0d] < ARRAY_SIZE(gdi_tuner))
2981         ? gdi_tuner[eeprom_data[0x0d]].name : NULL;
2982 
2983     pr_info("GDI: tuner=%s\n", name ? name : "unknown");
2984     if (!name)
2985         return;
2986     core->board.tuner_type = gdi_tuner[eeprom_data[0x0d]].id;
2987     core->board.radio.type = gdi_tuner[eeprom_data[0x0d]].fm ?
2988         CX88_RADIO : 0;
2989 }
2990 
2991 /*
2992  * some Divco specific stuff
2993  */
2994 static int cx88_dvico_xc2028_callback(struct cx88_core *core,
2995                       int command, int arg)
2996 {
2997     switch (command) {
2998     case XC2028_TUNER_RESET:
2999         switch (core->boardnr) {
3000         case CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO:
3001             /* GPIO-4 xc3028 tuner */
3002 
3003             cx_set(MO_GP0_IO, 0x00001000);
3004             cx_clear(MO_GP0_IO, 0x00000010);
3005             msleep(100);
3006             cx_set(MO_GP0_IO, 0x00000010);
3007             msleep(100);
3008             break;
3009         default:
3010             cx_write(MO_GP0_IO, 0x101000);
3011             mdelay(5);
3012             cx_set(MO_GP0_IO, 0x101010);
3013         }
3014         break;
3015     default:
3016         return -EINVAL;
3017     }
3018 
3019     return 0;
3020 }
3021 
3022 /*
3023  * some Geniatech specific stuff
3024  */
3025 
3026 static int cx88_xc3028_geniatech_tuner_callback(struct cx88_core *core,
3027                         int command, int mode)
3028 {
3029     switch (command) {
3030     case XC2028_TUNER_RESET:
3031         switch (INPUT(core->input).type) {
3032         case CX88_RADIO:
3033             break;
3034         case CX88_VMUX_DVB:
3035             cx_write(MO_GP1_IO, 0x030302);
3036             mdelay(50);
3037             break;
3038         default:
3039             cx_write(MO_GP1_IO, 0x030301);
3040             mdelay(50);
3041         }
3042         cx_write(MO_GP1_IO, 0x101010);
3043         mdelay(50);
3044         cx_write(MO_GP1_IO, 0x101000);
3045         mdelay(50);
3046         cx_write(MO_GP1_IO, 0x101010);
3047         mdelay(50);
3048         return 0;
3049     }
3050     return -EINVAL;
3051 }
3052 
3053 static int cx88_xc3028_winfast1800h_callback(struct cx88_core *core,
3054                          int command, int arg)
3055 {
3056     switch (command) {
3057     case XC2028_TUNER_RESET:
3058         /* GPIO 12 (xc3028 tuner reset) */
3059         cx_set(MO_GP1_IO, 0x1010);
3060         mdelay(50);
3061         cx_clear(MO_GP1_IO, 0x10);
3062         mdelay(75);
3063         cx_set(MO_GP1_IO, 0x10);
3064         mdelay(75);
3065         return 0;
3066     }
3067     return -EINVAL;
3068 }
3069 
3070 static int cx88_xc4000_winfast2000h_plus_callback(struct cx88_core *core,
3071                           int command, int arg)
3072 {
3073     switch (command) {
3074     case XC4000_TUNER_RESET:
3075         /* GPIO 12 (xc4000 tuner reset) */
3076         cx_set(MO_GP1_IO, 0x1010);
3077         mdelay(50);
3078         cx_clear(MO_GP1_IO, 0x10);
3079         mdelay(75);
3080         cx_set(MO_GP1_IO, 0x10);
3081         mdelay(75);
3082         return 0;
3083     }
3084     return -EINVAL;
3085 }
3086 
3087 /*
3088  * some Divco specific stuff
3089  */
3090 static int cx88_pv_8000gt_callback(struct cx88_core *core,
3091                    int command, int arg)
3092 {
3093     switch (command) {
3094     case XC2028_TUNER_RESET:
3095         cx_write(MO_GP2_IO, 0xcf7);
3096         mdelay(50);
3097         cx_write(MO_GP2_IO, 0xef5);
3098         mdelay(50);
3099         cx_write(MO_GP2_IO, 0xcf7);
3100         break;
3101     default:
3102         return -EINVAL;
3103     }
3104 
3105     return 0;
3106 }
3107 
3108 /*
3109  * some DViCO specific stuff
3110  */
3111 
3112 static void dvico_fusionhdtv_hybrid_init(struct cx88_core *core)
3113 {
3114     struct i2c_msg msg = { .addr = 0x45, .flags = 0 };
3115     int i, err;
3116     static u8 init_bufs[13][5] = {
3117         { 0x10, 0x00, 0x20, 0x01, 0x03 },
3118         { 0x10, 0x10, 0x01, 0x00, 0x21 },
3119         { 0x10, 0x10, 0x10, 0x00, 0xCA },
3120         { 0x10, 0x10, 0x12, 0x00, 0x08 },
3121         { 0x10, 0x10, 0x13, 0x00, 0x0A },
3122         { 0x10, 0x10, 0x16, 0x01, 0xC0 },
3123         { 0x10, 0x10, 0x22, 0x01, 0x3D },
3124         { 0x10, 0x10, 0x73, 0x01, 0x2E },
3125         { 0x10, 0x10, 0x72, 0x00, 0xC5 },
3126         { 0x10, 0x10, 0x71, 0x01, 0x97 },
3127         { 0x10, 0x10, 0x70, 0x00, 0x0F },
3128         { 0x10, 0x10, 0xB0, 0x00, 0x01 },
3129         { 0x03, 0x0C },
3130     };
3131 
3132     for (i = 0; i < ARRAY_SIZE(init_bufs); i++) {
3133         msg.buf = init_bufs[i];
3134         msg.len = (i != 12 ? 5 : 2);
3135         err = i2c_transfer(&core->i2c_adap, &msg, 1);
3136         if (err != 1) {
3137             pr_warn("dvico_fusionhdtv_hybrid_init buf %d failed (err = %d)!\n",
3138                 i, err);
3139             return;
3140         }
3141     }
3142 }
3143 
3144 static int cx88_xc2028_tuner_callback(struct cx88_core *core,
3145                       int command, int arg)
3146 {
3147     /* Board-specific callbacks */
3148     switch (core->boardnr) {
3149     case CX88_BOARD_POWERCOLOR_REAL_ANGEL:
3150     case CX88_BOARD_GENIATECH_X8000_MT:
3151     case CX88_BOARD_KWORLD_ATSC_120:
3152         return cx88_xc3028_geniatech_tuner_callback(core,
3153                             command, arg);
3154     case CX88_BOARD_PROLINK_PV_8000GT:
3155     case CX88_BOARD_PROLINK_PV_GLOBAL_XTREME:
3156         return cx88_pv_8000gt_callback(core, command, arg);
3157     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO:
3158     case CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO:
3159         return cx88_dvico_xc2028_callback(core, command, arg);
3160     case CX88_BOARD_NOTONLYTV_LV3H:
3161     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL:
3162     case CX88_BOARD_WINFAST_DTV1800H:
3163         return cx88_xc3028_winfast1800h_callback(core, command, arg);
3164     }
3165 
3166     switch (command) {
3167     case XC2028_TUNER_RESET:
3168         switch (INPUT(core->input).type) {
3169         case CX88_RADIO:
3170             dprintk(1, "setting GPIO to radio!\n");
3171             cx_write(MO_GP0_IO, 0x4ff);
3172             mdelay(250);
3173             cx_write(MO_GP2_IO, 0xff);
3174             mdelay(250);
3175             break;
3176         case CX88_VMUX_DVB: /* Digital TV*/
3177         default:        /* Analog TV */
3178             dprintk(1, "setting GPIO to TV!\n");
3179             break;
3180         }
3181         cx_write(MO_GP1_IO, 0x101010);
3182         mdelay(250);
3183         cx_write(MO_GP1_IO, 0x101000);
3184         mdelay(250);
3185         cx_write(MO_GP1_IO, 0x101010);
3186         mdelay(250);
3187         return 0;
3188     }
3189     return -EINVAL;
3190 }
3191 
3192 static int cx88_xc4000_tuner_callback(struct cx88_core *core,
3193                       int command, int arg)
3194 {
3195     /* Board-specific callbacks */
3196     switch (core->boardnr) {
3197     case CX88_BOARD_WINFAST_DTV1800H_XC4000:
3198     case CX88_BOARD_WINFAST_DTV2000H_PLUS:
3199     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36:
3200     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43:
3201         return cx88_xc4000_winfast2000h_plus_callback(core,
3202                                   command, arg);
3203     }
3204     return -EINVAL;
3205 }
3206 
3207 /*
3208  * Tuner callback function. Currently only needed for the Pinnacle
3209  * PCTV HD 800i with an xc5000 silicon tuner. This is used for both
3210  * analog tuner attach (tuner-core.c) and dvb tuner attach (cx88-dvb.c)
3211  */
3212 static int cx88_xc5000_tuner_callback(struct cx88_core *core,
3213                       int command, int arg)
3214 {
3215     switch (core->boardnr) {
3216     case CX88_BOARD_PINNACLE_PCTV_HD_800i:
3217         if (command == 0) { /* This is the reset command from xc5000 */
3218 
3219             /*
3220              * djh - According to the engineer at PCTV Systems,
3221              * the xc5000 reset pin is supposed to be on GPIO12.
3222              * However, despite three nights of effort, pulling
3223              * that GPIO low didn't reset the xc5000.  While
3224              * pulling MO_SRST_IO low does reset the xc5000, this
3225              * also resets in the s5h1409 being reset as well.
3226              * This causes tuning to always fail since the internal
3227              * state of the s5h1409 does not match the driver's
3228              * state.  Given that the only two conditions in which
3229              * the driver performs a reset is during firmware load
3230              * and powering down the chip, I am taking out the
3231              * reset.  We know that the chip is being reset
3232              * when the cx88 comes online, and not being able to
3233              * do power management for this board is worse than
3234              * not having any tuning at all.
3235              */
3236             return 0;
3237         }
3238 
3239         dprintk(1, "xc5000: unknown tuner callback command.\n");
3240         return -EINVAL;
3241     case CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD:
3242         if (command == 0) { /* This is the reset command from xc5000 */
3243             cx_clear(MO_GP0_IO, 0x00000010);
3244             usleep_range(10000, 20000);
3245             cx_set(MO_GP0_IO, 0x00000010);
3246             return 0;
3247         }
3248 
3249         dprintk(1, "xc5000: unknown tuner callback command.\n");
3250         return -EINVAL;
3251     }
3252     return 0; /* Should never be here */
3253 }
3254 
3255 int cx88_tuner_callback(void *priv, int component, int command, int arg)
3256 {
3257     struct i2c_algo_bit_data *i2c_algo = priv;
3258     struct cx88_core *core;
3259 
3260     if (!i2c_algo) {
3261         pr_err("Error - i2c private data undefined.\n");
3262         return -EINVAL;
3263     }
3264 
3265     core = i2c_algo->data;
3266 
3267     if (!core) {
3268         pr_err("Error - device struct undefined.\n");
3269         return -EINVAL;
3270     }
3271 
3272     if (component != DVB_FRONTEND_COMPONENT_TUNER)
3273         return -EINVAL;
3274 
3275     switch (core->board.tuner_type) {
3276     case TUNER_XC2028:
3277         dprintk(1, "Calling XC2028/3028 callback\n");
3278         return cx88_xc2028_tuner_callback(core, command, arg);
3279     case TUNER_XC4000:
3280         dprintk(1, "Calling XC4000 callback\n");
3281         return cx88_xc4000_tuner_callback(core, command, arg);
3282     case TUNER_XC5000:
3283         dprintk(1, "Calling XC5000 callback\n");
3284         return cx88_xc5000_tuner_callback(core, command, arg);
3285     }
3286     pr_err("Error: Calling callback for tuner %d\n",
3287            core->board.tuner_type);
3288     return -EINVAL;
3289 }
3290 EXPORT_SYMBOL(cx88_tuner_callback);
3291 
3292 /* ----------------------------------------------------------------------- */
3293 
3294 static void cx88_card_list(struct cx88_core *core, struct pci_dev *pci)
3295 {
3296     int i;
3297 
3298     if (!pci->subsystem_vendor && !pci->subsystem_device) {
3299         pr_err("Your board has no valid PCI Subsystem ID and thus can't\n");
3300         pr_err("be autodetected.  Please pass card=<n> insmod option to\n");
3301         pr_err("workaround that.  Redirect complaints to the vendor of\n");
3302         pr_err("the TV card\n");
3303     } else {
3304         pr_err("Your board isn't known (yet) to the driver.  You can\n");
3305         pr_err("try to pick one of the existing card configs via\n");
3306         pr_err("card=<n> insmod option.  Updating to the latest\n");
3307         pr_err("version might help as well.\n");
3308     }
3309     pr_err("Here is a list of valid choices for the card=<n> insmod option:\n");
3310     for (i = 0; i < ARRAY_SIZE(cx88_boards); i++)
3311         pr_err("    card=%d -> %s\n", i, cx88_boards[i].name);
3312 }
3313 
3314 static void cx88_card_setup_pre_i2c(struct cx88_core *core)
3315 {
3316     switch (core->boardnr) {
3317     case CX88_BOARD_HAUPPAUGE_HVR1300:
3318         /*
3319          * Bring the 702 demod up before i2c scanning/attach or
3320          * devices are hidden.
3321          *
3322          * We leave here with the 702 on the bus
3323          *
3324          * "reset the IR receiver on GPIO[3]"
3325          * Reported by Mike Crash <mike AT mikecrash.com>
3326          */
3327         cx_write(MO_GP0_IO, 0x0000ef88);
3328         udelay(1000);
3329         cx_clear(MO_GP0_IO, 0x00000088);
3330         udelay(50);
3331         cx_set(MO_GP0_IO, 0x00000088); /* 702 out of reset */
3332         udelay(1000);
3333         break;
3334 
3335     case CX88_BOARD_PROLINK_PV_GLOBAL_XTREME:
3336     case CX88_BOARD_PROLINK_PV_8000GT:
3337         cx_write(MO_GP2_IO, 0xcf7);
3338         msleep(50);
3339         cx_write(MO_GP2_IO, 0xef5);
3340         msleep(50);
3341         cx_write(MO_GP2_IO, 0xcf7);
3342         usleep_range(10000, 20000);
3343         break;
3344 
3345     case CX88_BOARD_DVICO_FUSIONHDTV_7_GOLD:
3346         /* Enable the xc5000 tuner */
3347         cx_set(MO_GP0_IO, 0x00001010);
3348         break;
3349 
3350     case CX88_BOARD_WINFAST_DTV2000H_J:
3351     case CX88_BOARD_HAUPPAUGE_HVR3000:
3352     case CX88_BOARD_HAUPPAUGE_HVR4000:
3353         /* Init GPIO */
3354         cx_write(MO_GP0_IO, core->board.input[0].gpio0);
3355         udelay(1000);
3356         cx_clear(MO_GP0_IO, 0x00000080);
3357         udelay(50);
3358         cx_set(MO_GP0_IO, 0x00000080); /* 702 out of reset */
3359         udelay(1000);
3360         break;
3361 
3362     case CX88_BOARD_NOTONLYTV_LV3H:
3363     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL:
3364     case CX88_BOARD_WINFAST_DTV1800H:
3365         cx88_xc3028_winfast1800h_callback(core, XC2028_TUNER_RESET, 0);
3366         break;
3367 
3368     case CX88_BOARD_WINFAST_DTV1800H_XC4000:
3369     case CX88_BOARD_WINFAST_DTV2000H_PLUS:
3370     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36:
3371     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43:
3372         cx88_xc4000_winfast2000h_plus_callback(core,
3373                                XC4000_TUNER_RESET, 0);
3374         break;
3375 
3376     case CX88_BOARD_TWINHAN_VP1027_DVBS:
3377         cx_write(MO_GP0_IO, 0x00003230);
3378         cx_write(MO_GP0_IO, 0x00003210);
3379         usleep_range(10000, 20000);
3380         cx_write(MO_GP0_IO, 0x00001230);
3381         break;
3382     }
3383 }
3384 
3385 /*
3386  * Sets board-dependent xc3028 configuration
3387  */
3388 void cx88_setup_xc3028(struct cx88_core *core, struct xc2028_ctrl *ctl)
3389 {
3390     memset(ctl, 0, sizeof(*ctl));
3391 
3392     ctl->fname   = XC2028_DEFAULT_FIRMWARE;
3393     ctl->max_len = 64;
3394 
3395     switch (core->boardnr) {
3396     case CX88_BOARD_POWERCOLOR_REAL_ANGEL:
3397         /* Now works with firmware version 2.7 */
3398         if (core->i2c_algo.udelay < 16)
3399             core->i2c_algo.udelay = 16;
3400         break;
3401     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO:
3402     case CX88_BOARD_WINFAST_DTV1800H:
3403         ctl->demod = XC3028_FE_ZARLINK456;
3404         break;
3405     case CX88_BOARD_KWORLD_ATSC_120:
3406     case CX88_BOARD_DVICO_FUSIONHDTV_5_PCI_NANO:
3407         ctl->demod = XC3028_FE_OREN538;
3408         break;
3409     case CX88_BOARD_GENIATECH_X8000_MT:
3410         /*
3411          * FIXME: For this board, the xc3028 never recovers after being
3412          * powered down (the reset GPIO probably is not set properly).
3413          * We don't have access to the hardware so we cannot determine
3414          * which GPIO is used for xc3028, so just disable power xc3028
3415          * power management for now
3416          */
3417         ctl->disable_power_mgmt = 1;
3418         break;
3419     case CX88_BOARD_NOTONLYTV_LV3H:
3420         ctl->demod          = XC3028_FE_ZARLINK456;
3421         ctl->fname          = XC3028L_DEFAULT_FIRMWARE;
3422         ctl->read_not_reliable  = 1;
3423         break;
3424     case CX88_BOARD_WINFAST_TV2000_XP_GLOBAL:
3425     case CX88_BOARD_PROLINK_PV_GLOBAL_XTREME:
3426     case CX88_BOARD_PROLINK_PV_8000GT:
3427         /*
3428          * Those boards uses non-MTS firmware
3429          */
3430         break;
3431     case CX88_BOARD_PINNACLE_HYBRID_PCTV:
3432     case CX88_BOARD_TERRATEC_CINERGY_HT_PCI_MKII:
3433         ctl->demod = XC3028_FE_ZARLINK456;
3434         ctl->mts = 1;
3435         break;
3436     default:
3437         ctl->demod = XC3028_FE_OREN538;
3438         ctl->mts = 1;
3439     }
3440 }
3441 EXPORT_SYMBOL_GPL(cx88_setup_xc3028);
3442 
3443 static void cx88_card_setup(struct cx88_core *core)
3444 {
3445     static u8 eeprom[256];
3446     struct tuner_setup tun_setup;
3447     unsigned int mode_mask = T_RADIO | T_ANALOG_TV;
3448 
3449     memset(&tun_setup, 0, sizeof(tun_setup));
3450 
3451     if (!core->i2c_rc) {
3452         core->i2c_client.addr = 0xa0 >> 1;
3453         tveeprom_read(&core->i2c_client, eeprom, sizeof(eeprom));
3454     }
3455 
3456     switch (core->boardnr) {
3457     case CX88_BOARD_HAUPPAUGE:
3458     case CX88_BOARD_HAUPPAUGE_ROSLYN:
3459         if (!core->i2c_rc)
3460             hauppauge_eeprom(core, eeprom + 8);
3461         break;
3462     case CX88_BOARD_GDI:
3463         if (!core->i2c_rc)
3464             gdi_eeprom(core, eeprom);
3465         break;
3466     case CX88_BOARD_LEADTEK_PVR2000:
3467     case CX88_BOARD_WINFAST_DV2000:
3468     case CX88_BOARD_WINFAST2000XP_EXPERT:
3469         if (!core->i2c_rc)
3470             leadtek_eeprom(core, eeprom);
3471         break;
3472     case CX88_BOARD_HAUPPAUGE_NOVASPLUS_S1:
3473     case CX88_BOARD_HAUPPAUGE_NOVASE2_S1:
3474     case CX88_BOARD_HAUPPAUGE_DVB_T1:
3475     case CX88_BOARD_HAUPPAUGE_HVR1100:
3476     case CX88_BOARD_HAUPPAUGE_HVR1100LP:
3477     case CX88_BOARD_HAUPPAUGE_HVR3000:
3478     case CX88_BOARD_HAUPPAUGE_HVR1300:
3479     case CX88_BOARD_HAUPPAUGE_HVR4000:
3480     case CX88_BOARD_HAUPPAUGE_HVR4000LITE:
3481     case CX88_BOARD_HAUPPAUGE_IRONLY:
3482         if (!core->i2c_rc)
3483             hauppauge_eeprom(core, eeprom);
3484         break;
3485     case CX88_BOARD_KWORLD_DVBS_100:
3486         cx_write(MO_GP0_IO, 0x000007f8);
3487         cx_write(MO_GP1_IO, 0x00000001);
3488         break;
3489     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PRO:
3490         /* GPIO0:0 is hooked to demod reset */
3491         /* GPIO0:4 is hooked to xc3028 reset */
3492         cx_write(MO_GP0_IO, 0x00111100);
3493         usleep_range(10000, 20000);
3494         cx_write(MO_GP0_IO, 0x00111111);
3495         break;
3496     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_DUAL:
3497         /* GPIO0:6 is hooked to FX2 reset pin */
3498         cx_set(MO_GP0_IO, 0x00004040);
3499         cx_clear(MO_GP0_IO, 0x00000040);
3500         msleep(1000);
3501         cx_set(MO_GP0_IO, 0x00004040);
3502         fallthrough;
3503     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T1:
3504     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_PLUS:
3505     case CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID:
3506         /* GPIO0:0 is hooked to mt352 reset pin */
3507         cx_set(MO_GP0_IO, 0x00000101);
3508         cx_clear(MO_GP0_IO, 0x00000001);
3509         usleep_range(10000, 20000);
3510         cx_set(MO_GP0_IO, 0x00000101);
3511         if (!core->i2c_rc &&
3512             core->boardnr == CX88_BOARD_DVICO_FUSIONHDTV_DVB_T_HYBRID)
3513             dvico_fusionhdtv_hybrid_init(core);
3514         break;
3515     case CX88_BOARD_KWORLD_DVB_T:
3516     case CX88_BOARD_DNTV_LIVE_DVB_T:
3517         cx_set(MO_GP0_IO, 0x00000707);
3518         cx_set(MO_GP2_IO, 0x00000101);
3519         cx_clear(MO_GP2_IO, 0x00000001);
3520         usleep_range(10000, 20000);
3521         cx_clear(MO_GP0_IO, 0x00000007);
3522         cx_set(MO_GP2_IO, 0x00000101);
3523         break;
3524     case CX88_BOARD_DNTV_LIVE_DVB_T_PRO:
3525         cx_write(MO_GP0_IO, 0x00080808);
3526         break;
3527     case CX88_BOARD_ATI_HDTVWONDER:
3528         if (!core->i2c_rc) {
3529             /* enable tuner */
3530             int i;
3531             static const u8 buffer[][2] = {
3532                 {0x10, 0x12},
3533                 {0x13, 0x04},
3534                 {0x16, 0x00},
3535                 {0x14, 0x04},
3536                 {0x17, 0x00}
3537             };
3538             core->i2c_client.addr = 0x0a;
3539 
3540             for (i = 0; i < ARRAY_SIZE(buffer); i++)
3541                 if (i2c_master_send(&core->i2c_client,
3542                             buffer[i], 2) != 2)
3543                     pr_warn("Unable to enable tuner(%i).\n",
3544                         i);
3545         }
3546         break;
3547     case CX88_BOARD_MSI_TVANYWHERE_MASTER:
3548     {
3549         struct v4l2_priv_tun_config tea5767_cfg;
3550         struct tea5767_ctrl ctl;
3551 
3552         memset(&ctl, 0, sizeof(ctl));
3553 
3554         ctl.high_cut  = 1;
3555         ctl.st_noise  = 1;
3556         ctl.deemph_75 = 1;
3557         ctl.xtal_freq = TEA5767_HIGH_LO_13MHz;
3558 
3559         tea5767_cfg.tuner = TUNER_TEA5767;
3560         tea5767_cfg.priv  = &ctl;
3561 
3562         call_all(core, tuner, s_config, &tea5767_cfg);
3563         break;
3564     }
3565     case  CX88_BOARD_TEVII_S420:
3566     case  CX88_BOARD_TEVII_S460:
3567     case  CX88_BOARD_TEVII_S464:
3568     case  CX88_BOARD_OMICOM_SS4_PCI:
3569     case  CX88_BOARD_TBS_8910:
3570     case  CX88_BOARD_TBS_8920:
3571     case  CX88_BOARD_PROF_6200:
3572     case  CX88_BOARD_PROF_7300:
3573     case  CX88_BOARD_PROF_7301:
3574     case  CX88_BOARD_SATTRADE_ST4200:
3575         cx_write(MO_GP0_IO, 0x8000);
3576         msleep(100);
3577         cx_write(MO_SRST_IO, 0);
3578         usleep_range(10000, 20000);
3579         cx_write(MO_GP0_IO, 0x8080);
3580         msleep(100);
3581         cx_write(MO_SRST_IO, 1);
3582         msleep(100);
3583         break;
3584     } /*end switch() */
3585 
3586     /* Setup tuners */
3587     if (core->board.radio_type != UNSET) {
3588         tun_setup.mode_mask      = T_RADIO;
3589         tun_setup.type           = core->board.radio_type;
3590         tun_setup.addr           = core->board.radio_addr;
3591         tun_setup.tuner_callback = cx88_tuner_callback;
3592         call_all(core, tuner, s_type_addr, &tun_setup);
3593         mode_mask &= ~T_RADIO;
3594     }
3595 
3596     if (core->board.tuner_type != UNSET) {
3597         tun_setup.mode_mask      = mode_mask;
3598         tun_setup.type           = core->board.tuner_type;
3599         tun_setup.addr           = core->board.tuner_addr;
3600         tun_setup.tuner_callback = cx88_tuner_callback;
3601 
3602         call_all(core, tuner, s_type_addr, &tun_setup);
3603     }
3604 
3605     if (core->board.tda9887_conf) {
3606         struct v4l2_priv_tun_config tda9887_cfg;
3607 
3608         tda9887_cfg.tuner = TUNER_TDA9887;
3609         tda9887_cfg.priv  = &core->board.tda9887_conf;
3610 
3611         call_all(core, tuner, s_config, &tda9887_cfg);
3612     }
3613 
3614     if (core->board.tuner_type == TUNER_XC2028) {
3615         struct v4l2_priv_tun_config  xc2028_cfg;
3616         struct xc2028_ctrl           ctl;
3617 
3618         /* Fills device-dependent initialization parameters */
3619         cx88_setup_xc3028(core, &ctl);
3620 
3621         /* Sends parameters to xc2028/3028 tuner */
3622         memset(&xc2028_cfg, 0, sizeof(xc2028_cfg));
3623         xc2028_cfg.tuner = TUNER_XC2028;
3624         xc2028_cfg.priv  = &ctl;
3625         dprintk(1, "Asking xc2028/3028 to load firmware %s\n",
3626             ctl.fname);
3627         call_all(core, tuner, s_config, &xc2028_cfg);
3628     }
3629     call_all(core, tuner, standby);
3630 }
3631 
3632 /* ------------------------------------------------------------------ */
3633 
3634 static int cx88_pci_quirks(const char *name, struct pci_dev *pci)
3635 {
3636     unsigned int lat = UNSET;
3637     u8 ctrl = 0;
3638     u8 value;
3639 
3640     /* check pci quirks */
3641     if (pci_pci_problems & PCIPCI_TRITON) {
3642         pr_info("quirk: PCIPCI_TRITON -- set TBFX\n");
3643         ctrl |= CX88X_EN_TBFX;
3644     }
3645     if (pci_pci_problems & PCIPCI_NATOMA) {
3646         pr_info("quirk: PCIPCI_NATOMA -- set TBFX\n");
3647         ctrl |= CX88X_EN_TBFX;
3648     }
3649     if (pci_pci_problems & PCIPCI_VIAETBF) {
3650         pr_info("quirk: PCIPCI_VIAETBF -- set TBFX\n");
3651         ctrl |= CX88X_EN_TBFX;
3652     }
3653     if (pci_pci_problems & PCIPCI_VSFX) {
3654         pr_info("quirk: PCIPCI_VSFX -- set VSFX\n");
3655         ctrl |= CX88X_EN_VSFX;
3656     }
3657 #ifdef PCIPCI_ALIMAGIK
3658     if (pci_pci_problems & PCIPCI_ALIMAGIK) {
3659         pr_info("quirk: PCIPCI_ALIMAGIK -- latency fixup\n");
3660         lat = 0x0A;
3661     }
3662 #endif
3663 
3664     /* check insmod options */
3665     if (latency != UNSET)
3666         lat = latency;
3667 
3668     /* apply stuff */
3669     if (ctrl) {
3670         pci_read_config_byte(pci, CX88X_DEVCTRL, &value);
3671         value |= ctrl;
3672         pci_write_config_byte(pci, CX88X_DEVCTRL, value);
3673     }
3674     if (lat != UNSET) {
3675         pr_info("setting pci latency timer to %d\n", latency);
3676         pci_write_config_byte(pci, PCI_LATENCY_TIMER, latency);
3677     }
3678     return 0;
3679 }
3680 
3681 int cx88_get_resources(const struct cx88_core *core, struct pci_dev *pci)
3682 {
3683     if (request_mem_region(pci_resource_start(pci, 0),
3684                    pci_resource_len(pci, 0),
3685                    core->name))
3686         return 0;
3687     pr_err("func %d: Can't get MMIO memory @ 0x%llx, subsystem: %04x:%04x\n",
3688            PCI_FUNC(pci->devfn),
3689            (unsigned long long)pci_resource_start(pci, 0),
3690            pci->subsystem_vendor, pci->subsystem_device);
3691     return -EBUSY;
3692 }
3693 
3694 /*
3695  * Allocate and initialize the cx88 core struct.  One should hold the
3696  * devlist mutex before calling this.
3697  */
3698 struct cx88_core *cx88_core_create(struct pci_dev *pci, int nr)
3699 {
3700     struct cx88_core *core;
3701     int i;
3702 
3703     core = kzalloc(sizeof(*core), GFP_KERNEL);
3704     if (!core)
3705         return NULL;
3706 
3707     refcount_set(&core->refcount, 1);
3708     core->pci_bus  = pci->bus->number;
3709     core->pci_slot = PCI_SLOT(pci->devfn);
3710     core->pci_irqmask = PCI_INT_RISC_RD_BERRINT | PCI_INT_RISC_WR_BERRINT |
3711                 PCI_INT_BRDG_BERRINT | PCI_INT_SRC_DMA_BERRINT |
3712                 PCI_INT_DST_DMA_BERRINT | PCI_INT_IPB_DMA_BERRINT;
3713     mutex_init(&core->lock);
3714 
3715     core->nr = nr;
3716     sprintf(core->name, "cx88[%d]", core->nr);
3717 
3718     /*
3719      * Note: Setting initial standard here would cause first call to
3720      * cx88_set_tvnorm() to return without programming any registers.  Leave
3721      * it blank for at this point and it will get set later in
3722      * cx8800_initdev()
3723      */
3724     core->tvnorm  = 0;
3725 
3726     core->width   = 320;
3727     core->height  = 240;
3728     core->field   = V4L2_FIELD_INTERLACED;
3729 
3730     strscpy(core->v4l2_dev.name, core->name, sizeof(core->v4l2_dev.name));
3731     if (v4l2_device_register(NULL, &core->v4l2_dev)) {
3732         kfree(core);
3733         return NULL;
3734     }
3735 
3736     if (v4l2_ctrl_handler_init(&core->video_hdl, 13)) {
3737         v4l2_device_unregister(&core->v4l2_dev);
3738         kfree(core);
3739         return NULL;
3740     }
3741 
3742     if (v4l2_ctrl_handler_init(&core->audio_hdl, 13)) {
3743         v4l2_ctrl_handler_free(&core->video_hdl);
3744         v4l2_device_unregister(&core->v4l2_dev);
3745         kfree(core);
3746         return NULL;
3747     }
3748 
3749     if (cx88_get_resources(core, pci) != 0) {
3750         v4l2_ctrl_handler_free(&core->video_hdl);
3751         v4l2_ctrl_handler_free(&core->audio_hdl);
3752         v4l2_device_unregister(&core->v4l2_dev);
3753         kfree(core);
3754         return NULL;
3755     }
3756 
3757     /* PCI stuff */
3758     cx88_pci_quirks(core->name, pci);
3759     core->lmmio = ioremap(pci_resource_start(pci, 0),
3760                   pci_resource_len(pci, 0));
3761     core->bmmio = (u8 __iomem *)core->lmmio;
3762 
3763     if (!core->lmmio) {
3764         release_mem_region(pci_resource_start(pci, 0),
3765                    pci_resource_len(pci, 0));
3766         v4l2_ctrl_handler_free(&core->video_hdl);
3767         v4l2_ctrl_handler_free(&core->audio_hdl);
3768         v4l2_device_unregister(&core->v4l2_dev);
3769         kfree(core);
3770         return NULL;
3771     }
3772 
3773     /* board config */
3774     core->boardnr = UNSET;
3775     if (card[core->nr] < ARRAY_SIZE(cx88_boards))
3776         core->boardnr = card[core->nr];
3777     for (i = 0; core->boardnr == UNSET && i < ARRAY_SIZE(cx88_subids); i++)
3778         if (pci->subsystem_vendor == cx88_subids[i].subvendor &&
3779             pci->subsystem_device == cx88_subids[i].subdevice)
3780             core->boardnr = cx88_subids[i].card;
3781     if (core->boardnr == UNSET) {
3782         core->boardnr = CX88_BOARD_UNKNOWN;
3783         cx88_card_list(core, pci);
3784     }
3785 
3786     core->board = cx88_boards[core->boardnr];
3787 
3788     if (!core->board.num_frontends && (core->board.mpeg & CX88_MPEG_DVB))
3789         core->board.num_frontends = 1;
3790 
3791     pr_info("subsystem: %04x:%04x, board: %s [card=%d,%s], frontend(s): %d\n",
3792         pci->subsystem_vendor, pci->subsystem_device, core->board.name,
3793         core->boardnr, card[core->nr] == core->boardnr ?
3794         "insmod option" : "autodetected",
3795         core->board.num_frontends);
3796 
3797     if (tuner[core->nr] != UNSET)
3798         core->board.tuner_type = tuner[core->nr];
3799     if (radio[core->nr] != UNSET)
3800         core->board.radio_type = radio[core->nr];
3801 
3802     dprintk(1, "TV tuner type %d, Radio tuner type %d\n",
3803         core->board.tuner_type, core->board.radio_type);
3804 
3805     /* init hardware */
3806     cx88_reset(core);
3807     cx88_card_setup_pre_i2c(core);
3808     cx88_i2c_init(core, pci);
3809 
3810     /* load tuner module, if needed */
3811     if (core->board.tuner_type != UNSET) {
3812         /*
3813          * Ignore 0x6b and 0x6f on cx88 boards.
3814          * FusionHDTV5 RT Gold has an ir receiver at 0x6b
3815          * and an RTC at 0x6f which can get corrupted if probed.
3816          */
3817         static const unsigned short tv_addrs[] = {
3818             0x42, 0x43, 0x4a, 0x4b,     /* tda8290 */
3819             0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
3820             0x68, 0x69, 0x6a, 0x6c, 0x6d, 0x6e,
3821             I2C_CLIENT_END
3822         };
3823         int has_demod = (core->board.tda9887_conf & TDA9887_PRESENT);
3824 
3825         /*
3826          * I don't trust the radio_type as is stored in the card
3827          * definitions, so we just probe for it.
3828          * The radio_type is sometimes missing, or set to UNSET but
3829          * later code configures a tea5767.
3830          */
3831         v4l2_i2c_new_subdev(&core->v4l2_dev, &core->i2c_adap,
3832                     "tuner", 0,
3833                     v4l2_i2c_tuner_addrs(ADDRS_RADIO));
3834         if (has_demod)
3835             v4l2_i2c_new_subdev(&core->v4l2_dev,
3836                         &core->i2c_adap, "tuner",
3837                 0, v4l2_i2c_tuner_addrs(ADDRS_DEMOD));
3838         if (core->board.tuner_addr == ADDR_UNSET) {
3839             v4l2_i2c_new_subdev(&core->v4l2_dev,
3840                         &core->i2c_adap, "tuner",
3841                 0, has_demod ? tv_addrs + 4 : tv_addrs);
3842         } else {
3843             v4l2_i2c_new_subdev(&core->v4l2_dev, &core->i2c_adap,
3844                         "tuner", core->board.tuner_addr,
3845                         NULL);
3846         }
3847     }
3848 
3849     cx88_card_setup(core);
3850     if (!disable_ir) {
3851         cx88_i2c_init_ir(core);
3852         cx88_ir_init(core, pci);
3853     }
3854 
3855     return core;
3856 }