6f8e818cd3c20890e2bb91c142c2273defafba01
[vlc.git] / include / stream_output.h
1 /*****************************************************************************
2  * stream_output.h : stream output module
3  *****************************************************************************
4  * Copyright (C) 2002 VideoLAN
5  * $Id: stream_output.h,v 1.12 2003/08/09 14:59:24 gbazin Exp $
6  *
7  * Authors: Christophe Massiot <massiot@via.ecp.fr>
8  *          Laurent Aimar <fenrir@via.ecp.fr>
9  *          Eric Petit <titer@videolan.org>
10  *
11  * This program is free software; you can redistribute it and/or modify
12  * it under the terms of the GNU General Public License as published by
13  * the Free Software Foundation; either version 2 of the License, or
14  * (at your option) any later version.
15  *
16  * This program is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  * GNU General Public License for more details.
20  *
21  * You should have received a copy of the GNU General Public License
22  * along with this program; if not, write to the Free Software
23  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111, USA.
24  *****************************************************************************/
25
26 /*****************************************************************************
27  * sout_instance_t: stream output thread descriptor
28  *****************************************************************************/
29
30 /*
31  * i_allocated_size: size of allocated buffer
32  * p_allocated_buffer: where data has been allocated
33  *
34  * i_buffer_size: sizeof buffer from p_buffer
35  * p_buffer: where data begins
36  * i_size: size of valid data
37  *
38  */
39 #define SOUT_BUFFER_FLAGS_HEADER    0x0001
40
41 /*
42  * Flags for muxer/access private usage.
43  */
44 #define SOUT_BUFFER_FLAGS_PRIVATE_MASK  0xffff0000
45 #define SOUT_BUFFER_FLAGS_PRIVATE_SHIFT 16
46
47 struct sout_buffer_t
48 {
49     size_t                  i_allocated_size;
50     byte_t                  *p_allocated_buffer;
51
52     size_t                  i_buffer_size;
53     byte_t                  *p_buffer;
54
55     size_t                  i_size;
56     mtime_t                 i_length;
57
58     mtime_t                 i_dts;
59     mtime_t                 i_pts;
60
61     uint32_t                i_flags;
62     int                     i_bitrate;
63
64     struct sout_buffer_t    *p_next;
65 };
66
67 struct sout_format_t
68 {
69     int             i_cat;
70     vlc_fourcc_t    i_fourcc;
71
72     /* audio */
73     int             i_sample_rate;
74     int             i_channels;
75     int             i_block_align;
76
77     /* video */
78     int             i_width;
79     int             i_height;
80
81     int             i_bitrate;
82     int             i_extra_data;
83     uint8_t         *p_extra_data;
84
85 };
86
87 struct sout_fifo_t
88 {
89     vlc_mutex_t         lock;                         /* fifo data lock */
90     vlc_cond_t          wait;         /* fifo data conditional variable */
91
92     int                 i_depth;
93     sout_buffer_t       *p_first;
94     sout_buffer_t       **pp_last;
95 };
96
97 typedef struct sout_stream_id_t  sout_stream_id_t;
98
99 /* for mux */
100 struct sout_input_t
101 {
102     sout_instance_t *p_sout;
103
104     sout_format_t   *p_fmt;
105     sout_fifo_t     *p_fifo;
106
107     void            *p_sys;
108 };
109
110 /* for packetizer */
111 struct sout_packetizer_input_t
112 {
113
114     sout_instance_t     *p_sout;
115
116     sout_format_t       *p_fmt;
117
118     sout_stream_id_t    *id;
119 };
120
121
122 #define SOUT_METHOD_NONE        0x00
123 #define SOUT_METHOD_FILE        0x10
124 #define SOUT_METHOD_NETWORK     0x20
125
126 typedef struct sout_access_out_sys_t   sout_access_out_sys_t;
127 struct sout_access_out_t
128 {
129     VLC_COMMON_MEMBERS
130
131     module_t                *p_module;
132
133     sout_instance_t         *p_sout;
134
135     char                    *psz_access;
136     sout_cfg_t              *p_cfg;
137
138     char                    *psz_name;
139     sout_access_out_sys_t   *p_sys;
140     int                     (* pf_seek  )( sout_access_out_t *,
141                                            off_t );
142     int                     (* pf_write )( sout_access_out_t *,
143                                            sout_buffer_t * );
144 };
145 /*
146  * i_query parameter of pf_mux_capacity
147  */
148 /* SOUT_MUX_CAP_GET_ADD_STREAM_ANY_TIME:    p_args=NULL, p_answer=&boolean */
149 #define SOUT_MUX_CAP_GET_ADD_STREAM_ANY_TIME    0x01
150 /* SOUT_MUX_CAP_GET_STREAMABLE:             p_args=NULL, p_answer=&boolean */
151 #define SOUT_MUX_CAP_GET_STREAMABLE             0x02
152 /*
153  * return error code
154  */
155 #define SOUT_MUX_CAP_ERR_OK                 0x00
156 #define SOUT_MUX_CAP_ERR_UNKNOWN            0x01
157 #define SOUT_MUX_CAP_ERR_UNIMPLEMENTED      0x02
158
159 typedef struct sout_mux_sys_t sout_mux_sys_t;
160 struct  sout_mux_t
161 {
162     VLC_COMMON_MEMBERS
163     module_t                *p_module;
164
165     sout_instance_t         *p_sout;
166
167     char                    *psz_mux;
168     sout_cfg_t              *p_cfg;
169
170     sout_access_out_t       *p_access;
171
172     int                     i_preheader;
173     int                     (* pf_capacity)  ( sout_mux_t *,
174                                                int, void *, void *);
175     int                     (* pf_addstream )( sout_mux_t *,
176                                                sout_input_t * );
177     int                     (* pf_delstream )( sout_mux_t *,
178                                                sout_input_t * );
179     int                     (* pf_mux )      ( sout_mux_t * );
180
181
182     /* here are all inputs accepted by muxer */
183     int                     i_nb_inputs;
184     sout_input_t            **pp_inputs;
185
186
187     /* mux private */
188     sout_mux_sys_t          *p_sys;
189
190 //    /* creater private */
191 //    void                    *p_sys_owner;
192
193     /* XXX private to stream_output.c */
194     /* if muxer doesn't support adding stream at any time then we first wait
195      *  for stream then we refuse all stream and start muxing */
196     vlc_bool_t  b_add_stream_any_time;
197     vlc_bool_t  b_waiting_stream;
198     /* we wait one second after first stream added */
199     mtime_t     i_add_stream_start;
200 };
201
202
203
204 struct sout_cfg_t
205 {
206     sout_cfg_t  *p_next;
207
208     char        *psz_name;
209     char        *psz_value;
210 };
211
212 typedef struct sout_stream_sys_t sout_stream_sys_t;
213 struct sout_stream_t
214 {
215     VLC_COMMON_MEMBERS
216
217     module_t                *p_module;
218     sout_instance_t         *p_sout;
219
220     char                    *psz_name;
221     sout_cfg_t              *p_cfg;
222     char                    *psz_next;
223
224     /* add, remove a stream */
225     sout_stream_id_t *      (*pf_add) ( sout_stream_t *, sout_format_t * );
226     int                     (*pf_del) ( sout_stream_t *, sout_stream_id_t * );
227
228     /* manage a packet */
229     int                     (*pf_send)( sout_stream_t *, sout_stream_id_t *, sout_buffer_t* );
230
231     /* private */
232     sout_stream_sys_t       *p_sys;
233 };
234
235 typedef struct sout_instance_sys_t sout_instance_sys_t;
236 struct sout_instance_t
237 {
238     VLC_COMMON_MEMBERS
239
240     char * psz_sout;
241     char * psz_chain;
242
243     /* muxer data */
244     int                     i_preheader;    /* max over all muxer */
245
246     int                     i_padding;      /* needed by some decoders */
247
248     vlc_mutex_t             lock;
249     sout_stream_t           *p_stream;
250
251     /* sout private */
252     sout_instance_sys_t     *p_sys;
253 };
254
255 /* some macro */
256 #define TAB_APPEND( count, tab, p )             \
257     if( (count) > 0 )                           \
258     {                                           \
259         (tab) = realloc( (tab), sizeof( void ** ) * ( (count) + 1 ) ); \
260     }                                           \
261     else                                        \
262     {                                           \
263         (tab) = malloc( sizeof( void ** ) );    \
264     }                                           \
265     (void**)(tab)[(count)] = (void*)(p);        \
266     (count)++
267
268 #define TAB_FIND( count, tab, p, index )        \
269     {                                           \
270         int _i_;                                \
271         (index) = -1;                           \
272         for( _i_ = 0; _i_ < (count); _i_++ )    \
273         {                                       \
274             if((void**)(tab)[_i_]==(void*)(p))  \
275             {                                   \
276                 (index) = _i_;                  \
277                 break;                          \
278             }                                   \
279         }                                       \
280     }
281
282 #define TAB_REMOVE( count, tab, p )             \
283     {                                           \
284         int i_index;                            \
285         TAB_FIND( count, tab, p, i_index );     \
286         if( i_index >= 0 )                      \
287         {                                       \
288             if( count > 1 )                     \
289             {                                   \
290                 memmove( ((void**)tab + i_index),    \
291                          ((void**)tab + i_index+1),  \
292                          ( (count) - i_index - 1 ) * sizeof( void* ) );\
293             }                                   \
294             else                                \
295             {                                   \
296                 free( tab );                    \
297                 (tab) = NULL;                   \
298             }                                   \
299             (count)--;                          \
300         }                                       \
301     }
302
303 static inline sout_cfg_t *sout_cfg_find( sout_cfg_t *p_cfg, char *psz_name )
304 {
305     while( p_cfg && strcmp( p_cfg->psz_name, psz_name ) )
306     {
307         p_cfg = p_cfg->p_next;
308     }
309
310     return p_cfg;
311 }
312
313 static inline char *sout_cfg_find_value( sout_cfg_t *p_cfg, char *psz_name )
314 {
315     while( p_cfg && strcmp( p_cfg->psz_name, psz_name ) )
316     {
317         p_cfg = p_cfg->p_next;
318     }
319
320     if( p_cfg && p_cfg->psz_value )
321     {
322         return( p_cfg->psz_value );
323     }
324
325     return NULL;
326 }
327 /*****************************************************************************
328  * Prototypes
329  *****************************************************************************/
330 #define sout_NewInstance(a,b) __sout_NewInstance(VLC_OBJECT(a),b)
331 VLC_EXPORT( sout_instance_t *, __sout_NewInstance,  ( vlc_object_t *, char * ) );
332 VLC_EXPORT( void,              sout_DeleteInstance, ( sout_instance_t * ) );
333
334 VLC_EXPORT( sout_fifo_t *,   sout_FifoCreate,     ( sout_instance_t * ) );
335 VLC_EXPORT( void,            sout_FifoDestroy,    ( sout_instance_t *, sout_fifo_t * ) );
336 VLC_EXPORT( void,            sout_FifoFree,       ( sout_instance_t *,sout_fifo_t * ) );
337
338 VLC_EXPORT( void,            sout_FifoPut,        ( sout_fifo_t *, sout_buffer_t* ) );
339 VLC_EXPORT( sout_buffer_t *, sout_FifoGet,        ( sout_fifo_t * ) );
340 VLC_EXPORT( sout_buffer_t *, sout_FifoShow,       ( sout_fifo_t * ) );
341
342
343 #define sout_InputNew( a, b ) __sout_InputNew( VLC_OBJECT(a), b )
344 VLC_EXPORT( sout_packetizer_input_t *, __sout_InputNew,       ( vlc_object_t *, sout_format_t * ) );
345 VLC_EXPORT( int,            sout_InputDelete,      ( sout_packetizer_input_t * ) );
346 VLC_EXPORT( int,            sout_InputSendBuffer,  ( sout_packetizer_input_t *, sout_buffer_t* ) );
347
348 VLC_EXPORT( sout_buffer_t*, sout_BufferNew,    ( sout_instance_t *, size_t ) );
349 VLC_EXPORT( int,            sout_BufferRealloc,( sout_instance_t *, sout_buffer_t*, size_t ) );
350 VLC_EXPORT( int,            sout_BufferReallocFromPreHeader,( sout_instance_t *, sout_buffer_t*, size_t ) );
351 VLC_EXPORT( int,            sout_BufferDelete, ( sout_instance_t *, sout_buffer_t* ) );
352 VLC_EXPORT( sout_buffer_t*, sout_BufferDuplicate,(sout_instance_t *, sout_buffer_t * ) );
353 VLC_EXPORT( void,           sout_BufferChain,  ( sout_buffer_t **, sout_buffer_t * ) );
354
355 VLC_EXPORT( sout_access_out_t *, sout_AccessOutNew, ( sout_instance_t *, char *psz_access, char *psz_name ) );
356 VLC_EXPORT( void,                sout_AccessOutDelete, ( sout_access_out_t * ) );
357 VLC_EXPORT( int,                 sout_AccessOutSeek,   ( sout_access_out_t *, off_t ) );
358 VLC_EXPORT( int,                 sout_AccessOutWrite,  ( sout_access_out_t *, sout_buffer_t * ) );
359
360 VLC_EXPORT( sout_mux_t *,       sout_MuxNew,          ( sout_instance_t*, char *, sout_access_out_t * ) );
361 VLC_EXPORT( sout_input_t *,     sout_MuxAddStream,    ( sout_mux_t *, sout_format_t * ) );
362 VLC_EXPORT( void,               sout_MuxDeleteStream, ( sout_mux_t *, sout_input_t * ) );
363 VLC_EXPORT( void,               sout_MuxDelete,       ( sout_mux_t * ) );
364 VLC_EXPORT( void,               sout_MuxSendBuffer, ( sout_mux_t *, sout_input_t  *, sout_buffer_t * ) );
365
366 VLC_EXPORT( char *,             sout_cfg_parser, ( char **, sout_cfg_t **, char * ) );
367 VLC_EXPORT( sout_stream_t *,    sout_stream_new, ( sout_instance_t *, char *psz_chain ) );
368 VLC_EXPORT( void,               sout_stream_delete, ( sout_stream_t *p_stream ) );
369