3 * Copyright (c) 2007 Mauro Carvalho Chehab (mchehab@infradead.org)
5 * Copyright (c) 2007 Michel Ludwig (michel.ludwig@gmail.com)
8 * This code is placed under the terms of the GNU General Public License v2
11 #include <linux/i2c.h>
12 #include <asm/div64.h>
13 #include <linux/firmware.h>
14 #include <linux/videodev2.h>
15 #include <linux/delay.h>
16 #include <media/tuner.h>
17 #include <linux/mutex.h>
18 #include "tuner-i2c.h"
19 #include "tuner-xc2028.h"
20 #include "tuner-xc2028-types.h"
22 #include <linux/dvb/frontend.h>
23 #include "dvb_frontend.h"
26 #define PREFIX "xc2028"
29 module_param(debug
, int, 0644);
30 MODULE_PARM_DESC(debug
, "enable verbose debug messages");
32 static char audio_std
[8];
33 module_param_string(audio_std
, audio_std
, sizeof(audio_std
), 0);
34 MODULE_PARM_DESC(audio_std
,
35 "Audio standard. XC3028 audio decoder explicitly "
36 "needs to know what audio\n"
37 "standard is needed for some video standards with audio A2 or NICAM.\n"
38 "The valid values are:\n"
46 static LIST_HEAD(xc2028_list
);
47 static DEFINE_MUTEX(xc2028_list_mutex
);
49 /* struct for storing firmware table */
50 struct firmware_description
{
57 struct firmware_properties
{
61 unsigned int scode_table
;
66 struct list_head xc2028_list
;
67 struct tuner_i2c_props i2c_props
;
68 int (*tuner_callback
) (void *dev
,
69 int command
, int arg
);
74 struct firmware_description
*firm
;
81 struct xc2028_ctrl ctrl
;
83 struct firmware_properties cur_fw
;
88 #define i2c_send(priv, buf, size) ({ \
90 _rc = tuner_i2c_xfer_send(&priv->i2c_props, buf, size); \
92 tuner_info("i2c output error: rc = %d (should be %d)\n",\
97 #define i2c_rcv(priv, buf, size) ({ \
99 _rc = tuner_i2c_xfer_recv(&priv->i2c_props, buf, size); \
101 tuner_err("i2c input error: rc = %d (should be %d)\n", \
106 #define i2c_send_recv(priv, obuf, osize, ibuf, isize) ({ \
108 _rc = tuner_i2c_xfer_send_recv(&priv->i2c_props, obuf, osize, \
111 tuner_err("i2c input error: rc = %d (should be %d)\n", \
116 #define send_seq(priv, data...) ({ \
117 static u8 _val[] = data; \
119 if (sizeof(_val) != \
120 (_rc = tuner_i2c_xfer_send(&priv->i2c_props, \
121 _val, sizeof(_val)))) { \
122 tuner_err("Error on line %d: %d\n", __LINE__, _rc); \
128 static unsigned int xc2028_get_reg(struct xc2028_data
*priv
, u16 reg
, u16
*val
)
130 unsigned char buf
[2];
131 unsigned char ibuf
[2];
133 tuner_dbg("%s %04x called\n", __FUNCTION__
, reg
);
136 buf
[1] = (unsigned char) reg
;
138 if (i2c_send_recv(priv
, buf
, 2, ibuf
, 2) != 2)
141 *val
= (ibuf
[1]) | (ibuf
[0] << 8);
145 void dump_firm_type(unsigned int type
)
191 if (type
& TOYOTA388
)
192 printk("TOYOTA388 ");
193 if (type
& TOYOTA794
)
194 printk("TOYOTA794 ");
197 if (type
& ZARLINK456
)
198 printk("ZARLINK456 ");
209 static v4l2_std_id
parse_audio_std_option(void)
211 if (strcasecmp(audio_std
, "A2") == 0)
213 if (strcasecmp(audio_std
, "A2/A") == 0)
214 return V4L2_STD_A2_A
;
215 if (strcasecmp(audio_std
, "A2/B") == 0)
216 return V4L2_STD_A2_B
;
217 if (strcasecmp(audio_std
, "NICAM") == 0)
218 return V4L2_STD_NICAM
;
219 if (strcasecmp(audio_std
, "NICAM/A") == 0)
220 return V4L2_STD_NICAM_A
;
221 if (strcasecmp(audio_std
, "NICAM/B") == 0)
222 return V4L2_STD_NICAM_B
;
227 static void free_firmware(struct xc2028_data
*priv
)
234 for (i
= 0; i
< priv
->firm_size
; i
++)
235 kfree(priv
->firm
[i
].ptr
);
242 memset(&priv
->cur_fw
, 0, sizeof(priv
->cur_fw
));
245 static int load_all_firmwares(struct dvb_frontend
*fe
)
247 struct xc2028_data
*priv
= fe
->tuner_priv
;
248 const struct firmware
*fw
= NULL
;
249 unsigned char *p
, *endp
;
254 tuner_dbg("%s called\n", __FUNCTION__
);
256 tuner_dbg("Reading firmware %s\n", priv
->ctrl
.fname
);
257 rc
= request_firmware(&fw
, priv
->ctrl
.fname
,
258 &priv
->i2c_props
.adap
->dev
);
261 tuner_err("Error: firmware %s not found.\n",
264 tuner_err("Error %d while requesting firmware %s \n",
265 rc
, priv
->ctrl
.fname
);
272 if (fw
->size
< sizeof(name
) - 1 + 2 + 2) {
273 tuner_err("Error: firmware file %s has invalid size!\n",
278 memcpy(name
, p
, sizeof(name
) - 1);
279 name
[sizeof(name
) - 1] = 0;
280 p
+= sizeof(name
) - 1;
282 priv
->firm_version
= le16_to_cpu(*(__u16
*) p
);
285 n_array
= le16_to_cpu(*(__u16
*) p
);
288 tuner_info("Loading %d firmware images from %s, type: %s, ver %d.%d\n",
289 n_array
, priv
->ctrl
.fname
, name
,
290 priv
->firm_version
>> 8, priv
->firm_version
& 0xff);
292 priv
->firm
= kzalloc(sizeof(*priv
->firm
) * n_array
, GFP_KERNEL
);
293 if (priv
->firm
== NULL
) {
294 tuner_err("Not enough memory to load firmware file.\n");
298 priv
->firm_size
= n_array
;
307 tuner_err("More firmware images in file than "
312 /* Checks if there's enough bytes to read */
313 if (p
+ sizeof(type
) + sizeof(id
) + sizeof(size
) > endp
) {
314 tuner_err("Firmware header is incomplete!\n");
318 type
= le32_to_cpu(*(__u32
*) p
);
321 id
= le64_to_cpu(*(v4l2_std_id
*) p
);
324 size
= le32_to_cpu(*(__u32
*) p
);
327 if ((!size
) || (size
+ p
> endp
)) {
328 tuner_err("Firmware type ");
329 dump_firm_type(type
);
330 printk("(%x), id %llx is corrupted "
331 "(size=%d, expected %d)\n",
332 type
, (unsigned long long)id
,
333 (unsigned)(endp
- p
), size
);
337 priv
->firm
[n
].ptr
= kzalloc(size
, GFP_KERNEL
);
338 if (priv
->firm
[n
].ptr
== NULL
) {
339 tuner_err("Not enough memory to load firmware file.\n");
343 tuner_dbg("Reading firmware type ");
345 dump_firm_type(type
);
346 printk("(%x), id %llx, size=%d.\n",
347 type
, (unsigned long long)id
, size
);
350 memcpy(priv
->firm
[n
].ptr
, p
, size
);
351 priv
->firm
[n
].type
= type
;
352 priv
->firm
[n
].id
= id
;
353 priv
->firm
[n
].size
= size
;
358 if (n
+ 1 != priv
->firm_size
) {
359 tuner_err("Firmware file is incomplete!\n");
367 tuner_err("Error: firmware file is corrupted!\n");
370 tuner_info("Releasing partially loaded firmware file.\n");
374 release_firmware(fw
);
376 tuner_dbg("Firmware files loaded.\n");
381 static int seek_firmware(struct dvb_frontend
*fe
, unsigned int type
,
384 struct xc2028_data
*priv
= fe
->tuner_priv
;
385 int i
, best_i
= -1, best_nr_matches
= 0;
387 tuner_dbg("%s called, want type=", __FUNCTION__
);
389 dump_firm_type(type
);
390 printk("(%x), id %016llx.\n", type
, (unsigned long long)*id
);
394 tuner_err("Error! firmware not loaded\n");
398 if (((type
& ~SCODE
) == 0) && (*id
== 0))
403 else if (type
& SCODE
)
405 else if (type
& DTV_TYPES
)
407 else if (type
& STD_SPECIFIC_TYPES
)
408 type
&= STD_SPECIFIC_TYPES
;
410 /* Seek for exact match */
411 for (i
= 0; i
< priv
->firm_size
; i
++) {
412 if ((type
== priv
->firm
[i
].type
) && (*id
== priv
->firm
[i
].id
))
416 /* Seek for generic video standard match */
417 for (i
= 0; i
< priv
->firm_size
; i
++) {
418 v4l2_std_id match_mask
;
421 if (type
!= priv
->firm
[i
].type
)
424 match_mask
= *id
& priv
->firm
[i
].id
;
428 if ((*id
& match_mask
) == *id
)
429 goto found
; /* Supports all the requested standards */
431 nr_matches
= hweight64(match_mask
);
432 if (nr_matches
> best_nr_matches
) {
433 best_nr_matches
= nr_matches
;
438 if (best_nr_matches
> 0) {
439 tuner_dbg("Selecting best matching firmware (%d bits) for "
440 "type=", best_nr_matches
);
441 dump_firm_type(type
);
442 printk("(%x), id %016llx:\n", type
, (unsigned long long)*id
);
447 /*FIXME: Would make sense to seek for type "hint" match ? */
453 *id
= priv
->firm
[i
].id
;
456 tuner_dbg("%s firmware for type=", (i
< 0) ? "Can't find" : "Found");
458 dump_firm_type(type
);
459 printk("(%x), id %016llx.\n", type
, (unsigned long long)*id
);
464 static int load_firmware(struct dvb_frontend
*fe
, unsigned int type
,
467 struct xc2028_data
*priv
= fe
->tuner_priv
;
469 unsigned char *p
, *endp
, buf
[priv
->ctrl
.max_len
];
471 tuner_dbg("%s called\n", __FUNCTION__
);
473 pos
= seek_firmware(fe
, type
, id
);
477 tuner_info("Loading firmware for type=");
478 dump_firm_type(priv
->firm
[pos
].type
);
479 printk("(%x), id %016llx.\n", priv
->firm
[pos
].type
,
480 (unsigned long long)*id
);
482 p
= priv
->firm
[pos
].ptr
;
483 endp
= p
+ priv
->firm
[pos
].size
;
488 /* Checks if there's enough bytes to read */
489 if (p
+ sizeof(size
) > endp
) {
490 tuner_err("Firmware chunk size is wrong\n");
494 size
= le16_to_cpu(*(__u16
*) p
);
501 /* Special callback command received */
502 rc
= priv
->tuner_callback(priv
->video_dev
,
503 XC2028_TUNER_RESET
, 0);
505 tuner_err("Error at RESET code %d\n",
511 if (size
>= 0xff00) {
514 rc
= priv
->tuner_callback(priv
->video_dev
,
515 XC2028_RESET_CLK
, 0);
517 tuner_err("Error at RESET code %d\n",
523 tuner_info("Invalid RESET code %d\n",
531 /* Checks for a sleep command */
533 msleep(size
& 0x7fff);
537 if ((size
+ p
> endp
)) {
538 tuner_err("missing bytes: need %d, have %d\n",
539 size
, (int)(endp
- p
));
547 /* Sends message chunks */
549 int len
= (size
< priv
->ctrl
.max_len
- 1) ?
550 size
: priv
->ctrl
.max_len
- 1;
552 memcpy(buf
+ 1, p
, len
);
554 rc
= i2c_send(priv
, buf
, len
+ 1);
556 tuner_err("%d returned from send\n", rc
);
567 static int load_scode(struct dvb_frontend
*fe
, unsigned int type
,
568 v4l2_std_id
*id
, int scode
)
570 struct xc2028_data
*priv
= fe
->tuner_priv
;
574 tuner_dbg("%s called\n", __FUNCTION__
);
576 pos
= seek_firmware(fe
, type
, id
);
580 p
= priv
->firm
[pos
].ptr
;
582 /* 16 SCODE entries per file; each SCODE entry is 12 bytes and
583 * has a 2-byte size header in the firmware format. */
584 if (priv
->firm
[pos
].size
!= 14 * 16 || scode
>= 16 ||
585 le16_to_cpu(*(__u16
*)(p
+ 14 * scode
)) != 12)
588 tuner_info("Loading SCODE for type=");
589 dump_firm_type(priv
->firm
[pos
].type
);
590 printk("(%x), id %016llx.\n", priv
->firm
[pos
].type
,
591 (unsigned long long)*id
);
593 if (priv
->firm_version
< 0x0202)
594 rc
= send_seq(priv
, {0x20, 0x00, 0x00, 0x00});
596 rc
= send_seq(priv
, {0xa0, 0x00, 0x00, 0x00});
600 rc
= i2c_send(priv
, p
+ 14 * scode
+ 2, 12);
604 rc
= send_seq(priv
, {0x00, 0x8c});
611 static int check_firmware(struct dvb_frontend
*fe
, enum tuner_mode new_mode
,
612 v4l2_std_id std
, fe_bandwidth_t bandwidth
)
614 struct xc2028_data
*priv
= fe
->tuner_priv
;
615 int rc
= 0, is_retry
= 0;
616 unsigned int type
= 0;
617 struct firmware_properties new_fw
;
618 u16 version
, hwmodel
;
621 tuner_dbg("%s called\n", __FUNCTION__
);
624 if (!priv
->ctrl
.fname
) {
625 tuner_info("xc2028/3028 firmware name not set!\n");
629 rc
= load_all_firmwares(fe
);
634 if (priv
->ctrl
.type
== XC2028_FIRM_MTS
)
636 if (bandwidth
== BANDWIDTH_7_MHZ
|| bandwidth
== BANDWIDTH_8_MHZ
)
639 /* FIXME: How to load FM and FM|INPUT1 firmwares? */
641 if (new_mode
== T_DIGITAL_TV
) {
642 if (priv
->ctrl
.d2633
)
648 case BANDWIDTH_8_MHZ
:
651 case BANDWIDTH_7_MHZ
:
654 case BANDWIDTH_6_MHZ
:
655 /* FIXME: Should allow select also ATSC */
659 tuner_err("error: bandwidth not supported.\n");
666 new_fw
.std_req
= std
;
667 new_fw
.scode_table
= SCODE
| priv
->ctrl
.scode_table
;
670 tuner_dbg("checking firmware, user requested type=");
672 dump_firm_type(new_fw
.type
);
673 printk("(%x), id %016llx, scode_tbl ", new_fw
.type
,
674 (unsigned long long)new_fw
.std_req
);
675 dump_firm_type(priv
->ctrl
.scode_table
);
676 printk("(%x), scode_nr %d\n", priv
->ctrl
.scode_table
,
680 /* No need to reload base firmware if it matches */
681 if (((BASE
| new_fw
.type
) & BASE_TYPES
) ==
682 (priv
->cur_fw
.type
& BASE_TYPES
)) {
683 tuner_dbg("BASE firmware not changed.\n");
687 /* Updating BASE - forget about all currently loaded firmware */
688 memset(&priv
->cur_fw
, 0, sizeof(priv
->cur_fw
));
690 /* Reset is needed before loading firmware */
691 rc
= priv
->tuner_callback(priv
->video_dev
,
692 XC2028_TUNER_RESET
, 0);
696 /* BASE firmwares are all std0 */
698 rc
= load_firmware(fe
, BASE
| new_fw
.type
, &std0
);
700 tuner_err("Error %d while loading base firmware\n",
705 /* Load INIT1, if needed */
706 tuner_dbg("Load init1 firmware, if exists\n");
708 rc
= load_firmware(fe
, BASE
| INIT1
| new_fw
.type
, &std0
);
709 if (rc
< 0 && rc
!= -ENOENT
) {
710 tuner_err("Error %d while loading init1 firmware\n",
717 * No need to reload standard specific firmware if base firmware
718 * was not reloaded and requested video standards have not changed.
720 if (priv
->cur_fw
.type
== (BASE
| new_fw
.type
) &&
721 priv
->cur_fw
.std_req
== std
) {
722 tuner_dbg("Std-specific firmware already loaded.\n");
723 goto skip_std_specific
;
726 /* Reloading std-specific firmware forces a SCODE update */
727 priv
->cur_fw
.scode_table
= 0;
729 /* Add audio hack to std mask */
730 if (new_mode
== T_ANALOG_TV
)
731 new_fw
.id
|= parse_audio_std_option();
733 rc
= load_firmware(fe
, new_fw
.type
, &new_fw
.id
);
738 if (priv
->cur_fw
.scode_table
== new_fw
.scode_table
&&
739 priv
->cur_fw
.scode_nr
== new_fw
.scode_nr
) {
740 tuner_dbg("SCODE firmware already loaded.\n");
744 /* Load SCODE firmware, if exists */
745 tuner_dbg("Trying to load scode %d\n", new_fw
.scode_nr
);
747 rc
= load_scode(fe
, new_fw
.type
| new_fw
.scode_table
,
748 &new_fw
.id
, new_fw
.scode_nr
);
751 if (xc2028_get_reg(priv
, 0x0004, &version
) < 0 ||
752 xc2028_get_reg(priv
, 0x0008, &hwmodel
) < 0) {
753 tuner_err("Unable to read tuner registers.\n");
757 tuner_info("Device is Xceive %d version %d.%d, "
758 "firmware version %d.%d\n",
759 hwmodel
, (version
& 0xf000) >> 12, (version
& 0xf00) >> 8,
760 (version
& 0xf0) >> 4, version
& 0xf);
762 /* Check firmware version against what we downloaded. */
763 if (priv
->firm_version
!= ((version
& 0xf0) << 4 | (version
& 0x0f))) {
764 tuner_err("Incorrect readback of firmware version.\n");
768 /* Check that the tuner hardware model remains consistent over time. */
769 if (priv
->hwmodel
== 0 && (hwmodel
== 2028 || hwmodel
== 3028)) {
770 priv
->hwmodel
= hwmodel
;
771 priv
->hwvers
= version
& 0xff00;
772 } else if (priv
->hwmodel
== 0 || priv
->hwmodel
!= hwmodel
||
773 priv
->hwvers
!= (version
& 0xff00)) {
774 tuner_err("Read invalid device hardware information - tuner "
779 memcpy(&priv
->cur_fw
, &new_fw
, sizeof(priv
->cur_fw
));
782 * By setting BASE in cur_fw.type only after successfully loading all
784 * 1. Identify that BASE firmware with type=0 has been loaded;
785 * 2. Tell whether BASE firmware was just changed the next time through.
787 priv
->cur_fw
.type
|= BASE
;
792 memset(&priv
->cur_fw
, 0, sizeof(priv
->cur_fw
));
796 tuner_dbg("Retrying firmware load\n");
805 static int xc2028_signal(struct dvb_frontend
*fe
, u16
*strength
)
807 struct xc2028_data
*priv
= fe
->tuner_priv
;
808 u16 frq_lock
, signal
= 0;
811 tuner_dbg("%s called\n", __FUNCTION__
);
813 mutex_lock(&priv
->lock
);
815 /* Sync Lock Indicator */
816 rc
= xc2028_get_reg(priv
, 0x0002, &frq_lock
);
817 if (rc
< 0 || frq_lock
== 0)
820 /* Frequency is locked. Return signal quality */
822 /* Get SNR of the video signal */
823 rc
= xc2028_get_reg(priv
, 0x0040, &signal
);
828 mutex_unlock(&priv
->lock
);
837 static int generic_set_tv_freq(struct dvb_frontend
*fe
, u32 freq
/* in Hz */ ,
838 enum tuner_mode new_mode
,
839 v4l2_std_id std
, fe_bandwidth_t bandwidth
)
841 struct xc2028_data
*priv
= fe
->tuner_priv
;
843 unsigned char buf
[4];
846 tuner_dbg("%s called\n", __FUNCTION__
);
848 mutex_lock(&priv
->lock
);
850 /* HACK: It seems that specific firmware need to be reloaded
851 when watching analog TV and freq is changed */
852 if (new_mode
!= T_DIGITAL_TV
)
853 priv
->cur_fw
.type
= 0;
855 tuner_dbg("should set frequency %d kHz\n", freq
/ 1000);
857 if (check_firmware(fe
, new_mode
, std
, bandwidth
) < 0)
860 if (new_mode
== T_DIGITAL_TV
) {
862 if (priv
->cur_fw
.type
& DTV7
)
866 div
= (freq
- offset
+ DIV
/ 2) / DIV
;
868 /* CMD= Set frequency */
869 if (priv
->firm_version
< 0x0202)
870 rc
= send_seq(priv
, {0x00, 0x02, 0x00, 0x00});
872 rc
= send_seq(priv
, {0x80, 0x02, 0x00, 0x00});
876 rc
= priv
->tuner_callback(priv
->video_dev
, XC2028_RESET_CLK
, 1);
882 buf
[0] = 0xff & (div
>> 24);
883 buf
[1] = 0xff & (div
>> 16);
884 buf
[2] = 0xff & (div
>> 8);
885 buf
[3] = 0xff & (div
);
887 rc
= i2c_send(priv
, buf
, sizeof(buf
));
892 priv
->frequency
= freq
;
894 tuner_dbg("divisor= %02x %02x %02x %02x (freq=%d.%03d)\n",
895 buf
[0], buf
[1], buf
[2], buf
[3],
896 freq
/ 1000000, (freq
% 1000000) / 1000);
901 mutex_unlock(&priv
->lock
);
906 static int xc2028_set_tv_freq(struct dvb_frontend
*fe
,
907 struct analog_parameters
*p
)
909 struct xc2028_data
*priv
= fe
->tuner_priv
;
911 tuner_dbg("%s called\n", __FUNCTION__
);
913 return generic_set_tv_freq(fe
, 62500l * p
->frequency
, T_ANALOG_TV
,
914 p
->std
, BANDWIDTH_8_MHZ
);
915 /* XXX Are some analog standards 6MHz? */
918 static int xc2028_set_params(struct dvb_frontend
*fe
,
919 struct dvb_frontend_parameters
*p
)
921 struct xc2028_data
*priv
= fe
->tuner_priv
;
923 tuner_dbg("%s called\n", __FUNCTION__
);
925 /* FIXME: Only OFDM implemented */
926 if (fe
->ops
.info
.type
!= FE_OFDM
) {
927 tuner_err("DTV type not implemented.\n");
931 return generic_set_tv_freq(fe
, p
->frequency
, T_DIGITAL_TV
,
933 p
->u
.ofdm
.bandwidth
);
937 static int xc2028_sleep(struct dvb_frontend
*fe
)
939 struct xc2028_data
*priv
= fe
->tuner_priv
;
942 tuner_dbg("%s called\n", __FUNCTION__
);
944 mutex_lock(&priv
->lock
);
946 if (priv
->firm_version
< 0x0202)
947 rc
= send_seq(priv
, {0x00, 0x08, 0x00, 0x00});
949 rc
= send_seq(priv
, {0x80, 0x08, 0x00, 0x00});
951 priv
->cur_fw
.type
= 0; /* need firmware reload */
953 mutex_unlock(&priv
->lock
);
959 static int xc2028_dvb_release(struct dvb_frontend
*fe
)
961 struct xc2028_data
*priv
= fe
->tuner_priv
;
963 tuner_dbg("%s called\n", __FUNCTION__
);
965 mutex_lock(&xc2028_list_mutex
);
970 list_del(&priv
->xc2028_list
);
972 kfree(priv
->ctrl
.fname
);
976 fe
->tuner_priv
= NULL
;
979 mutex_unlock(&xc2028_list_mutex
);
984 static int xc2028_get_frequency(struct dvb_frontend
*fe
, u32
*frequency
)
986 struct xc2028_data
*priv
= fe
->tuner_priv
;
988 tuner_dbg("%s called\n", __FUNCTION__
);
990 *frequency
= priv
->frequency
;
995 static int xc2028_set_config(struct dvb_frontend
*fe
, void *priv_cfg
)
997 struct xc2028_data
*priv
= fe
->tuner_priv
;
998 struct xc2028_ctrl
*p
= priv_cfg
;
1001 tuner_dbg("%s called\n", __FUNCTION__
);
1003 mutex_lock(&priv
->lock
);
1005 kfree(priv
->ctrl
.fname
);
1006 free_firmware(priv
);
1008 memcpy(&priv
->ctrl
, p
, sizeof(priv
->ctrl
));
1009 priv
->ctrl
.fname
= NULL
;
1012 priv
->ctrl
.fname
= kstrdup(p
->fname
, GFP_KERNEL
);
1013 if (priv
->ctrl
.fname
== NULL
)
1017 if (priv
->ctrl
.max_len
< 9)
1018 priv
->ctrl
.max_len
= 13;
1020 mutex_unlock(&priv
->lock
);
1025 static const struct dvb_tuner_ops xc2028_dvb_tuner_ops
= {
1027 .name
= "Xceive XC3028",
1028 .frequency_min
= 42000000,
1029 .frequency_max
= 864000000,
1030 .frequency_step
= 50000,
1033 .set_config
= xc2028_set_config
,
1034 .set_analog_params
= xc2028_set_tv_freq
,
1035 .release
= xc2028_dvb_release
,
1036 .get_frequency
= xc2028_get_frequency
,
1037 .get_rf_strength
= xc2028_signal
,
1038 .set_params
= xc2028_set_params
,
1039 .sleep
= xc2028_sleep
,
1043 void *xc2028_attach(struct dvb_frontend
*fe
, struct xc2028_config
*cfg
)
1045 struct xc2028_data
*priv
;
1049 printk(KERN_DEBUG PREFIX
": Xcv2028/3028 init called!\n");
1051 if (NULL
== cfg
->video_dev
)
1055 printk(KERN_ERR PREFIX
": No frontend!\n");
1059 video_dev
= cfg
->video_dev
;
1061 mutex_lock(&xc2028_list_mutex
);
1063 list_for_each_entry(priv
, &xc2028_list
, xc2028_list
) {
1064 if (priv
->video_dev
== cfg
->video_dev
) {
1071 priv
= kzalloc(sizeof(*priv
), GFP_KERNEL
);
1073 mutex_unlock(&xc2028_list_mutex
);
1077 priv
->i2c_props
.addr
= cfg
->i2c_addr
;
1078 priv
->i2c_props
.adap
= cfg
->i2c_adap
;
1079 priv
->video_dev
= video_dev
;
1080 priv
->tuner_callback
= cfg
->callback
;
1081 priv
->ctrl
.max_len
= 13;
1083 mutex_init(&priv
->lock
);
1085 list_add_tail(&priv
->xc2028_list
, &xc2028_list
);
1088 fe
->tuner_priv
= priv
;
1091 memcpy(&fe
->ops
.tuner_ops
, &xc2028_dvb_tuner_ops
,
1092 sizeof(xc2028_dvb_tuner_ops
));
1094 tuner_info("type set to %s\n", "XCeive xc2028/xc3028 tuner");
1096 mutex_unlock(&xc2028_list_mutex
);
1101 EXPORT_SYMBOL(xc2028_attach
);
1103 MODULE_DESCRIPTION("Xceive xc2028/xc3028 tuner driver");
1104 MODULE_AUTHOR("Michel Ludwig <michel.ludwig@gmail.com>");
1105 MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@infradead.org>");
1106 MODULE_LICENSE("GPL");