Skip to content

Commit

Permalink
AE: let timestamps from sink delay propagate as far up as possible
Browse files Browse the repository at this point in the history
  • Loading branch information
elupus committed Jun 4, 2014
1 parent c91fe5e commit d66354d
Show file tree
Hide file tree
Showing 5 changed files with 35 additions and 31 deletions.
42 changes: 17 additions & 25 deletions xbmc/cores/AudioEngine/Engines/ActiveAE/ActiveAE.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,7 @@ using namespace ActiveAE;
void CEngineStats::Reset(unsigned int sampleRate)
{
CSingleLock lock(m_lock);
m_sinkUpdate = CurrentHostCounter();
m_sinkDelay = 0;
m_sinkDelay.SetDelay(0.0);
m_sinkSampleRate = sampleRate;
m_bufferedSamples = 0;
m_suspended = false;
Expand All @@ -49,8 +48,7 @@ void CEngineStats::Reset(unsigned int sampleRate)
void CEngineStats::UpdateSinkDelay(const AEDelayStatus& status, int samples)
{
CSingleLock lock(m_lock);
m_sinkUpdate = status.tick;
m_sinkDelay = status.delay;
m_sinkDelay = status;
if (samples > m_bufferedSamples)
{
CLog::Log(LOGERROR, "CEngineStats::UpdateSinkDelay - inconsistency in buffer time");
Expand Down Expand Up @@ -79,33 +77,21 @@ void CEngineStats::AddSamples(int samples, std::list<CActiveAEStream*> &streams)
}
}

float CEngineStats::GetDelay()
void CEngineStats::GetDelay(AEDelayStatus& status)
{
CSingleLock lock(m_lock);
int64_t now = CurrentHostCounter();
float delay = m_sinkDelay - (double)(now-m_sinkUpdate) / CurrentHostFrequency();
delay += (float)m_bufferedSamples / m_sinkSampleRate;

if (delay < 0)
delay = 0.0;

return delay;
status = m_sinkDelay;
status.delay += (double)m_bufferedSamples / m_sinkSampleRate;
}

// this is used to sync a/v so we need to add sink latency here
float CEngineStats::GetDelay(CActiveAEStream *stream)
void CEngineStats::GetDelay(AEDelayStatus& status, CActiveAEStream *stream)
{
CSingleLock lock(m_lock);
int64_t now = CurrentHostCounter();
float delay = m_sinkDelay - (double)(now-m_sinkUpdate) / CurrentHostFrequency();
delay += m_sinkLatency;
delay += (float)m_bufferedSamples / m_sinkSampleRate;

if (delay < 0)
delay = 0.0;
GetDelay(status);

delay += stream->m_bufferedTime / stream->m_streamResampleRatio;
return delay;
status.delay += m_sinkLatency;
status.delay += stream->m_bufferedTime / stream->m_streamResampleRatio;
}

float CEngineStats::GetCacheTime(CActiveAEStream *stream)
Expand Down Expand Up @@ -589,7 +575,11 @@ void CActiveAE::StateMachine(int signal, Protocol *port, Message *msg)
if (m_extKeepConfig)
m_extDrainTimer.Set(m_extKeepConfig);
else
m_extDrainTimer.Set(m_stats.GetDelay() * 1000);
{
AEDelayStatus status;
m_stats.GetDelay(status);
m_extDrainTimer.Set(status.GetDelay() * 1000);
}
m_extDrain = true;
}
m_extTimeout = 0;
Expand Down Expand Up @@ -1913,8 +1903,10 @@ bool CActiveAE::RunStages()
}
else
CLog::Log(LOGWARNING,"ActiveAE::%s - viz ran out of free buffers", __FUNCTION__);
AEDelayStatus status;
m_stats.GetDelay(status);
unsigned int now = XbmcThreads::SystemClockMillis();
unsigned int timestamp = now + m_stats.GetDelay() * 1000;
unsigned int timestamp = now + status.GetDelay() * 1000;
busy |= m_vizBuffers->ResampleBuffers(timestamp);
while(!m_vizBuffers->m_outputSamples.empty())
{
Expand Down
9 changes: 4 additions & 5 deletions xbmc/cores/AudioEngine/Engines/ActiveAE/ActiveAE.h
Original file line number Diff line number Diff line change
Expand Up @@ -162,8 +162,8 @@ class CEngineStats
void Reset(unsigned int sampleRate);
void UpdateSinkDelay(const AEDelayStatus& status, int samples);
void AddSamples(int samples, std::list<CActiveAEStream*> &streams);
float GetDelay();
float GetDelay(CActiveAEStream *stream);
void GetDelay(AEDelayStatus& status);
void GetDelay(AEDelayStatus& status, CActiveAEStream *stream);
float GetCacheTime(CActiveAEStream *stream);
float GetCacheTotal(CActiveAEStream *stream);
float GetWaterLevel();
Expand All @@ -173,12 +173,11 @@ class CEngineStats
bool IsSuspended();
CCriticalSection *GetLock() { return &m_lock; }
protected:
float m_sinkDelay;
float m_sinkCacheTotal;
float m_sinkLatency;
int m_bufferedSamples;
unsigned int m_sinkSampleRate;
int64_t m_sinkUpdate;
AEDelayStatus m_sinkDelay;
bool m_suspended;
CCriticalSection m_lock;
};
Expand Down Expand Up @@ -242,7 +241,7 @@ class CActiveAE : public IAE, private CThread
void PlaySound(CActiveAESound *sound);
uint8_t **AllocSoundSample(SampleConfig &config, int &samples, int &bytes_per_sample, int &planes, int &linesize);
void FreeSoundSample(uint8_t **data);
float GetDelay(CActiveAEStream *stream) { return m_stats.GetDelay(stream); }
void GetDelay(AEDelayStatus& status, CActiveAEStream *stream) { m_stats.GetDelay(status, stream); }
float GetCacheTime(CActiveAEStream *stream) { return m_stats.GetCacheTime(stream); }
float GetCacheTotal(CActiveAEStream *stream) { return m_stats.GetCacheTotal(stream); }
void FlushStream(CActiveAEStream *stream);
Expand Down
4 changes: 3 additions & 1 deletion xbmc/cores/AudioEngine/Engines/ActiveAE/ActiveAEStream.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -280,7 +280,9 @@ unsigned int CActiveAEStream::AddData(void *data, unsigned int size)

double CActiveAEStream::GetDelay()
{
return AE.GetDelay(this);
AEDelayStatus status;
AE.GetDelay(status, this);
return status.GetDelay();
}

bool CActiveAEStream::IsBuffering()
Expand Down
10 changes: 10 additions & 0 deletions xbmc/cores/AudioEngine/Utils/AEUtil.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,16 @@ void AEDelayStatus::SetDelay(double d)
tick = CurrentHostCounter();
}

double AEDelayStatus::GetDelay()
{
double d = delay;
d -= (double)(CurrentHostCounter() - tick) / CurrentHostFrequency();
if(d < 0)
return 0.0;
else
return d;
}

CAEChannelInfo CAEUtil::GuessChLayout(const unsigned int channels)
{
CLog::Log(LOGWARNING, "CAEUtil::GuessChLayout - "
Expand Down
1 change: 1 addition & 0 deletions xbmc/cores/AudioEngine/Utils/AEUtil.h
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ struct AEDelayStatus
{}

void SetDelay(double d);
double GetDelay();

double delay; /*!< delay in sink currently */
int64_t tick; /*!< timestamp when delay was calculated */
Expand Down

0 comments on commit d66354d

Please sign in to comment.