/* * $Id: dummyadap.c,v 1.5 2003/07/01 03:51:07 obi Exp $ * * Dummy Adapter Driver * * Homepage: http://www.tuxbox.org * * Copyright (C) 2002 Florian Schirmer * * 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 #include #include #include #include #include "drivers/media/dvb/dvb-core/dmxdev.h" #include "drivers/media/dvb/dvb-core/dvbdev.h" #include "drivers/media/dvb/dvb-core/dvb_demux.h" #include "drivers/media/dvb/dvb-core/dvb_frontend.h" #include "dvb_dummy_fe.h" /* #define DVB_MAJOR 250 #define DVB_DEVICE_VIDEO 0 #define DVB_DEVICE_AUDIO 1 #define DVB_DEVICE_SEC 2 #define DVB_DEVICE_FRONTEND 3 #define DVB_DEVICE_DEMUX 4 #define DVB_DEVICE_DVR 5 #define DVB_DEVICE_CA 6 #define DVB_DEVICE_NET 7 #define DVB_DEVICE_OSD 8 struct dvb_adapter { int num; #include #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)) devfs_handle_t devfs_handle; #endif struct list_head list_head; struct list_head device_list; const char *name; u8 proposed_mac [6]; }; struct dvb_device { struct list_head list_head; struct file_operations *fops; #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)) devfs_handle_t devfs_handle; #endif struct dvb_adapter *adapter; int type; u32 id; // in theory, 'users' can vanish now, // but I don't want to change too much now... int readers; int writers; int users; // don't really need those !? -- FIXME: use video_usercopy int (*kernel_ioctl)(struct inode *inode, struct file *file, unsigned int cmd, void *arg); void *priv; }; struct dvb_frontend { struct dvb_frontend_ops ops; struct dvb_adapter *dvb; void* demodulator_priv; void* tuner_priv; void* frontend_priv; void* misc_priv; }; dvb_register_adapter(&fc->dvb_adapter,"FlexCop Digital TV device",fc->owner,fc->dev); */ #define TS_DMA_PACKETS (8) #define TS_DMA_BYTES (188 * TS_DMA_PACKETS) struct dummy2 { /* pci */ struct pci_dev *pdev; u8 __iomem *io_mem; /* dvb */ struct dmx_frontend hw_frontend; struct dmx_frontend mem_frontend; struct dmxdev dmxdev; struct dvb_adapter dvb_adapter; struct dvb_demux demux; struct dvb_frontend *fe; //struct dvb_net dvbnet; unsigned int full_ts_users; unsigned int users; /* i2c */ //struct i2c_algo_bit_data i2c_bit; struct i2c_adapter i2c_adap; unsigned int i2cbug; /* irq */ unsigned int overflow; /* dma */ dma_addr_t dma_addr; u8 dma_buf[TS_DMA_BYTES]; u8 dummy[4096]; }; static struct dummy2 *adap; static struct dvb_demux demux; static struct dmxdev dmxdevice; static struct dmx_frontend fe_hw; static struct dmx_frontend fe_mem; static struct dvb_i2c_bus *i2c_bus; static struct dvb_frontend *frontend; static void dummyadap_before_after_tune(fe_status_t fe_status, void *data) { // printk("dummyadap: before_after_tune\n"); } static int dummyadap_after_ioctl(struct dvb_frontend *fe, unsigned int cmd, void *arg) { // printk("dummyadap: after_ioctl\n"); return 0; } static int dummyadap_before_ioctl(struct dvb_frontend *fe, unsigned int cmd, void *arg) { // printk("dummyadap: before_ioctl\n"); // Returning 0 will skip the fe ioctl return -ENODEV; } static int dummyadap_write_to_decoder(struct dvb_demux_feed *dvbdmxfeed, u8 *buf, size_t count) { printk("dummyadap: write_to_decoder\n"); return 0; } static int dummyadap_start_feed(struct dvb_demux_feed *dvbdmxfeed) { struct dvb_demux *dvbdmx = dvbdmxfeed->demux; printk("dummyadap: start_feed\n"); if (!dvbdmx->dmx.frontend) return -EINVAL; printk(" pid: 0x%04X\n", dvbdmxfeed->pid); switch(dvbdmxfeed->type) { case DMX_TYPE_TS: printk(" type: DMX_TYPE_TS\n"); break; case DMX_TYPE_SEC: printk(" type: DMX_TYPE_SEC\n"); break; default: printk(" type: unknown (%d)\n", dvbdmxfeed->type); return -EINVAL; } printk(" ts_type:"); if (dvbdmxfeed->ts_type & TS_DECODER) printk(" TS_DECODER"); if (dvbdmxfeed->ts_type & TS_PACKET) printk(" TS_PACKET"); if (dvbdmxfeed->ts_type & TS_PAYLOAD_ONLY) printk(" TS_PAYLOAD_ONLY"); printk("\n"); switch(dvbdmxfeed->pes_type) { case DMX_TS_PES_VIDEO: printk(" pes_type: DMX_TS_PES_VIDEO\n"); break; case DMX_TS_PES_AUDIO: printk(" pes_type: DMX_TS_PES_AUDIO\n"); break; case DMX_TS_PES_TELETEXT: printk(" pes_type: DMX_TS_PES_TELETEXT\n"); break; case DMX_TS_PES_PCR: printk(" pes_type: DMX_TS_PES_PCR\n"); break; case DMX_TS_PES_OTHER: printk(" pes_type: DMX_TS_PES_OTHER\n"); break; default: printk(" pes_type: unknown (%d)\n", dvbdmxfeed->pes_type); return -EINVAL; } return 0; } static int dummyadap_stop_feed(struct dvb_demux_feed *dvbdmxfeed) { printk("dummyadap: stop_feed\n"); return 0; } static int __init dummyadap_init(void) { int result; //adap = kmalloc(sizeof(struct dummy), GFP_KERNEL); //frontend = dvb_dummy_fe_qpsk_attach(); if ((result = dvb_register_adapter(&adap,"Dummy adaptor",&frontend->frontend_priv, DVB_DEVICE_FRONTEND)) < 0) { printk("dummyadap: dvb_register_adapter failed (errno = %d)\n", result); return result; } //dvb_register_adapter(&pluto->dvb_adapter, DRIVER_NAME, THIS_MODULE, &pdev->dev); if ((result = dvb_register_adapter(&adap->dvb_adapter,"Dummy adaptor",THIS_MODULE,&adap->pdev)) < 0) { printk("dummyadap: dvb_register_adapter failed (errno = %d)\n", result); return result; } memset(&adap->demux, 0x0, sizeof(adap->demux)); //demux.dmx.vendor = "Dummy Vendor"; //demux.dmx.model = "Dummy Model"; //demux.dmx.id = "demux0_0"; adap->demux.dmx.capabilities = DMX_TS_FILTERING | DMX_SECTION_FILTERING; adap->demux.priv = NULL; adap->demux.filternum = 31; adap->demux.feednum = 31; adap->demux.start_feed = dummyadap_start_feed; adap->demux.stop_feed = dummyadap_stop_feed; adap->demux.write_to_decoder = dummyadap_write_to_decoder; if ((result = dvb_dmx_init(&adap->demux)) < 0) { printk("dummyadap: dvb_dmx_init failed (errno = %d)\n", result); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } adap->dmxdev.filternum = 32; adap->dmxdev.demux = &adap->demux.dmx; adap->dmxdev.capabilities = 0; if ((result = dvb_dmxdev_init(&adap->dmxdev, &adap->dvb_adapter)) < 0) { printk("dummyadap: dvb_dmxdev_init failed (errno = %d)\n", result); dvb_dmx_release(&adap->demux); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } adap->fe = dvb_dummy_fe_qpsk_attach(); //fe_hw.id = "hw_frontend"; //fe_hw.vendor = "Dummy Vendor"; //fe_hw.model = "hw"; adap->hw_frontend.source = DMX_FRONTEND_0; if ((result = adap->demux.dmx.add_frontend(&adap->demux.dmx, &adap->hw_frontend)) < 0) { printk("dummyadap: dvb_dmx_init failed (errno = %d)\n", result); dvb_dmxdev_release(&adap->dmxdev); dvb_dmx_release(&adap->demux); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } //fe_mem.id = "mem_frontend"; //fe_mem.vendor = "memory"; //fe_mem.model = "sw"; adap->mem_frontend.source = DMX_MEMORY_FE; if ((result = adap->demux.dmx.add_frontend(&adap->demux.dmx, &adap->mem_frontend)) < 0) { printk("dummyadap: dvb_dmx_init failed (errno = %d)\n", result); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->mem_frontend); dvb_dmxdev_release(&adap->dmxdev); dvb_dmx_release(&adap->demux); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } if ((result = adap->demux.dmx.connect_frontend(&adap->demux.dmx, &adap->hw_frontend)) < 0) { printk("dummyadap: dvb_dmx_init failed (errno = %d)\n", result); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->mem_frontend); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->hw_frontend); dvb_dmxdev_release(&adap->dmxdev); dvb_dmx_release(&adap->demux); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } /* if ((result = dvb_add_frontend_notifier(&adap->dvb_adapter, dummyadap_before_after_tune, NULL)) < 0) { printk("dummyadap: dvb_add_frontend_notifier failed (errno = %d)\n", result); adap->demux.dmx.close(&adap->demux.dmx); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->mem_frontend); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->hw_frontend); dvb_dmxdev_release(&adap->dmxdev); dvb_dmx_release(&adap->demux); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } if ((result = dvb_add_frontend_ioctls(&adap->dvb_adapter, dummyadap_before_ioctl, dummyadap_after_ioctl, NULL)) < 0) { printk("dummyadap: dvb_add_frontend_ioctls failed (errno = %d)\n", result); dvb_remove_frontend_notifier(&adap->dvb_adapter, dummyadap_before_after_tune); adap->demux.dmx.close(&adap->demux.dmx); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->mem_frontend); adap->demux.dmx.remove_frontend(&adap->demux.dmx, &adap->hw_frontend); dvb_dmxdev_release(&adap->dmxdev); dvb_dmx_release(&adap->demux); //dvb_unregister_i2c_bus(dummyadap_i2c_master_xfer, adap, 0); dvb_unregister_adapter(&adap->dvb_adapter); return result; } */ return 0; } static void __exit dummyadap_exit(void) { } #ifdef MODULE module_init(dummyadap_init); module_exit(dummyadap_exit); MODULE_DESCRIPTION("dummy dvb adapter driver"); MODULE_AUTHOR("Florian Schirmer "); #ifdef MODULE_LICENSE MODULE_LICENSE("GPL"); #endif #endif