upload tizen1.0 source
[kernel/linux-2.6.36.git] / drivers / media / dvb / dvb-usb / dw2102.c
1 /* DVB USB framework compliant Linux driver for the
2 *       DVBWorld DVB-S 2101, 2102, DVB-S2 2104, DVB-C 3101,
3 *       TeVii S600, S630, S650,
4 *       Prof 1100, 7500 Cards
5 * Copyright (C) 2008,2009 Igor M. Liplianin (liplianin@me.by)
6 *
7 *       This program is free software; you can redistribute it and/or modify it
8 *       under the terms of the GNU General Public License as published by the
9 *       Free Software Foundation, version 2.
10 *
11 * see Documentation/dvb/README.dvb-usb for more information
12 */
13 #include "dw2102.h"
14 #include "si21xx.h"
15 #include "stv0299.h"
16 #include "z0194a.h"
17 #include "stv0288.h"
18 #include "stb6000.h"
19 #include "eds1547.h"
20 #include "cx24116.h"
21 #include "tda1002x.h"
22 #include "mt312.h"
23 #include "zl10039.h"
24 #include "ds3000.h"
25 #include "stv0900.h"
26 #include "stv6110.h"
27 #include "stb6100.h"
28 #include "stb6100_proc.h"
29
30 #ifndef USB_PID_DW2102
31 #define USB_PID_DW2102 0x2102
32 #endif
33
34 #ifndef USB_PID_DW2104
35 #define USB_PID_DW2104 0x2104
36 #endif
37
38 #ifndef USB_PID_DW3101
39 #define USB_PID_DW3101 0x3101
40 #endif
41
42 #ifndef USB_PID_CINERGY_S
43 #define USB_PID_CINERGY_S 0x0064
44 #endif
45
46 #ifndef USB_PID_TEVII_S630
47 #define USB_PID_TEVII_S630 0xd630
48 #endif
49
50 #ifndef USB_PID_TEVII_S650
51 #define USB_PID_TEVII_S650 0xd650
52 #endif
53
54 #ifndef USB_PID_TEVII_S660
55 #define USB_PID_TEVII_S660 0xd660
56 #endif
57
58 #ifndef USB_PID_PROF_1100
59 #define USB_PID_PROF_1100 0xb012
60 #endif
61
62 #define DW210X_READ_MSG 0
63 #define DW210X_WRITE_MSG 1
64
65 #define REG_1F_SYMBOLRATE_BYTE0 0x1f
66 #define REG_20_SYMBOLRATE_BYTE1 0x20
67 #define REG_21_SYMBOLRATE_BYTE2 0x21
68 /* on my own*/
69 #define DW2102_VOLTAGE_CTRL (0x1800)
70 #define DW2102_RC_QUERY (0x1a00)
71
72 #define err_str "did not find the firmware file. (%s) " \
73                 "Please see linux/Documentation/dvb/ for more details " \
74                 "on firmware-problems."
75
76 struct ir_codes_dvb_usb_table_table {
77         struct ir_scancode *rc_keys;
78         int rc_keys_size;
79 };
80
81 /* debug */
82 static int dvb_usb_dw2102_debug;
83 module_param_named(debug, dvb_usb_dw2102_debug, int, 0644);
84 MODULE_PARM_DESC(debug, "set debugging level (1=info 2=xfer 4=rc(or-able))."
85                                                 DVB_USB_DEBUG_STATUS);
86
87 /* keymaps */
88 static int ir_keymap;
89 module_param_named(keymap, ir_keymap, int, 0644);
90 MODULE_PARM_DESC(keymap, "set keymap 0=default 1=dvbworld 2=tevii 3=tbs  ...");
91
92 /* demod probe */
93 static int demod_probe = 1;
94 module_param_named(demod, demod_probe, int, 0644);
95 MODULE_PARM_DESC(demod, "demod to probe (1=cx24116 2=stv0903+stv6110 "
96                         "4=stv0903+stb6100(or-able)).");
97
98 DVB_DEFINE_MOD_OPT_ADAPTER_NR(adapter_nr);
99
100 static int dw210x_op_rw(struct usb_device *dev, u8 request, u16 value,
101                         u16 index, u8 * data, u16 len, int flags)
102 {
103         int ret;
104         u8 u8buf[len];
105
106         unsigned int pipe = (flags == DW210X_READ_MSG) ?
107                                 usb_rcvctrlpipe(dev, 0) : usb_sndctrlpipe(dev, 0);
108         u8 request_type = (flags == DW210X_READ_MSG) ? USB_DIR_IN : USB_DIR_OUT;
109
110         if (flags == DW210X_WRITE_MSG)
111                 memcpy(u8buf, data, len);
112         ret = usb_control_msg(dev, pipe, request, request_type | USB_TYPE_VENDOR,
113                                 value, index , u8buf, len, 2000);
114
115         if (flags == DW210X_READ_MSG)
116                 memcpy(data, u8buf, len);
117         return ret;
118 }
119
120 /* I2C */
121 static int dw2102_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
122                 int num)
123 {
124         struct dvb_usb_device *d = i2c_get_adapdata(adap);
125         int i = 0, ret = 0;
126         u8 buf6[] = {0x2c, 0x05, 0xc0, 0, 0, 0, 0};
127         u16 value;
128
129         if (!d)
130                 return -ENODEV;
131         if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
132                 return -EAGAIN;
133
134         switch (num) {
135         case 2:
136                 /* read stv0299 register */
137                 value = msg[0].buf[0];/* register */
138                 for (i = 0; i < msg[1].len; i++) {
139                         value = value + i;
140                         ret = dw210x_op_rw(d->udev, 0xb5, value, 0,
141                                         buf6, 2, DW210X_READ_MSG);
142                         msg[1].buf[i] = buf6[0];
143                 }
144                 break;
145         case 1:
146                 switch (msg[0].addr) {
147                 case 0x68:
148                         /* write to stv0299 register */
149                         buf6[0] = 0x2a;
150                         buf6[1] = msg[0].buf[0];
151                         buf6[2] = msg[0].buf[1];
152                         ret = dw210x_op_rw(d->udev, 0xb2, 0, 0,
153                                         buf6, 3, DW210X_WRITE_MSG);
154                         break;
155                 case 0x60:
156                         if (msg[0].flags == 0) {
157                         /* write to tuner pll */
158                                 buf6[0] = 0x2c;
159                                 buf6[1] = 5;
160                                 buf6[2] = 0xc0;
161                                 buf6[3] = msg[0].buf[0];
162                                 buf6[4] = msg[0].buf[1];
163                                 buf6[5] = msg[0].buf[2];
164                                 buf6[6] = msg[0].buf[3];
165                                 ret = dw210x_op_rw(d->udev, 0xb2, 0, 0,
166                                                 buf6, 7, DW210X_WRITE_MSG);
167                         } else {
168                         /* read from tuner */
169                                 ret = dw210x_op_rw(d->udev, 0xb5, 0, 0,
170                                                 buf6, 1, DW210X_READ_MSG);
171                                 msg[0].buf[0] = buf6[0];
172                         }
173                         break;
174                 case (DW2102_RC_QUERY):
175                         ret  = dw210x_op_rw(d->udev, 0xb8, 0, 0,
176                                         buf6, 2, DW210X_READ_MSG);
177                         msg[0].buf[0] = buf6[0];
178                         msg[0].buf[1] = buf6[1];
179                         break;
180                 case (DW2102_VOLTAGE_CTRL):
181                         buf6[0] = 0x30;
182                         buf6[1] = msg[0].buf[0];
183                         ret = dw210x_op_rw(d->udev, 0xb2, 0, 0,
184                                         buf6, 2, DW210X_WRITE_MSG);
185                         break;
186                 }
187
188                 break;
189         }
190
191         mutex_unlock(&d->i2c_mutex);
192         return num;
193 }
194
195 static int dw2102_serit_i2c_transfer(struct i2c_adapter *adap,
196                                                 struct i2c_msg msg[], int num)
197 {
198         struct dvb_usb_device *d = i2c_get_adapdata(adap);
199         int ret = 0;
200         u8 buf6[] = {0, 0, 0, 0, 0, 0, 0};
201
202         if (!d)
203                 return -ENODEV;
204         if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
205                 return -EAGAIN;
206
207         switch (num) {
208         case 2:
209                 /* read si2109 register by number */
210                 buf6[0] = msg[0].addr << 1;
211                 buf6[1] = msg[0].len;
212                 buf6[2] = msg[0].buf[0];
213                 ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
214                                 buf6, msg[0].len + 2, DW210X_WRITE_MSG);
215                 /* read si2109 register */
216                 ret = dw210x_op_rw(d->udev, 0xc3, 0xd0, 0,
217                                 buf6, msg[1].len + 2, DW210X_READ_MSG);
218                 memcpy(msg[1].buf, buf6 + 2, msg[1].len);
219
220                 break;
221         case 1:
222                 switch (msg[0].addr) {
223                 case 0x68:
224                         /* write to si2109 register */
225                         buf6[0] = msg[0].addr << 1;
226                         buf6[1] = msg[0].len;
227                         memcpy(buf6 + 2, msg[0].buf, msg[0].len);
228                         ret = dw210x_op_rw(d->udev, 0xc2, 0, 0, buf6,
229                                         msg[0].len + 2, DW210X_WRITE_MSG);
230                         break;
231                 case(DW2102_RC_QUERY):
232                         ret  = dw210x_op_rw(d->udev, 0xb8, 0, 0,
233                                         buf6, 2, DW210X_READ_MSG);
234                         msg[0].buf[0] = buf6[0];
235                         msg[0].buf[1] = buf6[1];
236                         break;
237                 case(DW2102_VOLTAGE_CTRL):
238                         buf6[0] = 0x30;
239                         buf6[1] = msg[0].buf[0];
240                         ret = dw210x_op_rw(d->udev, 0xb2, 0, 0,
241                                         buf6, 2, DW210X_WRITE_MSG);
242                         break;
243                 }
244                 break;
245         }
246
247         mutex_unlock(&d->i2c_mutex);
248         return num;
249 }
250
251 static int dw2102_earda_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], int num)
252 {
253         struct dvb_usb_device *d = i2c_get_adapdata(adap);
254         int ret = 0;
255
256         if (!d)
257                 return -ENODEV;
258         if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
259                 return -EAGAIN;
260
261         switch (num) {
262         case 2: {
263                 /* read */
264                 /* first write first register number */
265                 u8 ibuf[msg[1].len + 2], obuf[3];
266                 obuf[0] = msg[0].addr << 1;
267                 obuf[1] = msg[0].len;
268                 obuf[2] = msg[0].buf[0];
269                 ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
270                                 obuf, msg[0].len + 2, DW210X_WRITE_MSG);
271                 /* second read registers */
272                 ret = dw210x_op_rw(d->udev, 0xc3, 0xd1 , 0,
273                                 ibuf, msg[1].len + 2, DW210X_READ_MSG);
274                 memcpy(msg[1].buf, ibuf + 2, msg[1].len);
275
276                 break;
277         }
278         case 1:
279                 switch (msg[0].addr) {
280                 case 0x68: {
281                         /* write to register */
282                         u8 obuf[msg[0].len + 2];
283                         obuf[0] = msg[0].addr << 1;
284                         obuf[1] = msg[0].len;
285                         memcpy(obuf + 2, msg[0].buf, msg[0].len);
286                         ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
287                                         obuf, msg[0].len + 2, DW210X_WRITE_MSG);
288                         break;
289                 }
290                 case 0x61: {
291                         /* write to tuner */
292                         u8 obuf[msg[0].len + 2];
293                         obuf[0] = msg[0].addr << 1;
294                         obuf[1] = msg[0].len;
295                         memcpy(obuf + 2, msg[0].buf, msg[0].len);
296                         ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
297                                         obuf, msg[0].len + 2, DW210X_WRITE_MSG);
298                         break;
299                 }
300                 case(DW2102_RC_QUERY): {
301                         u8 ibuf[2];
302                         ret  = dw210x_op_rw(d->udev, 0xb8, 0, 0,
303                                         ibuf, 2, DW210X_READ_MSG);
304                         memcpy(msg[0].buf, ibuf , 2);
305                         break;
306                 }
307                 case(DW2102_VOLTAGE_CTRL): {
308                         u8 obuf[2];
309                         obuf[0] = 0x30;
310                         obuf[1] = msg[0].buf[0];
311                         ret = dw210x_op_rw(d->udev, 0xb2, 0, 0,
312                                         obuf, 2, DW210X_WRITE_MSG);
313                         break;
314                 }
315                 }
316
317                 break;
318         }
319
320         mutex_unlock(&d->i2c_mutex);
321         return num;
322 }
323
324 static int dw2104_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[], int num)
325 {
326         struct dvb_usb_device *d = i2c_get_adapdata(adap);
327         int ret = 0;
328         int len, i, j;
329
330         if (!d)
331                 return -ENODEV;
332         if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
333                 return -EAGAIN;
334
335         for (j = 0; j < num; j++) {
336                 switch (msg[j].addr) {
337                 case(DW2102_RC_QUERY): {
338                         u8 ibuf[2];
339                         ret  = dw210x_op_rw(d->udev, 0xb8, 0, 0,
340                                         ibuf, 2, DW210X_READ_MSG);
341                         memcpy(msg[j].buf, ibuf , 2);
342                         break;
343                 }
344                 case(DW2102_VOLTAGE_CTRL): {
345                         u8 obuf[2];
346                         obuf[0] = 0x30;
347                         obuf[1] = msg[j].buf[0];
348                         ret = dw210x_op_rw(d->udev, 0xb2, 0, 0,
349                                         obuf, 2, DW210X_WRITE_MSG);
350                         break;
351                 }
352                 /*case 0x55: cx24116
353                 case 0x6a: stv0903
354                 case 0x68: ds3000, stv0903
355                 case 0x60: ts2020, stv6110, stb6100 */
356                 default: {
357                         if (msg[j].flags == I2C_M_RD) {
358                                 /* read registers */
359                                 u8  ibuf[msg[j].len + 2];
360                                 ret = dw210x_op_rw(d->udev, 0xc3,
361                                                 (msg[j].addr << 1) + 1, 0,
362                                                 ibuf, msg[j].len + 2,
363                                                 DW210X_READ_MSG);
364                                 memcpy(msg[j].buf, ibuf + 2, msg[j].len);
365                         mdelay(10);
366                         } else if (((msg[j].buf[0] == 0xb0) &&
367                                                 (msg[j].addr == 0x68)) ||
368                                                 ((msg[j].buf[0] == 0xf7) &&
369                                                 (msg[j].addr == 0x55))) {
370                                 /* write firmware */
371                                 u8 obuf[19];
372                                 obuf[0] = msg[j].addr << 1;
373                                 obuf[1] = (msg[j].len > 15 ? 17 : msg[j].len);
374                                 obuf[2] = msg[j].buf[0];
375                                 len = msg[j].len - 1;
376                                 i = 1;
377                                 do {
378                                         memcpy(obuf + 3, msg[j].buf + i,
379                                                         (len > 16 ? 16 : len));
380                                         ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
381                                                 obuf, (len > 16 ? 16 : len) + 3,
382                                                 DW210X_WRITE_MSG);
383                                         i += 16;
384                                         len -= 16;
385                                 } while (len > 0);
386                         } else {
387                                 /* write registers */
388                                 u8 obuf[msg[j].len + 2];
389                                 obuf[0] = msg[j].addr << 1;
390                                 obuf[1] = msg[j].len;
391                                 memcpy(obuf + 2, msg[j].buf, msg[j].len);
392                                 ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
393                                                 obuf, msg[j].len + 2,
394                                                 DW210X_WRITE_MSG);
395                         }
396                         break;
397                 }
398                 }
399
400         }
401
402         mutex_unlock(&d->i2c_mutex);
403         return num;
404 }
405
406 static int dw3101_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
407                                                                 int num)
408 {
409         struct dvb_usb_device *d = i2c_get_adapdata(adap);
410         int ret = 0, i;
411
412         if (!d)
413                 return -ENODEV;
414         if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
415                 return -EAGAIN;
416
417         switch (num) {
418         case 2: {
419                 /* read */
420                 /* first write first register number */
421                 u8 ibuf[msg[1].len + 2], obuf[3];
422                 obuf[0] = msg[0].addr << 1;
423                 obuf[1] = msg[0].len;
424                 obuf[2] = msg[0].buf[0];
425                 ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
426                                 obuf, msg[0].len + 2, DW210X_WRITE_MSG);
427                 /* second read registers */
428                 ret = dw210x_op_rw(d->udev, 0xc3, 0x19 , 0,
429                                 ibuf, msg[1].len + 2, DW210X_READ_MSG);
430                 memcpy(msg[1].buf, ibuf + 2, msg[1].len);
431
432                 break;
433         }
434         case 1:
435                 switch (msg[0].addr) {
436                 case 0x60:
437                 case 0x0c: {
438                         /* write to register */
439                         u8 obuf[msg[0].len + 2];
440                         obuf[0] = msg[0].addr << 1;
441                         obuf[1] = msg[0].len;
442                         memcpy(obuf + 2, msg[0].buf, msg[0].len);
443                         ret = dw210x_op_rw(d->udev, 0xc2, 0, 0,
444                                         obuf, msg[0].len + 2, DW210X_WRITE_MSG);
445                         break;
446                 }
447                 case(DW2102_RC_QUERY): {
448                         u8 ibuf[2];
449                         ret  = dw210x_op_rw(d->udev, 0xb8, 0, 0,
450                                         ibuf, 2, DW210X_READ_MSG);
451                         memcpy(msg[0].buf, ibuf , 2);
452                         break;
453                 }
454                 }
455
456                 break;
457         }
458
459         for (i = 0; i < num; i++) {
460                 deb_xfer("%02x:%02x: %s ", i, msg[i].addr,
461                                 msg[i].flags == 0 ? ">>>" : "<<<");
462                 debug_dump(msg[i].buf, msg[i].len, deb_xfer);
463         }
464
465         mutex_unlock(&d->i2c_mutex);
466         return num;
467 }
468
469 static int s6x0_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
470                                                                 int num)
471 {
472         struct dvb_usb_device *d = i2c_get_adapdata(adap);
473         struct usb_device *udev;
474         int ret = 0;
475         int len, i, j;
476
477         if (!d)
478                 return -ENODEV;
479         udev = d->udev;
480         if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
481                 return -EAGAIN;
482
483         for (j = 0; j < num; j++) {
484                 switch (msg[j].addr) {
485                 case (DW2102_RC_QUERY): {
486                         u8 ibuf[4];
487                         ret  = dw210x_op_rw(d->udev, 0xb8, 0, 0,
488                                         ibuf, 4, DW210X_READ_MSG);
489                         memcpy(msg[j].buf, ibuf + 1, 2);
490                         break;
491                 }
492                 case (DW2102_VOLTAGE_CTRL): {
493                         u8 obuf[2];
494
495                         obuf[0] = 1;
496                         obuf[1] = msg[j].buf[1];/* off-on */
497                         ret = dw210x_op_rw(d->udev, 0x8a, 0, 0,
498                                         obuf, 2, DW210X_WRITE_MSG);
499                         obuf[0] = 3;
500                         obuf[1] = msg[j].buf[0];/* 13v-18v */
501                         ret = dw210x_op_rw(d->udev, 0x8a, 0, 0,
502                                         obuf, 2, DW210X_WRITE_MSG);
503                         break;
504                 }
505                 /*case 0x55: cx24116
506                 case 0x6a: stv0903
507                 case 0x68: ds3000, stv0903
508                 case 0x60: ts2020, stv6110, stb6100
509                 case 0xa0: eeprom */
510                 default: {
511                         if (msg[j].flags == I2C_M_RD) {
512                                 /* read registers */
513                                 u8 ibuf[msg[j].len];
514                                 ret = dw210x_op_rw(d->udev, 0x91, 0, 0,
515                                                 ibuf, msg[j].len,
516                                                 DW210X_READ_MSG);
517                                 memcpy(msg[j].buf, ibuf, msg[j].len);
518                                 break;
519                         } else if ((msg[j].buf[0] == 0xb0) &&
520                                                 (msg[j].addr == 0x68)) {
521                                 /* write firmware */
522                                 u8 obuf[19];
523                                 obuf[0] = (msg[j].len > 16 ?
524                                                 18 : msg[j].len + 1);
525                                 obuf[1] = msg[j].addr << 1;
526                                 obuf[2] = msg[j].buf[0];
527                                 len = msg[j].len - 1;
528                                 i = 1;
529                                 do {
530                                         memcpy(obuf + 3, msg[j].buf + i,
531                                                         (len > 16 ? 16 : len));
532                                         ret = dw210x_op_rw(d->udev, 0x80, 0, 0,
533                                                 obuf, (len > 16 ? 16 : len) + 3,
534                                                 DW210X_WRITE_MSG);
535                                         i += 16;
536                                         len -= 16;
537                                 } while (len > 0);
538                         } else if ((udev->descriptor.idProduct == 0x7500)
539                                         && (j < (num - 1))) {
540                                 /* write register addr before read */
541                                 u8 obuf[msg[j].len + 2];
542                                 obuf[0] = msg[j + 1].len;
543                                 obuf[1] = (msg[j].addr << 1);
544                                 memcpy(obuf + 2, msg[j].buf, msg[j].len);
545                                 ret = dw210x_op_rw(d->udev, 0x92, 0, 0,
546                                                 obuf, msg[j].len + 2,
547                                                 DW210X_WRITE_MSG);
548                                 break;
549                         } else {
550                                 /* write registers */
551                                 u8 obuf[msg[j].len + 2];
552                                 obuf[0] = msg[j].len + 1;
553                                 obuf[1] = (msg[j].addr << 1);
554                                 memcpy(obuf + 2, msg[j].buf, msg[j].len);
555                                 ret = dw210x_op_rw(d->udev,
556                                                 (num > 1 ? 0x90 : 0x80), 0, 0,
557                                                 obuf, msg[j].len + 2,
558                                                 DW210X_WRITE_MSG);
559                                 break;
560                         }
561                         break;
562                 }
563                 }
564
565                 msleep(3);
566         }
567
568         mutex_unlock(&d->i2c_mutex);
569         return num;
570 }
571
572 static u32 dw210x_i2c_func(struct i2c_adapter *adapter)
573 {
574         return I2C_FUNC_I2C;
575 }
576
577 static struct i2c_algorithm dw2102_i2c_algo = {
578         .master_xfer = dw2102_i2c_transfer,
579         .functionality = dw210x_i2c_func,
580 };
581
582 static struct i2c_algorithm dw2102_serit_i2c_algo = {
583         .master_xfer = dw2102_serit_i2c_transfer,
584         .functionality = dw210x_i2c_func,
585 };
586
587 static struct i2c_algorithm dw2102_earda_i2c_algo = {
588         .master_xfer = dw2102_earda_i2c_transfer,
589         .functionality = dw210x_i2c_func,
590 };
591
592 static struct i2c_algorithm dw2104_i2c_algo = {
593         .master_xfer = dw2104_i2c_transfer,
594         .functionality = dw210x_i2c_func,
595 };
596
597 static struct i2c_algorithm dw3101_i2c_algo = {
598         .master_xfer = dw3101_i2c_transfer,
599         .functionality = dw210x_i2c_func,
600 };
601
602 static struct i2c_algorithm s6x0_i2c_algo = {
603         .master_xfer = s6x0_i2c_transfer,
604         .functionality = dw210x_i2c_func,
605 };
606
607 static int dw210x_read_mac_address(struct dvb_usb_device *d, u8 mac[6])
608 {
609         int i;
610         u8 ibuf[] = {0, 0};
611         u8 eeprom[256], eepromline[16];
612
613         for (i = 0; i < 256; i++) {
614                 if (dw210x_op_rw(d->udev, 0xb6, 0xa0 , i, ibuf, 2, DW210X_READ_MSG) < 0) {
615                         err("read eeprom failed.");
616                         return -1;
617                 } else {
618                         eepromline[i%16] = ibuf[0];
619                         eeprom[i] = ibuf[0];
620                 }
621                 if ((i % 16) == 15) {
622                         deb_xfer("%02x: ", i - 15);
623                         debug_dump(eepromline, 16, deb_xfer);
624                 }
625         }
626
627         memcpy(mac, eeprom + 8, 6);
628         return 0;
629 };
630
631 static int s6x0_read_mac_address(struct dvb_usb_device *d, u8 mac[6])
632 {
633         int i, ret;
634         u8 ibuf[] = { 0 }, obuf[] = { 0 };
635         u8 eeprom[256], eepromline[16];
636         struct i2c_msg msg[] = {
637                 {
638                         .addr = 0xa0 >> 1,
639                         .flags = 0,
640                         .buf = obuf,
641                         .len = 1,
642                 }, {
643                         .addr = 0xa0 >> 1,
644                         .flags = I2C_M_RD,
645                         .buf = ibuf,
646                         .len = 1,
647                 }
648         };
649
650         for (i = 0; i < 256; i++) {
651                 obuf[0] = i;
652                 ret = s6x0_i2c_transfer(&d->i2c_adap, msg, 2);
653                 if (ret != 2) {
654                         err("read eeprom failed.");
655                         return -1;
656                 } else {
657                         eepromline[i % 16] = ibuf[0];
658                         eeprom[i] = ibuf[0];
659                 }
660
661                 if ((i % 16) == 15) {
662                         deb_xfer("%02x: ", i - 15);
663                         debug_dump(eepromline, 16, deb_xfer);
664                 }
665         }
666
667         memcpy(mac, eeprom + 16, 6);
668         return 0;
669 };
670
671 static int dw210x_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage)
672 {
673         static u8 command_13v[] = {0x00, 0x01};
674         static u8 command_18v[] = {0x01, 0x01};
675         static u8 command_off[] = {0x00, 0x00};
676         struct i2c_msg msg = {
677                 .addr = DW2102_VOLTAGE_CTRL,
678                 .flags = 0,
679                 .buf = command_off,
680                 .len = 2,
681         };
682
683         struct dvb_usb_adapter *udev_adap =
684                 (struct dvb_usb_adapter *)(fe->dvb->priv);
685         if (voltage == SEC_VOLTAGE_18)
686                 msg.buf = command_18v;
687         else if (voltage == SEC_VOLTAGE_13)
688                 msg.buf = command_13v;
689
690         i2c_transfer(&udev_adap->dev->i2c_adap, &msg, 1);
691
692         return 0;
693 }
694
695 static struct stv0299_config sharp_z0194a_config = {
696         .demod_address = 0x68,
697         .inittab = sharp_z0194a_inittab,
698         .mclk = 88000000UL,
699         .invert = 1,
700         .skip_reinit = 0,
701         .lock_output = STV0299_LOCKOUTPUT_1,
702         .volt13_op0_op1 = STV0299_VOLT13_OP1,
703         .min_delay_ms = 100,
704         .set_symbol_rate = sharp_z0194a_set_symbol_rate,
705 };
706
707 static struct cx24116_config dw2104_config = {
708         .demod_address = 0x55,
709         .mpg_clk_pos_pol = 0x01,
710 };
711
712 static struct si21xx_config serit_sp1511lhb_config = {
713         .demod_address = 0x68,
714         .min_delay_ms = 100,
715
716 };
717
718 static struct tda10023_config dw3101_tda10023_config = {
719         .demod_address = 0x0c,
720         .invert = 1,
721 };
722
723 static struct mt312_config zl313_config = {
724         .demod_address = 0x0e,
725 };
726
727 static struct ds3000_config dw2104_ds3000_config = {
728         .demod_address = 0x68,
729 };
730
731 static struct stv0900_config dw2104a_stv0900_config = {
732         .demod_address = 0x6a,
733         .demod_mode = 0,
734         .xtal = 27000000,
735         .clkmode = 3,/* 0-CLKI, 2-XTALI, else AUTO */
736         .diseqc_mode = 2,/* 2/3 PWM */
737         .tun1_maddress = 0,/* 0x60 */
738         .tun1_adc = 0,/* 2 Vpp */
739         .path1_mode = 3,
740 };
741
742 static struct stb6100_config dw2104a_stb6100_config = {
743         .tuner_address = 0x60,
744         .refclock = 27000000,
745 };
746
747 static struct stv0900_config dw2104_stv0900_config = {
748         .demod_address = 0x68,
749         .demod_mode = 0,
750         .xtal = 8000000,
751         .clkmode = 3,
752         .diseqc_mode = 2,
753         .tun1_maddress = 0,
754         .tun1_adc = 1,/* 1 Vpp */
755         .path1_mode = 3,
756 };
757
758 static struct stv6110_config dw2104_stv6110_config = {
759         .i2c_address = 0x60,
760         .mclk = 16000000,
761         .clk_div = 1,
762 };
763
764 static struct stv0900_config prof_7500_stv0900_config = {
765         .demod_address = 0x6a,
766         .demod_mode = 0,
767         .xtal = 27000000,
768         .clkmode = 3,/* 0-CLKI, 2-XTALI, else AUTO */
769         .diseqc_mode = 2,/* 2/3 PWM */
770         .tun1_maddress = 0,/* 0x60 */
771         .tun1_adc = 0,/* 2 Vpp */
772         .path1_mode = 3,
773         .tun1_type = 3,
774 };
775
776 static int dw2104_frontend_attach(struct dvb_usb_adapter *d)
777 {
778         struct dvb_tuner_ops *tuner_ops = NULL;
779
780         if (demod_probe & 4) {
781                 d->fe = dvb_attach(stv0900_attach, &dw2104a_stv0900_config,
782                                 &d->dev->i2c_adap, 0);
783                 if (d->fe != NULL) {
784                         if (dvb_attach(stb6100_attach, d->fe,
785                                         &dw2104a_stb6100_config,
786                                         &d->dev->i2c_adap)) {
787                                 tuner_ops = &d->fe->ops.tuner_ops;
788                                 tuner_ops->set_frequency = stb6100_set_freq;
789                                 tuner_ops->get_frequency = stb6100_get_freq;
790                                 tuner_ops->set_bandwidth = stb6100_set_bandw;
791                                 tuner_ops->get_bandwidth = stb6100_get_bandw;
792                                 d->fe->ops.set_voltage = dw210x_set_voltage;
793                                 info("Attached STV0900+STB6100!\n");
794                                 return 0;
795                         }
796                 }
797         }
798
799         if (demod_probe & 2) {
800                 d->fe = dvb_attach(stv0900_attach, &dw2104_stv0900_config,
801                                 &d->dev->i2c_adap, 0);
802                 if (d->fe != NULL) {
803                         if (dvb_attach(stv6110_attach, d->fe,
804                                         &dw2104_stv6110_config,
805                                         &d->dev->i2c_adap)) {
806                                 d->fe->ops.set_voltage = dw210x_set_voltage;
807                                 info("Attached STV0900+STV6110A!\n");
808                                 return 0;
809                         }
810                 }
811         }
812
813         if (demod_probe & 1) {
814                 d->fe = dvb_attach(cx24116_attach, &dw2104_config,
815                                 &d->dev->i2c_adap);
816                 if (d->fe != NULL) {
817                         d->fe->ops.set_voltage = dw210x_set_voltage;
818                         info("Attached cx24116!\n");
819                         return 0;
820                 }
821         }
822
823         d->fe = dvb_attach(ds3000_attach, &dw2104_ds3000_config,
824                         &d->dev->i2c_adap);
825         if (d->fe != NULL) {
826                 d->fe->ops.set_voltage = dw210x_set_voltage;
827                 info("Attached DS3000!\n");
828                 return 0;
829         }
830
831         return -EIO;
832 }
833
834 static struct dvb_usb_device_properties dw2102_properties;
835 static struct dvb_usb_device_properties dw2104_properties;
836 static struct dvb_usb_device_properties s6x0_properties;
837
838 static int dw2102_frontend_attach(struct dvb_usb_adapter *d)
839 {
840         if (dw2102_properties.i2c_algo == &dw2102_serit_i2c_algo) {
841                 /*dw2102_properties.adapter->tuner_attach = NULL;*/
842                 d->fe = dvb_attach(si21xx_attach, &serit_sp1511lhb_config,
843                                         &d->dev->i2c_adap);
844                 if (d->fe != NULL) {
845                         d->fe->ops.set_voltage = dw210x_set_voltage;
846                         info("Attached si21xx!\n");
847                         return 0;
848                 }
849         }
850
851         if (dw2102_properties.i2c_algo == &dw2102_earda_i2c_algo) {
852                 d->fe = dvb_attach(stv0288_attach, &earda_config,
853                                         &d->dev->i2c_adap);
854                 if (d->fe != NULL) {
855                         if (dvb_attach(stb6000_attach, d->fe, 0x61,
856                                         &d->dev->i2c_adap)) {
857                                 d->fe->ops.set_voltage = dw210x_set_voltage;
858                                 info("Attached stv0288!\n");
859                                 return 0;
860                         }
861                 }
862         }
863
864         if (dw2102_properties.i2c_algo == &dw2102_i2c_algo) {
865                 /*dw2102_properties.adapter->tuner_attach = dw2102_tuner_attach;*/
866                 d->fe = dvb_attach(stv0299_attach, &sharp_z0194a_config,
867                                         &d->dev->i2c_adap);
868                 if (d->fe != NULL) {
869                         d->fe->ops.set_voltage = dw210x_set_voltage;
870                         info("Attached stv0299!\n");
871                         return 0;
872                 }
873         }
874         return -EIO;
875 }
876
877 static int dw3101_frontend_attach(struct dvb_usb_adapter *d)
878 {
879         d->fe = dvb_attach(tda10023_attach, &dw3101_tda10023_config,
880                                 &d->dev->i2c_adap, 0x48);
881         if (d->fe != NULL) {
882                 info("Attached tda10023!\n");
883                 return 0;
884         }
885         return -EIO;
886 }
887
888 static int s6x0_frontend_attach(struct dvb_usb_adapter *d)
889 {
890         d->fe = dvb_attach(mt312_attach, &zl313_config,
891                         &d->dev->i2c_adap);
892         if (d->fe != NULL) {
893                 if (dvb_attach(zl10039_attach, d->fe, 0x60,
894                                 &d->dev->i2c_adap)) {
895                         d->fe->ops.set_voltage = dw210x_set_voltage;
896                         info("Attached zl100313+zl10039!\n");
897                         return 0;
898                 }
899         }
900
901         d->fe = dvb_attach(stv0288_attach, &earda_config,
902                         &d->dev->i2c_adap);
903         if (d->fe != NULL) {
904                 if (dvb_attach(stb6000_attach, d->fe, 0x61,
905                                 &d->dev->i2c_adap)) {
906                         d->fe->ops.set_voltage = dw210x_set_voltage;
907                         info("Attached stv0288+stb6000!\n");
908                         return 0;
909                 }
910         }
911
912         d->fe = dvb_attach(ds3000_attach, &dw2104_ds3000_config,
913                         &d->dev->i2c_adap);
914         if (d->fe != NULL) {
915                 d->fe->ops.set_voltage = dw210x_set_voltage;
916                 info("Attached ds3000+ds2020!\n");
917                 return 0;
918         }
919
920         return -EIO;
921 }
922
923 static int prof_7500_frontend_attach(struct dvb_usb_adapter *d)
924 {
925         d->fe = dvb_attach(stv0900_attach, &prof_7500_stv0900_config,
926                                         &d->dev->i2c_adap, 0);
927         if (d->fe == NULL)
928                 return -EIO;
929         d->fe->ops.set_voltage = dw210x_set_voltage;
930
931         info("Attached STV0900+STB6100A!\n");
932
933         return 0;
934 }
935
936 static int dw2102_tuner_attach(struct dvb_usb_adapter *adap)
937 {
938         dvb_attach(dvb_pll_attach, adap->fe, 0x60,
939                 &adap->dev->i2c_adap, DVB_PLL_OPERA1);
940         return 0;
941 }
942
943 static int dw3101_tuner_attach(struct dvb_usb_adapter *adap)
944 {
945         dvb_attach(dvb_pll_attach, adap->fe, 0x60,
946                 &adap->dev->i2c_adap, DVB_PLL_TUA6034);
947
948         return 0;
949 }
950
951 static struct ir_scancode ir_codes_dw210x_table[] = {
952         { 0xf80a, KEY_Q },              /*power*/
953         { 0xf80c, KEY_M },              /*mute*/
954         { 0xf811, KEY_1 },
955         { 0xf812, KEY_2 },
956         { 0xf813, KEY_3 },
957         { 0xf814, KEY_4 },
958         { 0xf815, KEY_5 },
959         { 0xf816, KEY_6 },
960         { 0xf817, KEY_7 },
961         { 0xf818, KEY_8 },
962         { 0xf819, KEY_9 },
963         { 0xf810, KEY_0 },
964         { 0xf81c, KEY_PAGEUP }, /*ch+*/
965         { 0xf80f, KEY_PAGEDOWN },       /*ch-*/
966         { 0xf81a, KEY_O },              /*vol+*/
967         { 0xf80e, KEY_Z },              /*vol-*/
968         { 0xf804, KEY_R },              /*rec*/
969         { 0xf809, KEY_D },              /*fav*/
970         { 0xf808, KEY_BACKSPACE },      /*rewind*/
971         { 0xf807, KEY_A },              /*fast*/
972         { 0xf80b, KEY_P },              /*pause*/
973         { 0xf802, KEY_ESC },    /*cancel*/
974         { 0xf803, KEY_G },              /*tab*/
975         { 0xf800, KEY_UP },             /*up*/
976         { 0xf81f, KEY_ENTER },  /*ok*/
977         { 0xf801, KEY_DOWN },   /*down*/
978         { 0xf805, KEY_C },              /*cap*/
979         { 0xf806, KEY_S },              /*stop*/
980         { 0xf840, KEY_F },              /*full*/
981         { 0xf81e, KEY_W },              /*tvmode*/
982         { 0xf81b, KEY_B },              /*recall*/
983 };
984
985 static struct ir_scancode ir_codes_tevii_table[] = {
986         { 0xf80a, KEY_POWER },
987         { 0xf80c, KEY_MUTE },
988         { 0xf811, KEY_1 },
989         { 0xf812, KEY_2 },
990         { 0xf813, KEY_3 },
991         { 0xf814, KEY_4 },
992         { 0xf815, KEY_5 },
993         { 0xf816, KEY_6 },
994         { 0xf817, KEY_7 },
995         { 0xf818, KEY_8 },
996         { 0xf819, KEY_9 },
997         { 0xf810, KEY_0 },
998         { 0xf81c, KEY_MENU },
999         { 0xf80f, KEY_VOLUMEDOWN },
1000         { 0xf81a, KEY_LAST },
1001         { 0xf80e, KEY_OPEN },
1002         { 0xf804, KEY_RECORD },
1003         { 0xf809, KEY_VOLUMEUP },
1004         { 0xf808, KEY_CHANNELUP },
1005         { 0xf807, KEY_PVR },
1006         { 0xf80b, KEY_TIME },
1007         { 0xf802, KEY_RIGHT },
1008         { 0xf803, KEY_LEFT },
1009         { 0xf800, KEY_UP },
1010         { 0xf81f, KEY_OK },
1011         { 0xf801, KEY_DOWN },
1012         { 0xf805, KEY_TUNER },
1013         { 0xf806, KEY_CHANNELDOWN },
1014         { 0xf840, KEY_PLAYPAUSE },
1015         { 0xf81e, KEY_REWIND },
1016         { 0xf81b, KEY_FAVORITES },
1017         { 0xf81d, KEY_BACK },
1018         { 0xf84d, KEY_FASTFORWARD },
1019         { 0xf844, KEY_EPG },
1020         { 0xf84c, KEY_INFO },
1021         { 0xf841, KEY_AB },
1022         { 0xf843, KEY_AUDIO },
1023         { 0xf845, KEY_SUBTITLE },
1024         { 0xf84a, KEY_LIST },
1025         { 0xf846, KEY_F1 },
1026         { 0xf847, KEY_F2 },
1027         { 0xf85e, KEY_F3 },
1028         { 0xf85c, KEY_F4 },
1029         { 0xf852, KEY_F5 },
1030         { 0xf85a, KEY_F6 },
1031         { 0xf856, KEY_MODE },
1032         { 0xf858, KEY_SWITCHVIDEOMODE },
1033 };
1034
1035 static struct ir_scancode ir_codes_tbs_table[] = {
1036         { 0xf884, KEY_POWER },
1037         { 0xf894, KEY_MUTE },
1038         { 0xf887, KEY_1 },
1039         { 0xf886, KEY_2 },
1040         { 0xf885, KEY_3 },
1041         { 0xf88b, KEY_4 },
1042         { 0xf88a, KEY_5 },
1043         { 0xf889, KEY_6 },
1044         { 0xf88f, KEY_7 },
1045         { 0xf88e, KEY_8 },
1046         { 0xf88d, KEY_9 },
1047         { 0xf892, KEY_0 },
1048         { 0xf896, KEY_CHANNELUP },
1049         { 0xf891, KEY_CHANNELDOWN },
1050         { 0xf893, KEY_VOLUMEUP },
1051         { 0xf88c, KEY_VOLUMEDOWN },
1052         { 0xf883, KEY_RECORD },
1053         { 0xf898, KEY_PAUSE  },
1054         { 0xf899, KEY_OK },
1055         { 0xf89a, KEY_SHUFFLE },
1056         { 0xf881, KEY_UP },
1057         { 0xf890, KEY_LEFT },
1058         { 0xf882, KEY_RIGHT },
1059         { 0xf888, KEY_DOWN },
1060         { 0xf895, KEY_FAVORITES },
1061         { 0xf897, KEY_SUBTITLE },
1062         { 0xf89d, KEY_ZOOM },
1063         { 0xf89f, KEY_EXIT },
1064         { 0xf89e, KEY_MENU },
1065         { 0xf89c, KEY_EPG },
1066         { 0xf880, KEY_PREVIOUS },
1067         { 0xf89b, KEY_MODE }
1068 };
1069
1070 static struct ir_codes_dvb_usb_table_table keys_tables[] = {
1071         { ir_codes_dw210x_table, ARRAY_SIZE(ir_codes_dw210x_table) },
1072         { ir_codes_tevii_table, ARRAY_SIZE(ir_codes_tevii_table) },
1073         { ir_codes_tbs_table, ARRAY_SIZE(ir_codes_tbs_table) },
1074 };
1075
1076 static int dw2102_rc_query(struct dvb_usb_device *d, u32 *event, int *state)
1077 {
1078         struct ir_scancode *keymap = d->props.rc.legacy.rc_key_map;
1079         int keymap_size = d->props.rc.legacy.rc_key_map_size;
1080         u8 key[2];
1081         struct i2c_msg msg = {
1082                 .addr = DW2102_RC_QUERY,
1083                 .flags = I2C_M_RD,
1084                 .buf = key,
1085                 .len = 2
1086         };
1087         int i;
1088         /* override keymap */
1089         if ((ir_keymap > 0) && (ir_keymap <= ARRAY_SIZE(keys_tables))) {
1090                 keymap = keys_tables[ir_keymap - 1].rc_keys ;
1091                 keymap_size = keys_tables[ir_keymap - 1].rc_keys_size;
1092         }
1093
1094         *state = REMOTE_NO_KEY_PRESSED;
1095         if (d->props.i2c_algo->master_xfer(&d->i2c_adap, &msg, 1) == 1) {
1096                 for (i = 0; i < keymap_size ; i++) {
1097                         if (rc5_data(&keymap[i]) == msg.buf[0]) {
1098                                 *state = REMOTE_KEY_PRESSED;
1099                                 *event = keymap[i].keycode;
1100                                 break;
1101                         }
1102
1103                 }
1104
1105                 if ((*state) == REMOTE_KEY_PRESSED)
1106                         deb_rc("%s: found rc key: %x, %x, event: %x\n",
1107                                         __func__, key[0], key[1], (*event));
1108                 else if (key[0] != 0xff)
1109                         deb_rc("%s: unknown rc key: %x, %x\n",
1110                                         __func__, key[0], key[1]);
1111
1112         }
1113
1114         return 0;
1115 }
1116
1117 static struct usb_device_id dw2102_table[] = {
1118         {USB_DEVICE(USB_VID_CYPRESS, USB_PID_DW2102)},
1119         {USB_DEVICE(USB_VID_CYPRESS, 0x2101)},
1120         {USB_DEVICE(USB_VID_CYPRESS, USB_PID_DW2104)},
1121         {USB_DEVICE(0x9022, USB_PID_TEVII_S650)},
1122         {USB_DEVICE(USB_VID_TERRATEC, USB_PID_CINERGY_S)},
1123         {USB_DEVICE(USB_VID_CYPRESS, USB_PID_DW3101)},
1124         {USB_DEVICE(0x9022, USB_PID_TEVII_S630)},
1125         {USB_DEVICE(0x3011, USB_PID_PROF_1100)},
1126         {USB_DEVICE(0x9022, USB_PID_TEVII_S660)},
1127         {USB_DEVICE(0x3034, 0x7500)},
1128         { }
1129 };
1130
1131 MODULE_DEVICE_TABLE(usb, dw2102_table);
1132
1133 static int dw2102_load_firmware(struct usb_device *dev,
1134                         const struct firmware *frmwr)
1135 {
1136         u8 *b, *p;
1137         int ret = 0, i;
1138         u8 reset;
1139         u8 reset16[] = {0, 0, 0, 0, 0, 0, 0};
1140         const struct firmware *fw;
1141         const char *fw_2101 = "dvb-usb-dw2101.fw";
1142
1143         switch (dev->descriptor.idProduct) {
1144         case 0x2101:
1145                 ret = request_firmware(&fw, fw_2101, &dev->dev);
1146                 if (ret != 0) {
1147                         err(err_str, fw_2101);
1148                         return ret;
1149                 }
1150                 break;
1151         default:
1152                 fw = frmwr;
1153                 break;
1154         }
1155         info("start downloading DW210X firmware");
1156         p = kmalloc(fw->size, GFP_KERNEL);
1157         reset = 1;
1158         /*stop the CPU*/
1159         dw210x_op_rw(dev, 0xa0, 0x7f92, 0, &reset, 1, DW210X_WRITE_MSG);
1160         dw210x_op_rw(dev, 0xa0, 0xe600, 0, &reset, 1, DW210X_WRITE_MSG);
1161
1162         if (p != NULL) {
1163                 memcpy(p, fw->data, fw->size);
1164                 for (i = 0; i < fw->size; i += 0x40) {
1165                         b = (u8 *) p + i;
1166                         if (dw210x_op_rw(dev, 0xa0, i, 0, b , 0x40,
1167                                         DW210X_WRITE_MSG) != 0x40) {
1168                                 err("error while transferring firmware");
1169                                 ret = -EINVAL;
1170                                 break;
1171                         }
1172                 }
1173                 /* restart the CPU */
1174                 reset = 0;
1175                 if (ret || dw210x_op_rw(dev, 0xa0, 0x7f92, 0, &reset, 1,
1176                                         DW210X_WRITE_MSG) != 1) {
1177                         err("could not restart the USB controller CPU.");
1178                         ret = -EINVAL;
1179                 }
1180                 if (ret || dw210x_op_rw(dev, 0xa0, 0xe600, 0, &reset, 1,
1181                                         DW210X_WRITE_MSG) != 1) {
1182                         err("could not restart the USB controller CPU.");
1183                         ret = -EINVAL;
1184                 }
1185                 /* init registers */
1186                 switch (dev->descriptor.idProduct) {
1187                 case USB_PID_PROF_1100:
1188                         s6x0_properties.rc.legacy.rc_key_map = ir_codes_tbs_table;
1189                         s6x0_properties.rc.legacy.rc_key_map_size =
1190                                         ARRAY_SIZE(ir_codes_tbs_table);
1191                         break;
1192                 case USB_PID_TEVII_S650:
1193                         dw2104_properties.rc.legacy.rc_key_map = ir_codes_tevii_table;
1194                         dw2104_properties.rc.legacy.rc_key_map_size =
1195                                         ARRAY_SIZE(ir_codes_tevii_table);
1196                 case USB_PID_DW2104:
1197                         reset = 1;
1198                         dw210x_op_rw(dev, 0xc4, 0x0000, 0, &reset, 1,
1199                                         DW210X_WRITE_MSG);
1200                         /* break omitted intentionally */
1201                 case USB_PID_DW3101:
1202                         reset = 0;
1203                         dw210x_op_rw(dev, 0xbf, 0x0040, 0, &reset, 0,
1204                                         DW210X_WRITE_MSG);
1205                         break;
1206                 case USB_PID_CINERGY_S:
1207                 case USB_PID_DW2102:
1208                         dw210x_op_rw(dev, 0xbf, 0x0040, 0, &reset, 0,
1209                                         DW210X_WRITE_MSG);
1210                         dw210x_op_rw(dev, 0xb9, 0x0000, 0, &reset16[0], 2,
1211                                         DW210X_READ_MSG);
1212                         /* check STV0299 frontend  */
1213                         dw210x_op_rw(dev, 0xb5, 0, 0, &reset16[0], 2,
1214                                         DW210X_READ_MSG);
1215                         if ((reset16[0] == 0xa1) || (reset16[0] == 0x80)) {
1216                                 dw2102_properties.i2c_algo = &dw2102_i2c_algo;
1217                                 dw2102_properties.adapter->tuner_attach = &dw2102_tuner_attach;
1218                                 break;
1219                         } else {
1220                                 /* check STV0288 frontend  */
1221                                 reset16[0] = 0xd0;
1222                                 reset16[1] = 1;
1223                                 reset16[2] = 0;
1224                                 dw210x_op_rw(dev, 0xc2, 0, 0, &reset16[0], 3,
1225                                                 DW210X_WRITE_MSG);
1226                                 dw210x_op_rw(dev, 0xc3, 0xd1, 0, &reset16[0], 3,
1227                                                 DW210X_READ_MSG);
1228                                 if (reset16[2] == 0x11) {
1229                                         dw2102_properties.i2c_algo = &dw2102_earda_i2c_algo;
1230                                         break;
1231                                 }
1232                         }
1233                 case 0x2101:
1234                         dw210x_op_rw(dev, 0xbc, 0x0030, 0, &reset16[0], 2,
1235                                         DW210X_READ_MSG);
1236                         dw210x_op_rw(dev, 0xba, 0x0000, 0, &reset16[0], 7,
1237                                         DW210X_READ_MSG);
1238                         dw210x_op_rw(dev, 0xba, 0x0000, 0, &reset16[0], 7,
1239                                         DW210X_READ_MSG);
1240                         dw210x_op_rw(dev, 0xb9, 0x0000, 0, &reset16[0], 2,
1241                                         DW210X_READ_MSG);
1242                         break;
1243                 }
1244
1245                 msleep(100);
1246                 kfree(p);
1247         }
1248         return ret;
1249 }
1250
1251 static struct dvb_usb_device_properties dw2102_properties = {
1252         .caps = DVB_USB_IS_AN_I2C_ADAPTER,
1253         .usb_ctrl = DEVICE_SPECIFIC,
1254         .firmware = "dvb-usb-dw2102.fw",
1255         .no_reconnect = 1,
1256
1257         .i2c_algo = &dw2102_serit_i2c_algo,
1258
1259         .rc.legacy = {
1260                 .rc_key_map = ir_codes_dw210x_table,
1261                 .rc_key_map_size = ARRAY_SIZE(ir_codes_dw210x_table),
1262                 .rc_interval = 150,
1263                 .rc_query = dw2102_rc_query,
1264         },
1265
1266         .generic_bulk_ctrl_endpoint = 0x81,
1267         /* parameter for the MPEG2-data transfer */
1268         .num_adapters = 1,
1269         .download_firmware = dw2102_load_firmware,
1270         .read_mac_address = dw210x_read_mac_address,
1271         .adapter = {
1272                 {
1273                         .frontend_attach = dw2102_frontend_attach,
1274                         .streaming_ctrl = NULL,
1275                         .tuner_attach = NULL,
1276                         .stream = {
1277                                 .type = USB_BULK,
1278                                 .count = 8,
1279                                 .endpoint = 0x82,
1280                                 .u = {
1281                                         .bulk = {
1282                                                 .buffersize = 4096,
1283                                         }
1284                                 }
1285                         },
1286                 }
1287         },
1288         .num_device_descs = 3,
1289         .devices = {
1290                 {"DVBWorld DVB-S 2102 USB2.0",
1291                         {&dw2102_table[0], NULL},
1292                         {NULL},
1293                 },
1294                 {"DVBWorld DVB-S 2101 USB2.0",
1295                         {&dw2102_table[1], NULL},
1296                         {NULL},
1297                 },
1298                 {"TerraTec Cinergy S USB",
1299                         {&dw2102_table[4], NULL},
1300                         {NULL},
1301                 },
1302         }
1303 };
1304
1305 static struct dvb_usb_device_properties dw2104_properties = {
1306         .caps = DVB_USB_IS_AN_I2C_ADAPTER,
1307         .usb_ctrl = DEVICE_SPECIFIC,
1308         .firmware = "dvb-usb-dw2104.fw",
1309         .no_reconnect = 1,
1310
1311         .i2c_algo = &dw2104_i2c_algo,
1312         .rc.legacy = {
1313                 .rc_key_map = ir_codes_dw210x_table,
1314                 .rc_key_map_size = ARRAY_SIZE(ir_codes_dw210x_table),
1315                 .rc_interval = 150,
1316                 .rc_query = dw2102_rc_query,
1317         },
1318
1319         .generic_bulk_ctrl_endpoint = 0x81,
1320         /* parameter for the MPEG2-data transfer */
1321         .num_adapters = 1,
1322         .download_firmware = dw2102_load_firmware,
1323         .read_mac_address = dw210x_read_mac_address,
1324         .adapter = {
1325                 {
1326                         .frontend_attach = dw2104_frontend_attach,
1327                         .streaming_ctrl = NULL,
1328                         /*.tuner_attach = dw2104_tuner_attach,*/
1329                         .stream = {
1330                                 .type = USB_BULK,
1331                                 .count = 8,
1332                                 .endpoint = 0x82,
1333                                 .u = {
1334                                         .bulk = {
1335                                                 .buffersize = 4096,
1336                                         }
1337                                 }
1338                         },
1339                 }
1340         },
1341         .num_device_descs = 2,
1342         .devices = {
1343                 { "DVBWorld DW2104 USB2.0",
1344                         {&dw2102_table[2], NULL},
1345                         {NULL},
1346                 },
1347                 { "TeVii S650 USB2.0",
1348                         {&dw2102_table[3], NULL},
1349                         {NULL},
1350                 },
1351         }
1352 };
1353
1354 static struct dvb_usb_device_properties dw3101_properties = {
1355         .caps = DVB_USB_IS_AN_I2C_ADAPTER,
1356         .usb_ctrl = DEVICE_SPECIFIC,
1357         .firmware = "dvb-usb-dw3101.fw",
1358         .no_reconnect = 1,
1359
1360         .i2c_algo = &dw3101_i2c_algo,
1361         .rc.legacy = {
1362                 .rc_key_map = ir_codes_dw210x_table,
1363                 .rc_key_map_size = ARRAY_SIZE(ir_codes_dw210x_table),
1364                 .rc_interval = 150,
1365                 .rc_query = dw2102_rc_query,
1366         },
1367
1368         .generic_bulk_ctrl_endpoint = 0x81,
1369         /* parameter for the MPEG2-data transfer */
1370         .num_adapters = 1,
1371         .download_firmware = dw2102_load_firmware,
1372         .read_mac_address = dw210x_read_mac_address,
1373         .adapter = {
1374                 {
1375                         .frontend_attach = dw3101_frontend_attach,
1376                         .streaming_ctrl = NULL,
1377                         .tuner_attach = dw3101_tuner_attach,
1378                         .stream = {
1379                                 .type = USB_BULK,
1380                                 .count = 8,
1381                                 .endpoint = 0x82,
1382                                 .u = {
1383                                         .bulk = {
1384                                                 .buffersize = 4096,
1385                                         }
1386                                 }
1387                         },
1388                 }
1389         },
1390         .num_device_descs = 1,
1391         .devices = {
1392                 { "DVBWorld DVB-C 3101 USB2.0",
1393                         {&dw2102_table[5], NULL},
1394                         {NULL},
1395                 },
1396         }
1397 };
1398
1399 static struct dvb_usb_device_properties s6x0_properties = {
1400         .caps = DVB_USB_IS_AN_I2C_ADAPTER,
1401         .usb_ctrl = DEVICE_SPECIFIC,
1402         .firmware = "dvb-usb-s630.fw",
1403         .no_reconnect = 1,
1404
1405         .i2c_algo = &s6x0_i2c_algo,
1406         .rc.legacy = {
1407                 .rc_key_map = ir_codes_tevii_table,
1408                 .rc_key_map_size = ARRAY_SIZE(ir_codes_tevii_table),
1409                 .rc_interval = 150,
1410                 .rc_query = dw2102_rc_query,
1411         },
1412
1413         .generic_bulk_ctrl_endpoint = 0x81,
1414         .num_adapters = 1,
1415         .download_firmware = dw2102_load_firmware,
1416         .read_mac_address = s6x0_read_mac_address,
1417         .adapter = {
1418                 {
1419                         .frontend_attach = s6x0_frontend_attach,
1420                         .streaming_ctrl = NULL,
1421                         .tuner_attach = NULL,
1422                         .stream = {
1423                                 .type = USB_BULK,
1424                                 .count = 8,
1425                                 .endpoint = 0x82,
1426                                 .u = {
1427                                         .bulk = {
1428                                                 .buffersize = 4096,
1429                                         }
1430                                 }
1431                         },
1432                 }
1433         },
1434         .num_device_descs = 3,
1435         .devices = {
1436                 {"TeVii S630 USB",
1437                         {&dw2102_table[6], NULL},
1438                         {NULL},
1439                 },
1440                 {"Prof 1100 USB ",
1441                         {&dw2102_table[7], NULL},
1442                         {NULL},
1443                 },
1444                 {"TeVii S660 USB",
1445                         {&dw2102_table[8], NULL},
1446                         {NULL},
1447                 },
1448         }
1449 };
1450
1451 struct dvb_usb_device_properties *p7500;
1452 static struct dvb_usb_device_description d7500 = {
1453         "Prof 7500 USB DVB-S2",
1454         {&dw2102_table[9], NULL},
1455         {NULL},
1456 };
1457
1458 static int dw2102_probe(struct usb_interface *intf,
1459                 const struct usb_device_id *id)
1460 {
1461
1462         p7500 = kzalloc(sizeof(struct dvb_usb_device_properties), GFP_KERNEL);
1463         if (!p7500)
1464                 return -ENOMEM;
1465         /* copy default structure */
1466         memcpy(p7500, &s6x0_properties,
1467                         sizeof(struct dvb_usb_device_properties));
1468         /* fill only different fields */
1469         p7500->firmware = "dvb-usb-p7500.fw";
1470         p7500->devices[0] = d7500;
1471         p7500->rc.legacy.rc_key_map = ir_codes_tbs_table;
1472         p7500->rc.legacy.rc_key_map_size = ARRAY_SIZE(ir_codes_tbs_table);
1473         p7500->adapter->frontend_attach = prof_7500_frontend_attach;
1474
1475         if (0 == dvb_usb_device_init(intf, &dw2102_properties,
1476                         THIS_MODULE, NULL, adapter_nr) ||
1477             0 == dvb_usb_device_init(intf, &dw2104_properties,
1478                         THIS_MODULE, NULL, adapter_nr) ||
1479             0 == dvb_usb_device_init(intf, &dw3101_properties,
1480                         THIS_MODULE, NULL, adapter_nr) ||
1481             0 == dvb_usb_device_init(intf, &s6x0_properties,
1482                         THIS_MODULE, NULL, adapter_nr) ||
1483             0 == dvb_usb_device_init(intf, p7500,
1484                         THIS_MODULE, NULL, adapter_nr))
1485                 return 0;
1486
1487         return -ENODEV;
1488 }
1489
1490 static struct usb_driver dw2102_driver = {
1491         .name = "dw2102",
1492         .probe = dw2102_probe,
1493         .disconnect = dvb_usb_device_exit,
1494         .id_table = dw2102_table,
1495 };
1496
1497 static int __init dw2102_module_init(void)
1498 {
1499         int ret =  usb_register(&dw2102_driver);
1500         if (ret)
1501                 err("usb_register failed. Error number %d", ret);
1502
1503         return ret;
1504 }
1505
1506 static void __exit dw2102_module_exit(void)
1507 {
1508         usb_deregister(&dw2102_driver);
1509 }
1510
1511 module_init(dw2102_module_init);
1512 module_exit(dw2102_module_exit);
1513
1514 MODULE_AUTHOR("Igor M. Liplianin (c) liplianin@me.by");
1515 MODULE_DESCRIPTION("Driver for DVBWorld DVB-S 2101, 2102, DVB-S2 2104,"
1516                                 " DVB-C 3101 USB2.0,"
1517                                 " TeVii S600, S630, S650, S660 USB2.0,"
1518                                 " Prof 1100, 7500 USB2.0 devices");
1519 MODULE_VERSION("0.1");
1520 MODULE_LICENSE("GPL");