1 /*
2  * tveeprom - eeprom decoder for tvcard configuration eeproms
3  *
4  * Data and decoding routines shamelessly borrowed from bttv-cards.c
5  * eeprom access routine shamelessly borrowed from bttv-if.c
6  * which are:
7 
8     Copyright (C) 1996,97,98 Ralph  Metzler (rjkm@thp.uni-koeln.de)
9 			   & Marcus Metzler (mocm@thp.uni-koeln.de)
10     (c) 1999-2001 Gerd Knorr <kraxel@goldbach.in-berlin.de>
11 
12  * Adjustments to fit a more general model and all bugs:
13 
14 	Copyright (C) 2003 John Klar <linpvr at projectplasma.com>
15 
16  * This program is free software; you can redistribute it and/or modify
17  * it under the terms of the GNU General Public License as published by
18  * the Free Software Foundation; either version 2 of the License, or
19  * (at your option) any later version.
20  *
21  * This program is distributed in the hope that it will be useful,
22  * but WITHOUT ANY WARRANTY; without even the implied warranty of
23  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24  * GNU General Public License for more details.
25  *
26  * You should have received a copy of the GNU General Public License
27  * along with this program; if not, write to the Free Software
28  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29  */
30 
31 
32 #include <linux/module.h>
33 #include <linux/errno.h>
34 #include <linux/kernel.h>
35 #include <linux/init.h>
36 #include <linux/types.h>
37 #include <linux/videodev2.h>
38 #include <linux/i2c.h>
39 
40 #include <media/tuner.h>
41 #include <media/tveeprom.h>
42 #include <media/v4l2-common.h>
43 #include <media/v4l2-chip-ident.h>
44 
45 MODULE_DESCRIPTION("i2c Hauppauge eeprom decoder driver");
46 MODULE_AUTHOR("John Klar");
47 MODULE_LICENSE("GPL");
48 
49 static int debug;
50 module_param(debug, int, 0644);
51 MODULE_PARM_DESC(debug, "Debug level (0-1)");
52 
53 #define STRM(array, i) \
54 	(i < sizeof(array) / sizeof(char *) ? array[i] : "unknown")
55 
56 #define tveeprom_info(fmt, arg...) \
57 	v4l_printk(KERN_INFO, "tveeprom", c->adapter, c->addr, fmt , ## arg)
58 #define tveeprom_warn(fmt, arg...) \
59 	v4l_printk(KERN_WARNING, "tveeprom", c->adapter, c->addr, fmt , ## arg)
60 #define tveeprom_dbg(fmt, arg...) do { \
61 	if (debug) \
62 		v4l_printk(KERN_DEBUG, "tveeprom", \
63 				c->adapter, c->addr, fmt , ## arg); \
64 	} while (0)
65 
66 /*
67  * The Hauppauge eeprom uses an 8bit field to determine which
68  * tuner formats the tuner supports.
69  */
70 static struct HAUPPAUGE_TUNER_FMT
71 {
72 	int	id;
73 	char *name;
74 }
75 hauppauge_tuner_fmt[] =
76 {
77 	{ V4L2_STD_UNKNOWN,                   " UNKNOWN" },
78 	{ V4L2_STD_UNKNOWN,                   " FM" },
79 	{ V4L2_STD_B|V4L2_STD_GH,             " PAL(B/G)" },
80 	{ V4L2_STD_MN,                        " NTSC(M)" },
81 	{ V4L2_STD_PAL_I,                     " PAL(I)" },
82 	{ V4L2_STD_SECAM_L|V4L2_STD_SECAM_LC, " SECAM(L/L')" },
83 	{ V4L2_STD_DK,                        " PAL(D/D1/K)" },
84 	{ V4L2_STD_ATSC,                      " ATSC/DVB Digital" },
85 };
86 
87 /* This is the full list of possible tuners. Many thanks to Hauppauge for
88    supplying this information. Note that many tuners where only used for
89    testing and never made it to the outside world. So you will only see
90    a subset in actual produced cards. */
91 static struct HAUPPAUGE_TUNER
92 {
93 	int  id;
94 	char *name;
95 }
96 hauppauge_tuner[] =
97 {
98 	/* 0-9 */
99 	{ TUNER_ABSENT,        		"None" },
100 	{ TUNER_ABSENT,        		"External" },
101 	{ TUNER_ABSENT,        		"Unspecified" },
102 	{ TUNER_PHILIPS_PAL,   		"Philips FI1216" },
103 	{ TUNER_PHILIPS_SECAM, 		"Philips FI1216MF" },
104 	{ TUNER_PHILIPS_NTSC,  		"Philips FI1236" },
105 	{ TUNER_PHILIPS_PAL_I, 		"Philips FI1246" },
106 	{ TUNER_PHILIPS_PAL_DK,		"Philips FI1256" },
107 	{ TUNER_PHILIPS_PAL,   		"Philips FI1216 MK2" },
108 	{ TUNER_PHILIPS_SECAM, 		"Philips FI1216MF MK2" },
109 	/* 10-19 */
110 	{ TUNER_PHILIPS_NTSC,  		"Philips FI1236 MK2" },
111 	{ TUNER_PHILIPS_PAL_I, 		"Philips FI1246 MK2" },
112 	{ TUNER_PHILIPS_PAL_DK,		"Philips FI1256 MK2" },
113 	{ TUNER_TEMIC_NTSC,    		"Temic 4032FY5" },
114 	{ TUNER_TEMIC_PAL,     		"Temic 4002FH5" },
115 	{ TUNER_TEMIC_PAL_I,   		"Temic 4062FY5" },
116 	{ TUNER_PHILIPS_PAL,   		"Philips FR1216 MK2" },
117 	{ TUNER_PHILIPS_SECAM, 		"Philips FR1216MF MK2" },
118 	{ TUNER_PHILIPS_NTSC,  		"Philips FR1236 MK2" },
119 	{ TUNER_PHILIPS_PAL_I, 		"Philips FR1246 MK2" },
120 	/* 20-29 */
121 	{ TUNER_PHILIPS_PAL_DK,		"Philips FR1256 MK2" },
122 	{ TUNER_PHILIPS_PAL,   		"Philips FM1216" },
123 	{ TUNER_PHILIPS_SECAM, 		"Philips FM1216MF" },
124 	{ TUNER_PHILIPS_NTSC,  		"Philips FM1236" },
125 	{ TUNER_PHILIPS_PAL_I, 		"Philips FM1246" },
126 	{ TUNER_PHILIPS_PAL_DK,		"Philips FM1256" },
127 	{ TUNER_TEMIC_4036FY5_NTSC, 	"Temic 4036FY5" },
128 	{ TUNER_ABSENT,        		"Samsung TCPN9082D" },
129 	{ TUNER_ABSENT,        		"Samsung TCPM9092P" },
130 	{ TUNER_TEMIC_4006FH5_PAL, 	"Temic 4006FH5" },
131 	/* 30-39 */
132 	{ TUNER_ABSENT,        		"Samsung TCPN9085D" },
133 	{ TUNER_ABSENT,        		"Samsung TCPB9085P" },
134 	{ TUNER_ABSENT,        		"Samsung TCPL9091P" },
135 	{ TUNER_TEMIC_4039FR5_NTSC, 	"Temic 4039FR5" },
136 	{ TUNER_PHILIPS_FQ1216ME,   	"Philips FQ1216 ME" },
137 	{ TUNER_TEMIC_4066FY5_PAL_I, 	"Temic 4066FY5" },
138 	{ TUNER_PHILIPS_NTSC,        	"Philips TD1536" },
139 	{ TUNER_PHILIPS_NTSC,        	"Philips TD1536D" },
140 	{ TUNER_PHILIPS_NTSC,  		"Philips FMR1236" }, /* mono radio */
141 	{ TUNER_ABSENT,        		"Philips FI1256MP" },
142 	/* 40-49 */
143 	{ TUNER_ABSENT,        		"Samsung TCPQ9091P" },
144 	{ TUNER_TEMIC_4006FN5_MULTI_PAL, "Temic 4006FN5" },
145 	{ TUNER_TEMIC_4009FR5_PAL, 	"Temic 4009FR5" },
146 	{ TUNER_TEMIC_4046FM5,     	"Temic 4046FM5" },
147 	{ TUNER_TEMIC_4009FN5_MULTI_PAL_FM, "Temic 4009FN5" },
148 	{ TUNER_ABSENT,        		"Philips TD1536D FH 44"},
149 	{ TUNER_LG_NTSC_FM,    		"LG TP18NSR01F"},
150 	{ TUNER_LG_PAL_FM,     		"LG TP18PSB01D"},
151 	{ TUNER_LG_PAL,        		"LG TP18PSB11D"},
152 	{ TUNER_LG_PAL_I_FM,   		"LG TAPC-I001D"},
153 	/* 50-59 */
154 	{ TUNER_LG_PAL_I,      		"LG TAPC-I701D"},
155 	{ TUNER_ABSENT,       		"Temic 4042FI5"},
156 	{ TUNER_MICROTUNE_4049FM5, 	"Microtune 4049 FM5"},
157 	{ TUNER_ABSENT,        		"LG TPI8NSR11F"},
158 	{ TUNER_ABSENT,        		"Microtune 4049 FM5 Alt I2C"},
159 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"Philips FQ1216ME MK3"},
160 	{ TUNER_ABSENT,        		"Philips FI1236 MK3"},
161 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"Philips FM1216 ME MK3"},
162 	{ TUNER_PHILIPS_FM1236_MK3, 	"Philips FM1236 MK3"},
163 	{ TUNER_ABSENT,        		"Philips FM1216MP MK3"},
164 	/* 60-69 */
165 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"LG S001D MK3"},
166 	{ TUNER_ABSENT,        		"LG M001D MK3"},
167 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"LG S701D MK3"},
168 	{ TUNER_ABSENT,        		"LG M701D MK3"},
169 	{ TUNER_ABSENT,        		"Temic 4146FM5"},
170 	{ TUNER_ABSENT,        		"Temic 4136FY5"},
171 	{ TUNER_ABSENT,        		"Temic 4106FH5"},
172 	{ TUNER_ABSENT,        		"Philips FQ1216LMP MK3"},
173 	{ TUNER_LG_NTSC_TAPE,  		"LG TAPE H001F MK3"},
174 	{ TUNER_LG_NTSC_TAPE,  		"LG TAPE H701F MK3"},
175 	/* 70-79 */
176 	{ TUNER_ABSENT,        		"LG TALN H200T"},
177 	{ TUNER_ABSENT,        		"LG TALN H250T"},
178 	{ TUNER_ABSENT,        		"LG TALN M200T"},
179 	{ TUNER_ABSENT,        		"LG TALN Z200T"},
180 	{ TUNER_ABSENT,        		"LG TALN S200T"},
181 	{ TUNER_ABSENT,        		"Thompson DTT7595"},
182 	{ TUNER_ABSENT,        		"Thompson DTT7592"},
183 	{ TUNER_ABSENT,        		"Silicon TDA8275C1 8290"},
184 	{ TUNER_ABSENT,        		"Silicon TDA8275C1 8290 FM"},
185 	{ TUNER_ABSENT,        		"Thompson DTT757"},
186 	/* 80-89 */
187 	{ TUNER_PHILIPS_FQ1216LME_MK3, 	"Philips FQ1216LME MK3"},
188 	{ TUNER_LG_PAL_NEW_TAPC, 	"LG TAPC G701D"},
189 	{ TUNER_LG_NTSC_NEW_TAPC, 	"LG TAPC H791F"},
190 	{ TUNER_LG_PAL_NEW_TAPC, 	"TCL 2002MB 3"},
191 	{ TUNER_LG_PAL_NEW_TAPC, 	"TCL 2002MI 3"},
192 	{ TUNER_TCL_2002N,     		"TCL 2002N 6A"},
193 	{ TUNER_PHILIPS_FM1236_MK3, 	"Philips FQ1236 MK3"},
194 	{ TUNER_SAMSUNG_TCPN_2121P30A, 	"Samsung TCPN 2121P30A"},
195 	{ TUNER_ABSENT,        		"Samsung TCPE 4121P30A"},
196 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"TCL MFPE05 2"},
197 	/* 90-99 */
198 	{ TUNER_ABSENT,        		"LG TALN H202T"},
199 	{ TUNER_PHILIPS_FQ1216AME_MK4, 	"Philips FQ1216AME MK4"},
200 	{ TUNER_PHILIPS_FQ1236A_MK4, 	"Philips FQ1236A MK4"},
201 	{ TUNER_ABSENT,       		"Philips FQ1286A MK4"},
202 	{ TUNER_ABSENT,        		"Philips FQ1216ME MK5"},
203 	{ TUNER_ABSENT,        		"Philips FQ1236 MK5"},
204 	{ TUNER_SAMSUNG_TCPG_6121P30A, 	"Samsung TCPG 6121P30A"},
205 	{ TUNER_TCL_2002MB,    		"TCL 2002MB_3H"},
206 	{ TUNER_ABSENT,        		"TCL 2002MI_3H"},
207 	{ TUNER_TCL_2002N,     		"TCL 2002N 5H"},
208 	/* 100-109 */
209 	{ TUNER_PHILIPS_FMD1216ME_MK3, 	"Philips FMD1216ME"},
210 	{ TUNER_TEA5767,       		"Philips TEA5768HL FM Radio"},
211 	{ TUNER_ABSENT,        		"Panasonic ENV57H12D5"},
212 	{ TUNER_PHILIPS_FM1236_MK3, 	"TCL MFNM05-4"},
213 	{ TUNER_PHILIPS_FM1236_MK3,	"TCL MNM05-4"},
214 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"TCL MPE05-2"},
215 	{ TUNER_ABSENT,        		"TCL MQNM05-4"},
216 	{ TUNER_ABSENT,        		"LG TAPC-W701D"},
217 	{ TUNER_ABSENT,        		"TCL 9886P-WM"},
218 	{ TUNER_ABSENT,        		"TCL 1676NM-WM"},
219 	/* 110-119 */
220 	{ TUNER_ABSENT,        		"Thompson DTT75105"},
221 	{ TUNER_ABSENT,        		"Conexant_CX24109"},
222 	{ TUNER_TCL_2002N,     		"TCL M2523_5N_E"},
223 	{ TUNER_TCL_2002MB,    		"TCL M2523_3DB_E"},
224 	{ TUNER_ABSENT,        		"Philips 8275A"},
225 	{ TUNER_ABSENT,        		"Microtune MT2060"},
226 	{ TUNER_PHILIPS_FM1236_MK3, 	"Philips FM1236 MK5"},
227 	{ TUNER_PHILIPS_FM1216ME_MK3, 	"Philips FM1216ME MK5"},
228 	{ TUNER_ABSENT,        		"TCL M2523_3DI_E"},
229 	{ TUNER_ABSENT,        		"Samsung THPD5222FG30A"},
230 	/* 120-129 */
231 	{ TUNER_XC2028,        		"Xceive XC3028"},
232 	{ TUNER_PHILIPS_FQ1216LME_MK3,	"Philips FQ1216LME MK5"},
233 	{ TUNER_ABSENT,        		"Philips FQD1216LME"},
234 	{ TUNER_ABSENT,        		"Conexant CX24118A"},
235 	{ TUNER_ABSENT,        		"TCL DMF11WIP"},
236 	{ TUNER_ABSENT,        		"TCL MFNM05_4H_E"},
237 	{ TUNER_ABSENT,        		"TCL MNM05_4H_E"},
238 	{ TUNER_ABSENT,        		"TCL MPE05_2H_E"},
239 	{ TUNER_ABSENT,        		"TCL MQNM05_4_U"},
240 	{ TUNER_ABSENT,        		"TCL M2523_5NH_E"},
241 	/* 130-139 */
242 	{ TUNER_ABSENT,        		"TCL M2523_3DBH_E"},
243 	{ TUNER_ABSENT,        		"TCL M2523_3DIH_E"},
244 	{ TUNER_ABSENT,        		"TCL MFPE05_2_U"},
245 	{ TUNER_PHILIPS_FMD1216MEX_MK3,	"Philips FMD1216MEX"},
246 	{ TUNER_ABSENT,        		"Philips FRH2036B"},
247 	{ TUNER_ABSENT,        		"Panasonic ENGF75_01GF"},
248 	{ TUNER_ABSENT,        		"MaxLinear MXL5005"},
249 	{ TUNER_ABSENT,        		"MaxLinear MXL5003"},
250 	{ TUNER_ABSENT,        		"Xceive XC2028"},
251 	{ TUNER_ABSENT,        		"Microtune MT2131"},
252 	/* 140-149 */
253 	{ TUNER_ABSENT,        		"Philips 8275A_8295"},
254 	{ TUNER_ABSENT,        		"TCL MF02GIP_5N_E"},
255 	{ TUNER_ABSENT,        		"TCL MF02GIP_3DB_E"},
256 	{ TUNER_ABSENT,        		"TCL MF02GIP_3DI_E"},
257 	{ TUNER_ABSENT,        		"Microtune MT2266"},
258 	{ TUNER_ABSENT,        		"TCL MF10WPP_4N_E"},
259 	{ TUNER_ABSENT,        		"LG TAPQ_H702F"},
260 	{ TUNER_ABSENT,        		"TCL M09WPP_4N_E"},
261 	{ TUNER_ABSENT,        		"MaxLinear MXL5005_v2"},
262 	{ TUNER_PHILIPS_TDA8290, 	"Philips 18271_8295"},
263 	/* 150-159 */
264 	{ TUNER_XC5000,                 "Xceive XC5000"},
265 	{ TUNER_ABSENT,                 "Xceive XC3028L"},
266 	{ TUNER_ABSENT,                 "NXP 18271C2_716x"},
267 	{ TUNER_ABSENT,                 "Xceive XC4000"},
268 	{ TUNER_ABSENT,                 "Dibcom 7070"},
269 	{ TUNER_PHILIPS_TDA8290,        "NXP 18271C2"},
270 	{ TUNER_ABSENT,                 "Siano SMS1010"},
271 	{ TUNER_ABSENT,                 "Siano SMS1150"},
272 	{ TUNER_ABSENT,                 "MaxLinear 5007"},
273 	{ TUNER_ABSENT,                 "TCL M09WPP_2P_E"},
274 	/* 160-169 */
275 	{ TUNER_ABSENT,                 "Siano SMS1180"},
276 	{ TUNER_ABSENT,                 "Maxim_MAX2165"},
277 	{ TUNER_ABSENT,                 "Siano SMS1140"},
278 	{ TUNER_ABSENT,                 "Siano SMS1150 B1"},
279 	{ TUNER_ABSENT,                 "MaxLinear 111"},
280 	{ TUNER_ABSENT,                 "Dibcom 7770"},
281 	{ TUNER_ABSENT,                 "Siano SMS1180VNS"},
282 	{ TUNER_ABSENT,                 "Siano SMS1184"},
283 	{ TUNER_PHILIPS_FQ1236_MK5,	"TCL M30WTP-4N-E"},
284 	{ TUNER_ABSENT,                 "TCL_M11WPP_2PN_E"},
285 	/* 170-179 */
286 	{ TUNER_ABSENT,                 "MaxLinear 301"},
287 	{ TUNER_ABSENT,                 "Mirics MSi001"},
288 	{ TUNER_ABSENT,                 "MaxLinear MxL241SF"},
289 	{ TUNER_ABSENT,                 "Xceive XC5000C"},
290 	{ TUNER_ABSENT,                 "Montage M68TS2020"},
291 };
292 
293 /* Use V4L2_IDENT_AMBIGUOUS for those audio 'chips' that are
294  * internal to a video chip, i.e. not a separate audio chip. */
295 static struct HAUPPAUGE_AUDIOIC
296 {
297 	u32   id;
298 	char *name;
299 }
300 audioIC[] =
301 {
302 	/* 0-4 */
303 	{ V4L2_IDENT_NONE,      "None"      },
304 	{ V4L2_IDENT_UNKNOWN,   "TEA6300"   },
305 	{ V4L2_IDENT_UNKNOWN,   "TEA6320"   },
306 	{ V4L2_IDENT_UNKNOWN,   "TDA9850"   },
307 	{ V4L2_IDENT_MSPX4XX,   "MSP3400C"  },
308 	/* 5-9 */
309 	{ V4L2_IDENT_MSPX4XX,   "MSP3410D"  },
310 	{ V4L2_IDENT_MSPX4XX,   "MSP3415"   },
311 	{ V4L2_IDENT_MSPX4XX,   "MSP3430"   },
312 	{ V4L2_IDENT_MSPX4XX,   "MSP3438"   },
313 	{ V4L2_IDENT_UNKNOWN,   "CS5331"    },
314 	/* 10-14 */
315 	{ V4L2_IDENT_MSPX4XX,   "MSP3435"   },
316 	{ V4L2_IDENT_MSPX4XX,   "MSP3440"   },
317 	{ V4L2_IDENT_MSPX4XX,   "MSP3445"   },
318 	{ V4L2_IDENT_MSPX4XX,   "MSP3411"   },
319 	{ V4L2_IDENT_MSPX4XX,   "MSP3416"   },
320 	/* 15-19 */
321 	{ V4L2_IDENT_MSPX4XX,   "MSP3425"   },
322 	{ V4L2_IDENT_MSPX4XX,   "MSP3451"   },
323 	{ V4L2_IDENT_MSPX4XX,   "MSP3418"   },
324 	{ V4L2_IDENT_UNKNOWN,   "Type 0x12" },
325 	{ V4L2_IDENT_UNKNOWN,   "OKI7716"   },
326 	/* 20-24 */
327 	{ V4L2_IDENT_MSPX4XX,   "MSP4410"   },
328 	{ V4L2_IDENT_MSPX4XX,   "MSP4420"   },
329 	{ V4L2_IDENT_MSPX4XX,   "MSP4440"   },
330 	{ V4L2_IDENT_MSPX4XX,   "MSP4450"   },
331 	{ V4L2_IDENT_MSPX4XX,   "MSP4408"   },
332 	/* 25-29 */
333 	{ V4L2_IDENT_MSPX4XX,   "MSP4418"   },
334 	{ V4L2_IDENT_MSPX4XX,   "MSP4428"   },
335 	{ V4L2_IDENT_MSPX4XX,   "MSP4448"   },
336 	{ V4L2_IDENT_MSPX4XX,   "MSP4458"   },
337 	{ V4L2_IDENT_MSPX4XX,   "Type 0x1d" },
338 	/* 30-34 */
339 	{ V4L2_IDENT_AMBIGUOUS, "CX880"     },
340 	{ V4L2_IDENT_AMBIGUOUS, "CX881"     },
341 	{ V4L2_IDENT_AMBIGUOUS, "CX883"     },
342 	{ V4L2_IDENT_AMBIGUOUS, "CX882"     },
343 	{ V4L2_IDENT_AMBIGUOUS, "CX25840"   },
344 	/* 35-39 */
345 	{ V4L2_IDENT_AMBIGUOUS, "CX25841"   },
346 	{ V4L2_IDENT_AMBIGUOUS, "CX25842"   },
347 	{ V4L2_IDENT_AMBIGUOUS, "CX25843"   },
348 	{ V4L2_IDENT_AMBIGUOUS, "CX23418"   },
349 	{ V4L2_IDENT_AMBIGUOUS, "CX23885"   },
350 	/* 40-44 */
351 	{ V4L2_IDENT_AMBIGUOUS, "CX23888"   },
352 	{ V4L2_IDENT_AMBIGUOUS, "SAA7131"   },
353 	{ V4L2_IDENT_AMBIGUOUS, "CX23887"   },
354 	{ V4L2_IDENT_AMBIGUOUS, "SAA7164"   },
355 	{ V4L2_IDENT_AMBIGUOUS, "AU8522"    },
356 };
357 
358 /* This list is supplied by Hauppauge. Thanks! */
359 static const char *decoderIC[] = {
360 	/* 0-4 */
361 	"None", "BT815", "BT817", "BT819", "BT815A",
362 	/* 5-9 */
363 	"BT817A", "BT819A", "BT827", "BT829", "BT848",
364 	/* 10-14 */
365 	"BT848A", "BT849A", "BT829A", "BT827A", "BT878",
366 	/* 15-19 */
367 	"BT879", "BT880", "VPX3226E", "SAA7114", "SAA7115",
368 	/* 20-24 */
369 	"CX880", "CX881", "CX883", "SAA7111", "SAA7113",
370 	/* 25-29 */
371 	"CX882", "TVP5150A", "CX25840", "CX25841", "CX25842",
372 	/* 30-34 */
373 	"CX25843", "CX23418", "NEC61153", "CX23885", "CX23888",
374 	/* 35-39 */
375 	"SAA7131", "CX25837", "CX23887", "CX23885A", "CX23887A",
376 	/* 40-42 */
377 	"SAA7164", "CX23885B", "AU8522"
378 };
379 
hasRadioTuner(int tunerType)380 static int hasRadioTuner(int tunerType)
381 {
382 	switch (tunerType) {
383 	case 18: /* PNPEnv_TUNER_FR1236_MK2 */
384 	case 23: /* PNPEnv_TUNER_FM1236 */
385 	case 38: /* PNPEnv_TUNER_FMR1236 */
386 	case 16: /* PNPEnv_TUNER_FR1216_MK2 */
387 	case 19: /* PNPEnv_TUNER_FR1246_MK2 */
388 	case 21: /* PNPEnv_TUNER_FM1216 */
389 	case 24: /* PNPEnv_TUNER_FM1246 */
390 	case 17: /* PNPEnv_TUNER_FR1216MF_MK2 */
391 	case 22: /* PNPEnv_TUNER_FM1216MF */
392 	case 20: /* PNPEnv_TUNER_FR1256_MK2 */
393 	case 25: /* PNPEnv_TUNER_FM1256 */
394 	case 33: /* PNPEnv_TUNER_4039FR5 */
395 	case 42: /* PNPEnv_TUNER_4009FR5 */
396 	case 52: /* PNPEnv_TUNER_4049FM5 */
397 	case 54: /* PNPEnv_TUNER_4049FM5_AltI2C */
398 	case 44: /* PNPEnv_TUNER_4009FN5 */
399 	case 31: /* PNPEnv_TUNER_TCPB9085P */
400 	case 30: /* PNPEnv_TUNER_TCPN9085D */
401 	case 46: /* PNPEnv_TUNER_TP18NSR01F */
402 	case 47: /* PNPEnv_TUNER_TP18PSB01D */
403 	case 49: /* PNPEnv_TUNER_TAPC_I001D */
404 	case 60: /* PNPEnv_TUNER_TAPE_S001D_MK3 */
405 	case 57: /* PNPEnv_TUNER_FM1216ME_MK3 */
406 	case 59: /* PNPEnv_TUNER_FM1216MP_MK3 */
407 	case 58: /* PNPEnv_TUNER_FM1236_MK3 */
408 	case 68: /* PNPEnv_TUNER_TAPE_H001F_MK3 */
409 	case 61: /* PNPEnv_TUNER_TAPE_M001D_MK3 */
410 	case 78: /* PNPEnv_TUNER_TDA8275C1_8290_FM */
411 	case 89: /* PNPEnv_TUNER_TCL_MFPE05_2 */
412 	case 92: /* PNPEnv_TUNER_PHILIPS_FQ1236A_MK4 */
413 	case 105:
414 		return 1;
415 	}
416 	return 0;
417 }
418 
tveeprom_hauppauge_analog(struct i2c_client * c,struct tveeprom * tvee,unsigned char * eeprom_data)419 void tveeprom_hauppauge_analog(struct i2c_client *c, struct tveeprom *tvee,
420 				unsigned char *eeprom_data)
421 {
422 	/* ----------------------------------------------
423 	** The hauppauge eeprom format is tagged
424 	**
425 	** if packet[0] == 0x84, then packet[0..1] == length
426 	** else length = packet[0] & 3f;
427 	** if packet[0] & f8 == f8, then EOD and packet[1] == checksum
428 	**
429 	** In our (ivtv) case we're interested in the following:
430 	** tuner type:   tag [00].05 or [0a].01 (index into hauppauge_tuner)
431 	** tuner fmts:   tag [00].04 or [0a].00 (bitmask index into
432 	**		 hauppauge_tuner_fmt)
433 	** radio:        tag [00].{last} or [0e].00  (bitmask.  bit2=FM)
434 	** audio proc:   tag [02].01 or [05].00 (mask with 0x7f)
435 	** decoder proc: tag [09].01)
436 
437 	** Fun info:
438 	** model:      tag [00].07-08 or [06].00-01
439 	** revision:   tag [00].09-0b or [06].04-06
440 	** serial#:    tag [01].05-07 or [04].04-06
441 
442 	** # of inputs/outputs ???
443 	*/
444 
445 	int i, j, len, done, beenhere, tag, start;
446 
447 	int tuner1 = 0, t_format1 = 0, audioic = -1;
448 	char *t_name1 = NULL;
449 	const char *t_fmt_name1[8] = { " none", "", "", "", "", "", "", "" };
450 
451 	int tuner2 = 0, t_format2 = 0;
452 	char *t_name2 = NULL;
453 	const char *t_fmt_name2[8] = { " none", "", "", "", "", "", "", "" };
454 
455 	memset(tvee, 0, sizeof(*tvee));
456 	tvee->tuner_type = TUNER_ABSENT;
457 	tvee->tuner2_type = TUNER_ABSENT;
458 
459 	done = len = beenhere = 0;
460 
461 	/* Different eeprom start offsets for em28xx, cx2388x and cx23418 */
462 	if (eeprom_data[0] == 0x1a &&
463 	    eeprom_data[1] == 0xeb &&
464 	    eeprom_data[2] == 0x67 &&
465 	    eeprom_data[3] == 0x95)
466 		start = 0xa0; /* Generic em28xx offset */
467 	else if ((eeprom_data[0] & 0xe1) == 0x01 &&
468 		 eeprom_data[1] == 0x00 &&
469 		 eeprom_data[2] == 0x00 &&
470 		 eeprom_data[8] == 0x84)
471 		start = 8; /* Generic cx2388x offset */
472 	else if (eeprom_data[1] == 0x70 &&
473 		 eeprom_data[2] == 0x00 &&
474 		 eeprom_data[4] == 0x74 &&
475 		 eeprom_data[8] == 0x84)
476 		start = 8; /* Generic cx23418 offset (models 74xxx) */
477 	else
478 		start = 0;
479 
480 	for (i = start; !done && i < 256; i += len) {
481 		if (eeprom_data[i] == 0x84) {
482 			len = eeprom_data[i + 1] + (eeprom_data[i + 2] << 8);
483 			i += 3;
484 		} else if ((eeprom_data[i] & 0xf0) == 0x70) {
485 			if (eeprom_data[i] & 0x08) {
486 				/* verify checksum! */
487 				done = 1;
488 				break;
489 			}
490 			len = eeprom_data[i] & 0x07;
491 			++i;
492 		} else {
493 			tveeprom_warn("Encountered bad packet header [%02x]. "
494 				"Corrupt or not a Hauppauge eeprom.\n",
495 				eeprom_data[i]);
496 			return;
497 		}
498 
499 		if (debug) {
500 			tveeprom_info("Tag [%02x] + %d bytes:",
501 					eeprom_data[i], len - 1);
502 			for (j = 1; j < len; j++)
503 				printk(KERN_CONT " %02x", eeprom_data[i + j]);
504 			printk(KERN_CONT "\n");
505 		}
506 
507 		/* process by tag */
508 		tag = eeprom_data[i];
509 		switch (tag) {
510 		case 0x00:
511 			/* tag: 'Comprehensive' */
512 			tuner1 = eeprom_data[i+6];
513 			t_format1 = eeprom_data[i+5];
514 			tvee->has_radio = eeprom_data[i+len-1];
515 			/* old style tag, don't know how to detect
516 			IR presence, mark as unknown. */
517 			tvee->has_ir = 0;
518 			tvee->model =
519 				eeprom_data[i+8] +
520 				(eeprom_data[i+9] << 8);
521 			tvee->revision = eeprom_data[i+10] +
522 				(eeprom_data[i+11] << 8) +
523 				(eeprom_data[i+12] << 16);
524 			break;
525 
526 		case 0x01:
527 			/* tag: 'SerialID' */
528 			tvee->serial_number =
529 				eeprom_data[i+6] +
530 				(eeprom_data[i+7] << 8) +
531 				(eeprom_data[i+8] << 16);
532 			break;
533 
534 		case 0x02:
535 			/* tag 'AudioInfo'
536 			Note mask with 0x7F, high bit used on some older models
537 			to indicate 4052 mux was removed in favor of using MSP
538 			inputs directly. */
539 			audioic = eeprom_data[i+2] & 0x7f;
540 			if (audioic < ARRAY_SIZE(audioIC))
541 				tvee->audio_processor = audioIC[audioic].id;
542 			else
543 				tvee->audio_processor = V4L2_IDENT_UNKNOWN;
544 			break;
545 
546 		/* case 0x03: tag 'EEInfo' */
547 
548 		case 0x04:
549 			/* tag 'SerialID2' */
550 			tvee->serial_number =
551 				eeprom_data[i+5] +
552 				(eeprom_data[i+6] << 8) +
553 				(eeprom_data[i+7] << 16);
554 
555 			if ((eeprom_data[i + 8] & 0xf0) &&
556 					(tvee->serial_number < 0xffffff)) {
557 				tvee->MAC_address[0] = 0x00;
558 				tvee->MAC_address[1] = 0x0D;
559 				tvee->MAC_address[2] = 0xFE;
560 				tvee->MAC_address[3] = eeprom_data[i + 7];
561 				tvee->MAC_address[4] = eeprom_data[i + 6];
562 				tvee->MAC_address[5] = eeprom_data[i + 5];
563 				tvee->has_MAC_address = 1;
564 			}
565 			break;
566 
567 		case 0x05:
568 			/* tag 'Audio2'
569 			Note mask with 0x7F, high bit used on some older models
570 			to indicate 4052 mux was removed in favor of using MSP
571 			inputs directly. */
572 			audioic = eeprom_data[i+1] & 0x7f;
573 			if (audioic < ARRAY_SIZE(audioIC))
574 				tvee->audio_processor = audioIC[audioic].id;
575 			else
576 				tvee->audio_processor = V4L2_IDENT_UNKNOWN;
577 
578 			break;
579 
580 		case 0x06:
581 			/* tag 'ModelRev' */
582 			tvee->model =
583 				eeprom_data[i + 1] +
584 				(eeprom_data[i + 2] << 8) +
585 				(eeprom_data[i + 3] << 16) +
586 				(eeprom_data[i + 4] << 24);
587 			tvee->revision =
588 				eeprom_data[i + 5] +
589 				(eeprom_data[i + 6] << 8) +
590 				(eeprom_data[i + 7] << 16);
591 			break;
592 
593 		case 0x07:
594 			/* tag 'Details': according to Hauppauge not interesting
595 			on any PCI-era or later boards. */
596 			break;
597 
598 		/* there is no tag 0x08 defined */
599 
600 		case 0x09:
601 			/* tag 'Video' */
602 			tvee->decoder_processor = eeprom_data[i + 1];
603 			break;
604 
605 		case 0x0a:
606 			/* tag 'Tuner' */
607 			if (beenhere == 0) {
608 				tuner1 = eeprom_data[i + 2];
609 				t_format1 = eeprom_data[i + 1];
610 				beenhere = 1;
611 			} else {
612 				/* a second (radio) tuner may be present */
613 				tuner2 = eeprom_data[i + 2];
614 				t_format2 = eeprom_data[i + 1];
615 				/* not a TV tuner? */
616 				if (t_format2 == 0)
617 					tvee->has_radio = 1; /* must be radio */
618 			}
619 			break;
620 
621 		case 0x0b:
622 			/* tag 'Inputs': according to Hauppauge this is specific
623 			to each driver family, so no good assumptions can be
624 			made. */
625 			break;
626 
627 		/* case 0x0c: tag 'Balun' */
628 		/* case 0x0d: tag 'Teletext' */
629 
630 		case 0x0e:
631 			/* tag: 'Radio' */
632 			tvee->has_radio = eeprom_data[i+1];
633 			break;
634 
635 		case 0x0f:
636 			/* tag 'IRInfo' */
637 			tvee->has_ir = 1 | (eeprom_data[i+1] << 1);
638 			break;
639 
640 		/* case 0x10: tag 'VBIInfo' */
641 		/* case 0x11: tag 'QCInfo' */
642 		/* case 0x12: tag 'InfoBits' */
643 
644 		default:
645 			tveeprom_dbg("Not sure what to do with tag [%02x]\n",
646 					tag);
647 			/* dump the rest of the packet? */
648 		}
649 	}
650 
651 	if (!done) {
652 		tveeprom_warn("Ran out of data!\n");
653 		return;
654 	}
655 
656 	if (tvee->revision != 0) {
657 		tvee->rev_str[0] = 32 + ((tvee->revision >> 18) & 0x3f);
658 		tvee->rev_str[1] = 32 + ((tvee->revision >> 12) & 0x3f);
659 		tvee->rev_str[2] = 32 + ((tvee->revision >>  6) & 0x3f);
660 		tvee->rev_str[3] = 32 + (tvee->revision & 0x3f);
661 		tvee->rev_str[4] = 0;
662 	}
663 
664 	if (hasRadioTuner(tuner1) && !tvee->has_radio) {
665 		tveeprom_info("The eeprom says no radio is present, but the tuner type\n");
666 		tveeprom_info("indicates otherwise. I will assume that radio is present.\n");
667 		tvee->has_radio = 1;
668 	}
669 
670 	if (tuner1 < ARRAY_SIZE(hauppauge_tuner)) {
671 		tvee->tuner_type = hauppauge_tuner[tuner1].id;
672 		t_name1 = hauppauge_tuner[tuner1].name;
673 	} else {
674 		t_name1 = "unknown";
675 	}
676 
677 	if (tuner2 < ARRAY_SIZE(hauppauge_tuner)) {
678 		tvee->tuner2_type = hauppauge_tuner[tuner2].id;
679 		t_name2 = hauppauge_tuner[tuner2].name;
680 	} else {
681 		t_name2 = "unknown";
682 	}
683 
684 	tvee->tuner_hauppauge_model = tuner1;
685 	tvee->tuner2_hauppauge_model = tuner2;
686 	tvee->tuner_formats = 0;
687 	tvee->tuner2_formats = 0;
688 	for (i = j = 0; i < 8; i++) {
689 		if (t_format1 & (1 << i)) {
690 			tvee->tuner_formats |= hauppauge_tuner_fmt[i].id;
691 			t_fmt_name1[j++] = hauppauge_tuner_fmt[i].name;
692 		}
693 	}
694 	for (i = j = 0; i < 8; i++) {
695 		if (t_format2 & (1 << i)) {
696 			tvee->tuner2_formats |= hauppauge_tuner_fmt[i].id;
697 			t_fmt_name2[j++] = hauppauge_tuner_fmt[i].name;
698 		}
699 	}
700 
701 	tveeprom_info("Hauppauge model %d, rev %s, serial# %d\n",
702 		tvee->model, tvee->rev_str, tvee->serial_number);
703 	if (tvee->has_MAC_address == 1)
704 		tveeprom_info("MAC address is %pM\n", tvee->MAC_address);
705 	tveeprom_info("tuner model is %s (idx %d, type %d)\n",
706 		t_name1, tuner1, tvee->tuner_type);
707 	tveeprom_info("TV standards%s%s%s%s%s%s%s%s (eeprom 0x%02x)\n",
708 		t_fmt_name1[0], t_fmt_name1[1], t_fmt_name1[2],
709 		t_fmt_name1[3],	t_fmt_name1[4], t_fmt_name1[5],
710 		t_fmt_name1[6], t_fmt_name1[7],	t_format1);
711 	if (tuner2)
712 		tveeprom_info("second tuner model is %s (idx %d, type %d)\n",
713 					t_name2, tuner2, tvee->tuner2_type);
714 	if (t_format2)
715 		tveeprom_info("TV standards%s%s%s%s%s%s%s%s (eeprom 0x%02x)\n",
716 			t_fmt_name2[0], t_fmt_name2[1], t_fmt_name2[2],
717 			t_fmt_name2[3],	t_fmt_name2[4], t_fmt_name2[5],
718 			t_fmt_name2[6], t_fmt_name2[7], t_format2);
719 	if (audioic < 0) {
720 		tveeprom_info("audio processor is unknown (no idx)\n");
721 		tvee->audio_processor = V4L2_IDENT_UNKNOWN;
722 	} else {
723 		if (audioic < ARRAY_SIZE(audioIC))
724 			tveeprom_info("audio processor is %s (idx %d)\n",
725 					audioIC[audioic].name, audioic);
726 		else
727 			tveeprom_info("audio processor is unknown (idx %d)\n",
728 								audioic);
729 	}
730 	if (tvee->decoder_processor)
731 		tveeprom_info("decoder processor is %s (idx %d)\n",
732 			STRM(decoderIC, tvee->decoder_processor),
733 			tvee->decoder_processor);
734 	if (tvee->has_ir)
735 		tveeprom_info("has %sradio, has %sIR receiver, has %sIR transmitter\n",
736 				tvee->has_radio ? "" : "no ",
737 				(tvee->has_ir & 2) ? "" : "no ",
738 				(tvee->has_ir & 4) ? "" : "no ");
739 	else
740 		tveeprom_info("has %sradio\n",
741 				tvee->has_radio ? "" : "no ");
742 }
743 EXPORT_SYMBOL(tveeprom_hauppauge_analog);
744 
745 /* ----------------------------------------------------------------------- */
746 /* generic helper functions                                                */
747 
tveeprom_read(struct i2c_client * c,unsigned char * eedata,int len)748 int tveeprom_read(struct i2c_client *c, unsigned char *eedata, int len)
749 {
750 	unsigned char buf;
751 	int err;
752 
753 	buf = 0;
754 	err = i2c_master_send(c, &buf, 1);
755 	if (err != 1) {
756 		tveeprom_info("Huh, no eeprom present (err=%d)?\n", err);
757 		return -1;
758 	}
759 	err = i2c_master_recv(c, eedata, len);
760 	if (err != len) {
761 		tveeprom_warn("i2c eeprom read error (err=%d)\n", err);
762 		return -1;
763 	}
764 	if (debug) {
765 		int i;
766 
767 		tveeprom_info("full 256-byte eeprom dump:\n");
768 		for (i = 0; i < len; i++) {
769 			if (0 == (i % 16))
770 				tveeprom_info("%02x:", i);
771 			printk(KERN_CONT " %02x", eedata[i]);
772 			if (15 == (i % 16))
773 				printk(KERN_CONT "\n");
774 		}
775 	}
776 	return 0;
777 }
778 EXPORT_SYMBOL(tveeprom_read);
779 
780 /*
781  * Local variables:
782  * c-basic-offset: 8
783  * End:
784  */
785