blob: 518d7ad217df23edab68316fda6510b11e7a3035 [file] [log] [blame]
Marco Gittler941491f2007-04-19 11:26:47 -03001/* DVB USB framework compliant Linux driver for the Opera1 DVB-S Card
2*
3* Copyright (C) 2006 Mario Hlawitschka (dh1pa@amsat.org)
4* Copyright (C) 2006 Marco Gittler (g.marco@freenet.de)
5*
6* This program is free software; you can redistribute it and/or modify it
7* under the terms of the GNU General Public License as published by the Free
8* Software Foundation, version 2.
9*
10* see Documentation/dvb/README.dvb-usb for more information
11*/
12
13#include "opera1.h"
14#include "stv0299.h"
15
16#define OPERA_READ_MSG 0
17#define OPERA_WRITE_MSG 1
18#define OPERA_I2C_TUNER 0xd1
19
20#define READ_FX2_REG_REQ 0xba
21#define READ_MAC_ADDR 0x08
22#define OPERA_WRITE_FX2 0xbb
23#define OPERA_TUNER_REQ 0xb1
24#define REG_1F_SYMBOLRATE_BYTE0 0x1f
25#define REG_20_SYMBOLRATE_BYTE1 0x20
26#define REG_21_SYMBOLRATE_BYTE2 0x21
27
Marco Gittler86534e52007-04-23 17:52:58 -030028#define ADDR_B600_VOLTAGE_13V (0x02)
29#define ADDR_B601_VOLTAGE_18V (0x03)
30#define ADDR_B1A6_STREAM_CTRL (0x04)
31#define ADDR_B880_READ_REMOTE (0x05)
32
Marco Gittler941491f2007-04-19 11:26:47 -030033struct opera1_state {
34 u32 last_key_pressed;
35};
36struct opera_rc_keys {
37 u32 keycode;
38 u32 event;
39};
40
41int dvb_usb_opera1_debug;
42module_param_named(debug, dvb_usb_opera1_debug, int, 0644);
43MODULE_PARM_DESC(debug,
44 "set debugging level (1=info,xfer=2,pll=4,ts=8,err=16,rc=32,fw=64 (or-able))."
45 DVB_USB_DEBUG_STATUS);
46
47static int opera1_xilinx_rw(struct usb_device *dev, u8 request, u16 value,
48 u8 * data, u16 len, int flags)
49{
50 int ret;
51 u8 r;
52 u8 u8buf[len];
53
54 unsigned int pipe = (flags == OPERA_READ_MSG) ?
55 usb_rcvctrlpipe(dev,0) : usb_sndctrlpipe(dev, 0);
56 u8 request_type = (flags == OPERA_READ_MSG) ? USB_DIR_IN : USB_DIR_OUT;
57
58 if (flags == OPERA_WRITE_MSG)
59 memcpy(u8buf, data, len);
60 ret =
61 usb_control_msg(dev, pipe, request, request_type | USB_TYPE_VENDOR,
62 value, 0x0, u8buf, len, 2000);
63
64 if (request == OPERA_TUNER_REQ) {
65 if (usb_control_msg(dev, usb_rcvctrlpipe(dev, 0),
66 OPERA_TUNER_REQ, USB_DIR_IN | USB_TYPE_VENDOR,
67 0x01, 0x0, &r, 1, 2000)<1 || r!=0x08)
68 return 0;
69 }
70 if (flags == OPERA_READ_MSG)
71 memcpy(data, u8buf, len);
72 return ret;
73}
74
75/* I2C */
76
77static int opera1_usb_i2c_msgxfer(struct dvb_usb_device *dev, u16 addr,
Marco Gittler86534e52007-04-23 17:52:58 -030078 u8 * buf, u16 len)
Marco Gittler941491f2007-04-19 11:26:47 -030079{
80 int ret = 0;
81 u8 request;
82 u16 value;
83
84 if (!dev) {
85 info("no usb_device");
86 return -EINVAL;
87 }
88 if (mutex_lock_interruptible(&dev->usb_mutex) < 0)
89 return -EAGAIN;
90
Marco Gittler86534e52007-04-23 17:52:58 -030091 switch (addr>>1){
92 case ADDR_B600_VOLTAGE_13V:
93 request=0xb6;
94 value=0x00;
95 break;
96 case ADDR_B601_VOLTAGE_18V:
97 request=0xb6;
98 value=0x01;
99 break;
100 case ADDR_B1A6_STREAM_CTRL:
101 request=0xb1;
102 value=0xa6;
103 break;
104 case ADDR_B880_READ_REMOTE:
105 request=0xb8;
106 value=0x80;
107 break;
108 default:
109 request=0xb1;
110 value=addr;
Marco Gittler941491f2007-04-19 11:26:47 -0300111 }
Marco Gittler86534e52007-04-23 17:52:58 -0300112 ret = opera1_xilinx_rw(dev->udev, request,
113 value, buf, len,
114 addr&0x01?OPERA_READ_MSG:OPERA_WRITE_MSG);
Marco Gittler941491f2007-04-19 11:26:47 -0300115
116 mutex_unlock(&dev->usb_mutex);
117 return ret;
118}
119
120static int opera1_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[],
121 int num)
122{
123 struct dvb_usb_device *d = i2c_get_adapdata(adap);
124 int i = 0, tmp = 0;
125
126 if (!d)
127 return -ENODEV;
128 if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
129 return -EAGAIN;
130
131 for (i = 0; i < num; i++) {
132 if ((tmp = opera1_usb_i2c_msgxfer(d,
Marco Gittler86534e52007-04-23 17:52:58 -0300133 (msg[i].addr<<1)|(msg[i].flags&I2C_M_RD?0x01:0),
Marco Gittler941491f2007-04-19 11:26:47 -0300134 msg[i].buf,
Marco Gittler86534e52007-04-23 17:52:58 -0300135 msg[i].len
136 )!= msg[i].len)) {
Marco Gittler941491f2007-04-19 11:26:47 -0300137 break;
138 }
139 if (dvb_usb_opera1_debug & 0x10)
140 info("sending i2c mesage %d %d", tmp, msg[i].len);
141 }
142 mutex_unlock(&d->i2c_mutex);
143 return num;
144}
145
146static u32 opera1_i2c_func(struct i2c_adapter *adapter)
147{
148 return I2C_FUNC_I2C;
149}
150
151static struct i2c_algorithm opera1_i2c_algo = {
152 .master_xfer = opera1_i2c_xfer,
153 .functionality = opera1_i2c_func,
154};
155
156static int opera1_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage)
157{
158 static u8 command_13v[1]={0x00};
159 static u8 command_18v[1]={0x01};
160 struct i2c_msg msg[] = {
Marco Gittler86534e52007-04-23 17:52:58 -0300161 {.addr = ADDR_B600_VOLTAGE_13V,.flags = 0,.buf = command_13v,.len = 1},
Marco Gittler941491f2007-04-19 11:26:47 -0300162 };
163 struct dvb_usb_adapter *udev_adap =
164 (struct dvb_usb_adapter *)(fe->dvb->priv);
165 if (voltage == SEC_VOLTAGE_18) {
Marco Gittler86534e52007-04-23 17:52:58 -0300166 msg[0].addr = ADDR_B601_VOLTAGE_18V;
Marco Gittler941491f2007-04-19 11:26:47 -0300167 msg[0].buf = command_18v;
168 }
169 i2c_transfer(&udev_adap->dev->i2c_adap, msg, 1);
170 return 0;
171}
172
173static int opera1_stv0299_set_symbol_rate(struct dvb_frontend *fe, u32 srate,
174 u32 ratio)
175{
176 stv0299_writereg(fe, 0x13, 0x98);
177 stv0299_writereg(fe, 0x14, 0x95);
178 stv0299_writereg(fe, REG_1F_SYMBOLRATE_BYTE0, (ratio >> 16) & 0xff);
179 stv0299_writereg(fe, REG_20_SYMBOLRATE_BYTE1, (ratio >> 8) & 0xff);
180 stv0299_writereg(fe, REG_21_SYMBOLRATE_BYTE2, (ratio) & 0xf0);
181 return 0;
182
183}
184static u8 opera1_inittab[] = {
185 0x00, 0xa1,
186 0x01, 0x15,
187 0x02, 0x00,
188 0x03, 0x00,
189 0x04, 0x7d,
190 0x05, 0x05,
191 0x06, 0x02,
192 0x07, 0x00,
193 0x0b, 0x00,
194 0x0c, 0x01,
195 0x0d, 0x81,
196 0x0e, 0x44,
197 0x0f, 0x19,
198 0x10, 0x3f,
199 0x11, 0x84,
200 0x12, 0xda,
201 0x13, 0x98,
202 0x14, 0x95,
203 0x15, 0xc9,
204 0x16, 0xeb,
205 0x17, 0x00,
206 0x18, 0x19,
207 0x19, 0x8b,
208 0x1a, 0x00,
209 0x1b, 0x82,
210 0x1c, 0x7f,
211 0x1d, 0x00,
212 0x1e, 0x00,
213 REG_1F_SYMBOLRATE_BYTE0, 0x06,
214 REG_20_SYMBOLRATE_BYTE1, 0x50,
215 REG_21_SYMBOLRATE_BYTE2, 0x10,
216 0x22, 0x00,
217 0x23, 0x00,
218 0x24, 0x37,
219 0x25, 0xbc,
220 0x26, 0x00,
221 0x27, 0x00,
222 0x28, 0x00,
223 0x29, 0x1e,
224 0x2a, 0x14,
225 0x2b, 0x1f,
226 0x2c, 0x09,
227 0x2d, 0x0a,
228 0x2e, 0x00,
229 0x2f, 0x00,
230 0x30, 0x00,
231 0x31, 0x1f,
232 0x32, 0x19,
233 0x33, 0xfc,
234 0x34, 0x13,
235 0xff, 0xff,
236};
237
238static struct stv0299_config opera1_stv0299_config = {
Marco Gittler86534e52007-04-23 17:52:58 -0300239 .demod_address = 0xd0>>1,
Marco Gittler941491f2007-04-19 11:26:47 -0300240 .min_delay_ms = 100,
241 .mclk = 88000000UL,
242 .invert = 1,
243 .skip_reinit = 0,
244 .lock_output = STV0229_LOCKOUTPUT_0,
245 .volt13_op0_op1 = STV0299_VOLT13_OP0,
246 .inittab = opera1_inittab,
247 .set_symbol_rate = opera1_stv0299_set_symbol_rate,
248};
249
250static int opera1_frontend_attach(struct dvb_usb_adapter *d)
251{
252 if ((d->fe =
253 dvb_attach(stv0299_attach, &opera1_stv0299_config,
254 &d->dev->i2c_adap)) != NULL) {
255 d->fe->ops.set_voltage = opera1_set_voltage;
256 return 0;
257 }
258 info("not attached stv0299");
259 return -EIO;
260}
261
262static int opera1_tuner_attach(struct dvb_usb_adapter *adap)
263{
Marco Gittler86534e52007-04-23 17:52:58 -0300264 dvb_attach(
265 dvb_pll_attach, adap->fe, 0xc0>>1,
266 &adap->dev->i2c_adap, &dvb_pll_opera1
267 );
Marco Gittler941491f2007-04-19 11:26:47 -0300268 return 0;
269}
270
271static int opera1_power_ctrl(struct dvb_usb_device *d, int onoff)
272{
Marco Gittler941491f2007-04-19 11:26:47 -0300273 u8 val = onoff ? 0x01 : 0x00;
Marco Gittler86534e52007-04-23 17:52:58 -0300274
Marco Gittler941491f2007-04-19 11:26:47 -0300275 if (dvb_usb_opera1_debug)
276 info("power %s", onoff ? "on" : "off");
Marco Gittler86534e52007-04-23 17:52:58 -0300277 return opera1_xilinx_rw(d->udev, 0xb7, val,
278 &val, 1, OPERA_WRITE_MSG);
Marco Gittler941491f2007-04-19 11:26:47 -0300279}
280
281static int opera1_streaming_ctrl(struct dvb_usb_adapter *adap, int onoff)
282{
283 static u8 buf_start[2] = { 0xff, 0x03 };
284 static u8 buf_stop[2] = { 0xff, 0x00 };
285 struct i2c_msg start_tuner[] = {
Marco Gittler86534e52007-04-23 17:52:58 -0300286 {.addr = ADDR_B1A6_STREAM_CTRL,.buf = onoff ? buf_start : buf_stop,.len = 2},
Marco Gittler941491f2007-04-19 11:26:47 -0300287 };
288 if (dvb_usb_opera1_debug)
289 info("streaming %s", onoff ? "on" : "off");
290 i2c_transfer(&adap->dev->i2c_adap, start_tuner, 1);
291 return 0;
292}
293
294static int opera1_pid_filter(struct dvb_usb_adapter *adap, int index, u16 pid,
295 int onoff)
296{
297 u8 b_pid[3];
298 struct i2c_msg msg[] = {
Marco Gittler86534e52007-04-23 17:52:58 -0300299 {.addr = ADDR_B1A6_STREAM_CTRL,.buf = b_pid,.len = 3},
Marco Gittler941491f2007-04-19 11:26:47 -0300300 };
301 if (dvb_usb_opera1_debug)
302 info("pidfilter index: %d pid: %d %s", index, pid,
303 onoff ? "on" : "off");
304 b_pid[0] = (2 * index) + 4;
305 b_pid[1] = onoff ? (pid & 0xff) : (0x00);
306 b_pid[2] = onoff ? ((pid >> 8) & 0xff) : (0x00);
307 i2c_transfer(&adap->dev->i2c_adap, msg, 1);
308 return 0;
309}
310
311static int opera1_pid_filter_control(struct dvb_usb_adapter *adap, int onoff)
312{
313 int u = 0x04;
314 u8 b_pid[3];
315 struct i2c_msg msg[] = {
Marco Gittler86534e52007-04-23 17:52:58 -0300316 {.addr = ADDR_B1A6_STREAM_CTRL,.buf = b_pid,.len = 3},
Marco Gittler941491f2007-04-19 11:26:47 -0300317 };
318 if (dvb_usb_opera1_debug)
319 info("%s hw-pidfilter", onoff ? "enable" : "disable");
320 for (; u < 0x7e; u += 2) {
321 b_pid[0] = u;
322 b_pid[1] = 0;
323 b_pid[2] = 0x80;
324 i2c_transfer(&adap->dev->i2c_adap, msg, 1);
325 }
326 return 0;
327}
328
329static struct dvb_usb_rc_key opera1_rc_keys[] = {
330 {0x5f, 0xa0, KEY_1},
331 {0x51, 0xaf, KEY_2},
332 {0x5d, 0xa2, KEY_3},
333 {0x41, 0xbe, KEY_4},
334 {0x0b, 0xf5, KEY_5},
335 {0x43, 0xbd, KEY_6},
336 {0x47, 0xb8, KEY_7},
337 {0x49, 0xb6, KEY_8},
338 {0x05, 0xfa, KEY_9},
339 {0x45, 0xba, KEY_0},
340 {0x09, 0xf6, KEY_UP}, /*chanup */
341 {0x1b, 0xe5, KEY_DOWN}, /*chandown */
342 {0x5d, 0xa3, KEY_LEFT}, /*voldown */
343 {0x5f, 0xa1, KEY_RIGHT}, /*volup */
344 {0x07, 0xf8, KEY_SPACE}, /*tab */
345 {0x1f, 0xe1, KEY_ENTER}, /*play ok */
346 {0x1b, 0xe4, KEY_Z}, /*zoom */
347 {0x59, 0xa6, KEY_M}, /*mute */
348 {0x5b, 0xa5, KEY_F}, /*tv/f */
349 {0x19, 0xe7, KEY_R}, /*rec */
350 {0x01, 0xfe, KEY_S}, /*Stop */
351 {0x03, 0xfd, KEY_P}, /*pause */
352 {0x03, 0xfc, KEY_W}, /*<- -> */
353 {0x07, 0xf9, KEY_C}, /*capture */
354 {0x47, 0xb9, KEY_Q}, /*exit */
355 {0x43, 0xbc, KEY_O}, /*power */
356
357};
358
359static int opera1_rc_query(struct dvb_usb_device *dev, u32 * event, int *state)
360{
361 struct opera1_state *opst = dev->priv;
362 u8 rcbuffer[32];
363 const u16 startmarker1 = 0x10ed;
364 const u16 startmarker2 = 0x11ec;
365 struct i2c_msg read_remote[] = {
Marco Gittler86534e52007-04-23 17:52:58 -0300366 {.addr = ADDR_B880_READ_REMOTE,.buf = rcbuffer,.flags = I2C_M_RD,.len = 32},
Marco Gittler941491f2007-04-19 11:26:47 -0300367 };
368 int i = 0;
369 u32 send_key = 0;
370
371 if (i2c_transfer(&dev->i2c_adap, read_remote, 1) == 1) {
372 for (i = 0; i < 32; i++) {
373 if (rcbuffer[i])
374 send_key |= 1;
375 if (i < 31)
376 send_key = send_key << 1;
377 }
378 if (send_key & 0x8000)
379 send_key = (send_key << 1) | (send_key >> 15 & 0x01);
380
381 if (send_key == 0xffff && opst->last_key_pressed != 0) {
382 *state = REMOTE_KEY_REPEAT;
383 *event = opst->last_key_pressed;
384 return 0;
385 }
386 for (; send_key != 0;) {
387 if (send_key >> 16 == startmarker2) {
388 break;
389 } else if (send_key >> 16 == startmarker1) {
390 send_key =
391 (send_key & 0xfffeffff) | (startmarker1 << 16);
392 break;
393 } else
394 send_key >>= 1;
395 }
396
397 if (send_key == 0)
398 return 0;
399
400 send_key = (send_key & 0xffff) | 0x0100;
401
402 for (i = 0; i < ARRAY_SIZE(opera1_rc_keys); i++) {
403 if ((opera1_rc_keys[i].custom * 256 +
404 opera1_rc_keys[i].data) == (send_key & 0xffff)) {
405 *state = REMOTE_KEY_PRESSED;
406 *event = opera1_rc_keys[i].event;
407 opst->last_key_pressed =
408 opera1_rc_keys[i].event;
409 break;
410 }
411 opst->last_key_pressed = 0;
412 }
413 } else
414 *state = REMOTE_NO_KEY_PRESSED;
415 return 0;
416}
417
418static struct usb_device_id opera1_table[] = {
419 {USB_DEVICE(USB_VID_CYPRESS, USB_PID_OPERA1_COLD)},
420 {USB_DEVICE(USB_VID_OPERA1, USB_PID_OPERA1_WARM)},
421 {}
422};
423
424MODULE_DEVICE_TABLE(usb, opera1_table);
425
426static int opera1_read_mac_address(struct dvb_usb_device *d, u8 mac[6])
427{
428 u8 command[] = { READ_MAC_ADDR };
429 opera1_xilinx_rw(d->udev, 0xb1, 0xa0, command, 1, OPERA_WRITE_MSG);
430 opera1_xilinx_rw(d->udev, 0xb1, 0xa1, mac, 6, OPERA_READ_MSG);
431 return 0;
432}
433static int opera1_xilinx_load_firmware(struct usb_device *dev,
434 const char *filename)
435{
436 const struct firmware *fw = NULL;
437 u8 *b, *p;
438 int ret = 0, i;
439 u8 testval;
440 info("start downloading fpga firmware");
441
442 if ((ret = request_firmware(&fw, filename, &dev->dev)) != 0) {
443 err("did not find the firmware file. (%s) "
444 "Please see linux/Documentation/dvb/ for more details on firmware-problems.",
445 filename);
446 return ret;
447 } else {
448 p = kmalloc(fw->size, GFP_KERNEL);
449 opera1_xilinx_rw(dev, 0xbc, 0x00, &testval, 1, OPERA_READ_MSG);
450 if (p != NULL && testval != 0x67) {
451
452 u8 reset = 0, fpga_command = 0;
453 memcpy(p, fw->data, fw->size);
454 /* clear fpga ? */
455 opera1_xilinx_rw(dev, 0xbc, 0xaa, &fpga_command, 1,
456 OPERA_WRITE_MSG);
457 for (i = 0; p[i] != 0 && i < fw->size;) {
458 b = (u8 *) p + i;
459 if (opera1_xilinx_rw
460 (dev, OPERA_WRITE_FX2, 0x0, b + 1, b[0],
461 OPERA_WRITE_MSG) != b[0]
462 ) {
463 err("error while transferring firmware");
464 ret = -EINVAL;
465 break;
466 }
467 i = i + 1 + b[0];
468 }
469 /* restart the CPU */
470 if (ret || opera1_xilinx_rw
471 (dev, 0xa0, 0xe600, &reset, 1,
472 OPERA_WRITE_MSG) != 1) {
473 err("could not restart the USB controller CPU.");
474 ret = -EINVAL;
475 }
476 kfree(p);
477 }
478 }
479 if (fw) {
480 release_firmware(fw);
481 }
482 return ret;
483}
484
485static struct dvb_usb_device_properties opera1_properties = {
486 .caps = DVB_USB_IS_AN_I2C_ADAPTER,
487 .usb_ctrl = CYPRESS_FX2,
Marco Gittler86534e52007-04-23 17:52:58 -0300488 .firmware = "dvb-usb-opera-01.fw",
Marco Gittler941491f2007-04-19 11:26:47 -0300489 .size_of_priv = sizeof(struct opera1_state),
490
491 .power_ctrl = opera1_power_ctrl,
492 .i2c_algo = &opera1_i2c_algo,
493
494 .rc_key_map = opera1_rc_keys,
495 .rc_key_map_size = ARRAY_SIZE(opera1_rc_keys),
496 .rc_interval = 200,
497 .rc_query = opera1_rc_query,
498 .read_mac_address = opera1_read_mac_address,
499 .generic_bulk_ctrl_endpoint = 0x00,
500 /* parameter for the MPEG2-data transfer */
501 .num_adapters = 1,
502 .adapter = {
503 {
504 .frontend_attach = opera1_frontend_attach,
505 .streaming_ctrl = opera1_streaming_ctrl,
506 .tuner_attach = opera1_tuner_attach,
507 .caps =
508 DVB_USB_ADAP_HAS_PID_FILTER |
509 DVB_USB_ADAP_PID_FILTER_CAN_BE_TURNED_OFF,
510 .pid_filter = opera1_pid_filter,
511 .pid_filter_ctrl = opera1_pid_filter_control,
512 .pid_filter_count = 252,
513 .stream = {
514 .type = USB_BULK,
515 .count = 10,
516 .endpoint = 0x82,
517 .u = {
518 .bulk = {
519 .buffersize = 4096,
520 }
521 }
522 },
523 }
524 },
525 .num_device_descs = 1,
526 .devices = {
527 {"Opera1 DVB-S USB2.0",
528 {&opera1_table[0], NULL},
529 {&opera1_table[1], NULL},
530 },
531 }
532};
533
534static int opera1_probe(struct usb_interface *intf,
535 const struct usb_device_id *id)
536{
537 struct dvb_usb_device *d;
538 struct usb_device *udev = interface_to_usbdev(intf);
539
540 if (udev->descriptor.idProduct == USB_PID_OPERA1_WARM &&
541 udev->descriptor.idVendor == USB_VID_OPERA1 &&
542 (d == NULL
Marco Gittler86534e52007-04-23 17:52:58 -0300543 || opera1_xilinx_load_firmware(udev, "dvb-usb-opera1-fpga.fw") != 0)
Marco Gittler941491f2007-04-19 11:26:47 -0300544 ) {
545 return -EINVAL;
546 }
547
548 if (dvb_usb_device_init(intf, &opera1_properties, THIS_MODULE, &d) != 0)
549 return -EINVAL;
550 return 0;
551}
552
553static struct usb_driver opera1_driver = {
554 .name = "opera1",
555 .probe = opera1_probe,
556 .disconnect = dvb_usb_device_exit,
557 .id_table = opera1_table,
558};
559
560static int __init opera1_module_init(void)
561{
562 int result = 0;
563 if ((result = usb_register(&opera1_driver))) {
564 err("usb_register failed. Error number %d", result);
565 }
566 return result;
567}
568
569static void __exit opera1_module_exit(void)
570{
571 usb_deregister(&opera1_driver);
572}
573
574module_init(opera1_module_init);
575module_exit(opera1_module_exit);
576
577MODULE_AUTHOR("Mario Hlawitschka (c) dh1pa@amsat.org");
578MODULE_AUTHOR("Marco Gittler (c) g.marco@freenet.de");
579MODULE_DESCRIPTION("Driver for Opera1 DVB-S device");
580MODULE_VERSION("0.1");
581MODULE_LICENSE("GPL");