diff options
author | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-10-11 22:09:32 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-10-11 22:09:32 -0400 |
commit | c634920abaf9c0a93266a57beff6fce9d3852cb2 (patch) | |
tree | 5ac85f54905a8cd3b12b262c66189084cbff54fc /drivers/media/video/cx88/cx88-mpeg.c | |
parent | 6abd2c860e34add677de50e8b134f5af6f4b0893 (diff) | |
parent | a991f44b79fa49b281eb078eed4a76a42101012a (diff) |
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/v4l-dvb
* 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/v4l-dvb: (310 commits)
V4L/DVB (6316): Change list_for_each+list_entry to list_for_each_entry
V4L/DVB (6315): pvrusb2: Change list_for_each+list_entry to list_for_each_entry
V4L/DVB (6314): saa7134: Replace list_for_each+list_entry with list_for_each_entry
V4L/DVB (6313): ivtv: Replace list_for_each+list_entry with list_for_each_entry
V4L/DVB (6312): cx88: Replace list_for_each+list_entry with list_for_each_entry
V4L/DVB (6311): dvb: Replace list_for_each+list_entry with list_for_each_entry
V4L/DVB (6308): V4L: zc0301, remove bad usage of ERESTARTSYS
V4L/DVB (6307): V4L: w9968cf, remove bad usage of ERESTARTSYS
V4L/DVB (6306): Few clenups for saa7134 resume code
V4L/DVB (6305): V4L: videobuf-core.c avoid NULL dereferences in videobuf-core
V4L/DVB (6301): pvrusb: Update DEBUGIFC sysfs to kernel 2.6.13+
V4L/DVB (6300): CodingStyle cleanup
V4L/DVB (6299): dvb: Add dependencies for VIDEOBUF_DVB
V4L/DVB (6297): cx23885: remove wrong Kconfig selection of VIDEOBUF
V4L/DVB (6296): dib0700: add support for AverMedia DVB-T Express card
V4L/DVB (6295): saa7134: add autodetection for KWorld ATSC-115
V4L/DVB (6293): V4L: convert struct class_device to struct device
V4L/DVB (6292): videobuf_core init always require callback implementation
V4L/DVB (6291): Fix: avoid oops on some SMP machines
V4L/DVB (6290): remove videobuf_set_pci_ops
...
Diffstat (limited to 'drivers/media/video/cx88/cx88-mpeg.c')
-rw-r--r-- | drivers/media/video/cx88/cx88-mpeg.c | 142 |
1 files changed, 75 insertions, 67 deletions
diff --git a/drivers/media/video/cx88/cx88-mpeg.c b/drivers/media/video/cx88/cx88-mpeg.c index da7a6b591a67..a652f294d23d 100644 --- a/drivers/media/video/cx88/cx88-mpeg.c +++ b/drivers/media/video/cx88/cx88-mpeg.c | |||
@@ -23,12 +23,10 @@ | |||
23 | */ | 23 | */ |
24 | 24 | ||
25 | #include <linux/module.h> | 25 | #include <linux/module.h> |
26 | #include <linux/moduleparam.h> | ||
27 | #include <linux/init.h> | 26 | #include <linux/init.h> |
28 | #include <linux/device.h> | 27 | #include <linux/device.h> |
29 | #include <linux/dma-mapping.h> | 28 | #include <linux/dma-mapping.h> |
30 | #include <linux/interrupt.h> | 29 | #include <linux/interrupt.h> |
31 | #include <linux/dma-mapping.h> | ||
32 | #include <asm/delay.h> | 30 | #include <asm/delay.h> |
33 | 31 | ||
34 | #include "cx88.h" | 32 | #include "cx88.h" |
@@ -56,9 +54,9 @@ static void request_module_async(struct work_struct *work) | |||
56 | { | 54 | { |
57 | struct cx8802_dev *dev=container_of(work, struct cx8802_dev, request_module_wk); | 55 | struct cx8802_dev *dev=container_of(work, struct cx8802_dev, request_module_wk); |
58 | 56 | ||
59 | if (cx88_boards[dev->core->board].mpeg & CX88_MPEG_DVB) | 57 | if (dev->core->board.mpeg & CX88_MPEG_DVB) |
60 | request_module("cx88-dvb"); | 58 | request_module("cx88-dvb"); |
61 | if (cx88_boards[dev->core->board].mpeg & CX88_MPEG_BLACKBIRD) | 59 | if (dev->core->board.mpeg & CX88_MPEG_BLACKBIRD) |
62 | request_module("cx88-blackbird"); | 60 | request_module("cx88-blackbird"); |
63 | } | 61 | } |
64 | 62 | ||
@@ -96,7 +94,7 @@ static int cx8802_start_dma(struct cx8802_dev *dev, | |||
96 | dprintk( 1, "core->active_type_id = 0x%08x\n", core->active_type_id); | 94 | dprintk( 1, "core->active_type_id = 0x%08x\n", core->active_type_id); |
97 | 95 | ||
98 | if ( (core->active_type_id == CX88_MPEG_DVB) && | 96 | if ( (core->active_type_id == CX88_MPEG_DVB) && |
99 | (cx88_boards[core->board].mpeg & CX88_MPEG_DVB) ) { | 97 | (core->board.mpeg & CX88_MPEG_DVB) ) { |
100 | 98 | ||
101 | dprintk( 1, "cx8802_start_dma doing .dvb\n"); | 99 | dprintk( 1, "cx8802_start_dma doing .dvb\n"); |
102 | /* negedge driven & software reset */ | 100 | /* negedge driven & software reset */ |
@@ -104,7 +102,7 @@ static int cx8802_start_dma(struct cx8802_dev *dev, | |||
104 | udelay(100); | 102 | udelay(100); |
105 | cx_write(MO_PINMUX_IO, 0x00); | 103 | cx_write(MO_PINMUX_IO, 0x00); |
106 | cx_write(TS_HW_SOP_CNTRL,0x47<<16|188<<4|0x01); | 104 | cx_write(TS_HW_SOP_CNTRL,0x47<<16|188<<4|0x01); |
107 | switch (core->board) { | 105 | switch (core->boardnr) { |
108 | case CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q: | 106 | case CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q: |
109 | case CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_T: | 107 | case CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_T: |
110 | case CX88_BOARD_DVICO_FUSIONHDTV_5_GOLD: | 108 | case CX88_BOARD_DVICO_FUSIONHDTV_5_GOLD: |
@@ -125,7 +123,7 @@ static int cx8802_start_dma(struct cx8802_dev *dev, | |||
125 | cx_write(TS_GEN_CNTRL, dev->ts_gen_cntrl); | 123 | cx_write(TS_GEN_CNTRL, dev->ts_gen_cntrl); |
126 | udelay(100); | 124 | udelay(100); |
127 | } else if ( (core->active_type_id == CX88_MPEG_BLACKBIRD) && | 125 | } else if ( (core->active_type_id == CX88_MPEG_BLACKBIRD) && |
128 | (cx88_boards[core->board].mpeg & CX88_MPEG_BLACKBIRD) ) { | 126 | (core->board.mpeg & CX88_MPEG_BLACKBIRD) ) { |
129 | dprintk( 1, "cx8802_start_dma doing .blackbird\n"); | 127 | dprintk( 1, "cx8802_start_dma doing .blackbird\n"); |
130 | cx_write(MO_PINMUX_IO, 0x88); /* enable MPEG parallel IO */ | 128 | cx_write(MO_PINMUX_IO, 0x88); /* enable MPEG parallel IO */ |
131 | 129 | ||
@@ -139,7 +137,7 @@ static int cx8802_start_dma(struct cx8802_dev *dev, | |||
139 | udelay(100); | 137 | udelay(100); |
140 | } else { | 138 | } else { |
141 | printk( "%s() Failed. Unsupported value in .mpeg (0x%08x)\n", __FUNCTION__, | 139 | printk( "%s() Failed. Unsupported value in .mpeg (0x%08x)\n", __FUNCTION__, |
142 | cx88_boards[core->board].mpeg ); | 140 | core->board.mpeg ); |
143 | return -EINVAL; | 141 | return -EINVAL; |
144 | } | 142 | } |
145 | 143 | ||
@@ -149,7 +147,7 @@ static int cx8802_start_dma(struct cx8802_dev *dev, | |||
149 | 147 | ||
150 | /* enable irqs */ | 148 | /* enable irqs */ |
151 | dprintk( 1, "setting the interrupt mask\n" ); | 149 | dprintk( 1, "setting the interrupt mask\n" ); |
152 | cx_set(MO_PCI_INTMSK, core->pci_irqmask | 0x04); | 150 | cx_set(MO_PCI_INTMSK, core->pci_irqmask | PCI_INT_TSINT); |
153 | cx_set(MO_TS_INTMSK, 0x1f0011); | 151 | cx_set(MO_TS_INTMSK, 0x1f0011); |
154 | 152 | ||
155 | /* start dma */ | 153 | /* start dma */ |
@@ -167,7 +165,7 @@ static int cx8802_stop_dma(struct cx8802_dev *dev) | |||
167 | cx_clear(MO_TS_DMACNTRL, 0x11); | 165 | cx_clear(MO_TS_DMACNTRL, 0x11); |
168 | 166 | ||
169 | /* disable irqs */ | 167 | /* disable irqs */ |
170 | cx_clear(MO_PCI_INTMSK, 0x000004); | 168 | cx_clear(MO_PCI_INTMSK, PCI_INT_TSINT); |
171 | cx_clear(MO_TS_INTMSK, 0x1f0011); | 169 | cx_clear(MO_TS_INTMSK, 0x1f0011); |
172 | 170 | ||
173 | /* Reset the controller */ | 171 | /* Reset the controller */ |
@@ -181,43 +179,43 @@ static int cx8802_restart_queue(struct cx8802_dev *dev, | |||
181 | struct cx88_buffer *buf; | 179 | struct cx88_buffer *buf; |
182 | struct list_head *item; | 180 | struct list_head *item; |
183 | 181 | ||
184 | dprintk( 1, "cx8802_restart_queue\n" ); | 182 | dprintk( 1, "cx8802_restart_queue\n" ); |
185 | if (list_empty(&q->active)) | 183 | if (list_empty(&q->active)) |
186 | { | 184 | { |
187 | struct cx88_buffer *prev; | 185 | struct cx88_buffer *prev; |
188 | prev = NULL; | 186 | prev = NULL; |
189 | 187 | ||
190 | dprintk(1, "cx8802_restart_queue: queue is empty\n" ); | 188 | dprintk(1, "cx8802_restart_queue: queue is empty\n" ); |
191 | 189 | ||
192 | for (;;) { | 190 | for (;;) { |
193 | if (list_empty(&q->queued)) | 191 | if (list_empty(&q->queued)) |
194 | return 0; | 192 | return 0; |
195 | buf = list_entry(q->queued.next, struct cx88_buffer, vb.queue); | 193 | buf = list_entry(q->queued.next, struct cx88_buffer, vb.queue); |
196 | if (NULL == prev) { | 194 | if (NULL == prev) { |
197 | list_del(&buf->vb.queue); | 195 | list_del(&buf->vb.queue); |
198 | list_add_tail(&buf->vb.queue,&q->active); | 196 | list_add_tail(&buf->vb.queue,&q->active); |
199 | cx8802_start_dma(dev, q, buf); | 197 | cx8802_start_dma(dev, q, buf); |
200 | buf->vb.state = STATE_ACTIVE; | 198 | buf->vb.state = STATE_ACTIVE; |
201 | buf->count = q->count++; | 199 | buf->count = q->count++; |
202 | mod_timer(&q->timeout, jiffies+BUFFER_TIMEOUT); | 200 | mod_timer(&q->timeout, jiffies+BUFFER_TIMEOUT); |
203 | dprintk(1,"[%p/%d] restart_queue - first active\n", | 201 | dprintk(1,"[%p/%d] restart_queue - first active\n", |
204 | buf,buf->vb.i); | 202 | buf,buf->vb.i); |
205 | 203 | ||
206 | } else if (prev->vb.width == buf->vb.width && | 204 | } else if (prev->vb.width == buf->vb.width && |
207 | prev->vb.height == buf->vb.height && | 205 | prev->vb.height == buf->vb.height && |
208 | prev->fmt == buf->fmt) { | 206 | prev->fmt == buf->fmt) { |
209 | list_del(&buf->vb.queue); | 207 | list_del(&buf->vb.queue); |
210 | list_add_tail(&buf->vb.queue,&q->active); | 208 | list_add_tail(&buf->vb.queue,&q->active); |
211 | buf->vb.state = STATE_ACTIVE; | 209 | buf->vb.state = STATE_ACTIVE; |
212 | buf->count = q->count++; | 210 | buf->count = q->count++; |
213 | prev->risc.jmp[1] = cpu_to_le32(buf->risc.dma); | 211 | prev->risc.jmp[1] = cpu_to_le32(buf->risc.dma); |
214 | dprintk(1,"[%p/%d] restart_queue - move to active\n", | 212 | dprintk(1,"[%p/%d] restart_queue - move to active\n", |
215 | buf,buf->vb.i); | 213 | buf,buf->vb.i); |
216 | } else { | 214 | } else { |
217 | return 0; | 215 | return 0; |
218 | } | 216 | } |
219 | prev = buf; | 217 | prev = buf; |
220 | } | 218 | } |
221 | return 0; | 219 | return 0; |
222 | } | 220 | } |
223 | 221 | ||
@@ -239,6 +237,7 @@ int cx8802_buf_prepare(struct videobuf_queue *q, struct cx8802_dev *dev, | |||
239 | struct cx88_buffer *buf, enum v4l2_field field) | 237 | struct cx88_buffer *buf, enum v4l2_field field) |
240 | { | 238 | { |
241 | int size = dev->ts_packet_size * dev->ts_packet_count; | 239 | int size = dev->ts_packet_size * dev->ts_packet_count; |
240 | struct videobuf_dmabuf *dma=videobuf_to_dma(&buf->vb); | ||
242 | int rc; | 241 | int rc; |
243 | 242 | ||
244 | dprintk(1, "%s: %p\n", __FUNCTION__, buf); | 243 | dprintk(1, "%s: %p\n", __FUNCTION__, buf); |
@@ -254,8 +253,8 @@ int cx8802_buf_prepare(struct videobuf_queue *q, struct cx8802_dev *dev, | |||
254 | if (0 != (rc = videobuf_iolock(q,&buf->vb,NULL))) | 253 | if (0 != (rc = videobuf_iolock(q,&buf->vb,NULL))) |
255 | goto fail; | 254 | goto fail; |
256 | cx88_risc_databuffer(dev->pci, &buf->risc, | 255 | cx88_risc_databuffer(dev->pci, &buf->risc, |
257 | buf->vb.dma.sglist, | 256 | dma->sglist, |
258 | buf->vb.width, buf->vb.height); | 257 | buf->vb.width, buf->vb.height, 0); |
259 | } | 258 | } |
260 | buf->vb.state = STATE_PREPARED; | 259 | buf->vb.state = STATE_PREPARED; |
261 | return 0; | 260 | return 0; |
@@ -414,7 +413,8 @@ static irqreturn_t cx8802_irq(int irq, void *dev_id) | |||
414 | int loop, handled = 0; | 413 | int loop, handled = 0; |
415 | 414 | ||
416 | for (loop = 0; loop < MAX_IRQ_LOOP; loop++) { | 415 | for (loop = 0; loop < MAX_IRQ_LOOP; loop++) { |
417 | status = cx_read(MO_PCI_INTSTAT) & (core->pci_irqmask | 0x04); | 416 | status = cx_read(MO_PCI_INTSTAT) & |
417 | (core->pci_irqmask | PCI_INT_TSINT); | ||
418 | if (0 == status) | 418 | if (0 == status) |
419 | goto out; | 419 | goto out; |
420 | dprintk( 1, "cx8802_irq\n" ); | 420 | dprintk( 1, "cx8802_irq\n" ); |
@@ -425,7 +425,7 @@ static irqreturn_t cx8802_irq(int irq, void *dev_id) | |||
425 | 425 | ||
426 | if (status & core->pci_irqmask) | 426 | if (status & core->pci_irqmask) |
427 | cx88_core_irq(core,status); | 427 | cx88_core_irq(core,status); |
428 | if (status & 0x04) | 428 | if (status & PCI_INT_TSINT) |
429 | cx8802_mpeg_irq(dev); | 429 | cx8802_mpeg_irq(dev); |
430 | }; | 430 | }; |
431 | if (MAX_IRQ_LOOP == loop) { | 431 | if (MAX_IRQ_LOOP == loop) { |
@@ -676,22 +676,24 @@ int cx8802_register_driver(struct cx8802_driver *drv) | |||
676 | struct list_head *list; | 676 | struct list_head *list; |
677 | int err = 0, i = 0; | 677 | int err = 0, i = 0; |
678 | 678 | ||
679 | printk(KERN_INFO "%s() ->registering driver type=%s access=%s\n", __FUNCTION__ , | 679 | printk(KERN_INFO |
680 | drv->type_id == CX88_MPEG_DVB ? "dvb" : "blackbird", | 680 | "cx88/2: registering cx8802 driver, type: %s access: %s\n", |
681 | drv->hw_access == CX8802_DRVCTL_SHARED ? "shared" : "exclusive"); | 681 | drv->type_id == CX88_MPEG_DVB ? "dvb" : "blackbird", |
682 | drv->hw_access == CX8802_DRVCTL_SHARED ? "shared" : "exclusive"); | ||
682 | 683 | ||
683 | if ((err = cx8802_check_driver(drv)) != 0) { | 684 | if ((err = cx8802_check_driver(drv)) != 0) { |
684 | printk(KERN_INFO "%s() cx8802_driver is invalid\n", __FUNCTION__ ); | 685 | printk(KERN_ERR "cx88/2: cx8802_driver is invalid\n"); |
685 | return err; | 686 | return err; |
686 | } | 687 | } |
687 | 688 | ||
688 | list_for_each(list,&cx8802_devlist) { | 689 | list_for_each(list,&cx8802_devlist) { |
689 | h = list_entry(list, struct cx8802_dev, devlist); | 690 | h = list_entry(list, struct cx8802_dev, devlist); |
690 | 691 | ||
691 | printk(KERN_INFO "CORE %s: subsystem: %04x:%04x, board: %s [card=%d]\n", | 692 | printk(KERN_INFO |
692 | h->core->name,h->pci->subsystem_vendor, | 693 | "%s/2: subsystem: %04x:%04x, board: %s [card=%d]\n", |
693 | h->pci->subsystem_device,cx88_boards[h->core->board].name, | 694 | h->core->name, h->pci->subsystem_vendor, |
694 | h->core->board); | 695 | h->pci->subsystem_device, h->core->board.name, |
696 | h->core->boardnr); | ||
695 | 697 | ||
696 | /* Bring up a new struct for each driver instance */ | 698 | /* Bring up a new struct for each driver instance */ |
697 | driver = kzalloc(sizeof(*drv),GFP_KERNEL); | 699 | driver = kzalloc(sizeof(*drv),GFP_KERNEL); |
@@ -713,7 +715,9 @@ int cx8802_register_driver(struct cx8802_driver *drv) | |||
713 | list_add_tail(&driver->devlist,&h->drvlist.devlist); | 715 | list_add_tail(&driver->devlist,&h->drvlist.devlist); |
714 | mutex_unlock(&drv->core->lock); | 716 | mutex_unlock(&drv->core->lock); |
715 | } else { | 717 | } else { |
716 | printk(KERN_ERR "%s() ->probe failed err = %d\n", __FUNCTION__, err); | 718 | printk(KERN_ERR |
719 | "%s/2: cx8802 probe failed, err = %d\n", | ||
720 | h->core->name, err); | ||
717 | } | 721 | } |
718 | 722 | ||
719 | } | 723 | } |
@@ -733,17 +737,20 @@ int cx8802_unregister_driver(struct cx8802_driver *drv) | |||
733 | struct list_head *list2, *q; | 737 | struct list_head *list2, *q; |
734 | int err = 0, i = 0; | 738 | int err = 0, i = 0; |
735 | 739 | ||
736 | printk(KERN_INFO "%s() ->unregistering driver type=%s\n", __FUNCTION__ , | 740 | printk(KERN_INFO |
737 | drv->type_id == CX88_MPEG_DVB ? "dvb" : "blackbird"); | 741 | "cx88/2: unregistering cx8802 driver, type: %s access: %s\n", |
742 | drv->type_id == CX88_MPEG_DVB ? "dvb" : "blackbird", | ||
743 | drv->hw_access == CX8802_DRVCTL_SHARED ? "shared" : "exclusive"); | ||
738 | 744 | ||
739 | list_for_each(list,&cx8802_devlist) { | 745 | list_for_each(list,&cx8802_devlist) { |
740 | i++; | 746 | i++; |
741 | h = list_entry(list, struct cx8802_dev, devlist); | 747 | h = list_entry(list, struct cx8802_dev, devlist); |
742 | 748 | ||
743 | printk(KERN_INFO "CORE %s: subsystem: %04x:%04x, board: %s [card=%d]\n", | 749 | printk(KERN_INFO |
744 | h->core->name,h->pci->subsystem_vendor, | 750 | "%s/2: subsystem: %04x:%04x, board: %s [card=%d]\n", |
745 | h->pci->subsystem_device,cx88_boards[h->core->board].name, | 751 | h->core->name, h->pci->subsystem_vendor, |
746 | h->core->board); | 752 | h->pci->subsystem_device, h->core->board.name, |
753 | h->core->boardnr); | ||
747 | 754 | ||
748 | list_for_each_safe(list2, q, &h->drvlist.devlist) { | 755 | list_for_each_safe(list2, q, &h->drvlist.devlist) { |
749 | d = list_entry(list2, struct cx8802_driver, devlist); | 756 | d = list_entry(list2, struct cx8802_driver, devlist); |
@@ -758,7 +765,8 @@ int cx8802_unregister_driver(struct cx8802_driver *drv) | |||
758 | list_del(list2); | 765 | list_del(list2); |
759 | mutex_unlock(&drv->core->lock); | 766 | mutex_unlock(&drv->core->lock); |
760 | } else | 767 | } else |
761 | printk(KERN_ERR "%s() ->remove failed err = %d\n", __FUNCTION__, err); | 768 | printk(KERN_ERR "%s/2: cx8802 driver remove " |
769 | "failed (%d)\n", h->core->name, err); | ||
762 | 770 | ||
763 | } | 771 | } |
764 | 772 | ||
@@ -783,7 +791,7 @@ static int __devinit cx8802_probe(struct pci_dev *pci_dev, | |||
783 | printk("%s/2: cx2388x 8802 Driver Manager\n", core->name); | 791 | printk("%s/2: cx2388x 8802 Driver Manager\n", core->name); |
784 | 792 | ||
785 | err = -ENODEV; | 793 | err = -ENODEV; |
786 | if (!cx88_boards[core->board].mpeg) | 794 | if (!core->board.mpeg) |
787 | goto fail_core; | 795 | goto fail_core; |
788 | 796 | ||
789 | err = -ENOMEM; | 797 | err = -ENOMEM; |
@@ -866,7 +874,7 @@ static struct pci_driver cx8802_pci_driver = { | |||
866 | 874 | ||
867 | static int cx8802_init(void) | 875 | static int cx8802_init(void) |
868 | { | 876 | { |
869 | printk(KERN_INFO "cx2388x cx88-mpeg Driver Manager version %d.%d.%d loaded\n", | 877 | printk(KERN_INFO "cx88/2: cx2388x MPEG-TS Driver Manager version %d.%d.%d loaded\n", |
870 | (CX88_VERSION_CODE >> 16) & 0xff, | 878 | (CX88_VERSION_CODE >> 16) & 0xff, |
871 | (CX88_VERSION_CODE >> 8) & 0xff, | 879 | (CX88_VERSION_CODE >> 8) & 0xff, |
872 | CX88_VERSION_CODE & 0xff); | 880 | CX88_VERSION_CODE & 0xff); |