* commit '28096e0a806e57376541e6222d315619906e3c55': h264: wait for initial complete frame before outputing frames Conflicts: doc/APIchanges libavcodec/h264.c libavcodec/mpegvideo.h libavutil/frame.h libavutil/version.h
Unified · Split
| @@ -15,6 +15,9 @@ libavutil: 2012-10-22 · 14 unmodified lines | ||
| 15 | 15 | |
| 16 | 16 | API changes, most recent first: |
| 17 | 17 | |
| 18 | +2013-08-xx - xxxxxxx - lavu 52.17.0 - avframe.h | |
| 19 | + Add AVFrame.flags and AV_FRAME_FLAG_CORRUPT. | |
| 20 | + | |
| 18 | 21 | 2013-10-27 - xxxxxxx - lavc 55.39.100 - avcodec.h |
| 19 | 22 | Add CODEC_CAP_DELAY support to avcodec_decode_subtitle2. |
| 20 | 23 | |
| @@ -692,6 +692,7 @@ typedef struct RcOverride{ · 691 unmodified lines | ||
| 692 | 692 | #define CODEC_FLAG_UNALIGNED 0x0001 |
| 693 | 693 | #define CODEC_FLAG_QSCALE 0x0002 ///< Use fixed qscale. |
| 694 | 694 | #define CODEC_FLAG_4MV 0x0004 ///< 4 MV per MB allowed / advanced prediction for H.263. |
| 695 | +#define CODEC_FLAG_OUTPUT_CORRUPT 0x0008 ///< Output even those frames that might be corrupted | |
| 695 | 696 | #define CODEC_FLAG_QPEL 0x0010 ///< Use qpel MC. |
| 696 | 697 | #define CODEC_FLAG_GMC 0x0020 ///< Use GMC. |
| 697 | 698 | #define CODEC_FLAG_MV0 0x0040 ///< Always try a MB with MV=<0,0>. |
| @@ -361,10 +361,10 @@ static int ref_picture(H264Context *h, Picture *dst, Picture *src) · 360 unmodified lines | ||
| 361 | 361 | dst->field_picture = src->field_picture; |
| 362 | 362 | dst->needs_realloc = src->needs_realloc; |
| 363 | 363 | dst->reference = src->reference; |
| 364 | − dst->sync = src->sync; | |
| 365 | 364 | dst->crop = src->crop; |
| 366 | 365 | dst->crop_left = src->crop_left; |
| 367 | 366 | dst->crop_top = src->crop_top; |
| 367 | + dst->recovered = src->recovered; | |
| 368 | 368 | |
| 369 | 369 | return 0; |
| 370 | 370 | fail: |
| @@ -1902,7 +1902,7 @@ static int decode_update_thread_context(AVCodecContext *dst, · 1531 unmodified lines | ||
| 1902 | 1902 | copy_picture_range(h->delayed_pic, h1->delayed_pic, |
| 1903 | 1903 | MAX_DELAYED_PIC_COUNT + 2, h, h1); |
| 1904 | 1904 | |
| 1905 | − h->sync = h1->sync; | |
| 1905 | + h->frame_recovered = h1->frame_recovered; | |
| 1906 | 1906 | |
| 1907 | 1907 | if (context_reinitialized) |
| 1908 | 1908 | h264_set_parameter_from_sps(h); |
| @@ -1919,6 +1919,8 @@ static int decode_update_thread_context(AVCodecContext *dst, · 10 unmodified lines | ||
| 1919 | 1919 | h->prev_frame_num = h->frame_num; |
| 1920 | 1920 | h->outputed_poc = h->next_outputed_poc; |
| 1921 | 1921 | |
| 1922 | + h->recovery_frame = h1->recovery_frame; | |
| 1923 | + | |
| 1922 | 1924 | return err; |
| 1923 | 1925 | } |
| 1924 | 1926 | |
| @@ -1959,12 +1961,12 @@ static int h264_frame_start(H264Context *h) · 34 unmodified lines | ||
| 1959 | 1961 | * See decode_nal_units(). |
| 1960 | 1962 | */ |
| 1961 | 1963 | pic->f.key_frame = 0; |
| 1962 | − pic->sync = 0; | |
| 1963 | 1964 | pic->mmco_reset = 0; |
| 1965 | + pic->recovered = 0; | |
| 1964 | 1966 | |
| 1965 | 1967 | if ((ret = alloc_picture(h, pic)) < 0) |
| 1966 | 1968 | return ret; |
| 1967 | − if(!h->sync && !h->avctx->hwaccel && | |
| 1969 | + if(!h->frame_recovered && !h->avctx->hwaccel && | |
| 1968 | 1970 | !(h->avctx->codec->capabilities & CODEC_CAP_HWACCEL_VDPAU)) |
| 1969 | 1971 | avpriv_color_frame(&pic->f, c); |
| 1970 | 1972 | |
| @@ -2189,8 +2191,15 @@ static void decode_postinit(H264Context *h, int setup_finished) · 218 unmodified lines | ||
| 2189 | 2191 | av_log(h->avctx, AV_LOG_DEBUG, "no picture %s\n", out_of_order ? "ooo" : ""); |
| 2190 | 2192 | } |
| 2191 | 2193 | |
| 2192 | − if (h->next_output_pic && h->next_output_pic->sync) { | |
| 2193 | − h->sync |= 2; | |
| 2194 | + if (h->next_output_pic) { | |
| 2195 | + if (h->next_output_pic->recovered) { | |
| 2196 | + // We have reached an recovery point and all frames after it in | |
| 2197 | + // display order are "recovered". | |
| 2198 | + h->frame_recovered |= FRAME_RECOVERED_SEI; | |
| 2199 | + } | |
| 2200 | +#if 0 | |
| 2201 | + h->next_output_pic->recovered |= !!(h->frame_recovered & FRAME_RECOVERED_SEI); | |
| 2202 | +#endif | |
| 2194 | 2203 | } |
| 2195 | 2204 | |
| 2196 | 2205 | if (setup_finished && !h->avctx->hwaccel) |
| @@ -2781,8 +2790,8 @@ static void flush_change(H264Context *h) · 584 unmodified lines | ||
| 2781 | 2790 | memset(h->default_ref_list[0], 0, sizeof(h->default_ref_list[0])); |
| 2782 | 2791 | memset(h->default_ref_list[1], 0, sizeof(h->default_ref_list[1])); |
| 2783 | 2792 | ff_h264_reset_sei(h); |
| 2784 | − h->recovery_frame= -1; | |
| 2785 | − h->sync= 0; | |
| 2793 | + h->recovery_frame = -1; | |
| 2794 | + h->frame_recovered = 0; | |
| 2786 | 2795 | h->list_count = 0; |
| 2787 | 2796 | h->current_slice = 0; |
| 2788 | 2797 | h->mmco_reset = 1; |
| @@ -4844,8 +4853,8 @@ again: · 2055 unmodified lines | ||
| 4844 | 4853 | if ( h->sei_recovery_frame_cnt >= 0 |
| 4845 | 4854 | && ( h->recovery_frame<0 |
| 4846 | 4855 | || ((h->recovery_frame - h->frame_num) & ((1 << h->sps.log2_max_frame_num)-1)) > h->sei_recovery_frame_cnt)) { |
| 4847 | − h->recovery_frame = (h->frame_num + h->sei_recovery_frame_cnt) % | |
| 4848 | − (1 << h->sps.log2_max_frame_num); | |
| 4856 | + h->recovery_frame = (h->frame_num + h->sei_recovery_frame_cnt) & | |
| 4857 | + ((1 << h->sps.log2_max_frame_num) - 1); | |
| 4849 | 4858 | |
| 4850 | 4859 | if (!h->valid_recovery_point) |
| 4851 | 4860 | h->recovery_frame = h->frame_num; |
| @@ -4854,14 +4863,22 @@ again: · 2 unmodified lines | ||
| 4854 | 4863 | h->cur_pic_ptr->f.key_frame |= |
| 4855 | 4864 | (hx->nal_unit_type == NAL_IDR_SLICE); |
| 4856 | 4865 | |
| 4857 | − if (h->recovery_frame == h->frame_num) { | |
| 4858 | − h->cur_pic_ptr->sync |= 1; | |
| 4859 | − h->recovery_frame = -1; | |
| 4866 | + if (hx->nal_unit_type == NAL_IDR_SLICE || | |
| 4867 | + h->recovery_frame == h->frame_num) { | |
| 4868 | + h->recovery_frame = -1; | |
| 4869 | + h->cur_pic_ptr->recovered = 1; | |
| 4860 | 4870 | } |
| 4861 | − | |
| 4862 | − h->sync |= !!h->cur_pic_ptr->f.key_frame; | |
| 4863 | − h->sync |= 3*!!(avctx->flags2 & CODEC_FLAG2_SHOW_ALL); | |
| 4864 | − h->cur_pic_ptr->sync |= h->sync; | |
| 4871 | + // If we have an IDR, all frames after it in decoded order are | |
| 4872 | + // "recovered". | |
| 4873 | + if (hx->nal_unit_type == NAL_IDR_SLICE) | |
| 4874 | + h->frame_recovered |= FRAME_RECOVERED_IDR; | |
| 4875 | + h->frame_recovered |= 3*!!(avctx->flags2 & CODEC_FLAG2_SHOW_ALL); | |
| 4876 | + h->frame_recovered |= 3*!!(avctx->flags & CODEC_FLAG_OUTPUT_CORRUPT); | |
| 4877 | +#if 1 | |
| 4878 | + h->cur_pic_ptr->recovered |= h->frame_recovered; | |
| 4879 | +#else | |
| 4880 | + h->cur_pic_ptr->recovered |= !!(h->frame_recovered & FRAME_RECOVERED_IDR); | |
| 4881 | +#endif | |
| 4865 | 4882 | |
| 4866 | 4883 | if (h->current_slice == 1) { |
| 4867 | 4884 | if (!(avctx->flags2 & CODEC_FLAG2_CHUNKS)) |
| @@ -5135,7 +5152,15 @@ not_extra: · 267 unmodified lines | ||
| 5135 | 5152 | |
| 5136 | 5153 | /* Wait for second field. */ |
| 5137 | 5154 | *got_frame = 0; |
| 5138 | − if (h->next_output_pic && (h->next_output_pic->sync || h->sync>1)) { | |
| 5155 | +#if 1 | |
| 5156 | + if (h->next_output_pic && (h->next_output_pic->recovered || h->frame_recovered>1)) { | |
| 5157 | +#else | |
| 5158 | + if (h->next_output_pic && ( | |
| 5159 | + h->next_output_pic->recovered)) { | |
| 5160 | +#endif | |
| 5161 | + if (!h->next_output_pic->recovered) | |
| 5162 | + h->next_output_pic->f.flags |= AV_FRAME_FLAG_CORRUPT; | |
| 5163 | + | |
| 5139 | 5164 | ret = output_frame(h, pict, h->next_output_pic); |
| 5140 | 5165 | if (ret < 0) |
| 5141 | 5166 | return ret; |
| @@ -641,6 +641,14 @@ typedef struct H264Context { · 640 unmodified lines | ||
| 641 | 641 | * frames. |
| 642 | 642 | */ |
| 643 | 643 | int sei_recovery_frame_cnt; |
| 644 | + | |
| 645 | + /** | |
| 646 | + * Are the SEI recovery points looking valid. | |
| 647 | + */ | |
| 648 | + int valid_recovery_point; | |
| 649 | + | |
| 650 | + FPA sei_fpa; | |
| 651 | + | |
| 644 | 652 | /** |
| 645 | 653 | * recovery_frame is the frame_num at which the next frame should |
| 646 | 654 | * be fully constructed. |
| @@ -649,12 +657,18 @@ typedef struct H264Context { · 2 unmodified lines | ||
| 649 | 657 | */ |
| 650 | 658 | int recovery_frame; |
| 651 | 659 | |
| 652 | − /** | |
| 653 | − * Are the SEI recovery points looking valid. | |
| 654 | − */ | |
| 655 | − int valid_recovery_point; | |
| 660 | +/** | |
| 661 | + * We have seen an IDR, so all the following frames in coded order are correctly | |
| 662 | + * decodable. | |
| 663 | + */ | |
| 664 | +#define FRAME_RECOVERED_IDR (1 << 0) | |
| 665 | +/** | |
| 666 | + * Sufficient number of frames have been decoded since a SEI recovery point, | |
| 667 | + * so all the following frames in presentation order are correct. | |
| 668 | + */ | |
| 669 | +#define FRAME_RECOVERED_SEI (1 << 1) | |
| 656 | 670 | |
| 657 | − FPA sei_fpa; | |
| 671 | + int frame_recovered; ///< Initial frame has been completely recovered | |
| 658 | 672 | |
| 659 | 673 | int luma_weight_flag[2]; ///< 7.4.3.2 luma_weight_lX_flag |
| 660 | 674 | int chroma_weight_flag[2]; ///< 7.4.3.2 chroma_weight_lX_flag |
| @@ -668,8 +682,6 @@ typedef struct H264Context { · 7 unmodified lines | ||
| 668 | 682 | |
| 669 | 683 | int16_t slice_row[MAX_SLICES]; ///< to detect when MAX_SLICES is too low |
| 670 | 684 | |
| 671 | − int sync; ///< did we had a keyframe or recovery point | |
| 672 | − | |
| 673 | 685 | uint8_t parse_history[4]; |
| 674 | 686 | int parse_history_count; |
| 675 | 687 | int parse_last_mb; |
| @@ -733,9 +733,9 @@ int ff_h264_execute_ref_pic_marking(H264Context *h, MMCO *mmco, int mmco_count) · 732 unmodified lines | ||
| 733 | 733 | print_long_term(h); |
| 734 | 734 | |
| 735 | 735 | if(err >= 0 && h->long_ref_count==0 && h->short_ref_count<=2 && h->pps.ref_count[0]<=2 + (h->picture_structure != PICT_FRAME) && h->cur_pic_ptr->f.pict_type == AV_PICTURE_TYPE_I){ |
| 736 | − h->cur_pic_ptr->sync |= 1; | |
| 736 | + h->cur_pic_ptr->recovered |= 1; | |
| 737 | 737 | if(!h->avctx->has_b_frames) |
| 738 | − h->sync = 2; | |
| 738 | + h->frame_recovered = 2; | |
| 739 | 739 | } |
| 740 | 740 | |
| 741 | 741 | return (h->avctx->err_recognition & AV_EF_EXPLODE) ? err : 0; |
| @@ -167,7 +167,6 @@ typedef struct Picture{ · 166 unmodified lines | ||
| 167 | 167 | int ref_count[2][2]; ///< number of entries in ref_poc (FIXME need per slice) |
| 168 | 168 | int mbaff; ///< h264 1 -> MBAFF frame 0-> not MBAFF |
| 169 | 169 | int field_picture; ///< whether or not the picture was encoded in separate fields |
| 170 | − int sync; ///< has been decoded after a keyframe | |
| 171 | 170 | |
| 172 | 171 | int mb_var_sum; ///< sum of MB variance for current frame |
| 173 | 172 | int mc_mb_var_sum; ///< motion compensated MB variance for current frame |
| @@ -177,6 +176,7 @@ typedef struct Picture{ · 3 unmodified lines | ||
| 177 | 176 | |
| 178 | 177 | int reference; |
| 179 | 178 | int shared; |
| 179 | + int recovered; ///< Picture at IDR or recovery point + recovery count | |
| 180 | 180 | |
| 181 | 181 | int crop; |
| 182 | 182 | int crop_left; |
| @@ -70,6 +70,7 @@ static const AVOption avcodec_options[] = { · 69 unmodified lines | ||
| 70 | 70 | {"aic", "H.263 advanced intra coding / MPEG-4 AC prediction", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG_AC_PRED }, INT_MIN, INT_MAX, V|E, "flags"}, |
| 71 | 71 | {"ilme", "interlaced motion estimation", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG_INTERLACED_ME }, INT_MIN, INT_MAX, V|E, "flags"}, |
| 72 | 72 | {"cgop", "closed GOP", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG_CLOSED_GOP }, INT_MIN, INT_MAX, V|E, "flags"}, |
| 73 | +{"output_corrupt", "Output even potentially corrupted frames", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG_OUTPUT_CORRUPT }, INT_MIN, INT_MAX, V|D, "flags"}, | |
| 73 | 74 | {"fast", "allow non-spec-compliant speedup tricks", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG2_FAST }, INT_MIN, INT_MAX, V|E, "flags2"}, |
| 74 | 75 | {"noout", "skip bitstream encoding", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG2_NO_OUTPUT }, INT_MIN, INT_MAX, V|E, "flags2"}, |
| 75 | 76 | {"ignorecrop", "ignore cropping information from sps", 0, AV_OPT_TYPE_CONST, {.i64 = CODEC_FLAG2_IGNORE_CROP }, INT_MIN, INT_MAX, V|D, "flags2"}, |
| @@ -386,6 +386,16 @@ typedef struct AVFrame { · 385 unmodified lines | ||
| 386 | 386 | AVFrameSideData **side_data; |
| 387 | 387 | int nb_side_data; |
| 388 | 388 | |
| 389 | +/** | |
| 390 | + * The frame data may be corrupted, e.g. due to decoding errors. | |
| 391 | + */ | |
| 392 | +#define AV_FRAME_FLAG_CORRUPT (1 << 0) | |
| 393 | + | |
| 394 | + /** | |
| 395 | + * Frame flags, a combination of AV_FRAME_FLAG_* | |
| 396 | + */ | |
| 397 | + int flags; | |
| 398 | + | |
| 389 | 399 | /** |
| 390 | 400 | * frame timestamp estimated using various heuristics, in stream time base |
| 391 | 401 | * Code outside libavcodec should access this field using: |
| @@ -75,7 +75,7 @@ · 74 unmodified lines | ||
| 75 | 75 | */ |
| 76 | 76 | |
| 77 | 77 | #define LIBAVUTIL_VERSION_MAJOR 52 |
| 78 | −#define LIBAVUTIL_VERSION_MINOR 48 | |
| 78 | +#define LIBAVUTIL_VERSION_MINOR 49 | |
| 79 | 79 | #define LIBAVUTIL_VERSION_MICRO 100 |
| 80 | 80 | |
| 81 | 81 | #define LIBAVUTIL_VERSION_INT AV_VERSION_INT(LIBAVUTIL_VERSION_MAJOR, \ |