1 /*
2 * budget-ci.c: driver for the SAA7146 based Budget DVB cards
3 *
4 * Compiled from various sources by Michael Hunold <michael@mihu.de>
5 *
6 * msp430 IR support contributed by Jack Thomasson <jkt@Helius.COM>
7 * partially based on the Siemens DVB driver by Ralph+Marcus Metzler
8 *
9 * CI interface support (c) 2004 Andrew de Quincey <adq_dvb@lidskialf.net>
10 *
11 * This program is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU General Public License
13 * as published by the Free Software Foundation; either version 2
14 * of the License, or (at your option) any later version.
15 *
16 *
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
21 *
22 *
23 * You should have received a copy of the GNU General Public License
24 * along with this program; if not, write to the Free Software
25 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
26 * Or, point your browser to http://www.gnu.org/copyleft/gpl.html
27 *
28 *
29 * the project's page is at http://www.linuxtv.org/dvb/
30 */
31
32 #include "budget.h"
33
34 #include <linux/module.h>
35 #include <linux/errno.h>
36 #include <linux/slab.h>
37 #include <linux/interrupt.h>
38 #include <linux/input.h>
39 #include <linux/spinlock.h>
40
41 #include "dvb_ca_en50221.h"
42 #include "stv0299.h"
43 #include "tda1004x.h"
44
45 #define DEBIADDR_IR 0x1234
46 #define DEBIADDR_CICONTROL 0x0000
47 #define DEBIADDR_CIVERSION 0x4000
48 #define DEBIADDR_IO 0x1000
49 #define DEBIADDR_ATTR 0x3000
50
51 #define CICONTROL_RESET 0x01
52 #define CICONTROL_ENABLETS 0x02
53 #define CICONTROL_CAMDETECT 0x08
54
55 #define DEBICICTL 0x00420000
56 #define DEBICICAM 0x02420000
57
58 #define SLOTSTATUS_NONE 1
59 #define SLOTSTATUS_PRESENT 2
60 #define SLOTSTATUS_RESET 4
61 #define SLOTSTATUS_READY 8
62 #define SLOTSTATUS_OCCUPIED (SLOTSTATUS_PRESENT|SLOTSTATUS_RESET|SLOTSTATUS_READY)
63
64 struct budget_ci {
65 struct budget budget;
66 struct input_dev input_dev;
67 struct tasklet_struct msp430_irq_tasklet;
68 struct tasklet_struct ciintf_irq_tasklet;
69 int slot_status;
70 struct dvb_ca_en50221 ca;
71 char ir_dev_name[50];
72 };
73
74 /* from reading the following remotes:
75 Zenith Universal 7 / TV Mode 807 / VCR Mode 837
76 Hauppauge (from NOVA-CI-s box product)
77 i've taken a "middle of the road" approach and note the differences
78 */
79 static u16 key_map[64] = {
80 /* 0x0X */
81 KEY_0, KEY_1, KEY_2, KEY_3, KEY_4, KEY_5, KEY_6, KEY_7, KEY_8,
82 KEY_9,
83 KEY_ENTER,
84 KEY_RED,
85 KEY_POWER, /* RADIO on Hauppauge */
86 KEY_MUTE,
87 0,
88 KEY_A, /* TV on Hauppauge */
89 /* 0x1X */
90 KEY_VOLUMEUP, KEY_VOLUMEDOWN,
91 0, 0,
92 KEY_B,
93 0, 0, 0, 0, 0, 0, 0,
94 KEY_UP, KEY_DOWN,
95 KEY_OPTION, /* RESERVED on Hauppauge */
96 KEY_BREAK,
97 /* 0x2X */
98 KEY_CHANNELUP, KEY_CHANNELDOWN,
99 KEY_PREVIOUS, /* Prev. Ch on Zenith, SOURCE on Hauppauge */
100 0, KEY_RESTART, KEY_OK,
101 KEY_CYCLEWINDOWS, /* MINIMIZE on Hauppauge */
102 0,
103 KEY_ENTER, /* VCR mode on Zenith */
104 KEY_PAUSE,
105 0,
106 KEY_RIGHT, KEY_LEFT,
107 0,
108 KEY_MENU, /* FULL SCREEN on Hauppauge */
109 0,
110 /* 0x3X */
111 KEY_SLOW,
112 KEY_PREVIOUS, /* VCR mode on Zenith */
113 KEY_REWIND,
114 0,
115 KEY_FASTFORWARD,
116 KEY_PLAY, KEY_STOP,
117 KEY_RECORD,
118 KEY_TUNER, /* TV/VCR on Zenith */
119 0,
120 KEY_C,
121 0,
122 KEY_EXIT,
123 KEY_POWER2,
124 KEY_TUNER, /* VCR mode on Zenith */
125 0,
126 };
127
128
129 static void msp430_ir_debounce (unsigned long data)
130 {
131 struct input_dev *dev = (struct input_dev *) data;
132
133 if (dev->rep[0] == 0 || dev->rep[0] == ~0) {
134 input_event(dev, EV_KEY, key_map[dev->repeat_key], !!0);
135 return;
136 }
137
138 dev->rep[0] = 0;
139 dev->timer.expires = jiffies + HZ * 350 / 1000;
140 add_timer(&dev->timer);
141 input_event(dev, EV_KEY, key_map[dev->repeat_key], 2); /* REPEAT */
142 }
143
144
145
146 static void msp430_ir_interrupt (unsigned long data)
147 {
148 struct budget_ci *budget_ci = (struct budget_ci*) data;
149 struct input_dev *dev = &budget_ci->input_dev;
150 unsigned int code =
151 ttpci_budget_debiread(&budget_ci->budget, DEBINOSWAP, DEBIADDR_IR, 2, 1, 0) >> 8;
152
153 if (code & 0x40) {
154 code &= 0x3f;
155
156 if (timer_pending(&dev->timer)) {
157 if (code == dev->repeat_key) {
158 ++dev->rep[0];
159 return;
160 }
161 del_timer(&dev->timer);
162 input_event(dev, EV_KEY, key_map[dev->repeat_key], !!0);
163 }
164
165 if (!key_map[code]) {
166 printk("DVB (%s): no key for %02x!\n", __FUNCTION__, code);
167 return;
168 }
169
170 /* initialize debounce and repeat */
171 dev->repeat_key = code;
172 /* Zenith remote _always_ sends 2 sequences */
173 dev->rep[0] = ~0;
174 /* 350 milliseconds */
175 dev->timer.expires = jiffies + HZ * 350 / 1000;
176 /* MAKE */
177 input_event(dev, EV_KEY, key_map[code], !0);
178 add_timer(&dev->timer);
179 }
180 }
181
182
183 static int msp430_ir_init (struct budget_ci *budget_ci)
184 {
185 struct saa7146_dev *saa = budget_ci->budget.dev;
186 int i;
187
188 memset(&budget_ci->input_dev, 0, sizeof(struct input_dev));
189
190 sprintf (budget_ci->ir_dev_name, "Budget-CI dvb ir receiver %s", saa->name);
191 budget_ci->input_dev.name = budget_ci->ir_dev_name;
192
193 set_bit(EV_KEY, budget_ci->input_dev.evbit);
194
195 for (i=0; i<sizeof(key_map)/sizeof(*key_map); i++)
196 if (key_map[i])
197 set_bit(key_map[i], budget_ci->input_dev.keybit);
198
199 input_register_device(&budget_ci->input_dev);
200
201 budget_ci->input_dev.timer.function = msp430_ir_debounce;
202
203 saa7146_write(saa, IER, saa7146_read(saa, IER) | MASK_06);
204
205 saa7146_setgpio(saa, 3, SAA7146_GPIO_IRQHI);
206
207 return 0;
208 }
209
210
211 static void msp430_ir_deinit (struct budget_ci *budget_ci)
212 {
213 struct saa7146_dev *saa = budget_ci->budget.dev;
214 struct input_dev *dev = &budget_ci->input_dev;
215
216 saa7146_write(saa, IER, saa7146_read(saa, IER) & ~MASK_06);
217 saa7146_setgpio(saa, 3, SAA7146_GPIO_INPUT);
218
219 if (del_timer(&dev->timer))
220 input_event(dev, EV_KEY, key_map[dev->repeat_key], !!0);
221
222 input_unregister_device(dev);
223 }
224
225 static int ciintf_read_attribute_mem(struct dvb_ca_en50221 *ca, int slot, int address)
226 {
227 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
228
229 if (slot != 0)
230 return -EINVAL;
231
232 return ttpci_budget_debiread(&budget_ci->budget, DEBICICAM,
233 DEBIADDR_ATTR | (address & 0xfff), 1, 1, 0);
234 }
235
236 static int ciintf_write_attribute_mem(struct dvb_ca_en50221 *ca, int slot, int address, u8 value)
237 {
238 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
239
240 if (slot != 0)
241 return -EINVAL;
242
243 return ttpci_budget_debiwrite(&budget_ci->budget, DEBICICAM,
244 DEBIADDR_ATTR | (address & 0xfff), 1, value, 1, 0);
245 }
246
247 static int ciintf_read_cam_control(struct dvb_ca_en50221 *ca, int slot, u8 address)
248 {
249 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
250
251 if (slot != 0)
252 return -EINVAL;
253
254 return ttpci_budget_debiread(&budget_ci->budget, DEBICICAM,
255 DEBIADDR_IO | (address & 3), 1, 1, 0);
256 }
257
258 static int ciintf_write_cam_control(struct dvb_ca_en50221 *ca, int slot, u8 address, u8 value)
259 {
260 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
261
262 if (slot != 0)
263 return -EINVAL;
264
265 return ttpci_budget_debiwrite(&budget_ci->budget, DEBICICAM,
266 DEBIADDR_IO | (address & 3), 1, value, 1, 0);
267 }
268
269 static int ciintf_slot_reset(struct dvb_ca_en50221 *ca, int slot)
270 {
271 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
272 struct saa7146_dev *saa = budget_ci->budget.dev;
273
274 if (slot != 0)
275 return -EINVAL;
276
277 // trigger on RISING edge during reset so we know when READY is re-asserted
278 saa7146_setgpio(saa, 0, SAA7146_GPIO_IRQHI);
279 budget_ci->slot_status = SLOTSTATUS_RESET;
280 ttpci_budget_debiwrite(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1, 0, 1, 0);
281 msleep(1);
282 ttpci_budget_debiwrite(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1,
283 CICONTROL_RESET, 1, 0);
284
285 saa7146_setgpio(saa, 1, SAA7146_GPIO_OUTHI);
286 ttpci_budget_set_video_port(saa, BUDGET_VIDEO_PORTB);
287 return 0;
288 }
289
290 static int ciintf_slot_shutdown(struct dvb_ca_en50221 *ca, int slot)
291 {
292 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
293 struct saa7146_dev *saa = budget_ci->budget.dev;
294
295 if (slot != 0)
296 return -EINVAL;
297
298 saa7146_setgpio(saa, 1, SAA7146_GPIO_OUTHI);
299 ttpci_budget_set_video_port(saa, BUDGET_VIDEO_PORTB);
300 return 0;
301 }
302
303 static int ciintf_slot_ts_enable(struct dvb_ca_en50221 *ca, int slot)
304 {
305 struct budget_ci* budget_ci = (struct budget_ci*) ca->data;
306 struct saa7146_dev *saa = budget_ci->budget.dev;
307 int tmp;
308
309 if (slot != 0)
310 return -EINVAL;
311
312 saa7146_setgpio(saa, 1, SAA7146_GPIO_OUTLO);
313
314 tmp = ttpci_budget_debiread(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1, 1, 0);
315 ttpci_budget_debiwrite(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1,
316 tmp | CICONTROL_ENABLETS, 1, 0);
317
318 ttpci_budget_set_video_port(saa, BUDGET_VIDEO_PORTA);
319 return 0;
320 }
321
322
323 static void ciintf_interrupt (unsigned long data)
324 {
325 struct budget_ci *budget_ci = (struct budget_ci*) data;
326 struct saa7146_dev *saa = budget_ci->budget.dev;
327 unsigned int flags;
328
329 // ensure we don't get spurious IRQs during initialisation
330 if (!budget_ci->budget.ci_present)
331 return;
332
333 // read the CAM status
334 flags = ttpci_budget_debiread(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1, 1, 0);
335 if (flags & CICONTROL_CAMDETECT) {
336
337 // GPIO should be set to trigger on falling edge if a CAM is present
338 saa7146_setgpio(saa, 0, SAA7146_GPIO_IRQLO);
339
340 if (budget_ci->slot_status & SLOTSTATUS_NONE) {
341 // CAM insertion IRQ
342 budget_ci->slot_status = SLOTSTATUS_PRESENT;
343 dvb_ca_en50221_camchange_irq(&budget_ci->ca, 0,
344 DVB_CA_EN50221_CAMCHANGE_INSERTED);
345
346 } else if (budget_ci->slot_status & SLOTSTATUS_RESET) {
347 // CAM ready (reset completed)
348 budget_ci->slot_status = SLOTSTATUS_READY;
349 dvb_ca_en50221_camready_irq(&budget_ci->ca, 0);
350
351 } else if (budget_ci->slot_status & SLOTSTATUS_READY) {
352 // FR/DA IRQ
353 dvb_ca_en50221_frda_irq(&budget_ci->ca, 0);
354 }
355 } else {
356
357 // trigger on rising edge if a CAM is not present - when a CAM is inserted, we
358 // only want to get the IRQ when it sets READY. If we trigger on the falling edge,
359 // the CAM might not actually be ready yet.
360 saa7146_setgpio(saa, 0, SAA7146_GPIO_IRQHI);
361
362 // generate a CAM removal IRQ if we haven't already
363 if (budget_ci->slot_status & SLOTSTATUS_OCCUPIED) {
364 // CAM removal IRQ
365 budget_ci->slot_status = SLOTSTATUS_NONE;
366 dvb_ca_en50221_camchange_irq(&budget_ci->ca, 0,
367 DVB_CA_EN50221_CAMCHANGE_REMOVED);
368 }
369 }
370 }
371
372 static int ciintf_init(struct budget_ci* budget_ci)
373 {
374 struct saa7146_dev *saa = budget_ci->budget.dev;
375 int flags;
376 int result;
377
378 memset(&budget_ci->ca, 0, sizeof(struct dvb_ca_en50221));
379
380 // enable DEBI pins
381 saa7146_write(saa, MC1, saa7146_read(saa, MC1) | (0x800 << 16) | 0x800);
382
383 // test if it is there
384 if ((ttpci_budget_debiread(&budget_ci->budget, DEBICICTL, DEBIADDR_CIVERSION, 1, 1, 0) & 0xa0) != 0xa0) {
385 result = -ENODEV;
386 goto error;
387 }
388 // determine whether a CAM is present or not
389 flags = ttpci_budget_debiread(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1, 1, 0);
390 budget_ci->slot_status = SLOTSTATUS_NONE;
391 if (flags & CICONTROL_CAMDETECT)
392 budget_ci->slot_status = SLOTSTATUS_PRESENT;
393
394 // register CI interface
395 budget_ci->ca.owner = THIS_MODULE;
396 budget_ci->ca.read_attribute_mem = ciintf_read_attribute_mem;
397 budget_ci->ca.write_attribute_mem = ciintf_write_attribute_mem;
398 budget_ci->ca.read_cam_control = ciintf_read_cam_control;
399 budget_ci->ca.write_cam_control = ciintf_write_cam_control;
400 budget_ci->ca.slot_reset = ciintf_slot_reset;
401 budget_ci->ca.slot_shutdown = ciintf_slot_shutdown;
402 budget_ci->ca.slot_ts_enable = ciintf_slot_ts_enable;
403 budget_ci->ca.data = budget_ci;
404 if ((result = dvb_ca_en50221_init(budget_ci->budget.dvb_adapter,
405 &budget_ci->ca,
406 DVB_CA_EN50221_FLAG_IRQ_CAMCHANGE |
407 DVB_CA_EN50221_FLAG_IRQ_FR |
408 DVB_CA_EN50221_FLAG_IRQ_DA, 1)) != 0) {
409 printk("budget_ci: CI interface detected, but initialisation failed.\n");
410 goto error;
411 }
412
413 // Setup CI slot IRQ
414 tasklet_init (&budget_ci->ciintf_irq_tasklet, ciintf_interrupt, (unsigned long) budget_ci);
415 if (budget_ci->slot_status != SLOTSTATUS_NONE) {
416 saa7146_setgpio(saa, 0, SAA7146_GPIO_IRQLO);
417 } else {
418 saa7146_setgpio(saa, 0, SAA7146_GPIO_IRQHI);
419 }
420 saa7146_write(saa, IER, saa7146_read(saa, IER) | MASK_03);
421 ttpci_budget_debiwrite(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1,
422 CICONTROL_RESET, 1, 0);
423
424 // success!
425 printk("budget_ci: CI interface initialised\n");
426 budget_ci->budget.ci_present = 1;
427
428 // forge a fake CI IRQ so the CAM state is setup correctly
429 flags = DVB_CA_EN50221_CAMCHANGE_REMOVED;
430 if (budget_ci->slot_status != SLOTSTATUS_NONE)
431 flags = DVB_CA_EN50221_CAMCHANGE_INSERTED;
432 dvb_ca_en50221_camchange_irq(&budget_ci->ca, 0, flags);
433
434 return 0;
435
436 error:
437 saa7146_write(saa, MC1, saa7146_read(saa, MC1) | (0x800 << 16));
438 return result;
439 }
440
441 static void ciintf_deinit(struct budget_ci* budget_ci)
442 {
443 struct saa7146_dev *saa = budget_ci->budget.dev;
444
445 // disable CI interrupts
446 saa7146_write(saa, IER, saa7146_read(saa, IER) & ~MASK_03);
447 saa7146_setgpio(saa, 0, SAA7146_GPIO_INPUT);
448 tasklet_kill(&budget_ci->ciintf_irq_tasklet);
449 ttpci_budget_debiwrite(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1, 0, 1, 0);
450 msleep(1);
451 ttpci_budget_debiwrite(&budget_ci->budget, DEBICICTL, DEBIADDR_CICONTROL, 1,
452 CICONTROL_RESET, 1, 0);
453
454 // disable TS data stream to CI interface
455 saa7146_setgpio(saa, 1, SAA7146_GPIO_INPUT);
456
457 // release the CA device
458 dvb_ca_en50221_release(&budget_ci->ca);
459
460 // disable DEBI pins
461 saa7146_write(saa, MC1, saa7146_read(saa, MC1) | (0x800 << 16));
462 }
463
464 static void budget_ci_irq (struct saa7146_dev *dev, u32 *isr)
465 {
466 struct budget_ci *budget_ci = (struct budget_ci*) dev->ext_priv;
467
468 dprintk(8, "dev: %p, budget_ci: %p\n", dev, budget_ci);
469
470 if (*isr & MASK_06)
471 tasklet_schedule (&budget_ci->msp430_irq_tasklet);
472
473 if (*isr & MASK_10)
474 ttpci_budget_irq10_handler (dev, isr);
475
476 if ((*isr & MASK_03) && (budget_ci->budget.ci_present))
477 tasklet_schedule (&budget_ci->ciintf_irq_tasklet);
478 }
479
480
481 static u8 alps_bsru6_inittab[] = {
482 0x01, 0x15,
483 0x02, 0x00,
484 0x03, 0x00,
485 0x04, 0x7d, /* F22FR = 0x7d, F22 = f_VCO / 128 / 0x7d = 22 kHz */
486 0x05, 0x35, /* I2CT = 0, SCLT = 1, SDAT = 1 */
487 0x06, 0x40, /* DAC not used, set to high impendance mode */
488 0x07, 0x00, /* DAC LSB */
489 0x08, 0x40, /* DiSEqC off, LNB power on OP2/LOCK pin on */
490 0x09, 0x00, /* FIFO */
491 0x0c, 0x51, /* OP1 ctl = Normal, OP1 val = 1 (LNB Power ON) */
492 0x0d, 0x82, /* DC offset compensation = ON, beta_agc1 = 2 */
493 0x0e, 0x23, /* alpha_tmg = 2, beta_tmg = 3 */
494 0x10, 0x3f, // AGC2 0x3d
495 0x11, 0x84,
496 0x12, 0xb5, // Lock detect: -64 Carrier freq detect:on
497 0x15, 0xc9, // lock detector threshold
498 0x16, 0x00,
499 0x17, 0x00,
500 0x18, 0x00,
501 0x19, 0x00,
502 0x1a, 0x00,
503 0x1f, 0x50,
504 0x20, 0x00,
505 0x21, 0x00,
506 0x22, 0x00,
507 0x23, 0x00,
508 0x28, 0x00, // out imp: normal out type: parallel FEC mode:0
509 0x29, 0x1e, // 1/2 threshold
510 0x2a, 0x14, // 2/3 threshold
511 0x2b, 0x0f, // 3/4 threshold
512 0x2c, 0x09, // 5/6 threshold
513 0x2d, 0x05, // 7/8 threshold
514 0x2e, 0x01,
515 0x31, 0x1f, // test all FECs
516 0x32, 0x19, // viterbi and synchro search
517 0x33, 0xfc, // rs control
518 0x34, 0x93, // error control
519 0x0f, 0x52,
520 0xff, 0xff
521 };
522
523 static int alps_bsru6_set_symbol_rate(struct dvb_frontend *fe, u32 srate, u32 ratio)
524 {
525 u8 aclk = 0;
526 u8 bclk = 0;
527
528 if (srate < 1500000) {
529 aclk = 0xb7;
530 bclk = 0x47;
531 } else if (srate < 3000000) {
532 aclk = 0xb7;
533 bclk = 0x4b;
534 } else if (srate < 7000000) {
535 aclk = 0xb7;
536 bclk = 0x4f;
537 } else if (srate < 14000000) {
538 aclk = 0xb7;
539 bclk = 0x53;
540 } else if (srate < 30000000) {
541 aclk = 0xb6;
542 bclk = 0x53;
543 } else if (srate < 45000000) {
544 aclk = 0xb4;
545 bclk = 0x51;
546 }
547
548 stv0299_writereg(fe, 0x13, aclk);
549 stv0299_writereg(fe, 0x14, bclk);
550 stv0299_writereg(fe, 0x1f, (ratio >> 16) & 0xff);
551 stv0299_writereg(fe, 0x20, (ratio >> 8) & 0xff);
552 stv0299_writereg(fe, 0x21, (ratio) & 0xf0);
553
554 return 0;
555 }
556
557 static int alps_bsru6_pll_set(struct dvb_frontend *fe, struct dvb_frontend_parameters *params)
558 {
559 struct budget_ci *budget_ci = (struct budget_ci *) fe->dvb->priv;
560 u8 buf[4];
561 u32 div;
562 struct i2c_msg msg = {.addr = 0x61,.flags = 0,.buf = buf,.len = sizeof(buf) };
563
564 if ((params->frequency < 950000) || (params->frequency > 2150000))
565 return -EINVAL;
566
567 div = (params->frequency + (125 - 1)) / 125; // round correctly
568 buf[0] = (div >> 8) & 0x7f;
569 buf[1] = div & 0xff;
570 buf[2] = 0x80 | ((div & 0x18000) >> 10) | 4;
571 buf[3] = 0xC4;
572
573 if (params->frequency > 1530000)
574 buf[3] = 0xc0;
575
576 if (i2c_transfer(&budget_ci->budget.i2c_adap, &msg, 1) != 1)
577 return -EIO;
578 return 0;
579 }
580
581 static struct stv0299_config alps_bsru6_config = {
582
583 .demod_address = 0x68,
584 .inittab = alps_bsru6_inittab,
585 .mclk = 88000000UL,
586 .invert = 1,
587 .enhanced_tuning = 0,
588 .skip_reinit = 0,
589 .lock_output = STV0229_LOCKOUTPUT_1,
590 .volt13_op0_op1 = STV0299_VOLT13_OP1,
591 .min_delay_ms = 100,
592 .set_symbol_rate = alps_bsru6_set_symbol_rate,
593 .pll_set = alps_bsru6_pll_set,
594 };
595
596
597
598
599 static u8 philips_su1278_tt_inittab[] = {
600 0x01, 0x0f,
601 0x02, 0x30,
602 0x03, 0x00,
603 0x04, 0x5b,
604 0x05, 0x85,
605 0x06, 0x02,
606 0x07, 0x00,
607 0x08, 0x02,
608 0x09, 0x00,
609 0x0C, 0x01,
610 0x0D, 0x81,
611 0x0E, 0x44,
612 0x0f, 0x14,
613 0x10, 0x3c,
614 0x11, 0x84,
615 0x12, 0xda,
616 0x13, 0x97,
617 0x14, 0x95,
618 0x15, 0xc9,
619 0x16, 0x19,
620 0x17, 0x8c,
621 0x18, 0x59,
622 0x19, 0xf8,
623 0x1a, 0xfe,
624 0x1c, 0x7f,
625 0x1d, 0x00,
626 0x1e, 0x00,
627 0x1f, 0x50,
628 0x20, 0x00,
629 0x21, 0x00,
630 0x22, 0x00,
631 0x23, 0x00,
632 0x28, 0x00,
633 0x29, 0x28,
634 0x2a, 0x14,
635 0x2b, 0x0f,
636 0x2c, 0x09,
637 0x2d, 0x09,
638 0x31, 0x1f,
639 0x32, 0x19,
640 0x33, 0xfc,
641 0x34, 0x93,
642 0xff, 0xff
643 };
644
645 static int philips_su1278_tt_set_symbol_rate(struct dvb_frontend *fe, u32 srate, u32 ratio)
646 {
647 stv0299_writereg(fe, 0x0e, 0x44);
648 if (srate >= 10000000) {
649 stv0299_writereg(fe, 0x13, 0x97);
650 stv0299_writereg(fe, 0x14, 0x95);
651 stv0299_writereg(fe, 0x15, 0xc9);
652 stv0299_writereg(fe, 0x17, 0x8c);
653 stv0299_writereg(fe, 0x1a, 0xfe);
654 stv0299_writereg(fe, 0x1c, 0x7f);
655 stv0299_writereg(fe, 0x2d, 0x09);
656 } else {
657 stv0299_writereg(fe, 0x13, 0x99);
658 stv0299_writereg(fe, 0x14, 0x8d);
659 stv0299_writereg(fe, 0x15, 0xce);
660 stv0299_writereg(fe, 0x17, 0x43);
661 stv0299_writereg(fe, 0x1a, 0x1d);
662 stv0299_writereg(fe, 0x1c, 0x12);
663 stv0299_writereg(fe, 0x2d, 0x05);
664 }
665 stv0299_writereg(fe, 0x0e, 0x23);
666 stv0299_writereg(fe, 0x0f, 0x94);
667 stv0299_writereg(fe, 0x10, 0x39);
668 stv0299_writereg(fe, 0x15, 0xc9);
669
670 stv0299_writereg(fe, 0x1f, (ratio >> 16) & 0xff);
671 stv0299_writereg(fe, 0x20, (ratio >> 8) & 0xff);
672 stv0299_writereg(fe, 0x21, (ratio) & 0xf0);
673
674 return 0;
675 }
676
677 static int philips_su1278_tt_pll_set(struct dvb_frontend *fe,
678 struct dvb_frontend_parameters *params)
679 {
680 struct budget_ci *budget_ci = (struct budget_ci *) fe->dvb->priv;
681 u32 div;
682 u8 buf[4];
683 struct i2c_msg msg = {.addr = 0x60,.flags = 0,.buf = buf,.len = sizeof(buf) };
684
685 if ((params->frequency < 950000) || (params->frequency > 2150000))
686 return -EINVAL;
687
688 div = (params->frequency + (500 - 1)) / 500; // round correctly
689 buf[0] = (div >> 8) & 0x7f;
690 buf[1] = div & 0xff;
691 buf[2] = 0x80 | ((div & 0x18000) >> 10) | 2;
692 buf[3] = 0x20;
693
694 if (params->u.qpsk.symbol_rate < 4000000)
695 buf[3] |= 1;
696
697 if (params->frequency < 1250000)
698 buf[3] |= 0;
699 else if (params->frequency < 1550000)
700 buf[3] |= 0x40;
701 else if (params->frequency < 2050000)
702 buf[3] |= 0x80;
703 else if (params->frequency < 2150000)
704 buf[3] |= 0xC0;
705
706 if (i2c_transfer(&budget_ci->budget.i2c_adap, &msg, 1) != 1)
707 return -EIO;
708 return 0;
709 }
710
711 static struct stv0299_config philips_su1278_tt_config = {
712
713 .demod_address = 0x68,
714 .inittab = philips_su1278_tt_inittab,
715 .mclk = 64000000UL,
716 .invert = 0,
717 .enhanced_tuning = 1,
718 .skip_reinit = 1,
719 .lock_output = STV0229_LOCKOUTPUT_1,
720 .volt13_op0_op1 = STV0299_VOLT13_OP1,
721 .min_delay_ms = 50,
722 .set_symbol_rate = philips_su1278_tt_set_symbol_rate,
723 .pll_set = philips_su1278_tt_pll_set,
724 };
725
726
727
728 static int philips_tdm1316l_pll_init(struct dvb_frontend *fe)
729 {
730 struct budget_ci *budget_ci = (struct budget_ci *) fe->dvb->priv;
731 static u8 td1316_init[] = { 0x0b, 0xf5, 0x85, 0xab };
732 static u8 disable_mc44BC374c[] = { 0x1d, 0x74, 0xa0, 0x68 };
733 struct i2c_msg tuner_msg = {.addr = 0x63,.flags = 0,.buf = td1316_init,.len =
734 sizeof(td1316_init) };
735
736 // setup PLL configuration
737 if (i2c_transfer(&budget_ci->budget.i2c_adap, &tuner_msg, 1) != 1)
738 return -EIO;
739 msleep(1);
740
741 // disable the mc44BC374c (do not check for errors)
742 tuner_msg.addr = 0x65;
743 tuner_msg.buf = disable_mc44BC374c;
744 tuner_msg.len = sizeof(disable_mc44BC374c);
745 if (i2c_transfer(&budget_ci->budget.i2c_adap, &tuner_msg, 1) != 1) {
746 i2c_transfer(&budget_ci->budget.i2c_adap, &tuner_msg, 1);
747 }
748
749 return 0;
750 }
751
752 static int philips_tdm1316l_pll_set(struct dvb_frontend *fe, struct dvb_frontend_parameters *params)
753 {
754 struct budget_ci *budget_ci = (struct budget_ci *) fe->dvb->priv;
755 u8 tuner_buf[4];
756 struct i2c_msg tuner_msg = {.addr = 0x63,.flags = 0,.buf = tuner_buf,.len = sizeof(tuner_buf) };
757 int tuner_frequency = 0;
758 u8 band, cp, filter;
759
760 // determine charge pump
761 tuner_frequency = params->frequency + 36130000;
762 if (tuner_frequency < 87000000)
763 return -EINVAL;
764 else if (tuner_frequency < 130000000)
765 cp = 3;
766 else if (tuner_frequency < 160000000)
767 cp = 5;
768 else if (tuner_frequency < 200000000)
769 cp = 6;
770 else if (tuner_frequency < 290000000)
771 cp = 3;
772 else if (tuner_frequency < 420000000)
773 cp = 5;
774 else if (tuner_frequency < 480000000)
775 cp = 6;
776 else if (tuner_frequency < 620000000)
777 cp = 3;
778 else if (tuner_frequency < 830000000)
779 cp = 5;
780 else if (tuner_frequency < 895000000)
781 cp = 7;
782 else
783 return -EINVAL;
784
785 // determine band
786 if (params->frequency < 49000000)
787 return -EINVAL;
788 else if (params->frequency < 159000000)
789 band = 1;
790 else if (params->frequency < 444000000)
791 band = 2;
792 else if (params->frequency < 861000000)
793 band = 4;
794 else
795 return -EINVAL;
796
797 // setup PLL filter and TDA9889
798 switch (params->u.ofdm.bandwidth) {
799 case BANDWIDTH_6_MHZ:
800 tda1004x_write_byte(fe, 0x0C, 0x14);
801 filter = 0;
802 break;
803
804 case BANDWIDTH_7_MHZ:
805 tda1004x_write_byte(fe, 0x0C, 0x80);
806 filter = 0;
807 break;
808
809 case BANDWIDTH_8_MHZ:
810 tda1004x_write_byte(fe, 0x0C, 0x14);
811 filter = 1;
812 break;
813
814 default:
815 return -EINVAL;
816 }
817
818 // calculate divisor
819 // ((36130000+((1000000/6)/2)) + Finput)/(1000000/6)
820 tuner_frequency = (((params->frequency / 1000) * 6) + 217280) / 1000;
821
822 // setup tuner buffer
823 tuner_buf[0] = tuner_frequency >> 8;
824 tuner_buf[1] = tuner_frequency & 0xff;
825 tuner_buf[2] = 0xca;
826 tuner_buf[3] = (cp << 5) | (filter << 3) | band;
827
828 if (i2c_transfer(&budget_ci->budget.i2c_adap, &tuner_msg, 1) != 1)
829 return -EIO;
830
831 msleep(1);
832 return 0;
833 }
834
835 static int philips_tdm1316l_request_firmware(struct dvb_frontend *fe,
836 const struct firmware **fw, char *name)
837 {
838 struct budget_ci *budget_ci = (struct budget_ci *) fe->dvb->priv;
839
840 return request_firmware(fw, name, &budget_ci->budget.dev->pci->dev);
841 }
842
843 static struct tda1004x_config philips_tdm1316l_config = {
844
845 .demod_address = 0x8,
846 .invert = 0,
847 .invert_oclk = 0,
848 .pll_init = philips_tdm1316l_pll_init,
849 .pll_set = philips_tdm1316l_pll_set,
850 .request_firmware = philips_tdm1316l_request_firmware,
851 };
852
853
854
855 static void frontend_init(struct budget_ci *budget_ci)
856 {
857 switch (budget_ci->budget.dev->pci->subsystem_device) {
858 case 0x100c: // Hauppauge/TT Nova-CI budget (stv0299/ALPS BSRU6(tsa5059))
859 budget_ci->budget.dvb_frontend =
860 stv0299_attach(&alps_bsru6_config, &budget_ci->budget.i2c_adap);
861 if (budget_ci->budget.dvb_frontend) {
862 break;
863 }
864 break;
865
866 case 0x100f: // Hauppauge/TT Nova-CI budget (stv0299b/Philips su1278(tsa5059))
867 budget_ci->budget.dvb_frontend =
868 stv0299_attach(&philips_su1278_tt_config, &budget_ci->budget.i2c_adap);
869 if (budget_ci->budget.dvb_frontend) {
870 break;
871 }
872 break;
873
874 case 0x1011: // Hauppauge/TT Nova-T budget (tda10045/Philips tdm1316l(tda6651tt) + TDA9889)
875 budget_ci->budget.dvb_frontend =
876 tda10045_attach(&philips_tdm1316l_config, &budget_ci->budget.i2c_adap);
877 if (budget_ci->budget.dvb_frontend) {
878 break;
879 }
880 break;
881 }
882
883 if (budget_ci->budget.dvb_frontend == NULL) {
884 printk("budget-ci: A frontend driver was not found for device %04x/%04x subsystem %04x/%04x\n",
885 budget_ci->budget.dev->pci->vendor,
886 budget_ci->budget.dev->pci->device,
887 budget_ci->budget.dev->pci->subsystem_vendor,
888 budget_ci->budget.dev->pci->subsystem_device);
889 } else {
890 if (dvb_register_frontend
891 (budget_ci->budget.dvb_adapter, budget_ci->budget.dvb_frontend)) {
892 printk("budget-ci: Frontend registration failed!\n");
893 if (budget_ci->budget.dvb_frontend->ops->release)
894 budget_ci->budget.dvb_frontend->ops->release(budget_ci->budget.dvb_frontend);
895 budget_ci->budget.dvb_frontend = NULL;
896 }
897 }
898 }
899
900 static int budget_ci_attach(struct saa7146_dev *dev, struct saa7146_pci_extension_data *info)
901 {
902 struct budget_ci *budget_ci;
903 int err;
904
905 if (!(budget_ci = kmalloc (sizeof(struct budget_ci), GFP_KERNEL)))
906 return -ENOMEM;
907
908 dprintk(2, "budget_ci: %p\n", budget_ci);
909
910 budget_ci->budget.ci_present = 0;
911
912 dev->ext_priv = budget_ci;
913
914 if ((err = ttpci_budget_init(&budget_ci->budget, dev, info, THIS_MODULE))) {
915 kfree (budget_ci);
916 return err;
917 }
918
919 tasklet_init (&budget_ci->msp430_irq_tasklet, msp430_ir_interrupt,
920 (unsigned long) budget_ci);
921
922 msp430_ir_init (budget_ci);
923
924 ciintf_init(budget_ci);
925
926 budget_ci->budget.dvb_adapter->priv = budget_ci;
927 frontend_init(budget_ci);
928
929 return 0;
930 }
931
932
933
934 static int budget_ci_detach (struct saa7146_dev* dev)
935 {
936 struct budget_ci *budget_ci = (struct budget_ci*) dev->ext_priv;
937 struct saa7146_dev *saa = budget_ci->budget.dev;
938 int err;
939
940 if (budget_ci->budget.ci_present)
941 ciintf_deinit(budget_ci);
942 if (budget_ci->budget.dvb_frontend)
943 dvb_unregister_frontend(budget_ci->budget.dvb_frontend);
944 err = ttpci_budget_deinit (&budget_ci->budget);
945
946 tasklet_kill (&budget_ci->msp430_irq_tasklet);
947
948 msp430_ir_deinit (budget_ci);
949
950 // disable frontend and CI interface
951 saa7146_setgpio(saa, 2, SAA7146_GPIO_INPUT);
952
953 kfree (budget_ci);
954
955 return err;
956 }
957
958
959
960 static struct saa7146_extension budget_extension;
961
962 MAKE_BUDGET_INFO(ttbci, "TT-Budget/WinTV-NOVA-CI PCI", BUDGET_TT_HW_DISEQC);
963 MAKE_BUDGET_INFO(ttbt2, "TT-Budget/WinTV-NOVA-T PCI", BUDGET_TT);
964
965 static struct pci_device_id pci_tbl[] = {
966 MAKE_EXTENSION_PCI(ttbci, 0x13c2, 0x100c),
967 MAKE_EXTENSION_PCI(ttbci, 0x13c2, 0x100f),
968 MAKE_EXTENSION_PCI(ttbt2, 0x13c2, 0x1011),
969 {
970 .vendor = 0,
971 }
972 };
973
974 MODULE_DEVICE_TABLE(pci, pci_tbl);
975
976 static struct saa7146_extension budget_extension = {
977 .name = "budget_ci dvb\0",
978 .flags = 0,
979
980 .module = THIS_MODULE,
981 .pci_tbl = &pci_tbl[0],
982 .attach = budget_ci_attach,
983 .detach = budget_ci_detach,
984
985 .irq_mask = MASK_03 | MASK_06 | MASK_10,
986 .irq_func = budget_ci_irq,
987 };
988
989
990 static int __init budget_ci_init(void)
991 {
992 return saa7146_register_extension(&budget_extension);
993 }
994
995 static void __exit budget_ci_exit(void)
996 {
997 saa7146_unregister_extension(&budget_extension);
998 }
999
1000 module_init(budget_ci_init);
1001 module_exit(budget_ci_exit);
1002
1003 MODULE_LICENSE("GPL");
1004 MODULE_AUTHOR("Michael Hunold, Jack Thomasson, Andrew de Quincey, others");
1005 MODULE_DESCRIPTION("driver for the SAA7146 based so-called "
1006 "budget PCI DVB cards w/ CI-module produced by "
1007 "Siemens, Technotrend, Hauppauge");
1008
1009
|
This page was automatically generated by the
LXR engine.
|