Merge "Fix AudioFlinger dump"
diff --git a/drm/mediadrm/plugins/clearkey/aidl/CryptoPlugin.cpp b/drm/mediadrm/plugins/clearkey/aidl/CryptoPlugin.cpp
index 201cf02..afc9b6a 100644
--- a/drm/mediadrm/plugins/clearkey/aidl/CryptoPlugin.cpp
+++ b/drm/mediadrm/plugins/clearkey/aidl/CryptoPlugin.cpp
@@ -144,6 +144,11 @@
clearDataLengths.push_back(ss.numBytesOfClearData);
encryptedDataLengths.push_back(ss.numBytesOfEncryptedData);
}
+ if (in_args.keyId.size() != kBlockSize || in_args.iv.size() != kBlockSize) {
+ android_errorWriteLog(0x534e4554, "244569759");
+ detailedError = "invalid decrypt parameter size";
+ return toNdkScopedAStatus(Status::ERROR_DRM_CANNOT_HANDLE, detailedError);
+ }
auto res =
mSession->decrypt(in_args.keyId.data(), in_args.iv.data(),
srcPtr, static_cast<uint8_t*>(destPtr),
diff --git a/drm/mediadrm/plugins/clearkey/aidl/DrmPlugin.cpp b/drm/mediadrm/plugins/clearkey/aidl/DrmPlugin.cpp
index 12aa4ea..054eabd 100644
--- a/drm/mediadrm/plugins/clearkey/aidl/DrmPlugin.cpp
+++ b/drm/mediadrm/plugins/clearkey/aidl/DrmPlugin.cpp
@@ -177,7 +177,7 @@
UNUSED(in_optionalParameters);
KeyRequestType keyRequestType = KeyRequestType::UNKNOWN;
- std::string defaultUrl("https://default.url");
+ std::string defaultUrl("");
_aidl_return->request = {};
_aidl_return->requestType = keyRequestType;
diff --git a/drm/mediadrm/plugins/clearkey/hidl/CryptoPlugin.cpp b/drm/mediadrm/plugins/clearkey/hidl/CryptoPlugin.cpp
index 3a675f6..7bc320d 100644
--- a/drm/mediadrm/plugins/clearkey/hidl/CryptoPlugin.cpp
+++ b/drm/mediadrm/plugins/clearkey/hidl/CryptoPlugin.cpp
@@ -206,6 +206,11 @@
return Void();
} else if (mode == Mode::AES_CTR) {
size_t bytesDecrypted;
+ if (keyId.size() != kBlockSize || iv.size() != kBlockSize) {
+ android_errorWriteLog(0x534e4554, "244569759");
+ _hidl_cb(Status_V1_2::ERROR_DRM_CANNOT_HANDLE, 0, "invalid decrypt parameter size");
+ return Void();
+ }
Status_V1_2 res = mSession->decrypt(keyId.data(), iv.data(), srcPtr,
static_cast<uint8_t*>(destPtr), toVector(subSamples), &bytesDecrypted);
if (res == Status_V1_2::OK) {
diff --git a/media/codec2/components/vpx/C2SoftVpxEnc.cpp b/media/codec2/components/vpx/C2SoftVpxEnc.cpp
index 2efc00f..2a019d4 100644
--- a/media/codec2/components/vpx/C2SoftVpxEnc.cpp
+++ b/media/codec2/components/vpx/C2SoftVpxEnc.cpp
@@ -59,7 +59,7 @@
addParameter(
DefineParam(mSize, C2_PARAMKEY_PICTURE_SIZE)
- .withDefault(new C2StreamPictureSizeInfo::input(0u, 320, 240))
+ .withDefault(new C2StreamPictureSizeInfo::input(0u, 64, 64))
.withFields({
C2F(mSize, width).inRange(2, 2048, 2),
C2F(mSize, height).inRange(2, 2048, 2),
@@ -81,7 +81,7 @@
addParameter(
DefineParam(mFrameRate, C2_PARAMKEY_FRAME_RATE)
- .withDefault(new C2StreamFrameRateInfo::output(0u, 30.))
+ .withDefault(new C2StreamFrameRateInfo::output(0u, 1.))
// TODO: More restriction?
.withFields({C2F(mFrameRate, value).greaterThan(0.)})
.withSetter(
@@ -127,10 +127,18 @@
C2F(mProfileLevel, profile).equalTo(
PROFILE_VP9_0
),
- C2F(mProfileLevel, level).equalTo(
- LEVEL_VP9_4_1),
+ C2F(mProfileLevel, level).oneOf({
+ C2Config::LEVEL_VP9_1,
+ C2Config::LEVEL_VP9_1_1,
+ C2Config::LEVEL_VP9_2,
+ C2Config::LEVEL_VP9_2_1,
+ C2Config::LEVEL_VP9_3,
+ C2Config::LEVEL_VP9_3_1,
+ C2Config::LEVEL_VP9_4,
+ C2Config::LEVEL_VP9_4_1,
+ }),
})
- .withSetter(ProfileLevelSetter)
+ .withSetter(ProfileLevelSetter, mSize, mFrameRate, mBitrate)
.build());
#else
addParameter(
@@ -144,7 +152,7 @@
C2F(mProfileLevel, level).equalTo(
LEVEL_UNUSED),
})
- .withSetter(ProfileLevelSetter)
+ .withSetter(ProfileLevelSetter, mSize, mFrameRate, mBitrate)
.build());
#endif
addParameter(
@@ -217,14 +225,84 @@
}
C2R C2SoftVpxEnc::IntfImpl::ProfileLevelSetter(bool mayBlock,
- C2P<C2StreamProfileLevelInfo::output>& me) {
+ C2P<C2StreamProfileLevelInfo::output>& me,
+ const C2P<C2StreamPictureSizeInfo::input>& size,
+ const C2P<C2StreamFrameRateInfo::output>& frameRate,
+ const C2P<C2StreamBitrateInfo::output>& bitrate) {
(void)mayBlock;
+#ifdef VP9
if (!me.F(me.v.profile).supportsAtAll(me.v.profile)) {
me.set().profile = PROFILE_VP9_0;
}
- if (!me.F(me.v.level).supportsAtAll(me.v.level)) {
+ struct LevelLimits {
+ C2Config::level_t level;
+ float samplesPerSec;
+ uint64_t samples;
+ uint32_t bitrate;
+ size_t dimension;
+ };
+ constexpr LevelLimits kLimits[] = {
+ {LEVEL_VP9_1, 829440, 36864, 200000, 512},
+ {LEVEL_VP9_1_1, 2764800, 73728, 800000, 768},
+ {LEVEL_VP9_2, 4608000, 122880, 1800000, 960},
+ {LEVEL_VP9_2_1, 9216000, 245760, 3600000, 1344},
+ {LEVEL_VP9_3, 20736000, 552960, 7200000, 2048},
+ {LEVEL_VP9_3_1, 36864000, 983040, 12000000, 2752},
+ {LEVEL_VP9_4, 83558400, 2228224, 18000000, 4160},
+ {LEVEL_VP9_4_1, 160432128, 2228224, 30000000, 4160},
+ };
+
+ uint64_t samples = size.v.width * size.v.height;
+ float samplesPerSec = float(samples) * frameRate.v.value;
+ size_t dimension = std::max(size.v.width, size.v.height);
+
+ // Check if the supplied level meets the samples / bitrate requirements.
+ // If not, update the level with the lowest level meeting the requirements.
+ bool found = false;
+
+ // By default needsUpdate = false in case the supplied level does meet
+ // the requirements.
+ bool needsUpdate = false;
+ for (const LevelLimits& limit : kLimits) {
+ if (samples > limit.samples) continue;
+ if (samplesPerSec > limit.samplesPerSec) continue;
+ if (bitrate.v.value > limit.bitrate) continue;
+ if (dimension > limit.dimension) continue;
+
+ // This is the lowest level that meets the requirements, and if
+ // we haven't seen the supplied level yet, that means we don't
+ // need the update.
+ if (needsUpdate) {
+ ALOGD("Given level %x does not cover current configuration: "
+ "adjusting to %x",
+ me.v.level, limit.level);
+ me.set().level = limit.level;
+ }
+ found = true;
+ break;
+
+ if (me.v.level == limit.level) {
+ // We break out of the loop when the lowest feasible level is
+ // found. The fact that we're here means that our level doesn't
+ // meet the requirement and needs to be updated.
+ needsUpdate = true;
+ }
+ }
+ if (!found) {
+ // We set to the highest supported level.
me.set().level = LEVEL_VP9_4_1;
}
+#else
+ (void)size;
+ (void)frameRate;
+ (void)bitrate;
+ if (!me.F(me.v.profile).supportsAtAll(me.v.profile)) {
+ me.set().profile = PROFILE_VP8_0;
+ }
+ if (!me.F(me.v.level).supportsAtAll(me.v.level)) {
+ me.set().level = LEVEL_UNUSED;
+ }
+#endif
return C2R::Ok();
}
diff --git a/media/codec2/components/vpx/C2SoftVpxEnc.h b/media/codec2/components/vpx/C2SoftVpxEnc.h
index 714fadb..bfb4444 100644
--- a/media/codec2/components/vpx/C2SoftVpxEnc.h
+++ b/media/codec2/components/vpx/C2SoftVpxEnc.h
@@ -243,9 +243,10 @@
static C2R SizeSetter(bool mayBlock, const C2P<C2StreamPictureSizeInfo::input> &oldMe,
C2P<C2StreamPictureSizeInfo::input> &me);
- static C2R ProfileLevelSetter(
- bool mayBlock,
- C2P<C2StreamProfileLevelInfo::output> &me);
+ static C2R ProfileLevelSetter(bool mayBlock, C2P<C2StreamProfileLevelInfo::output>& me,
+ const C2P<C2StreamPictureSizeInfo::input>& size,
+ const C2P<C2StreamFrameRateInfo::output>& frameRate,
+ const C2P<C2StreamBitrateInfo::output>& bitrate);
static C2R LayeringSetter(bool mayBlock, C2P<C2StreamTemporalLayeringTuning::output>& me);
diff --git a/media/codec2/sfplugin/CCodecBuffers.h b/media/codec2/sfplugin/CCodecBuffers.h
index c8e9930..6335f13 100644
--- a/media/codec2/sfplugin/CCodecBuffers.h
+++ b/media/codec2/sfplugin/CCodecBuffers.h
@@ -72,7 +72,7 @@
virtual void getArray(Vector<sp<MediaCodecBuffer>> *) const {}
/**
- * Return number of buffers the client owns.
+ * Return number of buffers owned by the client or the component.
*/
virtual size_t numActiveSlots() const = 0;
@@ -595,8 +595,7 @@
void flush();
/**
- * Return the number of buffers that are sent to the client but not released
- * yet.
+ * Return the number of buffers that are sent to the client or the component.
*/
size_t numActiveSlots() const;
@@ -716,8 +715,7 @@
void grow(size_t newSize, std::function<sp<Codec2Buffer>()> alloc);
/**
- * Return the number of buffers that are sent to the client but not released
- * yet.
+ * Return the number of buffers that are sent to the client or the component.
*/
size_t numActiveSlots() const;
diff --git a/media/codec2/sfplugin/Codec2Buffer.cpp b/media/codec2/sfplugin/Codec2Buffer.cpp
index 876c96d..b9270de 100644
--- a/media/codec2/sfplugin/Codec2Buffer.cpp
+++ b/media/codec2/sfplugin/Codec2Buffer.cpp
@@ -533,7 +533,7 @@
* align(mHeight, 64) / plane.rowSampling;
}
- if (minPtr == mView.data()[0] && (maxPtr - minPtr + 1) <= planeSize) {
+ if (minPtr == mView.data()[0] && (maxPtr - minPtr) <= planeSize) {
// FIXME: this is risky as reading/writing data out of bound results
// in an undefined behavior, but gralloc does assume a
// contiguous mapping
@@ -545,8 +545,7 @@
mediaImage->mPlane[i].mHorizSubsampling = plane.colSampling;
mediaImage->mPlane[i].mVertSubsampling = plane.rowSampling;
}
- mWrapped = new ABuffer(const_cast<uint8_t *>(minPtr),
- maxPtr - minPtr + 1);
+ mWrapped = new ABuffer(const_cast<uint8_t *>(minPtr), maxPtr - minPtr);
ALOGV("Converter: wrapped (capacity=%zu)", mWrapped->capacity());
}
}
diff --git a/media/libaaudio/Android.bp b/media/libaaudio/Android.bp
index add28e0..4b417a7 100644
--- a/media/libaaudio/Android.bp
+++ b/media/libaaudio/Android.bp
@@ -36,6 +36,9 @@
symbol_file: "src/libaaudio.map.txt",
first_version: "26",
unversioned_until: "current",
+ export_header_libs: [
+ "libAAudio_headers",
+ ],
}
cc_library_headers {
diff --git a/media/libaaudio/src/core/AudioStreamBuilder.cpp b/media/libaaudio/src/core/AudioStreamBuilder.cpp
index 04b4325..91fd5bf 100644
--- a/media/libaaudio/src/core/AudioStreamBuilder.cpp
+++ b/media/libaaudio/src/core/AudioStreamBuilder.cpp
@@ -24,7 +24,6 @@
#include <aaudio/AAudio.h>
#include <aaudio/AAudioTesting.h>
-#include <android/media/audio/common/AudioMMapPolicy.h>
#include <android/media/audio/common/AudioMMapPolicyInfo.h>
#include <android/media/audio/common/AudioMMapPolicyType.h>
#include <media/AudioSystem.h>
@@ -37,10 +36,10 @@
#include "core/AudioStreamBuilder.h"
#include "legacy/AudioStreamRecord.h"
#include "legacy/AudioStreamTrack.h"
+#include "utility/AAudioUtilities.h"
using namespace aaudio;
-using android::media::audio::common::AudioMMapPolicy;
using android::media::audio::common::AudioMMapPolicyInfo;
using android::media::audio::common::AudioMMapPolicyType;
@@ -95,37 +94,6 @@
return result;
}
-namespace {
-
-aaudio_policy_t aidl2legacy_aaudio_policy(AudioMMapPolicy aidl) {
- switch (aidl) {
- case AudioMMapPolicy::NEVER:
- return AAUDIO_POLICY_NEVER;
- case AudioMMapPolicy::AUTO:
- return AAUDIO_POLICY_AUTO;
- case AudioMMapPolicy::ALWAYS:
- return AAUDIO_POLICY_ALWAYS;
- case AudioMMapPolicy::UNSPECIFIED:
- default:
- return AAUDIO_UNSPECIFIED;
- }
-}
-
-// The aaudio policy will be ALWAYS, NEVER, UNSPECIFIED only when all policy info are
-// ALWAYS, NEVER or UNSPECIFIED. Otherwise, the aaudio policy will be AUTO.
-aaudio_policy_t getAAudioPolicy(
- const std::vector<AudioMMapPolicyInfo>& policyInfos) {
- if (policyInfos.empty()) return AAUDIO_POLICY_AUTO;
- for (size_t i = 1; i < policyInfos.size(); ++i) {
- if (policyInfos.at(i).mmapPolicy != policyInfos.at(0).mmapPolicy) {
- return AAUDIO_POLICY_AUTO;
- }
- }
- return aidl2legacy_aaudio_policy(policyInfos.at(0).mmapPolicy);
-}
-
-} // namespace
-
// Try to open using MMAP path if that is allowed.
// Fall back to Legacy path if MMAP not available.
// Exact behavior is controlled by MMapPolicy.
@@ -150,7 +118,7 @@
// If not specified then get from a system property.
if (mmapPolicy == AAUDIO_UNSPECIFIED && android::AudioSystem::getMmapPolicyInfo(
AudioMMapPolicyType::DEFAULT, &policyInfos) == NO_ERROR) {
- mmapPolicy = getAAudioPolicy(policyInfos);
+ mmapPolicy = AAudio_getAAudioPolicy(policyInfos);
}
// If still not specified then use the default.
if (mmapPolicy == AAUDIO_UNSPECIFIED) {
@@ -161,7 +129,7 @@
aaudio_policy_t mmapExclusivePolicy = AAUDIO_UNSPECIFIED;
if (android::AudioSystem::getMmapPolicyInfo(
AudioMMapPolicyType::EXCLUSIVE, &policyInfos) == NO_ERROR) {
- mmapExclusivePolicy = getAAudioPolicy(policyInfos);
+ mmapExclusivePolicy = AAudio_getAAudioPolicy(policyInfos);
}
if (mmapExclusivePolicy == AAUDIO_UNSPECIFIED) {
mmapExclusivePolicy = AAUDIO_MMAP_EXCLUSIVE_POLICY_DEFAULT;
diff --git a/media/libaaudio/src/utility/AAudioUtilities.cpp b/media/libaaudio/src/utility/AAudioUtilities.cpp
index a197ced..0afa11b 100644
--- a/media/libaaudio/src/utility/AAudioUtilities.cpp
+++ b/media/libaaudio/src/utility/AAudioUtilities.cpp
@@ -16,24 +16,28 @@
#define LOG_TAG "AAudio"
//#define LOG_NDEBUG 0
-#include <utils/Log.h>
-#include <cutils/properties.h>
+#include <assert.h>
+#include <math.h>
#include <stdint.h>
+
+#include <aaudio/AAudioTesting.h>
+#include <android/media/audio/common/AudioMMapPolicy.h>
+#include <cutils/properties.h>
#include <sys/types.h>
+#include <system/audio.h>
#include <utils/Errors.h>
+#include <utils/Log.h>
#include "aaudio/AAudio.h"
#include "core/AudioGlobal.h"
-#include <aaudio/AAudioTesting.h>
-#include <math.h>
-#include <system/audio.h>
-#include <assert.h>
-
#include "utility/AAudioUtilities.h"
using namespace android;
+using android::media::audio::common::AudioMMapPolicy;
+using android::media::audio::common::AudioMMapPolicyInfo;
+
status_t AAudioConvert_aaudioToAndroidStatus(aaudio_result_t result) {
// This covers the case for AAUDIO_OK and for positive results.
if (result >= 0) {
@@ -638,3 +642,31 @@
}
return result;
}
+
+namespace {
+
+aaudio_policy_t aidl2legacy_aaudio_policy(AudioMMapPolicy aidl) {
+ switch (aidl) {
+ case AudioMMapPolicy::NEVER:
+ return AAUDIO_POLICY_NEVER;
+ case AudioMMapPolicy::AUTO:
+ return AAUDIO_POLICY_AUTO;
+ case AudioMMapPolicy::ALWAYS:
+ return AAUDIO_POLICY_ALWAYS;
+ case AudioMMapPolicy::UNSPECIFIED:
+ default:
+ return AAUDIO_UNSPECIFIED;
+ }
+}
+
+} // namespace
+
+aaudio_policy_t AAudio_getAAudioPolicy(const std::vector<AudioMMapPolicyInfo>& policyInfos) {
+ if (policyInfos.empty()) return AAUDIO_POLICY_AUTO;
+ for (size_t i = 1; i < policyInfos.size(); ++i) {
+ if (policyInfos.at(i).mmapPolicy != policyInfos.at(0).mmapPolicy) {
+ return AAUDIO_POLICY_AUTO;
+ }
+ }
+ return aidl2legacy_aaudio_policy(policyInfos.at(0).mmapPolicy);
+}
diff --git a/media/libaaudio/src/utility/AAudioUtilities.h b/media/libaaudio/src/utility/AAudioUtilities.h
index b59ce1c..ac75306 100644
--- a/media/libaaudio/src/utility/AAudioUtilities.h
+++ b/media/libaaudio/src/utility/AAudioUtilities.h
@@ -19,14 +19,17 @@
#include <algorithm>
#include <functional>
+#include <vector>
#include <stdint.h>
#include <sys/types.h>
#include <unistd.h>
+#include <android/media/audio/common/AudioMMapPolicyInfo.h>
#include <utils/Errors.h>
#include <system/audio.h>
#include "aaudio/AAudio.h"
+#include "aaudio/AAudioTesting.h"
/**
* Convert an AAudio result into the closest matching Android status.
@@ -343,4 +346,9 @@
AAUDIO_CHANNEL_INDEX_MASK_24 = AAUDIO_CHANNEL_BIT_INDEX | (1 << 24) - 1,
};
+// The aaudio policy will be ALWAYS, NEVER, UNSPECIFIED only when all policy info are
+// ALWAYS, NEVER or UNSPECIFIED. Otherwise, the aaudio policy will be AUTO.
+aaudio_policy_t AAudio_getAAudioPolicy(
+ const std::vector<android::media::audio::common::AudioMMapPolicyInfo>& policyInfos);
+
#endif //UTILITY_AAUDIO_UTILITIES_H
diff --git a/media/libaaudio/tests/Android.bp b/media/libaaudio/tests/Android.bp
index 4b45909..438be0a 100644
--- a/media/libaaudio/tests/Android.bp
+++ b/media/libaaudio/tests/Android.bp
@@ -214,3 +214,17 @@
srcs: ["test_disconnect_race.cpp"],
shared_libs: ["libaaudio"],
}
+
+cc_test {
+ name: "aaudio_test_mmap_path",
+ defaults: [
+ "libaaudio_tests_defaults",
+ ],
+ srcs: ["test_mmap_path.cpp"],
+ shared_libs: [
+ "libaaudio",
+ "libaaudio_internal",
+ "libaudioclient",
+ "liblog",
+ ],
+}
diff --git a/media/libaaudio/tests/test_mmap_path.cpp b/media/libaaudio/tests/test_mmap_path.cpp
new file mode 100644
index 0000000..c8376f6
--- /dev/null
+++ b/media/libaaudio/tests/test_mmap_path.cpp
@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#define LOG_TAG "test_mmap_path"
+
+#include <vector>
+
+#include <aaudio/AAudio.h>
+#include <aaudio/AAudioTesting.h>
+#include <android/log.h>
+#include <android/media/audio/common/AudioMMapPolicyInfo.h>
+#include <android/media/audio/common/AudioMMapPolicyType.h>
+#include <media/AudioSystem.h>
+
+#include <gtest/gtest.h>
+
+#include "utility/AAudioUtilities.h"
+
+using android::media::audio::common::AudioMMapPolicyInfo;
+using android::media::audio::common::AudioMMapPolicyType;
+
+/**
+ * Open a stream via AAudio API and set the performance mode as LOW_LATENCY. When MMAP is supported,
+ * the stream is supposed to be on MMAP path instead of legacy path. This is guaranteed on pixel
+ * devices, but may not be guaranteed on other vendor devices.
+ * @param direction the direction for the stream
+ */
+static void openStreamAndVerify(aaudio_direction_t direction) {
+ std::vector<AudioMMapPolicyInfo> policyInfos;
+ ASSERT_EQ(android::NO_ERROR, android::AudioSystem::getMmapPolicyInfo(
+ AudioMMapPolicyType::DEFAULT, &policyInfos));
+ if (AAudio_getAAudioPolicy(policyInfos) == AAUDIO_POLICY_NEVER) {
+ // Query the system MMAP policy, if it is NEVER, it indicates there is no MMAP support.
+ // In that case, there is no need to run the test. The reason of adding the query is to
+ // avoid someone accidentally run the test on device that doesn't support MMAP,
+ // such as cuttlefish.
+ ALOGD("Skip test as mmap is not supported");
+ return;
+ }
+
+ AAudioStreamBuilder *aaudioBuilder = nullptr;
+ AAudioStream *aaudioStream = nullptr;
+
+ ASSERT_EQ(AAUDIO_OK, AAudio_createStreamBuilder(&aaudioBuilder));
+
+ AAudioStreamBuilder_setDirection(aaudioBuilder, direction);
+ AAudioStreamBuilder_setPerformanceMode(aaudioBuilder, AAUDIO_PERFORMANCE_MODE_LOW_LATENCY);
+
+ EXPECT_EQ(AAUDIO_OK, AAudioStreamBuilder_openStream(aaudioBuilder, &aaudioStream));
+ EXPECT_EQ(AAUDIO_PERFORMANCE_MODE_LOW_LATENCY, AAudioStream_getPerformanceMode(aaudioStream));
+ EXPECT_TRUE(AAudioStream_isMMapUsed(aaudioStream));
+
+ AAudioStream_close(aaudioStream);
+ AAudioStreamBuilder_delete(aaudioBuilder);
+}
+
+TEST(test_mmap_path, input) {
+ openStreamAndVerify(AAUDIO_DIRECTION_INPUT);
+}
+
+TEST(test_mmap_path, output) {
+ openStreamAndVerify(AAUDIO_DIRECTION_OUTPUT);
+}
diff --git a/media/libaudioclient/Android.bp b/media/libaudioclient/Android.bp
index b6ddf56..6c198d3 100644
--- a/media/libaudioclient/Android.bp
+++ b/media/libaudioclient/Android.bp
@@ -48,7 +48,7 @@
cc_library {
name: "libaudiopolicy",
srcs: [
- "AudioAttributes.cpp",
+ "VolumeGroupAttributes.cpp",
"AudioPolicy.cpp",
"AudioProductStrategy.cpp",
"AudioVolumeGroup.cpp",
diff --git a/media/libaudioclient/AudioProductStrategy.cpp b/media/libaudioclient/AudioProductStrategy.cpp
index ecd423a..381faf6 100644
--- a/media/libaudioclient/AudioProductStrategy.cpp
+++ b/media/libaudioclient/AudioProductStrategy.cpp
@@ -18,7 +18,7 @@
//#define LOG_NDEBUG 0
#include <utils/Log.h>
#include <media/AudioProductStrategy.h>
-#include <media/AudioAttributes.h>
+#include <media/VolumeGroupAttributes.h>
#include <media/PolicyAidlConversion.h>
namespace android {
@@ -42,8 +42,8 @@
aidl.name = legacy.getName();
aidl.audioAttributes = VALUE_OR_RETURN(
convertContainer<std::vector<media::AudioAttributesEx>>(
- legacy.getAudioAttributes(),
- legacy2aidl_AudioAttributes_AudioAttributesEx));
+ legacy.getVolumeGroupAttributes(),
+ legacy2aidl_VolumeGroupAttributes_AudioAttributesEx));
aidl.id = VALUE_OR_RETURN(legacy2aidl_product_strategy_t_int32_t(legacy.getId()));
return aidl;
}
@@ -53,9 +53,9 @@
return AudioProductStrategy(
aidl.name,
VALUE_OR_RETURN(
- convertContainer<std::vector<AudioAttributes>>(
+ convertContainer<std::vector<VolumeGroupAttributes>>(
aidl.audioAttributes,
- aidl2legacy_AudioAttributesEx_AudioAttributes)),
+ aidl2legacy_AudioAttributesEx_VolumeGroupAttributes)),
VALUE_OR_RETURN(aidl2legacy_int32_t_product_strategy_t(aidl.id)));
}
diff --git a/media/libaudioclient/AudioSystem.cpp b/media/libaudioclient/AudioSystem.cpp
index 05f27b0..af00ab1 100644
--- a/media/libaudioclient/AudioSystem.cpp
+++ b/media/libaudioclient/AudioSystem.cpp
@@ -1336,7 +1336,7 @@
return result.value_or(PRODUCT_STRATEGY_NONE);
}
-status_t AudioSystem::getDevicesForAttributes(const AudioAttributes& aa,
+status_t AudioSystem::getDevicesForAttributes(const audio_attributes_t& aa,
AudioDeviceTypeAddrVector* devices,
bool forVolume) {
if (devices == nullptr) {
@@ -1345,8 +1345,8 @@
const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service();
if (aps == 0) return PERMISSION_DENIED;
- media::AudioAttributesEx aaAidl = VALUE_OR_RETURN_STATUS(
- legacy2aidl_AudioAttributes_AudioAttributesEx(aa));
+ media::AudioAttributesInternal aaAidl = VALUE_OR_RETURN_STATUS(
+ legacy2aidl_audio_attributes_t_AudioAttributesInternal(aa));
std::vector<AudioDevice> retAidl;
RETURN_STATUS_IF_ERROR(
statusTFromBinderStatus(aps->getDevicesForAttributes(aaAidl, forVolume, &retAidl)));
@@ -2093,7 +2093,7 @@
AudioProductStrategyVector strategies;
listAudioProductStrategies(strategies);
for (const auto& strategy : strategies) {
- auto attrVect = strategy.getAudioAttributes();
+ auto attrVect = strategy.getVolumeGroupAttributes();
auto iter = std::find_if(begin(attrVect), end(attrVect), [&stream](const auto& attributes) {
return attributes.getStreamType() == stream;
});
@@ -2107,7 +2107,7 @@
audio_stream_type_t AudioSystem::attributesToStreamType(const audio_attributes_t& attr) {
product_strategy_t psId;
- status_t ret = AudioSystem::getProductStrategyFromAudioAttributes(AudioAttributes(attr), psId);
+ status_t ret = AudioSystem::getProductStrategyFromAudioAttributes(attr, psId);
if (ret != NO_ERROR) {
ALOGE("no strategy found for attributes %s", toString(attr).c_str());
return AUDIO_STREAM_MUSIC;
@@ -2116,7 +2116,7 @@
listAudioProductStrategies(strategies);
for (const auto& strategy : strategies) {
if (strategy.getId() == psId) {
- auto attrVect = strategy.getAudioAttributes();
+ auto attrVect = strategy.getVolumeGroupAttributes();
auto iter = std::find_if(begin(attrVect), end(attrVect), [&attr](const auto& refAttr) {
return AudioProductStrategy::attributesMatches(
refAttr.getAttributes(), attr);
@@ -2137,14 +2137,14 @@
return AUDIO_STREAM_MUSIC;
}
-status_t AudioSystem::getProductStrategyFromAudioAttributes(const AudioAttributes& aa,
+status_t AudioSystem::getProductStrategyFromAudioAttributes(const audio_attributes_t& aa,
product_strategy_t& productStrategy,
bool fallbackOnDefault) {
const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service();
if (aps == 0) return PERMISSION_DENIED;
- media::AudioAttributesEx aaAidl = VALUE_OR_RETURN_STATUS(
- legacy2aidl_AudioAttributes_AudioAttributesEx(aa));
+ media::AudioAttributesInternal aaAidl = VALUE_OR_RETURN_STATUS(
+ legacy2aidl_audio_attributes_t_AudioAttributesInternal(aa));
int32_t productStrategyAidl;
RETURN_STATUS_IF_ERROR(statusTFromBinderStatus(
@@ -2167,14 +2167,14 @@
return OK;
}
-status_t AudioSystem::getVolumeGroupFromAudioAttributes(const AudioAttributes& aa,
+status_t AudioSystem::getVolumeGroupFromAudioAttributes(const audio_attributes_t &aa,
volume_group_t& volumeGroup,
bool fallbackOnDefault) {
const sp<IAudioPolicyService>& aps = AudioSystem::get_audio_policy_service();
if (aps == 0) return PERMISSION_DENIED;
- media::AudioAttributesEx aaAidl = VALUE_OR_RETURN_STATUS(
- legacy2aidl_AudioAttributes_AudioAttributesEx(aa));
+ media::AudioAttributesInternal aaAidl = VALUE_OR_RETURN_STATUS(
+ legacy2aidl_audio_attributes_t_AudioAttributesInternal(aa));
int32_t volumeGroupAidl;
RETURN_STATUS_IF_ERROR(statusTFromBinderStatus(
aps->getVolumeGroupFromAudioAttributes(aaAidl, fallbackOnDefault, &volumeGroupAidl)));
diff --git a/media/libaudioclient/AudioVolumeGroup.cpp b/media/libaudioclient/AudioVolumeGroup.cpp
index ab95246..978599e 100644
--- a/media/libaudioclient/AudioVolumeGroup.cpp
+++ b/media/libaudioclient/AudioVolumeGroup.cpp
@@ -23,7 +23,6 @@
#include <media/AidlConversion.h>
#include <media/AudioVolumeGroup.h>
-#include <media/AudioAttributes.h>
#include <media/PolicyAidlConversion.h>
namespace android {
diff --git a/media/libaudioclient/AudioAttributes.cpp b/media/libaudioclient/VolumeGroupAttributes.cpp
similarity index 73%
rename from media/libaudioclient/AudioAttributes.cpp
rename to media/libaudioclient/VolumeGroupAttributes.cpp
index 260c06c..2de4667 100644
--- a/media/libaudioclient/AudioAttributes.cpp
+++ b/media/libaudioclient/VolumeGroupAttributes.cpp
@@ -14,33 +14,33 @@
* limitations under the License.
*/
-#define LOG_TAG "AudioAttributes"
+#define LOG_TAG "VolumeGroupAttributes"
//#define LOG_NDEBUG 0
#include <utils/Log.h>
#include <binder/Parcel.h>
#include <media/AidlConversion.h>
-#include <media/AudioAttributes.h>
+#include <media/VolumeGroupAttributes.h>
#include <media/PolicyAidlConversion.h>
namespace android {
-status_t AudioAttributes::readFromParcel(const Parcel* parcel) {
+status_t VolumeGroupAttributes::readFromParcel(const Parcel* parcel) {
media::AudioAttributesEx aidl;
RETURN_STATUS_IF_ERROR(aidl.readFromParcel(parcel));
- *this = VALUE_OR_RETURN_STATUS(aidl2legacy_AudioAttributesEx_AudioAttributes(aidl));
+ *this = VALUE_OR_RETURN_STATUS(aidl2legacy_AudioAttributesEx_VolumeGroupAttributes(aidl));
return OK;
}
-status_t AudioAttributes::writeToParcel(Parcel* parcel) const {
+status_t VolumeGroupAttributes::writeToParcel(Parcel* parcel) const {
media::AudioAttributesEx aidl = VALUE_OR_RETURN_STATUS(
- legacy2aidl_AudioAttributes_AudioAttributesEx(*this));
+ legacy2aidl_VolumeGroupAttributes_AudioAttributesEx(*this));
return aidl.writeToParcel(parcel);
}
ConversionResult<media::AudioAttributesEx>
-legacy2aidl_AudioAttributes_AudioAttributesEx(const AudioAttributes& legacy) {
+legacy2aidl_VolumeGroupAttributes_AudioAttributesEx(const VolumeGroupAttributes& legacy) {
media::AudioAttributesEx aidl;
aidl.attributes = VALUE_OR_RETURN(
legacy2aidl_audio_attributes_t_AudioAttributesInternal(legacy.getAttributes()));
@@ -50,9 +50,9 @@
return aidl;
}
-ConversionResult<AudioAttributes>
-aidl2legacy_AudioAttributesEx_AudioAttributes(const media::AudioAttributesEx& aidl) {
- return AudioAttributes(VALUE_OR_RETURN(aidl2legacy_int32_t_volume_group_t(aidl.groupId)),
+ConversionResult<VolumeGroupAttributes>
+aidl2legacy_AudioAttributesEx_VolumeGroupAttributes(const media::AudioAttributesEx& aidl) {
+ return VolumeGroupAttributes(VALUE_OR_RETURN(aidl2legacy_int32_t_volume_group_t(aidl.groupId)),
VALUE_OR_RETURN(aidl2legacy_AudioStreamType_audio_stream_type_t(
aidl.streamType)),
VALUE_OR_RETURN(aidl2legacy_AudioAttributesInternal_audio_attributes_t(
diff --git a/media/libaudioclient/aidl/android/media/IAudioPolicyService.aidl b/media/libaudioclient/aidl/android/media/IAudioPolicyService.aidl
index 8ac89a8..24b59bf 100644
--- a/media/libaudioclient/aidl/android/media/IAudioPolicyService.aidl
+++ b/media/libaudioclient/aidl/android/media/IAudioPolicyService.aidl
@@ -137,7 +137,7 @@
int /* product_strategy_t */ getStrategyForStream(AudioStreamType stream);
- AudioDevice[] getDevicesForAttributes(in AudioAttributesEx attr, boolean forVolume);
+ AudioDevice[] getDevicesForAttributes(in AudioAttributesInternal attr, boolean forVolume);
int /* audio_io_handle_t */ getOutputForEffect(in EffectDescriptor desc);
@@ -313,11 +313,11 @@
boolean isUltrasoundSupported();
AudioProductStrategy[] listAudioProductStrategies();
- int /* product_strategy_t */ getProductStrategyFromAudioAttributes(in AudioAttributesEx aa,
- boolean fallbackOnDefault);
+ int /* product_strategy_t */ getProductStrategyFromAudioAttributes(
+ in AudioAttributesInternal aa, boolean fallbackOnDefault);
AudioVolumeGroup[] listAudioVolumeGroups();
- int /* volume_group_t */ getVolumeGroupFromAudioAttributes(in AudioAttributesEx aa,
+ int /* volume_group_t */ getVolumeGroupFromAudioAttributes(in AudioAttributesInternal aa,
boolean fallbackOnDefault);
void setRttEnabled(boolean enabled);
diff --git a/media/libaudioclient/include/media/AudioProductStrategy.h b/media/libaudioclient/include/media/AudioProductStrategy.h
index b55b506..7bcb5aa 100644
--- a/media/libaudioclient/include/media/AudioProductStrategy.h
+++ b/media/libaudioclient/include/media/AudioProductStrategy.h
@@ -20,7 +20,7 @@
#include <android/media/AudioProductStrategy.h>
#include <media/AidlConversionUtil.h>
#include <media/AudioCommonTypes.h>
-#include <media/AudioAttributes.h>
+#include <media/VolumeGroupAttributes.h>
#include <system/audio.h>
#include <system/audio_policy.h>
#include <binder/Parcelable.h>
@@ -31,12 +31,15 @@
{
public:
AudioProductStrategy() {}
- AudioProductStrategy(const std::string &name, const std::vector<AudioAttributes> &attributes,
+ AudioProductStrategy(const std::string &name,
+ const std::vector<VolumeGroupAttributes> &attributes,
product_strategy_t id) :
- mName(name), mAudioAttributes(attributes), mId(id) {}
+ mName(name), mVolumeGroupAttributes(attributes), mId(id) {}
const std::string &getName() const { return mName; }
- std::vector<AudioAttributes> getAudioAttributes() const { return mAudioAttributes; }
+ std::vector<VolumeGroupAttributes> getVolumeGroupAttributes() const {
+ return mVolumeGroupAttributes;
+ }
product_strategy_t getId() const { return mId; }
status_t readFromParcel(const Parcel *parcel) override;
@@ -58,7 +61,7 @@
const audio_attributes_t clientAttritubes);
private:
std::string mName;
- std::vector<AudioAttributes> mAudioAttributes;
+ std::vector<VolumeGroupAttributes> mVolumeGroupAttributes;
product_strategy_t mId;
};
diff --git a/media/libaudioclient/include/media/AudioSystem.h b/media/libaudioclient/include/media/AudioSystem.h
index 1c414ec..6e6b9c8 100644
--- a/media/libaudioclient/include/media/AudioSystem.h
+++ b/media/libaudioclient/include/media/AudioSystem.h
@@ -370,7 +370,7 @@
static status_t getMinVolumeIndexForAttributes(const audio_attributes_t &attr, int &index);
static product_strategy_t getStrategyForStream(audio_stream_type_t stream);
- static status_t getDevicesForAttributes(const AudioAttributes &aa,
+ static status_t getDevicesForAttributes(const audio_attributes_t &aa,
AudioDeviceTypeAddrVector *devices,
bool forVolume);
@@ -494,7 +494,7 @@
static status_t listAudioProductStrategies(AudioProductStrategyVector &strategies);
static status_t getProductStrategyFromAudioAttributes(
- const AudioAttributes &aa, product_strategy_t &productStrategy,
+ const audio_attributes_t &aa, product_strategy_t &productStrategy,
bool fallbackOnDefault = true);
static audio_attributes_t streamTypeToAttributes(audio_stream_type_t stream);
@@ -503,7 +503,8 @@
static status_t listAudioVolumeGroups(AudioVolumeGroupVector &groups);
static status_t getVolumeGroupFromAudioAttributes(
- const AudioAttributes &aa, volume_group_t &volumeGroup, bool fallbackOnDefault = true);
+ const audio_attributes_t &aa, volume_group_t &volumeGroup,
+ bool fallbackOnDefault = true);
static status_t setRttEnabled(bool enabled);
diff --git a/media/libaudioclient/include/media/AudioAttributes.h b/media/libaudioclient/include/media/VolumeGroupAttributes.h
similarity index 74%
rename from media/libaudioclient/include/media/AudioAttributes.h
rename to media/libaudioclient/include/media/VolumeGroupAttributes.h
index 24bd179..0859995 100644
--- a/media/libaudioclient/include/media/AudioAttributes.h
+++ b/media/libaudioclient/include/media/VolumeGroupAttributes.h
@@ -26,15 +26,20 @@
namespace android {
-class AudioAttributes : public Parcelable
+class VolumeGroupAttributes : public Parcelable
{
public:
- AudioAttributes() = default;
- AudioAttributes(const audio_attributes_t &attributes) : mAttributes(attributes) {} // NOLINT
- AudioAttributes(volume_group_t groupId,
+ VolumeGroupAttributes() = default;
+ VolumeGroupAttributes(const audio_attributes_t &attributes)
+ : mAttributes(attributes) {} // NOLINT
+ VolumeGroupAttributes(volume_group_t groupId,
audio_stream_type_t stream,
const audio_attributes_t &attributes) :
- mAttributes(attributes), mStreamType(stream), mGroupId(groupId) {}
+ mAttributes(attributes), mStreamType(stream), mGroupId(groupId) {
+ // TODO: align native & JAVA source initializer.
+ // As far as this class concerns attributes for volume group, it applies only to playback.
+ mAttributes.source = AUDIO_SOURCE_INVALID;
+ }
audio_attributes_t getAttributes() const { return mAttributes; }
@@ -61,8 +66,8 @@
// AIDL conversion routines.
ConversionResult<media::AudioAttributesEx>
-legacy2aidl_AudioAttributes_AudioAttributesEx(const AudioAttributes& legacy);
-ConversionResult<AudioAttributes>
-aidl2legacy_AudioAttributesEx_AudioAttributes(const media::AudioAttributesEx& aidl);
+legacy2aidl_VolumeGroupAttributes_AudioAttributesEx(const VolumeGroupAttributes& legacy);
+ConversionResult<VolumeGroupAttributes>
+aidl2legacy_AudioAttributesEx_VolumeGroupAttributes(const media::AudioAttributesEx& aidl);
} // namespace android
diff --git a/media/libaudioclient/tests/audioclient_serialization_tests.cpp b/media/libaudioclient/tests/audioclient_serialization_tests.cpp
index ef8500b..07e53f8 100644
--- a/media/libaudioclient/tests/audioclient_serialization_tests.cpp
+++ b/media/libaudioclient/tests/audioclient_serialization_tests.cpp
@@ -119,16 +119,17 @@
TEST_F(SerializationTest, AudioProductStrategyBinderization) {
for (int j = 0; j < 512; j++) {
const std::string name{"Test APSBinderization for seed::" + std::to_string(mSeed)};
- std::vector<AudioAttributes> audioattributesvector;
+ std::vector<VolumeGroupAttributes> volumeGroupAttrVector;
for (auto i = 0; i < 16; i++) {
audio_attributes_t attributes;
fillAudioAttributes(attributes);
- AudioAttributes audioattributes{static_cast<volume_group_t>(rand()),
- kStreamtypes[rand() % kStreamtypes.size()], attributes};
- audioattributesvector.push_back(audioattributes);
+ VolumeGroupAttributes volumeGroupAttr{static_cast<volume_group_t>(rand()),
+ kStreamtypes[rand() % kStreamtypes.size()],
+ attributes};
+ volumeGroupAttrVector.push_back(volumeGroupAttr);
}
product_strategy_t psId = static_cast<product_strategy_t>(rand());
- AudioProductStrategy aps{name, audioattributesvector, psId};
+ AudioProductStrategy aps{name, volumeGroupAttrVector, psId};
Parcel p;
EXPECT_EQ(NO_ERROR, aps.writeToParcel(&p)) << name;
@@ -138,12 +139,12 @@
EXPECT_EQ(NO_ERROR, apsCopy.readFromParcel(&p)) << name;
EXPECT_EQ(apsCopy.getName(), name) << name;
EXPECT_EQ(apsCopy.getId(), psId) << name;
- auto avec = apsCopy.getAudioAttributes();
- EXPECT_EQ(avec.size(), audioattributesvector.size()) << name;
- for (int i = 0; i < audioattributesvector.size(); i++) {
- EXPECT_EQ(avec[i].getGroupId(), audioattributesvector[i].getGroupId()) << name;
- EXPECT_EQ(avec[i].getStreamType(), audioattributesvector[i].getStreamType()) << name;
- EXPECT_TRUE(avec[i].getAttributes() == audioattributesvector[i].getAttributes())
+ auto avec = apsCopy.getVolumeGroupAttributes();
+ EXPECT_EQ(avec.size(), volumeGroupAttrVector.size()) << name;
+ for (int i = 0; i < volumeGroupAttrVector.size(); i++) {
+ EXPECT_EQ(avec[i].getGroupId(), volumeGroupAttrVector[i].getGroupId()) << name;
+ EXPECT_EQ(avec[i].getStreamType(), volumeGroupAttrVector[i].getStreamType()) << name;
+ EXPECT_TRUE(avec[i].getAttributes() == volumeGroupAttrVector[i].getAttributes())
<< name;
}
}
@@ -293,17 +294,17 @@
audio_stream_type_t stream = mAudioStream;
audio_attributes_t attributes;
fillAudioAttributes(attributes);
- AudioAttributes audioattributes{groupId, stream, attributes};
+ VolumeGroupAttributes volumeGroupAttr{groupId, stream, attributes};
Parcel p;
- EXPECT_EQ(NO_ERROR, audioattributes.writeToParcel(&p)) << msg;
+ EXPECT_EQ(NO_ERROR, volumeGroupAttr.writeToParcel(&p)) << msg;
- AudioAttributes audioattributesCopy;
+ VolumeGroupAttributes volumeGroupAttrCopy;
p.setDataPosition(0);
- EXPECT_EQ(NO_ERROR, audioattributesCopy.readFromParcel(&p)) << msg;
- EXPECT_EQ(audioattributesCopy.getGroupId(), audioattributes.getGroupId()) << msg;
- EXPECT_EQ(audioattributesCopy.getStreamType(), audioattributes.getStreamType()) << msg;
- EXPECT_TRUE(audioattributesCopy.getAttributes() == attributes) << msg;
+ EXPECT_EQ(NO_ERROR, volumeGroupAttrCopy.readFromParcel(&p)) << msg;
+ EXPECT_EQ(volumeGroupAttrCopy.getGroupId(), volumeGroupAttr.getGroupId()) << msg;
+ EXPECT_EQ(volumeGroupAttrCopy.getStreamType(), volumeGroupAttr.getStreamType()) << msg;
+ EXPECT_TRUE(volumeGroupAttrCopy.getAttributes() == attributes) << msg;
}
// audioStream
diff --git a/media/libaudioclient/tests/audiosystem_tests.cpp b/media/libaudioclient/tests/audiosystem_tests.cpp
index aed847c..3dd2c95 100644
--- a/media/libaudioclient/tests/audiosystem_tests.cpp
+++ b/media/libaudioclient/tests/audiosystem_tests.cpp
@@ -332,7 +332,7 @@
bool isPublicStrategy(const AudioProductStrategy& strategy) {
bool result = true;
- for (auto& attribute : strategy.getAudioAttributes()) {
+ for (auto& attribute : strategy.getVolumeGroupAttributes()) {
if (attribute.getAttributes() == AUDIO_ATTRIBUTES_INITIALIZER &&
(uint32_t(attribute.getStreamType()) >= AUDIO_STREAM_PUBLIC_CNT)) {
result = false;
@@ -371,7 +371,7 @@
for (const auto& strategy : strategies) {
if (!isPublicStrategy(strategy)) continue;
- for (const auto& att : strategy.getAudioAttributes()) {
+ for (const auto& att : strategy.getVolumeGroupAttributes()) {
if (strategy.attributesMatches(att.getAttributes(), attributes)) {
hasStrategyForMedia = true;
mediaStrategy = strategy;
diff --git a/media/libstagefright/ACodec.cpp b/media/libstagefright/ACodec.cpp
index 52c4c0f..f15e062 100644
--- a/media/libstagefright/ACodec.cpp
+++ b/media/libstagefright/ACodec.cpp
@@ -785,7 +785,7 @@
// we cannot change the number of output buffers while OMX is running
// set up surface to the same count
- Vector<BufferInfo> &buffers = mBuffers[kPortIndexOutput];
+ std::vector<BufferInfo> &buffers = mBuffers[kPortIndexOutput];
ALOGV("setting up surface for %zu buffers", buffers.size());
err = native_window_set_buffer_count(nativeWindow, buffers.size());
@@ -825,7 +825,7 @@
// cancel undequeued buffers to new surface
if (!storingMetadataInDecodedBuffers()) {
for (size_t i = 0; i < buffers.size(); ++i) {
- BufferInfo &info = buffers.editItemAt(i);
+ BufferInfo &info = buffers[i];
if (info.mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) {
ALOGV("canceling buffer %p", info.mGraphicBuffer->getNativeBuffer());
err = nativeWindow->cancelBuffer(
@@ -872,7 +872,7 @@
CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput);
CHECK(mAllocator[portIndex] == NULL);
- CHECK(mBuffers[portIndex].isEmpty());
+ CHECK(mBuffers[portIndex].empty());
status_t err;
if (mNativeWindow != NULL && portIndex == kPortIndexOutput) {
@@ -951,6 +951,7 @@
const sp<AMessage> &format =
portIndex == kPortIndexInput ? mInputFormat : mOutputFormat;
+ mBuffers[portIndex].reserve(def.nBufferCountActual);
for (OMX_U32 i = 0; i < def.nBufferCountActual && err == OK; ++i) {
hidl_memory hidlMemToken;
sp<TMemory> hidlMem;
@@ -1039,7 +1040,7 @@
}
}
- mBuffers[portIndex].push(info);
+ mBuffers[portIndex].push_back(info);
}
}
}
@@ -1250,6 +1251,7 @@
mComponentName.c_str(), bufferCount, bufferSize);
// Dequeue buffers and send them to OMX
+ mBuffers[kPortIndexOutput].reserve(bufferCount);
for (OMX_U32 i = 0; i < bufferCount; i++) {
ANativeWindowBuffer *buf;
int fenceFd;
@@ -1275,7 +1277,7 @@
info.mData = new MediaCodecBuffer(mOutputFormat, new ABuffer(bufferSize));
info.mCodecData = info.mData;
- mBuffers[kPortIndexOutput].push(info);
+ mBuffers[kPortIndexOutput].push_back(info);
IOMX::buffer_id bufferId;
err = mOMXNode->useBuffer(kPortIndexOutput, graphicBuffer, &bufferId);
@@ -1285,7 +1287,7 @@
break;
}
- mBuffers[kPortIndexOutput].editItemAt(i).mBufferID = bufferId;
+ mBuffers[kPortIndexOutput][i].mBufferID = bufferId;
ALOGV("[%s] Registered graphic buffer with ID %u (pointer = %p)",
mComponentName.c_str(),
@@ -1307,7 +1309,7 @@
}
for (OMX_U32 i = cancelStart; i < cancelEnd; i++) {
- BufferInfo *info = &mBuffers[kPortIndexOutput].editItemAt(i);
+ BufferInfo *info = &mBuffers[kPortIndexOutput][i];
if (info->mStatus == BufferInfo::OWNED_BY_US) {
status_t error = cancelBufferToNativeWindow(info);
if (err == 0) {
@@ -1336,6 +1338,7 @@
ALOGV("[%s] Allocating %u meta buffers on output port",
mComponentName.c_str(), bufferCount);
+ mBuffers[kPortIndexOutput].reserve(bufferCount);
for (OMX_U32 i = 0; i < bufferCount; i++) {
BufferInfo info;
info.mStatus = BufferInfo::OWNED_BY_NATIVE_WINDOW;
@@ -1353,7 +1356,7 @@
info.mCodecData = info.mData;
err = mOMXNode->useBuffer(kPortIndexOutput, OMXBuffer::sPreset, &info.mBufferID);
- mBuffers[kPortIndexOutput].push(info);
+ mBuffers[kPortIndexOutput].push_back(info);
ALOGV("[%s] allocated meta buffer with ID %u",
mComponentName.c_str(), info.mBufferID);
@@ -1462,7 +1465,7 @@
it != done.cend(); ++it) {
ssize_t index = it->getIndex();
if (index >= 0 && (size_t)index < mBuffers[kPortIndexOutput].size()) {
- mBuffers[kPortIndexOutput].editItemAt(index).mRenderInfo = NULL;
+ mBuffers[kPortIndexOutput][index].mRenderInfo = NULL;
} else if (index >= 0) {
// THIS SHOULD NEVER HAPPEN
ALOGE("invalid index %zd in %zu", index, mBuffers[kPortIndexOutput].size());
@@ -1502,7 +1505,7 @@
bool stale = false;
for (size_t i = mBuffers[kPortIndexOutput].size(); i > 0;) {
i--;
- BufferInfo *info = &mBuffers[kPortIndexOutput].editItemAt(i);
+ BufferInfo *info = &mBuffers[kPortIndexOutput][i];
if (info->mGraphicBuffer != NULL &&
info->mGraphicBuffer->handle == buf->handle) {
@@ -1550,8 +1553,7 @@
BufferInfo *oldest = NULL;
for (size_t i = mBuffers[kPortIndexOutput].size(); i > 0;) {
i--;
- BufferInfo *info =
- &mBuffers[kPortIndexOutput].editItemAt(i);
+ BufferInfo *info = &mBuffers[kPortIndexOutput][i];
if (info->mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW &&
(oldest == NULL ||
// avoid potential issues from counter rolling over
@@ -1608,8 +1610,7 @@
status_t err = OK;
for (size_t i = mBuffers[kPortIndexOutput].size(); i > 0;) {
i--;
- BufferInfo *info =
- &mBuffers[kPortIndexOutput].editItemAt(i);
+ BufferInfo *info = &mBuffers[kPortIndexOutput][i];
// At this time some buffers may still be with the component
// or being drained.
@@ -1626,7 +1627,7 @@
}
status_t ACodec::freeBuffer(OMX_U32 portIndex, size_t i) {
- BufferInfo *info = &mBuffers[portIndex].editItemAt(i);
+ BufferInfo *info = &mBuffers[portIndex][i];
status_t err = OK;
// there should not be any fences in the metadata
@@ -1666,14 +1667,14 @@
}
// remove buffer even if mOMXNode->freeBuffer fails
- mBuffers[portIndex].removeAt(i);
+ mBuffers[portIndex].erase(mBuffers[portIndex].begin() + i);
return err;
}
ACodec::BufferInfo *ACodec::findBufferByID(
uint32_t portIndex, IOMX::buffer_id bufferID, ssize_t *index) {
for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) {
- BufferInfo *info = &mBuffers[portIndex].editItemAt(i);
+ BufferInfo *info = &mBuffers[portIndex][i];
if (info->mBufferID == bufferID) {
if (index != NULL) {
@@ -5102,7 +5103,7 @@
size_t n = 0;
for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) {
- const BufferInfo &info = mBuffers[portIndex].itemAt(i);
+ const BufferInfo &info = mBuffers[portIndex][i];
if (info.mStatus == BufferInfo::OWNED_BY_COMPONENT) {
++n;
@@ -5116,7 +5117,7 @@
size_t n = 0;
for (size_t i = 0; i < mBuffers[kPortIndexOutput].size(); ++i) {
- const BufferInfo &info = mBuffers[kPortIndexOutput].itemAt(i);
+ const BufferInfo &info = mBuffers[kPortIndexOutput][i];
if (info.mStatus == BufferInfo::OWNED_BY_NATIVE_WINDOW) {
++n;
@@ -5143,7 +5144,7 @@
bool ACodec::allYourBuffersAreBelongToUs(
OMX_U32 portIndex) {
for (size_t i = 0; i < mBuffers[portIndex].size(); ++i) {
- BufferInfo *info = &mBuffers[portIndex].editItemAt(i);
+ BufferInfo *info = &mBuffers[portIndex][i];
if (info->mStatus != BufferInfo::OWNED_BY_US
&& info->mStatus != BufferInfo::OWNED_BY_NATIVE_WINDOW) {
@@ -5167,12 +5168,11 @@
}
void ACodec::processDeferredMessages() {
- List<sp<AMessage> > queue = mDeferredQueue;
+ std::list<sp<AMessage>> queue = mDeferredQueue;
mDeferredQueue.clear();
- List<sp<AMessage> >::iterator it = queue.begin();
- while (it != queue.end()) {
- onMessageReceived(*it++);
+ for(const sp<AMessage> &msg : queue) {
+ onMessageReceived(msg);
}
}
@@ -6483,7 +6483,7 @@
BufferInfo *eligible = NULL;
for (size_t i = 0; i < mCodec->mBuffers[kPortIndexInput].size(); ++i) {
- BufferInfo *info = &mCodec->mBuffers[kPortIndexInput].editItemAt(i);
+ BufferInfo *info = &mCodec->mBuffers[kPortIndexInput][i];
#if 0
if (info->mStatus == BufferInfo::OWNED_BY_UPSTREAM) {
@@ -7515,7 +7515,7 @@
// submit as many buffers as there are input buffers with the codec
// in case we are in port reconfiguring
for (size_t i = 0; i < mCodec->mBuffers[kPortIndexInput].size(); ++i) {
- BufferInfo *info = &mCodec->mBuffers[kPortIndexInput].editItemAt(i);
+ BufferInfo *info = &mCodec->mBuffers[kPortIndexInput][i];
if (info->mStatus == BufferInfo::OWNED_BY_COMPONENT) {
if (mCodec->submitOutputMetadataBuffer() != OK)
@@ -7533,7 +7533,7 @@
void ACodec::ExecutingState::submitRegularOutputBuffers() {
bool failed = false;
for (size_t i = 0; i < mCodec->mBuffers[kPortIndexOutput].size(); ++i) {
- BufferInfo *info = &mCodec->mBuffers[kPortIndexOutput].editItemAt(i);
+ BufferInfo *info = &mCodec->mBuffers[kPortIndexOutput][i];
if (mCodec->mNativeWindow != NULL) {
if (info->mStatus != BufferInfo::OWNED_BY_US
@@ -7590,7 +7590,7 @@
}
for (size_t i = 0; i < mCodec->mBuffers[kPortIndexInput].size(); i++) {
- BufferInfo *info = &mCodec->mBuffers[kPortIndexInput].editItemAt(i);
+ BufferInfo *info = &mCodec->mBuffers[kPortIndexInput][i];
if (info->mStatus == BufferInfo::OWNED_BY_US) {
postFillThisBuffer(info);
}
@@ -8594,7 +8594,7 @@
ALOGV("[%s] Output port now disabled.", mCodec->mComponentName.c_str());
status_t err = OK;
- if (!mCodec->mBuffers[kPortIndexOutput].isEmpty()) {
+ if (!mCodec->mBuffers[kPortIndexOutput].empty()) {
ALOGE("disabled port should be empty, but has %zu buffers",
mCodec->mBuffers[kPortIndexOutput].size());
err = FAILED_TRANSACTION;
diff --git a/media/libstagefright/MediaCodec.cpp b/media/libstagefright/MediaCodec.cpp
index c963e19..6ef52c7 100644
--- a/media/libstagefright/MediaCodec.cpp
+++ b/media/libstagefright/MediaCodec.cpp
@@ -5289,7 +5289,7 @@
MediaCodec::BufferInfo *MediaCodec::peekNextPortBuffer(int32_t portIndex) {
CHECK(portIndex == kPortIndexInput || portIndex == kPortIndexOutput);
- List<size_t> *availBuffers = &mAvailPortBuffers[portIndex];
+ std::list<size_t> *availBuffers = &mAvailPortBuffers[portIndex];
if (availBuffers->empty()) {
return nullptr;
@@ -5306,7 +5306,7 @@
return -EAGAIN;
}
- List<size_t> *availBuffers = &mAvailPortBuffers[portIndex];
+ std::list<size_t> *availBuffers = &mAvailPortBuffers[portIndex];
size_t index = *availBuffers->begin();
CHECK_EQ(info, &mPortBuffers[portIndex][index]);
availBuffers->erase(availBuffers->begin());
diff --git a/media/libstagefright/MediaCodecList.cpp b/media/libstagefright/MediaCodecList.cpp
index a3040f4..5e16b34 100644
--- a/media/libstagefright/MediaCodecList.cpp
+++ b/media/libstagefright/MediaCodecList.cpp
@@ -511,8 +511,6 @@
int32_t profile = -1;
if (format->findInt32("profile", &profile)) {
- int32_t level = -1;
- format->findInt32("level", &level);
Vector<MediaCodecInfo::ProfileLevel> profileLevels;
capabilities->getSupportedProfileLevels(&profileLevels);
auto it = profileLevels.begin();
@@ -520,14 +518,11 @@
if (profile != it->mProfile) {
continue;
}
- if (level > -1 && level > it->mLevel) {
- continue;
- }
break;
}
if (it == profileLevels.end()) {
- ALOGV("Codec does not support profile %d with level %d", profile, level);
+ ALOGV("Codec does not support profile %d", profile);
return false;
}
}
diff --git a/media/libstagefright/include/media/stagefright/ACodec.h b/media/libstagefright/include/media/stagefright/ACodec.h
index 5a21755..38a4c1e 100644
--- a/media/libstagefright/include/media/stagefright/ACodec.h
+++ b/media/libstagefright/include/media/stagefright/ACodec.h
@@ -18,6 +18,8 @@
#define A_CODEC_H_
#include <stdint.h>
+#include <list>
+#include <vector>
#include <android/native_window.h>
#include <media/hardware/MetadataBufferType.h>
#include <media/MediaCodecInfo.h>
@@ -265,11 +267,11 @@
sp<AMessage> mBaseOutputFormat;
FrameRenderTracker mRenderTracker; // render information for buffers rendered by ACodec
- Vector<BufferInfo> mBuffers[2];
+ std::vector<BufferInfo> mBuffers[2];
bool mPortEOS[2];
status_t mInputEOSResult;
- List<sp<AMessage> > mDeferredQueue;
+ std::list<sp<AMessage>> mDeferredQueue;
sp<AMessage> mLastOutputFormat;
bool mIsVideo;
diff --git a/media/libstagefright/include/media/stagefright/MediaCodec.h b/media/libstagefright/include/media/stagefright/MediaCodec.h
index 1d2d711..6f6a4e6 100644
--- a/media/libstagefright/include/media/stagefright/MediaCodec.h
+++ b/media/libstagefright/include/media/stagefright/MediaCodec.h
@@ -18,6 +18,7 @@
#define MEDIA_CODEC_H_
+#include <list>
#include <memory>
#include <vector>
@@ -483,7 +484,7 @@
// stop/flush/reset/release.
Mutex mBufferLock;
- List<size_t> mAvailPortBuffers[2];
+ std::list<size_t> mAvailPortBuffers[2];
std::vector<BufferInfo> mPortBuffers[2];
int32_t mDequeueInputTimeoutGeneration;
@@ -501,7 +502,7 @@
sp<IDescrambler> mDescrambler;
- List<sp<ABuffer> > mCSD;
+ std::list<sp<ABuffer> > mCSD;
sp<AMessage> mActivityNotify;
diff --git a/media/ndk/Android.bp b/media/ndk/Android.bp
index ddc71db..fded4f5 100644
--- a/media/ndk/Android.bp
+++ b/media/ndk/Android.bp
@@ -52,6 +52,9 @@
symbol_file: "libmediandk.map.txt",
first_version: "21",
unversioned_until: "current",
+ export_header_libs: [
+ "libmediandk_headers",
+ ],
}
ndk_headers {
@@ -167,7 +170,7 @@
stubs: {
symbol_file: "libmediandk.map.txt",
versions: ["29"],
- }
+ },
}
cc_library {
diff --git a/media/ndk/NdkImage.cpp b/media/ndk/NdkImage.cpp
index 0bdb41b..c2093ac 100644
--- a/media/ndk/NdkImage.cpp
+++ b/media/ndk/NdkImage.cpp
@@ -264,6 +264,13 @@
case HAL_PIXEL_FORMAT_YCrCb_420_SP:
*pixelStride = (planeIdx == 0) ? 1 : 2;
return AMEDIA_OK;
+ case HAL_PIXEL_FORMAT_YCBCR_P010:
+ if (mLockedBuffer->dataCb && mLockedBuffer->dataCr) {
+ *pixelStride = (planeIdx == 0) ? 2 : mLockedBuffer->chromaStep;
+ } else {
+ *pixelStride = (planeIdx == 0) ? 2 : 4;
+ }
+ return AMEDIA_OK;
case HAL_PIXEL_FORMAT_Y8:
*pixelStride = 1;
return AMEDIA_OK;
@@ -333,6 +340,13 @@
*rowStride = (planeIdx == 0) ? mLockedBuffer->stride
: ALIGN(mLockedBuffer->stride / 2, 16);
return AMEDIA_OK;
+ case HAL_PIXEL_FORMAT_YCBCR_P010:
+ if (mLockedBuffer->dataCb && mLockedBuffer->dataCr) {
+ *rowStride = (planeIdx == 0) ? mLockedBuffer->stride : mLockedBuffer->chromaStride;
+ } else {
+ *rowStride = mLockedBuffer->stride * 2;
+ }
+ return AMEDIA_OK;
case HAL_PIXEL_FORMAT_RAW10:
case HAL_PIXEL_FORMAT_RAW12:
// RAW10 and RAW12 are used for 10-bit and 12-bit raw data, they are single plane
@@ -490,6 +504,47 @@
: (planeIdx == 1) ? cb : cr;
dataSize = (planeIdx == 0) ? ySize : cSize;
break;
+ case HAL_PIXEL_FORMAT_YCBCR_P010:
+ if (mLockedBuffer->height % 2 != 0) {
+ ALOGE("YCBCR_P010: height (%d) should be a multiple of 2", mLockedBuffer->height);
+ return AMEDIA_ERROR_UNKNOWN;
+ }
+
+ if (mLockedBuffer->width <= 0) {
+ ALOGE("YCBCR_P010: width (%d) should be a > 0", mLockedBuffer->width);
+ return AMEDIA_ERROR_UNKNOWN;
+ }
+
+ if (mLockedBuffer->height <= 0) {
+ ALOGE("YCBCR_P010: height (%d) should be a > 0", mLockedBuffer->height);
+ return AMEDIA_ERROR_UNKNOWN;
+ }
+
+ if (mLockedBuffer->dataCb && mLockedBuffer->dataCr) {
+ pData = (planeIdx == 0) ? mLockedBuffer->data :
+ (planeIdx == 1) ? mLockedBuffer->dataCb : mLockedBuffer->dataCr;
+ // only map until last pixel
+ if (planeIdx == 0) {
+ cStride = mLockedBuffer->stride;
+ dataSize = cStride * (mLockedBuffer->height - 1) + mLockedBuffer->width * 2;
+ } else {
+ bytesPerPixel = mLockedBuffer->chromaStep;
+ cStride = mLockedBuffer->chromaStride;
+ dataSize = cStride * (mLockedBuffer->height / 2 - 1) +
+ bytesPerPixel * (mLockedBuffer->width / 2);
+ }
+ break;
+ }
+
+ cStride = mLockedBuffer->stride * 2;
+ ySize = cStride * mLockedBuffer->height;
+ cSize = ySize / 2;
+ cb = mLockedBuffer->data + ySize;
+ cr = cb + 2;
+
+ pData = (planeIdx == 0) ? mLockedBuffer->data : (planeIdx == 1) ? cb : cr;
+ dataSize = (planeIdx == 0) ? ySize : cSize;
+ break;
case HAL_PIXEL_FORMAT_Y8:
// Single plane, 8bpp.
diff --git a/media/ndk/NdkImageReader.cpp b/media/ndk/NdkImageReader.cpp
index ac5cba8..067c8f4 100644
--- a/media/ndk/NdkImageReader.cpp
+++ b/media/ndk/NdkImageReader.cpp
@@ -76,6 +76,7 @@
case AIMAGE_FORMAT_HEIC:
case AIMAGE_FORMAT_DEPTH_JPEG:
case AIMAGE_FORMAT_RAW_DEPTH10:
+ case HAL_PIXEL_FORMAT_YCBCR_P010:
return true;
case AIMAGE_FORMAT_PRIVATE:
// For private format, cpu usage is prohibited.
@@ -89,6 +90,7 @@
AImageReader::getNumPlanesForFormat(int32_t format) {
switch (format) {
case AIMAGE_FORMAT_YUV_420_888:
+ case HAL_PIXEL_FORMAT_YCBCR_P010:
return 3;
case AIMAGE_FORMAT_RGBA_8888:
case AIMAGE_FORMAT_RGBX_8888:
diff --git a/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.cpp b/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.cpp
index c7ce950..fa81cd8 100644
--- a/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.cpp
+++ b/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.cpp
@@ -264,11 +264,11 @@
}
}
-AMediaFormat* NdkMediaCodecFuzzerBase::getSampleCodecFormat() {
- AMediaFormat* format = AMediaFormat_new();
+void NdkMediaCodecFuzzerBase::setCodecFormat() {
std::string value;
int32_t count = 0;
int32_t maxFormatKeys = 0;
+ AMediaFormat_clear(mFormat);
/*set mimeType*/
if (mFdp->ConsumeBool()) {
@@ -277,37 +277,36 @@
value = mFdp->PickValueInArray(kMimeTypes);
}
if (mFdp->ConsumeBool()) {
- AMediaFormat_setString(format, AMEDIAFORMAT_KEY_MIME, value.c_str());
+ AMediaFormat_setString(mFormat, AMEDIAFORMAT_KEY_MIME, value.c_str());
}
maxFormatKeys = mFdp->ConsumeIntegralInRange<int32_t>(0, std::size(kFormatStringKeys));
for (count = 0; count < maxFormatKeys; ++count) {
std::string formatKey = mFdp->PickValueInArray(kFormatStringKeys);
- formatSetString(format, formatKey.c_str(), mFdp);
+ formatSetString(mFormat, formatKey.c_str(), mFdp);
}
maxFormatKeys = mFdp->ConsumeIntegralInRange<int32_t>(0, std::size(kFormatIntKeys));
for (count = 0; count < maxFormatKeys; ++count) {
std::string formatKey = mFdp->PickValueInArray(kFormatIntKeys);
- formatSetInt(format, formatKey.c_str(), mFdp);
+ formatSetInt(mFormat, formatKey.c_str(), mFdp);
}
maxFormatKeys = mFdp->ConsumeIntegralInRange<int32_t>(0, std::size(kFormatFloatKeys));
for (count = 0; count < maxFormatKeys; ++count) {
std::string formatKey = mFdp->PickValueInArray(kFormatFloatKeys);
- formatSetFloat(format, formatKey.c_str(), mFdp);
+ formatSetFloat(mFormat, formatKey.c_str(), mFdp);
}
maxFormatKeys = mFdp->ConsumeIntegralInRange<int32_t>(0, std::size(kFormatBufferKeys));
for (count = 0; count < maxFormatKeys; ++count) {
std::string formatKey = mFdp->PickValueInArray(kFormatBufferKeys);
- formatSetBuffer(format, formatKey.c_str(), mFdp);
+ formatSetBuffer(mFormat, formatKey.c_str(), mFdp);
}
- return format;
}
AMediaCodec* NdkMediaCodecFuzzerBase::createCodec(bool isEncoder, bool isCodecForClient) {
- mFormat = getSampleCodecFormat();
+ setCodecFormat();
return (mFdp->ConsumeBool() ? createAMediaCodecByname(isEncoder, isCodecForClient)
: createAMediaCodecByType(isEncoder, isCodecForClient));
}
diff --git a/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.h b/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.h
index e810e55..2875f9f 100644
--- a/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.h
+++ b/media/ndk/fuzzer/NdkMediaCodecFuzzerBase.h
@@ -39,6 +39,7 @@
class NdkMediaCodecFuzzerBase {
public:
+ NdkMediaCodecFuzzerBase() { mFormat = AMediaFormat_new(); }
void invokeCodecFormatAPI(AMediaCodec* codec);
void invokeInputBufferOperationAPI(AMediaCodec* codec);
void invokeOutputBufferOperationAPI(AMediaCodec* codec);
@@ -57,7 +58,7 @@
AMediaCodec* createAMediaCodecByType(bool isEncoder, bool isCodecForClient);
AMediaFormat* getSampleAudioFormat();
AMediaFormat* getSampleVideoFormat();
- AMediaFormat* getSampleCodecFormat();
+ void setCodecFormat();
AMediaFormat* mFormat = nullptr;
FuzzedDataProvider* mFdp = nullptr;
};
diff --git a/services/audioflinger/AudioFlinger.cpp b/services/audioflinger/AudioFlinger.cpp
index a86eefb..4c873f9 100644
--- a/services/audioflinger/AudioFlinger.cpp
+++ b/services/audioflinger/AudioFlinger.cpp
@@ -1078,6 +1078,8 @@
clientPid = callingPid;
adjAttributionSource.pid = VALUE_OR_RETURN_STATUS(legacy2aidl_pid_t_int32_t(callingPid));
}
+ adjAttributionSource = AudioFlinger::checkAttributionSourcePackage(
+ adjAttributionSource);
audio_session_t sessionId = input.sessionId;
if (sessionId == AUDIO_SESSION_ALLOCATE) {
@@ -2296,7 +2298,8 @@
__func__, callingUid, callingPid, currentPid);
adjAttributionSource.pid = VALUE_OR_RETURN_STATUS(legacy2aidl_pid_t_int32_t(callingPid));
}
-
+ adjAttributionSource = AudioFlinger::checkAttributionSourcePackage(
+ adjAttributionSource);
// we don't yet support anything other than linear PCM
if (!audio_is_valid_format(input.config.format) || !audio_is_linear_pcm(input.config.format)) {
ALOGE("createRecord() invalid format %#x", input.config.format);
@@ -3946,6 +3949,7 @@
adjAttributionSource.pid = VALUE_OR_RETURN_STATUS(legacy2aidl_pid_t_int32_t(callingPid));
currentPid = callingPid;
}
+ adjAttributionSource = AudioFlinger::checkAttributionSourcePackage(adjAttributionSource);
ALOGV("createEffect pid %d, effectClient %p, priority %d, sessionId %d, io %d, factory %p",
adjAttributionSource.pid, effectClient.get(), priority, sessionId, io,
diff --git a/services/audioflinger/Threads.cpp b/services/audioflinger/Threads.cpp
index b021c5e..d1d359c 100644
--- a/services/audioflinger/Threads.cpp
+++ b/services/audioflinger/Threads.cpp
@@ -8348,8 +8348,6 @@
audio_input_flags_t inputFlags = mInput->flags;
audio_input_flags_t requestedFlags = *flags;
uint32_t sampleRate;
- AttributionSourceState checkedAttributionSource = AudioFlinger::checkAttributionSourcePackage(
- attributionSource);
lStatus = initCheck();
if (lStatus != NO_ERROR) {
@@ -8364,7 +8362,7 @@
}
if (maxSharedAudioHistoryMs != 0) {
- if (!captureHotwordAllowed(checkedAttributionSource)) {
+ if (!captureHotwordAllowed(attributionSource)) {
lStatus = PERMISSION_DENIED;
goto Exit;
}
@@ -8485,16 +8483,16 @@
Mutex::Autolock _l(mLock);
int32_t startFrames = -1;
if (!mSharedAudioPackageName.empty()
- && mSharedAudioPackageName == checkedAttributionSource.packageName
+ && mSharedAudioPackageName == attributionSource.packageName
&& mSharedAudioSessionId == sessionId
- && captureHotwordAllowed(checkedAttributionSource)) {
+ && captureHotwordAllowed(attributionSource)) {
startFrames = mSharedAudioStartFrames;
}
track = new RecordTrack(this, client, attr, sampleRate,
format, channelMask, frameCount,
nullptr /* buffer */, (size_t)0 /* bufferSize */, sessionId, creatorPid,
- checkedAttributionSource, *flags, TrackBase::TYPE_DEFAULT, portId,
+ attributionSource, *flags, TrackBase::TYPE_DEFAULT, portId,
startFrames);
lStatus = track->initCheck();
diff --git a/services/audioflinger/Tracks.cpp b/services/audioflinger/Tracks.cpp
index cfb296c..1f64f93 100644
--- a/services/audioflinger/Tracks.cpp
+++ b/services/audioflinger/Tracks.cpp
@@ -530,10 +530,7 @@
id, attr.flags);
return nullptr;
}
-
- AttributionSourceState checkedAttributionSource = AudioFlinger::checkAttributionSourcePackage(
- attributionSource);
- return new OpPlayAudioMonitor(checkedAttributionSource, attr.usage, id);
+ return new OpPlayAudioMonitor(attributionSource, attr.usage, id);
}
AudioFlinger::PlaybackThread::OpPlayAudioMonitor::OpPlayAudioMonitor(
diff --git a/services/audiopolicy/AudioPolicyInterface.h b/services/audiopolicy/AudioPolicyInterface.h
index c4c27e8..b85382e 100644
--- a/services/audiopolicy/AudioPolicyInterface.h
+++ b/services/audiopolicy/AudioPolicyInterface.h
@@ -307,13 +307,13 @@
virtual status_t listAudioProductStrategies(AudioProductStrategyVector &strategies) = 0;
virtual status_t getProductStrategyFromAudioAttributes(
- const AudioAttributes &aa, product_strategy_t &productStrategy,
+ const audio_attributes_t &aa, product_strategy_t &productStrategy,
bool fallbackOnDefault) = 0;
virtual status_t listAudioVolumeGroups(AudioVolumeGroupVector &groups) = 0;
virtual status_t getVolumeGroupFromAudioAttributes(
- const AudioAttributes &aa, volume_group_t &volumeGroup, bool fallbackOnDefault) = 0;
+ const audio_attributes_t &aa, volume_group_t &volumeGroup, bool fallbackOnDefault) = 0;
virtual bool isCallScreenModeSupported() = 0;
diff --git a/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h b/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h
index afffcd5..3b19e52 100644
--- a/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h
+++ b/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h
@@ -76,7 +76,7 @@
sp<AudioPolicyMix> &primaryMix,
std::vector<sp<AudioPolicyMix>> *secondaryMixes);
- sp<DeviceDescriptor> getDeviceAndMixForInputSource(audio_source_t inputSource,
+ sp<DeviceDescriptor> getDeviceAndMixForInputSource(const audio_attributes_t& attributes,
const DeviceVector &availableDeviceTypes,
uid_t uid,
sp<AudioPolicyMix> *policyMix) const;
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
index 65fab43..56c0603 100644
--- a/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
@@ -28,6 +28,61 @@
namespace android {
namespace {
+// Returns true if the criterion matches.
+// The exclude criteria are handled in the same way as positive
+// ones - only condition is matched (the function will return
+// same result both for RULE_MATCH_X and RULE_EXCLUDE_X).
+bool isCriterionMatched(const AudioMixMatchCriterion& criterion,
+ const audio_attributes_t& attr,
+ const uid_t uid) {
+ uint32_t ruleWithoutExclusion = criterion.mRule & ~RULE_EXCLUSION_MASK;
+ switch(ruleWithoutExclusion) {
+ case RULE_MATCH_ATTRIBUTE_USAGE:
+ return criterion.mValue.mUsage == attr.usage;
+ case RULE_MATCH_ATTRIBUTE_CAPTURE_PRESET:
+ return criterion.mValue.mSource == attr.source;
+ case RULE_MATCH_UID:
+ return criterion.mValue.mUid == uid;
+ case RULE_MATCH_USERID:
+ {
+ userid_t userId = multiuser_get_user_id(uid);
+ return criterion.mValue.mUserId == userId;
+ }
+ }
+ ALOGE("Encountered invalid mix rule 0x%x", criterion.mRule);
+ return false;
+}
+
+// Returns true if vector of criteria is matched:
+// - If any of the exclude criteria is matched the criteria doesn't match.
+// - Otherwise, for each 'dimension' of positive rule present
+// (usage, capture preset, uid, userid...) at least one rule must match
+// for the criteria to match.
+bool areMixCriteriaMatched(const std::vector<AudioMixMatchCriterion>& criteria,
+ const audio_attributes_t& attr,
+ const uid_t uid) {
+ // If any of the exclusion criteria are matched the mix doesn't match.
+ auto isMatchingExcludeCriterion = [&](const AudioMixMatchCriterion& c) {
+ return c.isExcludeCriterion() && isCriterionMatched(c, attr, uid);
+ };
+ if (std::any_of(criteria.begin(), criteria.end(), isMatchingExcludeCriterion)) {
+ return false;
+ }
+
+ uint32_t presentPositiveRules = 0; // Bitmask of all present positive criteria.
+ uint32_t matchedPositiveRules = 0; // Bitmask of all matched positive criteria.
+ for (const auto& criterion : criteria) {
+ if (criterion.isExcludeCriterion()) {
+ continue;
+ }
+ presentPositiveRules |= criterion.mRule;
+ if (isCriterionMatched(criterion, attr, uid)) {
+ matchedPositiveRules |= criterion.mRule;
+ }
+ }
+ return presentPositiveRules == matchedPositiveRules;
+}
+
// Consistency checks: for each "dimension" of rules (usage, uid...), we can
// only have MATCH rules, or EXCLUDE rules in each dimension, not a combination.
bool areMixCriteriaConsistent(const std::vector<AudioMixMatchCriterion>& criteria) {
@@ -268,119 +323,19 @@
return MixMatchStatus::NO_MATCH;
}
- int userId = (int) multiuser_get_user_id(uid);
-
- // TODO if adding more player rules (currently only 2), make rule handling "generic"
- // as there is no difference in the treatment of usage- or uid-based rules
- bool hasUsageMatchRules = false;
- bool hasUsageExcludeRules = false;
- bool usageMatchFound = false;
- bool usageExclusionFound = false;
-
- bool hasUidMatchRules = false;
- bool hasUidExcludeRules = false;
- bool uidMatchFound = false;
- bool uidExclusionFound = false;
-
- bool hasUserIdExcludeRules = false;
- bool userIdExclusionFound = false;
- bool hasUserIdMatchRules = false;
- bool userIdMatchFound = false;
-
-
- bool hasAddrMatch = false;
-
- // iterate over all mix criteria to list what rules this mix contains
- for (size_t j = 0; j < mix->mCriteria.size(); j++) {
- ALOGV(" getOutputForAttr: mix %zu: inspecting mix criteria %zu of %zu",
- mixIndex, j, mix->mCriteria.size());
-
- // if there is an address match, prioritize that match
- if (strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
- strncmp(attributes.tags + strlen("addr="),
- mix->mDeviceAddress.string(),
- AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - strlen("addr=") - 1) == 0) {
- hasAddrMatch = true;
- break;
- }
-
- switch (mix->mCriteria[j].mRule) {
- case RULE_MATCH_ATTRIBUTE_USAGE:
- ALOGV("\tmix has RULE_MATCH_ATTRIBUTE_USAGE for usage %d",
- mix->mCriteria[j].mValue.mUsage);
- hasUsageMatchRules = true;
- if (mix->mCriteria[j].mValue.mUsage == attributes.usage) {
- // found one match against all allowed usages
- usageMatchFound = true;
- }
- break;
- case RULE_EXCLUDE_ATTRIBUTE_USAGE:
- ALOGV("\tmix has RULE_EXCLUDE_ATTRIBUTE_USAGE for usage %d",
- mix->mCriteria[j].mValue.mUsage);
- hasUsageExcludeRules = true;
- if (mix->mCriteria[j].mValue.mUsage == attributes.usage) {
- // found this usage is to be excluded
- usageExclusionFound = true;
- }
- break;
- case RULE_MATCH_UID:
- ALOGV("\tmix has RULE_MATCH_UID for uid %d", mix->mCriteria[j].mValue.mUid);
- hasUidMatchRules = true;
- if (mix->mCriteria[j].mValue.mUid == uid) {
- // found one UID match against all allowed UIDs
- uidMatchFound = true;
- }
- break;
- case RULE_EXCLUDE_UID:
- ALOGV("\tmix has RULE_EXCLUDE_UID for uid %d", mix->mCriteria[j].mValue.mUid);
- hasUidExcludeRules = true;
- if (mix->mCriteria[j].mValue.mUid == uid) {
- // found this UID is to be excluded
- uidExclusionFound = true;
- }
- break;
- case RULE_MATCH_USERID:
- ALOGV("\tmix has RULE_MATCH_USERID for userId %d",
- mix->mCriteria[j].mValue.mUserId);
- hasUserIdMatchRules = true;
- if (mix->mCriteria[j].mValue.mUserId == userId) {
- // found one userId match against all allowed userIds
- userIdMatchFound = true;
- }
- break;
- case RULE_EXCLUDE_USERID:
- ALOGV("\tmix has RULE_EXCLUDE_USERID for userId %d",
- mix->mCriteria[j].mValue.mUserId);
- hasUserIdExcludeRules = true;
- if (mix->mCriteria[j].mValue.mUserId == userId) {
- // found this userId is to be excluded
- userIdExclusionFound = true;
- }
- break;
- default:
- break;
- }
-
-
- if ((hasUsageExcludeRules && usageExclusionFound)
- || (hasUidExcludeRules && uidExclusionFound)
- || (hasUserIdExcludeRules && userIdExclusionFound)) {
- break; // stop iterating on criteria because an exclusion was found (will fail)
- }
- }//iterate on mix criteria
-
- // determine if exiting on success (or implicit failure as desc is 0)
- if (hasAddrMatch ||
- !((hasUsageExcludeRules && usageExclusionFound) ||
- (hasUsageMatchRules && !usageMatchFound) ||
- (hasUidExcludeRules && uidExclusionFound) ||
- (hasUidMatchRules && !uidMatchFound) ||
- (hasUserIdExcludeRules && userIdExclusionFound) ||
- (hasUserIdMatchRules && !userIdMatchFound))) {
+ // if there is an address match, prioritize that match
+ if (strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
+ strncmp(attributes.tags + strlen("addr="),
+ mix->mDeviceAddress.string(),
+ AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - strlen("addr=") - 1) == 0) {
ALOGV("\tgetOutputForAttr will use mix %zu", mixIndex);
return MixMatchStatus::MATCH;
}
+ if (areMixCriteriaMatched(mix->mCriteria, attributes, uid)) {
+ ALOGV("\tgetOutputForAttr will use mix %zu", mixIndex);
+ return MixMatchStatus::MATCH;
+ }
} else if (mix->mMixType == MIX_TYPE_RECORDERS) {
if (attributes.usage == AUDIO_USAGE_VIRTUAL_SOURCE &&
strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
@@ -411,7 +366,7 @@
}
sp<DeviceDescriptor> AudioPolicyMixCollection::getDeviceAndMixForInputSource(
- audio_source_t inputSource,
+ const audio_attributes_t& attributes,
const DeviceVector &availDevices,
uid_t uid,
sp<AudioPolicyMix> *policyMix) const
@@ -421,28 +376,17 @@
if (mix->mMixType != MIX_TYPE_RECORDERS) {
continue;
}
- for (size_t j = 0; j < mix->mCriteria.size(); j++) {
- if ((RULE_MATCH_ATTRIBUTE_CAPTURE_PRESET == mix->mCriteria[j].mRule &&
- mix->mCriteria[j].mValue.mSource == inputSource) ||
- (RULE_EXCLUDE_ATTRIBUTE_CAPTURE_PRESET == mix->mCriteria[j].mRule &&
- mix->mCriteria[j].mValue.mSource != inputSource) ||
- (RULE_MATCH_UID == mix->mCriteria[j].mRule &&
- mix->mCriteria[j].mValue.mUid == uid) ||
- (RULE_EXCLUDE_UID == mix->mCriteria[j].mRule &&
- mix->mCriteria[j].mValue.mUid != uid)) {
- // assuming PolicyMix only for remote submix for input
- // so mix->mDeviceType can only be AUDIO_DEVICE_OUT_REMOTE_SUBMIX
- audio_devices_t device = AUDIO_DEVICE_IN_REMOTE_SUBMIX;
- auto mixDevice =
- availDevices.getDevice(device, mix->mDeviceAddress, AUDIO_FORMAT_DEFAULT);
+ if (areMixCriteriaMatched(mix->mCriteria, attributes, uid)) {
+ // Assuming PolicyMix only for remote submix for input
+ // so mix->mDeviceType can only be AUDIO_DEVICE_OUT_REMOTE_SUBMIX.
+ auto mixDevice = availDevices.getDevice(AUDIO_DEVICE_IN_REMOTE_SUBMIX,
+ mix->mDeviceAddress, AUDIO_FORMAT_DEFAULT);
if (mixDevice != nullptr) {
if (policyMix != nullptr) {
*policyMix = mix;
}
return mixDevice;
}
- break;
- }
}
}
return nullptr;
diff --git a/services/audiopolicy/engine/common/include/ProductStrategy.h b/services/audiopolicy/engine/common/include/ProductStrategy.h
index 2aa2f9a..e8251e3 100644
--- a/services/audiopolicy/engine/common/include/ProductStrategy.h
+++ b/services/audiopolicy/engine/common/include/ProductStrategy.h
@@ -24,7 +24,7 @@
#include <vector>
#include <HandleGenerator.h>
-#include <media/AudioAttributes.h>
+#include <media/VolumeGroupAttributes.h>
#include <media/AudioContainers.h>
#include <media/AudioDeviceTypeAddr.h>
#include <media/AudioPolicy.h>
@@ -43,20 +43,14 @@
class ProductStrategy : public virtual RefBase, private HandleGenerator<uint32_t>
{
private:
- struct AudioAttributes {
- audio_stream_type_t mStream = AUDIO_STREAM_DEFAULT;
- volume_group_t mVolumeGroup = VOLUME_GROUP_NONE;
- audio_attributes_t mAttributes = AUDIO_ATTRIBUTES_INITIALIZER;
- };
-
- using AudioAttributesVector = std::vector<AudioAttributes>;
+ using VolumeGroupAttributesVector = std::vector<VolumeGroupAttributes>;
public:
ProductStrategy(const std::string &name);
- void addAttributes(const AudioAttributes &audioAttributes);
+ void addAttributes(const VolumeGroupAttributes &volumeGroupAttributes);
- std::vector<android::AudioAttributes> listAudioAttributes() const;
+ std::vector<android::VolumeGroupAttributes> listVolumeGroupAttributes() const;
std::string getName() const { return mName; }
AttributesVector getAudioAttributes() const;
@@ -105,7 +99,7 @@
private:
std::string mName;
- AudioAttributesVector mAttributesVector;
+ VolumeGroupAttributesVector mAttributesVector;
product_strategy_t mId;
diff --git a/services/audiopolicy/engine/common/src/EngineBase.cpp b/services/audiopolicy/engine/common/src/EngineBase.cpp
index 99507ee..9b78758 100644
--- a/services/audiopolicy/engine/common/src/EngineBase.cpp
+++ b/services/audiopolicy/engine/common/src/EngineBase.cpp
@@ -145,7 +145,7 @@
};
auto addSupportedAttributesToGroup = [](auto &group, auto &volumeGroup, auto &strategy) {
for (const auto &attr : group.attributesVect) {
- strategy->addAttributes({group.stream, volumeGroup->getId(), attr});
+ strategy->addAttributes({volumeGroup->getId(), group.stream, attr});
volumeGroup->addSupportedAttributes(attr);
}
};
@@ -284,7 +284,7 @@
for (const auto &iter : mProductStrategies) {
const auto &productStrategy = iter.second;
strategies.push_back(
- {productStrategy->getName(), productStrategy->listAudioAttributes(),
+ {productStrategy->getName(), productStrategy->listVolumeGroupAttributes(),
productStrategy->getId()});
}
return NO_ERROR;
diff --git a/services/audiopolicy/engine/common/src/ProductStrategy.cpp b/services/audiopolicy/engine/common/src/ProductStrategy.cpp
index fbfcf72..c104c97 100644
--- a/services/audiopolicy/engine/common/src/ProductStrategy.cpp
+++ b/services/audiopolicy/engine/common/src/ProductStrategy.cpp
@@ -36,16 +36,16 @@
{
}
-void ProductStrategy::addAttributes(const AudioAttributes &audioAttributes)
+void ProductStrategy::addAttributes(const VolumeGroupAttributes &volumeGroupAttributes)
{
- mAttributesVector.push_back(audioAttributes);
+ mAttributesVector.push_back(volumeGroupAttributes);
}
-std::vector<android::AudioAttributes> ProductStrategy::listAudioAttributes() const
+std::vector<android::VolumeGroupAttributes> ProductStrategy::listVolumeGroupAttributes() const
{
- std::vector<android::AudioAttributes> androidAa;
+ std::vector<android::VolumeGroupAttributes> androidAa;
for (const auto &attr : mAttributesVector) {
- androidAa.push_back({attr.mVolumeGroup, attr.mStream, attr.mAttributes});
+ androidAa.push_back({attr.getGroupId(), attr.getStreamType(), attr.getAttributes()});
}
return androidAa;
}
@@ -54,7 +54,7 @@
{
AttributesVector attrVector;
for (const auto &attrGroup : mAttributesVector) {
- attrVector.push_back(attrGroup.mAttributes);
+ attrVector.push_back(attrGroup.getAttributes());
}
if (not attrVector.empty()) {
return attrVector;
@@ -66,7 +66,7 @@
{
return std::find_if(begin(mAttributesVector), end(mAttributesVector),
[&attr](const auto &supportedAttr) {
- return AudioProductStrategy::attributesMatches(supportedAttr.mAttributes, attr);
+ return AudioProductStrategy::attributesMatches(supportedAttr.getAttributes(), attr);
}) != end(mAttributesVector);
}
@@ -75,11 +75,11 @@
{
const auto &iter = std::find_if(begin(mAttributesVector), end(mAttributesVector),
[&attr](const auto &supportedAttr) {
- return AudioProductStrategy::attributesMatches(supportedAttr.mAttributes, attr); });
+ return AudioProductStrategy::attributesMatches(supportedAttr.getAttributes(), attr); });
if (iter == end(mAttributesVector)) {
return AUDIO_STREAM_DEFAULT;
}
- audio_stream_type_t streamType = iter->mStream;
+ audio_stream_type_t streamType = iter->getStreamType();
ALOGW_IF(streamType == AUDIO_STREAM_DEFAULT,
"%s: Strategy %s supporting attributes %s has not stream type associated"
"fallback on MUSIC. Do not use stream volume API", __func__, mName.c_str(),
@@ -91,23 +91,23 @@
{
const auto iter = std::find_if(begin(mAttributesVector), end(mAttributesVector),
[&streamType](const auto &supportedAttr) {
- return supportedAttr.mStream == streamType; });
- return iter != end(mAttributesVector) ? iter->mAttributes : AUDIO_ATTRIBUTES_INITIALIZER;
+ return supportedAttr.getStreamType() == streamType; });
+ return iter != end(mAttributesVector) ? iter->getAttributes() : AUDIO_ATTRIBUTES_INITIALIZER;
}
bool ProductStrategy::isDefault() const
{
return std::find_if(begin(mAttributesVector), end(mAttributesVector), [](const auto &attr) {
- return attr.mAttributes == defaultAttr; }) != end(mAttributesVector);
+ return attr.getAttributes() == defaultAttr; }) != end(mAttributesVector);
}
StreamTypeVector ProductStrategy::getSupportedStreams() const
{
StreamTypeVector streams;
for (const auto &supportedAttr : mAttributesVector) {
- if (std::find(begin(streams), end(streams), supportedAttr.mStream) == end(streams) &&
- supportedAttr.mStream != AUDIO_STREAM_DEFAULT) {
- streams.push_back(supportedAttr.mStream);
+ if (std::find(begin(streams), end(streams), supportedAttr.getStreamType())
+ == end(streams) && supportedAttr.getStreamType() != AUDIO_STREAM_DEFAULT) {
+ streams.push_back(supportedAttr.getStreamType());
}
}
return streams;
@@ -117,14 +117,14 @@
{
return std::find_if(begin(mAttributesVector), end(mAttributesVector),
[&streamType](const auto &supportedAttr) {
- return supportedAttr.mStream == streamType; }) != end(mAttributesVector);
+ return supportedAttr.getStreamType() == streamType; }) != end(mAttributesVector);
}
volume_group_t ProductStrategy::getVolumeGroupForAttributes(const audio_attributes_t &attr) const
{
for (const auto &supportedAttr : mAttributesVector) {
- if (AudioProductStrategy::attributesMatches(supportedAttr.mAttributes, attr)) {
- return supportedAttr.mVolumeGroup;
+ if (AudioProductStrategy::attributesMatches(supportedAttr.getAttributes(), attr)) {
+ return supportedAttr.getGroupId();
}
}
return VOLUME_GROUP_NONE;
@@ -133,8 +133,8 @@
volume_group_t ProductStrategy::getVolumeGroupForStreamType(audio_stream_type_t stream) const
{
for (const auto &supportedAttr : mAttributesVector) {
- if (supportedAttr.mStream == stream) {
- return supportedAttr.mVolumeGroup;
+ if (supportedAttr.getStreamType() == stream) {
+ return supportedAttr.getGroupId();
}
}
return VOLUME_GROUP_NONE;
@@ -143,8 +143,10 @@
volume_group_t ProductStrategy::getDefaultVolumeGroup() const
{
const auto &iter = std::find_if(begin(mAttributesVector), end(mAttributesVector),
- [](const auto &attr) {return attr.mAttributes == defaultAttr;});
- return iter != end(mAttributesVector) ? iter->mVolumeGroup : VOLUME_GROUP_NONE;
+ [](const auto &attr) {
+ return attr.getAttributes() == defaultAttr;
+ });
+ return iter != end(mAttributesVector) ? iter->getGroupId() : VOLUME_GROUP_NONE;
}
void ProductStrategy::dump(String8 *dst, int spaces) const
@@ -155,11 +157,11 @@
deviceLiteral.c_str(), mDeviceAddress.c_str());
for (const auto &attr : mAttributesVector) {
- dst->appendFormat("%*sGroup: %d stream: %s\n", spaces + 3, "", attr.mVolumeGroup,
- android::toString(attr.mStream).c_str());
+ dst->appendFormat("%*sGroup: %d stream: %s\n", spaces + 3, "", attr.getGroupId(),
+ android::toString(attr.getStreamType()).c_str());
dst->appendFormat("%*s Attributes: ", spaces + 3, "");
- std::string attStr =
- attr.mAttributes == defaultAttr ? "{ Any }" : android::toString(attr.mAttributes);
+ std::string attStr = attr.getAttributes() == defaultAttr ?
+ "{ Any }" : android::toString(attr.getAttributes());
dst->appendFormat("%s\n", attStr.c_str());
}
}
diff --git a/services/audiopolicy/engineconfigurable/src/Engine.cpp b/services/audiopolicy/engineconfigurable/src/Engine.cpp
index 3d74920..2831a9b 100644
--- a/services/audiopolicy/engineconfigurable/src/Engine.cpp
+++ b/services/audiopolicy/engineconfigurable/src/Engine.cpp
@@ -333,7 +333,7 @@
return device;
}
- device = policyMixes.getDeviceAndMixForInputSource(attr.source,
+ device = policyMixes.getDeviceAndMixForInputSource(attr,
availableInputDevices,
uid,
mix);
diff --git a/services/audiopolicy/enginedefault/src/Engine.cpp b/services/audiopolicy/enginedefault/src/Engine.cpp
index 924b4ad..a3a7e15 100644
--- a/services/audiopolicy/enginedefault/src/Engine.cpp
+++ b/services/audiopolicy/enginedefault/src/Engine.cpp
@@ -797,7 +797,7 @@
return device;
}
- device = policyMixes.getDeviceAndMixForInputSource(attr.source,
+ device = policyMixes.getDeviceAndMixForInputSource(attr,
availableInputDevices,
uid,
mix);
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.h b/services/audiopolicy/managerdefault/AudioPolicyManager.h
index 74460c7..fcfa192 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.h
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.h
@@ -356,11 +356,10 @@
}
virtual status_t getProductStrategyFromAudioAttributes(
- const AudioAttributes &aa, product_strategy_t &productStrategy,
+ const audio_attributes_t &aa, product_strategy_t &productStrategy,
bool fallbackOnDefault)
{
- productStrategy = mEngine->getProductStrategyForAttributes(
- aa.getAttributes(), fallbackOnDefault);
+ productStrategy = mEngine->getProductStrategyForAttributes(aa, fallbackOnDefault);
return (fallbackOnDefault && productStrategy == PRODUCT_STRATEGY_NONE) ?
BAD_VALUE : NO_ERROR;
}
@@ -371,10 +370,9 @@
}
virtual status_t getVolumeGroupFromAudioAttributes(
- const AudioAttributes &aa, volume_group_t &volumeGroup, bool fallbackOnDefault)
+ const audio_attributes_t &aa, volume_group_t &volumeGroup, bool fallbackOnDefault)
{
- volumeGroup = mEngine->getVolumeGroupForAttributes(
- aa.getAttributes(), fallbackOnDefault);
+ volumeGroup = mEngine->getVolumeGroupForAttributes(aa, fallbackOnDefault);
return (fallbackOnDefault && volumeGroup == VOLUME_GROUP_NONE) ?
BAD_VALUE : NO_ERROR;
}
diff --git a/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp b/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp
index b15b61d..e8be08f 100644
--- a/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp
+++ b/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp
@@ -1176,12 +1176,12 @@
return Status::ok();
}
-Status AudioPolicyService::getDevicesForAttributes(const media::AudioAttributesEx& attrAidl,
+Status AudioPolicyService::getDevicesForAttributes(const media::AudioAttributesInternal& attrAidl,
bool forVolume,
std::vector<AudioDevice>* _aidl_return)
{
- AudioAttributes aa = VALUE_OR_RETURN_BINDER_STATUS(
- aidl2legacy_AudioAttributesEx_AudioAttributes(attrAidl));
+ audio_attributes_t aa = VALUE_OR_RETURN_BINDER_STATUS(
+ aidl2legacy_AudioAttributesInternal_audio_attributes_t(attrAidl));
AudioDeviceTypeAddrVector devices;
if (mAudioPolicyManager == NULL) {
@@ -1190,8 +1190,7 @@
Mutex::Autolock _l(mLock);
AutoCallerClear acc;
RETURN_IF_BINDER_ERROR(binderStatusFromStatusT(
- mAudioPolicyManager->getDevicesForAttributes(
- aa.getAttributes(), &devices, forVolume)));
+ mAudioPolicyManager->getDevicesForAttributes(aa, &devices, forVolume)));
*_aidl_return = VALUE_OR_RETURN_BINDER_STATUS(
convertContainer<std::vector<AudioDevice>>(devices,
legacy2aidl_AudioDeviceTypeAddress));
@@ -2084,9 +2083,10 @@
}
Status AudioPolicyService::getProductStrategyFromAudioAttributes(
- const media::AudioAttributesEx& aaAidl, bool fallbackOnDefault, int32_t* _aidl_return) {
- AudioAttributes aa = VALUE_OR_RETURN_BINDER_STATUS(
- aidl2legacy_AudioAttributesEx_AudioAttributes(aaAidl));
+ const media::AudioAttributesInternal& aaAidl,
+ bool fallbackOnDefault, int32_t* _aidl_return) {
+ audio_attributes_t aa = VALUE_OR_RETURN_BINDER_STATUS(
+ aidl2legacy_AudioAttributesInternal_audio_attributes_t(aaAidl));
product_strategy_t productStrategy;
if (mAudioPolicyManager == NULL) {
@@ -2117,9 +2117,10 @@
}
Status AudioPolicyService::getVolumeGroupFromAudioAttributes(
- const media::AudioAttributesEx& aaAidl, bool fallbackOnDefault, int32_t* _aidl_return) {
- AudioAttributes aa = VALUE_OR_RETURN_BINDER_STATUS(
- aidl2legacy_AudioAttributesEx_AudioAttributes(aaAidl));
+ const media::AudioAttributesInternal& aaAidl,
+ bool fallbackOnDefault, int32_t* _aidl_return) {
+ audio_attributes_t aa = VALUE_OR_RETURN_BINDER_STATUS(
+ aidl2legacy_AudioAttributesInternal_audio_attributes_t(aaAidl));
volume_group_t volumeGroup;
if (mAudioPolicyManager == NULL) {
diff --git a/services/audiopolicy/service/AudioPolicyService.h b/services/audiopolicy/service/AudioPolicyService.h
index 5c37f99..3a7fffa 100644
--- a/services/audiopolicy/service/AudioPolicyService.h
+++ b/services/audiopolicy/service/AudioPolicyService.h
@@ -134,7 +134,7 @@
int32_t* _aidl_return) override;
binder::Status getStrategyForStream(AudioStreamType stream,
int32_t* _aidl_return) override;
- binder::Status getDevicesForAttributes(const media::AudioAttributesEx& attr,
+ binder::Status getDevicesForAttributes(const media::AudioAttributesInternal& attr,
bool forVolume,
std::vector<AudioDevice>* _aidl_return) override;
binder::Status getOutputForEffect(const media::EffectDescriptor& desc,
@@ -224,12 +224,12 @@
binder::Status isUltrasoundSupported(bool* _aidl_return) override;
binder::Status listAudioProductStrategies(
std::vector<media::AudioProductStrategy>* _aidl_return) override;
- binder::Status getProductStrategyFromAudioAttributes(const media::AudioAttributesEx& aa,
+ binder::Status getProductStrategyFromAudioAttributes(const media::AudioAttributesInternal& aa,
bool fallbackOnDefault,
int32_t* _aidl_return) override;
binder::Status listAudioVolumeGroups(
std::vector<media::AudioVolumeGroup>* _aidl_return) override;
- binder::Status getVolumeGroupFromAudioAttributes(const media::AudioAttributesEx& aa,
+ binder::Status getVolumeGroupFromAudioAttributes(const media::AudioAttributesInternal& aa,
bool fallbackOnDefault,
int32_t* _aidl_return) override;
binder::Status setRttEnabled(bool enabled) override;
diff --git a/services/camera/libcameraservice/CameraService.cpp b/services/camera/libcameraservice/CameraService.cpp
index bc8981e..2569954 100644
--- a/services/camera/libcameraservice/CameraService.cpp
+++ b/services/camera/libcameraservice/CameraService.cpp
@@ -1767,20 +1767,68 @@
return ret;
}
+String16 CameraService::getPackageNameFromUid(int clientUid) {
+ String16 packageName("");
+
+ sp<IServiceManager> sm = defaultServiceManager();
+ sp<IBinder> binder = sm->getService(String16(kPermissionServiceName));
+ if (binder == 0) {
+ ALOGE("Cannot get permission service");
+ // Return empty package name and the further interaction
+ // with camera will likely fail
+ return packageName;
+ }
+
+ sp<IPermissionController> permCtrl = interface_cast<IPermissionController>(binder);
+ Vector<String16> packages;
+
+ permCtrl->getPackagesForUid(clientUid, packages);
+
+ if (packages.isEmpty()) {
+ ALOGE("No packages for calling UID %d", clientUid);
+ // Return empty package name and the further interaction
+ // with camera will likely fail
+ return packageName;
+ }
+
+ // Arbitrarily pick the first name in the list
+ packageName = packages[0];
+
+ return packageName;
+}
+
template<class CALLBACK, class CLIENT>
Status CameraService::connectHelper(const sp<CALLBACK>& cameraCb, const String8& cameraId,
- int api1CameraId, const String16& clientPackageName, bool systemNativeClient,
+ int api1CameraId, const String16& clientPackageNameMaybe, bool systemNativeClient,
const std::optional<String16>& clientFeatureId, int clientUid, int clientPid,
apiLevel effectiveApiLevel, bool shimUpdateOnly, int oomScoreOffset, int targetSdkVersion,
/*out*/sp<CLIENT>& device) {
binder::Status ret = binder::Status::ok();
+ bool isNonSystemNdk = false;
+ String16 clientPackageName;
+ if (clientPackageNameMaybe.size() <= 0) {
+ // NDK calls don't come with package names, but we need one for various cases.
+ // Generally, there's a 1:1 mapping between UID and package name, but shared UIDs
+ // do exist. For all authentication cases, all packages under the same UID get the
+ // same permissions, so picking any associated package name is sufficient. For some
+ // other cases, this may give inaccurate names for clients in logs.
+ isNonSystemNdk = true;
+ int packageUid = (clientUid == USE_CALLING_UID) ?
+ CameraThreadState::getCallingUid() : clientUid;
+ clientPackageName = getPackageNameFromUid(packageUid);
+ } else {
+ clientPackageName = clientPackageNameMaybe;
+ }
+
String8 clientName8(clientPackageName);
int originalClientPid = 0;
+ int packagePid = (clientPid == USE_CALLING_PID) ?
+ CameraThreadState::getCallingPid() : clientPid;
ALOGI("CameraService::connect call (PID %d \"%s\", camera ID %s) and "
- "Camera API version %d", clientPid, clientName8.string(), cameraId.string(),
+ "Camera API version %d", packagePid, clientName8.string(), cameraId.string(),
static_cast<int>(effectiveApiLevel));
nsecs_t openTimeNs = systemTime();
@@ -1788,7 +1836,7 @@
sp<CLIENT> client = nullptr;
int facing = -1;
int orientation = 0;
- bool isNonSystemNdk = (clientPackageName.size() == 0);
+
{
// Acquire mServiceLock and prevent other clients from connecting
std::unique_ptr<AutoConditionLock> lock =
@@ -3279,37 +3327,6 @@
sCameraService = cameraService;
}
- // In some cases the calling code has no access to the package it runs under.
- // For example, NDK camera API.
- // In this case we will get the packages for the calling UID and pick the first one
- // for attributing the app op. This will work correctly for runtime permissions
- // as for legacy apps we will toggle the app op for all packages in the UID.
- // The caveat is that the operation may be attributed to the wrong package and
- // stats based on app ops may be slightly off.
- if (mClientPackageName.size() <= 0) {
- sp<IServiceManager> sm = defaultServiceManager();
- sp<IBinder> binder = sm->getService(String16(kPermissionServiceName));
- if (binder == 0) {
- ALOGE("Cannot get permission service");
- // Leave mClientPackageName unchanged (empty) and the further interaction
- // with camera will fail in BasicClient::startCameraOps
- return;
- }
-
- sp<IPermissionController> permCtrl = interface_cast<IPermissionController>(binder);
- Vector<String16> packages;
-
- permCtrl->getPackagesForUid(mClientUid, packages);
-
- if (packages.isEmpty()) {
- ALOGE("No packages for calling UID");
- // Leave mClientPackageName unchanged (empty) and the further interaction
- // with camera will fail in BasicClient::startCameraOps
- return;
- }
- mClientPackageName = packages[0];
- }
-
// There are 2 scenarios in which a client won't have AppOps operations
// (both scenarios : native clients)
// 1) It's an system native client*, the package name will be empty
diff --git a/services/camera/libcameraservice/CameraService.h b/services/camera/libcameraservice/CameraService.h
index 0395475..6e2300a 100644
--- a/services/camera/libcameraservice/CameraService.h
+++ b/services/camera/libcameraservice/CameraService.h
@@ -834,10 +834,19 @@
// sorted in alpha-numeric order.
void filterAPI1SystemCameraLocked(const std::vector<std::string> &normalDeviceIds);
+ // In some cases the calling code has no access to the package it runs under.
+ // For example, NDK camera API.
+ // In this case we will get the packages for the calling UID and pick the first one
+ // for attributing the app op. This will work correctly for runtime permissions
+ // as for legacy apps we will toggle the app op for all packages in the UID.
+ // The caveat is that the operation may be attributed to the wrong package and
+ // stats based on app ops may be slightly off.
+ String16 getPackageNameFromUid(int clientUid);
+
// Single implementation shared between the various connect calls
template<class CALLBACK, class CLIENT>
binder::Status connectHelper(const sp<CALLBACK>& cameraCb, const String8& cameraId,
- int api1CameraId, const String16& clientPackageName, bool systemNativeClient,
+ int api1CameraId, const String16& clientPackageNameMaybe, bool systemNativeClient,
const std::optional<String16>& clientFeatureId, int clientUid, int clientPid,
apiLevel effectiveApiLevel, bool shimUpdateOnly, int scoreOffset, int targetSdkVersion,
/*out*/sp<CLIENT>& device);
diff --git a/services/camera/libcameraservice/common/Camera2ClientBase.cpp b/services/camera/libcameraservice/common/Camera2ClientBase.cpp
index f926b88..95b4050 100644
--- a/services/camera/libcameraservice/common/Camera2ClientBase.cpp
+++ b/services/camera/libcameraservice/common/Camera2ClientBase.cpp
@@ -40,8 +40,6 @@
namespace android {
-const static size_t kDisconnectTimeoutMs = 2500;
-
using namespace camera2;
// Interface used by CameraService
@@ -266,10 +264,16 @@
template <typename TClientBase>
binder::Status Camera2ClientBase<TClientBase>::disconnect() {
- if (mCameraServiceWatchdog != nullptr) {
+ if (mCameraServiceWatchdog != nullptr && mDevice != nullptr) {
+ // Timer for the disconnect call should be greater than getExpectedInFlightDuration
+ // since this duration is used to error handle methods in the disconnect sequence
+ // thus allowing existing error handling methods to execute first
+ uint64_t maxExpectedDuration =
+ ns2ms(mDevice->getExpectedInFlightDuration() + kBufferTimeDisconnectNs);
+
// Initialization from hal succeeded, time disconnect.
return mCameraServiceWatchdog->WATCH_CUSTOM_TIMER(disconnectImpl(),
- kDisconnectTimeoutMs / kCycleLengthMs, kCycleLengthMs);
+ maxExpectedDuration / kCycleLengthMs, kCycleLengthMs);
}
return disconnectImpl();
}
diff --git a/services/camera/libcameraservice/common/Camera2ClientBase.h b/services/camera/libcameraservice/common/Camera2ClientBase.h
index 6e37589..37a7200 100644
--- a/services/camera/libcameraservice/common/Camera2ClientBase.h
+++ b/services/camera/libcameraservice/common/Camera2ClientBase.h
@@ -134,6 +134,9 @@
protected:
+ // Used for watchdog timeout to monitor disconnect
+ static const nsecs_t kBufferTimeDisconnectNs = 3000000000; // 3 sec.
+
// The PID provided in the constructor call
pid_t mInitialClientPid;
bool mOverrideForPerfClass = false;
diff --git a/services/camera/libcameraservice/device3/Camera3Device.cpp b/services/camera/libcameraservice/device3/Camera3Device.cpp
index 3672666..ca75102 100644
--- a/services/camera/libcameraservice/device3/Camera3Device.cpp
+++ b/services/camera/libcameraservice/device3/Camera3Device.cpp
@@ -1744,7 +1744,7 @@
}
// Calculate expected duration for flush with additional buffer time in ms for watchdog
- uint64_t maxExpectedDuration = (getExpectedInFlightDuration() + kBaseGetBufferWait) / 1e6;
+ uint64_t maxExpectedDuration = ns2ms(getExpectedInFlightDuration() + kBaseGetBufferWait);
status_t res = mCameraServiceWatchdog->WATCH_CUSTOM_TIMER(mRequestThread->flush(),
maxExpectedDuration / kCycleLengthMs, kCycleLengthMs);
diff --git a/services/camera/libcameraservice/device3/Camera3OutputStream.cpp b/services/camera/libcameraservice/device3/Camera3OutputStream.cpp
index ec8d484..3ef29bc 100644
--- a/services/camera/libcameraservice/device3/Camera3OutputStream.cpp
+++ b/services/camera/libcameraservice/device3/Camera3OutputStream.cpp
@@ -1407,18 +1407,24 @@
}
nsecs_t Camera3OutputStream::syncTimestampToDisplayLocked(nsecs_t t) {
+ nsecs_t currentTime = systemTime();
+ if (!mFixedFps) {
+ mLastCaptureTime = t;
+ mLastPresentTime = currentTime;
+ return t;
+ }
+
ParcelableVsyncEventData parcelableVsyncEventData;
auto res = mDisplayEventReceiver.getLatestVsyncEventData(&parcelableVsyncEventData);
if (res != OK) {
ALOGE("%s: Stream %d: Error getting latest vsync event data: %s (%d)",
__FUNCTION__, mId, strerror(-res), res);
mLastCaptureTime = t;
- mLastPresentTime = t;
+ mLastPresentTime = currentTime;
return t;
}
const VsyncEventData& vsyncEventData = parcelableVsyncEventData.vsync;
- nsecs_t currentTime = systemTime();
nsecs_t minPresentT = mLastPresentTime + vsyncEventData.frameInterval / 2;
// Find the best presentation time without worrying about previous frame's
@@ -1523,8 +1529,8 @@
}
}
- if (expectedPresentT == mLastPresentTime && expectedPresentT <=
- vsyncEventData.frameTimelines[maxTimelines].expectedPresentationTime) {
+ if (expectedPresentT == mLastPresentTime && expectedPresentT <
+ vsyncEventData.frameTimelines[maxTimelines-1].expectedPresentationTime) {
// Couldn't find a reasonable presentation time. Using last frame's
// presentation time would cause a frame drop. The best option now
// is to use the next VSync as long as the last presentation time
diff --git a/services/camera/libcameraservice/device3/Camera3OutputStream.h b/services/camera/libcameraservice/device3/Camera3OutputStream.h
index 741bca2..db988a0 100644
--- a/services/camera/libcameraservice/device3/Camera3OutputStream.h
+++ b/services/camera/libcameraservice/device3/Camera3OutputStream.h
@@ -432,7 +432,7 @@
static constexpr nsecs_t kSpacingResetIntervalNs = 50000000LL; // 50 millisecond
static constexpr nsecs_t kTimelineThresholdNs = 1000000LL; // 1 millisecond
static constexpr float kMaxIntervalRatioDeviation = 0.05f;
- static constexpr int kMaxTimelines = 3;
+ static constexpr int kMaxTimelines = 2;
nsecs_t syncTimestampToDisplayLocked(nsecs_t t);
// Re-space frames by delaying queueBuffer so that frame delivery has
diff --git a/services/camera/libcameraservice/device3/PreviewFrameSpacer.cpp b/services/camera/libcameraservice/device3/PreviewFrameSpacer.cpp
index 67f42b4..b3cb178 100644
--- a/services/camera/libcameraservice/device3/PreviewFrameSpacer.cpp
+++ b/services/camera/libcameraservice/device3/PreviewFrameSpacer.cpp
@@ -68,7 +68,7 @@
return true;
}
- // Cache the frame to match readout time interval, for up to 33ms
+ // Cache the frame to match readout time interval, for up to kMaxFrameWaitTime
nsecs_t expectedQueueTime = mLastCameraPresentTime + readoutInterval;
nsecs_t frameWaitTime = std::min(kMaxFrameWaitTime, expectedQueueTime - currentTime);
if (frameWaitTime > 0 && mPendingBuffers.size() < 2) {
diff --git a/services/camera/libcameraservice/device3/PreviewFrameSpacer.h b/services/camera/libcameraservice/device3/PreviewFrameSpacer.h
index e165768..cb9690c 100644
--- a/services/camera/libcameraservice/device3/PreviewFrameSpacer.h
+++ b/services/camera/libcameraservice/device3/PreviewFrameSpacer.h
@@ -85,7 +85,7 @@
nsecs_t mLastCameraPresentTime = 0;
static constexpr nsecs_t kWaitDuration = 5000000LL; // 50ms
static constexpr nsecs_t kFrameIntervalThreshold = 80000000LL; // 80ms
- static constexpr nsecs_t kMaxFrameWaitTime = 33333333LL; // 33ms
+ static constexpr nsecs_t kMaxFrameWaitTime = 10000000LL; // 10ms
};
}; //namespace camera3