New patch. 1) Define a generic DVB_ATTACH() macro usable for any DVB sub module. 2) Call symbol_put() on release so we release module usage counters properly.
diff -r 2b05b5271ae1 linux/drivers/media/dvb/dvb-core/dvbdev.h --- a/linux/drivers/media/dvb/dvb-core/dvbdev.h Thu Apr 13 12:29:04 2006 -0400 +++ b/linux/drivers/media/dvb/dvb-core/dvbdev.h Tue Apr 18 01:13:27 2006 +0100 @@ -104,4 +104,13 @@ extern int dvb_usercopy(struct inode *in int (*func)(struct inode *inode, struct file *file, unsigned int cmd, void *arg)); +#define DVB_ATTACH(RESULT, MODULE, FUNCTION,ARGS...) \ +do { \ + typeof(&FUNCTION) __a; \ + request_module(MODULE); \ + __a = symbol_get(FUNCTION); \ + if (__a) RESULT = __a(ARGS); \ + else RESULT = NULL; \ +} while(0); + #endif /* #ifndef _DVBDEV_H_ */ diff -r 2b05b5271ae1 linux/drivers/media/dvb/frontends/stv0297.c --- a/linux/drivers/media/dvb/frontends/stv0297.c Thu Apr 13 12:29:04 2006 -0400 +++ b/linux/drivers/media/dvb/frontends/stv0297.c Tue Apr 18 01:13:27 2006 +0100 @@ -616,6 +616,7 @@ static void stv0297_release(struct dvb_f static void stv0297_release(struct dvb_frontend *fe) { struct stv0297_state *state = fe->demodulator_priv; + symbol_put(stv2097_attach); kfree(state); } diff -r 2b05b5271ae1 linux/drivers/media/dvb/frontends/stv0299.c --- a/linux/drivers/media/dvb/frontends/stv0299.c Thu Apr 13 12:29:04 2006 -0400 +++ b/linux/drivers/media/dvb/frontends/stv0299.c Tue Apr 18 01:13:27 2006 +0100 @@ -629,6 +629,7 @@ static void stv0299_release(struct dvb_f static void stv0299_release(struct dvb_frontend* fe) { struct stv0299_state* state = fe->demodulator_priv; + symbol_put(stv0299_attach); kfree(state); } diff -r 2b05b5271ae1 linux/drivers/media/dvb/frontends/tda1004x.c --- a/linux/drivers/media/dvb/frontends/tda1004x.c Thu Apr 13 12:29:04 2006 -0400 +++ b/linux/drivers/media/dvb/frontends/tda1004x.c Tue Apr 18 01:13:27 2006 +0100 @@ -1211,9 +1211,17 @@ static int tda1004x_get_tune_settings(st return 0; } -static void tda1004x_release(struct dvb_frontend* fe) +static void tda10045_release(struct dvb_frontend* fe) { struct tda1004x_state *state = fe->demodulator_priv; + symbol_put(tda10045_attach); + kfree(state); +} + +static void tda10046_release(struct dvb_frontend* fe) +{ + struct tda1004x_state *state = fe->demodulator_priv; + symbol_put(tda10046_attach); kfree(state); } @@ -1231,7 +1239,7 @@ static struct dvb_frontend_ops tda10045_ FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO }, - .release = tda1004x_release, + .release = tda10045_release, .init = tda10045_init, .sleep = tda1004x_sleep, @@ -1289,7 +1297,7 @@ static struct dvb_frontend_ops tda10046_ FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO }, - .release = tda1004x_release, + .release = tda10046_release, .init = tda10046_init, .sleep = tda1004x_sleep, diff -r 2b05b5271ae1 linux/drivers/media/dvb/ttpci/budget-ci.c --- a/linux/drivers/media/dvb/ttpci/budget-ci.c Thu Apr 13 12:29:04 2006 -0400 +++ b/linux/drivers/media/dvb/ttpci/budget-ci.c Tue Apr 18 01:13:27 2006 +0100 @@ -590,6 +590,7 @@ static u8 philips_su1278_tt_inittab[] = static int philips_su1278_tt_set_symbol_rate(struct dvb_frontend *fe, u32 srate, u32 ratio) { +/* stv0299_writereg(fe, 0x0e, 0x44); if (srate >= 10000000) { stv0299_writereg(fe, 0x13, 0x97); @@ -616,6 +617,7 @@ static int philips_su1278_tt_set_symbol_ stv0299_writereg(fe, 0x1f, (ratio >> 16) & 0xff); stv0299_writereg(fe, 0x20, (ratio >> 8) & 0xff); stv0299_writereg(fe, 0x21, (ratio) & 0xf0); +*/ return 0; } @@ -742,17 +744,17 @@ static int philips_tdm1316l_pll_set(stru // setup PLL filter and TDA9889 switch (params->u.ofdm.bandwidth) { case BANDWIDTH_6_MHZ: - tda1004x_write_byte(fe, 0x0C, 0x14); +// tda1004x_write_byte(fe, 0x0C, 0x14); filter = 0; break; case BANDWIDTH_7_MHZ: - tda1004x_write_byte(fe, 0x0C, 0x80); +// tda1004x_write_byte(fe, 0x0C, 0x80); filter = 0; break; case BANDWIDTH_8_MHZ: - tda1004x_write_byte(fe, 0x0C, 0x14); +// tda1004x_write_byte(fe, 0x0C, 0x14); filter = 1; break; @@ -857,13 +859,13 @@ static int dvbc_philips_tdm1316l_pll_set tuner_buf[3] = (cp << 5) | (filter << 3) | band; tuner_buf[4] = 0x80; - stv0297_enable_plli2c(fe); +// stv0297_enable_plli2c(fe); if (i2c_transfer(&budget_ci->budget.i2c_adap, &tuner_msg, 1) != 1) return -EIO; msleep(50); - stv0297_enable_plli2c(fe); +// stv0297_enable_plli2c(fe); if (i2c_transfer(&budget_ci->budget.i2c_adap, &tuner_msg, 1) != 1) return -EIO; @@ -972,23 +974,18 @@ static struct stv0297_config dvbc_philip .pll_set = dvbc_philips_tdm1316l_pll_set, }; - - - static void frontend_init(struct budget_ci *budget_ci) { switch (budget_ci->budget.dev->pci->subsystem_device) { case 0x100c: // Hauppauge/TT Nova-CI budget (stv0299/ALPS BSRU6(tsa5059)) - budget_ci->budget.dvb_frontend = - stv0299_attach(&alps_bsru6_config, &budget_ci->budget.i2c_adap); + DVB_ATTACH(budget_ci->budget.dvb_frontend, "stv0299", stv0299_attach, &alps_bsru6_config, &budget_ci->budget.i2c_adap); if (budget_ci->budget.dvb_frontend) { break; } break; case 0x100f: // Hauppauge/TT Nova-CI budget (stv0299b/Philips su1278(tsa5059)) - budget_ci->budget.dvb_frontend = - stv0299_attach(&philips_su1278_tt_config, &budget_ci->budget.i2c_adap); + DVB_ATTACH(budget_ci->budget.dvb_frontend, "stv2099", stv0299_attach, &philips_su1278_tt_config, &budget_ci->budget.i2c_adap); if (budget_ci->budget.dvb_frontend) { break; } @@ -996,8 +993,7 @@ static void frontend_init(struct budget_ case 0x1010: // TT DVB-C CI budget (stv0297/Philips tdm1316l(tda6651tt)) budget_ci->tuner_pll_address = 0x61; - budget_ci->budget.dvb_frontend = - stv0297_attach(&dvbc_philips_tdm1316l_config, &budget_ci->budget.i2c_adap); + DVB_ATTACH(budget_ci->budget.dvb_frontend, "stv0297", stv0297_attach, &dvbc_philips_tdm1316l_config, &budget_ci->budget.i2c_adap); if (budget_ci->budget.dvb_frontend) { break; } @@ -1005,8 +1001,7 @@ static void frontend_init(struct budget_ case 0x1011: // Hauppauge/TT Nova-T budget (tda10045/Philips tdm1316l(tda6651tt) + TDA9889) budget_ci->tuner_pll_address = 0x63; - budget_ci->budget.dvb_frontend = - tda10045_attach(&philips_tdm1316l_config, &budget_ci->budget.i2c_adap); + DVB_ATTACH(budget_ci->budget.dvb_frontend, "tda1004x", tda10045_attach, &philips_tdm1316l_config, &budget_ci->budget.i2c_adap); if (budget_ci->budget.dvb_frontend) { break; } @@ -1014,15 +1009,14 @@ static void frontend_init(struct budget_ case 0x1012: // TT DVB-T CI budget (tda10046/Philips tdm1316l(tda6651tt)) budget_ci->tuner_pll_address = 0x60; - budget_ci->budget.dvb_frontend = - tda10046_attach(&philips_tdm1316l_config, &budget_ci->budget.i2c_adap); + DVB_ATTACH(budget_ci->budget.dvb_frontend, "tda1004x", tda10046_attach, &philips_tdm1316l_config, &budget_ci->budget.i2c_adap); if (budget_ci->budget.dvb_frontend) { break; } break; case 0x1017: // TT S-1500 PCI - budget_ci->budget.dvb_frontend = stv0299_attach(&alps_bsbe1_config, &budget_ci->budget.i2c_adap); + DVB_ATTACH(budget_ci->budget.dvb_frontend, "stv0299", stv0299_attach, &alps_bsbe1_config, &budget_ci->budget.i2c_adap); if (budget_ci->budget.dvb_frontend) { budget_ci->budget.dvb_frontend->ops->dishnetwork_send_legacy_command = NULL; if (lnbp21_init(budget_ci->budget.dvb_frontend, &budget_ci->budget.i2c_adap, LNBP21_LLC, 0)) {
_______________________________________________ linux-dvb@xxxxxxxxxxx http://www.linuxtv.org/cgi-bin/mailman/listinfo/linux-dvb