aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/dvb
diff options
context:
space:
mode:
authorDevin Heitmueller <dheitmueller@linuxtv.org>2009-03-11 02:00:36 -0400
committerMauro Carvalho Chehab <mchehab@redhat.com>2009-03-30 11:43:24 -0400
commit209fdf66b8699a6b2998b58e572d67230dae507f (patch)
treea2b287bf353d610d50b1d041d15e3f8a927fe70c /drivers/media/dvb
parent7bf63eda681e095ca3c39d075354053107febf80 (diff)
V4L/DVB (11064): au8522: make use of hybrid framework so analog/digital demod can share state
Make use of the hybrid tuner framework so the analog and digital parts of the au8522 demodulator can make use of the same shared state. Thanks to Michael Krufky <mkrufky@linuxtv.org> and Steven Toth <stoth@linuxtv.org> for providing sample hardware, engineering level support, and testing. Signed-off-by: Devin Heitmueller <dheitmueller@linuxtv.org> Signed-off-by: Michael Krufky <mkrufky@linuxtv.org> Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
Diffstat (limited to 'drivers/media/dvb')
-rw-r--r--drivers/media/dvb/frontends/au8522_dig.c45
-rw-r--r--drivers/media/dvb/frontends/au8522_priv.h8
2 files changed, 46 insertions, 7 deletions
diff --git a/drivers/media/dvb/frontends/au8522_dig.c b/drivers/media/dvb/frontends/au8522_dig.c
index fa3ecbed1e58..b04346687c68 100644
--- a/drivers/media/dvb/frontends/au8522_dig.c
+++ b/drivers/media/dvb/frontends/au8522_dig.c
@@ -31,6 +31,10 @@
31 31
32static int debug; 32static int debug;
33 33
34/* Despite the name "hybrid_tuner", the framework works just as well for
35 hybrid demodulators as well... */
36static LIST_HEAD(hybrid_tuner_instance_list);
37
34#define dprintk(arg...) do { \ 38#define dprintk(arg...) do { \
35 if (debug) \ 39 if (debug) \
36 printk(arg); \ 40 printk(arg); \
@@ -786,23 +790,50 @@ static int au8522_get_tune_settings(struct dvb_frontend *fe,
786 return 0; 790 return 0;
787} 791}
788 792
793static struct dvb_frontend_ops au8522_ops;
794
795int au8522_get_state(struct au8522_state **state, struct i2c_adapter *i2c,
796 u8 client_address)
797{
798 return hybrid_tuner_request_state(struct au8522_state, (*state),
799 hybrid_tuner_instance_list,
800 i2c, client_address, "au8522");
801}
802
803void au8522_release_state(struct au8522_state *state)
804{
805 if (state != NULL)
806 hybrid_tuner_release_state(state);
807}
808
809
789static void au8522_release(struct dvb_frontend *fe) 810static void au8522_release(struct dvb_frontend *fe)
790{ 811{
791 struct au8522_state *state = fe->demodulator_priv; 812 struct au8522_state *state = fe->demodulator_priv;
792 kfree(state); 813 au8522_release_state(state);
793} 814}
794 815
795static struct dvb_frontend_ops au8522_ops;
796
797struct dvb_frontend *au8522_attach(const struct au8522_config *config, 816struct dvb_frontend *au8522_attach(const struct au8522_config *config,
798 struct i2c_adapter *i2c) 817 struct i2c_adapter *i2c)
799{ 818{
800 struct au8522_state *state = NULL; 819 struct au8522_state *state = NULL;
820 int instance;
801 821
802 /* allocate memory for the internal state */ 822 /* allocate memory for the internal state */
803 state = kmalloc(sizeof(struct au8522_state), GFP_KERNEL); 823 instance = au8522_get_state(&state, i2c, config->demod_address);
804 if (state == NULL) 824 switch (instance) {
805 goto error; 825 case 0:
826 dprintk("%s state allocation failed\n", __func__);
827 break;
828 case 1:
829 /* new demod instance */
830 dprintk("%s using new instance\n", __func__);
831 break;
832 default:
833 /* existing demod instance */
834 dprintk("%s using existing instance\n", __func__);
835 break;
836 }
806 837
807 /* setup the state */ 838 /* setup the state */
808 state->config = config; 839 state->config = config;
@@ -824,7 +855,7 @@ struct dvb_frontend *au8522_attach(const struct au8522_config *config,
824 return &state->frontend; 855 return &state->frontend;
825 856
826error: 857error:
827 kfree(state); 858 au8522_release_state(state);
828 return NULL; 859 return NULL;
829} 860}
830EXPORT_SYMBOL(au8522_attach); 861EXPORT_SYMBOL(au8522_attach);
diff --git a/drivers/media/dvb/frontends/au8522_priv.h b/drivers/media/dvb/frontends/au8522_priv.h
index 569675d295d5..98b09caa2123 100644
--- a/drivers/media/dvb/frontends/au8522_priv.h
+++ b/drivers/media/dvb/frontends/au8522_priv.h
@@ -37,6 +37,10 @@
37struct au8522_state { 37struct au8522_state {
38 struct i2c_adapter *i2c; 38 struct i2c_adapter *i2c;
39 39
40 /* Used for sharing of the state between analog and digital mode */
41 struct tuner_i2c_props i2c_props;
42 struct list_head hybrid_tuner_instance_list;
43
40 /* configuration settings */ 44 /* configuration settings */
41 const struct au8522_config *config; 45 const struct au8522_config *config;
42 46
@@ -55,3 +59,7 @@ int au8522_writereg(struct au8522_state *state, u16 reg, u8 data);
55u8 au8522_readreg(struct au8522_state *state, u16 reg); 59u8 au8522_readreg(struct au8522_state *state, u16 reg);
56int au8522_init(struct dvb_frontend *fe); 60int au8522_init(struct dvb_frontend *fe);
57int au8522_sleep(struct dvb_frontend *fe); 61int au8522_sleep(struct dvb_frontend *fe);
62
63int au8522_get_state(struct au8522_state **state, struct i2c_adapter *i2c,
64 u8 client_address);
65void au8522_release_state(struct au8522_state *state);