Bug 1656438 - Take the desired buffering as parameter in ClockDrift, AudioResampler, and friends. r=padenot

This makes us able to write tests for different buffer lengths.

Differential Revision: https://phabricator.services.mozilla.com/D89760
This commit is contained in:
Andreas Pehrson 2020-09-17 06:10:54 +00:00
Родитель 6f74e25fa2
Коммит 48120f9199
3 изменённых файлов: 38 добавлений и 23 удалений

Просмотреть файл

@ -36,15 +36,11 @@ class ClockDrift final {
/**
* Provide the nominal source and the target sample rate.
*/
ClockDrift(int32_t aSourceRate, int32_t aTargetRate)
ClockDrift(int32_t aSourceRate, int32_t aTargetRate,
int32_t aDesiredBuffering)
: mSourceRate(aSourceRate),
mTargetRate(aTargetRate),
mDesiredBuffering(5 * mSourceRate / 100) {
if (Preferences::HasUserValue("media.clockdrift.buffering")) {
int msecs = Preferences::GetInt("media.clockdrift.buffering");
mDesiredBuffering = msecs * mSourceRate / 100;
}
}
mDesiredBuffering(aDesiredBuffering) {}
/**
* The correction in the form of a ratio. A correction of 0.98 means that the
@ -118,14 +114,15 @@ class ClockDrift final {
mCorrection = std::min(std::max(mCorrection, 0.9f), 1.1f);
}
private:
public:
const int32_t mSourceRate;
const int32_t mTargetRate;
const int32_t mDesiredBuffering;
private:
float mCorrection = 1.0;
float mPreviousCorrection = 1.0;
const int32_t mAdjustementWindow = 100;
int32_t mDesiredBuffering; // defult: 5ms
int32_t mSourceClock = 0;
int32_t mTargetClock = 0;
@ -154,9 +151,12 @@ class ClockDrift final {
class AudioDriftCorrection final {
public:
AudioDriftCorrection(int32_t aSourceRate, int32_t aTargetRate)
: mClockDrift(aSourceRate, aTargetRate),
mResampler(aSourceRate, aTargetRate, aTargetRate / 20 /*50ms*/),
mTargetRate(aTargetRate) {}
: mDesiredBuffering(
std::max(1, Preferences::GetInt("media.clockdrift.buffering", 5)) *
aSourceRate / 1000),
mTargetRate(aTargetRate),
mClockDrift(aSourceRate, aTargetRate, mDesiredBuffering),
mResampler(aSourceRate, aTargetRate, mDesiredBuffering) {}
/**
* The source audio frames and request the number of target audio frames must
@ -188,10 +188,12 @@ class AudioDriftCorrection final {
return output;
}
const int32_t mDesiredBuffering;
const int32_t mTargetRate;
private:
ClockDrift mClockDrift;
AudioResampler mResampler;
const int32_t mTargetRate;
};
}; // namespace mozilla

Просмотреть файл

@ -136,9 +136,10 @@ void DynamicResampler::UpdateResampler(int aOutRate, int aChannels) {
// because allocates and this is executed in audio thread.
mInternalInBuffer.Clear();
for (int i = 0; i < mChannels; ++i) {
// Pre-allocate something big, 100ms of audio.
AudioRingBuffer* b =
mInternalInBuffer.AppendElement(sizeof(float) * mInRate / 10);
// Pre-allocate something big, twice the pre-buffer, or at least 100ms.
AudioRingBuffer* b = mInternalInBuffer.AppendElement(
sizeof(float) *
std::max(2 * mPreBufferFrames, static_cast<uint32_t>(mInRate) / 10));
if (mSampleFormat != AUDIO_FORMAT_SILENCE) {
// In ctor this update is not needed
b->SetSampleFormat(mSampleFormat);

Просмотреть файл

@ -13,7 +13,10 @@
TEST(TestClockDrift, Basic)
{
ClockDrift c(48000, 48000);
// Keep buffered frames to the wanted level in order to not affect that test.
const int buffered = 5 * 480;
ClockDrift c(48000, 48000, buffered);
EXPECT_EQ(c.GetCorrection(), 1.0);
// Keep buffered frames to the wanted level in order to not affect that test.
@ -43,7 +46,10 @@ TEST(TestClockDrift, Basic)
TEST(TestClockDrift, BasicResampler)
{
ClockDrift c(24000, 48000);
// Keep buffered frames to the wanted level in order to not affect that test.
const int buffered = 5 * 240;
ClockDrift c(24000, 48000, buffered);
for (int i = 0; i < 100; ++i) {
c.UpdateClock(240, 480, 5 * 240);
EXPECT_FLOAT_EQ(c.GetCorrection(), 1.0);
@ -76,7 +82,7 @@ TEST(TestClockDrift, BasicResampler)
TEST(TestClockDrift, BufferedInput)
{
ClockDrift c(48000, 48000);
ClockDrift c(48000, 48000, 5 * 480);
EXPECT_EQ(c.GetCorrection(), 1.0);
for (int i = 0; i < 100; ++i) {
@ -110,7 +116,7 @@ TEST(TestClockDrift, BufferedInput)
TEST(TestClockDrift, BufferedInputWithResampling)
{
ClockDrift c(24000, 48000);
ClockDrift c(24000, 48000, 5 * 240);
EXPECT_EQ(c.GetCorrection(), 1.0);
for (int i = 0; i < 100; ++i) {
@ -144,7 +150,10 @@ TEST(TestClockDrift, BufferedInputWithResampling)
TEST(TestClockDrift, Clamp)
{
ClockDrift c(48000, 48000);
// Keep buffered frames to the wanted level in order to not affect that test.
const int buffered = 5 * 480;
ClockDrift c(48000, 48000, buffered);
for (int i = 0; i < 100; ++i) {
c.UpdateClock(480, 480 + 2 * 48, 5 * 480); // +20%
@ -160,7 +169,10 @@ TEST(TestClockDrift, Clamp)
TEST(TestClockDrift, SmallDiff)
{
ClockDrift c(48000, 48000);
// Keep buffered frames to the wanted level in order to not affect that test.
const int buffered = 5 * 480;
ClockDrift c(48000, 48000, buffered);
for (int i = 0; i < 100; ++i) {
c.UpdateClock(480 + 4, 480, 5 * 480);
@ -185,7 +197,7 @@ TEST(TestClockDrift, SmallDiff)
TEST(TestClockDrift, SmallBufferedFrames)
{
ClockDrift c(48000, 48000);
ClockDrift c(48000, 48000, 5 * 480);
EXPECT_FLOAT_EQ(c.GetCorrection(), 1.0);
c.UpdateClock(480, 480, 5 * 480);