Ticket #10616: 10616-v1.patch

File 10616-v1.patch, 20.9 KB (added by danielk, 7 years ago)

Attempt at better fix.

  • mythtv/libs/libmythtv/playercontext.h

    diff --git a/mythtv/libs/libmythtv/playercontext.h b/mythtv/libs/libmythtv/playercontext.h
    index a4ce9f1..3e97186 100644
    a b typedef enum 
    4343typedef deque<QString>         StringDeque;
    4444typedef QHash<QString,QString> InfoMap;
    4545
    46 class MTV_PUBLIC PlayerContext : public QObject
     46class MTV_PUBLIC PlayerContext
    4747{
    48     Q_OBJECT
    4948  public:
    5049    PlayerContext(const QString &inUseID = QString("Unknown"));
    5150    ~PlayerContext();
  • mythtv/programs/mythtranscode/transcode.cpp

    diff --git a/mythtv/programs/mythtranscode/transcode.cpp b/mythtv/programs/mythtranscode/transcode.cpp
    index 1c3ea9e..414f2b8 100644
    a b Transcode::Transcode(ProgramInfo *pginfo) : 
    721721    m_proginfo(pginfo),
    722722    keyframedist(30),
    723723    nvr(NULL),
    724     player(NULL),
    725     player_ctx(NULL),
    726     inRingBuffer(NULL),
     724    ctx(NULL),
    727725    outRingBuffer(NULL),
    728726    fifow(NULL),
    729727    kfa_table(NULL),
    Transcode::~Transcode() 
    744742{
    745743    if (nvr)
    746744        delete nvr;
    747     if (player_ctx)
    748     {
    749         player       = NULL;
    750         inRingBuffer = NULL;
    751         delete player_ctx;
    752     }
     745    SetPlayerContext(NULL);
    753746    if (outRingBuffer)
    754747        delete outRingBuffer;
    755748    if (fifow)
    bool Transcode::GetProfile(QString profileName, QString encodingType, 
    831824    return true;
    832825}
    833826
     827void Transcode::SetPlayerContext(PlayerContext *player_ctx)
     828{
     829    if (player_ctx == ctx)
     830        return;
     831
     832    delete ctx;
     833    ctx = player_ctx;
     834}
     835
    834836static QString get_str_option(RecordingProfile &profile, const QString &name)
    835837{
    836838    const Setting *setting = profile.byName(name);
    int Transcode::TranscodeFile(const QString &inputname, 
    919921    }
    920922
    921923    // Input setup
    922     if (hls && (hlsStreamID != -1))
    923         inRingBuffer = RingBuffer::Create(hls->GetSourceFile(), false, false);
    924     else
    925         inRingBuffer = RingBuffer::Create(inputname, false, false);
    926 
    927     player = new MythPlayer(kVideoIsNull);
    928 
    929     player_ctx = new PlayerContext(kTranscoderInUseID);
     924    PlayerContext *player_ctx = new PlayerContext(kTranscoderInUseID);
    930925    player_ctx->SetPlayingInfo(m_proginfo);
    931     player_ctx->SetRingBuffer(inRingBuffer);
    932     player_ctx->SetPlayer(player);
    933     player->SetPlayerInfo(NULL, NULL, true, player_ctx);
     926    player_ctx->SetRingBuffer(
     927        (hls && (hlsStreamID != -1)) ?
     928        RingBuffer::Create(hls->GetSourceFile(), false, false) :
     929        RingBuffer::Create(inputname, false, false));
     930    player_ctx->SetPlayer(new MythPlayer(kVideoIsNull));
     931    SetPlayerContext(player_ctx);
     932    GetPlayer()->SetPlayerInfo(NULL, NULL, true, GetPlayerContext());
    934933
    935934    if (showprogress)
    936935    {
    int Transcode::TranscodeFile(const QString &inputname, 
    940939    AudioOutput *audioOutput = new AudioReencodeBuffer(FORMAT_NONE, 0,
    941940                                                       passthru);
    942941    AudioReencodeBuffer *arb = ((AudioReencodeBuffer*)audioOutput);
    943     player->GetAudio()->SetAudioOutput(audioOutput);
    944     player->SetTranscoding(true);
     942    GetPlayer()->GetAudio()->SetAudioOutput(audioOutput);
     943    GetPlayer()->SetTranscoding(true);
    945944
    946     if (player->OpenFile() < 0)
     945    if (GetPlayer()->OpenFile() < 0)
    947946    {
    948947        LOG(VB_GENERAL, LOG_ERR, "Transcoding aborted, error opening file.");
    949         if (player_ctx)
    950             delete player_ctx;
     948        SetPlayerContext(NULL);
    951949        return REENCODE_ERROR;
    952950    }
    953951
    int Transcode::TranscodeFile(const QString &inputname, 
    955953    {
    956954        LOG(VB_GENERAL, LOG_INFO,
    957955            QString("Set audiotrack number to %1").arg(AudioTrackNo));
    958         player->GetDecoder()->SetTrack(kTrackTypeAudio, AudioTrackNo);
     956        GetPlayer()->GetDecoder()->SetTrack(kTrackTypeAudio, AudioTrackNo);
    959957    }
    960958
    961     long long total_frame_count = player->GetTotalFrameCount();
     959    long long total_frame_count = GetPlayer()->GetTotalFrameCount();
    962960    long long new_frame_count = total_frame_count;
    963961    if (honorCutList && m_proginfo)
    964962    {
    int Transcode::TranscodeFile(const QString &inputname, 
    10051003            (JobQueue::IsJobRunning(JOB_COMMFLAG, *m_proginfo)))
    10061004        {
    10071005            LOG(VB_GENERAL, LOG_INFO, "Transcoding aborted, cutlist changed");
    1008             if (player_ctx)
    1009                 delete player_ctx;
     1006            SetPlayerContext(NULL);
    10101007            return REENCODE_CUTLIST_CHANGE;
    10111008        }
    10121009        m_proginfo->ClearMarkupFlag(MARK_UPDATED_CUT);
    10131010        curtime = curtime.addSecs(60);
    10141011    }
    10151012
    1016     player->GetAudio()->ReinitAudio();
    1017     QString encodingType = player->GetEncodingType();
     1013    GetPlayer()->GetAudio()->ReinitAudio();
     1014    QString encodingType = GetPlayer()->GetEncodingType();
    10181015    bool copyvideo = false, copyaudio = false;
    10191016
    10201017    QString vidsetting = NULL, audsetting = NULL, vidfilters = NULL;
    10211018
    1022     QSize buf_size = player->GetVideoBufferSize();
     1019    QSize buf_size = GetPlayer()->GetVideoBufferSize();
    10231020    int video_width = buf_size.width();
    10241021    int video_height = buf_size.height();
    10251022
    int Transcode::TranscodeFile(const QString &inputname, 
    10301027           "will treat it as such.");
    10311028    }
    10321029
    1033     DecoderBase* dec = player->GetDecoder();
     1030    DecoderBase* dec = GetPlayer()->GetDecoder();
    10341031    float video_aspect = dec ? dec->GetVideoAspect() : 4.0f / 3.0f;
    1035     float video_frame_rate = player->GetFrameRate();
     1032    float video_frame_rate = GetPlayer()->GetFrameRate();
    10361033    int newWidth = video_width;
    10371034    int newHeight = video_height;
    10381035    bool halfFramerate = false;
    int Transcode::TranscodeFile(const QString &inputname, 
    10741071        {
    10751072            LOG(VB_GENERAL, LOG_ERR,
    10761073                "Transcoding aborted, error creating AVFormatWriter.");
    1077             if (player_ctx)
    1078                 delete player_ctx;
     1074            SetPlayerContext(NULL);
    10791075            return REENCODE_ERROR;
    10801076        }
    10811077
    int Transcode::TranscodeFile(const QString &inputname, 
    11031099                {
    11041100                    LOG(VB_GENERAL, LOG_ERR, "Transcoding aborted, error "
    11051101                        "creating low-bitrate AVFormatWriter.");
    1106                     if (player_ctx)
    1107                         delete player_ctx;
     1102                    SetPlayerContext(NULL);
    11081103                    return REENCODE_ERROR;
    11091104                }
    11101105
    int Transcode::TranscodeFile(const QString &inputname, 
    11351130                (!hls->InitForWrite()))
    11361131            {
    11371132                LOG(VB_GENERAL, LOG_ERR, "hls->InitForWrite() failed");
    1138                 if (player_ctx)
    1139                     delete player_ctx;
     1133                SetPlayerContext(NULL);
    11401134                return REENCODE_ERROR;
    11411135            }
    11421136
    int Transcode::TranscodeFile(const QString &inputname, 
    11871181        if (!avfw->Init())
    11881182        {
    11891183            LOG(VB_GENERAL, LOG_ERR, "avfw->Init() failed");
    1190             if (player_ctx)
    1191                 delete player_ctx;
     1184            SetPlayerContext(NULL);
    11921185            return REENCODE_ERROR;
    11931186        }
    11941187
    11951188        if (!avfw->OpenFile())
    11961189        {
    11971190            LOG(VB_GENERAL, LOG_ERR, "avfw->OpenFile() failed");
    1198             if (player_ctx)
    1199                 delete player_ctx;
     1191            SetPlayerContext(NULL);
    12001192            return REENCODE_ERROR;
    12011193        }
    12021194
    12031195        if (avfw2 && !avfw2->Init())
    12041196        {
    12051197            LOG(VB_GENERAL, LOG_ERR, "avfw2->Init() failed");
    1206             if (player_ctx)
    1207                 delete player_ctx;
     1198            SetPlayerContext(NULL);
    12081199            return REENCODE_ERROR;
    12091200        }
    12101201
    12111202        if (avfw2 && !avfw2->OpenFile())
    12121203        {
    12131204            LOG(VB_GENERAL, LOG_ERR, "avfw2->OpenFile() failed");
    1214             if (player_ctx)
    1215                 delete player_ctx;
     1205            SetPlayerContext(NULL);
    12161206            return REENCODE_ERROR;
    12171207        }
    12181208
    12191209        arb->m_audioFrameSize = avfw->GetAudioFrameSize() * arb->m_channels * 2;
    12201210
    1221         player->SetVideoFilters(
     1211        GetPlayer()->SetVideoFilters(
    12221212            gCoreContext->GetSetting("HTTPLiveStreamFilters"));
    12231213    }
    12241214    else if (fifodir.isEmpty())
    int Transcode::TranscodeFile(const QString &inputname, 
    12261216        if (!GetProfile(profileName, encodingType, video_height,
    12271217                        (int)round(video_frame_rate))) {
    12281218            LOG(VB_GENERAL, LOG_ERR, "Transcoding aborted, no profile found.");
    1229             if (player_ctx)
    1230                 delete player_ctx;
     1219            SetPlayerContext(NULL);
    12311220            return REENCODE_ERROR;
    12321221        }
    12331222
    int Transcode::TranscodeFile(const QString &inputname, 
    12551244            get_int_option(profile, "transcodelossless"))
    12561245        {
    12571246            LOG(VB_GENERAL, LOG_NOTICE, "Switching to MPEG-2 transcoder.");
    1258             if (player_ctx)
    1259                 delete player_ctx;
     1247            SetPlayerContext(NULL);
    12601248            return REENCODE_MPEG2TRANS;
    12611249        }
    12621250
    int Transcode::TranscodeFile(const QString &inputname, 
    12701258        {
    12711259            int actualHeight = (video_height == 1088 ? 1080 : video_height);
    12721260
    1273             player->SetVideoFilters(vidfilters);
     1261            GetPlayer()->SetVideoFilters(vidfilters);
    12741262            newWidth = get_int_option(profile, "width");
    12751263            newHeight = get_int_option(profile, "height");
    12761264
    int Transcode::TranscodeFile(const QString &inputname, 
    13021290                    .arg(newWidth).arg(newHeight));
    13031291        }
    13041292        else  // lossy and no resize
    1305             player->SetVideoFilters(vidfilters);
     1293            GetPlayer()->SetVideoFilters(vidfilters);
    13061294
    13071295        // this is ripped from tv_rec SetupRecording. It'd be nice to merge
    13081296        nvr->SetOption("inpixfmt", FMT_YV12);
    int Transcode::TranscodeFile(const QString &inputname, 
    13571345            LOG(VB_GENERAL, LOG_ERR, "No video information found!");
    13581346            LOG(VB_GENERAL, LOG_ERR, "Please ensure that recording profiles "
    13591347                                     "for the transcoder are set");
    1360             if (player_ctx)
    1361                 delete player_ctx;
     1348            SetPlayerContext(NULL);
    13621349            return REENCODE_ERROR;
    13631350        }
    13641351        else
    13651352        {
    13661353            LOG(VB_GENERAL, LOG_ERR,
    13671354                QString("Unknown video codec: %1").arg(vidsetting));
    1368             if (player_ctx)
    1369                 delete player_ctx;
     1355            SetPlayerContext(NULL);
    13701356            return REENCODE_ERROR;
    13711357        }
    13721358
    int Transcode::TranscodeFile(const QString &inputname, 
    14551441            cutter = new Cutter();
    14561442            cutter->SetCutList(deleteMap);
    14571443
    1458             player->SetCutList(cutter->AdjustedCutList());
     1444            GetPlayer()->SetCutList(cutter->AdjustedCutList());
    14591445        }
    14601446        else
    14611447        {
    14621448            // Have the player apply the cut list
    1463             player->SetCutList(deleteMap);
     1449            GetPlayer()->SetCutList(deleteMap);
    14641450        }
    14651451    }
    14661452
    1467     player->InitForTranscode(copyaudio, copyvideo);
    1468     if (player->IsErrored())
     1453    GetPlayer()->InitForTranscode(copyaudio, copyvideo);
     1454    if (GetPlayer()->IsErrored())
    14691455    {
    14701456        LOG(VB_GENERAL, LOG_ERR,
    14711457            "Unable to initialize MythPlayer for Transcode");
    1472         if (player_ctx)
    1473             delete player_ctx;
     1458        SetPlayerContext(NULL);
    14741459        return REENCODE_ERROR;
    14751460    }
    14761461
    int Transcode::TranscodeFile(const QString &inputname, 
    14921477
    14931478    if (!fifodir.isEmpty())
    14941479    {
    1495         AudioPlayer *aplayer = player->GetAudio();
     1480        AudioPlayer *aplayer = GetPlayer()->GetAudio();
    14961481        const char  *audio_codec_name;
    14971482
    14981483        switch(aplayer->GetCodec())
    int Transcode::TranscodeFile(const QString &inputname, 
    15281513            bool is_key;
    15291514            int did_ff;
    15301515            frm_dir_map_t::iterator dm_iter;
    1531             player->TranscodeGetNextFrame(dm_iter, did_ff, is_key, true);
     1516            GetPlayer()->TranscodeGetNextFrame(dm_iter, did_ff, is_key, true);
    15321517
    1533             QSize buf_size = player->GetVideoBufferSize();
     1518            QSize buf_size = GetPlayer()->GetVideoBufferSize();
    15341519            video_width = buf_size.width();
    15351520            video_height = buf_size.height();
    1536             video_aspect = player->GetVideoAspect();
    1537             video_frame_rate = player->GetFrameRate();
     1521            video_aspect = GetPlayer()->GetVideoAspect();
     1522            video_frame_rate = GetPlayer()->GetFrameRate();
    15381523        }
    15391524
    15401525        // Display details of the format of the fifo data.
    int Transcode::TranscodeFile(const QString &inputname, 
    15581543            // Request was for just the format of fifo data, not for
    15591544            // the actual transcode, so stop here.
    15601545            unlink(outputname.toLocal8Bit().constData());
    1561             if (player_ctx)
    1562                 delete player_ctx;
     1546            SetPlayerContext(NULL);
    15631547            return REENCODE_OK;
    15641548        }
    15651549
    int Transcode::TranscodeFile(const QString &inputname, 
    15771561            LOG(VB_GENERAL, LOG_ERR,
    15781562                "Error initializing fifo writer.  Aborting");
    15791563            unlink(outputname.toLocal8Bit().constData());
    1580             if (player_ctx)
    1581                 delete player_ctx;
     1564            SetPlayerContext(NULL);
    15821565            return REENCODE_ERROR;
    15831566        }
    15841567        LOG(VB_GENERAL, LOG_INFO,
    int Transcode::TranscodeFile(const QString &inputname, 
    16091592    float rateTimeConv = arb->m_eff_audiorate / 1000.0f;
    16101593    float vidFrameTime = 1000.0f / video_frame_rate;
    16111594    int wait_recover = 0;
    1612     VideoOutput *videoOutput = player->GetVideoOutput();
     1595    VideoOutput *videoOutput = GetPlayer()->GetVideoOutput();
    16131596    bool is_key = 0;
    16141597    bool first_loop = true;
    16151598    unsigned char *newFrame = new unsigned char[frame.size];
    int Transcode::TranscodeFile(const QString &inputname, 
    16291612        LOG(VB_GENERAL, LOG_INFO, "Transcoding Video and Audio");
    16301613
    16311614    TranscodeFrameQueue *frameQueue =
    1632         new TranscodeFrameQueue(player, videoOutput, honorCutList);
     1615        new TranscodeFrameQueue(GetPlayer(), videoOutput, honorCutList);
    16331616    MThreadPool::globalInstance()->start(frameQueue, "TranscodeFrameQueue");
    16341617
    16351618    QTime flagTime;
    int Transcode::TranscodeFile(const QString &inputname, 
    16491632    {
    16501633        if (first_loop)
    16511634        {
    1652             copyaudio = player->GetRawAudioState();
     1635            copyaudio = GetPlayer()->GetRawAudioState();
    16531636            first_loop = false;
    16541637        }
    16551638
    int Transcode::TranscodeFile(const QString &inputname, 
    17651748                }
    17661749            }
    17671750            videoOutput->DoneDisplayingFrame(lastDecode);
    1768             player->GetCC608Reader()->FlushTxtBuffers();
     1751            GetPlayer()->GetCC608Reader()->FlushTxtBuffers();
    17691752            lasttimecode = frame.timecode;
    17701753        }
    17711754        else if (copyaudio)
    17721755        {
    17731756            // Encoding from NuppelVideo to NuppelVideo with MP3 audio
    17741757            // So let's not decode/reencode audio
    1775             if (!player->GetRawAudioState())
     1758            if (!GetPlayer()->GetRawAudioState())
    17761759            {
    17771760                // The Raw state changed during decode.  This is not good
    17781761                LOG(VB_GENERAL, LOG_ERR, "Transcoding aborted, MythPlayer "
    int Transcode::TranscodeFile(const QString &inputname, 
    17801763
    17811764                unlink(outputname.toLocal8Bit().constData());
    17821765                delete [] newFrame;
    1783                 if (player_ctx)
    1784                     delete player_ctx;
     1766                SetPlayerContext(NULL);
    17851767                if (frameQueue)
    17861768                    frameQueue->stop();
    17871769                return REENCODE_ERROR;
    int Transcode::TranscodeFile(const QString &inputname, 
    18011783
    18021784                    //need to correct the frame# and timecode here
    18031785                    // Question:  Is it necessary to change the timecodes?
    1804                     long sync_offset;
    1805                     sync_offset = player->UpdateStoredFrameNum(curFrameNum);
     1786                    long sync_offset =
     1787                        GetPlayer()->UpdateStoredFrameNum(curFrameNum);
    18061788                    nvr->UpdateSeekTable(num_keyframes, sync_offset);
    18071789                    ReencoderAddKFA(curFrameNum, lastKeyFrame, num_keyframes);
    18081790                    num_keyframes++;
    int Transcode::TranscodeFile(const QString &inputname, 
    18211803            lasttimecode = frame.timecode;
    18221804            frame.timecode -= timecodeOffset;
    18231805
    1824             if (! player->WriteStoredData(outRingBuffer, (did_ff == 0),
    1825                                       timecodeOffset))
     1806            if (!GetPlayer()->WriteStoredData(
     1807                    outRingBuffer, (did_ff == 0), timecodeOffset))
    18261808            {
    18271809                if (video_aspect != new_aspect)
    18281810                {
    int Transcode::TranscodeFile(const QString &inputname, 
    18301812                    nvr->SetNewVideoParams(video_aspect);
    18311813                }
    18321814
    1833                 QSize buf_size = player->GetVideoBufferSize();
     1815                QSize buf_size = GetPlayer()->GetVideoBufferSize();
    18341816
    18351817                if (video_width != buf_size.width() ||
    18361818                    video_height != buf_size.height())
    int Transcode::TranscodeFile(const QString &inputname, 
    18771859
    18781860                nvr->WriteVideo(&frame, true, writekeyframe);
    18791861            }
    1880             player->GetCC608Reader()->FlushTxtBuffers();
     1862            GetPlayer()->GetCC608Reader()->FlushTxtBuffers();
    18811863        }
    18821864        else
    18831865        {
    int Transcode::TranscodeFile(const QString &inputname, 
    18961878            }
    18971879
    18981880
    1899             QSize buf_size = player->GetVideoBufferSize();
     1881            QSize buf_size = GetPlayer()->GetVideoBufferSize();
    19001882
    19011883            if (video_width != buf_size.width() ||
    19021884                video_height != buf_size.height())
    int Transcode::TranscodeFile(const QString &inputname, 
    19791961                                "NVR::WriteAudio");
    19801962
    19811963                            delete [] newFrame;
    1982                             if (player_ctx)
    1983                                 delete player_ctx;
     1964                            SetPlayerContext(NULL);
    19841965                            if (frameQueue)
    19851966                                frameQueue->stop();
    19861967                            delete ab;
    int Transcode::TranscodeFile(const QString &inputname, 
    19961977            }
    19971978
    19981979            if (!avfMode)
    1999                 player->GetCC608Reader()->
     1980            {
     1981                GetPlayer()->GetCC608Reader()->
    20001982                    TranscodeWriteText(&TranscodeWriteText, (void *)(nvr));
     1983            }
    20011984            lasttimecode = frame.timecode;
    20021985            frame.timecode -= timecodeOffset;
    20031986
    int Transcode::TranscodeFile(const QString &inputname, 
    20662049
    20672050                unlink(outputname.toLocal8Bit().constData());
    20682051                delete [] newFrame;
    2069                 if (player_ctx)
    2070                     delete player_ctx;
     2052                SetPlayerContext(NULL);
    20712053                if (frameQueue)
    20722054                    frameQueue->stop();
    20732055                return REENCODE_CUTLIST_CHANGE;
    int Transcode::TranscodeFile(const QString &inputname, 
    20822064
    20832065                    unlink(outputname.toLocal8Bit().constData());
    20842066                    delete [] newFrame;
    2085                     if (player_ctx)
    2086                         delete player_ctx;
     2067                    SetPlayerContext(NULL);
    20872068                    if (frameQueue)
    20882069                        frameQueue->stop();
    20892070                    return REENCODE_STOPPED;
    int Transcode::TranscodeFile(const QString &inputname, 
    21162097        curFrameNum++;
    21172098        frame.frameNumber = 1 + (curFrameNum << 1);
    21182099
    2119         player->DiscardVideoFrame(lastDecode);
     2100        GetPlayer()->DiscardVideoFrame(lastDecode);
    21202101    }
    21212102
    21222103    sws_freeContext(scontext);
    int Transcode::TranscodeFile(const QString &inputname, 
    21752156        frameQueue->stop();
    21762157
    21772158    delete [] newFrame;
    2178     if (player_ctx)
    2179         delete player_ctx;
     2159    SetPlayerContext(NULL);
     2160
    21802161    return REENCODE_OK;
    21812162}
    21822163
  • mythtv/programs/mythtranscode/transcode.h

    diff --git a/mythtv/programs/mythtranscode/transcode.h b/mythtv/programs/mythtranscode/transcode.h
    index ce5b909..9c5f7a4 100644
    a b  
    1 #include <QPointer>
    21#include "recordingprofile.h"
    32#include "fifowriter.h"
    43#include "transcodedefs.h"
    class Transcode : public QObject 
    4342    bool GetProfile(QString profileName, QString encodingType, int height,
    4443                    int frameRate);
    4544    void ReencoderAddKFA(long curframe, long lastkey, long num_keyframes);
     45    void SetPlayerContext(PlayerContext*);
     46    PlayerContext *GetPlayerContext(void) { return ctx; }
     47    MythPlayer *GetPlayer(void) { return (ctx) ? ctx->player : NULL; }
    4648
    4749  private:
    4850    ProgramInfo            *m_proginfo;
    4951    RecordingProfile        profile;
    5052    int                     keyframedist;
    5153    NuppelVideoRecorder    *nvr;
    52     MythPlayer             *player;
    53     QPointer<PlayerContext> player_ctx;
    54     RingBuffer             *inRingBuffer;
     54    PlayerContext          *ctx;
    5555    RingBuffer             *outRingBuffer;
    5656    FIFOWriter             *fifow;
    5757    KFATable               *kfa_table;