blob: 69b30f7d4dbb3fa9bae1b2267644edc832c71b02 [file] [log] [blame]
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001/*
2 * Copyright (C) 2015 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17//#define LOG_NDEBUG 0
18#define LOG_TAG "ACameraMetadata"
19
20#include "ACameraMetadata.h"
Jayant Chowdhary6c37df02024-03-11 20:12:14 +000021
22#include <camera_metadata_hidden.h>
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080023#include <utils/Vector.h>
Yin-Chia Yehc3603822016-01-18 22:11:19 -080024#include <system/graphics.h>
Colin Cross7e8d4ba2017-05-04 16:17:42 -070025#include <media/NdkImage.h>
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080026
27using namespace android;
28
Yin-Chia Yehf6e6a8e2021-04-08 11:49:42 -070029// Formats not listed in the public API, but still available to AImageReader
30// Enum value must match corresponding enum in ui/PublicFormat.h (which is not
31// available to VNDK)
32enum AIMAGE_PRIVATE_FORMATS {
33 /**
34 * Unprocessed implementation-dependent raw
35 * depth measurements, opaque with 16 bit
36 * samples.
37 *
38 */
39
40 AIMAGE_FORMAT_RAW_DEPTH = 0x1002,
41
42 /**
43 * Device specific 10 bits depth RAW image format.
44 *
45 * <p>Unprocessed implementation-dependent raw depth measurements, opaque with 10 bit samples
46 * and device specific bit layout.</p>
47 */
48 AIMAGE_FORMAT_RAW_DEPTH10 = 0x1003,
49};
50
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080051/**
52 * ACameraMetadata Implementation
53 */
54ACameraMetadata::ACameraMetadata(camera_metadata_t* buffer, ACAMERA_METADATA_TYPE type) :
Eino-Ville Talvalab949b612020-02-06 11:08:41 -080055 mData(std::make_shared<CameraMetadata>(buffer)),
Jiawen Chen9f713e82020-01-15 11:06:13 -050056 mType(type) {
57 init();
58}
59
Eino-Ville Talvalab949b612020-02-06 11:08:41 -080060ACameraMetadata::ACameraMetadata(const std::shared_ptr<CameraMetadata>& cameraMetadata,
61 ACAMERA_METADATA_TYPE type) :
Jiawen Chen9f713e82020-01-15 11:06:13 -050062 mData(cameraMetadata),
Jiawen Chen9f713e82020-01-15 11:06:13 -050063 mType(type) {
64 init();
65}
66
67ACameraMetadata::ACameraMetadata(const ACameraMetadata& other) :
Eino-Ville Talvalab949b612020-02-06 11:08:41 -080068 mData(std::make_shared<CameraMetadata>(*(other.mData))),
Jiawen Chen9f713e82020-01-15 11:06:13 -050069 mType(other.mType) {
Jiawen Chen9f713e82020-01-15 11:06:13 -050070}
71
72ACameraMetadata::~ACameraMetadata() {
Jiawen Chen9f713e82020-01-15 11:06:13 -050073}
74
75void
76ACameraMetadata::init() {
Yin-Chia Yehead91462016-01-06 16:45:08 -080077 if (mType == ACM_CHARACTERISTICS) {
78 filterUnsupportedFeatures();
Yin-Chia Yehc3603822016-01-18 22:11:19 -080079 filterStreamConfigurations();
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -070080 filterDurations(ANDROID_SCALER_AVAILABLE_MIN_FRAME_DURATIONS);
81 filterDurations(ANDROID_SCALER_AVAILABLE_STALL_DURATIONS);
82 filterDurations(ANDROID_DEPTH_AVAILABLE_DEPTH_MIN_FRAME_DURATIONS);
83 filterDurations(ANDROID_DEPTH_AVAILABLE_DEPTH_STALL_DURATIONS);
Shuzhen Wang68ac7ad2019-01-30 14:03:28 -080084 filterDurations(ANDROID_HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS);
85 filterDurations(ANDROID_HEIC_AVAILABLE_HEIC_STALL_DURATIONS);
Emilian Peev44df34d2019-02-12 09:30:15 -080086 filterDurations(ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS);
87 filterDurations(ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS);
Yin-Chia Yehead91462016-01-06 16:45:08 -080088 }
89 // TODO: filter request/result keys
Jayant Chowdhary6c37df02024-03-11 20:12:14 +000090 const CameraMetadata& metadata = *mData;
91 const camera_metadata_t *rawMetadata = metadata.getAndLock();
92 metadata_vendor_id_t vendorTagId = get_camera_metadata_vendor_id(rawMetadata);
93 metadata.unlock(rawMetadata);
94 sp<VendorTagDescriptorCache> vtCache = VendorTagDescriptorCache::getGlobalVendorTagCache();
95 if (vtCache == nullptr) {
96 ALOGE("%s: error vendor tag descriptor cache is not initialized", __FUNCTION__);
97 return;
98 }
99 vtCache->getVendorTagDescriptor(vendorTagId, &mVTags);
100 if (mVTags == nullptr) {
101 ALOGE("%s: error retrieving vendor tag descriptor", __FUNCTION__);
102 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800103}
104
105bool
106ACameraMetadata::isNdkSupportedCapability(int32_t capability) {
107 switch (capability) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800108 case ANDROID_REQUEST_AVAILABLE_CAPABILITIES_YUV_REPROCESSING:
109 case ANDROID_REQUEST_AVAILABLE_CAPABILITIES_PRIVATE_REPROCESSING:
110 case ANDROID_REQUEST_AVAILABLE_CAPABILITIES_CONSTRAINED_HIGH_SPEED_VIDEO:
111 return false;
112 default:
Jayant Chowdhary62899df2019-04-02 16:53:34 -0700113 // Assuming every capability passed to this function is actually a
114 // valid capability.
115 return true;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800116 }
117}
118
119void
120ACameraMetadata::filterUnsupportedFeatures() {
121 // Hide unsupported capabilities (reprocessing)
Jiawen Chen9f713e82020-01-15 11:06:13 -0500122 camera_metadata_entry entry = mData->find(ANDROID_REQUEST_AVAILABLE_CAPABILITIES);
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800123 if (entry.count == 0 || entry.type != TYPE_BYTE) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800124 ALOGE("%s: malformed available capability key! count %zu, type %d",
125 __FUNCTION__, entry.count, entry.type);
126 return;
127 }
128
129 Vector<uint8_t> capabilities;
130 capabilities.setCapacity(entry.count);
131 for (size_t i = 0; i < entry.count; i++) {
132 uint8_t capability = entry.data.u8[i];
133 if (isNdkSupportedCapability(capability)) {
134 capabilities.push(capability);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800135
136 if (capability == ANDROID_REQUEST_AVAILABLE_CAPABILITIES_LOGICAL_MULTI_CAMERA) {
137 derivePhysicalCameraIds();
138 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800139 }
140 }
Jiawen Chen9f713e82020-01-15 11:06:13 -0500141 mData->update(ANDROID_REQUEST_AVAILABLE_CAPABILITIES, capabilities);
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800142}
143
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800144void
145ACameraMetadata::derivePhysicalCameraIds() {
146 ACameraMetadata_const_entry entry;
147 auto ret = getConstEntry(ACAMERA_LOGICAL_MULTI_CAMERA_PHYSICAL_IDS, &entry);
148 if (ret != ACAMERA_OK) {
149 ALOGE("%s: Get ACAMERA_LOGICAL_MULTI_CAMERA_PHYSICAL_IDS key failed. ret %d",
150 __FUNCTION__, ret);
151 return;
152 }
153
154 const uint8_t* ids = entry.data.u8;
155 size_t start = 0;
156 for (size_t i = 0; i < entry.count; ++i) {
157 if (ids[i] == '\0') {
158 if (start != i) {
Emilian Peev1da379a2019-02-05 15:36:31 -0800159 mStaticPhysicalCameraIdValues.push_back(String8((const char *)ids+start));
Tomasz Wasilczyk12b04a52023-08-11 15:52:22 +0000160 mStaticPhysicalCameraIds.push_back(mStaticPhysicalCameraIdValues.back().c_str());
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800161 }
162 start = i+1;
163 }
164 }
165
166 if (mStaticPhysicalCameraIds.size() < 2) {
167 ALOGW("%s: Logical multi-camera device only has %zu physical cameras",
168 __FUNCTION__, mStaticPhysicalCameraIds.size());
169 }
170}
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800171
172void
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -0700173ACameraMetadata::filterDurations(uint32_t tag) {
174 const int STREAM_CONFIGURATION_SIZE = 4;
175 const int STREAM_FORMAT_OFFSET = 0;
176 const int STREAM_WIDTH_OFFSET = 1;
177 const int STREAM_HEIGHT_OFFSET = 2;
178 const int STREAM_DURATION_OFFSET = 3;
Yin-Chia Yeha5b6b2f2020-03-12 11:19:14 -0700179
Jiawen Chen9f713e82020-01-15 11:06:13 -0500180 camera_metadata_entry entry = mData->find(tag);
Yin-Chia Yeha5b6b2f2020-03-12 11:19:14 -0700181
182 if (entry.count == 0) {
183 // Duration keys can be missing when corresponding capture feature is not supported
184 return;
185 }
186
187 if (entry.count % 4 || entry.type != TYPE_INT64) {
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -0700188 ALOGE("%s: malformed duration key %d! count %zu, type %d",
189 __FUNCTION__, tag, entry.count, entry.type);
190 return;
191 }
Yin-Chia Yeha5b6b2f2020-03-12 11:19:14 -0700192
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -0700193 Vector<int64_t> filteredDurations;
194 filteredDurations.setCapacity(entry.count * 2);
195
196 for (size_t i=0; i < entry.count; i += STREAM_CONFIGURATION_SIZE) {
197 int64_t format = entry.data.i64[i + STREAM_FORMAT_OFFSET];
198 int64_t width = entry.data.i64[i + STREAM_WIDTH_OFFSET];
199 int64_t height = entry.data.i64[i + STREAM_HEIGHT_OFFSET];
Fang Hui00bf4252021-11-01 22:38:42 +0800200 int64_t duration = entry.data.i64[i + STREAM_DURATION_OFFSET];
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -0700201
202 // Leave the unfiltered format in so apps depending on previous wrong
203 // filter behavior continue to work
204 filteredDurations.push_back(format);
205 filteredDurations.push_back(width);
206 filteredDurations.push_back(height);
207 filteredDurations.push_back(duration);
208
209 // Translate HAL formats to NDK format
210 switch (tag) {
211 case ANDROID_SCALER_AVAILABLE_MIN_FRAME_DURATIONS:
212 case ANDROID_SCALER_AVAILABLE_STALL_DURATIONS:
213 if (format == HAL_PIXEL_FORMAT_BLOB) {
214 format = AIMAGE_FORMAT_JPEG;
215 filteredDurations.push_back(format);
216 filteredDurations.push_back(width);
217 filteredDurations.push_back(height);
218 filteredDurations.push_back(duration);
219 }
220 break;
221 case ANDROID_DEPTH_AVAILABLE_DEPTH_MIN_FRAME_DURATIONS:
222 case ANDROID_DEPTH_AVAILABLE_DEPTH_STALL_DURATIONS:
223 if (format == HAL_PIXEL_FORMAT_BLOB) {
224 format = AIMAGE_FORMAT_DEPTH_POINT_CLOUD;
225 filteredDurations.push_back(format);
226 filteredDurations.push_back(width);
227 filteredDurations.push_back(height);
228 filteredDurations.push_back(duration);
229 } else if (format == HAL_PIXEL_FORMAT_Y16) {
230 format = AIMAGE_FORMAT_DEPTH16;
231 filteredDurations.push_back(format);
232 filteredDurations.push_back(width);
233 filteredDurations.push_back(height);
234 filteredDurations.push_back(duration);
235 }
236 break;
Shuzhen Wang68ac7ad2019-01-30 14:03:28 -0800237 case ANDROID_HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS:
238 case ANDROID_HEIC_AVAILABLE_HEIC_STALL_DURATIONS:
239 if (format == HAL_PIXEL_FORMAT_BLOB) {
240 format = AIMAGE_FORMAT_HEIC;
241 filteredDurations.push_back(format);
242 filteredDurations.push_back(width);
243 filteredDurations.push_back(height);
244 filteredDurations.push_back(duration);
245 }
246 break;
Emilian Peev44df34d2019-02-12 09:30:15 -0800247 case ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS:
248 case ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS:
249 if (format == HAL_PIXEL_FORMAT_BLOB) {
250 format = AIMAGE_FORMAT_DEPTH_JPEG;
251 filteredDurations.push_back(format);
252 filteredDurations.push_back(width);
253 filteredDurations.push_back(height);
254 filteredDurations.push_back(duration);
255 }
256 break;
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -0700257 default:
258 // Should not reach here
259 ALOGE("%s: Unkown tag 0x%x", __FUNCTION__, tag);
260 }
261 }
262
Jiawen Chen9f713e82020-01-15 11:06:13 -0500263 mData->update(tag, filteredDurations);
Yin-Chia Yehe57e9a22018-08-23 15:36:41 -0700264}
265
266void
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800267ACameraMetadata::filterStreamConfigurations() {
268 const int STREAM_CONFIGURATION_SIZE = 4;
269 const int STREAM_FORMAT_OFFSET = 0;
270 const int STREAM_WIDTH_OFFSET = 1;
271 const int STREAM_HEIGHT_OFFSET = 2;
272 const int STREAM_IS_INPUT_OFFSET = 3;
Jiawen Chen9f713e82020-01-15 11:06:13 -0500273 camera_metadata_entry entry = mData->find(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS);
Yin-Chia Yeh38c13a72019-02-26 14:02:15 -0800274 if (entry.count > 0 && (entry.count % 4 || entry.type != TYPE_INT32)) {
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800275 ALOGE("%s: malformed available stream configuration key! count %zu, type %d",
276 __FUNCTION__, entry.count, entry.type);
277 return;
278 }
279
280 Vector<int32_t> filteredStreamConfigs;
281 filteredStreamConfigs.setCapacity(entry.count);
282
283 for (size_t i=0; i < entry.count; i += STREAM_CONFIGURATION_SIZE) {
284 int32_t format = entry.data.i32[i + STREAM_FORMAT_OFFSET];
285 int32_t width = entry.data.i32[i + STREAM_WIDTH_OFFSET];
286 int32_t height = entry.data.i32[i + STREAM_HEIGHT_OFFSET];
287 int32_t isInput = entry.data.i32[i + STREAM_IS_INPUT_OFFSET];
288 if (isInput == ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_INPUT) {
289 // Hide input streams
290 continue;
291 }
292 // Translate HAL formats to NDK format
293 if (format == HAL_PIXEL_FORMAT_BLOB) {
294 format = AIMAGE_FORMAT_JPEG;
295 }
296 filteredStreamConfigs.push_back(format);
297 filteredStreamConfigs.push_back(width);
298 filteredStreamConfigs.push_back(height);
299 filteredStreamConfigs.push_back(isInput);
300 }
301
Yin-Chia Yeh38c13a72019-02-26 14:02:15 -0800302 if (filteredStreamConfigs.size() > 0) {
Jiawen Chen9f713e82020-01-15 11:06:13 -0500303 mData->update(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS, filteredStreamConfigs);
Yin-Chia Yeh38c13a72019-02-26 14:02:15 -0800304 }
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800305
Jiawen Chen9f713e82020-01-15 11:06:13 -0500306 entry = mData->find(ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS);
Yin-Chia Yeh38c13a72019-02-26 14:02:15 -0800307 if (entry.count > 0 && (entry.count % 4 || entry.type != TYPE_INT32)) {
308 ALOGE("%s: malformed available depth stream configuration key! count %zu, type %d",
309 __FUNCTION__, entry.count, entry.type);
310 return;
311 }
312
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800313 Vector<int32_t> filteredDepthStreamConfigs;
314 filteredDepthStreamConfigs.setCapacity(entry.count);
315
316 for (size_t i=0; i < entry.count; i += STREAM_CONFIGURATION_SIZE) {
317 int32_t format = entry.data.i32[i + STREAM_FORMAT_OFFSET];
318 int32_t width = entry.data.i32[i + STREAM_WIDTH_OFFSET];
319 int32_t height = entry.data.i32[i + STREAM_HEIGHT_OFFSET];
320 int32_t isInput = entry.data.i32[i + STREAM_IS_INPUT_OFFSET];
321 if (isInput == ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_INPUT) {
322 // Hide input streams
323 continue;
324 }
325 // Translate HAL formats to NDK format
326 if (format == HAL_PIXEL_FORMAT_BLOB) {
327 format = AIMAGE_FORMAT_DEPTH_POINT_CLOUD;
328 } else if (format == HAL_PIXEL_FORMAT_Y16) {
329 format = AIMAGE_FORMAT_DEPTH16;
Yin-Chia Yehf6e6a8e2021-04-08 11:49:42 -0700330 } else if (format == HAL_PIXEL_FORMAT_RAW16) {
331 format = static_cast<int32_t>(AIMAGE_FORMAT_RAW_DEPTH);
332 } else if (format == HAL_PIXEL_FORMAT_RAW10) {
333 format = static_cast<int32_t>(AIMAGE_FORMAT_RAW_DEPTH10);
Yin-Chia Yehc3603822016-01-18 22:11:19 -0800334 }
335
336 filteredDepthStreamConfigs.push_back(format);
337 filteredDepthStreamConfigs.push_back(width);
338 filteredDepthStreamConfigs.push_back(height);
339 filteredDepthStreamConfigs.push_back(isInput);
340 }
Yin-Chia Yeh38c13a72019-02-26 14:02:15 -0800341
342 if (filteredDepthStreamConfigs.size() > 0) {
Jiawen Chen9f713e82020-01-15 11:06:13 -0500343 mData->update(ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS,
Yin-Chia Yeh38c13a72019-02-26 14:02:15 -0800344 filteredDepthStreamConfigs);
345 }
Shuzhen Wang68ac7ad2019-01-30 14:03:28 -0800346
Jiawen Chen9f713e82020-01-15 11:06:13 -0500347 entry = mData->find(ANDROID_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS);
Shuzhen Wang68ac7ad2019-01-30 14:03:28 -0800348 Vector<int32_t> filteredHeicStreamConfigs;
349 filteredHeicStreamConfigs.setCapacity(entry.count);
350
351 for (size_t i=0; i < entry.count; i += STREAM_CONFIGURATION_SIZE) {
352 int32_t format = entry.data.i32[i + STREAM_FORMAT_OFFSET];
353 int32_t width = entry.data.i32[i + STREAM_WIDTH_OFFSET];
354 int32_t height = entry.data.i32[i + STREAM_HEIGHT_OFFSET];
355 int32_t isInput = entry.data.i32[i + STREAM_IS_INPUT_OFFSET];
356 if (isInput == ACAMERA_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS_INPUT) {
357 // Hide input streams
358 continue;
359 }
360 // Translate HAL formats to NDK format
361 if (format == HAL_PIXEL_FORMAT_BLOB) {
362 format = AIMAGE_FORMAT_HEIC;
363 }
364
365 filteredHeicStreamConfigs.push_back(format);
366 filteredHeicStreamConfigs.push_back(width);
367 filteredHeicStreamConfigs.push_back(height);
368 filteredHeicStreamConfigs.push_back(isInput);
369 }
Jiawen Chen9f713e82020-01-15 11:06:13 -0500370 mData->update(ANDROID_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS, filteredHeicStreamConfigs);
Emilian Peev44df34d2019-02-12 09:30:15 -0800371
Jiawen Chen9f713e82020-01-15 11:06:13 -0500372 entry = mData->find(ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS);
Emilian Peev44df34d2019-02-12 09:30:15 -0800373 Vector<int32_t> filteredDynamicDepthStreamConfigs;
374 filteredDynamicDepthStreamConfigs.setCapacity(entry.count);
375
376 for (size_t i = 0; i < entry.count; i += STREAM_CONFIGURATION_SIZE) {
377 int32_t format = entry.data.i32[i + STREAM_FORMAT_OFFSET];
378 int32_t width = entry.data.i32[i + STREAM_WIDTH_OFFSET];
379 int32_t height = entry.data.i32[i + STREAM_HEIGHT_OFFSET];
380 int32_t isInput = entry.data.i32[i + STREAM_IS_INPUT_OFFSET];
381 if (isInput == ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS_INPUT) {
382 // Hide input streams
383 continue;
384 }
385 // Translate HAL formats to NDK format
386 if (format == HAL_PIXEL_FORMAT_BLOB) {
387 format = AIMAGE_FORMAT_DEPTH_JPEG;
388 }
389
390 filteredDynamicDepthStreamConfigs.push_back(format);
391 filteredDynamicDepthStreamConfigs.push_back(width);
392 filteredDynamicDepthStreamConfigs.push_back(height);
393 filteredDynamicDepthStreamConfigs.push_back(isInput);
394 }
Jiawen Chen9f713e82020-01-15 11:06:13 -0500395 mData->update(ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS,
Emilian Peev44df34d2019-02-12 09:30:15 -0800396 filteredDynamicDepthStreamConfigs);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800397}
398
399bool
400ACameraMetadata::isVendorTag(const uint32_t tag) {
401 uint32_t tag_section = tag >> 16;
402 if (tag_section >= VENDOR_SECTION) {
403 return true;
404 }
405 return false;
406}
407
408camera_status_t
409ACameraMetadata::getConstEntry(uint32_t tag, ACameraMetadata_const_entry* entry) const {
410 if (entry == nullptr) {
411 return ACAMERA_ERROR_INVALID_PARAMETER;
412 }
413
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800414 Mutex::Autolock _l(mLock);
415
Eino-Ville Talvalab949b612020-02-06 11:08:41 -0800416 camera_metadata_ro_entry rawEntry = static_cast<const CameraMetadata*>(mData.get())->find(tag);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800417 if (rawEntry.count == 0) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800418 return ACAMERA_ERROR_METADATA_NOT_FOUND;
419 }
420 entry->tag = tag;
421 entry->type = rawEntry.type;
422 entry->count = rawEntry.count;
423 entry->data.u8 = rawEntry.data.u8;
424 return ACAMERA_OK;
425}
426
427camera_status_t
428ACameraMetadata::update(uint32_t tag, uint32_t count, const uint8_t* data) {
429 return updateImpl<uint8_t>(tag, count, data);
430}
431
432camera_status_t
433ACameraMetadata::update(uint32_t tag, uint32_t count, const int32_t* data) {
434 return updateImpl<int32_t>(tag, count, data);
435}
436
437camera_status_t
438ACameraMetadata::update(uint32_t tag, uint32_t count, const float* data) {
439 return updateImpl<float>(tag, count, data);
440}
441
442camera_status_t
443ACameraMetadata::update(uint32_t tag, uint32_t count, const double* data) {
444 return updateImpl<double>(tag, count, data);
445}
446
447camera_status_t
448ACameraMetadata::update(uint32_t tag, uint32_t count, const int64_t* data) {
449 return updateImpl<int64_t>(tag, count, data);
450}
451
452camera_status_t
453ACameraMetadata::update(uint32_t tag, uint32_t count, const ACameraMetadata_rational* data) {
454 return updateImpl<camera_metadata_rational_t>(tag, count, data);
455}
456
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800457camera_status_t
458ACameraMetadata::getTags(/*out*/int32_t* numTags,
459 /*out*/const uint32_t** tags) const {
460 Mutex::Autolock _l(mLock);
461 if (mTags.size() == 0) {
Jiawen Chen9f713e82020-01-15 11:06:13 -0500462 size_t entry_count = mData->entryCount();
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800463 mTags.setCapacity(entry_count);
Jiawen Chen9f713e82020-01-15 11:06:13 -0500464 const camera_metadata_t* rawMetadata = mData->getAndLock();
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800465 for (size_t i = 0; i < entry_count; i++) {
466 camera_metadata_ro_entry_t entry;
467 int ret = get_camera_metadata_ro_entry(rawMetadata, i, &entry);
468 if (ret != 0) {
Lida Wange05c3292020-10-22 22:38:40 -0700469 mData->unlock(rawMetadata);
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800470 ALOGE("%s: error reading metadata index %zu", __FUNCTION__, i);
471 return ACAMERA_ERROR_UNKNOWN;
472 }
473 // Hide system key from users
474 if (sSystemTags.count(entry.tag) == 0) {
475 mTags.push_back(entry.tag);
476 }
477 }
Jiawen Chen9f713e82020-01-15 11:06:13 -0500478 mData->unlock(rawMetadata);
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800479 }
480
481 *numTags = mTags.size();
482 *tags = mTags.array();
483 return ACAMERA_OK;
484}
485
486const CameraMetadata&
Emilian Peev5fbe0ba2017-10-20 15:45:45 +0100487ACameraMetadata::getInternalData() const {
Jiawen Chen9f713e82020-01-15 11:06:13 -0500488 return (*mData);
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800489}
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800490
Jayant Chowdhary6c37df02024-03-11 20:12:14 +0000491camera_status_t
492ACameraMetadata::getTagFromName(const char *name, uint32_t *tag) const {
493 Mutex::Autolock _l(mLock);
494 status_t status = CameraMetadata::getTagFromName(name, mVTags.get(), tag);
495 return status == OK ? ACAMERA_OK : ACAMERA_ERROR_METADATA_NOT_FOUND;
496}
497
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800498bool
499ACameraMetadata::isLogicalMultiCamera(size_t* count, const char*const** physicalCameraIds) const {
500 if (mType != ACM_CHARACTERISTICS) {
501 ALOGE("%s must be called for a static metadata!", __FUNCTION__);
502 return false;
503 }
504 if (count == nullptr || physicalCameraIds == nullptr) {
505 ALOGE("%s: Invalid input count: %p, physicalCameraIds: %p", __FUNCTION__,
506 count, physicalCameraIds);
507 return false;
508 }
509
510 if (mStaticPhysicalCameraIds.size() >= 2) {
511 *count = mStaticPhysicalCameraIds.size();
512 *physicalCameraIds = mStaticPhysicalCameraIds.data();
513 return true;
514 }
515
516 return false;
517}
518
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800519// TODO: some of key below should be hidden from user
520// ex: ACAMERA_REQUEST_ID and ACAMERA_REPROCESS_EFFECTIVE_EXPOSURE_FACTOR
521/*@O~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~
522 * The key entries below this point are generated from metadata
523 * definitions in /system/media/camera/docs. Do not modify by hand or
524 * modify the comment blocks at the start or end.
525 *~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~*/
526
527bool
528ACameraMetadata::isCaptureRequestTag(const uint32_t tag) {
529 // Skip check for vendor keys
530 if (isVendorTag(tag)) {
531 return true;
532 }
533
534 switch (tag) {
535 case ACAMERA_COLOR_CORRECTION_MODE:
536 case ACAMERA_COLOR_CORRECTION_TRANSFORM:
537 case ACAMERA_COLOR_CORRECTION_GAINS:
538 case ACAMERA_COLOR_CORRECTION_ABERRATION_MODE:
539 case ACAMERA_CONTROL_AE_ANTIBANDING_MODE:
540 case ACAMERA_CONTROL_AE_EXPOSURE_COMPENSATION:
541 case ACAMERA_CONTROL_AE_LOCK:
542 case ACAMERA_CONTROL_AE_MODE:
543 case ACAMERA_CONTROL_AE_REGIONS:
544 case ACAMERA_CONTROL_AE_TARGET_FPS_RANGE:
545 case ACAMERA_CONTROL_AE_PRECAPTURE_TRIGGER:
546 case ACAMERA_CONTROL_AF_MODE:
547 case ACAMERA_CONTROL_AF_REGIONS:
548 case ACAMERA_CONTROL_AF_TRIGGER:
549 case ACAMERA_CONTROL_AWB_LOCK:
550 case ACAMERA_CONTROL_AWB_MODE:
551 case ACAMERA_CONTROL_AWB_REGIONS:
552 case ACAMERA_CONTROL_CAPTURE_INTENT:
553 case ACAMERA_CONTROL_EFFECT_MODE:
554 case ACAMERA_CONTROL_MODE:
555 case ACAMERA_CONTROL_SCENE_MODE:
556 case ACAMERA_CONTROL_VIDEO_STABILIZATION_MODE:
557 case ACAMERA_CONTROL_POST_RAW_SENSITIVITY_BOOST:
Chien-Yu Chenc0dede92017-01-11 11:10:28 -0800558 case ACAMERA_CONTROL_ENABLE_ZSL:
Shuzhen Wangaa0ae2b2020-03-16 16:00:45 -0700559 case ACAMERA_CONTROL_EXTENDED_SCENE_MODE:
Shuzhen Wangdbdf72b2019-11-13 11:22:12 -0800560 case ACAMERA_CONTROL_ZOOM_RATIO:
Bharatt Kukreja963325d2022-09-02 22:32:45 +0000561 case ACAMERA_CONTROL_SETTINGS_OVERRIDE:
Bharatt Kukrejabedaadb2022-09-15 20:22:32 +0000562 case ACAMERA_CONTROL_AUTOFRAMING:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800563 case ACAMERA_EDGE_MODE:
564 case ACAMERA_FLASH_MODE:
Rucha Katakwar0ff1af02023-08-11 13:25:20 -0700565 case ACAMERA_FLASH_STRENGTH_LEVEL:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800566 case ACAMERA_HOT_PIXEL_MODE:
567 case ACAMERA_JPEG_GPS_COORDINATES:
568 case ACAMERA_JPEG_GPS_PROCESSING_METHOD:
569 case ACAMERA_JPEG_GPS_TIMESTAMP:
570 case ACAMERA_JPEG_ORIENTATION:
571 case ACAMERA_JPEG_QUALITY:
572 case ACAMERA_JPEG_THUMBNAIL_QUALITY:
573 case ACAMERA_JPEG_THUMBNAIL_SIZE:
574 case ACAMERA_LENS_APERTURE:
575 case ACAMERA_LENS_FILTER_DENSITY:
576 case ACAMERA_LENS_FOCAL_LENGTH:
577 case ACAMERA_LENS_FOCUS_DISTANCE:
578 case ACAMERA_LENS_OPTICAL_STABILIZATION_MODE:
579 case ACAMERA_NOISE_REDUCTION_MODE:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800580 case ACAMERA_SCALER_CROP_REGION:
Eino-Ville Talvalae2a88922020-01-06 13:09:21 -0800581 case ACAMERA_SCALER_ROTATE_AND_CROP:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800582 case ACAMERA_SENSOR_EXPOSURE_TIME:
583 case ACAMERA_SENSOR_FRAME_DURATION:
584 case ACAMERA_SENSOR_SENSITIVITY:
585 case ACAMERA_SENSOR_TEST_PATTERN_DATA:
586 case ACAMERA_SENSOR_TEST_PATTERN_MODE:
Jayant Chowdharyb6be3c42020-11-15 10:44:38 -0800587 case ACAMERA_SENSOR_PIXEL_MODE:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800588 case ACAMERA_SHADING_MODE:
589 case ACAMERA_STATISTICS_FACE_DETECT_MODE:
590 case ACAMERA_STATISTICS_HOT_PIXEL_MAP_MODE:
591 case ACAMERA_STATISTICS_LENS_SHADING_MAP_MODE:
Chien-Yu Chen5ca4a9b2018-01-18 12:23:50 -0800592 case ACAMERA_STATISTICS_OIS_DATA_MODE:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800593 case ACAMERA_TONEMAP_CURVE_BLUE:
594 case ACAMERA_TONEMAP_CURVE_GREEN:
595 case ACAMERA_TONEMAP_CURVE_RED:
596 case ACAMERA_TONEMAP_MODE:
597 case ACAMERA_TONEMAP_GAMMA:
598 case ACAMERA_TONEMAP_PRESET_CURVE:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800599 case ACAMERA_BLACK_LEVEL_LOCK:
Eino-Ville Talvala2d960922018-03-13 19:46:23 -0700600 case ACAMERA_DISTORTION_CORRECTION_MODE:
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800601 return true;
602 default:
603 return false;
604 }
605}
606
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800607// System tags that should be hidden from users
608std::unordered_set<uint32_t> ACameraMetadata::sSystemTags ({
609 ANDROID_CONTROL_SCENE_MODE_OVERRIDES,
610 ANDROID_CONTROL_AE_PRECAPTURE_ID,
611 ANDROID_CONTROL_AF_TRIGGER_ID,
Shuzhen Wang3c00b092022-11-08 22:53:07 +0000612 ANDROID_CONTROL_SETTINGS_OVERRIDING_FRAME_NUMBER,
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800613 ANDROID_DEMOSAIC_MODE,
614 ANDROID_EDGE_STRENGTH,
615 ANDROID_FLASH_FIRING_POWER,
616 ANDROID_FLASH_FIRING_TIME,
617 ANDROID_FLASH_COLOR_TEMPERATURE,
618 ANDROID_FLASH_MAX_ENERGY,
619 ANDROID_FLASH_INFO_CHARGE_DURATION,
620 ANDROID_JPEG_MAX_SIZE,
621 ANDROID_JPEG_SIZE,
622 ANDROID_NOISE_REDUCTION_STRENGTH,
623 ANDROID_QUIRKS_METERING_CROP_REGION,
624 ANDROID_QUIRKS_TRIGGER_AF_WITH_AUTO,
625 ANDROID_QUIRKS_USE_ZSL_FORMAT,
626 ANDROID_REQUEST_INPUT_STREAMS,
627 ANDROID_REQUEST_METADATA_MODE,
628 ANDROID_REQUEST_OUTPUT_STREAMS,
629 ANDROID_REQUEST_TYPE,
630 ANDROID_REQUEST_MAX_NUM_REPROCESS_STREAMS,
631 ANDROID_SCALER_AVAILABLE_RAW_MIN_DURATIONS,
632 ANDROID_SCALER_AVAILABLE_RAW_SIZES,
633 ANDROID_SENSOR_BASE_GAIN_FACTOR,
634 ANDROID_SENSOR_PROFILE_HUE_SAT_MAP_DIMENSIONS,
635 ANDROID_SENSOR_TEMPERATURE,
636 ANDROID_SENSOR_PROFILE_HUE_SAT_MAP,
637 ANDROID_SENSOR_PROFILE_TONE_CURVE,
638 ANDROID_SENSOR_OPAQUE_RAW_SIZE,
Jayant Chowdharyb6be3c42020-11-15 10:44:38 -0800639 ANDROID_SENSOR_OPAQUE_RAW_SIZE_MAXIMUM_RESOLUTION,
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800640 ANDROID_SHADING_STRENGTH,
641 ANDROID_STATISTICS_HISTOGRAM_MODE,
642 ANDROID_STATISTICS_SHARPNESS_MAP_MODE,
643 ANDROID_STATISTICS_HISTOGRAM,
644 ANDROID_STATISTICS_SHARPNESS_MAP,
645 ANDROID_STATISTICS_INFO_HISTOGRAM_BUCKET_COUNT,
646 ANDROID_STATISTICS_INFO_MAX_HISTOGRAM_COUNT,
647 ANDROID_STATISTICS_INFO_MAX_SHARPNESS_MAP_VALUE,
648 ANDROID_STATISTICS_INFO_SHARPNESS_MAP_SIZE,
Yin-Chia Yeh2be96a22018-09-17 11:51:24 -0700649 ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION,
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800650 ANDROID_DEPTH_MAX_DEPTH_SAMPLES,
Shuzhen Wang68ac7ad2019-01-30 14:03:28 -0800651 ANDROID_HEIC_INFO_SUPPORTED,
652 ANDROID_HEIC_INFO_MAX_JPEG_APP_SEGMENTS_COUNT,
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -0800653});
654
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800655/*~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~
656 * End generated code
657 *~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~@~O@*/