summaryrefslogtreecommitdiffstats
path: root/media/libstagefright/MediaCodec.cpp
diff options
context:
space:
mode:
authorAndreas Huber <andih@google.com>2012-05-08 11:21:26 -0700
committerAndreas Huber <andih@google.com>2012-05-08 11:26:22 -0700
commit8ee516a515c70a492c395b67ce12e19e7d159804 (patch)
treeae968718f25cd7972a03c00e7496a6deb225fc1f /media/libstagefright/MediaCodec.cpp
parenta62bde0a391f65a418d77c46e6ba468433d81dba (diff)
downloadframeworks_av-8ee516a515c70a492c395b67ce12e19e7d159804.zip
frameworks_av-8ee516a515c70a492c395b67ce12e19e7d159804.tar.gz
frameworks_av-8ee516a515c70a492c395b67ce12e19e7d159804.tar.bz2
Submit codec specific data automatically
if it is contained in the format passed to MediaCodec::configure. Change-Id: I8ef6755e8389ec47b44a9c70904ea6c03a00f4f2 related-to-bug: 6364139
Diffstat (limited to 'media/libstagefright/MediaCodec.cpp')
-rw-r--r--media/libstagefright/MediaCodec.cpp72
1 files changed, 72 insertions, 0 deletions
diff --git a/media/libstagefright/MediaCodec.cpp b/media/libstagefright/MediaCodec.cpp
index 2df0dd2..e032cfc 100644
--- a/media/libstagefright/MediaCodec.cpp
+++ b/media/libstagefright/MediaCodec.cpp
@@ -646,6 +646,28 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
break;
}
+ if (!mCSD.empty()) {
+ ssize_t index = dequeuePortBuffer(kPortIndexInput);
+ CHECK_GE(index, 0);
+
+ // If codec specific data had been specified as
+ // part of the format in the call to configure and
+ // if there's more csd left, we submit it here
+ // clients only get access to input buffers once
+ // this data has been exhausted.
+
+ status_t err = queueCSDInputBuffer(index);
+
+ if (err != OK) {
+ ALOGE("queueCSDInputBuffer failed w/ error %d",
+ err);
+
+ mFlags |= kFlagStickyError;
+ cancelPendingDequeueOperations();
+ }
+ break;
+ }
+
if (mFlags & kFlagDequeueInputPending) {
CHECK(handleDequeueInputBuffer(mDequeueInputReplyID));
@@ -811,6 +833,8 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
format->setInt32("encoder", true);
}
+ extractCSD(format);
+
mCodec->initiateConfigureComponent(format);
break;
}
@@ -1107,6 +1131,54 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
}
}
+void MediaCodec::extractCSD(const sp<AMessage> &format) {
+ mCSD.clear();
+
+ size_t i = 0;
+ for (;;) {
+ sp<ABuffer> csd;
+ if (!format->findBuffer(StringPrintf("csd-%u", i).c_str(), &csd)) {
+ break;
+ }
+
+ mCSD.push_back(csd);
+ ++i;
+ }
+
+ ALOGV("Found %u pieces of codec specific data.", mCSD.size());
+}
+
+status_t MediaCodec::queueCSDInputBuffer(size_t bufferIndex) {
+ CHECK(!mCSD.empty());
+
+ BufferInfo *info =
+ &mPortBuffers[kPortIndexInput].editItemAt(bufferIndex);
+
+ sp<ABuffer> csd = *mCSD.begin();
+ mCSD.erase(mCSD.begin());
+
+ const sp<ABuffer> &codecInputData =
+ (mCrypto != NULL) ? info->mEncryptedData : info->mData;
+
+ if (csd->size() > codecInputData->capacity()) {
+ return -EINVAL;
+ }
+
+ memcpy(codecInputData->data(), csd->data(), csd->size());
+
+ AString errorDetailMsg;
+
+ sp<AMessage> msg = new AMessage(kWhatQueueInputBuffer, id());
+ msg->setSize("index", bufferIndex);
+ msg->setSize("offset", 0);
+ msg->setSize("size", csd->size());
+ msg->setInt64("timeUs", 0ll);
+ msg->setInt32("flags", BUFFER_FLAG_CODECCONFIG);
+ msg->setPointer("errorDetailMsg", &errorDetailMsg);
+
+ return onQueueInputBuffer(msg);
+}
+
void MediaCodec::setState(State newState) {
if (newState == INITIALIZED) {
delete mSoftRenderer;