summaryrefslogtreecommitdiffstats
path: root/media/libstagefright/MediaCodec.cpp
diff options
context:
space:
mode:
authorAndy McFadden <fadden@android.com>2013-03-05 17:41:25 +0000
committerAndroid (Google) Code Review <android-gerrit@google.com>2013-03-05 17:41:25 +0000
commita7a5917a064710edea9cfacc8eda44532150e852 (patch)
tree506ee93cee969d2f1be4cda5346c12a514dd4441 /media/libstagefright/MediaCodec.cpp
parent0c57461f2c19f3a271c66f52cf8c9b2a82b13518 (diff)
parentf779bb50d9746d9526541c3e6dcdf619cac941b7 (diff)
downloadframeworks_av-a7a5917a064710edea9cfacc8eda44532150e852.zip
frameworks_av-a7a5917a064710edea9cfacc8eda44532150e852.tar.gz
frameworks_av-a7a5917a064710edea9cfacc8eda44532150e852.tar.bz2
Merge "Implement Surface input to MediaCodec." into jb-mr2-dev
Diffstat (limited to 'media/libstagefright/MediaCodec.cpp')
-rw-r--r--media/libstagefright/MediaCodec.cpp101
1 files changed, 101 insertions, 0 deletions
diff --git a/media/libstagefright/MediaCodec.cpp b/media/libstagefright/MediaCodec.cpp
index 83be0fd..79ea04c 100644
--- a/media/libstagefright/MediaCodec.cpp
+++ b/media/libstagefright/MediaCodec.cpp
@@ -30,6 +30,7 @@
#include <media/stagefright/foundation/AString.h>
#include <media/stagefright/foundation/hexdump.h>
#include <media/stagefright/ACodec.h>
+#include <media/stagefright/BufferProducerWrapper.h>
#include <media/stagefright/MediaErrors.h>
#include <media/stagefright/MetaData.h>
#include <media/stagefright/NativeWindowWrapper.h>
@@ -62,6 +63,7 @@ MediaCodec::MediaCodec(const sp<ALooper> &looper)
: mState(UNINITIALIZED),
mLooper(looper),
mCodec(new ACodec),
+ mReplyID(0),
mFlags(0),
mSoftRenderer(NULL),
mDequeueInputTimeoutGeneration(0),
@@ -154,6 +156,28 @@ status_t MediaCodec::configure(
return PostAndAwaitResponse(msg, &response);
}
+status_t MediaCodec::createInputSurface(
+ sp<IGraphicBufferProducer>* bufferProducer) {
+ sp<AMessage> msg = new AMessage(kWhatCreateInputSurface, id());
+
+ // TODO(fadden): require MediaFormat colorFormat == AndroidOpaque
+
+ sp<AMessage> response;
+ status_t err = PostAndAwaitResponse(msg, &response);
+ if (err == NO_ERROR) {
+ // unwrap the sp<IGraphicBufferProducer>
+ sp<RefBase> obj;
+ bool found = response->findObject("input-surface", &obj);
+ CHECK(found);
+ sp<BufferProducerWrapper> wrapper(
+ static_cast<BufferProducerWrapper*>(obj.get()));
+ *bufferProducer = wrapper->getBufferProducer();
+ } else {
+ ALOGW("createInputSurface failed, err=%d", err);
+ }
+ return err;
+}
+
status_t MediaCodec::start() {
sp<AMessage> msg = new AMessage(kWhatStart, id());
@@ -232,6 +256,8 @@ status_t MediaCodec::queueSecureInputBuffer(
}
status_t MediaCodec::dequeueInputBuffer(size_t *index, int64_t timeoutUs) {
+ // TODO(fadden): fail if an input Surface has been configured
+
sp<AMessage> msg = new AMessage(kWhatDequeueInputBuffer, id());
msg->setInt64("timeoutUs", timeoutUs);
@@ -288,6 +314,13 @@ status_t MediaCodec::releaseOutputBuffer(size_t index) {
return PostAndAwaitResponse(msg, &response);
}
+status_t MediaCodec::signalEndOfInputStream() {
+ sp<AMessage> msg = new AMessage(kWhatSignalEndOfInputStream, id());
+
+ sp<AMessage> response;
+ return PostAndAwaitResponse(msg, &response);
+}
+
status_t MediaCodec::getOutputFormat(sp<AMessage> *format) const {
sp<AMessage> msg = new AMessage(kWhatGetOutputFormat, id());
@@ -575,6 +608,36 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
break;
}
+ case ACodec::kWhatInputSurfaceCreated:
+ {
+ // response to ACodec::kWhatCreateInputSurface
+ status_t err = NO_ERROR;
+ sp<AMessage> response = new AMessage();
+ if (!msg->findInt32("err", &err)) {
+ sp<RefBase> obj;
+ msg->findObject("input-surface", &obj);
+ CHECK(obj != NULL);
+ response->setObject("input-surface", obj);
+ } else {
+ response->setInt32("err", err);
+ }
+ response->postReply(mReplyID);
+ break;
+ }
+
+ case ACodec::kWhatSignaledInputEOS:
+ {
+ // response to ACodec::kWhatSignalEndOfInputStream
+ sp<AMessage> response = new AMessage();
+ status_t err;
+ if (msg->findInt32("err", &err)) {
+ response->setInt32("err", err);
+ }
+ response->postReply(mReplyID);
+ break;
+ }
+
+
case ACodec::kWhatBuffersAllocated:
{
int32_t portIndex;
@@ -881,6 +944,25 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
break;
}
+ case kWhatCreateInputSurface:
+ {
+ uint32_t replyID;
+ CHECK(msg->senderAwaitsResponse(&replyID));
+
+ // Must be configured, but can't have been started yet.
+ if (mState != CONFIGURED) {
+ sp<AMessage> response = new AMessage;
+ response->setInt32("err", INVALID_OPERATION);
+
+ response->postReply(replyID);
+ break;
+ }
+
+ mReplyID = replyID;
+ mCodec->initiateCreateInputSurface();
+ break;
+ }
+
case kWhatStart:
{
uint32_t replyID;
@@ -947,6 +1029,7 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
case kWhatDequeueInputBuffer:
{
+ // TODO(fadden): make this fail if we're using an input Surface
uint32_t replyID;
CHECK(msg->senderAwaitsResponse(&replyID));
@@ -1093,6 +1176,24 @@ void MediaCodec::onMessageReceived(const sp<AMessage> &msg) {
break;
}
+ case kWhatSignalEndOfInputStream:
+ {
+ uint32_t replyID;
+ CHECK(msg->senderAwaitsResponse(&replyID));
+
+ if (mState != STARTED || (mFlags & kFlagStickyError)) {
+ sp<AMessage> response = new AMessage;
+ response->setInt32("err", INVALID_OPERATION);
+
+ response->postReply(replyID);
+ break;
+ }
+
+ mReplyID = replyID;
+ mCodec->signalEndOfInputStream();
+ break;
+ }
+
case kWhatGetBuffers:
{
uint32_t replyID;