^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-or-later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) DVB device driver for cx231xx
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) Copyright (C) 2008 <srinivasa.deevi at conexant dot com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) Based on em28xx driver
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include "cx231xx.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <media/dvbdev.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <media/dmxdev.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <media/dvb_demux.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <media/dvb_net.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include <media/dvb_frontend.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include <media/v4l2-common.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #include <media/tuner.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #include "xc5000.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) #include "s5h1432.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #include "tda18271.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #include "s5h1411.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #include "lgdt3305.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) #include "si2165.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) #include "si2168.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #include "mb86a20s.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #include "si2157.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) #include "lgdt3306a.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) #include "r820t.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) #include "mn88473.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) MODULE_DESCRIPTION("driver for cx231xx based DVB cards");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) MODULE_AUTHOR("Srinivasa Deevi <srinivasa.deevi@conexant.com>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) static unsigned int debug;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) module_param(debug, int, 0644);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) MODULE_PARM_DESC(debug, "enable debug messages [dvb]");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) DVB_DEFINE_MOD_OPT_ADAPTER_NR(adapter_nr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) #define CX231XX_DVB_NUM_BUFS 5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) #define CX231XX_DVB_MAX_PACKETSIZE 564
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) #define CX231XX_DVB_MAX_PACKETS 64
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) #define CX231XX_DVB_MAX_FRONTENDS 2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) struct cx231xx_dvb {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) struct dvb_frontend *frontend[CX231XX_DVB_MAX_FRONTENDS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) /* feed count management */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) struct mutex lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) int nfeeds;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) /* general boilerplate stuff */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) struct dvb_adapter adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) struct dvb_demux demux;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) struct dmxdev dmxdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) struct dmx_frontend fe_hw;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) struct dmx_frontend fe_mem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) struct dvb_net net;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) struct i2c_client *i2c_client_demod[2];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) struct i2c_client *i2c_client_tuner;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) static struct s5h1432_config dvico_s5h1432_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) .output_mode = S5H1432_SERIAL_OUTPUT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) .gpio = S5H1432_GPIO_ON,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) .qam_if = S5H1432_IF_4000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) .vsb_if = S5H1432_IF_4000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) .inversion = S5H1432_INVERSION_OFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) .status_mode = S5H1432_DEMODLOCKING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) .mpeg_timing = S5H1432_MPEGTIMING_CONTINUOUS_NONINVERTING_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) static struct tda18271_std_map cnxt_rde253s_tda18271_std_map = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) .dvbt_6 = { .if_freq = 4000, .agc_mode = 3, .std = 4,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) .if_lvl = 1, .rfagc_top = 0x37, },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) .dvbt_7 = { .if_freq = 4000, .agc_mode = 3, .std = 5,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) .if_lvl = 1, .rfagc_top = 0x37, },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) .dvbt_8 = { .if_freq = 4000, .agc_mode = 3, .std = 6,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) .if_lvl = 1, .rfagc_top = 0x37, },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) static struct tda18271_std_map mb86a20s_tda18271_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) .dvbt_6 = { .if_freq = 4000, .agc_mode = 3, .std = 4,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) .if_lvl = 0, .rfagc_top = 0x37, },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) static struct tda18271_config cnxt_rde253s_tunerconfig = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) .std_map = &cnxt_rde253s_tda18271_std_map,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) .gate = TDA18271_GATE_ANALOG,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) static struct s5h1411_config tda18271_s5h1411_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) .output_mode = S5H1411_SERIAL_OUTPUT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) .gpio = S5H1411_GPIO_OFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) .vsb_if = S5H1411_IF_3250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) .qam_if = S5H1411_IF_4000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) .inversion = S5H1411_INVERSION_ON,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) .status_mode = S5H1411_DEMODLOCKING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) .mpeg_timing = S5H1411_MPEGTIMING_CONTINUOUS_NONINVERTING_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) static struct s5h1411_config xc5000_s5h1411_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) .output_mode = S5H1411_SERIAL_OUTPUT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) .gpio = S5H1411_GPIO_OFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) .vsb_if = S5H1411_IF_3250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) .qam_if = S5H1411_IF_3250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) .inversion = S5H1411_INVERSION_OFF,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) .status_mode = S5H1411_DEMODLOCKING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) .mpeg_timing = S5H1411_MPEGTIMING_CONTINUOUS_NONINVERTING_CLOCK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) static struct lgdt3305_config hcw_lgdt3305_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) .i2c_addr = 0x0e,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) .mpeg_mode = LGDT3305_MPEG_SERIAL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) .tpclk_edge = LGDT3305_TPCLK_FALLING_EDGE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) .tpvalid_polarity = LGDT3305_TP_VALID_HIGH,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) .deny_i2c_rptr = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) .spectral_inversion = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) .qam_if_khz = 4000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) .vsb_if_khz = 3250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) static struct tda18271_std_map hauppauge_tda18271_std_map = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) .atsc_6 = { .if_freq = 3250, .agc_mode = 3, .std = 4,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) .if_lvl = 1, .rfagc_top = 0x58, },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) .qam_6 = { .if_freq = 4000, .agc_mode = 3, .std = 5,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) .if_lvl = 1, .rfagc_top = 0x58, },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) static struct tda18271_config hcw_tda18271_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) .std_map = &hauppauge_tda18271_std_map,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) .gate = TDA18271_GATE_DIGITAL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) static const struct mb86a20s_config pv_mb86a20s_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) .demod_address = 0x10,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) .is_serial = true,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) static struct tda18271_config pv_tda18271_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) .std_map = &mb86a20s_tda18271_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) .gate = TDA18271_GATE_DIGITAL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) .small_i2c = TDA18271_03_BYTE_CHUNK_INIT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) static const struct lgdt3306a_config hauppauge_955q_lgdt3306a_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) .qam_if_khz = 4000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) .vsb_if_khz = 3250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) .spectral_inversion = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) .mpeg_mode = LGDT3306A_MPEG_SERIAL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) .tpclk_edge = LGDT3306A_TPCLK_RISING_EDGE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) .tpvalid_polarity = LGDT3306A_TP_VALID_HIGH,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) .xtalMHz = 25,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) static struct r820t_config astrometa_t2hybrid_r820t_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) .i2c_addr = 0x3a, /* 0x74 >> 1 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) .xtal = 16000000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) .rafael_chip = CHIP_R828D,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) .max_i2c_msg_len = 2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) static inline void print_err_status(struct cx231xx *dev, int packet, int status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) char *errmsg = "Unknown";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) switch (status) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) case -ENOENT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) errmsg = "unlinked synchronously";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) case -ECONNRESET:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) errmsg = "unlinked asynchronously";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) case -ENOSR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) errmsg = "Buffer error (overrun)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) case -EPIPE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) errmsg = "Stalled (device not responding)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) case -EOVERFLOW:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) errmsg = "Babble (bad cable?)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) case -EPROTO:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) errmsg = "Bit-stuff error (bad cable?)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) case -EILSEQ:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) errmsg = "CRC/Timeout (could be anything)";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) case -ETIME:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) errmsg = "Device does not respond";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) if (packet < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) dev_dbg(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) "URB status %d [%s].\n", status, errmsg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) dev_dbg(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) "URB packet %d, status %d [%s].\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) packet, status, errmsg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) static inline int dvb_isoc_copy(struct cx231xx *dev, struct urb *urb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) if (!dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) if (dev->state & DEV_DISCONNECTED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) if (urb->status < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) print_err_status(dev, -1, urb->status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) if (urb->status == -ENOENT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) for (i = 0; i < urb->number_of_packets; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) int status = urb->iso_frame_desc[i].status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) if (status < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) print_err_status(dev, i, status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) if (urb->iso_frame_desc[i].status != -EPROTO)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) dvb_dmx_swfilter(&dev->dvb->demux,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) urb->transfer_buffer +
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) urb->iso_frame_desc[i].offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) urb->iso_frame_desc[i].actual_length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) static inline int dvb_bulk_copy(struct cx231xx *dev, struct urb *urb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) if (!dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) if (dev->state & DEV_DISCONNECTED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) if (urb->status < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) print_err_status(dev, -1, urb->status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) if (urb->status == -ENOENT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) /* Feed the transport payload into the kernel demux */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) dvb_dmx_swfilter(&dev->dvb->demux,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) urb->transfer_buffer, urb->actual_length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) static int start_streaming(struct cx231xx_dvb *dvb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) struct cx231xx *dev = dvb->adapter.priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) if (dev->USE_ISO) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) dev_dbg(dev->dev, "DVB transfer mode is ISO.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) cx231xx_set_alt_setting(dev, INDEX_TS1, 5);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) rc = cx231xx_set_mode(dev, CX231XX_DIGITAL_MODE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) if (rc < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) dev->mode_tv = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) return cx231xx_init_isoc(dev, CX231XX_DVB_MAX_PACKETS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) CX231XX_DVB_NUM_BUFS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) dev->ts1_mode.max_pkt_size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) dvb_isoc_copy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) dev_dbg(dev->dev, "DVB transfer mode is BULK.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) cx231xx_set_alt_setting(dev, INDEX_TS1, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) rc = cx231xx_set_mode(dev, CX231XX_DIGITAL_MODE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) if (rc < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) dev->mode_tv = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) return cx231xx_init_bulk(dev, CX231XX_DVB_MAX_PACKETS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) CX231XX_DVB_NUM_BUFS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) dev->ts1_mode.max_pkt_size,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) dvb_bulk_copy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) static int stop_streaming(struct cx231xx_dvb *dvb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) struct cx231xx *dev = dvb->adapter.priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) if (dev->USE_ISO)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) cx231xx_uninit_isoc(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) cx231xx_uninit_bulk(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) cx231xx_set_mode(dev, CX231XX_SUSPEND);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) static int start_feed(struct dvb_demux_feed *feed)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) struct dvb_demux *demux = feed->demux;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) struct cx231xx_dvb *dvb = demux->priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) int rc, ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) if (!demux->dmx.frontend)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) mutex_lock(&dvb->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) dvb->nfeeds++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) rc = dvb->nfeeds;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) if (dvb->nfeeds == 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) ret = start_streaming(dvb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) rc = ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) mutex_unlock(&dvb->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) static int stop_feed(struct dvb_demux_feed *feed)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) struct dvb_demux *demux = feed->demux;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) struct cx231xx_dvb *dvb = demux->priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) int err = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) mutex_lock(&dvb->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) dvb->nfeeds--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) if (0 == dvb->nfeeds)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) err = stop_streaming(dvb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) mutex_unlock(&dvb->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) /* ------------------------------------------------------------------ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) static int cx231xx_dvb_bus_ctrl(struct dvb_frontend *fe, int acquire)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) struct cx231xx *dev = fe->dvb->priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) if (acquire)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) return cx231xx_set_mode(dev, CX231XX_DIGITAL_MODE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) return cx231xx_set_mode(dev, CX231XX_SUSPEND);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) /* ------------------------------------------------------------------ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) static struct xc5000_config cnxt_rde250_tunerconfig = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) .i2c_address = 0x61,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) .if_khz = 4000,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) static struct xc5000_config cnxt_rdu250_tunerconfig = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) .i2c_address = 0x61,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) .if_khz = 3250,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) /* ------------------------------------------------------------------ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) #if 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) static int attach_xc5000(u8 addr, struct cx231xx *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) struct dvb_frontend *fe;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) struct xc5000_config cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) memset(&cfg, 0, sizeof(cfg));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) cfg.i2c_adap = cx231xx_get_i2c_adap(dev, dev->board.tuner_i2c_master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) cfg.i2c_addr = addr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) dev_err(dev->dev, "%s/2: dvb frontend not attached. Can't attach xc5000\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) dev->name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) fe = dvb_attach(xc5000_attach, dev->dvb->frontend[0], &cfg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) if (!fe) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) dev_err(dev->dev, "%s/2: xc5000 attach failed\n", dev->name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) dvb_frontend_detach(dev->dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) dev->dvb->frontend[0] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) dev_info(dev->dev, "%s/2: xc5000 attached\n", dev->name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) int cx231xx_set_analog_freq(struct cx231xx *dev, u32 freq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) if (dev->dvb && dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) struct dvb_tuner_ops *dops = &dev->dvb->frontend[0]->ops.tuner_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) if (dops->set_analog_params != NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) struct analog_parameters params;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) params.frequency = freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) params.std = dev->norm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) params.mode = 0; /* 0- Air; 1 - cable */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) /*params.audmode = ; */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) /* Set the analog parameters to set the frequency */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) dops->set_analog_params(dev->dvb->frontend[0], ¶ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) int cx231xx_reset_analog_tuner(struct cx231xx *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) int status = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) if (dev->dvb && dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) struct dvb_tuner_ops *dops = &dev->dvb->frontend[0]->ops.tuner_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) if (dops->init != NULL && !dev->xc_fw_load_done) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) dev_dbg(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) "Reloading firmware for XC5000\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) status = dops->init(dev->dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) if (status == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) dev->xc_fw_load_done = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) dev_dbg(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) "XC5000 firmware download completed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) dev->xc_fw_load_done = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) dev_dbg(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) "XC5000 firmware download failed !!!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) return status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) /* ------------------------------------------------------------------ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) static int register_dvb(struct cx231xx_dvb *dvb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) struct module *module,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) struct cx231xx *dev, struct device *device)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) int result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) mutex_init(&dvb->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) /* register adapter */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) result = dvb_register_adapter(&dvb->adapter, dev->name, module, device,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) adapter_nr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) "%s: dvb_register_adapter failed (errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) goto fail_adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) dvb_register_media_controller(&dvb->adapter, dev->media_dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) /* Ensure all frontends negotiate bus access */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) dvb->frontend[0]->ops.ts_bus_ctrl = cx231xx_dvb_bus_ctrl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) if (dvb->frontend[1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) dvb->frontend[1]->ops.ts_bus_ctrl = cx231xx_dvb_bus_ctrl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) dvb->adapter.priv = dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) /* register frontend */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) result = dvb_register_frontend(&dvb->adapter, dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) "%s: dvb_register_frontend failed (errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) goto fail_frontend0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) if (dvb->frontend[1]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) result = dvb_register_frontend(&dvb->adapter, dvb->frontend[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) "%s: 2nd dvb_register_frontend failed (errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) goto fail_frontend1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) /* MFE lock */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) dvb->adapter.mfe_shared = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) /* register demux stuff */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) dvb->demux.dmx.capabilities =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) DMX_TS_FILTERING | DMX_SECTION_FILTERING |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) DMX_MEMORY_BASED_FILTERING;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) dvb->demux.priv = dvb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) dvb->demux.filternum = 256;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) dvb->demux.feednum = 256;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) dvb->demux.start_feed = start_feed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) dvb->demux.stop_feed = stop_feed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) result = dvb_dmx_init(&dvb->demux);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) "%s: dvb_dmx_init failed (errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) goto fail_dmx;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) dvb->dmxdev.filternum = 256;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) dvb->dmxdev.demux = &dvb->demux.dmx;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) dvb->dmxdev.capabilities = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) result = dvb_dmxdev_init(&dvb->dmxdev, &dvb->adapter);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) "%s: dvb_dmxdev_init failed (errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) goto fail_dmxdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) dvb->fe_hw.source = DMX_FRONTEND_0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) result = dvb->demux.dmx.add_frontend(&dvb->demux.dmx, &dvb->fe_hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) "%s: add_frontend failed (DMX_FRONTEND_0, errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) goto fail_fe_hw;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) dvb->fe_mem.source = DMX_MEMORY_FE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) result = dvb->demux.dmx.add_frontend(&dvb->demux.dmx, &dvb->fe_mem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) "%s: add_frontend failed (DMX_MEMORY_FE, errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) goto fail_fe_mem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) result = dvb->demux.dmx.connect_frontend(&dvb->demux.dmx, &dvb->fe_hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) if (result < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) dev_warn(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) "%s: connect_frontend failed (errno = %d)\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) dev->name, result);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) goto fail_fe_conn;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) /* register network adapter */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) dvb_net_init(&dvb->adapter, &dvb->net, &dvb->demux.dmx);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) result = dvb_create_media_graph(&dvb->adapter,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) dev->tuner_type == TUNER_ABSENT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) if (result < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) goto fail_create_graph;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) fail_create_graph:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) dvb_net_release(&dvb->net);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) fail_fe_conn:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_mem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) fail_fe_mem:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) fail_fe_hw:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) dvb_dmxdev_release(&dvb->dmxdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) fail_dmxdev:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) dvb_dmx_release(&dvb->demux);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) fail_dmx:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) if (dvb->frontend[1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) dvb_unregister_frontend(dvb->frontend[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) dvb_unregister_frontend(dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) fail_frontend1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) if (dvb->frontend[1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) dvb_frontend_detach(dvb->frontend[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) fail_frontend0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) dvb_frontend_detach(dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) dvb_unregister_adapter(&dvb->adapter);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) fail_adapter:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) return result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) static void unregister_dvb(struct cx231xx_dvb *dvb)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) dvb_net_release(&dvb->net);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_mem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) dvb_dmxdev_release(&dvb->dmxdev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) dvb_dmx_release(&dvb->demux);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) if (dvb->frontend[1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) dvb_unregister_frontend(dvb->frontend[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) dvb_unregister_frontend(dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) if (dvb->frontend[1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) dvb_frontend_detach(dvb->frontend[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) dvb_frontend_detach(dvb->frontend[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) dvb_unregister_adapter(&dvb->adapter);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) /* remove I2C tuner */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) dvb_module_release(dvb->i2c_client_tuner);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) dvb->i2c_client_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) /* remove I2C demod(s) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) dvb_module_release(dvb->i2c_client_demod[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) dvb->i2c_client_demod[1] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) dvb_module_release(dvb->i2c_client_demod[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) dvb->i2c_client_demod[0] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) static int dvb_init(struct cx231xx *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) int result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) struct cx231xx_dvb *dvb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) struct i2c_adapter *tuner_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) struct i2c_adapter *demod_i2c;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) struct i2c_client *client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) struct i2c_adapter *adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) if (!dev->board.has_dvb) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) /* This device does not support the extension */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) dvb = kzalloc(sizeof(struct cx231xx_dvb), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) if (dvb == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) dev_info(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) "cx231xx_dvb: memory allocation failed\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) dev->dvb = dvb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) dev->cx231xx_set_analog_freq = cx231xx_set_analog_freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) dev->cx231xx_reset_analog_tuner = cx231xx_reset_analog_tuner;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) tuner_i2c = cx231xx_get_i2c_adap(dev, dev->board.tuner_i2c_master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) demod_i2c = cx231xx_get_i2c_adap(dev, dev->board.demod_i2c_master);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) mutex_lock(&dev->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) cx231xx_set_mode(dev, CX231XX_DIGITAL_MODE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) cx231xx_demod_reset(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) /* init frontend */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) switch (dev->model) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) case CX231XX_BOARD_CNXT_CARRAERA:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) case CX231XX_BOARD_CNXT_RDE_250:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) dev->dvb->frontend[0] = dvb_attach(s5h1432_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) &dvico_s5h1432_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) demod_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) "Failed to attach s5h1432 front end\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) if (!dvb_attach(xc5000_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) &cnxt_rde250_tunerconfig)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) case CX231XX_BOARD_CNXT_SHELBY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) case CX231XX_BOARD_CNXT_RDU_250:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) dev->dvb->frontend[0] = dvb_attach(s5h1411_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) &xc5000_s5h1411_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) demod_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) "Failed to attach s5h1411 front end\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) if (!dvb_attach(xc5000_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) &cnxt_rdu250_tunerconfig)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) case CX231XX_BOARD_CNXT_RDE_253S:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) dev->dvb->frontend[0] = dvb_attach(s5h1432_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) &dvico_s5h1432_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) demod_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) "Failed to attach s5h1432 front end\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) if (!dvb_attach(tda18271_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) dev->board.tuner_addr, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) &cnxt_rde253s_tunerconfig)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) case CX231XX_BOARD_CNXT_RDU_253S:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) case CX231XX_BOARD_KWORLD_UB445_USB_HYBRID:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) dev->dvb->frontend[0] = dvb_attach(s5h1411_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) &tda18271_s5h1411_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) demod_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) "Failed to attach s5h1411 front end\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) if (!dvb_attach(tda18271_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) dev->board.tuner_addr, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) &cnxt_rde253s_tunerconfig)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) case CX231XX_BOARD_HAUPPAUGE_EXETER:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) dev_info(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) "%s: looking for tuner / demod on i2c bus: %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) __func__, i2c_adapter_id(tuner_i2c));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) dev->dvb->frontend[0] = dvb_attach(lgdt3305_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) &hcw_lgdt3305_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) demod_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) "Failed to attach LG3305 front end\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) dvb_attach(tda18271_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) dev->board.tuner_addr, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) &hcw_tda18271_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) case CX231XX_BOARD_HAUPPAUGE_930C_HD_1113xx:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) struct si2165_platform_data si2165_pdata = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) /* attach demod */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) si2165_pdata.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) si2165_pdata.chip_mode = SI2165_MODE_PLL_XTAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) si2165_pdata.ref_freq_hz = 16000000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) client = dvb_module_probe("si2165", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) &si2165_pdata);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) dev->dvb->frontend[0]->ops.i2c_gate_ctrl = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) dvb_attach(tda18271_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) dev->board.tuner_addr, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) &hcw_tda18271_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) dev->cx231xx_reset_analog_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) case CX231XX_BOARD_HAUPPAUGE_930C_HD_1114xx:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) struct si2165_platform_data si2165_pdata = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) struct si2157_config si2157_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) /* attach demod */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) si2165_pdata.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) si2165_pdata.chip_mode = SI2165_MODE_PLL_EXT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) si2165_pdata.ref_freq_hz = 24000000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) client = dvb_module_probe("si2165", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) &si2165_pdata);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) dev->dvb->frontend[0]->ops.i2c_gate_ctrl = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) /* attach tuner */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) si2157_config.fe = dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) #ifdef CONFIG_MEDIA_CONTROLLER_DVB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) si2157_config.mdev = dev->media_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) si2157_config.if_port = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) si2157_config.inversion = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) client = dvb_module_probe("si2157", NULL, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) dev->board.tuner_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) &si2157_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) dev->cx231xx_reset_analog_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) dev->dvb->i2c_client_tuner = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) case CX231XX_BOARD_HAUPPAUGE_955Q:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) struct si2157_config si2157_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) struct lgdt3306a_config lgdt3306a_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) lgdt3306a_config = hauppauge_955q_lgdt3306a_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) lgdt3306a_config.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) lgdt3306a_config.i2c_adapter = &adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) client = dvb_module_probe("lgdt3306a", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) &lgdt3306a_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) dev->dvb->frontend[0]->ops.i2c_gate_ctrl = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) /* attach tuner */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) si2157_config.fe = dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) #ifdef CONFIG_MEDIA_CONTROLLER_DVB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) si2157_config.mdev = dev->media_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) si2157_config.if_port = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) si2157_config.inversion = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) client = dvb_module_probe("si2157", NULL, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) dev->board.tuner_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) &si2157_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) dev->cx231xx_reset_analog_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) dev->dvb->i2c_client_tuner = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891) case CX231XX_BOARD_PV_PLAYTV_USB_HYBRID:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) case CX231XX_BOARD_KWORLD_UB430_USB_HYBRID:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) dev_info(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) "%s: looking for demod on i2c bus: %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) __func__, i2c_adapter_id(tuner_i2c));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) dev->dvb->frontend[0] = dvb_attach(mb86a20s_attach,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) &pv_mb86a20s_config,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) demod_i2c);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) if (!dev->dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) "Failed to attach mb86a20s demod\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) dvb_attach(tda18271_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) dev->board.tuner_addr, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) &pv_tda18271_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) case CX231XX_BOARD_EVROMEDIA_FULL_HYBRID_FULLHD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) struct si2157_config si2157_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) struct si2168_config si2168_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 922) /* attach demodulator chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 923) si2168_config.ts_mode = SI2168_TS_SERIAL; /* from *.inf file */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 924) si2168_config.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 925) si2168_config.i2c_adapter = &adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 926) si2168_config.ts_clock_inv = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 927)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 928) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 929) client = dvb_module_probe("si2168", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 930) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 931) &si2168_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 932) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 933) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 934) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 935) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 936) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 937)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 938) /* attach tuner chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 939) si2157_config.fe = dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 940) #ifdef CONFIG_MEDIA_CONTROLLER_DVB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 941) si2157_config.mdev = dev->media_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 942) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 943) si2157_config.if_port = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 944) si2157_config.inversion = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 945)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 946) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 947) client = dvb_module_probe("si2157", NULL, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 948) dev->board.tuner_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 949) &si2157_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 950) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 951) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 952) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 953) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 954) dev->cx231xx_reset_analog_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 955) dev->dvb->i2c_client_tuner = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 956) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 957) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 958) case CX231XX_BOARD_ASTROMETA_T2HYBRID:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 959) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 960) struct mn88473_config mn88473_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 961)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 962) /* attach demodulator chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 963) mn88473_config.i2c_wr_max = 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 964) mn88473_config.xtal = 25000000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 965) mn88473_config.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 966)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 967) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 968) client = dvb_module_probe("mn88473", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 969) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 970) &mn88473_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 971) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 972) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 973) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 974) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 975) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 976)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 977) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 978) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 979)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 980) /* attach tuner chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 981) dvb_attach(r820t_attach, dev->dvb->frontend[0],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 982) tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 983) &astrometa_t2hybrid_r820t_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 984) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 985) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 986) case CX231XX_BOARD_HAUPPAUGE_935C:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 987) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 988) struct si2157_config si2157_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 989) struct si2168_config si2168_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 990)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 991) /* attach demodulator chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 992) si2168_config.ts_mode = SI2168_TS_SERIAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 993) si2168_config.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 994) si2168_config.i2c_adapter = &adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 995) si2168_config.ts_clock_inv = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 996)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 997) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 998) client = dvb_module_probe("si2168", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 999) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1000) &si2168_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1001) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1002) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1003) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1004) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1005) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1006) dev->dvb->frontend[0]->ops.i2c_gate_ctrl = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1007)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1008) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1009) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1010)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1011) /* attach tuner */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1012) si2157_config.fe = dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1013) #ifdef CONFIG_MEDIA_CONTROLLER_DVB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1014) si2157_config.mdev = dev->media_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1015) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1016) si2157_config.if_port = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1017) si2157_config.inversion = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1018)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1019) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1020) client = dvb_module_probe("si2157", NULL, tuner_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1021) dev->board.tuner_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1022) &si2157_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1023) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1024) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1025) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1026) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1027) dev->cx231xx_reset_analog_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1028) dev->dvb->i2c_client_tuner = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1029) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1030) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1031) case CX231XX_BOARD_HAUPPAUGE_975:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1032) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1033) struct i2c_adapter *adapter2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1034) struct si2157_config si2157_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1035) struct lgdt3306a_config lgdt3306a_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1036) struct si2168_config si2168_config = {};
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1037)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1038) /* attach first demodulator chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1039) lgdt3306a_config = hauppauge_955q_lgdt3306a_config;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1040) lgdt3306a_config.fe = &dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1041) lgdt3306a_config.i2c_adapter = &adapter;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1042)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1043) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1044) client = dvb_module_probe("lgdt3306a", NULL, demod_i2c,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1045) dev->board.demod_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1046) &lgdt3306a_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1047) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1048) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1049) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1050) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1051) dvb->i2c_client_demod[0] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1052)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1053) /* attach second demodulator chip */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1054) si2168_config.ts_mode = SI2168_TS_SERIAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1055) si2168_config.fe = &dev->dvb->frontend[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1056) si2168_config.i2c_adapter = &adapter2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1057) si2168_config.ts_clock_inv = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1058)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1059) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1060) client = dvb_module_probe("si2168", NULL, adapter,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1061) dev->board.demod_addr2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1062) &si2168_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1063) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1064) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1065) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1066) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1067) dvb->i2c_client_demod[1] = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1068) dvb->frontend[1]->id = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1069)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1070) /* define general-purpose callback pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1071) dvb->frontend[0]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1072) dvb->frontend[1]->callback = cx231xx_tuner_callback;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1073)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1074) /* attach tuner */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1075) si2157_config.fe = dev->dvb->frontend[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1076) #ifdef CONFIG_MEDIA_CONTROLLER_DVB
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1077) si2157_config.mdev = dev->media_dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1078) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1079) si2157_config.if_port = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1080) si2157_config.inversion = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1081)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1082) /* perform probe/init/attach */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1083) client = dvb_module_probe("si2157", NULL, adapter,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1084) dev->board.tuner_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1085) &si2157_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1086) if (!client) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1087) result = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1088) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1089) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1090) dev->cx231xx_reset_analog_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1091) dvb->i2c_client_tuner = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1092)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1093) dvb->frontend[1]->tuner_priv = dvb->frontend[0]->tuner_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1094)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1095) memcpy(&dvb->frontend[1]->ops.tuner_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1096) &dvb->frontend[0]->ops.tuner_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1097) sizeof(struct dvb_tuner_ops));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1098) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1099) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1100) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1101) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1102) "%s/2: The frontend of your DVB/ATSC card isn't supported yet\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1103) dev->name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1104) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1105) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1106) if (!dvb->frontend[0]) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1107) dev_err(dev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1108) "%s/2: frontend initialization failed\n", dev->name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1109) result = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1110) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1111) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1112)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1113) /* register everything */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1114) result = register_dvb(dvb, THIS_MODULE, dev, dev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1115)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1116) if (result < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1117) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1118)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1120) dev_info(dev->dev, "Successfully loaded cx231xx-dvb\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1122) ret:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1123) cx231xx_set_mode(dev, CX231XX_SUSPEND);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1124) mutex_unlock(&dev->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1125) return result;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1126)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1127) out_free:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1128) /* remove I2C tuner */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1129) dvb_module_release(dvb->i2c_client_tuner);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1130) dvb->i2c_client_tuner = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1131) /* remove I2C demod(s) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1132) dvb_module_release(dvb->i2c_client_demod[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1133) dvb->i2c_client_demod[1] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1134) dvb_module_release(dvb->i2c_client_demod[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1135) dvb->i2c_client_demod[0] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1136) kfree(dvb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1137) dev->dvb = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1138) goto ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1139) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1140)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1141) static int dvb_fini(struct cx231xx *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1142) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1143) if (!dev->board.has_dvb) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1144) /* This device does not support the extension */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1145) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1146) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1148) if (dev->dvb) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1149) unregister_dvb(dev->dvb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1150) kfree(dev->dvb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1151) dev->dvb = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1152) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1153)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1154) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1155) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1157) static struct cx231xx_ops dvb_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1158) .id = CX231XX_DVB,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1159) .name = "Cx231xx dvb Extension",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1160) .init = dvb_init,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1161) .fini = dvb_fini,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1162) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1163)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1164) static int __init cx231xx_dvb_register(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1165) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1166) return cx231xx_register_extension(&dvb_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1167) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1168)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1169) static void __exit cx231xx_dvb_unregister(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1170) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1171) cx231xx_unregister_extension(&dvb_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1172) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1173)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1174) module_init(cx231xx_dvb_register);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1175) module_exit(cx231xx_dvb_unregister);