summaryrefslogtreecommitdiff
path: root/linux/drivers/media/dvb/ttusb-dec
diff options
context:
space:
mode:
authorAndrew de Quincy <devnull@localhost>2004-10-28 17:37:07 +0000
committerAndrew de Quincy <devnull@localhost>2004-10-28 17:37:07 +0000
commit25da23146538519f0f644671c49868bfb560740a (patch)
tree7987970be2d5e86492325711d234ff59319f2685 /linux/drivers/media/dvb/ttusb-dec
parentdcc0614123e60b1b01ed67850ebd22a517d8c086 (diff)
downloadmediapointer-dvb-s2-25da23146538519f0f644671c49868bfb560740a.tar.gz
mediapointer-dvb-s2-25da23146538519f0f644671c49868bfb560740a.tar.bz2
Imported FE_REFACTORING to HEAD
Diffstat (limited to 'linux/drivers/media/dvb/ttusb-dec')
-rw-r--r--linux/drivers/media/dvb/ttusb-dec/Makefile2
-rw-r--r--linux/drivers/media/dvb/ttusb-dec/ttusb_dec.c337
-rw-r--r--linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.c258
-rw-r--r--linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.h38
4 files changed, 338 insertions, 297 deletions
diff --git a/linux/drivers/media/dvb/ttusb-dec/Makefile b/linux/drivers/media/dvb/ttusb-dec/Makefile
index bf4e38740..b41bf1f06 100644
--- a/linux/drivers/media/dvb/ttusb-dec/Makefile
+++ b/linux/drivers/media/dvb/ttusb-dec/Makefile
@@ -1,3 +1,3 @@
-obj-$(CONFIG_DVB_TTUSB_DEC) += ttusb_dec.o
+obj-$(CONFIG_DVB_TTUSB_DEC) += ttusb_dec.o ttusbdecfe.o
EXTRA_CFLAGS = -Idrivers/media/dvb/dvb-core/
diff --git a/linux/drivers/media/dvb/ttusb-dec/ttusb_dec.c b/linux/drivers/media/dvb/ttusb-dec/ttusb_dec.c
index 6f1c40a7c..737ecbc16 100644
--- a/linux/drivers/media/dvb/ttusb-dec/ttusb_dec.c
+++ b/linux/drivers/media/dvb/ttusb-dec/ttusb_dec.c
@@ -42,6 +42,7 @@
#include "dvb_filter.h"
#include "dvb_frontend.h"
#include "dvb_net.h"
+#include "ttusbdecfe.h"
static int debug;
static int output_pva;
@@ -69,9 +70,6 @@ MODULE_PARM_DESC(output_pva, "Output PVA from dvr device (default:off)");
#define MAX_PVA_LENGTH 6144
-#define LOF_HI 10600000
-#define LOF_LO 9750000
-
enum ttusb_dec_model {
TTUSB_DEC2000T,
TTUSB_DEC2540T,
@@ -102,12 +100,9 @@ struct ttusb_dec {
struct dvb_demux demux;
struct dmx_frontend frontend;
struct dvb_net dvb_net;
- struct dvb_frontend_info *frontend_info;
- int (*frontend_ioctl) (struct dvb_frontend *, unsigned int, void *);
+ struct dvb_frontend* fe;
u16 pid[DMX_PES_OTHER];
- int hi_band;
- int voltage;
/* USB bits */
struct usb_device *udev;
@@ -166,32 +161,6 @@ struct filter_info {
struct list_head filter_info_list;
};
-static struct dvb_frontend_info dec2000t_frontend_info = {
- .name = "TechnoTrend/Hauppauge DEC2000-t Frontend",
- .type = FE_OFDM,
- .frequency_min = 51000000,
- .frequency_max = 858000000,
- .frequency_stepsize = 62500,
- .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
- FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
- FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
- FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO |
- FE_CAN_HIERARCHY_AUTO,
-};
-
-static struct dvb_frontend_info dec3000s_frontend_info = {
- .name = "TechnoTrend/Hauppauge DEC3000-s Frontend",
- .type = FE_QPSK,
- .frequency_min = 950000,
- .frequency_max = 2150000,
- .frequency_stepsize = 125,
- .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
- FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
- FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
- FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO |
- FE_CAN_HIERARCHY_AUTO,
-};
-
static void ttusb_dec_set_model(struct ttusb_dec *dec,
enum ttusb_dec_model model);
@@ -1404,6 +1373,7 @@ static void ttusb_dec_exit_dvb(struct ttusb_dec *dec)
dec->demux.dmx.remove_frontend(&dec->demux.dmx, &dec->frontend);
dvb_dmxdev_release(&dec->dmxdev);
dvb_dmx_release(&dec->demux);
+ if (dec->fe) dvb_unregister_frontend(dec->fe);
dvb_unregister_adapter(dec->adapter);
}
@@ -1435,261 +1405,6 @@ static void ttusb_dec_exit_tasklet(struct ttusb_dec *dec)
}
}
-static int ttusb_dec_2000t_frontend_ioctl(struct dvb_frontend *fe, unsigned int cmd,
- void *arg)
-{
- struct ttusb_dec *dec = fe->data;
-
- dprintk("%s\n", __FUNCTION__);
-
- switch (cmd) {
- case FE_GET_INFO:
- dprintk("%s: FE_GET_INFO\n", __FUNCTION__);
- memcpy(arg, dec->frontend_info,
- sizeof (struct dvb_frontend_info));
- break;
-
- case FE_READ_STATUS: {
- fe_status_t *status = (fe_status_t *)arg;
- dprintk("%s: FE_READ_STATUS\n", __FUNCTION__);
- *status = FE_HAS_SIGNAL | FE_HAS_VITERBI |
- FE_HAS_SYNC | FE_HAS_CARRIER | FE_HAS_LOCK;
- break;
- }
-
- case FE_READ_BER: {
- u32 *ber = (u32 *)arg;
- dprintk("%s: FE_READ_BER\n", __FUNCTION__);
- *ber = 0;
- return -ENOSYS;
- break;
- }
-
- case FE_READ_SIGNAL_STRENGTH: {
- dprintk("%s: FE_READ_SIGNAL_STRENGTH\n", __FUNCTION__);
- *(s32 *)arg = 0xFF;
- return -ENOSYS;
- break;
- }
-
- case FE_READ_SNR:
- dprintk("%s: FE_READ_SNR\n", __FUNCTION__);
- *(s32 *)arg = 0;
- return -ENOSYS;
- break;
-
- case FE_READ_UNCORRECTED_BLOCKS:
- dprintk("%s: FE_READ_UNCORRECTED_BLOCKS\n", __FUNCTION__);
- *(u32 *)arg = 0;
- return -ENOSYS;
- break;
-
- case FE_SET_FRONTEND: {
- struct dvb_frontend_parameters *p =
- (struct dvb_frontend_parameters *)arg;
- u8 b[] = { 0x00, 0x00, 0x00, 0x03,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x01,
- 0x00, 0x00, 0x00, 0xff,
- 0x00, 0x00, 0x00, 0xff };
- u32 freq;
-
- dprintk("%s: FE_SET_FRONTEND\n", __FUNCTION__);
-
- dprintk(" frequency->%d\n", p->frequency);
- dprintk(" symbol_rate->%d\n",
- p->u.qam.symbol_rate);
- dprintk(" inversion->%d\n", p->inversion);
-
- freq = htonl(p->frequency / 1000);
- memcpy(&b[4], &freq, sizeof (u32));
- ttusb_dec_send_command(dec, 0x71, sizeof(b), b, NULL, NULL);
-
- break;
- }
-
- case FE_GET_FRONTEND:
- dprintk("%s: FE_GET_FRONTEND\n", __FUNCTION__);
- break;
-
- case FE_SLEEP:
- dprintk("%s: FE_SLEEP\n", __FUNCTION__);
- return -ENOSYS;
- break;
-
- case FE_INIT:
- dprintk("%s: FE_INIT\n", __FUNCTION__);
- break;
-
- default:
- dprintk("%s: unknown IOCTL (0x%X)\n", __FUNCTION__, cmd);
- return -EINVAL;
- }
-
- return 0;
-}
-
-static int ttusb_dec_3000s_frontend_ioctl(struct dvb_frontend *fe,
- unsigned int cmd, void *arg)
-{
- struct ttusb_dec *dec = fe->data;
-
- dprintk("%s\n", __FUNCTION__);
-
- switch (cmd) {
-
- case FE_GET_INFO:
- dprintk("%s: FE_GET_INFO\n", __FUNCTION__);
- memcpy(arg, dec->frontend_info,
- sizeof (struct dvb_frontend_info));
- break;
-
- case FE_READ_STATUS: {
- fe_status_t *status = (fe_status_t *)arg;
- dprintk("%s: FE_READ_STATUS\n", __FUNCTION__);
- *status = FE_HAS_SIGNAL | FE_HAS_VITERBI |
- FE_HAS_SYNC | FE_HAS_CARRIER | FE_HAS_LOCK;
- break;
- }
-
- case FE_READ_BER: {
- u32 *ber = (u32 *)arg;
- dprintk("%s: FE_READ_BER\n", __FUNCTION__);
- *ber = 0;
- return -ENOSYS;
- break;
- }
-
- case FE_READ_SIGNAL_STRENGTH: {
- dprintk("%s: FE_READ_SIGNAL_STRENGTH\n", __FUNCTION__);
- *(s32 *)arg = 0xFF;
- return -ENOSYS;
- break;
- }
-
- case FE_READ_SNR:
- dprintk("%s: FE_READ_SNR\n", __FUNCTION__);
- *(s32 *)arg = 0;
- return -ENOSYS;
- break;
-
- case FE_READ_UNCORRECTED_BLOCKS:
- dprintk("%s: FE_READ_UNCORRECTED_BLOCKS\n", __FUNCTION__);
- *(u32 *)arg = 0;
- return -ENOSYS;
- break;
-
- case FE_SET_FRONTEND: {
- struct dvb_frontend_parameters *p =
- (struct dvb_frontend_parameters *)arg;
- u8 b[] = { 0x00, 0x00, 0x00, 0x01,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x01,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00 };
- u32 freq;
- u32 sym_rate;
- u32 band;
- u32 lnb_voltage;
-
- dprintk("%s: FE_SET_FRONTEND\n", __FUNCTION__);
-
- dprintk(" frequency->%d\n", p->frequency);
- dprintk(" symbol_rate->%d\n",
- p->u.qam.symbol_rate);
- dprintk(" inversion->%d\n", p->inversion);
-
- freq = htonl(p->frequency +
- (dec->hi_band ? LOF_HI : LOF_LO));
- memcpy(&b[4], &freq, sizeof(u32));
- sym_rate = htonl(p->u.qam.symbol_rate);
- memcpy(&b[12], &sym_rate, sizeof(u32));
- band = htonl(dec->hi_band ? LOF_HI : LOF_LO);
- memcpy(&b[24], &band, sizeof(u32));
- lnb_voltage = htonl(dec->voltage);
- memcpy(&b[28], &lnb_voltage, sizeof(u32));
-
- ttusb_dec_send_command(dec, 0x71, sizeof(b), b, NULL, NULL);
-
- break;
- }
-
- case FE_GET_FRONTEND:
- dprintk("%s: FE_GET_FRONTEND\n", __FUNCTION__);
- break;
-
- case FE_SLEEP:
- dprintk("%s: FE_SLEEP\n", __FUNCTION__);
- return -ENOSYS;
- break;
-
- case FE_INIT:
- dprintk("%s: FE_INIT\n", __FUNCTION__);
- break;
-
- case FE_DISEQC_SEND_MASTER_CMD: {
- u8 b[] = { 0x00, 0xff, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00 };
- struct dvb_diseqc_master_cmd *cmd = arg;
- memcpy(&b[4], cmd->msg, cmd->msg_len);
- dprintk("%s: FE_DISEQC_SEND_MASTER_CMD\n", __FUNCTION__);
- ttusb_dec_send_command(dec, 0x72,
- sizeof(b) - (6 - cmd->msg_len), b,
- NULL, NULL);
- break;
- }
-
- case FE_DISEQC_SEND_BURST:
- dprintk("%s: FE_DISEQC_SEND_BURST\n", __FUNCTION__);
- break;
-
- case FE_SET_TONE: {
- fe_sec_tone_mode_t tone = (fe_sec_tone_mode_t)arg;
- dprintk("%s: FE_SET_TONE\n", __FUNCTION__);
- dec->hi_band = (SEC_TONE_ON == tone);
- break;
- }
-
- case FE_SET_VOLTAGE:
- dprintk("%s: FE_SET_VOLTAGE\n", __FUNCTION__);
- switch ((fe_sec_voltage_t) arg) {
- case SEC_VOLTAGE_13:
- dec->voltage = 13;
- break;
- case SEC_VOLTAGE_18:
- dec->voltage = 18;
- break;
- default:
- return -EINVAL;
- break;
- }
- break;
-
- default:
- dprintk("%s: unknown IOCTL (0x%X)\n", __FUNCTION__, cmd);
- return -EINVAL;
- }
-
- return 0;
-}
-
-static void ttusb_dec_init_frontend(struct ttusb_dec *dec)
-{
- int ret;
- ret = dvb_register_frontend(dec->frontend_ioctl, dec->adapter, dec, dec->frontend_info, THIS_MODULE);
-}
-
-static void ttusb_dec_exit_frontend(struct ttusb_dec *dec)
-{
- dvb_unregister_frontend(dec->frontend_ioctl, dec->adapter);
-}
-
static void ttusb_dec_init_filters(struct ttusb_dec *dec)
{
INIT_LIST_HEAD(&dec->filter_info_list);
@@ -1708,6 +1423,18 @@ static void ttusb_dec_exit_filters(struct ttusb_dec *dec)
}
}
+int fe_send_command(struct dvb_frontend* fe, const u8 command,
+ int param_length, const u8 params[],
+ int *result_length, u8 cmd_result[])
+{
+ struct ttusb_dec* dec = (struct ttusb_dec*) fe->dvb->priv;
+ return ttusb_dec_send_command(dec, command, param_length, params, result_length, cmd_result);
+}
+
+struct ttusbdecfe_config fe_config = {
+ .send_command = fe_send_command
+};
+
static int ttusb_dec_probe(struct usb_interface *intf,
const struct usb_device_id *id)
{
@@ -1749,7 +1476,32 @@ static int ttusb_dec_probe(struct usb_interface *intf,
return 0;
}
ttusb_dec_init_dvb(dec);
- ttusb_dec_init_frontend(dec);
+
+ dec->adapter->priv = dec;
+ switch (id->idProduct) {
+ case 0x1006:
+ dec->fe = ttusbdecfe_dvbs_attach(&fe_config);
+ break;
+
+ case 0x1008:
+ case 0x1009:
+ dec->fe = ttusbdecfe_dvbt_attach(&fe_config);
+ break;
+ }
+
+ if (dec->fe == NULL) {
+ printk("dvb-ttusb-dec: A frontend driver was not found for device %04x/%04x\n",
+ dec->udev->descriptor.idVendor,
+ dec->udev->descriptor.idProduct);
+ } else {
+ if (dvb_register_frontend(dec->adapter, dec->fe)) {
+ printk("budget-ci: Frontend registration failed!\n");
+ if (dec->fe->ops->release)
+ dec->fe->ops->release(dec->fe);
+ dec->fe = NULL;
+ }
+ }
+
ttusb_dec_init_v_pes(dec);
ttusb_dec_init_filters(dec);
ttusb_dec_init_tasklet(dec);
@@ -1773,7 +1525,6 @@ static void ttusb_dec_disconnect(struct usb_interface *intf)
ttusb_dec_exit_tasklet(dec);
ttusb_dec_exit_filters(dec);
ttusb_dec_exit_usb(dec);
- ttusb_dec_exit_frontend(dec);
ttusb_dec_exit_dvb(dec);
}
@@ -1789,22 +1540,16 @@ static void ttusb_dec_set_model(struct ttusb_dec *dec,
case TTUSB_DEC2000T:
dec->model_name = "DEC2000-t";
dec->firmware_name = "dvb-ttusb-dec-2000t.fw";
- dec->frontend_info = &dec2000t_frontend_info;
- dec->frontend_ioctl = ttusb_dec_2000t_frontend_ioctl;
break;
case TTUSB_DEC2540T:
dec->model_name = "DEC2540-t";
dec->firmware_name = "dvb-ttusb-dec-2540t.fw";
- dec->frontend_info = &dec2000t_frontend_info;
- dec->frontend_ioctl = ttusb_dec_2000t_frontend_ioctl;
break;
case TTUSB_DEC3000S:
dec->model_name = "DEC3000-s";
dec->firmware_name = "dvb-ttusb-dec-3000s.fw";
- dec->frontend_info = &dec3000s_frontend_info;
- dec->frontend_ioctl = ttusb_dec_3000s_frontend_ioctl;
break;
}
}
diff --git a/linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.c b/linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.c
new file mode 100644
index 000000000..d6dd11c98
--- /dev/null
+++ b/linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.c
@@ -0,0 +1,258 @@
+/*
+ * TTUSB DEC Frontend Driver
+ *
+ * Copyright (C) 2003-2004 Alex Woods <linux-dvb@giblets.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ */
+
+#include "dvb_frontend.h"
+#include "ttusbdecfe.h"
+
+
+#define LOF_HI 10600000
+#define LOF_LO 9750000
+
+struct ttusbdecfe_state {
+
+ struct dvb_frontend_ops ops;
+
+ /* configuration settings */
+ const struct ttusbdecfe_config* config;
+
+ struct dvb_frontend frontend;
+
+ u8 hi_band;
+ u8 voltage;
+};
+
+
+static int ttusbdecfe_read_status(struct dvb_frontend* fe, fe_status_t* status)
+{
+ *status = FE_HAS_SIGNAL | FE_HAS_VITERBI |
+ FE_HAS_SYNC | FE_HAS_CARRIER | FE_HAS_LOCK;
+
+ return 0;
+}
+
+static int ttusbdecfe_dvbt_set_frontend(struct dvb_frontend* fe, struct dvb_frontend_parameters *p)
+{
+ struct ttusbdecfe_state* state = (struct ttusbdecfe_state*) fe->demodulator_priv;
+ u8 b[] = { 0x00, 0x00, 0x00, 0x03,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x01,
+ 0x00, 0x00, 0x00, 0xff,
+ 0x00, 0x00, 0x00, 0xff };
+
+ u32 freq = htonl(p->frequency / 1000);
+ memcpy(&b[4], &freq, sizeof (u32));
+ state->config->send_command(fe, 0x71, sizeof(b), b, NULL, NULL);
+
+ return 0;
+}
+
+static int ttusbdecfe_dvbs_set_frontend(struct dvb_frontend* fe, struct dvb_frontend_parameters *p)
+{
+ struct ttusbdecfe_state* state = (struct ttusbdecfe_state*) fe->demodulator_priv;
+
+ u8 b[] = { 0x00, 0x00, 0x00, 0x01,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x01,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00 };
+ u32 freq;
+ u32 sym_rate;
+ u32 band;
+ u32 lnb_voltage;
+
+ freq = htonl(p->frequency +
+ (state->hi_band ? LOF_HI : LOF_LO));
+ memcpy(&b[4], &freq, sizeof(u32));
+ sym_rate = htonl(p->u.qam.symbol_rate);
+ memcpy(&b[12], &sym_rate, sizeof(u32));
+ band = htonl(state->hi_band ? LOF_HI : LOF_LO);
+ memcpy(&b[24], &band, sizeof(u32));
+ lnb_voltage = htonl(state->voltage);
+ memcpy(&b[28], &lnb_voltage, sizeof(u32));
+
+ state->config->send_command(fe, 0x71, sizeof(b), b, NULL, NULL);
+
+ return 0;
+}
+
+static int ttusbdecfe_dvbs_diseqc_send_master_cmd(struct dvb_frontend* fe, struct dvb_diseqc_master_cmd *cmd)
+{
+ struct ttusbdecfe_state* state = (struct ttusbdecfe_state*) fe->demodulator_priv;
+ u8 b[] = { 0x00, 0xff, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00 };
+
+ memcpy(&b[4], cmd->msg, cmd->msg_len);
+
+ state->config->send_command(fe, 0x72,
+ sizeof(b) - (6 - cmd->msg_len), b,
+ NULL, NULL);
+
+ return 0;
+}
+
+
+static int ttusbdecfe_dvbs_set_tone(struct dvb_frontend* fe, fe_sec_tone_mode_t tone)
+{
+ struct ttusbdecfe_state* state = (struct ttusbdecfe_state*) fe->demodulator_priv;
+
+ state->hi_band = (SEC_TONE_ON == tone);
+
+ return 0;
+}
+
+
+static int ttusbdecfe_dvbs_set_voltage(struct dvb_frontend* fe, fe_sec_voltage_t voltage)
+{
+ struct ttusbdecfe_state* state = (struct ttusbdecfe_state*) fe->demodulator_priv;
+
+ switch (voltage) {
+ case SEC_VOLTAGE_13:
+ state->voltage = 13;
+ break;
+ case SEC_VOLTAGE_18:
+ state->voltage = 18;
+ break;
+ default:
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+static void ttusbdecfe_release(struct dvb_frontend* fe)
+{
+ struct ttusbdecfe_state* state = (struct ttusbdecfe_state*) fe->demodulator_priv;
+ kfree(state);
+}
+
+static struct dvb_frontend_ops ttusbdecfe_dvbt_ops;
+
+struct dvb_frontend* ttusbdecfe_dvbt_attach(const struct ttusbdecfe_config* config)
+{
+ struct ttusbdecfe_state* state = NULL;
+
+ /* allocate memory for the internal state */
+ state = (struct ttusbdecfe_state*) kmalloc(sizeof(struct ttusbdecfe_state), GFP_KERNEL);
+ if (state == NULL) goto error;
+
+ /* setup the state */
+ state->config = config;
+ memcpy(&state->ops, &ttusbdecfe_dvbt_ops, sizeof(struct dvb_frontend_ops));
+
+ /* create dvb_frontend */
+ state->frontend.ops = &state->ops;
+ state->frontend.demodulator_priv = state;
+ return &state->frontend;
+
+error:
+ if (state) kfree(state);
+ return NULL;
+}
+
+static struct dvb_frontend_ops ttusbdecfe_dvbs_ops;
+
+struct dvb_frontend* ttusbdecfe_dvbs_attach(const struct ttusbdecfe_config* config)
+{
+ struct ttusbdecfe_state* state = NULL;
+
+ /* allocate memory for the internal state */
+ state = (struct ttusbdecfe_state*) kmalloc(sizeof(struct ttusbdecfe_state), GFP_KERNEL);
+ if (state == NULL) goto error;
+
+ /* setup the state */
+ state->config = config;
+ state->voltage = 0;
+ state->hi_band = 0;
+ memcpy(&state->ops, &ttusbdecfe_dvbs_ops, sizeof(struct dvb_frontend_ops));
+
+ /* create dvb_frontend */
+ state->frontend.ops = &state->ops;
+ state->frontend.demodulator_priv = state;
+ return &state->frontend;
+
+error:
+ if (state) kfree(state);
+ return NULL;
+}
+
+static struct dvb_frontend_ops ttusbdecfe_dvbt_ops = {
+
+ .info = {
+ .name = "TechnoTrend/Hauppauge DEC2000-t Frontend",
+ .type = FE_OFDM,
+ .frequency_min = 51000000,
+ .frequency_max = 858000000,
+ .frequency_stepsize = 62500,
+ .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
+ FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
+ FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
+ FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO |
+ FE_CAN_HIERARCHY_AUTO,
+ },
+
+ .release = ttusbdecfe_release,
+
+ .set_frontend = ttusbdecfe_dvbt_set_frontend,
+
+ .read_status = ttusbdecfe_read_status,
+};
+
+static struct dvb_frontend_ops ttusbdecfe_dvbs_ops = {
+
+ .info = {
+ .name = "TechnoTrend/Hauppauge DEC3000-s Frontend",
+ .type = FE_QPSK,
+ .frequency_min = 950000,
+ .frequency_max = 2150000,
+ .frequency_stepsize = 125,
+ .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
+ FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
+ FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
+ FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO |
+ FE_CAN_HIERARCHY_AUTO,
+ },
+
+ .release = ttusbdecfe_release,
+
+ .set_frontend = ttusbdecfe_dvbs_set_frontend,
+
+ .read_status = ttusbdecfe_read_status,
+
+ .diseqc_send_master_cmd = ttusbdecfe_dvbs_diseqc_send_master_cmd,
+ .set_voltage = ttusbdecfe_dvbs_set_voltage,
+ .set_tone = ttusbdecfe_dvbs_set_tone,
+};
+
+MODULE_PARM(debug,"i");
+MODULE_PARM_DESC(debug, "Enable verbose debug messages");
+
+MODULE_DESCRIPTION("TTUSB DEC DVB-T/S Demodulator driver");
+MODULE_AUTHOR("Alex Woods/Andrew de Quincey");
+MODULE_LICENSE("GPL");
+
+EXPORT_SYMBOL(ttusbdecfe_dvbt_attach);
+EXPORT_SYMBOL(ttusbdecfe_dvbs_attach);
diff --git a/linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.h b/linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.h
new file mode 100644
index 000000000..15ccc3d1a
--- /dev/null
+++ b/linux/drivers/media/dvb/ttusb-dec/ttusbdecfe.h
@@ -0,0 +1,38 @@
+/*
+ * TTUSB DEC Driver
+ *
+ * Copyright (C) 2003-2004 Alex Woods <linux-dvb@giblets.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ */
+
+#ifndef TTUSBDECFE_H
+#define TTUSBDECFE_H
+
+#include <linux/dvb/frontend.h>
+
+struct ttusbdecfe_config
+{
+ int (*send_command)(struct dvb_frontend* fe, const u8 command,
+ int param_length, const u8 params[],
+ int *result_length, u8 cmd_result[]);
+};
+
+extern struct dvb_frontend* ttusbdecfe_dvbs_attach(const struct ttusbdecfe_config* config);
+
+extern struct dvb_frontend* ttusbdecfe_dvbt_attach(const struct ttusbdecfe_config* config);
+
+#endif // TTUSBDECFE_H