Merge "Camera: Add input side to camera3 HAL device" into jb-mr2-dev
diff --git a/include/media/ToneGenerator.h b/include/media/ToneGenerator.h
index 0529bcd..2183fbe 100644
--- a/include/media/ToneGenerator.h
+++ b/include/media/ToneGenerator.h
@@ -271,6 +271,7 @@
float mVolume; // Volume applied to audio track
audio_stream_type_t mStreamType; // Audio stream used for output
unsigned int mProcessSize; // Size of audio blocks generated at a time by audioCallback() (in PCM frames).
+ struct timespec mStartTime; // tone start time: needed to guaranty actual tone duration
bool initAudioTrack();
static void audioCallback(int event, void* user, void *info);
diff --git a/media/libmedia/ToneGenerator.cpp b/media/libmedia/ToneGenerator.cpp
index 58d495e..9ea3ea7 100644
--- a/media/libmedia/ToneGenerator.cpp
+++ b/media/libmedia/ToneGenerator.cpp
@@ -922,6 +922,9 @@
ALOGV("Immediate start, time %d", (unsigned int)(systemTime()/1000000));
lResult = true;
mState = TONE_STARTING;
+ if (clock_gettime(CLOCK_MONOTONIC, &mStartTime) != 0) {
+ mStartTime.tv_sec = 0;
+ }
mLock.unlock();
mpAudioTrack->start();
mLock.lock();
@@ -940,6 +943,7 @@
} else {
ALOGV("Delayed start");
mState = TONE_RESTARTING;
+ mStartTime.tv_sec = 0;
lStatus = mWaitCbkCond.waitRelative(mLock, seconds(3));
if (lStatus == NO_ERROR) {
if (mState != TONE_IDLE) {
@@ -976,21 +980,49 @@
ALOGV("stopTone");
mLock.lock();
- if (mState == TONE_PLAYING || mState == TONE_STARTING || mState == TONE_RESTARTING) {
- mState = TONE_STOPPING;
+ if (mState != TONE_IDLE && mState != TONE_INIT) {
+ if (mState == TONE_PLAYING || mState == TONE_STARTING || mState == TONE_RESTARTING) {
+ struct timespec stopTime;
+ // If the start time is valid, make sure that the number of audio samples produced
+ // corresponds at least to the time between the start and stop commands.
+ // This is needed in case of cold start of the output stream.
+ if ((mStartTime. tv_sec != 0) && (clock_gettime(CLOCK_MONOTONIC, &stopTime) == 0)) {
+ time_t sec = stopTime.tv_sec - mStartTime.tv_sec;
+ long nsec = stopTime.tv_nsec - mStartTime.tv_nsec;
+ long durationMs;
+ if (nsec < 0) {
+ --sec;
+ nsec += 1000000000;
+ }
+
+ if ((sec + 1) > ((long)(INT_MAX / mSamplingRate))) {
+ mMaxSmp = sec * mSamplingRate;
+ } else {
+ // mSamplingRate is always > 1000
+ sec = sec * 1000 + nsec / 1000000; // duration in milliseconds
+ mMaxSmp = (sec * mSamplingRate) / 1000;
+ }
+ ALOGV("stopTone() forcing mMaxSmp to %d, total for far %d", mMaxSmp, mTotalSmp);
+ } else {
+ mState = TONE_STOPPING;
+ }
+ }
ALOGV("waiting cond");
status_t lStatus = mWaitCbkCond.waitRelative(mLock, seconds(3));
if (lStatus == NO_ERROR) {
+ // If the tone was restarted exit now before calling clearWaveGens();
+ if (mState != TONE_INIT) {
+ return;
+ }
ALOGV("track stop complete, time %d", (unsigned int)(systemTime()/1000000));
} else {
ALOGE("--- Stop timed out");
mState = TONE_IDLE;
mpAudioTrack->stop();
}
+ clearWaveGens();
}
- clearWaveGens();
-
mLock.unlock();
}
@@ -1258,6 +1290,9 @@
ALOGV("Cbk restarting track");
if (lpToneGen->prepareWave()) {
lpToneGen->mState = TONE_STARTING;
+ if (clock_gettime(CLOCK_MONOTONIC, &lpToneGen->mStartTime) != 0) {
+ lpToneGen->mStartTime.tv_sec = 0;
+ }
// must reload lpToneDesc as prepareWave() may change mpToneDesc
lpToneDesc = lpToneGen->mpToneDesc;
} else {
@@ -1299,7 +1334,7 @@
}
if (lSignal)
- lpToneGen->mWaitCbkCond.signal();
+ lpToneGen->mWaitCbkCond.broadcast();
lpToneGen->mLock.unlock();
}
}
diff --git a/media/libmediaplayerservice/StagefrightRecorder.cpp b/media/libmediaplayerservice/StagefrightRecorder.cpp
index c2c9985..095d5ca 100644
--- a/media/libmediaplayerservice/StagefrightRecorder.cpp
+++ b/media/libmediaplayerservice/StagefrightRecorder.cpp
@@ -70,7 +70,8 @@
mOutputFd(-1),
mAudioSource(AUDIO_SOURCE_CNT),
mVideoSource(VIDEO_SOURCE_LIST_END),
- mStarted(false), mSurfaceMediaSource(NULL) {
+ mStarted(false), mSurfaceMediaSource(NULL),
+ mCaptureTimeLapse(false) {
ALOGV("Constructor");
reset();