1*ec779b8eSAndroid Build Coastguard Worker /*
2*ec779b8eSAndroid Build Coastguard Worker * Copyright (C) 2018 The Android Open Source Project
3*ec779b8eSAndroid Build Coastguard Worker *
4*ec779b8eSAndroid Build Coastguard Worker * Licensed under the Apache License, Version 2.0 (the "License");
5*ec779b8eSAndroid Build Coastguard Worker * you may not use this file except in compliance with the License.
6*ec779b8eSAndroid Build Coastguard Worker * You may obtain a copy of the License at
7*ec779b8eSAndroid Build Coastguard Worker *
8*ec779b8eSAndroid Build Coastguard Worker * http://www.apache.org/licenses/LICENSE-2.0
9*ec779b8eSAndroid Build Coastguard Worker *
10*ec779b8eSAndroid Build Coastguard Worker * Unless required by applicable law or agreed to in writing, software
11*ec779b8eSAndroid Build Coastguard Worker * distributed under the License is distributed on an "AS IS" BASIS,
12*ec779b8eSAndroid Build Coastguard Worker * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*ec779b8eSAndroid Build Coastguard Worker * See the License for the specific language governing permissions and
14*ec779b8eSAndroid Build Coastguard Worker * limitations under the License.
15*ec779b8eSAndroid Build Coastguard Worker */
16*ec779b8eSAndroid Build Coastguard Worker
17*ec779b8eSAndroid Build Coastguard Worker //#define LOG_NDEBUG 0
18*ec779b8eSAndroid Build Coastguard Worker #define LOG_TAG "CCodecConfig"
19*ec779b8eSAndroid Build Coastguard Worker
20*ec779b8eSAndroid Build Coastguard Worker #include <initializer_list>
21*ec779b8eSAndroid Build Coastguard Worker
22*ec779b8eSAndroid Build Coastguard Worker #include <android_media_codec.h>
23*ec779b8eSAndroid Build Coastguard Worker
24*ec779b8eSAndroid Build Coastguard Worker #include <cutils/properties.h>
25*ec779b8eSAndroid Build Coastguard Worker #include <log/log.h>
26*ec779b8eSAndroid Build Coastguard Worker #include <utils/NativeHandle.h>
27*ec779b8eSAndroid Build Coastguard Worker
28*ec779b8eSAndroid Build Coastguard Worker #include <android-base/properties.h>
29*ec779b8eSAndroid Build Coastguard Worker
30*ec779b8eSAndroid Build Coastguard Worker #include <C2Component.h>
31*ec779b8eSAndroid Build Coastguard Worker #include <C2Param.h>
32*ec779b8eSAndroid Build Coastguard Worker #include <util/C2InterfaceHelper.h>
33*ec779b8eSAndroid Build Coastguard Worker
34*ec779b8eSAndroid Build Coastguard Worker #include <media/stagefright/CodecBase.h>
35*ec779b8eSAndroid Build Coastguard Worker #include <media/stagefright/MediaCodecConstants.h>
36*ec779b8eSAndroid Build Coastguard Worker
37*ec779b8eSAndroid Build Coastguard Worker #include "CCodecConfig.h"
38*ec779b8eSAndroid Build Coastguard Worker #include "Codec2Mapper.h"
39*ec779b8eSAndroid Build Coastguard Worker
40*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_REF_LEVEL 64 /* 64*-0.25dB = -16 dB below full scale for mobile conf */
41*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_DRC_CUT 127 /* maximum compression of dynamic range for mobile conf */
42*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_DRC_BOOST 127 /* maximum compression of dynamic range for mobile conf */
43*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_DRC_HEAVY 1 /* switch for heavy compression for mobile conf */
44*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_DRC_EFFECT 3 /* MPEG-D DRC effect type; 3 => Limited playback range */
45*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_DRC_ALBUM 0 /* MPEG-D DRC album mode; 0 => album mode is disabled, 1 => album mode is enabled */
46*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_OUTPUT_LOUDNESS -1 /* decoder output loudness; -1 => the value is unknown, otherwise dB step value (e.g. 64 for -16 dB) */
47*ec779b8eSAndroid Build Coastguard Worker #define DRC_DEFAULT_MOBILE_ENC_LEVEL (-1) /* encoder target level; -1 => the value is unknown, otherwise dB step value (e.g. 64 for -16 dB) */
48*ec779b8eSAndroid Build Coastguard Worker // names of properties that can be used to override the default DRC settings
49*ec779b8eSAndroid Build Coastguard Worker #define PROP_DRC_OVERRIDE_REF_LEVEL "aac_drc_reference_level"
50*ec779b8eSAndroid Build Coastguard Worker #define PROP_DRC_OVERRIDE_CUT "aac_drc_cut"
51*ec779b8eSAndroid Build Coastguard Worker #define PROP_DRC_OVERRIDE_BOOST "aac_drc_boost"
52*ec779b8eSAndroid Build Coastguard Worker #define PROP_DRC_OVERRIDE_HEAVY "aac_drc_heavy"
53*ec779b8eSAndroid Build Coastguard Worker #define PROP_DRC_OVERRIDE_ENC_LEVEL "aac_drc_enc_target_level"
54*ec779b8eSAndroid Build Coastguard Worker #define PROP_DRC_OVERRIDE_EFFECT "ro.aac_drc_effect_type"
55*ec779b8eSAndroid Build Coastguard Worker
56*ec779b8eSAndroid Build Coastguard Worker namespace android {
57*ec779b8eSAndroid Build Coastguard Worker
58*ec779b8eSAndroid Build Coastguard Worker // CCodecConfig
59*ec779b8eSAndroid Build Coastguard Worker
60*ec779b8eSAndroid Build Coastguard Worker namespace {
61*ec779b8eSAndroid Build Coastguard Worker
C2ValueToMessageItem(const C2Value & value,AMessage::ItemData & item)62*ec779b8eSAndroid Build Coastguard Worker void C2ValueToMessageItem(const C2Value &value, AMessage::ItemData &item) {
63*ec779b8eSAndroid Build Coastguard Worker int32_t int32Value;
64*ec779b8eSAndroid Build Coastguard Worker uint32_t uint32Value;
65*ec779b8eSAndroid Build Coastguard Worker int64_t int64Value;
66*ec779b8eSAndroid Build Coastguard Worker uint64_t uint64Value;
67*ec779b8eSAndroid Build Coastguard Worker float floatValue;
68*ec779b8eSAndroid Build Coastguard Worker if (value.get(&int32Value)) {
69*ec779b8eSAndroid Build Coastguard Worker item.set(int32Value);
70*ec779b8eSAndroid Build Coastguard Worker } else if (value.get(&uint32Value) && uint32Value <= uint32_t(INT32_MAX)) {
71*ec779b8eSAndroid Build Coastguard Worker // SDK does not support unsigned values
72*ec779b8eSAndroid Build Coastguard Worker item.set((int32_t)uint32Value);
73*ec779b8eSAndroid Build Coastguard Worker } else if (value.get(&int64Value)) {
74*ec779b8eSAndroid Build Coastguard Worker item.set(int64Value);
75*ec779b8eSAndroid Build Coastguard Worker } else if (value.get(&uint64Value) && uint64Value <= uint64_t(INT64_MAX)) {
76*ec779b8eSAndroid Build Coastguard Worker // SDK does not support unsigned values
77*ec779b8eSAndroid Build Coastguard Worker item.set((int64_t)uint64Value);
78*ec779b8eSAndroid Build Coastguard Worker } else if (value.get(&floatValue)) {
79*ec779b8eSAndroid Build Coastguard Worker item.set(floatValue);
80*ec779b8eSAndroid Build Coastguard Worker }
81*ec779b8eSAndroid Build Coastguard Worker }
82*ec779b8eSAndroid Build Coastguard Worker
83*ec779b8eSAndroid Build Coastguard Worker /**
84*ec779b8eSAndroid Build Coastguard Worker * mapping between SDK and Codec 2.0 configurations.
85*ec779b8eSAndroid Build Coastguard Worker */
86*ec779b8eSAndroid Build Coastguard Worker struct ConfigMapper {
87*ec779b8eSAndroid Build Coastguard Worker /**
88*ec779b8eSAndroid Build Coastguard Worker * Value mapper (C2Value => C2Value)
89*ec779b8eSAndroid Build Coastguard Worker */
90*ec779b8eSAndroid Build Coastguard Worker typedef std::function<C2Value(C2Value)> Mapper;
91*ec779b8eSAndroid Build Coastguard Worker
92*ec779b8eSAndroid Build Coastguard Worker /// shorthand
93*ec779b8eSAndroid Build Coastguard Worker typedef CCodecConfig::Domain Domain;
94*ec779b8eSAndroid Build Coastguard Worker
ConfigMapperandroid::__anonbcc861780111::ConfigMapper95*ec779b8eSAndroid Build Coastguard Worker ConfigMapper(std::string mediaKey, C2String c2struct, C2String c2field)
96*ec779b8eSAndroid Build Coastguard Worker : mDomain(Domain::ALL), mMediaKey(mediaKey), mStruct(c2struct), mField(c2field) { }
97*ec779b8eSAndroid Build Coastguard Worker
98*ec779b8eSAndroid Build Coastguard Worker /// Limits this parameter to the given domain
limitToandroid::__anonbcc861780111::ConfigMapper99*ec779b8eSAndroid Build Coastguard Worker ConfigMapper &limitTo(uint32_t domain) {
100*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(domain & Domain::GUARD_BIT);
101*ec779b8eSAndroid Build Coastguard Worker mDomain = Domain(mDomain & domain);
102*ec779b8eSAndroid Build Coastguard Worker return *this;
103*ec779b8eSAndroid Build Coastguard Worker }
104*ec779b8eSAndroid Build Coastguard Worker
105*ec779b8eSAndroid Build Coastguard Worker /// Adds SDK => Codec 2.0 mapper (should not be in the SDK format)
withMapperandroid::__anonbcc861780111::ConfigMapper106*ec779b8eSAndroid Build Coastguard Worker ConfigMapper &withMapper(Mapper mapper) {
107*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(!mMapper);
108*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(!mReverse);
109*ec779b8eSAndroid Build Coastguard Worker mMapper = mapper;
110*ec779b8eSAndroid Build Coastguard Worker return *this;
111*ec779b8eSAndroid Build Coastguard Worker }
112*ec779b8eSAndroid Build Coastguard Worker
113*ec779b8eSAndroid Build Coastguard Worker /// Adds SDK <=> Codec 2.0 value mappers
withMappersandroid::__anonbcc861780111::ConfigMapper114*ec779b8eSAndroid Build Coastguard Worker ConfigMapper &withMappers(Mapper mapper, Mapper reverse) {
115*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(!mMapper);
116*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(!mReverse);
117*ec779b8eSAndroid Build Coastguard Worker mMapper = mapper;
118*ec779b8eSAndroid Build Coastguard Worker mReverse = reverse;
119*ec779b8eSAndroid Build Coastguard Worker return *this;
120*ec779b8eSAndroid Build Coastguard Worker }
121*ec779b8eSAndroid Build Coastguard Worker
122*ec779b8eSAndroid Build Coastguard Worker /// Adds SDK <=> Codec 2.0 value mappers based on C2Mapper
123*ec779b8eSAndroid Build Coastguard Worker template<typename C2Type, typename SdkType=int32_t>
withC2Mappersandroid::__anonbcc861780111::ConfigMapper124*ec779b8eSAndroid Build Coastguard Worker ConfigMapper &withC2Mappers() {
125*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(!mMapper);
126*ec779b8eSAndroid Build Coastguard Worker C2_CHECK(!mReverse);
127*ec779b8eSAndroid Build Coastguard Worker mMapper = [](C2Value v) -> C2Value {
128*ec779b8eSAndroid Build Coastguard Worker SdkType sdkValue;
129*ec779b8eSAndroid Build Coastguard Worker C2Type c2Value;
130*ec779b8eSAndroid Build Coastguard Worker if (v.get(&sdkValue) && C2Mapper::map(sdkValue, &c2Value)) {
131*ec779b8eSAndroid Build Coastguard Worker return c2Value;
132*ec779b8eSAndroid Build Coastguard Worker }
133*ec779b8eSAndroid Build Coastguard Worker return C2Value();
134*ec779b8eSAndroid Build Coastguard Worker };
135*ec779b8eSAndroid Build Coastguard Worker mReverse = [](C2Value v) -> C2Value {
136*ec779b8eSAndroid Build Coastguard Worker SdkType sdkValue;
137*ec779b8eSAndroid Build Coastguard Worker C2Type c2Value;
138*ec779b8eSAndroid Build Coastguard Worker using C2ValueType=typename _c2_reduce_enum_to_underlying_type<C2Type>::type;
139*ec779b8eSAndroid Build Coastguard Worker if (v.get((C2ValueType*)&c2Value) && C2Mapper::map(c2Value, &sdkValue)) {
140*ec779b8eSAndroid Build Coastguard Worker return sdkValue;
141*ec779b8eSAndroid Build Coastguard Worker }
142*ec779b8eSAndroid Build Coastguard Worker return C2Value();
143*ec779b8eSAndroid Build Coastguard Worker };
144*ec779b8eSAndroid Build Coastguard Worker return *this;
145*ec779b8eSAndroid Build Coastguard Worker }
146*ec779b8eSAndroid Build Coastguard Worker
147*ec779b8eSAndroid Build Coastguard Worker /// Maps from SDK values in an AMessage to a suitable C2Value.
mapFromMessageandroid::__anonbcc861780111::ConfigMapper148*ec779b8eSAndroid Build Coastguard Worker C2Value mapFromMessage(const AMessage::ItemData &item) const {
149*ec779b8eSAndroid Build Coastguard Worker C2Value value;
150*ec779b8eSAndroid Build Coastguard Worker int32_t int32Value;
151*ec779b8eSAndroid Build Coastguard Worker int64_t int64Value;
152*ec779b8eSAndroid Build Coastguard Worker float floatValue;
153*ec779b8eSAndroid Build Coastguard Worker double doubleValue;
154*ec779b8eSAndroid Build Coastguard Worker if (item.find(&int32Value)) {
155*ec779b8eSAndroid Build Coastguard Worker value = int32Value;
156*ec779b8eSAndroid Build Coastguard Worker } else if (item.find(&int64Value)) {
157*ec779b8eSAndroid Build Coastguard Worker value = int64Value;
158*ec779b8eSAndroid Build Coastguard Worker } else if (item.find(&floatValue)) {
159*ec779b8eSAndroid Build Coastguard Worker value = floatValue;
160*ec779b8eSAndroid Build Coastguard Worker } else if (item.find(&doubleValue)) {
161*ec779b8eSAndroid Build Coastguard Worker value = (float)doubleValue;
162*ec779b8eSAndroid Build Coastguard Worker }
163*ec779b8eSAndroid Build Coastguard Worker if (value.type() != C2Value::NO_INIT && mMapper) {
164*ec779b8eSAndroid Build Coastguard Worker value = mMapper(value);
165*ec779b8eSAndroid Build Coastguard Worker }
166*ec779b8eSAndroid Build Coastguard Worker return value;
167*ec779b8eSAndroid Build Coastguard Worker }
168*ec779b8eSAndroid Build Coastguard Worker
169*ec779b8eSAndroid Build Coastguard Worker /// Maps from a C2Value to an SDK value in an AMessage.
mapToMessageandroid::__anonbcc861780111::ConfigMapper170*ec779b8eSAndroid Build Coastguard Worker AMessage::ItemData mapToMessage(C2Value value) const {
171*ec779b8eSAndroid Build Coastguard Worker AMessage::ItemData item;
172*ec779b8eSAndroid Build Coastguard Worker if (value.type() != C2Value::NO_INIT && mReverse) {
173*ec779b8eSAndroid Build Coastguard Worker value = mReverse(value);
174*ec779b8eSAndroid Build Coastguard Worker }
175*ec779b8eSAndroid Build Coastguard Worker C2ValueToMessageItem(value, item);
176*ec779b8eSAndroid Build Coastguard Worker return item;
177*ec779b8eSAndroid Build Coastguard Worker }
178*ec779b8eSAndroid Build Coastguard Worker
domainandroid::__anonbcc861780111::ConfigMapper179*ec779b8eSAndroid Build Coastguard Worker Domain domain() const { return mDomain; }
mediaKeyandroid::__anonbcc861780111::ConfigMapper180*ec779b8eSAndroid Build Coastguard Worker std::string mediaKey() const { return mMediaKey; }
pathandroid::__anonbcc861780111::ConfigMapper181*ec779b8eSAndroid Build Coastguard Worker std::string path() const { return mField.size() ? mStruct + '.' + mField : mStruct; }
mapperandroid::__anonbcc861780111::ConfigMapper182*ec779b8eSAndroid Build Coastguard Worker Mapper mapper() const { return mMapper; }
reverseandroid::__anonbcc861780111::ConfigMapper183*ec779b8eSAndroid Build Coastguard Worker Mapper reverse() const { return mReverse; }
184*ec779b8eSAndroid Build Coastguard Worker
185*ec779b8eSAndroid Build Coastguard Worker private:
186*ec779b8eSAndroid Build Coastguard Worker Domain mDomain; ///< parameter domain (mask) containing port, kind and config domains
187*ec779b8eSAndroid Build Coastguard Worker std::string mMediaKey; ///< SDK key
188*ec779b8eSAndroid Build Coastguard Worker C2String mStruct; ///< Codec 2.0 struct name
189*ec779b8eSAndroid Build Coastguard Worker C2String mField; ///< Codec 2.0 field name
190*ec779b8eSAndroid Build Coastguard Worker Mapper mMapper; ///< optional SDK => Codec 2.0 value mapper
191*ec779b8eSAndroid Build Coastguard Worker Mapper mReverse; ///< optional Codec 2.0 => SDK value mapper
192*ec779b8eSAndroid Build Coastguard Worker };
193*ec779b8eSAndroid Build Coastguard Worker
194*ec779b8eSAndroid Build Coastguard Worker template <typename PORT, typename STREAM>
QueryMediaTypeImpl(const std::shared_ptr<Codec2Client::Configurable> & configurable)195*ec779b8eSAndroid Build Coastguard Worker AString QueryMediaTypeImpl(
196*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable) {
197*ec779b8eSAndroid Build Coastguard Worker AString mediaType;
198*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2Param>> queried;
199*ec779b8eSAndroid Build Coastguard Worker c2_status_t c2err = configurable->query(
200*ec779b8eSAndroid Build Coastguard Worker {}, { PORT::PARAM_TYPE, STREAM::PARAM_TYPE }, C2_DONT_BLOCK, &queried);
201*ec779b8eSAndroid Build Coastguard Worker if (c2err != C2_OK && queried.size() == 0) {
202*ec779b8eSAndroid Build Coastguard Worker ALOGD("Query media type failed => %s", asString(c2err));
203*ec779b8eSAndroid Build Coastguard Worker } else {
204*ec779b8eSAndroid Build Coastguard Worker PORT *portMediaType =
205*ec779b8eSAndroid Build Coastguard Worker PORT::From(queried[0].get());
206*ec779b8eSAndroid Build Coastguard Worker if (portMediaType) {
207*ec779b8eSAndroid Build Coastguard Worker mediaType = AString(
208*ec779b8eSAndroid Build Coastguard Worker portMediaType->m.value,
209*ec779b8eSAndroid Build Coastguard Worker strnlen(portMediaType->m.value, portMediaType->flexCount()));
210*ec779b8eSAndroid Build Coastguard Worker } else {
211*ec779b8eSAndroid Build Coastguard Worker STREAM *streamMediaType = STREAM::From(queried[0].get());
212*ec779b8eSAndroid Build Coastguard Worker if (streamMediaType) {
213*ec779b8eSAndroid Build Coastguard Worker mediaType = AString(
214*ec779b8eSAndroid Build Coastguard Worker streamMediaType->m.value,
215*ec779b8eSAndroid Build Coastguard Worker strnlen(streamMediaType->m.value, streamMediaType->flexCount()));
216*ec779b8eSAndroid Build Coastguard Worker }
217*ec779b8eSAndroid Build Coastguard Worker }
218*ec779b8eSAndroid Build Coastguard Worker ALOGD("read media type: %s", mediaType.c_str());
219*ec779b8eSAndroid Build Coastguard Worker }
220*ec779b8eSAndroid Build Coastguard Worker return mediaType;
221*ec779b8eSAndroid Build Coastguard Worker }
222*ec779b8eSAndroid Build Coastguard Worker
QueryMediaType(bool input,const std::shared_ptr<Codec2Client::Configurable> & configurable)223*ec779b8eSAndroid Build Coastguard Worker AString QueryMediaType(
224*ec779b8eSAndroid Build Coastguard Worker bool input, const std::shared_ptr<Codec2Client::Configurable> &configurable) {
225*ec779b8eSAndroid Build Coastguard Worker typedef C2PortMediaTypeSetting P;
226*ec779b8eSAndroid Build Coastguard Worker typedef C2StreamMediaTypeSetting S;
227*ec779b8eSAndroid Build Coastguard Worker if (input) {
228*ec779b8eSAndroid Build Coastguard Worker return QueryMediaTypeImpl<P::input, S::input>(configurable);
229*ec779b8eSAndroid Build Coastguard Worker } else {
230*ec779b8eSAndroid Build Coastguard Worker return QueryMediaTypeImpl<P::output, S::output>(configurable);
231*ec779b8eSAndroid Build Coastguard Worker }
232*ec779b8eSAndroid Build Coastguard Worker }
233*ec779b8eSAndroid Build Coastguard Worker
234*ec779b8eSAndroid Build Coastguard Worker } // namespace
235*ec779b8eSAndroid Build Coastguard Worker
236*ec779b8eSAndroid Build Coastguard Worker /**
237*ec779b8eSAndroid Build Coastguard Worker * Set of standard parameters used by CCodec that are exposed to MediaCodec.
238*ec779b8eSAndroid Build Coastguard Worker */
239*ec779b8eSAndroid Build Coastguard Worker struct StandardParams {
240*ec779b8eSAndroid Build Coastguard Worker typedef CCodecConfig::Domain Domain;
241*ec779b8eSAndroid Build Coastguard Worker
242*ec779b8eSAndroid Build Coastguard Worker // standard (MediaCodec) params are keyed by media format key
243*ec779b8eSAndroid Build Coastguard Worker typedef std::string SdkKey;
244*ec779b8eSAndroid Build Coastguard Worker
245*ec779b8eSAndroid Build Coastguard Worker /// used to return reference to no config mappers in getConfigMappersForSdkKey
246*ec779b8eSAndroid Build Coastguard Worker static const std::vector<ConfigMapper> NO_MAPPERS;
247*ec779b8eSAndroid Build Coastguard Worker
248*ec779b8eSAndroid Build Coastguard Worker /// Returns Codec 2.0 equivalent parameters for an SDK format key.
getConfigMappersForSdkKeyandroid::StandardParams249*ec779b8eSAndroid Build Coastguard Worker const std::vector<ConfigMapper> &getConfigMappersForSdkKey(std::string key) const {
250*ec779b8eSAndroid Build Coastguard Worker auto it = mConfigMappers.find(key);
251*ec779b8eSAndroid Build Coastguard Worker if (it == mConfigMappers.end()) {
252*ec779b8eSAndroid Build Coastguard Worker if (mComplained.count(key) == 0) {
253*ec779b8eSAndroid Build Coastguard Worker ALOGD("no c2 equivalents for %s", key.c_str());
254*ec779b8eSAndroid Build Coastguard Worker mComplained.insert(key);
255*ec779b8eSAndroid Build Coastguard Worker }
256*ec779b8eSAndroid Build Coastguard Worker return NO_MAPPERS;
257*ec779b8eSAndroid Build Coastguard Worker }
258*ec779b8eSAndroid Build Coastguard Worker ALOGV("found %zu eqs for %s", it->second.size(), key.c_str());
259*ec779b8eSAndroid Build Coastguard Worker return it->second;
260*ec779b8eSAndroid Build Coastguard Worker }
261*ec779b8eSAndroid Build Coastguard Worker
262*ec779b8eSAndroid Build Coastguard Worker /**
263*ec779b8eSAndroid Build Coastguard Worker * Adds a SDK <=> Codec 2.0 parameter mapping. Multiple Codec 2.0 parameters may map to a
264*ec779b8eSAndroid Build Coastguard Worker * single SDK key, in which case they shall be ordered from least authoritative to most
265*ec779b8eSAndroid Build Coastguard Worker * authoritative. When constructing SDK formats, the last mapped Codec 2.0 parameter that
266*ec779b8eSAndroid Build Coastguard Worker * is supported by the component will determine the exposed value. (TODO: perhaps restrict this
267*ec779b8eSAndroid Build Coastguard Worker * by domain.)
268*ec779b8eSAndroid Build Coastguard Worker */
addandroid::StandardParams269*ec779b8eSAndroid Build Coastguard Worker void add(const ConfigMapper &cm) {
270*ec779b8eSAndroid Build Coastguard Worker auto it = mConfigMappers.find(cm.mediaKey());
271*ec779b8eSAndroid Build Coastguard Worker ALOGV("%c%c%c%c %c%c%c %04x %9s %s => %s",
272*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_INPUT) ? 'I' : ' '),
273*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_OUTPUT) ? 'O' : ' '),
274*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_CODED) ? 'C' : ' '),
275*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_RAW) ? 'R' : ' '),
276*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_CONFIG) ? 'c' : ' '),
277*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_PARAM) ? 'p' : ' '),
278*ec779b8eSAndroid Build Coastguard Worker ((cm.domain() & Domain::IS_READ) ? 'r' : ' '),
279*ec779b8eSAndroid Build Coastguard Worker cm.domain(),
280*ec779b8eSAndroid Build Coastguard Worker it == mConfigMappers.end() ? "adding" : "extending",
281*ec779b8eSAndroid Build Coastguard Worker cm.mediaKey().c_str(), cm.path().c_str());
282*ec779b8eSAndroid Build Coastguard Worker if (it == mConfigMappers.end()) {
283*ec779b8eSAndroid Build Coastguard Worker std::vector<ConfigMapper> eqs = { cm };
284*ec779b8eSAndroid Build Coastguard Worker mConfigMappers.emplace(cm.mediaKey(), eqs);
285*ec779b8eSAndroid Build Coastguard Worker } else {
286*ec779b8eSAndroid Build Coastguard Worker it->second.push_back(cm);
287*ec779b8eSAndroid Build Coastguard Worker }
288*ec779b8eSAndroid Build Coastguard Worker }
289*ec779b8eSAndroid Build Coastguard Worker
290*ec779b8eSAndroid Build Coastguard Worker // Updates or adds a mapper for a "sdkkey"
updateConfigMappersForKeyandroid::StandardParams291*ec779b8eSAndroid Build Coastguard Worker void updateConfigMappersForKey(const SdkKey& key,
292*ec779b8eSAndroid Build Coastguard Worker const std::vector<ConfigMapper>& vec_cm) {
293*ec779b8eSAndroid Build Coastguard Worker mConfigMappers.insert_or_assign(key, vec_cm);
294*ec779b8eSAndroid Build Coastguard Worker }
295*ec779b8eSAndroid Build Coastguard Worker
296*ec779b8eSAndroid Build Coastguard Worker /**
297*ec779b8eSAndroid Build Coastguard Worker * Returns all paths for a specific domain.
298*ec779b8eSAndroid Build Coastguard Worker *
299*ec779b8eSAndroid Build Coastguard Worker * \param any maximum domain mask. Returned parameters must match at least one of the domains
300*ec779b8eSAndroid Build Coastguard Worker * in the mask.
301*ec779b8eSAndroid Build Coastguard Worker * \param all minimum domain mask. Returned parameters must match all of the domains in the
302*ec779b8eSAndroid Build Coastguard Worker * mask. This is restricted to the bits of the maximum mask.
303*ec779b8eSAndroid Build Coastguard Worker */
getPathsForDomainandroid::StandardParams304*ec779b8eSAndroid Build Coastguard Worker std::vector<std::string> getPathsForDomain(
305*ec779b8eSAndroid Build Coastguard Worker Domain any, Domain all = Domain::ALL) const {
306*ec779b8eSAndroid Build Coastguard Worker std::vector<std::string> res;
307*ec779b8eSAndroid Build Coastguard Worker for (const auto &[key, mappers] : mConfigMappers) {
308*ec779b8eSAndroid Build Coastguard Worker for (const ConfigMapper &cm : mappers) {
309*ec779b8eSAndroid Build Coastguard Worker ALOGV("filtering %s %x %x %x %x", cm.path().c_str(), cm.domain(), any,
310*ec779b8eSAndroid Build Coastguard Worker (cm.domain() & any), (cm.domain() & any & all));
311*ec779b8eSAndroid Build Coastguard Worker if ((cm.domain() & any) && ((cm.domain() & any & all) == (any & all))) {
312*ec779b8eSAndroid Build Coastguard Worker res.push_back(cm.path());
313*ec779b8eSAndroid Build Coastguard Worker }
314*ec779b8eSAndroid Build Coastguard Worker }
315*ec779b8eSAndroid Build Coastguard Worker }
316*ec779b8eSAndroid Build Coastguard Worker return res;
317*ec779b8eSAndroid Build Coastguard Worker }
318*ec779b8eSAndroid Build Coastguard Worker
319*ec779b8eSAndroid Build Coastguard Worker /**
320*ec779b8eSAndroid Build Coastguard Worker * Returns SDK <=> Codec 2.0 mappings.
321*ec779b8eSAndroid Build Coastguard Worker *
322*ec779b8eSAndroid Build Coastguard Worker * TODO: replace these with better methods as this exposes the inner structure.
323*ec779b8eSAndroid Build Coastguard Worker */
getKeysandroid::StandardParams324*ec779b8eSAndroid Build Coastguard Worker const std::map<SdkKey, std::vector<ConfigMapper>> getKeys() const {
325*ec779b8eSAndroid Build Coastguard Worker return mConfigMappers;
326*ec779b8eSAndroid Build Coastguard Worker }
327*ec779b8eSAndroid Build Coastguard Worker
328*ec779b8eSAndroid Build Coastguard Worker private:
329*ec779b8eSAndroid Build Coastguard Worker std::map<SdkKey, std::vector<ConfigMapper>> mConfigMappers;
330*ec779b8eSAndroid Build Coastguard Worker mutable std::set<std::string> mComplained;
331*ec779b8eSAndroid Build Coastguard Worker };
332*ec779b8eSAndroid Build Coastguard Worker
333*ec779b8eSAndroid Build Coastguard Worker const std::vector<ConfigMapper> StandardParams::NO_MAPPERS;
334*ec779b8eSAndroid Build Coastguard Worker
335*ec779b8eSAndroid Build Coastguard Worker
CCodecConfig()336*ec779b8eSAndroid Build Coastguard Worker CCodecConfig::CCodecConfig()
337*ec779b8eSAndroid Build Coastguard Worker : mInputFormat(new AMessage),
338*ec779b8eSAndroid Build Coastguard Worker mOutputFormat(new AMessage),
339*ec779b8eSAndroid Build Coastguard Worker mUsingSurface(false),
340*ec779b8eSAndroid Build Coastguard Worker mTunneled(false),
341*ec779b8eSAndroid Build Coastguard Worker mPushBlankBuffersOnStop(false) { }
342*ec779b8eSAndroid Build Coastguard Worker
initializeStandardParams()343*ec779b8eSAndroid Build Coastguard Worker void CCodecConfig::initializeStandardParams() {
344*ec779b8eSAndroid Build Coastguard Worker typedef Domain D;
345*ec779b8eSAndroid Build Coastguard Worker mStandardParams = std::make_shared<StandardParams>();
346*ec779b8eSAndroid Build Coastguard Worker std::function<void(const ConfigMapper &)> add =
347*ec779b8eSAndroid Build Coastguard Worker [params = mStandardParams](const ConfigMapper &cm) {
348*ec779b8eSAndroid Build Coastguard Worker params->add(cm);
349*ec779b8eSAndroid Build Coastguard Worker };
350*ec779b8eSAndroid Build Coastguard Worker std::function<void(const ConfigMapper &)> deprecated = add;
351*ec779b8eSAndroid Build Coastguard Worker
352*ec779b8eSAndroid Build Coastguard Worker // allow int32 or float SDK values and represent them as float
353*ec779b8eSAndroid Build Coastguard Worker ConfigMapper::Mapper makeFloat = [](C2Value v) -> C2Value {
354*ec779b8eSAndroid Build Coastguard Worker // convert from i32 to float
355*ec779b8eSAndroid Build Coastguard Worker int32_t i32Value;
356*ec779b8eSAndroid Build Coastguard Worker float fpValue;
357*ec779b8eSAndroid Build Coastguard Worker if (v.get(&i32Value)) {
358*ec779b8eSAndroid Build Coastguard Worker return (float)i32Value;
359*ec779b8eSAndroid Build Coastguard Worker } else if (v.get(&fpValue)) {
360*ec779b8eSAndroid Build Coastguard Worker return fpValue;
361*ec779b8eSAndroid Build Coastguard Worker }
362*ec779b8eSAndroid Build Coastguard Worker return C2Value();
363*ec779b8eSAndroid Build Coastguard Worker };
364*ec779b8eSAndroid Build Coastguard Worker
365*ec779b8eSAndroid Build Coastguard Worker ConfigMapper::Mapper negate = [](C2Value v) -> C2Value {
366*ec779b8eSAndroid Build Coastguard Worker int32_t value;
367*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
368*ec779b8eSAndroid Build Coastguard Worker return -value;
369*ec779b8eSAndroid Build Coastguard Worker }
370*ec779b8eSAndroid Build Coastguard Worker return C2Value();
371*ec779b8eSAndroid Build Coastguard Worker };
372*ec779b8eSAndroid Build Coastguard Worker
373*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MIME, C2_PARAMKEY_INPUT_MEDIA_TYPE, "value")
374*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::INPUT & D::READ));
375*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MIME, C2_PARAMKEY_OUTPUT_MEDIA_TYPE, "value")
376*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::OUTPUT & D::READ));
377*ec779b8eSAndroid Build Coastguard Worker
378*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_BIT_RATE, C2_PARAMKEY_BITRATE, "value")
379*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::CODED));
380*ec779b8eSAndroid Build Coastguard Worker // Some audio decoders require bitrate information to be set
381*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_BIT_RATE, C2_PARAMKEY_BITRATE, "value")
382*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & D::CODED));
383*ec779b8eSAndroid Build Coastguard Worker // we also need to put the bitrate in the max bitrate field
384*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MAX_BIT_RATE, C2_PARAMKEY_BITRATE, "value")
385*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::READ & D::OUTPUT));
386*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(PARAMETER_KEY_VIDEO_BITRATE, C2_PARAMKEY_BITRATE, "value")
387*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO & D::PARAM));
388*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_BITRATE_MODE, C2_PARAMKEY_BITRATE_MODE, "value")
389*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::CODED)
390*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Config::bitrate_mode_t>());
391*ec779b8eSAndroid Build Coastguard Worker // remove when codecs switch to PARAMKEY and new modes
392*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_BITRATE_MODE, "coded.bitrate-mode", "value")
393*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER));
394*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_FRAME_RATE, C2_PARAMKEY_FRAME_RATE, "value")
395*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO)
396*ec779b8eSAndroid Build Coastguard Worker .withMappers(makeFloat, [](C2Value v) -> C2Value {
397*ec779b8eSAndroid Build Coastguard Worker // read back always as int
398*ec779b8eSAndroid Build Coastguard Worker float value;
399*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
400*ec779b8eSAndroid Build Coastguard Worker return (int32_t) (value + 0.5);
401*ec779b8eSAndroid Build Coastguard Worker }
402*ec779b8eSAndroid Build Coastguard Worker return C2Value();
403*ec779b8eSAndroid Build Coastguard Worker }));
404*ec779b8eSAndroid Build Coastguard Worker
405*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MAX_INPUT_SIZE, C2_PARAMKEY_INPUT_MAX_BUFFER_SIZE, "value")
406*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::INPUT));
407*ec779b8eSAndroid Build Coastguard Worker
408*ec779b8eSAndroid Build Coastguard Worker // remove when codecs switch to PARAMKEY
409*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_MAX_INPUT_SIZE, "coded.max-frame-size", "value")
410*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::INPUT));
411*ec779b8eSAndroid Build Coastguard Worker
412*ec779b8eSAndroid Build Coastguard Worker // large frame params
413*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_BUFFER_BATCH_MAX_OUTPUT_SIZE,
414*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_OUTPUT_LARGE_FRAME, "max-size")
415*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::OUTPUT));
416*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_BUFFER_BATCH_THRESHOLD_OUTPUT_SIZE,
417*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_OUTPUT_LARGE_FRAME, "threshold-size")
418*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::OUTPUT));
419*ec779b8eSAndroid Build Coastguard Worker
420*ec779b8eSAndroid Build Coastguard Worker // Rotation
421*ec779b8eSAndroid Build Coastguard Worker // Note: SDK rotation is clock-wise, while C2 rotation is counter-clock-wise
422*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_ROTATION, C2_PARAMKEY_VUI_ROTATION, "value")
423*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::CODED)
424*ec779b8eSAndroid Build Coastguard Worker .withMappers(negate, negate));
425*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_ROTATION, C2_PARAMKEY_ROTATION, "value")
426*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW)
427*ec779b8eSAndroid Build Coastguard Worker .withMappers(negate, negate));
428*ec779b8eSAndroid Build Coastguard Worker
429*ec779b8eSAndroid Build Coastguard Worker // android 'video-scaling'
430*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._video-scaling", C2_PARAMKEY_SURFACE_SCALING_MODE, "value")
431*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::DECODER & D::RAW));
432*ec779b8eSAndroid Build Coastguard Worker
433*ec779b8eSAndroid Build Coastguard Worker // Color Aspects
434*ec779b8eSAndroid Build Coastguard Worker //
435*ec779b8eSAndroid Build Coastguard Worker // configure default for decoders
436*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_RANGE, C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "range")
437*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::CODED & (D::CONFIG | D::PARAM))
438*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::range_t>());
439*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_TRANSFER, C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "transfer")
440*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::CODED & (D::CONFIG | D::PARAM))
441*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::transfer_t>());
442*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-primaries", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "primaries")
443*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::CODED & (D::CONFIG | D::PARAM)));
444*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-matrix", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "matrix")
445*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::CODED & (D::CONFIG | D::PARAM)));
446*ec779b8eSAndroid Build Coastguard Worker
447*ec779b8eSAndroid Build Coastguard Worker // read back default for decoders. This is needed in case the component does not support
448*ec779b8eSAndroid Build Coastguard Worker // color aspects. In that case, these values get copied to color-* keys.
449*ec779b8eSAndroid Build Coastguard Worker // TRICKY: We read these values at raw port, since that's where we want to read these.
450*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("default-color-range", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "range")
451*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ)
452*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::range_t>());
453*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("default-color-transfer", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "transfer")
454*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ)
455*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::transfer_t>());
456*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("default-color-primaries", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "primaries")
457*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ));
458*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("default-color-matrix", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS, "matrix")
459*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ));
460*ec779b8eSAndroid Build Coastguard Worker
461*ec779b8eSAndroid Build Coastguard Worker // read back final for decoder output (also, configure final aspects as well. This should be
462*ec779b8eSAndroid Build Coastguard Worker // overwritten based on coded/default values if component supports color aspects, but is used
463*ec779b8eSAndroid Build Coastguard Worker // as final values if component does not support aspects at all)
464*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_RANGE, C2_PARAMKEY_COLOR_ASPECTS, "range")
465*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ)
466*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::range_t>());
467*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_TRANSFER, C2_PARAMKEY_COLOR_ASPECTS, "transfer")
468*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ)
469*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::transfer_t>());
470*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-primaries", C2_PARAMKEY_COLOR_ASPECTS, "primaries")
471*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ));
472*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-matrix", C2_PARAMKEY_COLOR_ASPECTS, "matrix")
473*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::READ));
474*ec779b8eSAndroid Build Coastguard Worker
475*ec779b8eSAndroid Build Coastguard Worker // configure transfer request
476*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-transfer-request", C2_PARAMKEY_COLOR_ASPECTS, "transfer")
477*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::DECODER & D::RAW & D::CONFIG)
478*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::transfer_t>());
479*ec779b8eSAndroid Build Coastguard Worker
480*ec779b8eSAndroid Build Coastguard Worker // configure source aspects for encoders and read them back on the coded(!) port.
481*ec779b8eSAndroid Build Coastguard Worker // This is to ensure muxing the desired aspects into the container.
482*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_RANGE, C2_PARAMKEY_COLOR_ASPECTS, "range")
483*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::CODED)
484*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::range_t>());
485*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_TRANSFER, C2_PARAMKEY_COLOR_ASPECTS, "transfer")
486*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::CODED)
487*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::transfer_t>());
488*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-primaries", C2_PARAMKEY_COLOR_ASPECTS, "primaries")
489*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::CODED));
490*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-matrix", C2_PARAMKEY_COLOR_ASPECTS, "matrix")
491*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::CODED));
492*ec779b8eSAndroid Build Coastguard Worker
493*ec779b8eSAndroid Build Coastguard Worker // read back coded aspects for encoders (on the raw port), but also configure
494*ec779b8eSAndroid Build Coastguard Worker // desired aspects here.
495*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_RANGE, C2_PARAMKEY_VUI_COLOR_ASPECTS, "range")
496*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::RAW)
497*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::range_t>());
498*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COLOR_TRANSFER, C2_PARAMKEY_VUI_COLOR_ASPECTS, "transfer")
499*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::RAW)
500*ec779b8eSAndroid Build Coastguard Worker .withC2Mappers<C2Color::transfer_t>());
501*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-primaries", C2_PARAMKEY_VUI_COLOR_ASPECTS, "primaries")
502*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::RAW));
503*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("color-matrix", C2_PARAMKEY_VUI_COLOR_ASPECTS, "matrix")
504*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::ENCODER & D::RAW));
505*ec779b8eSAndroid Build Coastguard Worker
506*ec779b8eSAndroid Build Coastguard Worker // Dataspace
507*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._dataspace", C2_PARAMKEY_DATA_SPACE, "value")
508*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
509*ec779b8eSAndroid Build Coastguard Worker
510*ec779b8eSAndroid Build Coastguard Worker // HDR
511*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.red.x", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.red.x")
512*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
513*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.red.y", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.red.y")
514*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
515*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.green.x", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.green.x")
516*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
517*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.green.y", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.green.y")
518*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
519*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.blue.x", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.blue.x")
520*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
521*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.blue.y", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.blue.y")
522*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
523*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.white.x", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.white.x")
524*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
525*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.white.y", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.white.y")
526*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
527*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.max-luminance", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.max-luminance")
528*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
529*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("smpte2086.min-luminance", C2_PARAMKEY_HDR_STATIC_INFO, "mastering.min-luminance")
530*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
531*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("cta861.max-cll", C2_PARAMKEY_HDR_STATIC_INFO, "max-cll")
532*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
533*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("cta861.max-fall", C2_PARAMKEY_HDR_STATIC_INFO, "max-fall")
534*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
535*ec779b8eSAndroid Build Coastguard Worker
536*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(C2_PARAMKEY_HDR_FORMAT, C2_PARAMKEY_HDR_FORMAT, "value")
537*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::CODED & D::CONFIG));
538*ec779b8eSAndroid Build Coastguard Worker
539*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(std::string(KEY_FEATURE_) + FEATURE_SecurePlayback,
540*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_SECURE_MODE, "value"));
541*ec779b8eSAndroid Build Coastguard Worker
542*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PREPEND_HEADER_TO_SYNC_FRAMES,
543*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_PREPEND_HEADER_MODE, "value")
544*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO)
545*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
546*ec779b8eSAndroid Build Coastguard Worker int32_t value;
547*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
548*ec779b8eSAndroid Build Coastguard Worker return value ? C2Value(C2Config::PREPEND_HEADER_TO_ALL_SYNC)
549*ec779b8eSAndroid Build Coastguard Worker : C2Value(C2Config::PREPEND_HEADER_TO_NONE);
550*ec779b8eSAndroid Build Coastguard Worker }
551*ec779b8eSAndroid Build Coastguard Worker return C2Value();
552*ec779b8eSAndroid Build Coastguard Worker }, [](C2Value v) -> C2Value {
553*ec779b8eSAndroid Build Coastguard Worker C2Config::prepend_header_mode_t value;
554*ec779b8eSAndroid Build Coastguard Worker using C2ValueType=typename _c2_reduce_enum_to_underlying_type<decltype(value)>::type;
555*ec779b8eSAndroid Build Coastguard Worker if (v.get((C2ValueType *)&value)) {
556*ec779b8eSAndroid Build Coastguard Worker switch (value) {
557*ec779b8eSAndroid Build Coastguard Worker case C2Config::PREPEND_HEADER_TO_NONE: return 0;
558*ec779b8eSAndroid Build Coastguard Worker case C2Config::PREPEND_HEADER_TO_ALL_SYNC: return 1;
559*ec779b8eSAndroid Build Coastguard Worker case C2Config::PREPEND_HEADER_ON_CHANGE: [[fallthrough]];
560*ec779b8eSAndroid Build Coastguard Worker default: return C2Value();
561*ec779b8eSAndroid Build Coastguard Worker }
562*ec779b8eSAndroid Build Coastguard Worker }
563*ec779b8eSAndroid Build Coastguard Worker return C2Value();
564*ec779b8eSAndroid Build Coastguard Worker }));
565*ec779b8eSAndroid Build Coastguard Worker // remove when codecs switch to PARAMKEY
566*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_PREPEND_HEADER_TO_SYNC_FRAMES,
567*ec779b8eSAndroid Build Coastguard Worker "coding.add-csd-to-sync-frames", "value")
568*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO));
569*ec779b8eSAndroid Build Coastguard Worker // convert to timestamp base
570*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_I_FRAME_INTERVAL, C2_PARAMKEY_SYNC_FRAME_INTERVAL, "value")
571*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::ENCODER & D::CONFIG)
572*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value v) -> C2Value {
573*ec779b8eSAndroid Build Coastguard Worker // convert from i32 to float
574*ec779b8eSAndroid Build Coastguard Worker int32_t i32Value;
575*ec779b8eSAndroid Build Coastguard Worker float fpValue;
576*ec779b8eSAndroid Build Coastguard Worker if (v.get(&i32Value)) {
577*ec779b8eSAndroid Build Coastguard Worker return int64_t(1000000) * i32Value;
578*ec779b8eSAndroid Build Coastguard Worker } else if (v.get(&fpValue)) {
579*ec779b8eSAndroid Build Coastguard Worker return int64_t(c2_min(1000000 * fpValue + 0.5, (double)INT64_MAX));
580*ec779b8eSAndroid Build Coastguard Worker }
581*ec779b8eSAndroid Build Coastguard Worker return C2Value();
582*ec779b8eSAndroid Build Coastguard Worker }));
583*ec779b8eSAndroid Build Coastguard Worker // remove when codecs switch to proper coding.gop (add support for calculating gop)
584*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper("i-frame-period", "coding.gop", "intra-period")
585*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO));
586*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_INTRA_REFRESH_PERIOD, C2_PARAMKEY_INTRA_REFRESH, "period")
587*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::ENCODER)
588*ec779b8eSAndroid Build Coastguard Worker .withMappers(makeFloat, [](C2Value v) -> C2Value {
589*ec779b8eSAndroid Build Coastguard Worker // read back always as int
590*ec779b8eSAndroid Build Coastguard Worker float value;
591*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
592*ec779b8eSAndroid Build Coastguard Worker return (int32_t)value;
593*ec779b8eSAndroid Build Coastguard Worker }
594*ec779b8eSAndroid Build Coastguard Worker return C2Value();
595*ec779b8eSAndroid Build Coastguard Worker }));
596*ec779b8eSAndroid Build Coastguard Worker
597*ec779b8eSAndroid Build Coastguard Worker if (android::media::codec::provider_->region_of_interest()
598*ec779b8eSAndroid Build Coastguard Worker && android::media::codec::provider_->region_of_interest_support()) {
599*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(C2_PARAMKEY_QP_OFFSET_RECTS, C2_PARAMKEY_QP_OFFSET_RECTS, "")
600*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & (D::CONFIG | D::PARAM) & D::ENCODER & D::INPUT));
601*ec779b8eSAndroid Build Coastguard Worker }
602*ec779b8eSAndroid Build Coastguard Worker
603*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(PARAMETER_KEY_REQUEST_SYNC_FRAME,
604*ec779b8eSAndroid Build Coastguard Worker "coding.request-sync", "value")
605*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::PARAM & D::ENCODER)
606*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value) -> C2Value { return uint32_t(1); }));
607*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(PARAMETER_KEY_REQUEST_SYNC_FRAME,
608*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_REQUEST_SYNC_FRAME, "value")
609*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::PARAM & D::ENCODER)
610*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value) -> C2Value { return uint32_t(1); }));
611*ec779b8eSAndroid Build Coastguard Worker
612*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_OPERATING_RATE, C2_PARAMKEY_OPERATING_RATE, "value")
613*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::PARAM | D::CONFIG) // write-only
614*ec779b8eSAndroid Build Coastguard Worker .withMapper(makeFloat));
615*ec779b8eSAndroid Build Coastguard Worker // C2 priorities are inverted
616*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PRIORITY, C2_PARAMKEY_PRIORITY, "value")
617*ec779b8eSAndroid Build Coastguard Worker .withMappers(negate, negate));
618*ec779b8eSAndroid Build Coastguard Worker // remove when codecs switch to PARAMKEY
619*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_OPERATING_RATE, "ctrl.operating-rate", "value")
620*ec779b8eSAndroid Build Coastguard Worker .withMapper(makeFloat));
621*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_PRIORITY, "ctrl.priority", "value"));
622*ec779b8eSAndroid Build Coastguard Worker
623*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_WIDTH, C2_PARAMKEY_PICTURE_SIZE, "width")
624*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO | D::IMAGE));
625*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_HEIGHT, C2_PARAMKEY_PICTURE_SIZE, "height")
626*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO | D::IMAGE));
627*ec779b8eSAndroid Build Coastguard Worker
628*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("crop-left", C2_PARAMKEY_CROP_RECT, "left")
629*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO | D::IMAGE));
630*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("crop-top", C2_PARAMKEY_CROP_RECT, "top")
631*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO | D::IMAGE));
632*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("crop-width", C2_PARAMKEY_CROP_RECT, "width")
633*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO | D::IMAGE));
634*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("crop-height", C2_PARAMKEY_CROP_RECT, "height")
635*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO | D::IMAGE));
636*ec779b8eSAndroid Build Coastguard Worker
637*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MAX_WIDTH, C2_PARAMKEY_MAX_PICTURE_SIZE, "width")
638*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
639*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MAX_HEIGHT, C2_PARAMKEY_MAX_PICTURE_SIZE, "height")
640*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
641*ec779b8eSAndroid Build Coastguard Worker
642*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("csd-0", C2_PARAMKEY_INIT_DATA, "value")
643*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::OUTPUT & D::READ));
644*ec779b8eSAndroid Build Coastguard Worker
645*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_HDR10_PLUS_INFO, C2_PARAMKEY_INPUT_HDR10_PLUS_INFO, "value")
646*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::PARAM & D::INPUT & (D::CONFIG | D::PARAM)));
647*ec779b8eSAndroid Build Coastguard Worker
648*ec779b8eSAndroid Build Coastguard Worker deprecated(ConfigMapper(KEY_HDR10_PLUS_INFO, C2_PARAMKEY_OUTPUT_HDR10_PLUS_INFO, "value")
649*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::OUTPUT & D::READ));
650*ec779b8eSAndroid Build Coastguard Worker
651*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(
652*ec779b8eSAndroid Build Coastguard Worker std::string(C2_PARAMKEY_INPUT_HDR_DYNAMIC_INFO) + ".type",
653*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_INPUT_HDR_DYNAMIC_INFO, "type")
654*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::PARAM & D::INPUT & (D::CONFIG | D::PARAM)));
655*ec779b8eSAndroid Build Coastguard Worker
656*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(
657*ec779b8eSAndroid Build Coastguard Worker std::string(C2_PARAMKEY_INPUT_HDR_DYNAMIC_INFO) + ".data",
658*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_INPUT_HDR_DYNAMIC_INFO, "data")
659*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::PARAM & D::INPUT & (D::CONFIG | D::PARAM)));
660*ec779b8eSAndroid Build Coastguard Worker
661*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(
662*ec779b8eSAndroid Build Coastguard Worker std::string(C2_PARAMKEY_OUTPUT_HDR_DYNAMIC_INFO) + ".type",
663*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_OUTPUT_HDR_DYNAMIC_INFO, "type")
664*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::OUTPUT & D::READ));
665*ec779b8eSAndroid Build Coastguard Worker
666*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(
667*ec779b8eSAndroid Build Coastguard Worker std::string(C2_PARAMKEY_OUTPUT_HDR_DYNAMIC_INFO) + ".data",
668*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_OUTPUT_HDR_DYNAMIC_INFO, "data")
669*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::OUTPUT & D::READ));
670*ec779b8eSAndroid Build Coastguard Worker
671*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(C2_PARAMKEY_TEMPORAL_LAYERING, C2_PARAMKEY_TEMPORAL_LAYERING, "")
672*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO & D::OUTPUT));
673*ec779b8eSAndroid Build Coastguard Worker
674*ec779b8eSAndroid Build Coastguard Worker // Pixel Format (use local key for actual pixel format as we don't distinguish between
675*ec779b8eSAndroid Build Coastguard Worker // SDK layouts for flexible format and we need the actual SDK color format in the media format)
676*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._color-format", C2_PARAMKEY_PIXEL_FORMAT, "value")
677*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW)
678*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
679*ec779b8eSAndroid Build Coastguard Worker int32_t value;
680*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
681*ec779b8eSAndroid Build Coastguard Worker uint32_t result;
682*ec779b8eSAndroid Build Coastguard Worker if (C2Mapper::mapPixelFormatFrameworkToCodec(value, &result)) {
683*ec779b8eSAndroid Build Coastguard Worker return result;
684*ec779b8eSAndroid Build Coastguard Worker }
685*ec779b8eSAndroid Build Coastguard Worker }
686*ec779b8eSAndroid Build Coastguard Worker return C2Value();
687*ec779b8eSAndroid Build Coastguard Worker }, [](C2Value v) -> C2Value {
688*ec779b8eSAndroid Build Coastguard Worker uint32_t value;
689*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
690*ec779b8eSAndroid Build Coastguard Worker int32_t result;
691*ec779b8eSAndroid Build Coastguard Worker if (C2Mapper::mapPixelFormatCodecToFramework(value, &result)) {
692*ec779b8eSAndroid Build Coastguard Worker return result;
693*ec779b8eSAndroid Build Coastguard Worker }
694*ec779b8eSAndroid Build Coastguard Worker }
695*ec779b8eSAndroid Build Coastguard Worker return C2Value();
696*ec779b8eSAndroid Build Coastguard Worker }));
697*ec779b8eSAndroid Build Coastguard Worker
698*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PIXEL_ASPECT_RATIO_WIDTH, C2_PARAMKEY_PIXEL_ASPECT_RATIO, "width")
699*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
700*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PIXEL_ASPECT_RATIO_HEIGHT, C2_PARAMKEY_PIXEL_ASPECT_RATIO, "height")
701*ec779b8eSAndroid Build Coastguard Worker .limitTo((D::VIDEO | D::IMAGE) & D::RAW));
702*ec779b8eSAndroid Build Coastguard Worker
703*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_CHANNEL_COUNT, C2_PARAMKEY_CHANNEL_COUNT, "value")
704*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO)); // read back to both formats
705*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_CHANNEL_COUNT, C2_PARAMKEY_CODED_CHANNEL_COUNT, "value")
706*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::CODED));
707*ec779b8eSAndroid Build Coastguard Worker
708*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_SAMPLE_RATE, C2_PARAMKEY_SAMPLE_RATE, "value")
709*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO)); // read back to both port formats
710*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_SAMPLE_RATE, C2_PARAMKEY_CODED_SAMPLE_RATE, "value")
711*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::CODED));
712*ec779b8eSAndroid Build Coastguard Worker
713*ec779b8eSAndroid Build Coastguard Worker auto pcmEncodingMapper = [](C2Value v) -> C2Value {
714*ec779b8eSAndroid Build Coastguard Worker int32_t value;
715*ec779b8eSAndroid Build Coastguard Worker C2Config::pcm_encoding_t to;
716*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value) && C2Mapper::map(value, &to)) {
717*ec779b8eSAndroid Build Coastguard Worker return to;
718*ec779b8eSAndroid Build Coastguard Worker }
719*ec779b8eSAndroid Build Coastguard Worker return C2Value();
720*ec779b8eSAndroid Build Coastguard Worker };
721*ec779b8eSAndroid Build Coastguard Worker auto pcmEncodingReverse = [](C2Value v) -> C2Value {
722*ec779b8eSAndroid Build Coastguard Worker C2Config::pcm_encoding_t value;
723*ec779b8eSAndroid Build Coastguard Worker int32_t to;
724*ec779b8eSAndroid Build Coastguard Worker using C2ValueType=typename _c2_reduce_enum_to_underlying_type<decltype(value)>::type;
725*ec779b8eSAndroid Build Coastguard Worker if (v.get((C2ValueType*)&value) && C2Mapper::map(value, &to)) {
726*ec779b8eSAndroid Build Coastguard Worker return to;
727*ec779b8eSAndroid Build Coastguard Worker }
728*ec779b8eSAndroid Build Coastguard Worker return C2Value();
729*ec779b8eSAndroid Build Coastguard Worker };
730*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PCM_ENCODING, C2_PARAMKEY_PCM_ENCODING, "value")
731*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO)
732*ec779b8eSAndroid Build Coastguard Worker .withMappers(pcmEncodingMapper, pcmEncodingReverse));
733*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._codec-pcm-encoding", C2_PARAMKEY_PCM_ENCODING, "value")
734*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::READ)
735*ec779b8eSAndroid Build Coastguard Worker .withMappers(pcmEncodingMapper, pcmEncodingReverse));
736*ec779b8eSAndroid Build Coastguard Worker
737*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_IS_ADTS, C2_PARAMKEY_AAC_PACKAGING, "value")
738*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::CODED)
739*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
740*ec779b8eSAndroid Build Coastguard Worker int32_t value;
741*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value) && value) {
742*ec779b8eSAndroid Build Coastguard Worker return C2Config::AAC_PACKAGING_ADTS;
743*ec779b8eSAndroid Build Coastguard Worker }
744*ec779b8eSAndroid Build Coastguard Worker return C2Value();
745*ec779b8eSAndroid Build Coastguard Worker }, [](C2Value v) -> C2Value {
746*ec779b8eSAndroid Build Coastguard Worker uint32_t value;
747*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value) && value == C2Config::AAC_PACKAGING_ADTS) {
748*ec779b8eSAndroid Build Coastguard Worker return (int32_t)1;
749*ec779b8eSAndroid Build Coastguard Worker }
750*ec779b8eSAndroid Build Coastguard Worker return C2Value();
751*ec779b8eSAndroid Build Coastguard Worker }));
752*ec779b8eSAndroid Build Coastguard Worker
753*ec779b8eSAndroid Build Coastguard Worker std::shared_ptr<C2Mapper::ProfileLevelMapper> mapper =
754*ec779b8eSAndroid Build Coastguard Worker C2Mapper::GetProfileLevelMapper(mCodingMediaType);
755*ec779b8eSAndroid Build Coastguard Worker
756*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PROFILE, C2_PARAMKEY_PROFILE_LEVEL, "profile")
757*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::CODED)
758*ec779b8eSAndroid Build Coastguard Worker .withMappers([mapper](C2Value v) -> C2Value {
759*ec779b8eSAndroid Build Coastguard Worker C2Config::profile_t c2 = PROFILE_UNUSED;
760*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
761*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get(&sdk) && mapper->mapProfile(sdk, &c2)) {
762*ec779b8eSAndroid Build Coastguard Worker return c2;
763*ec779b8eSAndroid Build Coastguard Worker }
764*ec779b8eSAndroid Build Coastguard Worker return PROFILE_UNUSED;
765*ec779b8eSAndroid Build Coastguard Worker }, [mapper](C2Value v) -> C2Value {
766*ec779b8eSAndroid Build Coastguard Worker C2Config::profile_t c2;
767*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
768*ec779b8eSAndroid Build Coastguard Worker using C2ValueType=typename _c2_reduce_enum_to_underlying_type<decltype(c2)>::type;
769*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get((C2ValueType*)&c2) && mapper->mapProfile(c2, &sdk)) {
770*ec779b8eSAndroid Build Coastguard Worker return sdk;
771*ec779b8eSAndroid Build Coastguard Worker }
772*ec779b8eSAndroid Build Coastguard Worker return C2Value();
773*ec779b8eSAndroid Build Coastguard Worker }));
774*ec779b8eSAndroid Build Coastguard Worker
775*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_LEVEL, C2_PARAMKEY_PROFILE_LEVEL, "level")
776*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::CODED)
777*ec779b8eSAndroid Build Coastguard Worker .withMappers([mapper](C2Value v) -> C2Value {
778*ec779b8eSAndroid Build Coastguard Worker C2Config::level_t c2 = LEVEL_UNUSED;
779*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
780*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get(&sdk) && mapper->mapLevel(sdk, &c2)) {
781*ec779b8eSAndroid Build Coastguard Worker return c2;
782*ec779b8eSAndroid Build Coastguard Worker }
783*ec779b8eSAndroid Build Coastguard Worker return LEVEL_UNUSED;
784*ec779b8eSAndroid Build Coastguard Worker }, [mapper](C2Value v) -> C2Value {
785*ec779b8eSAndroid Build Coastguard Worker C2Config::level_t c2;
786*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
787*ec779b8eSAndroid Build Coastguard Worker using C2ValueType=typename _c2_reduce_enum_to_underlying_type<decltype(c2)>::type;
788*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get((C2ValueType*)&c2) && mapper->mapLevel(c2, &sdk)) {
789*ec779b8eSAndroid Build Coastguard Worker return sdk;
790*ec779b8eSAndroid Build Coastguard Worker }
791*ec779b8eSAndroid Build Coastguard Worker return C2Value();
792*ec779b8eSAndroid Build Coastguard Worker }));
793*ec779b8eSAndroid Build Coastguard Worker
794*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_PROFILE, C2_PARAMKEY_PROFILE_LEVEL, "profile")
795*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::ENCODER & (D::CONFIG | D::PARAM))
796*ec779b8eSAndroid Build Coastguard Worker .withMapper([mapper](C2Value v) -> C2Value {
797*ec779b8eSAndroid Build Coastguard Worker C2Config::profile_t c2 = PROFILE_UNUSED;
798*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
799*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get(&sdk) && mapper->mapProfile(sdk, &c2)) {
800*ec779b8eSAndroid Build Coastguard Worker return c2;
801*ec779b8eSAndroid Build Coastguard Worker }
802*ec779b8eSAndroid Build Coastguard Worker return PROFILE_UNUSED;
803*ec779b8eSAndroid Build Coastguard Worker }));
804*ec779b8eSAndroid Build Coastguard Worker
805*ec779b8eSAndroid Build Coastguard Worker // convert to dBFS and add default
806*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_TARGET_REFERENCE_LEVEL, C2_PARAMKEY_DRC_TARGET_REFERENCE_LEVEL, "value")
807*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM | D::READ))
808*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
809*ec779b8eSAndroid Build Coastguard Worker int32_t value;
810*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < -1) {
811*ec779b8eSAndroid Build Coastguard Worker value = property_get_int32(PROP_DRC_OVERRIDE_REF_LEVEL, DRC_DEFAULT_MOBILE_REF_LEVEL);
812*ec779b8eSAndroid Build Coastguard Worker }
813*ec779b8eSAndroid Build Coastguard Worker return float(-0.25 * c2_min(value, 127));
814*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
815*ec779b8eSAndroid Build Coastguard Worker float value;
816*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
817*ec779b8eSAndroid Build Coastguard Worker return (int32_t) (-4. * value);
818*ec779b8eSAndroid Build Coastguard Worker }
819*ec779b8eSAndroid Build Coastguard Worker return C2Value();
820*ec779b8eSAndroid Build Coastguard Worker }));
821*ec779b8eSAndroid Build Coastguard Worker
822*ec779b8eSAndroid Build Coastguard Worker // convert to 0-1 (%) and add default
823*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_ATTENUATION_FACTOR, C2_PARAMKEY_DRC_ATTENUATION_FACTOR, "value")
824*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM | D::READ))
825*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
826*ec779b8eSAndroid Build Coastguard Worker int32_t value;
827*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < 0) {
828*ec779b8eSAndroid Build Coastguard Worker value = property_get_int32(PROP_DRC_OVERRIDE_CUT, DRC_DEFAULT_MOBILE_DRC_CUT);
829*ec779b8eSAndroid Build Coastguard Worker }
830*ec779b8eSAndroid Build Coastguard Worker return float(c2_min(value, 127) / 127.);
831*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
832*ec779b8eSAndroid Build Coastguard Worker float value;
833*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
834*ec779b8eSAndroid Build Coastguard Worker return (int32_t) (value * 127. + 0.5);
835*ec779b8eSAndroid Build Coastguard Worker }
836*ec779b8eSAndroid Build Coastguard Worker else {
837*ec779b8eSAndroid Build Coastguard Worker return C2Value();
838*ec779b8eSAndroid Build Coastguard Worker }
839*ec779b8eSAndroid Build Coastguard Worker }));
840*ec779b8eSAndroid Build Coastguard Worker
841*ec779b8eSAndroid Build Coastguard Worker // convert to 0-1 (%) and add default
842*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_BOOST_FACTOR, C2_PARAMKEY_DRC_BOOST_FACTOR, "value")
843*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM | D::READ))
844*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
845*ec779b8eSAndroid Build Coastguard Worker int32_t value;
846*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < 0) {
847*ec779b8eSAndroid Build Coastguard Worker value = property_get_int32(PROP_DRC_OVERRIDE_BOOST, DRC_DEFAULT_MOBILE_DRC_BOOST);
848*ec779b8eSAndroid Build Coastguard Worker }
849*ec779b8eSAndroid Build Coastguard Worker return float(c2_min(value, 127) / 127.);
850*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
851*ec779b8eSAndroid Build Coastguard Worker float value;
852*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
853*ec779b8eSAndroid Build Coastguard Worker return (int32_t) (value * 127. + 0.5);
854*ec779b8eSAndroid Build Coastguard Worker }
855*ec779b8eSAndroid Build Coastguard Worker else {
856*ec779b8eSAndroid Build Coastguard Worker return C2Value();
857*ec779b8eSAndroid Build Coastguard Worker }
858*ec779b8eSAndroid Build Coastguard Worker }));
859*ec779b8eSAndroid Build Coastguard Worker
860*ec779b8eSAndroid Build Coastguard Worker // convert to compression type and add default
861*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_HEAVY_COMPRESSION, C2_PARAMKEY_DRC_COMPRESSION_MODE, "value")
862*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM))
863*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value v) -> C2Value {
864*ec779b8eSAndroid Build Coastguard Worker int32_t value;
865*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < 0) {
866*ec779b8eSAndroid Build Coastguard Worker value = property_get_int32(PROP_DRC_OVERRIDE_HEAVY, DRC_DEFAULT_MOBILE_DRC_HEAVY);
867*ec779b8eSAndroid Build Coastguard Worker }
868*ec779b8eSAndroid Build Coastguard Worker return value == 1 ? C2Config::DRC_COMPRESSION_HEAVY : C2Config::DRC_COMPRESSION_LIGHT;
869*ec779b8eSAndroid Build Coastguard Worker }));
870*ec779b8eSAndroid Build Coastguard Worker
871*ec779b8eSAndroid Build Coastguard Worker // convert to dBFS and add default
872*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_ENCODED_TARGET_LEVEL, C2_PARAMKEY_DRC_ENCODED_TARGET_LEVEL, "value")
873*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM | D::READ))
874*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
875*ec779b8eSAndroid Build Coastguard Worker int32_t value;
876*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < 0) {
877*ec779b8eSAndroid Build Coastguard Worker value = property_get_int32(PROP_DRC_OVERRIDE_ENC_LEVEL, DRC_DEFAULT_MOBILE_ENC_LEVEL);
878*ec779b8eSAndroid Build Coastguard Worker }
879*ec779b8eSAndroid Build Coastguard Worker return float(-0.25 * c2_min(value, 127));
880*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
881*ec779b8eSAndroid Build Coastguard Worker float value;
882*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
883*ec779b8eSAndroid Build Coastguard Worker return (int32_t) (-4. * value);
884*ec779b8eSAndroid Build Coastguard Worker }
885*ec779b8eSAndroid Build Coastguard Worker else {
886*ec779b8eSAndroid Build Coastguard Worker return C2Value();
887*ec779b8eSAndroid Build Coastguard Worker }
888*ec779b8eSAndroid Build Coastguard Worker }));
889*ec779b8eSAndroid Build Coastguard Worker
890*ec779b8eSAndroid Build Coastguard Worker // convert to effect type (these map to SDK values) and add default
891*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_EFFECT_TYPE, C2_PARAMKEY_DRC_EFFECT_TYPE, "value")
892*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM | D::READ))
893*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
894*ec779b8eSAndroid Build Coastguard Worker int32_t value;
895*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < -1 || value > 8) {
896*ec779b8eSAndroid Build Coastguard Worker value = property_get_int32(PROP_DRC_OVERRIDE_EFFECT, DRC_DEFAULT_MOBILE_DRC_EFFECT);
897*ec779b8eSAndroid Build Coastguard Worker // ensure value is within range
898*ec779b8eSAndroid Build Coastguard Worker if (value < -1 || value > 8) {
899*ec779b8eSAndroid Build Coastguard Worker value = DRC_DEFAULT_MOBILE_DRC_EFFECT;
900*ec779b8eSAndroid Build Coastguard Worker }
901*ec779b8eSAndroid Build Coastguard Worker }
902*ec779b8eSAndroid Build Coastguard Worker return value;
903*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
904*ec779b8eSAndroid Build Coastguard Worker int32_t value;
905*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
906*ec779b8eSAndroid Build Coastguard Worker return value;
907*ec779b8eSAndroid Build Coastguard Worker }
908*ec779b8eSAndroid Build Coastguard Worker else {
909*ec779b8eSAndroid Build Coastguard Worker return C2Value();
910*ec779b8eSAndroid Build Coastguard Worker }
911*ec779b8eSAndroid Build Coastguard Worker }));
912*ec779b8eSAndroid Build Coastguard Worker
913*ec779b8eSAndroid Build Coastguard Worker // convert to album mode and add default
914*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_ALBUM_MODE, C2_PARAMKEY_DRC_ALBUM_MODE, "value")
915*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & (D::CONFIG | D::PARAM | D::READ))
916*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
917*ec779b8eSAndroid Build Coastguard Worker int32_t value;
918*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < 0 || value > 1) {
919*ec779b8eSAndroid Build Coastguard Worker value = DRC_DEFAULT_MOBILE_DRC_ALBUM;
920*ec779b8eSAndroid Build Coastguard Worker // ensure value is within range
921*ec779b8eSAndroid Build Coastguard Worker if (value < 0 || value > 1) {
922*ec779b8eSAndroid Build Coastguard Worker value = DRC_DEFAULT_MOBILE_DRC_ALBUM;
923*ec779b8eSAndroid Build Coastguard Worker }
924*ec779b8eSAndroid Build Coastguard Worker }
925*ec779b8eSAndroid Build Coastguard Worker return value;
926*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
927*ec779b8eSAndroid Build Coastguard Worker int32_t value;
928*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
929*ec779b8eSAndroid Build Coastguard Worker return value;
930*ec779b8eSAndroid Build Coastguard Worker }
931*ec779b8eSAndroid Build Coastguard Worker else {
932*ec779b8eSAndroid Build Coastguard Worker return C2Value();
933*ec779b8eSAndroid Build Coastguard Worker }
934*ec779b8eSAndroid Build Coastguard Worker }));
935*ec779b8eSAndroid Build Coastguard Worker
936*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_DRC_OUTPUT_LOUDNESS, C2_PARAMKEY_DRC_OUTPUT_LOUDNESS, "value")
937*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::OUTPUT & D::DECODER & D::READ)
938*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
939*ec779b8eSAndroid Build Coastguard Worker int32_t value;
940*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < -1) {
941*ec779b8eSAndroid Build Coastguard Worker value = DRC_DEFAULT_MOBILE_OUTPUT_LOUDNESS;
942*ec779b8eSAndroid Build Coastguard Worker }
943*ec779b8eSAndroid Build Coastguard Worker return float(-0.25 * c2_min(value, 127));
944*ec779b8eSAndroid Build Coastguard Worker },[](C2Value v) -> C2Value {
945*ec779b8eSAndroid Build Coastguard Worker float value;
946*ec779b8eSAndroid Build Coastguard Worker if (v.get(&value)) {
947*ec779b8eSAndroid Build Coastguard Worker return (int32_t) (-4. * value);
948*ec779b8eSAndroid Build Coastguard Worker }
949*ec779b8eSAndroid Build Coastguard Worker return C2Value();
950*ec779b8eSAndroid Build Coastguard Worker }));
951*ec779b8eSAndroid Build Coastguard Worker
952*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_MAX_OUTPUT_CHANNEL_COUNT, C2_PARAMKEY_MAX_CHANNEL_COUNT, "value")
953*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & (D::CONFIG | D::PARAM | D::READ)));
954*ec779b8eSAndroid Build Coastguard Worker
955*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_MAX_OUTPUT_CHANNEL_COUNT, C2_PARAMKEY_MAX_CHANNEL_COUNT, "value")
956*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & (D::CONFIG | D::PARAM | D::READ)));
957*ec779b8eSAndroid Build Coastguard Worker
958*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_CHANNEL_MASK, C2_PARAMKEY_CHANNEL_MASK, "value")
959*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::DECODER & D::READ));
960*ec779b8eSAndroid Build Coastguard Worker
961*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_CHANNEL_MASK, C2_PARAMKEY_CHANNEL_MASK, "value")
962*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::ENCODER & D::CONFIG));
963*ec779b8eSAndroid Build Coastguard Worker
964*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_AAC_SBR_MODE, C2_PARAMKEY_AAC_SBR_MODE, "value")
965*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::ENCODER & (D::CONFIG | D::PARAM | D::READ))
966*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value v) -> C2Value {
967*ec779b8eSAndroid Build Coastguard Worker int32_t value;
968*ec779b8eSAndroid Build Coastguard Worker if (!v.get(&value) || value < 0) {
969*ec779b8eSAndroid Build Coastguard Worker return C2Config::AAC_SBR_AUTO;
970*ec779b8eSAndroid Build Coastguard Worker }
971*ec779b8eSAndroid Build Coastguard Worker switch (value) {
972*ec779b8eSAndroid Build Coastguard Worker case 0: return C2Config::AAC_SBR_OFF;
973*ec779b8eSAndroid Build Coastguard Worker case 1: return C2Config::AAC_SBR_SINGLE_RATE;
974*ec779b8eSAndroid Build Coastguard Worker case 2: return C2Config::AAC_SBR_DUAL_RATE;
975*ec779b8eSAndroid Build Coastguard Worker default: return C2Config::AAC_SBR_AUTO + 1; // invalid value
976*ec779b8eSAndroid Build Coastguard Worker }
977*ec779b8eSAndroid Build Coastguard Worker }));
978*ec779b8eSAndroid Build Coastguard Worker
979*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._encoding-quality-level", C2_PARAMKEY_ENCODING_QUALITY_LEVEL, "value")
980*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & (D::CONFIG | D::PARAM)));
981*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_QUALITY, C2_PARAMKEY_QUALITY, "value")
982*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & (D::CONFIG | D::PARAM)));
983*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_FLAC_COMPRESSION_LEVEL, C2_PARAMKEY_COMPLEXITY, "value")
984*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::AUDIO & D::ENCODER));
985*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_COMPLEXITY, C2_PARAMKEY_COMPLEXITY, "value")
986*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & (D::CONFIG | D::PARAM)));
987*ec779b8eSAndroid Build Coastguard Worker
988*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_GRID_COLUMNS, C2_PARAMKEY_TILE_LAYOUT, "columns")
989*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::IMAGE));
990*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_GRID_ROWS, C2_PARAMKEY_TILE_LAYOUT, "rows")
991*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::IMAGE));
992*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_TILE_WIDTH, C2_PARAMKEY_TILE_LAYOUT, "tile.width")
993*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::IMAGE));
994*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_TILE_HEIGHT, C2_PARAMKEY_TILE_LAYOUT, "tile.height")
995*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::IMAGE));
996*ec779b8eSAndroid Build Coastguard Worker
997*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_LATENCY, C2_PARAMKEY_PIPELINE_DELAY_REQUEST, "value")
998*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::VIDEO & D::ENCODER));
999*ec779b8eSAndroid Build Coastguard Worker
1000*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(C2_PARAMKEY_INPUT_TIME_STRETCH, C2_PARAMKEY_INPUT_TIME_STRETCH, "value"));
1001*ec779b8eSAndroid Build Coastguard Worker
1002*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_LOW_LATENCY, C2_PARAMKEY_LOW_LATENCY_MODE, "value")
1003*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::DECODER & (D::CONFIG | D::PARAM))
1004*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value v) -> C2Value {
1005*ec779b8eSAndroid Build Coastguard Worker int32_t value = 0;
1006*ec779b8eSAndroid Build Coastguard Worker (void)v.get(&value);
1007*ec779b8eSAndroid Build Coastguard Worker return value == 0 ? C2_FALSE : C2_TRUE;
1008*ec779b8eSAndroid Build Coastguard Worker }));
1009*ec779b8eSAndroid Build Coastguard Worker
1010*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._trigger-tunnel-peek", C2_PARAMKEY_TUNNEL_START_RENDER, "value")
1011*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::PARAM & D::VIDEO & D::DECODER)
1012*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value v) -> C2Value {
1013*ec779b8eSAndroid Build Coastguard Worker int32_t value = 0;
1014*ec779b8eSAndroid Build Coastguard Worker (void)v.get(&value);
1015*ec779b8eSAndroid Build Coastguard Worker return value == 0 ? C2_FALSE : C2_TRUE;
1016*ec779b8eSAndroid Build Coastguard Worker }));
1017*ec779b8eSAndroid Build Coastguard Worker
1018*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper("android._tunnel-peek-set-legacy", C2_PARAMKEY_TUNNEL_PEEK_MODE, "value")
1019*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::PARAM & D::VIDEO & D::DECODER)
1020*ec779b8eSAndroid Build Coastguard Worker .withMapper([](C2Value v) -> C2Value {
1021*ec779b8eSAndroid Build Coastguard Worker int32_t value = 0;
1022*ec779b8eSAndroid Build Coastguard Worker (void)v.get(&value);
1023*ec779b8eSAndroid Build Coastguard Worker return value == 0
1024*ec779b8eSAndroid Build Coastguard Worker ? C2Value(C2PlatformConfig::SPECIFIED_PEEK)
1025*ec779b8eSAndroid Build Coastguard Worker : C2Value(C2PlatformConfig::UNSPECIFIED_PEEK);
1026*ec779b8eSAndroid Build Coastguard Worker }));
1027*ec779b8eSAndroid Build Coastguard Worker
1028*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_VIDEO_QP_AVERAGE, C2_PARAMKEY_AVERAGE_QP, "value")
1029*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO & D::READ));
1030*ec779b8eSAndroid Build Coastguard Worker
1031*ec779b8eSAndroid Build Coastguard Worker add(ConfigMapper(KEY_PICTURE_TYPE, C2_PARAMKEY_PICTURE_TYPE, "value")
1032*ec779b8eSAndroid Build Coastguard Worker .limitTo(D::ENCODER & D::VIDEO & D::READ)
1033*ec779b8eSAndroid Build Coastguard Worker .withMappers([](C2Value v) -> C2Value {
1034*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
1035*ec779b8eSAndroid Build Coastguard Worker C2Config::picture_type_t c2;
1036*ec779b8eSAndroid Build Coastguard Worker if (v.get(&sdk) && C2Mapper::map(sdk, &c2)) {
1037*ec779b8eSAndroid Build Coastguard Worker return C2Value(c2);
1038*ec779b8eSAndroid Build Coastguard Worker }
1039*ec779b8eSAndroid Build Coastguard Worker return C2Value();
1040*ec779b8eSAndroid Build Coastguard Worker }, [](C2Value v) -> C2Value {
1041*ec779b8eSAndroid Build Coastguard Worker C2Config::picture_type_t c2;
1042*ec779b8eSAndroid Build Coastguard Worker int32_t sdk = PICTURE_TYPE_UNKNOWN;
1043*ec779b8eSAndroid Build Coastguard Worker using C2ValueType=typename _c2_reduce_enum_to_underlying_type<decltype(c2)>::type;
1044*ec779b8eSAndroid Build Coastguard Worker if (v.get((C2ValueType*)&c2) && C2Mapper::map(c2, &sdk)) {
1045*ec779b8eSAndroid Build Coastguard Worker return sdk;
1046*ec779b8eSAndroid Build Coastguard Worker }
1047*ec779b8eSAndroid Build Coastguard Worker return C2Value();
1048*ec779b8eSAndroid Build Coastguard Worker }));
1049*ec779b8eSAndroid Build Coastguard Worker
1050*ec779b8eSAndroid Build Coastguard Worker /* still to do
1051*ec779b8eSAndroid Build Coastguard Worker not yet used by MediaCodec, but defined as MediaFormat
1052*ec779b8eSAndroid Build Coastguard Worker KEY_AUDIO_SESSION_ID // we use "audio-hw-sync"
1053*ec779b8eSAndroid Build Coastguard Worker KEY_OUTPUT_REORDER_DEPTH
1054*ec779b8eSAndroid Build Coastguard Worker */
1055*ec779b8eSAndroid Build Coastguard Worker }
1056*ec779b8eSAndroid Build Coastguard Worker
initialize(const std::shared_ptr<C2ParamReflector> & reflector,const std::shared_ptr<Codec2Client::Configurable> & configurable)1057*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::initialize(
1058*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<C2ParamReflector> &reflector,
1059*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable) {
1060*ec779b8eSAndroid Build Coastguard Worker C2ComponentDomainSetting domain(C2Component::DOMAIN_OTHER);
1061*ec779b8eSAndroid Build Coastguard Worker C2ComponentKindSetting kind(C2Component::KIND_OTHER);
1062*ec779b8eSAndroid Build Coastguard Worker
1063*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2Param>> queried;
1064*ec779b8eSAndroid Build Coastguard Worker c2_status_t c2err = configurable->query({ &domain, &kind }, {}, C2_DONT_BLOCK, &queried);
1065*ec779b8eSAndroid Build Coastguard Worker if (c2err != C2_OK) {
1066*ec779b8eSAndroid Build Coastguard Worker ALOGD("Query domain & kind failed => %s", asString(c2err));
1067*ec779b8eSAndroid Build Coastguard Worker // TEMP: determine kind from component name
1068*ec779b8eSAndroid Build Coastguard Worker if (kind.value == C2Component::KIND_OTHER) {
1069*ec779b8eSAndroid Build Coastguard Worker if (configurable->getName().find("encoder") != std::string::npos) {
1070*ec779b8eSAndroid Build Coastguard Worker kind.value = C2Component::KIND_ENCODER;
1071*ec779b8eSAndroid Build Coastguard Worker } else if (configurable->getName().find("decoder") != std::string::npos) {
1072*ec779b8eSAndroid Build Coastguard Worker kind.value = C2Component::KIND_DECODER;
1073*ec779b8eSAndroid Build Coastguard Worker }
1074*ec779b8eSAndroid Build Coastguard Worker }
1075*ec779b8eSAndroid Build Coastguard Worker
1076*ec779b8eSAndroid Build Coastguard Worker // TEMP: determine domain from media type (port (preferred) or stream #0)
1077*ec779b8eSAndroid Build Coastguard Worker if (domain.value == C2Component::DOMAIN_OTHER) {
1078*ec779b8eSAndroid Build Coastguard Worker AString mediaType = QueryMediaType(true /* input */, configurable);
1079*ec779b8eSAndroid Build Coastguard Worker if (mediaType.startsWith("audio/")) {
1080*ec779b8eSAndroid Build Coastguard Worker domain.value = C2Component::DOMAIN_AUDIO;
1081*ec779b8eSAndroid Build Coastguard Worker } else if (mediaType.startsWith("video/")) {
1082*ec779b8eSAndroid Build Coastguard Worker domain.value = C2Component::DOMAIN_VIDEO;
1083*ec779b8eSAndroid Build Coastguard Worker } else if (mediaType.startsWith("image/")) {
1084*ec779b8eSAndroid Build Coastguard Worker domain.value = C2Component::DOMAIN_IMAGE;
1085*ec779b8eSAndroid Build Coastguard Worker }
1086*ec779b8eSAndroid Build Coastguard Worker }
1087*ec779b8eSAndroid Build Coastguard Worker }
1088*ec779b8eSAndroid Build Coastguard Worker
1089*ec779b8eSAndroid Build Coastguard Worker mDomain = (domain.value == C2Component::DOMAIN_VIDEO ? Domain::IS_VIDEO :
1090*ec779b8eSAndroid Build Coastguard Worker domain.value == C2Component::DOMAIN_IMAGE ? Domain::IS_IMAGE :
1091*ec779b8eSAndroid Build Coastguard Worker domain.value == C2Component::DOMAIN_AUDIO ? Domain::IS_AUDIO : Domain::OTHER_DOMAIN)
1092*ec779b8eSAndroid Build Coastguard Worker | (kind.value == C2Component::KIND_DECODER ? Domain::IS_DECODER :
1093*ec779b8eSAndroid Build Coastguard Worker kind.value == C2Component::KIND_ENCODER ? Domain::IS_ENCODER : Domain::OTHER_KIND);
1094*ec779b8eSAndroid Build Coastguard Worker
1095*ec779b8eSAndroid Build Coastguard Worker mInputDomain = Domain(((mDomain & IS_DECODER) ? IS_CODED : IS_RAW) | IS_INPUT);
1096*ec779b8eSAndroid Build Coastguard Worker mOutputDomain = Domain(((mDomain & IS_ENCODER) ? IS_CODED : IS_RAW) | IS_OUTPUT);
1097*ec779b8eSAndroid Build Coastguard Worker
1098*ec779b8eSAndroid Build Coastguard Worker ALOGV("domain is %#x (%u %u)", mDomain, domain.value, kind.value);
1099*ec779b8eSAndroid Build Coastguard Worker
1100*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param::Index> paramIndices;
1101*ec779b8eSAndroid Build Coastguard Worker switch (kind.value) {
1102*ec779b8eSAndroid Build Coastguard Worker case C2Component::KIND_DECODER:
1103*ec779b8eSAndroid Build Coastguard Worker mCodingMediaType = QueryMediaType(true /* input */, configurable).c_str();
1104*ec779b8eSAndroid Build Coastguard Worker break;
1105*ec779b8eSAndroid Build Coastguard Worker case C2Component::KIND_ENCODER:
1106*ec779b8eSAndroid Build Coastguard Worker mCodingMediaType = QueryMediaType(false /* input */, configurable).c_str();
1107*ec779b8eSAndroid Build Coastguard Worker break;
1108*ec779b8eSAndroid Build Coastguard Worker default:
1109*ec779b8eSAndroid Build Coastguard Worker mCodingMediaType = "";
1110*ec779b8eSAndroid Build Coastguard Worker }
1111*ec779b8eSAndroid Build Coastguard Worker
1112*ec779b8eSAndroid Build Coastguard Worker c2err = configurable->querySupportedParams(&mParamDescs);
1113*ec779b8eSAndroid Build Coastguard Worker if (c2err != C2_OK) {
1114*ec779b8eSAndroid Build Coastguard Worker ALOGD("Query supported params failed after returning %zu values => %s",
1115*ec779b8eSAndroid Build Coastguard Worker mParamDescs.size(), asString(c2err));
1116*ec779b8eSAndroid Build Coastguard Worker return UNKNOWN_ERROR;
1117*ec779b8eSAndroid Build Coastguard Worker }
1118*ec779b8eSAndroid Build Coastguard Worker for (const std::shared_ptr<C2ParamDescriptor> &desc : mParamDescs) {
1119*ec779b8eSAndroid Build Coastguard Worker mSupportedIndices.emplace(desc->index());
1120*ec779b8eSAndroid Build Coastguard Worker }
1121*ec779b8eSAndroid Build Coastguard Worker
1122*ec779b8eSAndroid Build Coastguard Worker mReflector = reflector;
1123*ec779b8eSAndroid Build Coastguard Worker if (mReflector == nullptr) {
1124*ec779b8eSAndroid Build Coastguard Worker ALOGE("Null param reflector");
1125*ec779b8eSAndroid Build Coastguard Worker return UNKNOWN_ERROR;
1126*ec779b8eSAndroid Build Coastguard Worker }
1127*ec779b8eSAndroid Build Coastguard Worker
1128*ec779b8eSAndroid Build Coastguard Worker // enumerate all fields
1129*ec779b8eSAndroid Build Coastguard Worker mParamUpdater = std::make_shared<ReflectedParamUpdater>();
1130*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->clear();
1131*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->supportWholeParam(
1132*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_TEMPORAL_LAYERING, C2StreamTemporalLayeringTuning::CORE_INDEX);
1133*ec779b8eSAndroid Build Coastguard Worker if (android::media::codec::provider_->region_of_interest()
1134*ec779b8eSAndroid Build Coastguard Worker && android::media::codec::provider_->region_of_interest_support()) {
1135*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->supportWholeParam(
1136*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_QP_OFFSET_RECTS, C2StreamQpOffsetRects::CORE_INDEX);
1137*ec779b8eSAndroid Build Coastguard Worker }
1138*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->addParamDesc(mReflector, mParamDescs);
1139*ec779b8eSAndroid Build Coastguard Worker
1140*ec779b8eSAndroid Build Coastguard Worker // TEMP: add some standard fields even if not reflected
1141*ec779b8eSAndroid Build Coastguard Worker if (kind.value == C2Component::KIND_ENCODER) {
1142*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->addStandardParam<C2StreamInitDataInfo::output>(C2_PARAMKEY_INIT_DATA);
1143*ec779b8eSAndroid Build Coastguard Worker }
1144*ec779b8eSAndroid Build Coastguard Worker if (domain.value == C2Component::DOMAIN_IMAGE || domain.value == C2Component::DOMAIN_VIDEO) {
1145*ec779b8eSAndroid Build Coastguard Worker if (kind.value != C2Component::KIND_ENCODER) {
1146*ec779b8eSAndroid Build Coastguard Worker addLocalParam<C2StreamPictureSizeInfo::output>(C2_PARAMKEY_PICTURE_SIZE);
1147*ec779b8eSAndroid Build Coastguard Worker addLocalParam<C2StreamCropRectInfo::output>(C2_PARAMKEY_CROP_RECT);
1148*ec779b8eSAndroid Build Coastguard Worker addLocalParam(
1149*ec779b8eSAndroid Build Coastguard Worker new C2StreamPixelAspectRatioInfo::output(0u, 1u, 1u),
1150*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_PIXEL_ASPECT_RATIO);
1151*ec779b8eSAndroid Build Coastguard Worker addLocalParam(new C2StreamRotationInfo::output(0u, 0), C2_PARAMKEY_ROTATION);
1152*ec779b8eSAndroid Build Coastguard Worker addLocalParam(
1153*ec779b8eSAndroid Build Coastguard Worker new C2StreamColorAspectsTuning::output(0u),
1154*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_DEFAULT_COLOR_ASPECTS);
1155*ec779b8eSAndroid Build Coastguard Worker addLocalParam<C2StreamDataSpaceInfo::output>(C2_PARAMKEY_DATA_SPACE);
1156*ec779b8eSAndroid Build Coastguard Worker addLocalParam<C2StreamHdrStaticInfo::output>(C2_PARAMKEY_HDR_STATIC_INFO);
1157*ec779b8eSAndroid Build Coastguard Worker addLocalParam(
1158*ec779b8eSAndroid Build Coastguard Worker new C2StreamSurfaceScalingInfo::output(0u, VIDEO_SCALING_MODE_SCALE_TO_FIT),
1159*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_SURFACE_SCALING_MODE);
1160*ec779b8eSAndroid Build Coastguard Worker } else {
1161*ec779b8eSAndroid Build Coastguard Worker addLocalParam(new C2StreamColorAspectsInfo::input(0u), C2_PARAMKEY_COLOR_ASPECTS);
1162*ec779b8eSAndroid Build Coastguard Worker
1163*ec779b8eSAndroid Build Coastguard Worker if (domain.value == C2Component::DOMAIN_VIDEO) {
1164*ec779b8eSAndroid Build Coastguard Worker addLocalParam(new C2AndroidStreamAverageBlockQuantizationInfo::output(0u, 0),
1165*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_AVERAGE_QP);
1166*ec779b8eSAndroid Build Coastguard Worker addLocalParam(new C2StreamPictureTypeInfo::output(0u, 0),
1167*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_PICTURE_TYPE);
1168*ec779b8eSAndroid Build Coastguard Worker }
1169*ec779b8eSAndroid Build Coastguard Worker }
1170*ec779b8eSAndroid Build Coastguard Worker }
1171*ec779b8eSAndroid Build Coastguard Worker
1172*ec779b8eSAndroid Build Coastguard Worker initializeStandardParams();
1173*ec779b8eSAndroid Build Coastguard Worker
1174*ec779b8eSAndroid Build Coastguard Worker // subscribe to all supported standard (exposed) params
1175*ec779b8eSAndroid Build Coastguard Worker // TODO: limit this to params that are actually in the domain
1176*ec779b8eSAndroid Build Coastguard Worker std::vector<std::string> formatKeys = mStandardParams->getPathsForDomain(Domain(1 << 30));
1177*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param::Index> indices;
1178*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->getParamIndicesForKeys(formatKeys, &indices);
1179*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.insert(indices.begin(), indices.end());
1180*ec779b8eSAndroid Build Coastguard Worker
1181*ec779b8eSAndroid Build Coastguard Worker // also subscribe to some non-SDK standard parameters
1182*ec779b8eSAndroid Build Coastguard Worker // for number of input/output buffers
1183*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2PortSuggestedBufferCountTuning::input::PARAM_TYPE);
1184*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2PortSuggestedBufferCountTuning::output::PARAM_TYPE);
1185*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2ActualPipelineDelayTuning::PARAM_TYPE);
1186*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2PortActualDelayTuning::input::PARAM_TYPE);
1187*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2PortActualDelayTuning::output::PARAM_TYPE);
1188*ec779b8eSAndroid Build Coastguard Worker // for output buffer array allocation
1189*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2StreamMaxBufferSizeInfo::output::PARAM_TYPE);
1190*ec779b8eSAndroid Build Coastguard Worker // init data (CSD)
1191*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.emplace(C2StreamInitDataInfo::output::PARAM_TYPE);
1192*ec779b8eSAndroid Build Coastguard Worker
1193*ec779b8eSAndroid Build Coastguard Worker for (const std::shared_ptr<C2ParamDescriptor> &desc : mParamDescs) {
1194*ec779b8eSAndroid Build Coastguard Worker if (desc->index().isVendor()) {
1195*ec779b8eSAndroid Build Coastguard Worker std::vector<std::string> keys;
1196*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->getKeysForParamIndex(desc->index(), &keys);
1197*ec779b8eSAndroid Build Coastguard Worker for (const std::string &key : keys) {
1198*ec779b8eSAndroid Build Coastguard Worker mVendorParams.insert_or_assign(key, desc);
1199*ec779b8eSAndroid Build Coastguard Worker }
1200*ec779b8eSAndroid Build Coastguard Worker }
1201*ec779b8eSAndroid Build Coastguard Worker }
1202*ec779b8eSAndroid Build Coastguard Worker
1203*ec779b8eSAndroid Build Coastguard Worker // Parameters that are not subscribed initially, but can be subscribed
1204*ec779b8eSAndroid Build Coastguard Worker // upon explicit request.
1205*ec779b8eSAndroid Build Coastguard Worker static const std::initializer_list<C2Param::Index> kOptionalParams = {
1206*ec779b8eSAndroid Build Coastguard Worker C2AndroidStreamAverageBlockQuantizationInfo::output::PARAM_TYPE,
1207*ec779b8eSAndroid Build Coastguard Worker C2StreamPictureTypeInfo::output::PARAM_TYPE,
1208*ec779b8eSAndroid Build Coastguard Worker };
1209*ec779b8eSAndroid Build Coastguard Worker for (const C2Param::Index &index : kOptionalParams) {
1210*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.erase(index);
1211*ec779b8eSAndroid Build Coastguard Worker }
1212*ec779b8eSAndroid Build Coastguard Worker subscribeToConfigUpdate(configurable, {}, C2_MAY_BLOCK);
1213*ec779b8eSAndroid Build Coastguard Worker
1214*ec779b8eSAndroid Build Coastguard Worker return OK;
1215*ec779b8eSAndroid Build Coastguard Worker }
1216*ec779b8eSAndroid Build Coastguard Worker
subscribeToConfigUpdate(const std::shared_ptr<Codec2Client::Configurable> & configurable,const std::vector<C2Param::Index> & indices,c2_blocking_t blocking)1217*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::subscribeToConfigUpdate(
1218*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable,
1219*ec779b8eSAndroid Build Coastguard Worker const std::vector<C2Param::Index> &indices,
1220*ec779b8eSAndroid Build Coastguard Worker c2_blocking_t blocking) {
1221*ec779b8eSAndroid Build Coastguard Worker static const int32_t kProductFirstApiLevel =
1222*ec779b8eSAndroid Build Coastguard Worker base::GetIntProperty<int32_t>("ro.product.first_api_level", 0);
1223*ec779b8eSAndroid Build Coastguard Worker static const int32_t kBoardApiLevel =
1224*ec779b8eSAndroid Build Coastguard Worker base::GetIntProperty<int32_t>("ro.board.first_api_level", 0);
1225*ec779b8eSAndroid Build Coastguard Worker static const int32_t kFirstApiLevel =
1226*ec779b8eSAndroid Build Coastguard Worker (kBoardApiLevel != 0) ? kBoardApiLevel : kProductFirstApiLevel;
1227*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.insert(indices.begin(), indices.end());
1228*ec779b8eSAndroid Build Coastguard Worker if (mSubscribedIndices.size() != mSubscribedIndicesSize
1229*ec779b8eSAndroid Build Coastguard Worker && kFirstApiLevel >= __ANDROID_API_T__) {
1230*ec779b8eSAndroid Build Coastguard Worker std::vector<uint32_t> indicesVector;
1231*ec779b8eSAndroid Build Coastguard Worker for (C2Param::Index ix : mSubscribedIndices) {
1232*ec779b8eSAndroid Build Coastguard Worker indicesVector.push_back(ix);
1233*ec779b8eSAndroid Build Coastguard Worker }
1234*ec779b8eSAndroid Build Coastguard Worker std::unique_ptr<C2SubscribedParamIndicesTuning> subscribeTuning =
1235*ec779b8eSAndroid Build Coastguard Worker C2SubscribedParamIndicesTuning::AllocUnique(indicesVector);
1236*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2SettingResult>> results;
1237*ec779b8eSAndroid Build Coastguard Worker c2_status_t c2Err = configurable->config({ subscribeTuning.get() }, blocking, &results);
1238*ec779b8eSAndroid Build Coastguard Worker if (c2Err != C2_OK && c2Err != C2_BAD_INDEX) {
1239*ec779b8eSAndroid Build Coastguard Worker ALOGD("Failed to subscribe to parameters => %s", asString(c2Err));
1240*ec779b8eSAndroid Build Coastguard Worker // TODO: error
1241*ec779b8eSAndroid Build Coastguard Worker }
1242*ec779b8eSAndroid Build Coastguard Worker ALOGV("Subscribed to %zu params", mSubscribedIndices.size());
1243*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndicesSize = mSubscribedIndices.size();
1244*ec779b8eSAndroid Build Coastguard Worker }
1245*ec779b8eSAndroid Build Coastguard Worker #if defined(LOG_NDEBUG) && !LOG_NDEBUG
1246*ec779b8eSAndroid Build Coastguard Worker ALOGV("subscribed to %zu params:", mSubscribedIndices.size());
1247*ec779b8eSAndroid Build Coastguard Worker std::stringstream ss;
1248*ec779b8eSAndroid Build Coastguard Worker for (const C2Param::Index &index : mSubscribedIndices) {
1249*ec779b8eSAndroid Build Coastguard Worker ss << index << " ";
1250*ec779b8eSAndroid Build Coastguard Worker if (ss.str().length() > 70) {
1251*ec779b8eSAndroid Build Coastguard Worker ALOGV("%s", ss.str().c_str());
1252*ec779b8eSAndroid Build Coastguard Worker std::stringstream().swap(ss);
1253*ec779b8eSAndroid Build Coastguard Worker }
1254*ec779b8eSAndroid Build Coastguard Worker }
1255*ec779b8eSAndroid Build Coastguard Worker if (!ss.str().empty()) {
1256*ec779b8eSAndroid Build Coastguard Worker ALOGV("%s", ss.str().c_str());
1257*ec779b8eSAndroid Build Coastguard Worker }
1258*ec779b8eSAndroid Build Coastguard Worker #endif
1259*ec779b8eSAndroid Build Coastguard Worker return OK;
1260*ec779b8eSAndroid Build Coastguard Worker }
1261*ec779b8eSAndroid Build Coastguard Worker
queryConfiguration(const std::shared_ptr<Codec2Client::Configurable> & configurable)1262*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::queryConfiguration(
1263*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable) {
1264*ec779b8eSAndroid Build Coastguard Worker // query all subscribed parameters
1265*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param::Index> indices(mSubscribedIndices.begin(), mSubscribedIndices.end());
1266*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2Param>> queried;
1267*ec779b8eSAndroid Build Coastguard Worker c2_status_t c2Err = configurable->query({}, indices, C2_MAY_BLOCK, &queried);
1268*ec779b8eSAndroid Build Coastguard Worker if (c2Err != OK) {
1269*ec779b8eSAndroid Build Coastguard Worker ALOGI("query failed after returning %zu values (%s)", queried.size(), asString(c2Err));
1270*ec779b8eSAndroid Build Coastguard Worker // TODO: error
1271*ec779b8eSAndroid Build Coastguard Worker }
1272*ec779b8eSAndroid Build Coastguard Worker
1273*ec779b8eSAndroid Build Coastguard Worker updateConfiguration(queried, ALL);
1274*ec779b8eSAndroid Build Coastguard Worker return OK;
1275*ec779b8eSAndroid Build Coastguard Worker }
1276*ec779b8eSAndroid Build Coastguard Worker
updateConfiguration(std::vector<std::unique_ptr<C2Param>> & configUpdate,Domain domain)1277*ec779b8eSAndroid Build Coastguard Worker bool CCodecConfig::updateConfiguration(
1278*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2Param>> &configUpdate, Domain domain) {
1279*ec779b8eSAndroid Build Coastguard Worker ALOGV("updating configuration with %zu params", configUpdate.size());
1280*ec779b8eSAndroid Build Coastguard Worker bool changed = false;
1281*ec779b8eSAndroid Build Coastguard Worker for (std::unique_ptr<C2Param> &p : configUpdate) {
1282*ec779b8eSAndroid Build Coastguard Worker if (p && *p) {
1283*ec779b8eSAndroid Build Coastguard Worker // Allow unsubscribed vendor parameters to go through --- it may be
1284*ec779b8eSAndroid Build Coastguard Worker // later handled by the format shaper.
1285*ec779b8eSAndroid Build Coastguard Worker if (!p->isVendor() && mSubscribedIndices.count(p->index()) == 0) {
1286*ec779b8eSAndroid Build Coastguard Worker ALOGV("updateConfiguration: skipped unsubscribed param %08x", p->index());
1287*ec779b8eSAndroid Build Coastguard Worker continue;
1288*ec779b8eSAndroid Build Coastguard Worker }
1289*ec779b8eSAndroid Build Coastguard Worker auto insertion = mCurrentConfig.emplace(p->index(), nullptr);
1290*ec779b8eSAndroid Build Coastguard Worker if (insertion.second || *insertion.first->second != *p) {
1291*ec779b8eSAndroid Build Coastguard Worker if (mSupportedIndices.count(p->index()) || mLocalParams.count(p->index())) {
1292*ec779b8eSAndroid Build Coastguard Worker // only track changes in supported (reflected or local) indices
1293*ec779b8eSAndroid Build Coastguard Worker changed = true;
1294*ec779b8eSAndroid Build Coastguard Worker } else {
1295*ec779b8eSAndroid Build Coastguard Worker ALOGV("an unlisted config was %s: %#x",
1296*ec779b8eSAndroid Build Coastguard Worker insertion.second ? "added" : "updated", p->index());
1297*ec779b8eSAndroid Build Coastguard Worker }
1298*ec779b8eSAndroid Build Coastguard Worker }
1299*ec779b8eSAndroid Build Coastguard Worker insertion.first->second = std::move(p);
1300*ec779b8eSAndroid Build Coastguard Worker }
1301*ec779b8eSAndroid Build Coastguard Worker }
1302*ec779b8eSAndroid Build Coastguard Worker if (mInputSurface
1303*ec779b8eSAndroid Build Coastguard Worker && (domain & mOutputDomain)
1304*ec779b8eSAndroid Build Coastguard Worker && mInputSurfaceDataspace != mInputSurface->getDataspace()) {
1305*ec779b8eSAndroid Build Coastguard Worker changed = true;
1306*ec779b8eSAndroid Build Coastguard Worker mInputSurfaceDataspace = mInputSurface->getDataspace();
1307*ec779b8eSAndroid Build Coastguard Worker }
1308*ec779b8eSAndroid Build Coastguard Worker
1309*ec779b8eSAndroid Build Coastguard Worker ALOGV("updated configuration has %zu params (%s)", mCurrentConfig.size(),
1310*ec779b8eSAndroid Build Coastguard Worker changed ? "CHANGED" : "no change");
1311*ec779b8eSAndroid Build Coastguard Worker if (changed) {
1312*ec779b8eSAndroid Build Coastguard Worker return updateFormats(domain);
1313*ec779b8eSAndroid Build Coastguard Worker }
1314*ec779b8eSAndroid Build Coastguard Worker return false;
1315*ec779b8eSAndroid Build Coastguard Worker }
1316*ec779b8eSAndroid Build Coastguard Worker
updateFormats(Domain domain)1317*ec779b8eSAndroid Build Coastguard Worker bool CCodecConfig::updateFormats(Domain domain) {
1318*ec779b8eSAndroid Build Coastguard Worker // get addresses of params in the current config
1319*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param*> paramPointers;
1320*ec779b8eSAndroid Build Coastguard Worker for (const auto &it : mCurrentConfig) {
1321*ec779b8eSAndroid Build Coastguard Worker paramPointers.push_back(it.second.get());
1322*ec779b8eSAndroid Build Coastguard Worker }
1323*ec779b8eSAndroid Build Coastguard Worker
1324*ec779b8eSAndroid Build Coastguard Worker ReflectedParamUpdater::Dict reflected = mParamUpdater->getParams(paramPointers);
1325*ec779b8eSAndroid Build Coastguard Worker std::string config = reflected.debugString();
1326*ec779b8eSAndroid Build Coastguard Worker std::set<std::string> configLines;
1327*ec779b8eSAndroid Build Coastguard Worker std::string diff;
1328*ec779b8eSAndroid Build Coastguard Worker for (size_t start = 0; start != std::string::npos; ) {
1329*ec779b8eSAndroid Build Coastguard Worker size_t end = config.find('\n', start);
1330*ec779b8eSAndroid Build Coastguard Worker size_t count = (end == std::string::npos)
1331*ec779b8eSAndroid Build Coastguard Worker ? std::string::npos
1332*ec779b8eSAndroid Build Coastguard Worker : end - start + 1;
1333*ec779b8eSAndroid Build Coastguard Worker std::string line = config.substr(start, count);
1334*ec779b8eSAndroid Build Coastguard Worker configLines.insert(line);
1335*ec779b8eSAndroid Build Coastguard Worker if (mLastConfig.count(line) == 0) {
1336*ec779b8eSAndroid Build Coastguard Worker diff.append(line);
1337*ec779b8eSAndroid Build Coastguard Worker }
1338*ec779b8eSAndroid Build Coastguard Worker start = (end == std::string::npos) ? std::string::npos : end + 1;
1339*ec779b8eSAndroid Build Coastguard Worker }
1340*ec779b8eSAndroid Build Coastguard Worker if (!diff.empty()) {
1341*ec779b8eSAndroid Build Coastguard Worker ALOGD("c2 config diff is %s", diff.c_str());
1342*ec779b8eSAndroid Build Coastguard Worker }
1343*ec779b8eSAndroid Build Coastguard Worker mLastConfig.swap(configLines);
1344*ec779b8eSAndroid Build Coastguard Worker
1345*ec779b8eSAndroid Build Coastguard Worker bool changed = false;
1346*ec779b8eSAndroid Build Coastguard Worker if (domain & mInputDomain) {
1347*ec779b8eSAndroid Build Coastguard Worker sp<AMessage> oldFormat = mInputFormat;
1348*ec779b8eSAndroid Build Coastguard Worker mInputFormat = mInputFormat->dup(); // trigger format changed
1349*ec779b8eSAndroid Build Coastguard Worker mInputFormat->extend(getFormatForDomain(reflected, mInputDomain));
1350*ec779b8eSAndroid Build Coastguard Worker if (mInputFormat->countEntries() != oldFormat->countEntries()
1351*ec779b8eSAndroid Build Coastguard Worker || mInputFormat->changesFrom(oldFormat)->countEntries() > 0) {
1352*ec779b8eSAndroid Build Coastguard Worker changed = true;
1353*ec779b8eSAndroid Build Coastguard Worker } else {
1354*ec779b8eSAndroid Build Coastguard Worker mInputFormat = oldFormat; // no change
1355*ec779b8eSAndroid Build Coastguard Worker }
1356*ec779b8eSAndroid Build Coastguard Worker }
1357*ec779b8eSAndroid Build Coastguard Worker if (domain & mOutputDomain) {
1358*ec779b8eSAndroid Build Coastguard Worker sp<AMessage> oldFormat = mOutputFormat;
1359*ec779b8eSAndroid Build Coastguard Worker mOutputFormat = mOutputFormat->dup(); // trigger output format changed
1360*ec779b8eSAndroid Build Coastguard Worker mOutputFormat->extend(getFormatForDomain(reflected, mOutputDomain));
1361*ec779b8eSAndroid Build Coastguard Worker if (mOutputFormat->countEntries() != oldFormat->countEntries()
1362*ec779b8eSAndroid Build Coastguard Worker || mOutputFormat->changesFrom(oldFormat)->countEntries() > 0) {
1363*ec779b8eSAndroid Build Coastguard Worker changed = true;
1364*ec779b8eSAndroid Build Coastguard Worker } else {
1365*ec779b8eSAndroid Build Coastguard Worker mOutputFormat = oldFormat; // no change
1366*ec779b8eSAndroid Build Coastguard Worker }
1367*ec779b8eSAndroid Build Coastguard Worker }
1368*ec779b8eSAndroid Build Coastguard Worker ALOGV_IF(changed, "format(s) changed");
1369*ec779b8eSAndroid Build Coastguard Worker return changed;
1370*ec779b8eSAndroid Build Coastguard Worker }
1371*ec779b8eSAndroid Build Coastguard Worker
getFormatForDomain(const ReflectedParamUpdater::Dict & reflected,Domain portDomain) const1372*ec779b8eSAndroid Build Coastguard Worker sp<AMessage> CCodecConfig::getFormatForDomain(
1373*ec779b8eSAndroid Build Coastguard Worker const ReflectedParamUpdater::Dict &reflected,
1374*ec779b8eSAndroid Build Coastguard Worker Domain portDomain) const {
1375*ec779b8eSAndroid Build Coastguard Worker sp<AMessage> msg = new AMessage;
1376*ec779b8eSAndroid Build Coastguard Worker for (const auto &[key, mappers] : mStandardParams->getKeys()) {
1377*ec779b8eSAndroid Build Coastguard Worker for (const ConfigMapper &cm : mappers) {
1378*ec779b8eSAndroid Build Coastguard Worker if ((cm.domain() & portDomain) == 0 // input-output-coded-raw
1379*ec779b8eSAndroid Build Coastguard Worker || (cm.domain() & mDomain) != mDomain // component domain + kind (these must match)
1380*ec779b8eSAndroid Build Coastguard Worker || (cm.domain() & IS_READ) == 0) {
1381*ec779b8eSAndroid Build Coastguard Worker continue;
1382*ec779b8eSAndroid Build Coastguard Worker }
1383*ec779b8eSAndroid Build Coastguard Worker auto it = reflected.find(cm.path());
1384*ec779b8eSAndroid Build Coastguard Worker if (it == reflected.end()) {
1385*ec779b8eSAndroid Build Coastguard Worker continue;
1386*ec779b8eSAndroid Build Coastguard Worker }
1387*ec779b8eSAndroid Build Coastguard Worker C2Value c2Value;
1388*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> bufValue;
1389*ec779b8eSAndroid Build Coastguard Worker AString strValue;
1390*ec779b8eSAndroid Build Coastguard Worker AMessage::ItemData item;
1391*ec779b8eSAndroid Build Coastguard Worker if (it->second.find(&c2Value)) {
1392*ec779b8eSAndroid Build Coastguard Worker item = cm.mapToMessage(c2Value);
1393*ec779b8eSAndroid Build Coastguard Worker } else if (it->second.find(&bufValue)) {
1394*ec779b8eSAndroid Build Coastguard Worker item.set(bufValue);
1395*ec779b8eSAndroid Build Coastguard Worker } else if (it->second.find(&strValue)) {
1396*ec779b8eSAndroid Build Coastguard Worker item.set(strValue);
1397*ec779b8eSAndroid Build Coastguard Worker } else {
1398*ec779b8eSAndroid Build Coastguard Worker ALOGD("unexpected untyped query value for key: %s", cm.path().c_str());
1399*ec779b8eSAndroid Build Coastguard Worker continue;
1400*ec779b8eSAndroid Build Coastguard Worker }
1401*ec779b8eSAndroid Build Coastguard Worker msg->setItem(key.c_str(), item);
1402*ec779b8eSAndroid Build Coastguard Worker }
1403*ec779b8eSAndroid Build Coastguard Worker }
1404*ec779b8eSAndroid Build Coastguard Worker
1405*ec779b8eSAndroid Build Coastguard Worker bool input = (portDomain & Domain::IS_INPUT);
1406*ec779b8eSAndroid Build Coastguard Worker std::vector<std::string> vendorKeys;
1407*ec779b8eSAndroid Build Coastguard Worker for (const auto &[key, value] : reflected) {
1408*ec779b8eSAndroid Build Coastguard Worker auto it = mVendorParams.find(key);
1409*ec779b8eSAndroid Build Coastguard Worker if (it == mVendorParams.end()) {
1410*ec779b8eSAndroid Build Coastguard Worker continue;
1411*ec779b8eSAndroid Build Coastguard Worker }
1412*ec779b8eSAndroid Build Coastguard Worker C2Param::Index index = it->second->index();
1413*ec779b8eSAndroid Build Coastguard Worker if (mSubscribedIndices.count(index) == 0) {
1414*ec779b8eSAndroid Build Coastguard Worker continue;
1415*ec779b8eSAndroid Build Coastguard Worker }
1416*ec779b8eSAndroid Build Coastguard Worker // For vendor parameters, we only care about direction
1417*ec779b8eSAndroid Build Coastguard Worker if ((input && !index.forInput())
1418*ec779b8eSAndroid Build Coastguard Worker || (!input && !index.forOutput())) {
1419*ec779b8eSAndroid Build Coastguard Worker continue;
1420*ec779b8eSAndroid Build Coastguard Worker }
1421*ec779b8eSAndroid Build Coastguard Worker C2Value c2Value;
1422*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> bufValue;
1423*ec779b8eSAndroid Build Coastguard Worker AString strValue;
1424*ec779b8eSAndroid Build Coastguard Worker AMessage::ItemData item;
1425*ec779b8eSAndroid Build Coastguard Worker if (value.find(&c2Value)) {
1426*ec779b8eSAndroid Build Coastguard Worker C2ValueToMessageItem(c2Value, item);
1427*ec779b8eSAndroid Build Coastguard Worker } else if (value.find(&bufValue)) {
1428*ec779b8eSAndroid Build Coastguard Worker item.set(bufValue);
1429*ec779b8eSAndroid Build Coastguard Worker } else if (value.find(&strValue)) {
1430*ec779b8eSAndroid Build Coastguard Worker item.set(strValue);
1431*ec779b8eSAndroid Build Coastguard Worker } else {
1432*ec779b8eSAndroid Build Coastguard Worker ALOGD("unexpected untyped query value for key: %s", key.c_str());
1433*ec779b8eSAndroid Build Coastguard Worker continue;
1434*ec779b8eSAndroid Build Coastguard Worker }
1435*ec779b8eSAndroid Build Coastguard Worker msg->setItem(key.c_str(), item);
1436*ec779b8eSAndroid Build Coastguard Worker }
1437*ec779b8eSAndroid Build Coastguard Worker
1438*ec779b8eSAndroid Build Coastguard Worker { // convert from Codec 2.0 rect to MediaFormat rect and add crop rect if not present
1439*ec779b8eSAndroid Build Coastguard Worker int32_t left, top, width, height;
1440*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32("crop-left", &left) && msg->findInt32("crop-width", &width)
1441*ec779b8eSAndroid Build Coastguard Worker && msg->findInt32("crop-top", &top) && msg->findInt32("crop-height", &height)
1442*ec779b8eSAndroid Build Coastguard Worker && left >= 0 && width >=0 && width <= INT32_MAX - left
1443*ec779b8eSAndroid Build Coastguard Worker && top >= 0 && height >=0 && height <= INT32_MAX - top) {
1444*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("crop-left"));
1445*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("crop-top"));
1446*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("crop-width"));
1447*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("crop-height"));
1448*ec779b8eSAndroid Build Coastguard Worker msg->setRect("crop", left, top, left + width - 1, top + height - 1);
1449*ec779b8eSAndroid Build Coastguard Worker } else if (msg->findInt32("width", &width) && msg->findInt32("height", &height)) {
1450*ec779b8eSAndroid Build Coastguard Worker msg->setRect("crop", 0, 0, width - 1, height - 1);
1451*ec779b8eSAndroid Build Coastguard Worker }
1452*ec779b8eSAndroid Build Coastguard Worker }
1453*ec779b8eSAndroid Build Coastguard Worker
1454*ec779b8eSAndroid Build Coastguard Worker { // convert temporal layering to schema
1455*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> tmp;
1456*ec779b8eSAndroid Build Coastguard Worker if (msg->findBuffer(C2_PARAMKEY_TEMPORAL_LAYERING, &tmp) && tmp != nullptr) {
1457*ec779b8eSAndroid Build Coastguard Worker C2StreamTemporalLayeringTuning *layering =
1458*ec779b8eSAndroid Build Coastguard Worker C2StreamTemporalLayeringTuning::From(C2Param::From(tmp->data(), tmp->size()));
1459*ec779b8eSAndroid Build Coastguard Worker if (layering && layering->m.layerCount > 0
1460*ec779b8eSAndroid Build Coastguard Worker && layering->m.bLayerCount < layering->m.layerCount) {
1461*ec779b8eSAndroid Build Coastguard Worker // check if this is webrtc compatible
1462*ec779b8eSAndroid Build Coastguard Worker AString mime;
1463*ec779b8eSAndroid Build Coastguard Worker if (msg->findString(KEY_MIME, &mime) &&
1464*ec779b8eSAndroid Build Coastguard Worker mime.equalsIgnoreCase(MIMETYPE_VIDEO_VP8) &&
1465*ec779b8eSAndroid Build Coastguard Worker layering->m.bLayerCount == 0 &&
1466*ec779b8eSAndroid Build Coastguard Worker (layering->m.layerCount == 1
1467*ec779b8eSAndroid Build Coastguard Worker || (layering->m.layerCount == 2
1468*ec779b8eSAndroid Build Coastguard Worker && layering->flexCount() >= 1
1469*ec779b8eSAndroid Build Coastguard Worker && layering->m.bitrateRatios[0] == .6f)
1470*ec779b8eSAndroid Build Coastguard Worker || (layering->m.layerCount == 3
1471*ec779b8eSAndroid Build Coastguard Worker && layering->flexCount() >= 2
1472*ec779b8eSAndroid Build Coastguard Worker && layering->m.bitrateRatios[0] == .4f
1473*ec779b8eSAndroid Build Coastguard Worker && layering->m.bitrateRatios[1] == .6f)
1474*ec779b8eSAndroid Build Coastguard Worker || (layering->m.layerCount == 4
1475*ec779b8eSAndroid Build Coastguard Worker && layering->flexCount() >= 3
1476*ec779b8eSAndroid Build Coastguard Worker && layering->m.bitrateRatios[0] == .25f
1477*ec779b8eSAndroid Build Coastguard Worker && layering->m.bitrateRatios[1] == .4f
1478*ec779b8eSAndroid Build Coastguard Worker && layering->m.bitrateRatios[2] == .6f))) {
1479*ec779b8eSAndroid Build Coastguard Worker msg->setString(KEY_TEMPORAL_LAYERING, AStringPrintf(
1480*ec779b8eSAndroid Build Coastguard Worker "webrtc.vp8.%u-layer", layering->m.layerCount));
1481*ec779b8eSAndroid Build Coastguard Worker } else if (layering->m.bLayerCount) {
1482*ec779b8eSAndroid Build Coastguard Worker msg->setString(KEY_TEMPORAL_LAYERING, AStringPrintf(
1483*ec779b8eSAndroid Build Coastguard Worker "android.generic.%u+%u",
1484*ec779b8eSAndroid Build Coastguard Worker layering->m.layerCount - layering->m.bLayerCount,
1485*ec779b8eSAndroid Build Coastguard Worker layering->m.bLayerCount));
1486*ec779b8eSAndroid Build Coastguard Worker } else if (layering->m.bLayerCount) {
1487*ec779b8eSAndroid Build Coastguard Worker msg->setString(KEY_TEMPORAL_LAYERING, AStringPrintf(
1488*ec779b8eSAndroid Build Coastguard Worker "android.generic.%u", layering->m.layerCount));
1489*ec779b8eSAndroid Build Coastguard Worker }
1490*ec779b8eSAndroid Build Coastguard Worker }
1491*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName(C2_PARAMKEY_TEMPORAL_LAYERING));
1492*ec779b8eSAndroid Build Coastguard Worker }
1493*ec779b8eSAndroid Build Coastguard Worker }
1494*ec779b8eSAndroid Build Coastguard Worker
1495*ec779b8eSAndroid Build Coastguard Worker // Remove KEY_AAC_SBR_MODE from SDK message if it is outside supported range
1496*ec779b8eSAndroid Build Coastguard Worker // as SDK doesn't have a way to signal default sbr mode based on profile and
1497*ec779b8eSAndroid Build Coastguard Worker // requires that the key isn't present in format to signal that
1498*ec779b8eSAndroid Build Coastguard Worker int sbrMode;
1499*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32(KEY_AAC_SBR_MODE, &sbrMode) && (sbrMode < 0 || sbrMode > 2)) {
1500*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName(KEY_AAC_SBR_MODE));
1501*ec779b8eSAndroid Build Coastguard Worker }
1502*ec779b8eSAndroid Build Coastguard Worker
1503*ec779b8eSAndroid Build Coastguard Worker { // convert color info
1504*ec779b8eSAndroid Build Coastguard Worker // move default color to color aspect if not read from the component
1505*ec779b8eSAndroid Build Coastguard Worker int32_t tmp;
1506*ec779b8eSAndroid Build Coastguard Worker int32_t range;
1507*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32("default-color-range", &range)) {
1508*ec779b8eSAndroid Build Coastguard Worker if (!msg->findInt32(KEY_COLOR_RANGE, &tmp)) {
1509*ec779b8eSAndroid Build Coastguard Worker msg->setInt32(KEY_COLOR_RANGE, range);
1510*ec779b8eSAndroid Build Coastguard Worker }
1511*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("default-color-range"));
1512*ec779b8eSAndroid Build Coastguard Worker }
1513*ec779b8eSAndroid Build Coastguard Worker int32_t transfer;
1514*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32("default-color-transfer", &transfer)) {
1515*ec779b8eSAndroid Build Coastguard Worker if (!msg->findInt32(KEY_COLOR_TRANSFER, &tmp)) {
1516*ec779b8eSAndroid Build Coastguard Worker msg->setInt32(KEY_COLOR_TRANSFER, transfer);
1517*ec779b8eSAndroid Build Coastguard Worker }
1518*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("default-color-transfer"));
1519*ec779b8eSAndroid Build Coastguard Worker }
1520*ec779b8eSAndroid Build Coastguard Worker C2Color::primaries_t primaries;
1521*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32("default-color-primaries", (int32_t*)&primaries)) {
1522*ec779b8eSAndroid Build Coastguard Worker if (!msg->findInt32("color-primaries", &tmp)) {
1523*ec779b8eSAndroid Build Coastguard Worker msg->setInt32("color-primaries", primaries);
1524*ec779b8eSAndroid Build Coastguard Worker }
1525*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("default-color-primaries"));
1526*ec779b8eSAndroid Build Coastguard Worker }
1527*ec779b8eSAndroid Build Coastguard Worker C2Color::matrix_t matrix;
1528*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32("default-color-matrix", (int32_t*)&matrix)) {
1529*ec779b8eSAndroid Build Coastguard Worker if (!msg->findInt32("color-matrix", &tmp)) {
1530*ec779b8eSAndroid Build Coastguard Worker msg->setInt32("color-matrix", matrix);
1531*ec779b8eSAndroid Build Coastguard Worker }
1532*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("default-color-matrix"));
1533*ec779b8eSAndroid Build Coastguard Worker }
1534*ec779b8eSAndroid Build Coastguard Worker
1535*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32("color-primaries", (int32_t*)&primaries)
1536*ec779b8eSAndroid Build Coastguard Worker && msg->findInt32("color-matrix", (int32_t*)&matrix)) {
1537*ec779b8eSAndroid Build Coastguard Worker int32_t standard;
1538*ec779b8eSAndroid Build Coastguard Worker
1539*ec779b8eSAndroid Build Coastguard Worker if (C2Mapper::map(primaries, matrix, &standard)) {
1540*ec779b8eSAndroid Build Coastguard Worker msg->setInt32(KEY_COLOR_STANDARD, standard);
1541*ec779b8eSAndroid Build Coastguard Worker }
1542*ec779b8eSAndroid Build Coastguard Worker
1543*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("color-primaries"));
1544*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("color-matrix"));
1545*ec779b8eSAndroid Build Coastguard Worker }
1546*ec779b8eSAndroid Build Coastguard Worker
1547*ec779b8eSAndroid Build Coastguard Worker // calculate dataspace for raw graphic buffers if not specified by component, or if
1548*ec779b8eSAndroid Build Coastguard Worker // using surface with unspecified aspects (as those must be defaulted which may change
1549*ec779b8eSAndroid Build Coastguard Worker // the dataspace)
1550*ec779b8eSAndroid Build Coastguard Worker if ((portDomain & IS_RAW) && (mDomain & (IS_IMAGE | IS_VIDEO))) {
1551*ec779b8eSAndroid Build Coastguard Worker android_dataspace dataspace;
1552*ec779b8eSAndroid Build Coastguard Worker ColorAspects aspects = {
1553*ec779b8eSAndroid Build Coastguard Worker ColorAspects::RangeUnspecified, ColorAspects::PrimariesUnspecified,
1554*ec779b8eSAndroid Build Coastguard Worker ColorAspects::TransferUnspecified, ColorAspects::MatrixUnspecified
1555*ec779b8eSAndroid Build Coastguard Worker };
1556*ec779b8eSAndroid Build Coastguard Worker ColorUtils::getColorAspectsFromFormat(msg, aspects);
1557*ec779b8eSAndroid Build Coastguard Worker ColorAspects origAspects = aspects;
1558*ec779b8eSAndroid Build Coastguard Worker if (mUsingSurface) {
1559*ec779b8eSAndroid Build Coastguard Worker // get image size (default to HD)
1560*ec779b8eSAndroid Build Coastguard Worker int32_t width = 1280;
1561*ec779b8eSAndroid Build Coastguard Worker int32_t height = 720;
1562*ec779b8eSAndroid Build Coastguard Worker int32_t left, top, right, bottom;
1563*ec779b8eSAndroid Build Coastguard Worker if (msg->findRect("crop", &left, &top, &right, &bottom)) {
1564*ec779b8eSAndroid Build Coastguard Worker width = right - left + 1;
1565*ec779b8eSAndroid Build Coastguard Worker height = bottom - top + 1;
1566*ec779b8eSAndroid Build Coastguard Worker } else {
1567*ec779b8eSAndroid Build Coastguard Worker (void)msg->findInt32(KEY_WIDTH, &width);
1568*ec779b8eSAndroid Build Coastguard Worker (void)msg->findInt32(KEY_HEIGHT, &height);
1569*ec779b8eSAndroid Build Coastguard Worker }
1570*ec779b8eSAndroid Build Coastguard Worker ColorUtils::setDefaultCodecColorAspectsIfNeeded(aspects, width, height);
1571*ec779b8eSAndroid Build Coastguard Worker ColorUtils::setColorAspectsIntoFormat(aspects, msg);
1572*ec779b8eSAndroid Build Coastguard Worker }
1573*ec779b8eSAndroid Build Coastguard Worker
1574*ec779b8eSAndroid Build Coastguard Worker if (!msg->findInt32("android._dataspace", (int32_t*)&dataspace)
1575*ec779b8eSAndroid Build Coastguard Worker || aspects.mRange != origAspects.mRange
1576*ec779b8eSAndroid Build Coastguard Worker || aspects.mPrimaries != origAspects.mPrimaries
1577*ec779b8eSAndroid Build Coastguard Worker || aspects.mTransfer != origAspects.mTransfer
1578*ec779b8eSAndroid Build Coastguard Worker || aspects.mMatrixCoeffs != origAspects.mMatrixCoeffs) {
1579*ec779b8eSAndroid Build Coastguard Worker dataspace = ColorUtils::getDataSpaceForColorAspects(aspects, true /* mayExpand */);
1580*ec779b8eSAndroid Build Coastguard Worker msg->setInt32("android._dataspace", dataspace);
1581*ec779b8eSAndroid Build Coastguard Worker }
1582*ec779b8eSAndroid Build Coastguard Worker }
1583*ec779b8eSAndroid Build Coastguard Worker
1584*ec779b8eSAndroid Build Coastguard Worker if (mInputSurface) {
1585*ec779b8eSAndroid Build Coastguard Worker android_dataspace dataspace = mInputSurface->getDataspace();
1586*ec779b8eSAndroid Build Coastguard Worker ColorUtils::convertDataSpaceToV0(dataspace);
1587*ec779b8eSAndroid Build Coastguard Worker int32_t standard;
1588*ec779b8eSAndroid Build Coastguard Worker ColorUtils::getColorConfigFromDataSpace(dataspace, &range, &standard, &transfer);
1589*ec779b8eSAndroid Build Coastguard Worker if (range != 0) {
1590*ec779b8eSAndroid Build Coastguard Worker msg->setInt32(KEY_COLOR_RANGE, range);
1591*ec779b8eSAndroid Build Coastguard Worker }
1592*ec779b8eSAndroid Build Coastguard Worker if (standard != 0) {
1593*ec779b8eSAndroid Build Coastguard Worker msg->setInt32(KEY_COLOR_STANDARD, standard);
1594*ec779b8eSAndroid Build Coastguard Worker }
1595*ec779b8eSAndroid Build Coastguard Worker if (transfer != 0) {
1596*ec779b8eSAndroid Build Coastguard Worker msg->setInt32(KEY_COLOR_TRANSFER, transfer);
1597*ec779b8eSAndroid Build Coastguard Worker }
1598*ec779b8eSAndroid Build Coastguard Worker msg->setInt32("android._dataspace", dataspace);
1599*ec779b8eSAndroid Build Coastguard Worker }
1600*ec779b8eSAndroid Build Coastguard Worker
1601*ec779b8eSAndroid Build Coastguard Worker // HDR static info
1602*ec779b8eSAndroid Build Coastguard Worker
1603*ec779b8eSAndroid Build Coastguard Worker C2HdrStaticMetadataStruct hdr;
1604*ec779b8eSAndroid Build Coastguard Worker if (msg->findFloat("smpte2086.red.x", &hdr.mastering.red.x)
1605*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.red.y", &hdr.mastering.red.y)
1606*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.green.x", &hdr.mastering.green.x)
1607*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.green.y", &hdr.mastering.green.y)
1608*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.blue.x", &hdr.mastering.blue.x)
1609*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.blue.y", &hdr.mastering.blue.y)
1610*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.white.x", &hdr.mastering.white.x)
1611*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.white.y", &hdr.mastering.white.y)
1612*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.max-luminance", &hdr.mastering.maxLuminance)
1613*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("smpte2086.min-luminance", &hdr.mastering.minLuminance)
1614*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("cta861.max-cll", &hdr.maxCll)
1615*ec779b8eSAndroid Build Coastguard Worker && msg->findFloat("cta861.max-fall", &hdr.maxFall)) {
1616*ec779b8eSAndroid Build Coastguard Worker if (hdr.mastering.red.x >= 0 && hdr.mastering.red.x <= 1
1617*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.red.y >= 0 && hdr.mastering.red.y <= 1
1618*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.green.x >= 0 && hdr.mastering.green.x <= 1
1619*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.green.y >= 0 && hdr.mastering.green.y <= 1
1620*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.blue.x >= 0 && hdr.mastering.blue.x <= 1
1621*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.blue.y >= 0 && hdr.mastering.blue.y <= 1
1622*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.white.x >= 0 && hdr.mastering.white.x <= 1
1623*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.white.y >= 0 && hdr.mastering.white.y <= 1
1624*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.maxLuminance >= 0 && hdr.mastering.maxLuminance <= 65535
1625*ec779b8eSAndroid Build Coastguard Worker && hdr.mastering.minLuminance >= 0 && hdr.mastering.minLuminance <= 6.5535
1626*ec779b8eSAndroid Build Coastguard Worker && hdr.maxCll >= 0 && hdr.maxCll <= 65535
1627*ec779b8eSAndroid Build Coastguard Worker && hdr.maxFall >= 0 && hdr.maxFall <= 65535) {
1628*ec779b8eSAndroid Build Coastguard Worker HDRStaticInfo meta;
1629*ec779b8eSAndroid Build Coastguard Worker meta.mID = meta.kType1;
1630*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mR.x = hdr.mastering.red.x / 0.00002 + 0.5;
1631*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mR.y = hdr.mastering.red.y / 0.00002 + 0.5;
1632*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mG.x = hdr.mastering.green.x / 0.00002 + 0.5;
1633*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mG.y = hdr.mastering.green.y / 0.00002 + 0.5;
1634*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mB.x = hdr.mastering.blue.x / 0.00002 + 0.5;
1635*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mB.y = hdr.mastering.blue.y / 0.00002 + 0.5;
1636*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mW.x = hdr.mastering.white.x / 0.00002 + 0.5;
1637*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mW.y = hdr.mastering.white.y / 0.00002 + 0.5;
1638*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mMaxDisplayLuminance = hdr.mastering.maxLuminance + 0.5;
1639*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mMinDisplayLuminance = hdr.mastering.minLuminance / 0.0001 + 0.5;
1640*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mMaxContentLightLevel = hdr.maxCll + 0.5;
1641*ec779b8eSAndroid Build Coastguard Worker meta.sType1.mMaxFrameAverageLightLevel = hdr.maxFall + 0.5;
1642*ec779b8eSAndroid Build Coastguard Worker msg->setBuffer(KEY_HDR_STATIC_INFO, ABuffer::CreateAsCopy(&meta, sizeof(meta)));
1643*ec779b8eSAndroid Build Coastguard Worker } else {
1644*ec779b8eSAndroid Build Coastguard Worker ALOGD("found invalid HDR static metadata %s", msg->debugString(8).c_str());
1645*ec779b8eSAndroid Build Coastguard Worker }
1646*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.red.x"));
1647*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.red.y"));
1648*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.green.x"));
1649*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.green.y"));
1650*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.blue.x"));
1651*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.blue.y"));
1652*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.white.x"));
1653*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.white.y"));
1654*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.max-luminance"));
1655*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("smpte2086.min-luminance"));
1656*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("cta861.max-cll"));
1657*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName("cta861.max-fall"));
1658*ec779b8eSAndroid Build Coastguard Worker }
1659*ec779b8eSAndroid Build Coastguard Worker
1660*ec779b8eSAndroid Build Coastguard Worker // HDR dynamic info
1661*ec779b8eSAndroid Build Coastguard Worker std::string keyPrefix = input ? C2_PARAMKEY_INPUT_HDR_DYNAMIC_INFO
1662*ec779b8eSAndroid Build Coastguard Worker : C2_PARAMKEY_OUTPUT_HDR_DYNAMIC_INFO;
1663*ec779b8eSAndroid Build Coastguard Worker std::string typeKey = keyPrefix + ".type";
1664*ec779b8eSAndroid Build Coastguard Worker std::string dataKey = keyPrefix + ".data";
1665*ec779b8eSAndroid Build Coastguard Worker int32_t type;
1666*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> data;
1667*ec779b8eSAndroid Build Coastguard Worker if (msg->findInt32(typeKey.c_str(), &type)
1668*ec779b8eSAndroid Build Coastguard Worker && msg->findBuffer(dataKey.c_str(), &data)) {
1669*ec779b8eSAndroid Build Coastguard Worker if (type == HDR_DYNAMIC_METADATA_TYPE_SMPTE_2094_40) {
1670*ec779b8eSAndroid Build Coastguard Worker msg->setBuffer(KEY_HDR10_PLUS_INFO, data);
1671*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName(typeKey.c_str()));
1672*ec779b8eSAndroid Build Coastguard Worker msg->removeEntryAt(msg->findEntryByName(dataKey.c_str()));
1673*ec779b8eSAndroid Build Coastguard Worker }
1674*ec779b8eSAndroid Build Coastguard Worker }
1675*ec779b8eSAndroid Build Coastguard Worker }
1676*ec779b8eSAndroid Build Coastguard Worker
1677*ec779b8eSAndroid Build Coastguard Worker ALOGV("converted to SDK values as %s", msg->debugString().c_str());
1678*ec779b8eSAndroid Build Coastguard Worker return msg;
1679*ec779b8eSAndroid Build Coastguard Worker }
1680*ec779b8eSAndroid Build Coastguard Worker
1681*ec779b8eSAndroid Build Coastguard Worker /// converts an AMessage value to a ParamUpdater value
convert(const AMessage::ItemData & from,ReflectedParamUpdater::Value * to)1682*ec779b8eSAndroid Build Coastguard Worker static void convert(const AMessage::ItemData &from, ReflectedParamUpdater::Value *to) {
1683*ec779b8eSAndroid Build Coastguard Worker int32_t int32Value;
1684*ec779b8eSAndroid Build Coastguard Worker int64_t int64Value;
1685*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> bufValue;
1686*ec779b8eSAndroid Build Coastguard Worker AString strValue;
1687*ec779b8eSAndroid Build Coastguard Worker float floatValue;
1688*ec779b8eSAndroid Build Coastguard Worker double doubleValue;
1689*ec779b8eSAndroid Build Coastguard Worker
1690*ec779b8eSAndroid Build Coastguard Worker if (from.find(&int32Value)) {
1691*ec779b8eSAndroid Build Coastguard Worker to->set(int32Value);
1692*ec779b8eSAndroid Build Coastguard Worker } else if (from.find(&int64Value)) {
1693*ec779b8eSAndroid Build Coastguard Worker to->set(int64Value);
1694*ec779b8eSAndroid Build Coastguard Worker } else if (from.find(&bufValue)) {
1695*ec779b8eSAndroid Build Coastguard Worker to->set(bufValue);
1696*ec779b8eSAndroid Build Coastguard Worker } else if (from.find(&strValue)) {
1697*ec779b8eSAndroid Build Coastguard Worker to->set(strValue);
1698*ec779b8eSAndroid Build Coastguard Worker } else if (from.find(&floatValue)) {
1699*ec779b8eSAndroid Build Coastguard Worker to->set(C2Value(floatValue));
1700*ec779b8eSAndroid Build Coastguard Worker } else if (from.find(&doubleValue)) {
1701*ec779b8eSAndroid Build Coastguard Worker // convert double to float
1702*ec779b8eSAndroid Build Coastguard Worker to->set(C2Value((float)doubleValue));
1703*ec779b8eSAndroid Build Coastguard Worker }
1704*ec779b8eSAndroid Build Coastguard Worker // ignore all other AMessage types
1705*ec779b8eSAndroid Build Coastguard Worker }
1706*ec779b8eSAndroid Build Coastguard Worker
1707*ec779b8eSAndroid Build Coastguard Worker /// relaxes Codec 2.0 specific value types to SDK types (mainly removes signedness and counterness
1708*ec779b8eSAndroid Build Coastguard Worker /// from 32/64-bit values.)
relaxValues(ReflectedParamUpdater::Value & item)1709*ec779b8eSAndroid Build Coastguard Worker static void relaxValues(ReflectedParamUpdater::Value &item) {
1710*ec779b8eSAndroid Build Coastguard Worker C2Value c2Value;
1711*ec779b8eSAndroid Build Coastguard Worker int32_t int32Value;
1712*ec779b8eSAndroid Build Coastguard Worker int64_t int64Value;
1713*ec779b8eSAndroid Build Coastguard Worker (void)item.find(&c2Value);
1714*ec779b8eSAndroid Build Coastguard Worker if (c2Value.get(&int32Value) || c2Value.get((uint32_t*)&int32Value)
1715*ec779b8eSAndroid Build Coastguard Worker || c2Value.get((c2_cntr32_t*)&int32Value)) {
1716*ec779b8eSAndroid Build Coastguard Worker item.set(int32Value);
1717*ec779b8eSAndroid Build Coastguard Worker } else if (c2Value.get(&int64Value)
1718*ec779b8eSAndroid Build Coastguard Worker || c2Value.get((uint64_t*)&int64Value)
1719*ec779b8eSAndroid Build Coastguard Worker || c2Value.get((c2_cntr64_t*)&int64Value)) {
1720*ec779b8eSAndroid Build Coastguard Worker item.set(int64Value);
1721*ec779b8eSAndroid Build Coastguard Worker }
1722*ec779b8eSAndroid Build Coastguard Worker }
1723*ec779b8eSAndroid Build Coastguard Worker
getReflectedFormat(const sp<AMessage> & params_,Domain configDomain) const1724*ec779b8eSAndroid Build Coastguard Worker ReflectedParamUpdater::Dict CCodecConfig::getReflectedFormat(
1725*ec779b8eSAndroid Build Coastguard Worker const sp<AMessage> ¶ms_, Domain configDomain) const {
1726*ec779b8eSAndroid Build Coastguard Worker // create a modifiable copy of params
1727*ec779b8eSAndroid Build Coastguard Worker sp<AMessage> params = params_->dup();
1728*ec779b8eSAndroid Build Coastguard Worker ALOGV("filtering with config domain %x", configDomain);
1729*ec779b8eSAndroid Build Coastguard Worker
1730*ec779b8eSAndroid Build Coastguard Worker // convert some macro parameters to Codec 2.0 specific expressions
1731*ec779b8eSAndroid Build Coastguard Worker
1732*ec779b8eSAndroid Build Coastguard Worker { // make i-frame-interval frame based
1733*ec779b8eSAndroid Build Coastguard Worker float iFrameInterval;
1734*ec779b8eSAndroid Build Coastguard Worker if (params->findAsFloat(KEY_I_FRAME_INTERVAL, &iFrameInterval)) {
1735*ec779b8eSAndroid Build Coastguard Worker float frameRate;
1736*ec779b8eSAndroid Build Coastguard Worker if (params->findAsFloat(KEY_FRAME_RATE, &frameRate)) {
1737*ec779b8eSAndroid Build Coastguard Worker params->setInt32("i-frame-period",
1738*ec779b8eSAndroid Build Coastguard Worker (frameRate <= 0 || iFrameInterval < 0)
1739*ec779b8eSAndroid Build Coastguard Worker ? -1 /* no sync frames */
1740*ec779b8eSAndroid Build Coastguard Worker : (int32_t)c2_min(iFrameInterval * frameRate + 0.5,
1741*ec779b8eSAndroid Build Coastguard Worker (float)INT32_MAX));
1742*ec779b8eSAndroid Build Coastguard Worker }
1743*ec779b8eSAndroid Build Coastguard Worker }
1744*ec779b8eSAndroid Build Coastguard Worker }
1745*ec779b8eSAndroid Build Coastguard Worker
1746*ec779b8eSAndroid Build Coastguard Worker if (mDomain == (IS_VIDEO | IS_ENCODER)) {
1747*ec779b8eSAndroid Build Coastguard Worker // convert capture-rate into input-time-stretch
1748*ec779b8eSAndroid Build Coastguard Worker float frameRate, captureRate;
1749*ec779b8eSAndroid Build Coastguard Worker if (params->findAsFloat(KEY_FRAME_RATE, &frameRate)) {
1750*ec779b8eSAndroid Build Coastguard Worker if (!params->findAsFloat("time-lapse-fps", &captureRate)
1751*ec779b8eSAndroid Build Coastguard Worker && !params->findAsFloat(KEY_CAPTURE_RATE, &captureRate)) {
1752*ec779b8eSAndroid Build Coastguard Worker captureRate = frameRate;
1753*ec779b8eSAndroid Build Coastguard Worker }
1754*ec779b8eSAndroid Build Coastguard Worker if (captureRate > 0 && frameRate > 0) {
1755*ec779b8eSAndroid Build Coastguard Worker params->setFloat(C2_PARAMKEY_INPUT_TIME_STRETCH, captureRate / frameRate);
1756*ec779b8eSAndroid Build Coastguard Worker }
1757*ec779b8eSAndroid Build Coastguard Worker }
1758*ec779b8eSAndroid Build Coastguard Worker
1759*ec779b8eSAndroid Build Coastguard Worker // add HDR format for video encoding
1760*ec779b8eSAndroid Build Coastguard Worker if (configDomain == IS_CONFIG) {
1761*ec779b8eSAndroid Build Coastguard Worker // don't assume here that transfer is set for HDR, only require it for HLG
1762*ec779b8eSAndroid Build Coastguard Worker int transfer = 0;
1763*ec779b8eSAndroid Build Coastguard Worker params->findInt32(KEY_COLOR_TRANSFER, &transfer);
1764*ec779b8eSAndroid Build Coastguard Worker
1765*ec779b8eSAndroid Build Coastguard Worker int profile;
1766*ec779b8eSAndroid Build Coastguard Worker if (params->findInt32(KEY_PROFILE, &profile)) {
1767*ec779b8eSAndroid Build Coastguard Worker std::shared_ptr<C2Mapper::ProfileLevelMapper> mapper =
1768*ec779b8eSAndroid Build Coastguard Worker C2Mapper::GetProfileLevelMapper(mCodingMediaType);
1769*ec779b8eSAndroid Build Coastguard Worker C2Config::hdr_format_t c2 = C2Config::hdr_format_t::UNKNOWN;
1770*ec779b8eSAndroid Build Coastguard Worker if (mapper && mapper->mapHdrFormat(profile, &c2)) {
1771*ec779b8eSAndroid Build Coastguard Worker if (c2 == C2Config::hdr_format_t::HLG &&
1772*ec779b8eSAndroid Build Coastguard Worker transfer != COLOR_TRANSFER_HLG) {
1773*ec779b8eSAndroid Build Coastguard Worker c2 = C2Config::hdr_format_t::UNKNOWN;
1774*ec779b8eSAndroid Build Coastguard Worker }
1775*ec779b8eSAndroid Build Coastguard Worker params->setInt32(C2_PARAMKEY_HDR_FORMAT, c2);
1776*ec779b8eSAndroid Build Coastguard Worker }
1777*ec779b8eSAndroid Build Coastguard Worker }
1778*ec779b8eSAndroid Build Coastguard Worker }
1779*ec779b8eSAndroid Build Coastguard Worker }
1780*ec779b8eSAndroid Build Coastguard Worker
1781*ec779b8eSAndroid Build Coastguard Worker { // reflect temporal layering into a binary blob
1782*ec779b8eSAndroid Build Coastguard Worker AString schema;
1783*ec779b8eSAndroid Build Coastguard Worker if (params->findString(KEY_TEMPORAL_LAYERING, &schema)) {
1784*ec779b8eSAndroid Build Coastguard Worker unsigned int numLayers = 0;
1785*ec779b8eSAndroid Build Coastguard Worker unsigned int numBLayers = 0;
1786*ec779b8eSAndroid Build Coastguard Worker int tags;
1787*ec779b8eSAndroid Build Coastguard Worker char dummy;
1788*ec779b8eSAndroid Build Coastguard Worker std::unique_ptr<C2StreamTemporalLayeringTuning::output> layering;
1789*ec779b8eSAndroid Build Coastguard Worker if (sscanf(schema.c_str(), "webrtc.vp8.%u-layer%c", &numLayers, &dummy) == 1
1790*ec779b8eSAndroid Build Coastguard Worker && numLayers > 0) {
1791*ec779b8eSAndroid Build Coastguard Worker switch (numLayers) {
1792*ec779b8eSAndroid Build Coastguard Worker case 1:
1793*ec779b8eSAndroid Build Coastguard Worker layering = C2StreamTemporalLayeringTuning::output::AllocUnique(
1794*ec779b8eSAndroid Build Coastguard Worker {}, 0u, 1u, 0u);
1795*ec779b8eSAndroid Build Coastguard Worker break;
1796*ec779b8eSAndroid Build Coastguard Worker case 2:
1797*ec779b8eSAndroid Build Coastguard Worker layering = C2StreamTemporalLayeringTuning::output::AllocUnique(
1798*ec779b8eSAndroid Build Coastguard Worker { .6f }, 0u, 2u, 0u);
1799*ec779b8eSAndroid Build Coastguard Worker break;
1800*ec779b8eSAndroid Build Coastguard Worker case 3:
1801*ec779b8eSAndroid Build Coastguard Worker layering = C2StreamTemporalLayeringTuning::output::AllocUnique(
1802*ec779b8eSAndroid Build Coastguard Worker { .4f, .6f }, 0u, 3u, 0u);
1803*ec779b8eSAndroid Build Coastguard Worker break;
1804*ec779b8eSAndroid Build Coastguard Worker default:
1805*ec779b8eSAndroid Build Coastguard Worker layering = C2StreamTemporalLayeringTuning::output::AllocUnique(
1806*ec779b8eSAndroid Build Coastguard Worker { .25f, .4f, .6f }, 0u, 4u, 0u);
1807*ec779b8eSAndroid Build Coastguard Worker break;
1808*ec779b8eSAndroid Build Coastguard Worker }
1809*ec779b8eSAndroid Build Coastguard Worker } else if ((tags = sscanf(schema.c_str(), "android.generic.%u%c%u%c",
1810*ec779b8eSAndroid Build Coastguard Worker &numLayers, &dummy, &numBLayers, &dummy))
1811*ec779b8eSAndroid Build Coastguard Worker && (tags == 1 || (tags == 3 && dummy == '+'))
1812*ec779b8eSAndroid Build Coastguard Worker && numLayers > 0 && numLayers < UINT32_MAX - numBLayers) {
1813*ec779b8eSAndroid Build Coastguard Worker layering = C2StreamTemporalLayeringTuning::output::AllocUnique(
1814*ec779b8eSAndroid Build Coastguard Worker {}, 0u, numLayers + numBLayers, numBLayers);
1815*ec779b8eSAndroid Build Coastguard Worker } else {
1816*ec779b8eSAndroid Build Coastguard Worker ALOGD("Ignoring unsupported ts-schema [%s]", schema.c_str());
1817*ec779b8eSAndroid Build Coastguard Worker }
1818*ec779b8eSAndroid Build Coastguard Worker if (layering) {
1819*ec779b8eSAndroid Build Coastguard Worker params->setBuffer(C2_PARAMKEY_TEMPORAL_LAYERING,
1820*ec779b8eSAndroid Build Coastguard Worker ABuffer::CreateAsCopy(layering.get(), layering->size()));
1821*ec779b8eSAndroid Build Coastguard Worker }
1822*ec779b8eSAndroid Build Coastguard Worker }
1823*ec779b8eSAndroid Build Coastguard Worker }
1824*ec779b8eSAndroid Build Coastguard Worker
1825*ec779b8eSAndroid Build Coastguard Worker { // convert from MediaFormat rect to Codec 2.0 rect
1826*ec779b8eSAndroid Build Coastguard Worker int32_t offset;
1827*ec779b8eSAndroid Build Coastguard Worker int32_t end;
1828*ec779b8eSAndroid Build Coastguard Worker AMessage::ItemData item;
1829*ec779b8eSAndroid Build Coastguard Worker if (params->findInt32("crop-left", &offset) && params->findInt32("crop-right", &end)
1830*ec779b8eSAndroid Build Coastguard Worker && offset >= 0 && end >= offset - 1) {
1831*ec779b8eSAndroid Build Coastguard Worker size_t ix = params->findEntryByName("crop-right");
1832*ec779b8eSAndroid Build Coastguard Worker params->setEntryNameAt(ix, "crop-width");
1833*ec779b8eSAndroid Build Coastguard Worker item.set(end - offset + 1);
1834*ec779b8eSAndroid Build Coastguard Worker params->setEntryAt(ix, item);
1835*ec779b8eSAndroid Build Coastguard Worker }
1836*ec779b8eSAndroid Build Coastguard Worker if (params->findInt32("crop-top", &offset) && params->findInt32("crop-bottom", &end)
1837*ec779b8eSAndroid Build Coastguard Worker && offset >= 0 && end >= offset - 1) {
1838*ec779b8eSAndroid Build Coastguard Worker size_t ix = params->findEntryByName("crop-bottom");
1839*ec779b8eSAndroid Build Coastguard Worker params->setEntryNameAt(ix, "crop-height");
1840*ec779b8eSAndroid Build Coastguard Worker item.set(end - offset + 1);
1841*ec779b8eSAndroid Build Coastguard Worker params->setEntryAt(ix, item);
1842*ec779b8eSAndroid Build Coastguard Worker }
1843*ec779b8eSAndroid Build Coastguard Worker }
1844*ec779b8eSAndroid Build Coastguard Worker
1845*ec779b8eSAndroid Build Coastguard Worker { // convert color info
1846*ec779b8eSAndroid Build Coastguard Worker int32_t standard;
1847*ec779b8eSAndroid Build Coastguard Worker if (params->findInt32(KEY_COLOR_STANDARD, &standard)) {
1848*ec779b8eSAndroid Build Coastguard Worker C2Color::primaries_t primaries;
1849*ec779b8eSAndroid Build Coastguard Worker C2Color::matrix_t matrix;
1850*ec779b8eSAndroid Build Coastguard Worker
1851*ec779b8eSAndroid Build Coastguard Worker if (C2Mapper::map(standard, &primaries, &matrix)) {
1852*ec779b8eSAndroid Build Coastguard Worker params->setInt32("color-primaries", primaries);
1853*ec779b8eSAndroid Build Coastguard Worker params->setInt32("color-matrix", matrix);
1854*ec779b8eSAndroid Build Coastguard Worker }
1855*ec779b8eSAndroid Build Coastguard Worker }
1856*ec779b8eSAndroid Build Coastguard Worker
1857*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> hdrMeta;
1858*ec779b8eSAndroid Build Coastguard Worker if (params->findBuffer(KEY_HDR_STATIC_INFO, &hdrMeta)
1859*ec779b8eSAndroid Build Coastguard Worker && hdrMeta->size() == sizeof(HDRStaticInfo)) {
1860*ec779b8eSAndroid Build Coastguard Worker HDRStaticInfo *meta = (HDRStaticInfo*)hdrMeta->data();
1861*ec779b8eSAndroid Build Coastguard Worker if (meta->mID == meta->kType1) {
1862*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.red.x", meta->sType1.mR.x * 0.00002);
1863*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.red.y", meta->sType1.mR.y * 0.00002);
1864*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.green.x", meta->sType1.mG.x * 0.00002);
1865*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.green.y", meta->sType1.mG.y * 0.00002);
1866*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.blue.x", meta->sType1.mB.x * 0.00002);
1867*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.blue.y", meta->sType1.mB.y * 0.00002);
1868*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.white.x", meta->sType1.mW.x * 0.00002);
1869*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.white.y", meta->sType1.mW.y * 0.00002);
1870*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.max-luminance", meta->sType1.mMaxDisplayLuminance);
1871*ec779b8eSAndroid Build Coastguard Worker params->setFloat("smpte2086.min-luminance", meta->sType1.mMinDisplayLuminance * 0.0001);
1872*ec779b8eSAndroid Build Coastguard Worker params->setFloat("cta861.max-cll", meta->sType1.mMaxContentLightLevel);
1873*ec779b8eSAndroid Build Coastguard Worker params->setFloat("cta861.max-fall", meta->sType1.mMaxFrameAverageLightLevel);
1874*ec779b8eSAndroid Build Coastguard Worker }
1875*ec779b8eSAndroid Build Coastguard Worker }
1876*ec779b8eSAndroid Build Coastguard Worker
1877*ec779b8eSAndroid Build Coastguard Worker sp<ABuffer> hdrDynamicInfo;
1878*ec779b8eSAndroid Build Coastguard Worker if (params->findBuffer(KEY_HDR10_PLUS_INFO, &hdrDynamicInfo)) {
1879*ec779b8eSAndroid Build Coastguard Worker for (const std::string &prefix : { C2_PARAMKEY_INPUT_HDR_DYNAMIC_INFO,
1880*ec779b8eSAndroid Build Coastguard Worker C2_PARAMKEY_OUTPUT_HDR_DYNAMIC_INFO }) {
1881*ec779b8eSAndroid Build Coastguard Worker params->setInt32((prefix + ".type").c_str(),
1882*ec779b8eSAndroid Build Coastguard Worker HDR_DYNAMIC_METADATA_TYPE_SMPTE_2094_40);
1883*ec779b8eSAndroid Build Coastguard Worker params->setBuffer((prefix + ".data").c_str(), hdrDynamicInfo);
1884*ec779b8eSAndroid Build Coastguard Worker }
1885*ec779b8eSAndroid Build Coastguard Worker }
1886*ec779b8eSAndroid Build Coastguard Worker }
1887*ec779b8eSAndroid Build Coastguard Worker
1888*ec779b8eSAndroid Build Coastguard Worker if (android::media::codec::provider_->region_of_interest()
1889*ec779b8eSAndroid Build Coastguard Worker && android::media::codec::provider_->region_of_interest_support()) {
1890*ec779b8eSAndroid Build Coastguard Worker if (mDomain == (IS_VIDEO | IS_ENCODER)) {
1891*ec779b8eSAndroid Build Coastguard Worker AString qpOffsetRects;
1892*ec779b8eSAndroid Build Coastguard Worker if (params->findString(PARAMETER_KEY_QP_OFFSET_RECTS, &qpOffsetRects)) {
1893*ec779b8eSAndroid Build Coastguard Worker int width, height;
1894*ec779b8eSAndroid Build Coastguard Worker mInputFormat->findInt32("width", &width);
1895*ec779b8eSAndroid Build Coastguard Worker mInputFormat->findInt32("height", &height);
1896*ec779b8eSAndroid Build Coastguard Worker std::vector<C2QpOffsetRectStruct> c2QpOffsetRects;
1897*ec779b8eSAndroid Build Coastguard Worker char mutableStrQpOffsetRects[strlen(qpOffsetRects.c_str()) + 1];
1898*ec779b8eSAndroid Build Coastguard Worker strcpy(mutableStrQpOffsetRects, qpOffsetRects.c_str());
1899*ec779b8eSAndroid Build Coastguard Worker char* savePtr;
1900*ec779b8eSAndroid Build Coastguard Worker char* box = strtok_r(mutableStrQpOffsetRects, ";", &savePtr);
1901*ec779b8eSAndroid Build Coastguard Worker while (box != nullptr) {
1902*ec779b8eSAndroid Build Coastguard Worker int top, left, bottom, right, offset;
1903*ec779b8eSAndroid Build Coastguard Worker if (sscanf(box, "%d,%d-%d,%d=%d", &top, &left, &bottom, &right, &offset) == 5) {
1904*ec779b8eSAndroid Build Coastguard Worker left = c2_max(0, left);
1905*ec779b8eSAndroid Build Coastguard Worker top = c2_max(0, top);
1906*ec779b8eSAndroid Build Coastguard Worker right = c2_min(right, width);
1907*ec779b8eSAndroid Build Coastguard Worker bottom = c2_min(bottom, height);
1908*ec779b8eSAndroid Build Coastguard Worker if (right > left && bottom > top) {
1909*ec779b8eSAndroid Build Coastguard Worker C2Rect rect(right - left, bottom - top);
1910*ec779b8eSAndroid Build Coastguard Worker rect = rect.at(left, top);
1911*ec779b8eSAndroid Build Coastguard Worker c2QpOffsetRects.push_back(C2QpOffsetRectStruct(rect, offset));
1912*ec779b8eSAndroid Build Coastguard Worker } else {
1913*ec779b8eSAndroid Build Coastguard Worker ALOGE("Rects configuration %s is not valid.", box);
1914*ec779b8eSAndroid Build Coastguard Worker }
1915*ec779b8eSAndroid Build Coastguard Worker } else {
1916*ec779b8eSAndroid Build Coastguard Worker ALOGE("Rects configuration %s doesn't follow the string pattern.", box);
1917*ec779b8eSAndroid Build Coastguard Worker }
1918*ec779b8eSAndroid Build Coastguard Worker box = strtok_r(nullptr, ";", &savePtr);
1919*ec779b8eSAndroid Build Coastguard Worker }
1920*ec779b8eSAndroid Build Coastguard Worker if (c2QpOffsetRects.size() != 0) {
1921*ec779b8eSAndroid Build Coastguard Worker const std::unique_ptr<C2StreamQpOffsetRects::output> regions =
1922*ec779b8eSAndroid Build Coastguard Worker C2StreamQpOffsetRects::output::AllocUnique(
1923*ec779b8eSAndroid Build Coastguard Worker c2QpOffsetRects.size(), 0u, c2QpOffsetRects);
1924*ec779b8eSAndroid Build Coastguard Worker params->setBuffer(C2_PARAMKEY_QP_OFFSET_RECTS,
1925*ec779b8eSAndroid Build Coastguard Worker ABuffer::CreateAsCopy(regions.get(), regions->size()));
1926*ec779b8eSAndroid Build Coastguard Worker }
1927*ec779b8eSAndroid Build Coastguard Worker }
1928*ec779b8eSAndroid Build Coastguard Worker }
1929*ec779b8eSAndroid Build Coastguard Worker }
1930*ec779b8eSAndroid Build Coastguard Worker
1931*ec779b8eSAndroid Build Coastguard Worker // this is to verify that we set proper signedness for standard parameters
1932*ec779b8eSAndroid Build Coastguard Worker bool beVeryStrict = property_get_bool("debug.stagefright.ccodec_strict_type", false);
1933*ec779b8eSAndroid Build Coastguard Worker // this is to allow vendors to use the wrong signedness for standard parameters
1934*ec779b8eSAndroid Build Coastguard Worker bool beVeryLax = property_get_bool("debug.stagefright.ccodec_lax_type", false);
1935*ec779b8eSAndroid Build Coastguard Worker
1936*ec779b8eSAndroid Build Coastguard Worker ReflectedParamUpdater::Dict filtered;
1937*ec779b8eSAndroid Build Coastguard Worker for (size_t ix = 0; ix < params->countEntries(); ++ix) {
1938*ec779b8eSAndroid Build Coastguard Worker AMessage::Type type;
1939*ec779b8eSAndroid Build Coastguard Worker AString name = params->getEntryNameAt(ix, &type);
1940*ec779b8eSAndroid Build Coastguard Worker AMessage::ItemData msgItem = params->getEntryAt(ix);
1941*ec779b8eSAndroid Build Coastguard Worker ReflectedParamUpdater::Value item;
1942*ec779b8eSAndroid Build Coastguard Worker convert(msgItem, &item); // convert item to param updater item
1943*ec779b8eSAndroid Build Coastguard Worker
1944*ec779b8eSAndroid Build Coastguard Worker if (name.startsWith("vendor.")) {
1945*ec779b8eSAndroid Build Coastguard Worker // vendor params pass through as is
1946*ec779b8eSAndroid Build Coastguard Worker filtered.emplace(name.c_str(), item);
1947*ec779b8eSAndroid Build Coastguard Worker continue;
1948*ec779b8eSAndroid Build Coastguard Worker }
1949*ec779b8eSAndroid Build Coastguard Worker // standard parameters may get modified, filtered or duplicated
1950*ec779b8eSAndroid Build Coastguard Worker for (const ConfigMapper &cm : mStandardParams->getConfigMappersForSdkKey(name.c_str())) {
1951*ec779b8eSAndroid Build Coastguard Worker // note: we ignore port domain for configuration
1952*ec779b8eSAndroid Build Coastguard Worker if ((cm.domain() & configDomain)
1953*ec779b8eSAndroid Build Coastguard Worker // component domain + kind (these must match)
1954*ec779b8eSAndroid Build Coastguard Worker && (cm.domain() & mDomain) == mDomain) {
1955*ec779b8eSAndroid Build Coastguard Worker // map arithmetic values, pass through string or buffer
1956*ec779b8eSAndroid Build Coastguard Worker switch (type) {
1957*ec779b8eSAndroid Build Coastguard Worker case AMessage::kTypeBuffer:
1958*ec779b8eSAndroid Build Coastguard Worker case AMessage::kTypeString:
1959*ec779b8eSAndroid Build Coastguard Worker break;
1960*ec779b8eSAndroid Build Coastguard Worker case AMessage::kTypeInt32:
1961*ec779b8eSAndroid Build Coastguard Worker case AMessage::kTypeInt64:
1962*ec779b8eSAndroid Build Coastguard Worker case AMessage::kTypeFloat:
1963*ec779b8eSAndroid Build Coastguard Worker case AMessage::kTypeDouble:
1964*ec779b8eSAndroid Build Coastguard Worker // for now only map settings with mappers as we are not creating
1965*ec779b8eSAndroid Build Coastguard Worker // signed <=> unsigned mappers
1966*ec779b8eSAndroid Build Coastguard Worker // TODO: be precise about signed unsigned
1967*ec779b8eSAndroid Build Coastguard Worker if (beVeryStrict || cm.mapper()) {
1968*ec779b8eSAndroid Build Coastguard Worker item.set(cm.mapFromMessage(params->getEntryAt(ix)));
1969*ec779b8eSAndroid Build Coastguard Worker // also allow to relax type strictness
1970*ec779b8eSAndroid Build Coastguard Worker if (beVeryLax) {
1971*ec779b8eSAndroid Build Coastguard Worker relaxValues(item);
1972*ec779b8eSAndroid Build Coastguard Worker }
1973*ec779b8eSAndroid Build Coastguard Worker }
1974*ec779b8eSAndroid Build Coastguard Worker break;
1975*ec779b8eSAndroid Build Coastguard Worker default:
1976*ec779b8eSAndroid Build Coastguard Worker continue;
1977*ec779b8eSAndroid Build Coastguard Worker }
1978*ec779b8eSAndroid Build Coastguard Worker filtered.emplace(cm.path(), item);
1979*ec779b8eSAndroid Build Coastguard Worker }
1980*ec779b8eSAndroid Build Coastguard Worker }
1981*ec779b8eSAndroid Build Coastguard Worker }
1982*ec779b8eSAndroid Build Coastguard Worker ALOGV("filter src msg %s", params->debugString(4).c_str());
1983*ec779b8eSAndroid Build Coastguard Worker ALOGV("filter dst params %s", filtered.debugString(4).c_str());
1984*ec779b8eSAndroid Build Coastguard Worker return filtered;
1985*ec779b8eSAndroid Build Coastguard Worker }
1986*ec779b8eSAndroid Build Coastguard Worker
getConfigUpdateFromSdkParams(std::shared_ptr<Codec2Client::Configurable> configurable,const sp<AMessage> & sdkParams,Domain configDomain,c2_blocking_t blocking,std::vector<std::unique_ptr<C2Param>> * configUpdate) const1987*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::getConfigUpdateFromSdkParams(
1988*ec779b8eSAndroid Build Coastguard Worker std::shared_ptr<Codec2Client::Configurable> configurable,
1989*ec779b8eSAndroid Build Coastguard Worker const sp<AMessage> &sdkParams, Domain configDomain,
1990*ec779b8eSAndroid Build Coastguard Worker c2_blocking_t blocking,
1991*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2Param>> *configUpdate) const {
1992*ec779b8eSAndroid Build Coastguard Worker // update the mappers if we know something more of this format.
1993*ec779b8eSAndroid Build Coastguard Worker // AV1 10b or 8b encoding request.
1994*ec779b8eSAndroid Build Coastguard Worker AString mime;
1995*ec779b8eSAndroid Build Coastguard Worker int32_t requestedSdkProfile = -1;
1996*ec779b8eSAndroid Build Coastguard Worker if ((mDomain == (IS_VIDEO | IS_ENCODER)) &&
1997*ec779b8eSAndroid Build Coastguard Worker sdkParams->findString(KEY_MIME, &mime) &&
1998*ec779b8eSAndroid Build Coastguard Worker mime == MIMETYPE_VIDEO_AV1) {
1999*ec779b8eSAndroid Build Coastguard Worker
2000*ec779b8eSAndroid Build Coastguard Worker sdkParams->findInt32(KEY_PROFILE, &requestedSdkProfile);
2001*ec779b8eSAndroid Build Coastguard Worker bool is10bAv1EncodeRequested = (requestedSdkProfile == AV1ProfileMain10);
2002*ec779b8eSAndroid Build Coastguard Worker
2003*ec779b8eSAndroid Build Coastguard Worker int32_t bitDepth = (is10bAv1EncodeRequested) ? 10 : 8;
2004*ec779b8eSAndroid Build Coastguard Worker // we always initilze with an 8b mapper. Update this only if needed.
2005*ec779b8eSAndroid Build Coastguard Worker if (bitDepth != 8) {
2006*ec779b8eSAndroid Build Coastguard Worker std::shared_ptr<C2Mapper::ProfileLevelMapper> mapper =
2007*ec779b8eSAndroid Build Coastguard Worker C2Mapper::GetBitDepthProfileLevelMapper(mCodingMediaType, bitDepth);
2008*ec779b8eSAndroid Build Coastguard Worker mStandardParams->updateConfigMappersForKey(StandardParams::SdkKey(KEY_PROFILE),
2009*ec779b8eSAndroid Build Coastguard Worker {
2010*ec779b8eSAndroid Build Coastguard Worker ConfigMapper(KEY_PROFILE, C2_PARAMKEY_PROFILE_LEVEL, "profile")
2011*ec779b8eSAndroid Build Coastguard Worker .limitTo(Domain::CODED)
2012*ec779b8eSAndroid Build Coastguard Worker .withMappers([mapper](C2Value v) -> C2Value {
2013*ec779b8eSAndroid Build Coastguard Worker C2Config::profile_t c2 = PROFILE_UNUSED;
2014*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
2015*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get(&sdk) && mapper->mapProfile(sdk, &c2)) {
2016*ec779b8eSAndroid Build Coastguard Worker return c2;
2017*ec779b8eSAndroid Build Coastguard Worker }
2018*ec779b8eSAndroid Build Coastguard Worker return PROFILE_UNUSED;
2019*ec779b8eSAndroid Build Coastguard Worker }, [mapper](C2Value v) -> C2Value {
2020*ec779b8eSAndroid Build Coastguard Worker C2Config::profile_t c2;
2021*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
2022*ec779b8eSAndroid Build Coastguard Worker using C2ValueType =
2023*ec779b8eSAndroid Build Coastguard Worker typename _c2_reduce_enum_to_underlying_type<decltype(c2)>::type;
2024*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get((C2ValueType*)&c2) && mapper->mapProfile(c2, &sdk)) {
2025*ec779b8eSAndroid Build Coastguard Worker return sdk;
2026*ec779b8eSAndroid Build Coastguard Worker }
2027*ec779b8eSAndroid Build Coastguard Worker return C2Value();
2028*ec779b8eSAndroid Build Coastguard Worker })});
2029*ec779b8eSAndroid Build Coastguard Worker mStandardParams->updateConfigMappersForKey(StandardParams::SdkKey(KEY_LEVEL),
2030*ec779b8eSAndroid Build Coastguard Worker {
2031*ec779b8eSAndroid Build Coastguard Worker ConfigMapper(KEY_LEVEL, C2_PARAMKEY_PROFILE_LEVEL, "level")
2032*ec779b8eSAndroid Build Coastguard Worker .limitTo(Domain::CODED)
2033*ec779b8eSAndroid Build Coastguard Worker .withMappers([mapper](C2Value v) -> C2Value {
2034*ec779b8eSAndroid Build Coastguard Worker C2Config::level_t c2 = LEVEL_UNUSED;
2035*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
2036*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get(&sdk) && mapper->mapLevel(sdk, &c2)) {
2037*ec779b8eSAndroid Build Coastguard Worker return c2;
2038*ec779b8eSAndroid Build Coastguard Worker }
2039*ec779b8eSAndroid Build Coastguard Worker return LEVEL_UNUSED;
2040*ec779b8eSAndroid Build Coastguard Worker }, [mapper](C2Value v) -> C2Value {
2041*ec779b8eSAndroid Build Coastguard Worker C2Config::level_t c2;
2042*ec779b8eSAndroid Build Coastguard Worker int32_t sdk;
2043*ec779b8eSAndroid Build Coastguard Worker using C2ValueType =
2044*ec779b8eSAndroid Build Coastguard Worker typename _c2_reduce_enum_to_underlying_type<decltype(c2)>::type;
2045*ec779b8eSAndroid Build Coastguard Worker if (mapper && v.get((C2ValueType*)&c2) && mapper->mapLevel(c2, &sdk)) {
2046*ec779b8eSAndroid Build Coastguard Worker return sdk;
2047*ec779b8eSAndroid Build Coastguard Worker }
2048*ec779b8eSAndroid Build Coastguard Worker return C2Value();
2049*ec779b8eSAndroid Build Coastguard Worker })});
2050*ec779b8eSAndroid Build Coastguard Worker }
2051*ec779b8eSAndroid Build Coastguard Worker }
2052*ec779b8eSAndroid Build Coastguard Worker
2053*ec779b8eSAndroid Build Coastguard Worker ReflectedParamUpdater::Dict params = getReflectedFormat(sdkParams, configDomain);
2054*ec779b8eSAndroid Build Coastguard Worker
2055*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param::Index> indices;
2056*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->getParamIndicesFromMessage(params, &indices);
2057*ec779b8eSAndroid Build Coastguard Worker if (indices.empty()) {
2058*ec779b8eSAndroid Build Coastguard Worker ALOGD("no recognized params in: %s", params.debugString().c_str());
2059*ec779b8eSAndroid Build Coastguard Worker return OK;
2060*ec779b8eSAndroid Build Coastguard Worker }
2061*ec779b8eSAndroid Build Coastguard Worker
2062*ec779b8eSAndroid Build Coastguard Worker configUpdate->clear();
2063*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param::Index> supportedIndices;
2064*ec779b8eSAndroid Build Coastguard Worker for (C2Param::Index ix : indices) {
2065*ec779b8eSAndroid Build Coastguard Worker if (mSupportedIndices.count(ix)) {
2066*ec779b8eSAndroid Build Coastguard Worker supportedIndices.push_back(ix);
2067*ec779b8eSAndroid Build Coastguard Worker } else if (mLocalParams.count(ix)) {
2068*ec779b8eSAndroid Build Coastguard Worker // query local parameter here
2069*ec779b8eSAndroid Build Coastguard Worker auto it = mCurrentConfig.find(ix);
2070*ec779b8eSAndroid Build Coastguard Worker if (it != mCurrentConfig.end()) {
2071*ec779b8eSAndroid Build Coastguard Worker configUpdate->emplace_back(C2Param::Copy(*it->second));
2072*ec779b8eSAndroid Build Coastguard Worker }
2073*ec779b8eSAndroid Build Coastguard Worker }
2074*ec779b8eSAndroid Build Coastguard Worker }
2075*ec779b8eSAndroid Build Coastguard Worker
2076*ec779b8eSAndroid Build Coastguard Worker c2_status_t err = configurable->query({ }, supportedIndices, blocking, configUpdate);
2077*ec779b8eSAndroid Build Coastguard Worker if (err != C2_OK) {
2078*ec779b8eSAndroid Build Coastguard Worker ALOGD("query failed after returning %zu params => %s", configUpdate->size(), asString(err));
2079*ec779b8eSAndroid Build Coastguard Worker }
2080*ec779b8eSAndroid Build Coastguard Worker
2081*ec779b8eSAndroid Build Coastguard Worker if (configUpdate->size()) {
2082*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->updateParamsFromMessage(params, configUpdate);
2083*ec779b8eSAndroid Build Coastguard Worker }
2084*ec779b8eSAndroid Build Coastguard Worker return OK;
2085*ec779b8eSAndroid Build Coastguard Worker }
2086*ec779b8eSAndroid Build Coastguard Worker
setParameters(std::shared_ptr<Codec2Client::Configurable> configurable,std::vector<std::unique_ptr<C2Param>> & configUpdate,c2_blocking_t blocking)2087*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::setParameters(
2088*ec779b8eSAndroid Build Coastguard Worker std::shared_ptr<Codec2Client::Configurable> configurable,
2089*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2Param>> &configUpdate,
2090*ec779b8eSAndroid Build Coastguard Worker c2_blocking_t blocking) {
2091*ec779b8eSAndroid Build Coastguard Worker status_t result = OK;
2092*ec779b8eSAndroid Build Coastguard Worker if (configUpdate.empty()) {
2093*ec779b8eSAndroid Build Coastguard Worker return OK;
2094*ec779b8eSAndroid Build Coastguard Worker }
2095*ec779b8eSAndroid Build Coastguard Worker
2096*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param::Index> indices;
2097*ec779b8eSAndroid Build Coastguard Worker std::vector<C2Param *> paramVector;
2098*ec779b8eSAndroid Build Coastguard Worker for (const std::unique_ptr<C2Param> ¶m : configUpdate) {
2099*ec779b8eSAndroid Build Coastguard Worker if (mSupportedIndices.count(param->index())) {
2100*ec779b8eSAndroid Build Coastguard Worker // component parameter
2101*ec779b8eSAndroid Build Coastguard Worker paramVector.push_back(param.get());
2102*ec779b8eSAndroid Build Coastguard Worker indices.push_back(param->index());
2103*ec779b8eSAndroid Build Coastguard Worker } else if (mLocalParams.count(param->index())) {
2104*ec779b8eSAndroid Build Coastguard Worker // handle local parameter here
2105*ec779b8eSAndroid Build Coastguard Worker LocalParamValidator validator = mLocalParams.find(param->index())->second;
2106*ec779b8eSAndroid Build Coastguard Worker c2_status_t err = C2_OK;
2107*ec779b8eSAndroid Build Coastguard Worker std::unique_ptr<C2Param> copy = C2Param::Copy(*param);
2108*ec779b8eSAndroid Build Coastguard Worker if (validator) {
2109*ec779b8eSAndroid Build Coastguard Worker err = validator(copy);
2110*ec779b8eSAndroid Build Coastguard Worker }
2111*ec779b8eSAndroid Build Coastguard Worker if (err == C2_OK) {
2112*ec779b8eSAndroid Build Coastguard Worker ALOGV("updated local parameter value for %s",
2113*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->getParamName(param->index()).c_str());
2114*ec779b8eSAndroid Build Coastguard Worker
2115*ec779b8eSAndroid Build Coastguard Worker mCurrentConfig[param->index()] = std::move(copy);
2116*ec779b8eSAndroid Build Coastguard Worker } else {
2117*ec779b8eSAndroid Build Coastguard Worker ALOGD("failed to set parameter value for %s => %s",
2118*ec779b8eSAndroid Build Coastguard Worker mParamUpdater->getParamName(param->index()).c_str(), asString(err));
2119*ec779b8eSAndroid Build Coastguard Worker result = BAD_VALUE;
2120*ec779b8eSAndroid Build Coastguard Worker }
2121*ec779b8eSAndroid Build Coastguard Worker }
2122*ec779b8eSAndroid Build Coastguard Worker }
2123*ec779b8eSAndroid Build Coastguard Worker // update subscribed param indices
2124*ec779b8eSAndroid Build Coastguard Worker subscribeToConfigUpdate(configurable, indices, blocking);
2125*ec779b8eSAndroid Build Coastguard Worker
2126*ec779b8eSAndroid Build Coastguard Worker std::vector<std::unique_ptr<C2SettingResult>> failures;
2127*ec779b8eSAndroid Build Coastguard Worker c2_status_t err = configurable->config(paramVector, blocking, &failures);
2128*ec779b8eSAndroid Build Coastguard Worker if (err != C2_OK) {
2129*ec779b8eSAndroid Build Coastguard Worker ALOGD("config failed => %s", asString(err));
2130*ec779b8eSAndroid Build Coastguard Worker // This is non-fatal.
2131*ec779b8eSAndroid Build Coastguard Worker }
2132*ec779b8eSAndroid Build Coastguard Worker for (const std::unique_ptr<C2SettingResult> &failure : failures) {
2133*ec779b8eSAndroid Build Coastguard Worker switch (failure->failure) {
2134*ec779b8eSAndroid Build Coastguard Worker case C2SettingResult::BAD_VALUE:
2135*ec779b8eSAndroid Build Coastguard Worker ALOGD("Bad parameter value");
2136*ec779b8eSAndroid Build Coastguard Worker result = BAD_VALUE;
2137*ec779b8eSAndroid Build Coastguard Worker break;
2138*ec779b8eSAndroid Build Coastguard Worker default:
2139*ec779b8eSAndroid Build Coastguard Worker ALOGV("failure = %d", int(failure->failure));
2140*ec779b8eSAndroid Build Coastguard Worker break;
2141*ec779b8eSAndroid Build Coastguard Worker }
2142*ec779b8eSAndroid Build Coastguard Worker }
2143*ec779b8eSAndroid Build Coastguard Worker
2144*ec779b8eSAndroid Build Coastguard Worker // Re-query parameter values in case config could not update them and update the current
2145*ec779b8eSAndroid Build Coastguard Worker // configuration.
2146*ec779b8eSAndroid Build Coastguard Worker configUpdate.clear();
2147*ec779b8eSAndroid Build Coastguard Worker err = configurable->query({}, indices, blocking, &configUpdate);
2148*ec779b8eSAndroid Build Coastguard Worker if (err != C2_OK) {
2149*ec779b8eSAndroid Build Coastguard Worker ALOGD("query failed after returning %zu params => %s", configUpdate.size(), asString(err));
2150*ec779b8eSAndroid Build Coastguard Worker }
2151*ec779b8eSAndroid Build Coastguard Worker (void)updateConfiguration(configUpdate, ALL);
2152*ec779b8eSAndroid Build Coastguard Worker
2153*ec779b8eSAndroid Build Coastguard Worker // TODO: error value
2154*ec779b8eSAndroid Build Coastguard Worker return result;
2155*ec779b8eSAndroid Build Coastguard Worker }
2156*ec779b8eSAndroid Build Coastguard Worker
getConfigParameterValue(C2Param::Index index) const2157*ec779b8eSAndroid Build Coastguard Worker const C2Param *CCodecConfig::getConfigParameterValue(C2Param::Index index) const {
2158*ec779b8eSAndroid Build Coastguard Worker auto it = mCurrentConfig.find(index);
2159*ec779b8eSAndroid Build Coastguard Worker if (it == mCurrentConfig.end()) {
2160*ec779b8eSAndroid Build Coastguard Worker return nullptr;
2161*ec779b8eSAndroid Build Coastguard Worker } else {
2162*ec779b8eSAndroid Build Coastguard Worker return it->second.get();
2163*ec779b8eSAndroid Build Coastguard Worker }
2164*ec779b8eSAndroid Build Coastguard Worker }
2165*ec779b8eSAndroid Build Coastguard Worker
subscribeToAllVendorParams(const std::shared_ptr<Codec2Client::Configurable> & configurable,c2_blocking_t blocking)2166*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::subscribeToAllVendorParams(
2167*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable,
2168*ec779b8eSAndroid Build Coastguard Worker c2_blocking_t blocking) {
2169*ec779b8eSAndroid Build Coastguard Worker for (const auto &[path, desc] : mVendorParams) {
2170*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.insert(desc->index());
2171*ec779b8eSAndroid Build Coastguard Worker }
2172*ec779b8eSAndroid Build Coastguard Worker return subscribeToConfigUpdate(configurable, {}, blocking);
2173*ec779b8eSAndroid Build Coastguard Worker }
2174*ec779b8eSAndroid Build Coastguard Worker
querySupportedParameters(std::vector<std::string> * names)2175*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::querySupportedParameters(std::vector<std::string> *names) {
2176*ec779b8eSAndroid Build Coastguard Worker if (!names) {
2177*ec779b8eSAndroid Build Coastguard Worker return BAD_VALUE;
2178*ec779b8eSAndroid Build Coastguard Worker }
2179*ec779b8eSAndroid Build Coastguard Worker names->clear();
2180*ec779b8eSAndroid Build Coastguard Worker // TODO: expand to standard params
2181*ec779b8eSAndroid Build Coastguard Worker for (const auto &[key, desc] : mVendorParams) {
2182*ec779b8eSAndroid Build Coastguard Worker if (desc->isVisible()) {
2183*ec779b8eSAndroid Build Coastguard Worker names->push_back(key);
2184*ec779b8eSAndroid Build Coastguard Worker }
2185*ec779b8eSAndroid Build Coastguard Worker }
2186*ec779b8eSAndroid Build Coastguard Worker return OK;
2187*ec779b8eSAndroid Build Coastguard Worker }
2188*ec779b8eSAndroid Build Coastguard Worker
describe(const std::string & name,CodecParameterDescriptor * desc)2189*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::describe(const std::string &name, CodecParameterDescriptor *desc) {
2190*ec779b8eSAndroid Build Coastguard Worker if (!desc) {
2191*ec779b8eSAndroid Build Coastguard Worker return BAD_VALUE;
2192*ec779b8eSAndroid Build Coastguard Worker }
2193*ec779b8eSAndroid Build Coastguard Worker // TODO: expand to standard params
2194*ec779b8eSAndroid Build Coastguard Worker desc->name = name;
2195*ec779b8eSAndroid Build Coastguard Worker switch (mParamUpdater->getTypeForKey(name)) {
2196*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::INT32:
2197*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::UINT32:
2198*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::CNTR32:
2199*ec779b8eSAndroid Build Coastguard Worker desc->type = AMessage::kTypeInt32;
2200*ec779b8eSAndroid Build Coastguard Worker return OK;
2201*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::INT64:
2202*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::UINT64:
2203*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::CNTR64:
2204*ec779b8eSAndroid Build Coastguard Worker desc->type = AMessage::kTypeInt64;
2205*ec779b8eSAndroid Build Coastguard Worker return OK;
2206*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::FLOAT:
2207*ec779b8eSAndroid Build Coastguard Worker desc->type = AMessage::kTypeFloat;
2208*ec779b8eSAndroid Build Coastguard Worker return OK;
2209*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::STRING:
2210*ec779b8eSAndroid Build Coastguard Worker desc->type = AMessage::kTypeString;
2211*ec779b8eSAndroid Build Coastguard Worker return OK;
2212*ec779b8eSAndroid Build Coastguard Worker case C2FieldDescriptor::BLOB:
2213*ec779b8eSAndroid Build Coastguard Worker desc->type = AMessage::kTypeBuffer;
2214*ec779b8eSAndroid Build Coastguard Worker return OK;
2215*ec779b8eSAndroid Build Coastguard Worker default:
2216*ec779b8eSAndroid Build Coastguard Worker return NAME_NOT_FOUND;
2217*ec779b8eSAndroid Build Coastguard Worker }
2218*ec779b8eSAndroid Build Coastguard Worker }
2219*ec779b8eSAndroid Build Coastguard Worker
subscribeToVendorConfigUpdate(const std::shared_ptr<Codec2Client::Configurable> & configurable,const std::vector<std::string> & names,c2_blocking_t blocking)2220*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::subscribeToVendorConfigUpdate(
2221*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable,
2222*ec779b8eSAndroid Build Coastguard Worker const std::vector<std::string> &names,
2223*ec779b8eSAndroid Build Coastguard Worker c2_blocking_t blocking) {
2224*ec779b8eSAndroid Build Coastguard Worker for (const std::string &name : names) {
2225*ec779b8eSAndroid Build Coastguard Worker auto it = mVendorParams.find(name);
2226*ec779b8eSAndroid Build Coastguard Worker if (it == mVendorParams.end()) {
2227*ec779b8eSAndroid Build Coastguard Worker ALOGD("%s is not a recognized vendor parameter; ignored.", name.c_str());
2228*ec779b8eSAndroid Build Coastguard Worker continue;
2229*ec779b8eSAndroid Build Coastguard Worker }
2230*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.insert(it->second->index());
2231*ec779b8eSAndroid Build Coastguard Worker }
2232*ec779b8eSAndroid Build Coastguard Worker return subscribeToConfigUpdate(configurable, {}, blocking);
2233*ec779b8eSAndroid Build Coastguard Worker }
2234*ec779b8eSAndroid Build Coastguard Worker
unsubscribeFromVendorConfigUpdate(const std::shared_ptr<Codec2Client::Configurable> & configurable,const std::vector<std::string> & names,c2_blocking_t blocking)2235*ec779b8eSAndroid Build Coastguard Worker status_t CCodecConfig::unsubscribeFromVendorConfigUpdate(
2236*ec779b8eSAndroid Build Coastguard Worker const std::shared_ptr<Codec2Client::Configurable> &configurable,
2237*ec779b8eSAndroid Build Coastguard Worker const std::vector<std::string> &names,
2238*ec779b8eSAndroid Build Coastguard Worker c2_blocking_t blocking) {
2239*ec779b8eSAndroid Build Coastguard Worker for (const std::string &name : names) {
2240*ec779b8eSAndroid Build Coastguard Worker auto it = mVendorParams.find(name);
2241*ec779b8eSAndroid Build Coastguard Worker if (it == mVendorParams.end()) {
2242*ec779b8eSAndroid Build Coastguard Worker ALOGD("%s is not a recognized vendor parameter; ignored.", name.c_str());
2243*ec779b8eSAndroid Build Coastguard Worker continue;
2244*ec779b8eSAndroid Build Coastguard Worker }
2245*ec779b8eSAndroid Build Coastguard Worker mSubscribedIndices.erase(it->second->index());
2246*ec779b8eSAndroid Build Coastguard Worker }
2247*ec779b8eSAndroid Build Coastguard Worker return subscribeToConfigUpdate(configurable, {}, blocking);
2248*ec779b8eSAndroid Build Coastguard Worker }
2249*ec779b8eSAndroid Build Coastguard Worker
2250*ec779b8eSAndroid Build Coastguard Worker } // namespace android
2251