diff options
author | Lajos Molnar <lajos@google.com> | 2015-02-05 02:17:13 +0000 |
---|---|---|
committer | Android Git Automerger <android-git-automerger@android.com> | 2015-02-05 02:17:13 +0000 |
commit | bcd22f0f3a4cd5f78e03af23aafadb2d1aec6794 (patch) | |
tree | 3c1e2d2b109f1541be254870e9ab054506666521 | |
parent | a291dabcab10cafc1749d1d9493d269049502256 (diff) | |
parent | 0662f5b0c43fcfdf055704d02ea41202c9b6094a (diff) | |
download | frameworks_av-bcd22f0f3a4cd5f78e03af23aafadb2d1aec6794.zip frameworks_av-bcd22f0f3a4cd5f78e03af23aafadb2d1aec6794.tar.gz frameworks_av-bcd22f0f3a4cd5f78e03af23aafadb2d1aec6794.tar.bz2 |
am 0662f5b0: Merge "stagefright: add fallback for native flex-YUV support" into lmp-mr1-dev
* commit '0662f5b0c43fcfdf055704d02ea41202c9b6094a':
stagefright: add fallback for native flex-YUV support
-rw-r--r-- | include/media/stagefright/MediaCodec.h | 2 | ||||
-rw-r--r-- | media/libstagefright/ACodec.cpp | 90 | ||||
-rw-r--r-- | media/libstagefright/MediaCodec.cpp | 11 |
3 files changed, 83 insertions, 20 deletions
diff --git a/include/media/stagefright/MediaCodec.h b/include/media/stagefright/MediaCodec.h index 54a4e8b..d448097 100644 --- a/include/media/stagefright/MediaCodec.h +++ b/include/media/stagefright/MediaCodec.h @@ -194,7 +194,7 @@ private: }; enum { - kFlagIsSoftwareCodec = 1, + kFlagUsesSoftwareRenderer = 1, kFlagOutputFormatChanged = 2, kFlagOutputBuffersChanged = 4, kFlagStickyError = 8, diff --git a/media/libstagefright/ACodec.cpp b/media/libstagefright/ACodec.cpp index 11043f8..72518a9 100644 --- a/media/libstagefright/ACodec.cpp +++ b/media/libstagefright/ACodec.cpp @@ -1258,9 +1258,10 @@ status_t ACodec::configureCodec( } } + // NOTE: we only use native window for video decoders sp<RefBase> obj; bool haveNativeWindow = msg->findObject("native-window", &obj) - && obj != NULL; + && obj != NULL && video && !encoder; mStoreMetaDataInOutputBuffers = false; if (video && !encoder) { inputFormat->setInt32("adaptive-playback", false); @@ -1275,7 +1276,7 @@ status_t ACodec::configureCodec( mFlags |= kFlagPushBlankBuffersToNativeWindowOnShutdown; } } - if (!encoder && video && haveNativeWindow) { + if (haveNativeWindow) { sp<NativeWindowWrapper> windowWrapper( static_cast<NativeWindowWrapper *>(obj.get())); sp<ANativeWindow> nativeWindow = windowWrapper->getNativeWindow(); @@ -1324,6 +1325,8 @@ status_t ACodec::configureCodec( if (err != OK) { ALOGW("[%s] prepareForAdaptivePlayback failed w/ err %d", mComponentName.c_str(), err); + // allow failure + err = OK; } else { inputFormat->setInt32("max-width", maxWidth); inputFormat->setInt32("max-height", maxHeight); @@ -1417,11 +1420,80 @@ status_t ACodec::configureCodec( } if (video) { + // determine need for software renderer + bool usingSwRenderer = false; + if (haveNativeWindow && mComponentName.startsWith("OMX.google.")) { + usingSwRenderer = true; + haveNativeWindow = false; + } + if (encoder) { err = setupVideoEncoder(mime, msg); } else { err = setupVideoDecoder(mime, msg, haveNativeWindow); } + + if (err != OK) { + return err; + } + + if (haveNativeWindow) { + sp<NativeWindowWrapper> nativeWindow( + static_cast<NativeWindowWrapper *>(obj.get())); + CHECK(nativeWindow != NULL); + mNativeWindow = nativeWindow->getNativeWindow(); + + native_window_set_scaling_mode( + mNativeWindow.get(), NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW); + } + + // initialize native window now to get actual output format + // TODO: this is needed for some encoders even though they don't use native window + CHECK_EQ((status_t)OK, initNativeWindow()); + + // fallback for devices that do not handle flex-YUV for native buffers + if (haveNativeWindow) { + int32_t requestedColorFormat = OMX_COLOR_FormatUnused; + if (msg->findInt32("color-format", &requestedColorFormat) && + requestedColorFormat == OMX_COLOR_FormatYUV420Flexible) { + CHECK_EQ(getPortFormat(kPortIndexOutput, outputFormat), (status_t)OK); + int32_t colorFormat = OMX_COLOR_FormatUnused; + OMX_U32 flexibleEquivalent = OMX_COLOR_FormatUnused; + CHECK(outputFormat->findInt32("color-format", &colorFormat)); + ALOGD("[%s] Requested output format %#x and got %#x.", + mComponentName.c_str(), requestedColorFormat, colorFormat); + if (!isFlexibleColorFormat( + mOMX, mNode, colorFormat, haveNativeWindow, &flexibleEquivalent) + || flexibleEquivalent != (OMX_U32)requestedColorFormat) { + // device did not handle flex-YUV request for native window, fall back + // to SW renderer + ALOGI("[%s] Falling back to software renderer", mComponentName.c_str()); + mNativeWindow.clear(); + haveNativeWindow = false; + usingSwRenderer = true; + if (mStoreMetaDataInOutputBuffers) { + err = mOMX->storeMetaDataInBuffers(mNode, kPortIndexOutput, OMX_FALSE); + mStoreMetaDataInOutputBuffers = false; + // TODO: implement adaptive-playback support for bytebuffer mode. + // This is done by SW codecs, but most HW codecs don't support it. + inputFormat->setInt32("adaptive-playback", false); + } + if (err == OK) { + err = mOMX->enableGraphicBuffers(mNode, kPortIndexOutput, OMX_FALSE); + } + if (mFlags & kFlagIsGrallocUsageProtected) { + // fallback is not supported for protected playback + err = PERMISSION_DENIED; + } else if (err == OK) { + err = setupVideoDecoder(mime, msg, false); + } + } + } + } + + if (usingSwRenderer) { + outputFormat->setInt32("using-sw-renderer", 1); + } } else if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_MPEG)) { int32_t numChannels, sampleRate; if (!msg->findInt32("channel-count", &numChannels) @@ -4922,20 +4994,6 @@ bool ACodec::LoadedState::onConfigureComponent( return false; } - sp<RefBase> obj; - if (msg->findObject("native-window", &obj) - && strncmp("OMX.google.", mCodec->mComponentName.c_str(), 11)) { - sp<NativeWindowWrapper> nativeWindow( - static_cast<NativeWindowWrapper *>(obj.get())); - CHECK(nativeWindow != NULL); - mCodec->mNativeWindow = nativeWindow->getNativeWindow(); - - native_window_set_scaling_mode( - mCodec->mNativeWindow.get(), - NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW); - } - CHECK_EQ((status_t)OK, mCodec->initNativeWindow()); - { sp<AMessage> notify = mCodec->mNotify->dup(); notify->setInt32("what", CodecBase::kWhatComponentConfigured); diff --git a/media/libstagefright/MediaCodec.cpp b/media/libstagefright/MediaCodec.cpp index c2381b4..a9c3a04 100644 --- a/media/libstagefright/MediaCodec.cpp +++ b/media/libstagefright/MediaCodec.cpp @@ -869,9 +869,9 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) { CHECK(msg->findString("componentName", &mComponentName)); if (mComponentName.startsWith("OMX.google.")) { - mFlags |= kFlagIsSoftwareCodec; + mFlags |= kFlagUsesSoftwareRenderer; } else { - mFlags &= ~kFlagIsSoftwareCodec; + mFlags &= ~kFlagUsesSoftwareRenderer; } if (mComponentName.endsWith(".secure")) { @@ -894,6 +894,11 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) { CHECK(msg->findMessage("input-format", &mInputFormat)); CHECK(msg->findMessage("output-format", &mOutputFormat)); + int32_t usingSwRenderer; + if (mOutputFormat->findInt32("using-sw-renderer", &usingSwRenderer) + && usingSwRenderer) { + mFlags |= kFlagUsesSoftwareRenderer; + } setState(CONFIGURED); (new AMessage)->postReply(mReplyID); break; @@ -989,7 +994,7 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) { if (mSoftRenderer == NULL && mNativeWindow != NULL && - (mFlags & kFlagIsSoftwareCodec)) { + (mFlags & kFlagUsesSoftwareRenderer)) { AString mime; CHECK(msg->findString("mime", &mime)); |