Ticket #4242: myth_IOMultiplier_r14915.diff

File myth_IOMultiplier_r14915.diff, 8.6 KB (added by Mark Buechler <Mark.Buechler@…>, 16 years ago)

The patch.

  • libs/libmythtv/RingBuffer.cpp

    diff -rup mythtv.orig/libs/libmythtv/RingBuffer.cpp mythtv/libs/libmythtv/RingBuffer.cpp
    old new using namespace std; 
    4242
    4343const uint RingBuffer::kBufferSize = 3 * 1024 * 1024;
    4444
    45 #define CHUNK 32768 /* readblocksize increments */
     45#define DEF_CHUNK 32768 /* default readblocksize increments */
    4646
    4747#define PNG_MIN_SIZE   20 /* header plus one empty chunk */
    4848#define NUV_MIN_SIZE  204 /* header size? */
    RingBuffer::RingBuffer(const QString &lf 
    9696      readsallowed(false),      wantseek(false), setswitchtonext(false),
    9797      rawbitrate(4000),         playspeed(1.0f),
    9898      fill_threshold(65536),    fill_min(-1),
    99       readblocksize(CHUNK),    wanttoread(0),
     99      readblocksize(DEF_CHUNK), wanttoread(0),
    100100      numfailures(0),           commserror(false),
    101101      dvdPriv(NULL),            oldfile(false),
    102102      livetvchain(NULL),        ignoreliveeof(false),
    RingBuffer::RingBuffer(const QString &lf 
    118118        return;
    119119    }
    120120
     121    int io_multiplier = gContext->GetNumSetting("ReadWriteMultiplier", 5);
     122
     123    read_chunk_size = (2<<(io_multiplier - 1)) * 1024;
     124    max_read_size = 640 / (32 / (2<<(io_multiplier - 1))) * 1024;
     125
     126    VERBOSE(VB_GENERAL, LOC + QString("Using io multiplier %1, chunk/max = "
     127                                                                     "%2/%3")
     128                                                          .arg(io_multiplier)
     129                                                          .arg(read_chunk_size)
     130                                                          .arg(max_read_size));
     131
    121132    if (read_retries != (uint)-1)
    122133        OpenFile(filename, read_retries);
    123134}
    void RingBuffer::CalcReadAheadThresh(voi 
    531542    pthread_rwlock_wrlock(&rwlock);
    532543    wantseek       = false;
    533544    readsallowed   = false;
    534     readblocksize  = CHUNK;
     545    readblocksize  = read_chunk_size;
    535546
    536547    // loop without sleeping if the buffered data is less than this
    537     fill_threshold = CHUNK * 2;
     548    fill_threshold = read_chunk_size * 2;
    538549    fill_min       = 1;
    539550
    540551#ifdef USING_FRONTEND
    int RingBuffer::ReadBufAvail(void) const 
    606617void RingBuffer::ResetReadAhead(long long newinternal)
    607618{
    608619    readAheadLock.lock();
    609     readblocksize = CHUNK;
     620    readblocksize = read_chunk_size;
    610621    rbrpos = 0;
    611622    rbwpos = 0;
    612623    internalreadpos = newinternal;
    void RingBuffer::ReadAheadThread(void) 
    720731
    721732    struct timeval lastread, now;
    722733    gettimeofday(&lastread, NULL);
    723     const int KB640 = 640*1024;
    724734    int readtimeavg = 300;
    725735    int readinterval;
    726736
    727737    pausereadthread = false;
    728738
    729     readAheadBuffer = new char[kBufferSize + KB640];
     739    readAheadBuffer = new char[kBufferSize + max_read_size];
    730740
    731741    ResetReadAhead(0);
    732742    totfree = ReadBufFree();
    void RingBuffer::ReadAheadThread(void) 
    777787
    778788            readtimeavg = (readtimeavg * 9 + readinterval) / 10;
    779789
    780             if (readtimeavg < 200 && readblocksize < KB640)
     790            if (readtimeavg < 200 && readblocksize < max_read_size)
    781791            {
    782                 readblocksize += CHUNK;
     792                readblocksize += read_chunk_size;
    783793                //VERBOSE(VB_PLAYBACK,
    784794                //    QString("Avg read interval was %1 msec. %2K block size")
    785795                //            .arg(readtimeavg).arg(readblocksize/1024));
    786796                readtimeavg = 300;
    787797            }
    788             else if (readtimeavg > 400 && readblocksize > CHUNK)
     798            else if (readtimeavg > 400 && readblocksize > read_chunk_size)
    789799            {
    790                 readblocksize -= CHUNK;
     800                readblocksize -= read_chunk_size;
    791801                //VERBOSE(VB_PLAYBACK,
    792802                //    QString("Avg read interval was %1 msec. %2K block size")
    793803                //            .arg(readtimeavg).arg(readblocksize/1024));
  • libs/libmythtv/RingBuffer.h

    diff -rup mythtv.orig/libs/libmythtv/RingBuffer.h mythtv/libs/libmythtv/RingBuffer.h
    old new class MPUBLIC RingBuffer 
    126126    long long readpos;
    127127    long long writepos;
    128128
     129    int read_chunk_size;
     130    int max_read_size;
     131
    129132    bool stopreads;
    130133
    131134    mutable pthread_rwlock_t rwlock;
  • libs/libmythtv/ThreadedFileWriter.cpp

    diff -rup mythtv.orig/libs/libmythtv/ThreadedFileWriter.cpp mythtv/libs/libmythtv/ThreadedFileWriter.cpp
    old new  
    2222#define LOC_ERR QString("TFW, Error: ")
    2323
    2424const uint ThreadedFileWriter::TFW_DEF_BUF_SIZE   = 2*1024*1024;
    25 const uint ThreadedFileWriter::TFW_MAX_WRITE_SIZE = TFW_DEF_BUF_SIZE / 4;
    26 const uint ThreadedFileWriter::TFW_MIN_WRITE_SIZE = TFW_DEF_BUF_SIZE / 32;
     25const uint ThreadedFileWriter::TFW_MAX_WRITE_SIZE = TFW_DEF_BUF_SIZE /
     26                                                    (128 / (2<<(5-1)));
     27const uint ThreadedFileWriter::TFW_MIN_WRITE_SIZE = TFW_DEF_BUF_SIZE /
     28                                                    (1024 / (2<<(5-1)));
    2729
    2830/** \class ThreadedFileWriter
    2931 *  \brief This class supports the writing of recordings to disk.
    bool ThreadedFileWriter::Open(void) 
    148150        bzero(buf, TFW_DEF_BUF_SIZE + 64);
    149151
    150152        tfw_buf_size = TFW_DEF_BUF_SIZE;
    151         tfw_min_write_size = TFW_MIN_WRITE_SIZE;
     153        int io_multiplier = gContext->GetNumSetting("ReadWriteMultiplier", 5);
     154
     155        tfw_min_write_size = TFW_DEF_BUF_SIZE / (1024 / (2<<(io_multiplier - 1)));
     156        tfw_max_write_size = TFW_DEF_BUF_SIZE / (128 / (2<<(io_multiplier - 1)));
     157
     158        VERBOSE(VB_RECORD, LOC + QString("Using io multiplier %1, "
     159                                          "min/max = %2/%3")
     160                                                     .arg(io_multiplier)
     161                                                     .arg(tfw_min_write_size)
     162                                                     .arg(tfw_max_write_size));
     163
    152164        pthread_create(&writer, NULL, boot_writer, this);
    153165        pthread_create(&syncer, NULL, boot_syncer, this);
    154166        return true;
    void ThreadedFileWriter::DiskLoop(void) 
    364376           buffer is valid, and we try to write all of it at once which
    365377           takes a long time. During this time, the other thread fills up
    366378           the 10% that was free... */
    367         size = (size > TFW_MAX_WRITE_SIZE) ? TFW_MAX_WRITE_SIZE : size;
     379        size = (size > tfw_max_write_size) ? tfw_max_write_size : size;
    368380
    369381        bool write_ok;
    370382        if (ignore_writes)
  • libs/libmythtv/ThreadedFileWriter.h

    diff -rup mythtv.orig/libs/libmythtv/ThreadedFileWriter.h mythtv/libs/libmythtv/ThreadedFileWriter.h
    old new class ThreadedFileWriter 
    4848    bool            in_dtor;
    4949    bool            ignore_writes;
    5050    long long       tfw_min_write_size;
     51    long long       tfw_max_write_size;
    5152
    5253    // buffer position state
    5354    uint            rpos;    ///< points to end of data written to disk
  • programs/mythtv-setup/backendsettings.cpp

    diff -rup mythtv.orig/programs/mythtv-setup/backendsettings.cpp mythtv/programs/mythtv-setup/backendsettings.cpp
    old new static GlobalSpinBox *HDRingbufferSize() 
    171171    return bs;
    172172}
    173173
     174static GlobalSpinBox *ReadWriteMultiplier()
     175{
     176    GlobalSpinBox *bs = new GlobalSpinBox(
     177        "ReadWriteMultiplier", 2, 6, 1);
     178    bs->setLabel(QObject::tr("File read & write size multiplier"));
     179    bs->setHelpText(QObject::tr("This fine tunes filesystem reads & writes "
     180                    "for differently performing storage "
     181                    "systems. Use caution when adjusting from the default of "
     182                    "5 as this may negatively impact LiveTV and recordings."));
     183    bs->setValue(5);
     184    return bs;
     185}
     186
    174187static HostLineEdit *MiscStatusScript()
    175188{
    176189    HostLineEdit *he = new HostLineEdit("MiscStatusScript");
    BackendSettings::BackendSettings() { 
    760773    fm->addChild(DeletesFollowLinks());
    761774    fm->addChild(TruncateDeletes());
    762775    fm->addChild(HDRingbufferSize());
     776    fm->addChild(ReadWriteMultiplier());
    763777    group2->addChild(fm);
    764778    VerticalConfigurationGroup* misc = new VerticalConfigurationGroup(false);
    765779    misc->addChild(MiscStatusScript());