1 /*
2  *  demuxer.c
3  *
4  *  Copyright (C) Thomas Oestreich - June 2001
5  *
6  *  This file is part of transcode, a video stream processing tool
7  *
8  *  transcode is free software; you can redistribute it and/or modify
9  *  it under the terms of the GNU General Public License as published by
10  *  the Free Software Foundation; either version 2, or (at your option)
11  *  any later version.
12  *
13  *  transcode is distributed in the hope that it will be useful,
14  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  *  GNU General Public License for more details.
17  *
18  *  You should have received a copy of the GNU General Public License
19  *  along with GNU Make; see the file COPYING.  If not, write to
20  *  the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
21  *
22  */
23 
24 #include "transcode.h"
25 #include "libtc/libtc.h"
26 #include "tcinfo.h"
27 
28 #include "ioaux.h"
29 #include "aux_pes.h"
30 #include "seqinfo.h"
31 #include "demuxer.h"
32 #include "packets.h"
33 
34 #include <math.h>
35 
36 static int demux_mode=TC_DEMUX_SEQ_ADJUST;
37 
38 int gop, gop_pts, gop_cnt;
39 
40 typedef struct timecode_struc	/* Time_code Struktur laut MPEG		*/
41 {   unsigned long msb;		/* fuer SCR, DTS, PTS			*/
42     unsigned long lsb;
43     unsigned long reference_ext;
44     unsigned long negative;     /* for delays when doing multiple files */
45 } Timecode_struc;
46 
47 #define MAX_FFFFFFFF 4294967295.0 	/* = 0xffffffff in hex.	*/
48 
49 /* ------------------------------------------------------------
50  *
51  * support code (scr_rewrite()) moved from aux_pes.c
52  *
53  * ------------------------------------------------------------*/
54 
make_timecode(double timestamp,Timecode_struc * pointer)55 static void make_timecode (double timestamp, Timecode_struc *pointer)
56 {
57     double temp_ts;
58 
59     if (timestamp < 0.0) {
60       pointer->negative = 1;
61       timestamp = -timestamp;
62     } else
63       pointer->negative = 0;
64 
65     temp_ts = floor(timestamp / 300.0);
66 
67     if (temp_ts > MAX_FFFFFFFF) {
68       pointer->msb=1;
69       temp_ts -= MAX_FFFFFFFF;
70       pointer->lsb=(unsigned long)temp_ts;
71     } else {
72       pointer->msb=0;
73       pointer->lsb=(unsigned long)temp_ts;
74     }
75 
76     pointer->reference_ext = (unsigned long)(timestamp - (floor(timestamp / 300.0) * 300.0));
77 
78 }
79 
80 #define MPEG2_MARKER_SCR	1		/* MPEG2 Marker SCR	*/
81 
82 /*************************************************************************
83     Kopiert einen TimeCode in einen Bytebuffer. Dabei wird er nach
84     MPEG-Verfahren in bits aufgesplittet.
85 
86     Makes a Copy of a TimeCode in a Buffer, splitting it into bitfields
87     according to MPEG-System
88 *************************************************************************/
89 
buffer_timecode_scr(Timecode_struc * pointer,unsigned char ** buffer)90 static void buffer_timecode_scr (Timecode_struc *pointer, unsigned char **buffer)
91 {
92 
93   unsigned char temp;
94   unsigned char marker=MPEG2_MARKER_SCR;
95 
96 
97   temp = (marker << 6) | (pointer->msb << 5) |
98     ((pointer->lsb >> 27) & 0x18) | 0x4 | ((pointer->lsb >> 28) & 0x3);
99   *((*buffer)++)=temp;
100   temp = (pointer->lsb & 0x0ff00000) >> 20;
101   *((*buffer)++)=temp;
102   temp = ((pointer->lsb & 0x000f8000) >> 12) | 0x4 |
103     ((pointer->lsb & 0x00006000) >> 13);
104   *((*buffer)++)=temp;
105   temp = (pointer->lsb & 0x00001fe0) >> 5;
106   *((*buffer)++)=temp;
107   temp = ((pointer->lsb & 0x0000001f) << 3) | 0x4 |
108     ((pointer->reference_ext & 0x00000180) >> 7);
109   *((*buffer)++)=temp;
110   temp = ((pointer->reference_ext & 0x0000007F) << 1) | 1;
111   *((*buffer)++)=temp;
112 
113 }
114 
scr_rewrite(char * buf,uint32_t pts)115 static void scr_rewrite(char *buf, uint32_t pts)
116 {
117   Timecode_struc timecode;
118   unsigned char * ucbuf = (unsigned char *)buf;
119 
120   timecode.msb = 0;
121   timecode.lsb = 0;
122   timecode.reference_ext = 0;
123   timecode.negative = 0;
124 
125   make_timecode((double) pts, &timecode);
126 
127   buffer_timecode_scr(&timecode, &ucbuf);
128 }
129 
130 /* ------------------------------------------------------------
131  *
132  * demuxer / synchronization thread
133  *
134  * ------------------------------------------------------------*/
135 
tcdemux_thread(info_t * ipipe)136 void tcdemux_thread(info_t *ipipe)
137 {
138 
139     int k, id=0, zz=0;
140 
141     int j, i, bytes, filesize;
142     char *buffer=NULL;
143 
144     int payload_id=0, select=PACKAGE_ALL;
145 
146     double pts=0.0f, ref_pts=0.0f, resync_pts=-1.0f, pts_diff=0.0f, track_initial_pts=0.0f;
147     double av_fine_pts1=-1.0f, av_fine_pts2=-1.0f, av_fine_diff=0.0f;
148 
149     uint32_t frame_based_lpts=0;
150 
151     int unit_seek=0, unit, track=0, is_track=0;
152 
153     int resync_seq1=0, resync_seq2=INT_MAX, seq_dump, seq_seek;
154     int keep_seq = 0;
155     int hard_fps = 0;
156 
157     int has_pts_dts=0, demux_video=0, demux_audio=0;
158 
159     int flag_flush        = 0;
160     int flag_force        = 0;
161     int flag_eos          = 0;
162     int flag_has_audio    = 0;
163     int flag_append_audio = 0;
164     int flag_notify       = 1;
165     int flag_avsync       = 1;
166     int flag_skip         = 0;
167     int flag_sync_reset   = 0;
168     int flag_sync_active  = 0;
169     int flag_loop_all     = 0;
170     int flag_av_fine_tune = 0;
171     int flag_rewrite_scr  = 0;
172     int flag_field_encoded= 0;
173 
174     //for demux_mode=2
175     int seq_picture_ctr=0, pack_picture_ctr=0, sequence_ctr=0, packet_ctr=0;
176 
177     char buf[256];
178     const char *logfile;
179     unsigned long i_pts, i_dts;
180     unsigned int packet_size=VOB_PACKET_SIZE;
181     seq_list_t *ptr=NULL;
182     double fps;
183 
184 
185     // allocate space
186     if((buffer = tc_zalloc(packet_size))==NULL) {
187       tc_log_perror(__FILE__, "out of memory");
188       exit(1);
189     }
190 
191     // copy info parameter to local variables
192 
193     unit_seek   = ipipe->ps_unit;
194     resync_seq1 = ipipe->ps_seq1;
195     resync_seq2 = ipipe->ps_seq2;
196     track       = ipipe->track;
197 
198     //map track on substream id
199 
200     switch(ipipe->codec) {
201 
202     case TC_CODEC_SUB:
203       track+=0x20;
204       flag_rewrite_scr=1;
205       break;
206     case TC_CODEC_AC3:
207       track+=0x80;
208       break;
209     case TC_CODEC_PCM:
210       track+=0xA0;
211       break;
212     case TC_CODEC_MP3:
213       track+=0xC0;
214       break;
215     case TC_CODEC_MPEG2:
216       // for MPEG2 video, use this substream id for sync adjustment
217       track=ipipe->subid;
218       demux_video=1;
219       break;
220     }
221 
222     //0.6.0pre4
223     if(demux_video==0) {
224 
225 	if(ipipe->demux == TC_DEMUX_SEQ_FSYNC)
226 	    ipipe->demux=TC_DEMUX_SEQ_ADJUST;
227 
228 	if(ipipe->demux == TC_DEMUX_SEQ_FSYNC2)
229 	    ipipe->demux=TC_DEMUX_SEQ_ADJUST2;
230 
231 	//substream synchonized with video in "force frame rate" mode
232 	demux_audio=1;
233     }
234 
235     if(ipipe->demux == TC_DEMUX_SEQ_FSYNC || ipipe->demux == TC_DEMUX_SEQ_FSYNC2 || ipipe->demux == TC_DEMUX_SEQ_LIST) {
236 
237       //allocate buffer
238       if(flush_buffer_init(ipipe->fd_out, ipipe->verbose)<0) {
239 	tc_log_error(__FILE__, "flush buffer facility init failed");
240 	exit(1);
241       }
242 
243       //need to open the logfile
244       if(seq_init(ipipe->name, ipipe->fd_log, ipipe->fps, ipipe->verbose)<0) {
245 	tc_log_error(__FILE__, "sync mode init failed");
246 	exit(1);
247       }
248     }
249 
250 
251     //new default behaving:
252     //    if(unit_seek==0 && resync_seq1==0 && resync_seq2 == INT_MAX) flag_loop_all=1;
253     //changes 0.6.0pre3:
254     //tcprobe selects start unit --> switch to flag_loop_all always true
255     // for any given unit
256     if(resync_seq1==0 && resync_seq2 == INT_MAX) flag_loop_all=1;
257 
258     demux_mode  = ipipe->demux;
259     select      = ipipe->select;
260     fps         = ipipe->fps;
261     logfile     = ipipe->name;
262     keep_seq    = ipipe->keep_seq;
263     hard_fps    = ipipe->hard_fps_flag;
264 
265     j=0;  //packet counter
266     i=0;  //skipped packets counter
267     k=0;  //unit counter
268 
269     // will be switched on as soon start of sequences to flush is reached
270     flag_flush=0;
271 
272     flag_notify=1;
273 
274     flag_avsync=0;
275     flag_append_audio=0;
276 
277     if(keep_seq) flag_sync_active=1;
278 
279     unit=unit_seek;
280 
281     seq_seek = resync_seq1;
282     seq_dump = resync_seq2 - resync_seq1;
283 
284     ++unit_seek;
285     ++seq_seek;
286 
287     if(!flag_loop_all) {
288       tc_log_msg(__FILE__, "seeking to sequence %d:%d ...", unit, resync_seq1);
289     }
290 
291     filesize = 0;
292     for(;;) {
293 
294       /* ------------------------------------------------------------
295        *
296        * (I) read a 2048k block
297        *
298        * ------------------------------------------------------------*/
299 
300       if((bytes=tc_pread(ipipe->fd_in, buffer, packet_size)) != packet_size) {
301 
302 	//program end code?
303 	if(bytes==4) {
304 	  if(scan_pack_header(buffer, MPEG_PROGRAM_END_CODE)) {
305 	    if(ipipe->verbose & TC_DEBUG)
306 	      tc_log_msg(__FILE__, "(pid=%d) program stream end code detected",
307 			 getpid());
308 	    break;
309 	  }
310 	}
311 
312 	if(bytes)
313 	  tc_log_warn(__FILE__, "invalid program stream packet size (%d/%d)",
314 		      bytes, packet_size);
315 
316 	break;
317       }
318       filesize += bytes;
319 
320       // do not make any tests in pass-through mode
321       if(demux_mode==TC_DEMUX_OFF) goto flush_packet;
322 
323       /* ------------------------------------------------------------
324        *
325        * (II) packet header ok?
326        *
327        * ------------------------------------------------------------*/
328 
329 
330       if(!scan_pack_header(buffer, TC_MAGIC_VOB)) {
331 
332 	if(flag_notify && (ipipe->verbose & TC_DEBUG))
333 	  tc_log_warn(__FILE__, "(pid=%d) invalid packet header detected",
334 		      getpid());
335 
336 	// something else?
337 
338 	if(scan_pack_header(buffer, MPEG_VIDEO) | scan_pack_header(buffer, MPEG_AUDIO)) {
339 
340 	    if(ipipe->verbose & TC_STATS)
341 		tc_log_msg(__FILE__, "(pid=%d) MPEG system stream detected",
342 			   getpid());
343 
344 	    if(scan_pack_header(buffer, MPEG_VIDEO)) payload_id=PACKAGE_VIDEO;
345 	    if(scan_pack_header(buffer, MPEG_AUDIO)) payload_id=PACKAGE_AUDIO_MP3;
346 
347 	    // no further processing
348 	    goto flush_packet;
349 	} else {
350 
351 	    tc_log_warn(__FILE__, "(pid=%d) '0x%02x%02x%02x%02x' not yet supported",
352 			getpid(), buffer[0] & 0xff, buffer[1] & 0xff,
353 			buffer[2] & 0xff, buffer[3] & 0xff);
354 	    break;
355 	}
356       } else {
357 
358 	//MPEG1?
359 	if ((buffer[4] & 0xf0) == 0x20) {
360 
361 	  payload_id=PACKAGE_MPEG1;
362 	  flag_flush=1;
363 
364 	  if(ipipe->verbose & TC_STATS)
365 	    tc_log_msg(__FILE__, "(pid=%d) MPEG-1 video stream detected",
366 		       getpid());
367 
368 	  // no further processing
369 	  goto flush_packet;
370 	}
371       }
372 
373 
374       /* ------------------------------------------------------------
375        *
376        * (III) analyze packet contents
377        *
378        * ------------------------------------------------------------*/
379 
380 
381       // proceed with a valid package, assume defaults
382 
383       flag_skip=0;          //do not skip
384       has_pts_dts=0;        //no pts_dts stamp
385       payload_id=0;         //payload unknown
386       flag_sync_reset=0;    //no reset of syncinfo
387 
388       id = buffer[17] & 0xff;  //payload id byte
389 
390       //MPEG 2?
391       if ((buffer[4] & 0xc0) == 0x40) {
392 
393 	// do not change any flags
394 
395 	if(ipipe->verbose & TC_STATS) {
396 	  //display info only once
397 	  tc_log_msg(__FILE__, "(pid=%d) MPEG-2 video stream detected",
398 		     getpid());
399 	}
400       } else {
401 
402 	//MPEG1
403 	if ((buffer[4] & 0xf0) == 0x20) {
404 
405 	  payload_id=PACKAGE_MPEG1;
406 
407 	  if(ipipe->verbose & TC_STATS) {
408 	    //display info only once
409 	    tc_log_msg(__FILE__, "(pid=%d) MPEG-1 video stream detected",
410 		       getpid());
411 	  }
412 	} else {
413 
414 	  payload_id=PACKAGE_PASS;
415 
416 	  if(ipipe->verbose & TC_DEBUG)
417 	    tc_log_warn(__FILE__, "(pid=%d) unknown stream packet id detected",
418 			getpid());
419 	}
420 
421 	//flush all MPEG1 stuff
422 	goto flush_packet;
423       }
424 
425       /* ------------------------------------------------------------
426        *
427        * (IV) audio payload
428        *
429        * ------------------------------------------------------------*/
430 
431       // check payload id
432       // process this audio packet?
433 
434       // sync to AC3 audio mode?
435       if(id == P_ID_AC3) payload_id = PACKAGE_PRIVATE_STREAM;
436 
437       // sync to MP3 audio mode?
438       if(id >= 0xc0 && id <= 0xdf) payload_id = PACKAGE_AUDIO_MP3;
439 
440       // are we dealing with the right track?
441       // check here:
442 
443       is_track=0;
444 
445       if(payload_id == PACKAGE_PRIVATE_STREAM) {
446 
447 	//position of track code
448 	uint8_t *_buf=buffer+14;
449 	uint8_t *_tmp=_buf + 9 + _buf[8];
450 
451 	is_track = ((*_tmp) == track) ? 1:0;
452 
453 	if(ipipe->verbose & TC_STATS)
454 	  tc_log_msg(__FILE__, "substream [0x%x] %d", *_tmp, is_track);
455 
456 	if(is_track==0) {
457 	  flag_skip=1;  //drop this packet
458 	} else {
459 	  flag_skip=0;
460 	  goto sync_track;
461 	}
462       }
463 
464       if(payload_id & PACKAGE_AUDIO_MP3) {
465 
466 	is_track = ((id) == track) ? 1:0;
467 	if(is_track==0) flag_skip=1;  //drop this packet
468 
469 	if(ipipe->verbose & TC_STATS)
470 	  tc_log_msg(__FILE__, "MPEG audio track [0x%x] %d", id, is_track);
471       }
472 
473     sync_track:
474 
475       if(is_track) {
476 
477 
478 	if(flag_sync_active==0) {
479 
480 	  //first valid audio packet!
481 
482 	  // get pts time stamp:
483 	  ac_memcpy(buf, &buffer[20], 16);
484 	  has_pts_dts=get_pts_dts(buf, &i_pts, &i_dts);
485 
486 	  if(has_pts_dts) {
487 	    track_initial_pts=(double)i_pts/90000.;
488 	  } else {
489 	    //fallback to scr time stamp:
490 	    ac_memcpy(buf, &buffer[4], 6);
491 	    track_initial_pts = read_time_stamp(buf);
492 	  }
493 
494 	  if(resync_pts<0) {
495 	    pts_diff = track_initial_pts;
496 	  } else {
497 	    pts_diff = track_initial_pts - resync_pts;
498 	  }
499 
500 	  //pts_diff<0 is OK, the packets will be dropped to establish sync
501 	  //pts_diff>0 is not so simple, since we need to drop video
502 	  //packets, already submitted to flush buffer
503 
504 	  //enable sync mode, check for PTS giant leap????
505 	  if(pts_diff < TC_DEMUX_MIN_PTS || pts_diff > TC_DEMUX_CRIT_PTS)
506 	    flag_sync_active = 1;
507 
508 	  //0.6.0pre5: frame dropping handled by transcode
509 	  flag_sync_active=1;
510 
511 	  //unless this flag is on, the video sequence is dropped
512 	  //in TC_DEMUX_SEQ_FSYNC mode
513 	}
514 
515 
516 	// sync now, if requested:
517 
518 	if(!unit_seek) flag_has_audio=1; //unit has audio packets
519 
520 
521 	// need to find the time difference of two audio packets
522 	// for fine-tuning AV sync.
523 
524 	if(flag_av_fine_tune == 0) {
525 	  // get pts time stamp:
526 	  ac_memcpy(buf, &buffer[20], 16);
527 	  has_pts_dts=get_pts_dts(buf, &i_pts, &i_dts);
528 
529 	  if(av_fine_pts1<0) {
530 	    av_fine_pts1 = (double)i_pts/90000.;
531 	  } else {
532 	    av_fine_pts2 = (double)i_pts/90000.;
533 	    flag_av_fine_tune=1;
534 	  }
535 
536 	  //diff:
537 	  if(flag_av_fine_tune==1) {
538 	    av_fine_diff=av_fine_pts2-av_fine_pts1;
539 	    if(ipipe->verbose & TC_DEBUG)
540 	      tc_log_msg(__FILE__, "AV fine-tuning: %d ms",
541 			 (int)(av_fine_diff*1000));
542 	  }
543 
544 	  //sanity check:
545 	  if(av_fine_diff<0) av_fine_diff=0.0f;
546 
547 	}
548 
549 	//Pre-processing: check if we need to re-sync?
550 
551 	if(demux_mode == TC_DEMUX_SEQ_FSYNC2 || demux_mode == TC_DEMUX_SEQ_ADJUST2) {
552 	    //new demux modes let transcode handle audio sync shift
553 	    flag_avsync=0;
554 	    flag_skip=0;
555 	}
556 
557 	if(flag_avsync) {
558 
559 	  // get pts time stamp:
560 	  ac_memcpy(buf, &buffer[20], 16);
561 	  has_pts_dts=get_pts_dts(buf, &i_pts, &i_dts);
562 
563 	  if(has_pts_dts) {
564 	    pts=(double)i_pts/90000.;
565 	  } else {
566 	    //fallback to scr time stamp:
567 	    ac_memcpy(buf, &buffer[4], 6);
568 	    pts = read_time_stamp(buf);
569 	  }
570 
571 	  pts_diff = pts - resync_pts;
572 
573 	  //correction
574 	  //FIXME
575 	  pts_diff += av_fine_diff;
576 
577 	  if(pts_diff<0) {
578 	    flag_skip=1;
579 
580 	    if(ipipe->verbose & TC_DEBUG)
581 	      tc_log_msg(__FILE__, "(pid=%d) audio packet %06d for PU [%d] skipped (%.4f)",
582 			 getpid(), j, ((k==0)? 0:k-1), pts-resync_pts);
583 	  } else {
584 	    //reset
585 	    flag_skip=0;
586 	    flag_avsync=0;
587 	    if(ipipe->verbose)
588 	      tc_log_msg(__FILE__, "(pid=%d) AV sync established for PU [%d] at PTS=%.4f (%.4f)",
589 			 getpid(), k-1, pts, pts-resync_pts);
590 	  }
591 	}
592 
593 	//Post-processing: more audio packets?
594 
595 	if(flag_append_audio) {
596 
597 	  //need to flush a few audio packets, if video ahead
598 
599 	  // get pts time stamp:
600 	  ac_memcpy(buf, &buffer[20], 16);
601 	  has_pts_dts=get_pts_dts(buf, &i_pts, &i_dts);
602 
603 	  if(has_pts_dts) {
604 	    pts=(double)i_pts/90000.;
605 	  } else {
606 	    //fallback to scr time stamp:
607 	    ac_memcpy(buf, &buffer[4], 6);
608 	    pts = read_time_stamp(buf);
609 	  }
610 
611 	  pts_diff = pts - resync_pts;
612 
613 	  if(pts_diff<0) {
614 
615 	    //append this packet
616 	    flag_skip=0;
617 
618 	    if(ipipe->verbose & TC_DEBUG)
619 	      tc_log_msg(__FILE__, "(pid=%d) audio packet %06d for PU [%d] appended (%.4f)",
620 			 getpid(), j, ((k==0)? 0:k-1), pts-resync_pts);
621 	  } else {
622 	    //abort - all done
623 	    flag_eos=1;
624 	    if(ipipe->verbose)
625 	      tc_log_msg(__FILE__, "(pid=%d) AV sync abandoned for PU [%d] at PTS=%.4f (%.4f)",
626 			 getpid(), k-1, pts, pts-resync_pts);
627 	  }
628 	}
629       }
630 
631       //only go for audio in this phase
632       if(flag_append_audio) goto flush_packet;
633 
634       /* ------------------------------------------------------------
635        *
636        * (V) misc payload
637        *
638        * ------------------------------------------------------------*/
639 
640 
641       if(id == P_ID_PROG || id == P_ID_PADD)  {
642 
643 	payload_id=PACKAGE_NAV;
644 
645 	// get pts time stamp:
646 	ac_memcpy(buf, &buffer[20], 16);
647 	has_pts_dts=get_pts_dts(buf, &i_pts, &i_dts);
648 
649 	if(has_pts_dts) {
650 	  pts=(double)i_pts/90000.;
651 	} else {
652 	  //fallback to scr time stamp:
653 	  ac_memcpy(buf, &buffer[4], 6);
654 	  pts = read_time_stamp(buf);
655 	}
656 
657 	//do not dump this packet
658 	flag_skip=1;
659       }
660 
661       /* ------------------------------------------------------------
662        *
663        * (VI) video payload
664        *
665        * ------------------------------------------------------------*/
666 
667 
668       if(id == P_ID_MPEG) {
669 
670 	payload_id = PACKAGE_VIDEO;
671 
672 	// get pts time stamp:
673 	ac_memcpy(buf, &buffer[4], 6);
674 	pts = read_time_stamp(buf);
675 
676 	//read full packet header
677 	ac_memcpy(buf, &buffer[20], 16);
678 	has_pts_dts=get_pts_dts(buf, &i_pts, &i_dts);
679 
680 	//need frame/field encoding information
681 	zz=scan_pack_ext(buffer);
682 	if(zz>0) flag_field_encoded=zz;
683 
684 	//need precise number of pics in this sequence
685 	pack_picture_ctr = scan_pack_pics(buffer);
686 
687 	seq_picture_ctr += pack_picture_ctr;
688 
689 	frame_based_lpts = (seq_picture_ctr-1);
690 
691 	//need this pack for subtitle PTS information
692 	if(flag_rewrite_scr && has_pts_dts) flag_force=1;
693 
694 	// only process packets with pts/dts time stamp, since
695 	// they (all?) have a sequence start code
696 
697 	if(has_pts_dts) {
698 
699 	  if (ipipe->verbose & TC_STATS)
700 	    tc_log_msg(__FILE__, "(pid=%d) PTS-DTS detected in packet [%06d]",
701 		       getpid(), j);
702 
703 	  // default first(=0) unit ?
704 	  if(k==0) {
705 
706 	    --unit_seek;
707 	    flag_sync_reset=1;
708 
709 	    if(ipipe->verbose & TC_DEBUG)
710 	      tc_log_msg(__FILE__, "(pid=%d) MPEG sequence start code in packet %06d for PU [0]",
711 			 getpid(), j);
712 
713 	    k++;
714 	  }
715 
716 
717 	  if(pts<ref_pts) {
718 
719 	    --unit_seek;
720 	    flag_sync_reset=1;
721 
722 	    // past next unit - abort
723 	    // or process all following units?
724 
725 	    if(unit_seek<0 && flag_loop_all==0) flag_eos=1;
726 
727 	    //experimental: try to resync
728 	    //flag_avsync = 1;
729 
730 	    if(ipipe->verbose & TC_DEBUG)
731 	      tc_log_msg(__FILE__, "(pid=%d) PTS reset (%.3f->%.3f) in packet %06d for PU [%d]",
732 			 getpid(), ref_pts, pts, j, k);
733 
734 	    k++;
735 	  }
736 
737 
738 	  // only decrement sequence counter in right unit, i.e.
739 	  // unit_seek=0;
740 	  if(!unit_seek) --seq_seek;
741 
742 	  // flush all sequences until the end of the unit
743 	  // or end of stream
744 	  // or resync_seq2 is reached
745 
746 	  if(seq_seek==0) {
747 
748 	    //re read packet header
749 	    ac_memcpy(buf, &buffer[20], 16);
750 	    get_pts_dts(buf, &i_pts, &i_dts);
751 
752 	    resync_pts = (double) i_pts / 90000;
753 
754 	    if(!flag_flush) {
755 
756 	      // need to dump requested seq_dump sequences
757 	      seq_seek=seq_dump;
758 	      flag_flush = 1;
759 
760 	      flag_avsync = 1;
761 
762 	      // may be a useful info for the user
763 	      if(ipipe->verbose)
764 		tc_log_msg(__FILE__, "(pid=%d) processing PU [%d], on at PTS=%.4f sec",
765 			   getpid(), k-1, resync_pts);
766 
767 	    } else {
768 				// finished, all sequences flushed, switch
769 			        // to audio packets post processing
770 	      flag_append_audio = 1;
771 	      flag_skip = 1;  //flush mode on, but do not write this one
772 
773 	      // may be a useful info for the user
774 	      if(ipipe->verbose)
775 		tc_log_msg(__FILE__, "(pid=%d) processing PU [%d], off at PTS=%.4f sec",
776 			   getpid(), k-1, resync_pts);
777 	    }
778 	  }
779 
780 	  //---------------------------------------------------
781 	  //gather information on the sequences before flushing
782 	  //---------------------------------------------------
783 
784 	  if((demux_mode == TC_DEMUX_SEQ_FSYNC || demux_mode == TC_DEMUX_SEQ_FSYNC2) && flag_flush) {
785 
786 	    ptr = seq_register(sequence_ctr);
787 
788 	    zz=(flag_field_encoded==3)?(seq_picture_ctr-pack_picture_ctr):
789 		(seq_picture_ctr-pack_picture_ctr)/2;
790 
791 	    if(sequence_ctr)  seq_update(ptr->prev, i_pts, zz, packet_ctr, flag_sync_active, hard_fps);
792 
793 	    //init sequence information structure for current sequence
794 
795 	    ptr->pts = i_pts;
796 	    ptr->dts = i_dts;
797 	    ptr->pics_first_packet = pack_picture_ctr;
798 	    ptr->sync_reset = flag_sync_reset;
799 
800 	    //reset/update
801 	    seq_picture_ctr = 0;
802 	    packet_ctr = 0;
803 	    ++sequence_ctr;
804 
805 	    //shift resync_pts, since sequence is dropped
806 	    if(flag_sync_active==0) resync_pts=(double) i_pts / 90000;
807 
808 	  } //end TC_DEMUX_SEQ_FSYNC mode
809 
810 	  //---------------------------------------------------
811 	  //print out sequence information for frame navigation
812 	  //---------------------------------------------------
813 
814 	  if((demux_mode == TC_DEMUX_SEQ_LIST) && flag_flush) {
815 
816 	    ptr = seq_register(sequence_ctr);
817 
818 	    zz=(flag_field_encoded==3)?(seq_picture_ctr-pack_picture_ctr):
819 		(seq_picture_ctr-pack_picture_ctr)/2;
820 
821 	    if(sequence_ctr)  seq_list(ptr->prev, i_pts, zz, packet_ctr, flag_sync_active);
822 
823 	    //init sequence information structure for current sequence
824 
825 	    ptr->pts = i_pts;
826 	    ptr->dts = i_dts;
827 	    ptr->pics_first_packet = pack_picture_ctr;
828 	    ptr->sync_reset = flag_sync_reset;
829 	    ptr->packet_ctr=j;
830 
831 	    //reset/update
832 	    seq_picture_ctr = 0;
833 	    packet_ctr = 0;
834 	    ++sequence_ctr;
835 
836 	    //shift resync_pts, since sequence is dropped
837 	    if(flag_sync_active==0) resync_pts=(double) i_pts / 90000;
838 
839 	  } //end TC_DEMUX_SEQ_LIST mode
840 
841 	  //reset sync pts, if no audio/substream has been found (0.6.0pre4)
842 	  if(flag_sync_active==0 && demux_audio) {
843 	    resync_pts=(double) i_pts / 90000;
844 	    if(ipipe->verbose & TC_DEBUG)
845 	      tc_log_msg(__FILE__, "new initial PTS=%f", resync_pts);
846 	  }
847 
848 	}// PTS-DTS flag yes
849 
850 	ref_pts=pts;
851 
852       }// MPEG video packet
853 
854       /* ------------------------------------------------------------
855        *
856        * (VII) evaluate scan results - flush packet
857        *
858        * ------------------------------------------------------------*/
859 
860     flush_packet:
861 
862 
863       if(ipipe->verbose & TC_STATS)
864 	tc_log_msg(__FILE__, "INFO: j=%05d, i=%05d, skip=%d, flush=%d, force=%d, pay=%3d, sid=0x%02x, eos=%d",
865 		   j, i, flag_skip, flag_flush, flag_force, payload_id, id, flag_eos);
866 
867       //need to rewrite SCR pack header entry based on
868       //frame_based_pts information for transcode:
869       if(flag_rewrite_scr) scr_rewrite(&buffer[4], ((flag_field_encoded==3)?frame_based_lpts:frame_based_lpts/2));
870 
871       //flush here:
872 
873       switch(demux_mode) {
874 
875       case TC_DEMUX_DEBUG:
876 	if((flag_flush && !flag_skip && (payload_id & select))
877 	   || flag_force) scan_pack_payload(buffer, packet_size, j, ipipe->verbose);
878 	break;
879 
880       case TC_DEMUX_DEBUG_ALL:
881 	scan_pack_payload(buffer, packet_size, j, ipipe->verbose);
882 	break;
883 
884       case TC_DEMUX_SEQ_FSYNC:
885       case TC_DEMUX_SEQ_FSYNC2:
886 
887 	if((flag_flush && !flag_skip && (payload_id & select)) || flag_force) {
888 
889 	  //count current sequence packets to be flushed
890 	  ++packet_ctr;
891 
892 	  if(ipipe->verbose & TC_STATS)
893 	    tc_log_msg(__FILE__, "flushing packet (%d/%d)", sequence_ctr, j);
894 
895 	  if(flush_buffer_write(ipipe->fd_out, buffer, packet_size) != packet_size) {
896 	    tc_log_perror(__FILE__, "write program stream packet");
897 	    exit(1);
898 	  }
899 
900 	  //reset
901 	  flag_force=0;
902 	}
903 
904 	break;
905 
906       case TC_DEMUX_SEQ_ADJUST:
907       case TC_DEMUX_SEQ_ADJUST2:
908 
909 	if((flag_flush && !flag_skip && (payload_id & select)) || flag_force) {
910 
911 	  if(tc_pwrite(ipipe->fd_out, buffer, packet_size) != packet_size) {
912 	    tc_log_perror(__FILE__, "write program stream packet");
913 	    exit(1);
914 	  }
915 
916 	  //reset
917 	  flag_force=0;
918 
919 	  if(ipipe->verbose & TC_STATS)
920 	    tc_log_msg(__FILE__, "writing packet %d", j);
921 
922 	} else {
923 
924 	  ++i;
925 	  if(ipipe->verbose & TC_STATS)
926 	    tc_log_msg(__FILE__, "skipping packet %d", j);
927 	}
928 
929 	break;
930 
931 
932       case TC_DEMUX_SEQ_LIST:
933 
934 	//count packs
935 	++packet_ctr;
936 
937 	// nothing to do
938 	break;
939 
940       case TC_DEMUX_OFF:
941 
942 	if(tc_pwrite(ipipe->fd_out, buffer, packet_size) != packet_size) {
943 	  tc_log_perror(__FILE__, "write program stream packet");
944 	  exit(1);
945 	}
946 
947 	if(ipipe->verbose & TC_STATS)
948 	  tc_log_msg(__FILE__, "writing packet %d", j);
949 
950 	break;
951       }
952 
953       //aborting?
954       if(flag_eos) break;
955 
956       //total packs (2k each) counter
957       ++j;
958 
959     } // process next packet/block
960 
961     if(ipipe->verbose & TC_SYNC)
962       tc_log_msg(__FILE__, "EOS - flushing packet buffer");
963 
964     //post processing
965 
966     if(demux_mode == TC_DEMUX_SEQ_FSYNC || demux_mode == TC_DEMUX_SEQ_FSYNC2) {
967       seq_close();
968       flush_buffer_close();
969     }
970 
971     if(demux_mode == TC_DEMUX_SEQ_LIST) {
972 
973       ptr = seq_register(sequence_ctr);
974 
975       zz=(flag_field_encoded==3)?(seq_picture_ctr-pack_picture_ctr):
976 	  (seq_picture_ctr-pack_picture_ctr)/2;
977 
978       if(ptr!=NULL && ptr->id)  seq_list(ptr->prev, ref_pts, zz, packet_ctr, flag_sync_active);
979 
980       fflush(stdout);
981 
982       //summary
983       seq_list_frames();
984 
985       seq_close();
986       flush_buffer_close();
987 
988     }
989 
990     //summary
991     if(ipipe->verbose & TC_DEBUG)
992       tc_log_msg(__FILE__, "(pid=%d) %d/%d packets discarded", getpid(), i, j);
993 
994     if(buffer!=NULL) free(buffer);
995 
996     return;
997 }
998 
999