Permalink
Browse files

ssif: tidy up the logic for merging ssif packets

  • Loading branch information...
popcornmix committed Jan 23, 2016
1 parent e5fb05e commit 4005fb8ea3d3cc5c078a692c43538e614c44f38e
Showing with 75 additions and 82 deletions.
  1. +75 −82 xbmc/cores/VideoPlayer/DVDDemuxers/DVDDemuxFFmpeg.cpp
@@ -21,6 +21,7 @@
#include "DVDDemuxFFmpeg.h"
#include <utility>
#include <assert.h>
#include "commons/Exception.h"
#include "cores/FFmpeg.h"
@@ -195,7 +196,6 @@ CDVDDemuxFFmpeg::CDVDDemuxFFmpeg() : CDVDDemux()
m_bMatroska = false;
m_bAVI = false;
m_bSSIF = false;
m_bSSIFSyncing = false;
m_speed = DVD_PLAYSPEED_NORMAL;
m_program = UINT_MAX;
m_pkt.result = -1;
@@ -503,7 +503,7 @@ bool CDVDDemuxFFmpeg::Open(CDVDInputStream* pInput, bool streaminfo, bool filein
if (m_checkvideo)
{
// make sure we start video with an i-frame
//ResetVideoStreams();
ResetVideoStreams();
}
}
else
@@ -539,6 +539,9 @@ void CDVDDemuxFFmpeg::Dispose()
{
m_pkt.result = -1;
av_free_packet(&m_pkt.pkt);
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> Dispose: flushing queue(%d,%d)", m_MVCqueue.size(), m_H264queue.size());
#endif
while (!m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
@@ -549,7 +552,6 @@ void CDVDDemuxFFmpeg::Dispose()
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
m_MVCqueue.pop();
}
m_bSSIFSyncing = true;
if (m_pFormatContext)
{
@@ -598,6 +600,9 @@ void CDVDDemuxFFmpeg::Flush()
m_pkt.result = -1;
av_free_packet(&m_pkt.pkt);
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> Flush: flushing queue(%d,%d)", m_MVCqueue.size(), m_H264queue.size());
#endif
while (!m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
@@ -608,7 +613,6 @@ void CDVDDemuxFFmpeg::Flush()
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
m_MVCqueue.pop();
}
m_bSSIFSyncing = true;
}
void CDVDDemuxFFmpeg::Abort()
@@ -764,102 +768,76 @@ DemuxPacket* movePacket(DemuxPacket* &srcPkt)
DemuxPacket* CDVDDemuxFFmpeg::GetMVCPacket()
{
// Here, we recreate a h264 MVC packet from the base one + buffered MVC NALU's
DemuxPacket* newpkt = NULL;
double tsH264 = DVD_NOPTS_VALUE;
DemuxPacket* h264pkt = NULL;
if (!m_H264queue.empty())
while (!m_H264queue.empty() && !m_MVCqueue.empty())
{
h264pkt = m_H264queue.front();
tsH264 = (h264pkt->dts != DVD_NOPTS_VALUE ? h264pkt->dts : h264pkt->pts);
//CLog::Log(LOGDEBUG, ">>> MVC h264 packet: %d, pts(%f) dts (%f)", h264pkt->iSize, h264pkt->pts, h264pkt->dts);
}
DemuxPacket* h264pkt = m_H264queue.front();
double tsH264 = (h264pkt->dts != DVD_NOPTS_VALUE ? h264pkt->dts : h264pkt->pts);
DemuxPacket* mvcpkt = m_MVCqueue.front();
double tsMVC = (mvcpkt->dts != DVD_NOPTS_VALUE ? mvcpkt->dts : mvcpkt->pts);
double tsMVC = DVD_NOPTS_VALUE;
DemuxPacket* mvcpkt = NULL;
if (!m_MVCqueue.empty())
{
mvcpkt = m_MVCqueue.front();
tsMVC = (mvcpkt->dts != DVD_NOPTS_VALUE ? mvcpkt->dts : mvcpkt->pts);
//CLog::Log(LOGDEBUG, ">>> MVC mvc packet: %d, pts(%f) dts (%f)", mvcpkt->iSize, mvcpkt->pts, mvcpkt->dts);
}
if (tsH264 == tsMVC)
{
m_bSSIFSyncing = false;
m_H264queue.pop();
m_MVCqueue.pop();
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC merge packet: %d+%d, pts(%f/%f) dts (%f/%f)", h264pkt->iSize, mvcpkt->iSize, h264pkt->pts, mvcpkt->pts, h264pkt->dts, mvcpkt->dts);
#endif
newpkt = mergePacket(h264pkt, mvcpkt);
if (!m_MVCqueue.empty())
if (tsH264 == tsMVC)
{
mvcpkt = m_MVCqueue.front();
while (mvcpkt->dts == DVD_NOPTS_VALUE && mvcpkt->pts == DVD_NOPTS_VALUE)
m_H264queue.pop();
m_MVCqueue.pop();
while (!m_H264queue.empty())
{
// Append leftover
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC merge leftover: %d+%d, pts(%f) dts (%f)", newpkt->iSize, mvcpkt->iSize, newpkt->pts, newpkt->dts);
#endif
newpkt = mergePacket(newpkt, mvcpkt);
m_MVCqueue.pop();
if (m_MVCqueue.empty())
DemuxPacket* pkt = m_H264queue.front();
double ts = (pkt->dts != DVD_NOPTS_VALUE ? pkt->dts : pkt->pts);
if (ts == DVD_NOPTS_VALUE)
{
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC merge h264 fragment: %6d+%6d, pts(%.3f/%.3f) dts(%.3f/%.3f)", h264pkt->iSize, pkt->iSize, h264pkt->pts*1e-6, pkt->pts*1e-6, h264pkt->dts*1e-6, pkt->dts*1e-6);
#endif
h264pkt = mergePacket(h264pkt, pkt);
m_H264queue.pop();
}
else
break;
mvcpkt = m_MVCqueue.front();
}
}
}
else if (tsH264 > tsMVC)
{
// H264 before MVC ?
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC missing mvc: %d, pts(%f) dts (%f)", h264pkt->iSize, h264pkt->pts, h264pkt->dts);
#endif
if (m_bSSIFSyncing)
{
if (!m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
m_H264queue.pop();
}
while (!m_MVCqueue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
m_MVCqueue.pop();
DemuxPacket* pkt = m_MVCqueue.front();
double ts = (pkt->dts != DVD_NOPTS_VALUE ? pkt->dts : pkt->pts);
if (ts == DVD_NOPTS_VALUE)
{
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC merge mvc fragment: %6d+%6d, pts(%.3f/%.3f) dts(%.3f/%.3f)", mvcpkt->iSize, pkt->iSize, mvcpkt->pts*1e-6, pkt->pts*1e-6, mvcpkt->dts*1e-6, pkt->dts*1e-6);
#endif
mvcpkt = mergePacket(mvcpkt, pkt);
m_MVCqueue.pop();
}
else
break;
}
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC merge packet: %6d+%6d, pts(%.3f/%.3f) dts(%.3f/%.3f)", h264pkt->iSize, mvcpkt->iSize, h264pkt->pts*1e-6, mvcpkt->pts*1e-6, h264pkt->dts*1e-6, mvcpkt->dts*1e-6);
#endif
return mergePacket(h264pkt, mvcpkt);
}
else if (!m_MVCqueue.empty())
else if (tsH264 > tsMVC)
{
// pop or we are stuck
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC discard mvc: %6d, pts(%.3f) dts(%.3f)", mvcpkt->iSize, mvcpkt->pts*1e-6, mvcpkt->dts*1e-6);
#endif
CDVDDemuxUtils::FreeDemuxPacket(mvcpkt);
m_MVCqueue.pop();
}
newpkt = CDVDDemuxUtils::AllocateDemuxPacket(0);
newpkt->iSize = 0;
}
else
{
if (m_bSSIFSyncing && !m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
m_H264queue.pop();
}
else if (!m_H264queue.empty())
else
{
// missing an MVC packets
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC missing mvc2: %d, pts(%f) dts (%f)", h264pkt->iSize, h264pkt->pts, h264pkt->dts);
CLog::Log(LOGDEBUG, ">>> MVC discard h264: %6d, pts(%.3f) dts(%.3f)", h264pkt->iSize, h264pkt->pts*1e-6, h264pkt->dts*1e-6);
#endif
// pop or we are stuck
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
CDVDDemuxUtils::FreeDemuxPacket(h264pkt);
m_H264queue.pop();
}
newpkt = CDVDDemuxUtils::AllocateDemuxPacket(0);
newpkt->iSize = 0;
}
return newpkt;
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> MVC waiting. MVC(%d) H264(%d)", m_MVCqueue.size(), m_H264queue.size());
#endif
return CDVDDemuxUtils::AllocateDemuxPacket(0);
}
DemuxPacket* CDVDDemuxFFmpeg::Read()
@@ -926,6 +904,11 @@ DemuxPacket* CDVDDemuxFFmpeg::Read()
m_pkt.result = -1;
av_free_packet(&m_pkt.pkt);
while (!m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
m_H264queue.pop();
}
while (!m_MVCqueue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
@@ -1086,6 +1069,9 @@ DemuxPacket* CDVDDemuxFFmpeg::Read()
{
DemuxPacket* newpkt = movePacket(pPacket);
m_H264queue.push(newpkt);
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> Got H264: %6d, pts(%.3f) dts(%.3f) queue(%d)", newpkt->iSize, newpkt->pts*1e-6, newpkt->dts*1e-6, m_H264queue.size());
#endif
pPacket = GetMVCPacket();
}
}
@@ -1095,6 +1081,9 @@ DemuxPacket* CDVDDemuxFFmpeg::Read()
{
DemuxPacket* newpkt = movePacket(pPacket);
m_MVCqueue.push(newpkt);
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> Got MVC: %6d, pts(%.3f) dts(%.3f) queue(%d)", newpkt->iSize, newpkt->pts*1e-6, newpkt->dts*1e-6, m_MVCqueue.size());
#endif
pPacket = GetMVCPacket();
if (pPacket->iSize)
stream = GetStreamInternal(pPacket->iStreamId);
@@ -1122,6 +1111,9 @@ bool CDVDDemuxFFmpeg::SeekTime(int time, bool backwords, double *startpts)
m_pkt.result = -1;
av_free_packet(&m_pkt.pkt);
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> SeekTime: flushing queue(%d,%d)", m_MVCqueue.size(), m_H264queue.size());
#endif
while (!m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
@@ -1132,7 +1124,6 @@ bool CDVDDemuxFFmpeg::SeekTime(int time, bool backwords, double *startpts)
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
m_MVCqueue.pop();
}
m_bSSIFSyncing = true;
CDVDInputStream::ISeekTime* ist = dynamic_cast<CDVDInputStream::ISeekTime*>(m_pInput);
if (ist)
@@ -1200,6 +1191,9 @@ bool CDVDDemuxFFmpeg::SeekByte(int64_t pos)
m_pkt.result = -1;
av_free_packet(&m_pkt.pkt);
#if defined(DEBUG_VERBOSE)
CLog::Log(LOGDEBUG, ">>> SeekByte: flushing queue(%d,%d)", m_MVCqueue.size(), m_H264queue.size());
#endif
while (!m_H264queue.empty())
{
CDVDDemuxUtils::FreeDemuxPacket(m_H264queue.front());
@@ -1210,7 +1204,6 @@ bool CDVDDemuxFFmpeg::SeekByte(int64_t pos)
CDVDDemuxUtils::FreeDemuxPacket(m_MVCqueue.front());
m_MVCqueue.pop();
}
m_bSSIFSyncing = true;
return (ret >= 0);
}

0 comments on commit 4005fb8

Please sign in to comment.