comparison mpeg.c @ 452:11d07f14b077 libavformat

mpeg SVCD compatibility, SCR fixes, standard compliance - fixed VBR+constrained bitstream header flags for non-VCD - more sane (and SVCD compatible) value for video stream->max_buffer_size - always write at least one PES header stuffing byte for MPEG-2 to prevent accidental start code generation - do not write more than 16 stuffing bytes in a PES header (not allowed). Use padding packets instead. - include a PES extension in the first MPEG-2 packet - fill the first pack of SVCD files with padding - "sanity hack" that prevents the SCR from overtaking the PTS for non-VCD - fixed VCD PTS values to correspond to the SCR - always include DTS in the first SVCD packet (fixes lots of compatibility problems with DVD players) patch by (Hauke Duden <H.NS.Duden at gmx dot net>)
author michael
date Mon, 26 Apr 2004 22:16:06 +0000
parents 94aa265c18b9
children 696f41bc8784
comparison
equal deleted inserted replaced
451:31784bdb76ee 452:11d07f14b077
142 /* This header applies only to the video stream (see VCD standard p. IV-7)*/ 142 /* This header applies only to the video stream (see VCD standard p. IV-7)*/
143 put_bits(&pb, 6, 0); 143 put_bits(&pb, 6, 0);
144 } else 144 } else
145 put_bits(&pb, 6, s->audio_bound); 145 put_bits(&pb, 6, s->audio_bound);
146 146
147 if (s->is_vcd) 147 if (s->is_vcd) {
148 put_bits(&pb, 1, 0); /* see VCD standard, p. IV-7*/ 148 /* see VCD standard, p. IV-7*/
149 else 149 put_bits(&pb, 1, 0);
150 put_bits(&pb, 1, 1); /* variable bitrate*/ 150 put_bits(&pb, 1, 1);
151 put_bits(&pb, 1, 1); /* non constrainted bit stream */ 151 } else {
152 put_bits(&pb, 1, 0); /* variable bitrate*/
153 put_bits(&pb, 1, 0); /* non constrainted bit stream */
154 }
152 155
153 if (s->is_vcd) { 156 if (s->is_vcd) {
154 /* see VCD standard p IV-7 */ 157 /* see VCD standard p IV-7 */
155 put_bits(&pb, 1, 1); /* audio locked */ 158 put_bits(&pb, 1, 1); /* audio locked */
156 put_bits(&pb, 1, 1); /* video locked */ 159 put_bits(&pb, 1, 1); /* video locked */
284 stream->lpcm_header[2] = 0x80; 287 stream->lpcm_header[2] = 0x80;
285 stream->lpcm_align = st->codec.channels * 2; 288 stream->lpcm_align = st->codec.channels * 2;
286 } else { 289 } else {
287 stream->id = mpa_id++; 290 stream->id = mpa_id++;
288 } 291 }
292
293 /* This value HAS to be used for VCD (see VCD standard, p. IV-7).
294 Right now it is also used for everything else.*/
289 stream->max_buffer_size = 4 * 1024; 295 stream->max_buffer_size = 4 * 1024;
290 s->audio_bound++; 296 s->audio_bound++;
291 break; 297 break;
292 case CODEC_TYPE_VIDEO: 298 case CODEC_TYPE_VIDEO:
293 /* by default, video is used for the SCR computation */ 299 /* by default, video is used for the SCR computation */
294 if (s->scr_stream_index == -1) 300 if (s->scr_stream_index == -1)
295 s->scr_stream_index = i; 301 s->scr_stream_index = i;
296 stream->id = mpv_id++; 302 stream->id = mpv_id++;
297 stream->max_buffer_size = 46 * 1024; 303 if (s->is_vcd)
304 /* see VCD standard, p. IV-7*/
305 stream->max_buffer_size = 46 * 1024;
306 else
307 /* This value HAS to be used for SVCD (see SVCD standard, p. 26 V.2.3.2).
308 Right now it is also used for everything else.*/
309 stream->max_buffer_size = 230 * 1024;
298 s->video_bound++; 310 s->video_bound++;
299 break; 311 break;
300 default: 312 default:
301 av_abort(); 313 av_abort();
302 } 314 }
463 if ((s->packet_number % s->system_header_freq) == 0) 475 if ((s->packet_number % s->system_header_freq) == 0)
464 buf_index += s->system_header_size; 476 buf_index += s->system_header_size;
465 } 477 }
466 } 478 }
467 479
468 if (s->is_vcd && stream->packet_number==0) 480 if ((s->is_vcd && stream->packet_number==0)
481 || (s->is_svcd && s->packet_number==0))
469 /* the first pack of each stream contains only the pack header, 482 /* the first pack of each stream contains only the pack header,
470 the system header and some padding (see VCD standard p. IV-6) 483 the system header and some padding (see VCD standard p. IV-6)
471 Add the padding size, so that the actual payload becomes 0.*/ 484 Add the padding size, so that the actual payload becomes 0.*/
472 buf_index += s->packet_size - buf_index; 485 buf_index += s->packet_size - buf_index;
473 else { 486 else {
474 /* packet header size */ 487 /* packet header size */
475 buf_index += 6; 488 buf_index += 6;
476 if (s->is_mpeg2) 489 if (s->is_mpeg2) {
477 buf_index += 3; 490 buf_index += 3;
491 if (stream->packet_number==0)
492 buf_index += 3; /* PES extension */
493 buf_index += 1; /* obligatory stuffing byte */
494 }
478 if (pts != AV_NOPTS_VALUE) { 495 if (pts != AV_NOPTS_VALUE) {
479 if (dts != pts) 496 if (dts != pts)
480 buf_index += 5 + 5; 497 buf_index += 5 + 5;
481 else 498 else
482 buf_index += 5; 499 buf_index += 5;
552 int size, payload_size, startcode, id, stuffing_size, i, header_len; 569 int size, payload_size, startcode, id, stuffing_size, i, header_len;
553 int packet_size; 570 int packet_size;
554 uint8_t buffer[128]; 571 uint8_t buffer[128];
555 int zero_trail_bytes = 0; 572 int zero_trail_bytes = 0;
556 int pad_packet_bytes = 0; 573 int pad_packet_bytes = 0;
574 int pes_flags;
575 int general_pack = 0; /*"general" pack without data specific to one stream?*/
557 576
558 id = stream->id; 577 id = stream->id;
559 578
560 #if 0 579 #if 0
561 printf("packet ID=%2x PTS=%0.3f\n", 580 printf("packet ID=%2x PTS=%0.3f\n",
593 if (s->is_vcd && id == AUDIO_ID) 612 if (s->is_vcd && id == AUDIO_ID)
594 /* The VCD standard demands that 20 zero bytes follow 613 /* The VCD standard demands that 20 zero bytes follow
595 each audio pack (see standard p. IV-8).*/ 614 each audio pack (see standard p. IV-8).*/
596 zero_trail_bytes += 20; 615 zero_trail_bytes += 20;
597 616
598 if (s->is_vcd && stream->packet_number==0) { 617 if ((s->is_vcd && stream->packet_number==0)
599 /* the first pack of each stream contains only the pack header, 618 || (s->is_svcd && s->packet_number==0)) {
619 /* for VCD the first pack of each stream contains only the pack header,
600 the system header and lots of padding (see VCD standard p. IV-6). 620 the system header and lots of padding (see VCD standard p. IV-6).
601 In the case of an audio pack, 20 zero bytes are also added at 621 In the case of an audio pack, 20 zero bytes are also added at
602 the end.*/ 622 the end.*/
623 /* For SVCD we fill the very first pack to increase compatibility with
624 some DVD players. Not mandated by the standard.*/
625 if (s->is_svcd)
626 general_pack = 1; /* the system header refers to both streams and no stream data*/
603 pad_packet_bytes = packet_size - zero_trail_bytes; 627 pad_packet_bytes = packet_size - zero_trail_bytes;
604 } 628 }
605 629
606 packet_size -= pad_packet_bytes + zero_trail_bytes; 630 packet_size -= pad_packet_bytes + zero_trail_bytes;
607 631
611 packet_size -= 6; 635 packet_size -= 6;
612 636
613 /* packet header */ 637 /* packet header */
614 if (s->is_mpeg2) { 638 if (s->is_mpeg2) {
615 header_len = 3; 639 header_len = 3;
640 if (stream->packet_number==0)
641 header_len += 3; /* PES extension */
642 header_len += 1; /* obligatory stuffing byte */
616 } else { 643 } else {
617 header_len = 0; 644 header_len = 0;
618 } 645 }
619 if (pts != AV_NOPTS_VALUE) { 646 if (pts != AV_NOPTS_VALUE) {
620 if (dts != pts) 647 if (dts != pts)
637 } 664 }
638 665
639 stuffing_size = payload_size - stream->buffer_ptr; 666 stuffing_size = payload_size - stream->buffer_ptr;
640 if (stuffing_size < 0) 667 if (stuffing_size < 0)
641 stuffing_size = 0; 668 stuffing_size = 0;
669 if (stuffing_size > 16) { /*<=16 for MPEG-1, <=32 for MPEG-2*/
670 pad_packet_bytes += stuffing_size;
671 packet_size -= stuffing_size;
672 payload_size -= stuffing_size;
673 stuffing_size = 0;
674 }
675
642 put_be32(&ctx->pb, startcode); 676 put_be32(&ctx->pb, startcode);
643 677
644 put_be16(&ctx->pb, packet_size); 678 put_be16(&ctx->pb, packet_size);
645 679
646 if (!s->is_mpeg2) 680 if (!s->is_mpeg2)
648 put_byte(&ctx->pb, 0xff); 682 put_byte(&ctx->pb, 0xff);
649 683
650 if (s->is_mpeg2) { 684 if (s->is_mpeg2) {
651 put_byte(&ctx->pb, 0x80); /* mpeg2 id */ 685 put_byte(&ctx->pb, 0x80); /* mpeg2 id */
652 686
687 pes_flags=0;
688
653 if (pts != AV_NOPTS_VALUE) { 689 if (pts != AV_NOPTS_VALUE) {
654 if (dts != pts) { 690 pes_flags |= 0x80;
655 put_byte(&ctx->pb, 0xc0); /* flags */ 691 if (dts != pts)
656 put_byte(&ctx->pb, header_len - 3 + stuffing_size); 692 pes_flags |= 0x40;
657 put_timestamp(&ctx->pb, 0x03, pts);
658 put_timestamp(&ctx->pb, 0x01, dts);
659 } else {
660 put_byte(&ctx->pb, 0x80); /* flags */
661 put_byte(&ctx->pb, header_len - 3 + stuffing_size);
662 put_timestamp(&ctx->pb, 0x02, pts);
663 }
664 } else {
665 put_byte(&ctx->pb, 0x00); /* flags */
666 put_byte(&ctx->pb, header_len - 3 + stuffing_size);
667 } 693 }
694
695 /* Both the MPEG-2 and the SVCD standards demand that the
696 P-STD_buffer_size field be included in the first packet of
697 every stream. (see SVCD standard p. 26 V.2.3.1 and V.2.3.2
698 and MPEG-2 standard 2.7.7) */
699 if (stream->packet_number == 0)
700 pes_flags |= 0x01;
701
702 put_byte(&ctx->pb, pes_flags); /* flags */
703 put_byte(&ctx->pb, header_len - 3 + stuffing_size);
704
705 if (pes_flags & 0x80) /*write pts*/
706 put_timestamp(&ctx->pb, (pes_flags & 0x40) ? 0x03 : 0x02, pts);
707 if (pes_flags & 0x40) /*write dts*/
708 put_timestamp(&ctx->pb, 0x01, dts);
709
710 if (pes_flags & 0x01) { /*write pes extension*/
711 put_byte(&ctx->pb, 0x10); /* flags */
712
713 /* P-STD buffer info */
714 if (id == AUDIO_ID)
715 put_be16(&ctx->pb, 0x4000 | stream->max_buffer_size/128);
716 else
717 put_be16(&ctx->pb, 0x6000 | stream->max_buffer_size/1024);
718 }
719
668 } else { 720 } else {
669 if (pts != AV_NOPTS_VALUE) { 721 if (pts != AV_NOPTS_VALUE) {
670 if (dts != pts) { 722 if (dts != pts) {
671 put_timestamp(&ctx->pb, 0x03, pts); 723 put_timestamp(&ctx->pb, 0x03, pts);
672 put_timestamp(&ctx->pb, 0x01, dts); 724 put_timestamp(&ctx->pb, 0x01, dts);
692 put_byte(&ctx->pb, stream->nb_frames); 744 put_byte(&ctx->pb, stream->nb_frames);
693 put_be16(&ctx->pb, stream->frame_start_offset); 745 put_be16(&ctx->pb, stream->frame_start_offset);
694 } 746 }
695 } 747 }
696 748
697 if (s->is_mpeg2) 749 if (s->is_mpeg2) {
750 /* special stuffing byte that is always written
751 to prevent accidental generation of start codes. */
752 put_byte(&ctx->pb, 0xff);
753
698 for(i=0;i<stuffing_size;i++) 754 for(i=0;i<stuffing_size;i++)
699 put_byte(&ctx->pb, 0xff); 755 put_byte(&ctx->pb, 0xff);
756 }
700 757
701 /* output data */ 758 /* output data */
702 put_buffer(&ctx->pb, stream->buffer, payload_size - stuffing_size); 759 put_buffer(&ctx->pb, stream->buffer, payload_size - stuffing_size);
703 } 760 }
704 761
709 put_byte(&ctx->pb, 0x00); 766 put_byte(&ctx->pb, 0x00);
710 767
711 put_flush_packet(&ctx->pb); 768 put_flush_packet(&ctx->pb);
712 769
713 s->packet_number++; 770 s->packet_number++;
714 stream->packet_number++; 771
772 /* only increase the stream packet number if this pack actually contains
773 something that is specific to this stream! I.e. a dedicated header
774 or some data.*/
775 if (!general_pack)
776 stream->packet_number++;
715 stream->nb_frames = 0; 777 stream->nb_frames = 0;
716 stream->frame_start_offset = 0; 778 stream->frame_start_offset = 0;
717 } 779 }
718 780
719 static void put_vcd_padding_sector(AVFormatContext *ctx) 781 static void put_vcd_padding_sector(AVFormatContext *ctx)
779 #endif 841 #endif
780 } else { 842 } else {
781 pts = timestamp; 843 pts = timestamp;
782 dts = timestamp; 844 dts = timestamp;
783 } 845 }
846
784 *ppts = pts & ((1LL << 33) - 1); 847 *ppts = pts & ((1LL << 33) - 1);
785 *pdts = dts & ((1LL << 33) - 1); 848 *pdts = dts & ((1LL << 33) - 1);
786 } 849 }
787 850
788 static int64_t update_scr(AVFormatContext *ctx,int stream_index,int64_t pts) 851 static int64_t update_scr(AVFormatContext *ctx,int stream_index,int64_t pts)
789 { 852 {
790 MpegMuxContext *s = ctx->priv_data; 853 MpegMuxContext *s = ctx->priv_data;
791 int64_t scr; 854 int64_t scr;
792 855 StreamInfo *stream;
793 if (s->is_vcd) 856 int i;
857
858 if (s->is_vcd) {
794 /* Since the data delivery rate is constant, SCR is computed 859 /* Since the data delivery rate is constant, SCR is computed
795 using the formula C + i * 1200 where C is the start constant 860 using the formula C + i * 1200 where C is the start constant
796 and i is the pack index. 861 and i is the pack index.
797 It is recommended that SCR 0 is at the beginning of the VCD front 862 It is recommended that SCR 0 is at the beginning of the VCD front
798 margin (a sequence of empty Form 2 sectors on the CD). 863 margin (a sequence of empty Form 2 sectors on the CD).
800 we use C = 30*1200 = 36000 865 we use C = 30*1200 = 36000
801 (Note that even if the front margin is not 30 sectors the file 866 (Note that even if the front margin is not 30 sectors the file
802 will still be correct according to the standard. It just won't have 867 will still be correct according to the standard. It just won't have
803 the "recommended" value).*/ 868 the "recommended" value).*/
804 scr = 36000 + s->packet_number * 1200; 869 scr = 36000 + s->packet_number * 1200;
870
871
872 #if 0
873 for(i=0;i<ctx->nb_streams;i++) {
874 stream = ctx->streams[i]->priv_data;
875
876 if(scr > stream->start_pts && stream->start_pts!=AV_NOPTS_VALUE) {
877 av_log(ctx, AV_LOG_DEBUG, "mpeg vcd: SCR above PTS (scr=%0.3f, stream index=%d, stream_pts=%0.3f).\n", scr/90000.0, i, stream->start_pts / 90000.0);
878 }
879 }
880 #endif
881 }
805 else { 882 else {
883
884
806 /* XXX I believe this calculation of SCR is wrong. SCR 885 /* XXX I believe this calculation of SCR is wrong. SCR
807 specifies at which time the data should enter the decoder. 886 specifies at which time the data should enter the decoder.
808 Two packs cannot enter the decoder at the same time. */ 887 Two packs cannot enter the decoder at the same time. */
809 888
810 /* XXX: system clock should be computed precisely, especially for 889 /* XXX: system clock should be computed precisely, especially for
812 if (stream_index == s->scr_stream_index 891 if (stream_index == s->scr_stream_index
813 && pts != AV_NOPTS_VALUE) 892 && pts != AV_NOPTS_VALUE)
814 scr = pts; 893 scr = pts;
815 else 894 else
816 scr = s->last_scr; 895 scr = s->last_scr;
896
897 /* "Sanity hack": make sure that the SCR does not overtake the pts of
898 buffered data that is still waiting to be written.*/
899 for(i=0;i<ctx->nb_streams;i++) {
900 stream = ctx->streams[i]->priv_data;
901
902 if(scr > stream->start_pts && stream->start_pts!=AV_NOPTS_VALUE) {
903 /* av_log(ctx, AV_LOG_DEBUG, "mpeg: restricting scr to stream pts (scr=%0.3f, stream index=%d, stream_pts=%0.3f).\n", scr/90000.0, i, stream->start_pts / 90000.0); */
904 scr = stream->start_pts;
905 }
906 }
817 } 907 }
818 908
819 s->last_scr=scr; 909 s->last_scr=scr;
820 910
821 return scr; 911 return scr;
832 int64_t pts, dts, new_start_pts, new_start_dts; 922 int64_t pts, dts, new_start_pts, new_start_dts;
833 int len, avail_size; 923 int len, avail_size;
834 924
835 compute_pts_dts(st, &pts, &dts, timestamp); 925 compute_pts_dts(st, &pts, &dts, timestamp);
836 926
927 if(s->is_svcd) {
928 /* offset pts and dts slightly into the future to be able
929 to do the compatibility fix below.*/
930 pts = (pts + 2) & ((1LL << 33) - 1);
931 dts = (dts + 2) & ((1LL << 33) - 1);
932
933 if (stream->packet_number == 0 && dts == pts)
934 /* For the very first packet we want to force the DTS to be included.
935 This increases compatibility with lots of DVD players.
936 Since the MPEG-2 standard mandates that DTS is only written when
937 it is different from PTS we have to move it slightly into the past.*/
938 dts = (dts - 2) & ((1LL << 33) - 1);
939 }
940 if(s->is_vcd) {
941 /* We have to offset the PTS, so that it is consistent with the SCR.
942 SCR starts at 36000, but the first two packs contain only padding
943 and the first pack from the other stream, respectively, may also have
944 been written before.
945 So the real data starts at SCR 36000+3*1200. */
946 pts = (pts + 36000 + 3600) & ((1LL << 33) - 1);
947 dts = (dts + 36000 + 3600) & ((1LL << 33) - 1);
948 }
837 949
838 #if 0 950 #if 0
839 update_scr(ctx,stream_index,pts); 951 update_scr(ctx,stream_index,pts);
840 952
841 printf("%d: pts=%0.3f dts=%0.3f scr=%0.3f\n", 953 printf("%d: pts=%0.3f dts=%0.3f scr=%0.3f\n",