diff options
author | Gerd Knorr <devnull@localhost> | 2004-07-30 13:43:39 +0000 |
---|---|---|
committer | Gerd Knorr <devnull@localhost> | 2004-07-30 13:43:39 +0000 |
commit | 4df008f985ce28551d586721818b7a7a00b8b1dd (patch) | |
tree | a435231150c5e27b174891ffb6e0f8ddf17a40cc /linux | |
parent | 016aa2e20f1ca4b4f5430c4e945878b73a866894 (diff) | |
download | mediapointer-dvb-s2-4df008f985ce28551d586721818b7a7a00b8b1dd.tar.gz mediapointer-dvb-s2-4df008f985ce28551d586721818b7a7a00b8b1dd.tar.bz2 |
- cx88: more reorganization + code shuffeling.
Diffstat (limited to 'linux')
-rw-r--r-- | linux/drivers/media/video/bttvp.h | 8 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-blackbird.c | 242 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-core.c | 8 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-dvb.c | 364 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-mpeg.c | 235 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-tvaudio.c | 3 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-vbi.c | 4 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88-video.c | 9 | ||||
-rw-r--r-- | linux/drivers/media/video/cx88/cx88.h | 19 | ||||
-rw-r--r-- | linux/drivers/media/video/saa6752hs.c | 4 | ||||
-rw-r--r-- | linux/drivers/media/video/saa7134/saa6752hs.c | 4 | ||||
-rw-r--r-- | linux/drivers/media/video/saa7134/saa7134.h | 11 | ||||
-rw-r--r-- | linux/include/media/id.h | 5 |
13 files changed, 646 insertions, 270 deletions
diff --git a/linux/drivers/media/video/bttvp.h b/linux/drivers/media/video/bttvp.h index 58a40841d..4d1e3a807 100644 --- a/linux/drivers/media/video/bttvp.h +++ b/linux/drivers/media/video/bttvp.h @@ -51,13 +51,7 @@ #include <media/tuner.h> #include <media/ir-common.h> #endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,23) -#define irqreturn_t void -#define IRQ_RETVAL(foobar) -#endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0) -#define iminor(inode) minor(inode->i_rdev) -#endif +#include "compat.h" #include "bt848.h" #include "bttv.h" diff --git a/linux/drivers/media/video/cx88/cx88-blackbird.c b/linux/drivers/media/video/cx88/cx88-blackbird.c index b0f3a1005..0725ea76c 100644 --- a/linux/drivers/media/video/cx88/cx88-blackbird.c +++ b/linux/drivers/media/video/cx88/cx88-blackbird.c @@ -1,7 +1,7 @@ /* - * $Id: cx88-blackbird.c,v 1.1 2004/07/29 21:35:48 kraxel Exp $ + * $Id: cx88-blackbird.c,v 1.2 2004/07/30 13:43:39 kraxel Exp $ * - * Support for a cx23416 mpeg encoder via cx2388x host port (PCI function #4). + * Support for a cx23416 mpeg encoder via cx2388x host port. * "blackbird" reference design. * * (c) 2004 Jelle Foks <jelle@foks.8m.com> @@ -24,6 +24,19 @@ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ +#include <linux/module.h> +#include <linux/init.h> +#include <linux/device.h> +#include <linux/fs.h> + +#include "cx88.h" + +MODULE_DESCRIPTION("driver for cx2388x/cx23416 based mpeg encoder cards"); +MODULE_AUTHOR("Chris Pascoe <c.pascoe@itee.uq.edu.au>"); +MODULE_LICENSE("GPL"); + +/* ------------------------------------------------------------------ */ + #define BLACKBIRD_FIRM_ENC_FILENAME "blackbird-fw-enc.bin" #define BLACKBIRD_FIRM_IMAGE_SIZE 256*1024 @@ -71,6 +84,7 @@ #define IVTV_REG_VPU (0x9058 /*| IVTV_REG_OFFSET*/) #define IVTV_REG_APU (0xA064 /*| IVTV_REG_OFFSET*/) +#if 0 /* initialize the dma for the mpegport, called from cx88-video.c:cx8800_initdev */ int cx8800_mpegport_init_dma(struct cx8800_dev *dev) @@ -114,7 +128,7 @@ int cx8800_mpegport_init_dma(struct cx8800_dev *dev) cx_set(MO_TS_INTSTAT, 0); cx_write(MO_TS_INTMSK, 0x1f1101); /* all except the irq2 bit */ - cx_write(MO_TS_GPCNTRL, 3); /* reset gp counter to 0 */ + cx_write(MO_TS_GPCNTRL, GP_COUNT_CONTROL_RESET); /* reset gp counter to 0 */ cx_write(TS_HW_SOP_CNTRL, 0x408); /* mpeg start byte */ //cx_write(TS_HW_SOP_CNTRL, 0x2F0BC0); /* mpeg start byte ts: 0x2F0BC0 ? */ cx_write(TS_VALERR_CNTRL, 0x2000); @@ -594,5 +608,227 @@ int mpegport_initialize_codec(struct cx8800_dev *dev) return retval; } +#endif + +/* ------------------------------------------------------------------ */ + +static int mpeg_do_ioctl(struct inode *inode, struct file *file, + unsigned int cmd, void *arg) +{ + struct cx8802_fh *fh = file->private_data; + +#if 0 + struct cx8802_dev *dev = fh->dev; + + if (mpeg_debug > 1) + cx88_print_ioctl(dev->core->name,cmd); +#endif + + switch (cmd) { + + /* --- capture ioctls ---------------------------------------- */ + case VIDIOC_ENUM_FMT: + { + struct v4l2_fmtdesc *f = arg; + int index; + + index = f->index; + if (index != 0) + return -EINVAL; + + memset(f,0,sizeof(*f)); + f->index = index; + strlcpy(f->description, "MPEG TS", sizeof(f->description)); + f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; + f->pixelformat = V4L2_PIX_FMT_MPEG; + return 0; + } + case VIDIOC_G_FMT: + case VIDIOC_S_FMT: + case VIDIOC_TRY_FMT: + { + /* FIXME -- quick'n'dirty for exactly one size ... */ + struct v4l2_format *f = arg; + + memset(f,0,sizeof(*f)); + f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; + f->fmt.pix.width = 720; + f->fmt.pix.height = 576; + f->fmt.pix.pixelformat = V4L2_PIX_FMT_MPEG; + f->fmt.pix.sizeimage = 1024 * 512 /* FIXME: BUFFER_SIZE */; + } + + /* --- streaming capture ------------------------------------- */ + case VIDIOC_REQBUFS: + return videobuf_reqbufs(file, &fh->mpegq, arg); + + case VIDIOC_QUERYBUF: + return videobuf_querybuf(&fh->mpegq, arg); + + case VIDIOC_QBUF: + return videobuf_qbuf(file, &fh->mpegq, arg); + + case VIDIOC_DQBUF: + return videobuf_dqbuf(file, &fh->mpegq, arg); + + case VIDIOC_STREAMON: + return videobuf_streamon(file, &fh->mpegq); + + case VIDIOC_STREAMOFF: + return videobuf_streamoff(file, &fh->mpegq); + + default: + return -EINVAL; + } + return 0; +} + +static int mpeg_ioctl(struct inode *inode, struct file *file, + unsigned int cmd, unsigned long arg) +{ + return video_usercopy(inode, file, cmd, arg, mpeg_do_ioctl); +} + +static int mpeg_open(struct inode *inode, struct file *file) +{ + int minor = iminor(inode); + struct cx8802_dev *h,*dev = NULL; + struct cx8802_fh *fh; + struct list_head *list; + + list_for_each(list,&cx8802_devlist) { + h = list_entry(list, struct cx8802_dev, devlist); + if (h->mpeg_dev->minor == minor) + dev = h; + } + if (NULL == dev) + return -ENODEV; + +#if 0 /* FIXME */ + if (mpegport_initialize_codec(dev) < 0) + return -EINVAL; + dprintk(1,"open minor=%d\n",minor); +#endif + + /* allocate + initialize per filehandle data */ + fh = kmalloc(sizeof(*fh),GFP_KERNEL); + if (NULL == fh) + return -ENOMEM; + memset(fh,0,sizeof(*fh)); + file->private_data = fh; + fh->dev = dev; + + videobuf_queue_init(&fh->mpegq, &cx8802_mpeg_qops, + dev->pci, &dev->slock, + V4L2_BUF_TYPE_VIDEO_CAPTURE, + V4L2_FIELD_TOP, + sizeof(struct cx88_buffer)); + init_MUTEX(&fh->mpegq.lock); + + return 0; +} + +static int mpeg_release(struct inode *inode, struct file *file) +{ + struct cx8802_fh *fh = file->private_data; + +#if 0 /* FIXME */ + mpegport_api_cmd(fh->dev, IVTV_API_END_CAPTURE, 3, 0, 1, 0, 0x13); +#endif + + /* stop mpeg capture */ + if (fh->mpegq.streaming) + videobuf_streamoff(file,&fh->mpegq); + if (fh->mpegq.reading) + videobuf_read_stop(file,&fh->mpegq); + + file->private_data = NULL; + kfree(fh); + return 0; +} + +static ssize_t +mpeg_read(struct file *file, char *data, size_t count, loff_t *ppos) +{ + struct cx8802_fh *fh = file->private_data; + + return videobuf_read_stream(file, &fh->mpegq, data, count, ppos, 0); +} + +static unsigned int +mpeg_poll(struct file *file, struct poll_table_struct *wait) +{ + struct cx8802_fh *fh = file->private_data; + + return videobuf_poll_stream(file, &fh->mpegq, wait); +} + +static int +mpeg_mmap(struct file *file, struct vm_area_struct * vma) +{ + struct cx8802_fh *fh = file->private_data; + + return videobuf_mmap_mapper(vma, &fh->mpegq); +} + +static struct file_operations mpeg_fops = +{ + .owner = THIS_MODULE, + .open = mpeg_open, + .release = mpeg_release, + .read = mpeg_read, + .poll = mpeg_poll, + .mmap = mpeg_mmap, + .ioctl = mpeg_ioctl, + .llseek = no_llseek, +}; + +static struct video_device cx8802_mpeg_template = +{ + .name = "cx8802", + .type = VID_TYPE_CAPTURE|VID_TYPE_TUNER|VID_TYPE_SCALES|VID_TYPE_MPEG_ENCODER, + .hardware = 0, + .fops = &mpeg_fops, + .minor = -1, +}; /* ------------------------------------------------------------------ */ + +static void cx8802_unregister_video(struct cx8802_dev *dev) +{ + if (dev->mpeg_dev) { + if (-1 != dev->mpeg_dev->minor) + video_unregister_device(dev->mpeg_dev); + else + video_device_release(dev->mpeg_dev); + dev->mpeg_dev = NULL; + } +} + +static int cx8802_register_video(struct cx8802_dev *dev) +{ + int err; + + dev->mpeg_dev = cx88_vdev_init(dev->core,dev->pci, + &cx8802_mpeg_template,"mpeg"); + err = video_register_device(dev->mpeg_dev,VFL_TYPE_GRABBER, -1); + if (err < 0) { + printk(KERN_INFO "%s/2: can't register mpeg device\n", + dev->core->name); + return err; + } + printk(KERN_INFO "%s/2: registered device video%d [mpeg]\n", + dev->core->name,dev->mpeg_dev->minor & 0x1f); +} + +#if 0 +module_init(cx8802_init); +module_exit(cx8802_fini); +#endif + +/* ----------------------------------------------------------- */ +/* + * Local variables: + * c-basic-offset: 8 + * End: + */ diff --git a/linux/drivers/media/video/cx88/cx88-core.c b/linux/drivers/media/video/cx88/cx88-core.c index b0d80a681..8661674fd 100644 --- a/linux/drivers/media/video/cx88/cx88-core.c +++ b/linux/drivers/media/video/cx88/cx88-core.c @@ -609,8 +609,7 @@ int cx88_reset(struct cx88_core *core) cx_write(MO_INT1_STAT, 0xFFFFFFFF); // Clear RISC int /* wait a bit */ - set_current_state(TASK_INTERRUPTIBLE); - schedule_timeout(HZ/10); + msleep(100); /* init sram */ cx88_sram_channel_setup(core, &cx88_sram_channels[SRAM_CH21], 720*4, 0); @@ -644,6 +643,11 @@ int cx88_reset(struct cx88_core *core) cx_write(MO_PCI_INTSTAT, 0xFFFFFFFF); // Clear PCI int cx_write(MO_INT1_STAT, 0xFFFFFFFF); // Clear RISC int + /* Reset on-board parts */ + cx_write(MO_SRST_IO, 0); + msleep(10); + cx_write(MO_SRST_IO, 1); + return 0; } diff --git a/linux/drivers/media/video/cx88/cx88-dvb.c b/linux/drivers/media/video/cx88/cx88-dvb.c new file mode 100644 index 000000000..08cc56d27 --- /dev/null +++ b/linux/drivers/media/video/cx88/cx88-dvb.c @@ -0,0 +1,364 @@ +/* + * device driver for Conexant 2388x based TV cards + * MPEG Transport Stream (DVB) routines + * + * (c) 2004 Chris Pascoe <c.pascoe@itee.uq.edu.au> + * + * 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 <linux/module.h> +#include <linux/init.h> +#include <linux/device.h> +#include <linux/fs.h> + +#include "cx88.h" + +MODULE_DESCRIPTION("driver for cx2388x based DVB cards"); +MODULE_AUTHOR("Chris Pascoe <c.pascoe@itee.uq.edu.au>"); +MODULE_LICENSE("GPL"); + +/* ------------------------------------------------------------------ */ + +#if 0 +static void cx88_dvb_tasklet(unsigned long data) +{ + struct cx8800_dvb *dvb = (struct cx8800_dvb *)data; + struct cx8800_dev *dev = dvb->dev; + struct cx88_dmaqueue *q = &dvb->tsq; + struct cx88_buffer *buf; + unsigned long flags; + + /* Process any pending buffers */ + spin_lock_irqsave(&dev->slock, flags); + while (! list_empty(&q->queued)) { + /* get items */ + buf = list_entry(q->queued.next, struct cx88_buffer, vb.queue); + spin_unlock_irqrestore(&dev->slock, flags); + + /* Hand the received frames to the software filter */ + (dvb->ts_includes_fec ? dvb_dmx_swfilter_204 : dvb_dmx_swfilter) + (&dvb->demux, (char *)buf->vb.dma.vmalloc, + buf->vb.field_count * buf->bpl); + + /* Reactivate the buffer */ + spin_lock_irqsave(&dev->slock, flags); + list_del(&buf->vb.queue); + activate_ts_buffer(dvb, buf, 1); + } + spin_unlock_irqrestore(&dev->slock, flags); +} + +static void cx8800_wakeup_dvb_tasklet(struct cx8800_dvb *dvb, + unsigned int maxframe, int timeout_case) +{ + struct cx88_dmaqueue *q = &dvb->tsq; + struct cx88_buffer *buf; + int processed_buffers = 0; + + /* Called with dev->slock held */ + + dprintk(2, "cx8800_wakeup_dvb_tasklet called, maxframe: %d, " + "timeout_case: %d\n", maxframe, timeout_case); + + while (! list_empty(&q->active)) { + buf = list_entry(q->active.next, struct cx88_buffer, vb.queue); + + /* Calculate how many frames that are waiting for processing */ + maxframe &= 0xffff; + buf->count &= 0xffff; + buf->vb.field_count = (maxframe - buf->count) & 0xffff; + + dprintk(2, "[%p/%d] wakeup reg=%d buf=%d, field_count=%d, " + "processed=%d\n", buf, buf->vb.i, maxframe, buf->count, + buf->vb.field_count, processed_buffers); + + /* Reject any incomplete buffer if we aren't handling a timeout, + * as data transfer into it is still occurring. */ + if (buf->vb.field_count < buf->vb.height && !timeout_case) { + if (! processed_buffers) { + dprintk(2, "incomplete buffer: mf: %d, count: " + "%d, fc: %d height: %d\n", maxframe, + buf->count, buf->vb.field_count, + buf->vb.height); + return; /* Don't re-timeout... */ + } + break; + } + + /* We've got no frames to process, so just reschedule + * the timeout. */ + if (buf->vb.field_count == 0) { + dprintk(2, "no frames... %d %d\n", maxframe, + buf->count); + break; + } + + /* We can't possibly have more frames than we have size for + * in the buffer, so trim back how many we think we have. */ + if (buf->vb.field_count > buf->vb.height) { + if (buf->vb.field_count > buf->vb.height * 2 && + ++too_many_frames_in_one_interrupt == 10) { + printk(KERN_WARNING "%s: you should consider" + "increasing ts_frames_per_irq (%d " + "frame/irq overload)\n", dvb->dev->name, + (buf->vb.field_count - buf->vb.height)); + } + buf->vb.field_count = buf->vb.height; + } + + /* Mark the buffer as done. */ + buf->vb.state = timeout_case ? STATE_ERROR : STATE_DONE; + + /* Move the buffer from the active queue to the + * queued-for-processing queue */ + list_move_tail(&buf->vb.queue, &q->queued); + + /* Schedule the tasklet to process them */ + tasklet_schedule(&dvb->dvb_tasklet); + + /* Don't queue more than one buffer if we timed out. */ + if (timeout_case) + break; + + /* Record that we processed a buffer. */ + processed_buffers++; + } + + if (list_empty(&q->active)) { + del_timer(&q->timeout); + } else { + mod_timer(&q->timeout, jiffies + TS_BUFFER_TIMEOUT); + } +} + +/* ---------------------------------------------------------------------------- */ + +static int master_xfer(struct dvb_i2c_bus *i2c, const struct i2c_msg msgs[], + int num) +{ + struct cx8800_dvb *dvb = (struct cx8800_dvb *)i2c->data; + struct cx8800_dev *dev = dvb->dev; + int retval; + + if (down_interruptible(&dvb->dvb_i2c_lock)) + return -ERESTARTSYS; + + retval = i2c_transfer(&dev->i2c_adap, (struct i2c_msg *)msgs, num); + + up(&dvb->dvb_i2c_lock); + + return retval; +} + +static int dvb_cx8800_start_feed(struct dvb_demux_feed *feed) +{ + struct dvb_demux *demux = feed->demux; + struct cx8800_dvb *dvb = demux->priv; + + dprintk(2, "dvb_cx8800_start_feed\n"); + + if (!demux->dmx.frontend) + return -EINVAL; + + return start_ts_capture(dvb); +} + +static int dvb_cx8800_stop_feed(struct dvb_demux_feed *feed) +{ + struct dvb_demux *demux = feed->demux; + struct cx8800_dvb *dvb = demux->priv; + + dprintk(2, "dvb_cx8800_stop_feed\n"); + + if (!demux->dmx.frontend) + return -EINVAL; + + return stop_ts_capture(dvb); +} + +static void cx8800_ts_release_dev(struct cx8800_dev *dev) +{ + struct cx8800_dvb *dvb = dev->dvb; + + /* Force us to stop any feed */ + spin_lock(&dvb->feedlock); + if (dvb->ts_feeding != 0) { + spin_unlock(&dvb->feedlock); + printk("Error: releasing a card while feed in progress\n"); + stop_ts_capture(dvb); + } else + spin_unlock(&dvb->feedlock); + + + /* release everything we registered */ + dvb_net_release(&dvb->dvbnet); + dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_mem); + dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_hw); + dvb_dmxdev_release(&dvb->dmxdev); + dvb_dmx_release(&dvb->demux); + dvb_unregister_i2c_bus(master_xfer, dvb->dvb_adapter, 0); + dvb_unregister_adapter(dvb->dvb_adapter); + btcx_riscmem_free(dev->pci, &dvb->tsq.stopper); + + /* Free ourselves */ + kfree(dvb); + dev->dvb = NULL; + return; +} + +static void cx8800_ts_resume_dev(struct cx8800_dev *dev) +{ + /* Called with dev->slock held */ + cx8800_restart_ts_queue(dev->dvb); +} + +static int cx8800_ts_attach_dev(struct cx8800_dev *dev) +{ + struct cx8800_dvb *dvb; + int result; + + /* Take DVB hardware out of reset */ + cx_set(MO_GP0_IO, cx88_boards[dev->board].ts.gpio0); + cx_clear(MO_GP0_IO, cx88_boards[dev->board].ts.gpio0 & 0xff); + udelay(500); + cx_set(MO_GP0_IO, cx88_boards[dev->board].ts.gpio0); + + /* Allocate a DVB structure */ + dvb = kmalloc(sizeof(struct cx8800_dvb), GFP_KERNEL); + if (dvb == NULL) { + result = -ENOMEM; + goto fail; + } + memset(dvb, 0, sizeof(struct cx8800_dvb)); + + /* Record our device and details */ + dvb->dev = dev; + dvb->irq_handler = cx8800_ts_irq; + dvb->release_dev = cx8800_ts_release_dev; + dvb->resume_dev = cx8800_ts_resume_dev; + + /* init TS dma queues */ + INIT_LIST_HEAD(&dvb->tsq.active); + INIT_LIST_HEAD(&dvb->tsq.queued); + dvb->tsq.timeout.function = cx8800_ts_timeout; + dvb->tsq.timeout.data = (unsigned long) dvb; + init_timer(&dvb->tsq.timeout); + cx88_risc_stopper(dev->pci, &dvb->tsq.stopper, + MO_TS_DMACNTRL, 0x11, 0x00); + + /* init TS feed spinlock */ + dvb->feedlock = SPIN_LOCK_UNLOCKED; + + /* Clear any pending interrupts */ + cx8800_stop_ts_dma(dvb); + + if ((result = + dvb_register_adapter(&dvb->dvb_adapter, dev->name, + THIS_MODULE)) < 0) { + printk(KERN_WARNING + "%s: dvb_register_adapter failed (errno = %d)\n", + dev->name, result); + goto fail; + } + + init_MUTEX(&dvb->dvb_i2c_lock); + + if (! dvb_register_i2c_bus(master_xfer, dvb, dvb->dvb_adapter, 0)) { + printk(KERN_WARNING "%s: dvb_register_i2c_bus failed\n", + dev->name); + result = -EFAULT; + goto fail2; + } + + memset(&dvb->demux, 0, sizeof(struct dvb_demux)); + + dvb->demux.dmx.capabilities = + DMX_TS_FILTERING | DMX_SECTION_FILTERING | + DMX_MEMORY_BASED_FILTERING; + + dvb->demux.priv = dvb; + dvb->demux.filternum = 256; + dvb->demux.feednum = 256; + dvb->demux.start_feed = dvb_cx8800_start_feed; + dvb->demux.stop_feed = dvb_cx8800_stop_feed; + dvb->demux.write_to_decoder = NULL; + + if ((result = dvb_dmx_init(&dvb->demux)) < 0) { + printk(KERN_WARNING "%s: dvb_dmx_init failed (errno = %d)\n", + dev->name, result); + goto fail3; + } + + dvb->dmxdev.filternum = 256; + dvb->dmxdev.demux = &dvb->demux.dmx; + dvb->dmxdev.capabilities = 0; + + if ((result = dvb_dmxdev_init(&dvb->dmxdev, dvb->dvb_adapter)) < 0) { + printk(KERN_WARNING "%s: dvb_dmxdev_init failed (errno = %d)\n", + dev->name, result); + goto fail4; + } + + dvb->fe_hw.source = DMX_FRONTEND_0; + + if ((result = + dvb->demux.dmx.add_frontend(&dvb->demux.dmx, &dvb->fe_hw)) < 0) { + printk(KERN_WARNING "%s: dvb_dmx_init failed (errno = %d)\n", + dev->name, result); + goto fail5; + } + + dvb->fe_mem.source = DMX_MEMORY_FE; + + if ((result = + dvb->demux.dmx.add_frontend(&dvb->demux.dmx, &dvb->fe_mem)) < 0) { + printk(KERN_WARNING "%s: dvb_dmx_init failed (errno = %d)\n", + dev->name, result); + goto fail6; + } + + if ((result = + dvb->demux.dmx.connect_frontend(&dvb->demux.dmx, + &dvb->fe_hw)) < 0) { + printk(KERN_WARNING "%s: dvb_dmx_init failed (errno = %d)\n", + dev->name, result); + goto fail7; + } + + dvb_net_init(dvb->dvb_adapter, &dvb->dvbnet, &dvb->demux.dmx); + + dev->dvb = dvb; + printk(KERN_INFO "DVB attached to dev %p, dvb: %p\n", dev, dvb); + + return 0; + +fail7: + dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_mem); +fail6: + dvb->demux.dmx.remove_frontend(&dvb->demux.dmx, &dvb->fe_hw); +fail5: + dvb_dmxdev_release(&dvb->dmxdev); +fail4: + dvb_dmx_release(&dvb->demux); +fail3: + dvb_unregister_i2c_bus(master_xfer, dvb->dvb_adapter, 0); +fail2: + dvb_unregister_adapter(dvb->dvb_adapter); +fail: + return result; +} + +#endif diff --git a/linux/drivers/media/video/cx88/cx88-mpeg.c b/linux/drivers/media/video/cx88/cx88-mpeg.c index eca7b012a..d05e925c4 100644 --- a/linux/drivers/media/video/cx88/cx88-mpeg.c +++ b/linux/drivers/media/video/cx88/cx88-mpeg.c @@ -1,5 +1,5 @@ /* - * $Id: cx88-mpeg.c,v 1.2 2004/07/30 11:14:05 kraxel Exp $ + * $Id: cx88-mpeg.c,v 1.3 2004/07/30 13:43:39 kraxel Exp $ * * Support for the mpeg transport stream transfers * PCI function #2 of the cx2388x. @@ -36,7 +36,7 @@ /* ------------------------------------------------------------------ */ -MODULE_DESCRIPTION("mpeg driver module for cx2388x based TV cards"); +MODULE_DESCRIPTION("mpeg driver for cx2388x based TV cards"); MODULE_AUTHOR("Jelle Foks <jelle@foks.8m.com>"); MODULE_AUTHOR("Gerd Knorr <kraxel@bytesex.org> [SuSE Labs]"); MODULE_LICENSE("GPL"); @@ -52,7 +52,7 @@ MODULE_PARM_DESC(mpeg_debug,"enable debug messages [mpeg]"); #define dprintk(level,fmt, arg...) if (mpeg_debug >= level) \ printk(KERN_DEBUG "%s/2: " fmt, dev->core->name , ## arg) -static LIST_HEAD(cx8802_devlist); +LIST_HEAD(cx8802_devlist); /* ------------------------------------------------------------------ */ @@ -68,21 +68,25 @@ int cx8802_start_dma(struct cx8802_dev *dev, cx88_sram_channel_setup(core, &cx88_sram_channels[SRAM_CH28], PACKET_SIZE, buf->risc.dma); - //cx_set(VID_CAPTURE_CONTROL,0x0); /* should this??? */ - /* enable capture */ +#if 0 /* from DVB -- for transport streams only? */ + /* Setup TS portion of chip */ + cx_write(TS_GEN_CNTRL, 0x0c); + + /* write TS length to chip */ + cx_write(MO_TS_LNGTH, buf->bpl); +#endif /* reset counter */ - cx_write(MO_TS_GPCNTRL,0x3); /* general purpose counter for risc program (?) */ + cx_write(MO_TS_GPCNTRL, GP_COUNT_CONTROL_RESET); q->count = 1; /* enable irqs */ - cx_set(MO_PCI_INTMSK, 0x4); /* enable ts_int */ - cx_set(MO_TS_INTMSK, 0x1f1101); /* all except the irq2 bit */ + cx_set(MO_PCI_INTMSK, 0x00fc04); + cx_set(MO_TS_INTMSK, 0x1f0011); /* start dma */ - cx_set(MO_DEV_CNTRL2, (1<<5)); /* enable the risc controller */ - cx_set(MO_TS_DMACNTRL, 0x11); /* enable TS RISC and FIFO */ - + cx_set(MO_DEV_CNTRL2, (1<<5)); + cx_set(MO_TS_DMACNTRL, 0x11); return 0; } @@ -167,7 +171,7 @@ mpeg_buf_queue(struct file *file, struct videobuf_buffer *vb) struct cx88_dmaqueue *q = &dev->mpegq; /* add jump to stopper */ - buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | 0x10000); + buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | RISC_CNT_INC); buf->risc.jmp[1] = cpu_to_le32(q->stopper.dma); if (list_empty(&q->active)) { @@ -212,186 +216,6 @@ struct videobuf_queue_ops cx8802_mpeg_qops = { .buf_release = mpeg_buf_release, }; -/* ------------------------------------------------------------------ */ - -static int mpeg_do_ioctl(struct inode *inode, struct file *file, - unsigned int cmd, void *arg) -{ - struct cx8802_fh *fh = file->private_data; - struct cx8802_dev *dev = fh->dev; - - if (mpeg_debug > 1) - cx88_print_ioctl(dev->core->name,cmd); - - switch (cmd) { - - /* --- capture ioctls ---------------------------------------- */ - case VIDIOC_ENUM_FMT: - { - struct v4l2_fmtdesc *f = arg; - int index; - - index = f->index; - if (index != 0) - return -EINVAL; - - memset(f,0,sizeof(*f)); - f->index = index; - strlcpy(f->description, "MPEG TS", sizeof(f->description)); - f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; - f->pixelformat = V4L2_PIX_FMT_MPEG; - return 0; - } - case VIDIOC_G_FMT: - case VIDIOC_S_FMT: - case VIDIOC_TRY_FMT: - { - /* FIXME -- quick'n'dirty for exactly one size ... */ - struct v4l2_format *f = arg; - - memset(f,0,sizeof(*f)); - f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; - f->fmt.pix.width = 720; - f->fmt.pix.height = 576; - f->fmt.pix.pixelformat = V4L2_PIX_FMT_MPEG; - f->fmt.pix.sizeimage = BUFFER_SIZE; - } - - /* --- streaming capture ------------------------------------- */ - case VIDIOC_REQBUFS: - return videobuf_reqbufs(file, &fh->mpegq, arg); - - case VIDIOC_QUERYBUF: - return videobuf_querybuf(&fh->mpegq, arg); - - case VIDIOC_QBUF: - return videobuf_qbuf(file, &fh->mpegq, arg); - - case VIDIOC_DQBUF: - return videobuf_dqbuf(file, &fh->mpegq, arg); - - case VIDIOC_STREAMON: - return videobuf_streamon(file, &fh->mpegq); - - case VIDIOC_STREAMOFF: - return videobuf_streamoff(file, &fh->mpegq); - - default: - return -EINVAL; - } - return 0; -} - -static int mpeg_ioctl(struct inode *inode, struct file *file, - unsigned int cmd, unsigned long arg) -{ - return video_usercopy(inode, file, cmd, arg, mpeg_do_ioctl); -} - -static int mpeg_open(struct inode *inode, struct file *file) -{ - int minor = iminor(inode); - struct cx8802_dev *h,*dev = NULL; - struct cx8802_fh *fh; - struct list_head *list; - - list_for_each(list,&cx8802_devlist) { - h = list_entry(list, struct cx8802_dev, devlist); - if (h->mpeg_dev->minor == minor) - dev = h; - } - if (NULL == dev) - return -ENODEV; - -#if 0 /* FIXME */ - if (mpegport_initialize_codec(dev) < 0) - return -EINVAL; -#endif - - dprintk(1,"open minor=%d\n",minor); - - /* allocate + initialize per filehandle data */ - fh = kmalloc(sizeof(*fh),GFP_KERNEL); - if (NULL == fh) - return -ENOMEM; - memset(fh,0,sizeof(*fh)); - file->private_data = fh; - fh->dev = dev; - - videobuf_queue_init(&fh->mpegq, &cx8802_mpeg_qops, - dev->pci, &dev->slock, - V4L2_BUF_TYPE_VIDEO_CAPTURE, - V4L2_FIELD_TOP, - sizeof(struct cx88_buffer)); - init_MUTEX(&fh->mpegq.lock); - - return 0; -} - -static int mpeg_release(struct inode *inode, struct file *file) -{ - struct cx8802_fh *fh = file->private_data; - -#if 0 /* FIXME */ - mpegport_api_cmd(fh->dev, IVTV_API_END_CAPTURE, 3, 0, 1, 0, 0x13); -#endif - - /* stop mpeg capture */ - if (fh->mpegq.streaming) - videobuf_streamoff(file,&fh->mpegq); - if (fh->mpegq.reading) - videobuf_read_stop(file,&fh->mpegq); - - file->private_data = NULL; - kfree(fh); - return 0; -} - -static ssize_t -mpeg_read(struct file *file, char *data, size_t count, loff_t *ppos) -{ - struct cx8802_fh *fh = file->private_data; - - return videobuf_read_stream(file, &fh->mpegq, data, count, ppos, 0); -} - -static unsigned int -mpeg_poll(struct file *file, struct poll_table_struct *wait) -{ - struct cx8802_fh *fh = file->private_data; - - return videobuf_poll_stream(file, &fh->mpegq, wait); -} - -static int -mpeg_mmap(struct file *file, struct vm_area_struct * vma) -{ - struct cx8802_fh *fh = file->private_data; - - return videobuf_mmap_mapper(vma, &fh->mpegq); -} - -static struct file_operations mpeg_fops = -{ - .owner = THIS_MODULE, - .open = mpeg_open, - .release = mpeg_release, - .read = mpeg_read, - .poll = mpeg_poll, - .mmap = mpeg_mmap, - .ioctl = mpeg_ioctl, - .llseek = no_llseek, -}; - -static struct video_device cx8802_mpeg_template = -{ - .name = "cx8802", - .type = VID_TYPE_CAPTURE|VID_TYPE_TUNER|VID_TYPE_SCALES|VID_TYPE_MPEG_ENCODER, - .hardware = 0, - .fops = &mpeg_fops, - .minor = -1, -}; - /* ----------------------------------------------------------- */ /* exported stuff */ @@ -496,17 +320,6 @@ static irqreturn_t cx8802_irq(int irq, void *dev_id, struct pt_regs *regs) /* ----------------------------------------------------------- */ -static void cx8802_unregister_video(struct cx8802_dev *dev) -{ - if (dev->mpeg_dev) { - if (-1 != dev->mpeg_dev->minor) - video_unregister_device(dev->mpeg_dev); - else - video_device_release(dev->mpeg_dev); - dev->mpeg_dev = NULL; - } -} - static int __devinit cx8802_initdev(struct pci_dev *pci_dev, const struct pci_device_id *pci_id) { @@ -551,11 +364,11 @@ static int __devinit cx8802_initdev(struct pci_dev *pci_dev, if (cx88_boards[core->board].blackbird) { printk("%s/2: cx23416 based mpeg encoder (blackbird design)\n", core->name); - /* todo */ + /* todo: register v4l device, init cx23416 encoder */ } else if (cx88_boards[core->board].dvb) { printk("%s/2: has DVB support\n", core->name); - /* todo */ + /* todo: register dvb device */ } else { printk("%s/2: don't what the mpeg port on this card is used for\n" "%s/2: going to ignore it, sorry\n", @@ -596,17 +409,6 @@ static int __devinit cx8802_initdev(struct pci_dev *pci_dev, cx88_card_setup(dev); #endif - /* register v4l devices */ - dev->mpeg_dev = cx88_vdev_init(core,dev->pci,&cx8802_mpeg_template,"mpeg"); - err = video_register_device(dev->mpeg_dev,VFL_TYPE_GRABBER, -1); - if (err < 0) { - printk(KERN_INFO "%s/2: can't register mpeg device\n", - core->name); - return err; - } - printk(KERN_INFO "%s/2: registered device video%d [mpeg]\n", - core->name,dev->mpeg_dev->minor & 0x1f); - /* everything worked */ list_add_tail(&dev->devlist,&cx8802_devlist); pci_set_drvdata(pci_dev,dev); @@ -630,7 +432,6 @@ static void __devexit cx8802_finidev(struct pci_dev *pci_dev) /* unregister stuff */ free_irq(pci_dev->irq, dev); - cx8802_unregister_video(dev); pci_set_drvdata(pci_dev, NULL); /* free memory */ diff --git a/linux/drivers/media/video/cx88/cx88-tvaudio.c b/linux/drivers/media/video/cx88/cx88-tvaudio.c index 0810b9ede..a4abb2d49 100644 --- a/linux/drivers/media/video/cx88/cx88-tvaudio.c +++ b/linux/drivers/media/video/cx88/cx88-tvaudio.c @@ -803,8 +803,7 @@ int cx88_audio_thread(void *data) dprintk("cx88: tvaudio thread started\n"); for (;;) { - set_current_state(TASK_INTERRUPTIBLE); - schedule_timeout(HZ*3); + msleep(1000); if (signal_pending(current)) break; if (dev->shutdown) diff --git a/linux/drivers/media/video/cx88/cx88-vbi.c b/linux/drivers/media/video/cx88/cx88-vbi.c index cdd6953fb..23fd96b83 100644 --- a/linux/drivers/media/video/cx88/cx88-vbi.c +++ b/linux/drivers/media/video/cx88/cx88-vbi.c @@ -57,7 +57,7 @@ int cx8800_start_vbi_dma(struct cx8800_dev *dev, (1 << 11) )); /* reset counter */ - cx_write(MO_VBI_GPCNTRL,0x3); + cx_write(MO_VBI_GPCNTRL, GP_COUNT_CONTROL_RESET); q->count = 1; /* enable irqs */ @@ -182,7 +182,7 @@ vbi_queue(struct file *file, struct videobuf_buffer *vb) struct cx88_dmaqueue *q = &dev->vbiq; /* add jump to stopper */ - buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | 0x10000); + buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | RISC_CNT_INC); buf->risc.jmp[1] = cpu_to_le32(q->stopper.dma); if (list_empty(&q->active)) { diff --git a/linux/drivers/media/video/cx88/cx88-video.c b/linux/drivers/media/video/cx88/cx88-video.c index 120f0db62..fe87431a6 100644 --- a/linux/drivers/media/video/cx88/cx88-video.c +++ b/linux/drivers/media/video/cx88/cx88-video.c @@ -1,5 +1,5 @@ /* - * $Id: cx88-video.c,v 1.30 2004/07/30 11:14:05 kraxel Exp $ + * $Id: cx88-video.c,v 1.31 2004/07/30 13:43:39 kraxel Exp $ * * device driver for Conexant 2388x based TV cards * video4linux video interface @@ -466,8 +466,7 @@ static int set_pll(struct cx8800_dev *dev, int prescale, u32 ofreq) return 0; } dprintk(1,"pll not locked yet, waiting ...\n"); - set_current_state(TASK_INTERRUPTIBLE); - schedule_timeout(HZ/10); + msleep(100); } dprintk(1,"pll NOT locked [pre=%d,ofreq=%d]\n",prescale,ofreq); return -1; @@ -735,7 +734,7 @@ static int start_video_dma(struct cx8800_dev *dev, cx_write(MO_COLOR_CTRL, buf->fmt->cxformat | ColorFormatGamma); /* reset counter */ - cx_write(MO_VIDY_GPCNTRL,0x3); + cx_write(MO_VIDY_GPCNTRL,GP_COUNT_CONTROL_RESET); q->count = 1; /* enable irqs */ @@ -912,7 +911,7 @@ buffer_queue(struct file *file, struct videobuf_buffer *vb) struct cx88_dmaqueue *q = &dev->vidq; /* add jump to stopper */ - buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | 0x10000); + buf->risc.jmp[0] = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | RISC_CNT_INC); buf->risc.jmp[1] = cpu_to_le32(q->stopper.dma); if (!list_empty(&q->queued)) { diff --git a/linux/drivers/media/video/cx88/cx88.h b/linux/drivers/media/video/cx88/cx88.h index 36a9edacf..3502d378a 100644 --- a/linux/drivers/media/video/cx88/cx88.h +++ b/linux/drivers/media/video/cx88/cx88.h @@ -1,5 +1,5 @@ /* - * $Id: cx88.h,v 1.22 2004/07/30 11:14:05 kraxel Exp $ + * $Id: cx88.h,v 1.23 2004/07/30 13:43:39 kraxel Exp $ * * v4l2 device driver for cx2388x based TV cards * @@ -36,16 +36,7 @@ #include <media/tuner.h> #include <media/audiochip.h> #endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,23) -# define irqreturn_t void -# define IRQ_RETVAL(foobar) -#endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,71) -# define strlcpy(dest,src,len) strncpy(dest,src,(len)-1) -#endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0) -# define iminor(inode) minor(inode->i_rdev) -#endif +#include "compat.h" #include "btcx-risc.h" #include "cx88-reg.h" @@ -468,6 +459,12 @@ void cx88_get_stereo(struct cx8800_dev *dev, struct v4l2_tuner *t); void cx88_set_stereo(struct cx8800_dev *dev, u32 mode); int cx88_audio_thread(void *data); +/* ----------------------------------------------------------- */ +/* cx88-mpeg.c */ + +extern struct list_head cx8802_devlist; +extern struct videobuf_queue_ops cx8802_mpeg_qops; + /* * Local variables: * c-basic-offset: 8 diff --git a/linux/drivers/media/video/saa6752hs.c b/linux/drivers/media/video/saa6752hs.c index a60588e2d..8478a3d25 100644 --- a/linux/drivers/media/video/saa6752hs.c +++ b/linux/drivers/media/video/saa6752hs.c @@ -20,9 +20,7 @@ #include <media/id.h> #include <media/saa6752hs.h> #endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,71) -# define strlcpy(dest,src,len) strncpy(dest,src,(len)-1) -#endif +#include "compat.h" /* Addresses to scan */ static unsigned short normal_i2c[] = {0x20, I2C_CLIENT_END}; diff --git a/linux/drivers/media/video/saa7134/saa6752hs.c b/linux/drivers/media/video/saa7134/saa6752hs.c index a60588e2d..8478a3d25 100644 --- a/linux/drivers/media/video/saa7134/saa6752hs.c +++ b/linux/drivers/media/video/saa7134/saa6752hs.c @@ -20,9 +20,7 @@ #include <media/id.h> #include <media/saa6752hs.h> #endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,71) -# define strlcpy(dest,src,len) strncpy(dest,src,(len)-1) -#endif +#include "compat.h" /* Addresses to scan */ static unsigned short normal_i2c[] = {0x20, I2C_CLIENT_END}; diff --git a/linux/drivers/media/video/saa7134/saa7134.h b/linux/drivers/media/video/saa7134/saa7134.h index 2e21f216d..873977a59 100644 --- a/linux/drivers/media/video/saa7134/saa7134.h +++ b/linux/drivers/media/video/saa7134/saa7134.h @@ -43,16 +43,7 @@ #include <media/id.h> #include <media/ir-common.h> #endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,23) -# define irqreturn_t void -# define IRQ_RETVAL(foobar) -#endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,71) -# define strlcpy(dest,src,len) strncpy(dest,src,(len)-1) -#endif -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,0) -# define iminor(inode) minor(inode->i_rdev) -#endif +#include "compat.h" #ifndef TRUE # define TRUE (1==1) diff --git a/linux/include/media/id.h b/linux/include/media/id.h index af202e7d4..1b0320dc8 100644 --- a/linux/include/media/id.h +++ b/linux/include/media/id.h @@ -35,8 +35,3 @@ #ifndef I2C_ALGO_SAA7134 # define I2C_ALGO_SAA7134 0x090000 #endif - -/* kernel compatibility */ -#if defined(I2C_ADAP_CLASS_TV_ANALOG) && !defined(I2C_CLASS_TV_ANALOG) -# define I2C_CLASS_TV_ANALOG I2C_ADAP_CLASS_TV_ANALOG -#endif |