1 /*
2 * Copyright (C) 2019 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 #include <gtest/gtest.h>
18 #define LOG_TAG "CameraVendorTagTests"
19 #include <log/log.h>
20
21 #include <vector>
22
23 #include "system/camera_metadata.h"
24 #include "vendor_tag_defs.h"
25 #include "vendor_tag_utils.h"
26 #include "vendor_tags.h"
27
28 namespace android {
29 namespace google_camera_hal {
30
31 static constexpr uint32_t kDataBytes = 256;
32 static constexpr uint32_t kNumEntries = 10;
33
TEST(CameraVendorTagTest,TestCharacteristics)34 TEST(CameraVendorTagTest, TestCharacteristics) {
35 auto hal_metadata = HalCameraMetadata::Create(kNumEntries, kDataBytes);
36 ASSERT_NE(hal_metadata, nullptr) << "Creating hal_metadata failed.";
37
38 std::vector<uint32_t> dummy_keys = {
39 VendorTagIds::kLogicalCamDefaultPhysicalId};
40 status_t res = hal_metadata->Set(
41 ANDROID_REQUEST_AVAILABLE_REQUEST_KEYS,
42 reinterpret_cast<int32_t*>(dummy_keys.data()), dummy_keys.size());
43 ASSERT_EQ(res, OK);
44
45 res = hal_metadata->Set(ANDROID_REQUEST_AVAILABLE_RESULT_KEYS,
46 reinterpret_cast<int32_t*>(dummy_keys.data()),
47 dummy_keys.size());
48 ASSERT_EQ(res, OK);
49
50 res = hal_metadata->Set(ANDROID_REQUEST_AVAILABLE_SESSION_KEYS,
51 reinterpret_cast<int32_t*>(dummy_keys.data()),
52 dummy_keys.size());
53 ASSERT_EQ(res, OK);
54
55 res = hal_metadata->Set(ANDROID_REQUEST_AVAILABLE_CHARACTERISTICS_KEYS,
56 reinterpret_cast<int32_t*>(dummy_keys.data()),
57 dummy_keys.size());
58 ASSERT_EQ(res, OK);
59
60 res = hal_vendor_tag_utils::ModifyCharacteristicsKeys(hal_metadata.get());
61 EXPECT_EQ(res, OK);
62
63 res = hal_vendor_tag_utils::ModifyCharacteristicsKeys(nullptr);
64 EXPECT_NE(res, OK) << "ModifyCameraCharacteristics() should have failed with "
65 "a nullptr metadata";
66 }
67
TEST(CameraVendorTagTest,TestDefaultRequest)68 TEST(CameraVendorTagTest, TestDefaultRequest) {
69 std::vector<RequestTemplate> request_templates = {
70 RequestTemplate::kPreview, RequestTemplate::kStillCapture,
71 RequestTemplate::kVideoRecord, RequestTemplate::kVideoSnapshot,
72 RequestTemplate::kZeroShutterLag};
73
74 status_t res;
75 for (auto& request_template : request_templates) {
76 auto hal_metadata = HalCameraMetadata::Create(kNumEntries, kDataBytes);
77 ASSERT_NE(hal_metadata, nullptr) << "Creating hal_metadata failed.";
78
79 res = hal_vendor_tag_utils::ModifyDefaultRequestSettings(
80 request_template, hal_metadata.get());
81 EXPECT_EQ(res, OK) << "ModifyDefaultRequestSettings() failed for request "
82 "template (%u)"
83 << static_cast<uint32_t>(request_template);
84 }
85 }
86
TEST(CameraVendorTagTest,TestValidVendorTags)87 TEST(CameraVendorTagTest, TestValidVendorTags) {
88 uint32_t hwl_tag_id = VENDOR_SECTION_START;
89 uint32_t hal_tag_id = kHalVendorTagSectionStart;
90
91 ASSERT_LT(hwl_tag_id, hal_tag_id) << "Error! HAL vendor tag section start "
92 << "must be greater than "
93 << "VENDOR_SECTION_START";
94
95 std::vector<VendorTagSection> hwl_sections = {
96 {.section_name = "com.google.hwl.internal",
97 .tags = {{.tag_id = hwl_tag_id++,
98 .tag_name = "magic",
99 .tag_type = CameraMetadataType::kFloat},
100 {.tag_id = hwl_tag_id++,
101 .tag_name = "wand",
102 .tag_type = CameraMetadataType::kFloat}}},
103 {.section_name = "com.google.3a",
104 .tags = {{.tag_id = hwl_tag_id++,
105 .tag_name = "aec",
106 .tag_type = CameraMetadataType::kFloat},
107 {.tag_id = hwl_tag_id++,
108 .tag_name = "awb",
109 .tag_type = CameraMetadataType::kInt32}}}};
110
111 std::vector<VendorTagSection> hal_sections = {
112 {.section_name = "com.pixel.experimental",
113 .tags = {{.tag_id = hal_tag_id++,
114 .tag_name = "hybrid_ae.enabled",
115 .tag_type = CameraMetadataType::kByte}}},
116 /* Overlaps with HWL vendor section above; this is allowed */
117 {.section_name = "com.google.3a",
118 .tags = {{.tag_id = hal_tag_id++,
119 .tag_name = "af",
120 .tag_type = CameraMetadataType::kFloat}}}};
121
122 std::vector<VendorTagSection> combined_sections;
123 status_t ret = vendor_tag_utils::CombineVendorTags(hwl_sections, hal_sections,
124 &combined_sections);
125
126 EXPECT_EQ(ret, OK) << "CombineVendorTags() failed for valid tags!";
127
128 ret = vendor_tag_utils::CombineVendorTags(hwl_sections, hal_sections,
129 /*destination=*/nullptr);
130 EXPECT_NE(ret, OK) << "CombineVendorTags() should have failed with nullptr";
131
132 // Test metadata operations on above tags. They should fail since the camera
133 // framework hasn't been initialized via VendorTagManager utility class
134 auto metadata = HalCameraMetadata::Create(kNumEntries, kDataBytes);
135 ASSERT_NE(metadata, nullptr) << "Creating metadata failed.";
136 // Hard coded vendor tag ID for 'com.google.hwl.internal.magic' from above
137 uint32_t magic_tag_id = VENDOR_SECTION_START;
138 float good_magic = 42.1337f;
139 // Try to set a random value to above vendor tag
140 ret = metadata->Set(magic_tag_id, &good_magic, /*count=*/1);
141 EXPECT_NE(ret, OK) << "Error! Setting metadata should have failed before "
142 << "initializing VendorTagManager";
143
144 // Framework camera_metadata operations relying on 'vendor_tag_ops_t' should
145 // fail before VendorTagManager is initialized with the vendor tags
146 int count = VendorTagManager::GetInstance().GetCount();
147 EXPECT_EQ(0, count) << "Error! VendorTagManager should return a count of 0"
148 << " before being initialized";
149
150 // Now initialize VendorTagManager, and expect metadata operations same
151 // as previously done above to succeed
152 ret = VendorTagManager::GetInstance().AddTags(combined_sections);
153 ASSERT_EQ(ret, OK);
154 count = VendorTagManager::GetInstance().GetCount();
155 int expected_count = 0;
156 for (auto& section : hal_sections) {
157 expected_count += section.tags.size();
158 }
159 for (auto& section : hwl_sections) {
160 expected_count += section.tags.size();
161 }
162 EXPECT_EQ(count, expected_count);
163
164 ret = metadata->Set(magic_tag_id, &good_magic, /*count=*/1);
165 EXPECT_EQ(ret, OK) << "Error! Setting metadata should have succeeded after "
166 << "initializing VendorTagManager";
167
168 // Try setting metadata with an invalid type (expected is float)
169 int32_t dark_magic = 13;
170 ret = metadata->Set(magic_tag_id, &dark_magic, /*count=*/1);
171 EXPECT_NE(ret, OK) << "Error! Setting metadata with an incorrect payload "
172 << "type should have failed";
173
174 // For debugging fun - print the combined list of vendor tags
175 ALOGI("Vendor tag list START");
176 ALOGI("---------------------");
177 if (count > 0) {
178 uint32_t* tag_id_list = new uint32_t[count];
179 VendorTagManager::GetInstance().GetAllTags(tag_id_list);
180 for (int i = 0; i < count; i++) {
181 uint32_t tag_id = tag_id_list[i];
182 const char* section_name =
183 VendorTagManager::GetInstance().GetSectionName(tag_id);
184 const char* tag_name = VendorTagManager::GetInstance().GetTagName(tag_id);
185 int tag_type = VendorTagManager::GetInstance().GetTagType(tag_id);
186 ALOGI("ID: 0x%x (%u)\tType: %d\t%s.%s", tag_id, tag_id, tag_type,
187 section_name, tag_name);
188 }
189
190 delete[] tag_id_list;
191 ALOGI("Vendor tag list END");
192 ALOGI("-------------------");
193 }
194
195 ret = VendorTagManager::GetInstance().AddTags(combined_sections);
196 EXPECT_NE(ret, OK) << "Calling AddTags with the same tags should fail.";
197
198 std::vector<VendorTagSection> extra_sections = {
199 {.section_name = "extra_section",
200 .tags = {{.tag_id = hal_tag_id++,
201 .tag_name = "extra_tag",
202 .tag_type = CameraMetadataType::kByte}}}};
203
204 ret = VendorTagManager::GetInstance().AddTags(extra_sections);
205 EXPECT_EQ(ret, OK) << "Adding extra tag sections should succeed";
206 expected_count += 1;
207 count = VendorTagManager::GetInstance().GetCount();
208 EXPECT_EQ(count, expected_count);
209
210 VendorTagManager::GetInstance().Reset();
211 count = VendorTagManager::GetInstance().GetCount();
212 EXPECT_EQ(0, count) << "Error! VendorTagManager should return a count of 0"
213 << " after being reset";
214 }
215
TEST(CameraVendorTagTest,TestVendorTagsOverlappingIds)216 TEST(CameraVendorTagTest, TestVendorTagsOverlappingIds) {
217 // Make the HAL and HWL tag IDs overlap
218 uint32_t hwl_tag_id = kHalVendorTagSectionStart;
219 uint32_t hal_tag_id = kHalVendorTagSectionStart;
220
221 std::vector<VendorTagSection> hwl_sections = {
222 {.section_name = "com.google.hwl.internal",
223 .tags = {{.tag_id = hwl_tag_id++,
224 .tag_name = "magic",
225 .tag_type = CameraMetadataType::kFloat},
226 {.tag_id = hwl_tag_id++,
227 .tag_name = "wand",
228 .tag_type = CameraMetadataType::kFloat}}},
229 {.section_name = "com.google.hwl.3a",
230 .tags = {{.tag_id = hwl_tag_id++,
231 .tag_name = "aec",
232 .tag_type = CameraMetadataType::kFloat},
233 {.tag_id = hwl_tag_id++,
234 .tag_name = "awb",
235 .tag_type = CameraMetadataType::kInt32}}}};
236
237 std::vector<VendorTagSection> hal_sections = {
238 {.section_name = "com.pixel.experimental",
239 .tags = {{.tag_id = hal_tag_id++,
240 .tag_name = "hybrid_ae.enabled",
241 .tag_type = CameraMetadataType::kByte}}},
242 {.section_name = "com.google.hwl.3a",
243 .tags = {{.tag_id = hal_tag_id++,
244 .tag_name = "af",
245 .tag_type = CameraMetadataType::kFloat}}}};
246
247 std::vector<VendorTagSection> combined_sections;
248 status_t ret = vendor_tag_utils::CombineVendorTags(hwl_sections, hal_sections,
249 &combined_sections);
250
251 EXPECT_NE(ret, OK) << "CombineVendorTags() succeeded for invalid tags!";
252 }
253
TEST(CameraVendorTagTest,TestVendorTagsOverlappingNames)254 TEST(CameraVendorTagTest, TestVendorTagsOverlappingNames) {
255 uint32_t hwl_tag_id = VENDOR_SECTION_START;
256 uint32_t hal_tag_id = kHalVendorTagSectionStart;
257
258 // Define duplicate tag name in both sections: com.google.hwl.3a.aec
259 std::vector<VendorTagSection> hwl_sections = {
260 {.section_name = "com.google.hwl.internal",
261 .tags = {{.tag_id = hwl_tag_id++,
262 .tag_name = "magic",
263 .tag_type = CameraMetadataType::kFloat},
264 {.tag_id = hwl_tag_id++,
265 .tag_name = "wand",
266 .tag_type = CameraMetadataType::kFloat}}},
267 {.section_name = "com.google.hwl.3a",
268 .tags = {{.tag_id = hwl_tag_id++,
269 .tag_name = "aec",
270 .tag_type = CameraMetadataType::kFloat},
271 {.tag_id = hwl_tag_id++,
272 .tag_name = "awb",
273 .tag_type = CameraMetadataType::kInt32}}}};
274
275 std::vector<VendorTagSection> hal_sections = {
276 {.section_name = "com.pixel.experimental",
277 .tags = {{.tag_id = hal_tag_id++,
278 .tag_name = "hybrid_ae.enabled",
279 .tag_type = CameraMetadataType::kByte}}},
280 {.section_name = "com.google.hwl.3a",
281 .tags = {{.tag_id = hal_tag_id++,
282 .tag_name = "aec",
283 .tag_type = CameraMetadataType::kFloat}}}};
284
285 std::vector<VendorTagSection> combined_sections;
286 status_t ret = vendor_tag_utils::CombineVendorTags(hwl_sections, hal_sections,
287 &combined_sections);
288
289 EXPECT_NE(ret, OK) << "CombineVendorTags() succeeded for invalid tags";
290 }
291 } // namespace google_camera_hal
292 } // namespace android
293