Ticket #4515: 4515-bradley-v1.patch

File 4515-bradley-v1.patch, 5.6 KB (added by danielk, 16 years ago)

Reviewed patch

  • libs/libmythtv/dvbrecorder.cpp

     
    491491        _buffer_packets = !FindMPEG2Keyframes(&tspacket);
    492492    }
    493493
    494     return ProcessTSPacket(tspacket);
     494    return ProcessAVTSPacket(tspacket);
    495495}
    496496
    497497bool DVBRecorder::ProcessAudioTSPacket(const TSPacket &tspacket)
    498498{
    499499    _buffer_packets = !FindAudioKeyframes(&tspacket);
    500     return ProcessTSPacket(tspacket);
     500    return ProcessAVTSPacket(tspacket);
    501501}
    502502
    503 bool DVBRecorder::ProcessTSPacket(const TSPacket &tspacket)
     503/// Common code for processing both audio and video packets
     504bool DVBRecorder::ProcessAVTSPacket(const TSPacket &tspacket)
    504505{
    505506    const uint pid = tspacket.PID();
    506507
     
    513514    }
    514515
    515516    // Sync recording start to first keyframe
     517    // (Delay's until first GOP to avoid decoder crash on res change)
    516518    if (_wait_for_keyframe_option && _first_keyframe < 0)
    517519        return true;
    518520
     
    529531        _pid_status[pid] |= kPayloadStartSeen;
    530532    }
    531533
     534    return ProcessTSPacketCommon(tspacket);
     535}
     536
     537bool DVBRecorder::ProcessTSPacket(const TSPacket &tspacket)
     538{
     539    _buffer_packets = !FindOtherKeyframes(&tspacket);
     540    return ProcessTSPacketCommon(tspacket);
     541}
     542
     543bool DVBRecorder::ProcessTSPacketCommon(const TSPacket &tspacket)
     544{
     545    // Care must be taken to make sure that the packet actually gets written
     546    // as the decision to actually write it has already been made
     547    const uint pid = tspacket.PID();
     548
     549    // Check continuity counter
     550    if ((pid != 0x1fff) && !CheckCC(pid, tspacket.ContinuityCounter()))
     551    {
     552        VERBOSE(VB_RECORD, LOC +
     553                QString("PID 0x%1 discontinuity detected").arg(pid,0,16));
     554        _continuity_error_count++;
     555    }
     556
    532557    BufferedWrite(tspacket);
    533558
    534559    return true;
    535560}
     561
     562void DVBRecorder::BufferedWrite(const TSPacket &tspacket)
     563{
     564    // Care must be taken to make sure that the packet actually gets written
     565    // as the decision to actually write it has already been made
     566
     567    // Do we have to buffer the packet for exact keyframe detection?
     568    if (_buffer_packets)
     569    {
     570        int idx = _payload_buffer.size();
     571        _payload_buffer.resize(idx + TSPacket::SIZE);
     572        memcpy(&_payload_buffer[idx], tspacket.data(), TSPacket::SIZE);
     573        return;
     574    }
     575
     576    // We are free to write the packet, but if we have buffered packet[s]
     577    // we have to write them first...
     578    if (!_payload_buffer.empty())
     579    {
     580        if (ringBuffer)
     581            ringBuffer->Write(&_payload_buffer[0], _payload_buffer.size());
     582        _payload_buffer.clear();
     583    }
     584
     585    if (ringBuffer)
     586        ringBuffer->Write(tspacket.data(), TSPacket::SIZE);
     587}
  • libs/libmythtv/dvbrecorder.h

     
    6464    bool IsOpen(void) const { return _stream_fd >= 0; }
    6565    void Close(void);
    6666
     67    // Methods to handle MHEG, when there are no A/V streams
     68    bool ProcessAVTSPacket(const TSPacket &tspacket);
     69    bool ProcessTSPacketCommon(const TSPacket &tspacket);
     70    void BufferedWrite(const TSPacket &tspacket);
     71
     72    // MPEG Stream Listener
    6773    void HandlePAT(const ProgramAssociationTable*);
    6874    void HandleCAT(const ConditionalAccessTable*) {}
    6975    void HandlePMT(uint pid, const ProgramMapTable*);
  • libs/libmythtv/dtvrecorder.h

     
    6565    bool FindH264Keyframes(const TSPacket* tspacket);
    6666    void HandleH264Keyframe(void);
    6767
     68    // MHEG no A/V support
     69    bool FindOtherKeyframes(const TSPacket *tspacket);
     70
    6871    // file handle for stream
    6972    int _stream_fd;
    7073
     
    7780    unsigned long long _last_gop_seen;
    7881    unsigned long long _last_seq_seen;
    7982    unsigned long long _last_keyframe_seen;
     83    bool               _has_written_mheg_keyframe;
    8084
    8185    // H.264 support
    8286    bool _pes_synced;
  • libs/libmythtv/dtvrecorder.cpp

     
    3838    // used for scanning pes headers for keyframes
    3939    _start_code(0xffffffff),        _first_keyframe(-1),
    4040    _last_gop_seen(0),              _last_seq_seen(0),
    41     _last_keyframe_seen(0),
     41    _last_keyframe_seen(0),         _has_written_mheg_keyframe(false),
    4242    // H.264 support
    4343    _pes_synced(false),
    4444    _seen_sps(false),
     
    146146
    147147    //_start_code
    148148    _first_keyframe             =-1;
     149    _has_written_mheg_keyframe  = false;
    149150    _last_keyframe_seen         = 0;
    150151    _last_gop_seen              = 0;
    151152    _last_seq_seen              = 0;
     
    344345    return hasKeyFrame;
    345346}
    346347
     348/** \brief This creates a fake keyframe for MHEG only streams.
     349 *
     350 *   This is for MHEG streams which contain no audio or video streams
     351 *   We write just one key-frame at the start so that the frontend
     352 *   can jump to the start of the stream.
     353 */
     354bool DTVRecorder::FindOtherKeyframes(const TSPacket *tspacket)
     355{
     356    if (_has_written_mheg_keyframe)
     357        return true;
     358
     359    _frames_seen_count++;
     360    _frames_written_count++;
     361    _last_keyframe_seen = _frames_seen_count;
     362    HandleKeyframe();
     363
     364    _has_written_mheg_keyframe = true;
     365
     366    return true;
     367}
     368
    347369// documented in recorderbase.h
    348370void DTVRecorder::SetNextRecording(const ProgramInfo *progInf, RingBuffer *rb)
    349371{