Ticket #2434: 2434-v2.patch

File 2434-v2.patch, 7.2 KB (added by Matt Holgate <matt-bulk-mythtv@…>, 13 years ago)

Modfied version of danielk's patch with additional lock

  • libs/libmythtv/NuppelVideoPlayer.cpp

     
    398398    PauseDecoder();
    399399
    400400    //cout << "stopping other threads" << endl;
     401    internalPauseLock.lock();
    401402    PauseVideo(waitvideo);
     403    internalPauseLock.unlock();
     404
    402405    if (audioOutput)
    403406    {
    404407        audio_paused = true;
     
    425428            QString("Play(%1, normal %2, unpause audio %3)")
    426429            .arg(speed,5,'f',1).arg(normal).arg(unpauseaudio));
    427430
     431    internalPauseLock.lock();
    428432    UnpauseVideo();
     433    internalPauseLock.unlock();
     434
    429435    if (audioOutput && unpauseaudio)
    430436        audio_paused = false;
    431437    if (ringBuffer)
     
    443449    return (actuallypaused &&
    444450            (ringBuffer == NULL || ringBuffer->isPaused()) &&
    445451            (audioOutput == NULL || audioOutput->GetPause()) &&
    446             GetVideoPause());
     452            IsVideoActuallyPaused());
    447453}
    448454
    449455void NuppelVideoPlayer::PauseVideo(bool wait)
    450456{
     457    QMutexLocker locker(&pauseUnpauseLock);
    451458    video_actually_paused = false;
    452459    pausevideo = true;
    453460
    454     if (wait && !video_actually_paused)
    455     {
    456         while (!videoThreadPaused.wait(1000))
     461    for (uint i = 0; wait && !video_actually_paused; i++)
    457462        {
    458             if (eof)
    459                 return;
     463        videoThreadPaused.wait(&pauseUnpauseLock, 250);
     464
     465        if (video_actually_paused || eof)
     466            break;
     467
     468        if ((i % 10) == 9)
    460469            VERBOSE(VB_IMPORTANT, "Waited too long for video out to pause");
    461470        }
    462     }
    463471}
    464472
    465 void NuppelVideoPlayer::UnpauseVideo(void)
     473void NuppelVideoPlayer::UnpauseVideo(bool wait)
    466474{
     475    QMutexLocker locker(&pauseUnpauseLock);
    467476    pausevideo = false;
     477
     478    for (uint i = 0; wait && video_actually_paused; i++)
     479    {
     480        videoThreadUnpaused.wait(&pauseUnpauseLock, 250);
     481
     482        if (!video_actually_paused || eof)
     483            break;
     484
     485        if ((i % 10) == 9)
     486            VERBOSE(VB_IMPORTANT, "Waited too long for video out to unpause");
     487    }
     488}
     489
     490void NuppelVideoPlayer::SetVideoActuallyPaused(bool val)
     491{
     492    QMutexLocker locker(&pauseUnpauseLock);
     493    video_actually_paused = val;
     494
     495    if (val)
     496        videoThreadPaused.wakeAll();
     497    else
     498        videoThreadUnpaused.wakeAll();
    468499}
    469500
    470501void NuppelVideoPlayer::SetPrebuffering(bool prebuffer)
     
    22912322        resetvideo = false;
    22922323    }
    22932324
    2294     video_actually_paused = true;
    2295     videoThreadPaused.wakeAll();
     2325    SetVideoActuallyPaused(true);
    22962326
    22972327    if (videoOutput->IsErrored())
    22982328    {
     
    23912421
    23922422void NuppelVideoPlayer::DisplayNormalFrame(void)
    23932423{
    2394     video_actually_paused = false;
     2424    SetVideoActuallyPaused(false);
    23952425    resetvideo = false;
    23962426
    23972427    if (!ringBuffer->InDVDMenuOrStillFrame())
     
    26742704        }
    26752705
    26762706        resetvideo = false;
    2677         video_actually_paused = pausevideo;
     2707        SetVideoActuallyPaused(pausevideo);
    26782708
    26792709        if (pausevideo)
    26802710        {
    2681             videoThreadPaused.wakeAll();
    26822711            videofiltersLock.lock();
    26832712            videoOutput->ProcessFrame(NULL, osd, videoFilters, pipplayer);
    26842713            videofiltersLock.unlock();
     
    32973326
    32983327            if (rewindtime >= 1)
    32993328            {
    3300                 PauseVideo();
     3329                QMutexLocker locker(&internalPauseLock);
    33013330
     3331                PauseVideo(true);
    33023332                DoRewind();
    3303 
    3304                 UnpauseVideo();
    3305                 while (GetVideoPause())
    3306                     usleep(1000);
     3333                UnpauseVideo(true);
    33073334            }
    33083335            rewindtime = 0;
    33093336        }
     
    33143341
    33153342            if (fftime >= 5)
    33163343            {
    3317                 PauseVideo();
     3344                QMutexLocker locker(&internalPauseLock);
     3345
     3346                PauseVideo(true);
    33183347
    33193348                if (fftime >= 5)
    33203349                    DoFastForward();
     
    33223351                if (eof)
    33233352                    continue;
    33243353
    3325                 UnpauseVideo();
    3326                 while (GetVideoPause())
    3327                     usleep(1000);
     3354                UnpauseVideo(true);
    33283355            }
    33293356
    33303357            fftime = 0;
     
    33323359
    33333360        if (need_change_dvd_track)
    33343361        {
    3335             PauseVideo();
     3362            QMutexLocker locker(&internalPauseLock);
    33363363
     3364            PauseVideo(true);
    33373365            DoChangeDVDTrack();
    3338 
    3339             UnpauseVideo();
    3340             while (GetVideoPause())
    3341                 usleep(1000);
     3366            UnpauseVideo(true);
    33423367
    33433368            need_change_dvd_track = 0;
    33443369        }
    33453370
    33463371        if (skipcommercials != 0 && ffrew_skip == 1)
    33473372        {
    3348             PauseVideo();
     3373            QMutexLocker locker(&internalPauseLock);
    33493374
     3375            PauseVideo(true);
    33503376            DoSkipCommercials(skipcommercials);
    3351             UnpauseVideo();
    3352             while (GetVideoPause())
    3353                 usleep(1000);
     3377            UnpauseVideo(true);
    33543378
    33553379            skipcommercials = 0;
    33563380            continue;
     
    33773401                eof = true;
    33783402            else
    33793403            {
    3380                 PauseVideo();
     3404                QMutexLocker locker(&internalPauseLock);
     3405
     3406                PauseVideo(true);
    33813407                JumpToFrame(deleteIter.key());
    3382                 UnpauseVideo();
    3383                 while (GetVideoPause())
    3384                     usleep(1000);
     3408                UnpauseVideo(true);
    33853409            }
    33863410        }
    33873411    }
     
    55345558                        .arg(commBreakIter.key() -
    55355559                        (int)(commrewindamount * video_frame_rate)));
    55365560
    5537                     PauseVideo();
     5561                    {
     5562                        QMutexLocker locker(&internalPauseLock);
     5563
     5564                        PauseVideo(true);
    55385565                    JumpToFrame(commBreakIter.key() -
    55395566                        (int)(commrewindamount * video_frame_rate));
    5540                     UnpauseVideo();
    5541                     while (GetVideoPause())
    5542                         usleep(1000);
     5567                        UnpauseVideo(true);
     5568                    }
    55435569
    55445570                    GetFrame(1, true);
    55455571                }
  • libs/libmythtv/NuppelVideoPlayer.h

     
    409409
    410410    // Private pausing stuff
    411411    void PauseVideo(bool wait = true);
    412     void UnpauseVideo(void);
    413     bool GetVideoPause(void) const { return video_actually_paused; }
     412    void UnpauseVideo(bool wait = false);
     413    bool IsVideoActuallyPaused(void) const { return video_actually_paused; }
     414    void SetVideoActuallyPaused(bool val);
    414415
    415416    // Private decoder stuff
    416417    void  SetDecoder(DecoderBase *dec);
     
    513514    // State
    514515    QWaitCondition decoderThreadPaused;
    515516    QWaitCondition videoThreadPaused;
     517    QWaitCondition videoThreadUnpaused;
    516518    QMutex   vidExitLock;
     519    QMutex   pauseUnpauseLock;
     520    QMutex   internalPauseLock;
    517521    bool     eof;             ///< At end of file/ringbuffer
    518522    bool     m_double_framerate;///< Output fps is double Video (input) rate
    519523    bool     m_can_double;    ///< VideoOutput capable of doubling frame rate