• Main Page
  • Related Pages
  • Modules
  • Namespaces
  • Classes
  • Files

avformatdecoder.cpp

Go to the documentation of this file.
00001 // C headers
00002 #include <cassert>
00003 #include <unistd.h>
00004 #include <cmath>
00005 
00006 // C++ headers
00007 #include <algorithm>
00008 #include <iostream>
00009 using namespace std;
00010 
00011 // MythTV headers
00012 #include "mythconfig.h"
00013 #include "avformatdecoder.h"
00014 #include "RingBuffer.h"
00015 #include "NuppelVideoPlayer.h"
00016 #include "remoteencoder.h"
00017 #include "programinfo.h"
00018 #include "mythcontext.h"
00019 #include "mythdbcon.h"
00020 #include "iso639.h"
00021 #include "mpegtables.h"
00022 #include "atscdescriptors.h"
00023 #include "dvbdescriptors.h"
00024 #include "cc608decoder.h"
00025 #include "cc708decoder.h"
00026 #include "interactivetv.h"
00027 #include "DVDRingBuffer.h"
00028 #include "videodisplayprofile.h"
00029 
00030 #include "videoout_dvdv.h"    // AvFormatDecoderPrivate has DVDV ptr
00031 #include "videoout_quartz.h"  // For VOQ::GetBestSupportedCodec()
00032 
00033 #ifdef USING_XVMC
00034 #include "videoout_xv.h"
00035 extern "C" {
00036 #include "libavcodec/xvmc_render.h"
00037 }
00038 #endif // USING_XVMC
00039 
00040 extern "C" {
00041 #include "../libavutil/avutil.h"
00042 #include "../libavcodec/ac3_parser.h"
00043 #include "../libmythmpeg2/mpeg2.h"
00044 #include "ivtv_myth.h"
00045 // from libavcodec
00046 extern const uint8_t *ff_find_start_code(const uint8_t * restrict p, const uint8_t *end, uint32_t * restrict state);
00047 }
00048 
00049 #define LOC QString("AFD: ")
00050 #define LOC_ERR QString("AFD Error: ")
00051 #define LOC_WARN QString("AFD Warning: ")
00052 
00053 #define MAX_AC3_FRAME_SIZE 6144
00054 
00055 static const float eps = 1E-5;
00056 
00057 static int cc608_parity(uint8_t byte);
00058 static int cc608_good_parity(const int *parity_table, uint16_t data);
00059 static void cc608_build_parity_table(int *parity_table);
00060 
00061 static int dts_syncinfo(uint8_t *indata_ptr, int *flags,
00062                         int *sample_rate, int *bit_rate);
00063 static int dts_decode_header(uint8_t *indata_ptr, int *rate,
00064                              int *nblks, int *sfreq);
00065 static int encode_frame(bool dts, unsigned char* data, int len,
00066                         short *samples, int &samples_size);
00067 
00068 int get_avf_buffer_xvmc(struct AVCodecContext *c, AVFrame *pic);
00069 int get_avf_buffer(struct AVCodecContext *c, AVFrame *pic);
00070 void release_avf_buffer(struct AVCodecContext *c, AVFrame *pic);
00071 void release_avf_buffer_xvmc(struct AVCodecContext *c, AVFrame *pic);
00072 void render_slice_xvmc(struct AVCodecContext *s, const AVFrame *src,
00073                        int offset[4], int y, int type, int height);
00074 void decode_cc_dvd(struct AVCodecContext *c, const uint8_t *buf, int buf_size);
00075 
00076 static void myth_av_log(void *ptr, int level, const char* fmt, va_list vl)
00077 {
00078     static QString full_line("");
00079     static const int msg_len = 255;
00080     static QMutex string_lock;
00081 
00082     // determine mythtv debug level from av log level
00083     uint verbose_level = (level < AV_LOG_WARNING) ? VB_IMPORTANT : VB_LIBAV;
00084 
00085     if (!(print_verbose_messages & verbose_level))
00086         return;
00087 
00088     string_lock.lock();
00089     if (full_line.isEmpty() && ptr) {
00090         AVClass* avc = *(AVClass**)ptr;
00091         full_line.sprintf("[%s @ %p]", avc->item_name(ptr), avc);
00092     }
00093 
00094     char str[msg_len+1];
00095     int bytes = vsnprintf(str, msg_len+1, fmt, vl);
00096     // check for truncted messages and fix them
00097     if (bytes > msg_len)
00098     {
00099         VERBOSE(VB_IMPORTANT, QString("Libav log output truncated %1 of %2 bytes written")
00100                 .arg(msg_len).arg(bytes));
00101         str[msg_len-1] = '\n';
00102     }
00103 
00104     full_line += QString(str);
00105     if (full_line.endsWith("\n"))
00106     {
00107         full_line.truncate(full_line.length() - 1);
00108         VERBOSE(verbose_level, full_line);
00109         full_line.truncate(0);
00110     }
00111     string_lock.unlock();
00112 }
00113 
00114 static int get_canonical_lang(const char *lang_cstr)
00115 {
00116     if (lang_cstr[0] == '\0' || lang_cstr[1] == '\0')
00117     {
00118         return iso639_str3_to_key("und");
00119     }
00120     else if (lang_cstr[2] == '\0')
00121     {
00122         QString tmp2 = lang_cstr;
00123         QString tmp3 = iso639_str2_to_str3(tmp2);
00124         int lang = iso639_str3_to_key(tmp3.ascii());
00125         return iso639_key_to_canonical_key(lang);
00126     }
00127     else
00128     {
00129         int lang = iso639_str3_to_key(lang_cstr);
00130         return iso639_key_to_canonical_key(lang);
00131     }
00132 }
00133 
00134 typedef MythDeque<AVFrame*> avframe_q;
00135 
00139 class AvFormatDecoderPrivate
00140 {
00141   public:
00142     AvFormatDecoderPrivate(bool allow_libmpeg2)
00143         : mpeg2dec(NULL), dvdvdec(NULL), allow_mpeg2dec(allow_libmpeg2) { ; }
00144    ~AvFormatDecoderPrivate() { DestroyMPEG2(); }
00145     
00146     bool InitMPEG2(const QString &dec);
00147     bool HasMPEG2Dec(void) const { return (bool)(mpeg2dec); }
00148     bool HasDVDVDec(void) const { return (bool)(dvdvdec); }
00149     bool HasDecoder(void) const { return HasMPEG2Dec() || HasDVDVDec(); }
00150 
00151     void DestroyMPEG2();
00152     void ResetMPEG2();
00153     int DecodeMPEG2Video(AVCodecContext *avctx, AVFrame *picture,
00154                          int *got_picture_ptr, uint8_t *buf, int buf_size);
00155 
00156     // Mac OS X Hardware DVD-Video decoder
00157     bool SetVideoSize(const QSize &video_dim);
00158     DVDV *GetDVDVDecoder(void) { return dvdvdec; }
00159 
00160   private:
00161     mpeg2dec_t *mpeg2dec;
00162     DVDV       *dvdvdec;
00163     bool        allow_mpeg2dec;
00164     avframe_q   partialFrames;
00165 };
00166 
00173 bool AvFormatDecoderPrivate::InitMPEG2(const QString &dec)
00174 {
00175     // only ffmpeg is used for decoding previews
00176     if (!allow_mpeg2dec)
00177         return false;
00178     DestroyMPEG2();
00179 
00180 #ifdef USING_DVDV
00181     if (dec == "macaccel")
00182     {
00183         dvdvdec = new DVDV();
00184         if (dvdvdec)
00185         {
00186             VERBOSE(VB_PLAYBACK,
00187                     LOC + "Using Mac Acceleration (DVDV) for video decoding");
00188         }
00189     }
00190 #endif // !USING_DVDV
00191 
00192     if (dec == "libmpeg2")
00193     {
00194         mpeg2dec = mpeg2_init();
00195         if (mpeg2dec)
00196             VERBOSE(VB_PLAYBACK, LOC + "Using libmpeg2 for video decoding");
00197     }
00198 
00199     return HasDecoder();
00200 }
00201 
00202 void AvFormatDecoderPrivate::DestroyMPEG2()
00203 {
00204     if (mpeg2dec)
00205     {
00206         mpeg2_close(mpeg2dec);
00207         mpeg2dec = NULL;
00208 
00209         avframe_q::iterator it = partialFrames.begin();
00210         for (; it != partialFrames.end(); ++it)
00211             delete (*it);
00212         partialFrames.clear();
00213     }
00214 
00215     if (dvdvdec)
00216     {
00217         delete dvdvdec;
00218         dvdvdec = NULL;
00219     }
00220 }
00221 
00222 void AvFormatDecoderPrivate::ResetMPEG2()
00223 {
00224     if (mpeg2dec)
00225     {
00226         mpeg2_reset(mpeg2dec, 0);
00227 
00228         avframe_q::iterator it = partialFrames.begin();
00229         for (; it != partialFrames.end(); ++it)
00230             delete (*it);
00231         partialFrames.clear();
00232     }
00233 
00234     if (dvdvdec)
00235         dvdvdec->Reset();
00236 }
00237 
00238 int AvFormatDecoderPrivate::DecodeMPEG2Video(AVCodecContext *avctx,
00239                                              AVFrame *picture,
00240                                              int *got_picture_ptr,
00241                                              uint8_t *buf, int buf_size)
00242 {
00243     if (dvdvdec)
00244     {
00245         if (!dvdvdec->PreProcessFrame(avctx))
00246         {
00247             VERBOSE(VB_ALL, "DVDV::PreProcessFrame() failed");
00248             DestroyMPEG2();
00249             return -1;
00250         }
00251 
00252         int ret = avcodec_decode_video(avctx, picture,
00253                                        got_picture_ptr, buf, buf_size);
00254 
00255         dvdvdec->PostProcessFrame(avctx, (VideoFrame *)(picture->opaque),
00256                                   picture->pict_type, *got_picture_ptr);
00257         return ret;
00258     }
00259 
00260     *got_picture_ptr = 0;
00261     const mpeg2_info_t *info = mpeg2_info(mpeg2dec);
00262     mpeg2_buffer(mpeg2dec, buf, buf + buf_size);
00263     while (1)
00264     {
00265         switch (mpeg2_parse(mpeg2dec))
00266         {
00267             case STATE_SEQUENCE:
00268                 // libmpeg2 needs three buffers to do its work.
00269                 // We set up two prediction buffers here, from
00270                 // the set of available video frames.
00271                 mpeg2_custom_fbuf(mpeg2dec, 1);
00272                 for (int i = 0; i < 2; i++)
00273                 {
00274                     avctx->get_buffer(avctx, picture);
00275                     mpeg2_set_buf(mpeg2dec, picture->data, picture->opaque);
00276                 }
00277                 break;
00278             case STATE_PICTURE:
00279                 // This sets up the third buffer for libmpeg2.
00280                 // We use up one of the three buffers for each
00281                 // frame shown. The frames get released once
00282                 // they are drawn (outside this routine).
00283                 avctx->get_buffer(avctx, picture);
00284                 mpeg2_set_buf(mpeg2dec, picture->data, picture->opaque);
00285                 break;
00286             case STATE_BUFFER:
00287                 // We're finished with the buffer...
00288                 if (partialFrames.size())
00289                 {
00290                     AVFrame *frm = partialFrames.dequeue();
00291                     *got_picture_ptr = 1;
00292                     *picture = *frm;
00293                     delete frm;
00294 #if 0
00295                     QString msg("");
00296                     AvFormatDecoder *nd = (AvFormatDecoder *)(avctx->opaque);
00297                     if (nd && nd->GetNVP() && nd->GetNVP()->getVideoOutput())
00298                         msg = nd->GetNVP()->getVideoOutput()->GetFrameStatus();
00299 
00300                     VERBOSE(VB_IMPORTANT, "ret frame: "<<picture->opaque
00301                             <<"           "<<msg);
00302 #endif
00303                 }
00304                 return buf_size;
00305             case STATE_INVALID:
00306                 // This is the error state. The decoder must be
00307                 // reset on an error.
00308                 ResetMPEG2();
00309                 return -1;
00310 
00311             case STATE_SLICE:
00312             case STATE_END:
00313             case STATE_INVALID_END:
00314                 if (info->display_fbuf)
00315                 {
00316                     bool exists = false;
00317                     avframe_q::iterator it = partialFrames.begin();
00318                     for (; it != partialFrames.end(); ++it)
00319                         if ((*it)->opaque == info->display_fbuf->id)
00320                             exists = true;
00321 
00322                     if (!exists)
00323                     {
00324                         AVFrame *frm = new AVFrame();
00325                         frm->data[0] = info->display_fbuf->buf[0];
00326                         frm->data[1] = info->display_fbuf->buf[1];
00327                         frm->data[2] = info->display_fbuf->buf[2];
00328                         frm->data[3] = NULL;
00329                         frm->opaque  = info->display_fbuf->id;
00330                         frm->type    = FF_BUFFER_TYPE_USER;
00331                         frm->top_field_first =
00332                             !!(info->display_picture->flags &
00333                                PIC_FLAG_TOP_FIELD_FIRST);
00334                         frm->interlaced_frame =
00335                             !(info->display_picture->flags &
00336                               PIC_FLAG_PROGRESSIVE_FRAME);
00337                         frm->repeat_pict = 
00338                             !!(info->display_picture->flags &
00339                                PIC_FLAG_REPEAT_FIELD); 
00340                         partialFrames.enqueue(frm);
00341                         
00342                     }
00343                 }
00344                 if (info->discard_fbuf)
00345                 {
00346                     bool exists = false;
00347                     avframe_q::iterator it = partialFrames.begin();
00348                     for (; it != partialFrames.end(); ++it)
00349                     {
00350                         if ((*it)->opaque == info->discard_fbuf->id)
00351                         {
00352                             exists = true;
00353                             (*it)->data[3] = (unsigned char*) 1;
00354                         }
00355                     }
00356 
00357                     if (!exists)
00358                     {
00359                         AVFrame frame;
00360                         frame.opaque = info->discard_fbuf->id;
00361                         frame.type   = FF_BUFFER_TYPE_USER;
00362                         avctx->release_buffer(avctx, &frame);
00363                     }
00364                 }
00365                 break;
00366             default:
00367                 break;
00368         }
00369     }
00370 }
00371 
00372 bool AvFormatDecoderPrivate::SetVideoSize(const QSize &video_dim)
00373 {
00374     if (dvdvdec && !dvdvdec->SetVideoSize(video_dim))
00375     {
00376         DestroyMPEG2();
00377         return false;
00378     }
00379 
00380     return true;
00381 }
00382 
00383 AvFormatDecoder::AvFormatDecoder(NuppelVideoPlayer *parent,
00384                                  ProgramInfo *pginfo,
00385                                  bool use_null_videoout,
00386                                  bool allow_libmpeg2)
00387     : DecoderBase(parent, pginfo),
00388       d(new AvFormatDecoderPrivate(allow_libmpeg2)),
00389       h264_kf_seq(new H264::KeyframeSequencer()),
00390       ic(NULL),
00391       frame_decoded(0),             decoded_video_frame(NULL),
00392       avfRingBuffer(NULL),
00393       directrendering(false),       drawband(false),
00394       gopset(false),                seen_gop(false),
00395       seq_count(0),                 firstgoppos(0),
00396       prevgoppos(0),                gotvideo(false),
00397       start_code_state(0xffffffff),
00398       lastvpts(0),                  lastapts(0),
00399       lastccptsu(0),
00400       using_null_videoout(use_null_videoout),
00401       video_codec_id(kCodec_NONE),
00402       maxkeyframedist(-1), 
00403       // Closed Caption & Teletext decoders
00404       ccd608(new CC608Decoder(parent)),
00405       ccd708(new CC708Decoder(parent)),
00406       ttd(new TeletextDecoder()),
00407       // Interactive TV
00408       itv(NULL),
00409       selectedVideoIndex(-1),
00410       // Audio
00411       audioSamples(new short int[AVCODEC_MAX_AUDIO_FRAME_SIZE]),
00412       allow_ac3_passthru(false),    allow_dts_passthru(false),
00413       disable_passthru(false),      max_channels(2),
00414       dummy_frame(NULL),
00415       // DVD
00416       lastdvdtitle(-1),
00417       decodeStillFrame(false),
00418       dvd_xvmc_enabled(false), dvd_video_codec_changed(false),
00419       dvdTitleChanged(false), mpeg_seq_end_seen(false)
00420 {
00421     bzero(&params, sizeof(AVFormatParameters));
00422     bzero(audioSamples, AVCODEC_MAX_AUDIO_FRAME_SIZE * sizeof(short int));
00423     ccd608->SetIgnoreTimecode(true);
00424 
00425     bool debug = (bool)(print_verbose_messages & VB_LIBAV);
00426     av_log_set_level((debug) ? AV_LOG_DEBUG : AV_LOG_ERROR);
00427     av_log_set_callback(myth_av_log);
00428 
00429     allow_ac3_passthru = gContext->GetNumSetting("AC3PassThru", false);
00430     allow_dts_passthru = gContext->GetNumSetting("DTSPassThru", false);
00431     max_channels = (uint) gContext->GetNumSetting("MaxChannels", 2);
00432 
00433     audioIn.sample_size = -32; // force SetupAudioStream to run once
00434     itv = GetNVP()->GetInteractiveTV();
00435 
00436     cc608_build_parity_table(cc608_parity_table);
00437 
00438     no_dts_hack = false;
00439 }
00440 
00441 AvFormatDecoder::~AvFormatDecoder()
00442 {
00443     while (storedPackets.count() > 0)
00444     {
00445         AVPacket *pkt = storedPackets.first();
00446         storedPackets.removeFirst();
00447         av_free_packet(pkt);
00448         delete pkt;
00449     }
00450 
00451     CloseContext();
00452     delete ccd608;
00453     delete ccd708;
00454     delete ttd;
00455     delete d;
00456     delete h264_kf_seq;
00457     if (audioSamples)
00458         delete [] audioSamples;
00459 
00460     if (dummy_frame)
00461     {
00462         delete [] dummy_frame->buf;
00463         delete dummy_frame;
00464         dummy_frame = NULL;
00465     }
00466 
00467     if (avfRingBuffer)
00468         delete avfRingBuffer;
00469 }
00470 
00471 void AvFormatDecoder::CloseCodecs()
00472 {
00473     if (ic)
00474     {
00475         for (uint i = 0; i < ic->nb_streams; i++)
00476         {
00477             QMutexLocker locker(&avcodeclock);
00478             AVStream *st = ic->streams[i];
00479             if (st->codec->codec)
00480                 avcodec_close(st->codec);
00481         }
00482     }
00483 }
00484     
00485 void AvFormatDecoder::CloseContext()
00486 {
00487     if (ic)
00488     {
00489         CloseCodecs();
00490         
00491         AVInputFormat *fmt = ic->iformat;
00492         ic->iformat->flags |= AVFMT_NOFILE;
00493 
00494         av_free(ic->pb.buffer);
00495         av_close_input_file(ic);
00496         ic = NULL;
00497         fmt->flags &= ~AVFMT_NOFILE;
00498     }
00499         
00500     d->DestroyMPEG2();
00501     h264_kf_seq->Reset();
00502 }
00503 
00504 static int64_t lsb3full(int64_t lsb, int64_t base_ts, int lsb_bits)
00505 {
00506     int64_t mask = (lsb_bits < 64) ? (1LL<<lsb_bits)-1 : -1LL;
00507     return  ((lsb - base_ts)&mask);
00508 }
00509 
00510 bool AvFormatDecoder::DoRewind(long long desiredFrame, bool discardFrames)
00511 {
00512     VERBOSE(VB_PLAYBACK, LOC + "DoRewind("
00513             <<desiredFrame<<", "
00514             <<( discardFrames ? "do" : "don't" )<<" discard frames)");
00515 
00516     if (recordingHasPositionMap || livetv)
00517         return DecoderBase::DoRewind(desiredFrame, discardFrames);
00518 
00519     // avformat-based seeking
00520     return DoFastForward(desiredFrame, discardFrames);
00521 }
00522 
00523 bool AvFormatDecoder::DoFastForward(long long desiredFrame, bool discardFrames)
00524 {
00525     VERBOSE(VB_PLAYBACK, LOC +
00526             QString("DoFastForward(%1 (%2), %3 discard frames)")
00527             .arg(desiredFrame).arg(framesPlayed)
00528             .arg((discardFrames) ? "do" : "don't"));
00529 
00530     if (recordingHasPositionMap || livetv)
00531         return DecoderBase::DoFastForward(desiredFrame, discardFrames);
00532 
00533     bool oldrawstate = getrawframes;
00534     getrawframes = false;
00535 
00536     AVStream *st = NULL;
00537     for (uint i = 0; i < ic->nb_streams; i++)
00538     {
00539         AVStream *st1 = ic->streams[i];
00540         if (st1 && st1->codec->codec_type == CODEC_TYPE_VIDEO)
00541         {
00542             st = st1;
00543             break;
00544         }
00545     }
00546     if (!st)
00547         return false;
00548 
00549     int64_t frameseekadjust = 0;
00550     AVCodecContext *context = st->codec;
00551 
00552     if (CODEC_IS_MPEG(context->codec_id))
00553         frameseekadjust = maxkeyframedist+1;
00554 
00555     // convert framenumber to normalized timestamp
00556     long double diff = (max(desiredFrame - frameseekadjust, 0LL)) * AV_TIME_BASE;
00557     long long ts = (long long)( diff / fps );
00558     if (av_seek_frame(ic, -1, ts, AVSEEK_FLAG_BACKWARD) < 0)
00559     {
00560         VERBOSE(VB_IMPORTANT, LOC_ERR 
00561                 <<"av_seek_frame(ic, -1, "<<ts<<", 0) -- error");
00562         return false;
00563     }
00564 
00565     // If seeking to start of stream force a DTS and start_time of zero as
00566     // libav sometimes returns the end of the stream instead.
00567     if (desiredFrame <= 1)
00568     {
00569         av_update_cur_dts(ic, st, 0);
00570         ic->start_time = 0;
00571     }
00572 
00573     int normalframes = 0;
00574 
00575     if (st->cur_dts != (int64_t)AV_NOPTS_VALUE)
00576     {
00577 
00578         int64_t adj_cur_dts = st->cur_dts;
00579 
00580         if (ic->start_time != (int64_t)AV_NOPTS_VALUE)
00581         {
00582             int64_t st1 = av_rescale(ic->start_time,
00583                                     st->time_base.den,
00584                                     AV_TIME_BASE * (int64_t)st->time_base.num);
00585             adj_cur_dts = lsb3full(adj_cur_dts, st1, st->pts_wrap_bits);
00586 
00587         }
00588 
00589         long long newts = av_rescale(adj_cur_dts,
00590                                 (int64_t)AV_TIME_BASE * (int64_t)st->time_base.num,
00591                                 st->time_base.den);
00592 
00593         // convert current timestamp to frame number
00594         lastKey = (long long)((newts*(long double)fps)/AV_TIME_BASE);
00595         framesPlayed = lastKey;
00596         framesRead = lastKey;
00597 
00598         normalframes = desiredFrame - framesPlayed;
00599         normalframes = max(normalframes, 0);
00600         no_dts_hack = false;
00601     }
00602     else
00603     {
00604         VERBOSE(VB_GENERAL, "No DTS Seeking Hack!");
00605         no_dts_hack = true;
00606         framesPlayed = desiredFrame;
00607         framesRead = desiredFrame;
00608         normalframes = 0;
00609     }
00610 
00611     SeekReset(lastKey, normalframes, discardFrames, discardFrames);
00612 
00613     if (discardFrames)
00614     {
00615         GetNVP()->SetFramesPlayed(framesPlayed + 1);
00616         GetNVP()->getVideoOutput()->SetFramesPlayed(framesPlayed + 1);
00617     }
00618 
00619     getrawframes = oldrawstate;
00620 
00621     return true;
00622 }
00623 
00624 void AvFormatDecoder::SeekReset(long long newKey, uint skipFrames,
00625                                 bool doflush, bool discardFrames)
00626 {
00627     if (ringBuffer->isDVD())
00628     {
00629         if (ringBuffer->InDVDMenuOrStillFrame() ||
00630             newKey == 0) 
00631             return;
00632     }
00633             
00634     VERBOSE(VB_PLAYBACK, LOC +
00635             QString("SeekReset(%1, %2, %3 flush, %4 discard)")
00636             .arg(newKey).arg(skipFrames)
00637             .arg((doflush) ? "do" : "don't")
00638             .arg((discardFrames) ? "do" : "don't"));
00639 
00640     DecoderBase::SeekReset(newKey, skipFrames, doflush, discardFrames);
00641 
00642     if (doflush)
00643     {
00644         lastapts = 0;
00645         lastvpts = 0;
00646         lastccptsu = 0;
00647         av_read_frame_flush(ic);
00648 
00649         // Only reset the internal state if we're using our seeking,
00650         // not when using libavformat's seeking
00651         if (recordingHasPositionMap || livetv)
00652         {
00653             ic->pb.pos = ringBuffer->GetReadPosition();
00654             ic->pb.buf_ptr = ic->pb.buffer;
00655             ic->pb.buf_end = ic->pb.buffer;
00656             ic->pb.eof_reached = 0;
00657         }
00658 
00659         // Flush the avcodec buffers
00660         VERBOSE(VB_PLAYBACK, LOC + "SeekReset() flushing");
00661         for (uint i = 0; i < ic->nb_streams; i++)
00662         {
00663             AVCodecContext *enc = ic->streams[i]->codec;
00664             if (enc->codec)
00665                 avcodec_flush_buffers(enc);
00666         }
00667         d->ResetMPEG2();
00668     }
00669 
00670     // Discard all the queued up decoded frames
00671     if (discardFrames)
00672         GetNVP()->DiscardVideoFrames(doflush);
00673 
00674     if (doflush)
00675     {
00676         // Free up the stored up packets
00677         while (storedPackets.count() > 0)
00678         {
00679             AVPacket *pkt = storedPackets.first();
00680             storedPackets.removeFirst();
00681             av_free_packet(pkt);
00682             delete pkt;
00683         }
00684 
00685         prevgoppos = 0;
00686         gopset = false;
00687         if (!ringBuffer->isDVD())
00688         {
00689             if (!no_dts_hack)
00690             {
00691                 framesPlayed = lastKey;
00692                 framesRead = lastKey;
00693             }
00694 
00695             no_dts_hack = false;
00696         }
00697     }
00698 
00699     // Skip all the desired number of skipFrames
00700     for (;skipFrames > 0 && !ateof; skipFrames--)
00701     {
00702         GetFrame(0);
00703         if (decoded_video_frame)
00704             GetNVP()->DiscardVideoFrame(decoded_video_frame);
00705     }
00706 }
00707 
00708 void AvFormatDecoder::Reset(bool reset_video_data, bool seek_reset)
00709 {
00710     VERBOSE(VB_PLAYBACK, LOC + QString("Reset(%1, %2)")
00711             .arg(reset_video_data).arg(seek_reset));
00712     if (seek_reset)
00713         SeekReset(0, 0, true, false);
00714 
00715     if (reset_video_data)
00716     {
00717         m_positionMap.clear();
00718         framesPlayed = 0;
00719         framesRead = 0;
00720         seen_gop = false;
00721         seq_count = 0;
00722     }
00723 }
00724 
00725 void AvFormatDecoder::Reset()
00726 {
00727     DecoderBase::Reset();
00728 
00729     if (ringBuffer->isDVD())
00730     {
00731         posmapStarted = false;
00732         SyncPositionMap();
00733     }
00734 
00735 #if 0
00736 // This is causing problems, and may not be needed anymore since
00737 // we do not reuse the same file for different streams anymore. -- dtk
00738 
00739     // mpeg ts reset
00740     if (QString("mpegts") == ic->iformat->name)
00741     {
00742         AVInputFormat *fmt = (AVInputFormat*) av_mallocz(sizeof(AVInputFormat));
00743         memcpy(fmt, ic->iformat, sizeof(AVInputFormat));
00744         fmt->flags |= AVFMT_NOFILE;
00745 
00746         CloseContext();
00747         ic = av_alloc_format_context();
00748         if (!ic)
00749         {
00750             VERBOSE(VB_IMPORTANT, LOC_ERR +
00751                     "Reset(): Could not allocate format context.");
00752             av_free(fmt);
00753             errored = true;
00754             return;
00755         }
00756 
00757         InitByteContext();
00758         ic->streams_changed = HandleStreamChange;
00759         ic->stream_change_data = this;
00760 
00761         char *filename = (char *)(ringBuffer->GetFilename().ascii());
00762         int err = av_open_input_file(&ic, filename, fmt, 0, &params);
00763         if (err < 0)
00764         {
00765             VERBOSE(VB_IMPORTANT, LOC_ERR + "Reset(): "
00766                     "avformat err("<<err<<") on av_open_input_file call.");
00767             av_free(fmt);
00768             errored = true;
00769             return;
00770         }
00771 
00772         fmt->flags &= ~AVFMT_NOFILE;
00773     }
00774 #endif
00775 }
00776 
00777 bool AvFormatDecoder::CanHandle(char testbuf[kDecoderProbeBufferSize], 
00778                                 const QString &filename, int testbufsize)
00779 {
00780     avcodeclock.lock();
00781     av_register_all();
00782     avcodeclock.unlock();
00783 
00784     AVProbeData probe;
00785 
00786     probe.filename = (char *)(filename.ascii());
00787     probe.buf = (unsigned char *)testbuf;
00788     probe.buf_size = testbufsize;
00789 
00790     if (av_probe_input_format(&probe, true))
00791         return true;
00792     return false;
00793 }
00794 
00795 void AvFormatDecoder::InitByteContext(void)
00796 {
00797     int streamed = 0;
00798     if (ringBuffer->isDVD() || ringBuffer->LiveMode())
00799         streamed = 1;
00800 
00801     readcontext.prot = &AVF_RingBuffer_Protocol;
00802     readcontext.flags = 0;
00803     readcontext.is_streamed = streamed;
00804     readcontext.max_packet_size = 0;
00805     readcontext.priv_data = avfRingBuffer;
00806 
00807     if (ringBuffer->isDVD())
00808         ic->pb.buffer_size = 2048;
00809     else
00810         ic->pb.buffer_size = 32768;
00811 
00812     ic->pb.buffer = (unsigned char *)av_malloc(ic->pb.buffer_size);
00813     ic->pb.buf_ptr = ic->pb.buffer;
00814     ic->pb.write_flag = 0;
00815     ic->pb.buf_end = ic->pb.buffer;
00816     ic->pb.opaque = &readcontext;
00817     ic->pb.read_packet = AVF_Read_Packet;
00818     ic->pb.write_packet = AVF_Write_Packet;
00819     ic->pb.seek = AVF_Seek_Packet;
00820     ic->pb.pos = 0;
00821     ic->pb.must_flush = 0;
00822     ic->pb.eof_reached = 0;
00823     ic->pb.is_streamed = streamed;
00824     ic->pb.max_packet_size = 0;
00825 }
00826 
00827 extern "C" void HandleStreamChange(void* data) {
00828     AvFormatDecoder* decoder = (AvFormatDecoder*) data;
00829     int cnt = decoder->ic->nb_streams;
00830 
00831     VERBOSE(VB_PLAYBACK, LOC + "HandleStreamChange(): "
00832             "streams_changed "<<data<<" -- stream count "<<cnt);
00833 
00834     QMutexLocker locker(&avcodeclock);
00835     decoder->SeekReset(0, 0, true, true);
00836     decoder->ScanStreams(false);
00837 }
00838 
00851 int AvFormatDecoder::OpenFile(RingBuffer *rbuffer, bool novideo, 
00852                               char testbuf[kDecoderProbeBufferSize],
00853                               int testbufsize)
00854 {
00855     CloseContext();
00856 
00857     ringBuffer = rbuffer;
00858 
00859     if (avfRingBuffer)
00860         delete avfRingBuffer;
00861     avfRingBuffer = new AVFRingBuffer(rbuffer);
00862 
00863     AVInputFormat *fmt = NULL;
00864     char *filename = (char *)(rbuffer->GetFilename().ascii());
00865 
00866     AVProbeData probe;
00867     probe.filename = filename;
00868     probe.buf = (unsigned char *)testbuf;
00869     probe.buf_size = testbufsize;
00870 
00871     fmt = av_probe_input_format(&probe, true);
00872     if (!fmt)
00873     {
00874         VERBOSE(VB_IMPORTANT, LOC_ERR +
00875                 QString("Probe failed for file: \"%1\".").arg(filename));
00876         return -1;
00877     }
00878 
00879     fmt->flags |= AVFMT_NOFILE;
00880 
00881     ic = av_alloc_format_context();
00882     if (!ic)
00883     {
00884         VERBOSE(VB_IMPORTANT, LOC_ERR +
00885                 "Could not allocate format context.");
00886         return -1;
00887     }
00888 
00889     InitByteContext();
00890 
00891     int err = av_open_input_file(&ic, filename, fmt, 0, &params);
00892     if (err < 0)
00893     {
00894         VERBOSE(VB_IMPORTANT, LOC_ERR
00895                 <<"avformat err("<<err<<") on av_open_input_file call.");
00896         return -1;
00897     }
00898 
00899     int ret = -1;
00900     if (ringBuffer->isDVD())
00901     {
00902         AVPacket pkt1;
00903         while (ic->nb_streams == 0)
00904             ret = av_read_frame(ic,&pkt1);
00905         av_free_packet(&pkt1);
00906         ringBuffer->Seek(0, SEEK_SET);
00907         ringBuffer->DVD()->IgnoreStillOrWait(false);
00908     }
00909     else
00910     {
00911         QMutexLocker locker(&avcodeclock);
00912         ret = av_find_stream_info(ic);
00913     }
00914 
00915     if (ret < 0)
00916     {
00917         VERBOSE(VB_IMPORTANT, LOC_ERR + "Could not find codec parameters. " +
00918                 QString("file was \"%1\".").arg(filename));
00919         av_close_input_file(ic);
00920         ic = NULL;
00921         return -1;
00922     }
00923     ic->streams_changed = HandleStreamChange;
00924     ic->stream_change_data = this;
00925 
00926     fmt->flags &= ~AVFMT_NOFILE;
00927 
00928     if (!ringBuffer->isDVD() && !livetv)
00929         av_estimate_timings(ic, 0);
00930 
00931     // Scan for the initial A/V streams
00932     ret = ScanStreams(novideo);
00933     if (-1 == ret)
00934         return ret;
00935 
00936     AutoSelectTracks(); // This is needed for transcoder
00937 
00938     {
00939         int initialAudio = -1, initialVideo = -1;
00940         if (itv || (itv = GetNVP()->GetInteractiveTV()))
00941             itv->GetInitialStreams(initialAudio, initialVideo);
00942         if (initialAudio >= 0)
00943             SetAudioByComponentTag(initialAudio);
00944         if (initialVideo >= 0)
00945             SetVideoByComponentTag(initialVideo);
00946     }
00947 
00948     // Try to get a position map from the recorder if we don't have one yet.
00949     if (!recordingHasPositionMap)
00950     {
00951         if ((m_playbackinfo) || livetv || watchingrecording)
00952         {
00953             recordingHasPositionMap |= SyncPositionMap();
00954             if (recordingHasPositionMap && !livetv && !watchingrecording)
00955             {
00956                 hasFullPositionMap = true;
00957                 gopset = true;
00958             }
00959         }
00960     }
00961 
00962     // If we don't have a position map, set up ffmpeg for seeking
00963     if (!recordingHasPositionMap)
00964     {
00965         VERBOSE(VB_PLAYBACK, LOC +
00966                 "Recording has no position -- using libavformat seeking.");
00967         int64_t dur = ic->duration / (int64_t)AV_TIME_BASE;
00968 
00969         if (dur > 0)
00970         {
00971             GetNVP()->SetFileLength((int)(dur), (int)(dur * fps));
00972         }
00973         else
00974         {
00975             // the pvr-250 seems to overreport the bitrate by * 2
00976             float bytespersec = (float)bitrate / 8 / 2;
00977             float secs = ringBuffer->GetRealFileSize() * 1.0 / bytespersec;
00978             GetNVP()->SetFileLength((int)(secs), (int)(secs * fps));
00979         }
00980 
00981         // we will not see a position map from db or remote encoder,
00982         // set the gop interval to 15 frames.  if we guess wrong, the
00983         // auto detection will change it.
00984         keyframedist = 15;
00985         positionMapType = MARK_GOP_START;
00986 
00987         if (!strcmp(fmt->name, "avi"))
00988         {
00989             // avi keyframes are too irregular
00990             keyframedist = 1;
00991             positionMapType = MARK_GOP_BYFRAME;
00992         }
00993 
00994         dontSyncPositionMap = true;
00995     }
00996 
00997     // Don't build a seek index for MythTV files, the user needs to
00998     // use mythcommflag to build a proper MythTV position map for these.
00999     if (livetv || watchingrecording)
01000         ic->build_index = 0;
01001 
01002     dump_format(ic, 0, filename, 0);
01003 
01004     // print some useful information if playback debugging is on
01005     if (hasFullPositionMap)
01006         VERBOSE(VB_PLAYBACK, LOC + "Position map found");
01007     else if (recordingHasPositionMap)
01008         VERBOSE(VB_PLAYBACK, LOC + "Partial position map found");
01009     VERBOSE(VB_PLAYBACK, LOC +
01010             QString("Successfully opened decoder for file: "
01011                     "\"%1\". novideo(%2)").arg(filename).arg(novideo));
01012 
01013     // Return true if recording has position map
01014     return recordingHasPositionMap;
01015 }
01016 
01017 static float normalized_fps(AVStream *stream, AVCodecContext *enc)
01018 {
01019     float fps = 1.0f / av_q2d(enc->time_base);
01020 
01021     // Some formats report fps waaay too high. (wrong time_base)
01022     if (fps > 121.0f && (enc->time_base.den > 10000) &&
01023         (enc->time_base.num == 1))
01024     {
01025         enc->time_base.num = 1001;  // seems pretty standard
01026         if (av_q2d(enc->time_base) > 0)
01027             fps = 1.0f / av_q2d(enc->time_base);
01028     }
01029     // If it's still wonky, try the container's time_base
01030     if (fps > 121.0f || fps < 3.0f)
01031     {
01032         float tmpfps = 1.0f / av_q2d(stream->time_base);
01033         if (tmpfps > 20 && tmpfps < 70)
01034             fps = tmpfps;
01035     }
01036 
01037     // If it is still out of range, just assume NTSC...
01038     fps = (fps > 121.0f) ? (30000.0f / 1001.0f) : fps;
01039     return fps;
01040 }
01041 
01042 void AvFormatDecoder::InitVideoCodec(AVStream *stream, AVCodecContext *enc,
01043                                      bool selectedStream)
01044 {
01045     VERBOSE(VB_PLAYBACK, LOC
01046             <<"InitVideoCodec() "<<enc<<" "
01047             <<"id("<<codec_id_string(enc->codec_id)
01048             <<") type ("<<codec_type_string(enc->codec_type)
01049             <<").");
01050 
01051     float aspect_ratio = 0.0;
01052 
01053     if (ringBuffer->isDVD())
01054         directrendering = false;
01055 
01056     if (selectedStream)
01057     {
01058         fps = normalized_fps(stream, enc);
01059 
01060         if (enc->sample_aspect_ratio.num == 0)
01061             aspect_ratio = 0.0f;
01062         else
01063             aspect_ratio = av_q2d(enc->sample_aspect_ratio) *
01064                 enc->width / enc->height;
01065 
01066         if (aspect_ratio <= 0.0f || aspect_ratio > 6.0f)
01067             aspect_ratio = (float)enc->width / (float)enc->height;
01068 
01069         current_width = enc->width;
01070         current_height = enc->height;
01071         current_aspect = aspect_ratio;
01072     }
01073 
01074     enc->opaque = (void *)this;
01075     enc->get_buffer = avcodec_default_get_buffer;
01076     enc->release_buffer = avcodec_default_release_buffer;
01077     enc->draw_horiz_band = NULL;
01078     enc->slice_flags = 0;
01079 
01080     enc->error_resilience = FF_ER_COMPLIANT;
01081     enc->workaround_bugs = FF_BUG_AUTODETECT;
01082     enc->error_concealment = FF_EC_GUESS_MVS | FF_EC_DEBLOCK;
01083     enc->idct_algo = FF_IDCT_AUTO;
01084     enc->debug = 0;
01085     enc->rate_emu = 0;
01086     enc->error_rate = 0;
01087 
01088     AVCodec *codec = avcodec_find_decoder(enc->codec_id);    
01089 
01090     if (selectedStream &&
01091         !gContext->GetNumSetting("DecodeExtraAudio", 0) &&
01092         codec && !CODEC_IS_HW_ACCEL(codec->id))
01093     {
01094         SetLowBuffers(false);
01095     }
01096 
01097     if (codec && (codec->id == CODEC_ID_MPEG2VIDEO_XVMC ||
01098                   codec->id == CODEC_ID_MPEG2VIDEO_XVMC_VLD))
01099     {
01100         enc->flags |= CODEC_FLAG_EMU_EDGE;
01101         enc->get_buffer = get_avf_buffer_xvmc;
01102         enc->release_buffer = release_avf_buffer_xvmc;
01103         enc->draw_horiz_band = render_slice_xvmc;
01104         enc->slice_flags = SLICE_FLAG_CODED_ORDER |
01105             SLICE_FLAG_ALLOW_FIELD;
01106         if (selectedStream)
01107             directrendering = true;
01108     }
01109     else if (codec && codec->id == CODEC_ID_MPEG2VIDEO_DVDV)
01110     {
01111         enc->flags           |= (CODEC_FLAG_EMU_EDGE  |
01112 //                                 CODEC_FLAG_TRUNCATED | 
01113                                  CODEC_FLAG_LOW_DELAY |
01114                                  CODEC_FLAG2_FAST);
01115         enc->get_buffer       = get_avf_buffer;
01116         enc->release_buffer   = release_avf_buffer;
01117         enc->draw_horiz_band  = NULL;
01118         directrendering      |= selectedStream;
01119     }
01120     else if (codec && codec->capabilities & CODEC_CAP_DR1)
01121     {
01122         enc->flags          |= CODEC_FLAG_EMU_EDGE;
01123         enc->get_buffer      = get_avf_buffer;
01124         enc->release_buffer  = release_avf_buffer;
01125         enc->draw_horiz_band = NULL;
01126         if (selectedStream)
01127             directrendering = true;
01128     }
01129 
01130     if (selectedStream)
01131     {
01132         uint width  = enc->width;
01133         uint height = enc->height;
01134 
01135         if (width == 0 && height == 0)
01136         {
01137             VERBOSE(VB_PLAYBACK, LOC + "InitVideoCodec "
01138                     "invalid dimensions, resetting decoder.");
01139             width = 640;
01140             height = 480;
01141             fps = 29.97;
01142             aspect_ratio = 4.0 / 3;
01143         }
01144 
01145         GetNVP()->SetVideoParams(width, height, fps,
01146                                  keyframedist, aspect_ratio, kScan_Detect, 
01147                                  dvd_video_codec_changed);
01148     }
01149 }
01150 
01151 #if defined(USING_XVMC) || defined(USING_DVDV)
01152 static int mpeg_version(int codec_id)
01153 {
01154     switch (codec_id)
01155     {
01156         case CODEC_ID_MPEG1VIDEO:
01157             return 1;
01158         case CODEC_ID_MPEG2VIDEO:
01159         case CODEC_ID_MPEG2VIDEO_XVMC:
01160         case CODEC_ID_MPEG2VIDEO_XVMC_VLD:
01161         case CODEC_ID_MPEG2VIDEO_DVDV:
01162             return 2;
01163         case CODEC_ID_H263:
01164             return 3;
01165         case CODEC_ID_MPEG4:
01166             return 4;
01167         case CODEC_ID_H264:
01168             return 5;
01169     }
01170     return 0;
01171 }
01172 #endif // defined(USING_XVMC) || defined(USING_DVDV)
01173 
01174 #ifdef USING_XVMC
01175 static int xvmc_pixel_format(enum PixelFormat pix_fmt)
01176 {
01177     (void) pix_fmt;
01178     int xvmc_chroma = XVMC_CHROMA_FORMAT_420;
01179 #if 0
01180 // We don't support other chromas yet
01181     if (PIX_FMT_YUV420P == pix_fmt)
01182         xvmc_chroma = XVMC_CHROMA_FORMAT_420;
01183     else if (PIX_FMT_YUV422P == pix_fmt)
01184         xvmc_chroma = XVMC_CHROMA_FORMAT_422;
01185     else if (PIX_FMT_YUV420P == pix_fmt)
01186         xvmc_chroma = XVMC_CHROMA_FORMAT_444;
01187 #endif
01188     return xvmc_chroma;
01189 }
01190 #endif // USING_XVMC
01191 
01192 void default_captions(sinfo_vec_t *tracks, int av_index)
01193 {
01194     if (tracks[kTrackTypeCC608].empty())
01195     {
01196         tracks[kTrackTypeCC608].push_back(StreamInfo(av_index, 0, 0, 1));
01197         tracks[kTrackTypeCC608].push_back(StreamInfo(av_index, 0, 2, 3));
01198     }
01199 }
01200 
01201 // CC Parity checking 
01202 // taken from xine-lib libspucc
01203 
01204 static int cc608_parity(uint8_t byte)
01205 {
01206     int ones = 0;
01207 
01208     for (int i = 0; i < 7; i++)
01209     {
01210         if (byte & (1 << i))
01211             ones++;
01212     }
01213 
01214     return ones & 1;
01215 }
01216 
01217 // CC Parity checking 
01218 // taken from xine-lib libspucc
01219 
01220 static void cc608_build_parity_table(int *parity_table)
01221 {
01222     uint8_t byte;
01223     int parity_v;
01224     for (byte = 0; byte <= 127; byte++)
01225     {
01226         parity_v = cc608_parity(byte);
01227         /* CC uses odd parity (i.e., # of 1's in byte is odd.) */
01228         parity_table[byte] = parity_v;
01229         parity_table[byte | 0x80] = !parity_v;
01230     }
01231 }
01232 
01233 // CC Parity checking 
01234 // taken from xine-lib libspucc
01235 
01236 static int cc608_good_parity(const int *parity_table, uint16_t data)
01237 {
01238     int ret = parity_table[data & 0xff] && parity_table[(data & 0xff00) >> 8];
01239     if (!ret)
01240     {
01241         VERBOSE(VB_VBI, QString("VBI: Bad parity in EIA-608 data (%1)")
01242                 .arg(data,0,16));
01243     }
01244     return ret;
01245 }
01246 
01247 void AvFormatDecoder::ScanATSCCaptionStreams(int av_index)
01248 {
01249     tracks[kTrackTypeCC608].clear();
01250     tracks[kTrackTypeCC708].clear();
01251 
01252     // Figure out languages of ATSC captions
01253     if (!ic->cur_pmt_sect)
01254     {
01255         default_captions(tracks, av_index);
01256         return;
01257     }
01258 
01259     const PESPacket pes = PESPacket::ViewData(ic->cur_pmt_sect);
01260     const PSIPTable psip(pes);
01261     const ProgramMapTable pmt(psip);
01262 
01263     uint i;
01264     for (i = 0; i < pmt.StreamCount(); i++)
01265     {
01266         // MythTV remaps OpenCable Video to normal video during recording
01267         // so "dvb" is the safest choice for system info type, since this
01268         // will ignore other uses of the same stream id in DVB countries.
01269         if (pmt.IsVideo(i, "dvb"))
01270             break;
01271     }
01272 
01273     if (!pmt.IsVideo(i, "dvb"))
01274     {
01275         default_captions(tracks, av_index);
01276         return;
01277     }
01278 
01279     const desc_list_t desc_list = MPEGDescriptor::ParseOnlyInclude(
01280         pmt.StreamInfo(i), pmt.StreamInfoLength(i),
01281         DescriptorID::caption_service);
01282 
01283     map<int,uint> lang_cc_cnt[2];
01284     for (uint j = 0; j < desc_list.size(); j++)
01285     {
01286         const CaptionServiceDescriptor csd(desc_list[j]);
01287         for (uint k = 0; k < csd.ServicesCount(); k++)
01288         {
01289             int lang = csd.CanonicalLanguageKey(k);
01290             int type = csd.Type(k) ? 1 : 0;
01291             int lang_indx = lang_cc_cnt[type][lang];
01292             lang_cc_cnt[type][lang]++;
01293             if (type)
01294             {
01295                 StreamInfo si(av_index, lang, lang_indx,
01296                               csd.CaptionServiceNumber(k),
01297                               csd.EasyReader(k),
01298                               csd.WideAspectRatio(k));
01299 
01300                 tracks[kTrackTypeCC708].push_back(si);
01301 
01302                 VERBOSE(VB_PLAYBACK, LOC + QString(
01303                             "EIA-708 caption service #%1 "
01304                             "is in the %2 language.")
01305                         .arg(csd.CaptionServiceNumber(k))
01306                         .arg(iso639_key_toName(lang)));
01307             }
01308             else
01309             {
01310                 int line21 = csd.Line21Field(k) ? 2 : 1;
01311                 StreamInfo si(av_index, lang, lang_indx, line21);
01312                 tracks[kTrackTypeCC608].push_back(si);
01313 
01314                 VERBOSE(VB_PLAYBACK, LOC + QString(
01315                             "EIA-608 caption %1 is in the %2 language.")
01316                         .arg(line21).arg(iso639_key_toName(lang)));
01317             }
01318         }
01319     }
01320 
01321     default_captions(tracks, av_index);
01322 }
01323 
01324 void AvFormatDecoder::ScanTeletextCaptions(int av_index)
01325 {
01326     // ScanStreams() calls tracks[kTrackTypeTeletextCaptions].clear()
01327     if (!ic->cur_pmt_sect || tracks[kTrackTypeTeletextCaptions].size())
01328         return;
01329 
01330     const PESPacket pes = PESPacket::ViewData(ic->cur_pmt_sect);
01331     const PSIPTable psip(pes);
01332     const ProgramMapTable pmt(psip);
01333 
01334     for (uint i = 0; i < pmt.StreamCount(); i++)
01335     {
01336         if (pmt.StreamType(i) != 6)
01337             continue;
01338 
01339         const desc_list_t desc_list = MPEGDescriptor::ParseOnlyInclude(
01340             pmt.StreamInfo(i), pmt.StreamInfoLength(i),
01341             DescriptorID::teletext);
01342 
01343         for (uint j = 0; j < desc_list.size(); j++)
01344         {
01345             const TeletextDescriptor td(desc_list[j]);
01346             for (uint k = 0; k < td.StreamCount(); k++)
01347             {
01348                 int type = td.TeletextType(k);
01349                 if (type != 2)
01350                     continue;
01351 
01352                 int language = td.CanonicalLanguageKey(k);
01353                 int magazine = td.TeletextMagazineNum(k)?:8;
01354                 int pagenum  = td.TeletextPageNum(k);
01355                 int lang_idx = (magazine << 8) | pagenum;
01356 
01357                 StreamInfo si(av_index, language, lang_idx, 0);
01358                 tracks[kTrackTypeTeletextCaptions].push_back(si);
01359 
01360                 VERBOSE(VB_PLAYBACK, LOC + QString(
01361                             "Teletext caption #%1 is in the %2 language "
01362                             "on page %3 %4.")
01363                         .arg(k).arg(iso639_key_toName(language))
01364                         .arg(magazine).arg(pagenum));
01365             }
01366         }
01367 
01368         // Assume there is only one multiplexed teletext stream in PMT..
01369         if (tracks[kTrackTypeTeletextCaptions].size())
01370             break;
01371     }
01372 }
01373 
01378 void AvFormatDecoder::ScanDSMCCStreams(void)
01379 {
01380     if (!ic->cur_pmt_sect)
01381         return;
01382 
01383     if (!itv && ! (itv = GetNVP()->GetInteractiveTV()))
01384         return;
01385 
01386     const PESPacket pes = PESPacket::ViewData(ic->cur_pmt_sect);
01387     const PSIPTable psip(pes);
01388     const ProgramMapTable pmt(psip);
01389 
01390     for (uint i = 0; i < pmt.StreamCount(); i++)
01391     {
01392         if (! StreamID::IsObjectCarousel(pmt.StreamType(i)))
01393             continue;
01394 
01395         const desc_list_t desc_list = MPEGDescriptor::ParseOnlyInclude(
01396             pmt.StreamInfo(i), pmt.StreamInfoLength(i),
01397             DescriptorID::data_broadcast_id);
01398 
01399         for (uint j = 0; j < desc_list.size(); j++)
01400         {
01401             const unsigned char *desc = desc_list[j];
01402             desc++; // Skip tag
01403             uint length = *desc++;
01404             const unsigned char *endDesc = desc+length;
01405             uint dataBroadcastId = desc[0]<<8 | desc[1];
01406             if (dataBroadcastId != 0x0106) // ETSI/UK Profile
01407                 continue;
01408             desc += 2; // Skip data ID
01409             while (desc != endDesc)
01410             {
01411                 uint appTypeCode = desc[0]<<8 | desc[1];
01412                 desc += 3; // Skip app type code and boot priority hint
01413                 uint appSpecDataLen = *desc++;
01414                 if (appTypeCode == 0x101) // UK MHEG profile
01415                 {
01416                     const unsigned char *subDescEnd = desc + appSpecDataLen;
01417                     while (desc < subDescEnd)
01418                     {
01419                         uint sub_desc_tag = *desc++;
01420                         uint sub_desc_len = *desc++;
01421                         if (sub_desc_tag == 1) // Network boot info sub-descriptor.
01422                             itv->SetNetBootInfo(desc, sub_desc_len);
01423                         desc += sub_desc_len;
01424                     }
01425                 }
01426                 else desc += appSpecDataLen;
01427             }
01428         }
01429     }
01430 }
01431 
01432 int AvFormatDecoder::ScanStreams(bool novideo)
01433 {
01434     int scanerror = 0;
01435     bitrate = 0;
01436     fps = 0;
01437 
01438     tracks[kTrackTypeAudio].clear();
01439     tracks[kTrackTypeSubtitle].clear();
01440     tracks[kTrackTypeTeletextCaptions].clear();
01441     selectedVideoIndex = -1;
01442 
01443     map<int,uint> lang_sub_cnt;
01444     map<int,uint> lang_aud_cnt;
01445 
01446     if (ringBuffer->isDVD() &&
01447         ringBuffer->DVD()->AudioStreamsChanged())
01448     {
01449         ringBuffer->DVD()->AudioStreamsChanged(false);
01450         RemoveAudioStreams();
01451     }
01452 
01453     for (uint i = 0; i < ic->nb_streams; i++)
01454     {
01455         AVCodecContext *enc = ic->streams[i]->codec;
01456         VERBOSE(VB_PLAYBACK, LOC +
01457                 QString("Stream #%1, has id 0x%2 codec id %3, "
01458                         "type %4, bitrate %5 at 0x")
01459                 .arg(i).arg((int)ic->streams[i]->id)
01460                 .arg(codec_id_string(enc->codec_id))
01461                 .arg(codec_type_string(enc->codec_type))
01462                 .arg(enc->bit_rate)
01463                 <<((void*)ic->streams[i]));
01464 
01465         switch (enc->codec_type)
01466         {
01467             case CODEC_TYPE_VIDEO:
01468             {
01469                 //assert(enc->codec_id);
01470                 if (!enc->codec_id)
01471                 {
01472                     VERBOSE(VB_IMPORTANT,
01473                             LOC + QString("Stream #%1 has an unknown video "
01474                                           "codec id, skipping.").arg(i));
01475                     continue;
01476                 }
01477 
01478                 // HACK -- begin
01479                 // ffmpeg is unable to compute H.264 bitrates in mpegts?
01480                 if (CODEC_ID_H264 == enc->codec_id && enc->bit_rate == 0)
01481                     enc->bit_rate = 500000;
01482                 // HACK -- end
01483 
01484                 bitrate += enc->bit_rate;
01485                 if (novideo)
01486                     break;
01487 
01488                 // HACK -- ignore CODEC_ID_MPEG1VIDEO if the bit_rate
01489                 // is 0.  CBS/KTVT recordings seem to be screwing up.
01490                 if (enc->codec_id == CODEC_ID_MPEG1VIDEO &&
01491                     enc->bit_rate == 0)
01492                 {
01493                     VERBOSE(VB_IMPORTANT,
01494                             LOC + QString("Stream #%1 is MPEG1VIDEO with 0 bit rate, skipping.").arg(i));
01495                     continue;
01496                 }
01497 
01498                 d->DestroyMPEG2();
01499                 h264_kf_seq->Reset();
01500 
01501                 uint width  = max(enc->width, 16);
01502                 uint height = max(enc->height, 16);
01503                 VideoDisplayProfile vdp;
01504                 vdp.SetInput(QSize(width, height));
01505                 QString dec = vdp.GetDecoder();
01506                 uint thread_count = vdp.GetMaxCPUs();
01507                 VERBOSE(VB_PLAYBACK, QString("Using %1 CPUs for decoding")
01508                         .arg(ENABLE_THREADS ? thread_count : 1));
01509 
01510                 if (ENABLE_THREADS && thread_count > 1)
01511                 {
01512                     avcodec_thread_init(enc, thread_count);
01513                     enc->thread_count = thread_count;
01514                 }
01515 
01516                 bool handled = false;
01517 #ifdef USING_XVMC
01518                 if (!using_null_videoout && mpeg_version(enc->codec_id))
01519                 {
01520                     // HACK -- begin
01521                     // Force MPEG2 decoder on MPEG1 streams.
01522                     // Needed for broken transmitters which mark
01523                     // MPEG2 streams as MPEG1 streams, and should
01524                     // be harmless for unbroken ones.
01525                     if (CODEC_ID_MPEG1VIDEO == enc->codec_id)
01526                         enc->codec_id = CODEC_ID_MPEG2VIDEO;
01527                     // HACK -- end
01528 
01529                     bool force_xv = false;
01530                     if (ringBuffer && ringBuffer->isDVD())
01531                     {
01532                         if (dec.left(4) == "xvmc")
01533                             dvd_xvmc_enabled = true;
01534                                 
01535                         if (ringBuffer->InDVDMenuOrStillFrame() &&
01536                             dvd_xvmc_enabled)
01537                         {
01538                             force_xv = true;
01539                             enc->pix_fmt = PIX_FMT_YUV420P;
01540                         }
01541                     }
01542 
01543                     MythCodecID mcid;
01544                     mcid = VideoOutputXv::GetBestSupportedCodec(
01545                         /* disp dim     */ width, height,
01546                         /* osd dim      */ /*enc->width*/ 0, /*enc->height*/ 0,
01547                         /* mpeg type    */ mpeg_version(enc->codec_id),
01548                         /* xvmc pix fmt */ xvmc_pixel_format(enc->pix_fmt),
01549                         /* test surface */ kCodec_NORMAL_END > video_codec_id,
01550                         /* force_xv     */ force_xv);
01551                     bool vcd, idct, mc;
01552                     enc->codec_id = (CodecID)
01553                         myth2av_codecid(mcid, vcd, idct, mc);
01554 
01555                     if (ringBuffer && ringBuffer->isDVD() && 
01556                         (mcid == video_codec_id) &&
01557                         dvd_video_codec_changed)
01558                     {
01559                         dvd_video_codec_changed = false;
01560                         dvd_xvmc_enabled = false;
01561                     }
01562 
01563                     video_codec_id = mcid;
01564                     if (!force_xv && kCodec_NORMAL_END < mcid && kCodec_STD_XVMC_END > mcid)
01565                     {
01566                         enc->pix_fmt = (idct) ?
01567                             PIX_FMT_XVMC_MPEG2_IDCT : PIX_FMT_XVMC_MPEG2_MC;
01568                     }
01569                     handled = true;
01570                 }
01571 #elif USING_DVDV
01572                 if (!using_null_videoout && mpeg_version(enc->codec_id))
01573                 {
01574                     MythCodecID mcid;
01575                     mcid = VideoOutputQuartz::GetBestSupportedCodec(
01576                         /* disp dim     */ width, height,
01577                         /* osd dim      */ 0, 0,
01578                         /* mpeg type    */ mpeg_version(enc->codec_id),
01579                         /* pixel format */
01580                         (PIX_FMT_YUV420P == enc->pix_fmt) ? FOURCC_I420 : 0);
01581 
01582                     enc->codec_id = (CodecID) myth2av_codecid(mcid);
01583                     video_codec_id = mcid;
01584 
01585                     handled = true;
01586                 }
01587 #endif // USING_XVMC || USING_DVDV
01588 
01589                 if (!handled)
01590                 {
01591                     if (CODEC_ID_H264 == enc->codec_id)
01592                         video_codec_id = kCodec_H264;
01593                     else
01594                         video_codec_id = kCodec_MPEG2; // default to MPEG2
01595                 }
01596 
01597                 if (enc->codec)
01598                 {
01599                     VERBOSE(VB_IMPORTANT, LOC
01600                             <<"Warning, video codec "<<enc<<" "
01601                             <<"id("<<codec_id_string(enc->codec_id)
01602                             <<") type ("<<codec_type_string(enc->codec_type)
01603                             <<") already open.");
01604                 }
01605 
01606                 // Initialize alternate decoders when needed...
01607                 if (((dec == "libmpeg2") &&
01608                      (CODEC_ID_MPEG1VIDEO == enc->codec_id ||
01609                       CODEC_ID_MPEG2VIDEO == enc->codec_id)) ||
01610                     (CODEC_ID_MPEG2VIDEO_DVDV == enc->codec_id))
01611                 {
01612                     d->InitMPEG2(dec);
01613                     
01614                     // fallback if we can't handle this resolution
01615                     if (!d->SetVideoSize(QSize(width, height)))
01616                     {
01617                         VERBOSE(VB_IMPORTANT, LOC_WARN +
01618                                 "Failed to setup DVDV decoder, falling "
01619                                 "back to software decoding");
01620 
01621                         enc->codec_id  = CODEC_ID_MPEG2VIDEO;
01622                         video_codec_id = kCodec_MPEG2;
01623                     }
01624                 }
01625 
01626                 enc->decode_cc_dvd  = decode_cc_dvd;
01627 
01628                 // Set the default stream to the stream
01629                 // that is found first in the PMT
01630                 if (selectedVideoIndex < 0)
01631                 {
01632                     selectedVideoIndex = i;
01633                 }
01634 
01635                 InitVideoCodec(ic->streams[i], enc,
01636                                selectedVideoIndex == (int) i);
01637                 
01638                 ScanATSCCaptionStreams(i);
01639                 
01640                 VERBOSE(VB_PLAYBACK, LOC + 
01641                         QString("Using %1 for video decoding")
01642                         .arg(GetCodecDecoderName()));
01643 
01644                 break;
01645             }
01646             case CODEC_TYPE_AUDIO:
01647             {
01648                 if (enc->codec)
01649                 {
01650                     VERBOSE(VB_IMPORTANT, LOC
01651                             <<"Warning, audio codec "<<enc
01652                             <<" id("<<codec_id_string(enc->codec_id)
01653                             <<") type ("<<codec_type_string(enc->codec_type)
01654                             <<") already open, leaving it alone.");
01655                 }
01656                 //assert(enc->codec_id);
01657                 VERBOSE(VB_GENERAL, LOC + QString("codec %1 has %2 channels")
01658                         .arg(codec_id_string(enc->codec_id))
01659                         .arg(enc->channels));
01660 
01661 #if 0
01662                 // HACK MULTICHANNEL DTS passthru disabled for multichannel,
01663                 // dont know how to handle this
01664                 // HACK BEGIN REALLY UGLY HACK FOR DTS PASSTHRU
01665                 if (enc->codec_id == CODEC_ID_DTS)
01666                 {
01667                     enc->sample_rate = 48000;
01668                     enc->channels = 2;
01669                     // enc->bit_rate = what??;
01670                 }
01671                 // HACK END REALLY UGLY HACK FOR DTS PASSTHRU
01672 #endif
01673 
01674                 bitrate += enc->bit_rate;
01675                 break;
01676             }
01677             case CODEC_TYPE_SUBTITLE:
01678             {
01679                 bitrate += enc->bit_rate;
01680                 VERBOSE(VB_PLAYBACK, LOC + QString("subtitle codec (%1)")
01681                         .arg(codec_type_string(enc->codec_type)));
01682                 break;
01683             }
01684             case CODEC_TYPE_DATA:
01685             {
01686                 ScanTeletextCaptions(i);
01687                 bitrate += enc->bit_rate;
01688                 VERBOSE(VB_PLAYBACK, LOC + QString("data codec (%1)")
01689                         .arg(codec_type_string(enc->codec_type)));
01690                 break;
01691             }
01692             default:
01693             {
01694                 bitrate += enc->bit_rate;
01695                 VERBOSE(VB_PLAYBACK, LOC + QString("Unknown codec type (%1)")
01696                         .arg(codec_type_string(enc->codec_type)));
01697                 break;
01698             }
01699         }
01700 
01701         if (enc->codec_type != CODEC_TYPE_AUDIO && 
01702             enc->codec_type != CODEC_TYPE_VIDEO &&
01703             enc->codec_type != CODEC_TYPE_SUBTITLE)
01704             continue;
01705 
01706         VERBOSE(VB_PLAYBACK, LOC + QString("Looking for decoder for %1")
01707                 .arg(codec_id_string(enc->codec_id)));
01708         AVCodec *codec = avcodec_find_decoder(enc->codec_id);
01709         if (!codec)
01710         {
01711             VERBOSE(VB_IMPORTANT, LOC_ERR + 
01712                     QString("Could not find decoder for "
01713                             "codec (%1), ignoring.")
01714                     .arg(codec_id_string(enc->codec_id)));
01715 
01716             // Nigel's bogus codec-debug. Dump the list of codecs & decoders,
01717             // and have one last attempt to find a decoder. This is usually
01718             // only caused by build problems, where libavcodec needs a rebuild
01719             if (print_verbose_messages & VB_LIBAV)
01720             {
01721                 AVCodec *p = first_avcodec;
01722                 int      i = 1;
01723                 while (p)
01724                 {
01725                     if (p->name[0] != '\0')  printf("Codec %s:", p->name);
01726                     else                     printf("Codec %d, null name,", i);
01727                     if (p->decode == NULL)   puts("decoder is null");
01728           
01729                     if (p->id == enc->codec_id)
01730                     {   codec = p; break;    }
01731 
01732                     printf("Codec %d != %d\n", p->id, enc->codec_id);
01733                     p = p->next;
01734                     ++i;
01735                 }
01736             }
01737             if (!codec)
01738                 continue;
01739         }
01740 
01741         if (!enc->codec)
01742         {
01743             QMutexLocker locker(&avcodeclock);
01744 
01745             int open_val = avcodec_open(enc, codec);
01746             if (open_val < 0)
01747             {
01748                 VERBOSE(VB_IMPORTANT, LOC_ERR
01749                         <<"Could not open codec "<<enc<<", "
01750                         <<"id("<<codec_id_string(enc->codec_id)<<") "
01751                         <<"type("<<codec_type_string(enc->codec_type)<<") "
01752                         <<"aborting. reason "<<open_val);
01753                 //av_close_input_file(ic); // causes segfault
01754                 ic = NULL;
01755                 scanerror = -1;
01756                 break;
01757             }
01758             else
01759             {
01760                 VERBOSE(VB_GENERAL, LOC + "Opened codec "<<enc<<", "
01761                         <<"id("<<codec_id_string(enc->codec_id)<<") "
01762                         <<"type("<<codec_type_string(enc->codec_type)<<")");
01763             }
01764         }
01765 
01766         if (enc->codec_type == CODEC_TYPE_SUBTITLE)
01767         {
01768             int lang = get_canonical_lang(ic->streams[i]->language);
01769             int lang_indx = lang_aud_cnt[lang];
01770             lang_indx = lang_sub_cnt[lang];
01771             lang_sub_cnt[lang]++;
01772 
01773             tracks[kTrackTypeSubtitle].push_back(
01774                 StreamInfo(i, lang, lang_indx, ic->streams[i]->id));
01775 
01776             VERBOSE(VB_PLAYBACK, LOC + QString(
01777                         "Subtitle track #%1 is A/V stream #%2 "
01778                         "and is in the %3 language(%4).")
01779                     .arg(tracks[kTrackTypeSubtitle].size()).arg(i)
01780                     .arg(iso639_key_toName(lang)).arg(lang));
01781         }
01782 
01783         if (enc->codec_type == CODEC_TYPE_AUDIO)
01784         {
01785             int lang = get_canonical_lang(ic->streams[i]->language);
01786             int lang_indx = lang_aud_cnt[lang];
01787             lang_aud_cnt[lang]++;
01788 
01789             if (ic->streams[i]->codec->avcodec_dual_language)
01790             {
01791                 tracks[kTrackTypeAudio].push_back(
01792                     StreamInfo(i, lang, lang_indx, ic->streams[i]->id, 0));
01793                 tracks[kTrackTypeAudio].push_back(
01794                     StreamInfo(i, lang, lang_indx, ic->streams[i]->id, 1));
01795             }
01796             else
01797             {
01798                 tracks[kTrackTypeAudio].push_back(
01799                     StreamInfo(i, lang, lang_indx, ic->streams[i]->id));
01800             }
01801 
01802             VERBOSE(VB_AUDIO, LOC + QString(
01803                         "Audio Track #%1 is A/V stream #%2 "
01804                         "and has %3 channels in the %4 language(%5).")
01805                     .arg(tracks[kTrackTypeAudio].size()).arg(i)
01806                     .arg(enc->channels)
01807                     .arg(iso639_key_toName(lang)).arg(lang));
01808         }
01809     }
01810 
01811     if (bitrate > 0)
01812     {
01813         bitrate = (bitrate + 999) / 1000;
01814         if (ringBuffer)
01815             ringBuffer->UpdateRawBitrate(bitrate);
01816     }
01817 
01818     if (ringBuffer && ringBuffer->isDVD())
01819     {
01820         if (tracks[kTrackTypeAudio].size() > 1)
01821         {
01822             qBubbleSort(tracks[kTrackTypeAudio]);
01823             sinfo_vec_t::iterator it = tracks[kTrackTypeAudio].begin();
01824             for (; it != tracks[kTrackTypeAudio].end(); ++it)
01825             {
01826                 it->dvd_track_num =
01827                         ringBuffer->DVD()->GetAudioTrackNum(it->stream_id);
01828                 VERBOSE(VB_PLAYBACK, LOC + 
01829                             QString("DVD Audio Track Map "
01830                                     "Stream id #%1 track #%2 ")
01831                             .arg(it->stream_id).arg(it->dvd_track_num));
01832             }
01833             qBubbleSort(tracks[kTrackTypeAudio]);
01834             int trackNo = ringBuffer->DVD()->GetTrack(kTrackTypeAudio);
01835             if (trackNo >= (int)GetTrackCount(kTrackTypeAudio))
01836                 trackNo = GetTrackCount(kTrackTypeAudio) - 1;
01837             SetTrack(kTrackTypeAudio, trackNo);
01838         }
01839         if (tracks[kTrackTypeSubtitle].size() > 0)
01840         {
01841             qBubbleSort(tracks[kTrackTypeSubtitle]);
01842             sinfo_vec_t::iterator it = tracks[kTrackTypeSubtitle].begin();
01843             for(; it != tracks[kTrackTypeSubtitle].end(); ++it)
01844             {
01845                 it->dvd_track_num =
01846                         ringBuffer->DVD()->GetSubTrackNum(it->stream_id);
01847                 VERBOSE(VB_PLAYBACK, LOC +
01848                         QString("DVD Subtitle Track Map "
01849                                 "Stream id #%1 track #%2 ")
01850                         .arg(it->stream_id).arg(it->dvd_track_num));
01851             }
01852             qBubbleSort(tracks[kTrackTypeSubtitle]);
01853             int trackNo = ringBuffer->DVD()->GetTrack(kTrackTypeSubtitle);
01854             uint captionmode = GetNVP()->GetCaptionMode();
01855             int trackcount = (int)GetTrackCount(kTrackTypeSubtitle);
01856             if (captionmode == kDisplayAVSubtitle &&
01857                 (trackNo < 0 || trackNo >= trackcount))
01858             {
01859                 GetNVP()->SetCaptionsEnabled(false, false);
01860             }
01861             else if (trackNo >= 0 && trackNo < trackcount && 
01862                     !ringBuffer->InDVDMenuOrStillFrame())
01863             {
01864                     SetTrack(kTrackTypeSubtitle, trackNo);
01865                     GetNVP()->SetCaptionsEnabled(true, false);
01866             }
01867         }
01868     }
01869 
01870     // Select a new track at the next opportunity.
01871     ResetTracks();
01872 
01873     // We have to do this here to avoid the NVP getting stuck
01874     // waiting on audio.
01875     if (GetNVP()->HasAudioIn() && tracks[kTrackTypeAudio].empty())
01876     {
01877         GetNVP()->SetAudioParams(-1, -1, -1, false /* AC3/DTS pass-through */);
01878         GetNVP()->ReinitAudio();
01879         if (ringBuffer && ringBuffer->isDVD()) 
01880             audioIn = AudioInfo();
01881     }
01882 
01883     // if we don't have a video stream we still need to make sure some
01884     // video params are set properly
01885     if (selectedVideoIndex == -1)
01886     {
01887         QString tvformat = gContext->GetSetting("TVFormat").lower();
01888         if (tvformat == "ntsc" || tvformat == "ntsc-jp" ||
01889             tvformat == "pal-m" || tvformat == "atsc")
01890         {
01891             fps = 29.97;
01892             GetNVP()->SetVideoParams(-1, -1, 29.97, 1);
01893         }
01894         else
01895         {
01896             fps = 25.0;
01897             GetNVP()->SetVideoParams(-1, -1, 25.0, 1);
01898         }
01899     }
01900 
01901     if (GetNVP()->IsErrored())
01902         scanerror = -1;
01903 
01904     ScanDSMCCStreams();
01905 
01906     return scanerror;
01907 }
01908 
01921 void AvFormatDecoder::SetupAudioStreamSubIndexes(int streamIndex)
01922 {
01923     QMutexLocker locker(&avcodeclock);
01924 
01925     // Find the position of the streaminfo in tracks[kTrackTypeAudio] 
01926     sinfo_vec_t::iterator current = tracks[kTrackTypeAudio].begin();
01927     for (; current != tracks[kTrackTypeAudio].end(); ++current) 
01928     {
01929         if (current->av_stream_index == streamIndex)
01930             break;
01931     }
01932 
01933     if (current == tracks[kTrackTypeAudio].end())
01934     {
01935         VERBOSE(VB_IMPORTANT, LOC_WARN +
01936                 "Invalid stream index passed to "
01937                 "SetupAudioStreamSubIndexes: "<<streamIndex);
01938 
01939         return;
01940     }
01941 
01942     // Remove the extra substream or duplicate the current substream
01943     sinfo_vec_t::iterator next = current + 1;
01944     if (current->av_substream_index == -1)
01945     {
01946         // Split stream in two (Language I + Language II)
01947         StreamInfo lang1 = *current;
01948         StreamInfo lang2 = *current;
01949         lang1.av_substream_index = 0;
01950         lang2.av_substream_index = 1;
01951         *current = lang1;
01952         tracks[kTrackTypeAudio].insert(next, lang2);
01953         return;
01954     }
01955 
01956     if ((next == tracks[kTrackTypeAudio].end()) ||
01957         (next->av_stream_index != streamIndex))
01958     {
01959         QString msg = QString(
01960             "Expected substream 1 (Language I) of stream %1\n\t\t\t"
01961             "following substream 0, found end of list or another stream.")
01962             .arg(streamIndex);
01963 
01964         VERBOSE(VB_IMPORTANT, LOC_WARN + msg);
01965 
01966         return;
01967     }
01968 
01969     // Remove extra stream info
01970     StreamInfo stream = *current;
01971     stream.av_substream_index = -1;
01972     *current = stream;
01973     tracks[kTrackTypeAudio].erase(next);
01974 }
01975 
01976 int get_avf_buffer(struct AVCodecContext *c, AVFrame *pic)
01977 {
01978     AvFormatDecoder *nd = (AvFormatDecoder *)(c->opaque);
01979 
01980     VideoFrame *frame = nd->GetNVP()->GetNextVideoFrame(true);
01981 
01982     for (int i = 0; i < 3; i++)
01983     {
01984         pic->data[i]     = frame->buf + frame->offsets[i];
01985         pic->linesize[i] = frame->pitches[i];
01986     }
01987 
01988     pic->opaque = frame;
01989     pic->type = FF_BUFFER_TYPE_USER;
01990 
01991     pic->age = 256 * 256 * 256 * 64;
01992 
01993     return 1;
01994 }
01995 
02000 void AvFormatDecoder::RemoveAudioStreams()
02001 {
02002     if (!GetNVP() || !GetNVP()->HasAudioIn())
02003         return;
02004  
02005     QMutexLocker locker(&avcodeclock);
02006     for (uint i = 0; i < ic->nb_streams;)
02007     {
02008         AVStream *st = ic->streams[i];
02009         if (st->codec->codec_type == CODEC_TYPE_AUDIO)
02010         {
02011             av_remove_stream(ic, st->id, 0);
02012             i--;
02013         }
02014         else
02015             i++;
02016     }
02017     av_read_frame_flush(ic);
02018 }
02019 
02020 void release_avf_buffer(struct AVCodecContext *c, AVFrame *pic)
02021 {
02022     (void)c;
02023 
02024     if (pic->type == FF_BUFFER_TYPE_INTERNAL)
02025     {
02026         avcodec_default_release_buffer(c, pic);
02027         return;
02028     }
02029 
02030     AvFormatDecoder *nd = (AvFormatDecoder *)(c->opaque);
02031     if (nd && nd->GetNVP() && nd->GetNVP()->getVideoOutput())
02032         nd->GetNVP()->getVideoOutput()->DeLimboFrame((VideoFrame*)pic->opaque);
02033 
02034     assert(pic->type == FF_BUFFER_TYPE_USER);
02035 
02036     for (uint i = 0; i < 4; i++)
02037         pic->data[i] = NULL;
02038 }
02039 
02040 int get_avf_buffer_xvmc(struct AVCodecContext *c, AVFrame *pic)
02041 {
02042     AvFormatDecoder *nd = (AvFormatDecoder *)(c->opaque);
02043     VideoFrame *frame = nd->GetNVP()->GetNextVideoFrame(false);
02044 
02045     pic->data[0] = frame->priv[0];
02046     pic->data[1] = frame->priv[1];
02047     pic->data[2] = frame->buf;
02048 
02049     pic->linesize[0] = 0;
02050     pic->linesize[1] = 0;
02051     pic->linesize[2] = 0;
02052 
02053     pic->opaque = frame;
02054     pic->type = FF_BUFFER_TYPE_USER;
02055 
02056     pic->age = 256 * 256 * 256 * 64;
02057 
02058 #ifdef USING_XVMC
02059     xvmc_render_state_t *render = (xvmc_render_state_t *)frame->buf;
02060 
02061     render->state = MP_XVMC_STATE_PREDICTION;
02062     render->picture_structure = 0;
02063     render->flags = 0;
02064     render->start_mv_blocks_num = 0;
02065     render->filled_mv_blocks_num = 0;
02066     render->next_free_data_block_num = 0;
02067 #endif
02068 
02069     return 1;
02070 }
02071 
02072 void release_avf_buffer_xvmc(struct AVCodecContext *c, AVFrame *pic)
02073 {
02074     assert(pic->type == FF_BUFFER_TYPE_USER);
02075 
02076 #ifdef USING_XVMC
02077     xvmc_render_state_t *render = (xvmc_render_state_t *)pic->data[2];
02078     render->state &= ~MP_XVMC_STATE_PREDICTION;
02079 #endif
02080 
02081     AvFormatDecoder *nd = (AvFormatDecoder *)(c->opaque);
02082     if (nd && nd->GetNVP() && nd->GetNVP()->getVideoOutput())
02083         nd->GetNVP()->getVideoOutput()->DeLimboFrame((VideoFrame*)pic->opaque);
02084 
02085     for (uint i = 0; i < 4; i++)
02086         pic->data[i] = NULL;
02087 
02088 }
02089 
02090 void render_slice_xvmc(struct AVCodecContext *s, const AVFrame *src,
02091                        int offset[4], int y, int type, int height)
02092 {
02093     if (!src)
02094         return;
02095 
02096     (void)offset;
02097     (void)type;
02098 
02099     if (s && src && s->opaque && src->opaque)
02100     {
02101         AvFormatDecoder *nd = (AvFormatDecoder *)(s->opaque);
02102 
02103         int width = s->width;
02104 
02105         VideoFrame *frame = (VideoFrame *)src->opaque;
02106         nd->GetNVP()->DrawSlice(frame, 0, y, width, height);
02107     }
02108     else
02109     {
02110         VERBOSE(VB_IMPORTANT, LOC +
02111                 "render_slice_xvmc called with bad avctx or src");
02112     }
02113 }
02114 
02115 void decode_cc_dvd(struct AVCodecContext *s, const uint8_t *buf, int buf_size)
02116 {
02117     // taken from xine-lib libspucc by Christian Vogler
02118 
02119     AvFormatDecoder *nd = (AvFormatDecoder *)(s->opaque);
02120     unsigned long long utc = nd->lastccptsu;
02121 
02122     const uint8_t *current = buf;
02123     int curbytes = 0;
02124     uint8_t data1, data2;
02125     uint8_t cc_code;
02126     int odd_offset = 1;
02127 
02128     while (curbytes < buf_size)
02129     {
02130         int skip = 2;
02131 
02132         cc_code = *current++;
02133         curbytes++;
02134     
02135         if (buf_size - curbytes < 2)
02136             break;
02137     
02138         data1 = *current;
02139         data2 = *(current + 1);
02140     
02141         switch (cc_code)
02142         {
02143             case 0xfe:
02144                 /* expect 2 byte encoding (perhaps CC3, CC4?) */
02145                 /* ignore for time being */
02146                 skip = 2;
02147                 break;
02148 
02149             case 0xff:
02150             {
02151                 /* expect EIA-608 CC1/CC2 encoding */
02152                 int tc = utc / 1000;
02153                 int data = (data2 << 8) | data1;
02154                 if (cc608_good_parity(nd->cc608_parity_table, data))
02155                     nd->ccd608->FormatCCField(tc, 0, data);
02156                 utc += 33367;
02157                 skip = 5;
02158                 break;
02159             }
02160 
02161             case 0x00:
02162                 /* This seems to be just padding */
02163                 skip = 2;
02164                 break;
02165 
02166             case 0x01:
02167                 odd_offset = data2 & 0x80;
02168                 if (odd_offset)
02169                     skip = 2;
02170                 else
02171                     skip = 5;
02172                 break;
02173 
02174             default:
02175                 // rest is not needed?
02176                 goto done;
02177                 //skip = 2;
02178                 //break;
02179         }
02180         current += skip;
02181         curbytes += skip;
02182 
02183     }
02184   done:
02185     nd->lastccptsu = utc;
02186 }
02187 
02188 void AvFormatDecoder::DecodeDTVCC(const uint8_t *buf)
02189 {
02190     // closed caption data
02191     //cc_data() {
02192     // reserved                1 0.0   1  
02193     // process_cc_data_flag    1 0.1   bslbf 
02194     bool process_cc_data = buf[0] & 0x40;
02195     if (!process_cc_data)
02196         return; // early exit if process_cc_data_flag false
02197 
02198     // additional_data_flag    1 0.2   bslbf 
02199     //bool additional_data = buf[0] & 0x20;
02200     // cc_count                5 0.3   uimsbf 
02201     uint cc_count = buf[0] & 0x1f;
02202     // reserved                8 1.0   0xff
02203     // em_data                 8 2.0
02204 
02205     for (uint cur = 0; cur < cc_count; cur++)
02206     {
02207         uint cc_code  = buf[2+(cur*3)];
02208         bool cc_valid = cc_code & 0x04;
02209         if (!cc_valid)
02210             continue;
02211 
02212         uint data1    = buf[3+(cur*3)];
02213         uint data2    = buf[4+(cur*3)];
02214         uint data     = (data2 << 8) | data1;
02215         uint cc_type  = cc_code & 0x03;
02216 
02217         if (cc_type <= 0x1) // EIA-608 field-1/2
02218         {
02219             if (cc608_good_parity(cc608_parity_table, data))
02220                 ccd608->FormatCCField(lastccptsu / 1000, cc_type, data);
02221         }
02222         else // EIA-708 CC data
02223             ccd708->decode_cc_data(cc_type, data1, data2);
02224     }
02225 }
02226 
02227 void AvFormatDecoder::HandleGopStart(AVPacket *pkt)
02228 {
02229     if (prevgoppos != 0 && keyframedist != 1)
02230     {
02231         int tempKeyFrameDist = framesRead - 1 - prevgoppos;
02232         bool reset_kfd = false;
02233 
02234         if (!gopset) // gopset: we've seen 2 keyframes
02235         {
02236             VERBOSE(VB_PLAYBACK, LOC + "HandleGopStart: "
02237                     "gopset not set, syncing positionMap");
02238             SyncPositionMap();
02239             if (tempKeyFrameDist > 0)
02240             {
02241                 VERBOSE(VB_PLAYBACK, LOC + "HandleGopStart: " +
02242                         QString("Initial key frame distance: %1.")
02243                         .arg(keyframedist));
02244                 gopset       = true;
02245                 reset_kfd    = true;
02246             }
02247         }
02248         else if (keyframedist != tempKeyFrameDist && tempKeyFrameDist > 0)
02249         {
02250             VERBOSE(VB_PLAYBACK, LOC + "HandleGopStart: " +
02251                     QString("Key frame distance changed from %1 to %2.")
02252                     .arg(keyframedist).arg(tempKeyFrameDist));
02253             reset_kfd = true;
02254         }
02255 
02256         if (reset_kfd)
02257         {
02258             keyframedist    = tempKeyFrameDist;
02259             maxkeyframedist = max(keyframedist, maxkeyframedist);
02260 
02261             // FIXME: this needs to go
02262             bool is_ivtv    = (keyframedist == 15) || (keyframedist == 12);
02263             positionMapType = (is_ivtv) ? MARK_GOP_START : MARK_GOP_BYFRAME;
02264 
02265             GetNVP()->SetKeyframeDistance(keyframedist);
02266 
02267 #if 0
02268             // also reset length
02269             if (!m_positionMap.empty())
02270             {
02271                 long long index       = m_positionMap.back().index;
02272                 long long totframes   = index * keyframedist;
02273                 uint length = (uint)((totframes * 1.0f) / fps);
02274                 GetNVP()->SetFileLength(length, totframes);
02275             }
02276 #endif
02277         }
02278     }
02279 
02280     lastKey = prevgoppos = framesRead - 1;
02281 
02282     if (!hasFullPositionMap)
02283     {
02284         long long last_frame = 0;
02285         if (!m_positionMap.empty())
02286             last_frame = m_positionMap.back().index;
02287         if (keyframedist > 1)
02288             last_frame *= keyframedist;
02289 
02290         //cerr << "framesRead: " << framesRead << " last_frame: " << last_frame
02291         //    << " keyframedist: " << keyframedist << endl;
02292 
02293         // if we don't have an entry, fill it in with what we've just parsed
02294         if (framesRead > last_frame && keyframedist > 0)
02295         {
02296             long long startpos = pkt->pos;
02297 
02298             VERBOSE(VB_PLAYBACK|VB_TIMESTAMP, LOC + 
02299                     QString("positionMap[ %1 ] == %2.")
02300                     .arg(prevgoppos / keyframedist)
02301                     .arg(startpos));
02302 
02303             PosMapEntry entry = {prevgoppos / keyframedist,
02304                                  prevgoppos, startpos};
02305             m_positionMap.push_back(entry);
02306         }
02307 
02308 #if 0
02309         // If we are > 150 frames in and saw no positionmap at all, reset
02310         // length based on the actual bitrate seen so far
02311         if (framesRead > 150 && !recordingHasPositionMap && !livetv)
02312         {
02313             bitrate = (int)((pkt->pos * 8 * fps) / (framesRead - 1));
02314             float bytespersec = (float)bitrate / 8;
02315             float secs = ringBuffer->GetRealFileSize() * 1.0 / bytespersec;
02316             GetNVP()->SetFileLength((int)(secs), (int)(secs * fps));
02317         }
02318 #endif
02319     }
02320 }
02321 
02322 #define SEQ_START     0x000001b3
02323 #define GOP_START     0x000001b8
02324 #define PICTURE_START 0x00000100
02325 #define SLICE_MIN     0x00000101
02326 #define SLICE_MAX     0x000001af
02327 #define SEQ_END_CODE  0x000001b7
02328 
02329 void AvFormatDecoder::MpegPreProcessPkt(AVStream *stream, AVPacket *pkt)
02330 {
02331     AVCodecContext *context = stream->codec;
02332     const uint8_t *bufptr = pkt->data;
02333     const uint8_t *bufend = pkt->data + pkt->size;
02334 
02335     while (bufptr < bufend)
02336     {
02337         bufptr = ff_find_start_code(bufptr, bufend, &start_code_state);
02338        
02339         if (ringBuffer->isDVD() && start_code_state == SEQ_END_CODE)
02340         {
02341             mpeg_seq_end_seen = true;
02342             return;
02343         }
02344 
02345         if (start_code_state >= SLICE_MIN && start_code_state <= SLICE_MAX)
02346             continue;
02347         else if (SEQ_START == start_code_state)
02348         {
02349             if (bufptr + 11 >= pkt->data + pkt->size)
02350                 continue; // not enough valid data...
02351             SequenceHeader *seq = reinterpret_cast<SequenceHeader*>(
02352                 const_cast<uint8_t*>(bufptr));
02353 
02354             uint  width  = seq->width();
02355             uint  height = seq->height();
02356             float aspect = seq->aspect(context->sub_id == 1);
02357             float seqFPS = seq->fps();
02358 
02359             bool changed = (seqFPS > fps+0.01) || (seqFPS < fps-0.01);
02360             changed |= (width  != (uint)current_width );
02361             changed |= (height != (uint)current_height);
02362             changed |= fabs(aspect - current_aspect) > eps;
02363 
02364             if (changed)
02365             {
02366                 GetNVP()->SetVideoParams(width, height, seqFPS,
02367                                          keyframedist, aspect, 
02368                                          kScan_Detect);
02369                 
02370                 current_width  = width;
02371                 current_height = height;
02372                 current_aspect = aspect;
02373                 fps            = seqFPS;
02374 
02375                 d->ResetMPEG2();
02376 
02377                 gopset = false;
02378                 prevgoppos = 0;
02379                 lastapts = lastvpts = lastccptsu = 0;
02380 
02381                 // fps debugging info
02382                 float avFPS = normalized_fps(stream, context);
02383                 if ((seqFPS > avFPS+0.01) || (seqFPS < avFPS-0.01))
02384                 {
02385                     VERBOSE(VB_PLAYBACK, LOC +
02386                             QString("avFPS(%1) != seqFPS(%2)")
02387                             .arg(avFPS).arg(seqFPS));
02388                 }
02389             }
02390 
02391             seq_count++;
02392 
02393             if (!seen_gop && seq_count > 1)
02394             {
02395                 HandleGopStart(pkt);
02396                 pkt->flags |= PKT_FLAG_KEY;
02397             }
02398         }
02399         else if (GOP_START == start_code_state)
02400         {
02401             HandleGopStart(pkt);
02402             seen_gop = true;
02403             pkt->flags |= PKT_FLAG_KEY;
02404         }
02405     }
02406 }
02407 
02408 void AvFormatDecoder::H264PreProcessPkt(AVStream *stream, AVPacket *pkt)
02409 {
02410     AVCodecContext *context = stream->codec;
02411     const uint8_t  *buf     = pkt->data;
02412     const uint8_t  *buf_end = pkt->data + pkt->size;
02413 
02414     while (buf < buf_end)
02415     {
02416         uint32_t bytes_used = h264_kf_seq->AddBytes(buf, buf_end - buf, 0);
02417         buf += bytes_used;
02418 
02419         if (!h264_kf_seq->HasStateChanged() || !h264_kf_seq->IsOnKeyframe())
02420             continue;
02421 
02422         float aspect_ratio;
02423         if (context->sample_aspect_ratio.num == 0)
02424             aspect_ratio = 0.0f;
02425         else
02426             aspect_ratio = av_q2d(context->sample_aspect_ratio) *
02427                 context->width / context->height;
02428 
02429         if (aspect_ratio <= 0.0f || aspect_ratio > 6.0f)
02430             aspect_ratio = (float)context->width / context->height;
02431 
02432         uint  width  = context->width;
02433         uint  height = context->height;
02434         float seqFPS = normalized_fps(stream, context);
02435 
02436         bool changed = (seqFPS > fps+0.01) || (seqFPS < fps-0.01);
02437         changed |= (width  != (uint)current_width );
02438         changed |= (height != (uint)current_height);
02439         changed |= fabs(aspect_ratio - current_aspect) > eps;
02440 
02441         if (changed)
02442         {
02443             GetNVP()->SetVideoParams(width, height, seqFPS,
02444                                      keyframedist, aspect_ratio,
02445                                      kScan_Detect);
02446 
02447             current_width  = width;
02448             current_height = height;
02449             current_aspect = aspect_ratio;
02450             fps            = seqFPS;
02451 
02452             gopset = false;
02453             prevgoppos = 0;
02454             lastapts = lastvpts = lastccptsu = 0;
02455 
02456             // fps debugging info
02457             float avFPS = normalized_fps(stream, context);
02458             if ((seqFPS > avFPS+0.01) || (seqFPS < avFPS-0.01))
02459             {
02460                 VERBOSE(VB_PLAYBACK, LOC +
02461                         QString("avFPS(%1) != seqFPS(%2)")
02462                         .arg(avFPS).arg(seqFPS));
02463             }
02464         }
02465 
02466         HandleGopStart(pkt);
02467         pkt->flags |= PKT_FLAG_KEY;
02468     }
02469 }
02470 
02476 void AvFormatDecoder::ProcessVBIDataPacket(
02477     const AVStream *stream, const AVPacket *pkt)
02478 {
02479     (void) stream;
02480 
02481     const uint8_t *buf     = pkt->data;
02482     uint64_t linemask      = 0;
02483     unsigned long long utc = lastccptsu;
02484 
02485     // [i]tv0 means there is a linemask
02486     // [I]TV0 means there is no linemask and all lines are present
02487     if ((buf[0]=='t') && (buf[1]=='v') && (buf[2] == '0'))
02488     {
02490         memcpy(&linemask, buf + 3, 8);
02491         buf += 11;
02492     }
02493     else if ((buf[0]=='T') && (buf[1]=='V') && (buf[2] == '0'))
02494     {
02495         linemask = 0xffffffffffffffffLL;
02496         buf += 3;
02497     }
02498     else
02499     {
02500         VERBOSE(VB_VBI, LOC + QString("Unknown VBI data stream '%1%2%3'")
02501                 .arg(QChar(buf[0])).arg(QChar(buf[1])).arg(QChar(buf[2])));
02502         return;
02503     }
02504 
02505     static const uint min_blank = 6;
02506     for (uint i = 0; i < 36; i++)
02507     {
02508         if (!((linemask >> i) & 0x1))
02509             continue;
02510 
02511         const uint line  = ((i < 18) ? i : i-18) + min_blank;
02512         const uint field = (i<18) ? 0 : 1; 
02513         const uint id2 = *buf & 0xf;
02514         switch (id2)
02515         {
02516             case VBI_TYPE_TELETEXT:
02517                 // SECAM lines  6-23 
02518                 // PAL   lines  6-22
02519                 // NTSC  lines 10-21 (rare)
02520                 ttd->Decode(buf+1, VBI_IVTV);
02521                 break;
02522             case VBI_TYPE_CC:
02523                 // PAL   line 22 (rare)
02524                 // NTSC  line 21
02525                 if (21 == line)
02526                 {
02527                     int data = (buf[2] << 8) | buf[1];
02528                     if (cc608_good_parity(cc608_parity_table, data))
02529                         ccd608->FormatCCField(utc/1000, field, data);
02530                     utc += 33367;
02531                 }
02532                 break;
02533             case VBI_TYPE_VPS: // Video Programming System
02534                 // PAL   line 16
02535                 ccd608->DecodeVPS(buf+1); // a.k.a. PDC
02536                 break;
02537             case VBI_TYPE_WSS: // Wide Screen Signal
02538                 // PAL   line 23
02539                 // NTSC  line 20
02540                 ccd608->DecodeWSS(buf+1);
02541                 break;
02542         }
02543         buf += 43;
02544     }
02545     lastccptsu = utc;
02546 }
02547 
02552 void AvFormatDecoder::ProcessDVBDataPacket(
02553     const AVStream*, const AVPacket *pkt)
02554 {
02555     const uint8_t *buf     = pkt->data;
02556     const uint8_t *buf_end = pkt->data + pkt->size;
02557 
02558 
02559     while (buf < buf_end)
02560     {
02561         if (*buf == 0x10)
02562             buf++; // skip
02563 
02564         if (*buf == 0x02)
02565         {
02566             buf += 3;
02567             ttd->Decode(buf+1, VBI_DVB);
02568         }
02569         else if (*buf == 0x03)
02570         {
02571             buf += 3;
02572             ttd->Decode(buf+1, VBI_DVB_SUBTITLE);
02573         }
02574         else if (*buf == 0xff)
02575         {
02576             buf += 3;
02577         }
02578         else
02579         {
02580             VERBOSE(VB_VBI, QString("VBI: Unknown descriptor: %1").arg(*buf));
02581         }
02582 
02583         buf += 43;
02584     }
02585 }
02586 
02590 void AvFormatDecoder::ProcessDSMCCPacket(
02591     const AVStream *str, const AVPacket *pkt)
02592 {
02593     if (!itv && ! (itv = GetNVP()->GetInteractiveTV()))
02594         return;
02595 
02596     // The packet may contain several tables.
02597     uint8_t *data = pkt->data;
02598     int length = pkt->size;
02599     avcodeclock.lock();
02600     int componentTag = str->component_tag; //Contains component tag
02601     unsigned carouselId = (unsigned)str->codec->sub_id; //Contains carousel Id
02602     int dataBroadcastId = str->codec->flags; // Contains data broadcast Id.
02603     avcodeclock.unlock();
02604     while (length > 3)
02605     {
02606         uint16_t sectionLen = (((data[1] & 0xF) << 8) | data[2]) + 3;
02607 
02608         if (sectionLen > length) // This may well be filler
02609             return;
02610 
02611         itv->ProcessDSMCCSection(data, sectionLen,
02612                                  componentTag, carouselId,
02613                                  dataBroadcastId);
02614         length -= sectionLen;
02615         data += sectionLen;
02616     }
02617 }
02618 
02619 int AvFormatDecoder::SetTrack(uint type, int trackNo)
02620 {
02621     bool ret = DecoderBase::SetTrack(type, trackNo);
02622 
02623     if (kTrackTypeAudio == type)
02624     {
02625         QString msg = SetupAudioStream() ? "" : "not ";
02626         VERBOSE(VB_AUDIO, LOC + "Audio stream type "+msg+"changed.");
02627     }
02628 
02629     return ret;
02630 }
02631 
02632 QString AvFormatDecoder::GetTrackDesc(uint type, uint trackNo) const
02633 {
02634     if (trackNo >= tracks[type].size())
02635         return "";
02636 
02637     int lang_key = tracks[type][trackNo].language;
02638     if (kTrackTypeAudio == type)
02639     {
02640         if (ringBuffer->isDVD())
02641             lang_key = ringBuffer->DVD()->GetAudioLanguage(trackNo);
02642 
02643         QString msg = iso639_key_toName(lang_key);
02644 
02645         int av_index = tracks[kTrackTypeAudio][trackNo].av_stream_index;
02646         AVStream *s = ic->streams[av_index];
02647 
02648         if (!s)
02649             return QString("%1: %2").arg(trackNo + 1).arg(msg); 
02650 
02651         if (s->codec->codec_id == CODEC_ID_MP3)
02652             msg += QString(" MP%1").arg(s->codec->sub_id);
02653         else if (s->codec->codec)
02654             msg += QString(" %1").arg(s->codec->codec->name).upper();
02655 
02656         int channels = 0;
02657         if (ringBuffer->isDVD())
02658             channels = ringBuffer->DVD()->GetNumAudioChannels(trackNo);
02659         else if (s->codec->channels)
02660             channels = s->codec->channels;
02661 
02662         if (channels == 0)
02663             msg += QString(" ?ch");
02664         else if((channels > 4) && !(channels & 1))
02665             msg += QString(" %1.1ch").arg(channels - 1);
02666         else
02667             msg += QString(" %1ch").arg(channels);
02668 
02669         return QString("%1: %2").arg(trackNo + 1).arg(msg);
02670     }
02671     else if (kTrackTypeSubtitle == type)
02672     {
02673         if (ringBuffer->isDVD())
02674             lang_key = ringBuffer->DVD()->GetSubtitleLanguage(trackNo);
02675 
02676         return QObject::tr("Subtitle") + QString(" %1: %2")
02677             .arg(trackNo + 1).arg(iso639_key_toName(lang_key));
02678     }
02679     else
02680     {
02681         return DecoderBase::GetTrackDesc(type, trackNo);
02682     }
02683 }
02684 
02685 int AvFormatDecoder::GetTeletextDecoderType(void) const
02686 {
02687     return ttd->GetDecoderType();
02688 }
02689 
02690 void AvFormatDecoder::SetTeletextDecoderViewer(TeletextViewer *view)
02691 {
02692     ttd->SetViewer(view);
02693 }
02694 
02695 QString AvFormatDecoder::GetXDS(const QString &key) const
02696 {
02697     return ccd608->GetXDS(key);
02698 }
02699 
02700 bool AvFormatDecoder::SetAudioByComponentTag(int tag)
02701 {
02702     for (uint i = 0; i < tracks[kTrackTypeAudio].size(); i++)
02703     {
02704         AVStream *s  = ic->streams[tracks[kTrackTypeAudio][i].av_stream_index];
02705         if (s)
02706         {
02707             if (s->component_tag == tag || tag <= 0 && s->component_tag <= 0)
02708             {
02709                 return SetTrack(kTrackTypeAudio, i);
02710             }
02711         }
02712     }
02713     return false;
02714 }
02715 
02716 bool AvFormatDecoder::SetVideoByComponentTag(int tag)
02717 {
02718     for (uint i = 0; i < ic->nb_streams; i++)
02719     {
02720         AVStream *s  = ic->streams[i];
02721         if (s)
02722         {
02723             if (s->component_tag == tag)
02724             {
02725                 selectedVideoIndex = i;
02726                 return true;
02727             }
02728         }
02729     }
02730     return false;
02731 }
02732 
02733 // documented in decoderbase.cpp
02734 int AvFormatDecoder::AutoSelectTrack(uint type)
02735 {
02736     if (kTrackTypeAudio == type)
02737         return AutoSelectAudioTrack();
02738 
02739     if (ringBuffer->InDVDMenuOrStillFrame())
02740         return -1;
02741 
02742     return DecoderBase::AutoSelectTrack(type);
02743 }
02744 
02745 static vector<int> filter_lang(const sinfo_vec_t &tracks, int lang_key)
02746 {
02747     vector<int> ret;
02748 
02749     for (uint i = 0; i < tracks.size(); i++)
02750         if ((lang_key < 0) || tracks[i].language == lang_key)
02751             ret.push_back(i);
02752 
02753     return ret;
02754 }
02755 
02756 static int filter_max_ch(const AVFormatContext *ic,
02757                          const sinfo_vec_t     &tracks,
02758                          const vector<int>     &fs,
02759                          enum CodecID           codecId = CODEC_ID_NONE)
02760 {
02761     int selectedTrack = -1, max_seen = -1;
02762 
02763     vector<int>::const_iterator it = fs.begin();
02764     for (; it != fs.end(); ++it)
02765     {
02766         const int stream_index = tracks[*it].av_stream_index;
02767         const AVCodecContext *ctx = ic->streams[stream_index]->codec;
02768         if ((codecId == CODEC_ID_NONE || codecId == ctx->codec_id) &&
02769             (max_seen < ctx->channels))
02770         {
02771             selectedTrack = *it;
02772             max_seen = ctx->channels;
02773         }
02774     }
02775 
02776     return selectedTrack;
02777 }
02778 
02825 int AvFormatDecoder::AutoSelectAudioTrack(void)
02826 {
02827     const sinfo_vec_t &atracks = tracks[kTrackTypeAudio];
02828     StreamInfo        &wtrack  = wantedTrack[kTrackTypeAudio];
02829     StreamInfo        &strack  = selectedTrack[kTrackTypeAudio];
02830     int               &ctrack  = currentTrack[kTrackTypeAudio];
02831 
02832     uint numStreams = atracks.size();
02833     if ((ctrack >= 0) && (ctrack < (int)numStreams))
02834         return ctrack; // audio already selected
02835 
02836 #if 0
02837     // enable this to print streams
02838     for (uint i = 0; i < atracks.size(); i++)
02839     {
02840         int idx = atracks[i].av_stream_index;
02841         AVCodecContext *codec_ctx = ic->streams[idx]->codec;
02842         bool do_ac3_passthru = (allow_ac3_passthru && !transcoding &&
02843                                 !disable_passthru &&
02844                                 (codec_ctx->codec_id == CODEC_ID_AC3));
02845         bool do_dts_passthru = (allow_dts_passthru && !transcoding &&
02846                                 !disable_passthru &&
02847                                 (codec_ctx->codec_id == CODEC_ID_DTS));
02848         AudioInfo item(codec_ctx->codec_id,
02849                        codec_ctx->sample_rate, codec_ctx->channels,
02850                        do_ac3_passthru || do_dts_passthru);
02851         VERBOSE(VB_AUDIO, LOC + " * " + item.toString());
02852     }
02853 #endif
02854 
02855     int selTrack = (1 == numStreams) ? 0 : -1;
02856     int wlang    = wtrack.language;
02857 
02858     if ((selTrack < 0) && (wtrack.av_substream_index >= 0))
02859     {
02860         VERBOSE(VB_AUDIO, LOC + "Trying to reselect audio sub-stream");
02861         // Dual stream without language information: choose
02862         // the previous substream that was kept in wtrack,
02863         // ignoring the stream index (which might have changed). 
02864         int substream_index = wtrack.av_substream_index;
02865 
02866         for (uint i = 0; i < numStreams; i++)
02867         {
02868             if (atracks[i].av_substream_index == substream_index)
02869             {
02870                 selTrack = i;
02871                 break;
02872             }
02873         }
02874     }
02875 
02876     if ((selTrack < 0) && wlang >= -1 && numStreams)
02877     {
02878         VERBOSE(VB_AUDIO, LOC + "Trying to reselect audio track");
02879         // Try to reselect user selected subtitle stream.
02880         // This should find the stream after a commercial
02881         // break and in some cases after a channel change.
02882         uint windx = wtrack.language_index;
02883         for (uint i = 0; i < numStreams; i++)
02884         {
02885             if (wlang == atracks[i].language)
02886                 selTrack = i;
02887 
02888             if (windx == atracks[i].language_index)
02889                 break;
02890         }
02891     }
02892 
02893     if (selTrack < 0 && numStreams)
02894     {
02895         VERBOSE(VB_AUDIO, LOC + "Trying to select audio track (w/lang)");
02896         // try to get best track for most preferred language
02897         selTrack = -1;
02898         vector<int>::const_iterator it = languagePreference.begin();
02899         for (; it !=  languagePreference.end() && selTrack<0; ++it)
02900         {
02901             vector<int> flang = filter_lang(atracks, *it);
02902 
02903             if (allow_dts_passthru && !transcoding)
02904                 selTrack = filter_max_ch(ic, atracks, flang, CODEC_ID_DTS);
02905 
02906             if (selTrack < 0)
02907                 selTrack = filter_max_ch(ic, atracks, flang, CODEC_ID_AC3);
02908 
02909             if (selTrack < 0)
02910                 selTrack = filter_max_ch(ic, atracks, flang);
02911         }
02912         // try to get best track for any language
02913         if (selTrack < 0)
02914         {
02915             VERBOSE(VB_AUDIO, LOC + "Trying to select audio track (wo/lang)");
02916             vector<int> flang = filter_lang(atracks, -1);
02917 
02918             if (allow_dts_passthru && !transcoding)
02919                 selTrack = filter_max_ch(ic, atracks, flang, CODEC_ID_DTS);
02920 
02921             if (selTrack < 0)
02922                 selTrack = filter_max_ch(ic, atracks, flang, CODEC_ID_AC3);
02923 
02924             if (selTrack < 0)
02925                 selTrack = filter_max_ch(ic, atracks, flang);
02926         }
02927     }
02928 
02929     if (selTrack < 0)
02930     {
02931         strack.av_stream_index = -1;
02932         if (ctrack != selTrack)
02933         {
02934             VERBOSE(VB_AUDIO, LOC + "No suitable audio track exists.");
02935             ctrack = selTrack;
02936         }
02937     }
02938     else
02939     {
02940         ctrack = selTrack;
02941         strack = atracks[selTrack];
02942 
02943         if (wtrack.av_stream_index < 0)
02944             wtrack = strack;
02945 
02946         VERBOSE(VB_AUDIO, LOC +
02947                 QString("Selected track %1 (A/V Stream #%2)")
02948                 .arg(GetTrackDesc(kTrackTypeAudio, ctrack))
02949                 .arg(strack.av_stream_index));
02950     }
02951 
02952     SetupAudioStream();
02953     return selTrack;
02954 }
02955 
02956 static void extract_mono_channel(uint channel, AudioInfo *audioInfo,
02957                                  char *buffer, int bufsize)
02958 {
02959     // Only stereo -> mono (left or right) is supported
02960     if (audioInfo->channels != 2)
02961         return;
02962 
02963     if (channel >= (uint)audioInfo->channels)
02964         return;
02965 
02966     const uint samplesize = audioInfo->sample_size;
02967     const uint samples    = bufsize / samplesize;
02968     const uint halfsample = samplesize >> 1;
02969 
02970     const char *from = (channel == 1) ? buffer + halfsample : buffer;
02971     char *to         = (channel == 0) ? buffer + halfsample : buffer;
02972 
02973     for (uint sample = 0; sample < samples;
02974          (sample++), (from += samplesize), (to += samplesize))
02975     {
02976         memmove(to, from, halfsample);
02977     }
02978 }
02979 
02980 // documented in decoderbase.h
02981 bool AvFormatDecoder::GetFrame(int onlyvideo)
02982 {
02983     AVPacket *pkt = NULL;
02984     int len;
02985     unsigned char *ptr;
02986     int data_size = 0;
02987     long long pts;
02988     bool firstloop = false, have_err = false;
02989 
02990     gotvideo = false;
02991 
02992     frame_decoded = 0;
02993     decoded_video_frame = NULL;
02994 
02995     bool allowedquit = false;
02996     bool storevideoframes = false;
02997 
02998     avcodeclock.lock();
02999     AutoSelectTracks();
03000     avcodeclock.unlock();
03001 
03002     bool skipaudio = (lastvpts == 0);
03003 
03004     bool has_video = HasVideo(ic);
03005 
03006     if (!has_video && (onlyvideo >= 0))
03007     {
03008         gotvideo = GenerateDummyVideoFrame();
03009         onlyvideo = -1;
03010         skipaudio = false;
03011     }
03012 
03013     uint ofill = 0, ototal = 0, othresh = 0, total_decoded_audio = 0;
03014     if (GetNVP()->GetAudioBufferStatus(ofill, ototal))
03015     {
03016         othresh =  ((ototal>>1) + (ototal>>2));
03017         allowedquit = (onlyvideo < 0) && (ofill > othresh);
03018     }
03019 
03020     while (!allowedquit)
03021     {
03022         if ((onlyvideo == 0) &&
03023             ((currentTrack[kTrackTypeAudio] < 0) ||
03024              (selectedTrack[kTrackTypeAudio].av_stream_index < 0)))
03025         {
03026             // disable audio request if there are no audio streams anymore
03027             // and we have video, otherwise allow decoding to stop
03028             if (has_video)
03029                 onlyvideo = 1;
03030             else
03031                 allowedquit = true;
03032         }
03033 
03034         if (ringBuffer->isDVD())
03035         {
03036             int dvdtitle  = 0;
03037             int dvdpart = 0;
03038             ringBuffer->DVD()->GetPartAndTitle(dvdpart, dvdtitle);
03039             bool cellChanged = ringBuffer->DVD()->CellChanged();
03040             bool inDVDStill = ringBuffer->DVD()->InStillFrame();
03041             bool inDVDMenu  = ringBuffer->DVD()->IsInMenu();
03042             selectedVideoIndex = 0;
03043             if (dvdTitleChanged)
03044             {
03045                 if ((storedPackets.count() > 10 && !decodeStillFrame) ||
03046                     decodeStillFrame)
03047                 {
03048                     storevideoframes = false;
03049                     dvdTitleChanged = false;
03050                     ScanStreams(true);
03051                 }
03052                 else
03053                     storevideoframes = true;
03054             }
03055             else
03056             {
03057                 storevideoframes = false;
03058                 
03059                 if (decodeStillFrame && !inDVDStill)
03060                     decodeStillFrame = false;
03061                 
03062                 if (storedPackets.count() < 2 && !decodeStillFrame)
03063                     storevideoframes = true;
03064 
03065                 if (inDVDMenu && storedPackets.count() > 0)
03066                     ringBuffer->DVD()->SetRunSeekCellStart(false);
03067                 else if (inDVDStill)
03068                     ringBuffer->DVD()->RunSeekCellStart();
03069             }          
03070             if (GetNVP()->AtNormalSpeed() &&
03071                 ((cellChanged) || (lastdvdtitle != dvdtitle)))
03072             {
03073                 if (dvdtitle != lastdvdtitle)
03074                 {
03075                     VERBOSE(VB_PLAYBACK, LOC + "DVD Title Changed");
03076                     lastdvdtitle = dvdtitle;
03077                     if (lastdvdtitle != -1 )
03078                         dvdTitleChanged = true;
03079                     if (GetNVP() && GetNVP()->getVideoOutput())
03080                     {
03081                         if (ringBuffer->DVD()->InStillFrame())
03082                             GetNVP()->getVideoOutput()->SetPrebuffering(false);
03083                         else
03084                             GetNVP()->getVideoOutput()->SetPrebuffering(true);
03085                     }
03086                 }
03087                 
03088                 if (ringBuffer->DVD()->PGCLengthChanged())
03089                 {
03090                     posmapStarted = false;
03091                     m_positionMap.clear();
03092                     SyncPositionMap();
03093                 }
03094 
03095                 UpdateDVDFramesPlayed();
03096                 VERBOSE(VB_PLAYBACK, QString(LOC + "DVD Cell Changed. "
03097                                              "Update framesPlayed: %1 ")
03098                                              .arg(framesPlayed));
03099             }
03100         }
03101 
03102         if (gotvideo)
03103         {
03104             if (lowbuffers && onlyvideo == 0 &&
03105                 storedPackets.count() < 75 &&
03106                 lastapts < lastvpts + 100 &&
03107                 !ringBuffer->InDVDMenuOrStillFrame())
03108             {
03109                 storevideoframes = true;
03110             }
03111             else if (onlyvideo >= 0)
03112             {
03113                 if (storedPackets.count() >=75)
03114                     VERBOSE(VB_IMPORTANT,
03115                             QString("Audio %1 ms behind video but already %2 "
03116                                "video frames queued. AV-Sync might be broken.")
03117                             .arg(lastvpts-lastapts).arg(storedPackets.count()));
03118                 allowedquit = true;
03119                 continue;
03120             }
03121         }
03122 
03123         if (!storevideoframes && storedPackets.count() > 0)
03124         {
03125             if (pkt)
03126             {
03127                 av_free_packet(pkt);
03128                 delete pkt;
03129             }
03130             pkt = storedPackets.first();
03131             storedPackets.removeFirst();
03132         }
03133         else
03134         {
03135             if (!pkt)
03136             {
03137                 pkt = new AVPacket;
03138                 bzero(pkt, sizeof(AVPacket));
03139                 av_init_packet(pkt);
03140             }
03141 
03142             if (!ic || (av_read_frame(ic, pkt) < 0))
03143             {
03144                 ateof = true;
03145                 GetNVP()->SetEof();
03146                 if (pkt)
03147                     delete pkt;
03148                 return false;
03149             }
03150 
03151             if (waitingForChange && pkt->pos >= readAdjust)
03152                 FileChanged();
03153 
03154             if (pkt->pos > readAdjust)
03155                 pkt->pos -= readAdjust;
03156         }
03157 
03158         if (pkt->stream_index > (int) ic->nb_streams)
03159         {
03160             VERBOSE(VB_IMPORTANT, LOC_ERR + "Bad stream");
03161             av_free_packet(pkt);
03162             continue;
03163         }
03164 
03165         len = pkt->size;
03166         ptr = pkt->data;
03167         pts = 0;
03168 
03169         AVStream *curstream = ic->streams[pkt->stream_index];
03170 
03171         if (pkt->dts != (int64_t)AV_NOPTS_VALUE)
03172             pts = (long long)(av_q2d(curstream->time_base) * pkt->dts * 1000);
03173 
03174         if (ringBuffer->isDVD() && 
03175             curstream->codec->codec_type == CODEC_TYPE_VIDEO)
03176         {
03177             MpegPreProcessPkt(curstream, pkt);
03178 
03179             if (mpeg_seq_end_seen && storevideoframes)
03180             {
03181                 ringBuffer->DVD()->InStillFrame(true);
03182             }
03183 
03184             bool inDVDStill = ringBuffer->DVD()->InStillFrame();
03185 
03186             if (!decodeStillFrame && inDVDStill)
03187             {
03188                 decodeStillFrame = true;
03189                 gContext->RestoreScreensaver();
03190                 d->ResetMPEG2();
03191             }
03192             
03193             if (mpeg_seq_end_seen)
03194             {
03195                 mpeg_seq_end_seen = false;
03196                 av_free_packet(pkt);
03197                 pkt = NULL;
03198                 continue;
03199             }
03200 
03201             if (!d->HasMPEG2Dec())
03202             {
03203                 int current_width = curstream->codec->width;
03204                 int video_width = GetNVP()->GetVideoSize().width();
03205                 if (dvd_xvmc_enabled && GetNVP() && GetNVP()->getVideoOutput())
03206                 {
03207                     bool dvd_xvmc_active = false;
03208                     if (video_codec_id > kCodec_NORMAL_END &&
03209                         video_codec_id < kCodec_VLD_END)
03210                     {
03211                         dvd_xvmc_active = true;
03212                     }
03213 
03214                     bool indvdmenu   = ringBuffer->InDVDMenuOrStillFrame();
03215                     if ((indvdmenu && dvd_xvmc_active) ||
03216                         ((!indvdmenu && !dvd_xvmc_active)))
03217                     {
03218                         VERBOSE(VB_PLAYBACK, LOC + QString("DVD Codec Change "
03219                                     "indvdmenu %1 dvd_xvmc_active %2")
03220                                 .arg(indvdmenu).arg(dvd_xvmc_active));
03221                         dvd_video_codec_changed = true;
03222                     }
03223                 }
03224                 
03225                 if ((video_width > 0 && video_width != current_width) ||
03226                     dvd_video_codec_changed)
03227                 {
03228                     VERBOSE(VB_PLAYBACK, LOC + QString("DVD Stream/Codec Change "
03229                                 "video_width %1 current_width %2 "
03230                                 "dvd_video_codec_changed %3")
03231                             .arg(video_width).arg(current_width)
03232                             .arg(dvd_video_codec_changed));
03233                     av_free_packet(pkt);
03234                     CloseCodecs();
03235                     ScanStreams(false);
03236                     allowedquit = true;
03237                     dvd_video_codec_changed = false;
03238                     continue;
03239                 }
03240             }
03241         }
03242 
03243         if (storevideoframes &&
03244             curstream->codec->codec_type == CODEC_TYPE_VIDEO)
03245         {
03246             av_dup_packet(pkt);
03247             storedPackets.append(pkt);
03248             pkt = NULL;
03249             continue;
03250         }
03251 
03252         if (len > 0 && curstream->codec->codec_type == CODEC_TYPE_VIDEO &&
03253             pkt->stream_index == selectedVideoIndex)
03254         {
03255             AVCodecContext *context = curstream->codec;
03256 
03257             if (context->codec_id == CODEC_ID_MPEG1VIDEO ||
03258                 context->codec_id == CODEC_ID_MPEG2VIDEO ||
03259                 context->codec_id == CODEC_ID_MPEG2VIDEO_XVMC ||
03260                 context->codec_id == CODEC_ID_MPEG2VIDEO_XVMC_VLD)
03261             {
03262                 if (!ringBuffer->isDVD())
03263                     MpegPreProcessPkt(curstream, pkt);
03264             }
03265             else if (context->codec_id == CODEC_ID_H264)
03266             {
03267                 H264PreProcessPkt(curstream, pkt);
03268             }
03269             else
03270             {
03271                 if (pkt->flags & PKT_FLAG_KEY)
03272                 {
03273                     HandleGopStart(pkt);
03274                     seen_gop = true;
03275                 }
03276                 else
03277                 {
03278                     seq_count++;
03279                     if (!seen_gop && seq_count > 1)
03280                     {
03281                         HandleGopStart(pkt);
03282                     }
03283                 }
03284             }
03285 
03286             if (framesRead == 0 && !justAfterChange &&
03287                 !(pkt->flags & PKT_FLAG_KEY))
03288             {
03289                 av_free_packet(pkt);
03290                 continue;
03291             }
03292 
03293             framesRead++;
03294             justAfterChange = false;
03295 
03296             if (exitafterdecoded)
03297                 gotvideo = 1;
03298 
03299             // If the resolution changed in XXXPreProcessPkt, we may
03300             // have a fatal error, so check for this before continuing.
03301             if (GetNVP()->IsErrored())
03302             {
03303                 av_free_packet(pkt);
03304                 if (pkt)
03305                     delete pkt;
03306                 return false;
03307             }
03308         }
03309 
03310         if (len > 0 &&
03311             curstream->codec->codec_type == CODEC_TYPE_DATA &&
03312             curstream->codec->codec_id   == CODEC_ID_MPEG2VBI)
03313         {
03314             ProcessVBIDataPacket(curstream, pkt);
03315 
03316             av_free_packet(pkt);
03317             continue;
03318         }
03319 
03320         if (len > 0 &&
03321             curstream->codec->codec_type == CODEC_TYPE_DATA &&
03322             curstream->codec->codec_id   == CODEC_ID_DVB_VBI)
03323         {
03324             ProcessDVBDataPacket(curstream, pkt);
03325 
03326             av_free_packet(pkt);
03327             continue;
03328         }
03329 
03330         if (len > 0 &&
03331             curstream->codec->codec_type == CODEC_TYPE_DATA &&
03332             curstream->codec->codec_id   == CODEC_ID_DSMCC_B)
03333         {
03334             ProcessDSMCCPacket(curstream, pkt);
03335 
03336             av_free_packet(pkt);
03337 
03338             // Have to return regularly to ensure that the OSD is updated.
03339             // This applies both to MHEG and also channel browsing.
03340             if (onlyvideo < 0)
03341             {
03342                 allowedquit |= (itv && itv->ImageHasChanged());
03343                 OSD *osd = NULL;
03344                 if (!allowedquit && GetNVP() && (osd = GetNVP()->GetOSD()))
03345                     allowedquit |=  osd->HasChanged();
03346             }
03347 
03348             continue;
03349         }
03350 
03351         // we don't care about other data streams
03352         if (curstream->codec->codec_type == CODEC_TYPE_DATA)
03353         {
03354             av_free_packet(pkt);
03355             continue;
03356         }
03357 
03358         if (!curstream->codec->codec)
03359         {
03360             VERBOSE(VB_PLAYBACK, LOC +
03361                     QString("No codec for stream index %1, type(%2) id(%3:%4)")
03362                     .arg(pkt->stream_index)
03363                     .arg(codec_type_string(curstream->codec->codec_type))
03364                     .arg(codec_id_string(curstream->codec->codec_id))
03365                     .arg(curstream->codec->codec_id));
03366             av_free_packet(pkt);
03367             continue;
03368         }
03369 
03370         firstloop = true;
03371         have_err = false;
03372 
03373         avcodeclock.lock();
03374         int ctype  = curstream->codec->codec_type;
03375         int audIdx = selectedTrack[kTrackTypeAudio].av_stream_index;
03376         int audSubIdx = selectedTrack[kTrackTypeAudio].av_substream_index;
03377         int subIdx = selectedTrack[kTrackTypeSubtitle].av_stream_index;
03378         avcodeclock.unlock();
03379 
03380         while (!have_err && len > 0)
03381         {
03382             int ret = 0;
03383             switch (ctype)
03384             {
03385                 case CODEC_TYPE_AUDIO:
03386                 {
03387                     bool reselectAudioTrack = false;
03388 
03390                     if (!GetNVP()->HasAudioIn())
03391                     {
03392                         VERBOSE(VB_AUDIO, LOC + "Audio is disabled - trying to restart it");
03393                         reselectAudioTrack = true;
03394                     }
03396 
03397                     // detect switches between stereo and dual languages
03398                     bool wasDual = audSubIdx != -1;
03399                     bool isDual = curstream->codec->avcodec_dual_language;
03400                     if ((wasDual && !isDual) || (!wasDual &&  isDual))
03401                     {
03402                         SetupAudioStreamSubIndexes(audIdx);
03403                         reselectAudioTrack = true;
03404                     }                            
03405 
03406                     bool do_ac3_passthru =
03407                         (allow_ac3_passthru && !transcoding &&
03408                          (curstream->codec->codec_id == CODEC_ID_AC3));
03409                     bool do_dts_passthru =
03410                         (allow_dts_passthru && !transcoding &&
03411                          (curstream->codec->codec_id == CODEC_ID_DTS));
03412                     bool using_passthru = do_ac3_passthru || do_dts_passthru;
03413 
03414                     // detect channels on streams that need
03415                     // to be decoded before we can know this
03416                     bool already_decoded = false;
03417                     if (!curstream->codec->channels)
03418                     {
03419                         QMutexLocker locker(&avcodeclock);
03420                         VERBOSE(VB_IMPORTANT, LOC +
03421                                 QString("Setting channels to %1")
03422                                 .arg(audioOut.channels));
03423 
03424                         if (using_passthru)
03425                         {
03426                             // for passthru let it select the max number
03427                             // of channels
03428                             curstream->codec->channels = 0;
03429                             curstream->codec->request_channels = 0;
03430                         }
03431                         else
03432                         {
03433                             curstream->codec->channels = audioOut.channels;
03434                             curstream->codec->request_channels =
03435                                 audioOut.channels;
03436                         }
03437                         ret = avcodec_decode_audio(
03438                             curstream->codec, audioSamples,
03439                             &data_size, ptr, len);
03440                         already_decoded = true;
03441 
03442                         reselectAudioTrack |= curstream->codec->channels;
03443                     }
03444 
03445                     if (reselectAudioTrack)
03446                     {
03447                         QMutexLocker locker(&avcodeclock);
03448                         currentTrack[kTrackTypeAudio] = -1;
03449                         selectedTrack[kTrackTypeAudio]
03450                             .av_stream_index = -1;
03451                         audIdx = -1;
03452                         audSubIdx = -1;
03453                         AutoSelectAudioTrack();
03454                         audIdx = selectedTrack[kTrackTypeAudio]
03455                             .av_stream_index;
03456                         audSubIdx = selectedTrack[kTrackTypeAudio]
03457                             .av_substream_index;
03458                     }
03459 
03460                     if ((onlyvideo > 0) || (pkt->stream_index != audIdx))
03461                     {
03462                         ptr += len;
03463                         len = 0;
03464                         continue;
03465                     }
03466 
03467                     if (firstloop && pkt->pts != (int64_t)AV_NOPTS_VALUE)
03468                         lastapts = (long long)(av_q2d(curstream->time_base) *
03469                                                pkt->pts * 1000);
03470 
03471                     if (skipaudio)
03472                     {
03473                         if ((lastapts < lastvpts - (10.0 / fps)) || 
03474                             lastvpts == 0)
03475                         {
03476                             ptr += len;
03477                             len = 0;
03478                             continue;
03479                         }
03480                         else
03481                             skipaudio = false;
03482                     }
03483 
03484                     avcodeclock.lock();
03485                     data_size = 0;
03486                     if (audioOut.do_passthru)
03487                     {
03488                         data_size = pkt->size;
03489                         bool dts = CODEC_ID_DTS == curstream->codec->codec_id;
03490                         ret = encode_frame(dts, ptr, len,
03491                                            audioSamples, data_size);
03492                     }
03493                     else
03494                     {
03495                         AVCodecContext *ctx = curstream->codec;
03496 
03497                         if ((ctx->channels == 0) ||
03498                             (ctx->channels > audioOut.channels))
03499                         {
03500                             ctx->channels = audioOut.channels;
03501                         }
03502 
03503                         if (!already_decoded)
03504                         {
03505                             curstream->codec->request_channels =
03506                                 audioOut.channels;
03507                             ret = avcodec_decode_audio(
03508                                 ctx, audioSamples, &data_size, ptr, len);
03509                         }
03510 
03511                         // When decoding some audio streams the number of
03512                         // channels, etc isn't known until we try decoding it.
03513                         if ((ctx->sample_rate != audioOut.sample_rate) ||
03514                             (ctx->channels    != audioOut.channels))
03515                         {
03516                             VERBOSE(VB_IMPORTANT, "audio stream changed");
03517                             currentTrack[kTrackTypeAudio] = -1;
03518                             selectedTrack[kTrackTypeAudio]
03519                                 .av_stream_index = -1;
03520                             audIdx = -1;
03521                             AutoSelectAudioTrack();
03522                             data_size = 0;
03523                         }
03524                     }
03525                     avcodeclock.unlock();
03526 
03527                     // BEGIN Is this really safe? -- dtk
03528                     if (data_size <= 0)
03529                     {
03530                         ptr += ret;
03531                         len -= ret;
03532                         continue;
03533                     }
03534                     // END Is this really safe? -- dtk
03535 
03536                     long long temppts = lastapts;
03537 
03538                     // calc for next frame
03539                     lastapts += (long long)((double)(data_size * 1000) /
03540                                 (curstream->codec->channels * 2) / 
03541                                 curstream->codec->sample_rate);
03542 
03543                     VERBOSE(VB_PLAYBACK|VB_TIMESTAMP,
03544                             LOC + QString("audio timecode %1 %2 %3 %4") 
03545                             .arg(pkt->pts).arg(pkt->dts)
03546                             .arg(temppts).arg(lastapts)); 
03547 
03548                     if (audSubIdx != -1)
03549                     {
03550                         extract_mono_channel(audSubIdx, &audioOut,
03551                                              (char*)audioSamples, data_size);
03552                     }
03553 
03554                     GetNVP()->AddAudioData(
03555                         (char *)audioSamples, data_size, temppts);
03556 
03557                     total_decoded_audio += data_size;
03558 
03559                     allowedquit |= ringBuffer->InDVDMenuOrStillFrame();
03560                     allowedquit |= (onlyvideo < 0) &&
03561                         (ofill + total_decoded_audio > othresh);
03562 
03563                     // top off audio buffers initially in audio only mode
03564                     if (!allowedquit && (onlyvideo < 0))
03565                     {
03566                         uint fill, total;
03567                         GetNVP()->GetAudioBufferStatus(fill, total);
03568                         total /= 6; // HACK needed for some audio files
03569                         allowedquit =
03570                             (fill == 0) || (fill > (total>>1)) ||
03571                             ((total - fill) < (uint) data_size) ||
03572                             (ofill + total_decoded_audio > (total>>2)) ||
03573                             ((total - fill) < (uint) data_size * 2);
03574                     }
03575 
03576                     break;
03577                 }
03578                 case CODEC_TYPE_VIDEO:
03579                 {
03580                     if (pkt->stream_index != selectedVideoIndex)
03581                     {
03582                         ptr += pkt->size;
03583                         len -= pkt->size;
03584                         continue;
03585                     }
03586                     
03587                     if (firstloop && pts != (int64_t) AV_NOPTS_VALUE)
03588                     {
03589                         lastccptsu = (long long)
03590                             (av_q2d(curstream->time_base)*pkt->pts*1000000);
03591                     }
03592                     if (onlyvideo < 0)
03593                     {
03594                         framesPlayed++;
03595                         gotvideo = 1;
03596                         ptr += pkt->size;
03597                         len -= pkt->size;
03598                         continue;
03599                     }
03600 
03601                     AVCodecContext *context = curstream->codec;
03602                     AVFrame mpa_pic;
03603                     bzero(&mpa_pic, sizeof(AVFrame));
03604 
03605                     int gotpicture = 0;
03606 
03607                     avcodeclock.lock();
03608                     if (d->HasDecoder())
03609                     {
03610                         if (decodeStillFrame)
03611                         {
03612                             int count = 0;
03613                             // HACK
03614                             while (!gotpicture && count < 5)
03615                             {
03616                                 ret = d->DecodeMPEG2Video(context, &mpa_pic,
03617                                                   &gotpicture, ptr, len);
03618                                 count++;
03619                             }
03620                         }
03621                         else
03622                         {
03623                             ret = d->DecodeMPEG2Video(context, &mpa_pic,
03624                                                 &gotpicture, ptr, len);
03625                         }
03626                     }
03627                     else
03628                     {
03629                         ret = avcodec_decode_video(context, &mpa_pic,
03630                                                    &gotpicture, ptr, len);
03631                         // Reparse it to not drop the DVD still frame
03632                         if (decodeStillFrame)
03633                             ret = avcodec_decode_video(context, &mpa_pic,
03634                                                         &gotpicture, ptr, len);
03635                     }
03636                     avcodeclock.unlock();
03637