sd_ass: initialize structs for external tracks properly
[mplayer.git] / libmpdemux / demux_mpg.c
blob44ec85d2dbe60eab15e98764f7fd178d0f44f422
1 /*
2 * MPG/VOB file parser for DEMUXER v2.5
3 * copyright (c) 2001 by A'rpi/ESP-team
5 * This file is part of MPlayer.
7 * MPlayer is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
12 * MPlayer is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License along
18 * with MPlayer; if not, write to the Free Software Foundation, Inc.,
19 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <unistd.h>
25 #include <math.h>
27 #include "config.h"
28 #include "mp_msg.h"
29 #include "options.h"
31 #include "libavutil/attributes.h"
32 #include "libmpcodecs/dec_audio.h"
33 #include "stream/stream.h"
34 #include "demuxer.h"
35 #include "parse_es.h"
36 #include "stheader.h"
37 #include "mp3_hdr.h"
39 //#define MAX_PS_PACKETSIZE 2048
40 #define MAX_PS_PACKETSIZE (224*1024)
42 #define UNKNOWN 0
43 #define VIDEO_MPEG1 0x10000001
44 #define VIDEO_MPEG2 0x10000002
45 #define VIDEO_MPEG4 0x10000004
46 #define VIDEO_H264 0x10000005
47 #define AUDIO_MP2 0x50
48 #define AUDIO_A52 0x2000
49 #define AUDIO_LPCM_BE 0x10001
50 #define AUDIO_AAC mmioFOURCC('M', 'P', '4', 'A')
52 typedef struct mpg_demuxer {
53 float last_pts;
54 float first_pts; // first pts found in stream
55 float first_to_final_pts_len; // difference between final pts and first pts
56 int has_valid_timestamps; // !=0 iff time stamps look linear
57 // (not necessarily starting with 0)
58 unsigned int es_map[0x40]; //es map of stream types (associated to the pes id) from 0xb0 to 0xef
59 int num_a_streams;
60 int a_stream_ids[MAX_A_STREAMS];
61 } mpg_demuxer_t;
63 static int mpeg_pts_error=0;
64 off_t ps_probe = 0;
66 static int parse_psm(demuxer_t *demux, int len) {
67 unsigned char c, id, type;
68 unsigned int plen, prog_len, es_map_len;
69 mpg_demuxer_t *priv = (mpg_demuxer_t *) demux->priv;
71 mp_dbg(MSGT_DEMUX,MSGL_V, "PARSE_PSM, len=%d\n", len);
72 if(! len || len > 1018)
73 return 0;
75 c = stream_read_char(demux->stream);
76 if(! (c & 0x80)) {
77 stream_skip(demux->stream, len - 1); //not yet valid, discard
78 return 0;
80 stream_skip(demux->stream, 1);
81 prog_len = stream_read_word(demux->stream); //length of program descriptors
82 stream_skip(demux->stream, prog_len); //.. that we ignore
83 es_map_len = stream_read_word(demux->stream); //length of elementary streams map
84 es_map_len = FFMIN(es_map_len, len - prog_len - 8); //sanity check
85 while(es_map_len > 0) {
86 type = stream_read_char(demux->stream);
87 id = stream_read_char(demux->stream);
88 if(id >= 0xB0 && id <= 0xEF && priv) {
89 int idoffset = id - 0xB0;
90 switch(type) {
91 case 0x1:
92 priv->es_map[idoffset] = VIDEO_MPEG1;
93 break;
94 case 0x2:
95 priv->es_map[idoffset] = VIDEO_MPEG2;
96 break;
97 case 0x3:
98 case 0x4:
99 priv->es_map[idoffset] = AUDIO_MP2;
100 break;
101 case 0x0f:
102 case 0x11:
103 priv->es_map[idoffset] = AUDIO_AAC;
104 break;
105 case 0x10:
106 priv->es_map[idoffset] = VIDEO_MPEG4;
107 break;
108 case 0x1b:
109 priv->es_map[idoffset] = VIDEO_H264;
110 break;
111 case 0x81:
112 priv->es_map[idoffset] = AUDIO_A52;
113 break;
115 mp_dbg(MSGT_DEMUX,MSGL_V, "PSM ES, id=0x%x, type=%x, stype: %x\n", id, type, priv->es_map[idoffset]);
117 plen = stream_read_word(demux->stream); //length of elementary stream descriptors
118 plen = FFMIN(plen, es_map_len); //sanity check
119 stream_skip(demux->stream, plen); //skip descriptors for now
120 es_map_len -= 4 + plen;
122 stream_skip(demux->stream, 4); //skip crc32
123 return 1;
126 // 500000 is a wild guess
127 #define TIMESTAMP_PROBE_LEN 500000
129 //MAX_PTS_DIFF_FOR_CONSECUTIVE denotes the maximum difference
130 //between two pts to consider them consecutive
131 //1.0 is a wild guess
132 #define MAX_PTS_DIFF_FOR_CONSECUTIVE 1.0
134 //returns the first pts found within TIME_STAMP_PROBE_LEN bytes after stream_pos in demuxer's stream.
135 //if no pts is found or an error occurs, -1.0 is returned.
136 //Packs are freed.
137 static float read_first_mpeg_pts_at_position(demuxer_t* demuxer, off_t stream_pos)
139 stream_t *s = demuxer->stream;
140 mpg_demuxer_t *mpg_d = demuxer->priv;
141 float pts = -1.0; //the pts to return;
142 float found_pts1; //the most recently found pts
143 float found_pts2; //the pts found before found_pts1
144 float found_pts3; //the pts found before found_pts2
145 int found = 0;
147 if(!mpg_d || stream_pos < 0)
148 return pts;
150 found_pts3 = found_pts2 = found_pts1 = mpg_d->last_pts;
151 stream_seek(s, stream_pos);
153 //We look for pts.
154 //However, we do not stop at the first found one, as timestamps may reset
155 //Therefore, we seek until we found three consecutive
156 //pts within MAX_PTS_DIFF_FOR_CONSECUTIVE.
158 while(found<3 && !s->eof
159 && (fabsf(found_pts2-found_pts1) < MAX_PTS_DIFF_FOR_CONSECUTIVE)
160 && (fabsf(found_pts3-found_pts2) < MAX_PTS_DIFF_FOR_CONSECUTIVE)
161 && (stream_tell(s) < stream_pos + TIMESTAMP_PROBE_LEN)
162 && ds_fill_buffer(demuxer->video))
164 if(mpg_d->last_pts != found_pts1)
166 if(!found)
167 found_pts3 = found_pts2 = found_pts1 = mpg_d->last_pts; //the most recently found pts
168 else
170 found_pts3 = found_pts2;
171 found_pts2 = found_pts1;
172 found_pts1 = mpg_d->last_pts;
174 found++;
178 if(found == 3) pts = found_pts3;
180 //clean up from searching of first pts;
181 demux_flush(demuxer);
183 return pts;
186 /// Open an mpg physical stream
187 static demuxer_t* demux_mpg_open(demuxer_t* demuxer) {
188 stream_t *s = demuxer->stream;
189 mpg_demuxer_t* mpg_d;
191 if (!ds_fill_buffer(demuxer->video)) return 0;
192 mpg_d = calloc(1,sizeof(mpg_demuxer_t));
193 if(mpg_d)
195 demuxer->priv = mpg_d;
196 mpg_d->last_pts = -1.0;
197 mpg_d->first_pts = -1.0;
199 //if seeking is allowed set has_valid_timestamps if appropriate
200 if(demuxer->seekable
201 && (demuxer->stream->type == STREAMTYPE_FILE
202 || demuxer->stream->type == STREAMTYPE_VCD)
203 && demuxer->movi_start != demuxer-> movi_end
206 //We seek to the beginning of the stream, to somewhere in the
207 //middle, and to the end of the stream, while remembering the pts
208 //at each of the three positions. With these pts, we check whether
209 //or not the pts are "linear enough" to justify seeking by the pts
210 //of the stream
212 //The position where the stream is now
213 off_t pos = stream_tell(s);
214 float first_pts = read_first_mpeg_pts_at_position(demuxer, demuxer->movi_start);
215 if(first_pts != -1.0)
217 float middle_pts = read_first_mpeg_pts_at_position(demuxer, (demuxer->movi_end + demuxer->movi_start)/2);
218 if(middle_pts != -1.0)
220 float final_pts = read_first_mpeg_pts_at_position(demuxer, demuxer->movi_end - TIMESTAMP_PROBE_LEN);
221 if(final_pts != -1.0)
223 // found proper first, middle, and final pts.
224 float proportion = (middle_pts-first_pts==0) ? -1 : (final_pts-middle_pts)/(middle_pts-first_pts);
225 // if they are linear enough set has_valid_timestamps
226 if((0.5 < proportion) && (proportion < 2))
228 mpg_d->first_pts = first_pts;
229 mpg_d->first_to_final_pts_len = final_pts - first_pts;
230 mpg_d->has_valid_timestamps = 1;
236 //Cleaning up from seeking in stream
237 demuxer->stream->eof=0;
238 demuxer->video->eof=0;
239 demuxer->audio->eof=0;
241 stream_seek(s,pos);
242 ds_fill_buffer(demuxer->video);
243 } // if ( demuxer->seekable )
244 } // if ( mpg_d )
245 return demuxer;
248 static void demux_close_mpg(demuxer_t* demuxer) {
249 mpg_demuxer_t* mpg_d = demuxer->priv;
250 free(mpg_d);
254 static unsigned long long read_mpeg_timestamp(stream_t *s,int c){
255 unsigned int d,e;
256 unsigned long long pts;
257 d=stream_read_word(s);
258 e=stream_read_word(s);
259 if( ((c&1)!=1) || ((d&1)!=1) || ((e&1)!=1) ){
260 ++mpeg_pts_error;
261 return 0; // invalid pts
263 pts=(((uint64_t)((c>>1)&7))<<30)|((d>>1)<<15)|(e>>1);
264 mp_dbg(MSGT_DEMUX,MSGL_DBG3," pts {%llu}",pts);
265 return pts;
268 static void new_audio_stream(demuxer_t *demux, int aid){
269 if(!demux->a_streams[aid]){
270 mpg_demuxer_t *mpg_d=(mpg_demuxer_t*)demux->priv;
271 sh_audio_t* sh_a;
272 new_sh_audio(demux,aid);
273 sh_a = (sh_audio_t*)demux->a_streams[aid];
274 sh_a->needs_parsing = 1;
275 switch(aid & 0xE0){ // 1110 0000 b (high 3 bit: type low 5: id)
276 case 0x00: sh_a->format=0x50;break; // mpeg
277 case 0xA0: sh_a->format=0x10001;break; // dvd pcm
278 case 0x80: if((aid & 0xF8) == 0x88) sh_a->format=0x2001;//dts
279 else sh_a->format=0x2000;break; // ac3
281 //evo files
282 if((aid & 0xC0) == 0xC0) sh_a->format=0x2000;
283 else if(aid >= 0x98 && aid <= 0x9f) sh_a->format=0x2001;
284 if (mpg_d) mpg_d->a_stream_ids[mpg_d->num_a_streams++] = aid;
286 if(demux->audio->id==-1) demux->audio->id=aid;
289 static int demux_mpg_read_packet(demuxer_t *demux,int id){
290 int d av_unused;
291 int len;
292 int set_pts=0; // !=0 iff pts has been set to a proper value
293 unsigned char c=0;
294 unsigned long long pts=0;
295 unsigned long long dts av_unused = 0;
296 int l;
297 int pes_ext2_subid=-1;
298 double stream_pts = MP_NOPTS_VALUE;
299 demux_stream_t *ds=NULL;
300 demux_packet_t* dp;
301 mpg_demuxer_t *priv = (mpg_demuxer_t *) demux->priv;
303 mp_dbg(MSGT_DEMUX,MSGL_DBG3,"demux_read_packet: %X\n",id);
305 // if(id==0x1F0){
306 // demux->synced=0; // force resync after 0x1F0
307 // return -1;
310 // if(id==0x1BA) packet_start_pos=stream_tell(demux->stream);
311 if((id<0x1BC || id>=0x1F0) && id != 0x1FD) return -1;
312 if(id==0x1BE) return -1; // padding stream
313 if(id==0x1BF) return -1; // private2
315 len=stream_read_word(demux->stream);
316 mp_dbg(MSGT_DEMUX,MSGL_DBG3,"PACKET len=%d",len);
317 // if(len==62480){ demux->synced=0;return -1;} /* :) */
318 if(len==0 || len>MAX_PS_PACKETSIZE){
319 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"Invalid PS packet len: %d\n",len);
320 return -2; // invalid packet !!!!!!
323 mpeg_pts_error=0;
325 if(id==0x1BC) {
326 parse_psm(demux, len);
327 return 0;
330 while(len>0){ // Skip stuFFing bytes
331 c=stream_read_char(demux->stream);
332 --len;
333 if(c!=0xFF)break;
335 if((c>>6)==1){ // Read (skip) STD scale & size value
336 // printf(" STD_scale=%d",(c>>5)&1);
337 d=((c&0x1F)<<8)|stream_read_char(demux->stream);
338 len-=2;
339 // printf(" STD_size=%d",d);
340 c=stream_read_char(demux->stream);
342 // Read System-1 stream timestamps:
343 if((c>>4)==2){
344 pts=read_mpeg_timestamp(demux->stream,c);
345 set_pts=1;
346 len-=4;
347 } else
348 if((c>>4)==3){
349 pts=read_mpeg_timestamp(demux->stream,c);
350 c=stream_read_char(demux->stream);
351 if((c>>4)!=1) pts=0; //printf("{ERROR4}");
352 else set_pts = 1;
353 dts=read_mpeg_timestamp(demux->stream,c);
354 len-=4+1+4;
355 } else
356 if((c>>6)==2){
357 int pts_flags;
358 int hdrlen;
359 int parse_ext2;
360 // System-2 (.VOB) stream:
361 c=stream_read_char(demux->stream);
362 pts_flags=c>>6;
363 parse_ext2 = (id == 0x1FD) && ((c & 0x3F) == 1);
364 c=stream_read_char(demux->stream);
365 hdrlen=c;
366 len-=2;
367 mp_dbg(MSGT_DEMUX,MSGL_DBG3," hdrlen=%d (len=%d)",hdrlen,len);
368 if(hdrlen>len){ mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: invalid header length \n"); return -1;}
369 if(pts_flags==2 && hdrlen>=5){
370 c=stream_read_char(demux->stream);
371 pts=read_mpeg_timestamp(demux->stream,c);
372 set_pts=1;
373 len-=5;hdrlen-=5;
374 } else
375 if(pts_flags==3 && hdrlen>=10){
376 c=stream_read_char(demux->stream);
377 pts=read_mpeg_timestamp(demux->stream,c);
378 set_pts=1;
379 c=stream_read_char(demux->stream);
380 dts=read_mpeg_timestamp(demux->stream,c);
381 len-=10;hdrlen-=10;
383 len-=hdrlen;
384 if(parse_ext2 && hdrlen>=3) {
385 c=stream_read_char(demux->stream);
386 hdrlen--;
388 if((c & 0x0F) != 0x0F) {
389 mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: pes_extension_flag2 not set, discarding pes packet\n");
390 return -1;
392 if(c & 0x80) { //pes_private_data_flag
393 if(hdrlen<16) {
394 mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: not enough pes_private_data bytes: %d < 16, discarding pes packet\n", hdrlen);
395 return -1;
397 stream_skip(demux->stream, 16);
398 hdrlen-=16;
400 if(c & 0x40) { //pack_header_field_flag
401 int l = stream_read_char(demux->stream);
402 if(l < 0) //couldn't read from the stream?
403 return -1;
404 hdrlen--;
405 if(l < 0 || hdrlen < l) {
406 mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: not enough pack_header bytes: hdrlen: %d < skip: %d, discarding pes packet\n",
407 hdrlen, l);
408 return -1;
410 stream_skip(demux->stream, l);
411 hdrlen-=l;
413 if(c & 0x20) { //program_packet_sequence_counter_flag
414 if(hdrlen < 2) {
415 mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: not enough program_packet bytes: hdrlen: %d, discarding pes packet\n", hdrlen);
416 return -1;
418 stream_skip(demux->stream, 2);
419 hdrlen-=2;
421 if(c & 0x10) {
422 //STD
423 stream_skip(demux->stream, 2);
424 hdrlen-=2;
426 c=stream_read_char(demux->stream); //pes_extension2 flag
427 hdrlen--;
428 if(c!=0x81) { mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: unknown pes_extension2 format, len is > 1 \n"); return -1;}
429 c=stream_read_char(demux->stream); //pes_extension2 payload === substream id
430 hdrlen--;
431 if(c<0x55 || c>0x5F) { mp_msg(MSGT_DEMUX,MSGL_V,"demux_mpg: unknown vc1 substream_id: 0x%x \n", c); return -1;}
432 pes_ext2_subid=c;
434 if(hdrlen>0)
435 stream_skip(demux->stream,hdrlen); // skip header and stuffing bytes
437 if(id==0x1FD && pes_ext2_subid!=-1) {
438 //==== EVO VC1 STREAMS ===//
439 if(!demux->v_streams[pes_ext2_subid]) new_sh_video(demux,pes_ext2_subid);
440 if(demux->video->id==-1) demux->video->id=pes_ext2_subid;
441 if(demux->video->id==pes_ext2_subid){
442 ds=demux->video;
443 if(!ds->sh) ds->sh=demux->v_streams[pes_ext2_subid];
444 if(priv && ds->sh) {
445 sh_video_t *sh = (sh_video_t *)ds->sh;
446 sh->format = mmioFOURCC('W', 'V', 'C', '1');
450 //============== DVD Audio sub-stream ======================
451 if(id==0x1BD){
452 int aid, rawa52 = 0;
453 off_t tmppos;
454 unsigned int tmp;
456 tmppos = stream_tell(demux->stream);
457 tmp = stream_read_word(demux->stream);
458 stream_seek(demux->stream, tmppos);
459 /// vdr stores A52 without the 4 header bytes, so we have to check this condition first
460 if(tmp == 0x0B77) {
461 aid = 128;
462 rawa52 = 1;
464 else {
465 aid=stream_read_char(demux->stream);--len;
466 if(len<3) return -1; // invalid audio packet
469 // AID:
470 // 0x20..0x3F subtitle
471 // 0x80..0x87 and 0xC0..0xCF AC3 audio
472 // 0x88..0x8F and 0x98..0x9F DTS audio
473 // 0xA0..0xBF PCM audio
475 if((aid & 0xE0) == 0x20){
476 // subtitle:
477 aid&=0x1F;
479 if(!demux->s_streams[aid]){
480 sh_sub_t *sh = new_sh_sub(demux, aid);
481 if (sh) sh->type = 'v';
482 mp_msg(MSGT_DEMUX,MSGL_V,"==> Found subtitle: %d\n",aid);
485 if(demux->sub->id > -1)
486 demux->sub->id &= 0x1F;
487 if(!demux->opts->sub_lang && demux->sub->id == -1)
488 demux->sub->id = aid;
489 if(demux->sub->id==aid){
490 ds=demux->sub;
492 } else if((aid >= 0x80 && aid <= 0x8F) || (aid >= 0x98 && aid <= 0xAF) || (aid >= 0xC0 && aid <= 0xCF)) {
494 // aid=128+(aid&0x7F);
495 // aid=0x80..0xBF
496 new_audio_stream(demux, aid);
497 if(demux->audio->id==aid){
498 int type;
499 ds=demux->audio;
500 if(!ds->sh) ds->sh=demux->a_streams[aid];
501 // READ Packet: Skip additional audio header data:
502 if(!rawa52) {
503 c=stream_read_char(demux->stream);//num of frames
504 type=stream_read_char(demux->stream);//startpos hi
505 type=(type<<8)|stream_read_char(demux->stream);//startpos lo
506 // printf("\r[%02X][%04X]",c,type);
507 len-=3;
509 if((aid&0xE0)==0xA0 && len>=3){
510 unsigned char* hdr;
511 // save audio header as codecdata!
512 if(!((sh_audio_t*)(ds->sh))->codecdata_len){
513 ((sh_audio_t*)(ds->sh))->codecdata=malloc(3);
514 ((sh_audio_t*)(ds->sh))->codecdata_len=3;
516 hdr=((sh_audio_t*)(ds->sh))->codecdata;
517 // read LPCM header:
518 // emphasis[1], mute[1], rvd[1], frame number[5]:
519 hdr[0]=stream_read_char(demux->stream);
520 // printf(" [%01X:%02d]",c>>5,c&31);
521 // quantization[2],freq[2],rvd[1],channels[3]
522 hdr[1]=stream_read_char(demux->stream);
523 // printf("[%01X:%01X] ",c>>4,c&15);
524 // dynamic range control (0x80=off):
525 hdr[2]=stream_read_char(demux->stream);
526 // printf("[%02X] ",c);
527 len-=3;
528 if(len<=0) mp_msg(MSGT_DEMUX,MSGL_V,"End of packet while searching for PCM header\n");
530 // printf(" \n");
531 } // if(demux->audio->id==aid)
533 } else mp_msg(MSGT_DEMUX,MSGL_V,"Unknown 0x1BD substream: 0x%02X \n",aid);
534 } //if(id==0x1BD)
535 } else {
536 if(c!=0x0f){
537 mp_msg(MSGT_DEMUX,MSGL_V," {ERROR5,c=%d} \n",c);
538 return -1; // invalid packet !!!!!!
541 if(mpeg_pts_error) mp_msg(MSGT_DEMUX,MSGL_V," {PTS_err:%d} \n",mpeg_pts_error);
542 mp_dbg(MSGT_DEMUX,MSGL_DBG3," => len=%d\n",len);
544 // if(len<=0 || len>MAX_PS_PACKETSIZE) return -1; // Invalid packet size
545 if(len<=0 || len>MAX_PS_PACKETSIZE){
546 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"Invalid PS data len: %d\n",len);
547 return -1; // invalid packet !!!!!!
550 if(id>=0x1C0 && id<=0x1DF){
551 // mpeg audio
552 int aid=id-0x1C0;
553 new_audio_stream(demux, aid);
554 if(demux->audio->id==aid){
555 ds=demux->audio;
556 if(!ds->sh) ds->sh=demux->a_streams[aid];
557 if(priv && ds->sh) {
558 sh_audio_t *sh = (sh_audio_t *)ds->sh;
559 if(priv->es_map[id - 0x1B0])
560 sh->format = priv->es_map[id - 0x1B0];
561 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"ASSIGNED TO STREAM %d CODEC %x\n", id, priv->es_map[id - 0x1B0]);
564 } else
565 if(id>=0x1E0 && id<=0x1EF){
566 // mpeg video
567 int aid=id-0x1E0;
568 if(!demux->v_streams[aid]) new_sh_video(demux,aid);
569 if(demux->video->id==-1) demux->video->id=aid;
570 if(demux->video->id==aid){
571 ds=demux->video;
572 if(!ds->sh) ds->sh=demux->v_streams[aid];
573 if(priv && ds->sh) {
574 sh_video_t *sh = (sh_video_t *)ds->sh;
575 if(priv->es_map[id - 0x1B0]) {
576 sh->format = priv->es_map[id - 0x1B0];
577 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"ASSIGNED TO STREAM %d CODEC %x\n", id, priv->es_map[id - 0x1B0]);
583 if(ds){
584 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"DEMUX_MPG: Read %d data bytes from packet %04X\n",len,id);
585 // printf("packet start = 0x%X \n",stream_tell(demux->stream)-packet_start_pos);
587 dp=new_demux_packet(len);
588 if(!dp) {
589 mp_dbg(MSGT_DEMUX,MSGL_ERR,"DEMUX_MPG ERROR: couldn't create demux_packet(%d bytes)\n",len);
590 stream_skip(demux->stream,len);
591 return 0;
593 l = stream_read(demux->stream,dp->buffer,len);
594 if(l<len)
595 resize_demux_packet(dp, l);
596 len = l;
597 if(set_pts)
598 dp->pts=pts/90000.0f;
599 dp->pos=demux->filepos;
601 workaround:
602 set dp->stream_pts only when feeding the video stream, or strangely interleaved files
603 (such as SWIII) will show strange alternations in the stream time, wildly going
604 back and forth
606 if(ds == demux->video && stream_control(demux->stream, STREAM_CTRL_GET_CURRENT_TIME,(void *)&stream_pts)!=STREAM_UNSUPPORTED)
607 dp->stream_pts = stream_pts;
608 ds_add_packet(ds,dp);
609 if (demux->priv && set_pts) ((mpg_demuxer_t*)demux->priv)->last_pts = pts/90000.0f;
610 // if(ds==demux->sub) parse_dvdsub(ds->last->buffer,ds->last->len);
611 return 1;
613 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"DEMUX_MPG: Skipping %d data bytes from packet %04X\n",len,id);
614 if(len<=2356) stream_skip(demux->stream,len);
615 return 0;
618 static int num_elementary_packets100=0;
619 static int num_elementary_packets101=0;
620 static int num_elementary_packets12x=0;
621 static int num_elementary_packets1B6=0;
622 static int num_elementary_packetsPES=0;
623 static int num_mpeg12_startcode=0;
624 static int num_h264_slice=0; //combined slice
625 static int num_h264_dpa=0; //DPA Slice
626 static int num_h264_dpb=0; //DPB Slice
627 static int num_h264_dpc=0; //DPC Slice
628 static int num_h264_idr=0; //IDR Slice
629 static int num_h264_sps=0;
630 static int num_h264_pps=0;
632 static int num_mp3audio_packets=0;
634 static void clear_stats(void)
636 num_elementary_packets100=0;
637 num_elementary_packets101=0;
638 num_elementary_packets1B6=0;
639 num_elementary_packets12x=0;
640 num_elementary_packetsPES=0;
641 num_mpeg12_startcode=0;
642 num_h264_slice=0; //combined slice
643 num_h264_dpa=0; //DPA Slice
644 num_h264_dpb=0; //DPB Slice
645 num_h264_dpc=0; //DPC Slice
646 num_h264_idr=0; //IDR Slice
647 num_h264_sps=0;
648 num_h264_pps=0;
649 num_mp3audio_packets=0;
652 //assumes demuxer->synced < 2
653 static inline void update_stats(int head)
655 if(head==0x1B6) ++num_elementary_packets1B6;
656 else if(head==0x1B3 || head==0x1B8) ++num_mpeg12_startcode;
657 else if(head==0x100) ++num_elementary_packets100;
658 else if(head==0x101) ++num_elementary_packets101;
659 else if(head==0x1BD || (0x1C0<=head && head<=0x1EF))
660 num_elementary_packetsPES++;
661 else if(head>=0x120 && head<=0x12F) ++num_elementary_packets12x;
662 if(head>=0x100 && head<0x1B0)
664 if((head&~0x60) == 0x101) ++num_h264_slice;
665 else if((head&~0x60) == 0x102) ++num_h264_dpa;
666 else if((head&~0x60) == 0x103) ++num_h264_dpb;
667 else if((head&~0x60) == 0x104) ++num_h264_dpc;
668 else if((head&~0x60) == 0x105 && head != 0x105) ++num_h264_idr;
669 else if((head&~0x60) == 0x107 && head != 0x107) ++num_h264_sps;
670 else if((head&~0x60) == 0x108 && head != 0x108) ++num_h264_pps;
674 static int demux_mpg_probe(demuxer_t *demuxer) {
675 int pes av_unused = 1;
676 int tmp;
677 off_t tmppos;
678 int file_format = DEMUXER_TYPE_UNKNOWN;
680 tmppos=stream_tell(demuxer->stream);
681 tmp=stream_read_dword(demuxer->stream);
682 if(tmp==0x1E0 || tmp==0x1C0) {
683 tmp=stream_read_word(demuxer->stream);
684 if(tmp>1 && tmp<=2048) pes=0; // demuxer->synced=3; // PES...
686 stream_seek(demuxer->stream,tmppos);
688 clear_stats();
690 if(demux_mpg_open(demuxer))
691 file_format=DEMUXER_TYPE_MPEG_PS;
692 else {
693 mp_msg(MSGT_DEMUX,MSGL_V,"MPEG packet stats: p100: %d p101: %d p1B6: %d p12x: %d sli: %d a: %d b: %d c: %d idr: %d sps: %d pps: %d PES: %d MP3: %d, synced: %d\n",
694 num_elementary_packets100,num_elementary_packets101,
695 num_elementary_packets1B6,num_elementary_packets12x,
696 num_h264_slice, num_h264_dpa,
697 num_h264_dpb, num_h264_dpc=0,
698 num_h264_idr, num_h264_sps=0,
699 num_h264_pps,
700 num_elementary_packetsPES,num_mp3audio_packets, demuxer->synced);
702 //MPEG packet stats: p100: 458 p101: 458 PES: 0 MP3: 1103 (.m2v)
703 if(num_mp3audio_packets>50 && num_mp3audio_packets>2*num_elementary_packets100
704 && abs(num_elementary_packets100-num_elementary_packets101)>2)
705 return file_format;
707 // some hack to get meaningfull error messages to our unhappy users:
708 if(num_mpeg12_startcode>=2 && num_elementary_packets100>=2 && num_elementary_packets101>=2 &&
709 abs(num_elementary_packets101+8-num_elementary_packets100)<16) {
710 if(num_elementary_packetsPES>=4 && num_elementary_packetsPES>=num_elementary_packets100-4) {
711 return file_format;
713 file_format=DEMUXER_TYPE_MPEG_ES; // <-- hack is here :)
714 } else
715 // fuzzy mpeg4-es detection. do NOT enable without heavy testing of mpeg formats detection!
716 if(num_elementary_packets1B6>3 && num_elementary_packets12x>=1 &&
717 num_elementary_packetsPES==0 && num_elementary_packets100<=num_elementary_packets12x &&
718 demuxer->synced<2) {
719 file_format=DEMUXER_TYPE_MPEG4_ES;
720 } else
721 // fuzzy h264-es detection. do NOT enable without heavy testing of mpeg formats detection!
722 if((num_h264_slice>3 || (num_h264_dpa>3 && num_h264_dpb>3 && num_h264_dpc>3)) &&
723 /* FIXME num_h264_sps>=1 && */ num_h264_pps>=1 && num_h264_idr>=1 &&
724 num_elementary_packets1B6==0 && num_elementary_packetsPES==0 &&
725 demuxer->synced<2) {
726 file_format=DEMUXER_TYPE_H264_ES;
727 } else
729 if(demuxer->synced==2)
730 mp_msg(MSGT_DEMUXER, MSGL_ERR, "MPEG: %s",
731 mp_gtext("Missing video stream!? Contact the author, it may be a bug :(\n"));
732 else
733 mp_tmsg(MSGT_DEMUXER,MSGL_V,"Not MPEG System Stream format... (maybe Transport Stream?)\n");
736 //FIXME this shouldn't be necessary
737 stream_seek(demuxer->stream,tmppos);
738 return file_format;
741 static int demux_mpg_es_fill_buffer(demuxer_t *demux, demux_stream_t *ds){
742 // Elementary video stream
743 if(demux->stream->eof) return 0;
744 demux->filepos=stream_tell(demux->stream);
745 ds_read_packet(demux->video,demux->stream,STREAM_BUFFER_SIZE,0,demux->filepos,0);
746 return 1;
750 * \brief discard until 0x100 header and return a filled buffer
751 * \param b buffer-end pointer
752 * \param pos current pos in stream, negative since b points to end of buffer
753 * \param s stream to read from
754 * \return new position, differs from original pos when eof hit and thus
755 * b was modified to point to the new end of buffer
757 static int find_end(unsigned char **b, int pos, stream_t *s) {
758 register int state = 0xffffffff;
759 unsigned char *buf = *b;
760 int start = pos;
761 int read, unused;
762 // search already read part
763 while (state != 0x100 && pos) {
764 state = state << 8 | buf[pos++];
766 // continue search in stream
767 while (state != 0x100) {
768 register int c = stream_read_char(s);
769 if (c < 0) break;
770 state = state << 8 | c;
772 // modify previous header (from 0x1bc or 0x1bf to 0x100)
773 buf[start++] = 0;
774 // copy remaining buffer part to current pos
775 memmove(&buf[start], &buf[pos], -pos);
776 unused = start + -pos; // -unused bytes in buffer
777 read = stream_read(s, &buf[unused], -unused);
778 unused += read;
779 // fix buffer so it ends at pos == 0 (eof case)
780 *b = &buf[unused];
781 start -= unused;
782 return start;
786 * This format usually uses an insane bitrate, which makes this function
787 * performance-critical!
788 * Be sure to benchmark any changes with different compiler versions.
790 static int demux_mpg_gxf_fill_buffer(demuxer_t *demux, demux_stream_t *ds) {
791 demux_packet_t *pack;
792 int len;
793 demux->filepos = stream_tell(demux->stream);
794 pack = new_demux_packet(STREAM_BUFFER_SIZE);
795 len = stream_read(demux->stream, pack->buffer, STREAM_BUFFER_SIZE);
796 if (len <= 0)
798 free_demux_packet(pack);
799 return 0;
802 register uint32_t state = (uint32_t)demux->priv;
803 register int pos = -len;
804 unsigned char *buf = &pack->buffer[len];
805 do {
806 state = state << 8 | buf[pos];
807 if (unlikely((state | 3) == 0x1bf))
808 pos = find_end(&buf, pos, demux->stream);
809 } while (++pos < 0);
810 demux->priv = (void *)state;
811 len = buf - pack->buffer;
813 if (len < STREAM_BUFFER_SIZE)
814 resize_demux_packet(pack, len);
815 ds_add_packet(ds, pack);
816 return 1;
819 static int demux_mpg_fill_buffer(demuxer_t *demux, demux_stream_t *ds)
821 unsigned int head=0;
822 int skipped=0;
823 int max_packs=256; // 512kbyte
824 int ret=0;
826 // System stream
828 demux->filepos=stream_tell(demux->stream);
829 //lame workaround: this is needed to show the progress bar when playing dvdnav://
830 //(ths poor guy doesn't know teh length of the stream at startup)
831 demux->movi_end = demux->stream->end_pos;
832 head=stream_read_dword(demux->stream);
833 if((head&0xFFFFFF00)!=0x100){
834 // sync...
835 demux->filepos-=skipped;
836 while(1){
837 int c=stream_read_char(demux->stream);
838 if(c<0) break; //EOF
839 head<<=8;
840 if(head!=0x100){
841 head|=c;
842 if(mp_check_mp3_header(head)) ++num_mp3audio_packets;
843 ++skipped; //++demux->filepos;
844 continue;
846 head|=c;
847 break;
849 demux->filepos+=skipped;
851 if(stream_eof(demux->stream)) break;
852 // sure: head=0x000001XX
853 mp_dbg(MSGT_DEMUX,MSGL_DBG4,"*** head=0x%X\n",head);
854 if(demux->synced==0){
855 if(head==0x1BA) demux->synced=1; //else
856 // if(head==0x1BD || (head>=0x1C0 && head<=0x1EF)) demux->synced=3; // PES?
857 } else
858 if(demux->synced==1){
859 if(head==0x1BB || head==0x1BD || (head>=0x1C0 && head<=0x1EF)){
860 demux->synced=2;
861 mp_msg(MSGT_DEMUX,MSGL_V,"system stream synced at 0x%"PRIX64" (%"PRId64")!\n",(int64_t)demux->filepos,(int64_t)demux->filepos);
862 num_elementary_packets100=0; // requires for re-sync!
863 num_elementary_packets101=0; // requires for re-sync!
864 } else demux->synced=0;
865 } // else
866 if(demux->synced>=2){
867 ret=demux_mpg_read_packet(demux,head);
868 if(!ret)
869 if(--max_packs==0){
870 demux->stream->eof=1;
871 mp_tmsg(MSGT_DEMUX,MSGL_ERR,"demux: File doesn't contain the selected audio or video stream.\n");
872 return 0;
874 if(demux->synced==3) demux->synced=(ret==1)?2:0; // PES detect
875 } else {
876 update_stats(head);
877 if(head>=0x100 && head<0x1B0)
878 mp_msg(MSGT_DEMUX,MSGL_DBG3,"Opps... elementary video packet found: %03X\n",head);
879 else if((head>=0x1C0 && head<0x1F0) || head==0x1BD)
880 mp_msg(MSGT_DEMUX,MSGL_DBG3,"Opps... PES packet found: %03X\n",head);
882 if(((num_elementary_packets100>50 && num_elementary_packets101>50) ||
883 (num_elementary_packetsPES>50)) && skipped>4000000){
884 mp_msg(MSGT_DEMUX,MSGL_V,"sync_mpeg_ps: seems to be ES/PES stream...\n");
885 demux->stream->eof=1;
886 break;
888 if(num_mp3audio_packets>100 && num_elementary_packets100<10){
889 mp_msg(MSGT_DEMUX,MSGL_V,"sync_mpeg_ps: seems to be MP3 stream...\n");
890 demux->stream->eof=1;
891 break;
894 } while(ret!=1);
895 mp_dbg(MSGT_DEMUX,MSGL_DBG2,"demux: %d bad bytes skipped\n",skipped);
896 if(demux->stream->eof){
897 mp_msg(MSGT_DEMUX,MSGL_V,"MPEG Stream reached EOF\n");
898 return 0;
900 return 1;
903 static void demux_seek_mpg(demuxer_t *demuxer, float rel_seek_secs,
904 float audio_delay, int flags)
906 demux_stream_t *d_audio=demuxer->audio;
907 demux_stream_t *d_video=demuxer->video;
908 sh_audio_t *sh_audio=d_audio->sh;
909 sh_video_t *sh_video=d_video->sh;
910 mpg_demuxer_t *mpg_d=(mpg_demuxer_t*)demuxer->priv;
911 int precision = 1;
912 float oldpts = 0;
913 off_t oldpos = demuxer->filepos;
914 float newpts = 0;
915 off_t newpos = (flags & SEEK_ABSOLUTE) ? demuxer->movi_start : oldpos;
917 if(mpg_d)
918 oldpts = mpg_d->last_pts;
919 newpts = (flags & SEEK_ABSOLUTE) ? 0.0 : oldpts;
920 //================= seek in MPEG ==========================
921 //calculate the pts to seek to
922 if(flags & SEEK_FACTOR) {
923 if (mpg_d && mpg_d->first_to_final_pts_len > 0.0)
924 newpts += mpg_d->first_to_final_pts_len * rel_seek_secs;
925 else
926 newpts += rel_seek_secs * (demuxer->movi_end - demuxer->movi_start) * oldpts / oldpos;
927 } else
928 newpts += rel_seek_secs;
929 if (newpts < 0) newpts = 0;
931 if(flags&SEEK_FACTOR){
932 // float seek 0..1
933 newpos+=(demuxer->movi_end-demuxer->movi_start)*rel_seek_secs;
934 } else {
935 // time seek (secs)
936 if (mpg_d && mpg_d->has_valid_timestamps) {
937 if (mpg_d->first_to_final_pts_len > 0.0)
938 newpos += rel_seek_secs * (demuxer->movi_end - demuxer->movi_start) / mpg_d->first_to_final_pts_len;
939 else if (oldpts > 0.0)
940 newpos += rel_seek_secs * (oldpos - demuxer->movi_start) / oldpts;
941 } else if(!sh_video || !sh_video->i_bps) // unspecified or VBR
942 newpos+=2324*75*rel_seek_secs; // 174.3 kbyte/sec
943 else
944 newpos+=sh_video->i_bps*rel_seek_secs;
947 while (1) {
948 if(newpos<demuxer->movi_start){
949 if(demuxer->stream->type!=STREAMTYPE_VCD) demuxer->movi_start=0; // for VCD
950 if(newpos<demuxer->movi_start) newpos=demuxer->movi_start;
953 stream_seek(demuxer->stream,newpos);
955 // re-sync video:
956 videobuf_code_len=0; // reset ES stream buffer
958 ds_fill_buffer(d_video);
959 if(sh_audio){
960 ds_fill_buffer(d_audio);
963 while(1){
964 int i;
965 if(sh_audio && !d_audio->eof && d_video->pts && d_audio->pts){
966 float a_pts=d_audio->pts;
967 a_pts+=(ds_tell_pts(d_audio)-sh_audio->a_in_buffer_len)/(float)sh_audio->i_bps;
968 if(d_video->pts>a_pts){
969 skip_audio_frame(sh_audio); // sync audio
970 continue;
973 if(!sh_video) break;
974 i=sync_video_packet(d_video);
975 if(sh_video->format == mmioFOURCC('W', 'V', 'C', '1')) {
976 if(i==0x10E || i==0x10F) //entry point or sequence header
977 break;
978 } else
979 if(sh_video->format == 0x10000004) { //mpeg4
980 if(i==0x1B6) { //vop (frame) startcode
981 int pos = videobuf_len;
982 if(!read_video_packet(d_video)) break; // EOF
983 if((videobuffer[pos+4] & 0x3F) == 0) break; //I-frame
985 } else if(sh_video->format == 0x10000005){ //h264
986 if((i & ~0x60) == 0x105) break;
987 } else { //default mpeg1/2
988 if(i==0x1B3 || i==0x1B8) break; // found it!
990 if(!i || !skip_video_packet(d_video)) break; // EOF?
992 if(!mpg_d)
993 break;
994 if (!precision || abs(newpts - mpg_d->last_pts) < 0.5 || (mpg_d->last_pts == oldpts)) break;
995 if ((newpos - oldpos) * (mpg_d->last_pts - oldpts) < 0) { // invalid timestamps
996 mpg_d->has_valid_timestamps = 0;
997 break;
999 precision--;
1000 //prepare another seek because we are off by more than 0.5s
1001 if(mpg_d) {
1002 newpos += (newpts - mpg_d->last_pts) * (newpos - oldpos) / (mpg_d->last_pts - oldpts);
1003 demux_flush(demuxer);
1004 demuxer->stream->eof=0; // clear eof flag
1005 d_video->eof=0;
1006 d_audio->eof=0;
1011 static int demux_mpg_control(demuxer_t *demuxer, int cmd, void *arg)
1013 mpg_demuxer_t *mpg_d=(mpg_demuxer_t*)demuxer->priv;
1015 switch(cmd) {
1016 case DEMUXER_CTRL_GET_TIME_LENGTH:
1017 if(stream_control(demuxer->stream, STREAM_CTRL_GET_TIME_LENGTH, arg) != STREAM_UNSUPPORTED) {
1018 mp_msg(MSGT_DEMUXER,MSGL_DBG2,"\r\nDEMUX_MPG_CTRL, (%.3f)\r\n", *((double*)arg));
1019 return DEMUXER_CTRL_GUESS;
1021 if (mpg_d && mpg_d->has_valid_timestamps) {
1022 *((double *)arg)=(double)mpg_d->first_to_final_pts_len;
1023 return DEMUXER_CTRL_OK;
1025 return DEMUXER_CTRL_DONTKNOW;
1027 case DEMUXER_CTRL_GET_PERCENT_POS:
1028 if (mpg_d && mpg_d->has_valid_timestamps && mpg_d->first_to_final_pts_len > 0.0) {
1029 *((int *)arg)=(int)(100 * (mpg_d->last_pts-mpg_d->first_pts) / mpg_d->first_to_final_pts_len);
1030 return DEMUXER_CTRL_OK;
1032 return DEMUXER_CTRL_DONTKNOW;
1034 case DEMUXER_CTRL_SWITCH_AUDIO:
1035 if(! (mpg_d && mpg_d->num_a_streams > 1 && demuxer->audio && demuxer->audio->sh))
1036 return DEMUXER_CTRL_NOTIMPL;
1037 else {
1038 demux_stream_t *d_audio = demuxer->audio;
1039 sh_audio_t *sh_audio = d_audio->sh;
1040 sh_audio_t *sh_a = sh_audio;
1041 int i;
1042 if(!sh_audio)
1043 return DEMUXER_CTRL_NOTIMPL;
1044 if (*((int*)arg) < 0)
1046 for (i = 0; i < mpg_d->num_a_streams; i++) {
1047 if (d_audio->id == mpg_d->a_stream_ids[i]) break;
1049 i = (i+1) % mpg_d->num_a_streams;
1050 sh_a = (sh_audio_t*)demuxer->a_streams[mpg_d->a_stream_ids[i]];
1052 else {
1053 for (i = 0; i < mpg_d->num_a_streams; i++)
1054 if (*((int*)arg) == mpg_d->a_stream_ids[i]) break;
1055 if (i < mpg_d->num_a_streams)
1056 sh_a = (sh_audio_t*)demuxer->a_streams[*((int*)arg)];
1058 if (i < mpg_d->num_a_streams && d_audio->id != mpg_d->a_stream_ids[i]) {
1059 d_audio->id = mpg_d->a_stream_ids[i];
1060 d_audio->sh = sh_a;
1061 ds_free_packs(d_audio);
1064 *((int*)arg) = demuxer->audio->id;
1065 return DEMUXER_CTRL_OK;
1067 default:
1068 return DEMUXER_CTRL_NOTIMPL;
1073 static int demux_mpg_pes_probe(demuxer_t *demuxer) {
1074 demuxer->synced = 3;
1075 return (demux_mpg_probe(demuxer) == DEMUXER_TYPE_MPEG_PS) ? DEMUXER_TYPE_MPEG_PES : 0;
1079 static demuxer_t* demux_mpg_es_open(demuxer_t* demuxer)
1081 sh_video_t *sh_video=NULL;
1083 demuxer->audio->sh = NULL; // ES streams has no audio channel
1084 demuxer->video->sh = new_sh_video(demuxer,0); // create dummy video stream header, id=0
1085 sh_video=demuxer->video->sh;sh_video->ds=demuxer->video;
1087 return demuxer;
1090 static demuxer_t *demux_mpg_gxf_open(demuxer_t *demuxer) {
1091 demuxer->audio->sh = NULL;
1092 demuxer->video->sh = new_sh_video(demuxer,0);
1093 ((sh_video_t *)demuxer->video->sh)->ds = demuxer->video;
1094 demuxer->priv = (void *) 0xffffffff;
1095 return demuxer;
1098 static demuxer_t* demux_mpg_ps_open(demuxer_t* demuxer)
1100 sh_audio_t *sh_audio=NULL;
1101 sh_video_t *sh_video=NULL;
1103 sh_video=demuxer->video->sh;sh_video->ds=demuxer->video;
1105 if(demuxer->audio->id!=-2) {
1106 if(!ds_fill_buffer(demuxer->audio)){
1107 mp_msg(MSGT_DEMUXER, MSGL_INFO, "MPEG: %s",
1108 mp_gtext("No audio stream found -> no sound.\n"));
1109 demuxer->audio->sh=NULL;
1110 } else {
1111 sh_audio=demuxer->audio->sh;sh_audio->ds=demuxer->audio;
1115 if(!sh_video->format && ps_probe > 0) {
1116 int head;
1117 off_t pos = stream_tell(demuxer->stream);
1119 clear_stats();
1120 do {
1121 head=sync_video_packet(demuxer->video);
1122 if(!head) break;
1123 update_stats(head);
1124 skip_video_packet(demuxer->video);
1125 } while(stream_tell(demuxer->stream) < pos + ps_probe && !demuxer->stream->eof);
1127 ds_free_packs(demuxer->video);
1128 demuxer->stream->eof=0;
1129 stream_seek(demuxer->stream, pos);
1130 mp_msg(MSGT_DEMUX,MSGL_INFO,"MPEG packet stats: p100: %d p101: %d p1B6: %d p12x: %d sli: %d a: %d b: %d c: %d idr: %d sps: %d pps: %d\n",
1131 num_elementary_packets100, num_elementary_packets101,
1132 num_elementary_packets1B6, num_elementary_packets12x,
1133 num_h264_slice, num_h264_dpa, num_h264_dpb, num_h264_dpc,
1134 num_h264_idr, num_h264_sps, num_h264_pps);
1136 if(num_elementary_packets1B6>3 && num_elementary_packets12x>=1 &&
1137 num_elementary_packets100<=num_elementary_packets12x)
1138 sh_video->format = 0x10000004;
1139 else if((num_h264_slice>3 || (num_h264_dpa>3 && num_h264_dpb>3 && num_h264_dpc>3)) &&
1140 num_h264_sps>=1 && num_h264_pps>=1 && num_h264_idr>=1 &&
1141 num_elementary_packets1B6==0)
1142 sh_video->format = 0x10000005;
1143 else sh_video->format = 0x10000002;
1146 return demuxer;
1150 const demuxer_desc_t demuxer_desc_mpeg_ps = {
1151 "MPEG PS demuxer",
1152 "mpegps",
1153 "MPEG-PS",
1154 "Arpi?",
1155 "Mpeg",
1156 DEMUXER_TYPE_MPEG_PS,
1157 0, // unsafe autodetect
1158 demux_mpg_probe,
1159 demux_mpg_fill_buffer,
1160 demux_mpg_ps_open,
1161 demux_close_mpg,
1162 demux_seek_mpg,
1163 demux_mpg_control,
1167 const demuxer_desc_t demuxer_desc_mpeg_pes = {
1168 "MPEG PES demuxer",
1169 "mpegpes",
1170 "MPEG-PES",
1171 "Arpi?",
1172 "Mpeg",
1173 DEMUXER_TYPE_MPEG_PES,
1174 0, // unsafe autodetect
1175 demux_mpg_pes_probe,
1176 demux_mpg_fill_buffer,
1177 demux_mpg_ps_open,
1178 demux_close_mpg,
1179 demux_seek_mpg,
1180 demux_mpg_control,
1184 const demuxer_desc_t demuxer_desc_mpeg_gxf = {
1185 "MPEG ES in GXF demuxer",
1186 "mpeggxf",
1187 "MPEG-ES in GXF",
1188 "Reimar Doeffinger",
1189 "Mpeg",
1190 DEMUXER_TYPE_MPEG_GXF,
1191 0, // hack autodetection
1192 NULL,
1193 demux_mpg_gxf_fill_buffer,
1194 demux_mpg_gxf_open,
1195 NULL,
1196 NULL,
1197 NULL
1200 const demuxer_desc_t demuxer_desc_mpeg_es = {
1201 "MPEG ES demuxer",
1202 "mpeges",
1203 "MPEG-ES",
1204 "Arpi?",
1205 "Mpeg",
1206 DEMUXER_TYPE_MPEG_ES,
1207 0, // hack autodetection
1208 NULL,
1209 demux_mpg_es_fill_buffer,
1210 demux_mpg_es_open,
1211 demux_close_mpg,
1212 demux_seek_mpg,
1213 demux_mpg_control,
1217 const demuxer_desc_t demuxer_desc_mpeg4_es = {
1218 "MPEG4 ES demuxer",
1219 "mpeg4es",
1220 "MPEG-ES",
1221 "Arpi?",
1222 "Mpeg",
1223 DEMUXER_TYPE_MPEG4_ES,
1224 0, // hack autodetection
1225 NULL,
1226 demux_mpg_es_fill_buffer,
1227 demux_mpg_es_open,
1228 demux_close_mpg,
1229 demux_seek_mpg,
1230 demux_mpg_control,
1234 const demuxer_desc_t demuxer_desc_h264_es = {
1235 "H.264 ES demuxer",
1236 "h264es",
1237 "H264-ES",
1238 "Arpi?",
1239 "Mpeg",
1240 DEMUXER_TYPE_H264_ES,
1241 0, // hack autodetection
1242 NULL,
1243 demux_mpg_es_fill_buffer,
1244 demux_mpg_es_open,
1245 demux_close_mpg,
1246 demux_seek_mpg,
1247 demux_mpg_control,