]> git.sesse.net Git - vlc/blob - modules/mux/mpeg/ts.c
* ALL: portability fixes.
[vlc] / modules / mux / mpeg / ts.c
1 /*****************************************************************************
2  * ts.c: MPEG-II TS Muxer
3  *****************************************************************************
4  * Copyright (C) 2001, 2002 VideoLAN
5  * $Id: ts.c,v 1.44 2004/02/17 13:13:31 gbazin Exp $
6  *
7  * Authors: Laurent Aimar <fenrir@via.ecp.fr>
8  *          Eric Petit <titer@videolan.org>
9  *
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  * Preamble
28  *****************************************************************************/
29 #include <stdlib.h>
30
31 #include <vlc/vlc.h>
32 #include <vlc/input.h>
33 #include <vlc/sout.h>
34
35 #include "iso_lang.h"
36
37 #include "bits.h"
38 #include "pes.h"
39 #include "csa.h"
40
41 #if defined MODULE_NAME_IS_mux_ts_dvbpsi
42 #   ifdef HAVE_DVBPSI_DR_H
43 #       include <dvbpsi/dvbpsi.h>
44 #       include <dvbpsi/descriptor.h>
45 #       include <dvbpsi/pat.h>
46 #       include <dvbpsi/pmt.h>
47 #       include <dvbpsi/dr.h>
48 #       include <dvbpsi/psi.h>
49 #   else
50 #       include "dvbpsi.h"
51 #       include "descriptor.h"
52 #       include "tables/pat.h"
53 #       include "tables/pmt.h"
54 #       include "descriptors/dr.h"
55 #       include "psi.h"
56 #   endif
57 #endif
58
59 /*
60  * TODO:
61  *  - check PCR frequency requirement
62  *  - check PAT/PMT  "        "
63  *  - check PCR/PCR "soft"
64  *  - check if "registration" descriptor : "AC-3" should be a program
65  *    descriptor or an es one. (xine want an es one)
66  *
67  *  - remove creation of PAT/PMT without dvbpsi
68  *  - ?
69  * FIXME:
70  *  - subtitle support is far from perfect. I expect some subtitles drop
71  *    if they arrive a bit late
72  *    (We cannot rely on the fact that the fifo should be full)
73  */
74 /*****************************************************************************
75  * Module descriptor
76  *****************************************************************************/
77 static int     Open   ( vlc_object_t * );
78 static void    Close  ( vlc_object_t * );
79
80 vlc_module_begin();
81 #if defined MODULE_NAME_IS_mux_ts
82     set_description( _("TS muxer") );
83     set_capability( "sout mux", 100 );
84     add_shortcut( "ts" );
85     add_shortcut( "ts_nodvbpsi" );
86 #elif defined MODULE_NAME_IS_mux_ts_dvbpsi
87     set_description( _("TS muxer (libdvbpsi)") );
88     set_capability( "sout mux", 120 );
89     add_shortcut( "ts" );
90     add_shortcut( "ts_dvbpsi" );
91 #endif
92     set_callbacks( Open, Close );
93 vlc_module_end();
94
95 /*****************************************************************************
96  * Exported prototypes
97  *****************************************************************************/
98 static int     Capability(sout_mux_t *, int, void *, void * );
99 static int     AddStream( sout_mux_t *, sout_input_t * );
100 static int     DelStream( sout_mux_t *, sout_input_t * );
101 static int     Mux      ( sout_mux_t * );
102
103 /*****************************************************************************
104  * Local prototypes
105  *****************************************************************************/
106 #define SOUT_BUFFER_FLAGS_PRIVATE_PCR  ( 1 << SOUT_BUFFER_FLAGS_PRIVATE_SHIFT )
107 #define SOUT_BUFFER_FLAGS_PRIVATE_CSA  ( 2 << SOUT_BUFFER_FLAGS_PRIVATE_SHIFT )
108 typedef struct
109 {
110     int           i_depth;
111     sout_buffer_t *p_first;
112     sout_buffer_t **pp_last;
113 } sout_buffer_chain_t;
114
115 static inline void BufferChainInit  ( sout_buffer_chain_t *c )
116 {
117     c->i_depth = 0;
118     c->p_first = NULL;
119     c->pp_last = &c->p_first;
120 }
121 static inline void BufferChainAppend( sout_buffer_chain_t *c, sout_buffer_t *b )
122 {
123     *c->pp_last = b;
124     c->i_depth++;
125
126     while( b->p_next )
127     {
128         b = b->p_next;
129         c->i_depth++;
130     }
131     c->pp_last = &b->p_next;
132 }
133 static inline sout_buffer_t *BufferChainGet( sout_buffer_chain_t *c )
134 {
135     sout_buffer_t *b = c->p_first;
136
137     if( b )
138     {
139         c->i_depth--;
140         c->p_first = b->p_next;
141
142         if( c->p_first == NULL )
143         {
144             c->pp_last = &c->p_first;
145         }
146
147         b->p_next = NULL;
148     }
149     return b;
150 }
151 static inline void BufferChainClean( sout_instance_t *p_sout, sout_buffer_chain_t *c )
152 {
153     sout_buffer_t *b;
154
155     while( ( b = BufferChainGet( c ) ) )
156     {
157         sout_BufferDelete( p_sout, b );
158     }
159     BufferChainInit( c );
160 }
161
162 typedef struct ts_stream_s
163 {
164     int             i_pid;
165     int             i_stream_type;
166     int             i_stream_id;
167     int             i_continuity_counter;
168
169     /* to be used for carriege of DIV3 */
170     vlc_fourcc_t    i_bih_codec;
171     int             i_bih_width, i_bih_height;
172
173     /* Specific to mpeg4 in mpeg2ts */
174     int             i_es_id;
175
176     int             i_decoder_specific_info;
177     uint8_t         *p_decoder_specific_info;
178
179     /* language is iso639-2T */
180     uint8_t         lang[3];
181
182     sout_buffer_chain_t chain_pes;
183     mtime_t             i_pes_dts;
184     mtime_t             i_pes_length;
185     int                 i_pes_used;
186
187 } ts_stream_t;
188
189 struct sout_mux_sys_t
190 {
191     int             i_pcr_pid;
192     sout_input_t    *p_pcr_input;
193
194     int             i_audio_bound;
195     int             i_video_bound;
196
197     int             i_pid_video;
198     int             i_pid_audio;
199     int             i_pid_free; // first usable pid
200
201     int             i_pat_version_number;
202     ts_stream_t     pat;
203
204     int             i_pmt_version_number;
205     ts_stream_t     pmt;        // Up to now only one program
206
207     int             i_mpeg4_streams;
208
209     int             i_null_continuity_counter;  /* Needed ? */
210
211     /* for TS building */
212     int64_t             i_bitrate_min;
213     int64_t             i_bitrate_max;
214
215     int64_t             i_caching_delay;
216     int64_t             i_pcr_delay;
217
218     int64_t             i_dts_delay;
219
220     mtime_t             i_pcr;  /* last PCR emited */
221
222     csa_t               *csa;
223 };
224
225
226 /* Reserve a pid and return it */
227 static int  AllocatePID( sout_mux_sys_t *p_sys, int i_cat )
228 {
229     int i_pid;
230     if ( i_cat == VIDEO_ES && p_sys->i_pid_video )
231     {
232         i_pid = p_sys->i_pid_video;
233         p_sys->i_pid_video = 0;
234     }
235     else if ( i_cat == AUDIO_ES && p_sys->i_pid_audio )
236     {
237         i_pid = p_sys->i_pid_audio;
238         p_sys->i_pid_audio = 0;
239     }
240     else
241     {
242         i_pid = ++p_sys->i_pid_free;
243     }
244     return i_pid;
245 }
246
247 static void GetPAT( sout_mux_t *p_mux, sout_buffer_chain_t *c );
248 static void GetPMT( sout_mux_t *p_mux, sout_buffer_chain_t *c );
249
250 static sout_buffer_t *TSNew( sout_mux_t *p_mux, ts_stream_t *p_stream, vlc_bool_t b_pcr );
251 static void TSSetPCR( sout_buffer_t *p_ts, mtime_t i_dts );
252
253 static void PEStoTS  ( sout_instance_t *, sout_buffer_chain_t *, sout_buffer_t *, ts_stream_t * );
254
255 /*****************************************************************************
256  * Open:
257  *****************************************************************************/
258 static int Open( vlc_object_t *p_this )
259 {
260     sout_mux_t          *p_mux =(sout_mux_t*)p_this;
261     sout_mux_sys_t      *p_sys;
262     char                *val;
263
264     msg_Dbg( p_mux, "Open" );
265
266     p_sys = malloc( sizeof( sout_mux_sys_t ) );
267
268     p_mux->pf_capacity  = Capability;
269     p_mux->pf_addstream = AddStream;
270     p_mux->pf_delstream = DelStream;
271     p_mux->pf_mux       = Mux;
272     p_mux->p_sys        = p_sys;
273     p_mux->i_preheader  = 30; // really enough for a pes header
274
275     srand( (uint32_t)mdate() );
276
277     p_sys->i_audio_bound = 0;
278     p_sys->i_video_bound = 0;
279
280     p_sys->i_pat_version_number = rand() % 32;
281     p_sys->pat.i_pid = 0;
282     p_sys->pat.i_continuity_counter = 0;
283
284     p_sys->i_pmt_version_number = rand() % 32;
285     p_sys->pmt.i_pid = 0x42;
286     p_sys->pmt.i_continuity_counter = 0;
287
288     p_sys->i_pid_free = 0x43;
289
290     p_sys->i_pid_video = 0;
291     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "pid-video" ) ) )
292     {
293         p_sys->i_pid_video = strtol( val, NULL, 0 );
294         if ( p_sys->i_pid_video > p_sys->i_pid_free )
295         {
296             p_sys->i_pid_free = p_sys->i_pid_video + 1;
297         }
298     }
299     p_sys->i_pid_audio = 0;
300     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "pid-audio" ) ) )
301     {
302         p_sys->i_pid_audio = strtol( val, NULL, 0 );
303         if ( p_sys->i_pid_audio > p_sys->i_pid_free )
304         {
305             p_sys->i_pid_free = p_sys->i_pid_audio + 1;
306         }
307     }
308
309     p_sys->i_pcr_pid = 0x1fff;
310     p_sys->p_pcr_input = NULL;
311
312     p_sys->i_mpeg4_streams = 0;
313
314     p_sys->i_null_continuity_counter = 0;
315
316     /* Allow to create constrained stream */
317     p_sys->i_bitrate_min = 0;
318     p_sys->i_bitrate_max = 0;
319     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "bmin" ) ) )
320     {
321         p_sys->i_bitrate_min = atoll( val );
322     }
323     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "bmax" ) ) )
324     {
325         p_sys->i_bitrate_max = atoll( val );
326     }
327     if( p_sys->i_bitrate_min > 0 && p_sys->i_bitrate_max > 0 &&
328         p_sys->i_bitrate_min > p_sys->i_bitrate_max )
329     {
330         msg_Err( p_mux, "incompatible minimum and maximum bitrate, "
331                  "disabling bitrate control" );
332         p_sys->i_bitrate_min = 0;
333         p_sys->i_bitrate_max = 0;
334     }
335     if( p_sys->i_bitrate_min > 0 || p_sys->i_bitrate_max > 0 )
336     {
337         msg_Err( p_mux, "bmin and bmax no more supported (if you need them report it)" );
338     }
339
340     p_sys->i_caching_delay = 200000;
341     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "caching" ) ) )
342     {
343         p_sys->i_caching_delay = (int64_t)atoi( val ) * 1000;
344         if( p_sys->i_caching_delay <= 0 )
345         {
346             msg_Err( p_mux,
347                      "invalid caching ("I64Fd"ms) reseting to 200ms",
348                      p_sys->i_caching_delay / 1000 );
349             p_sys->i_caching_delay = 200000;
350         }
351     }
352     p_sys->i_pcr_delay = 30000;
353     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "pcr" ) ) )
354     {
355         p_sys->i_pcr_delay = (int64_t)atoi( val ) * 1000;
356         if( p_sys->i_pcr_delay <= 0 ||
357             p_sys->i_pcr_delay >= p_sys->i_caching_delay )
358         {
359             msg_Err( p_mux,
360                      "invalid pcr delay ("I64Fd"ms) reseting to 30ms",
361                      p_sys->i_pcr_delay / 1000 );
362             p_sys->i_pcr_delay = 30000;
363         }
364     }
365
366     msg_Dbg( p_mux, "caching="I64Fd" pcr="I64Fd,
367              p_sys->i_caching_delay, p_sys->i_pcr_delay );
368
369     p_sys->i_dts_delay = 200000;
370     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "dts-delay" ) ) )
371     {
372         p_sys->i_dts_delay = (int64_t)atoi( val ) * 1000;
373     }
374
375     /* for TS generation */
376     p_sys->i_pcr    = 0;
377
378     p_sys->csa      = NULL;
379     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "csa-ck" ) ) )
380     {
381         /* skip 0x */
382         if( val[0] == '0' && ( val[1] == 'x' || val[1] == 'X' ) )
383         {
384             val += 2;
385         }
386         if( strlen( val ) != 16 )
387         {
388             msg_Dbg( p_mux, "invalid csa ck (it must be 16 chars long)" );
389         }
390         else
391         {
392             /* Avoid using strtoll */
393             uint64_t i_ck;
394             uint8_t  ck[8];
395             int      i;
396
397             ck[0] = val[8];
398             val[8] = 0;
399             i_ck = strtol( val, NULL, 16 ) << 32;
400             val[8] = ck[0];
401             i_ck += strtol( &val[8], NULL, 16 );
402             for( i = 0; i < 8; i++ )
403             {
404                 ck[i] = ( i_ck >> ( 56 - 8*i) )&0xff;
405             }
406
407             msg_Dbg( p_mux, "using CSA scrambling with ck=%x:%x:%x:%x:%x:%x:%x:%x",
408                      ck[0], ck[1], ck[2], ck[3], ck[4], ck[5], ck[6], ck[7] );
409
410             p_sys->csa = csa_New();
411             csa_SetCW( p_sys->csa, ck, ck );
412         }
413     }
414     return VLC_SUCCESS;
415 }
416
417 /*****************************************************************************
418  * Close:
419  *****************************************************************************/
420 static void Close( vlc_object_t * p_this )
421 {
422     sout_mux_t          *p_mux = (sout_mux_t*)p_this;
423     sout_mux_sys_t      *p_sys = p_mux->p_sys;
424
425     msg_Dbg( p_mux, "Close" );
426     if( p_sys->csa )
427     {
428         csa_Delete( p_sys->csa );
429     }
430
431     free( p_sys );
432 }
433
434 /*****************************************************************************
435  * Capability:
436  *****************************************************************************/
437 static int Capability( sout_mux_t *p_mux, int i_query, void *p_args, void *p_answer )
438 {
439    switch( i_query )
440    {
441         case SOUT_MUX_CAP_GET_ADD_STREAM_ANY_TIME:
442             *(vlc_bool_t*)p_answer = VLC_TRUE;
443             return( SOUT_MUX_CAP_ERR_OK );
444         default:
445             return( SOUT_MUX_CAP_ERR_UNIMPLEMENTED );
446    }
447 }
448
449 /*****************************************************************************
450  * AddStream: called for each stream addition
451  *****************************************************************************/
452 static int AddStream( sout_mux_t *p_mux, sout_input_t *p_input )
453 {
454     sout_mux_sys_t      *p_sys = p_mux->p_sys;
455     ts_stream_t         *p_stream;
456
457     p_input->p_sys = (void*)p_stream = malloc( sizeof( ts_stream_t ) );
458
459     /* Init this new stream */
460     p_stream->i_pid = AllocatePID( p_sys, p_input->p_fmt->i_cat );
461     p_stream->i_continuity_counter    = 0;
462     p_stream->i_decoder_specific_info = 0;
463     p_stream->p_decoder_specific_info = NULL;
464
465     msg_Dbg( p_mux, "adding input codec=%4.4s pid=%d", (char*)&p_input->p_fmt->i_codec, p_stream->i_pid );
466
467     /* All others fields depand on codec */
468     switch( p_input->p_fmt->i_cat )
469     {
470         case VIDEO_ES:
471             switch( p_input->p_fmt->i_codec )
472             {
473                 case VLC_FOURCC( 'm', 'p','g', 'v' ):
474                     /* TODO: do we need to check MPEG-I/II ? */
475                     p_stream->i_stream_type = 0x02;
476                     p_stream->i_stream_id = 0xe0;
477                     break;
478                 case VLC_FOURCC( 'm', 'p','4', 'v' ):
479                     p_stream->i_stream_type = 0x10;
480                     p_stream->i_stream_id = 0xfa;
481                     p_sys->i_mpeg4_streams++;
482                     p_stream->i_es_id = p_stream->i_pid;
483                     break;
484                 /* XXX dirty dirty but somebody want that : using crapy MS-codec XXX */
485                 /* I didn't want to do that :P */
486                 case VLC_FOURCC( 'H', '2', '6', '3' ):
487                 case VLC_FOURCC( 'I', '2', '6', '3' ):
488                 case VLC_FOURCC( 'W', 'M', 'V', '2' ):
489                 case VLC_FOURCC( 'W', 'M', 'V', '1' ):
490                 case VLC_FOURCC( 'D', 'I', 'V', '3' ):
491                 case VLC_FOURCC( 'D', 'I', 'V', '2' ):
492                 case VLC_FOURCC( 'D', 'I', 'V', '1' ):
493                 case VLC_FOURCC( 'M', 'J', 'P', 'G' ):
494                     p_stream->i_stream_type = 0xa0; // private
495                     p_stream->i_stream_id = 0xa0;   // beurk
496                     p_stream->i_bih_codec  = p_input->p_fmt->i_codec;
497                     p_stream->i_bih_width  = p_input->p_fmt->video.i_width;
498                     p_stream->i_bih_height = p_input->p_fmt->video.i_height;
499                     break;
500                 default:
501                     free( p_stream );
502                     return VLC_EGENERIC;
503             }
504             p_sys->i_video_bound++;
505             break;
506
507         case AUDIO_ES:
508             switch( p_input->p_fmt->i_codec )
509             {
510                 case VLC_FOURCC( 'm', 'p','g', 'a' ):
511                     p_stream->i_stream_type = p_input->p_fmt->audio.i_rate >= 32000 ? 0x03 : 0x04;
512                     p_stream->i_stream_id = 0xc0;
513                     break;
514                 case VLC_FOURCC( 'a', '5','2', ' ' ):
515                     p_stream->i_stream_type = 0x81;
516                     p_stream->i_stream_id = 0xbd;
517                     break;
518                 case VLC_FOURCC( 'l', 'p','c', 'm' ):
519                     p_stream->i_stream_type = 0x83;
520                     p_stream->i_stream_id = 0xbd;
521                     break;
522                 case VLC_FOURCC( 'd', 't','s', ' ' ):
523                     p_stream->i_stream_type = 0x85;
524                     p_stream->i_stream_id = 0xbd;
525                     break;
526
527                 case VLC_FOURCC( 'm', 'p','4', 'a' ):
528                     p_stream->i_stream_type = 0x11;
529                     p_stream->i_stream_id = 0xfa;
530                     p_sys->i_mpeg4_streams++;
531                     p_stream->i_es_id = p_stream->i_pid;
532                     break;
533                 default:
534                     free( p_stream );
535                     return VLC_EGENERIC;
536             }
537             p_sys->i_audio_bound++;
538             break;
539
540         case SPU_ES:
541             switch( p_input->p_fmt->i_codec )
542             {
543                 case VLC_FOURCC( 's', 'p','u', ' ' ):
544                     p_stream->i_stream_type = 0x82;
545                     p_stream->i_stream_id = 0xbd;
546                     break;
547                 default:
548                     free( p_stream );
549                     return VLC_EGENERIC;
550             }
551             break;
552
553         default:
554             free( p_stream );
555             return VLC_EGENERIC;
556     }
557
558     p_stream->lang[0] =
559     p_stream->lang[1] =
560     p_stream->lang[2] = '\0';
561     if( p_input->p_fmt->psz_language )
562     {
563         char *psz = p_input->p_fmt->psz_language;
564         const iso639_lang_t *pl = NULL;
565
566         if( strlen( psz ) == 2 )
567         {
568             pl = GetLang_1( psz );
569         }
570         else if( strlen( psz ) == 3 )
571         {
572             pl = GetLang_2B( psz );
573             if( !strcmp( pl->psz_iso639_1, "??" ) )
574             {
575                 pl = GetLang_2T( psz );
576             }
577         }
578         if( pl && strcmp( pl->psz_iso639_1, "??" ) )
579         {
580             p_stream->lang[0] = pl->psz_iso639_2T[0];
581             p_stream->lang[1] = pl->psz_iso639_2T[1];
582             p_stream->lang[2] = pl->psz_iso639_2T[2];
583
584             msg_Dbg( p_mux, "    - lang=%c%c%c",
585                      p_stream->lang[0],
586                      p_stream->lang[1],
587                      p_stream->lang[2] );
588         }
589     }
590
591
592     /* Copy extra data (VOL for MPEG-4 and extra BitMapInfoHeader for VFW */
593     p_stream->i_decoder_specific_info = p_input->p_fmt->i_extra;
594     if( p_stream->i_decoder_specific_info > 0 )
595     {
596         p_stream->p_decoder_specific_info =
597             malloc( p_stream->i_decoder_specific_info );
598         memcpy( p_stream->p_decoder_specific_info,
599                 p_input->p_fmt->p_extra,
600                 p_input->p_fmt->i_extra );
601     }
602
603     /* Init pes chain */
604     BufferChainInit( &p_stream->chain_pes );
605     p_stream->i_pes_dts    = 0;
606     p_stream->i_pes_length = 0;
607     p_stream->i_pes_used   = 0;
608
609     /* We only change PMT version (PAT isn't changed) */
610     p_sys->i_pmt_version_number = ( p_sys->i_pmt_version_number + 1 )%32;
611
612     /* Update pcr_pid */
613     if( p_input->p_fmt->i_cat != SPU_ES &&
614         ( p_sys->i_pcr_pid == 0x1fff || p_input->p_fmt->i_cat == VIDEO_ES ) )
615     {
616         if( p_sys->p_pcr_input )
617         {
618             /* There was already a PCR stream, so clean context */
619             /* FIXME */
620         }
621         p_sys->i_pcr_pid   = p_stream->i_pid;
622         p_sys->p_pcr_input = p_input;
623
624         msg_Dbg( p_mux, "new PCR PID is %d", p_sys->i_pcr_pid );
625     }
626
627     return VLC_SUCCESS;
628 }
629
630 /*****************************************************************************
631  * DelStream: called before a stream deletion
632  *****************************************************************************/
633 static int DelStream( sout_mux_t *p_mux, sout_input_t *p_input )
634 {
635     sout_mux_sys_t  *p_sys = p_mux->p_sys;
636     ts_stream_t     *p_stream;
637     char            *val;
638
639     p_stream = (ts_stream_t*)p_input->p_sys;
640     msg_Dbg( p_mux, "removing input pid=%d", p_stream->i_pid );
641
642     if( p_sys->i_pcr_pid == p_stream->i_pid )
643     {
644         int i;
645
646         /* Find a new pcr stream (Prefer Video Stream) */
647         p_sys->i_pcr_pid = 0x1fff;
648         p_sys->p_pcr_input = NULL;
649         for( i = 0; i < p_mux->i_nb_inputs; i++ )
650         {
651             if( p_mux->pp_inputs[i] == p_input )
652             {
653                 continue;
654             }
655
656             if( p_mux->pp_inputs[i]->p_fmt->i_cat == VIDEO_ES )
657             {
658                 p_sys->i_pcr_pid  =
659                     ((ts_stream_t*)p_mux->pp_inputs[i]->p_sys)->i_pid;
660                 p_sys->p_pcr_input= p_mux->pp_inputs[i];
661                 break;
662             }
663             else if( p_mux->pp_inputs[i]->p_fmt->i_cat != SPU_ES &&
664                      p_sys->i_pcr_pid == 0x1fff )
665             {
666                 p_sys->i_pcr_pid  =
667                     ((ts_stream_t*)p_mux->pp_inputs[i]->p_sys)->i_pid;
668                 p_sys->p_pcr_input= p_mux->pp_inputs[i];
669             }
670         }
671         if( p_sys->p_pcr_input )
672         {
673             /* Empty TS buffer */
674             /* FIXME */
675         }
676         msg_Dbg( p_mux, "new PCR PID is %d", p_sys->i_pcr_pid );
677     }
678
679     /* Empty all data in chain_pes */
680     BufferChainClean( p_mux->p_sout, &p_stream->chain_pes );
681
682     if( p_stream->p_decoder_specific_info )
683     {
684         free( p_stream->p_decoder_specific_info );
685     }
686     if( p_stream->i_stream_id == 0xfa || p_stream->i_stream_id == 0xfb )
687     {
688         p_sys->i_mpeg4_streams--;
689     }
690     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "pid-video" ) ) )
691     {
692         int i_pid_video = strtol( val, NULL, 0 );
693         if ( i_pid_video == p_stream->i_pid )
694         {
695             p_sys->i_pid_video = i_pid_video;
696             msg_Dbg( p_mux, "freeing video PID %d", i_pid_video );
697         }
698     }
699     if( ( val = sout_cfg_find_value( p_mux->p_cfg, "pid-audio" ) ) )
700     {
701         int i_pid_audio = strtol( val, NULL, 0 );
702         if ( i_pid_audio == p_stream->i_pid )
703         {
704             p_sys->i_pid_audio = i_pid_audio;
705             msg_Dbg( p_mux, "freeing audio PID %d", i_pid_audio );
706         }
707     }
708     free( p_stream );
709
710     /* We only change PMT version (PAT isn't changed) */
711     p_sys->i_pmt_version_number++; p_sys->i_pmt_version_number %= 32;
712
713     return VLC_SUCCESS;
714 }
715
716 /*****************************************************************************
717  * Mux: Call each time there is new data for at least one stream
718  *****************************************************************************
719  *
720  *****************************************************************************/
721 static int Mux( sout_mux_t *p_mux )
722 {
723     sout_mux_sys_t  *p_sys = p_mux->p_sys;
724     ts_stream_t     *p_pcr_stream;
725
726     if( p_sys->i_pcr_pid == 0x1fff )
727     {
728         msg_Dbg( p_mux, "waiting PCR streams" );
729         msleep( 1000 );
730         return VLC_SUCCESS;
731     }
732     p_pcr_stream = (ts_stream_t*)p_sys->p_pcr_input->p_sys;
733
734     for( ;; )
735     {
736         sout_buffer_chain_t chain_ts;
737         int                 i_packet_count;
738         int                 i_packet_pos;
739         mtime_t             i_pcr_dts;
740         mtime_t             i_pcr_length;
741         int i;
742
743         /* 1: get enough PES packet for all input */
744         for( ;; )
745         {
746             vlc_bool_t b_ok = VLC_TRUE;
747             sout_buffer_t *p_data;
748
749             /* Accumulate enough data in the pcr stream (>i_caching_delay) */
750             /* Accumulate enough data in all other stream ( >= length of pcr) */
751             for( i = 0; i < p_mux->i_nb_inputs; i++ )
752             {
753                 sout_input_t *p_input = p_mux->pp_inputs[i];
754                 ts_stream_t *p_stream = (ts_stream_t*)p_input->p_sys;
755
756                 if( ( p_stream == p_pcr_stream && p_stream->i_pes_length <= p_sys->i_caching_delay ) ||
757                     p_stream->i_pes_dts + p_stream->i_pes_length < p_pcr_stream->i_pes_dts + p_pcr_stream->i_pes_length )
758                 {
759                     /* Need more data */
760                     if( p_input->p_fifo->i_depth <= 1 )
761                     {
762                         if( p_input->p_fmt->i_cat == AUDIO_ES ||
763                             p_input->p_fmt->i_cat == VIDEO_ES )
764                         {
765                             /* We need more data */
766                             return VLC_SUCCESS;
767                         }
768                         else if( p_input->p_fifo->i_depth <= 0 )
769                         {
770                             /* spu, only one packet is needed */
771                             continue;
772                         }
773                     }
774                     b_ok = VLC_FALSE;
775
776                     p_data = sout_FifoGet( p_input->p_fifo );
777                     if( p_input->p_fifo->i_depth > 0 )
778                     {
779                         sout_buffer_t *p_next = sout_FifoShow( p_input->p_fifo );
780
781                         p_data->i_length = p_next->i_dts - p_data->i_dts;
782                     }
783
784                     if( ( p_pcr_stream->i_pes_dts > 0 && p_data->i_dts - 2000000 > p_pcr_stream->i_pes_dts + p_pcr_stream->i_pes_length ) ||
785                         p_data->i_dts < p_stream->i_pes_dts ||
786                         ( p_stream->i_pes_dts > 0 && p_data->i_dts - 2000000 > p_stream->i_pes_dts + p_stream->i_pes_length ) )
787                     {
788                         msg_Warn( p_mux, "packet with too strange dts (dts=%lld,old=%lld,pcr=%lld)",
789                                   p_data->i_dts,
790                                   p_stream->i_pes_dts,
791                                   p_pcr_stream->i_pes_dts );
792                         sout_BufferDelete( p_mux->p_sout, p_data );
793
794                         BufferChainClean( p_mux->p_sout, &p_stream->chain_pes );
795                         p_stream->i_pes_dts = 0;
796                         p_stream->i_pes_used = 0;
797                         p_stream->i_pes_length = 0;
798
799                         BufferChainClean( p_mux->p_sout, &p_pcr_stream->chain_pes );
800                         p_pcr_stream->i_pes_dts = 0;
801                         p_pcr_stream->i_pes_used = 0;
802                         p_pcr_stream->i_pes_length = 0;
803
804                     }
805                     else
806                     {
807                         if( p_data->i_length < 0 || p_data->i_length > 2000000 )
808                         {
809                             /* FIXME choose a better value, but anyway we should never
810                              * have to do that */
811                             p_data->i_length = 1000;
812                         }
813                         p_stream->i_pes_length += p_data->i_length;
814                         if( p_stream->i_pes_dts == 0 )
815                         {
816                             p_stream->i_pes_dts = p_data->i_dts;
817                         }
818
819                         /* Convert to pes */
820                         E_( EStoPES )( p_mux->p_sout, &p_data, p_data, p_stream->i_stream_id, 1 );
821
822                         BufferChainAppend( &p_stream->chain_pes, p_data );
823                     }
824                 }
825             }
826
827             if( b_ok )
828             {
829                 break;
830             }
831         }
832
833         /* save */
834         i_pcr_dts      = p_pcr_stream->i_pes_dts;
835         i_pcr_length   = p_pcr_stream->i_pes_length;
836
837         /* msg_Dbg( p_mux, "starting muxing %lldms", i_pcr_length / 1000 ); */
838         /* 2: calculate non accurate total size of muxed ts */
839         i_packet_count = 0;
840         for( i = 0; i < p_mux->i_nb_inputs; i++ )
841         {
842             ts_stream_t *p_stream = (ts_stream_t*)p_mux->pp_inputs[i]->p_sys;
843             sout_buffer_t *p_pes;
844
845             /* False for pcr stream but it will be eough to do PCR algo */
846             for( p_pes = p_stream->chain_pes.p_first; p_pes != NULL; p_pes = p_pes->p_next )
847             {
848                 int i_size = p_pes->i_size;
849                 if( p_pes->i_dts + p_pes->i_length > p_pcr_stream->i_pes_dts + p_pcr_stream->i_pes_length )
850                 {
851                     mtime_t i_frag = p_pcr_stream->i_pes_dts + p_pcr_stream->i_pes_length - p_pes->i_dts;
852                     if( i_frag < 0 )
853                     {
854                         /* Next stream */
855                         break;
856                     }
857                     i_size = p_pes->i_size * i_frag / p_pes->i_length;
858                 }
859                 i_packet_count += ( i_size + 183 ) / 184;
860             }
861         }
862         /* add overhead for PCR (not really exact) */
863         i_packet_count += ( 8 * i_pcr_length / p_sys->i_pcr_delay + 175 ) / 176;
864
865
866         /* 3: mux PES into TS */
867         BufferChainInit( &chain_ts );
868         /* append PAT/PMT  -> FIXME with big pcr delay it won't have enough pat/pmt */
869         GetPAT( p_mux, &chain_ts);
870         GetPMT( p_mux, &chain_ts );
871         i_packet_pos = 0;
872         i_packet_count += chain_ts.i_depth;
873         /* msg_Dbg( p_mux, "estimated pck=%d", i_packet_count ); */
874
875         for( ;; )
876         {
877             int         i_stream;
878             mtime_t     i_dts;
879             ts_stream_t *p_stream;
880             sout_buffer_t *p_ts;
881             vlc_bool_t   b_pcr;
882
883             /* Select stream (lowest dts)*/
884             for( i = 0, i_stream = -1, i_dts = 0; i < p_mux->i_nb_inputs; i++ )
885             {
886                 p_stream = (ts_stream_t*)p_mux->pp_inputs[i]->p_sys;
887
888                 if( p_stream->i_pes_dts == 0 )
889                 {
890                     continue;
891                 }
892
893                 if( i_stream == -1 ||
894                     p_stream->i_pes_dts < i_dts )
895                 {
896                     i_stream = i;
897                     i_dts = p_stream->i_pes_dts;
898                 }
899             }
900             if( i_stream == -1 )
901             {
902                 break;
903             }
904             p_stream = (ts_stream_t*)p_mux->pp_inputs[i_stream]->p_sys;
905
906             /* do we need to issue pcr */
907             b_pcr = VLC_FALSE;
908             if( p_stream == p_pcr_stream &&
909                 i_pcr_dts + i_packet_pos * i_pcr_length / i_packet_count >= p_sys->i_pcr + p_sys->i_pcr_delay )
910             {
911                 b_pcr = VLC_TRUE;
912                 p_sys->i_pcr = i_pcr_dts + i_packet_pos * i_pcr_length / i_packet_count;
913             }
914
915             /* Build the TS packet */
916             p_ts = TSNew( p_mux, p_stream, b_pcr );
917             if( p_sys->csa )
918             {
919                 p_ts->i_flags |= SOUT_BUFFER_FLAGS_PRIVATE_CSA;
920             }
921             i_packet_pos++;
922
923             /* */
924             BufferChainAppend( &chain_ts, p_ts );
925         }
926
927         /* 4: date and send */
928         i_packet_count = chain_ts.i_depth;
929         /* msg_Dbg( p_mux, "real pck=%d", i_packet_count ); */
930         for( i = 0; i < i_packet_count; i++ )
931         {
932             sout_buffer_t *p_ts = BufferChainGet( &chain_ts );
933
934             p_ts->i_dts    = i_pcr_dts + i_pcr_length * i / i_packet_count;
935             p_ts->i_length = i_pcr_length / i_packet_count;
936
937             if( p_ts->i_flags&SOUT_BUFFER_FLAGS_PRIVATE_PCR )
938             {
939                 /* msg_Dbg( p_mux, "pcr=%lld ms", p_ts->i_dts / 1000 ); */
940                 TSSetPCR( p_ts, p_ts->i_dts - p_sys->i_dts_delay );
941             }
942             if( p_ts->i_flags&SOUT_BUFFER_FLAGS_PRIVATE_CSA )
943             {
944                 csa_Encrypt( p_sys->csa, p_ts->p_buffer, 0 );
945             }
946
947             /* latency */
948             p_ts->i_dts += 3*p_sys->i_caching_delay/2;
949
950             sout_AccessOutWrite( p_mux->p_access, p_ts );
951         }
952     }
953 }
954
955 static sout_buffer_t *TSNew( sout_mux_t *p_mux, ts_stream_t *p_stream, vlc_bool_t b_pcr )
956 {
957     sout_buffer_t *p_pes = p_stream->chain_pes.p_first;
958     sout_buffer_t *p_ts;
959
960     vlc_bool_t b_new_pes = VLC_FALSE;
961     vlc_bool_t b_adaptation_field = VLC_FALSE;
962
963     int        i_payload_max = 184 - ( b_pcr ? 8 : 0 );
964     int        i_payload;
965
966     if( p_stream->i_pes_used <= 0 )
967     {
968         b_new_pes = VLC_TRUE;
969     }
970     i_payload = __MIN( (int)p_pes->i_size - p_stream->i_pes_used, i_payload_max );
971
972     if( b_pcr || i_payload < i_payload_max )
973     {
974         b_adaptation_field = VLC_TRUE;
975     }
976
977     p_ts = sout_BufferNew( p_mux->p_sout, 188 );
978
979     p_ts->p_buffer[0] = 0x47;
980     p_ts->p_buffer[1] = ( b_new_pes ? 0x40 : 0x00 )|( ( p_stream->i_pid >> 8 )&0x1f );
981     p_ts->p_buffer[2] = p_stream->i_pid & 0xff;
982     p_ts->p_buffer[3] = ( b_adaptation_field ? 0x30 : 0x10 )|p_stream->i_continuity_counter;
983
984     p_stream->i_continuity_counter = (p_stream->i_continuity_counter+1)%16;
985
986     if( b_adaptation_field )
987     {
988         int i;
989
990         if( b_pcr )
991         {
992             int     i_stuffing = i_payload_max - i_payload;
993
994             p_ts->i_flags |= SOUT_BUFFER_FLAGS_PRIVATE_PCR;
995
996             p_ts->p_buffer[4] = 7 + i_stuffing;
997             p_ts->p_buffer[5] = 0x10;   /* flags */
998             p_ts->p_buffer[6] = ( 0 )&0xff;
999             p_ts->p_buffer[7] = ( 0 )&0xff;
1000             p_ts->p_buffer[8] = ( 0 )&0xff;
1001             p_ts->p_buffer[9] = ( 0 )&0xff;
1002             p_ts->p_buffer[10]= ( 0 )&0x80;
1003             p_ts->p_buffer[11]= 0;
1004
1005             for( i = 12; i < 12 + i_stuffing; i++ )
1006             {
1007                 p_ts->p_buffer[i] = 0xff;
1008             }
1009         }
1010         else
1011         {
1012             int i_stuffing = i_payload_max - i_payload;
1013
1014             p_ts->p_buffer[4] = i_stuffing - 1;
1015             if( i_stuffing > 1 )
1016             {
1017                 p_ts->p_buffer[5] = 0x00;
1018                 for( i = 6; i < 6 + i_stuffing - 2; i++ )
1019                 {
1020                     p_ts->p_buffer[i] = 0xff;
1021                 }
1022             }
1023         }
1024     }
1025
1026     /* copy payload */
1027     memcpy( &p_ts->p_buffer[188 - i_payload], &p_pes->p_buffer[p_stream->i_pes_used], i_payload );
1028
1029     p_stream->i_pes_used += i_payload;
1030     p_stream->i_pes_dts      = p_pes->i_dts + p_pes->i_length * p_stream->i_pes_used / p_pes->i_size;
1031     p_stream->i_pes_length  -= p_pes->i_length * i_payload / p_pes->i_size;
1032
1033     if( p_stream->i_pes_used >= (int)p_pes->i_size )
1034     {
1035         p_pes = BufferChainGet( &p_stream->chain_pes );
1036         sout_BufferDelete( p_mux->p_sout, p_pes );
1037
1038         p_pes = p_stream->chain_pes.p_first;
1039         if( p_pes )
1040         {
1041             p_stream->i_pes_dts    = p_pes->i_dts;
1042             p_stream->i_pes_length = 0;
1043             while( p_pes )
1044             {
1045                 p_stream->i_pes_length += p_pes->i_length;
1046
1047                 p_pes = p_pes->p_next;
1048             }
1049         }
1050         else
1051         {
1052             p_stream->i_pes_dts = 0;
1053             p_stream->i_pes_length = 0;
1054         }
1055         p_stream->i_pes_used = 0;
1056     }
1057
1058     return p_ts;
1059 }
1060
1061
1062 static void TSSetPCR( sout_buffer_t *p_ts, mtime_t i_dts )
1063 {
1064     mtime_t i_pcr = 9 * i_dts / 100;
1065
1066     p_ts->p_buffer[6]  = ( i_pcr >> 25 )&0xff;
1067     p_ts->p_buffer[7]  = ( i_pcr >> 17 )&0xff;
1068     p_ts->p_buffer[8]  = ( i_pcr >> 9  )&0xff;
1069     p_ts->p_buffer[9]  = ( i_pcr >> 1  )&0xff;
1070     p_ts->p_buffer[10]|= ( i_pcr << 7  )&0x80;
1071 }
1072
1073 #if 0
1074 static void TSSetConstraints( sout_mux_t *p_mux, sout_buffer_chain_t *c, mtime_t i_length, int i_bitrate_min, int i_bitrate_max )
1075 {
1076     sout_mux_sys_t  *p_sys = p_mux->p_sys;
1077     sout_buffer_chain_t s = *c;
1078
1079     int i_packets = 0;
1080     int i_packets_min = 0;
1081     int i_packets_max = 0;
1082
1083     if( i_length <= 0 )
1084     {
1085         return;
1086     }
1087
1088     i_packets     = c->i_depth;
1089     i_packets_min = ( (int64_t)i_bitrate_min * i_length / 8 / 1000000  + 187 ) / 188;
1090     i_packets_max = ( (int64_t)i_bitrate_max * i_length / 8 / 1000000  + 187 ) / 188;
1091
1092     if( i_packets < i_packets_min && i_packets_min > 0 )
1093     {
1094         sout_buffer_t *p_pk;
1095         int i_div = ( i_packets_min - i_packets ) / i_packets;
1096         int i_mod = ( i_packets_min - i_packets ) % i_packets;
1097         int i_rest = 0;
1098
1099         /* We need to pad with null packets (pid=0x1fff)
1100          * We try to melt null packets with true packets */
1101         msg_Dbg( p_mux,
1102                  "packets=%d but min=%d -> adding %d packets of padding",
1103                  i_packets, i_packets_min, i_packets_min - i_packets );
1104
1105         BufferChainInit( c );
1106         while( ( p_pk = BufferChainGet( &s ) ) )
1107         {
1108             int i, i_null;
1109
1110             BufferChainAppend( c, p_pk );
1111
1112             i_null = i_div + ( i_rest + i_mod ) / i_packets;
1113
1114             for( i = 0; i < i_null; i++ )
1115             {
1116                 sout_buffer_t *p_null;
1117
1118                 p_null = sout_BufferNew( p_mux->p_sout, 188 );
1119                 p_null->p_buffer[0] = 0x47;
1120                 p_null->p_buffer[1] = 0x1f;
1121                 p_null->p_buffer[2] = 0xff;
1122                 p_null->p_buffer[3] = 0x10 | p_sys->i_null_continuity_counter;
1123                 memset( &p_null->p_buffer[4], 0, 184 );
1124                 p_sys->i_null_continuity_counter =
1125                     ( p_sys->i_null_continuity_counter + 1 ) % 16;
1126
1127                 BufferChainAppend( c, p_null );
1128             }
1129
1130             i_rest = ( i_rest + i_mod ) % i_packets;
1131         }
1132     }
1133     else if( i_packets > i_packets_max && i_packets_max > 0 )
1134     {
1135         sout_buffer_t *p_pk;
1136         int           i;
1137
1138         /* Arg, we need to drop packets, I don't do something clever (like
1139          * dropping complete pid, b frames, ... ), I just get the right amount
1140          * of packets and discard the others */
1141         msg_Warn( p_mux,
1142                   "packets=%d but max=%d -> removing %d packets -> stream broken",
1143                   i_packets, i_packets_max, i_packets - i_packets_max );
1144
1145         BufferChainInit( c );
1146         for( i = 0; i < i_packets_max; i++ )
1147         {
1148             BufferChainAppend( c, BufferChainGet( &s ) );
1149         }
1150
1151         while( ( p_pk = BufferChainGet( &s ) ) )
1152         {
1153             sout_BufferDelete( p_mux->p_sout, p_pk );
1154         }
1155     }
1156 }
1157 #endif
1158
1159 static void PEStoTS( sout_instance_t *p_sout,
1160                      sout_buffer_chain_t *c, sout_buffer_t *p_pes,
1161                      ts_stream_t *p_stream )
1162 {
1163     uint8_t *p_data;
1164     int     i_size;
1165     int     b_new_pes;
1166
1167     /* get PES total size */
1168     i_size = p_pes->i_size;
1169     p_data = p_pes->p_buffer;
1170
1171     b_new_pes = VLC_TRUE;
1172
1173     for( ;; )
1174     {
1175         int           b_adaptation_field;
1176         int           i_copy;
1177         sout_buffer_t *p_ts;
1178
1179         p_ts = sout_BufferNew( p_sout, 188 );
1180         /* write header
1181          * 8b   0x47    sync byte
1182          * 1b           transport_error_indicator
1183          * 1b           payload_unit_start
1184          * 1b           transport_priority
1185          * 13b          pid
1186          * 2b           transport_scrambling_control
1187          * 2b           if adaptation_field 0x03 else 0x01
1188          * 4b           continuity_counter
1189          */
1190
1191         i_copy    = __MIN( i_size, 184 );
1192         b_adaptation_field = i_size < 184 ? VLC_TRUE : VLC_FALSE;
1193
1194         p_ts->p_buffer[0] = 0x47;
1195         p_ts->p_buffer[1] = ( b_new_pes ? 0x40 : 0x00 )|
1196                             ( ( p_stream->i_pid >> 8 )&0x1f );
1197         p_ts->p_buffer[2] = p_stream->i_pid & 0xff;
1198         p_ts->p_buffer[3] = ( b_adaptation_field ? 0x30 : 0x10 )|
1199                             p_stream->i_continuity_counter;
1200
1201         b_new_pes = VLC_FALSE;
1202         p_stream->i_continuity_counter = (p_stream->i_continuity_counter+1)%16;
1203
1204         if( b_adaptation_field )
1205         {
1206             int i_stuffing = 184 - i_copy;
1207             int i;
1208
1209             p_ts->p_buffer[4] = i_stuffing - 1;
1210             if( i_stuffing > 1 )
1211             {
1212                 p_ts->p_buffer[5] = 0x00;
1213                 for( i = 6; i < 6 + i_stuffing - 2; i++ )
1214                 {
1215                     p_ts->p_buffer[i] = 0xff;
1216                 }
1217             }
1218         }
1219         /* copy payload */
1220         memcpy( &p_ts->p_buffer[188 - i_copy], p_data, i_copy );
1221         p_data += i_copy;
1222         i_size -= i_copy;
1223
1224         BufferChainAppend( c, p_ts );
1225
1226         if( i_size <= 0 )
1227         {
1228             sout_buffer_t *p_next = p_pes->p_next;
1229
1230             p_pes->p_next = NULL;
1231             sout_BufferDelete( p_sout, p_pes );
1232             if( p_next == NULL )
1233             {
1234                 break;
1235             }
1236             b_new_pes = VLC_TRUE;
1237             p_pes = p_next;
1238             i_size = p_pes->i_size;
1239             p_data = p_pes->p_buffer;
1240         }
1241     }
1242
1243     return;
1244 }
1245
1246 #if defined MODULE_NAME_IS_mux_ts
1247 static uint32_t CalculateCRC( uint8_t *p_begin, int i_count )
1248 {
1249     static uint32_t CRC32[256] =
1250     {
1251         0x00000000, 0x04c11db7, 0x09823b6e, 0x0d4326d9,
1252         0x130476dc, 0x17c56b6b, 0x1a864db2, 0x1e475005,
1253         0x2608edb8, 0x22c9f00f, 0x2f8ad6d6, 0x2b4bcb61,
1254         0x350c9b64, 0x31cd86d3, 0x3c8ea00a, 0x384fbdbd,
1255         0x4c11db70, 0x48d0c6c7, 0x4593e01e, 0x4152fda9,
1256         0x5f15adac, 0x5bd4b01b, 0x569796c2, 0x52568b75,
1257         0x6a1936c8, 0x6ed82b7f, 0x639b0da6, 0x675a1011,
1258         0x791d4014, 0x7ddc5da3, 0x709f7b7a, 0x745e66cd,
1259         0x9823b6e0, 0x9ce2ab57, 0x91a18d8e, 0x95609039,
1260         0x8b27c03c, 0x8fe6dd8b, 0x82a5fb52, 0x8664e6e5,
1261         0xbe2b5b58, 0xbaea46ef, 0xb7a96036, 0xb3687d81,
1262         0xad2f2d84, 0xa9ee3033, 0xa4ad16ea, 0xa06c0b5d,
1263         0xd4326d90, 0xd0f37027, 0xddb056fe, 0xd9714b49,
1264         0xc7361b4c, 0xc3f706fb, 0xceb42022, 0xca753d95,
1265         0xf23a8028, 0xf6fb9d9f, 0xfbb8bb46, 0xff79a6f1,
1266         0xe13ef6f4, 0xe5ffeb43, 0xe8bccd9a, 0xec7dd02d,
1267         0x34867077, 0x30476dc0, 0x3d044b19, 0x39c556ae,
1268         0x278206ab, 0x23431b1c, 0x2e003dc5, 0x2ac12072,
1269         0x128e9dcf, 0x164f8078, 0x1b0ca6a1, 0x1fcdbb16,
1270         0x018aeb13, 0x054bf6a4, 0x0808d07d, 0x0cc9cdca,
1271         0x7897ab07, 0x7c56b6b0, 0x71159069, 0x75d48dde,
1272         0x6b93dddb, 0x6f52c06c, 0x6211e6b5, 0x66d0fb02,
1273         0x5e9f46bf, 0x5a5e5b08, 0x571d7dd1, 0x53dc6066,
1274         0x4d9b3063, 0x495a2dd4, 0x44190b0d, 0x40d816ba,
1275         0xaca5c697, 0xa864db20, 0xa527fdf9, 0xa1e6e04e,
1276         0xbfa1b04b, 0xbb60adfc, 0xb6238b25, 0xb2e29692,
1277         0x8aad2b2f, 0x8e6c3698, 0x832f1041, 0x87ee0df6,
1278         0x99a95df3, 0x9d684044, 0x902b669d, 0x94ea7b2a,
1279         0xe0b41de7, 0xe4750050, 0xe9362689, 0xedf73b3e,
1280         0xf3b06b3b, 0xf771768c, 0xfa325055, 0xfef34de2,
1281         0xc6bcf05f, 0xc27dede8, 0xcf3ecb31, 0xcbffd686,
1282         0xd5b88683, 0xd1799b34, 0xdc3abded, 0xd8fba05a,
1283         0x690ce0ee, 0x6dcdfd59, 0x608edb80, 0x644fc637,
1284         0x7a089632, 0x7ec98b85, 0x738aad5c, 0x774bb0eb,
1285         0x4f040d56, 0x4bc510e1, 0x46863638, 0x42472b8f,
1286         0x5c007b8a, 0x58c1663d, 0x558240e4, 0x51435d53,
1287         0x251d3b9e, 0x21dc2629, 0x2c9f00f0, 0x285e1d47,
1288         0x36194d42, 0x32d850f5, 0x3f9b762c, 0x3b5a6b9b,
1289         0x0315d626, 0x07d4cb91, 0x0a97ed48, 0x0e56f0ff,
1290         0x1011a0fa, 0x14d0bd4d, 0x19939b94, 0x1d528623,
1291         0xf12f560e, 0xf5ee4bb9, 0xf8ad6d60, 0xfc6c70d7,
1292         0xe22b20d2, 0xe6ea3d65, 0xeba91bbc, 0xef68060b,
1293         0xd727bbb6, 0xd3e6a601, 0xdea580d8, 0xda649d6f,
1294         0xc423cd6a, 0xc0e2d0dd, 0xcda1f604, 0xc960ebb3,
1295         0xbd3e8d7e, 0xb9ff90c9, 0xb4bcb610, 0xb07daba7,
1296         0xae3afba2, 0xaafbe615, 0xa7b8c0cc, 0xa379dd7b,
1297         0x9b3660c6, 0x9ff77d71, 0x92b45ba8, 0x9675461f,
1298         0x8832161a, 0x8cf30bad, 0x81b02d74, 0x857130c3,
1299         0x5d8a9099, 0x594b8d2e, 0x5408abf7, 0x50c9b640,
1300         0x4e8ee645, 0x4a4ffbf2, 0x470cdd2b, 0x43cdc09c,
1301         0x7b827d21, 0x7f436096, 0x7200464f, 0x76c15bf8,
1302         0x68860bfd, 0x6c47164a, 0x61043093, 0x65c52d24,
1303         0x119b4be9, 0x155a565e, 0x18197087, 0x1cd86d30,
1304         0x029f3d35, 0x065e2082, 0x0b1d065b, 0x0fdc1bec,
1305         0x3793a651, 0x3352bbe6, 0x3e119d3f, 0x3ad08088,
1306         0x2497d08d, 0x2056cd3a, 0x2d15ebe3, 0x29d4f654,
1307         0xc5a92679, 0xc1683bce, 0xcc2b1d17, 0xc8ea00a0,
1308         0xd6ad50a5, 0xd26c4d12, 0xdf2f6bcb, 0xdbee767c,
1309         0xe3a1cbc1, 0xe760d676, 0xea23f0af, 0xeee2ed18,
1310         0xf0a5bd1d, 0xf464a0aa, 0xf9278673, 0xfde69bc4,
1311         0x89b8fd09, 0x8d79e0be, 0x803ac667, 0x84fbdbd0,
1312         0x9abc8bd5, 0x9e7d9662, 0x933eb0bb, 0x97ffad0c,
1313         0xafb010b1, 0xab710d06, 0xa6322bdf, 0xa2f33668,
1314         0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4
1315     };
1316
1317     uint32_t i_crc = 0xffffffff;
1318
1319     /* Calculate the CRC */
1320     while( i_count > 0 )
1321     {
1322         i_crc = (i_crc<<8) ^ CRC32[ (i_crc>>24) ^ ((uint32_t)*p_begin) ];
1323         p_begin++;
1324         i_count--;
1325     }
1326
1327     return( i_crc );
1328 }
1329
1330 static void GetPAT( sout_mux_t *p_mux,
1331                     sout_buffer_chain_t *c )
1332 {
1333     sout_mux_sys_t      *p_sys = p_mux->p_sys;
1334     sout_buffer_t       *p_pat;
1335     bits_buffer_t bits;
1336
1337     p_pat = sout_BufferNew( p_mux->p_sout, 1024 );
1338
1339     p_pat->i_pts = 0;
1340     p_pat->i_dts = 0;
1341     p_pat->i_length = 0;
1342
1343     bits_initwrite( &bits, 1024, p_pat->p_buffer );
1344
1345     bits_write( &bits, 8, 0 );      // pointer
1346     bits_write( &bits, 8, 0x00 );   // table id
1347     bits_write( &bits, 1,  1 );     // section_syntax_indicator
1348     bits_write( &bits, 1,  0 );     // 0
1349     bits_write( &bits, 2,  0x03 );     // reserved FIXME
1350     bits_write( &bits, 12, 13 );    // XXX for one program only XXX 
1351     bits_write( &bits, 16, 0x01 );  // FIXME stream id
1352     bits_write( &bits, 2,  0x03 );     //  FIXME
1353     bits_write( &bits, 5,  p_sys->i_pat_version_number );
1354     bits_write( &bits, 1,  1 );     // current_next_indicator
1355     bits_write( &bits, 8,  0 );     // section number
1356     bits_write( &bits, 8,  0 );     // last section number
1357
1358     bits_write( &bits, 16, 1 );     // program number
1359     bits_write( &bits,  3, 0x07 );     // reserved
1360     bits_write( &bits, 13, p_sys->pmt.i_pid );  // program map pid
1361
1362     bits_write( &bits, 32, CalculateCRC( bits.p_data + 1, bits.i_data - 1) );
1363
1364     p_pat->i_size = bits.i_data;
1365
1366     PEStoTS( p_mux->p_sout, c, p_pat, &p_sys->pat );
1367 }
1368
1369 static void GetPMT( sout_mux_t *p_mux,
1370                     sout_buffer_chain_t *c )
1371 {
1372     sout_mux_sys_t      *p_sys = p_mux->p_sys;
1373     sout_buffer_t       *p_pmt;
1374     bits_buffer_t bits;
1375     int           i_stream;
1376
1377     p_pmt = sout_BufferNew( p_mux->p_sout, 1024 );
1378
1379     p_pmt->i_pts = 0;
1380     p_pmt->i_dts = 0;
1381     p_pmt->i_length = 0;
1382
1383     bits_initwrite( &bits, 1024, p_pmt->p_buffer );
1384
1385     bits_write( &bits, 8, 0 );      // pointer
1386     bits_write( &bits, 8, 0x02 );   // table id
1387     bits_write( &bits, 1,  1 );     // section_syntax_indicator
1388     bits_write( &bits, 1,  0 );     // 0
1389     bits_write( &bits, 2,  0 );     // reserved FIXME
1390     bits_write( &bits, 12, 13 + 5 * p_mux->i_nb_inputs );
1391     bits_write( &bits, 16, 1 );     // FIXME program number
1392     bits_write( &bits, 2,  0 );     //  FIXME
1393     bits_write( &bits, 5,  p_sys->i_pmt_version_number );
1394     bits_write( &bits, 1,  1 );     // current_next_indicator
1395     bits_write( &bits, 8,  0 );     // section number
1396     bits_write( &bits, 8,  0 );     // last section number
1397
1398     bits_write( &bits,  3, 0 );     // reserved
1399
1400     bits_write( &bits, 13, p_sys->i_pcr_pid );     //  FIXME FXIME PCR_PID FIXME
1401     bits_write( &bits,  4, 0 );     // reserved FIXME
1402
1403     bits_write( &bits, 12, 0 );    // program info len FIXME
1404
1405     for( i_stream = 0; i_stream < p_mux->i_nb_inputs; i_stream++ )
1406     {
1407         ts_stream_t *p_stream;
1408
1409         p_stream = (ts_stream_t*)p_mux->pp_inputs[i_stream]->p_sys;
1410
1411         bits_write( &bits,  8, p_stream->i_stream_type ); // stream_type
1412         bits_write( &bits,  3, 0 );                 // reserved
1413         bits_write( &bits, 13, p_stream->i_pid );   // es pid
1414         bits_write( &bits,  4, 0 );                 //reserved
1415         bits_write( &bits, 12, 0 );                 // es info len FIXME
1416     }
1417
1418     bits_write( &bits, 32, CalculateCRC( bits.p_data + 1, bits.i_data - 1) );
1419
1420     p_pmt->i_size = bits.i_data;
1421
1422     PEStoTS( p_mux->p_sout, c, p_pmt, &p_sys->pmt );
1423 }
1424 #elif defined MODULE_NAME_IS_mux_ts_dvbpsi
1425
1426 static sout_buffer_t *WritePSISection( sout_instance_t *p_sout,
1427                                        dvbpsi_psi_section_t* p_section )
1428 {
1429     sout_buffer_t   *p_psi, *p_first = NULL;
1430
1431
1432     while( p_section )
1433     {
1434         int             i_size;
1435
1436         i_size =  (uint32_t)( p_section->p_payload_end - p_section->p_data )+
1437                   ( p_section->b_syntax_indicator ? 4 : 0 );
1438
1439         p_psi = sout_BufferNew( p_sout, i_size + 1 );
1440         p_psi->i_pts = 0;
1441         p_psi->i_dts = 0;
1442         p_psi->i_length = 0;
1443         p_psi->i_size = i_size + 1;
1444
1445         p_psi->p_buffer[0] = 0; // pointer
1446         memcpy( p_psi->p_buffer + 1,
1447                 p_section->p_data,
1448                 i_size );
1449
1450         sout_BufferChain( &p_first, p_psi );
1451
1452         p_section = p_section->p_next;
1453     }
1454
1455     return( p_first );
1456 }
1457
1458 static void GetPAT( sout_mux_t *p_mux,
1459                     sout_buffer_chain_t *c )
1460 {
1461     sout_mux_sys_t       *p_sys = p_mux->p_sys;
1462     sout_buffer_t        *p_pat;
1463     dvbpsi_pat_t         pat;
1464     dvbpsi_psi_section_t *p_section;
1465
1466     dvbpsi_InitPAT( &pat,
1467                     0x01,    // i_ts_id
1468                     p_sys->i_pat_version_number,
1469                     1 );      // b_current_next
1470     /* add all program (only one) */
1471     dvbpsi_PATAddProgram( &pat,
1472                           1,                    // i_number
1473                           p_sys->pmt.i_pid );   // i_pid
1474
1475     p_section = dvbpsi_GenPATSections( &pat,
1476                                        0 );     // max program per section
1477
1478     p_pat = WritePSISection( p_mux->p_sout, p_section );
1479
1480     PEStoTS( p_mux->p_sout, c, p_pat, &p_sys->pat );
1481
1482     dvbpsi_DeletePSISections( p_section );
1483     dvbpsi_EmptyPAT( &pat );
1484 }
1485
1486 static uint32_t GetDescriptorLength24b( int i_length )
1487 {
1488     uint32_t    i_l1, i_l2, i_l3;
1489
1490     i_l1 = i_length&0x7f;
1491     i_l2 = ( i_length >> 7 )&0x7f;
1492     i_l3 = ( i_length >> 14 )&0x7f;
1493
1494     return( 0x808000 | ( i_l3 << 16 ) | ( i_l2 << 8 ) | i_l1 );
1495 }
1496
1497 static void GetPMT( sout_mux_t *p_mux,
1498                     sout_buffer_chain_t *c )
1499 {
1500     sout_mux_sys_t  *p_sys = p_mux->p_sys;
1501     sout_buffer_t   *p_pmt;
1502
1503     dvbpsi_pmt_t        pmt;
1504     dvbpsi_pmt_es_t     *p_es;
1505     dvbpsi_psi_section_t *p_section;
1506
1507     int                 i_stream;
1508
1509     dvbpsi_InitPMT( &pmt,
1510                     0x01,   // program number
1511                     p_sys->i_pmt_version_number,
1512                     1,      // b_current_next
1513                     p_sys->i_pcr_pid );
1514
1515     if( p_sys->i_mpeg4_streams > 0 )
1516     {
1517         uint8_t iod[4096];
1518         bits_buffer_t bits;
1519         bits_buffer_t bits_fix_IOD;
1520
1521         /* Make valgrind happy : it works at byte level not bit one so
1522          * bit_write confuse it (but DON'T CHANGE the way that bit_write is
1523          * working (needed when fixing some bits) */
1524         memset( iod, 0, 4096 );
1525
1526         bits_initwrite( &bits, 4096, iod );
1527         // IOD_label
1528         bits_write( &bits, 8,   0x01 );
1529         // InitialObjectDescriptor
1530         bits_align( &bits );
1531         bits_write( &bits, 8,   0x02 );     // tag
1532         bits_fix_IOD = bits;    // save states to fix length later
1533         bits_write( &bits, 24,  GetDescriptorLength24b( 0 ) ); // variable length (fixed later)
1534         bits_write( &bits, 10,  0x01 );     // ObjectDescriptorID
1535         bits_write( &bits, 1,   0x00 );     // URL Flag
1536         bits_write( &bits, 1,   0x00 );     // includeInlineProfileLevelFlag
1537         bits_write( &bits, 4,   0x0f );     // reserved
1538         bits_write( &bits, 8,   0xff );     // ODProfile (no ODcapability )
1539         bits_write( &bits, 8,   0xff );     // sceneProfile
1540         bits_write( &bits, 8,   0xfe );     // audioProfile (unspecified)
1541         bits_write( &bits, 8,   0xfe );     // visualProfile( // )
1542         bits_write( &bits, 8,   0xff );     // graphicProfile (no )
1543         for( i_stream = 0; i_stream < p_mux->i_nb_inputs; i_stream++ )
1544         {
1545             ts_stream_t *p_stream;
1546             p_stream = (ts_stream_t*)p_mux->pp_inputs[i_stream]->p_sys;
1547
1548             if( p_stream->i_stream_id == 0xfa || p_stream->i_stream_id == 0xfb )
1549             {
1550                 bits_buffer_t bits_fix_ESDescr, bits_fix_Decoder;
1551                 /* ES descriptor */
1552                 bits_align( &bits );
1553                 bits_write( &bits, 8,   0x03 );     // ES_DescrTag
1554                 bits_fix_ESDescr = bits;
1555                 bits_write( &bits, 24,  GetDescriptorLength24b( 0 ) ); // variable size
1556                 bits_write( &bits, 16,  p_stream->i_es_id );
1557                 bits_write( &bits, 1,   0x00 );     // streamDependency
1558                 bits_write( &bits, 1,   0x00 );     // URL Flag
1559                 bits_write( &bits, 1,   0x00 );     // OCRStreamFlag
1560                 bits_write( &bits, 5,   0x1f );     // streamPriority
1561
1562                     // DecoderConfigDesciptor
1563                 bits_align( &bits );
1564                 bits_write( &bits, 8,   0x04 ); // DecoderConfigDescrTag
1565                 bits_fix_Decoder = bits;
1566                 bits_write( &bits, 24,  GetDescriptorLength24b( 0 ) );
1567                 if( p_stream->i_stream_type == 0x10 )
1568                 {
1569                     bits_write( &bits, 8, 0x20 );   // Visual 14496-2
1570                     bits_write( &bits, 6, 0x04 );   // VisualStream
1571                 }
1572                 else if( p_stream->i_stream_type == 0x11 )
1573                 {
1574                     bits_write( &bits, 8, 0x40 );   // Audio 14496-3
1575                     bits_write( &bits, 6, 0x05 );   // AudioStream
1576                 }
1577                 else
1578                 {
1579                     bits_write( &bits, 8, 0x00 );
1580                     bits_write( &bits, 6, 0x00 );
1581
1582                     msg_Err( p_mux->p_sout,"Unsupported stream_type => broken IOD");
1583                 }
1584                 bits_write( &bits, 1,   0x00 );     // UpStream
1585                 bits_write( &bits, 1,   0x01 );     // reserved
1586                 bits_write( &bits, 24,  1024 * 1024 );  // bufferSizeDB
1587                 bits_write( &bits, 32,  0x7fffffff );   // maxBitrate
1588                 bits_write( &bits, 32,  0 );            // avgBitrate
1589
1590                 if( p_stream->i_decoder_specific_info > 0 )
1591                 {
1592                     int i;
1593                     // DecoderSpecificInfo
1594                     bits_align( &bits );
1595                     bits_write( &bits, 8,   0x05 ); // tag
1596                     bits_write( &bits, 24,
1597                                 GetDescriptorLength24b( p_stream->i_decoder_specific_info ) );
1598                     for( i = 0; i < p_stream->i_decoder_specific_info; i++ )
1599                     {
1600                         bits_write( &bits, 8,   ((uint8_t*)p_stream->p_decoder_specific_info)[i] );
1601                     }
1602                 }
1603                 /* fix Decoder length */
1604                 bits_write( &bits_fix_Decoder, 24,
1605                             GetDescriptorLength24b( bits.i_data - bits_fix_Decoder.i_data - 3 ) );
1606
1607                 /* SLConfigDescriptor : predifined (0x01) */
1608                 bits_align( &bits );
1609                 bits_write( &bits, 8,   0x06 ); // tag
1610                 bits_write( &bits, 24,  GetDescriptorLength24b( 8 ) );
1611                 bits_write( &bits, 8,   0x01 ); // predefined
1612                 bits_write( &bits, 1,   0 );   // durationFlag
1613                 bits_write( &bits, 32,  0 );   // OCRResolution
1614                 bits_write( &bits, 8,   0 );   // OCRLength
1615                 bits_write( &bits, 8,   0 );   // InstantBitrateLength
1616                 bits_align( &bits );
1617
1618                 /* fix ESDescr length */
1619                 bits_write( &bits_fix_ESDescr, 24,
1620                             GetDescriptorLength24b( bits.i_data - bits_fix_ESDescr.i_data - 3 ) );
1621             }
1622         }
1623         bits_align( &bits );
1624         /* fix IOD length */
1625         bits_write( &bits_fix_IOD, 24,
1626                     GetDescriptorLength24b( bits.i_data - bits_fix_IOD.i_data - 3 ) );
1627         dvbpsi_PMTAddDescriptor( &pmt,
1628                                  0x1d,
1629                                  bits.i_data,
1630                                  bits.p_data );
1631     }
1632
1633     for( i_stream = 0; i_stream < p_mux->i_nb_inputs; i_stream++ )
1634     {
1635         ts_stream_t *p_stream;
1636
1637         p_stream = (ts_stream_t*)p_mux->pp_inputs[i_stream]->p_sys;
1638
1639         p_es = dvbpsi_PMTAddES( &pmt,
1640                                 p_stream->i_stream_type,
1641                                 p_stream->i_pid );
1642         if( p_stream->i_stream_id == 0xfa || p_stream->i_stream_id == 0xfb )
1643         {
1644             uint8_t     es_id[2];
1645
1646             /* SL descriptor */
1647             es_id[0] = (p_stream->i_es_id >> 8)&0xff;
1648             es_id[1] = (p_stream->i_es_id)&0xff;
1649             dvbpsi_PMTESAddDescriptor( p_es, 0x1f, 2, es_id );
1650         }
1651         else if( p_stream->i_stream_type == 0xa0 )
1652         {
1653             uint8_t     data[512];
1654             int         i_extra = __MIN( p_stream->i_decoder_specific_info,
1655                                         502 );
1656
1657             /* private DIV3 descripor */
1658             memcpy( &data[0], &p_stream->i_bih_codec, 4 );
1659             data[4] = ( p_stream->i_bih_width >> 8 )&0xff;
1660             data[5] = ( p_stream->i_bih_width      )&0xff;
1661             data[6] = ( p_stream->i_bih_height>> 8 )&0xff;
1662             data[7] = ( p_stream->i_bih_height     )&0xff;
1663             data[8] = ( i_extra >> 8 )&0xff;
1664             data[9] = ( i_extra      )&0xff;
1665             if( i_extra > 0 )
1666             {
1667                 memcpy( &data[10], p_stream->p_decoder_specific_info, i_extra );
1668             }
1669
1670             /* 0xa0 is private */
1671             dvbpsi_PMTESAddDescriptor( p_es, 0xa0, i_extra  + 10, data );
1672         }
1673         else if( p_stream->i_stream_type == 0x81 )
1674         {
1675             uint8_t format[4] = { 0x41, 0x43, 0x2d, 0x33 };
1676
1677             /* "registration" descriptor : "AC-3" */
1678             dvbpsi_PMTESAddDescriptor( p_es, 0x05, 4, format );
1679         }
1680
1681         if( p_stream->lang[0] != 0 )
1682         {
1683             uint8_t data[4];
1684
1685             /* I construct the content myself, way faster than looking at
1686              * over complicated/mind broken libdvbpsi way */
1687             data[0] = p_stream->lang[0];
1688             data[1] = p_stream->lang[1];
1689             data[2] = p_stream->lang[2];
1690             data[3] = 0x00; /* audio type: 0x00 undefined */
1691
1692             dvbpsi_PMTESAddDescriptor( p_es, 0x0a, 4, data );
1693         }
1694     }
1695
1696     p_section = dvbpsi_GenPMTSections( &pmt );
1697
1698     p_pmt = WritePSISection( p_mux->p_sout, p_section );
1699
1700     PEStoTS( p_mux->p_sout, c, p_pmt, &p_sys->pmt );
1701
1702     dvbpsi_DeletePSISections( p_section );
1703     dvbpsi_EmptyPMT( &pmt );
1704 }
1705
1706 #endif
1707