Bug 1120079: Do not call Range Removal algorithm after endOfStream. r=cajbir

--HG--
extra : rebase_source : 6a77cda482230943d88df228425e23e20f8860e0
This commit is contained in:
Jean-Yves Avenard 2015-01-16 23:49:02 +11:00
Родитель 776799bb61
Коммит eb3a3abff9
5 изменённых файлов: 35 добавлений и 17 удалений

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

@ -189,15 +189,15 @@ MediaSource::SetDuration(double aDuration, ErrorResult& aRv)
aRv.Throw(NS_ERROR_DOM_INVALID_STATE_ERR);
return;
}
SetDuration(aDuration);
SetDuration(aDuration, MSRangeRemovalAction::RUN);
}
void
MediaSource::SetDuration(double aDuration)
MediaSource::SetDuration(double aDuration, MSRangeRemovalAction aAction)
{
MOZ_ASSERT(NS_IsMainThread());
MSE_API("MediaSource(%p)::SetDuration(aDuration=%f)", this, aDuration);
mDecoder->SetMediaSourceDuration(aDuration);
mDecoder->SetMediaSourceDuration(aDuration, aAction);
}
already_AddRefed<SourceBuffer>
@ -285,7 +285,8 @@ MediaSource::EndOfStream(const Optional<MediaSourceEndOfStreamError>& aError, Er
mSourceBuffers->Ended();
mDecoder->Ended();
if (!aError.WasPassed()) {
mDecoder->SetMediaSourceDuration(mSourceBuffers->GetHighestBufferedEndTime());
mDecoder->SetMediaSourceDuration(mSourceBuffers->GetHighestBufferedEndTime(),
MSRangeRemovalAction::SKIP);
if (aRv.Failed()) {
return;
}

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

@ -29,6 +29,11 @@ namespace mozilla {
class ErrorResult;
template <typename T> class AsyncEventRunner;
enum MSRangeRemovalAction: uint8_t {
RUN = 0,
SKIP = 1
};
namespace dom {
class GlobalObject;
@ -129,7 +134,7 @@ private:
void InitializationEvent();
// SetDuration with no checks.
void SetDuration(double aDuration);
void SetDuration(double aDuration, MSRangeRemovalAction aAction);
nsRefPtr<SourceBufferList> mSourceBuffers;
nsRefPtr<SourceBufferList> mActiveSourceBuffers;

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

@ -173,7 +173,7 @@ MediaSourceDecoder::IsExpectingMoreData()
class DurationChangedRunnable : public nsRunnable {
public:
explicit DurationChangedRunnable(MediaSourceDecoder* aDecoder,
DurationChangedRunnable(MediaSourceDecoder* aDecoder,
double aOldDuration,
double aNewDuration)
: mDecoder(aDecoder)
@ -218,11 +218,13 @@ MediaSourceDecoder::SetDecodedDuration(int64_t aDuration)
if (aDuration >= 0) {
duration /= USECS_PER_S;
}
SetMediaSourceDuration(duration);
// No need to call Range Removal algorithm as this is called following
// ReadMetadata and nothing has been added to the source buffers yet.
SetMediaSourceDuration(duration, MSRangeRemovalAction::SKIP);
}
void
MediaSourceDecoder::SetMediaSourceDuration(double aDuration)
MediaSourceDecoder::SetMediaSourceDuration(double aDuration, MSRangeRemovalAction aAction)
{
ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
double oldDuration = mMediaSourceDuration;
@ -233,6 +235,14 @@ MediaSourceDecoder::SetMediaSourceDuration(double aDuration)
mDecoderStateMachine->SetDuration(INT64_MAX);
mMediaSourceDuration = PositiveInfinity<double>();
}
if (aAction == MSRangeRemovalAction::SKIP) {
if (NS_IsMainThread()) {
MediaDecoder::DurationChanged();
} else {
nsCOMPtr<nsIRunnable> task = NS_NewRunnableMethod(this, &MediaDecoder::DurationChanged);
NS_DispatchToMainThread(task);
}
} else {
if (NS_IsMainThread()) {
DurationChanged(oldDuration, mMediaSourceDuration);
} else {
@ -241,6 +251,7 @@ MediaSourceDecoder::SetMediaSourceDuration(double aDuration)
NS_DispatchToMainThread(task);
}
}
}
double
MediaSourceDecoder::GetMediaSourceDuration()

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

@ -21,6 +21,7 @@ class MediaResource;
class MediaDecoderStateMachine;
class SourceBufferDecoder;
class TrackBuffer;
enum MSRangeRemovalAction : uint8_t;
namespace dom {
@ -56,7 +57,7 @@ public:
bool IsExpectingMoreData() MOZ_OVERRIDE;
void SetDecodedDuration(int64_t aDuration);
void SetMediaSourceDuration(double aDuration);
void SetMediaSourceDuration(double aDuration, MSRangeRemovalAction aAction);
double GetMediaSourceDuration();
void DurationChanged(double aOldDuration, double aNewDuration);

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

@ -332,7 +332,7 @@ SourceBuffer::CheckEndTime()
// Check if we need to update mMediaSource duration
double endTime = GetBufferedEnd();
if (endTime > mMediaSource->Duration()) {
mMediaSource->SetDuration(endTime);
mMediaSource->SetDuration(endTime, MSRangeRemovalAction::SKIP);
}
}