2 * Copyright 2012 Michael Chen <omxcodec@gmail.com>
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
18 #define LOG_TAG "SoftFFmpegAudio"
19 #include <utils/Log.h>
21 #include "SoftFFmpegAudio.h"
23 #include <media/stagefright/foundation/ADebug.h>
24 #include <media/stagefright/foundation/hexdump.h>
25 #include <media/stagefright/MediaDefs.h>
27 #include "ffmpeg_utils/ffmpeg_utils.h"
38 static void InitOMXParams(T *params) {
39 params->nSize = sizeof(T);
40 params->nVersion.s.nVersionMajor = 1;
41 params->nVersion.s.nVersionMinor = 0;
42 params->nVersion.s.nRevision = 0;
43 params->nVersion.s.nStep = 0;
46 SoftFFmpegAudio::SoftFFmpegAudio(
48 const OMX_CALLBACKTYPE *callbacks,
50 OMX_COMPONENTTYPE **component)
51 : SimpleSoftOMXComponent(name, callbacks, appData, component),
56 mExtradataReady(false),
57 mIgnoreExtradata(false),
58 mFlushComplete(false),
59 mSignalledError(false),
68 mSamplingFmt(AV_SAMPLE_FMT_S16),
69 mAudioConfigChanged(false),
70 mOutputPortSettingsChange(NONE) {
71 if (!strcmp(name, "OMX.ffmpeg.mp3.decoder")) {
73 mIgnoreExtradata = true;
74 } else if (!strcmp(name, "OMX.ffmpeg.mp1.decoder")) {
76 } else if (!strcmp(name, "OMX.ffmpeg.mp2.decoder")) {
78 } else if (!strcmp(name, "OMX.ffmpeg.aac.decoder")) {
80 } else if (!strcmp(name, "OMX.ffmpeg.ape.decoder")) {
82 } else if (!strcmp(name, "OMX.ffmpeg.wma.decoder")) {
84 } else if (!strcmp(name, "OMX.ffmpeg.dts.decoder")) {
86 } else if (!strcmp(name, "OMX.ffmpeg.ra.decoder")) {
89 CHECK(!strcmp(name, "OMX.ffmpeg.ac3.decoder"));
93 LOGV("SoftFFmpegAudio component: %s", name);
96 CHECK_EQ(initDecoder(), (status_t)OK);
99 SoftFFmpegAudio::~SoftFFmpegAudio() {
101 LOGV("~SoftFFmpegAudio");
106 void SoftFFmpegAudio::initPorts() {
107 OMX_PARAM_PORTDEFINITIONTYPE def;
111 def.eDir = OMX_DirInput;
112 def.nBufferCountMin = kNumBuffers;
113 def.nBufferCountActual = def.nBufferCountMin;
114 def.nBufferSize = 8192;
115 def.bEnabled = OMX_TRUE;
116 def.bPopulated = OMX_FALSE;
117 def.eDomain = OMX_PortDomainAudio;
118 def.bBuffersContiguous = OMX_FALSE;
119 def.nBufferAlignment = 1;
123 def.format.audio.cMIMEType = const_cast<char *>(MEDIA_MIMETYPE_AUDIO_MPEG);
124 def.format.audio.eEncoding = OMX_AUDIO_CodingMP3;
127 def.format.audio.cMIMEType = const_cast<char *>(MEDIA_MIMETYPE_AUDIO_MPEG_LAYER_I);
128 def.format.audio.eEncoding = OMX_AUDIO_CodingMP3;
131 def.format.audio.cMIMEType = const_cast<char *>(MEDIA_MIMETYPE_AUDIO_MPEG_LAYER_II);
132 def.format.audio.eEncoding = OMX_AUDIO_CodingMP3;
135 def.format.audio.cMIMEType = const_cast<char *>(MEDIA_MIMETYPE_AUDIO_AAC);
136 def.format.audio.eEncoding = OMX_AUDIO_CodingAAC;
139 def.format.audio.cMIMEType = const_cast<char *>(MEDIA_MIMETYPE_AUDIO_AC3);
141 //def.format.audio.eEncoding = OMX_AUDIO_CodingAC3;
142 def.format.audio.eEncoding = OMX_AUDIO_CodingAutoDetect; // right?? orz
145 CHECK(!"Should not be here. Unsupported mime type and compression format");
149 def.format.audio.pNativeRender = NULL;
150 def.format.audio.bFlagErrorConcealment = OMX_FALSE;
155 def.eDir = OMX_DirOutput;
156 def.nBufferCountMin = kNumBuffers;
157 def.nBufferCountActual = def.nBufferCountMin;
158 def.nBufferSize = kOutputBufferSize;
159 def.bEnabled = OMX_TRUE;
160 def.bPopulated = OMX_FALSE;
161 def.eDomain = OMX_PortDomainAudio;
162 def.bBuffersContiguous = OMX_FALSE;
163 def.nBufferAlignment = 2;
165 def.format.audio.cMIMEType = const_cast<char *>("audio/raw");
166 def.format.audio.pNativeRender = NULL;
167 def.format.audio.bFlagErrorConcealment = OMX_FALSE;
168 def.format.audio.eEncoding = OMX_AUDIO_CodingPCM;
173 static int lockmgr(void **mtx, enum AVLockOp op) {
176 *mtx = (void *)SDL_CreateMutex();
181 return !!SDL_LockMutex((SDL_mutex *)*mtx);
182 case AV_LOCK_RELEASE:
183 return !!SDL_UnlockMutex((SDL_mutex *)*mtx);
184 case AV_LOCK_DESTROY:
185 SDL_DestroyMutex((SDL_mutex *)*mtx);
191 void SoftFFmpegAudio::setAVCtxToDefault(AVCodecContext *avctx, const AVCodec *codec) {
194 avctx->workaround_bugs = 1;
196 if(avctx->lowres > codec->max_lowres){
197 LOGW("The maximum value for lowres supported by the decoder is %d",
199 avctx->lowres= codec->max_lowres;
201 avctx->idct_algo = 0;
202 avctx->skip_frame = AVDISCARD_DEFAULT;
203 avctx->skip_idct = AVDISCARD_DEFAULT;
204 avctx->skip_loop_filter = AVDISCARD_DEFAULT;
205 avctx->error_concealment = 3;
207 if(avctx->lowres) avctx->flags |= CODEC_FLAG_EMU_EDGE;
208 if (fast) avctx->flags2 |= CODEC_FLAG2_FAST;
209 if(codec->capabilities & CODEC_CAP_DR1)
210 avctx->flags |= CODEC_FLAG_EMU_EDGE;
213 status_t SoftFFmpegAudio::initDecoder() {
216 status = initFFmpeg();
220 mCtx = avcodec_alloc_context3(NULL);
223 LOGE("avcodec_alloc_context failed.");
227 mCtx->codec_type = AVMEDIA_TYPE_AUDIO;
230 mCtx->codec_id = CODEC_ID_MP3;
233 mCtx->codec_id = CODEC_ID_MP1;
236 mCtx->codec_id = CODEC_ID_MP2;
239 mCtx->codec_id = CODEC_ID_AAC;
242 mCtx->codec_id = CODEC_ID_AC3;
245 CHECK(!"Should not be here. Unsupported codec");
249 mCtx->codec = avcodec_find_decoder(mCtx->codec_id);
252 LOGE("find codec failed");
256 setAVCtxToDefault(mCtx, mCtx->codec);
258 mCtx->sample_fmt = AV_SAMPLE_FMT_S16;
260 mAudioSrcFmt = mAudioTgtFmt = AV_SAMPLE_FMT_S16;
261 mAudioSrcFreq = mAudioTgtFreq = mSamplingRate;
262 mAudioSrcChannels = mAudioTgtChannels = mNumChannels;
263 mAudioSrcChannelLayout = mAudioTgtChannelLayout =
264 av_get_default_channel_layout(mNumChannels);
266 memset(mSilenceBuffer, 0, kOutputBufferSize);
271 void SoftFFmpegAudio::deInitDecoder() {
273 //avcodec_flush_buffers(mCtx); // is it necessary? crash sometimes if call it
274 if (!mCtx->extradata) {
275 av_free(mCtx->extradata);
276 mCtx->extradata = NULL;
277 mCtx->extradata_size = 0;
291 OMX_ERRORTYPE SoftFFmpegAudio::internalGetParameter(
292 OMX_INDEXTYPE index, OMX_PTR params) {
293 int32_t channels = 0;
294 int32_t sampling_rate = 0;
297 case OMX_IndexParamAudioAac:
299 OMX_AUDIO_PARAM_AACPROFILETYPE *aacParams =
300 (OMX_AUDIO_PARAM_AACPROFILETYPE *)params;
302 if (aacParams->nPortIndex != 0) {
303 return OMX_ErrorUndefined;
306 aacParams->nBitRate = 0;
307 aacParams->nAudioBandWidth = 0;
308 aacParams->nAACtools = 0;
309 aacParams->nAACERtools = 0;
310 aacParams->eAACProfile = OMX_AUDIO_AACObjectMain;
311 aacParams->eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4FF;
312 aacParams->eChannelMode = OMX_AUDIO_ChannelModeStereo;
314 aacParams->nChannels = mNumChannels;
315 aacParams->nSampleRate = mSamplingRate;
317 return OMX_ErrorNone;
319 case OMX_IndexParamAudioPcm:
321 OMX_AUDIO_PARAM_PCMMODETYPE *pcmParams =
322 (OMX_AUDIO_PARAM_PCMMODETYPE *)params;
324 if (pcmParams->nPortIndex > 1) {
325 return OMX_ErrorUndefined;
328 pcmParams->eNumData = OMX_NumericalDataSigned;
329 pcmParams->eEndian = OMX_EndianBig;
330 pcmParams->bInterleaved = OMX_TRUE;
331 pcmParams->nBitPerSample = 16;
332 pcmParams->ePCMMode = OMX_AUDIO_PCMModeLinear;
333 pcmParams->eChannelMapping[0] = OMX_AUDIO_ChannelLF;
334 pcmParams->eChannelMapping[1] = OMX_AUDIO_ChannelRF;
336 channels = mNumChannels >= 2 ? 2 : 1;
337 sampling_rate = mSamplingRate;
338 // 4000 <= nSamplingRate <= 48000
339 if (mSamplingRate < 4000) {
340 sampling_rate = 4000;
341 } else if (mSamplingRate > 48000) {
342 sampling_rate = 48000;
345 // update src and target(except aac), only once!
346 mAudioSrcChannels = mAudioTgtChannels = channels;
347 mAudioSrcFreq = mAudioTgtFreq = sampling_rate;
348 mAudioSrcFmt = mAudioTgtFmt = AV_SAMPLE_FMT_S16;
349 mAudioSrcChannelLayout = mAudioTgtChannelLayout = av_get_default_channel_layout(channels);
351 pcmParams->nChannels = channels;
352 pcmParams->nSamplingRate = sampling_rate;
354 return OMX_ErrorNone;
358 return SimpleSoftOMXComponent::internalGetParameter(index, params);
362 OMX_ERRORTYPE SoftFFmpegAudio::internalSetParameter(
363 OMX_INDEXTYPE index, const OMX_PTR params) {
364 int32_t channels = 0;
365 int32_t sampling_rate = 0;
368 case OMX_IndexParamStandardComponentRole:
370 const OMX_PARAM_COMPONENTROLETYPE *roleParams =
371 (const OMX_PARAM_COMPONENTROLETYPE *)params;
373 bool supported = true;
376 if (strncmp((const char *)roleParams->cRole,
377 "audio_decoder.mp3", OMX_MAX_STRINGNAME_SIZE - 1))
381 if (strncmp((const char *)roleParams->cRole,
382 "audio_decoder.mp1", OMX_MAX_STRINGNAME_SIZE - 1))
386 if (strncmp((const char *)roleParams->cRole,
387 "audio_decoder.mp2", OMX_MAX_STRINGNAME_SIZE - 1))
391 if (strncmp((const char *)roleParams->cRole,
392 "audio_decoder.aac", OMX_MAX_STRINGNAME_SIZE - 1))
396 if (strncmp((const char *)roleParams->cRole,
397 "audio_decoder.ac3", OMX_MAX_STRINGNAME_SIZE - 1))
401 CHECK(!"Should not be here. Unsupported role.");
405 LOGE("unsupported role: %s", (const char *)roleParams->cRole);
406 return OMX_ErrorUndefined;
409 return OMX_ErrorNone;
411 case OMX_IndexParamAudioAac:
413 const OMX_AUDIO_PARAM_AACPROFILETYPE *aacParams =
414 (const OMX_AUDIO_PARAM_AACPROFILETYPE *)params;
416 if (aacParams->nPortIndex != 0) {
417 return OMX_ErrorUndefined;
420 mNumChannels = aacParams->nChannels;
421 mSamplingRate = aacParams->nSampleRate;
423 channels = mNumChannels >= 2 ? 2 : 1;
424 sampling_rate = mSamplingRate;
425 // 4000 <= nSamplingRate <= 48000
426 if (mSamplingRate < 4000) {
427 sampling_rate = 4000;
428 } else if (mSamplingRate > 48000) {
429 sampling_rate = 48000;
432 // update src and target(only aac), only once!
433 mAudioSrcChannels = mAudioTgtChannels = channels;
434 mAudioSrcFreq = mAudioTgtFreq = sampling_rate;
435 mAudioSrcFmt = mAudioTgtFmt = AV_SAMPLE_FMT_S16;
436 mAudioSrcChannelLayout = mAudioTgtChannelLayout = av_get_default_channel_layout(channels);
438 LOGV("got OMX_IndexParamAudioAac, mNumChannels: %d, mSamplingRate: %d",
439 mNumChannels, mSamplingRate);
441 return OMX_ErrorNone;
444 LOGI("internalSetParameter, index: 0x%x", index);
445 return SimpleSoftOMXComponent::internalSetParameter(index, params);
449 void SoftFFmpegAudio::onQueueFilled(OMX_U32 portIndex) {
453 int64_t decChannelLayout;
454 int32_t inputBufferUsedLength = 0;
455 BufferInfo *inInfo = NULL;
456 OMX_BUFFERHEADERTYPE *inHeader = NULL;
458 if (mSignalledError || mOutputPortSettingsChange != NONE) {
462 List<BufferInfo *> &inQueue = getPortQueue(0);
463 List<BufferInfo *> &outQueue = getPortQueue(1);
465 while ((!inQueue.empty() || mInputBufferSize > 0 ||
466 mAudioBufferSize > 0 || mFlushComplete) && !outQueue.empty()) {
467 if (!inQueue.empty() || mInputBufferSize > 0) {
468 inInfo = *inQueue.begin();
469 inHeader = inInfo->mHeader;
475 BufferInfo *outInfo = *outQueue.begin();
476 OMX_BUFFERHEADERTYPE *outHeader = outInfo->mHeader;
478 if (inHeader && inHeader->nFlags & OMX_BUFFERFLAG_EOS) {
479 inQueue.erase(inQueue.begin());
480 inInfo->mOwnedByUs = false;
481 notifyEmptyBufferDone(inHeader);
485 if (mReceivedEOS && (mFlushComplete || !(mCtx->codec->capabilities & CODEC_CAP_DELAY))) {
486 outHeader->nFilledLen = 0;
487 outHeader->nFlags = OMX_BUFFERFLAG_EOS;
489 outQueue.erase(outQueue.begin());
490 outInfo->mOwnedByUs = false;
491 notifyFillBufferDone(outHeader);
495 if (inHeader && inHeader->nFlags & OMX_BUFFERFLAG_CODECCONFIG) {
496 LOGI("got extradata, ignore: %d, size: %lu", mIgnoreExtradata, inHeader->nFilledLen);
497 hexdump(inHeader->pBuffer + inHeader->nOffset, inHeader->nFilledLen);
498 if (!mExtradataReady && !mIgnoreExtradata) {
499 int orig_extradata_size = mCtx->extradata_size;
500 mCtx->extradata_size += inHeader->nFilledLen;
501 mCtx->extradata = (uint8_t *)realloc(mCtx->extradata,
502 mCtx->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
503 if (!mCtx->extradata) {
504 LOGE("ffmpeg audio decoder failed to alloc extradata memory.");
505 notify(OMX_EventError, OMX_ErrorInsufficientResources, 0, NULL);
506 mSignalledError = true;
510 memcpy(mCtx->extradata + orig_extradata_size,
511 inHeader->pBuffer + inHeader->nOffset, inHeader->nFilledLen);
512 memset(mCtx->extradata + mCtx->extradata_size, 0, FF_INPUT_BUFFER_PADDING_SIZE);
514 inInfo->mOwnedByUs = false;
515 inQueue.erase(inQueue.begin());
517 notifyEmptyBufferDone(inHeader);
522 if (mIgnoreExtradata) {
523 LOGI("got extradata, size: %lu, but ignore it", inHeader->nFilledLen);
524 inInfo->mOwnedByUs = false;
525 inQueue.erase(inQueue.begin());
527 notifyEmptyBufferDone(inHeader);
535 if (!mExtradataReady && !mIgnoreExtradata) {
536 LOGI("extradata is ready");
537 hexdump(mCtx->extradata, mCtx->extradata_size);
538 mExtradataReady = true;
540 LOGI("open ffmpeg decoder now");
542 err = avcodec_open2(mCtx, mCtx->codec, NULL);
544 LOGE("ffmpeg audio decoder failed to initialize. (%d)", err);
545 notify(OMX_EventError, OMX_ErrorUndefined, 0, NULL);
546 mSignalledError = true;
552 /* update the audio clock with the pts */
553 if (inHeader && inHeader->nOffset == 0) {
554 mAnchorTimeUs = inHeader->nTimeStamp;
555 mNumFramesOutput = 0;
556 mInputBufferSize = inHeader->nFilledLen;
559 if (inHeader && mAudioBufferSize == 0 && !mFlushComplete) {
561 av_init_packet(&pkt);
562 if (!mFlushComplete) {
563 pkt.data = (uint8_t *)inHeader->pBuffer + inHeader->nOffset;
564 pkt.size = inHeader->nFilledLen;
565 pkt.pts = inHeader->nTimeStamp; // ingore it, we will compute it
569 pkt.pts = AV_NOPTS_VALUE;
572 LOGV("pkt size: %d, pts: %lld", pkt.size, pkt.pts);
575 if (!(mFrame = avcodec_alloc_frame())) {
576 LOGE("ffmpeg audio decoder failed to alloc memory.");
577 notify(OMX_EventError, OMX_ErrorInsufficientResources, 0, NULL);
578 mSignalledError = true;
582 avcodec_get_frame_defaults(mFrame);
586 inputBufferUsedLength = 0;
587 len = avcodec_decode_audio4(mCtx, mFrame, &gotFrm, &pkt);
589 LOGE("ffmpeg audio decoder failed to decode frame. (0x%x)", len);
591 /* if !mAudioConfigChanged, Don't fill the out buffer */
592 if (!mAudioConfigChanged) {
593 inInfo->mOwnedByUs = false;
594 inQueue.erase(inQueue.begin());
596 notifyEmptyBufferDone(inHeader);
601 inputBufferUsedLength = inHeader->nFilledLen;
602 /* if error, we skip the frame and play silence instead */
603 mPAudioBuffer = mSilenceBuffer;
604 mAudioBufferSize = kOutputBufferSize;
605 } else if (!gotFrm) {
606 LOGI("ffmpeg audio decoder failed to get frame.");
607 /* stop sending empty packets if the decoder is finished */
608 if (!pkt.data && mCtx->codec->capabilities & CODEC_CAP_DELAY)
609 mFlushComplete = true;
613 * FIXME, check mAudioConfigChanged when the first time you call the audio4!
614 * mCtx->sample_rate and mCtx->channels may be changed by audio decoder later, why???
616 if (!mAudioConfigChanged) {
617 if (mCtx->channels != mNumChannels || mCtx->sample_rate != mSamplingRate || mCtx->sample_fmt != mSamplingFmt) {
618 LOGI("audio OMX_EventPortSettingsChanged, mCtx->channels: %d, mNumChannels: %d, mCtx->sample_rate: %d, mSamplingRate: %d",
619 mCtx->channels, mNumChannels, mCtx->sample_rate, mSamplingRate);
620 mNumChannels = mCtx->channels;
621 mSamplingRate = mCtx->sample_rate;
622 mSamplingFmt = mCtx->sample_fmt;
623 mAudioConfigChanged = true;
624 notify(OMX_EventPortSettingsChanged, 1, 0, NULL);
625 mOutputPortSettingsChange = AWAITING_DISABLED;
628 // match with the default, set mAudioConfigChanged true anyway!
629 mAudioConfigChanged = true;
633 dataSize = av_samples_get_buffer_size(NULL, mNumChannels, mFrame->nb_samples, mSamplingFmt, 1);
635 decChannelLayout = av_get_default_channel_layout(mNumChannels);
636 if (mSamplingFmt != mAudioSrcFmt ||
637 decChannelLayout != mAudioSrcChannelLayout ||
638 mSamplingRate != mAudioSrcFreq ) {
641 mSwrCtx = swr_alloc_set_opts(NULL,
642 mAudioTgtChannelLayout, mAudioTgtFmt, mAudioTgtFreq,
643 decChannelLayout, mSamplingFmt, mSamplingRate,
645 if (!mSwrCtx || swr_init(mSwrCtx) < 0) {
646 LOGE("Cannot create sample rate converter for conversion of %d Hz %s %d channels to %d Hz %s %d channels!",
648 av_get_sample_fmt_name(mSamplingFmt),
651 av_get_sample_fmt_name(mAudioTgtFmt),
653 notify(OMX_EventError, OMX_ErrorUndefined, 0, NULL);
654 mSignalledError = true;
658 LOGI("Create sample rate converter for conversion of %d Hz %s %d channels to %d Hz %s %d channels!",
660 av_get_sample_fmt_name(mSamplingFmt),
663 av_get_sample_fmt_name(mAudioTgtFmt),
666 mAudioSrcChannelLayout = decChannelLayout;
667 mAudioSrcChannels = mNumChannels;
668 mAudioSrcFreq = mSamplingRate;
669 mAudioSrcFmt = mSamplingFmt;
673 const uint8_t *in[] = { mFrame->data[0] };
674 uint8_t *out[] = {mAudioBuf2};
675 int len2 = swr_convert(mSwrCtx, out, sizeof(mAudioBuf2) / mAudioTgtChannels / av_get_bytes_per_sample(mAudioTgtFmt),
676 in, mFrame->nb_samples);
678 LOGE("audio_resample() failed");
681 if (len2 == sizeof(mAudioBuf2) / mAudioTgtChannels / av_get_bytes_per_sample(mAudioTgtFmt)) {
682 LOGE("warning: audio buffer is probably too small");
685 mPAudioBuffer = mAudioBuf2;
686 mAudioBufferSize = len2 * mAudioTgtChannels * av_get_bytes_per_sample(mAudioTgtFmt);
688 mPAudioBuffer = mFrame->data[0];
689 mAudioBufferSize = dataSize;
692 inputBufferUsedLength = len;
694 LOGV("ffmpeg audio decoder get frame. (%d), mAudioBufferSize: %d", len, mAudioBufferSize);
699 size_t copyToOutputBufferLen = mAudioBufferSize;
700 if (mAudioBufferSize > kOutputBufferSize)
701 copyToOutputBufferLen = kOutputBufferSize;
703 outHeader->nOffset = 0;
704 outHeader->nFilledLen = copyToOutputBufferLen;
705 outHeader->nTimeStamp = mAnchorTimeUs
706 + (mNumFramesOutput * 1000000ll) / mSamplingRate;
707 memcpy(outHeader->pBuffer, mPAudioBuffer, copyToOutputBufferLen);
708 outHeader->nFlags = 0;
710 mPAudioBuffer += copyToOutputBufferLen;
711 mAudioBufferSize -= copyToOutputBufferLen;
712 mNumFramesOutput += copyToOutputBufferLen / av_get_bytes_per_sample(mCtx->sample_fmt) / mNumChannels;
715 CHECK_GE(inHeader->nFilledLen, inputBufferUsedLength);
716 inHeader->nOffset += inputBufferUsedLength;
717 inHeader->nFilledLen -= inputBufferUsedLength;
718 mInputBufferSize -= inputBufferUsedLength;
719 if (inHeader->nFilledLen == 0) {
720 inInfo->mOwnedByUs = false;
721 inQueue.erase(inQueue.begin());
723 notifyEmptyBufferDone(inHeader);
726 mInputBufferSize = 0;
730 outInfo->mOwnedByUs = false;
731 outQueue.erase(outQueue.begin());
733 notifyFillBufferDone(outHeader);
738 void SoftFFmpegAudio::onPortFlushCompleted(OMX_U32 portIndex) {
739 if (portIndex == 0 && mCtx) {
740 // Make sure that the next buffer output does not still
741 // depend on fragments from the last one decoded.
742 avcodec_flush_buffers(mCtx);
747 void SoftFFmpegAudio::onPortEnableCompleted(OMX_U32 portIndex, bool enabled) {
748 if (portIndex != 1) {
752 switch (mOutputPortSettingsChange) {
756 case AWAITING_DISABLED:
759 mOutputPortSettingsChange = AWAITING_ENABLED;
765 CHECK_EQ((int)mOutputPortSettingsChange, (int)AWAITING_ENABLED);
767 mOutputPortSettingsChange = NONE;
773 } // namespace android
775 android::SoftOMXComponent *createSoftOMXComponent(
776 const char *name, const OMX_CALLBACKTYPE *callbacks,
777 OMX_PTR appData, OMX_COMPONENTTYPE **component) {
778 return new android::SoftFFmpegAudio(name, callbacks, appData, component);