Bug 1319987: P4. Refactor H264 Converter. r=cpearce

We can make some assumptions now that the Input method is only called once and never again while a decode is pending.

MozReview-Commit-ID: EmzKEcwNY2J

--HG--
extra : rebase_source : 42ae59878962b425970a60abe25d98c023ef4fdf
This commit is contained in:
Jean-Yves Avenard 2016-12-30 21:51:42 +11:00
Родитель 6a0bd6027f
Коммит c64edca1b9
3 изменённых файлов: 26 добавлений и 43 удалений

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

@ -52,6 +52,9 @@ H264Converter::Init()
void
H264Converter::Input(MediaRawData* aSample)
{
MOZ_RELEASE_ASSERT(!mInitPromiseRequest.Exists(),
"Still processing previous sample");
if (!mp4_demuxer::AnnexB::ConvertSampleToAVCC(aSample)) {
// We need AVCC content to be able to later parse the SPS.
// This is a no-op if the data is already AVCC.
@ -60,19 +63,6 @@ H264Converter::Input(MediaRawData* aSample)
return;
}
if (mInitPromiseRequest.Exists()) {
if (mNeedKeyframe) {
if (!aSample->mKeyframe) {
// Frames dropped, we need a new one.
mCallback->InputExhausted();
return;
}
mNeedKeyframe = false;
}
mMediaRawSamples.AppendElement(aSample);
return;
}
nsresult rv;
if (!mDecoder) {
// It is not possible to create an AVCC H264 decoder without SPS.
@ -87,12 +77,13 @@ H264Converter::Input(MediaRawData* aSample)
}
} else {
rv = CheckForSPSChange(aSample);
if (rv == NS_ERROR_NOT_INITIALIZED) {
}
if (rv == NS_ERROR_DOM_MEDIA_INITIALIZING_DECODER) {
// The decoder is pending initialization.
mCallback->InputExhausted();
return;
}
}
if (NS_FAILED(rv)) {
mCallback->Error(
MediaResult(NS_ERROR_DOM_MEDIA_FATAL_ERR,
@ -229,14 +220,14 @@ H264Converter::CreateDecoderAndInit(MediaRawData* aSample)
if (NS_SUCCEEDED(rv)) {
// Queue the incoming sample.
mMediaRawSamples.AppendElement(aSample);
mPendingSample = aSample;
mDecoder->Init()
->Then(AbstractThread::GetCurrent()->AsTaskQueue(), __func__, this,
&H264Converter::OnDecoderInitDone,
&H264Converter::OnDecoderInitFailed)
->Track(mInitPromiseRequest);
return NS_ERROR_NOT_INITIALIZED;
return NS_ERROR_DOM_MEDIA_INITIALIZING_DECODER;
}
return rv;
}
@ -245,32 +236,23 @@ void
H264Converter::OnDecoderInitDone(const TrackType aTrackType)
{
mInitPromiseRequest.Complete();
bool gotInput = false;
for (uint32_t i = 0 ; i < mMediaRawSamples.Length(); i++) {
const RefPtr<MediaRawData>& sample = mMediaRawSamples[i];
if (mNeedKeyframe) {
if (!sample->mKeyframe) {
continue;
RefPtr<MediaRawData> sample = mPendingSample.forget();
if (mNeedKeyframe && !sample->mKeyframe) {
mCallback->InputExhausted();
return;
}
mNeedKeyframe = false;
}
if (!mNeedAVCC &&
!mp4_demuxer::AnnexB::ConvertSampleToAnnexB(sample, mNeedKeyframe)) {
mCallback->Error(MediaResult(NS_ERROR_OUT_OF_MEMORY,
RESULT_DETAIL("ConvertSampleToAnnexB")));
mMediaRawSamples.Clear();
return;
}
mDecoder->Input(sample);
}
if (!gotInput) {
mCallback->InputExhausted();
}
mMediaRawSamples.Clear();
}
void
H264Converter::OnDecoderInitFailed(MediaResult aError)
H264Converter::OnDecoderInitFailed(const MediaResult& aError)
{
mInitPromiseRequest.Complete();
mCallback->Error(

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

@ -59,14 +59,14 @@ private:
void UpdateConfigFromExtraData(MediaByteBuffer* aExtraData);
void OnDecoderInitDone(const TrackType aTrackType);
void OnDecoderInitFailed(MediaResult aError);
void OnDecoderInitFailed(const MediaResult& aError);
RefPtr<PlatformDecoderModule> mPDM;
VideoInfo mCurrentConfig;
RefPtr<layers::KnowsCompositor> mKnowsCompositor;
RefPtr<layers::ImageContainer> mImageContainer;
const RefPtr<TaskQueue> mTaskQueue;
nsTArray<RefPtr<MediaRawData>> mMediaRawSamples;
RefPtr<MediaRawData> mPendingSample;
MediaDataDecoderCallback* mCallback;
RefPtr<MediaDataDecoder> mDecoder;
MozPromiseRequestHolder<InitPromise> mInitPromiseRequest;

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

@ -987,6 +987,7 @@
ERROR(NS_ERROR_DOM_MEDIA_DEMUXER_ERR, FAILURE(12)),
ERROR(NS_ERROR_DOM_MEDIA_CDM_ERR, FAILURE(13)),
ERROR(NS_ERROR_DOM_MEDIA_NEED_NEW_DECODER, FAILURE(14)),
ERROR(NS_ERROR_DOM_MEDIA_INITIALIZING_DECODER, FAILURE(15)),
/* Internal platform-related errors */
ERROR(NS_ERROR_DOM_MEDIA_CUBEB_INITIALIZATION_ERR, FAILURE(101)),