Ticket #12010: mythtv-master-seektable.patch

File mythtv-master-seektable.patch, 9.5 KB (added by J.Pilk@…, 10 years ago)
  • mythtv/libs/libmythtv/avformatdecoder.cpp

    diff --git a/mythtv/libs/libmythtv/avformatdecoder.cpp b/mythtv/libs/libmythtv/avformatdecoder.cpp
    index 3a42b40..f61a8fa 100644
    a b AvFormatDecoder::AvFormatDecoder(MythPlayer *parent, 
    427427
    428428    cc608_build_parity_table(cc608_parity_table);
    429429
    430     SetIdrOnlyKeyframes(true);
     430    SetIdrOnlyKeyframes(false);
    431431
    432432    LOG(VB_PLAYBACK, LOG_DEBUG, LOC + QString("PlayerFlags: 0x%1")
    433433        .arg(playerFlags, 0, 16));
    int AvFormatDecoder::H264PreProcessPkt(AVStream *stream, AVPacket *pkt) 
    33543354                if (m_h264_parser->onFrameStart())
    33553355                    ++num_frames;
    33563356
    3357                 if (!m_h264_parser->onKeyFrameStart())
     3357                if (!m_h264_parser->onKeyFrameStart() || !m_h264_parser->seen_SPS())
    33583358                    continue;
    33593359            }
    33603360            else
  • mythtv/libs/libmythtv/mpeg/H264Parser.cpp

    diff --git a/mythtv/libs/libmythtv/mpeg/H264Parser.cpp b/mythtv/libs/libmythtv/mpeg/H264Parser.cpp
    index d0eebde..db79855 100644
    a b void H264Parser::Reset(void) 
    115115    slice_type = SLICE_UNDEF;
    116116    prev_pic_parameter_set_id = pic_parameter_set_id = -1;
    117117    prev_field_pic_flag = field_pic_flag = -1;
    118     prev_bottom_field_flag = bottom_field_flag = -1;
    119     prev_nal_ref_idc = nal_ref_idc = 111;  //  != [0|1|2|3]
    120     prev_pic_order_cnt_type = pic_order_cnt_type =
     118    prev_bottom_field_flag = bottom_field_flag = 0;
     119    prev_nal_ref_idc = nal_ref_idc = 0;
     120    prev_pic_order_cnt_type = pic_order_cnt_type = 0;
    121121    prev_pic_order_cnt_lsb = pic_order_cnt_lsb = 0;
    122122    prev_delta_pic_order_cnt_bottom = delta_pic_order_cnt_bottom = 0;
    123123    prev_delta_pic_order_cnt[0] = delta_pic_order_cnt[0] = 0;
    void H264Parser::Reset(void) 
    125125    prev_nal_unit_type = nal_unit_type = UNKNOWN;
    126126
    127127    // The value of idr_pic_id shall be in the range of 0 to 65535, inclusive.
    128     prev_idr_pic_id = idr_pic_id = 65536;
     128    prev_idr_pic_id = idr_pic_id = -1;
    129129
    130130    log2_max_frame_num = log2_max_pic_order_cnt_lsb = 0;
    131131    seq_parameter_set_id = 0;
    void H264Parser::Reset(void) 
    146146    frame_crop_top_offset = frame_crop_bottom_offset = 0;
    147147    aspect_ratio_idc = 0;
    148148    sar_width = sar_height = 0;
    149     unitsInTick = 0;
     149    prev_unitsInTick = 1; unitsInTick = 0;
    150150    timeScale = 0;
    151151    fixedRate = 0;
     152    stream_changed = false;
    152153
    153154    pkt_offset = AU_offset = frame_start_offset = keyframe_start_offset = 0;
    154155    on_frame = on_key_frame = false;
    bool H264Parser::new_AU(void) 
    260261
    261262    */
    262263
    263     bool       result = false;
     264    bool result = false;
    264265
    265266    if (prev_frame_num != -1)
    266267    {
    bool H264Parser::new_AU(void) 
    273274            result = true;
    274275        else if (field_pic_flag != prev_field_pic_flag)
    275276            result = true;
    276         else if ((bottom_field_flag != -1 && prev_bottom_field_flag != -1) &&
     277        else if ((bottom_field_flag != 0 && prev_bottom_field_flag != 0) &&
    277278                 bottom_field_flag != prev_bottom_field_flag)
    278279            result = true;
    279280        else if ((nal_ref_idc == 0 || prev_nal_ref_idc == 0) &&
    bool H264Parser::new_AU(void) 
    297298                 idr_pic_id != prev_idr_pic_id)
    298299            result = true;
    299300    }
     301    result |= au_contains_keyframe_message;
    300302
    301303    prev_frame_num = frame_num;
    302304    prev_pic_parameter_set_id = pic_parameter_set_id;
    bool H264Parser::decode_Header(GetBitContext *gb) 
    639641      that precedes the current slice in decoding order and has the
    640642      same value of colour_plane_id.
    641643     */
    642     /* uint first_mb_in_slice = */ get_ue_golomb(gb);
     644    /* uint first_mb_in_slice = */ get_ue_golomb_long(gb);
    643645
    644646    /*
    645647      slice_type specifies the coding type of the slice according to
    bool H264Parser::decode_Header(GetBitContext *gb) 
    718720      such IDR access unit shall differ from the idr_pic_id in the
    719721      second such IDR access unit. The value of idr_pic_id shall be in
    720722      the range of 0 to 65535, inclusive.
     723
     724      7.4.3
     725      If the current picture is an IDR picture, PrevRefFrameNum is set equal to 0
     726      but 7.4.1.2.4 says prev_frame_num raw header value is used for AU detection
     727      prev_frame_num = 0;  // but only for decoding process
    721728     */
     729
    722730    if (nal_unit_type == SLICE_IDR)
    723731    {
    724732        idr_pic_id = get_ue_golomb(gb);
    725733        is_keyframe = true;
    726734    }
    727     else
     735    else   // option all I frames as keyframes.
    728736        is_keyframe = (I_is_keyframe && isKeySlice(slice_type));
    729737
    730738    /*
    void H264Parser::vui_parameters(GetBitContext * gb) 
    12611269            sar_height = get_bits(gb, 16);
    12621270            break;
    12631271        }
     1272        if (aspect_ratio_idc != prev_aspect_ratio_idc)
     1273        {
     1274            stream_changed = true;
     1275            prev_aspect_ratio_idc = aspect_ratio_idc;
     1276        }
    12641277    }
    12651278    else
    12661279        sar_width = sar_height = 0;
    void H264Parser::vui_parameters(GetBitContext * gb) 
    12911304        unitsInTick = get_bits_long(gb, 32); //num_units_in_tick
    12921305        timeScale = get_bits_long(gb, 32);   //time_scale
    12931306        fixedRate = get_bits1(gb);
     1307        if (unitsInTick != prev_unitsInTick)
     1308        {
     1309            stream_changed = true;
     1310            prev_unitsInTick = unitsInTick;
     1311        }
    12941312    }
    12951313}
    12961314
  • mythtv/libs/libmythtv/mpeg/H264Parser.h

    diff --git a/mythtv/libs/libmythtv/mpeg/H264Parser.h b/mythtv/libs/libmythtv/mpeg/H264Parser.h
    index ad78946..5874c45 100644
    a b class H264Parser { 
    9494      slice_type – 5.
    9595    */
    9696    enum SLICE_type {
    97         SLICE_P = 0,
    98         SLICE_B = 1,
    99         SLICE_I = 2,
    100         SLICE_SP = 3,
    101         SLICE_SI = 4,
    102         SLICE_P_a = 5,
    103         SLICE_B_a = 6,
    104         SLICE_I_a = 7,
    105         SLICE_SP_a = 8,
    106         SLICE_SI_a = 9,
     97        SLICE_P     = 0,
     98        SLICE_B     = 1,
     99        SLICE_I     = 2,
     100        SLICE_SP    = 3,
     101        SLICE_SI    = 4,
     102        SLICE_P_a   = 5,
     103        SLICE_B_a   = 6,
     104        SLICE_I_a   = 7,
     105        SLICE_SP_a  = 8,
     106        SLICE_SI_a  = 9,
    107107        SLICE_UNDEF = 10
    108108    };
    109109
    110110    enum frame_type {
    111         FRAME = 'F',
    112         FIELD_TOP = 'T',
     111        FRAME        = 'F',
     112        FIELD_TOP    = 'T',
    113113        FIELD_BOTTOM = 'B'
    114114    };
    115115
    class H264Parser { 
    214214    bool       au_contains_keyframe_message;
    215215    bool       is_keyframe;
    216216    bool       I_is_keyframe;
     217    bool       stream_changed;
    217218
    218219    uint32_t   sync_accumulator;
    219220    uint8_t   *rbsp_buffer;
    class H264Parser { 
    253254    uint       frame_crop_right_offset;
    254255    uint       frame_crop_top_offset;
    255256    uint       frame_crop_bottom_offset;
    256     uint8_t    aspect_ratio_idc;
     257    uint8_t    aspect_ratio_idc, prev_aspect_ratio_idc;
    257258    uint       sar_width, sar_height;
    258     uint32_t   unitsInTick, timeScale;
     259    uint32_t   unitsInTick, prev_unitsInTick, timeScale;
    259260    bool       fixedRate;
    260261
    261262    uint64_t   pkt_offset, AU_offset, frame_start_offset, keyframe_start_offset;
  • mythtv/libs/libmythtv/mythcommflagplayer.cpp

    diff --git a/mythtv/libs/libmythtv/mythcommflagplayer.cpp b/mythtv/libs/libmythtv/mythcommflagplayer.cpp
    index b521e01..361c051 100644
    a b bool MythCommFlagPlayer::RebuildSeekTable( 
    106106        cout << "\r                         \r" << flush;
    107107
    108108    int prevperc = -1;
    109     bool usingIframes = false;
     109    bool usingIframes = true;
    110110    while (GetEof() == kEofStateNone)
    111111    {
    112112        if (inuse_timer.elapsed() > 2534)
    bool MythCommFlagPlayer::RebuildSeekTable( 
    182182        if (DecoderGetFrame(kDecodeNothing,true))
    183183            myFramesPlayed = decoder->GetFramesRead();
    184184
    185         // H.264 recordings from an HD-PVR contain IDR keyframes,
    186         // which are the only valid cut points for lossless cuts.
    187         // However, DVB-S h.264 recordings may lack IDR keyframes, in
    188         // which case we need to allow non-IDR I-frames.  If we get
    189         // far enough into the rebuild without having created any
    190         // seektable entries, we can assume it is because of the IDR
    191         // keyframe setting, and so we rewind and allow h.264 non-IDR
    192         // I-frames to be treated as keyframes.
     185        // H.264 recordings from an HD-PVR contain IDR keyframes
     186        // and are the only valid cut points for lossless cuts.
     187        // DVB-S(2)/T(2) H.264 recordings typically do not use
     188        // IDR keyframes & do not use I frames as keyframes.
     189        // If we get far enough into the rebuild without having created any
     190        // seektable entries, we assume it is because of the IDR
     191        // keyframe setting, and so we rewind and allow H.264 IDR
     192        // (HD-PVR type) detection.
    193193        uint64_t frames = decoder->GetFramesRead();
    194         if (!usingIframes &&
    195             (GetEof() != kEofStateNone || (frames > 1000 && frames < 1100)) &&
     194        if (usingIframes &&
     195            (GetEof() != kEofStateNone || (frames > 1000 && frames < 1100)) &&
    196196            !decoder->HasPositionMap())
    197197        {
    198             cout << "No I-frames found, rewinding..." << endl;
     198            cout << "No non-IDR keyframes found, rewinding..." << endl;
    199199            decoder->DoRewind(0);
    200200            decoder->Reset(true, true, true);
    201201            pmap_first = pmap_last = myFramesPlayed = 0;
    202             decoder->SetIdrOnlyKeyframes(false);
    203             usingIframes = true;
     202            decoder->SetIdrOnlyKeyframes(true);
     203            usingIframes = false;
    204204        }
    205205    }
    206206