1 /*****************************************************************************
2 * decoder_fifo.h: interface for decoders PES fifo
3 *****************************************************************************
4 * Copyright (C) 1999, 2000 VideoLAN
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * General Public License for more details.
18 * You should have received a copy of the GNU General Public
19 * License along with this program; if not, write to the
20 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21 * Boston, MA 02111-1307, USA.
22 *****************************************************************************/
24 /*****************************************************************************
30 *****************************************************************************/
32 /*****************************************************************************
34 *****************************************************************************/
36 /* FIXME: move to inline functions ??*/
37 #define DECODER_FIFO_ISEMPTY( fifo ) ( (fifo).i_start == (fifo).i_end )
38 #define DECODER_FIFO_ISFULL( fifo ) ( ( ( (fifo).i_end + 1 - (fifo).i_start ) \
40 #define DECODER_FIFO_START( fifo ) ( (fifo).buffer[ (fifo).i_start ] )
41 #define DECODER_FIFO_INCSTART( fifo ) ( (fifo).i_start = ((fifo).i_start + 1)\
43 #define DECODER_FIFO_END( fifo ) ( (fifo).buffer[ (fifo).i_end ] )
44 #define DECODER_FIFO_INCEND( fifo ) ( (fifo).i_end = ((fifo).i_end + 1) \
47 /*****************************************************************************
49 *****************************************************************************
50 * This rotative FIFO contains PES packets that are to be decoded...
51 *****************************************************************************/
54 vlc_mutex_t data_lock; /* fifo data lock */
55 vlc_cond_t data_wait; /* fifo data conditional variable */
57 /* buffer is an array of PES packets pointers */
58 pes_packet_t * buffer[FIFO_SIZE + 1];
64 /*****************************************************************************
65 * bit_fifo_t : bit fifo descriptor
66 *****************************************************************************
67 * This type describes a bit fifo used to store bits while working with the
68 * input stream at the bit level.
69 *****************************************************************************/
70 typedef struct bit_fifo_s
72 /* This unsigned integer allows us to work at the bit level. This buffer
73 * can contain 32 bits, and the used space can be found on the MSb's side
74 * and the available space on the LSb's side. */
77 /* Number of bits available in the bit buffer */
82 /*****************************************************************************
83 * bit_stream_t : bit stream descriptor
84 *****************************************************************************
85 * This type, based on a PES stream, includes all the structures needed to
86 * handle the input stream like a bit stream.
87 *****************************************************************************/
88 typedef struct bit_stream_s
93 /* The input thread feeds the stream with fresh PES packets */
94 input_thread_t * p_input;
95 /* The decoder fifo contains the data of the PES stream */
96 decoder_fifo_t * p_decoder_fifo;
101 /* Current TS packet (in the current PES packet of the PES stream) */
103 /* Pointer to the next byte that is to be read (in the current TS packet) */
105 /* Pointer to the last byte that is to be read (in the current TS packet */
116 void decoder_fifo_next( bit_stream_t * p_bit_stream );
117 /*****************************************************************************
118 * GetByte : reads the next byte in the input stream
119 *****************************************************************************/
120 static __inline__ byte_t GetByte( bit_stream_t * p_bit_stream )
122 /* Are there some bytes left in the current TS packet ? */
123 /* could change this test to have a if (! (bytes--)) instead */
124 if ( p_bit_stream->p_byte >= p_bit_stream->p_end )
126 /* no, switch to next TS packet */
127 decoder_fifo_next( p_bit_stream );
130 return( *(p_bit_stream->p_byte++));
133 /*****************************************************************************
134 * NeedBits : reads i_bits new bits in the bit stream and stores them in the
136 *****************************************************************************
137 * - i_bits must be less or equal 32 !
138 * - There is something important to notice with that function : if the number
139 * of bits available in the bit buffer when calling NeedBits() is greater than
140 * 24 (i_available > 24) but less than the number of needed bits
141 * (i_available < i_bits), the byte returned by GetByte() will be shifted with
142 * a negative value and the number of bits available in the bit buffer will be
143 * set to more than 32 !
144 *****************************************************************************/
145 static __inline__ void NeedBits( bit_stream_t * p_bit_stream, int i_bits )
147 while ( p_bit_stream->fifo.i_available < i_bits )
149 p_bit_stream->fifo.buffer |= ((u32)GetByte( p_bit_stream )) << (24 - p_bit_stream->fifo.i_available);
150 p_bit_stream->fifo.i_available += 8;
154 /*****************************************************************************
155 * DumpBits : removes i_bits bits from the bit buffer
156 *****************************************************************************
157 * - i_bits <= i_available
158 * - i_bits < 32 (because (u32 << 32) <=> (u32 = u32))
159 *****************************************************************************/
160 static __inline__ void DumpBits( bit_stream_t * p_bit_stream, int i_bits )
162 p_bit_stream->fifo.buffer <<= i_bits;
163 p_bit_stream->fifo.i_available -= i_bits;
166 /*****************************************************************************
167 * DumpBits32 : removes 32 bits from the bit buffer
168 *****************************************************************************
169 * This function actually believes that you have already put 32 bits in the
170 * bit buffer, so you can't you use it anytime.
171 *****************************************************************************/
172 static __inline__ void DumpBits32( bit_stream_t * p_bit_stream )
174 p_bit_stream->fifo.buffer = 0;
175 p_bit_stream->fifo.i_available = 0;
179 * For the following functions, please read VERY CAREFULLY the warning in
180 * NeedBits(). If i_bits > 24, the stream parser must be already aligned
181 * on an 8-bit boundary, or you will get curious results (that is, you
182 * need to call RealignBits() before).
185 /*****************************************************************************
186 * RemoveBits : removes i_bits bits from the bit buffer
187 *****************************************************************************/
188 static __inline__ void RemoveBits( bit_stream_t * p_bit_stream, int i_bits )
190 NeedBits( p_bit_stream, i_bits );
191 DumpBits( p_bit_stream, i_bits );
194 /*****************************************************************************
195 * RemoveBits32 : removes 32 bits from the bit buffer
196 *****************************************************************************/
197 static __inline__ void RemoveBits32( bit_stream_t * p_bit_stream )
199 NeedBits( p_bit_stream, 32 );
200 DumpBits32( p_bit_stream );
203 /*****************************************************************************
204 * ShowBits : return i_bits bits from the bit stream
205 *****************************************************************************/
206 static __inline__ u32 ShowBits( bit_stream_t * p_bit_stream, int i_bits )
208 NeedBits( p_bit_stream, i_bits );
209 return( p_bit_stream->fifo.buffer >> (32 - i_bits) );
212 /*****************************************************************************
213 * GetBits : returns i_bits bits from the bit stream and removes them
214 *****************************************************************************/
215 static __inline__ u32 GetBits( bit_stream_t * p_bit_stream, int i_bits )
219 NeedBits( p_bit_stream, i_bits );
220 i_buffer = p_bit_stream->fifo.buffer >> (32 - i_bits);
221 DumpBits( p_bit_stream, i_bits );
225 /*****************************************************************************
226 * GetBits32 : returns 32 bits from the bit stream and removes them
227 *****************************************************************************/
228 static __inline__ u32 GetBits32( bit_stream_t * p_bit_stream )
232 NeedBits( p_bit_stream, 32 );
233 i_buffer = p_bit_stream->fifo.buffer;
234 DumpBits32( p_bit_stream );
238 /*****************************************************************************
239 * RealignBits : realigns the bit buffer on an 8-bit boundary
240 *****************************************************************************/
241 static __inline__ void RealignBits( bit_stream_t * p_bit_stream )
243 DumpBits( p_bit_stream, p_bit_stream->fifo.i_available & 7 );