summaryrefslogtreecommitdiffstats
path: root/media/libstagefright/CameraSource.cpp
diff options
context:
space:
mode:
authorJames Dong <jdong@google.com>2010-07-21 14:51:35 -0700
committerJames Dong <jdong@google.com>2010-07-22 14:51:53 -0700
commit542db5d438988360d491a5add1040a2df9aa90c9 (patch)
tree2780e2456a9b540e245fa3e3c8e62d60c284b8dc /media/libstagefright/CameraSource.cpp
parent348a8eab84f4bba76c04ca83b2f5418467aa1a48 (diff)
downloadframeworks_av-542db5d438988360d491a5add1040a2df9aa90c9.zip
frameworks_av-542db5d438988360d491a5add1040a2df9aa90c9.tar.gz
frameworks_av-542db5d438988360d491a5add1040a2df9aa90c9.tar.bz2
Allows the authoring engine to skip frame.
This is 1st part of the work to allow audio and video resync if we found out that audio and video are out of sync during authoring - also fixed a problem in AACEncoder::read() where the buffer acquired from the buffer group does not release when error out at reading from source. Change-Id: I8a2740097fcfdf85e6178869afeb9f3687a99118
Diffstat (limited to 'media/libstagefright/CameraSource.cpp')
-rw-r--r--media/libstagefright/CameraSource.cpp51
1 files changed, 36 insertions, 15 deletions
diff --git a/media/libstagefright/CameraSource.cpp b/media/libstagefright/CameraSource.cpp
index 4cc176a..9c48daf 100644
--- a/media/libstagefright/CameraSource.cpp
+++ b/media/libstagefright/CameraSource.cpp
@@ -277,23 +277,44 @@ status_t CameraSource::read(
{
Mutex::Autolock autoLock(mLock);
- while (mStarted && mFramesReceived.empty()) {
- mFrameAvailableCondition.wait(mLock);
- }
- if (!mStarted) {
- return OK;
- }
- frame = *mFramesReceived.begin();
- mFramesReceived.erase(mFramesReceived.begin());
+ while (mStarted) {
+ while(mFramesReceived.empty()) {
+ mFrameAvailableCondition.wait(mLock);
+ }
+
+ if (!mStarted) {
+ return OK;
+ }
- frameTime = *mFrameTimes.begin();
- mFrameTimes.erase(mFrameTimes.begin());
+ frame = *mFramesReceived.begin();
+ mFramesReceived.erase(mFramesReceived.begin());
- mFramesBeingEncoded.push_back(frame);
- *buffer = new MediaBuffer(frame->pointer(), frame->size());
- (*buffer)->setObserver(this);
- (*buffer)->add_ref();
- (*buffer)->meta_data()->setInt64(kKeyTime, frameTime);
+ frameTime = *mFrameTimes.begin();
+ mFrameTimes.erase(mFrameTimes.begin());
+ int64_t skipTimeUs;
+ if (!options || !options->getSkipFrame(&skipTimeUs)) {
+ skipTimeUs = frameTime;
+ }
+ if (skipTimeUs > frameTime) {
+ LOGV("skipTimeUs: %lld us > frameTime: %lld us",
+ skipTimeUs, frameTime);
+ releaseOneRecordingFrame(frame);
+ ++mNumFramesDropped;
+ // Safeguard against the abuse of the kSkipFrame_Option.
+ if (skipTimeUs - frameTime >= 1E6) {
+ LOGE("Frame skipping requested is way too long: %lld us",
+ skipTimeUs - frameTime);
+ return UNKNOWN_ERROR;
+ }
+ } else {
+ mFramesBeingEncoded.push_back(frame);
+ *buffer = new MediaBuffer(frame->pointer(), frame->size());
+ (*buffer)->setObserver(this);
+ (*buffer)->add_ref();
+ (*buffer)->meta_data()->setInt64(kKeyTime, frameTime);
+ return OK;
+ }
+ }
}
return OK;
}