Ticket #5443: h264-parse-frame_num.patch

File h264-parse-frame_num.patch, 5.3 KB (added by jppoet@…, 17 years ago)

Parse frame_num from H.264

  • libs/libmythtv/dtvrecorder.cpp

     
    532532                hasKeyFrame = true;
    533533                hasFrame = true;
    534534            }
    535 
    536             if (_h264_kf_seq.IsOnFrame())
     535            else if (_h264_kf_seq.IsOnFrame())
    537536                hasFrame = true;
    538537        }
    539538    } // for (; i < TSPacket::SIZE; i++)
  • libs/libmythtv/mpeg/h264utils.h

     
    3535
    3636#include <stdint.h>
    3737
     38extern "C" {
     39#include "golomb.h"
     40}
     41
    3842namespace H264
    3943{
    4044
     
    174178
    175179  private:
    176180    void KeyframePredicate(const uint8_t new_first_NAL_byte); /* throw() */
     181    void decode_Header(GetBitContext * gb);
     182    void decode_SPS(GetBitContext * gb);
    177183
    178184    bool    errored;
    179185    bool    state_changed;
     
    182188    int64_t  sync_stream_offset;
    183189
    184190    uint8_t first_NAL_byte;
     191    int     log2_max_frame_num;
     192    int     frame_num, prev_frame_num;
    185193
    186194    bool    saw_AU_delimiter;
    187195    bool    saw_first_VCL_NAL_unit;
    188196    bool    saw_sps;
     197    bool    separate_colour_plane_flag;
    189198
    190199    bool    did_evaluate_once;
    191200    bool    keyframe;
    192201    int64_t keyframe_sync_stream_offset;
     202
     203    GetBitContext gb;
    193204};
    194205
    195206} // namespace H264
  • libs/libmythtv/mpeg/h264utils.cpp

     
    4242extern "C" {
    4343// from libavcodec
    4444extern const uint8_t *ff_find_start_code(const uint8_t * p, const uint8_t *end, uint32_t * state);
     45#include "avcodec.h"
    4546}
    4647
    4748namespace H264
     
    6263
    6364    first_NAL_byte = H264::NALUnitType::UNKNOWN;
    6465
     66    log2_max_frame_num = -1;
     67    frame_num = 0;
     68    prev_frame_num = -1;
     69
    6570    saw_AU_delimiter = false;
    6671    saw_first_VCL_NAL_unit = false;
    6772    saw_sps = false;
     73    separate_colour_plane_flag = false;
    6874
    6975    did_evaluate_once = false;
    7076    keyframe = false;
     
    154160        if ((sync_accumulator & 0xffffff00) == 0x00000100)
    155161        {
    156162            uint8_t k = *(local_bytes-1);
     163            uint8_t NAL_type = k & 0x1f;
    157164            sync_stream_offset = stream_offset;
    158165            keyframe = false;
    159166
    160167            KeyframePredicate(k);
    161168            first_NAL_byte = k;
    162169
     170            if (NAL_type == NALUnitType::SPS ||
     171                NAL_type == NALUnitType::SLICE ||
     172                NAL_type == NALUnitType::SLICE_DPA) {
     173            /*
     174              bitstream buffer, must be FF_INPUT_BUFFER_PADDING_SIZE
     175              bytes larger then the actual read bits
     176            */
     177                if (local_bytes + 20 + FF_INPUT_BUFFER_PADDING_SIZE <
     178                    local_bytes_end) {
     179                    init_get_bits(&gb, local_bytes,
     180                                  8 * (local_bytes_end - local_bytes));
     181                   
     182                    if (NAL_type == NALUnitType::SPS)
     183                        decode_SPS(&gb);
     184                    else
     185                        decode_Header(&gb);
     186                }
     187               
     188            }
     189            else if (NAL_type == NALUnitType::SLICE_IDR)
     190                frame_num = 0;
     191
    163192            return local_bytes - bytes;
    164193        }
    165194    }
     
    175204    return saw_first_VCL_NAL_unit;
    176205}
    177206
     207void KeyframeSequencer::decode_Header(GetBitContext * gb)
     208{
     209    uint first_mb_in_slice;
     210    uint slice_type;
     211    uint pic_parameter_set_id;
     212   
     213    if (log2_max_frame_num < 1)
     214    {
     215        std::cerr
     216            << "KeyframeSequencer::decode_Header: SPS has not been parsed!\n";
     217        return;
     218    }
     219
     220    prev_frame_num = frame_num;
     221
     222    first_mb_in_slice = get_ue_golomb(gb);
     223    slice_type = get_ue_golomb(gb);
     224    pic_parameter_set_id = get_ue_golomb(gb);
     225   
     226    if (separate_colour_plane_flag)
     227        get_bits(gb, 2);  // colour_plane_id
     228   
     229    frame_num = get_bits(gb, log2_max_frame_num);
     230}
     231
     232/*
     233 * Just the parts we need -- libavcodec used for example
     234 */
     235void KeyframeSequencer::decode_SPS(GetBitContext * gb)
     236{
     237    int profile_idc, chroma_format_idc;
     238    int idx;
     239
     240    profile_idc = get_bits(gb, 8); // profile_idc
     241    get_bits1(gb);   // constraint_set0_flag
     242    get_bits1(gb);   // constraint_set1_flag
     243    get_bits1(gb);   // constraint_set2_flag
     244    get_bits1(gb);   // constraint_set3_flag
     245    get_bits(gb, 4); // reserved
     246    get_bits(gb, 8); // level_idc
     247    get_ue_golomb(gb);  // sps_id
     248
     249    if(profile_idc >= 100){ // high profile
     250        if((chroma_format_idc = get_ue_golomb(gb)) == 3) // chroma_format_idc
     251            separate_colour_plane_flag = (get_bits1(gb) == 1);
     252        get_ue_golomb(gb);  // bit_depth_luma_minus8
     253        get_ue_golomb(gb);  // bit_depth_chroma_minus8
     254        get_bits1(gb);      // qpprime_y_zero_transform_bypass_flag
     255
     256        if (get_bits1(gb))      // seq_scaling_matrix_present_flag
     257        {
     258            for (idx = 0; idx < ((chroma_format_idc != 3) ? 8 : 12); ++idx)
     259            {
     260                get_bits1(gb);  // scaling_list
     261            }
     262        }
     263    }
     264
     265    log2_max_frame_num = get_ue_golomb(gb) + 4;
     266}
     267
    178268} // namespace H264
     269