diff options
-rw-r--r-- | drivers/media/dvb/ngene/Makefile | 2 | ||||
-rw-r--r-- | drivers/media/dvb/ngene/ngene-core.c | 130 | ||||
-rw-r--r-- | drivers/media/dvb/ngene/ngene-dvb.c | 172 | ||||
-rw-r--r-- | drivers/media/dvb/ngene/ngene.h | 17 |
4 files changed, 192 insertions, 129 deletions
diff --git a/drivers/media/dvb/ngene/Makefile b/drivers/media/dvb/ngene/Makefile index f01c4a1627d3..0608aabb14ee 100644 --- a/drivers/media/dvb/ngene/Makefile +++ b/drivers/media/dvb/ngene/Makefile | |||
@@ -2,7 +2,7 @@ | |||
2 | # Makefile for the nGene device driver | 2 | # Makefile for the nGene device driver |
3 | # | 3 | # |
4 | 4 | ||
5 | ngene-objs := ngene-core.o ngene-i2c.o ngene-cards.o | 5 | ngene-objs := ngene-core.o ngene-i2c.o ngene-cards.o ngene-dvb.o |
6 | 6 | ||
7 | obj-$(CONFIG_DVB_NGENE) += ngene.o | 7 | obj-$(CONFIG_DVB_NGENE) += ngene.o |
8 | 8 | ||
diff --git a/drivers/media/dvb/ngene/ngene-core.c b/drivers/media/dvb/ngene/ngene-core.c index 8a64f644192a..c8b4dfa0ab5f 100644 --- a/drivers/media/dvb/ngene/ngene-core.c +++ b/drivers/media/dvb/ngene/ngene-core.c | |||
@@ -503,7 +503,7 @@ static u8 ITUFeatureDecoderSetup[8] = { | |||
503 | 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x04, 0x00 | 503 | 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x04, 0x00 |
504 | }; | 504 | }; |
505 | 505 | ||
506 | static void FillTSBuffer(void *Buffer, int Length, u32 Flags) | 506 | void FillTSBuffer(void *Buffer, int Length, u32 Flags) |
507 | { | 507 | { |
508 | u32 *ptr = Buffer; | 508 | u32 *ptr = Buffer; |
509 | 509 | ||
@@ -716,62 +716,7 @@ static int ngene_command_stream_control(struct ngene *dev, u8 stream, | |||
716 | return 0; | 716 | return 0; |
717 | } | 717 | } |
718 | 718 | ||
719 | 719 | void set_transfer(struct ngene_channel *chan, int state) | |
720 | /****************************************************************************/ | ||
721 | /* EEPROM TAGS **************************************************************/ | ||
722 | /****************************************************************************/ | ||
723 | |||
724 | /****************************************************************************/ | ||
725 | /* DVB functions and API interface ******************************************/ | ||
726 | /****************************************************************************/ | ||
727 | |||
728 | static void swap_buffer(u32 *p, u32 len) | ||
729 | { | ||
730 | while (len) { | ||
731 | *p = swab32(*p); | ||
732 | p++; | ||
733 | len -= 4; | ||
734 | } | ||
735 | } | ||
736 | |||
737 | |||
738 | static void *tsin_exchange(void *priv, void *buf, u32 len, u32 clock, u32 flags) | ||
739 | { | ||
740 | struct ngene_channel *chan = priv; | ||
741 | |||
742 | |||
743 | #ifdef COMMAND_TIMEOUT_WORKAROUND | ||
744 | if (chan->users > 0) | ||
745 | #endif | ||
746 | dvb_dmx_swfilter(&chan->demux, buf, len); | ||
747 | return NULL; | ||
748 | } | ||
749 | |||
750 | u8 fill_ts[188] = { 0x47, 0x1f, 0xff, 0x10 }; | ||
751 | |||
752 | static void *tsout_exchange(void *priv, void *buf, u32 len, | ||
753 | u32 clock, u32 flags) | ||
754 | { | ||
755 | struct ngene_channel *chan = priv; | ||
756 | struct ngene *dev = chan->dev; | ||
757 | u32 alen; | ||
758 | |||
759 | alen = dvb_ringbuffer_avail(&dev->tsout_rbuf); | ||
760 | alen -= alen % 188; | ||
761 | |||
762 | if (alen < len) | ||
763 | FillTSBuffer(buf + alen, len - alen, flags); | ||
764 | else | ||
765 | alen = len; | ||
766 | dvb_ringbuffer_read(&dev->tsout_rbuf, buf, alen); | ||
767 | if (flags & DF_SWAP32) | ||
768 | swap_buffer((u32 *)buf, alen); | ||
769 | wake_up_interruptible(&dev->tsout_rbuf.queue); | ||
770 | return buf; | ||
771 | } | ||
772 | |||
773 | |||
774 | static void set_transfer(struct ngene_channel *chan, int state) | ||
775 | { | 720 | { |
776 | u8 control = 0, mode = 0, flags = 0; | 721 | u8 control = 0, mode = 0, flags = 0; |
777 | struct ngene *dev = chan->dev; | 722 | struct ngene *dev = chan->dev; |
@@ -838,77 +783,6 @@ static void set_transfer(struct ngene_channel *chan, int state) | |||
838 | } | 783 | } |
839 | } | 784 | } |
840 | 785 | ||
841 | static int ngene_start_feed(struct dvb_demux_feed *dvbdmxfeed) | ||
842 | { | ||
843 | struct dvb_demux *dvbdmx = dvbdmxfeed->demux; | ||
844 | struct ngene_channel *chan = dvbdmx->priv; | ||
845 | |||
846 | if (chan->users == 0) { | ||
847 | #ifdef COMMAND_TIMEOUT_WORKAROUND | ||
848 | if (!chan->running) | ||
849 | #endif | ||
850 | set_transfer(chan, 1); | ||
851 | /* msleep(10); */ | ||
852 | } | ||
853 | |||
854 | return ++chan->users; | ||
855 | } | ||
856 | |||
857 | static int ngene_stop_feed(struct dvb_demux_feed *dvbdmxfeed) | ||
858 | { | ||
859 | struct dvb_demux *dvbdmx = dvbdmxfeed->demux; | ||
860 | struct ngene_channel *chan = dvbdmx->priv; | ||
861 | |||
862 | if (--chan->users) | ||
863 | return chan->users; | ||
864 | |||
865 | #ifndef COMMAND_TIMEOUT_WORKAROUND | ||
866 | set_transfer(chan, 0); | ||
867 | #endif | ||
868 | |||
869 | return 0; | ||
870 | } | ||
871 | |||
872 | static int my_dvb_dmx_ts_card_init(struct dvb_demux *dvbdemux, char *id, | ||
873 | int (*start_feed)(struct dvb_demux_feed *), | ||
874 | int (*stop_feed)(struct dvb_demux_feed *), | ||
875 | void *priv) | ||
876 | { | ||
877 | dvbdemux->priv = priv; | ||
878 | |||
879 | dvbdemux->filternum = 256; | ||
880 | dvbdemux->feednum = 256; | ||
881 | dvbdemux->start_feed = start_feed; | ||
882 | dvbdemux->stop_feed = stop_feed; | ||
883 | dvbdemux->write_to_decoder = NULL; | ||
884 | dvbdemux->dmx.capabilities = (DMX_TS_FILTERING | | ||
885 | DMX_SECTION_FILTERING | | ||
886 | DMX_MEMORY_BASED_FILTERING); | ||
887 | return dvb_dmx_init(dvbdemux); | ||
888 | } | ||
889 | |||
890 | static int my_dvb_dmxdev_ts_card_init(struct dmxdev *dmxdev, | ||
891 | struct dvb_demux *dvbdemux, | ||
892 | struct dmx_frontend *hw_frontend, | ||
893 | struct dmx_frontend *mem_frontend, | ||
894 | struct dvb_adapter *dvb_adapter) | ||
895 | { | ||
896 | int ret; | ||
897 | |||
898 | dmxdev->filternum = 256; | ||
899 | dmxdev->demux = &dvbdemux->dmx; | ||
900 | dmxdev->capabilities = 0; | ||
901 | ret = dvb_dmxdev_init(dmxdev, dvb_adapter); | ||
902 | if (ret < 0) | ||
903 | return ret; | ||
904 | |||
905 | hw_frontend->source = DMX_FRONTEND_0; | ||
906 | dvbdemux->dmx.add_frontend(&dvbdemux->dmx, hw_frontend); | ||
907 | mem_frontend->source = DMX_MEMORY_FE; | ||
908 | dvbdemux->dmx.add_frontend(&dvbdemux->dmx, mem_frontend); | ||
909 | return dvbdemux->dmx.connect_frontend(&dvbdemux->dmx, hw_frontend); | ||
910 | } | ||
911 | |||
912 | 786 | ||
913 | /****************************************************************************/ | 787 | /****************************************************************************/ |
914 | /* nGene hardware init and release functions ********************************/ | 788 | /* nGene hardware init and release functions ********************************/ |
diff --git a/drivers/media/dvb/ngene/ngene-dvb.c b/drivers/media/dvb/ngene/ngene-dvb.c new file mode 100644 index 000000000000..96013eb353cd --- /dev/null +++ b/drivers/media/dvb/ngene/ngene-dvb.c | |||
@@ -0,0 +1,172 @@ | |||
1 | /* | ||
2 | * ngene-dvb.c: nGene PCIe bridge driver - DVB functions | ||
3 | * | ||
4 | * Copyright (C) 2005-2007 Micronas | ||
5 | * | ||
6 | * Copyright (C) 2008-2009 Ralph Metzler <rjkm@metzlerbros.de> | ||
7 | * Modifications for new nGene firmware, | ||
8 | * support for EEPROM-copying, | ||
9 | * support for new dual DVB-S2 card prototype | ||
10 | * | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * version 2 only, as published by the Free Software Foundation. | ||
15 | * | ||
16 | * | ||
17 | * This program is distributed in the hope that it will be useful, | ||
18 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
20 | * GNU General Public License for more details. | ||
21 | * | ||
22 | * | ||
23 | * You should have received a copy of the GNU General Public License | ||
24 | * along with this program; if not, write to the Free Software | ||
25 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA | ||
26 | * 02110-1301, USA | ||
27 | * Or, point your browser to http://www.gnu.org/copyleft/gpl.html | ||
28 | */ | ||
29 | |||
30 | #include <linux/module.h> | ||
31 | #include <linux/init.h> | ||
32 | #include <linux/delay.h> | ||
33 | #include <linux/slab.h> | ||
34 | #include <linux/poll.h> | ||
35 | #include <linux/io.h> | ||
36 | #include <asm/div64.h> | ||
37 | #include <linux/pci.h> | ||
38 | #include <linux/smp_lock.h> | ||
39 | #include <linux/timer.h> | ||
40 | #include <linux/version.h> | ||
41 | #include <linux/byteorder/generic.h> | ||
42 | #include <linux/firmware.h> | ||
43 | #include <linux/vmalloc.h> | ||
44 | |||
45 | #include "ngene.h" | ||
46 | |||
47 | #define COMMAND_TIMEOUT_WORKAROUND | ||
48 | |||
49 | |||
50 | /****************************************************************************/ | ||
51 | /* COMMAND API interface ****************************************************/ | ||
52 | /****************************************************************************/ | ||
53 | |||
54 | /****************************************************************************/ | ||
55 | /* DVB functions and API interface ******************************************/ | ||
56 | /****************************************************************************/ | ||
57 | |||
58 | static void swap_buffer(u32 *p, u32 len) | ||
59 | { | ||
60 | while (len) { | ||
61 | *p = swab32(*p); | ||
62 | p++; | ||
63 | len -= 4; | ||
64 | } | ||
65 | } | ||
66 | |||
67 | void *tsin_exchange(void *priv, void *buf, u32 len, u32 clock, u32 flags) | ||
68 | { | ||
69 | struct ngene_channel *chan = priv; | ||
70 | |||
71 | |||
72 | #ifdef COMMAND_TIMEOUT_WORKAROUND | ||
73 | if (chan->users > 0) | ||
74 | #endif | ||
75 | dvb_dmx_swfilter(&chan->demux, buf, len); | ||
76 | return NULL; | ||
77 | } | ||
78 | |||
79 | u8 fill_ts[188] = { 0x47, 0x1f, 0xff, 0x10 }; | ||
80 | |||
81 | void *tsout_exchange(void *priv, void *buf, u32 len, u32 clock, u32 flags) | ||
82 | { | ||
83 | struct ngene_channel *chan = priv; | ||
84 | struct ngene *dev = chan->dev; | ||
85 | u32 alen; | ||
86 | |||
87 | alen = dvb_ringbuffer_avail(&dev->tsout_rbuf); | ||
88 | alen -= alen % 188; | ||
89 | |||
90 | if (alen < len) | ||
91 | FillTSBuffer(buf + alen, len - alen, flags); | ||
92 | else | ||
93 | alen = len; | ||
94 | dvb_ringbuffer_read(&dev->tsout_rbuf, buf, alen); | ||
95 | if (flags & DF_SWAP32) | ||
96 | swap_buffer((u32 *)buf, alen); | ||
97 | wake_up_interruptible(&dev->tsout_rbuf.queue); | ||
98 | return buf; | ||
99 | } | ||
100 | |||
101 | |||
102 | |||
103 | int ngene_start_feed(struct dvb_demux_feed *dvbdmxfeed) | ||
104 | { | ||
105 | struct dvb_demux *dvbdmx = dvbdmxfeed->demux; | ||
106 | struct ngene_channel *chan = dvbdmx->priv; | ||
107 | |||
108 | if (chan->users == 0) { | ||
109 | #ifdef COMMAND_TIMEOUT_WORKAROUND | ||
110 | if (!chan->running) | ||
111 | #endif | ||
112 | set_transfer(chan, 1); | ||
113 | /* msleep(10); */ | ||
114 | } | ||
115 | |||
116 | return ++chan->users; | ||
117 | } | ||
118 | |||
119 | int ngene_stop_feed(struct dvb_demux_feed *dvbdmxfeed) | ||
120 | { | ||
121 | struct dvb_demux *dvbdmx = dvbdmxfeed->demux; | ||
122 | struct ngene_channel *chan = dvbdmx->priv; | ||
123 | |||
124 | if (--chan->users) | ||
125 | return chan->users; | ||
126 | |||
127 | #ifndef COMMAND_TIMEOUT_WORKAROUND | ||
128 | set_transfer(chan, 0); | ||
129 | #endif | ||
130 | |||
131 | return 0; | ||
132 | } | ||
133 | |||
134 | int my_dvb_dmx_ts_card_init(struct dvb_demux *dvbdemux, char *id, | ||
135 | int (*start_feed)(struct dvb_demux_feed *), | ||
136 | int (*stop_feed)(struct dvb_demux_feed *), | ||
137 | void *priv) | ||
138 | { | ||
139 | dvbdemux->priv = priv; | ||
140 | |||
141 | dvbdemux->filternum = 256; | ||
142 | dvbdemux->feednum = 256; | ||
143 | dvbdemux->start_feed = start_feed; | ||
144 | dvbdemux->stop_feed = stop_feed; | ||
145 | dvbdemux->write_to_decoder = NULL; | ||
146 | dvbdemux->dmx.capabilities = (DMX_TS_FILTERING | | ||
147 | DMX_SECTION_FILTERING | | ||
148 | DMX_MEMORY_BASED_FILTERING); | ||
149 | return dvb_dmx_init(dvbdemux); | ||
150 | } | ||
151 | |||
152 | int my_dvb_dmxdev_ts_card_init(struct dmxdev *dmxdev, | ||
153 | struct dvb_demux *dvbdemux, | ||
154 | struct dmx_frontend *hw_frontend, | ||
155 | struct dmx_frontend *mem_frontend, | ||
156 | struct dvb_adapter *dvb_adapter) | ||
157 | { | ||
158 | int ret; | ||
159 | |||
160 | dmxdev->filternum = 256; | ||
161 | dmxdev->demux = &dvbdemux->dmx; | ||
162 | dmxdev->capabilities = 0; | ||
163 | ret = dvb_dmxdev_init(dmxdev, dvb_adapter); | ||
164 | if (ret < 0) | ||
165 | return ret; | ||
166 | |||
167 | hw_frontend->source = DMX_FRONTEND_0; | ||
168 | dvbdemux->dmx.add_frontend(&dvbdemux->dmx, hw_frontend); | ||
169 | mem_frontend->source = DMX_MEMORY_FE; | ||
170 | dvbdemux->dmx.add_frontend(&dvbdemux->dmx, mem_frontend); | ||
171 | return dvbdemux->dmx.connect_frontend(&dvbdemux->dmx, hw_frontend); | ||
172 | } | ||
diff --git a/drivers/media/dvb/ngene/ngene.h b/drivers/media/dvb/ngene/ngene.h index c2dc8516cb20..676fcbb79026 100644 --- a/drivers/media/dvb/ngene/ngene.h +++ b/drivers/media/dvb/ngene/ngene.h | |||
@@ -862,10 +862,27 @@ int __devinit ngene_probe(struct pci_dev *pci_dev, | |||
862 | void __devexit ngene_remove(struct pci_dev *pdev); | 862 | void __devexit ngene_remove(struct pci_dev *pdev); |
863 | int ngene_command(struct ngene *dev, struct ngene_command *com); | 863 | int ngene_command(struct ngene *dev, struct ngene_command *com); |
864 | int ngene_command_gpio_set(struct ngene *dev, u8 select, u8 level); | 864 | int ngene_command_gpio_set(struct ngene *dev, u8 select, u8 level); |
865 | void set_transfer(struct ngene_channel *chan, int state); | ||
866 | void FillTSBuffer(void *Buffer, int Length, u32 Flags); | ||
865 | 867 | ||
866 | /* Provided by ngene-i2c.c */ | 868 | /* Provided by ngene-i2c.c */ |
867 | int ngene_i2c_init(struct ngene *dev, int dev_nr); | 869 | int ngene_i2c_init(struct ngene *dev, int dev_nr); |
868 | 870 | ||
871 | /* Provided by ngene-dvb.c */ | ||
872 | void *tsout_exchange(void *priv, void *buf, u32 len, u32 clock, u32 flags); | ||
873 | void *tsin_exchange(void *priv, void *buf, u32 len, u32 clock, u32 flags); | ||
874 | int ngene_start_feed(struct dvb_demux_feed *dvbdmxfeed); | ||
875 | int ngene_stop_feed(struct dvb_demux_feed *dvbdmxfeed); | ||
876 | int my_dvb_dmx_ts_card_init(struct dvb_demux *dvbdemux, char *id, | ||
877 | int (*start_feed)(struct dvb_demux_feed *), | ||
878 | int (*stop_feed)(struct dvb_demux_feed *), | ||
879 | void *priv); | ||
880 | int my_dvb_dmxdev_ts_card_init(struct dmxdev *dmxdev, | ||
881 | struct dvb_demux *dvbdemux, | ||
882 | struct dmx_frontend *hw_frontend, | ||
883 | struct dmx_frontend *mem_frontend, | ||
884 | struct dvb_adapter *dvb_adapter); | ||
885 | |||
869 | #endif | 886 | #endif |
870 | 887 | ||
871 | /* LocalWords: Endif | 888 | /* LocalWords: Endif |