Merge "MPEG4Writer: Enforce CSD size check only for MPEG-4 audio/video" into nyc-mr1-dev
diff --git a/include/media/ToneGenerator.h b/include/media/ToneGenerator.h
index c41c686..75515ac 100644
--- a/include/media/ToneGenerator.h
+++ b/include/media/ToneGenerator.h
@@ -195,6 +195,11 @@
TONE_JAPAN_RADIO_ACK, // Radio path acknowlegment: 400Hz, 1s ON, 2s OFF...
// UK Supervisory tones
TONE_UK_RINGTONE, // Ring Tone: A 400Hz + 450Hz tone repeated in a 0.4s on, 0.2s off, 0.4s on, 2.0s off pattern.
+ // AUSTRALIA Supervisory tones
+ TONE_AUSTRALIA_RINGTONE, // Ring tone: A 400Hz + 450Hz tone repeated in a 0.4s on, 0.2s off, 0.4s on, 2.0s off pattern.
+ TONE_AUSTRALIA_BUSY, // Busy tone: 425 Hz repeated in a 0.375s on, 0.375s off pattern.
+ TONE_AUSTRALIA_CALL_WAITING,// Call waiting tone: 425Hz tone repeated in a 0.2s on, 0.2s off, 0.2s on, 4.4s off pattern.
+ TONE_AUSTRALIA_CONGESTION, // Congestion tone: 425Hz tone repeated in a 0.375s on, 0.375s off pattern
NUM_ALTERNATE_TONES
};
@@ -202,6 +207,7 @@
ANSI,
JAPAN,
UK,
+ AUSTRALIA,
CEPT,
NUM_REGIONS
};
diff --git a/media/libmedia/ToneGenerator.cpp b/media/libmedia/ToneGenerator.cpp
index ffe896e..2f53637 100644
--- a/media/libmedia/ToneGenerator.cpp
+++ b/media/libmedia/ToneGenerator.cpp
@@ -747,9 +747,30 @@
{ .duration = 0, .waveFreq = { 0 }, 0, 0}},
.repeatCnt = ToneGenerator::TONEGEN_INF,
.repeatSegment = 0 }, // TONE_UK_RINGTONE
-
-
-
+ { .segments = { { .duration = 400, .waveFreq = { 400, 450, 0 }, 0, 0 },
+ { .duration = 200, .waveFreq = { 0 }, 0, 0 },
+ { .duration = 400, .waveFreq = { 400, 450, 0 }, 0, 0 },
+ { .duration = 2000, .waveFreq = { 0 }, 0, 0},
+ { .duration = 0, .waveFreq = { 0 }, 0, 0}},
+ .repeatCnt = ToneGenerator::TONEGEN_INF,
+ .repeatSegment = 0 }, // TONE_AUSTRALIA_RINGTONE
+ { .segments = { { .duration = 375, .waveFreq = { 425, 0 }, 0, 0 },
+ { .duration = 375, .waveFreq = { 0 }, 0, 0 },
+ { .duration = 0 , .waveFreq = { 0 }, 0, 0}},
+ .repeatCnt = ToneGenerator::TONEGEN_INF,
+ .repeatSegment = 0 }, // TONE_AUSTRALIA_BUSY
+ { .segments = { { .duration = 200, .waveFreq = { 425, 0 }, 0, 0 },
+ { .duration = 200, .waveFreq = { 0 }, 0, 0 },
+ { .duration = 200, .waveFreq = { 425, 0 }, 0, 0 },
+ { .duration = 4400, .waveFreq = { 0 }, 0, 0 },
+ { .duration = 0 , .waveFreq = { 0 }, 0, 0}},
+ .repeatCnt = ToneGenerator::TONEGEN_INF,
+ .repeatSegment = 0 }, // TONE_AUSTRALIA_CALL_WAITING
+ { .segments = { { .duration = 375, .waveFreq = { 425, 0 }, 0, 0 },
+ { .duration = 375, .waveFreq = { 0 }, 0, 0 },
+ { .duration = 0 , .waveFreq = { 0 }, 0, 0}},
+ .repeatCnt = ToneGenerator::TONEGEN_INF,
+ .repeatSegment = 0 }, // TONE_AUSTRALIA_CONGESTION
};
// Used by ToneGenerator::getToneForRegion() to convert user specified supervisory tone type
@@ -784,8 +805,17 @@
TONE_SUP_ERROR, // TONE_SUP_ERROR
TONE_SUP_CALL_WAITING, // TONE_SUP_CALL_WAITING
TONE_UK_RINGTONE // TONE_SUP_RINGTONE
+ },
+ { // AUSTRALIA
+ TONE_ANSI_DIAL, // TONE_SUP_DIAL
+ TONE_AUSTRALIA_BUSY, // TONE_SUP_BUSY
+ TONE_AUSTRALIA_CONGESTION, // TONE_SUP_CONGESTION
+ TONE_SUP_RADIO_ACK, // TONE_SUP_RADIO_ACK
+ TONE_SUP_RADIO_NOTAVAIL, // TONE_SUP_RADIO_NOTAVAIL
+ TONE_SUP_ERROR, // TONE_SUP_ERROR
+ TONE_AUSTRALIA_CALL_WAITING,// TONE_SUP_CALL_WAITING
+ TONE_AUSTRALIA_RINGTONE // TONE_SUP_RINGTONE
}
-
};
@@ -841,6 +871,8 @@
mRegion = JAPAN;
} else if (strstr(value, "uk") != NULL) {
mRegion = UK;
+ } else if (strstr(value, "au") != NULL) {
+ mRegion = AUSTRALIA;
} else {
mRegion = CEPT;
}
diff --git a/media/libmediaplayerservice/MediaPlayerService.cpp b/media/libmediaplayerservice/MediaPlayerService.cpp
index d790821..3cfed5e 100644
--- a/media/libmediaplayerservice/MediaPlayerService.cpp
+++ b/media/libmediaplayerservice/MediaPlayerService.cpp
@@ -1938,6 +1938,7 @@
continue;
}
callbackData->mSwitching = true; // begin track switch
+ callbackData->setOutput(NULL);
#else
// tryBeginTrackSwitch() returns false if the callback has the lock.
if (!mCallbackData->tryBeginTrackSwitch()) {
diff --git a/media/libstagefright/SampleTable.cpp b/media/libstagefright/SampleTable.cpp
index c9c49f5..eb1f193 100644
--- a/media/libstagefright/SampleTable.cpp
+++ b/media/libstagefright/SampleTable.cpp
@@ -18,6 +18,8 @@
//#define LOG_NDEBUG 0
#include <utils/Log.h>
+#include <limits>
+
#include "include/SampleTable.h"
#include "include/SampleIterator.h"
@@ -45,6 +47,8 @@
////////////////////////////////////////////////////////////////////////////////
+const off64_t kMaxOffset = std::numeric_limits<off64_t>::max();
+
struct SampleTable::CompositionDeltaLookup {
CompositionDeltaLookup();
@@ -233,11 +237,11 @@
mNumSampleToChunkOffsets = U32_AT(&header[4]);
- if ((data_size - 8) / 12 < mNumSampleToChunkOffsets) {
+ if ((data_size - 8) / sizeof(SampleToChunkEntry) < mNumSampleToChunkOffsets) {
return ERROR_MALFORMED;
}
- if ((uint64_t)SIZE_MAX / sizeof(SampleToChunkEntry) <=
+ if ((uint64_t)kMaxTotalSize / sizeof(SampleToChunkEntry) <=
(uint64_t)mNumSampleToChunkOffsets) {
ALOGE("Sample-to-chunk table size too large.");
return ERROR_OUT_OF_RANGE;
@@ -269,21 +273,19 @@
return OK;
}
- if ((off64_t)(SIZE_MAX - 8 -
+ if ((off64_t)(kMaxOffset - 8 -
((mNumSampleToChunkOffsets - 1) * sizeof(SampleToChunkEntry)))
< mSampleToChunkOffset) {
return ERROR_MALFORMED;
}
for (uint32_t i = 0; i < mNumSampleToChunkOffsets; ++i) {
- uint8_t buffer[12];
-
- if ((off64_t)(SIZE_MAX - 8 - (i * 12)) < mSampleToChunkOffset) {
- return ERROR_MALFORMED;
- }
+ uint8_t buffer[sizeof(SampleToChunkEntry)];
if (mDataSource->readAt(
- mSampleToChunkOffset + 8 + i * 12, buffer, sizeof(buffer))
+ mSampleToChunkOffset + 8 + i * sizeof(SampleToChunkEntry),
+ buffer,
+ sizeof(buffer))
!= (ssize_t)sizeof(buffer)) {
return ERROR_IO;
}
@@ -384,8 +386,7 @@
}
mTimeToSampleCount = U32_AT(&header[4]);
- if ((uint64_t)mTimeToSampleCount >
- (uint64_t)UINT32_MAX / (2 * sizeof(uint32_t))) {
+ if (mTimeToSampleCount > UINT32_MAX / (2 * sizeof(uint32_t))) {
// Choose this bound because
// 1) 2 * sizeof(uint32_t) is the amount of memory needed for one
// time-to-sample entry in the time-to-sample table.
@@ -469,7 +470,7 @@
mNumCompositionTimeDeltaEntries = numEntries;
uint64_t allocSize = (uint64_t)numEntries * 2 * sizeof(int32_t);
- if (allocSize > SIZE_MAX) {
+ if (allocSize > kMaxTotalSize) {
ALOGE("Composition-time-to-sample table size too large.");
return ERROR_OUT_OF_RANGE;
}
@@ -536,7 +537,7 @@
}
uint64_t allocSize = (uint64_t)mNumSyncSamples * sizeof(uint32_t);
- if (allocSize > SIZE_MAX) {
+ if (allocSize > kMaxTotalSize) {
ALOGE("Sync sample table size too large.");
return ERROR_OUT_OF_RANGE;
}
diff --git a/services/audioflinger/AudioMixer.cpp b/services/audioflinger/AudioMixer.cpp
index aea6b67..0be7199 100644
--- a/services/audioflinger/AudioMixer.cpp
+++ b/services/audioflinger/AudioMixer.cpp
@@ -430,7 +430,7 @@
{
ALOGV("AudioMixer::deleteTrackName(%d)", name);
name -= TRACK0;
- ALOG_ASSERT(uint32_t(name) < MAX_NUM_TRACKS, "bad track name %d", name);
+ LOG_ALWAYS_FATAL_IF(name < 0 || name >= (int)MAX_NUM_TRACKS, "bad track name %d", name);
ALOGV("deleteTrackName(%d)", name);
track_t& track(mState.tracks[ name ]);
if (track.enabled) {
diff --git a/services/audioflinger/Effects.cpp b/services/audioflinger/Effects.cpp
index e6c8abc..e3e518c 100644
--- a/services/audioflinger/Effects.cpp
+++ b/services/audioflinger/Effects.cpp
@@ -216,9 +216,10 @@
return mHandles.size();
}
-void AudioFlinger::EffectModule::updateState() {
+bool AudioFlinger::EffectModule::updateState() {
Mutex::Autolock _l(mLock);
+ bool started = false;
switch (mState) {
case RESTART:
reset_l();
@@ -233,6 +234,7 @@
}
if (start_l() == NO_ERROR) {
mState = ACTIVE;
+ started = true;
} else {
mState = IDLE;
}
@@ -256,6 +258,8 @@
default: //IDLE , ACTIVE, DESTROYED
break;
}
+
+ return started;
}
void AudioFlinger::EffectModule::process()
@@ -462,10 +466,22 @@
}
}
+// start() must be called with PlaybackThread::mLock or EffectChain::mLock held
status_t AudioFlinger::EffectModule::start()
{
- Mutex::Autolock _l(mLock);
- return start_l();
+ sp<EffectChain> chain;
+ status_t status;
+ {
+ Mutex::Autolock _l(mLock);
+ status = start_l();
+ if (status == NO_ERROR) {
+ chain = mChain.promote();
+ }
+ }
+ if (chain != 0) {
+ chain->resetVolume_l();
+ }
+ return status;
}
status_t AudioFlinger::EffectModule::start_l()
@@ -489,10 +505,6 @@
}
if (status == 0) {
addEffectToHal_l();
- sp<EffectChain> chain = mChain.promote();
- if (chain != 0) {
- chain->forceVolume();
- }
}
return status;
}
@@ -1349,7 +1361,7 @@
audio_session_t sessionId)
: mThread(thread), mSessionId(sessionId), mActiveTrackCnt(0), mTrackCnt(0), mTailBufferCount(0),
mOwnInBuffer(false), mVolumeCtrlIdx(-1), mLeftVolume(UINT_MAX), mRightVolume(UINT_MAX),
- mNewLeftVolume(UINT_MAX), mNewRightVolume(UINT_MAX), mForceVolume(false)
+ mNewLeftVolume(UINT_MAX), mNewRightVolume(UINT_MAX)
{
mStrategy = AudioSystem::getStrategyForStream(AUDIO_STREAM_MUSIC);
if (thread == NULL) {
@@ -1471,8 +1483,12 @@
mEffects[i]->process();
}
}
+ bool doResetVolume = false;
for (size_t i = 0; i < size; i++) {
- mEffects[i]->updateState();
+ doResetVolume = mEffects[i]->updateState() || doResetVolume;
+ }
+ if (doResetVolume) {
+ resetVolume_l();
}
}
@@ -1653,8 +1669,8 @@
}
}
-// setVolume_l() must be called with PlaybackThread::mLock held
-bool AudioFlinger::EffectChain::setVolume_l(uint32_t *left, uint32_t *right)
+// setVolume_l() must be called with PlaybackThread::mLock or EffectChain::mLock held
+bool AudioFlinger::EffectChain::setVolume_l(uint32_t *left, uint32_t *right, bool force)
{
uint32_t newLeft = *left;
uint32_t newRight = *right;
@@ -1672,7 +1688,7 @@
}
}
- if (!isVolumeForced() && ctrlIdx == mVolumeCtrlIdx &&
+ if (!force && ctrlIdx == mVolumeCtrlIdx &&
*left == mLeftVolume && *right == mRightVolume) {
if (hasControl) {
*left = mNewLeftVolume;
@@ -1714,6 +1730,16 @@
return hasControl;
}
+// resetVolume_l() must be called with PlaybackThread::mLock or EffectChain::mLock held
+void AudioFlinger::EffectChain::resetVolume_l()
+{
+ if ((mLeftVolume != UINT_MAX) && (mRightVolume != UINT_MAX)) {
+ uint32_t left = mLeftVolume;
+ uint32_t right = mRightVolume;
+ (void)setVolume_l(&left, &right, true);
+ }
+}
+
void AudioFlinger::EffectChain::syncHalEffectsState()
{
Mutex::Autolock _l(mLock);
diff --git a/services/audioflinger/Effects.h b/services/audioflinger/Effects.h
index 3b62652..322c06a 100644
--- a/services/audioflinger/Effects.h
+++ b/services/audioflinger/Effects.h
@@ -60,7 +60,7 @@
int id() const { return mId; }
void process();
- void updateState();
+ bool updateState();
status_t command(uint32_t cmdCode,
uint32_t cmdSize,
void *pCmdData,
@@ -277,7 +277,8 @@
sp<EffectModule> getEffectFromId_l(int id);
sp<EffectModule> getEffectFromType_l(const effect_uuid_t *type);
// FIXME use float to improve the dynamic range
- bool setVolume_l(uint32_t *left, uint32_t *right);
+ bool setVolume_l(uint32_t *left, uint32_t *right, bool force = false);
+ void resetVolume_l();
void setDevice_l(audio_devices_t device);
void setMode_l(audio_mode_t mode);
void setAudioSource_l(audio_source_t source);
@@ -323,13 +324,6 @@
// At least one non offloadable effect in the chain is enabled
bool isNonOffloadableEnabled();
- // use release_cas because we don't care about the observed value, just want to make sure the
- // new value is observable.
- void forceVolume() { android_atomic_release_cas(false, true, &mForceVolume); }
- // use acquire_cas because we are interested in the observed value and
- // we are the only observers.
- bool isVolumeForced() { return (android_atomic_acquire_cas(true, false, &mForceVolume) == 0); }
-
void syncHalEffectsState();
bool hasSoftwareEffect() const;
@@ -393,5 +387,4 @@
// timeLow fields among effect type UUIDs.
// Updated by updateSuspendedSessions_l() only.
KeyedVector< int, sp<SuspendedEffectDesc> > mSuspendedEffects;
- volatile int32_t mForceVolume; // force next volume command because a new effect was enabled
};
diff --git a/services/audioflinger/Threads.cpp b/services/audioflinger/Threads.cpp
index d093c32..aa2561e 100644
--- a/services/audioflinger/Threads.cpp
+++ b/services/audioflinger/Threads.cpp
@@ -5772,12 +5772,15 @@
mChannelMask,
frameCount,
IPCThreadState::self()->getCallingUid());
- if (outputTrack->cblk() != NULL) {
- thread->setStreamVolume(AUDIO_STREAM_PATCH, 1.0f);
- mOutputTracks.add(outputTrack);
- ALOGV("addOutputTrack() track %p, on thread %p", outputTrack.get(), thread);
- updateWaitTime_l();
+ status_t status = outputTrack != 0 ? outputTrack->initCheck() : (status_t) NO_MEMORY;
+ if (status != NO_ERROR) {
+ ALOGE("addOutputTrack() initCheck failed %d", status);
+ return;
}
+ thread->setStreamVolume(AUDIO_STREAM_PATCH, 1.0f);
+ mOutputTracks.add(outputTrack);
+ ALOGV("addOutputTrack() track %p, on thread %p", outputTrack.get(), thread);
+ updateWaitTime_l();
}
void AudioFlinger::DuplicatingThread::removeOutputTrack(MixerThread *thread)
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
index c0bb4e7..b752541 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
@@ -273,6 +273,9 @@
}
closeAllInputs();
+ // As the input device list can impact the output device selection, update
+ // getDeviceForStrategy() cache
+ updateDevicesAndOutputs();
if (mEngine->getPhoneState() == AUDIO_MODE_IN_CALL && hasPrimaryOutput()) {
audio_devices_t newDevice = getNewOutputDevice(mPrimaryOutput, false /*fromCache*/);
diff --git a/services/camera/libcameraservice/CameraService.cpp b/services/camera/libcameraservice/CameraService.cpp
index 4510d36..d0df6d1 100644
--- a/services/camera/libcameraservice/CameraService.cpp
+++ b/services/camera/libcameraservice/CameraService.cpp
@@ -2119,6 +2119,8 @@
}
finishCameraOps();
+ // Notify flashlight that a camera device is closed.
+ mCameraService->mFlashlight->deviceClosed(String8::format("%d", mCameraId));
ALOGI("%s: Disconnected client for camera %d for PID %d", __FUNCTION__, mCameraId, mClientPid);
// client shouldn't be able to call into us anymore
@@ -2216,10 +2218,6 @@
// Transition device state to CLOSED
mCameraService->updateProxyDeviceState(ICameraServiceProxy::CAMERA_STATE_CLOSED,
String8::format("%d", mCameraId));
-
- // Notify flashlight that a camera device is closed.
- mCameraService->mFlashlight->deviceClosed(
- String8::format("%d", mCameraId));
}
// Always stop watching, even if no camera op is active
if (mOpsCallback != NULL) {
diff --git a/services/camera/libcameraservice/device3/Camera3Device.cpp b/services/camera/libcameraservice/device3/Camera3Device.cpp
index bf94aca..40f8e75 100644
--- a/services/camera/libcameraservice/device3/Camera3Device.cpp
+++ b/services/camera/libcameraservice/device3/Camera3Device.cpp
@@ -3135,7 +3135,7 @@
mFlushLock.lock();
}
- ALOGVV("%s: %d: submitting %d requests in a batch.", __FUNCTION__, __LINE__,
+ ALOGVV("%s: %d: submitting %zu requests in a batch.", __FUNCTION__, __LINE__,
mNextRequests.size());
for (auto& nextRequest : mNextRequests) {
// Submit request and block until ready for next one
diff --git a/services/camera/libcameraservice/device3/Camera3OutputStream.cpp b/services/camera/libcameraservice/device3/Camera3OutputStream.cpp
index 299435a..7229929 100644
--- a/services/camera/libcameraservice/device3/Camera3OutputStream.cpp
+++ b/services/camera/libcameraservice/device3/Camera3OutputStream.cpp
@@ -472,6 +472,12 @@
__FUNCTION__, mTransform, strerror(-res), res);
}
+ // Set dequeueBuffer/attachBuffer timeout if the consumer is not hw composer or hw texture.
+ // We need skip these cases as timeout will disable the non-blocking (async) mode.
+ if (!(isConsumedByHWComposer() || isConsumedByHWTexture())) {
+ mConsumer->setDequeueTimeout(kDequeueBufferTimeout);
+ }
+
/**
* Camera3 Buffer manager is only supported by HAL3.3 onwards, as the older HALs requires
* buffers to be statically allocated for internal static buffer registration, while the
@@ -701,6 +707,17 @@
return (usage & GRALLOC_USAGE_HW_COMPOSER) != 0;
}
+bool Camera3OutputStream::isConsumedByHWTexture() const {
+ uint32_t usage = 0;
+ status_t res = getEndpointUsage(&usage);
+ if (res != OK) {
+ ALOGE("%s: getting end point usage failed: %s (%d).", __FUNCTION__, strerror(-res), res);
+ return false;
+ }
+
+ return (usage & GRALLOC_USAGE_HW_TEXTURE) != 0;
+}
+
}; // namespace camera3
}; // namespace android
diff --git a/services/camera/libcameraservice/device3/Camera3OutputStream.h b/services/camera/libcameraservice/device3/Camera3OutputStream.h
index 5507cfc..d450a69 100644
--- a/services/camera/libcameraservice/device3/Camera3OutputStream.h
+++ b/services/camera/libcameraservice/device3/Camera3OutputStream.h
@@ -128,6 +128,11 @@
bool isConsumedByHWComposer() const;
/**
+ * Return if this output stream is consumed by hardware texture.
+ */
+ bool isConsumedByHWTexture() const;
+
+ /**
* Return if the consumer configuration of this stream is deferred.
*/
virtual bool isConsumerConfigurationDeferred() const;
@@ -181,6 +186,9 @@
sp<Surface> mConsumer;
private:
+
+ static const nsecs_t kDequeueBufferTimeout = 1000000000; // 1 sec
+
int mTransform;
virtual status_t setTransformLocked(int transform);