caopengllayer: correct vertical alignment
[vlc.git] / modules / mux / mpeg / tables.c
blob9cab7d7fae4214d092ba0b743ea8840e64aa9259
1 /*****************************************************************************
2 * tables.c
3 *****************************************************************************
4 * Copyright (C) 2001-2005, 2015 VLC authors and VideoLAN
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU Lesser General Public License as published by
8 * the Free Software Foundation; either version 2.1 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public License
17 * along with this program; if not, write to the Free Software Foundation,
18 * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
19 *****************************************************************************/
20 #ifdef HAVE_CONFIG_H
21 # include "config.h"
22 #endif
24 #include <vlc_common.h>
25 #include <vlc_block.h>
26 #include <vlc_es.h>
28 # include <dvbpsi/dvbpsi.h>
29 # include <dvbpsi/demux.h>
30 # include <dvbpsi/descriptor.h>
31 # include <dvbpsi/pat.h>
32 # include <dvbpsi/pmt.h>
33 # include <dvbpsi/sdt.h>
34 # include <dvbpsi/dr.h>
35 # include <dvbpsi/psi.h>
37 #include "dvbpsi_compat.h"
39 #include "streams.h"
40 #include "tsutil.h"
41 #include "tables.h"
42 #include "bits.h"
43 #include "pes.h"
45 #include "../../codec/jpeg2000.h"
47 #include <assert.h>
49 block_t *WritePSISection( dvbpsi_psi_section_t* p_section )
51 block_t *p_psi, *p_first = NULL;
53 while( p_section )
55 int i_size = (uint32_t)(p_section->p_payload_end - p_section->p_data) +
56 (p_section->b_syntax_indicator ? 4 : 0);
58 p_psi = block_Alloc( i_size + 1 );
59 if( !p_psi )
60 goto error;
61 p_psi->i_pts = 0;
62 p_psi->i_dts = 0;
63 p_psi->i_length = 0;
64 p_psi->i_buffer = i_size + 1;
66 p_psi->p_buffer[0] = 0; /* pointer */
67 memcpy( p_psi->p_buffer + 1,
68 p_section->p_data,
69 i_size );
71 block_ChainAppend( &p_first, p_psi );
73 p_section = p_section->p_next;
76 return( p_first );
78 error:
79 if( p_first )
80 block_ChainRelease( p_first );
81 return NULL;
84 void BuildPAT( dvbpsi_t *p_dvbpsi,
85 void *p_opaque, PEStoTSCallback pf_callback,
86 int i_tsid, int i_pat_version_number,
87 tsmux_stream_t *p_pat,
88 unsigned i_programs, tsmux_stream_t *p_pmt, const int *pi_programs_number )
90 dvbpsi_pat_t patpsi;
91 dvbpsi_psi_section_t *p_section;
93 dvbpsi_pat_init( &patpsi, i_tsid, i_pat_version_number, true /* b_current_next */ );
94 /* add all programs */
95 for (unsigned i = 0; i < i_programs; i++ )
96 dvbpsi_pat_program_add( &patpsi, pi_programs_number[i], p_pmt[i].i_pid );
98 p_section = dvbpsi_pat_sections_generate( p_dvbpsi, &patpsi, 0 );
99 if( likely(p_section) )
101 block_t *p_block = WritePSISection( p_section );
102 if( likely(p_block) )
104 PEStoTS( p_opaque, pf_callback, p_block, p_pat->i_pid,
105 &p_pat->b_discontinuity, &p_pat->i_continuity_counter );
107 dvbpsi_DeletePSISections( p_section );
109 dvbpsi_pat_empty( &patpsi );
111 #if 1
113 static uint32_t GetDescriptorLength24b( int i_length )
115 uint32_t i_l1, i_l2, i_l3;
117 i_l1 = i_length&0x7f;
118 i_l2 = ( i_length >> 7 )&0x7f;
119 i_l3 = ( i_length >> 14 )&0x7f;
121 return( 0x808000 | ( i_l3 << 16 ) | ( i_l2 << 8 ) | i_l1 );
124 static void Mpeg4SUBTDecoderSpecific_55( bits_buffer_t *b )
126 bits_write( b, 8, 0x10 ); /* textFormat, 0x10 for 3GPP TS 26.245 */
127 bits_write( b, 8, 0x00 ); /* flags: 1b: associated video info flag
128 3b: reserved
129 1b: duration flag
130 3b: reserved */
131 bits_write( b, 8, 52 ); /* remaining size */
133 bits_write( b, 32, 0x00 ); /* display flags */
135 bits_write( b, 8, 0x00 ); /* horizontal justification (-1: left, 0 center, 1 right) */
136 bits_write( b, 8, 0x01 ); /* vertical justification (-1: top, 0 center, 1 bottom) */
138 bits_write( b, 24, 0x00 ); /* background rgb */
139 bits_write( b, 8, 0xff ); /* background a */
141 bits_write( b, 16, 0x00 ); /* text box top */
142 bits_write( b, 16, 0x00 ); /* text box left */
143 bits_write( b, 16, 0x00 ); /* text box bottom */
144 bits_write( b, 16, 0x00 ); /* text box right */
146 bits_write( b, 16, 0x00 ); /* start char */
147 bits_write( b, 16, 0x00 ); /* end char */
148 bits_write( b, 16, 0x00 ); /* default font id */
151 bits_write( b, 8, 0x00 ); /* font style flags */
152 bits_write( b, 8, 12 ); /* font size */
154 bits_write( b, 24, 0x00 ); /* foreground rgb */
155 bits_write( b, 8, 0x00 ); /* foreground a */
157 bits_write( b, 24, 0x00 );
158 bits_write( b, 8, 22 ); /* atom size */
160 bits_write( b, 8, 'f' ); /* atom id */
161 bits_write( b, 8, 't' );
162 bits_write( b, 8, 'a' );
163 bits_write( b, 8, 'b' );
165 bits_write( b, 8, 0x00 );
166 bits_write( b, 8, 0x01 ); /* entry count */
168 bits_write( b, 16, 0x00 ); /* font id */
169 bits_write( b, 8, 9 ); /* font name length */
170 const char fontname[] = "Helvetica";
171 for(int i=0; i<9; i++)
172 bits_write( b, 8, fontname[i] ); /* font name */
175 static void GetPMTmpeg4( vlc_object_t *p_object, dvbpsi_pmt_t *p_dvbpmt,
176 unsigned i_mapped_streams, const pes_mapped_stream_t *p_mapped_streams )
178 uint8_t iod[4096];
179 bits_buffer_t bits, bits_fix_IOD;
181 /* Make valgrind happy : it works at byte level not bit one so
182 * bit_write confuse it (but DON'T CHANGE the way that bit_write is
183 * working (needed when fixing some bits) */
184 memset( iod, 0, 4096 );
186 bits_initwrite( &bits, 4096, iod );
187 /* IOD_label_scope */
188 bits_write( &bits, 8, 0x11 );
189 /* IOD_label */
190 bits_write( &bits, 8, 0x01 );
191 /* InitialObjectDescriptor */
192 bits_align( &bits );
193 bits_write( &bits, 8, 0x02 ); /* tag */
194 bits_fix_IOD = bits; /* save states to fix length later */
195 bits_write( &bits, 24,
196 GetDescriptorLength24b( 0 ) ); /* variable length (fixed later) */
197 bits_write( &bits, 10, 0x01 ); /* ObjectDescriptorID */
198 bits_write( &bits, 1, 0x00 ); /* URL Flag */
199 bits_write( &bits, 1, 0x00 ); /* includeInlineProfileLevelFlag */
200 bits_write( &bits, 4, 0x0f ); /* reserved */
201 bits_write( &bits, 8, 0xff ); /* ODProfile (no ODcapability ) */
202 bits_write( &bits, 8, 0xff ); /* sceneProfile */
203 bits_write( &bits, 8, 0xfe ); /* audioProfile (unspecified) */
204 bits_write( &bits, 8, 0xfe ); /* visualProfile( // ) */
205 bits_write( &bits, 8, 0xff ); /* graphicProfile (no ) */
206 for (unsigned i = 0; i < i_mapped_streams; i++ )
208 const pes_mapped_stream_t *p_stream = &p_mapped_streams[i];
210 if( p_stream->pes->i_stream_id != 0xfa && p_stream->pes->i_stream_id != 0xfb &&
211 p_stream->pes->i_stream_id != 0xfe )
212 continue;
214 bits_buffer_t bits_fix_ESDescr, bits_fix_Decoder;
215 /* ES descriptor */
216 bits_align( &bits );
217 bits_write( &bits, 8, 0x03 ); /* ES_DescrTag */
218 bits_fix_ESDescr = bits;
219 bits_write( &bits, 24,
220 GetDescriptorLength24b( 0 ) ); /* variable size */
221 bits_write( &bits, 16, p_stream->pes->i_es_id );
222 bits_write( &bits, 1, 0x00 ); /* streamDependency */
223 bits_write( &bits, 1, 0x00 ); /* URL Flag */
224 bits_write( &bits, 1, 0x00 ); /* OCRStreamFlag */
225 bits_write( &bits, 5, 0x1f ); /* streamPriority */
227 /* DecoderConfigDesciptor */
228 bits_align( &bits );
229 bits_write( &bits, 8, 0x04 ); /* DecoderConfigDescrTag */
230 bits_fix_Decoder = bits;
231 bits_write( &bits, 24, GetDescriptorLength24b( 0 ) );
232 if( p_stream->ts->i_stream_type == 0x10 )
234 bits_write( &bits, 8, 0x20 ); /* Visual 14496-2 */
235 bits_write( &bits, 6, 0x04 ); /* VisualStream */
237 else if( p_stream->ts->i_stream_type == 0x1b )
239 bits_write( &bits, 8, 0x21 ); /* Visual 14496-2 */
240 bits_write( &bits, 6, 0x04 ); /* VisualStream */
242 else if( p_stream->ts->i_stream_type == 0x11 ||
243 p_stream->ts->i_stream_type == 0x0f )
245 bits_write( &bits, 8, 0x40 ); /* Audio 14496-3 */
246 bits_write( &bits, 6, 0x05 ); /* AudioStream */
248 else if( p_stream->ts->i_stream_type == 0x12 &&
249 p_stream->fmt->i_codec == VLC_CODEC_SUBT )
251 bits_write( &bits, 8, 0x0B ); /* Text Stream */
252 bits_write( &bits, 6, 0x04 ); /* VisualStream */
254 else
256 bits_write( &bits, 8, 0x00 );
257 bits_write( &bits, 6, 0x00 );
259 msg_Err( p_object, "Unsupported stream_type => broken IOD" );
261 bits_write( &bits, 1, 0x00 ); /* UpStream */
262 bits_write( &bits, 1, 0x01 ); /* reserved */
263 bits_write( &bits, 24, 1024 * 1024 ); /* bufferSizeDB */
264 bits_write( &bits, 32, 0x7fffffff ); /* maxBitrate */
265 bits_write( &bits, 32, 0 ); /* avgBitrate */
267 /* DecoderSpecificInfo */
268 if( p_stream->fmt->i_codec == VLC_CODEC_SUBT )
270 bits_align( &bits );
271 bits_write( &bits, 8, 0x05 ); /* tag */
272 bits_write( &bits, 24, 55 );
273 /* Create decoder specific info for subt */
274 Mpeg4SUBTDecoderSpecific_55( &bits );
276 else if( p_stream->fmt->i_extra > 0 )
278 /* DecoderSpecificInfo */
279 bits_align( &bits );
280 bits_write( &bits, 8, 0x05 ); /* tag */
281 bits_write( &bits, 24, GetDescriptorLength24b(
282 p_stream->fmt->i_extra ) );
283 for (int j = 0; j < p_stream->fmt->i_extra; j++ )
285 bits_write( &bits, 8,
286 ((uint8_t*)p_stream->fmt->p_extra)[j] );
290 /* fix Decoder length */
291 bits_write( &bits_fix_Decoder, 24,
292 GetDescriptorLength24b( bits.i_data -
293 bits_fix_Decoder.i_data - 3 ) );
295 /* SLConfigDescriptor : predefined (0x01) */
296 bits_align( &bits );
297 bits_write( &bits, 8, 0x06 ); /* tag */
298 bits_write( &bits, 24, GetDescriptorLength24b( 8 ) );
299 bits_write( &bits, 8, 0x01 );/* predefined */
300 bits_write( &bits, 1, 0 ); /* durationFlag */
301 bits_write( &bits, 32, 0 ); /* OCRResolution */
302 bits_write( &bits, 8, 0 ); /* OCRLength */
303 bits_write( &bits, 8, 0 ); /* InstantBitrateLength */
304 bits_align( &bits );
306 /* fix ESDescr length */
307 bits_write( &bits_fix_ESDescr, 24,
308 GetDescriptorLength24b( bits.i_data -
309 bits_fix_ESDescr.i_data - 3 ) );
311 bits_align( &bits );
312 /* fix IOD length */
313 bits_write( &bits_fix_IOD, 24,
314 GetDescriptorLength24b(bits.i_data - bits_fix_IOD.i_data - 3 ));
316 dvbpsi_pmt_descriptor_add(&p_dvbpmt[0], 0x1d, bits.i_data, bits.p_data);
319 static void UpdateServiceType( uint8_t *pi_service_cat, uint8_t *pi_service_type,
320 const tsmux_stream_t *p_ts, const es_format_t *fmt )
322 uint8_t i_type = 0x00;
324 switch( p_ts->i_stream_type )
326 case 0x01: /* MPEG1 */
327 case 0x02: /* MPEG2 */
328 case 0x80:
329 i_type = 0x01;
330 break;
332 case 0x24: /* HEVC */
333 case 0x10: /* MPEG4 */
334 case 0x1b: /* H264 */
335 case 0xA0: /* private */
336 case 0xd1: /* dirac */
337 i_type = 0x16;
338 break;
340 default:
341 break;
344 if( i_type == 0x01 && fmt->video.i_visible_height > 468 &&
345 fmt->video.i_visible_width > 720 ) /* MPEG2 SD -> HD */
347 i_type = 0x11;
349 else if( i_type == 0x16 && fmt->video.i_visible_height > 468 &&
350 fmt->video.i_visible_width > 720 ) /* Advanced codec SD -> HD */
352 i_type = 0x19;
355 if( i_type != 0x00 )
357 if( *pi_service_cat != VIDEO_ES || i_type > *pi_service_type )
359 *pi_service_type = i_type;
360 *pi_service_cat = VIDEO_ES;
362 return;
365 if( *pi_service_cat != VIDEO_ES ) /* Don't overwrite video */
367 /* Not video, try audio */
368 switch( p_ts->i_stream_type )
370 case 0x03: /* MPEG1 audio */
371 case 0x04: /* MPEG2 audio */
372 i_type = 0x02;
373 break;
375 case 0x06:
376 case 0x0f:
377 case 0x81:
378 case 0x83:
379 i_type = 0x0A; /* Avanced codec digital radio */
380 break;
382 default:
383 break;
386 if( i_type > *pi_service_type )
387 *pi_service_type = i_type;
391 static inline size_t Write_AnnexA_String( uint8_t *p_dest, const char *p_src )
393 size_t i_src;
394 if( p_src == NULL || !(i_src = strlen( p_src )) )
396 p_dest[0] = 0;
397 return 1;
400 bool b_latin = (p_src[0] > 0x20);
401 for ( size_t i=0; i< i_src && b_latin; i++ )
402 b_latin &= !( p_src[i] & 0x80 );
404 if( b_latin )
406 i_src = __MIN( i_src, UINT8_MAX );
407 p_dest[0] = i_src; /* Total size */
408 memcpy( &p_dest[1], p_src, i_src );
409 return 1 + i_src;
411 else
413 i_src = __MIN( i_src, UINT8_MAX - 1 );
414 p_dest[0] = 1 + i_src; /* Total size */
415 p_dest[1] = 0x15; /* UTF8 Encoding */
416 memcpy( &p_dest[2], p_src, i_src );
417 return 2 + i_src;
421 void BuildPMT( dvbpsi_t *p_dvbpsi, vlc_object_t *p_object,
422 ts_mux_standard standard,
423 void *p_opaque, PEStoTSCallback pf_callback,
424 int i_tsid, int i_pmt_version_number,
425 int i_pcr_pid,
426 sdt_psi_t *p_sdt,
427 unsigned i_programs, tsmux_stream_t *p_pmt, const int *pi_programs_number,
428 unsigned i_mapped_streams, const pes_mapped_stream_t *p_mapped_streams )
430 dvbpsi_pmt_t *dvbpmt = malloc( i_programs * sizeof(dvbpsi_pmt_t) );
431 if( !dvbpmt )
432 return;
434 VLC_UNUSED(standard);
435 dvbpsi_sdt_t sdtpsi;
436 uint8_t *pi_service_types = NULL;
437 uint8_t *pi_service_cats = NULL;
438 if( p_sdt )
440 dvbpsi_sdt_init( &sdtpsi, 0x42, i_tsid, 1, true, p_sdt->i_netid );
441 pi_service_types = calloc( i_programs * 2, sizeof *pi_service_types );
442 if( !pi_service_types )
444 free( dvbpmt );
445 return;
447 pi_service_cats = &pi_service_types[i_programs];
450 for (unsigned i = 0; i < i_programs; i++ )
452 dvbpsi_pmt_init( &dvbpmt[i],
453 pi_programs_number[i], /* program number */
454 i_pmt_version_number,
455 true, /* b_current_next */
456 i_pcr_pid );
459 for (unsigned i = 0; i < i_mapped_streams; i++ )
461 const pes_mapped_stream_t *p_stream = &p_mapped_streams[i];
462 if( p_stream->pes->i_stream_id == 0xfa ||
463 p_stream->pes->i_stream_id == 0xfb ||
464 p_stream->pes->i_stream_id == 0xfe )
466 /* Has at least 1 MPEG4 stream */
467 GetPMTmpeg4( p_object, dvbpmt, i_mapped_streams, p_mapped_streams );
468 break;
472 for (unsigned i = 0; i < i_mapped_streams; i++ )
474 const pes_mapped_stream_t *p_stream = &p_mapped_streams[i];
476 dvbpsi_pmt_es_t *p_es = dvbpsi_pmt_es_add( &dvbpmt[p_stream->i_mapped_prog],
477 p_stream->ts->i_stream_type, p_stream->ts->i_pid );
479 if( p_stream->pes->i_stream_id == 0xfa || p_stream->pes->i_stream_id == 0xfb )
481 uint8_t es_id[2];
483 /* SL descriptor */
484 es_id[0] = (p_stream->pes->i_es_id >> 8)&0xff;
485 es_id[1] = (p_stream->pes->i_es_id)&0xff;
486 dvbpsi_pmt_es_descriptor_add( p_es, 0x1f, 2, es_id );
488 else if( p_stream->ts->i_stream_type == 0xa0 )
490 uint8_t data[512];
491 size_t i_extra = __MIN( p_stream->fmt->i_extra, 502 );
493 /* private DIV3 descripor */
494 memcpy( &data[0], &p_stream->fmt->i_codec, 4 );
495 data[4] = ( p_stream->fmt->video.i_visible_width >> 8 )&0xff;
496 data[5] = ( p_stream->fmt->video.i_visible_width )&0xff;
497 data[6] = ( p_stream->fmt->video.i_visible_height>> 8 )&0xff;
498 data[7] = ( p_stream->fmt->video.i_visible_height )&0xff;
499 data[8] = ( i_extra >> 8 )&0xff;
500 data[9] = ( i_extra )&0xff;
501 if( i_extra > 0 )
503 memcpy( &data[10], p_stream->fmt->p_extra, i_extra );
506 /* 0xa0 is private */
507 dvbpsi_pmt_es_descriptor_add( p_es, 0xa0, i_extra + 10, data );
509 else if( p_stream->fmt->i_codec == VLC_CODEC_JPEG2000 )
511 uint8_t *p_data = calloc( 1, 24 + p_stream->fmt->i_extra );
512 if( p_data )
514 const int profile = j2k_get_profile( p_stream->fmt->video.i_visible_width,
515 p_stream->fmt->video.i_visible_height,
516 p_stream->fmt->video.i_frame_rate,
517 p_stream->fmt->video.i_frame_rate_base, true );
518 p_data[0] = 0x01;
519 if( profile < J2K_PROFILE_HD )
520 p_data[1] = 0x01; /* 0x0101 */
521 else if( profile < J2K_PROFILE_3G )
522 p_data[1] = 0x02; /* 0x0102 */
523 else
524 p_data[1] = 0x04; /* 0x0104 */
525 SetDWBE( &p_data[2], p_stream->fmt->video.i_visible_width );
526 SetDWBE( &p_data[6], p_stream->fmt->video.i_visible_height );
527 SetWBE( &p_data[18], p_stream->fmt->video.i_frame_rate_base );
528 SetWBE( &p_data[20], p_stream->fmt->video.i_frame_rate );
529 p_data[21] = j2k_get_color_spec( p_stream->fmt->video.primaries,
530 p_stream->fmt->video.transfer,
531 p_stream->fmt->video.space );
532 memcpy( &p_data[24], p_stream->fmt->p_extra, p_stream->fmt->i_extra );
533 dvbpsi_pmt_es_descriptor_add( p_es, 0x32, 24 + p_stream->fmt->i_extra, p_data );
534 free(p_data);
537 else if( p_stream->fmt->i_codec == VLC_CODEC_DIRAC )
539 /* Dirac registration descriptor */
541 uint8_t data[4] = { 'd', 'r', 'a', 'c' };
542 dvbpsi_pmt_es_descriptor_add( p_es, 0x05, 4, data );
544 else if( p_stream->fmt->i_codec == VLC_CODEC_DTS )
546 /* DTS registration descriptor (ETSI TS 101 154 Annex F) */
547 if(popcount(p_stream->fmt->audio.i_bytes_per_frame) == 1)
549 uint8_t i_ver = ctz( p_stream->fmt->audio.i_bytes_per_frame >> 8 );
550 if(i_ver > 0 && i_ver < 4)
552 uint8_t data[4] = { 'D', 'T', 'S', '0' + i_ver };
553 dvbpsi_pmt_es_descriptor_add( p_es, 0x05, 4, data );
557 else if( p_stream->fmt->i_codec == VLC_CODEC_A52 )
559 uint8_t format[4] = { 'A', 'C', '-', '3'};
561 /* "registration" descriptor : "AC-3" */
562 dvbpsi_pmt_es_descriptor_add( p_es, 0x05, 4, format );
564 if( standard == TS_MUX_STANDARD_ATSC )
566 assert(p_stream->ts->i_stream_type == 0x81);
567 /* FIXME: ATSC AC-3 audio_stream_descriptor */
568 uint8_t data[1] = { 0x00 };
569 dvbpsi_pmt_es_descriptor_add( p_es, 0x81, 1, data );
571 else
573 /* FIXME: DVB AC-3 descriptor */
574 uint8_t data[1] = { 0x00 };
575 dvbpsi_pmt_es_descriptor_add( p_es, 0x6a, 1, data );
578 else if( p_stream->fmt->i_codec == VLC_CODEC_EAC3 )
580 uint8_t format[4] = { 'E', 'A', 'C', '3'};
582 /* "registration" descriptor : "EAC3" */
583 dvbpsi_pmt_es_descriptor_add( p_es, 0x05, 4, format );
585 if( standard == TS_MUX_STANDARD_ATSC )
587 assert( p_stream->ts->i_stream_type == 0x87 );
588 /* FIXME: ATSC EAC3 audio_stream_descriptor */
589 uint8_t data[1] = { 0x00 };
590 dvbpsi_pmt_es_descriptor_add( p_es, 0xcc, 1, data );
591 /* FIXME: ATSC A-71 stream_info_details */
593 else
595 uint8_t data[1] = { 0x00 };
596 dvbpsi_pmt_es_descriptor_add( p_es, 0x7a, 1, data );
599 else if( p_stream->fmt->i_codec == VLC_CODEC_OPUS )
601 uint8_t data[2] = {
602 0x80, /* tag extension */
603 p_stream->fmt->audio.i_channels
605 dvbpsi_pmt_es_descriptor_add( p_es, 0x7f, 2, data );
606 uint8_t format[4] = { 'O', 'p', 'u', 's'};
607 /* "registration" descriptor : "Opus" */
608 dvbpsi_pmt_es_descriptor_add( p_es, 0x05, 4, format );
610 else if( p_stream->fmt->i_codec == VLC_CODEC_TELETEXT )
612 if( p_stream->fmt->i_extra )
614 dvbpsi_pmt_es_descriptor_add( p_es, 0x56,
615 p_stream->fmt->i_extra,
616 p_stream->fmt->p_extra );
618 continue;
620 else if( p_stream->fmt->i_codec == VLC_CODEC_DVBS )
622 /* DVB subtitles */
623 if( p_stream->fmt->i_extra )
625 /* pass-through from the TS demux */
626 dvbpsi_pmt_es_descriptor_add( p_es, 0x59,
627 p_stream->fmt->i_extra,
628 p_stream->fmt->p_extra );
630 else
632 /* from the dvbsub transcoder */
633 dvbpsi_subtitling_dr_t descr;
634 dvbpsi_subtitle_t sub;
635 dvbpsi_descriptor_t *p_descr;
637 memcpy( sub.i_iso6392_language_code, p_stream->pes->lang, 3 );
638 sub.i_subtitling_type = 0x10; /* no aspect-ratio criticality */
639 sub.i_composition_page_id = p_stream->pes->i_es_id & 0xFF;
640 sub.i_ancillary_page_id = p_stream->pes->i_es_id >> 16;
642 descr.i_subtitles_number = 1;
643 descr.p_subtitle[0] = sub;
645 p_descr = dvbpsi_GenSubtitlingDr( &descr, 0 );
646 /* Work around bug in old libdvbpsi */ p_descr->i_length = 8;
647 dvbpsi_pmt_es_descriptor_add( p_es, p_descr->i_tag,
648 p_descr->i_length, p_descr->p_data );
650 continue;
653 if( p_stream->pes->i_langs )
655 dvbpsi_pmt_es_descriptor_add( p_es, 0x0a, 4*p_stream->pes->i_langs,
656 p_stream->pes->lang);
659 if( p_sdt )
661 UpdateServiceType( &pi_service_cats[p_stream->i_mapped_prog],
662 &pi_service_types[p_stream->i_mapped_prog],
663 p_stream->ts, p_stream->fmt );
667 for (unsigned i = 0; i < i_programs; i++ )
669 dvbpsi_psi_section_t *sect = dvbpsi_pmt_sections_generate( p_dvbpsi, &dvbpmt[i] );
670 if( likely(sect) )
672 block_t *pmt = WritePSISection( sect );
673 if( likely(pmt) )
675 PEStoTS( p_opaque, pf_callback, pmt, p_pmt[i].i_pid,
676 &p_pmt[i].b_discontinuity, &p_pmt[i].i_continuity_counter );
678 dvbpsi_DeletePSISections(sect);
680 dvbpsi_pmt_empty( &dvbpmt[i] );
682 free( dvbpmt );
684 if( p_sdt )
686 for (unsigned i = 0; i < i_programs; i++ )
688 dvbpsi_sdt_service_t *p_service = dvbpsi_sdt_service_add( &sdtpsi,
689 pi_programs_number[i], /* service id */
690 false, /* eit schedule */
691 false, /* eit present */
692 4, /* running status ("4=RUNNING") */
693 false ); /* free ca */
695 const char *psz_sdtprov = p_sdt->desc[i].psz_provider;
696 const char *psz_sdtserv = p_sdt->desc[i].psz_service_name;
698 uint8_t p_sdt_desc[4 + 255 * 2];
699 size_t i_sdt_desc = 0;
701 /* mapped service type according to es types */
702 p_sdt_desc[i_sdt_desc++] = pi_service_types[i];
704 /* service provider name length */
705 i_sdt_desc += Write_AnnexA_String( &p_sdt_desc[i_sdt_desc], psz_sdtprov );
707 /* service name length */
708 i_sdt_desc += Write_AnnexA_String( &p_sdt_desc[i_sdt_desc], psz_sdtserv );
710 dvbpsi_sdt_service_descriptor_add( p_service, 0x48, i_sdt_desc, p_sdt_desc );
712 free( pi_service_types );
714 dvbpsi_psi_section_t *sect = dvbpsi_sdt_sections_generate( p_dvbpsi, &sdtpsi );
715 if( likely(sect) )
717 block_t *p_sdtblock = WritePSISection( sect );
718 if( likely(p_sdtblock) )
720 PEStoTS( p_opaque, pf_callback, p_sdtblock, p_sdt->ts.i_pid,
721 &p_sdt->ts.b_discontinuity, &p_sdt->ts.i_continuity_counter );
723 dvbpsi_DeletePSISections( sect );
725 dvbpsi_sdt_empty( &sdtpsi );
729 int FillPMTESParams( ts_mux_standard standard, const es_format_t *fmt,
730 tsmux_stream_t *ts, pesmux_stream_t *pes )
732 switch( fmt->i_codec )
734 /* VIDEO */
736 case VLC_CODEC_MPGV:
737 case VLC_CODEC_MP2V:
738 case VLC_CODEC_MP1V:
739 /* TODO: do we need to check MPEG-I/II ? */
740 ts->i_stream_type = 0x02;
741 pes->i_stream_id = 0xe0;
742 break;
743 case VLC_CODEC_MP4V:
744 ts->i_stream_type = 0x10;
745 pes->i_stream_id = 0xe0;
746 pes->i_es_id = ts->i_pid;
747 break;
748 case VLC_CODEC_HEVC:
749 ts->i_stream_type = 0x24;
750 pes->i_stream_id = 0xe0;
751 break;
752 case VLC_CODEC_H264:
753 ts->i_stream_type = 0x1b;
754 pes->i_stream_id = 0xe0;
755 break;
756 /* XXX dirty dirty but somebody want crapy MS-codec XXX */
757 case VLC_CODEC_H263I:
758 case VLC_CODEC_H263:
759 case VLC_CODEC_WMV3:
760 case VLC_CODEC_WMV2:
761 case VLC_CODEC_WMV1:
762 case VLC_CODEC_DIV3:
763 case VLC_CODEC_DIV2:
764 case VLC_CODEC_DIV1:
765 case VLC_CODEC_MJPG:
766 ts->i_stream_type = 0xa0; /* private */
767 pes->i_stream_id = 0xa0; /* beurk */
768 break;
769 case VLC_CODEC_DIRAC:
770 /* stream_id makes use of stream_id_extension */
771 pes->i_stream_id = (PES_EXTENDED_STREAM_ID << 8) | 0x60;
772 ts->i_stream_type = 0xd1;
773 break;
774 case VLC_CODEC_JPEG2000:
775 if( !j2k_is_valid_framerate( fmt->video.i_frame_rate,
776 fmt->video.i_frame_rate_base ) )
777 return VLC_EGENERIC;
778 ts->i_stream_type = 0x21;
779 pes->i_stream_id = 0xbd;
780 break;
782 /* AUDIO */
784 case VLC_CODEC_MPGA:
785 case VLC_CODEC_MP2:
786 case VLC_CODEC_MP3:
787 ts->i_stream_type = fmt->audio.i_rate >= 32000 ? 0x03 : 0x04;
788 pes->i_stream_id = 0xc0;
789 break;
790 case VLC_CODEC_A52:
791 pes->i_stream_id = 0xbd;
792 if( standard == TS_MUX_STANDARD_ATSC )
794 ts->i_stream_type = 0x81;
796 else
798 ts->i_stream_type = 0x06;
800 break;
801 case VLC_CODEC_DVD_LPCM:
802 ts->i_stream_type = 0x83;
803 pes->i_stream_id = 0xbd;
804 break;
805 case VLC_CODEC_OPUS:
806 if (fmt->audio.i_channels > 8)
807 return VLC_EGENERIC;
808 pes->i_stream_id = 0xbd;
809 pes->i_stream_id = 0x06;
810 break;
811 case VLC_CODEC_EAC3:
812 pes->i_stream_id = 0xbd;
813 if( standard == TS_MUX_STANDARD_ATSC )
815 /* FIXME: Mandatory EAC3 audio_descriptor */
816 ts->i_stream_type = 0x87;
818 else
820 ts->i_stream_type = 0x06;
822 break;
823 case VLC_CODEC_DTS:
824 if( standard == TS_MUX_STANDARD_ATSC )
826 return VLC_EGENERIC;
828 else
830 ts->i_stream_type = 0x06;
831 pes->i_stream_id = 0xbd;
833 break;
834 case VLC_CODEC_MP4A:
835 /* XXX: make that configurable in some way when LOAS
836 * is implemented for AAC in TS */
837 //ts->i_stream_type = 0x11; /* LOAS/LATM */
838 ts->i_stream_type = 0x0f; /* ADTS */
839 pes->i_stream_id = 0xc0;
840 pes->i_es_id = ts->i_pid;
841 break;
843 /* TEXT */
845 case VLC_CODEC_SPU:
846 ts->i_stream_type = 0x82;
847 pes->i_stream_id = 0xbd;
848 break;
849 case VLC_CODEC_SUBT:
850 ts->i_stream_type = 0x12;
851 pes->i_stream_id = 0xfa;
852 pes->i_es_id = ts->i_pid;
853 break;
854 case VLC_CODEC_DVBS:
855 ts->i_stream_type = 0x06;
856 pes->i_es_id = fmt->subs.dvb.i_id;
857 pes->i_stream_id = 0xbd;
858 break;
859 case VLC_CODEC_TELETEXT:
860 ts->i_stream_type = 0x06;
861 pes->i_stream_id = 0xbd; /* FIXME */
862 break;
864 default:
865 return VLC_EGENERIC;
868 return VLC_SUCCESS;
871 #endif