• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2016-2018 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_TAG "camera_hidl_hal_test"
18 
19 #include <algorithm>
20 #include <chrono>
21 #include <condition_variable>
22 #include <list>
23 #include <mutex>
24 #include <regex>
25 #include <string>
26 #include <unordered_map>
27 #include <unordered_set>
28 
29 #include <inttypes.h>
30 
31 #include <CameraMetadata.h>
32 #include <CameraParameters.h>
33 #include <android/hardware/camera/device/1.0/ICameraDevice.h>
34 #include <android/hardware/camera/device/3.2/ICameraDevice.h>
35 #include <android/hardware/camera/device/3.3/ICameraDeviceSession.h>
36 #include <android/hardware/camera/device/3.4/ICameraDeviceCallback.h>
37 #include <android/hardware/camera/device/3.4/ICameraDeviceSession.h>
38 #include <android/hardware/camera/device/3.5/ICameraDevice.h>
39 #include <android/hardware/camera/device/3.5/ICameraDeviceCallback.h>
40 #include <android/hardware/camera/device/3.5/ICameraDeviceSession.h>
41 #include <android/hardware/camera/device/3.6/ICameraDevice.h>
42 #include <android/hardware/camera/device/3.6/ICameraDeviceSession.h>
43 #include <android/hardware/camera/metadata/3.4/types.h>
44 #include <android/hardware/camera/provider/2.4/ICameraProvider.h>
45 #include <android/hardware/camera/provider/2.5/ICameraProvider.h>
46 #include <android/hardware/camera/provider/2.6/ICameraProvider.h>
47 #include <android/hardware/camera/provider/2.6/ICameraProviderCallback.h>
48 #include <android/hidl/manager/1.0/IServiceManager.h>
49 #include <binder/MemoryHeapBase.h>
50 #include <cutils/properties.h>
51 #include <fmq/MessageQueue.h>
52 #include <grallocusage/GrallocUsageConversion.h>
53 #include <gtest/gtest.h>
54 #include <gui/BufferItemConsumer.h>
55 #include <gui/BufferQueue.h>
56 #include <gui/Surface.h>
57 #include <hardware/gralloc.h>
58 #include <hardware/gralloc1.h>
59 #include <hidl/GtestPrinter.h>
60 #include <hidl/ServiceManagement.h>
61 #include <log/log.h>
62 #include <system/camera.h>
63 #include <system/camera_metadata.h>
64 #include <ui/GraphicBuffer.h>
65 #include <ui/GraphicBufferAllocator.h>
66 #include <ui/GraphicBufferMapper.h>
67 
68 #include <android/hidl/allocator/1.0/IAllocator.h>
69 #include <android/hidl/memory/1.0/IMapper.h>
70 #include <android/hidl/memory/1.0/IMemory.h>
71 
72 using namespace ::android::hardware::camera::device;
73 using ::android::BufferItemConsumer;
74 using ::android::BufferQueue;
75 using ::android::GraphicBuffer;
76 using ::android::IGraphicBufferConsumer;
77 using ::android::IGraphicBufferProducer;
78 using ::android::sp;
79 using ::android::Surface;
80 using ::android::wp;
81 using ::android::hardware::hidl_bitfield;
82 using ::android::hardware::hidl_handle;
83 using ::android::hardware::hidl_string;
84 using ::android::hardware::hidl_vec;
85 using ::android::hardware::kSynchronizedReadWrite;
86 using ::android::hardware::MessageQueue;
87 using ::android::hardware::Return;
88 using ::android::hardware::Void;
89 using ::android::hardware::camera::common::V1_0::CameraDeviceStatus;
90 using ::android::hardware::camera::common::V1_0::Status;
91 using ::android::hardware::camera::common::V1_0::TorchMode;
92 using ::android::hardware::camera::common::V1_0::TorchModeStatus;
93 using ::android::hardware::camera::common::V1_0::helper::CameraParameters;
94 using ::android::hardware::camera::common::V1_0::helper::Size;
95 using ::android::hardware::camera::device::V1_0::CameraFacing;
96 using ::android::hardware::camera::device::V1_0::CameraFrameMetadata;
97 using ::android::hardware::camera::device::V1_0::CommandType;
98 using ::android::hardware::camera::device::V1_0::DataCallbackMsg;
99 using ::android::hardware::camera::device::V1_0::FrameCallbackFlag;
100 using ::android::hardware::camera::device::V1_0::HandleTimestampMessage;
101 using ::android::hardware::camera::device::V1_0::ICameraDevicePreviewCallback;
102 using ::android::hardware::camera::device::V1_0::NotifyCallbackMsg;
103 using ::android::hardware::camera::device::V3_2::BufferCache;
104 using ::android::hardware::camera::device::V3_2::BufferStatus;
105 using ::android::hardware::camera::device::V3_2::CameraMetadata;
106 using ::android::hardware::camera::device::V3_2::CaptureRequest;
107 using ::android::hardware::camera::device::V3_2::CaptureResult;
108 using ::android::hardware::camera::device::V3_2::ErrorCode;
109 using ::android::hardware::camera::device::V3_2::ErrorMsg;
110 using ::android::hardware::camera::device::V3_2::HalStreamConfiguration;
111 using ::android::hardware::camera::device::V3_2::ICameraDevice;
112 using ::android::hardware::camera::device::V3_2::ICameraDeviceSession;
113 using ::android::hardware::camera::device::V3_2::MsgType;
114 using ::android::hardware::camera::device::V3_2::NotifyMsg;
115 using ::android::hardware::camera::device::V3_2::RequestTemplate;
116 using ::android::hardware::camera::device::V3_2::StreamBuffer;
117 using ::android::hardware::camera::device::V3_2::StreamConfiguration;
118 using ::android::hardware::camera::device::V3_2::StreamConfigurationMode;
119 using ::android::hardware::camera::device::V3_2::StreamRotation;
120 using ::android::hardware::camera::device::V3_2::StreamType;
121 using ::android::hardware::camera::device::V3_4::PhysicalCameraMetadata;
122 using ::android::hardware::camera::metadata::V3_4::
123         CameraMetadataEnumAndroidSensorInfoColorFilterArrangement;
124 using ::android::hardware::camera::metadata::V3_4::CameraMetadataTag;
125 using ::android::hardware::camera::provider::V2_4::ICameraProvider;
126 using ::android::hardware::camera::provider::V2_4::ICameraProviderCallback;
127 using ::android::hardware::camera::provider::V2_6::CameraIdAndStreamCombination;
128 using ::android::hardware::graphics::common::V1_0::BufferUsage;
129 using ::android::hardware::graphics::common::V1_0::Dataspace;
130 using ::android::hardware::graphics::common::V1_0::PixelFormat;
131 using ::android::hidl::allocator::V1_0::IAllocator;
132 using ::android::hidl::memory::V1_0::IMapper;
133 using ::android::hidl::memory::V1_0::IMemory;
134 using ResultMetadataQueue = MessageQueue<uint8_t, kSynchronizedReadWrite>;
135 using ::android::hidl::manager::V1_0::IServiceManager;
136 
137 using namespace ::android::hardware::camera;
138 
139 const uint32_t kMaxPreviewWidth = 1920;
140 const uint32_t kMaxPreviewHeight = 1080;
141 const uint32_t kMaxStillWidth = 2048;
142 const uint32_t kMaxStillHeight = 1536;
143 const uint32_t kMaxVideoWidth = 4096;
144 const uint32_t kMaxVideoHeight = 2160;
145 const int64_t kStreamBufferTimeoutSec = 3;
146 const int64_t kAutoFocusTimeoutSec = 5;
147 const int64_t kTorchTimeoutSec = 1;
148 const int64_t kEmptyFlushTimeoutMSec = 200;
149 const char kDumpOutput[] = "/dev/null";
150 const uint32_t kBurstFrameCount = 10;
151 const int64_t kBufferReturnTimeoutSec = 1;
152 
153 struct AvailableStream {
154     int32_t width;
155     int32_t height;
156     int32_t format;
157 };
158 
159 struct AvailableZSLInputOutput {
160     int32_t inputFormat;
161     int32_t outputFormat;
162 };
163 
164 enum ReprocessType {
165     PRIV_REPROCESS,
166     YUV_REPROCESS,
167 };
168 
169 enum SystemCameraKind {
170     /**
171      * These camera devices are visible to all apps and system components alike
172      */
173     PUBLIC = 0,
174 
175     /**
176      * These camera devices are visible only to processes having the
177      * android.permission.SYSTEM_CAMERA permission. They are not exposed to 3P
178      * apps.
179      */
180     SYSTEM_ONLY_CAMERA,
181 
182     /**
183      * These camera devices are visible only to HAL clients (that try to connect
184      * on a hwbinder thread).
185      */
186     HIDDEN_SECURE_CAMERA
187 };
188 
189 namespace {
190     // "device@<version>/legacy/<id>"
191     const char *kDeviceNameRE = "device@([0-9]+\\.[0-9]+)/%s/(.+)";
192     const int CAMERA_DEVICE_API_VERSION_3_6 = 0x306;
193     const int CAMERA_DEVICE_API_VERSION_3_5 = 0x305;
194     const int CAMERA_DEVICE_API_VERSION_3_4 = 0x304;
195     const int CAMERA_DEVICE_API_VERSION_3_3 = 0x303;
196     const int CAMERA_DEVICE_API_VERSION_3_2 = 0x302;
197     const int CAMERA_DEVICE_API_VERSION_1_0 = 0x100;
198     const char *kHAL3_6 = "3.6";
199     const char *kHAL3_5 = "3.5";
200     const char *kHAL3_4 = "3.4";
201     const char *kHAL3_3 = "3.3";
202     const char *kHAL3_2 = "3.2";
203     const char *kHAL1_0 = "1.0";
204 
matchDeviceName(const hidl_string & deviceName,const hidl_string & providerType,std::string * deviceVersion,std::string * cameraId)205     bool matchDeviceName(const hidl_string& deviceName,
206             const hidl_string &providerType,
207             std::string* deviceVersion,
208             std::string* cameraId) {
209         ::android::String8 pattern;
210         pattern.appendFormat(kDeviceNameRE, providerType.c_str());
211         std::regex e(pattern.string());
212         std::string deviceNameStd(deviceName.c_str());
213         std::smatch sm;
214         if (std::regex_match(deviceNameStd, sm, e)) {
215             if (deviceVersion != nullptr) {
216                 *deviceVersion = sm[1];
217             }
218             if (cameraId != nullptr) {
219                 *cameraId = sm[2];
220             }
221             return true;
222         }
223         return false;
224     }
225 
getCameraDeviceVersion(const hidl_string & deviceName,const hidl_string & providerType)226     int getCameraDeviceVersion(const hidl_string& deviceName,
227             const hidl_string &providerType) {
228         std::string version;
229         bool match = matchDeviceName(deviceName, providerType, &version, nullptr);
230         if (!match) {
231             return -1;
232         }
233 
234         if (version.compare(kHAL3_6) == 0) {
235             return CAMERA_DEVICE_API_VERSION_3_6;
236         } else if (version.compare(kHAL3_5) == 0) {
237             return CAMERA_DEVICE_API_VERSION_3_5;
238         } else if (version.compare(kHAL3_4) == 0) {
239             return CAMERA_DEVICE_API_VERSION_3_4;
240         } else if (version.compare(kHAL3_3) == 0) {
241             return CAMERA_DEVICE_API_VERSION_3_3;
242         } else if (version.compare(kHAL3_2) == 0) {
243             return CAMERA_DEVICE_API_VERSION_3_2;
244         } else if (version.compare(kHAL1_0) == 0) {
245             return CAMERA_DEVICE_API_VERSION_1_0;
246         }
247         return 0;
248     }
249 
parseProviderName(const std::string & name,std::string * type,uint32_t * id)250     bool parseProviderName(const std::string& name, std::string *type /*out*/,
251             uint32_t *id /*out*/) {
252         if (!type || !id) {
253             ADD_FAILURE();
254             return false;
255         }
256 
257         std::string::size_type slashIdx = name.find('/');
258         if (slashIdx == std::string::npos || slashIdx == name.size() - 1) {
259             ADD_FAILURE() << "Provider name does not have / separator between type"
260                     "and id";
261             return false;
262         }
263 
264         std::string typeVal = name.substr(0, slashIdx);
265 
266         char *endPtr;
267         errno = 0;
268         long idVal = strtol(name.c_str() + slashIdx + 1, &endPtr, 10);
269         if (errno != 0) {
270             ADD_FAILURE() << "cannot parse provider id as an integer:" <<
271                     name.c_str() << strerror(errno) << errno;
272             return false;
273         }
274         if (endPtr != name.c_str() + name.size()) {
275             ADD_FAILURE() << "provider id has unexpected length " << name.c_str();
276             return false;
277         }
278         if (idVal < 0) {
279             ADD_FAILURE() << "id is negative: " << name.c_str() << idVal;
280             return false;
281         }
282 
283         *type = typeVal;
284         *id = static_cast<uint32_t>(idVal);
285 
286         return true;
287     }
288 
mapToStatus(::android::status_t s)289     Status mapToStatus(::android::status_t s)  {
290         switch(s) {
291             case ::android::OK:
292                 return Status::OK ;
293             case ::android::BAD_VALUE:
294                 return Status::ILLEGAL_ARGUMENT ;
295             case -EBUSY:
296                 return Status::CAMERA_IN_USE;
297             case -EUSERS:
298                 return Status::MAX_CAMERAS_IN_USE;
299             case ::android::UNKNOWN_TRANSACTION:
300                 return Status::METHOD_NOT_SUPPORTED;
301             case ::android::INVALID_OPERATION:
302                 return Status::OPERATION_NOT_SUPPORTED;
303             case ::android::DEAD_OBJECT:
304                 return Status::CAMERA_DISCONNECTED;
305         }
306         ALOGW("Unexpected HAL status code %d", s);
307         return Status::OPERATION_NOT_SUPPORTED;
308     }
309 
getFirstApiLevel(int32_t * outApiLevel)310     void getFirstApiLevel(/*out*/int32_t* outApiLevel) {
311         int32_t firstApiLevel = property_get_int32("ro.product.first_api_level", /*default*/-1);
312         if (firstApiLevel < 0) {
313             firstApiLevel = property_get_int32("ro.build.version.sdk", /*default*/-1);
314         }
315         ASSERT_GT(firstApiLevel, 0); // first_api_level must exist
316         *outApiLevel = firstApiLevel;
317         return;
318     }
319 }
320 
321 struct BufferItemHander: public BufferItemConsumer::FrameAvailableListener {
BufferItemHanderBufferItemHander322     BufferItemHander(wp<BufferItemConsumer> consumer) : mConsumer(consumer) {}
323 
onFrameAvailableBufferItemHander324     void onFrameAvailable(const android::BufferItem&) override {
325         sp<BufferItemConsumer> consumer = mConsumer.promote();
326         ASSERT_NE(nullptr, consumer.get());
327 
328         android::BufferItem buffer;
329         ASSERT_EQ(android::OK, consumer->acquireBuffer(&buffer, 0));
330         ASSERT_EQ(android::OK, consumer->releaseBuffer(buffer));
331     }
332 
333  private:
334     wp<BufferItemConsumer> mConsumer;
335 };
336 
337 struct PreviewWindowCb : public ICameraDevicePreviewCallback {
PreviewWindowCbPreviewWindowCb338     PreviewWindowCb(sp<ANativeWindow> anw) : mPreviewWidth(0),
339             mPreviewHeight(0), mFormat(0), mPreviewUsage(0),
340             mPreviewSwapInterval(-1), mCrop{-1, -1, -1, -1}, mAnw(anw) {}
341 
342     using dequeueBuffer_cb =
343             std::function<void(Status status, uint64_t bufferId,
344                     const hidl_handle& buffer, uint32_t stride)>;
345     Return<void> dequeueBuffer(dequeueBuffer_cb _hidl_cb) override;
346 
347     Return<Status> enqueueBuffer(uint64_t bufferId) override;
348 
349     Return<Status> cancelBuffer(uint64_t bufferId) override;
350 
351     Return<Status> setBufferCount(uint32_t count) override;
352 
353     Return<Status> setBuffersGeometry(uint32_t w,
354             uint32_t h, PixelFormat format) override;
355 
356     Return<Status> setCrop(int32_t left, int32_t top,
357             int32_t right, int32_t bottom) override;
358 
359     Return<Status> setUsage(BufferUsage usage) override;
360 
361     Return<Status> setSwapInterval(int32_t interval) override;
362 
363     using getMinUndequeuedBufferCount_cb =
364             std::function<void(Status status, uint32_t count)>;
365     Return<void> getMinUndequeuedBufferCount(
366             getMinUndequeuedBufferCount_cb _hidl_cb) override;
367 
368     Return<Status> setTimestamp(int64_t timestamp) override;
369 
370  private:
371     struct BufferHasher {
operator ()PreviewWindowCb::BufferHasher372         size_t operator()(const buffer_handle_t& buf) const {
373             if (buf == nullptr)
374                 return 0;
375 
376             size_t result = 1;
377             result = 31 * result + buf->numFds;
378             for (int i = 0; i < buf->numFds; i++) {
379                 result = 31 * result + buf->data[i];
380             }
381             return result;
382         }
383     };
384 
385     struct BufferComparator {
operator ()PreviewWindowCb::BufferComparator386         bool operator()(const buffer_handle_t& buf1,
387                 const buffer_handle_t& buf2) const {
388             if (buf1->numFds == buf2->numFds) {
389                 for (int i = 0; i < buf1->numFds; i++) {
390                     if (buf1->data[i] != buf2->data[i]) {
391                         return false;
392                     }
393                 }
394                 return true;
395             }
396             return false;
397         }
398     };
399 
400     std::pair<bool, uint64_t> getBufferId(ANativeWindowBuffer* anb);
401     void cleanupCirculatingBuffers();
402 
403     std::mutex mBufferIdMapLock; // protecting mBufferIdMap and mNextBufferId
404     typedef std::unordered_map<const buffer_handle_t, uint64_t,
405             BufferHasher, BufferComparator> BufferIdMap;
406 
407     BufferIdMap mBufferIdMap; // stream ID -> per stream buffer ID map
408     std::unordered_map<uint64_t, ANativeWindowBuffer*> mReversedBufMap;
409     uint64_t mNextBufferId = 1;
410 
411     uint32_t mPreviewWidth, mPreviewHeight;
412     int mFormat, mPreviewUsage;
413     int32_t mPreviewSwapInterval;
414     android_native_rect_t mCrop;
415     sp<ANativeWindow> mAnw;     //Native window reference
416 };
417 
getBufferId(ANativeWindowBuffer * anb)418 std::pair<bool, uint64_t> PreviewWindowCb::getBufferId(
419         ANativeWindowBuffer* anb) {
420     std::lock_guard<std::mutex> lock(mBufferIdMapLock);
421 
422     buffer_handle_t& buf = anb->handle;
423     auto it = mBufferIdMap.find(buf);
424     if (it == mBufferIdMap.end()) {
425         uint64_t bufId = mNextBufferId++;
426         mBufferIdMap[buf] = bufId;
427         mReversedBufMap[bufId] = anb;
428         return std::make_pair(true, bufId);
429     } else {
430         return std::make_pair(false, it->second);
431     }
432 }
433 
cleanupCirculatingBuffers()434 void PreviewWindowCb::cleanupCirculatingBuffers() {
435     std::lock_guard<std::mutex> lock(mBufferIdMapLock);
436     mBufferIdMap.clear();
437     mReversedBufMap.clear();
438 }
439 
dequeueBuffer(dequeueBuffer_cb _hidl_cb)440 Return<void> PreviewWindowCb::dequeueBuffer(dequeueBuffer_cb _hidl_cb) {
441     ANativeWindowBuffer* anb;
442     auto rc = native_window_dequeue_buffer_and_wait(mAnw.get(), &anb);
443     uint64_t bufferId = 0;
444     uint32_t stride = 0;
445     hidl_handle buf = nullptr;
446     if (rc == ::android::OK) {
447         auto pair = getBufferId(anb);
448         buf = (pair.first) ? anb->handle : nullptr;
449         bufferId = pair.second;
450         stride = anb->stride;
451     }
452 
453     _hidl_cb(mapToStatus(rc), bufferId, buf, stride);
454     return Void();
455 }
456 
enqueueBuffer(uint64_t bufferId)457 Return<Status> PreviewWindowCb::enqueueBuffer(uint64_t bufferId) {
458     if (mReversedBufMap.count(bufferId) == 0) {
459         ALOGE("%s: bufferId %" PRIu64 " not found", __FUNCTION__, bufferId);
460         return Status::ILLEGAL_ARGUMENT;
461     }
462     return mapToStatus(mAnw->queueBuffer(mAnw.get(),
463             mReversedBufMap.at(bufferId), -1));
464 }
465 
cancelBuffer(uint64_t bufferId)466 Return<Status> PreviewWindowCb::cancelBuffer(uint64_t bufferId) {
467     if (mReversedBufMap.count(bufferId) == 0) {
468         ALOGE("%s: bufferId %" PRIu64 " not found", __FUNCTION__, bufferId);
469         return Status::ILLEGAL_ARGUMENT;
470     }
471     return mapToStatus(mAnw->cancelBuffer(mAnw.get(),
472             mReversedBufMap.at(bufferId), -1));
473 }
474 
setBufferCount(uint32_t count)475 Return<Status> PreviewWindowCb::setBufferCount(uint32_t count) {
476     if (mAnw.get() != nullptr) {
477         // WAR for b/27039775
478         native_window_api_disconnect(mAnw.get(), NATIVE_WINDOW_API_CAMERA);
479         native_window_api_connect(mAnw.get(), NATIVE_WINDOW_API_CAMERA);
480         if (mPreviewWidth != 0) {
481             native_window_set_buffers_dimensions(mAnw.get(),
482                     mPreviewWidth, mPreviewHeight);
483             native_window_set_buffers_format(mAnw.get(), mFormat);
484         }
485         if (mPreviewUsage != 0) {
486             native_window_set_usage(mAnw.get(), mPreviewUsage);
487         }
488         if (mPreviewSwapInterval >= 0) {
489             mAnw->setSwapInterval(mAnw.get(), mPreviewSwapInterval);
490         }
491         if (mCrop.left >= 0) {
492             native_window_set_crop(mAnw.get(), &(mCrop));
493         }
494     }
495 
496     auto rc = native_window_set_buffer_count(mAnw.get(), count);
497     if (rc == ::android::OK) {
498         cleanupCirculatingBuffers();
499     }
500 
501     return mapToStatus(rc);
502 }
503 
setBuffersGeometry(uint32_t w,uint32_t h,PixelFormat format)504 Return<Status> PreviewWindowCb::setBuffersGeometry(uint32_t w, uint32_t h,
505         PixelFormat format) {
506     auto rc = native_window_set_buffers_dimensions(mAnw.get(), w, h);
507     if (rc == ::android::OK) {
508         mPreviewWidth = w;
509         mPreviewHeight = h;
510         rc = native_window_set_buffers_format(mAnw.get(),
511                 static_cast<int>(format));
512         if (rc == ::android::OK) {
513             mFormat = static_cast<int>(format);
514         }
515     }
516 
517     return mapToStatus(rc);
518 }
519 
setCrop(int32_t left,int32_t top,int32_t right,int32_t bottom)520 Return<Status> PreviewWindowCb::setCrop(int32_t left, int32_t top,
521         int32_t right, int32_t bottom) {
522     android_native_rect_t crop = { left, top, right, bottom };
523     auto rc = native_window_set_crop(mAnw.get(), &crop);
524     if (rc == ::android::OK) {
525         mCrop = crop;
526     }
527     return mapToStatus(rc);
528 }
529 
setUsage(BufferUsage usage)530 Return<Status> PreviewWindowCb::setUsage(BufferUsage usage) {
531     auto rc = native_window_set_usage(mAnw.get(), static_cast<int>(usage));
532     if (rc == ::android::OK) {
533         mPreviewUsage =  static_cast<int>(usage);
534     }
535     return mapToStatus(rc);
536 }
537 
setSwapInterval(int32_t interval)538 Return<Status> PreviewWindowCb::setSwapInterval(int32_t interval) {
539     auto rc = mAnw->setSwapInterval(mAnw.get(), interval);
540     if (rc == ::android::OK) {
541         mPreviewSwapInterval = interval;
542     }
543     return mapToStatus(rc);
544 }
545 
getMinUndequeuedBufferCount(getMinUndequeuedBufferCount_cb _hidl_cb)546 Return<void> PreviewWindowCb::getMinUndequeuedBufferCount(
547         getMinUndequeuedBufferCount_cb _hidl_cb) {
548     int count = 0;
549     auto rc = mAnw->query(mAnw.get(),
550             NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, &count);
551     _hidl_cb(mapToStatus(rc), count);
552     return Void();
553 }
554 
setTimestamp(int64_t timestamp)555 Return<Status> PreviewWindowCb::setTimestamp(int64_t timestamp) {
556     return mapToStatus(native_window_set_buffers_timestamp(mAnw.get(),
557             timestamp));
558 }
559 
560 // The main test class for camera HIDL HAL.
561 class CameraHidlTest : public ::testing::TestWithParam<std::string> {
562 public:
SetUp()563  virtual void SetUp() override {
564      std::string service_name = GetParam();
565      ALOGI("get service with name: %s", service_name.c_str());
566      mProvider = ICameraProvider::getService(service_name);
567 
568      ASSERT_NE(mProvider, nullptr);
569 
570      uint32_t id;
571      ASSERT_TRUE(parseProviderName(service_name, &mProviderType, &id));
572 
573      castProvider(mProvider, &mProvider2_5, &mProvider2_6);
574      notifyDeviceState(provider::V2_5::DeviceState::NORMAL);
575  }
TearDown()576  virtual void TearDown() override {}
577 
578  hidl_vec<hidl_string> getCameraDeviceNames(sp<ICameraProvider> provider,
579                                             bool addSecureOnly = false);
580 
581  bool isSecureOnly(sp<ICameraProvider> provider, const hidl_string& name);
582 
583  std::map<hidl_string, hidl_string> getCameraDeviceIdToNameMap(sp<ICameraProvider> provider);
584 
585  hidl_vec<hidl_vec<hidl_string>> getConcurrentDeviceCombinations(
586          sp<::android::hardware::camera::provider::V2_6::ICameraProvider>&);
587 
588  struct EmptyDeviceCb : public V3_5::ICameraDeviceCallback {
processCaptureResultCameraHidlTest::EmptyDeviceCb589      virtual Return<void> processCaptureResult(
590          const hidl_vec<CaptureResult>& /*results*/) override {
591          ALOGI("processCaptureResult callback");
592          ADD_FAILURE();  // Empty callback should not reach here
593          return Void();
594      }
595 
processCaptureResult_3_4CameraHidlTest::EmptyDeviceCb596      virtual Return<void> processCaptureResult_3_4(
597          const hidl_vec<V3_4::CaptureResult>& /*results*/) override {
598          ALOGI("processCaptureResult_3_4 callback");
599          ADD_FAILURE();  // Empty callback should not reach here
600          return Void();
601      }
602 
notifyCameraHidlTest::EmptyDeviceCb603      virtual Return<void> notify(const hidl_vec<NotifyMsg>& /*msgs*/) override {
604          ALOGI("notify callback");
605          ADD_FAILURE();  // Empty callback should not reach here
606          return Void();
607      }
608 
requestStreamBuffersCameraHidlTest::EmptyDeviceCb609      virtual Return<void> requestStreamBuffers(
610              const hidl_vec<V3_5::BufferRequest>&,
611              requestStreamBuffers_cb _hidl_cb) override {
612          ALOGI("requestStreamBuffers callback");
613          // HAL might want to request buffer after configureStreams, but tests with EmptyDeviceCb
614          // doesn't actually need to send capture requests, so just return an error.
615          hidl_vec<V3_5::StreamBufferRet> emptyBufRets;
616          _hidl_cb(V3_5::BufferRequestStatus::FAILED_UNKNOWN, emptyBufRets);
617          return Void();
618      }
619 
returnStreamBuffersCameraHidlTest::EmptyDeviceCb620      virtual Return<void> returnStreamBuffers(const hidl_vec<StreamBuffer>&) override {
621          ALOGI("returnStreamBuffers");
622          ADD_FAILURE();  // Empty callback should not reach here
623          return Void();
624      }
625  };
626 
627     struct DeviceCb : public V3_5::ICameraDeviceCallback {
DeviceCbCameraHidlTest::DeviceCb628         DeviceCb(CameraHidlTest *parent, int deviceVersion, const camera_metadata_t *staticMeta) :
629                 mParent(parent), mDeviceVersion(deviceVersion) {
630             mStaticMetadata = staticMeta;
631         }
632 
633         Return<void> processCaptureResult_3_4(
634                 const hidl_vec<V3_4::CaptureResult>& results) override;
635         Return<void> processCaptureResult(const hidl_vec<CaptureResult>& results) override;
636         Return<void> notify(const hidl_vec<NotifyMsg>& msgs) override;
637 
638         Return<void> requestStreamBuffers(
639                 const hidl_vec<V3_5::BufferRequest>& bufReqs,
640                 requestStreamBuffers_cb _hidl_cb) override;
641 
642         Return<void> returnStreamBuffers(const hidl_vec<StreamBuffer>& buffers) override;
643 
644         void setCurrentStreamConfig(const hidl_vec<V3_4::Stream>& streams,
645                 const hidl_vec<V3_2::HalStream>& halStreams);
646 
647         void waitForBuffersReturned();
648 
649      private:
650         bool processCaptureResultLocked(const CaptureResult& results,
651                 hidl_vec<PhysicalCameraMetadata> physicalCameraMetadata);
652 
653         CameraHidlTest *mParent; // Parent object
654         int mDeviceVersion;
655         android::hardware::camera::common::V1_0::helper::CameraMetadata mStaticMetadata;
656         bool hasOutstandingBuffersLocked();
657 
658         /* members for requestStreamBuffers() and returnStreamBuffers()*/
659         std::mutex mLock; // protecting members below
660         bool                      mUseHalBufManager = false;
661         hidl_vec<V3_4::Stream>    mStreams;
662         hidl_vec<V3_2::HalStream> mHalStreams;
663         uint64_t mNextBufferId = 1;
664         using OutstandingBuffers = std::unordered_map<uint64_t, hidl_handle>;
665         // size == mStreams.size(). Tracking each streams outstanding buffers
666         std::vector<OutstandingBuffers> mOutstandingBufferIds;
667         std::condition_variable mFlushedCondition;
668     };
669 
670     struct TorchProviderCb : public ICameraProviderCallback {
TorchProviderCbCameraHidlTest::TorchProviderCb671         TorchProviderCb(CameraHidlTest *parent) : mParent(parent) {}
cameraDeviceStatusChangeCameraHidlTest::TorchProviderCb672         virtual Return<void> cameraDeviceStatusChange(
673                 const hidl_string&, CameraDeviceStatus) override {
674             return Void();
675         }
676 
torchModeStatusChangeCameraHidlTest::TorchProviderCb677         virtual Return<void> torchModeStatusChange(
678                 const hidl_string&, TorchModeStatus newStatus) override {
679             std::lock_guard<std::mutex> l(mParent->mTorchLock);
680             mParent->mTorchStatus = newStatus;
681             mParent->mTorchCond.notify_one();
682             return Void();
683         }
684 
685      private:
686         CameraHidlTest *mParent;               // Parent object
687     };
688 
689     struct Camera1DeviceCb :
690             public ::android::hardware::camera::device::V1_0::ICameraDeviceCallback {
Camera1DeviceCbCameraHidlTest::Camera1DeviceCb691         Camera1DeviceCb(CameraHidlTest *parent) : mParent(parent) {}
692 
693         Return<void> notifyCallback(NotifyCallbackMsg msgType,
694                 int32_t ext1, int32_t ext2) override;
695 
696         Return<uint32_t> registerMemory(const hidl_handle& descriptor,
697                 uint32_t bufferSize, uint32_t bufferCount) override;
698 
699         Return<void> unregisterMemory(uint32_t memId) override;
700 
701         Return<void> dataCallback(DataCallbackMsg msgType,
702                 uint32_t data, uint32_t bufferIndex,
703                 const CameraFrameMetadata& metadata) override;
704 
705         Return<void> dataCallbackTimestamp(DataCallbackMsg msgType,
706                 uint32_t data, uint32_t bufferIndex,
707                 int64_t timestamp) override;
708 
709         Return<void> handleCallbackTimestamp(DataCallbackMsg msgType,
710                 const hidl_handle& frameData,uint32_t data,
711                 uint32_t bufferIndex, int64_t timestamp) override;
712 
713         Return<void> handleCallbackTimestampBatch(DataCallbackMsg msgType,
714                 const ::android::hardware::hidl_vec<HandleTimestampMessage>& batch) override;
715 
716 
717      private:
718         CameraHidlTest *mParent;               // Parent object
719     };
720 
721     void notifyDeviceState(::android::hardware::camera::provider::V2_5::DeviceState newState);
722 
723     void openCameraDevice(const std::string &name, sp<ICameraProvider> provider,
724             sp<::android::hardware::camera::device::V1_0::ICameraDevice> *device /*out*/);
725     void setupPreviewWindow(
726             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device,
727             sp<BufferItemConsumer> *bufferItemConsumer /*out*/,
728             sp<BufferItemHander> *bufferHandler /*out*/);
729     void stopPreviewAndClose(
730             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device);
731     void startPreview(
732             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device);
733     void enableMsgType(unsigned int msgType,
734             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device);
735     void disableMsgType(unsigned int msgType,
736             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device);
737     void getParameters(
738             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device,
739             CameraParameters *cameraParams /*out*/);
740     void setParameters(
741             const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device,
742             const CameraParameters &cameraParams);
743     void allocateGraphicBuffer(uint32_t width, uint32_t height, uint64_t usage,
744             PixelFormat format, hidl_handle *buffer_handle /*out*/);
745     void waitForFrameLocked(DataCallbackMsg msgFrame,
746             std::unique_lock<std::mutex> &l);
747     void openEmptyDeviceSession(const std::string &name,
748             sp<ICameraProvider> provider,
749             sp<ICameraDeviceSession> *session /*out*/,
750             camera_metadata_t **staticMeta /*out*/,
751             ::android::sp<ICameraDevice> *device = nullptr/*out*/);
752     void castProvider(const sp<provider::V2_4::ICameraProvider>& provider,
753                       sp<provider::V2_5::ICameraProvider>* provider2_5 /*out*/,
754                       sp<provider::V2_6::ICameraProvider>* provider2_6 /*out*/);
755     void castSession(const sp<ICameraDeviceSession> &session, int32_t deviceVersion,
756             sp<device::V3_3::ICameraDeviceSession> *session3_3 /*out*/,
757             sp<device::V3_4::ICameraDeviceSession> *session3_4 /*out*/,
758             sp<device::V3_5::ICameraDeviceSession> *session3_5 /*out*/,
759             sp<device::V3_6::ICameraDeviceSession> *session3_6 /*out*/);
760     void castDevice(const sp<device::V3_2::ICameraDevice> &device, int32_t deviceVersion,
761             sp<device::V3_5::ICameraDevice> *device3_5/*out*/);
762     void createStreamConfiguration(const ::android::hardware::hidl_vec<V3_2::Stream>& streams3_2,
763             StreamConfigurationMode configMode,
764             ::android::hardware::camera::device::V3_2::StreamConfiguration *config3_2,
765             ::android::hardware::camera::device::V3_4::StreamConfiguration *config3_4,
766             ::android::hardware::camera::device::V3_5::StreamConfiguration *config3_5,
767             uint32_t jpegBufferSize = 0);
768 
769     void configureOfflineStillStream(const std::string &name, int32_t deviceVersion,
770             sp<ICameraProvider> provider,
771             const AvailableStream *threshold,
772             sp<device::V3_6::ICameraDeviceSession> *session/*out*/,
773             V3_2::Stream *stream /*out*/,
774             device::V3_6::HalStreamConfiguration *halStreamConfig /*out*/,
775             bool *supportsPartialResults /*out*/,
776             uint32_t *partialResultCount /*out*/,
777             sp<DeviceCb> *outCb /*out*/,
778             uint32_t *jpegBufferSize /*out*/,
779             bool *useHalBufManager /*out*/);
780     void configurePreviewStreams3_4(const std::string &name, int32_t deviceVersion,
781             sp<ICameraProvider> provider,
782             const AvailableStream *previewThreshold,
783             const std::unordered_set<std::string>& physicalIds,
784             sp<device::V3_4::ICameraDeviceSession> *session3_4 /*out*/,
785             sp<device::V3_5::ICameraDeviceSession> *session3_5 /*out*/,
786             V3_2::Stream* previewStream /*out*/,
787             device::V3_4::HalStreamConfiguration *halStreamConfig /*out*/,
788             bool *supportsPartialResults /*out*/,
789             uint32_t *partialResultCount /*out*/,
790             bool *useHalBufManager /*out*/,
791             sp<DeviceCb> *cb /*out*/,
792             uint32_t streamConfigCounter = 0,
793             bool allowUnsupport = false);
794     void configurePreviewStream(const std::string &name, int32_t deviceVersion,
795             sp<ICameraProvider> provider,
796             const AvailableStream *previewThreshold,
797             sp<ICameraDeviceSession> *session /*out*/,
798             V3_2::Stream *previewStream /*out*/,
799             HalStreamConfiguration *halStreamConfig /*out*/,
800             bool *supportsPartialResults /*out*/,
801             uint32_t *partialResultCount /*out*/,
802             bool *useHalBufManager /*out*/,
803             sp<DeviceCb> *cb /*out*/,
804             uint32_t streamConfigCounter = 0);
805     void configureSingleStream(const std::string& name, int32_t deviceVersion,
806             sp<ICameraProvider> provider,
807             const AvailableStream* previewThreshold, uint64_t bufferUsage,
808             RequestTemplate reqTemplate,
809             sp<ICameraDeviceSession>* session /*out*/,
810             V3_2::Stream* previewStream /*out*/,
811             HalStreamConfiguration* halStreamConfig /*out*/,
812             bool* supportsPartialResults /*out*/,
813             uint32_t* partialResultCount /*out*/, bool* useHalBufManager /*out*/,
814             sp<DeviceCb>* cb /*out*/, uint32_t streamConfigCounter = 0);
815 
816     void verifyLogicalCameraMetadata(const std::string& cameraName,
817             const ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice>& device,
818             const CameraMetadata& chars, int deviceVersion,
819             const hidl_vec<hidl_string>& deviceNames);
820     void verifyCameraCharacteristics(Status status, const CameraMetadata& chars);
821     void verifyExtendedSceneModeCharacteristics(const camera_metadata_t* metadata);
822     void verifyZoomCharacteristics(const camera_metadata_t* metadata);
823     void verifyRecommendedConfigs(const CameraMetadata& metadata);
824     void verifyMonochromeCharacteristics(const CameraMetadata& chars, int deviceVersion);
825     void verifyMonochromeCameraResult(
826             const ::android::hardware::camera::common::V1_0::helper::CameraMetadata& metadata);
827     void verifyStreamCombination(sp<device::V3_5::ICameraDevice> cameraDevice3_5,
828             const ::android::hardware::camera::device::V3_4::StreamConfiguration &config3_4,
829             bool expectedStatus, bool expectStreamCombQuery);
830     void verifyLogicalCameraResult(const camera_metadata_t* staticMetadata,
831             const ::android::hardware::camera::common::V1_0::helper::CameraMetadata& resultMetadata);
832 
833     void verifyBuffersReturned(sp<device::V3_2::ICameraDeviceSession> session,
834             int deviceVerison, int32_t streamId, sp<DeviceCb> cb,
835             uint32_t streamConfigCounter = 0);
836 
837     void verifyBuffersReturned(sp<device::V3_4::ICameraDeviceSession> session,
838             hidl_vec<int32_t> streamIds, sp<DeviceCb> cb,
839             uint32_t streamConfigCounter = 0);
840 
841     void verifySessionReconfigurationQuery(sp<device::V3_5::ICameraDeviceSession> session3_5,
842             camera_metadata* oldSessionParams, camera_metadata* newSessionParams);
843 
844     void verifyRequestTemplate(const camera_metadata_t* metadata, RequestTemplate requestTemplate);
845 
846     static bool isDepthOnly(const camera_metadata_t* staticMeta);
847 
848     static Status getAvailableOutputStreams(const camera_metadata_t *staticMeta,
849             std::vector<AvailableStream> &outputStreams,
850             const AvailableStream *threshold = nullptr);
851 
852     static Status getMaxOutputSizeForFormat(const camera_metadata_t* staticMeta, PixelFormat format,
853                                             Size* size);
854 
855     static Status getMandatoryConcurrentStreams(const camera_metadata_t* staticMeta,
856                                                 std::vector<AvailableStream>* outputStreams);
857 
858     static Status getJpegBufferSize(camera_metadata_t *staticMeta,
859             uint32_t* outBufSize);
860     static Status isConstrainedModeAvailable(camera_metadata_t *staticMeta);
861     static Status isLogicalMultiCamera(const camera_metadata_t *staticMeta);
862     static Status isOfflineSessionSupported(const camera_metadata_t *staticMeta);
863     static Status getPhysicalCameraIds(const camera_metadata_t *staticMeta,
864             std::unordered_set<std::string> *physicalIds/*out*/);
865     static Status getSupportedKeys(camera_metadata_t *staticMeta,
866             uint32_t tagId, std::unordered_set<int32_t> *requestIDs/*out*/);
867     static void fillOutputStreams(camera_metadata_ro_entry_t* entry,
868             std::vector<AvailableStream>& outputStreams,
869             const AvailableStream *threshold = nullptr,
870             const int32_t availableConfigOutputTag = 0u);
871     static void constructFilteredSettings(const sp<ICameraDeviceSession>& session,
872             const std::unordered_set<int32_t>& availableKeys, RequestTemplate reqTemplate,
873             android::hardware::camera::common::V1_0::helper::CameraMetadata* defaultSettings/*out*/,
874             android::hardware::camera::common::V1_0::helper::CameraMetadata* filteredSettings
875             /*out*/);
876     static Status pickConstrainedModeSize(camera_metadata_t *staticMeta,
877             AvailableStream &hfrStream);
878     static Status isZSLModeAvailable(const camera_metadata_t *staticMeta);
879     static Status isZSLModeAvailable(const camera_metadata_t *staticMeta, ReprocessType reprocType);
880     static Status getZSLInputOutputMap(camera_metadata_t *staticMeta,
881             std::vector<AvailableZSLInputOutput> &inputOutputMap);
882     static Status findLargestSize(
883             const std::vector<AvailableStream> &streamSizes,
884             int32_t format, AvailableStream &result);
885     static Status isAutoFocusModeAvailable(
886             CameraParameters &cameraParams, const char *mode) ;
887     static Status isMonochromeCamera(const camera_metadata_t *staticMeta);
888     static Status getSystemCameraKind(const camera_metadata_t* staticMeta,
889                                       SystemCameraKind* systemCameraKind);
890 
891     static V3_2::DataspaceFlags getDataspace(PixelFormat format);
892 
893     void processCaptureRequestInternal(uint64_t bufferusage, RequestTemplate reqTemplate,
894                                        bool useSecureOnlyCameras);
895 
896     // Used by switchToOffline where a new result queue is created for offline reqs
897     void updateInflightResultQueue(std::shared_ptr<ResultMetadataQueue> resultQueue);
898 
899 protected:
900 
901     // In-flight queue for tracking completion of capture requests.
902     struct InFlightRequest {
903         // Set by notify() SHUTTER call.
904         nsecs_t shutterTimestamp;
905 
906         bool errorCodeValid;
907         ErrorCode errorCode;
908 
909         //Is partial result supported
910         bool usePartialResult;
911 
912         //Partial result count expected
913         uint32_t numPartialResults;
914 
915         // Message queue
916         std::shared_ptr<ResultMetadataQueue> resultQueue;
917 
918         // Set by process_capture_result call with valid metadata
919         bool haveResultMetadata;
920 
921         // Decremented by calls to process_capture_result with valid output
922         // and input buffers
923         ssize_t numBuffersLeft;
924 
925          // A 64bit integer to index the frame number associated with this result.
926         int64_t frameNumber;
927 
928          // The partial result count (index) for this capture result.
929         int32_t partialResultCount;
930 
931         // For buffer drop errors, the stream ID for the stream that lost a buffer.
932         // For physical sub-camera result errors, the Id of the physical stream
933         // for the physical sub-camera.
934         // Otherwise -1.
935         int32_t errorStreamId;
936 
937         // If this request has any input buffer
938         bool hasInputBuffer;
939 
940         // Result metadata
941         ::android::hardware::camera::common::V1_0::helper::CameraMetadata collectedResult;
942 
943         // Buffers are added by process_capture_result when output buffers
944         // return from HAL but framework.
945         ::android::Vector<StreamBuffer> resultOutputBuffers;
946 
947         std::unordered_set<std::string> expectedPhysicalResults;
948 
InFlightRequestCameraHidlTest::InFlightRequest949         InFlightRequest() :
950                 shutterTimestamp(0),
951                 errorCodeValid(false),
952                 errorCode(ErrorCode::ERROR_BUFFER),
953                 usePartialResult(false),
954                 numPartialResults(0),
955                 resultQueue(nullptr),
956                 haveResultMetadata(false),
957                 numBuffersLeft(0),
958                 frameNumber(0),
959                 partialResultCount(0),
960                 errorStreamId(-1),
961                 hasInputBuffer(false) {}
962 
InFlightRequestCameraHidlTest::InFlightRequest963         InFlightRequest(ssize_t numBuffers, bool hasInput,
964                 bool partialResults, uint32_t partialCount,
965                 std::shared_ptr<ResultMetadataQueue> queue = nullptr) :
966                 shutterTimestamp(0),
967                 errorCodeValid(false),
968                 errorCode(ErrorCode::ERROR_BUFFER),
969                 usePartialResult(partialResults),
970                 numPartialResults(partialCount),
971                 resultQueue(queue),
972                 haveResultMetadata(false),
973                 numBuffersLeft(numBuffers),
974                 frameNumber(0),
975                 partialResultCount(0),
976                 errorStreamId(-1),
977                 hasInputBuffer(hasInput) {}
978 
InFlightRequestCameraHidlTest::InFlightRequest979         InFlightRequest(ssize_t numBuffers, bool hasInput,
980                 bool partialResults, uint32_t partialCount,
981                 const std::unordered_set<std::string>& extraPhysicalResult,
982                 std::shared_ptr<ResultMetadataQueue> queue = nullptr) :
983                 shutterTimestamp(0),
984                 errorCodeValid(false),
985                 errorCode(ErrorCode::ERROR_BUFFER),
986                 usePartialResult(partialResults),
987                 numPartialResults(partialCount),
988                 resultQueue(queue),
989                 haveResultMetadata(false),
990                 numBuffersLeft(numBuffers),
991                 frameNumber(0),
992                 partialResultCount(0),
993                 errorStreamId(-1),
994                 hasInputBuffer(hasInput),
995                 expectedPhysicalResults(extraPhysicalResult) {}
996     };
997 
998     // Map from frame number to the in-flight request state
999     typedef ::android::KeyedVector<uint32_t, InFlightRequest*> InFlightMap;
1000 
1001     std::mutex mLock;                          // Synchronize access to member variables
1002     std::condition_variable mResultCondition;  // Condition variable for incoming results
1003     InFlightMap mInflightMap;                  // Map of all inflight requests
1004 
1005     DataCallbackMsg mDataMessageTypeReceived;  // Most recent message type received through data callbacks
1006     uint32_t mVideoBufferIndex;                // Buffer index of the most recent video buffer
1007     uint32_t mVideoData;                       // Buffer data of the most recent video buffer
1008     hidl_handle mVideoNativeHandle;            // Most recent video buffer native handle
1009     NotifyCallbackMsg mNotifyMessage;          // Current notification message
1010 
1011     std::mutex mTorchLock;                     // Synchronize access to torch status
1012     std::condition_variable mTorchCond;        // Condition variable for torch status
1013     TorchModeStatus mTorchStatus;              // Current torch status
1014 
1015     // Holds camera registered buffers
1016     std::unordered_map<uint32_t, sp<::android::MemoryHeapBase> > mMemoryPool;
1017 
1018     // Camera provider service
1019     sp<ICameraProvider> mProvider;
1020     sp<::android::hardware::camera::provider::V2_5::ICameraProvider> mProvider2_5;
1021     sp<::android::hardware::camera::provider::V2_6::ICameraProvider> mProvider2_6;
1022 
1023     // Camera provider type.
1024     std::string mProviderType;
1025 };
1026 
notifyCallback(NotifyCallbackMsg msgType,int32_t ext1 __unused,int32_t ext2 __unused)1027 Return<void> CameraHidlTest::Camera1DeviceCb::notifyCallback(
1028         NotifyCallbackMsg msgType, int32_t ext1 __unused,
1029         int32_t ext2 __unused) {
1030     std::unique_lock<std::mutex> l(mParent->mLock);
1031     mParent->mNotifyMessage = msgType;
1032     mParent->mResultCondition.notify_one();
1033 
1034     return Void();
1035 }
1036 
registerMemory(const hidl_handle & descriptor,uint32_t bufferSize,uint32_t bufferCount)1037 Return<uint32_t> CameraHidlTest::Camera1DeviceCb::registerMemory(
1038         const hidl_handle& descriptor, uint32_t bufferSize,
1039         uint32_t bufferCount) {
1040     if (descriptor->numFds != 1) {
1041         ADD_FAILURE() << "camera memory descriptor has"
1042                 " numFds " <<  descriptor->numFds << " (expect 1)" ;
1043         return 0;
1044     }
1045     if (descriptor->data[0] < 0) {
1046         ADD_FAILURE() << "camera memory descriptor has"
1047                 " FD " << descriptor->data[0] << " (expect >= 0)";
1048         return 0;
1049     }
1050 
1051     sp<::android::MemoryHeapBase> pool = new ::android::MemoryHeapBase(
1052             descriptor->data[0], bufferSize*bufferCount, 0, 0);
1053     mParent->mMemoryPool.emplace(pool->getHeapID(), pool);
1054 
1055     return pool->getHeapID();
1056 }
1057 
unregisterMemory(uint32_t memId)1058 Return<void> CameraHidlTest::Camera1DeviceCb::unregisterMemory(uint32_t memId) {
1059     if (mParent->mMemoryPool.count(memId) == 0) {
1060         ALOGE("%s: memory pool ID %d not found", __FUNCTION__, memId);
1061         ADD_FAILURE();
1062         return Void();
1063     }
1064 
1065     mParent->mMemoryPool.erase(memId);
1066     return Void();
1067 }
1068 
dataCallback(DataCallbackMsg msgType __unused,uint32_t data __unused,uint32_t bufferIndex __unused,const CameraFrameMetadata & metadata __unused)1069 Return<void> CameraHidlTest::Camera1DeviceCb::dataCallback(
1070         DataCallbackMsg msgType __unused, uint32_t data __unused,
1071         uint32_t bufferIndex __unused,
1072         const CameraFrameMetadata& metadata __unused) {
1073     std::unique_lock<std::mutex> l(mParent->mLock);
1074     mParent->mDataMessageTypeReceived = msgType;
1075     mParent->mResultCondition.notify_one();
1076 
1077     return Void();
1078 }
1079 
dataCallbackTimestamp(DataCallbackMsg msgType,uint32_t data,uint32_t bufferIndex,int64_t timestamp __unused)1080 Return<void> CameraHidlTest::Camera1DeviceCb::dataCallbackTimestamp(
1081         DataCallbackMsg msgType, uint32_t data,
1082         uint32_t bufferIndex, int64_t timestamp __unused) {
1083     std::unique_lock<std::mutex> l(mParent->mLock);
1084     mParent->mDataMessageTypeReceived = msgType;
1085     mParent->mVideoBufferIndex = bufferIndex;
1086     if (mParent->mMemoryPool.count(data) == 0) {
1087         ADD_FAILURE() << "memory pool ID " << data << "not found";
1088     }
1089     mParent->mVideoData = data;
1090     mParent->mResultCondition.notify_one();
1091 
1092     return Void();
1093 }
1094 
handleCallbackTimestamp(DataCallbackMsg msgType,const hidl_handle & frameData,uint32_t data __unused,uint32_t bufferIndex,int64_t timestamp __unused)1095 Return<void> CameraHidlTest::Camera1DeviceCb::handleCallbackTimestamp(
1096         DataCallbackMsg msgType, const hidl_handle& frameData,
1097         uint32_t data __unused, uint32_t bufferIndex,
1098         int64_t timestamp __unused) {
1099     std::unique_lock<std::mutex> l(mParent->mLock);
1100     mParent->mDataMessageTypeReceived = msgType;
1101     mParent->mVideoBufferIndex = bufferIndex;
1102     if (mParent->mMemoryPool.count(data) == 0) {
1103         ADD_FAILURE() << "memory pool ID " << data << " not found";
1104     }
1105     mParent->mVideoData = data;
1106     mParent->mVideoNativeHandle = frameData;
1107     mParent->mResultCondition.notify_one();
1108 
1109     return Void();
1110 }
1111 
handleCallbackTimestampBatch(DataCallbackMsg msgType,const hidl_vec<HandleTimestampMessage> & batch)1112 Return<void> CameraHidlTest::Camera1DeviceCb::handleCallbackTimestampBatch(
1113         DataCallbackMsg msgType,
1114         const hidl_vec<HandleTimestampMessage>& batch) {
1115     std::unique_lock<std::mutex> l(mParent->mLock);
1116     for (auto& msg : batch) {
1117         mParent->mDataMessageTypeReceived = msgType;
1118         mParent->mVideoBufferIndex = msg.bufferIndex;
1119         if (mParent->mMemoryPool.count(msg.data) == 0) {
1120             ADD_FAILURE() << "memory pool ID " << msg.data << " not found";
1121         }
1122         mParent->mVideoData = msg.data;
1123         mParent->mVideoNativeHandle = msg.frameData;
1124         mParent->mResultCondition.notify_one();
1125     }
1126     return Void();
1127 }
1128 
processCaptureResult_3_4(const hidl_vec<V3_4::CaptureResult> & results)1129 Return<void> CameraHidlTest::DeviceCb::processCaptureResult_3_4(
1130         const hidl_vec<V3_4::CaptureResult>& results) {
1131 
1132     if (nullptr == mParent) {
1133         return Void();
1134     }
1135 
1136     bool notify = false;
1137     std::unique_lock<std::mutex> l(mParent->mLock);
1138     for (size_t i = 0 ; i < results.size(); i++) {
1139         notify = processCaptureResultLocked(results[i].v3_2, results[i].physicalCameraMetadata);
1140     }
1141 
1142     l.unlock();
1143     if (notify) {
1144         mParent->mResultCondition.notify_one();
1145     }
1146 
1147     return Void();
1148 }
1149 
processCaptureResult(const hidl_vec<CaptureResult> & results)1150 Return<void> CameraHidlTest::DeviceCb::processCaptureResult(
1151         const hidl_vec<CaptureResult>& results) {
1152     if (nullptr == mParent) {
1153         return Void();
1154     }
1155 
1156     bool notify = false;
1157     std::unique_lock<std::mutex> l(mParent->mLock);
1158     ::android::hardware::hidl_vec<PhysicalCameraMetadata> noPhysMetadata;
1159     for (size_t i = 0 ; i < results.size(); i++) {
1160         notify = processCaptureResultLocked(results[i], noPhysMetadata);
1161     }
1162 
1163     l.unlock();
1164     if (notify) {
1165         mParent->mResultCondition.notify_one();
1166     }
1167 
1168     return Void();
1169 }
1170 
processCaptureResultLocked(const CaptureResult & results,hidl_vec<PhysicalCameraMetadata> physicalCameraMetadata)1171 bool CameraHidlTest::DeviceCb::processCaptureResultLocked(const CaptureResult& results,
1172         hidl_vec<PhysicalCameraMetadata> physicalCameraMetadata) {
1173     bool notify = false;
1174     uint32_t frameNumber = results.frameNumber;
1175 
1176     if ((results.result.size() == 0) &&
1177             (results.outputBuffers.size() == 0) &&
1178             (results.inputBuffer.buffer == nullptr) &&
1179             (results.fmqResultSize == 0)) {
1180         ALOGE("%s: No result data provided by HAL for frame %d result count: %d",
1181                 __func__, frameNumber, (int) results.fmqResultSize);
1182         ADD_FAILURE();
1183         return notify;
1184     }
1185 
1186     ssize_t idx = mParent->mInflightMap.indexOfKey(frameNumber);
1187     if (::android::NAME_NOT_FOUND == idx) {
1188         ALOGE("%s: Unexpected frame number! received: %u",
1189                 __func__, frameNumber);
1190         ADD_FAILURE();
1191         return notify;
1192     }
1193 
1194     bool isPartialResult = false;
1195     bool hasInputBufferInRequest = false;
1196     InFlightRequest *request = mParent->mInflightMap.editValueAt(idx);
1197     ::android::hardware::camera::device::V3_2::CameraMetadata resultMetadata;
1198     size_t resultSize = 0;
1199     if (results.fmqResultSize > 0) {
1200         resultMetadata.resize(results.fmqResultSize);
1201         if (request->resultQueue == nullptr) {
1202             ADD_FAILURE();
1203             return notify;
1204         }
1205         if (!request->resultQueue->read(resultMetadata.data(),
1206                     results.fmqResultSize)) {
1207             ALOGE("%s: Frame %d: Cannot read camera metadata from fmq,"
1208                     "size = %" PRIu64, __func__, frameNumber,
1209                     results.fmqResultSize);
1210             ADD_FAILURE();
1211             return notify;
1212         }
1213 
1214         if (physicalCameraMetadata.size() != request->expectedPhysicalResults.size()) {
1215             ALOGE("%s: Frame %d: Returned physical metadata count %zu "
1216                     "must be equal to expected count %zu", __func__, frameNumber,
1217                     physicalCameraMetadata.size(), request->expectedPhysicalResults.size());
1218             ADD_FAILURE();
1219             return notify;
1220         }
1221         std::vector<::android::hardware::camera::device::V3_2::CameraMetadata> physResultMetadata;
1222         physResultMetadata.resize(physicalCameraMetadata.size());
1223         for (size_t i = 0; i < physicalCameraMetadata.size(); i++) {
1224             physResultMetadata[i].resize(physicalCameraMetadata[i].fmqMetadataSize);
1225             if (!request->resultQueue->read(physResultMetadata[i].data(),
1226                     physicalCameraMetadata[i].fmqMetadataSize)) {
1227                 ALOGE("%s: Frame %d: Cannot read physical camera metadata from fmq,"
1228                         "size = %" PRIu64, __func__, frameNumber,
1229                         physicalCameraMetadata[i].fmqMetadataSize);
1230                 ADD_FAILURE();
1231                 return notify;
1232             }
1233         }
1234         resultSize = resultMetadata.size();
1235     } else if (results.result.size() > 0) {
1236         resultMetadata.setToExternal(const_cast<uint8_t *>(
1237                     results.result.data()), results.result.size());
1238         resultSize = resultMetadata.size();
1239     }
1240 
1241     if (!request->usePartialResult && (resultSize > 0) &&
1242             (results.partialResult != 1)) {
1243         ALOGE("%s: Result is malformed for frame %d: partial_result %u "
1244                 "must be 1  if partial result is not supported", __func__,
1245                 frameNumber, results.partialResult);
1246         ADD_FAILURE();
1247         return notify;
1248     }
1249 
1250     if (results.partialResult != 0) {
1251         request->partialResultCount = results.partialResult;
1252     }
1253 
1254     // Check if this result carries only partial metadata
1255     if (request->usePartialResult && (resultSize > 0)) {
1256         if ((results.partialResult > request->numPartialResults) ||
1257                 (results.partialResult < 1)) {
1258             ALOGE("%s: Result is malformed for frame %d: partial_result %u"
1259                     " must be  in the range of [1, %d] when metadata is "
1260                     "included in the result", __func__, frameNumber,
1261                     results.partialResult, request->numPartialResults);
1262             ADD_FAILURE();
1263             return notify;
1264         }
1265         request->collectedResult.append(
1266                 reinterpret_cast<const camera_metadata_t*>(
1267                     resultMetadata.data()));
1268 
1269         isPartialResult =
1270             (results.partialResult < request->numPartialResults);
1271     } else if (resultSize > 0) {
1272         request->collectedResult.append(reinterpret_cast<const camera_metadata_t*>(
1273                     resultMetadata.data()));
1274         isPartialResult = false;
1275     }
1276 
1277     hasInputBufferInRequest = request->hasInputBuffer;
1278 
1279     // Did we get the (final) result metadata for this capture?
1280     if ((resultSize > 0) && !isPartialResult) {
1281         if (request->haveResultMetadata) {
1282             ALOGE("%s: Called multiple times with metadata for frame %d",
1283                     __func__, frameNumber);
1284             ADD_FAILURE();
1285             return notify;
1286         }
1287         request->haveResultMetadata = true;
1288         request->collectedResult.sort();
1289 
1290         // Verify final result metadata
1291         bool isAtLeast_3_5 = mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_5;
1292         if (isAtLeast_3_5) {
1293             auto staticMetadataBuffer = mStaticMetadata.getAndLock();
1294             bool isMonochrome = Status::OK ==
1295                     CameraHidlTest::isMonochromeCamera(staticMetadataBuffer);
1296             if (isMonochrome) {
1297                 mParent->verifyMonochromeCameraResult(request->collectedResult);
1298             }
1299 
1300             // Verify logical camera result metadata
1301             bool isLogicalCamera =
1302                     Status::OK == CameraHidlTest::isLogicalMultiCamera(staticMetadataBuffer);
1303             if (isLogicalCamera) {
1304                 mParent->verifyLogicalCameraResult(staticMetadataBuffer, request->collectedResult);
1305             }
1306             mStaticMetadata.unlock(staticMetadataBuffer);
1307         }
1308     }
1309 
1310     uint32_t numBuffersReturned = results.outputBuffers.size();
1311     if (results.inputBuffer.buffer != nullptr) {
1312         if (hasInputBufferInRequest) {
1313             numBuffersReturned += 1;
1314         } else {
1315             ALOGW("%s: Input buffer should be NULL if there is no input"
1316                     " buffer sent in the request", __func__);
1317         }
1318     }
1319     request->numBuffersLeft -= numBuffersReturned;
1320     if (request->numBuffersLeft < 0) {
1321         ALOGE("%s: Too many buffers returned for frame %d", __func__,
1322                 frameNumber);
1323         ADD_FAILURE();
1324         return notify;
1325     }
1326 
1327     request->resultOutputBuffers.appendArray(results.outputBuffers.data(),
1328             results.outputBuffers.size());
1329     // If shutter event is received notify the pending threads.
1330     if (request->shutterTimestamp != 0) {
1331         notify = true;
1332     }
1333 
1334     if (mUseHalBufManager) {
1335         // Don't return buffers of bufId 0 (empty buffer)
1336         std::vector<StreamBuffer> buffers;
1337         for (const auto& sb : results.outputBuffers) {
1338             if (sb.bufferId != 0) {
1339                 buffers.push_back(sb);
1340             }
1341         }
1342         returnStreamBuffers(buffers);
1343     }
1344     return notify;
1345 }
1346 
setCurrentStreamConfig(const hidl_vec<V3_4::Stream> & streams,const hidl_vec<V3_2::HalStream> & halStreams)1347 void CameraHidlTest::DeviceCb::setCurrentStreamConfig(
1348         const hidl_vec<V3_4::Stream>& streams, const hidl_vec<V3_2::HalStream>& halStreams) {
1349     ASSERT_EQ(streams.size(), halStreams.size());
1350     ASSERT_NE(streams.size(), 0);
1351     for (size_t i = 0; i < streams.size(); i++) {
1352         ASSERT_EQ(streams[i].v3_2.id, halStreams[i].id);
1353     }
1354     std::lock_guard<std::mutex> l(mLock);
1355     mUseHalBufManager = true;
1356     mStreams = streams;
1357     mHalStreams = halStreams;
1358     mOutstandingBufferIds.clear();
1359     for (size_t i = 0; i < streams.size(); i++) {
1360         mOutstandingBufferIds.emplace_back();
1361     }
1362 }
1363 
hasOutstandingBuffersLocked()1364 bool CameraHidlTest::DeviceCb::hasOutstandingBuffersLocked() {
1365     if (!mUseHalBufManager) {
1366         return false;
1367     }
1368     for (const auto& outstandingBuffers : mOutstandingBufferIds) {
1369         if (!outstandingBuffers.empty()) {
1370             return true;
1371         }
1372     }
1373     return false;
1374 }
1375 
waitForBuffersReturned()1376 void CameraHidlTest::DeviceCb::waitForBuffersReturned() {
1377     std::unique_lock<std::mutex> lk(mLock);
1378     if (hasOutstandingBuffersLocked()) {
1379         auto timeout = std::chrono::seconds(kBufferReturnTimeoutSec);
1380         auto st = mFlushedCondition.wait_for(lk, timeout);
1381         ASSERT_NE(std::cv_status::timeout, st);
1382     }
1383 }
1384 
notify(const hidl_vec<NotifyMsg> & messages)1385 Return<void> CameraHidlTest::DeviceCb::notify(
1386         const hidl_vec<NotifyMsg>& messages) {
1387     std::lock_guard<std::mutex> l(mParent->mLock);
1388 
1389     for (size_t i = 0; i < messages.size(); i++) {
1390         switch(messages[i].type) {
1391             case MsgType::ERROR:
1392                 if (ErrorCode::ERROR_DEVICE == messages[i].msg.error.errorCode) {
1393                     ALOGE("%s: Camera reported serious device error",
1394                           __func__);
1395                     ADD_FAILURE();
1396                 } else {
1397                     ssize_t idx = mParent->mInflightMap.indexOfKey(
1398                             messages[i].msg.error.frameNumber);
1399                     if (::android::NAME_NOT_FOUND == idx) {
1400                         ALOGE("%s: Unexpected error frame number! received: %u",
1401                               __func__, messages[i].msg.error.frameNumber);
1402                         ADD_FAILURE();
1403                         break;
1404                     }
1405                     InFlightRequest *r = mParent->mInflightMap.editValueAt(idx);
1406 
1407                     if (ErrorCode::ERROR_RESULT == messages[i].msg.error.errorCode &&
1408                             messages[i].msg.error.errorStreamId != -1) {
1409                         if (r->haveResultMetadata) {
1410                             ALOGE("%s: Camera must report physical camera result error before "
1411                                     "the final capture result!", __func__);
1412                             ADD_FAILURE();
1413                         } else {
1414                             for (size_t j = 0; j < mStreams.size(); j++) {
1415                                 if (mStreams[j].v3_2.id == messages[i].msg.error.errorStreamId) {
1416                                     hidl_string physicalCameraId = mStreams[j].physicalCameraId;
1417                                     bool idExpected = r->expectedPhysicalResults.find(
1418                                             physicalCameraId) != r->expectedPhysicalResults.end();
1419                                     if (!idExpected) {
1420                                         ALOGE("%s: ERROR_RESULT's error stream's physicalCameraId "
1421                                                 "%s must be expected", __func__,
1422                                                 physicalCameraId.c_str());
1423                                         ADD_FAILURE();
1424                                     } else {
1425                                         r->expectedPhysicalResults.erase(physicalCameraId);
1426                                     }
1427                                     break;
1428                                 }
1429                             }
1430                         }
1431                     } else {
1432                         r->errorCodeValid = true;
1433                         r->errorCode = messages[i].msg.error.errorCode;
1434                         r->errorStreamId = messages[i].msg.error.errorStreamId;
1435                   }
1436                 }
1437                 break;
1438             case MsgType::SHUTTER:
1439             {
1440                 ssize_t idx = mParent->mInflightMap.indexOfKey(messages[i].msg.shutter.frameNumber);
1441                 if (::android::NAME_NOT_FOUND == idx) {
1442                     ALOGE("%s: Unexpected shutter frame number! received: %u",
1443                           __func__, messages[i].msg.shutter.frameNumber);
1444                     ADD_FAILURE();
1445                     break;
1446                 }
1447                 InFlightRequest *r = mParent->mInflightMap.editValueAt(idx);
1448                 r->shutterTimestamp = messages[i].msg.shutter.timestamp;
1449             }
1450                 break;
1451             default:
1452                 ALOGE("%s: Unsupported notify message %d", __func__,
1453                       messages[i].type);
1454                 ADD_FAILURE();
1455                 break;
1456         }
1457     }
1458 
1459     mParent->mResultCondition.notify_one();
1460     return Void();
1461 }
1462 
requestStreamBuffers(const hidl_vec<V3_5::BufferRequest> & bufReqs,requestStreamBuffers_cb _hidl_cb)1463 Return<void> CameraHidlTest::DeviceCb::requestStreamBuffers(
1464         const hidl_vec<V3_5::BufferRequest>& bufReqs,
1465         requestStreamBuffers_cb _hidl_cb) {
1466     using V3_5::BufferRequestStatus;
1467     using V3_5::StreamBufferRet;
1468     using V3_5::StreamBufferRequestError;
1469     hidl_vec<StreamBufferRet> bufRets;
1470     std::unique_lock<std::mutex> l(mLock);
1471 
1472     if (!mUseHalBufManager) {
1473         ALOGE("%s: Camera does not support HAL buffer management", __FUNCTION__);
1474         ADD_FAILURE();
1475         _hidl_cb(BufferRequestStatus::FAILED_ILLEGAL_ARGUMENTS, bufRets);
1476         return Void();
1477     }
1478 
1479     if (bufReqs.size() > mStreams.size()) {
1480         ALOGE("%s: illegal buffer request: too many requests!", __FUNCTION__);
1481         ADD_FAILURE();
1482         _hidl_cb(BufferRequestStatus::FAILED_ILLEGAL_ARGUMENTS, bufRets);
1483         return Void();
1484     }
1485 
1486     std::vector<int32_t> indexes(bufReqs.size());
1487     for (size_t i = 0; i < bufReqs.size(); i++) {
1488         bool found = false;
1489         for (size_t idx = 0; idx < mStreams.size(); idx++) {
1490             if (bufReqs[i].streamId == mStreams[idx].v3_2.id) {
1491                 found = true;
1492                 indexes[i] = idx;
1493                 break;
1494             }
1495         }
1496         if (!found) {
1497             ALOGE("%s: illegal buffer request: unknown streamId %d!",
1498                     __FUNCTION__, bufReqs[i].streamId);
1499             ADD_FAILURE();
1500             _hidl_cb(BufferRequestStatus::FAILED_ILLEGAL_ARGUMENTS, bufRets);
1501             return Void();
1502         }
1503     }
1504 
1505     bool allStreamOk = true;
1506     bool atLeastOneStreamOk = false;
1507     bufRets.resize(bufReqs.size());
1508     for (size_t i = 0; i < bufReqs.size(); i++) {
1509         int32_t idx = indexes[i];
1510         const auto& stream = mStreams[idx];
1511         const auto& halStream = mHalStreams[idx];
1512         const V3_5::BufferRequest& bufReq = bufReqs[i];
1513         if (mOutstandingBufferIds[idx].size() + bufReq.numBuffersRequested > halStream.maxBuffers) {
1514             bufRets[i].streamId = stream.v3_2.id;
1515             bufRets[i].val.error(StreamBufferRequestError::MAX_BUFFER_EXCEEDED);
1516             allStreamOk = false;
1517             continue;
1518         }
1519 
1520         hidl_vec<StreamBuffer> tmpRetBuffers(bufReq.numBuffersRequested);
1521         for (size_t j = 0; j < bufReq.numBuffersRequested; j++) {
1522             hidl_handle buffer_handle;
1523             uint32_t w = stream.v3_2.width;
1524             uint32_t h = stream.v3_2.height;
1525             if (stream.v3_2.format == PixelFormat::BLOB) {
1526                 w = stream.bufferSize;
1527                 h = 1;
1528             }
1529             mParent->allocateGraphicBuffer(w, h,
1530                     android_convertGralloc1To0Usage(
1531                             halStream.producerUsage, halStream.consumerUsage),
1532                     halStream.overrideFormat, &buffer_handle);
1533 
1534             tmpRetBuffers[j] = {stream.v3_2.id, mNextBufferId, buffer_handle, BufferStatus::OK,
1535                                 nullptr, nullptr};
1536             mOutstandingBufferIds[idx].insert(std::make_pair(mNextBufferId++, buffer_handle));
1537         }
1538         atLeastOneStreamOk = true;
1539         bufRets[i].streamId = stream.v3_2.id;
1540         bufRets[i].val.buffers(std::move(tmpRetBuffers));
1541     }
1542 
1543     if (allStreamOk) {
1544         _hidl_cb(BufferRequestStatus::OK, bufRets);
1545     } else if (atLeastOneStreamOk) {
1546         _hidl_cb(BufferRequestStatus::FAILED_PARTIAL, bufRets);
1547     } else {
1548         _hidl_cb(BufferRequestStatus::FAILED_UNKNOWN, bufRets);
1549     }
1550 
1551     if (!hasOutstandingBuffersLocked()) {
1552         l.unlock();
1553         mFlushedCondition.notify_one();
1554     }
1555     return Void();
1556 }
1557 
returnStreamBuffers(const hidl_vec<StreamBuffer> & buffers)1558 Return<void> CameraHidlTest::DeviceCb::returnStreamBuffers(
1559         const hidl_vec<StreamBuffer>& buffers) {
1560     if (!mUseHalBufManager) {
1561         ALOGE("%s: Camera does not support HAL buffer management", __FUNCTION__);
1562         ADD_FAILURE();
1563     }
1564 
1565     std::unique_lock<std::mutex> l(mLock);
1566     for (const auto& buf : buffers) {
1567         bool found = false;
1568         for (size_t idx = 0; idx < mOutstandingBufferIds.size(); idx++) {
1569             if (mStreams[idx].v3_2.id == buf.streamId &&
1570                     mOutstandingBufferIds[idx].count(buf.bufferId) == 1) {
1571                 mOutstandingBufferIds[idx].erase(buf.bufferId);
1572                 // TODO: check do we need to close/delete native handle or assume we have enough
1573                 // memory to run till the test finish? since we do not capture much requests (and
1574                 // most of time one buffer is sufficient)
1575                 found = true;
1576                 break;
1577             }
1578         }
1579         if (found) {
1580             continue;
1581         }
1582         ALOGE("%s: unknown buffer ID %" PRIu64, __FUNCTION__, buf.bufferId);
1583         ADD_FAILURE();
1584     }
1585     if (!hasOutstandingBuffersLocked()) {
1586         l.unlock();
1587         mFlushedCondition.notify_one();
1588     }
1589     return Void();
1590 }
1591 
getCameraDeviceIdToNameMap(sp<ICameraProvider> provider)1592 std::map<hidl_string, hidl_string> CameraHidlTest::getCameraDeviceIdToNameMap(
1593         sp<ICameraProvider> provider) {
1594     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(provider);
1595     std::map<hidl_string, hidl_string> idToNameMap;
1596     for (auto& name : cameraDeviceNames) {
1597         std::string version, cameraId;
1598         if (!matchDeviceName(name, mProviderType, &version, &cameraId)) {
1599             ADD_FAILURE();
1600         }
1601         idToNameMap.insert(std::make_pair(hidl_string(cameraId), name));
1602     }
1603     return idToNameMap;
1604 }
1605 
getCameraDeviceNames(sp<ICameraProvider> provider,bool addSecureOnly)1606 hidl_vec<hidl_string> CameraHidlTest::getCameraDeviceNames(sp<ICameraProvider> provider,
1607                                                            bool addSecureOnly) {
1608     std::vector<std::string> cameraDeviceNames;
1609     Return<void> ret;
1610     ret = provider->getCameraIdList(
1611         [&](auto status, const auto& idList) {
1612             ALOGI("getCameraIdList returns status:%d", (int)status);
1613             for (size_t i = 0; i < idList.size(); i++) {
1614                 ALOGI("Camera Id[%zu] is %s", i, idList[i].c_str());
1615             }
1616             ASSERT_EQ(Status::OK, status);
1617             for (const auto& id : idList) {
1618                 cameraDeviceNames.push_back(id);
1619             }
1620         });
1621     if (!ret.isOk()) {
1622         ADD_FAILURE();
1623     }
1624 
1625     // External camera devices are reported through cameraDeviceStatusChange
1626     struct ProviderCb : public ICameraProviderCallback {
1627         virtual Return<void> cameraDeviceStatusChange(
1628                 const hidl_string& devName,
1629                 CameraDeviceStatus newStatus) override {
1630             ALOGI("camera device status callback name %s, status %d",
1631                     devName.c_str(), (int) newStatus);
1632             if (newStatus == CameraDeviceStatus::PRESENT) {
1633                 externalCameraDeviceNames.push_back(devName);
1634 
1635             }
1636             return Void();
1637         }
1638 
1639         virtual Return<void> torchModeStatusChange(
1640                 const hidl_string&, TorchModeStatus) override {
1641             return Void();
1642         }
1643 
1644         std::vector<std::string> externalCameraDeviceNames;
1645     };
1646     sp<ProviderCb> cb = new ProviderCb;
1647     auto status = mProvider->setCallback(cb);
1648 
1649     for (const auto& devName : cb->externalCameraDeviceNames) {
1650         if (cameraDeviceNames.end() == std::find(
1651                 cameraDeviceNames.begin(), cameraDeviceNames.end(), devName)) {
1652             cameraDeviceNames.push_back(devName);
1653         }
1654     }
1655 
1656     std::vector<hidl_string> retList;
1657     for (size_t i = 0; i < cameraDeviceNames.size(); i++) {
1658         bool isSecureOnlyCamera = isSecureOnly(mProvider, cameraDeviceNames[i]);
1659         if (addSecureOnly) {
1660             if (isSecureOnlyCamera) {
1661                 retList.emplace_back(cameraDeviceNames[i]);
1662             }
1663         } else if (!isSecureOnlyCamera) {
1664             retList.emplace_back(cameraDeviceNames[i]);
1665         }
1666     }
1667     hidl_vec<hidl_string> finalRetList = std::move(retList);
1668     return finalRetList;
1669 }
1670 
isSecureOnly(sp<ICameraProvider> provider,const hidl_string & name)1671 bool CameraHidlTest::isSecureOnly(sp<ICameraProvider> provider, const hidl_string& name) {
1672     Return<void> ret;
1673     ::android::sp<ICameraDevice> device3_x;
1674     bool retVal = false;
1675     if (getCameraDeviceVersion(mProviderType, name) == CAMERA_DEVICE_API_VERSION_1_0) {
1676         return false;
1677     }
1678     ret = provider->getCameraDeviceInterface_V3_x(name, [&](auto status, const auto& device) {
1679         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
1680         ASSERT_EQ(Status::OK, status);
1681         ASSERT_NE(device, nullptr);
1682         device3_x = device;
1683     });
1684     if (!ret.isOk()) {
1685         ADD_FAILURE() << "Failed to get camera device interface for " << name;
1686     }
1687     ret = device3_x->getCameraCharacteristics([&](Status s, CameraMetadata metadata) {
1688         ASSERT_EQ(Status::OK, s);
1689         camera_metadata_t* chars = (camera_metadata_t*)metadata.data();
1690         SystemCameraKind systemCameraKind = SystemCameraKind::PUBLIC;
1691         Status status = getSystemCameraKind(chars, &systemCameraKind);
1692         ASSERT_EQ(status, Status::OK);
1693         if (systemCameraKind == SystemCameraKind::HIDDEN_SECURE_CAMERA) {
1694             retVal = true;
1695         }
1696     });
1697     if (!ret.isOk()) {
1698         ADD_FAILURE() << "Failed to get camera characteristics for device " << name;
1699     }
1700     return retVal;
1701 }
1702 
getConcurrentDeviceCombinations(sp<::android::hardware::camera::provider::V2_6::ICameraProvider> & provider2_6)1703 hidl_vec<hidl_vec<hidl_string>> CameraHidlTest::getConcurrentDeviceCombinations(
1704         sp<::android::hardware::camera::provider::V2_6::ICameraProvider>& provider2_6) {
1705     hidl_vec<hidl_vec<hidl_string>> combinations;
1706     Return<void> ret = provider2_6->getConcurrentStreamingCameraIds(
1707             [&combinations](Status concurrentIdStatus,
1708                             const hidl_vec<hidl_vec<hidl_string>>& cameraDeviceIdCombinations) {
1709                 ASSERT_EQ(concurrentIdStatus, Status::OK);
1710                 combinations = cameraDeviceIdCombinations;
1711             });
1712     if (!ret.isOk()) {
1713         ADD_FAILURE();
1714     }
1715     return combinations;
1716 }
1717 
1718 // Test devices with first_api_level >= P does not advertise device@1.0
TEST_P(CameraHidlTest,noHal1AfterP)1719 TEST_P(CameraHidlTest, noHal1AfterP) {
1720     constexpr int32_t HAL1_PHASE_OUT_API_LEVEL = 28;
1721     int32_t firstApiLevel = 0;
1722     getFirstApiLevel(&firstApiLevel);
1723 
1724     // all devices with first API level == 28 and <= 1GB of RAM must set low_ram
1725     // and thus be allowed to continue using HAL1
1726     if ((firstApiLevel == HAL1_PHASE_OUT_API_LEVEL) &&
1727         (property_get_bool("ro.config.low_ram", /*default*/ false))) {
1728         ALOGI("Hal1 allowed for low ram device");
1729         return;
1730     }
1731 
1732     if (firstApiLevel >= HAL1_PHASE_OUT_API_LEVEL) {
1733         hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
1734         for (const auto& name : cameraDeviceNames) {
1735             int deviceVersion = getCameraDeviceVersion(name, mProviderType);
1736             ASSERT_NE(deviceVersion, 0); // Must be a valid device version
1737             ASSERT_NE(deviceVersion, CAMERA_DEVICE_API_VERSION_1_0); // Must not be device@1.0
1738         }
1739     }
1740 }
1741 
1742 // Test if ICameraProvider::isTorchModeSupported returns Status::OK
1743 // Also if first_api_level >= Q torch API must be supported.
TEST_P(CameraHidlTest,isTorchModeSupported)1744 TEST_P(CameraHidlTest, isTorchModeSupported) {
1745     constexpr int32_t API_LEVEL_Q = 29;
1746     int32_t firstApiLevel = 0;
1747     getFirstApiLevel(&firstApiLevel);
1748 
1749     Return<void> ret;
1750     ret = mProvider->isSetTorchModeSupported([&](auto status, bool support) {
1751         ALOGI("isSetTorchModeSupported returns status:%d supported:%d", (int)status, support);
1752         ASSERT_EQ(Status::OK, status);
1753         if (firstApiLevel >= API_LEVEL_Q) {
1754             ASSERT_EQ(true, support);
1755         }
1756     });
1757     ASSERT_TRUE(ret.isOk());
1758 }
1759 
1760 // TODO: consider removing this test if getCameraDeviceNames() has the same coverage
TEST_P(CameraHidlTest,getCameraIdList)1761 TEST_P(CameraHidlTest, getCameraIdList) {
1762     Return<void> ret;
1763     ret = mProvider->getCameraIdList([&](auto status, const auto& idList) {
1764         ALOGI("getCameraIdList returns status:%d", (int)status);
1765         for (size_t i = 0; i < idList.size(); i++) {
1766             ALOGI("Camera Id[%zu] is %s", i, idList[i].c_str());
1767         }
1768         ASSERT_EQ(Status::OK, status);
1769     });
1770     ASSERT_TRUE(ret.isOk());
1771 }
1772 
1773 // Test if ICameraProvider::getVendorTags returns Status::OK
TEST_P(CameraHidlTest,getVendorTags)1774 TEST_P(CameraHidlTest, getVendorTags) {
1775     Return<void> ret;
1776     ret = mProvider->getVendorTags([&](auto status, const auto& vendorTagSecs) {
1777         ALOGI("getVendorTags returns status:%d numSections %zu", (int)status, vendorTagSecs.size());
1778         for (size_t i = 0; i < vendorTagSecs.size(); i++) {
1779             ALOGI("Vendor tag section %zu name %s", i, vendorTagSecs[i].sectionName.c_str());
1780             for (size_t j = 0; j < vendorTagSecs[i].tags.size(); j++) {
1781                 const auto& tag = vendorTagSecs[i].tags[j];
1782                 ALOGI("Vendor tag id %u name %s type %d", tag.tagId, tag.tagName.c_str(),
1783                       (int)tag.tagType);
1784             }
1785         }
1786         ASSERT_EQ(Status::OK, status);
1787     });
1788     ASSERT_TRUE(ret.isOk());
1789 }
1790 
1791 // Test if ICameraProvider::setCallback returns Status::OK
TEST_P(CameraHidlTest,setCallback)1792 TEST_P(CameraHidlTest, setCallback) {
1793     struct ProviderCb : public ICameraProviderCallback {
1794         virtual Return<void> cameraDeviceStatusChange(
1795                 const hidl_string& cameraDeviceName,
1796                 CameraDeviceStatus newStatus) override {
1797             ALOGI("camera device status callback name %s, status %d",
1798                     cameraDeviceName.c_str(), (int) newStatus);
1799             return Void();
1800         }
1801 
1802         virtual Return<void> torchModeStatusChange(
1803                 const hidl_string& cameraDeviceName,
1804                 TorchModeStatus newStatus) override {
1805             ALOGI("Torch mode status callback name %s, status %d",
1806                     cameraDeviceName.c_str(), (int) newStatus);
1807             return Void();
1808         }
1809     };
1810 
1811     struct ProviderCb2_6
1812         : public ::android::hardware::camera::provider::V2_6::ICameraProviderCallback {
1813         virtual Return<void> cameraDeviceStatusChange(const hidl_string& cameraDeviceName,
1814                                                       CameraDeviceStatus newStatus) override {
1815             ALOGI("camera device status callback name %s, status %d", cameraDeviceName.c_str(),
1816                   (int)newStatus);
1817             return Void();
1818         }
1819 
1820         virtual Return<void> torchModeStatusChange(const hidl_string& cameraDeviceName,
1821                                                    TorchModeStatus newStatus) override {
1822             ALOGI("Torch mode status callback name %s, status %d", cameraDeviceName.c_str(),
1823                   (int)newStatus);
1824             return Void();
1825         }
1826 
1827         virtual Return<void> physicalCameraDeviceStatusChange(
1828                 const hidl_string& cameraDeviceName, const hidl_string& physicalCameraDeviceName,
1829                 CameraDeviceStatus newStatus) override {
1830             ALOGI("physical camera device status callback name %s, physical camera name %s,"
1831                   " status %d",
1832                   cameraDeviceName.c_str(), physicalCameraDeviceName.c_str(), (int)newStatus);
1833             return Void();
1834         }
1835     };
1836 
1837     sp<ProviderCb> cb = new ProviderCb;
1838     auto status = mProvider->setCallback(cb);
1839     ASSERT_TRUE(status.isOk());
1840     ASSERT_EQ(Status::OK, status);
1841     status = mProvider->setCallback(nullptr);
1842     ASSERT_TRUE(status.isOk());
1843     ASSERT_EQ(Status::OK, status);
1844 
1845     if (mProvider2_6.get() != nullptr) {
1846         sp<ProviderCb2_6> cb = new ProviderCb2_6;
1847         auto status = mProvider2_6->setCallback(cb);
1848         ASSERT_TRUE(status.isOk());
1849         ASSERT_EQ(Status::OK, status);
1850         status = mProvider2_6->setCallback(nullptr);
1851         ASSERT_TRUE(status.isOk());
1852         ASSERT_EQ(Status::OK, status);
1853     }
1854 }
1855 
1856 // Test if ICameraProvider::getCameraDeviceInterface returns Status::OK and non-null device
TEST_P(CameraHidlTest,getCameraDeviceInterface)1857 TEST_P(CameraHidlTest, getCameraDeviceInterface) {
1858     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
1859 
1860     for (const auto& name : cameraDeviceNames) {
1861         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
1862         switch (deviceVersion) {
1863             case CAMERA_DEVICE_API_VERSION_3_6:
1864             case CAMERA_DEVICE_API_VERSION_3_5:
1865             case CAMERA_DEVICE_API_VERSION_3_4:
1866             case CAMERA_DEVICE_API_VERSION_3_3:
1867             case CAMERA_DEVICE_API_VERSION_3_2: {
1868                 Return<void> ret;
1869                 ret = mProvider->getCameraDeviceInterface_V3_x(
1870                     name, [&](auto status, const auto& device3_x) {
1871                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
1872                         ASSERT_EQ(Status::OK, status);
1873                         ASSERT_NE(device3_x, nullptr);
1874                     });
1875                 ASSERT_TRUE(ret.isOk());
1876             }
1877             break;
1878             case CAMERA_DEVICE_API_VERSION_1_0: {
1879                 Return<void> ret;
1880                 ret = mProvider->getCameraDeviceInterface_V1_x(
1881                     name, [&](auto status, const auto& device1) {
1882                         ALOGI("getCameraDeviceInterface_V1_x returns status:%d", (int)status);
1883                         ASSERT_EQ(Status::OK, status);
1884                         ASSERT_NE(device1, nullptr);
1885                     });
1886                 ASSERT_TRUE(ret.isOk());
1887             }
1888             break;
1889             default: {
1890                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
1891                 ADD_FAILURE();
1892             }
1893             break;
1894         }
1895     }
1896 }
1897 
1898 // Verify that the device resource cost can be retrieved and the values are
1899 // correct.
TEST_P(CameraHidlTest,getResourceCost)1900 TEST_P(CameraHidlTest, getResourceCost) {
1901     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
1902 
1903     for (const auto& name : cameraDeviceNames) {
1904         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
1905         switch (deviceVersion) {
1906             case CAMERA_DEVICE_API_VERSION_3_6:
1907             case CAMERA_DEVICE_API_VERSION_3_5:
1908             case CAMERA_DEVICE_API_VERSION_3_4:
1909             case CAMERA_DEVICE_API_VERSION_3_3:
1910             case CAMERA_DEVICE_API_VERSION_3_2: {
1911                 ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> device3_x;
1912                 ALOGI("getResourceCost: Testing camera device %s", name.c_str());
1913                 Return<void> ret;
1914                 ret = mProvider->getCameraDeviceInterface_V3_x(
1915                     name, [&](auto status, const auto& device) {
1916                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
1917                         ASSERT_EQ(Status::OK, status);
1918                         ASSERT_NE(device, nullptr);
1919                         device3_x = device;
1920                     });
1921                 ASSERT_TRUE(ret.isOk());
1922 
1923                 ret = device3_x->getResourceCost([&](auto status, const auto& resourceCost) {
1924                     ALOGI("getResourceCost returns status:%d", (int)status);
1925                     ASSERT_EQ(Status::OK, status);
1926                     ALOGI("    Resource cost is %d", resourceCost.resourceCost);
1927                     ASSERT_LE(resourceCost.resourceCost, 100u);
1928                     for (const auto& name : resourceCost.conflictingDevices) {
1929                         ALOGI("    Conflicting device: %s", name.c_str());
1930                     }
1931                 });
1932                 ASSERT_TRUE(ret.isOk());
1933             }
1934             break;
1935             case CAMERA_DEVICE_API_VERSION_1_0: {
1936                 ::android::sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
1937                 ALOGI("getResourceCost: Testing camera device %s", name.c_str());
1938                 Return<void> ret;
1939                 ret = mProvider->getCameraDeviceInterface_V1_x(
1940                     name, [&](auto status, const auto& device) {
1941                         ALOGI("getCameraDeviceInterface_V1_x returns status:%d", (int)status);
1942                         ASSERT_EQ(Status::OK, status);
1943                         ASSERT_NE(device, nullptr);
1944                         device1 = device;
1945                     });
1946                 ASSERT_TRUE(ret.isOk());
1947 
1948                 ret = device1->getResourceCost([&](auto status, const auto& resourceCost) {
1949                     ALOGI("getResourceCost returns status:%d", (int)status);
1950                     ASSERT_EQ(Status::OK, status);
1951                     ALOGI("    Resource cost is %d", resourceCost.resourceCost);
1952                     ASSERT_LE(resourceCost.resourceCost, 100u);
1953                     for (const auto& name : resourceCost.conflictingDevices) {
1954                         ALOGI("    Conflicting device: %s", name.c_str());
1955                     }
1956                 });
1957                 ASSERT_TRUE(ret.isOk());
1958             }
1959             break;
1960             default: {
1961                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
1962                 ADD_FAILURE();
1963             }
1964             break;
1965         }
1966     }
1967 }
1968 
1969 // Verify that the static camera info can be retrieved
1970 // successfully.
TEST_P(CameraHidlTest,getCameraInfo)1971 TEST_P(CameraHidlTest, getCameraInfo) {
1972     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
1973 
1974     for (const auto& name : cameraDeviceNames) {
1975         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
1976             ::android::sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
1977             ALOGI("getCameraCharacteristics: Testing camera device %s", name.c_str());
1978             Return<void> ret;
1979             ret = mProvider->getCameraDeviceInterface_V1_x(
1980                 name, [&](auto status, const auto& device) {
1981                     ALOGI("getCameraDeviceInterface_V1_x returns status:%d", (int)status);
1982                     ASSERT_EQ(Status::OK, status);
1983                     ASSERT_NE(device, nullptr);
1984                     device1 = device;
1985                 });
1986             ASSERT_TRUE(ret.isOk());
1987 
1988             ret = device1->getCameraInfo([&](auto status, const auto& info) {
1989                 ALOGI("getCameraInfo returns status:%d", (int)status);
1990                 ASSERT_EQ(Status::OK, status);
1991                 switch (info.orientation) {
1992                     case 0:
1993                     case 90:
1994                     case 180:
1995                     case 270:
1996                         // Expected cases
1997                         ALOGI("camera orientation: %d", info.orientation);
1998                         break;
1999                     default:
2000                         FAIL() << "Unexpected camera orientation:" << info.orientation;
2001                 }
2002                 switch (info.facing) {
2003                     case CameraFacing::BACK:
2004                     case CameraFacing::FRONT:
2005                     case CameraFacing::EXTERNAL:
2006                         // Expected cases
2007                         ALOGI("camera facing: %d", info.facing);
2008                         break;
2009                     default:
2010                         FAIL() << "Unexpected camera facing:" << static_cast<uint32_t>(info.facing);
2011                 }
2012             });
2013             ASSERT_TRUE(ret.isOk());
2014         }
2015     }
2016 }
2017 
2018 // Check whether preview window can be configured
TEST_P(CameraHidlTest,setPreviewWindow)2019 TEST_P(CameraHidlTest, setPreviewWindow) {
2020     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2021 
2022     for (const auto& name : cameraDeviceNames) {
2023         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2024             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2025             openCameraDevice(name, mProvider, &device1 /*out*/);
2026             ASSERT_NE(nullptr, device1.get());
2027             sp<BufferItemConsumer> bufferItemConsumer;
2028             sp<BufferItemHander> bufferHandler;
2029             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2030 
2031             Return<void> ret;
2032             ret = device1->close();
2033             ASSERT_TRUE(ret.isOk());
2034         }
2035     }
2036 }
2037 
2038 // Verify that setting preview window fails in case device is not open
TEST_P(CameraHidlTest,setPreviewWindowInvalid)2039 TEST_P(CameraHidlTest, setPreviewWindowInvalid) {
2040     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2041 
2042     for (const auto& name : cameraDeviceNames) {
2043         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2044             ::android::sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2045             ALOGI("getCameraCharacteristics: Testing camera device %s", name.c_str());
2046             Return<void> ret;
2047             ret = mProvider->getCameraDeviceInterface_V1_x(
2048                 name, [&](auto status, const auto& device) {
2049                     ALOGI("getCameraDeviceInterface_V1_x returns status:%d", (int)status);
2050                     ASSERT_EQ(Status::OK, status);
2051                     ASSERT_NE(device, nullptr);
2052                     device1 = device;
2053                 });
2054             ASSERT_TRUE(ret.isOk());
2055 
2056             Return<Status> returnStatus = device1->setPreviewWindow(nullptr);
2057             ASSERT_TRUE(returnStatus.isOk());
2058             ASSERT_EQ(Status::OPERATION_NOT_SUPPORTED, returnStatus);
2059         }
2060     }
2061 }
2062 
2063 // Start and stop preview checking whether it gets enabled in between.
TEST_P(CameraHidlTest,startStopPreview)2064 TEST_P(CameraHidlTest, startStopPreview) {
2065     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2066 
2067     for (const auto& name : cameraDeviceNames) {
2068         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2069             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2070             openCameraDevice(name, mProvider, &device1 /*out*/);
2071             ASSERT_NE(nullptr, device1.get());
2072             sp<BufferItemConsumer> bufferItemConsumer;
2073             sp<BufferItemHander> bufferHandler;
2074             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2075 
2076             startPreview(device1);
2077 
2078             Return<bool> returnBoolStatus = device1->previewEnabled();
2079             ASSERT_TRUE(returnBoolStatus.isOk());
2080             ASSERT_TRUE(returnBoolStatus);
2081 
2082             stopPreviewAndClose(device1);
2083         }
2084     }
2085 }
2086 
2087 // Start preview without active preview window. Preview should start as soon
2088 // as a valid active window gets configured.
TEST_P(CameraHidlTest,startStopPreviewDelayed)2089 TEST_P(CameraHidlTest, startStopPreviewDelayed) {
2090     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2091 
2092     for (const auto& name : cameraDeviceNames) {
2093         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2094             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2095             openCameraDevice(name, mProvider, &device1 /*out*/);
2096             ASSERT_NE(nullptr, device1.get());
2097 
2098             Return<Status> returnStatus = device1->setPreviewWindow(nullptr);
2099             ASSERT_TRUE(returnStatus.isOk());
2100             ASSERT_EQ(Status::OK, returnStatus);
2101 
2102             startPreview(device1);
2103 
2104             sp<BufferItemConsumer> bufferItemConsumer;
2105             sp<BufferItemHander> bufferHandler;
2106             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2107 
2108             // Preview should get enabled now
2109             Return<bool> returnBoolStatus = device1->previewEnabled();
2110             ASSERT_TRUE(returnBoolStatus.isOk());
2111             ASSERT_TRUE(returnBoolStatus);
2112 
2113             stopPreviewAndClose(device1);
2114         }
2115     }
2116 }
2117 
2118 // Verify that image capture behaves as expected along with preview callbacks.
TEST_P(CameraHidlTest,takePicture)2119 TEST_P(CameraHidlTest, takePicture) {
2120     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2121 
2122     for (const auto& name : cameraDeviceNames) {
2123         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2124             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2125             openCameraDevice(name, mProvider, &device1 /*out*/);
2126             ASSERT_NE(nullptr, device1.get());
2127             sp<BufferItemConsumer> bufferItemConsumer;
2128             sp<BufferItemHander> bufferHandler;
2129             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2130 
2131             {
2132                 std::unique_lock<std::mutex> l(mLock);
2133                 mDataMessageTypeReceived = DataCallbackMsg::RAW_IMAGE_NOTIFY;
2134             }
2135 
2136             enableMsgType((unsigned int)DataCallbackMsg::PREVIEW_FRAME, device1);
2137             startPreview(device1);
2138 
2139             {
2140                 std::unique_lock<std::mutex> l(mLock);
2141                 waitForFrameLocked(DataCallbackMsg::PREVIEW_FRAME, l);
2142             }
2143 
2144             disableMsgType((unsigned int)DataCallbackMsg::PREVIEW_FRAME, device1);
2145             enableMsgType((unsigned int)DataCallbackMsg::COMPRESSED_IMAGE, device1);
2146 
2147             {
2148                 std::unique_lock<std::mutex> l(mLock);
2149                 mDataMessageTypeReceived = DataCallbackMsg::RAW_IMAGE_NOTIFY;
2150             }
2151 
2152             Return<Status> returnStatus = device1->takePicture();
2153             ASSERT_TRUE(returnStatus.isOk());
2154             ASSERT_EQ(Status::OK, returnStatus);
2155 
2156             {
2157                 std::unique_lock<std::mutex> l(mLock);
2158                 waitForFrameLocked(DataCallbackMsg::COMPRESSED_IMAGE, l);
2159             }
2160 
2161             disableMsgType((unsigned int)DataCallbackMsg::COMPRESSED_IMAGE, device1);
2162             stopPreviewAndClose(device1);
2163         }
2164     }
2165 }
2166 
2167 // Image capture should fail in case preview didn't get enabled first.
TEST_P(CameraHidlTest,takePictureFail)2168 TEST_P(CameraHidlTest, takePictureFail) {
2169     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2170 
2171     for (const auto& name : cameraDeviceNames) {
2172         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2173             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2174             openCameraDevice(name, mProvider, &device1 /*out*/);
2175             ASSERT_NE(nullptr, device1.get());
2176 
2177             Return<Status> returnStatus = device1->takePicture();
2178             ASSERT_TRUE(returnStatus.isOk());
2179             ASSERT_NE(Status::OK, returnStatus);
2180 
2181             Return<void> ret = device1->close();
2182             ASSERT_TRUE(ret.isOk());
2183         }
2184     }
2185 }
2186 
2187 // Verify that image capture can be cancelled.
TEST_P(CameraHidlTest,cancelPicture)2188 TEST_P(CameraHidlTest, cancelPicture) {
2189     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2190 
2191     for (const auto& name : cameraDeviceNames) {
2192         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2193             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2194             openCameraDevice(name, mProvider, &device1 /*out*/);
2195             ASSERT_NE(nullptr, device1.get());
2196             sp<BufferItemConsumer> bufferItemConsumer;
2197             sp<BufferItemHander> bufferHandler;
2198             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2199             startPreview(device1);
2200 
2201             Return<Status> returnStatus = device1->takePicture();
2202             ASSERT_TRUE(returnStatus.isOk());
2203             ASSERT_EQ(Status::OK, returnStatus);
2204 
2205             returnStatus = device1->cancelPicture();
2206             ASSERT_TRUE(returnStatus.isOk());
2207             ASSERT_EQ(Status::OK, returnStatus);
2208 
2209             stopPreviewAndClose(device1);
2210         }
2211     }
2212 }
2213 
2214 // Image capture cancel is a no-op when image capture is not running.
TEST_P(CameraHidlTest,cancelPictureNOP)2215 TEST_P(CameraHidlTest, cancelPictureNOP) {
2216     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2217 
2218     for (const auto& name : cameraDeviceNames) {
2219         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2220             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2221             openCameraDevice(name, mProvider, &device1 /*out*/);
2222             ASSERT_NE(nullptr, device1.get());
2223             sp<BufferItemConsumer> bufferItemConsumer;
2224             sp<BufferItemHander> bufferHandler;
2225             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2226             startPreview(device1);
2227 
2228             Return<Status> returnStatus = device1->cancelPicture();
2229             ASSERT_TRUE(returnStatus.isOk());
2230             ASSERT_EQ(Status::OK, returnStatus);
2231 
2232             stopPreviewAndClose(device1);
2233         }
2234     }
2235 }
2236 
2237 // Test basic video recording.
TEST_P(CameraHidlTest,startStopRecording)2238 TEST_P(CameraHidlTest, startStopRecording) {
2239     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2240 
2241     for (const auto& name : cameraDeviceNames) {
2242         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2243             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2244             openCameraDevice(name, mProvider, &device1 /*out*/);
2245             ASSERT_NE(nullptr, device1.get());
2246             sp<BufferItemConsumer> bufferItemConsumer;
2247             sp<BufferItemHander> bufferHandler;
2248             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2249 
2250             {
2251                 std::unique_lock<std::mutex> l(mLock);
2252                 mDataMessageTypeReceived = DataCallbackMsg::RAW_IMAGE_NOTIFY;
2253             }
2254 
2255             enableMsgType((unsigned int)DataCallbackMsg::PREVIEW_FRAME, device1);
2256             startPreview(device1);
2257 
2258             {
2259                 std::unique_lock<std::mutex> l(mLock);
2260                 waitForFrameLocked(DataCallbackMsg::PREVIEW_FRAME, l);
2261                 mDataMessageTypeReceived = DataCallbackMsg::RAW_IMAGE_NOTIFY;
2262                 mVideoBufferIndex = UINT32_MAX;
2263             }
2264 
2265             disableMsgType((unsigned int)DataCallbackMsg::PREVIEW_FRAME, device1);
2266 
2267             bool videoMetaEnabled = false;
2268             Return<Status> returnStatus = device1->storeMetaDataInBuffers(true);
2269             ASSERT_TRUE(returnStatus.isOk());
2270             // It is allowed for devices to not support this feature
2271             ASSERT_TRUE((Status::OK == returnStatus) ||
2272                         (Status::OPERATION_NOT_SUPPORTED == returnStatus));
2273             if (Status::OK == returnStatus) {
2274                 videoMetaEnabled = true;
2275             }
2276 
2277             enableMsgType((unsigned int)DataCallbackMsg::VIDEO_FRAME, device1);
2278             Return<bool> returnBoolStatus = device1->recordingEnabled();
2279             ASSERT_TRUE(returnBoolStatus.isOk());
2280             ASSERT_FALSE(returnBoolStatus);
2281 
2282             returnStatus = device1->startRecording();
2283             ASSERT_TRUE(returnStatus.isOk());
2284             ASSERT_EQ(Status::OK, returnStatus);
2285 
2286             {
2287                 std::unique_lock<std::mutex> l(mLock);
2288                 waitForFrameLocked(DataCallbackMsg::VIDEO_FRAME, l);
2289                 ASSERT_NE(UINT32_MAX, mVideoBufferIndex);
2290                 disableMsgType((unsigned int)DataCallbackMsg::VIDEO_FRAME, device1);
2291             }
2292 
2293             returnBoolStatus = device1->recordingEnabled();
2294             ASSERT_TRUE(returnBoolStatus.isOk());
2295             ASSERT_TRUE(returnBoolStatus);
2296 
2297             Return<void> ret;
2298             if (videoMetaEnabled) {
2299                 ret = device1->releaseRecordingFrameHandle(mVideoData, mVideoBufferIndex,
2300                                                            mVideoNativeHandle);
2301                 ASSERT_TRUE(ret.isOk());
2302             } else {
2303                 ret = device1->releaseRecordingFrame(mVideoData, mVideoBufferIndex);
2304                 ASSERT_TRUE(ret.isOk());
2305             }
2306 
2307             ret = device1->stopRecording();
2308             ASSERT_TRUE(ret.isOk());
2309 
2310             stopPreviewAndClose(device1);
2311         }
2312     }
2313 }
2314 
2315 // It shouldn't be possible to start recording without enabling preview first.
TEST_P(CameraHidlTest,startRecordingFail)2316 TEST_P(CameraHidlTest, startRecordingFail) {
2317     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2318 
2319     for (const auto& name : cameraDeviceNames) {
2320         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2321             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2322             openCameraDevice(name, mProvider, &device1 /*out*/);
2323             ASSERT_NE(nullptr, device1.get());
2324 
2325             Return<bool> returnBoolStatus = device1->recordingEnabled();
2326             ASSERT_TRUE(returnBoolStatus.isOk());
2327             ASSERT_FALSE(returnBoolStatus);
2328 
2329             Return<Status> returnStatus = device1->startRecording();
2330             ASSERT_TRUE(returnStatus.isOk());
2331             ASSERT_NE(Status::OK, returnStatus);
2332 
2333             Return<void> ret = device1->close();
2334             ASSERT_TRUE(ret.isOk());
2335         }
2336     }
2337 }
2338 
2339 // Check autofocus support if available.
TEST_P(CameraHidlTest,autoFocus)2340 TEST_P(CameraHidlTest, autoFocus) {
2341     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2342     std::vector<const char*> focusModes = {CameraParameters::FOCUS_MODE_AUTO,
2343                                            CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE,
2344                                            CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO};
2345 
2346     for (const auto& name : cameraDeviceNames) {
2347         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2348             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2349             openCameraDevice(name, mProvider, &device1 /*out*/);
2350             ASSERT_NE(nullptr, device1.get());
2351 
2352             CameraParameters cameraParams;
2353             getParameters(device1, &cameraParams /*out*/);
2354 
2355             if (Status::OK !=
2356                 isAutoFocusModeAvailable(cameraParams, CameraParameters::FOCUS_MODE_AUTO)) {
2357                 Return<void> ret = device1->close();
2358                 ASSERT_TRUE(ret.isOk());
2359                 continue;
2360             }
2361 
2362             sp<BufferItemConsumer> bufferItemConsumer;
2363             sp<BufferItemHander> bufferHandler;
2364             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2365             startPreview(device1);
2366             enableMsgType((unsigned int)NotifyCallbackMsg::FOCUS, device1);
2367 
2368             for (auto& iter : focusModes) {
2369                 if (Status::OK != isAutoFocusModeAvailable(cameraParams, iter)) {
2370                     continue;
2371                 }
2372 
2373                 cameraParams.set(CameraParameters::KEY_FOCUS_MODE, iter);
2374                 setParameters(device1, cameraParams);
2375                 {
2376                     std::unique_lock<std::mutex> l(mLock);
2377                     mNotifyMessage = NotifyCallbackMsg::ERROR;
2378                 }
2379 
2380                 Return<Status> returnStatus = device1->autoFocus();
2381                 ASSERT_TRUE(returnStatus.isOk());
2382                 ASSERT_EQ(Status::OK, returnStatus);
2383 
2384                 {
2385                     std::unique_lock<std::mutex> l(mLock);
2386                     while (NotifyCallbackMsg::FOCUS != mNotifyMessage) {
2387                         auto timeout = std::chrono::system_clock::now() +
2388                                        std::chrono::seconds(kAutoFocusTimeoutSec);
2389                         ASSERT_NE(std::cv_status::timeout, mResultCondition.wait_until(l, timeout));
2390                     }
2391                 }
2392             }
2393 
2394             disableMsgType((unsigned int)NotifyCallbackMsg::FOCUS, device1);
2395             stopPreviewAndClose(device1);
2396         }
2397     }
2398 }
2399 
2400 // In case autofocus is supported verify that it can be cancelled.
TEST_P(CameraHidlTest,cancelAutoFocus)2401 TEST_P(CameraHidlTest, cancelAutoFocus) {
2402     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2403 
2404     for (const auto& name : cameraDeviceNames) {
2405         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2406             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2407             openCameraDevice(name, mProvider, &device1 /*out*/);
2408             ASSERT_NE(nullptr, device1.get());
2409 
2410             CameraParameters cameraParams;
2411             getParameters(device1, &cameraParams /*out*/);
2412 
2413             if (Status::OK !=
2414                 isAutoFocusModeAvailable(cameraParams, CameraParameters::FOCUS_MODE_AUTO)) {
2415                 Return<void> ret = device1->close();
2416                 ASSERT_TRUE(ret.isOk());
2417                 continue;
2418             }
2419 
2420             // It should be fine to call before preview starts.
2421             ASSERT_EQ(Status::OK, device1->cancelAutoFocus());
2422 
2423             sp<BufferItemConsumer> bufferItemConsumer;
2424             sp<BufferItemHander> bufferHandler;
2425             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2426             startPreview(device1);
2427 
2428             // It should be fine to call after preview starts too.
2429             Return<Status> returnStatus = device1->cancelAutoFocus();
2430             ASSERT_TRUE(returnStatus.isOk());
2431             ASSERT_EQ(Status::OK, returnStatus);
2432 
2433             returnStatus = device1->autoFocus();
2434             ASSERT_TRUE(returnStatus.isOk());
2435             ASSERT_EQ(Status::OK, returnStatus);
2436 
2437             returnStatus = device1->cancelAutoFocus();
2438             ASSERT_TRUE(returnStatus.isOk());
2439             ASSERT_EQ(Status::OK, returnStatus);
2440 
2441             stopPreviewAndClose(device1);
2442         }
2443     }
2444 }
2445 
2446 // Check whether face detection is available and try to enable&disable.
TEST_P(CameraHidlTest,sendCommandFaceDetection)2447 TEST_P(CameraHidlTest, sendCommandFaceDetection) {
2448     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2449 
2450     for (const auto& name : cameraDeviceNames) {
2451         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2452             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2453             openCameraDevice(name, mProvider, &device1 /*out*/);
2454             ASSERT_NE(nullptr, device1.get());
2455 
2456             CameraParameters cameraParams;
2457             getParameters(device1, &cameraParams /*out*/);
2458 
2459             int32_t hwFaces = cameraParams.getInt(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_HW);
2460             int32_t swFaces = cameraParams.getInt(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_SW);
2461             if ((0 >= hwFaces) && (0 >= swFaces)) {
2462                 Return<void> ret = device1->close();
2463                 ASSERT_TRUE(ret.isOk());
2464                 continue;
2465             }
2466 
2467             sp<BufferItemConsumer> bufferItemConsumer;
2468             sp<BufferItemHander> bufferHandler;
2469             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2470             startPreview(device1);
2471 
2472             if (0 < hwFaces) {
2473                 Return<Status> returnStatus = device1->sendCommand(
2474                     CommandType::START_FACE_DETECTION, CAMERA_FACE_DETECTION_HW, 0);
2475                 ASSERT_TRUE(returnStatus.isOk());
2476                 ASSERT_EQ(Status::OK, returnStatus);
2477                 // TODO(epeev) : Enable and check for face notifications
2478                 returnStatus = device1->sendCommand(CommandType::STOP_FACE_DETECTION,
2479                                                     CAMERA_FACE_DETECTION_HW, 0);
2480                 ASSERT_TRUE(returnStatus.isOk());
2481                 ASSERT_EQ(Status::OK, returnStatus);
2482             }
2483 
2484             if (0 < swFaces) {
2485                 Return<Status> returnStatus = device1->sendCommand(
2486                     CommandType::START_FACE_DETECTION, CAMERA_FACE_DETECTION_SW, 0);
2487                 ASSERT_TRUE(returnStatus.isOk());
2488                 ASSERT_EQ(Status::OK, returnStatus);
2489                 // TODO(epeev) : Enable and check for face notifications
2490                 returnStatus = device1->sendCommand(CommandType::STOP_FACE_DETECTION,
2491                                                     CAMERA_FACE_DETECTION_SW, 0);
2492                 ASSERT_TRUE(returnStatus.isOk());
2493                 ASSERT_EQ(Status::OK, returnStatus);
2494             }
2495 
2496             stopPreviewAndClose(device1);
2497         }
2498     }
2499 }
2500 
2501 // Check whether smooth zoom is available and try to enable&disable.
TEST_P(CameraHidlTest,sendCommandSmoothZoom)2502 TEST_P(CameraHidlTest, sendCommandSmoothZoom) {
2503     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2504 
2505     for (const auto& name : cameraDeviceNames) {
2506         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2507             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2508             openCameraDevice(name, mProvider, &device1 /*out*/);
2509             ASSERT_NE(nullptr, device1.get());
2510 
2511             CameraParameters cameraParams;
2512             getParameters(device1, &cameraParams /*out*/);
2513 
2514             const char* smoothZoomStr =
2515                 cameraParams.get(CameraParameters::KEY_SMOOTH_ZOOM_SUPPORTED);
2516             bool smoothZoomSupported =
2517                 ((nullptr != smoothZoomStr) && (strcmp(smoothZoomStr, CameraParameters::TRUE) == 0))
2518                     ? true
2519                     : false;
2520             if (!smoothZoomSupported) {
2521                 Return<void> ret = device1->close();
2522                 ASSERT_TRUE(ret.isOk());
2523                 continue;
2524             }
2525 
2526             int32_t maxZoom = cameraParams.getInt(CameraParameters::KEY_MAX_ZOOM);
2527             ASSERT_TRUE(0 < maxZoom);
2528 
2529             sp<BufferItemConsumer> bufferItemConsumer;
2530             sp<BufferItemHander> bufferHandler;
2531             setupPreviewWindow(device1, &bufferItemConsumer /*out*/, &bufferHandler /*out*/);
2532             startPreview(device1);
2533             setParameters(device1, cameraParams);
2534 
2535             Return<Status> returnStatus =
2536                 device1->sendCommand(CommandType::START_SMOOTH_ZOOM, maxZoom, 0);
2537             ASSERT_TRUE(returnStatus.isOk());
2538             ASSERT_EQ(Status::OK, returnStatus);
2539             // TODO(epeev) : Enable and check for face notifications
2540             returnStatus = device1->sendCommand(CommandType::STOP_SMOOTH_ZOOM, 0, 0);
2541             ASSERT_TRUE(returnStatus.isOk());
2542             ASSERT_EQ(Status::OK, returnStatus);
2543 
2544             stopPreviewAndClose(device1);
2545         }
2546     }
2547 }
2548 
2549 // Basic correctness tests related to camera parameters.
TEST_P(CameraHidlTest,getSetParameters)2550 TEST_P(CameraHidlTest, getSetParameters) {
2551     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2552 
2553     for (const auto& name : cameraDeviceNames) {
2554         if (getCameraDeviceVersion(name, mProviderType) == CAMERA_DEVICE_API_VERSION_1_0) {
2555             sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2556             openCameraDevice(name, mProvider, &device1 /*out*/);
2557             ASSERT_NE(nullptr, device1.get());
2558 
2559             CameraParameters cameraParams;
2560             getParameters(device1, &cameraParams /*out*/);
2561 
2562             int32_t width, height;
2563             cameraParams.getPictureSize(&width, &height);
2564             ASSERT_TRUE((0 < width) && (0 < height));
2565             cameraParams.getPreviewSize(&width, &height);
2566             ASSERT_TRUE((0 < width) && (0 < height));
2567             int32_t minFps, maxFps;
2568             cameraParams.getPreviewFpsRange(&minFps, &maxFps);
2569             ASSERT_TRUE((0 < minFps) && (0 < maxFps));
2570             ASSERT_NE(nullptr, cameraParams.getPreviewFormat());
2571             ASSERT_NE(nullptr, cameraParams.getPictureFormat());
2572             ASSERT_TRUE(
2573                 strcmp(CameraParameters::PIXEL_FORMAT_JPEG, cameraParams.getPictureFormat()) == 0);
2574 
2575             const char* flashMode = cameraParams.get(CameraParameters::KEY_FLASH_MODE);
2576             ASSERT_TRUE((nullptr == flashMode) ||
2577                         (strcmp(CameraParameters::FLASH_MODE_OFF, flashMode) == 0));
2578 
2579             const char* wbMode = cameraParams.get(CameraParameters::KEY_WHITE_BALANCE);
2580             ASSERT_TRUE((nullptr == wbMode) ||
2581                         (strcmp(CameraParameters::WHITE_BALANCE_AUTO, wbMode) == 0));
2582 
2583             const char* effect = cameraParams.get(CameraParameters::KEY_EFFECT);
2584             ASSERT_TRUE((nullptr == effect) ||
2585                         (strcmp(CameraParameters::EFFECT_NONE, effect) == 0));
2586 
2587             ::android::Vector<Size> previewSizes;
2588             cameraParams.getSupportedPreviewSizes(previewSizes);
2589             ASSERT_FALSE(previewSizes.empty());
2590             ::android::Vector<Size> pictureSizes;
2591             cameraParams.getSupportedPictureSizes(pictureSizes);
2592             ASSERT_FALSE(pictureSizes.empty());
2593             const char* previewFormats =
2594                 cameraParams.get(CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS);
2595             ASSERT_NE(nullptr, previewFormats);
2596             ::android::String8 previewFormatsString(previewFormats);
2597             ASSERT_TRUE(previewFormatsString.contains(CameraParameters::PIXEL_FORMAT_YUV420SP));
2598             ASSERT_NE(nullptr, cameraParams.get(CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS));
2599             ASSERT_NE(nullptr,
2600                       cameraParams.get(CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES));
2601             const char* focusModes = cameraParams.get(CameraParameters::KEY_SUPPORTED_FOCUS_MODES);
2602             ASSERT_NE(nullptr, focusModes);
2603             ::android::String8 focusModesString(focusModes);
2604             const char* focusMode = cameraParams.get(CameraParameters::KEY_FOCUS_MODE);
2605             ASSERT_NE(nullptr, focusMode);
2606             // Auto focus mode should be default
2607             if (focusModesString.contains(CameraParameters::FOCUS_MODE_AUTO)) {
2608                 ASSERT_TRUE(strcmp(CameraParameters::FOCUS_MODE_AUTO, focusMode) == 0);
2609             }
2610             ASSERT_TRUE(0 < cameraParams.getInt(CameraParameters::KEY_FOCAL_LENGTH));
2611             int32_t horizontalViewAngle =
2612                 cameraParams.getInt(CameraParameters::KEY_HORIZONTAL_VIEW_ANGLE);
2613             ASSERT_TRUE((0 < horizontalViewAngle) && (360 >= horizontalViewAngle));
2614             int32_t verticalViewAngle =
2615                 cameraParams.getInt(CameraParameters::KEY_VERTICAL_VIEW_ANGLE);
2616             ASSERT_TRUE((0 < verticalViewAngle) && (360 >= verticalViewAngle));
2617             int32_t jpegQuality = cameraParams.getInt(CameraParameters::KEY_JPEG_QUALITY);
2618             ASSERT_TRUE((1 <= jpegQuality) && (100 >= jpegQuality));
2619             int32_t jpegThumbQuality =
2620                 cameraParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY);
2621             ASSERT_TRUE((1 <= jpegThumbQuality) && (100 >= jpegThumbQuality));
2622 
2623             cameraParams.setPictureSize(pictureSizes[0].width, pictureSizes[0].height);
2624             cameraParams.setPreviewSize(previewSizes[0].width, previewSizes[0].height);
2625 
2626             setParameters(device1, cameraParams);
2627             getParameters(device1, &cameraParams /*out*/);
2628 
2629             cameraParams.getPictureSize(&width, &height);
2630             ASSERT_TRUE((pictureSizes[0].width == width) && (pictureSizes[0].height == height));
2631             cameraParams.getPreviewSize(&width, &height);
2632             ASSERT_TRUE((previewSizes[0].width == width) && (previewSizes[0].height == height));
2633 
2634             Return<void> ret = device1->close();
2635             ASSERT_TRUE(ret.isOk());
2636         }
2637     }
2638 }
2639 
TEST_P(CameraHidlTest,systemCameraTest)2640 TEST_P(CameraHidlTest, systemCameraTest) {
2641     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2642     std::map<std::string, std::list<SystemCameraKind>> hiddenPhysicalIdToLogicalMap;
2643     for (const auto& name : cameraDeviceNames) {
2644         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
2645         switch (deviceVersion) {
2646             case CAMERA_DEVICE_API_VERSION_3_6:
2647             case CAMERA_DEVICE_API_VERSION_3_5:
2648             case CAMERA_DEVICE_API_VERSION_3_4:
2649             case CAMERA_DEVICE_API_VERSION_3_3:
2650             case CAMERA_DEVICE_API_VERSION_3_2: {
2651                 ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> device3_x;
2652                 ALOGI("getCameraCharacteristics: Testing camera device %s", name.c_str());
2653                 Return<void> ret;
2654                 ret = mProvider->getCameraDeviceInterface_V3_x(
2655                         name, [&](auto status, const auto& device) {
2656                             ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
2657                             ASSERT_EQ(Status::OK, status);
2658                             ASSERT_NE(device, nullptr);
2659                             device3_x = device;
2660                         });
2661                 ASSERT_TRUE(ret.isOk());
2662 
2663                 ret = device3_x->getCameraCharacteristics([&](auto status, const auto& chars) {
2664                     ASSERT_EQ(status, Status::OK);
2665                     const camera_metadata_t* staticMeta =
2666                             reinterpret_cast<const camera_metadata_t*>(chars.data());
2667                     ASSERT_NE(staticMeta, nullptr);
2668                     Status rc = isLogicalMultiCamera(staticMeta);
2669                     ASSERT_TRUE(Status::OK == rc || Status::METHOD_NOT_SUPPORTED == rc);
2670                     if (Status::METHOD_NOT_SUPPORTED == rc) {
2671                         return;
2672                     }
2673                     std::unordered_set<std::string> physicalIds;
2674                     ASSERT_EQ(Status::OK, getPhysicalCameraIds(staticMeta, &physicalIds));
2675                     SystemCameraKind systemCameraKind = SystemCameraKind::PUBLIC;
2676                     rc = getSystemCameraKind(staticMeta, &systemCameraKind);
2677                     ASSERT_EQ(rc, Status::OK);
2678                     for (auto physicalId : physicalIds) {
2679                         bool isPublicId = false;
2680                         for (auto& deviceName : cameraDeviceNames) {
2681                             std::string publicVersion, publicId;
2682                             ASSERT_TRUE(::matchDeviceName(deviceName, mProviderType, &publicVersion,
2683                                                           &publicId));
2684                             if (physicalId == publicId) {
2685                                 isPublicId = true;
2686                                 break;
2687                             }
2688                         }
2689                         // For hidden physical cameras, collect their associated logical cameras
2690                         // and store the system camera kind.
2691                         if (!isPublicId) {
2692                             auto it = hiddenPhysicalIdToLogicalMap.find(physicalId);
2693                             if (it == hiddenPhysicalIdToLogicalMap.end()) {
2694                                 hiddenPhysicalIdToLogicalMap.insert(std::make_pair(
2695                                         physicalId, std::list<SystemCameraKind>(systemCameraKind)));
2696                             } else {
2697                                 it->second.push_back(systemCameraKind);
2698                             }
2699                         }
2700                     }
2701                 });
2702                 ASSERT_TRUE(ret.isOk());
2703             } break;
2704             case CAMERA_DEVICE_API_VERSION_1_0: {
2705                 // Not applicable
2706             } break;
2707             default: {
2708                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
2709                 ADD_FAILURE();
2710             } break;
2711         }
2712     }
2713 
2714     // Check that the system camera kind of the logical cameras associated with
2715     // each hidden physical camera is the same.
2716     for (const auto& it : hiddenPhysicalIdToLogicalMap) {
2717         SystemCameraKind neededSystemCameraKind = it.second.front();
2718         for (auto foundSystemCamera : it.second) {
2719             ASSERT_EQ(neededSystemCameraKind, foundSystemCamera);
2720         }
2721     }
2722 }
2723 
2724 // Verify that the static camera characteristics can be retrieved
2725 // successfully.
TEST_P(CameraHidlTest,getCameraCharacteristics)2726 TEST_P(CameraHidlTest, getCameraCharacteristics) {
2727     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2728 
2729     for (const auto& name : cameraDeviceNames) {
2730         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
2731         switch (deviceVersion) {
2732             case CAMERA_DEVICE_API_VERSION_3_6:
2733             case CAMERA_DEVICE_API_VERSION_3_5:
2734             case CAMERA_DEVICE_API_VERSION_3_4:
2735             case CAMERA_DEVICE_API_VERSION_3_3:
2736             case CAMERA_DEVICE_API_VERSION_3_2: {
2737                 ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> device3_x;
2738                 ALOGI("getCameraCharacteristics: Testing camera device %s", name.c_str());
2739                 Return<void> ret;
2740                 ret = mProvider->getCameraDeviceInterface_V3_x(
2741                     name, [&](auto status, const auto& device) {
2742                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
2743                         ASSERT_EQ(Status::OK, status);
2744                         ASSERT_NE(device, nullptr);
2745                         device3_x = device;
2746                     });
2747                 ASSERT_TRUE(ret.isOk());
2748 
2749                 ret = device3_x->getCameraCharacteristics([&](auto status, const auto& chars) {
2750                     verifyCameraCharacteristics(status, chars);
2751                     verifyMonochromeCharacteristics(chars, deviceVersion);
2752                     verifyRecommendedConfigs(chars);
2753                     verifyLogicalCameraMetadata(name, device3_x, chars, deviceVersion,
2754                             cameraDeviceNames);
2755                 });
2756                 ASSERT_TRUE(ret.isOk());
2757 
2758                 //getPhysicalCameraCharacteristics will fail for publicly
2759                 //advertised camera IDs.
2760                 if (deviceVersion >= CAMERA_DEVICE_API_VERSION_3_5) {
2761                     auto castResult = device::V3_5::ICameraDevice::castFrom(device3_x);
2762                     ASSERT_TRUE(castResult.isOk());
2763                     ::android::sp<::android::hardware::camera::device::V3_5::ICameraDevice>
2764                             device3_5 = castResult;
2765                     ASSERT_NE(device3_5, nullptr);
2766 
2767                     std::string version, cameraId;
2768                     ASSERT_TRUE(::matchDeviceName(name, mProviderType, &version, &cameraId));
2769                     Return<void> ret = device3_5->getPhysicalCameraCharacteristics(cameraId,
2770                             [&](auto status, const auto& chars) {
2771                         ASSERT_TRUE(Status::ILLEGAL_ARGUMENT == status);
2772                         ASSERT_EQ(0, chars.size());
2773                     });
2774                     ASSERT_TRUE(ret.isOk());
2775                 }
2776             }
2777             break;
2778             case CAMERA_DEVICE_API_VERSION_1_0: {
2779                 //Not applicable
2780             }
2781             break;
2782             default: {
2783                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
2784                 ADD_FAILURE();
2785             }
2786             break;
2787         }
2788     }
2789 }
2790 
2791 //In case it is supported verify that torch can be enabled.
2792 //Check for corresponding toch callbacks as well.
TEST_P(CameraHidlTest,setTorchMode)2793 TEST_P(CameraHidlTest, setTorchMode) {
2794     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2795     bool torchControlSupported = false;
2796     Return<void> ret;
2797 
2798     ret = mProvider->isSetTorchModeSupported([&](auto status, bool support) {
2799         ALOGI("isSetTorchModeSupported returns status:%d supported:%d", (int)status, support);
2800         ASSERT_EQ(Status::OK, status);
2801         torchControlSupported = support;
2802     });
2803 
2804     sp<TorchProviderCb> cb = new TorchProviderCb(this);
2805     Return<Status> returnStatus = mProvider->setCallback(cb);
2806     ASSERT_TRUE(returnStatus.isOk());
2807     ASSERT_EQ(Status::OK, returnStatus);
2808 
2809     for (const auto& name : cameraDeviceNames) {
2810         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
2811         switch (deviceVersion) {
2812             case CAMERA_DEVICE_API_VERSION_3_6:
2813             case CAMERA_DEVICE_API_VERSION_3_5:
2814             case CAMERA_DEVICE_API_VERSION_3_4:
2815             case CAMERA_DEVICE_API_VERSION_3_3:
2816             case CAMERA_DEVICE_API_VERSION_3_2: {
2817                 ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> device3_x;
2818                 ALOGI("setTorchMode: Testing camera device %s", name.c_str());
2819                 ret = mProvider->getCameraDeviceInterface_V3_x(
2820                     name, [&](auto status, const auto& device) {
2821                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
2822                         ASSERT_EQ(Status::OK, status);
2823                         ASSERT_NE(device, nullptr);
2824                         device3_x = device;
2825                     });
2826                 ASSERT_TRUE(ret.isOk());
2827 
2828                 mTorchStatus = TorchModeStatus::NOT_AVAILABLE;
2829                 returnStatus = device3_x->setTorchMode(TorchMode::ON);
2830                 ASSERT_TRUE(returnStatus.isOk());
2831                 if (!torchControlSupported) {
2832                     ASSERT_EQ(Status::METHOD_NOT_SUPPORTED, returnStatus);
2833                 } else {
2834                     ASSERT_TRUE(returnStatus == Status::OK ||
2835                                 returnStatus == Status::OPERATION_NOT_SUPPORTED);
2836                     if (returnStatus == Status::OK) {
2837                         {
2838                             std::unique_lock<std::mutex> l(mTorchLock);
2839                             while (TorchModeStatus::NOT_AVAILABLE == mTorchStatus) {
2840                                 auto timeout = std::chrono::system_clock::now() +
2841                                                std::chrono::seconds(kTorchTimeoutSec);
2842                                 ASSERT_NE(std::cv_status::timeout, mTorchCond.wait_until(l, timeout));
2843                             }
2844                             ASSERT_EQ(TorchModeStatus::AVAILABLE_ON, mTorchStatus);
2845                             mTorchStatus = TorchModeStatus::NOT_AVAILABLE;
2846                         }
2847 
2848                         returnStatus = device3_x->setTorchMode(TorchMode::OFF);
2849                         ASSERT_TRUE(returnStatus.isOk());
2850                         ASSERT_EQ(Status::OK, returnStatus);
2851 
2852                         {
2853                             std::unique_lock<std::mutex> l(mTorchLock);
2854                             while (TorchModeStatus::NOT_AVAILABLE == mTorchStatus) {
2855                                 auto timeout = std::chrono::system_clock::now() +
2856                                                std::chrono::seconds(kTorchTimeoutSec);
2857                                 ASSERT_NE(std::cv_status::timeout, mTorchCond.wait_until(l, timeout));
2858                             }
2859                             ASSERT_EQ(TorchModeStatus::AVAILABLE_OFF, mTorchStatus);
2860                         }
2861                     }
2862                 }
2863             }
2864             break;
2865             case CAMERA_DEVICE_API_VERSION_1_0: {
2866                 ::android::sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2867                 ALOGI("dumpState: Testing camera device %s", name.c_str());
2868                 ret = mProvider->getCameraDeviceInterface_V1_x(
2869                     name, [&](auto status, const auto& device) {
2870                         ALOGI("getCameraDeviceInterface_V1_x returns status:%d", (int)status);
2871                         ASSERT_EQ(Status::OK, status);
2872                         ASSERT_NE(device, nullptr);
2873                         device1 = device;
2874                     });
2875                 ASSERT_TRUE(ret.isOk());
2876 
2877                 mTorchStatus = TorchModeStatus::NOT_AVAILABLE;
2878                 returnStatus = device1->setTorchMode(TorchMode::ON);
2879                 ASSERT_TRUE(returnStatus.isOk());
2880                 if (!torchControlSupported) {
2881                     ASSERT_EQ(Status::METHOD_NOT_SUPPORTED, returnStatus);
2882                 } else {
2883                     ASSERT_TRUE(returnStatus == Status::OK ||
2884                                 returnStatus == Status::OPERATION_NOT_SUPPORTED);
2885                     if (returnStatus == Status::OK) {
2886                         {
2887                             std::unique_lock<std::mutex> l(mTorchLock);
2888                             while (TorchModeStatus::NOT_AVAILABLE == mTorchStatus) {
2889                                 auto timeout = std::chrono::system_clock::now() +
2890                                                std::chrono::seconds(kTorchTimeoutSec);
2891                                 ASSERT_NE(std::cv_status::timeout, mTorchCond.wait_until(l,
2892                                         timeout));
2893                             }
2894                             ASSERT_EQ(TorchModeStatus::AVAILABLE_ON, mTorchStatus);
2895                             mTorchStatus = TorchModeStatus::NOT_AVAILABLE;
2896                         }
2897 
2898                         returnStatus = device1->setTorchMode(TorchMode::OFF);
2899                         ASSERT_TRUE(returnStatus.isOk());
2900                         ASSERT_EQ(Status::OK, returnStatus);
2901 
2902                         {
2903                             std::unique_lock<std::mutex> l(mTorchLock);
2904                             while (TorchModeStatus::NOT_AVAILABLE == mTorchStatus) {
2905                                 auto timeout = std::chrono::system_clock::now() +
2906                                                std::chrono::seconds(kTorchTimeoutSec);
2907                                 ASSERT_NE(std::cv_status::timeout, mTorchCond.wait_until(l,
2908                                         timeout));
2909                             }
2910                             ASSERT_EQ(TorchModeStatus::AVAILABLE_OFF, mTorchStatus);
2911                         }
2912                     }
2913                 }
2914                 ret = device1->close();
2915                 ASSERT_TRUE(ret.isOk());
2916             }
2917             break;
2918             default: {
2919                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
2920                 ADD_FAILURE();
2921             }
2922             break;
2923         }
2924     }
2925 
2926     returnStatus = mProvider->setCallback(nullptr);
2927     ASSERT_TRUE(returnStatus.isOk());
2928     ASSERT_EQ(Status::OK, returnStatus);
2929 }
2930 
2931 // Check dump functionality.
TEST_P(CameraHidlTest,dumpState)2932 TEST_P(CameraHidlTest, dumpState) {
2933     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
2934     Return<void> ret;
2935 
2936     for (const auto& name : cameraDeviceNames) {
2937         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
2938         switch (deviceVersion) {
2939             case CAMERA_DEVICE_API_VERSION_3_6:
2940             case CAMERA_DEVICE_API_VERSION_3_5:
2941             case CAMERA_DEVICE_API_VERSION_3_4:
2942             case CAMERA_DEVICE_API_VERSION_3_3:
2943             case CAMERA_DEVICE_API_VERSION_3_2: {
2944                 ::android::sp<ICameraDevice> device3_x;
2945                 ALOGI("dumpState: Testing camera device %s", name.c_str());
2946                 ret = mProvider->getCameraDeviceInterface_V3_x(
2947                     name, [&](auto status, const auto& device) {
2948                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
2949                         ASSERT_EQ(Status::OK, status);
2950                         ASSERT_NE(device, nullptr);
2951                         device3_x = device;
2952                     });
2953                 ASSERT_TRUE(ret.isOk());
2954 
2955                 native_handle_t* raw_handle = native_handle_create(1, 0);
2956                 raw_handle->data[0] = open(kDumpOutput, O_RDWR);
2957                 ASSERT_GE(raw_handle->data[0], 0);
2958                 hidl_handle handle = raw_handle;
2959                 ret = device3_x->dumpState(handle);
2960                 ASSERT_TRUE(ret.isOk());
2961                 close(raw_handle->data[0]);
2962                 native_handle_delete(raw_handle);
2963             }
2964             break;
2965             case CAMERA_DEVICE_API_VERSION_1_0: {
2966                 ::android::sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
2967                 ALOGI("dumpState: Testing camera device %s", name.c_str());
2968                 ret = mProvider->getCameraDeviceInterface_V1_x(
2969                     name, [&](auto status, const auto& device) {
2970                         ALOGI("getCameraDeviceInterface_V1_x returns status:%d", (int)status);
2971                         ASSERT_EQ(Status::OK, status);
2972                         ASSERT_NE(device, nullptr);
2973                         device1 = device;
2974                     });
2975                 ASSERT_TRUE(ret.isOk());
2976 
2977                 native_handle_t* raw_handle = native_handle_create(1, 0);
2978                 raw_handle->data[0] = open(kDumpOutput, O_RDWR);
2979                 ASSERT_GE(raw_handle->data[0], 0);
2980                 hidl_handle handle = raw_handle;
2981                 Return<Status> returnStatus = device1->dumpState(handle);
2982                 ASSERT_TRUE(returnStatus.isOk());
2983                 ASSERT_EQ(Status::OK, returnStatus);
2984                 close(raw_handle->data[0]);
2985                 native_handle_delete(raw_handle);
2986             }
2987             break;
2988             default: {
2989                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
2990                 ADD_FAILURE();
2991             }
2992             break;
2993         }
2994     }
2995 }
2996 
2997 // Open, dumpStates, then close
TEST_P(CameraHidlTest,openClose)2998 TEST_P(CameraHidlTest, openClose) {
2999     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3000     Return<void> ret;
3001 
3002     for (const auto& name : cameraDeviceNames) {
3003         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3004         switch (deviceVersion) {
3005             case CAMERA_DEVICE_API_VERSION_3_6:
3006             case CAMERA_DEVICE_API_VERSION_3_5:
3007             case CAMERA_DEVICE_API_VERSION_3_4:
3008             case CAMERA_DEVICE_API_VERSION_3_3:
3009             case CAMERA_DEVICE_API_VERSION_3_2: {
3010                 ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> device3_x;
3011                 ALOGI("openClose: Testing camera device %s", name.c_str());
3012                 ret = mProvider->getCameraDeviceInterface_V3_x(
3013                     name, [&](auto status, const auto& device) {
3014                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
3015                         ASSERT_EQ(Status::OK, status);
3016                         ASSERT_NE(device, nullptr);
3017                         device3_x = device;
3018                     });
3019                 ASSERT_TRUE(ret.isOk());
3020 
3021                 sp<EmptyDeviceCb> cb = new EmptyDeviceCb;
3022                 sp<ICameraDeviceSession> session;
3023                 ret = device3_x->open(cb, [&](auto status, const auto& newSession) {
3024                     ALOGI("device::open returns status:%d", (int)status);
3025                     ASSERT_EQ(Status::OK, status);
3026                     ASSERT_NE(newSession, nullptr);
3027                     session = newSession;
3028                 });
3029                 ASSERT_TRUE(ret.isOk());
3030                 // Ensure that a device labeling itself as 3.3/3.4 can have its session interface
3031                 // cast the 3.3/3.4 interface, and that lower versions can't be cast to it.
3032                 sp<device::V3_3::ICameraDeviceSession> sessionV3_3;
3033                 sp<device::V3_4::ICameraDeviceSession> sessionV3_4;
3034                 sp<device::V3_5::ICameraDeviceSession> sessionV3_5;
3035                 sp<device::V3_6::ICameraDeviceSession> sessionV3_6;
3036                 castSession(session, deviceVersion, &sessionV3_3,
3037                         &sessionV3_4, &sessionV3_5, &sessionV3_6);
3038                 if (deviceVersion == CAMERA_DEVICE_API_VERSION_3_6) {
3039                     ASSERT_TRUE(sessionV3_6.get() != nullptr);
3040                 } else if (deviceVersion == CAMERA_DEVICE_API_VERSION_3_5) {
3041                     ASSERT_TRUE(sessionV3_5.get() != nullptr);
3042                 } else if (deviceVersion == CAMERA_DEVICE_API_VERSION_3_4) {
3043                     ASSERT_TRUE(sessionV3_4.get() != nullptr);
3044                 } else if (deviceVersion == CAMERA_DEVICE_API_VERSION_3_3) {
3045                     ASSERT_TRUE(sessionV3_3.get() != nullptr);
3046                 } else { //V3_2
3047                     ASSERT_TRUE(sessionV3_3.get() == nullptr);
3048                     ASSERT_TRUE(sessionV3_4.get() == nullptr);
3049                     ASSERT_TRUE(sessionV3_5.get() == nullptr);
3050                 }
3051                 native_handle_t* raw_handle = native_handle_create(1, 0);
3052                 raw_handle->data[0] = open(kDumpOutput, O_RDWR);
3053                 ASSERT_GE(raw_handle->data[0], 0);
3054                 hidl_handle handle = raw_handle;
3055                 ret = device3_x->dumpState(handle);
3056                 ASSERT_TRUE(ret.isOk());
3057                 close(raw_handle->data[0]);
3058                 native_handle_delete(raw_handle);
3059 
3060                 ret = session->close();
3061                 ASSERT_TRUE(ret.isOk());
3062                 // TODO: test all session API calls return INTERNAL_ERROR after close
3063                 // TODO: keep a wp copy here and verify session cannot be promoted out of this scope
3064             }
3065             break;
3066             case CAMERA_DEVICE_API_VERSION_1_0: {
3067                 sp<::android::hardware::camera::device::V1_0::ICameraDevice> device1;
3068                 openCameraDevice(name, mProvider, &device1 /*out*/);
3069                 ASSERT_NE(nullptr, device1.get());
3070 
3071                 native_handle_t* raw_handle = native_handle_create(1, 0);
3072                 raw_handle->data[0] = open(kDumpOutput, O_RDWR);
3073                 ASSERT_GE(raw_handle->data[0], 0);
3074                 hidl_handle handle = raw_handle;
3075                 Return<Status> returnStatus = device1->dumpState(handle);
3076                 ASSERT_TRUE(returnStatus.isOk());
3077                 ASSERT_EQ(Status::OK, returnStatus);
3078                 close(raw_handle->data[0]);
3079                 native_handle_delete(raw_handle);
3080 
3081                 ret = device1->close();
3082                 ASSERT_TRUE(ret.isOk());
3083             }
3084             break;
3085             default: {
3086                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3087                 ADD_FAILURE();
3088             }
3089             break;
3090         }
3091     }
3092 }
3093 
3094 // Check whether all common default request settings can be sucessfully
3095 // constructed.
TEST_P(CameraHidlTest,constructDefaultRequestSettings)3096 TEST_P(CameraHidlTest, constructDefaultRequestSettings) {
3097     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3098 
3099     for (const auto& name : cameraDeviceNames) {
3100         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3101         switch (deviceVersion) {
3102             case CAMERA_DEVICE_API_VERSION_3_6:
3103             case CAMERA_DEVICE_API_VERSION_3_5:
3104             case CAMERA_DEVICE_API_VERSION_3_4:
3105             case CAMERA_DEVICE_API_VERSION_3_3:
3106             case CAMERA_DEVICE_API_VERSION_3_2: {
3107                 ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> device3_x;
3108                 Return<void> ret;
3109                 ALOGI("constructDefaultRequestSettings: Testing camera device %s", name.c_str());
3110                 ret = mProvider->getCameraDeviceInterface_V3_x(
3111                     name, [&](auto status, const auto& device) {
3112                         ALOGI("getCameraDeviceInterface_V3_x returns status:%d", (int)status);
3113                         ASSERT_EQ(Status::OK, status);
3114                         ASSERT_NE(device, nullptr);
3115                         device3_x = device;
3116                     });
3117                 ASSERT_TRUE(ret.isOk());
3118 
3119                 sp<EmptyDeviceCb> cb = new EmptyDeviceCb;
3120                 sp<ICameraDeviceSession> session;
3121                 ret = device3_x->open(cb, [&](auto status, const auto& newSession) {
3122                     ALOGI("device::open returns status:%d", (int)status);
3123                     ASSERT_EQ(Status::OK, status);
3124                     ASSERT_NE(newSession, nullptr);
3125                     session = newSession;
3126                 });
3127                 ASSERT_TRUE(ret.isOk());
3128 
3129                 for (uint32_t t = (uint32_t)RequestTemplate::PREVIEW;
3130                      t <= (uint32_t)RequestTemplate::MANUAL; t++) {
3131                     RequestTemplate reqTemplate = (RequestTemplate)t;
3132                     ret =
3133                         session->constructDefaultRequestSettings(
3134                             reqTemplate, [&](auto status, const auto& req) {
3135                                 ALOGI("constructDefaultRequestSettings returns status:%d",
3136                                       (int)status);
3137                                 if (reqTemplate == RequestTemplate::ZERO_SHUTTER_LAG ||
3138                                         reqTemplate == RequestTemplate::MANUAL) {
3139                                     // optional templates
3140                                     ASSERT_TRUE((status == Status::OK) ||
3141                                             (status == Status::ILLEGAL_ARGUMENT));
3142                                 } else {
3143                                     ASSERT_EQ(Status::OK, status);
3144                                 }
3145 
3146                                 if (status == Status::OK) {
3147                                     const camera_metadata_t* metadata =
3148                                         (camera_metadata_t*) req.data();
3149                                     size_t expectedSize = req.size();
3150                                     int result = validate_camera_metadata_structure(
3151                                             metadata, &expectedSize);
3152                                     ASSERT_TRUE((result == 0) ||
3153                                             (result == CAMERA_METADATA_VALIDATION_SHIFTED));
3154                                     verifyRequestTemplate(metadata, reqTemplate);
3155                                 } else {
3156                                     ASSERT_EQ(0u, req.size());
3157                                 }
3158                             });
3159                     ASSERT_TRUE(ret.isOk());
3160                 }
3161                 ret = session->close();
3162                 ASSERT_TRUE(ret.isOk());
3163             }
3164             break;
3165             case CAMERA_DEVICE_API_VERSION_1_0: {
3166                 //Not applicable
3167             }
3168             break;
3169             default: {
3170                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3171                 ADD_FAILURE();
3172             }
3173             break;
3174         }
3175     }
3176 }
3177 
3178 // Verify that all supported stream formats and sizes can be configured
3179 // successfully.
TEST_P(CameraHidlTest,configureStreamsAvailableOutputs)3180 TEST_P(CameraHidlTest, configureStreamsAvailableOutputs) {
3181     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3182     std::vector<AvailableStream> outputStreams;
3183 
3184     for (const auto& name : cameraDeviceNames) {
3185         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3186         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
3187             continue;
3188         } else if (deviceVersion <= 0) {
3189             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3190             ADD_FAILURE();
3191             return;
3192         }
3193 
3194         camera_metadata_t* staticMeta;
3195         Return<void> ret;
3196         sp<ICameraDeviceSession> session;
3197         sp<device::V3_3::ICameraDeviceSession> session3_3;
3198         sp<device::V3_4::ICameraDeviceSession> session3_4;
3199         sp<device::V3_5::ICameraDeviceSession> session3_5;
3200         sp<device::V3_6::ICameraDeviceSession> session3_6;
3201         sp<device::V3_2::ICameraDevice> cameraDevice;
3202         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
3203         openEmptyDeviceSession(name, mProvider,
3204                 &session /*out*/, &staticMeta /*out*/, &cameraDevice /*out*/);
3205         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
3206         castDevice(cameraDevice, deviceVersion, &cameraDevice3_5);
3207 
3208         outputStreams.clear();
3209         ASSERT_EQ(Status::OK, getAvailableOutputStreams(staticMeta, outputStreams));
3210         ASSERT_NE(0u, outputStreams.size());
3211 
3212         uint32_t jpegBufferSize = 0;
3213         ASSERT_EQ(Status::OK, getJpegBufferSize(staticMeta, &jpegBufferSize));
3214         ASSERT_NE(0u, jpegBufferSize);
3215 
3216         int32_t streamId = 0;
3217         uint32_t streamConfigCounter = 0;
3218         for (auto& it : outputStreams) {
3219             V3_2::Stream stream3_2;
3220             V3_2::DataspaceFlags dataspaceFlag = getDataspace(static_cast<PixelFormat>(it.format));
3221             stream3_2 = {streamId,
3222                              StreamType::OUTPUT,
3223                              static_cast<uint32_t>(it.width),
3224                              static_cast<uint32_t>(it.height),
3225                              static_cast<PixelFormat>(it.format),
3226                              GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3227                              dataspaceFlag,
3228                              StreamRotation::ROTATION_0};
3229             ::android::hardware::hidl_vec<V3_2::Stream> streams3_2 = {stream3_2};
3230             ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
3231             ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
3232             ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
3233             createStreamConfiguration(streams3_2, StreamConfigurationMode::NORMAL_MODE,
3234                                       &config3_2, &config3_4, &config3_5, jpegBufferSize);
3235             if (session3_5 != nullptr) {
3236                 bool expectStreamCombQuery = (isLogicalMultiCamera(staticMeta) == Status::OK);
3237                 verifyStreamCombination(cameraDevice3_5, config3_4,
3238                         /*expectedStatus*/ true, expectStreamCombQuery);
3239                 config3_5.streamConfigCounter = streamConfigCounter++;
3240                 ret = session3_5->configureStreams_3_5(config3_5,
3241                         [streamId](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3242                             ASSERT_EQ(Status::OK, s);
3243                             ASSERT_EQ(1u, halConfig.streams.size());
3244                             ASSERT_EQ(halConfig.streams[0].v3_3.v3_2.id, streamId);
3245                         });
3246             } else if (session3_4 != nullptr) {
3247                 ret = session3_4->configureStreams_3_4(config3_4,
3248                         [streamId](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3249                             ASSERT_EQ(Status::OK, s);
3250                             ASSERT_EQ(1u, halConfig.streams.size());
3251                             ASSERT_EQ(halConfig.streams[0].v3_3.v3_2.id, streamId);
3252                         });
3253             } else if (session3_3 != nullptr) {
3254                 ret = session3_3->configureStreams_3_3(config3_2,
3255                         [streamId](Status s, device::V3_3::HalStreamConfiguration halConfig) {
3256                             ASSERT_EQ(Status::OK, s);
3257                             ASSERT_EQ(1u, halConfig.streams.size());
3258                             ASSERT_EQ(halConfig.streams[0].v3_2.id, streamId);
3259                         });
3260             } else {
3261                 ret = session->configureStreams(config3_2,
3262                         [streamId](Status s, HalStreamConfiguration halConfig) {
3263                             ASSERT_EQ(Status::OK, s);
3264                             ASSERT_EQ(1u, halConfig.streams.size());
3265                             ASSERT_EQ(halConfig.streams[0].id, streamId);
3266                         });
3267             }
3268             ASSERT_TRUE(ret.isOk());
3269             streamId++;
3270         }
3271 
3272         free_camera_metadata(staticMeta);
3273         ret = session->close();
3274         ASSERT_TRUE(ret.isOk());
3275     }
3276 }
3277 
3278 // Verify that mandatory concurrent streams and outputs are supported.
TEST_P(CameraHidlTest,configureConcurrentStreamsAvailableOutputs)3279 TEST_P(CameraHidlTest, configureConcurrentStreamsAvailableOutputs) {
3280     struct CameraTestInfo {
3281         camera_metadata_t* staticMeta = nullptr;
3282         sp<ICameraDeviceSession> session;
3283         sp<device::V3_3::ICameraDeviceSession> session3_3;
3284         sp<device::V3_4::ICameraDeviceSession> session3_4;
3285         sp<device::V3_5::ICameraDeviceSession> session3_5;
3286         sp<device::V3_6::ICameraDeviceSession> session3_6;
3287         sp<device::V3_2::ICameraDevice> cameraDevice;
3288         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
3289         ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
3290         ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
3291         ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
3292     };
3293     if (mProvider2_6 == nullptr) {
3294         // This test is provider@2.6 specific
3295         ALOGW("%s provider not 2_6, skipping", __func__);
3296         return;
3297     }
3298 
3299     std::map<hidl_string, hidl_string> idToNameMap = getCameraDeviceIdToNameMap(mProvider2_6);
3300     hidl_vec<hidl_vec<hidl_string>> concurrentDeviceCombinations =
3301             getConcurrentDeviceCombinations(mProvider2_6);
3302     std::vector<AvailableStream> outputStreams;
3303     for (const auto& cameraDeviceIds : concurrentDeviceCombinations) {
3304         std::vector<CameraIdAndStreamCombination> cameraIdsAndStreamCombinations;
3305         std::vector<CameraTestInfo> cameraTestInfos;
3306         size_t i = 0;
3307         for (const auto& id : cameraDeviceIds) {
3308             CameraTestInfo cti;
3309             Return<void> ret;
3310             auto it = idToNameMap.find(id);
3311             ASSERT_TRUE(idToNameMap.end() != it);
3312             hidl_string name = it->second;
3313             int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3314             if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
3315                 continue;
3316             } else if (deviceVersion <= 0) {
3317                 ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3318                 ADD_FAILURE();
3319                 return;
3320             }
3321             openEmptyDeviceSession(name, mProvider2_6, &cti.session /*out*/,
3322                                    &cti.staticMeta /*out*/, &cti.cameraDevice /*out*/);
3323             castSession(cti.session, deviceVersion, &cti.session3_3, &cti.session3_4,
3324                         &cti.session3_5, &cti.session3_6);
3325             castDevice(cti.cameraDevice, deviceVersion, &cti.cameraDevice3_5);
3326 
3327             outputStreams.clear();
3328             ASSERT_EQ(Status::OK, getMandatoryConcurrentStreams(cti.staticMeta, &outputStreams));
3329             ASSERT_NE(0u, outputStreams.size());
3330 
3331             uint32_t jpegBufferSize = 0;
3332             ASSERT_EQ(Status::OK, getJpegBufferSize(cti.staticMeta, &jpegBufferSize));
3333             ASSERT_NE(0u, jpegBufferSize);
3334 
3335             int32_t streamId = 0;
3336             ::android::hardware::hidl_vec<V3_2::Stream> streams3_2(outputStreams.size());
3337             size_t j = 0;
3338             for (const auto& it : outputStreams) {
3339                 V3_2::Stream stream3_2;
3340                 V3_2::DataspaceFlags dataspaceFlag =
3341                         getDataspace(static_cast<PixelFormat>(it.format));
3342                 stream3_2 = {streamId++,
3343                              StreamType::OUTPUT,
3344                              static_cast<uint32_t>(it.width),
3345                              static_cast<uint32_t>(it.height),
3346                              static_cast<PixelFormat>(it.format),
3347                              GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3348                              dataspaceFlag,
3349                              StreamRotation::ROTATION_0};
3350                 streams3_2[j] = stream3_2;
3351                 j++;
3352             }
3353 
3354             // Add the created stream configs to cameraIdsAndStreamCombinations
3355             createStreamConfiguration(streams3_2, StreamConfigurationMode::NORMAL_MODE,
3356                                       &cti.config3_2, &cti.config3_4, &cti.config3_5,
3357                                       jpegBufferSize);
3358 
3359             cti.config3_5.streamConfigCounter = outputStreams.size();
3360             CameraIdAndStreamCombination cameraIdAndStreamCombination;
3361             cameraIdAndStreamCombination.cameraId = id;
3362             cameraIdAndStreamCombination.streamConfiguration = cti.config3_4;
3363             cameraIdsAndStreamCombinations.push_back(cameraIdAndStreamCombination);
3364             i++;
3365             cameraTestInfos.push_back(cti);
3366         }
3367         // Now verify that concurrent streams are supported
3368         auto cb = [](Status s, bool supported) {
3369             ASSERT_EQ(Status::OK, s);
3370             ASSERT_EQ(supported, true);
3371         };
3372 
3373         auto ret = mProvider2_6->isConcurrentStreamCombinationSupported(
3374                 cameraIdsAndStreamCombinations, cb);
3375 
3376         // Test the stream can actually be configured
3377         for (const auto& cti : cameraTestInfos) {
3378             if (cti.session3_5 != nullptr) {
3379                 bool expectStreamCombQuery = (isLogicalMultiCamera(cti.staticMeta) == Status::OK);
3380                 verifyStreamCombination(cti.cameraDevice3_5, cti.config3_4,
3381                                         /*expectedStatus*/ true, expectStreamCombQuery);
3382                 ret = cti.session3_5->configureStreams_3_5(
3383                         cti.config3_5,
3384                         [&cti](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3385                             ASSERT_EQ(Status::OK, s);
3386                             ASSERT_EQ(cti.config3_5.v3_4.streams.size(), halConfig.streams.size());
3387                         });
3388             } else if (cti.session3_4 != nullptr) {
3389                 ret = cti.session3_4->configureStreams_3_4(
3390                         cti.config3_4,
3391                         [&cti](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3392                             ASSERT_EQ(Status::OK, s);
3393                             ASSERT_EQ(cti.config3_4.streams.size(), halConfig.streams.size());
3394                         });
3395             } else if (cti.session3_3 != nullptr) {
3396                 ret = cti.session3_3->configureStreams_3_3(
3397                         cti.config3_2,
3398                         [&cti](Status s, device::V3_3::HalStreamConfiguration halConfig) {
3399                             ASSERT_EQ(Status::OK, s);
3400                             ASSERT_EQ(cti.config3_2.streams.size(), halConfig.streams.size());
3401                         });
3402             } else {
3403                 ret = cti.session->configureStreams(
3404                         cti.config3_2, [&cti](Status s, HalStreamConfiguration halConfig) {
3405                             ASSERT_EQ(Status::OK, s);
3406                             ASSERT_EQ(cti.config3_2.streams.size(), halConfig.streams.size());
3407                         });
3408             }
3409             ASSERT_TRUE(ret.isOk());
3410         }
3411 
3412         for (const auto& cti : cameraTestInfos) {
3413             free_camera_metadata(cti.staticMeta);
3414             ret = cti.session->close();
3415             ASSERT_TRUE(ret.isOk());
3416         }
3417     }
3418 }
3419 
3420 // Check for correct handling of invalid/incorrect configuration parameters.
TEST_P(CameraHidlTest,configureStreamsInvalidOutputs)3421 TEST_P(CameraHidlTest, configureStreamsInvalidOutputs) {
3422     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3423     std::vector<AvailableStream> outputStreams;
3424 
3425     for (const auto& name : cameraDeviceNames) {
3426         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3427         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
3428             continue;
3429         } else if (deviceVersion <= 0) {
3430             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3431             ADD_FAILURE();
3432             return;
3433         }
3434 
3435         camera_metadata_t* staticMeta;
3436         Return<void> ret;
3437         sp<ICameraDeviceSession> session;
3438         sp<device::V3_3::ICameraDeviceSession> session3_3;
3439         sp<device::V3_4::ICameraDeviceSession> session3_4;
3440         sp<device::V3_5::ICameraDeviceSession> session3_5;
3441         sp<device::V3_6::ICameraDeviceSession> session3_6;
3442         sp<device::V3_2::ICameraDevice> cameraDevice;
3443         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
3444         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMeta /*out*/,
3445                 &cameraDevice /*out*/);
3446         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
3447         castDevice(cameraDevice, deviceVersion, &cameraDevice3_5);
3448 
3449         outputStreams.clear();
3450         ASSERT_EQ(Status::OK, getAvailableOutputStreams(staticMeta, outputStreams));
3451         ASSERT_NE(0u, outputStreams.size());
3452 
3453         uint32_t jpegBufferSize = 0;
3454         ASSERT_EQ(Status::OK, getJpegBufferSize(staticMeta, &jpegBufferSize));
3455         ASSERT_NE(0u, jpegBufferSize);
3456 
3457         int32_t streamId = 0;
3458         V3_2::Stream stream3_2 = {streamId++,
3459                          StreamType::OUTPUT,
3460                          static_cast<uint32_t>(0),
3461                          static_cast<uint32_t>(0),
3462                          static_cast<PixelFormat>(outputStreams[0].format),
3463                          GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3464                          0,
3465                          StreamRotation::ROTATION_0};
3466         uint32_t streamConfigCounter = 0;
3467         ::android::hardware::hidl_vec<V3_2::Stream> streams = {stream3_2};
3468         ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
3469         ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
3470         ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
3471         createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
3472                                   &config3_2, &config3_4, &config3_5, jpegBufferSize);
3473         if (session3_5 != nullptr) {
3474             verifyStreamCombination(cameraDevice3_5, config3_4, /*expectedStatus*/ false,
3475                     /*expectStreamCombQuery*/false);
3476             config3_5.streamConfigCounter = streamConfigCounter++;
3477             ret = session3_5->configureStreams_3_5(config3_5,
3478                     [](Status s, device::V3_4::HalStreamConfiguration) {
3479                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
3480                             (Status::INTERNAL_ERROR == s));
3481                     });
3482         } else if (session3_4 != nullptr) {
3483             ret = session3_4->configureStreams_3_4(config3_4,
3484                     [](Status s, device::V3_4::HalStreamConfiguration) {
3485                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
3486                                 (Status::INTERNAL_ERROR == s));
3487                     });
3488         } else if(session3_3 != nullptr) {
3489             ret = session3_3->configureStreams_3_3(config3_2,
3490                     [](Status s, device::V3_3::HalStreamConfiguration) {
3491                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
3492                                 (Status::INTERNAL_ERROR == s));
3493                     });
3494         } else {
3495             ret = session->configureStreams(config3_2,
3496                     [](Status s, HalStreamConfiguration) {
3497                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
3498                                 (Status::INTERNAL_ERROR == s));
3499                     });
3500         }
3501         ASSERT_TRUE(ret.isOk());
3502 
3503         stream3_2 = {streamId++,
3504                   StreamType::OUTPUT,
3505                   static_cast<uint32_t>(UINT32_MAX),
3506                   static_cast<uint32_t>(UINT32_MAX),
3507                   static_cast<PixelFormat>(outputStreams[0].format),
3508                   GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3509                   0,
3510                   StreamRotation::ROTATION_0};
3511         streams[0] = stream3_2;
3512         createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
3513                 &config3_2, &config3_4, &config3_5, jpegBufferSize);
3514         if (session3_5 != nullptr) {
3515             config3_5.streamConfigCounter = streamConfigCounter++;
3516             ret = session3_5->configureStreams_3_5(config3_5, [](Status s,
3517                         device::V3_4::HalStreamConfiguration) {
3518                     ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3519                 });
3520         } else if(session3_4 != nullptr) {
3521             ret = session3_4->configureStreams_3_4(config3_4, [](Status s,
3522                         device::V3_4::HalStreamConfiguration) {
3523                     ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3524                 });
3525         } else if(session3_3 != nullptr) {
3526             ret = session3_3->configureStreams_3_3(config3_2, [](Status s,
3527                         device::V3_3::HalStreamConfiguration) {
3528                     ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3529                 });
3530         } else {
3531             ret = session->configureStreams(config3_2, [](Status s,
3532                         HalStreamConfiguration) {
3533                     ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3534                 });
3535         }
3536         ASSERT_TRUE(ret.isOk());
3537 
3538         for (auto& it : outputStreams) {
3539             stream3_2 = {streamId++,
3540                       StreamType::OUTPUT,
3541                       static_cast<uint32_t>(it.width),
3542                       static_cast<uint32_t>(it.height),
3543                       static_cast<PixelFormat>(UINT32_MAX),
3544                       GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3545                       0,
3546                       StreamRotation::ROTATION_0};
3547             streams[0] = stream3_2;
3548             createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
3549                     &config3_2, &config3_4, &config3_5, jpegBufferSize);
3550             if (session3_5 != nullptr) {
3551                 config3_5.streamConfigCounter = streamConfigCounter++;
3552                 ret = session3_5->configureStreams_3_5(config3_5,
3553                         [](Status s, device::V3_4::HalStreamConfiguration) {
3554                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3555                         });
3556             } else if(session3_4 != nullptr) {
3557                 ret = session3_4->configureStreams_3_4(config3_4,
3558                         [](Status s, device::V3_4::HalStreamConfiguration) {
3559                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3560                         });
3561             } else if(session3_3 != nullptr) {
3562                 ret = session3_3->configureStreams_3_3(config3_2,
3563                         [](Status s, device::V3_3::HalStreamConfiguration) {
3564                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3565                         });
3566             } else {
3567                 ret = session->configureStreams(config3_2,
3568                         [](Status s, HalStreamConfiguration) {
3569                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3570                         });
3571             }
3572             ASSERT_TRUE(ret.isOk());
3573 
3574             stream3_2 = {streamId++,
3575                       StreamType::OUTPUT,
3576                       static_cast<uint32_t>(it.width),
3577                       static_cast<uint32_t>(it.height),
3578                       static_cast<PixelFormat>(it.format),
3579                       GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3580                       0,
3581                       static_cast<StreamRotation>(UINT32_MAX)};
3582             streams[0] = stream3_2;
3583             createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
3584                     &config3_2, &config3_4, &config3_5, jpegBufferSize);
3585             if (session3_5 != nullptr) {
3586                 config3_5.streamConfigCounter = streamConfigCounter++;
3587                 ret = session3_5->configureStreams_3_5(config3_5,
3588                         [](Status s, device::V3_4::HalStreamConfiguration) {
3589                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3590                         });
3591             } else if(session3_4 != nullptr) {
3592                 ret = session3_4->configureStreams_3_4(config3_4,
3593                         [](Status s, device::V3_4::HalStreamConfiguration) {
3594                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3595                         });
3596             } else if(session3_3 != nullptr) {
3597                 ret = session3_3->configureStreams_3_3(config3_2,
3598                         [](Status s, device::V3_3::HalStreamConfiguration) {
3599                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3600                         });
3601             } else {
3602                 ret = session->configureStreams(config3_2,
3603                         [](Status s, HalStreamConfiguration) {
3604                             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
3605                         });
3606             }
3607             ASSERT_TRUE(ret.isOk());
3608         }
3609 
3610         free_camera_metadata(staticMeta);
3611         ret = session->close();
3612         ASSERT_TRUE(ret.isOk());
3613     }
3614 }
3615 
3616 // Check whether all supported ZSL output stream combinations can be
3617 // configured successfully.
TEST_P(CameraHidlTest,configureStreamsZSLInputOutputs)3618 TEST_P(CameraHidlTest, configureStreamsZSLInputOutputs) {
3619     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3620     std::vector<AvailableStream> inputStreams;
3621     std::vector<AvailableZSLInputOutput> inputOutputMap;
3622 
3623     for (const auto& name : cameraDeviceNames) {
3624         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3625         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
3626             continue;
3627         } else if (deviceVersion <= 0) {
3628             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3629             ADD_FAILURE();
3630             return;
3631         }
3632 
3633         camera_metadata_t* staticMeta;
3634         Return<void> ret;
3635         sp<ICameraDeviceSession> session;
3636         sp<device::V3_3::ICameraDeviceSession> session3_3;
3637         sp<device::V3_4::ICameraDeviceSession> session3_4;
3638         sp<device::V3_5::ICameraDeviceSession> session3_5;
3639         sp<device::V3_6::ICameraDeviceSession> session3_6;
3640         sp<device::V3_2::ICameraDevice> cameraDevice;
3641         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
3642         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMeta /*out*/,
3643                 &cameraDevice /*out*/);
3644         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
3645         castDevice(cameraDevice, deviceVersion, &cameraDevice3_5);
3646 
3647         Status rc = isZSLModeAvailable(staticMeta);
3648         if (Status::METHOD_NOT_SUPPORTED == rc) {
3649             ret = session->close();
3650             ASSERT_TRUE(ret.isOk());
3651             continue;
3652         }
3653         ASSERT_EQ(Status::OK, rc);
3654 
3655         inputStreams.clear();
3656         ASSERT_EQ(Status::OK, getAvailableOutputStreams(staticMeta, inputStreams));
3657         ASSERT_NE(0u, inputStreams.size());
3658 
3659         inputOutputMap.clear();
3660         ASSERT_EQ(Status::OK, getZSLInputOutputMap(staticMeta, inputOutputMap));
3661         ASSERT_NE(0u, inputOutputMap.size());
3662 
3663         bool supportMonoY8 = false;
3664         if (Status::OK == isMonochromeCamera(staticMeta)) {
3665             for (auto& it : inputStreams) {
3666                 if (it.format == static_cast<uint32_t>(PixelFormat::Y8)) {
3667                     supportMonoY8 = true;
3668                     break;
3669                 }
3670             }
3671         }
3672 
3673         uint32_t jpegBufferSize = 0;
3674         ASSERT_EQ(Status::OK, getJpegBufferSize(staticMeta, &jpegBufferSize));
3675         ASSERT_NE(0u, jpegBufferSize);
3676 
3677         int32_t streamId = 0;
3678         bool hasPrivToY8 = false, hasY8ToY8 = false, hasY8ToBlob = false;
3679         uint32_t streamConfigCounter = 0;
3680         for (auto& inputIter : inputOutputMap) {
3681             AvailableStream input;
3682             ASSERT_EQ(Status::OK, findLargestSize(inputStreams, inputIter.inputFormat,
3683                     input));
3684             ASSERT_NE(0u, inputStreams.size());
3685 
3686             if (inputIter.inputFormat == static_cast<uint32_t>(PixelFormat::IMPLEMENTATION_DEFINED)
3687                     && inputIter.outputFormat == static_cast<uint32_t>(PixelFormat::Y8)) {
3688                 hasPrivToY8 = true;
3689             } else if (inputIter.inputFormat == static_cast<uint32_t>(PixelFormat::Y8)) {
3690                 if (inputIter.outputFormat == static_cast<uint32_t>(PixelFormat::BLOB)) {
3691                     hasY8ToBlob = true;
3692                 } else if (inputIter.outputFormat == static_cast<uint32_t>(PixelFormat::Y8)) {
3693                     hasY8ToY8 = true;
3694                 }
3695             }
3696             AvailableStream outputThreshold = {INT32_MAX, INT32_MAX,
3697                                                inputIter.outputFormat};
3698             std::vector<AvailableStream> outputStreams;
3699             ASSERT_EQ(Status::OK,
3700                       getAvailableOutputStreams(staticMeta, outputStreams,
3701                               &outputThreshold));
3702             for (auto& outputIter : outputStreams) {
3703                 V3_2::Stream zslStream = {streamId++,
3704                                     StreamType::OUTPUT,
3705                                     static_cast<uint32_t>(input.width),
3706                                     static_cast<uint32_t>(input.height),
3707                                     static_cast<PixelFormat>(input.format),
3708                                     GRALLOC_USAGE_HW_CAMERA_ZSL,
3709                                     0,
3710                                     StreamRotation::ROTATION_0};
3711                 V3_2::Stream inputStream = {streamId++,
3712                                       StreamType::INPUT,
3713                                       static_cast<uint32_t>(input.width),
3714                                       static_cast<uint32_t>(input.height),
3715                                       static_cast<PixelFormat>(input.format),
3716                                       0,
3717                                       0,
3718                                       StreamRotation::ROTATION_0};
3719                 V3_2::Stream outputStream = {streamId++,
3720                                        StreamType::OUTPUT,
3721                                        static_cast<uint32_t>(outputIter.width),
3722                                        static_cast<uint32_t>(outputIter.height),
3723                                        static_cast<PixelFormat>(outputIter.format),
3724                                        GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3725                                        0,
3726                                        StreamRotation::ROTATION_0};
3727 
3728                 ::android::hardware::hidl_vec<V3_2::Stream> streams = {inputStream, zslStream,
3729                                                                  outputStream};
3730                 ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
3731                 ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
3732                 ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
3733                 createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
3734                                           &config3_2, &config3_4, &config3_5, jpegBufferSize);
3735                 if (session3_5 != nullptr) {
3736                     verifyStreamCombination(cameraDevice3_5, config3_4,
3737                             /*expectedStatus*/ true, /*expectStreamCombQuery*/ false);
3738                     config3_5.streamConfigCounter = streamConfigCounter++;
3739                     ret = session3_5->configureStreams_3_5(config3_5,
3740                             [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3741                                 ASSERT_EQ(Status::OK, s);
3742                                 ASSERT_EQ(3u, halConfig.streams.size());
3743                             });
3744                 } else if (session3_4 != nullptr) {
3745                     ret = session3_4->configureStreams_3_4(config3_4,
3746                             [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3747                                 ASSERT_EQ(Status::OK, s);
3748                                 ASSERT_EQ(3u, halConfig.streams.size());
3749                             });
3750                 } else if (session3_3 != nullptr) {
3751                     ret = session3_3->configureStreams_3_3(config3_2,
3752                             [](Status s, device::V3_3::HalStreamConfiguration halConfig) {
3753                                 ASSERT_EQ(Status::OK, s);
3754                                 ASSERT_EQ(3u, halConfig.streams.size());
3755                             });
3756                 } else {
3757                     ret = session->configureStreams(config3_2,
3758                             [](Status s, HalStreamConfiguration halConfig) {
3759                                 ASSERT_EQ(Status::OK, s);
3760                                 ASSERT_EQ(3u, halConfig.streams.size());
3761                             });
3762                 }
3763                 ASSERT_TRUE(ret.isOk());
3764             }
3765         }
3766 
3767         if (supportMonoY8) {
3768             if (Status::OK == isZSLModeAvailable(staticMeta, PRIV_REPROCESS)) {
3769                 ASSERT_TRUE(hasPrivToY8);
3770             }
3771             if (Status::OK == isZSLModeAvailable(staticMeta, YUV_REPROCESS)) {
3772                 ASSERT_TRUE(hasY8ToY8);
3773                 ASSERT_TRUE(hasY8ToBlob);
3774             }
3775         }
3776 
3777         free_camera_metadata(staticMeta);
3778         ret = session->close();
3779         ASSERT_TRUE(ret.isOk());
3780     }
3781 }
3782 
3783 // Check whether session parameters are supported. If Hal support for them
3784 // exist, then try to configure a preview stream using them.
TEST_P(CameraHidlTest,configureStreamsWithSessionParameters)3785 TEST_P(CameraHidlTest, configureStreamsWithSessionParameters) {
3786     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3787     std::vector<AvailableStream> outputPreviewStreams;
3788     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
3789                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
3790 
3791     for (const auto& name : cameraDeviceNames) {
3792         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3793         if (deviceVersion <= 0) {
3794             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3795             ADD_FAILURE();
3796             return;
3797         } else if (deviceVersion < CAMERA_DEVICE_API_VERSION_3_4) {
3798             continue;
3799         }
3800 
3801         camera_metadata_t* staticMetaBuffer;
3802         Return<void> ret;
3803         sp<ICameraDeviceSession> session;
3804         sp<device::V3_3::ICameraDeviceSession> session3_3;
3805         sp<device::V3_4::ICameraDeviceSession> session3_4;
3806         sp<device::V3_5::ICameraDeviceSession> session3_5;
3807         sp<device::V3_6::ICameraDeviceSession> session3_6;
3808         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMetaBuffer /*out*/);
3809         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
3810         if (deviceVersion == CAMERA_DEVICE_API_VERSION_3_4) {
3811             ASSERT_NE(session3_4, nullptr);
3812         } else {
3813             ASSERT_NE(session3_5, nullptr);
3814         }
3815 
3816         std::unordered_set<int32_t> availableSessionKeys;
3817         auto rc = getSupportedKeys(staticMetaBuffer, ANDROID_REQUEST_AVAILABLE_SESSION_KEYS,
3818                 &availableSessionKeys);
3819         ASSERT_TRUE(Status::OK == rc);
3820         if (availableSessionKeys.empty()) {
3821             free_camera_metadata(staticMetaBuffer);
3822             ret = session->close();
3823             ASSERT_TRUE(ret.isOk());
3824             continue;
3825         }
3826 
3827         android::hardware::camera::common::V1_0::helper::CameraMetadata previewRequestSettings;
3828         android::hardware::camera::common::V1_0::helper::CameraMetadata sessionParams,
3829                 modifiedSessionParams;
3830         constructFilteredSettings(session, availableSessionKeys, RequestTemplate::PREVIEW,
3831                 &previewRequestSettings, &sessionParams);
3832         if (sessionParams.isEmpty()) {
3833             free_camera_metadata(staticMetaBuffer);
3834             ret = session->close();
3835             ASSERT_TRUE(ret.isOk());
3836             continue;
3837         }
3838 
3839         outputPreviewStreams.clear();
3840 
3841         ASSERT_EQ(Status::OK, getAvailableOutputStreams(staticMetaBuffer, outputPreviewStreams,
3842                 &previewThreshold));
3843         ASSERT_NE(0u, outputPreviewStreams.size());
3844 
3845         V3_4::Stream previewStream;
3846         previewStream.v3_2 = {0,
3847                                 StreamType::OUTPUT,
3848                                 static_cast<uint32_t>(outputPreviewStreams[0].width),
3849                                 static_cast<uint32_t>(outputPreviewStreams[0].height),
3850                                 static_cast<PixelFormat>(outputPreviewStreams[0].format),
3851                                 GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3852                                 0,
3853                                 StreamRotation::ROTATION_0};
3854         previewStream.bufferSize = 0;
3855         ::android::hardware::hidl_vec<V3_4::Stream> streams = {previewStream};
3856         ::android::hardware::camera::device::V3_4::StreamConfiguration config;
3857         ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
3858         config.streams = streams;
3859         config.operationMode = StreamConfigurationMode::NORMAL_MODE;
3860         modifiedSessionParams = sessionParams;
3861         auto sessionParamsBuffer = sessionParams.release();
3862         config.sessionParams.setToExternal(reinterpret_cast<uint8_t *> (sessionParamsBuffer),
3863                 get_camera_metadata_size(sessionParamsBuffer));
3864         config3_5.v3_4 = config;
3865         config3_5.streamConfigCounter = 0;
3866         if (session3_5 != nullptr) {
3867             bool newSessionParamsAvailable = false;
3868             for (const auto& it : availableSessionKeys) {
3869                 if (modifiedSessionParams.exists(it)) {
3870                     modifiedSessionParams.erase(it);
3871                     newSessionParamsAvailable = true;
3872                     break;
3873                 }
3874             }
3875             if (newSessionParamsAvailable) {
3876                 auto modifiedSessionParamsBuffer = modifiedSessionParams.release();
3877                 verifySessionReconfigurationQuery(session3_5, sessionParamsBuffer,
3878                         modifiedSessionParamsBuffer);
3879                 modifiedSessionParams.acquire(modifiedSessionParamsBuffer);
3880             }
3881 
3882             ret = session3_5->configureStreams_3_5(config3_5,
3883                     [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3884                         ASSERT_EQ(Status::OK, s);
3885                         ASSERT_EQ(1u, halConfig.streams.size());
3886                     });
3887         } else {
3888             ret = session3_4->configureStreams_3_4(config,
3889                     [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3890                         ASSERT_EQ(Status::OK, s);
3891                         ASSERT_EQ(1u, halConfig.streams.size());
3892                     });
3893         }
3894         sessionParams.acquire(sessionParamsBuffer);
3895         ASSERT_TRUE(ret.isOk());
3896 
3897         free_camera_metadata(staticMetaBuffer);
3898         ret = session->close();
3899         ASSERT_TRUE(ret.isOk());
3900     }
3901 }
3902 
3903 // Verify that all supported preview + still capture stream combinations
3904 // can be configured successfully.
TEST_P(CameraHidlTest,configureStreamsPreviewStillOutputs)3905 TEST_P(CameraHidlTest, configureStreamsPreviewStillOutputs) {
3906     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
3907     std::vector<AvailableStream> outputBlobStreams;
3908     std::vector<AvailableStream> outputPreviewStreams;
3909     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
3910                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
3911     AvailableStream blobThreshold = {INT32_MAX, INT32_MAX,
3912                                      static_cast<int32_t>(PixelFormat::BLOB)};
3913 
3914     for (const auto& name : cameraDeviceNames) {
3915         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
3916         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
3917             continue;
3918         } else if (deviceVersion <= 0) {
3919             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
3920             ADD_FAILURE();
3921             return;
3922         }
3923 
3924         camera_metadata_t* staticMeta;
3925         Return<void> ret;
3926         sp<ICameraDeviceSession> session;
3927         sp<device::V3_3::ICameraDeviceSession> session3_3;
3928         sp<device::V3_4::ICameraDeviceSession> session3_4;
3929         sp<device::V3_5::ICameraDeviceSession> session3_5;
3930         sp<device::V3_6::ICameraDeviceSession> session3_6;
3931         sp<device::V3_2::ICameraDevice> cameraDevice;
3932         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
3933         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMeta /*out*/,
3934                 &cameraDevice /*out*/);
3935         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
3936         castDevice(cameraDevice, deviceVersion, &cameraDevice3_5);
3937 
3938         // Check if camera support depth only
3939         if (isDepthOnly(staticMeta)) {
3940             free_camera_metadata(staticMeta);
3941             ret = session->close();
3942             ASSERT_TRUE(ret.isOk());
3943             continue;
3944         }
3945 
3946         outputBlobStreams.clear();
3947         ASSERT_EQ(Status::OK,
3948                   getAvailableOutputStreams(staticMeta, outputBlobStreams,
3949                           &blobThreshold));
3950         ASSERT_NE(0u, outputBlobStreams.size());
3951 
3952         outputPreviewStreams.clear();
3953         ASSERT_EQ(Status::OK, getAvailableOutputStreams(staticMeta, outputPreviewStreams,
3954                 &previewThreshold));
3955         ASSERT_NE(0u, outputPreviewStreams.size());
3956 
3957         uint32_t jpegBufferSize = 0;
3958         ASSERT_EQ(Status::OK, getJpegBufferSize(staticMeta, &jpegBufferSize));
3959         ASSERT_NE(0u, jpegBufferSize);
3960 
3961         int32_t streamId = 0;
3962         uint32_t streamConfigCounter = 0;
3963         for (auto& blobIter : outputBlobStreams) {
3964             for (auto& previewIter : outputPreviewStreams) {
3965                 V3_2::Stream previewStream = {streamId++,
3966                                         StreamType::OUTPUT,
3967                                         static_cast<uint32_t>(previewIter.width),
3968                                         static_cast<uint32_t>(previewIter.height),
3969                                         static_cast<PixelFormat>(previewIter.format),
3970                                         GRALLOC1_CONSUMER_USAGE_HWCOMPOSER,
3971                                         0,
3972                                         StreamRotation::ROTATION_0};
3973                 V3_2::Stream blobStream = {streamId++,
3974                                      StreamType::OUTPUT,
3975                                      static_cast<uint32_t>(blobIter.width),
3976                                      static_cast<uint32_t>(blobIter.height),
3977                                      static_cast<PixelFormat>(blobIter.format),
3978                                      GRALLOC1_CONSUMER_USAGE_CPU_READ,
3979                                      static_cast<V3_2::DataspaceFlags>(Dataspace::V0_JFIF),
3980                                      StreamRotation::ROTATION_0};
3981                 ::android::hardware::hidl_vec<V3_2::Stream> streams = {previewStream,
3982                                                                  blobStream};
3983                 ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
3984                 ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
3985                 ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
3986                 createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
3987                                           &config3_2, &config3_4, &config3_5, jpegBufferSize);
3988                 if (session3_5 != nullptr) {
3989                     verifyStreamCombination(cameraDevice3_5, config3_4,
3990                             /*expectedStatus*/ true, /*expectStreamCombQuery*/ false);
3991                     config3_5.streamConfigCounter = streamConfigCounter++;
3992                     ret = session3_5->configureStreams_3_5(config3_5,
3993                             [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
3994                                 ASSERT_EQ(Status::OK, s);
3995                                 ASSERT_EQ(2u, halConfig.streams.size());
3996                             });
3997                 } else if (session3_4 != nullptr) {
3998                     ret = session3_4->configureStreams_3_4(config3_4,
3999                             [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
4000                                 ASSERT_EQ(Status::OK, s);
4001                                 ASSERT_EQ(2u, halConfig.streams.size());
4002                             });
4003                 } else if (session3_3 != nullptr) {
4004                     ret = session3_3->configureStreams_3_3(config3_2,
4005                             [](Status s, device::V3_3::HalStreamConfiguration halConfig) {
4006                                 ASSERT_EQ(Status::OK, s);
4007                                 ASSERT_EQ(2u, halConfig.streams.size());
4008                             });
4009                 } else {
4010                     ret = session->configureStreams(config3_2,
4011                             [](Status s, HalStreamConfiguration halConfig) {
4012                                 ASSERT_EQ(Status::OK, s);
4013                                 ASSERT_EQ(2u, halConfig.streams.size());
4014                             });
4015                 }
4016                 ASSERT_TRUE(ret.isOk());
4017             }
4018         }
4019 
4020         free_camera_metadata(staticMeta);
4021         ret = session->close();
4022         ASSERT_TRUE(ret.isOk());
4023     }
4024 }
4025 
4026 // In case constrained mode is supported, test whether it can be
4027 // configured. Additionally check for common invalid inputs when
4028 // using this mode.
TEST_P(CameraHidlTest,configureStreamsConstrainedOutputs)4029 TEST_P(CameraHidlTest, configureStreamsConstrainedOutputs) {
4030     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
4031 
4032     for (const auto& name : cameraDeviceNames) {
4033         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
4034         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
4035             continue;
4036         } else if (deviceVersion <= 0) {
4037             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
4038             ADD_FAILURE();
4039             return;
4040         }
4041 
4042         camera_metadata_t* staticMeta;
4043         Return<void> ret;
4044         sp<ICameraDeviceSession> session;
4045         sp<device::V3_3::ICameraDeviceSession> session3_3;
4046         sp<device::V3_4::ICameraDeviceSession> session3_4;
4047         sp<device::V3_5::ICameraDeviceSession> session3_5;
4048         sp<device::V3_6::ICameraDeviceSession> session3_6;
4049         sp<device::V3_2::ICameraDevice> cameraDevice;
4050         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
4051         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMeta /*out*/,
4052                 &cameraDevice /*out*/);
4053         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
4054         castDevice(cameraDevice, deviceVersion, &cameraDevice3_5);
4055 
4056         Status rc = isConstrainedModeAvailable(staticMeta);
4057         if (Status::METHOD_NOT_SUPPORTED == rc) {
4058             ret = session->close();
4059             ASSERT_TRUE(ret.isOk());
4060             continue;
4061         }
4062         ASSERT_EQ(Status::OK, rc);
4063 
4064         AvailableStream hfrStream;
4065         rc = pickConstrainedModeSize(staticMeta, hfrStream);
4066         ASSERT_EQ(Status::OK, rc);
4067 
4068         int32_t streamId = 0;
4069         uint32_t streamConfigCounter = 0;
4070         V3_2::Stream stream = {streamId,
4071                          StreamType::OUTPUT,
4072                          static_cast<uint32_t>(hfrStream.width),
4073                          static_cast<uint32_t>(hfrStream.height),
4074                          static_cast<PixelFormat>(hfrStream.format),
4075                          GRALLOC1_CONSUMER_USAGE_VIDEO_ENCODER,
4076                          0,
4077                          StreamRotation::ROTATION_0};
4078         ::android::hardware::hidl_vec<V3_2::Stream> streams = {stream};
4079         ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
4080         ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
4081         ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
4082         createStreamConfiguration(streams, StreamConfigurationMode::CONSTRAINED_HIGH_SPEED_MODE,
4083                                   &config3_2, &config3_4, &config3_5);
4084         if (session3_5 != nullptr) {
4085             verifyStreamCombination(cameraDevice3_5, config3_4,
4086                     /*expectedStatus*/ true, /*expectStreamCombQuery*/ false);
4087             config3_5.streamConfigCounter = streamConfigCounter++;
4088             ret = session3_5->configureStreams_3_5(config3_5,
4089                     [streamId](Status s, device::V3_4::HalStreamConfiguration halConfig) {
4090                         ASSERT_EQ(Status::OK, s);
4091                         ASSERT_EQ(1u, halConfig.streams.size());
4092                         ASSERT_EQ(halConfig.streams[0].v3_3.v3_2.id, streamId);
4093                     });
4094         } else if (session3_4 != nullptr) {
4095             ret = session3_4->configureStreams_3_4(config3_4,
4096                     [streamId](Status s, device::V3_4::HalStreamConfiguration halConfig) {
4097                         ASSERT_EQ(Status::OK, s);
4098                         ASSERT_EQ(1u, halConfig.streams.size());
4099                         ASSERT_EQ(halConfig.streams[0].v3_3.v3_2.id, streamId);
4100                     });
4101         } else if (session3_3 != nullptr) {
4102             ret = session3_3->configureStreams_3_3(config3_2,
4103                     [streamId](Status s, device::V3_3::HalStreamConfiguration halConfig) {
4104                         ASSERT_EQ(Status::OK, s);
4105                         ASSERT_EQ(1u, halConfig.streams.size());
4106                         ASSERT_EQ(halConfig.streams[0].v3_2.id, streamId);
4107                     });
4108         } else {
4109             ret = session->configureStreams(config3_2,
4110                     [streamId](Status s, HalStreamConfiguration halConfig) {
4111                         ASSERT_EQ(Status::OK, s);
4112                         ASSERT_EQ(1u, halConfig.streams.size());
4113                         ASSERT_EQ(halConfig.streams[0].id, streamId);
4114                     });
4115         }
4116         ASSERT_TRUE(ret.isOk());
4117 
4118         stream = {streamId++,
4119                   StreamType::OUTPUT,
4120                   static_cast<uint32_t>(0),
4121                   static_cast<uint32_t>(0),
4122                   static_cast<PixelFormat>(hfrStream.format),
4123                   GRALLOC1_CONSUMER_USAGE_VIDEO_ENCODER,
4124                   0,
4125                   StreamRotation::ROTATION_0};
4126         streams[0] = stream;
4127         createStreamConfiguration(streams, StreamConfigurationMode::CONSTRAINED_HIGH_SPEED_MODE,
4128                                   &config3_2, &config3_4, &config3_5);
4129         if (session3_5 != nullptr) {
4130             config3_5.streamConfigCounter = streamConfigCounter++;
4131             ret = session3_5->configureStreams_3_5(config3_5,
4132                     [](Status s, device::V3_4::HalStreamConfiguration) {
4133                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
4134                                 (Status::INTERNAL_ERROR == s));
4135                     });
4136         } else if (session3_4 != nullptr) {
4137             ret = session3_4->configureStreams_3_4(config3_4,
4138                     [](Status s, device::V3_4::HalStreamConfiguration) {
4139                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
4140                                 (Status::INTERNAL_ERROR == s));
4141                     });
4142         } else if (session3_3 != nullptr) {
4143             ret = session3_3->configureStreams_3_3(config3_2,
4144                     [](Status s, device::V3_3::HalStreamConfiguration) {
4145                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
4146                                 (Status::INTERNAL_ERROR == s));
4147                     });
4148         } else {
4149             ret = session->configureStreams(config3_2,
4150                     [](Status s, HalStreamConfiguration) {
4151                         ASSERT_TRUE((Status::ILLEGAL_ARGUMENT == s) ||
4152                                 (Status::INTERNAL_ERROR == s));
4153                     });
4154         }
4155         ASSERT_TRUE(ret.isOk());
4156 
4157         stream = {streamId++,
4158                   StreamType::OUTPUT,
4159                   static_cast<uint32_t>(UINT32_MAX),
4160                   static_cast<uint32_t>(UINT32_MAX),
4161                   static_cast<PixelFormat>(hfrStream.format),
4162                   GRALLOC1_CONSUMER_USAGE_VIDEO_ENCODER,
4163                   0,
4164                   StreamRotation::ROTATION_0};
4165         streams[0] = stream;
4166         createStreamConfiguration(streams, StreamConfigurationMode::CONSTRAINED_HIGH_SPEED_MODE,
4167                                   &config3_2, &config3_4, &config3_5);
4168         if (session3_5 != nullptr) {
4169             config3_5.streamConfigCounter = streamConfigCounter++;
4170             ret = session3_5->configureStreams_3_5(config3_5,
4171                     [](Status s, device::V3_4::HalStreamConfiguration) {
4172                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4173                     });
4174         } else if (session3_4 != nullptr) {
4175             ret = session3_4->configureStreams_3_4(config3_4,
4176                     [](Status s, device::V3_4::HalStreamConfiguration) {
4177                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4178                     });
4179         } else if (session3_3 != nullptr) {
4180             ret = session3_3->configureStreams_3_3(config3_2,
4181                     [](Status s, device::V3_3::HalStreamConfiguration) {
4182                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4183                     });
4184         } else {
4185             ret = session->configureStreams(config3_2,
4186                     [](Status s, HalStreamConfiguration) {
4187                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4188                     });
4189         }
4190         ASSERT_TRUE(ret.isOk());
4191 
4192         stream = {streamId++,
4193                   StreamType::OUTPUT,
4194                   static_cast<uint32_t>(hfrStream.width),
4195                   static_cast<uint32_t>(hfrStream.height),
4196                   static_cast<PixelFormat>(UINT32_MAX),
4197                   GRALLOC1_CONSUMER_USAGE_VIDEO_ENCODER,
4198                   0,
4199                   StreamRotation::ROTATION_0};
4200         streams[0] = stream;
4201         createStreamConfiguration(streams, StreamConfigurationMode::CONSTRAINED_HIGH_SPEED_MODE,
4202                                   &config3_2, &config3_4, &config3_5);
4203         if (session3_5 != nullptr) {
4204             config3_5.streamConfigCounter = streamConfigCounter++;
4205             ret = session3_5->configureStreams_3_5(config3_5,
4206                     [](Status s, device::V3_4::HalStreamConfiguration) {
4207                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4208                     });
4209         } else if (session3_4 != nullptr) {
4210             ret = session3_4->configureStreams_3_4(config3_4,
4211                     [](Status s, device::V3_4::HalStreamConfiguration) {
4212                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4213                     });
4214         } else if (session3_3 != nullptr) {
4215             ret = session3_3->configureStreams_3_3(config3_2,
4216                     [](Status s, device::V3_3::HalStreamConfiguration) {
4217                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4218                     });
4219         } else {
4220             ret = session->configureStreams(config3_2,
4221                     [](Status s, HalStreamConfiguration) {
4222                         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, s);
4223                     });
4224         }
4225         ASSERT_TRUE(ret.isOk());
4226 
4227         free_camera_metadata(staticMeta);
4228         ret = session->close();
4229         ASSERT_TRUE(ret.isOk());
4230     }
4231 }
4232 
4233 // Verify that all supported video + snapshot stream combinations can
4234 // be configured successfully.
TEST_P(CameraHidlTest,configureStreamsVideoStillOutputs)4235 TEST_P(CameraHidlTest, configureStreamsVideoStillOutputs) {
4236     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
4237     std::vector<AvailableStream> outputBlobStreams;
4238     std::vector<AvailableStream> outputVideoStreams;
4239     AvailableStream videoThreshold = {kMaxVideoWidth, kMaxVideoHeight,
4240                                       static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
4241     AvailableStream blobThreshold = {kMaxVideoWidth, kMaxVideoHeight,
4242                                      static_cast<int32_t>(PixelFormat::BLOB)};
4243 
4244     for (const auto& name : cameraDeviceNames) {
4245         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
4246         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
4247             continue;
4248         } else if (deviceVersion <= 0) {
4249             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
4250             ADD_FAILURE();
4251             return;
4252         }
4253 
4254         camera_metadata_t* staticMeta;
4255         Return<void> ret;
4256         sp<ICameraDeviceSession> session;
4257         sp<device::V3_3::ICameraDeviceSession> session3_3;
4258         sp<device::V3_4::ICameraDeviceSession> session3_4;
4259         sp<device::V3_5::ICameraDeviceSession> session3_5;
4260         sp<device::V3_6::ICameraDeviceSession> session3_6;
4261         sp<device::V3_2::ICameraDevice> cameraDevice;
4262         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
4263         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMeta /*out*/,
4264                 &cameraDevice /*out*/);
4265         castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
4266         castDevice(cameraDevice, deviceVersion, &cameraDevice3_5);
4267 
4268         // Check if camera support depth only
4269         if (isDepthOnly(staticMeta)) {
4270             free_camera_metadata(staticMeta);
4271             ret = session->close();
4272             ASSERT_TRUE(ret.isOk());
4273             continue;
4274         }
4275 
4276         outputBlobStreams.clear();
4277         ASSERT_EQ(Status::OK,
4278                   getAvailableOutputStreams(staticMeta, outputBlobStreams,
4279                           &blobThreshold));
4280         ASSERT_NE(0u, outputBlobStreams.size());
4281 
4282         outputVideoStreams.clear();
4283         ASSERT_EQ(Status::OK,
4284                   getAvailableOutputStreams(staticMeta, outputVideoStreams,
4285                           &videoThreshold));
4286         ASSERT_NE(0u, outputVideoStreams.size());
4287 
4288         uint32_t jpegBufferSize = 0;
4289         ASSERT_EQ(Status::OK, getJpegBufferSize(staticMeta, &jpegBufferSize));
4290         ASSERT_NE(0u, jpegBufferSize);
4291 
4292         int32_t streamId = 0;
4293         uint32_t streamConfigCounter = 0;
4294         for (auto& blobIter : outputBlobStreams) {
4295             for (auto& videoIter : outputVideoStreams) {
4296                 V3_2::Stream videoStream = {streamId++,
4297                                       StreamType::OUTPUT,
4298                                       static_cast<uint32_t>(videoIter.width),
4299                                       static_cast<uint32_t>(videoIter.height),
4300                                       static_cast<PixelFormat>(videoIter.format),
4301                                       GRALLOC1_CONSUMER_USAGE_VIDEO_ENCODER,
4302                                       0,
4303                                       StreamRotation::ROTATION_0};
4304                 V3_2::Stream blobStream = {streamId++,
4305                                      StreamType::OUTPUT,
4306                                      static_cast<uint32_t>(blobIter.width),
4307                                      static_cast<uint32_t>(blobIter.height),
4308                                      static_cast<PixelFormat>(blobIter.format),
4309                                      GRALLOC1_CONSUMER_USAGE_CPU_READ,
4310                                      static_cast<V3_2::DataspaceFlags>(Dataspace::V0_JFIF),
4311                                      StreamRotation::ROTATION_0};
4312                 ::android::hardware::hidl_vec<V3_2::Stream> streams = {videoStream, blobStream};
4313                 ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
4314                 ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
4315                 ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
4316                 createStreamConfiguration(streams, StreamConfigurationMode::NORMAL_MODE,
4317                                           &config3_2, &config3_4, &config3_5, jpegBufferSize);
4318                 if (session3_5 != nullptr) {
4319                     verifyStreamCombination(cameraDevice3_5, config3_4,
4320                             /*expectedStatus*/ true, /*expectStreamCombQuery*/ false);
4321                     config3_5.streamConfigCounter = streamConfigCounter++;
4322                     ret = session3_5->configureStreams_3_5(config3_5,
4323                             [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
4324                                 ASSERT_EQ(Status::OK, s);
4325                                 ASSERT_EQ(2u, halConfig.streams.size());
4326                             });
4327                 } else if (session3_4 != nullptr) {
4328                     ret = session3_4->configureStreams_3_4(config3_4,
4329                             [](Status s, device::V3_4::HalStreamConfiguration halConfig) {
4330                                 ASSERT_EQ(Status::OK, s);
4331                                 ASSERT_EQ(2u, halConfig.streams.size());
4332                             });
4333                 } else if (session3_3 != nullptr) {
4334                     ret = session3_3->configureStreams_3_3(config3_2,
4335                             [](Status s, device::V3_3::HalStreamConfiguration halConfig) {
4336                                 ASSERT_EQ(Status::OK, s);
4337                                 ASSERT_EQ(2u, halConfig.streams.size());
4338                             });
4339                 } else {
4340                     ret = session->configureStreams(config3_2,
4341                             [](Status s, HalStreamConfiguration halConfig) {
4342                                 ASSERT_EQ(Status::OK, s);
4343                                 ASSERT_EQ(2u, halConfig.streams.size());
4344                             });
4345                 }
4346                 ASSERT_TRUE(ret.isOk());
4347             }
4348         }
4349 
4350         free_camera_metadata(staticMeta);
4351         ret = session->close();
4352         ASSERT_TRUE(ret.isOk());
4353     }
4354 }
4355 
4356 // Generate and verify a camera capture request
TEST_P(CameraHidlTest,processCaptureRequestPreview)4357 TEST_P(CameraHidlTest, processCaptureRequestPreview) {
4358     processCaptureRequestInternal(GRALLOC1_CONSUMER_USAGE_HWCOMPOSER, RequestTemplate::PREVIEW,
4359                                   false /*secureOnlyCameras*/);
4360 }
4361 
4362 // Generate and verify a secure camera capture request
TEST_P(CameraHidlTest,processSecureCaptureRequest)4363 TEST_P(CameraHidlTest, processSecureCaptureRequest) {
4364     processCaptureRequestInternal(GRALLOC1_PRODUCER_USAGE_PROTECTED, RequestTemplate::STILL_CAPTURE,
4365                                   true /*secureOnlyCameras*/);
4366 }
4367 
processCaptureRequestInternal(uint64_t bufferUsage,RequestTemplate reqTemplate,bool useSecureOnlyCameras)4368 void CameraHidlTest::processCaptureRequestInternal(uint64_t bufferUsage,
4369                                                    RequestTemplate reqTemplate,
4370                                                    bool useSecureOnlyCameras) {
4371     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider, useSecureOnlyCameras);
4372     AvailableStream streamThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
4373                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
4374     uint64_t bufferId = 1;
4375     uint32_t frameNumber = 1;
4376     ::android::hardware::hidl_vec<uint8_t> settings;
4377 
4378     for (const auto& name : cameraDeviceNames) {
4379         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
4380         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
4381             continue;
4382         } else if (deviceVersion <= 0) {
4383             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
4384             ADD_FAILURE();
4385             return;
4386         }
4387 
4388         V3_2::Stream testStream;
4389         HalStreamConfiguration halStreamConfig;
4390         sp<ICameraDeviceSession> session;
4391         sp<DeviceCb> cb;
4392         bool supportsPartialResults = false;
4393         bool useHalBufManager = false;
4394         uint32_t partialResultCount = 0;
4395         configureSingleStream(name, deviceVersion, mProvider, &streamThreshold, bufferUsage,
4396                               reqTemplate, &session /*out*/, &testStream /*out*/,
4397                               &halStreamConfig /*out*/, &supportsPartialResults /*out*/,
4398                               &partialResultCount /*out*/, &useHalBufManager /*out*/, &cb /*out*/);
4399 
4400         std::shared_ptr<ResultMetadataQueue> resultQueue;
4401         auto resultQueueRet =
4402             session->getCaptureResultMetadataQueue(
4403                 [&resultQueue](const auto& descriptor) {
4404                     resultQueue = std::make_shared<ResultMetadataQueue>(
4405                             descriptor);
4406                     if (!resultQueue->isValid() ||
4407                             resultQueue->availableToWrite() <= 0) {
4408                         ALOGE("%s: HAL returns empty result metadata fmq,"
4409                                 " not use it", __func__);
4410                         resultQueue = nullptr;
4411                         // Don't use the queue onwards.
4412                     }
4413                 });
4414         ASSERT_TRUE(resultQueueRet.isOk());
4415 
4416         InFlightRequest inflightReq = {1, false, supportsPartialResults,
4417                                        partialResultCount, resultQueue};
4418 
4419         Return<void> ret;
4420         ret = session->constructDefaultRequestSettings(reqTemplate,
4421                                                        [&](auto status, const auto& req) {
4422                                                            ASSERT_EQ(Status::OK, status);
4423                                                            settings = req;
4424                                                        });
4425         ASSERT_TRUE(ret.isOk());
4426 
4427         hidl_handle buffer_handle;
4428         StreamBuffer outputBuffer;
4429         if (useHalBufManager) {
4430             outputBuffer = {halStreamConfig.streams[0].id,
4431                             /*bufferId*/ 0,
4432                             buffer_handle,
4433                             BufferStatus::OK,
4434                             nullptr,
4435                             nullptr};
4436         } else {
4437             allocateGraphicBuffer(testStream.width, testStream.height,
4438                                   /* We don't look at halStreamConfig.streams[0].consumerUsage
4439                                    * since that is 0 for output streams
4440                                    */
4441                                   android_convertGralloc1To0Usage(
4442                                           halStreamConfig.streams[0].producerUsage, bufferUsage),
4443                                   halStreamConfig.streams[0].overrideFormat, &buffer_handle);
4444             outputBuffer = {halStreamConfig.streams[0].id,
4445                             bufferId,
4446                             buffer_handle,
4447                             BufferStatus::OK,
4448                             nullptr,
4449                             nullptr};
4450         }
4451         ::android::hardware::hidl_vec<StreamBuffer> outputBuffers = {outputBuffer};
4452         StreamBuffer emptyInputBuffer = {-1, 0, nullptr, BufferStatus::ERROR, nullptr,
4453                                          nullptr};
4454         CaptureRequest request = {frameNumber, 0 /* fmqSettingsSize */, settings,
4455                                   emptyInputBuffer, outputBuffers};
4456 
4457         {
4458             std::unique_lock<std::mutex> l(mLock);
4459             mInflightMap.clear();
4460             mInflightMap.add(frameNumber, &inflightReq);
4461         }
4462 
4463         Status status = Status::INTERNAL_ERROR;
4464         uint32_t numRequestProcessed = 0;
4465         hidl_vec<BufferCache> cachesToRemove;
4466         Return<void> returnStatus = session->processCaptureRequest(
4467             {request}, cachesToRemove, [&status, &numRequestProcessed](auto s,
4468                     uint32_t n) {
4469                 status = s;
4470                 numRequestProcessed = n;
4471             });
4472         ASSERT_TRUE(returnStatus.isOk());
4473         ASSERT_EQ(Status::OK, status);
4474         ASSERT_EQ(numRequestProcessed, 1u);
4475 
4476         {
4477             std::unique_lock<std::mutex> l(mLock);
4478             while (!inflightReq.errorCodeValid &&
4479                    ((0 < inflightReq.numBuffersLeft) ||
4480                            (!inflightReq.haveResultMetadata))) {
4481                 auto timeout = std::chrono::system_clock::now() +
4482                                std::chrono::seconds(kStreamBufferTimeoutSec);
4483                 ASSERT_NE(std::cv_status::timeout,
4484                         mResultCondition.wait_until(l, timeout));
4485             }
4486 
4487             ASSERT_FALSE(inflightReq.errorCodeValid);
4488             ASSERT_NE(inflightReq.resultOutputBuffers.size(), 0u);
4489             ASSERT_EQ(testStream.id, inflightReq.resultOutputBuffers[0].streamId);
4490 
4491             request.frameNumber++;
4492             // Empty settings should be supported after the first call
4493             // for repeating requests.
4494             request.settings.setToExternal(nullptr, 0, true);
4495             // The buffer has been registered to HAL by bufferId, so per
4496             // API contract we should send a null handle for this buffer
4497             request.outputBuffers[0].buffer = nullptr;
4498             mInflightMap.clear();
4499             inflightReq = {1, false, supportsPartialResults, partialResultCount,
4500                            resultQueue};
4501             mInflightMap.add(request.frameNumber, &inflightReq);
4502         }
4503 
4504         returnStatus = session->processCaptureRequest(
4505             {request}, cachesToRemove, [&status, &numRequestProcessed](auto s,
4506                     uint32_t n) {
4507                 status = s;
4508                 numRequestProcessed = n;
4509             });
4510         ASSERT_TRUE(returnStatus.isOk());
4511         ASSERT_EQ(Status::OK, status);
4512         ASSERT_EQ(numRequestProcessed, 1u);
4513 
4514         {
4515             std::unique_lock<std::mutex> l(mLock);
4516             while (!inflightReq.errorCodeValid &&
4517                    ((0 < inflightReq.numBuffersLeft) ||
4518                            (!inflightReq.haveResultMetadata))) {
4519                 auto timeout = std::chrono::system_clock::now() +
4520                                std::chrono::seconds(kStreamBufferTimeoutSec);
4521                 ASSERT_NE(std::cv_status::timeout,
4522                         mResultCondition.wait_until(l, timeout));
4523             }
4524 
4525             ASSERT_FALSE(inflightReq.errorCodeValid);
4526             ASSERT_NE(inflightReq.resultOutputBuffers.size(), 0u);
4527             ASSERT_EQ(testStream.id, inflightReq.resultOutputBuffers[0].streamId);
4528         }
4529 
4530         if (useHalBufManager) {
4531             verifyBuffersReturned(session, deviceVersion, testStream.id, cb);
4532         }
4533 
4534         ret = session->close();
4535         ASSERT_TRUE(ret.isOk());
4536     }
4537 }
4538 
4539 // Generate and verify a multi-camera capture request
TEST_P(CameraHidlTest,processMultiCaptureRequestPreview)4540 TEST_P(CameraHidlTest, processMultiCaptureRequestPreview) {
4541     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
4542     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
4543                                         static_cast<int32_t>(PixelFormat::YCBCR_420_888)};
4544     uint64_t bufferId = 1;
4545     uint32_t frameNumber = 1;
4546     ::android::hardware::hidl_vec<uint8_t> settings;
4547     ::android::hardware::hidl_vec<uint8_t> emptySettings;
4548     hidl_string invalidPhysicalId = "-1";
4549 
4550     for (const auto& name : cameraDeviceNames) {
4551         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
4552         if (deviceVersion < CAMERA_DEVICE_API_VERSION_3_5) {
4553             continue;
4554         }
4555         std::string version, deviceId;
4556         ASSERT_TRUE(::matchDeviceName(name, mProviderType, &version, &deviceId));
4557         camera_metadata_t* staticMeta;
4558         Return<void> ret;
4559         sp<ICameraDeviceSession> session;
4560         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMeta /*out*/);
4561 
4562         Status rc = isLogicalMultiCamera(staticMeta);
4563         if (Status::METHOD_NOT_SUPPORTED == rc) {
4564             free_camera_metadata(staticMeta);
4565             ret = session->close();
4566             ASSERT_TRUE(ret.isOk());
4567             continue;
4568         }
4569         std::unordered_set<std::string> physicalIds;
4570         rc = getPhysicalCameraIds(staticMeta, &physicalIds);
4571         ASSERT_TRUE(Status::OK == rc);
4572         ASSERT_TRUE(physicalIds.size() > 1);
4573 
4574         std::unordered_set<int32_t> physicalRequestKeyIDs;
4575         rc = getSupportedKeys(staticMeta,
4576                 ANDROID_REQUEST_AVAILABLE_PHYSICAL_CAMERA_REQUEST_KEYS, &physicalRequestKeyIDs);
4577         ASSERT_TRUE(Status::OK == rc);
4578         if (physicalRequestKeyIDs.empty()) {
4579             free_camera_metadata(staticMeta);
4580             ret = session->close();
4581             ASSERT_TRUE(ret.isOk());
4582             // The logical camera doesn't support any individual physical requests.
4583             continue;
4584         }
4585 
4586         android::hardware::camera::common::V1_0::helper::CameraMetadata defaultPreviewSettings;
4587         android::hardware::camera::common::V1_0::helper::CameraMetadata filteredSettings;
4588         constructFilteredSettings(session, physicalRequestKeyIDs, RequestTemplate::PREVIEW,
4589                 &defaultPreviewSettings, &filteredSettings);
4590         if (filteredSettings.isEmpty()) {
4591             // No physical device settings in default request.
4592             free_camera_metadata(staticMeta);
4593             ret = session->close();
4594             ASSERT_TRUE(ret.isOk());
4595             continue;
4596         }
4597 
4598         const camera_metadata_t *settingsBuffer = defaultPreviewSettings.getAndLock();
4599         settings.setToExternal(
4600                 reinterpret_cast<uint8_t *> (const_cast<camera_metadata_t *> (settingsBuffer)),
4601                 get_camera_metadata_size(settingsBuffer));
4602 
4603         free_camera_metadata(staticMeta);
4604         ret = session->close();
4605         ASSERT_TRUE(ret.isOk());
4606 
4607         // Leave only 2 physical devices in the id set.
4608         auto it = physicalIds.begin();
4609         std::string physicalDeviceId = *it; it++;
4610         physicalIds.erase(++it, physicalIds.end());
4611         ASSERT_EQ(physicalIds.size(), 2u);
4612 
4613         V3_4::HalStreamConfiguration halStreamConfig;
4614         bool supportsPartialResults = false;
4615         bool useHalBufManager = false;
4616         uint32_t partialResultCount = 0;
4617         V3_2::Stream previewStream;
4618         sp<device::V3_4::ICameraDeviceSession> session3_4;
4619         sp<device::V3_5::ICameraDeviceSession> session3_5;
4620         sp<DeviceCb> cb;
4621         configurePreviewStreams3_4(name, deviceVersion, mProvider, &previewThreshold, physicalIds,
4622                 &session3_4, &session3_5, &previewStream, &halStreamConfig /*out*/,
4623                 &supportsPartialResults /*out*/, &partialResultCount /*out*/,
4624                 &useHalBufManager /*out*/, &cb /*out*/, 0 /*streamConfigCounter*/,
4625                 true /*allowUnsupport*/);
4626         if (session3_5 == nullptr) {
4627             ret = session3_4->close();
4628             ASSERT_TRUE(ret.isOk());
4629             continue;
4630         }
4631 
4632         std::shared_ptr<ResultMetadataQueue> resultQueue;
4633         auto resultQueueRet =
4634             session3_4->getCaptureResultMetadataQueue(
4635                 [&resultQueue](const auto& descriptor) {
4636                     resultQueue = std::make_shared<ResultMetadataQueue>(
4637                             descriptor);
4638                     if (!resultQueue->isValid() ||
4639                             resultQueue->availableToWrite() <= 0) {
4640                         ALOGE("%s: HAL returns empty result metadata fmq,"
4641                                 " not use it", __func__);
4642                         resultQueue = nullptr;
4643                         // Don't use the queue onwards.
4644                     }
4645                 });
4646         ASSERT_TRUE(resultQueueRet.isOk());
4647 
4648         InFlightRequest inflightReq = {static_cast<ssize_t> (halStreamConfig.streams.size()), false,
4649             supportsPartialResults, partialResultCount, physicalIds, resultQueue};
4650 
4651         std::vector<hidl_handle> graphicBuffers;
4652         graphicBuffers.reserve(halStreamConfig.streams.size());
4653         ::android::hardware::hidl_vec<StreamBuffer> outputBuffers;
4654         outputBuffers.resize(halStreamConfig.streams.size());
4655         size_t k = 0;
4656         for (const auto& halStream : halStreamConfig.streams) {
4657             hidl_handle buffer_handle;
4658             if (useHalBufManager) {
4659                 outputBuffers[k] = {halStream.v3_3.v3_2.id, /*bufferId*/0, buffer_handle,
4660                     BufferStatus::OK, nullptr, nullptr};
4661             } else {
4662                 allocateGraphicBuffer(previewStream.width, previewStream.height,
4663                         android_convertGralloc1To0Usage(halStream.v3_3.v3_2.producerUsage,
4664                             halStream.v3_3.v3_2.consumerUsage),
4665                         halStream.v3_3.v3_2.overrideFormat, &buffer_handle);
4666                 graphicBuffers.push_back(buffer_handle);
4667                 outputBuffers[k] = {halStream.v3_3.v3_2.id, bufferId, buffer_handle,
4668                     BufferStatus::OK, nullptr, nullptr};
4669                 bufferId++;
4670             }
4671             k++;
4672         }
4673         hidl_vec<V3_4::PhysicalCameraSetting> camSettings(1);
4674         const camera_metadata_t *filteredSettingsBuffer = filteredSettings.getAndLock();
4675         camSettings[0].settings.setToExternal(
4676                 reinterpret_cast<uint8_t *> (const_cast<camera_metadata_t *> (
4677                         filteredSettingsBuffer)),
4678                 get_camera_metadata_size(filteredSettingsBuffer));
4679         camSettings[0].fmqSettingsSize = 0;
4680         camSettings[0].physicalCameraId = physicalDeviceId;
4681 
4682         StreamBuffer emptyInputBuffer = {-1, 0, nullptr, BufferStatus::ERROR, nullptr, nullptr};
4683         V3_4::CaptureRequest request = {{frameNumber, 0 /* fmqSettingsSize */, settings,
4684                                   emptyInputBuffer, outputBuffers}, camSettings};
4685 
4686         {
4687             std::unique_lock<std::mutex> l(mLock);
4688             mInflightMap.clear();
4689             mInflightMap.add(frameNumber, &inflightReq);
4690         }
4691 
4692         Status stat = Status::INTERNAL_ERROR;
4693         uint32_t numRequestProcessed = 0;
4694         hidl_vec<BufferCache> cachesToRemove;
4695         Return<void> returnStatus = session3_4->processCaptureRequest_3_4(
4696             {request}, cachesToRemove, [&stat, &numRequestProcessed](auto s, uint32_t n) {
4697                 stat = s;
4698                 numRequestProcessed = n;
4699             });
4700         ASSERT_TRUE(returnStatus.isOk());
4701         ASSERT_EQ(Status::OK, stat);
4702         ASSERT_EQ(numRequestProcessed, 1u);
4703 
4704         {
4705             std::unique_lock<std::mutex> l(mLock);
4706             while (!inflightReq.errorCodeValid &&
4707                     ((0 < inflightReq.numBuffersLeft) ||
4708                      (!inflightReq.haveResultMetadata))) {
4709                 auto timeout = std::chrono::system_clock::now() +
4710                     std::chrono::seconds(kStreamBufferTimeoutSec);
4711                 ASSERT_NE(std::cv_status::timeout,
4712                         mResultCondition.wait_until(l, timeout));
4713             }
4714 
4715             ASSERT_FALSE(inflightReq.errorCodeValid);
4716             ASSERT_NE(inflightReq.resultOutputBuffers.size(), 0u);
4717 
4718             request.v3_2.frameNumber++;
4719             // Empty settings should be supported after the first call
4720             // for repeating requests.
4721             request.v3_2.settings.setToExternal(nullptr, 0, true);
4722             request.physicalCameraSettings[0].settings.setToExternal(nullptr, 0, true);
4723             // The buffer has been registered to HAL by bufferId, so per
4724             // API contract we should send a null handle for this buffer
4725             request.v3_2.outputBuffers[0].buffer = nullptr;
4726             mInflightMap.clear();
4727             inflightReq = {static_cast<ssize_t> (physicalIds.size()), false,
4728                 supportsPartialResults, partialResultCount, physicalIds, resultQueue};
4729             mInflightMap.add(request.v3_2.frameNumber, &inflightReq);
4730         }
4731 
4732         returnStatus = session3_4->processCaptureRequest_3_4(
4733             {request}, cachesToRemove, [&stat, &numRequestProcessed](auto s, uint32_t n) {
4734                 stat = s;
4735                 numRequestProcessed = n;
4736             });
4737         ASSERT_TRUE(returnStatus.isOk());
4738         ASSERT_EQ(Status::OK, stat);
4739         ASSERT_EQ(numRequestProcessed, 1u);
4740 
4741         {
4742             std::unique_lock<std::mutex> l(mLock);
4743             while (!inflightReq.errorCodeValid &&
4744                     ((0 < inflightReq.numBuffersLeft) ||
4745                      (!inflightReq.haveResultMetadata))) {
4746                 auto timeout = std::chrono::system_clock::now() +
4747                     std::chrono::seconds(kStreamBufferTimeoutSec);
4748                 ASSERT_NE(std::cv_status::timeout,
4749                         mResultCondition.wait_until(l, timeout));
4750             }
4751 
4752             ASSERT_FALSE(inflightReq.errorCodeValid);
4753             ASSERT_NE(inflightReq.resultOutputBuffers.size(), 0u);
4754         }
4755 
4756         // Invalid physical camera id should fail process requests
4757         frameNumber++;
4758         camSettings[0].physicalCameraId = invalidPhysicalId;
4759         camSettings[0].settings = settings;
4760         request = {{frameNumber, 0 /* fmqSettingsSize */, settings,
4761             emptyInputBuffer, outputBuffers}, camSettings};
4762         returnStatus = session3_4->processCaptureRequest_3_4(
4763             {request}, cachesToRemove, [&stat, &numRequestProcessed](auto s, uint32_t n) {
4764                 stat = s;
4765                 numRequestProcessed = n;
4766             });
4767         ASSERT_TRUE(returnStatus.isOk());
4768         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, stat);
4769 
4770         defaultPreviewSettings.unlock(settingsBuffer);
4771         filteredSettings.unlock(filteredSettingsBuffer);
4772 
4773         if (useHalBufManager) {
4774             hidl_vec<int32_t> streamIds(halStreamConfig.streams.size());
4775             for (size_t i = 0; i < streamIds.size(); i++) {
4776                 streamIds[i] = halStreamConfig.streams[i].v3_3.v3_2.id;
4777             }
4778             verifyBuffersReturned(session3_4, streamIds, cb);
4779         }
4780 
4781         ret = session3_4->close();
4782         ASSERT_TRUE(ret.isOk());
4783     }
4784 }
4785 
4786 // Generate and verify a burst containing alternating sensor sensitivity values
TEST_P(CameraHidlTest,processCaptureRequestBurstISO)4787 TEST_P(CameraHidlTest, processCaptureRequestBurstISO) {
4788     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
4789     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
4790                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
4791     uint64_t bufferId = 1;
4792     uint32_t frameNumber = 1;
4793     float isoTol = .03f;
4794     ::android::hardware::hidl_vec<uint8_t> settings;
4795 
4796     for (const auto& name : cameraDeviceNames) {
4797         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
4798         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
4799             continue;
4800         } else if (deviceVersion <= 0) {
4801             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
4802             ADD_FAILURE();
4803             return;
4804         }
4805         camera_metadata_t* staticMetaBuffer;
4806         Return<void> ret;
4807         sp<ICameraDeviceSession> session;
4808         openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMetaBuffer /*out*/);
4809         ::android::hardware::camera::common::V1_0::helper::CameraMetadata staticMeta(
4810                 staticMetaBuffer);
4811 
4812         camera_metadata_entry_t hwLevel = staticMeta.find(ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL);
4813         ASSERT_TRUE(0 < hwLevel.count);
4814         if (ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL_LIMITED == hwLevel.data.u8[0] ||
4815                 ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL_EXTERNAL == hwLevel.data.u8[0]) {
4816             //Limited/External devices can skip this test
4817             ret = session->close();
4818             ASSERT_TRUE(ret.isOk());
4819             continue;
4820         }
4821 
4822         camera_metadata_entry_t isoRange = staticMeta.find(ANDROID_SENSOR_INFO_SENSITIVITY_RANGE);
4823         ASSERT_EQ(isoRange.count, 2u);
4824 
4825         ret = session->close();
4826         ASSERT_TRUE(ret.isOk());
4827 
4828         bool supportsPartialResults = false;
4829         bool useHalBufManager = false;
4830         uint32_t partialResultCount = 0;
4831         V3_2::Stream previewStream;
4832         HalStreamConfiguration halStreamConfig;
4833         sp<DeviceCb> cb;
4834         configurePreviewStream(name, deviceVersion, mProvider, &previewThreshold,
4835                 &session /*out*/, &previewStream /*out*/, &halStreamConfig /*out*/,
4836                 &supportsPartialResults /*out*/, &partialResultCount /*out*/,
4837                 &useHalBufManager /*out*/, &cb /*out*/);
4838         std::shared_ptr<ResultMetadataQueue> resultQueue;
4839 
4840         auto resultQueueRet = session->getCaptureResultMetadataQueue(
4841             [&resultQueue](const auto& descriptor) {
4842                 resultQueue = std::make_shared<ResultMetadataQueue>(descriptor);
4843                 if (!resultQueue->isValid() || resultQueue->availableToWrite() <= 0) {
4844                     ALOGE("%s: HAL returns empty result metadata fmq,"
4845                             " not use it", __func__);
4846                     resultQueue = nullptr;
4847                     // Don't use the queue onwards.
4848                 }
4849             });
4850         ASSERT_TRUE(resultQueueRet.isOk());
4851         ASSERT_NE(nullptr, resultQueue);
4852 
4853         ret = session->constructDefaultRequestSettings(RequestTemplate::PREVIEW,
4854             [&](auto status, const auto& req) {
4855                 ASSERT_EQ(Status::OK, status);
4856                 settings = req; });
4857         ASSERT_TRUE(ret.isOk());
4858 
4859         ::android::hardware::camera::common::V1_0::helper::CameraMetadata requestMeta;
4860         StreamBuffer emptyInputBuffer = {-1, 0, nullptr, BufferStatus::ERROR, nullptr, nullptr};
4861         hidl_handle buffers[kBurstFrameCount];
4862         StreamBuffer outputBuffers[kBurstFrameCount];
4863         CaptureRequest requests[kBurstFrameCount];
4864         InFlightRequest inflightReqs[kBurstFrameCount];
4865         int32_t isoValues[kBurstFrameCount];
4866         hidl_vec<uint8_t> requestSettings[kBurstFrameCount];
4867         for (uint32_t i = 0; i < kBurstFrameCount; i++) {
4868             std::unique_lock<std::mutex> l(mLock);
4869 
4870             isoValues[i] = ((i % 2) == 0) ? isoRange.data.i32[0] : isoRange.data.i32[1];
4871             if (useHalBufManager) {
4872                 outputBuffers[i] = {halStreamConfig.streams[0].id, /*bufferId*/0,
4873                     nullptr, BufferStatus::OK, nullptr, nullptr};
4874             } else {
4875                 allocateGraphicBuffer(previewStream.width, previewStream.height,
4876                         android_convertGralloc1To0Usage(halStreamConfig.streams[0].producerUsage,
4877                             halStreamConfig.streams[0].consumerUsage),
4878                         halStreamConfig.streams[0].overrideFormat, &buffers[i]);
4879                 outputBuffers[i] = {halStreamConfig.streams[0].id, bufferId + i,
4880                     buffers[i], BufferStatus::OK, nullptr, nullptr};
4881             }
4882 
4883             requestMeta.append(reinterpret_cast<camera_metadata_t *> (settings.data()));
4884 
4885             // Disable all 3A routines
4886             uint8_t mode = static_cast<uint8_t>(ANDROID_CONTROL_MODE_OFF);
4887             ASSERT_EQ(::android::OK, requestMeta.update(ANDROID_CONTROL_MODE, &mode, 1));
4888             ASSERT_EQ(::android::OK, requestMeta.update(ANDROID_SENSOR_SENSITIVITY, &isoValues[i],
4889                         1));
4890             camera_metadata_t *metaBuffer = requestMeta.release();
4891             requestSettings[i].setToExternal(reinterpret_cast<uint8_t *> (metaBuffer),
4892                     get_camera_metadata_size(metaBuffer), true);
4893 
4894             requests[i] = {frameNumber + i, 0 /* fmqSettingsSize */, requestSettings[i],
4895                 emptyInputBuffer, {outputBuffers[i]}};
4896 
4897             inflightReqs[i] = {1, false, supportsPartialResults, partialResultCount, resultQueue};
4898             mInflightMap.add(frameNumber + i, &inflightReqs[i]);
4899         }
4900 
4901         Status status = Status::INTERNAL_ERROR;
4902         uint32_t numRequestProcessed = 0;
4903         hidl_vec<BufferCache> cachesToRemove;
4904         hidl_vec<CaptureRequest> burstRequest;
4905         burstRequest.setToExternal(requests, kBurstFrameCount);
4906         Return<void> returnStatus = session->processCaptureRequest(burstRequest, cachesToRemove,
4907                 [&status, &numRequestProcessed] (auto s, uint32_t n) {
4908                     status = s;
4909                     numRequestProcessed = n;
4910                 });
4911         ASSERT_TRUE(returnStatus.isOk());
4912         ASSERT_EQ(Status::OK, status);
4913         ASSERT_EQ(numRequestProcessed, kBurstFrameCount);
4914 
4915         for (size_t i = 0; i < kBurstFrameCount; i++) {
4916             std::unique_lock<std::mutex> l(mLock);
4917             while (!inflightReqs[i].errorCodeValid && ((0 < inflightReqs[i].numBuffersLeft) ||
4918                             (!inflightReqs[i].haveResultMetadata))) {
4919                 auto timeout = std::chrono::system_clock::now() +
4920                         std::chrono::seconds(kStreamBufferTimeoutSec);
4921                 ASSERT_NE(std::cv_status::timeout, mResultCondition.wait_until(l, timeout));
4922             }
4923 
4924             ASSERT_FALSE(inflightReqs[i].errorCodeValid);
4925             ASSERT_NE(inflightReqs[i].resultOutputBuffers.size(), 0u);
4926             ASSERT_EQ(previewStream.id, inflightReqs[i].resultOutputBuffers[0].streamId);
4927             ASSERT_FALSE(inflightReqs[i].collectedResult.isEmpty());
4928             ASSERT_TRUE(inflightReqs[i].collectedResult.exists(ANDROID_SENSOR_SENSITIVITY));
4929             camera_metadata_entry_t isoResult = inflightReqs[i].collectedResult.find(
4930                     ANDROID_SENSOR_SENSITIVITY);
4931             ASSERT_TRUE(std::abs(isoResult.data.i32[0] - isoValues[i]) <=
4932                         std::round(isoValues[i]*isoTol));
4933         }
4934 
4935         if (useHalBufManager) {
4936             verifyBuffersReturned(session, deviceVersion, previewStream.id, cb);
4937         }
4938         ret = session->close();
4939         ASSERT_TRUE(ret.isOk());
4940     }
4941 }
4942 
4943 // Test whether an incorrect capture request with missing settings will
4944 // be reported correctly.
TEST_P(CameraHidlTest,processCaptureRequestInvalidSinglePreview)4945 TEST_P(CameraHidlTest, processCaptureRequestInvalidSinglePreview) {
4946     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
4947     std::vector<AvailableStream> outputPreviewStreams;
4948     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
4949                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
4950     uint64_t bufferId = 1;
4951     uint32_t frameNumber = 1;
4952     ::android::hardware::hidl_vec<uint8_t> settings;
4953 
4954     for (const auto& name : cameraDeviceNames) {
4955         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
4956         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
4957             continue;
4958         } else if (deviceVersion <= 0) {
4959             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
4960             ADD_FAILURE();
4961             return;
4962         }
4963 
4964         V3_2::Stream previewStream;
4965         HalStreamConfiguration halStreamConfig;
4966         sp<ICameraDeviceSession> session;
4967         sp<DeviceCb> cb;
4968         bool supportsPartialResults = false;
4969         bool useHalBufManager = false;
4970         uint32_t partialResultCount = 0;
4971         configurePreviewStream(name, deviceVersion, mProvider, &previewThreshold, &session /*out*/,
4972                 &previewStream /*out*/, &halStreamConfig /*out*/,
4973                 &supportsPartialResults /*out*/,
4974                 &partialResultCount /*out*/, &useHalBufManager /*out*/, &cb /*out*/);
4975 
4976         hidl_handle buffer_handle;
4977 
4978         if (useHalBufManager) {
4979             bufferId = 0;
4980         } else {
4981             allocateGraphicBuffer(previewStream.width, previewStream.height,
4982                     android_convertGralloc1To0Usage(halStreamConfig.streams[0].producerUsage,
4983                         halStreamConfig.streams[0].consumerUsage),
4984                     halStreamConfig.streams[0].overrideFormat, &buffer_handle);
4985         }
4986 
4987         StreamBuffer outputBuffer = {halStreamConfig.streams[0].id,
4988                                      bufferId,
4989                                      buffer_handle,
4990                                      BufferStatus::OK,
4991                                      nullptr,
4992                                      nullptr};
4993         ::android::hardware::hidl_vec<StreamBuffer> outputBuffers = {outputBuffer};
4994         StreamBuffer emptyInputBuffer = {-1, 0, nullptr, BufferStatus::ERROR, nullptr,
4995                                          nullptr};
4996         CaptureRequest request = {frameNumber, 0 /* fmqSettingsSize */, settings,
4997                                   emptyInputBuffer, outputBuffers};
4998 
4999         // Settings were not correctly initialized, we should fail here
5000         Status status = Status::OK;
5001         uint32_t numRequestProcessed = 0;
5002         hidl_vec<BufferCache> cachesToRemove;
5003         Return<void> ret = session->processCaptureRequest(
5004             {request}, cachesToRemove, [&status, &numRequestProcessed](auto s,
5005                     uint32_t n) {
5006                 status = s;
5007                 numRequestProcessed = n;
5008             });
5009         ASSERT_TRUE(ret.isOk());
5010         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, status);
5011         ASSERT_EQ(numRequestProcessed, 0u);
5012 
5013         ret = session->close();
5014         ASSERT_TRUE(ret.isOk());
5015     }
5016 }
5017 
5018 // Verify camera offline session behavior
TEST_P(CameraHidlTest,switchToOffline)5019 TEST_P(CameraHidlTest, switchToOffline) {
5020     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
5021     AvailableStream threshold = {kMaxStillWidth, kMaxStillHeight,
5022                                         static_cast<int32_t>(PixelFormat::BLOB)};
5023     uint64_t bufferId = 1;
5024     uint32_t frameNumber = 1;
5025     ::android::hardware::hidl_vec<uint8_t> settings;
5026 
5027     for (const auto& name : cameraDeviceNames) {
5028         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
5029         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
5030             continue;
5031         } else if (deviceVersion <= 0) {
5032             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
5033             ADD_FAILURE();
5034             return;
5035         }
5036 
5037         camera_metadata_t* staticMetaBuffer;
5038         {
5039             Return<void> ret;
5040             sp<ICameraDeviceSession> session;
5041             openEmptyDeviceSession(name, mProvider, &session /*out*/, &staticMetaBuffer /*out*/);
5042             ::android::hardware::camera::common::V1_0::helper::CameraMetadata staticMeta(
5043                     staticMetaBuffer);
5044 
5045             if (isOfflineSessionSupported(staticMetaBuffer) != Status::OK) {
5046                 ret = session->close();
5047                 ASSERT_TRUE(ret.isOk());
5048                 continue;
5049             }
5050             ret = session->close();
5051             ASSERT_TRUE(ret.isOk());
5052         }
5053 
5054         bool supportsPartialResults = false;
5055         uint32_t partialResultCount = 0;
5056         V3_2::Stream stream;
5057         V3_6::HalStreamConfiguration halStreamConfig;
5058         sp<V3_6::ICameraDeviceSession> session;
5059         sp<DeviceCb> cb;
5060         uint32_t jpegBufferSize;
5061         bool useHalBufManager;
5062         configureOfflineStillStream(name, deviceVersion, mProvider, &threshold,
5063                 &session /*out*/, &stream /*out*/, &halStreamConfig /*out*/,
5064                 &supportsPartialResults /*out*/, &partialResultCount /*out*/, &cb /*out*/,
5065                 &jpegBufferSize /*out*/, &useHalBufManager /*out*/);
5066 
5067         auto ret = session->constructDefaultRequestSettings(RequestTemplate::STILL_CAPTURE,
5068             [&](auto status, const auto& req) {
5069                 ASSERT_EQ(Status::OK, status);
5070                 settings = req; });
5071         ASSERT_TRUE(ret.isOk());
5072 
5073         std::shared_ptr<ResultMetadataQueue> resultQueue;
5074         auto resultQueueRet =
5075             session->getCaptureResultMetadataQueue(
5076                 [&resultQueue](const auto& descriptor) {
5077                     resultQueue = std::make_shared<ResultMetadataQueue>(
5078                             descriptor);
5079                     if (!resultQueue->isValid() ||
5080                             resultQueue->availableToWrite() <= 0) {
5081                         ALOGE("%s: HAL returns empty result metadata fmq,"
5082                                 " not use it", __func__);
5083                         resultQueue = nullptr;
5084                         // Don't use the queue onwards.
5085                     }
5086                 });
5087         ASSERT_TRUE(resultQueueRet.isOk());
5088 
5089         ::android::hardware::camera::common::V1_0::helper::CameraMetadata requestMeta;
5090         StreamBuffer emptyInputBuffer = {-1, 0, nullptr, BufferStatus::ERROR, nullptr, nullptr};
5091         hidl_handle buffers[kBurstFrameCount];
5092         StreamBuffer outputBuffers[kBurstFrameCount];
5093         CaptureRequest requests[kBurstFrameCount];
5094         InFlightRequest inflightReqs[kBurstFrameCount];
5095         hidl_vec<uint8_t> requestSettings[kBurstFrameCount];
5096         auto halStreamConfig3_2 = halStreamConfig.streams[0].v3_4.v3_3.v3_2;
5097         for (uint32_t i = 0; i < kBurstFrameCount; i++) {
5098             std::unique_lock<std::mutex> l(mLock);
5099 
5100             if (useHalBufManager) {
5101                 outputBuffers[i] = {halStreamConfig3_2.id, /*bufferId*/ 0,
5102                         buffers[i], BufferStatus::OK, nullptr, nullptr};
5103             } else {
5104                 // jpeg buffer (w,h) = (blobLen, 1)
5105                 allocateGraphicBuffer(jpegBufferSize, /*height*/1,
5106                         android_convertGralloc1To0Usage(halStreamConfig3_2.producerUsage,
5107                             halStreamConfig3_2.consumerUsage),
5108                         halStreamConfig3_2.overrideFormat, &buffers[i]);
5109                 outputBuffers[i] = {halStreamConfig3_2.id, bufferId + i,
5110                     buffers[i], BufferStatus::OK, nullptr, nullptr};
5111             }
5112 
5113             requestMeta.clear();
5114             requestMeta.append(reinterpret_cast<camera_metadata_t *> (settings.data()));
5115 
5116             camera_metadata_t *metaBuffer = requestMeta.release();
5117             requestSettings[i].setToExternal(reinterpret_cast<uint8_t *> (metaBuffer),
5118                     get_camera_metadata_size(metaBuffer), true);
5119 
5120             requests[i] = {frameNumber + i, 0 /* fmqSettingsSize */, requestSettings[i],
5121                 emptyInputBuffer, {outputBuffers[i]}};
5122 
5123             inflightReqs[i] = {1, false, supportsPartialResults, partialResultCount,
5124                     resultQueue};
5125             mInflightMap.add(frameNumber + i, &inflightReqs[i]);
5126         }
5127 
5128         Status status = Status::INTERNAL_ERROR;
5129         uint32_t numRequestProcessed = 0;
5130         hidl_vec<BufferCache> cachesToRemove;
5131         hidl_vec<CaptureRequest> burstRequest;
5132         burstRequest.setToExternal(requests, kBurstFrameCount);
5133         Return<void> returnStatus = session->processCaptureRequest(burstRequest, cachesToRemove,
5134                 [&status, &numRequestProcessed] (auto s, uint32_t n) {
5135                     status = s;
5136                     numRequestProcessed = n;
5137                 });
5138         ASSERT_TRUE(returnStatus.isOk());
5139         ASSERT_EQ(Status::OK, status);
5140         ASSERT_EQ(numRequestProcessed, kBurstFrameCount);
5141 
5142         hidl_vec<int32_t> offlineStreamIds = {halStreamConfig3_2.id};
5143         V3_6::CameraOfflineSessionInfo offlineSessionInfo;
5144         sp<device::V3_6::ICameraOfflineSession> offlineSession;
5145         returnStatus = session->switchToOffline(offlineStreamIds,
5146                 [&status, &offlineSessionInfo, &offlineSession] (auto stat, auto info,
5147                     auto offSession) {
5148                     status = stat;
5149                     offlineSessionInfo = info;
5150                     offlineSession = offSession;
5151                 });
5152         ASSERT_TRUE(returnStatus.isOk());
5153 
5154         if (!halStreamConfig.streams[0].supportOffline) {
5155             ASSERT_EQ(status, Status::ILLEGAL_ARGUMENT);
5156             ret = session->close();
5157             ASSERT_TRUE(ret.isOk());
5158             continue;
5159         }
5160 
5161         ASSERT_EQ(status, Status::OK);
5162         // Hal might be unable to find any requests qualified for offline mode.
5163         if (offlineSession == nullptr) {
5164             ret = session->close();
5165             ASSERT_TRUE(ret.isOk());
5166             continue;
5167         }
5168 
5169         ASSERT_EQ(offlineSessionInfo.offlineStreams.size(), 1u);
5170         ASSERT_EQ(offlineSessionInfo.offlineStreams[0].id, halStreamConfig3_2.id);
5171         ASSERT_NE(offlineSessionInfo.offlineRequests.size(), 0u);
5172 
5173         // close device session to make sure offline session does not rely on it
5174         ret = session->close();
5175         ASSERT_TRUE(ret.isOk());
5176 
5177         std::shared_ptr<ResultMetadataQueue> offlineResultQueue;
5178         auto offlineResultQueueRet =
5179             offlineSession->getCaptureResultMetadataQueue(
5180                 [&offlineResultQueue](const auto& descriptor) {
5181                     offlineResultQueue = std::make_shared<ResultMetadataQueue>(
5182                             descriptor);
5183                     if (!offlineResultQueue->isValid() ||
5184                             offlineResultQueue->availableToWrite() <= 0) {
5185                         ALOGE("%s: offline session returns empty result metadata fmq,"
5186                                 " not use it", __func__);
5187                         offlineResultQueue = nullptr;
5188                         // Don't use the queue onwards.
5189                     }
5190                 });
5191         ASSERT_TRUE(offlineResultQueueRet.isOk());
5192 
5193         updateInflightResultQueue(offlineResultQueue);
5194 
5195         ret = offlineSession->setCallback(cb);
5196         ASSERT_TRUE(ret.isOk());
5197 
5198         for (size_t i = 0; i < kBurstFrameCount; i++) {
5199             std::unique_lock<std::mutex> l(mLock);
5200             while (!inflightReqs[i].errorCodeValid && ((0 < inflightReqs[i].numBuffersLeft) ||
5201                             (!inflightReqs[i].haveResultMetadata))) {
5202                 auto timeout = std::chrono::system_clock::now() +
5203                         std::chrono::seconds(kStreamBufferTimeoutSec);
5204                 ASSERT_NE(std::cv_status::timeout, mResultCondition.wait_until(l, timeout));
5205             }
5206 
5207             ASSERT_FALSE(inflightReqs[i].errorCodeValid);
5208             ASSERT_NE(inflightReqs[i].resultOutputBuffers.size(), 0u);
5209             ASSERT_EQ(stream.id, inflightReqs[i].resultOutputBuffers[0].streamId);
5210             ASSERT_FALSE(inflightReqs[i].collectedResult.isEmpty());
5211         }
5212 
5213 
5214         ret = offlineSession->close();
5215         ASSERT_TRUE(ret.isOk());
5216     }
5217 }
5218 
5219 // Check whether an invalid capture request with missing output buffers
5220 // will be reported correctly.
TEST_P(CameraHidlTest,processCaptureRequestInvalidBuffer)5221 TEST_P(CameraHidlTest, processCaptureRequestInvalidBuffer) {
5222     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
5223     std::vector<AvailableStream> outputBlobStreams;
5224     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
5225                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
5226     uint32_t frameNumber = 1;
5227     ::android::hardware::hidl_vec<uint8_t> settings;
5228 
5229     for (const auto& name : cameraDeviceNames) {
5230         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
5231         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
5232             continue;
5233         } else if (deviceVersion <= 0) {
5234             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
5235             ADD_FAILURE();
5236             return;
5237         }
5238 
5239         V3_2::Stream previewStream;
5240         HalStreamConfiguration halStreamConfig;
5241         sp<ICameraDeviceSession> session;
5242         sp<DeviceCb> cb;
5243         bool supportsPartialResults = false;
5244         bool useHalBufManager = false;
5245         uint32_t partialResultCount = 0;
5246         configurePreviewStream(name, deviceVersion, mProvider, &previewThreshold, &session /*out*/,
5247                 &previewStream /*out*/, &halStreamConfig /*out*/,
5248                 &supportsPartialResults /*out*/,
5249                 &partialResultCount /*out*/, &useHalBufManager /*out*/, &cb /*out*/);
5250 
5251         RequestTemplate reqTemplate = RequestTemplate::PREVIEW;
5252         Return<void> ret;
5253         ret = session->constructDefaultRequestSettings(reqTemplate,
5254                                                        [&](auto status, const auto& req) {
5255                                                            ASSERT_EQ(Status::OK, status);
5256                                                            settings = req;
5257                                                        });
5258         ASSERT_TRUE(ret.isOk());
5259 
5260         ::android::hardware::hidl_vec<StreamBuffer> emptyOutputBuffers;
5261         StreamBuffer emptyInputBuffer = {-1, 0, nullptr, BufferStatus::ERROR, nullptr,
5262                                          nullptr};
5263         CaptureRequest request = {frameNumber, 0 /* fmqSettingsSize */, settings,
5264                                   emptyInputBuffer, emptyOutputBuffers};
5265 
5266         // Output buffers are missing, we should fail here
5267         Status status = Status::OK;
5268         uint32_t numRequestProcessed = 0;
5269         hidl_vec<BufferCache> cachesToRemove;
5270         ret = session->processCaptureRequest(
5271             {request}, cachesToRemove, [&status, &numRequestProcessed](auto s,
5272                     uint32_t n) {
5273                 status = s;
5274                 numRequestProcessed = n;
5275             });
5276         ASSERT_TRUE(ret.isOk());
5277         ASSERT_EQ(Status::ILLEGAL_ARGUMENT, status);
5278         ASSERT_EQ(numRequestProcessed, 0u);
5279 
5280         ret = session->close();
5281         ASSERT_TRUE(ret.isOk());
5282     }
5283 }
5284 
5285 // Generate, trigger and flush a preview request
TEST_P(CameraHidlTest,flushPreviewRequest)5286 TEST_P(CameraHidlTest, flushPreviewRequest) {
5287     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
5288     std::vector<AvailableStream> outputPreviewStreams;
5289     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
5290                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
5291     uint64_t bufferId = 1;
5292     uint32_t frameNumber = 1;
5293     ::android::hardware::hidl_vec<uint8_t> settings;
5294 
5295     for (const auto& name : cameraDeviceNames) {
5296         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
5297         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
5298             continue;
5299         } else if (deviceVersion <= 0) {
5300             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
5301             ADD_FAILURE();
5302             return;
5303         }
5304 
5305         V3_2::Stream previewStream;
5306         HalStreamConfiguration halStreamConfig;
5307         sp<ICameraDeviceSession> session;
5308         sp<DeviceCb> cb;
5309         bool supportsPartialResults = false;
5310         bool useHalBufManager = false;
5311         uint32_t partialResultCount = 0;
5312         configurePreviewStream(name, deviceVersion, mProvider, &previewThreshold, &session /*out*/,
5313                 &previewStream /*out*/, &halStreamConfig /*out*/,
5314                 &supportsPartialResults /*out*/,
5315                 &partialResultCount /*out*/, &useHalBufManager /*out*/, &cb /*out*/);
5316 
5317         std::shared_ptr<ResultMetadataQueue> resultQueue;
5318         auto resultQueueRet =
5319             session->getCaptureResultMetadataQueue(
5320                 [&resultQueue](const auto& descriptor) {
5321                     resultQueue = std::make_shared<ResultMetadataQueue>(
5322                             descriptor);
5323                     if (!resultQueue->isValid() ||
5324                             resultQueue->availableToWrite() <= 0) {
5325                         ALOGE("%s: HAL returns empty result metadata fmq,"
5326                                 " not use it", __func__);
5327                         resultQueue = nullptr;
5328                         // Don't use the queue onwards.
5329                     }
5330                 });
5331         ASSERT_TRUE(resultQueueRet.isOk());
5332 
5333         InFlightRequest inflightReq = {1, false, supportsPartialResults,
5334                                        partialResultCount, resultQueue};
5335         RequestTemplate reqTemplate = RequestTemplate::PREVIEW;
5336         Return<void> ret;
5337         ret = session->constructDefaultRequestSettings(reqTemplate,
5338                                                        [&](auto status, const auto& req) {
5339                                                            ASSERT_EQ(Status::OK, status);
5340                                                            settings = req;
5341                                                        });
5342         ASSERT_TRUE(ret.isOk());
5343 
5344         hidl_handle buffer_handle;
5345         if (useHalBufManager) {
5346             bufferId = 0;
5347         } else {
5348             allocateGraphicBuffer(previewStream.width, previewStream.height,
5349                     android_convertGralloc1To0Usage(halStreamConfig.streams[0].producerUsage,
5350                         halStreamConfig.streams[0].consumerUsage),
5351                     halStreamConfig.streams[0].overrideFormat, &buffer_handle);
5352         }
5353 
5354         StreamBuffer outputBuffer = {halStreamConfig.streams[0].id,
5355                                      bufferId,
5356                                      buffer_handle,
5357                                      BufferStatus::OK,
5358                                      nullptr,
5359                                      nullptr};
5360         ::android::hardware::hidl_vec<StreamBuffer> outputBuffers = {outputBuffer};
5361         const StreamBuffer emptyInputBuffer = {-1, 0, nullptr,
5362                                                BufferStatus::ERROR, nullptr, nullptr};
5363         CaptureRequest request = {frameNumber, 0 /* fmqSettingsSize */, settings,
5364                                   emptyInputBuffer, outputBuffers};
5365 
5366         {
5367             std::unique_lock<std::mutex> l(mLock);
5368             mInflightMap.clear();
5369             mInflightMap.add(frameNumber, &inflightReq);
5370         }
5371 
5372         Status status = Status::INTERNAL_ERROR;
5373         uint32_t numRequestProcessed = 0;
5374         hidl_vec<BufferCache> cachesToRemove;
5375         ret = session->processCaptureRequest(
5376             {request}, cachesToRemove, [&status, &numRequestProcessed](auto s,
5377                     uint32_t n) {
5378                 status = s;
5379                 numRequestProcessed = n;
5380             });
5381 
5382         ASSERT_TRUE(ret.isOk());
5383         ASSERT_EQ(Status::OK, status);
5384         ASSERT_EQ(numRequestProcessed, 1u);
5385         // Flush before waiting for request to complete.
5386         Return<Status> returnStatus = session->flush();
5387         ASSERT_TRUE(returnStatus.isOk());
5388         ASSERT_EQ(Status::OK, returnStatus);
5389 
5390         {
5391             std::unique_lock<std::mutex> l(mLock);
5392             while (!inflightReq.errorCodeValid &&
5393                    ((0 < inflightReq.numBuffersLeft) ||
5394                            (!inflightReq.haveResultMetadata))) {
5395                 auto timeout = std::chrono::system_clock::now() +
5396                                std::chrono::seconds(kStreamBufferTimeoutSec);
5397                 ASSERT_NE(std::cv_status::timeout, mResultCondition.wait_until(l,
5398                         timeout));
5399             }
5400 
5401             if (!inflightReq.errorCodeValid) {
5402                 ASSERT_NE(inflightReq.resultOutputBuffers.size(), 0u);
5403                 ASSERT_EQ(previewStream.id, inflightReq.resultOutputBuffers[0].streamId);
5404             } else {
5405                 switch (inflightReq.errorCode) {
5406                     case ErrorCode::ERROR_REQUEST:
5407                     case ErrorCode::ERROR_RESULT:
5408                     case ErrorCode::ERROR_BUFFER:
5409                         // Expected
5410                         break;
5411                     case ErrorCode::ERROR_DEVICE:
5412                     default:
5413                         FAIL() << "Unexpected error:"
5414                                << static_cast<uint32_t>(inflightReq.errorCode);
5415                 }
5416             }
5417         }
5418 
5419         if (useHalBufManager) {
5420             verifyBuffersReturned(session, deviceVersion, previewStream.id, cb);
5421         }
5422 
5423         ret = session->close();
5424         ASSERT_TRUE(ret.isOk());
5425     }
5426 }
5427 
5428 // Verify that camera flushes correctly without any pending requests.
TEST_P(CameraHidlTest,flushEmpty)5429 TEST_P(CameraHidlTest, flushEmpty) {
5430     hidl_vec<hidl_string> cameraDeviceNames = getCameraDeviceNames(mProvider);
5431     std::vector<AvailableStream> outputPreviewStreams;
5432     AvailableStream previewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
5433                                         static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
5434 
5435     for (const auto& name : cameraDeviceNames) {
5436         int deviceVersion = getCameraDeviceVersion(name, mProviderType);
5437         if (deviceVersion == CAMERA_DEVICE_API_VERSION_1_0) {
5438             continue;
5439         } else if (deviceVersion <= 0) {
5440             ALOGE("%s: Unsupported device version %d", __func__, deviceVersion);
5441             ADD_FAILURE();
5442             return;
5443         }
5444 
5445         V3_2::Stream previewStream;
5446         HalStreamConfiguration halStreamConfig;
5447         sp<ICameraDeviceSession> session;
5448         sp<DeviceCb> cb;
5449         bool supportsPartialResults = false;
5450         bool useHalBufManager = false;
5451         uint32_t partialResultCount = 0;
5452         configurePreviewStream(name, deviceVersion, mProvider, &previewThreshold, &session /*out*/,
5453                 &previewStream /*out*/, &halStreamConfig /*out*/,
5454                 &supportsPartialResults /*out*/,
5455                 &partialResultCount /*out*/, &useHalBufManager /*out*/, &cb /*out*/);
5456 
5457         Return<Status> returnStatus = session->flush();
5458         ASSERT_TRUE(returnStatus.isOk());
5459         ASSERT_EQ(Status::OK, returnStatus);
5460 
5461         {
5462             std::unique_lock<std::mutex> l(mLock);
5463             auto timeout = std::chrono::system_clock::now() +
5464                            std::chrono::milliseconds(kEmptyFlushTimeoutMSec);
5465             ASSERT_EQ(std::cv_status::timeout, mResultCondition.wait_until(l, timeout));
5466         }
5467 
5468         Return<void> ret = session->close();
5469         ASSERT_TRUE(ret.isOk());
5470     }
5471 }
5472 
5473 // Test camera provider@2.5 notify method
TEST_P(CameraHidlTest,providerDeviceStateNotification)5474 TEST_P(CameraHidlTest, providerDeviceStateNotification) {
5475 
5476     notifyDeviceState(provider::V2_5::DeviceState::BACK_COVERED);
5477     notifyDeviceState(provider::V2_5::DeviceState::NORMAL);
5478 }
5479 
5480 // Retrieve all valid output stream resolutions from the camera
5481 // static characteristics.
getAvailableOutputStreams(const camera_metadata_t * staticMeta,std::vector<AvailableStream> & outputStreams,const AvailableStream * threshold)5482 Status CameraHidlTest::getAvailableOutputStreams(const camera_metadata_t *staticMeta,
5483         std::vector<AvailableStream> &outputStreams,
5484         const AvailableStream *threshold) {
5485     AvailableStream depthPreviewThreshold = {kMaxPreviewWidth, kMaxPreviewHeight,
5486                                              static_cast<int32_t>(PixelFormat::Y16)};
5487     if (nullptr == staticMeta) {
5488         return Status::ILLEGAL_ARGUMENT;
5489     }
5490 
5491     camera_metadata_ro_entry scalarEntry;
5492     camera_metadata_ro_entry depthEntry;
5493     int foundScalar = find_camera_metadata_ro_entry(staticMeta,
5494             ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS, &scalarEntry);
5495     int foundDepth = find_camera_metadata_ro_entry(staticMeta,
5496             ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS, &depthEntry);
5497     if ((0 != foundScalar || (0 != (scalarEntry.count % 4))) &&
5498         (0 != foundDepth || (0 != (depthEntry.count % 4)))) {
5499         return Status::ILLEGAL_ARGUMENT;
5500     }
5501 
5502     if(foundScalar == 0 && (0 == (scalarEntry.count % 4))) {
5503         fillOutputStreams(&scalarEntry, outputStreams, threshold,
5504                 ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT);
5505     }
5506 
5507     if(foundDepth == 0 && (0 == (depthEntry.count % 4))) {
5508         fillOutputStreams(&depthEntry, outputStreams, &depthPreviewThreshold,
5509                 ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS_OUTPUT);
5510     }
5511 
5512     return Status::OK;
5513 }
5514 
getMinSize(Size a,Size b)5515 static Size getMinSize(Size a, Size b) {
5516     if (a.width * a.height < b.width * b.height) {
5517         return a;
5518     }
5519     return b;
5520 }
5521 
5522 // TODO: Add more combinations
getMandatoryConcurrentStreams(const camera_metadata_t * staticMeta,std::vector<AvailableStream> * outputStreams)5523 Status CameraHidlTest::getMandatoryConcurrentStreams(const camera_metadata_t* staticMeta,
5524                                                      std::vector<AvailableStream>* outputStreams) {
5525     if (nullptr == staticMeta || nullptr == outputStreams) {
5526         return Status::ILLEGAL_ARGUMENT;
5527     }
5528 
5529     if (isDepthOnly(staticMeta)) {
5530         Size y16MaxSize(640, 480);
5531         Size maxAvailableY16Size;
5532         getMaxOutputSizeForFormat(staticMeta, PixelFormat::Y16, &maxAvailableY16Size);
5533         Size y16ChosenSize = getMinSize(y16MaxSize, maxAvailableY16Size);
5534         AvailableStream y16Stream = {.width = y16ChosenSize.width,
5535                                      .height = y16ChosenSize.height,
5536                                      .format = static_cast<int32_t>(PixelFormat::Y16)};
5537         outputStreams->push_back(y16Stream);
5538         return Status::OK;
5539     }
5540 
5541     Size yuvMaxSize(1280, 720);
5542     Size jpegMaxSize(1920, 1440);
5543     Size maxAvailableYuvSize;
5544     Size maxAvailableJpegSize;
5545     getMaxOutputSizeForFormat(staticMeta, PixelFormat::YCBCR_420_888, &maxAvailableYuvSize);
5546     getMaxOutputSizeForFormat(staticMeta, PixelFormat::BLOB, &maxAvailableJpegSize);
5547     Size yuvChosenSize = getMinSize(yuvMaxSize, maxAvailableYuvSize);
5548     Size jpegChosenSize = getMinSize(jpegMaxSize, maxAvailableJpegSize);
5549 
5550     AvailableStream yuvStream = {.width = yuvChosenSize.width,
5551                                  .height = yuvChosenSize.height,
5552                                  .format = static_cast<int32_t>(PixelFormat::YCBCR_420_888)};
5553 
5554     AvailableStream jpegStream = {.width = jpegChosenSize.width,
5555                                   .height = jpegChosenSize.height,
5556                                   .format = static_cast<int32_t>(PixelFormat::BLOB)};
5557     outputStreams->push_back(yuvStream);
5558     outputStreams->push_back(jpegStream);
5559 
5560     return Status::OK;
5561 }
5562 
getMaxOutputSizeForFormat(const camera_metadata_t * staticMeta,PixelFormat format,Size * size)5563 Status CameraHidlTest::getMaxOutputSizeForFormat(const camera_metadata_t* staticMeta,
5564                                                  PixelFormat format, Size* size) {
5565     std::vector<AvailableStream> outputStreams;
5566     if (size == nullptr || getAvailableOutputStreams(staticMeta, outputStreams) != Status::OK) {
5567         return Status::ILLEGAL_ARGUMENT;
5568     }
5569     Size maxSize;
5570     bool found = false;
5571     for (auto& outputStream : outputStreams) {
5572         if (static_cast<int32_t>(format) == outputStream.format &&
5573             (outputStream.width * outputStream.height > maxSize.width * maxSize.height)) {
5574             maxSize.width = outputStream.width;
5575             maxSize.height = outputStream.height;
5576             found = true;
5577         }
5578     }
5579     if (!found) {
5580         ALOGE("%s :chosen format %d not found", __FUNCTION__, static_cast<int32_t>(format));
5581         return Status::ILLEGAL_ARGUMENT;
5582     }
5583     *size = maxSize;
5584     return Status::OK;
5585 }
5586 
fillOutputStreams(camera_metadata_ro_entry_t * entry,std::vector<AvailableStream> & outputStreams,const AvailableStream * threshold,const int32_t availableConfigOutputTag)5587 void CameraHidlTest::fillOutputStreams(camera_metadata_ro_entry_t* entry,
5588         std::vector<AvailableStream>& outputStreams, const AvailableStream* threshold,
5589         const int32_t availableConfigOutputTag) {
5590     for (size_t i = 0; i < entry->count; i+=4) {
5591         if (availableConfigOutputTag == entry->data.i32[i + 3]) {
5592             if(nullptr == threshold) {
5593                 AvailableStream s = {entry->data.i32[i+1],
5594                         entry->data.i32[i+2], entry->data.i32[i]};
5595                 outputStreams.push_back(s);
5596             } else {
5597                 if ((threshold->format == entry->data.i32[i]) &&
5598                         (threshold->width >= entry->data.i32[i+1]) &&
5599                         (threshold->height >= entry->data.i32[i+2])) {
5600                     AvailableStream s = {entry->data.i32[i+1],
5601                             entry->data.i32[i+2], threshold->format};
5602                     outputStreams.push_back(s);
5603                 }
5604             }
5605         }
5606     }
5607 }
5608 
5609 // Get max jpeg buffer size in android.jpeg.maxSize
getJpegBufferSize(camera_metadata_t * staticMeta,uint32_t * outBufSize)5610 Status CameraHidlTest::getJpegBufferSize(camera_metadata_t *staticMeta, uint32_t* outBufSize) {
5611     if (nullptr == staticMeta || nullptr == outBufSize) {
5612         return Status::ILLEGAL_ARGUMENT;
5613     }
5614 
5615     camera_metadata_ro_entry entry;
5616     int rc = find_camera_metadata_ro_entry(staticMeta,
5617             ANDROID_JPEG_MAX_SIZE, &entry);
5618     if ((0 != rc) || (1 != entry.count)) {
5619         return Status::ILLEGAL_ARGUMENT;
5620     }
5621 
5622     *outBufSize = static_cast<uint32_t>(entry.data.i32[0]);
5623     return Status::OK;
5624 }
5625 
5626 // Check if the camera device has logical multi-camera capability.
isLogicalMultiCamera(const camera_metadata_t * staticMeta)5627 Status CameraHidlTest::isLogicalMultiCamera(const camera_metadata_t *staticMeta) {
5628     Status ret = Status::METHOD_NOT_SUPPORTED;
5629     if (nullptr == staticMeta) {
5630         return Status::ILLEGAL_ARGUMENT;
5631     }
5632 
5633     camera_metadata_ro_entry entry;
5634     int rc = find_camera_metadata_ro_entry(staticMeta,
5635             ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &entry);
5636     if (0 != rc) {
5637         return Status::ILLEGAL_ARGUMENT;
5638     }
5639 
5640     for (size_t i = 0; i < entry.count; i++) {
5641         if (ANDROID_REQUEST_AVAILABLE_CAPABILITIES_LOGICAL_MULTI_CAMERA == entry.data.u8[i]) {
5642             ret = Status::OK;
5643             break;
5644         }
5645     }
5646 
5647     return ret;
5648 }
5649 
5650 // Check if the camera device has logical multi-camera capability.
isOfflineSessionSupported(const camera_metadata_t * staticMeta)5651 Status CameraHidlTest::isOfflineSessionSupported(const camera_metadata_t *staticMeta) {
5652     Status ret = Status::METHOD_NOT_SUPPORTED;
5653     if (nullptr == staticMeta) {
5654         return Status::ILLEGAL_ARGUMENT;
5655     }
5656 
5657     camera_metadata_ro_entry entry;
5658     int rc = find_camera_metadata_ro_entry(staticMeta,
5659             ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &entry);
5660     if (0 != rc) {
5661         return Status::ILLEGAL_ARGUMENT;
5662     }
5663 
5664     for (size_t i = 0; i < entry.count; i++) {
5665         if (ANDROID_REQUEST_AVAILABLE_CAPABILITIES_OFFLINE_PROCESSING == entry.data.u8[i]) {
5666             ret = Status::OK;
5667             break;
5668         }
5669     }
5670 
5671     return ret;
5672 }
5673 
5674 // Generate a list of physical camera ids backing a logical multi-camera.
getPhysicalCameraIds(const camera_metadata_t * staticMeta,std::unordered_set<std::string> * physicalIds)5675 Status CameraHidlTest::getPhysicalCameraIds(const camera_metadata_t *staticMeta,
5676         std::unordered_set<std::string> *physicalIds) {
5677     if ((nullptr == staticMeta) || (nullptr == physicalIds)) {
5678         return Status::ILLEGAL_ARGUMENT;
5679     }
5680 
5681     camera_metadata_ro_entry entry;
5682     int rc = find_camera_metadata_ro_entry(staticMeta, ANDROID_LOGICAL_MULTI_CAMERA_PHYSICAL_IDS,
5683             &entry);
5684     if (0 != rc) {
5685         return Status::ILLEGAL_ARGUMENT;
5686     }
5687 
5688     const uint8_t* ids = entry.data.u8;
5689     size_t start = 0;
5690     for (size_t i = 0; i < entry.count; i++) {
5691         if (ids[i] == '\0') {
5692             if (start != i) {
5693                 std::string currentId(reinterpret_cast<const char *> (ids + start));
5694                 physicalIds->emplace(currentId);
5695             }
5696             start = i + 1;
5697         }
5698     }
5699 
5700     return Status::OK;
5701 }
5702 
5703 // Generate a set of suported camera key ids.
getSupportedKeys(camera_metadata_t * staticMeta,uint32_t tagId,std::unordered_set<int32_t> * requestIDs)5704 Status CameraHidlTest::getSupportedKeys(camera_metadata_t *staticMeta,
5705         uint32_t tagId, std::unordered_set<int32_t> *requestIDs) {
5706     if ((nullptr == staticMeta) || (nullptr == requestIDs)) {
5707         return Status::ILLEGAL_ARGUMENT;
5708     }
5709 
5710     camera_metadata_ro_entry entry;
5711     int rc = find_camera_metadata_ro_entry(staticMeta, tagId, &entry);
5712     if ((0 != rc) || (entry.count == 0)) {
5713         return Status::OK;
5714     }
5715 
5716     requestIDs->insert(entry.data.i32, entry.data.i32 + entry.count);
5717 
5718     return Status::OK;
5719 }
5720 
constructFilteredSettings(const sp<ICameraDeviceSession> & session,const std::unordered_set<int32_t> & availableKeys,RequestTemplate reqTemplate,android::hardware::camera::common::V1_0::helper::CameraMetadata * defaultSettings,android::hardware::camera::common::V1_0::helper::CameraMetadata * filteredSettings)5721 void CameraHidlTest::constructFilteredSettings(const sp<ICameraDeviceSession>& session,
5722         const std::unordered_set<int32_t>& availableKeys, RequestTemplate reqTemplate,
5723         android::hardware::camera::common::V1_0::helper::CameraMetadata* defaultSettings,
5724         android::hardware::camera::common::V1_0::helper::CameraMetadata* filteredSettings) {
5725     ASSERT_NE(defaultSettings, nullptr);
5726     ASSERT_NE(filteredSettings, nullptr);
5727 
5728     auto ret = session->constructDefaultRequestSettings(reqTemplate,
5729             [&defaultSettings] (auto status, const auto& req) mutable {
5730                 ASSERT_EQ(Status::OK, status);
5731 
5732                 const camera_metadata_t *metadata = reinterpret_cast<const camera_metadata_t*> (
5733                         req.data());
5734                 size_t expectedSize = req.size();
5735                 int result = validate_camera_metadata_structure(metadata, &expectedSize);
5736                 ASSERT_TRUE((result == 0) || (result == CAMERA_METADATA_VALIDATION_SHIFTED));
5737 
5738                 size_t entryCount = get_camera_metadata_entry_count(metadata);
5739                 ASSERT_GT(entryCount, 0u);
5740                 *defaultSettings = metadata;
5741                 });
5742     ASSERT_TRUE(ret.isOk());
5743     const android::hardware::camera::common::V1_0::helper::CameraMetadata &constSettings =
5744         *defaultSettings;
5745     for (const auto& keyIt : availableKeys) {
5746         camera_metadata_ro_entry entry = constSettings.find(keyIt);
5747         if (entry.count > 0) {
5748             filteredSettings->update(entry);
5749         }
5750     }
5751 }
5752 
5753 // Check if constrained mode is supported by using the static
5754 // camera characteristics.
isConstrainedModeAvailable(camera_metadata_t * staticMeta)5755 Status CameraHidlTest::isConstrainedModeAvailable(camera_metadata_t *staticMeta) {
5756     Status ret = Status::METHOD_NOT_SUPPORTED;
5757     if (nullptr == staticMeta) {
5758         return Status::ILLEGAL_ARGUMENT;
5759     }
5760 
5761     camera_metadata_ro_entry entry;
5762     int rc = find_camera_metadata_ro_entry(staticMeta,
5763             ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &entry);
5764     if (0 != rc) {
5765         return Status::ILLEGAL_ARGUMENT;
5766     }
5767 
5768     for (size_t i = 0; i < entry.count; i++) {
5769         if (ANDROID_REQUEST_AVAILABLE_CAPABILITIES_CONSTRAINED_HIGH_SPEED_VIDEO ==
5770                 entry.data.u8[i]) {
5771             ret = Status::OK;
5772             break;
5773         }
5774     }
5775 
5776     return ret;
5777 }
5778 
5779 // Pick the largest supported HFR mode from the static camera
5780 // characteristics.
pickConstrainedModeSize(camera_metadata_t * staticMeta,AvailableStream & hfrStream)5781 Status CameraHidlTest::pickConstrainedModeSize(camera_metadata_t *staticMeta,
5782         AvailableStream &hfrStream) {
5783     if (nullptr == staticMeta) {
5784         return Status::ILLEGAL_ARGUMENT;
5785     }
5786 
5787     camera_metadata_ro_entry entry;
5788     int rc = find_camera_metadata_ro_entry(staticMeta,
5789             ANDROID_CONTROL_AVAILABLE_HIGH_SPEED_VIDEO_CONFIGURATIONS, &entry);
5790     if (0 != rc) {
5791         return Status::METHOD_NOT_SUPPORTED;
5792     } else if (0 != (entry.count % 5)) {
5793         return Status::ILLEGAL_ARGUMENT;
5794     }
5795 
5796     hfrStream = {0, 0,
5797             static_cast<uint32_t>(PixelFormat::IMPLEMENTATION_DEFINED)};
5798     for (size_t i = 0; i < entry.count; i+=5) {
5799         int32_t w = entry.data.i32[i];
5800         int32_t h = entry.data.i32[i+1];
5801         if ((hfrStream.width * hfrStream.height) < (w *h)) {
5802             hfrStream.width = w;
5803             hfrStream.height = h;
5804         }
5805     }
5806 
5807     return Status::OK;
5808 }
5809 
5810 // Check whether ZSL is available using the static camera
5811 // characteristics.
isZSLModeAvailable(const camera_metadata_t * staticMeta)5812 Status CameraHidlTest::isZSLModeAvailable(const camera_metadata_t *staticMeta) {
5813     if (Status::OK == isZSLModeAvailable(staticMeta, PRIV_REPROCESS)) {
5814         return Status::OK;
5815     } else {
5816         return isZSLModeAvailable(staticMeta, YUV_REPROCESS);
5817     }
5818 }
5819 
isZSLModeAvailable(const camera_metadata_t * staticMeta,ReprocessType reprocType)5820 Status CameraHidlTest::isZSLModeAvailable(const camera_metadata_t *staticMeta,
5821         ReprocessType reprocType) {
5822 
5823     Status ret = Status::METHOD_NOT_SUPPORTED;
5824     if (nullptr == staticMeta) {
5825         return Status::ILLEGAL_ARGUMENT;
5826     }
5827 
5828     camera_metadata_ro_entry entry;
5829     int rc = find_camera_metadata_ro_entry(staticMeta,
5830             ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &entry);
5831     if (0 != rc) {
5832         return Status::ILLEGAL_ARGUMENT;
5833     }
5834 
5835     for (size_t i = 0; i < entry.count; i++) {
5836         if ((reprocType == PRIV_REPROCESS &&
5837                 ANDROID_REQUEST_AVAILABLE_CAPABILITIES_PRIVATE_REPROCESSING == entry.data.u8[i]) ||
5838                 (reprocType == YUV_REPROCESS &&
5839                 ANDROID_REQUEST_AVAILABLE_CAPABILITIES_YUV_REPROCESSING == entry.data.u8[i])) {
5840             ret = Status::OK;
5841             break;
5842         }
5843     }
5844 
5845     return ret;
5846 }
5847 
getSystemCameraKind(const camera_metadata_t * staticMeta,SystemCameraKind * systemCameraKind)5848 Status CameraHidlTest::getSystemCameraKind(const camera_metadata_t* staticMeta,
5849                                            SystemCameraKind* systemCameraKind) {
5850     Status ret = Status::OK;
5851     if (nullptr == staticMeta || nullptr == systemCameraKind) {
5852         return Status::ILLEGAL_ARGUMENT;
5853     }
5854 
5855     camera_metadata_ro_entry entry;
5856     int rc = find_camera_metadata_ro_entry(staticMeta, ANDROID_REQUEST_AVAILABLE_CAPABILITIES,
5857                                            &entry);
5858     if (0 != rc) {
5859         return Status::ILLEGAL_ARGUMENT;
5860     }
5861 
5862     if (entry.count == 1 &&
5863         entry.data.u8[0] == ANDROID_REQUEST_AVAILABLE_CAPABILITIES_SECURE_IMAGE_DATA) {
5864         *systemCameraKind = SystemCameraKind::HIDDEN_SECURE_CAMERA;
5865         return ret;
5866     }
5867 
5868     // Go through the capabilities and check if it has
5869     // ANDROID_REQUEST_AVAILABLE_CAPABILITIES_SYSTEM_CAMERA
5870     for (size_t i = 0; i < entry.count; ++i) {
5871         uint8_t capability = entry.data.u8[i];
5872         if (capability == ANDROID_REQUEST_AVAILABLE_CAPABILITIES_SYSTEM_CAMERA) {
5873             *systemCameraKind = SystemCameraKind::SYSTEM_ONLY_CAMERA;
5874             return ret;
5875         }
5876     }
5877     *systemCameraKind = SystemCameraKind::PUBLIC;
5878     return ret;
5879 }
5880 
5881 // Select an appropriate dataspace given a specific pixel format.
getDataspace(PixelFormat format)5882 V3_2::DataspaceFlags CameraHidlTest::getDataspace(PixelFormat format) {
5883     switch (format) {
5884         case PixelFormat::BLOB:
5885             return static_cast<V3_2::DataspaceFlags>(Dataspace::V0_JFIF);
5886         case PixelFormat::Y16:
5887             return static_cast<V3_2::DataspaceFlags>(Dataspace::DEPTH);
5888         case PixelFormat::RAW16:
5889         case PixelFormat::RAW_OPAQUE:
5890         case PixelFormat::RAW10:
5891         case PixelFormat::RAW12:
5892             return static_cast<V3_2::DataspaceFlags>(Dataspace::ARBITRARY);
5893         default:
5894             return static_cast<V3_2::DataspaceFlags>(Dataspace::UNKNOWN);
5895     }
5896 }
5897 
5898 // Check whether this is a monochrome camera using the static camera characteristics.
isMonochromeCamera(const camera_metadata_t * staticMeta)5899 Status CameraHidlTest::isMonochromeCamera(const camera_metadata_t *staticMeta) {
5900     Status ret = Status::METHOD_NOT_SUPPORTED;
5901     if (nullptr == staticMeta) {
5902         return Status::ILLEGAL_ARGUMENT;
5903     }
5904 
5905     camera_metadata_ro_entry entry;
5906     int rc = find_camera_metadata_ro_entry(staticMeta,
5907             ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &entry);
5908     if (0 != rc) {
5909         return Status::ILLEGAL_ARGUMENT;
5910     }
5911 
5912     for (size_t i = 0; i < entry.count; i++) {
5913         if (ANDROID_REQUEST_AVAILABLE_CAPABILITIES_MONOCHROME == entry.data.u8[i]) {
5914             ret = Status::OK;
5915             break;
5916         }
5917     }
5918 
5919     return ret;
5920 }
5921 
5922 // Retrieve the reprocess input-output format map from the static
5923 // camera characteristics.
getZSLInputOutputMap(camera_metadata_t * staticMeta,std::vector<AvailableZSLInputOutput> & inputOutputMap)5924 Status CameraHidlTest::getZSLInputOutputMap(camera_metadata_t *staticMeta,
5925         std::vector<AvailableZSLInputOutput> &inputOutputMap) {
5926     if (nullptr == staticMeta) {
5927         return Status::ILLEGAL_ARGUMENT;
5928     }
5929 
5930     camera_metadata_ro_entry entry;
5931     int rc = find_camera_metadata_ro_entry(staticMeta,
5932             ANDROID_SCALER_AVAILABLE_INPUT_OUTPUT_FORMATS_MAP, &entry);
5933     if ((0 != rc) || (0 >= entry.count)) {
5934         return Status::ILLEGAL_ARGUMENT;
5935     }
5936 
5937     const int32_t* contents = &entry.data.i32[0];
5938     for (size_t i = 0; i < entry.count; ) {
5939         int32_t inputFormat = contents[i++];
5940         int32_t length = contents[i++];
5941         for (int32_t j = 0; j < length; j++) {
5942             int32_t outputFormat = contents[i+j];
5943             AvailableZSLInputOutput zslEntry = {inputFormat, outputFormat};
5944             inputOutputMap.push_back(zslEntry);
5945         }
5946         i += length;
5947     }
5948 
5949     return Status::OK;
5950 }
5951 
5952 // Search for the largest stream size for a given format.
findLargestSize(const std::vector<AvailableStream> & streamSizes,int32_t format,AvailableStream & result)5953 Status CameraHidlTest::findLargestSize(
5954         const std::vector<AvailableStream> &streamSizes, int32_t format,
5955         AvailableStream &result) {
5956     result = {0, 0, 0};
5957     for (auto &iter : streamSizes) {
5958         if (format == iter.format) {
5959             if ((result.width * result.height) < (iter.width * iter.height)) {
5960                 result = iter;
5961             }
5962         }
5963     }
5964 
5965     return (result.format == format) ? Status::OK : Status::ILLEGAL_ARGUMENT;
5966 }
5967 
5968 // Check whether the camera device supports specific focus mode.
isAutoFocusModeAvailable(CameraParameters & cameraParams,const char * mode)5969 Status CameraHidlTest::isAutoFocusModeAvailable(
5970         CameraParameters &cameraParams,
5971         const char *mode) {
5972     ::android::String8 focusModes(cameraParams.get(
5973             CameraParameters::KEY_SUPPORTED_FOCUS_MODES));
5974     if (focusModes.contains(mode)) {
5975         return Status::OK;
5976     }
5977 
5978     return Status::METHOD_NOT_SUPPORTED;
5979 }
5980 
createStreamConfiguration(const::android::hardware::hidl_vec<V3_2::Stream> & streams3_2,StreamConfigurationMode configMode,::android::hardware::camera::device::V3_2::StreamConfiguration * config3_2,::android::hardware::camera::device::V3_4::StreamConfiguration * config3_4,::android::hardware::camera::device::V3_5::StreamConfiguration * config3_5,uint32_t jpegBufferSize)5981 void CameraHidlTest::createStreamConfiguration(
5982         const ::android::hardware::hidl_vec<V3_2::Stream>& streams3_2,
5983         StreamConfigurationMode configMode,
5984         ::android::hardware::camera::device::V3_2::StreamConfiguration *config3_2 /*out*/,
5985         ::android::hardware::camera::device::V3_4::StreamConfiguration *config3_4 /*out*/,
5986         ::android::hardware::camera::device::V3_5::StreamConfiguration *config3_5 /*out*/,
5987         uint32_t jpegBufferSize) {
5988     ASSERT_NE(nullptr, config3_2);
5989     ASSERT_NE(nullptr, config3_4);
5990     ASSERT_NE(nullptr, config3_5);
5991 
5992     ::android::hardware::hidl_vec<V3_4::Stream> streams3_4(streams3_2.size());
5993     size_t idx = 0;
5994     for (auto& stream3_2 : streams3_2) {
5995         V3_4::Stream stream;
5996         stream.v3_2 = stream3_2;
5997         stream.bufferSize = 0;
5998         if (stream3_2.format == PixelFormat::BLOB &&
5999                 stream3_2.dataSpace == static_cast<V3_2::DataspaceFlags>(Dataspace::V0_JFIF)) {
6000             stream.bufferSize = jpegBufferSize;
6001         }
6002         streams3_4[idx++] = stream;
6003     }
6004     // Caller is responsible to fill in non-zero config3_5->streamConfigCounter after this returns
6005     *config3_5 = {{streams3_4, configMode, {}}, 0};
6006     *config3_4 = config3_5->v3_4;
6007     *config3_2 = {streams3_2, configMode};
6008 }
6009 
6010 // Configure multiple preview streams using different physical ids.
configurePreviewStreams3_4(const std::string & name,int32_t deviceVersion,sp<ICameraProvider> provider,const AvailableStream * previewThreshold,const std::unordered_set<std::string> & physicalIds,sp<device::V3_4::ICameraDeviceSession> * session3_4,sp<device::V3_5::ICameraDeviceSession> * session3_5,V3_2::Stream * previewStream,device::V3_4::HalStreamConfiguration * halStreamConfig,bool * supportsPartialResults,uint32_t * partialResultCount,bool * useHalBufManager,sp<DeviceCb> * outCb,uint32_t streamConfigCounter,bool allowUnsupport)6011 void CameraHidlTest::configurePreviewStreams3_4(const std::string &name, int32_t deviceVersion,
6012         sp<ICameraProvider> provider,
6013         const AvailableStream *previewThreshold,
6014         const std::unordered_set<std::string>& physicalIds,
6015         sp<device::V3_4::ICameraDeviceSession> *session3_4 /*out*/,
6016         sp<device::V3_5::ICameraDeviceSession> *session3_5 /*out*/,
6017         V3_2::Stream *previewStream /*out*/,
6018         device::V3_4::HalStreamConfiguration *halStreamConfig /*out*/,
6019         bool *supportsPartialResults /*out*/,
6020         uint32_t *partialResultCount /*out*/,
6021         bool *useHalBufManager /*out*/,
6022         sp<DeviceCb> *outCb /*out*/,
6023         uint32_t streamConfigCounter,
6024         bool allowUnsupport) {
6025     ASSERT_NE(nullptr, session3_4);
6026     ASSERT_NE(nullptr, session3_5);
6027     ASSERT_NE(nullptr, halStreamConfig);
6028     ASSERT_NE(nullptr, previewStream);
6029     ASSERT_NE(nullptr, supportsPartialResults);
6030     ASSERT_NE(nullptr, partialResultCount);
6031     ASSERT_NE(nullptr, useHalBufManager);
6032     ASSERT_NE(nullptr, outCb);
6033     ASSERT_FALSE(physicalIds.empty());
6034 
6035     std::vector<AvailableStream> outputPreviewStreams;
6036     ::android::sp<ICameraDevice> device3_x;
6037     ALOGI("configureStreams: Testing camera device %s", name.c_str());
6038     Return<void> ret;
6039     ret = provider->getCameraDeviceInterface_V3_x(
6040         name,
6041         [&](auto status, const auto& device) {
6042             ALOGI("getCameraDeviceInterface_V3_x returns status:%d",
6043                   (int)status);
6044             ASSERT_EQ(Status::OK, status);
6045             ASSERT_NE(device, nullptr);
6046             device3_x = device;
6047         });
6048     ASSERT_TRUE(ret.isOk());
6049 
6050     camera_metadata_t *staticMeta;
6051     ret = device3_x->getCameraCharacteristics([&] (Status s,
6052             CameraMetadata metadata) {
6053         ASSERT_EQ(Status::OK, s);
6054         staticMeta = clone_camera_metadata(
6055                 reinterpret_cast<const camera_metadata_t*>(metadata.data()));
6056         ASSERT_NE(nullptr, staticMeta);
6057     });
6058     ASSERT_TRUE(ret.isOk());
6059 
6060     camera_metadata_ro_entry entry;
6061     auto status = find_camera_metadata_ro_entry(staticMeta,
6062             ANDROID_REQUEST_PARTIAL_RESULT_COUNT, &entry);
6063     if ((0 == status) && (entry.count > 0)) {
6064         *partialResultCount = entry.data.i32[0];
6065         *supportsPartialResults = (*partialResultCount > 1);
6066     }
6067 
6068     sp<DeviceCb> cb = new DeviceCb(this, deviceVersion, staticMeta);
6069     sp<ICameraDeviceSession> session;
6070     ret = device3_x->open(
6071         cb,
6072         [&session](auto status, const auto& newSession) {
6073             ALOGI("device::open returns status:%d", (int)status);
6074             ASSERT_EQ(Status::OK, status);
6075             ASSERT_NE(newSession, nullptr);
6076             session = newSession;
6077         });
6078     ASSERT_TRUE(ret.isOk());
6079     *outCb = cb;
6080 
6081     sp<device::V3_3::ICameraDeviceSession> session3_3;
6082     sp<device::V3_6::ICameraDeviceSession> session3_6;
6083     castSession(session, deviceVersion, &session3_3, session3_4, session3_5, &session3_6);
6084     ASSERT_NE(nullptr, (*session3_4).get());
6085 
6086     *useHalBufManager = false;
6087     status = find_camera_metadata_ro_entry(staticMeta,
6088             ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION, &entry);
6089     if ((0 == status) && (entry.count == 1)) {
6090         *useHalBufManager = (entry.data.u8[0] ==
6091             ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION_HIDL_DEVICE_3_5);
6092     }
6093 
6094     outputPreviewStreams.clear();
6095     auto rc = getAvailableOutputStreams(staticMeta,
6096             outputPreviewStreams, previewThreshold);
6097     free_camera_metadata(staticMeta);
6098     ASSERT_EQ(Status::OK, rc);
6099     ASSERT_FALSE(outputPreviewStreams.empty());
6100 
6101     ::android::hardware::hidl_vec<V3_4::Stream> streams3_4(physicalIds.size());
6102     int32_t streamId = 0;
6103     for (auto const& physicalId : physicalIds) {
6104         V3_4::Stream stream3_4 = {{streamId, StreamType::OUTPUT,
6105             static_cast<uint32_t> (outputPreviewStreams[0].width),
6106             static_cast<uint32_t> (outputPreviewStreams[0].height),
6107             static_cast<PixelFormat> (outputPreviewStreams[0].format),
6108             GRALLOC1_CONSUMER_USAGE_HWCOMPOSER, 0, StreamRotation::ROTATION_0},
6109             physicalId.c_str(), /*bufferSize*/ 0};
6110         streams3_4[streamId++] = stream3_4;
6111     }
6112 
6113     ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
6114     ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
6115     config3_4 = {streams3_4, StreamConfigurationMode::NORMAL_MODE, {}};
6116     RequestTemplate reqTemplate = RequestTemplate::PREVIEW;
6117     ret = (*session3_4)->constructDefaultRequestSettings(reqTemplate,
6118             [&config3_4](auto status, const auto& req) {
6119             ASSERT_EQ(Status::OK, status);
6120             config3_4.sessionParams = req;
6121             });
6122     ASSERT_TRUE(ret.isOk());
6123 
6124     ASSERT_TRUE(!allowUnsupport || deviceVersion == CAMERA_DEVICE_API_VERSION_3_5);
6125     if (allowUnsupport) {
6126         sp<device::V3_5::ICameraDevice> cameraDevice3_5;
6127         castDevice(device3_x, deviceVersion, &cameraDevice3_5);
6128 
6129         bool supported = false;
6130         ret = cameraDevice3_5->isStreamCombinationSupported(config3_4,
6131                 [&supported](Status s, bool combStatus) {
6132                     ASSERT_TRUE((Status::OK == s) ||
6133                             (Status::METHOD_NOT_SUPPORTED == s));
6134                     if (Status::OK == s) {
6135                         supported = combStatus;
6136                     }
6137                 });
6138         ASSERT_TRUE(ret.isOk());
6139         // If stream combination is not supported, return null session.
6140         if (!supported) {
6141             *session3_5 = nullptr;
6142             return;
6143         }
6144     }
6145 
6146     if (*session3_5 != nullptr) {
6147         config3_5.v3_4 = config3_4;
6148         config3_5.streamConfigCounter = streamConfigCounter;
6149         ret = (*session3_5)->configureStreams_3_5(config3_5,
6150                 [&] (Status s, device::V3_4::HalStreamConfiguration halConfig) {
6151                     ASSERT_EQ(Status::OK, s);
6152                     ASSERT_EQ(physicalIds.size(), halConfig.streams.size());
6153                     *halStreamConfig = halConfig;
6154                     if (*useHalBufManager) {
6155                         hidl_vec<V3_4::Stream> streams(physicalIds.size());
6156                         hidl_vec<V3_2::HalStream> halStreams(physicalIds.size());
6157                         for (size_t i = 0; i < physicalIds.size(); i++) {
6158                             streams[i] = streams3_4[i];
6159                             halStreams[i] = halConfig.streams[i].v3_3.v3_2;
6160                         }
6161                         cb->setCurrentStreamConfig(streams, halStreams);
6162                     }
6163                 });
6164     } else {
6165         ret = (*session3_4)->configureStreams_3_4(config3_4,
6166                 [&] (Status s, device::V3_4::HalStreamConfiguration halConfig) {
6167                 ASSERT_EQ(Status::OK, s);
6168                 ASSERT_EQ(physicalIds.size(), halConfig.streams.size());
6169                 *halStreamConfig = halConfig;
6170                 });
6171     }
6172     *previewStream = streams3_4[0].v3_2;
6173     ASSERT_TRUE(ret.isOk());
6174 }
6175 
6176 // Configure preview stream with possible offline session support
configureOfflineStillStream(const std::string & name,int32_t deviceVersion,sp<ICameraProvider> provider,const AvailableStream * threshold,sp<device::V3_6::ICameraDeviceSession> * session,V3_2::Stream * stream,device::V3_6::HalStreamConfiguration * halStreamConfig,bool * supportsPartialResults,uint32_t * partialResultCount,sp<DeviceCb> * outCb,uint32_t * jpegBufferSize,bool * useHalBufManager)6177 void CameraHidlTest::configureOfflineStillStream(const std::string &name,
6178         int32_t deviceVersion,
6179         sp<ICameraProvider> provider,
6180         const AvailableStream *threshold,
6181         sp<device::V3_6::ICameraDeviceSession> *session/*out*/,
6182         V3_2::Stream *stream /*out*/,
6183         device::V3_6::HalStreamConfiguration *halStreamConfig /*out*/,
6184         bool *supportsPartialResults /*out*/,
6185         uint32_t *partialResultCount /*out*/,
6186         sp<DeviceCb> *outCb /*out*/,
6187         uint32_t *jpegBufferSize /*out*/,
6188         bool *useHalBufManager /*out*/) {
6189     ASSERT_NE(nullptr, session);
6190     ASSERT_NE(nullptr, halStreamConfig);
6191     ASSERT_NE(nullptr, stream);
6192     ASSERT_NE(nullptr, supportsPartialResults);
6193     ASSERT_NE(nullptr, partialResultCount);
6194     ASSERT_NE(nullptr, outCb);
6195     ASSERT_NE(nullptr, jpegBufferSize);
6196     ASSERT_NE(nullptr, useHalBufManager);
6197 
6198     std::vector<AvailableStream> outputStreams;
6199     ::android::sp<device::V3_6::ICameraDevice> cameraDevice;
6200     ALOGI("configureStreams: Testing camera device %s", name.c_str());
6201     Return<void> ret;
6202     ret = provider->getCameraDeviceInterface_V3_x(
6203         name,
6204         [&cameraDevice](auto status, const auto& device) {
6205             ALOGI("getCameraDeviceInterface_V3_x returns status:%d",
6206                   (int)status);
6207             ASSERT_EQ(Status::OK, status);
6208             ASSERT_NE(device, nullptr);
6209             auto castResult = device::V3_6::ICameraDevice::castFrom(device);
6210             ASSERT_TRUE(castResult.isOk());
6211             cameraDevice = castResult;
6212         });
6213     ASSERT_TRUE(ret.isOk());
6214 
6215     camera_metadata_t *staticMeta;
6216     ret = cameraDevice->getCameraCharacteristics([&] (Status s,
6217             CameraMetadata metadata) {
6218         ASSERT_EQ(Status::OK, s);
6219         staticMeta = clone_camera_metadata(
6220                 reinterpret_cast<const camera_metadata_t*>(metadata.data()));
6221         ASSERT_NE(nullptr, staticMeta);
6222     });
6223     ASSERT_TRUE(ret.isOk());
6224 
6225     camera_metadata_ro_entry entry;
6226     auto status = find_camera_metadata_ro_entry(staticMeta,
6227             ANDROID_REQUEST_PARTIAL_RESULT_COUNT, &entry);
6228     if ((0 == status) && (entry.count > 0)) {
6229         *partialResultCount = entry.data.i32[0];
6230         *supportsPartialResults = (*partialResultCount > 1);
6231     }
6232 
6233     *useHalBufManager = false;
6234     status = find_camera_metadata_ro_entry(staticMeta,
6235             ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION, &entry);
6236     if ((0 == status) && (entry.count == 1)) {
6237         *useHalBufManager = (entry.data.u8[0] ==
6238             ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION_HIDL_DEVICE_3_5);
6239     }
6240 
6241     auto st = getJpegBufferSize(staticMeta, jpegBufferSize);
6242     ASSERT_EQ(st, Status::OK);
6243 
6244     sp<DeviceCb> cb = new DeviceCb(this, deviceVersion, staticMeta);
6245     ret = cameraDevice->open(cb, [&session](auto status, const auto& newSession) {
6246             ALOGI("device::open returns status:%d", (int)status);
6247             ASSERT_EQ(Status::OK, status);
6248             ASSERT_NE(newSession, nullptr);
6249             auto castResult = device::V3_6::ICameraDeviceSession::castFrom(newSession);
6250             ASSERT_TRUE(castResult.isOk());
6251             *session = castResult;
6252         });
6253     ASSERT_TRUE(ret.isOk());
6254     *outCb = cb;
6255 
6256     outputStreams.clear();
6257     auto rc = getAvailableOutputStreams(staticMeta,
6258             outputStreams, threshold);
6259     size_t idx = 0;
6260     int currLargest = outputStreams[0].width * outputStreams[0].height;
6261     for (size_t i = 0; i < outputStreams.size(); i++) {
6262         int area = outputStreams[i].width * outputStreams[i].height;
6263         if (area > currLargest) {
6264             idx = i;
6265             currLargest = area;
6266         }
6267     }
6268     free_camera_metadata(staticMeta);
6269     ASSERT_EQ(Status::OK, rc);
6270     ASSERT_FALSE(outputStreams.empty());
6271 
6272     V3_2::DataspaceFlags dataspaceFlag =
6273             getDataspace(static_cast<PixelFormat>(outputStreams[idx].format));
6274 
6275     ::android::hardware::hidl_vec<V3_4::Stream> streams3_4(/*size*/1);
6276     V3_4::Stream stream3_4 = {{ 0 /*streamId*/, StreamType::OUTPUT,
6277         static_cast<uint32_t> (outputStreams[idx].width),
6278         static_cast<uint32_t> (outputStreams[idx].height),
6279         static_cast<PixelFormat> (outputStreams[idx].format),
6280         GRALLOC1_CONSUMER_USAGE_CPU_READ, dataspaceFlag, StreamRotation::ROTATION_0},
6281         nullptr /*physicalId*/, /*bufferSize*/ *jpegBufferSize};
6282     streams3_4[0] = stream3_4;
6283 
6284     ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
6285     ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
6286     config3_4 = {streams3_4, StreamConfigurationMode::NORMAL_MODE, {}};
6287 
6288     config3_5.v3_4 = config3_4;
6289     config3_5.streamConfigCounter = 0;
6290     ret = (*session)->configureStreams_3_6(config3_5,
6291             [&] (Status s, device::V3_6::HalStreamConfiguration halConfig) {
6292                 ASSERT_EQ(Status::OK, s);
6293                 *halStreamConfig = halConfig;
6294 
6295                 if (*useHalBufManager) {
6296                     hidl_vec<V3_2::HalStream> halStreams3_2(1);
6297                     halStreams3_2[0] = halConfig.streams[0].v3_4.v3_3.v3_2;
6298                     cb->setCurrentStreamConfig(streams3_4, halStreams3_2);
6299                 }
6300             });
6301     *stream = streams3_4[0].v3_2;
6302     ASSERT_TRUE(ret.isOk());
6303 }
6304 
isDepthOnly(const camera_metadata_t * staticMeta)6305 bool CameraHidlTest::isDepthOnly(const camera_metadata_t* staticMeta) {
6306     camera_metadata_ro_entry scalarEntry;
6307     camera_metadata_ro_entry depthEntry;
6308 
6309     int rc = find_camera_metadata_ro_entry(
6310         staticMeta, ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &scalarEntry);
6311     if (rc == 0) {
6312         for (uint32_t i = 0; i < scalarEntry.count; i++) {
6313             if (scalarEntry.data.u8[i] == ANDROID_REQUEST_AVAILABLE_CAPABILITIES_BACKWARD_COMPATIBLE) {
6314                 return false;
6315             }
6316         }
6317     }
6318 
6319     for (uint32_t i = 0; i < scalarEntry.count; i++) {
6320         if (scalarEntry.data.u8[i] == ANDROID_REQUEST_AVAILABLE_CAPABILITIES_DEPTH_OUTPUT) {
6321 
6322             rc = find_camera_metadata_ro_entry(
6323                 staticMeta, ANDROID_DEPTH_AVAILABLE_DEPTH_STREAM_CONFIGURATIONS, &depthEntry);
6324             size_t i = 0;
6325             if (rc == 0 && depthEntry.data.i32[i] == static_cast<int32_t>(PixelFormat::Y16)) {
6326                 // only Depth16 format is supported now
6327                 return true;
6328             }
6329             break;
6330         }
6331     }
6332 
6333     return false;
6334 }
6335 
updateInflightResultQueue(std::shared_ptr<ResultMetadataQueue> resultQueue)6336 void CameraHidlTest::updateInflightResultQueue(std::shared_ptr<ResultMetadataQueue> resultQueue) {
6337     std::unique_lock<std::mutex> l(mLock);
6338     for (size_t i = 0; i < mInflightMap.size(); i++) {
6339         auto& req = mInflightMap.editValueAt(i);
6340         req->resultQueue = resultQueue;
6341     }
6342 }
6343 
6344 // Open a device session and configure a preview stream.
configurePreviewStream(const std::string & name,int32_t deviceVersion,sp<ICameraProvider> provider,const AvailableStream * previewThreshold,sp<ICameraDeviceSession> * session,V3_2::Stream * previewStream,HalStreamConfiguration * halStreamConfig,bool * supportsPartialResults,uint32_t * partialResultCount,bool * useHalBufManager,sp<DeviceCb> * outCb,uint32_t streamConfigCounter)6345 void CameraHidlTest::configurePreviewStream(const std::string &name, int32_t deviceVersion,
6346         sp<ICameraProvider> provider,
6347         const AvailableStream *previewThreshold,
6348         sp<ICameraDeviceSession> *session /*out*/,
6349         V3_2::Stream *previewStream /*out*/,
6350         HalStreamConfiguration *halStreamConfig /*out*/,
6351         bool *supportsPartialResults /*out*/,
6352         uint32_t *partialResultCount /*out*/,
6353         bool *useHalBufManager /*out*/,
6354         sp<DeviceCb> *outCb /*out*/,
6355         uint32_t streamConfigCounter) {
6356     configureSingleStream(name, deviceVersion, provider, previewThreshold,
6357                           GRALLOC1_CONSUMER_USAGE_HWCOMPOSER, RequestTemplate::PREVIEW, session,
6358                           previewStream, halStreamConfig, supportsPartialResults,
6359                           partialResultCount, useHalBufManager, outCb, streamConfigCounter);
6360 }
6361 // Open a device session and configure a preview stream.
configureSingleStream(const std::string & name,int32_t deviceVersion,sp<ICameraProvider> provider,const AvailableStream * previewThreshold,uint64_t bufferUsage,RequestTemplate reqTemplate,sp<ICameraDeviceSession> * session,V3_2::Stream * previewStream,HalStreamConfiguration * halStreamConfig,bool * supportsPartialResults,uint32_t * partialResultCount,bool * useHalBufManager,sp<DeviceCb> * outCb,uint32_t streamConfigCounter)6362 void CameraHidlTest::configureSingleStream(
6363         const std::string& name, int32_t deviceVersion, sp<ICameraProvider> provider,
6364         const AvailableStream* previewThreshold, uint64_t bufferUsage, RequestTemplate reqTemplate,
6365         sp<ICameraDeviceSession>* session /*out*/, V3_2::Stream* previewStream /*out*/,
6366         HalStreamConfiguration* halStreamConfig /*out*/, bool* supportsPartialResults /*out*/,
6367         uint32_t* partialResultCount /*out*/, bool* useHalBufManager /*out*/,
6368         sp<DeviceCb>* outCb /*out*/, uint32_t streamConfigCounter) {
6369     ASSERT_NE(nullptr, session);
6370     ASSERT_NE(nullptr, previewStream);
6371     ASSERT_NE(nullptr, halStreamConfig);
6372     ASSERT_NE(nullptr, supportsPartialResults);
6373     ASSERT_NE(nullptr, partialResultCount);
6374     ASSERT_NE(nullptr, useHalBufManager);
6375     ASSERT_NE(nullptr, outCb);
6376 
6377     std::vector<AvailableStream> outputPreviewStreams;
6378     ::android::sp<ICameraDevice> device3_x;
6379     ALOGI("configureStreams: Testing camera device %s", name.c_str());
6380     Return<void> ret;
6381     ret = provider->getCameraDeviceInterface_V3_x(
6382         name,
6383         [&](auto status, const auto& device) {
6384             ALOGI("getCameraDeviceInterface_V3_x returns status:%d",
6385                   (int)status);
6386             ASSERT_EQ(Status::OK, status);
6387             ASSERT_NE(device, nullptr);
6388             device3_x = device;
6389         });
6390     ASSERT_TRUE(ret.isOk());
6391 
6392     camera_metadata_t *staticMeta;
6393     ret = device3_x->getCameraCharacteristics([&] (Status s,
6394             CameraMetadata metadata) {
6395         ASSERT_EQ(Status::OK, s);
6396         staticMeta = clone_camera_metadata(
6397                 reinterpret_cast<const camera_metadata_t*>(metadata.data()));
6398         ASSERT_NE(nullptr, staticMeta);
6399     });
6400     ASSERT_TRUE(ret.isOk());
6401 
6402     camera_metadata_ro_entry entry;
6403     auto status = find_camera_metadata_ro_entry(staticMeta,
6404             ANDROID_REQUEST_PARTIAL_RESULT_COUNT, &entry);
6405     if ((0 == status) && (entry.count > 0)) {
6406         *partialResultCount = entry.data.i32[0];
6407         *supportsPartialResults = (*partialResultCount > 1);
6408     }
6409 
6410     sp<DeviceCb> cb = new DeviceCb(this, deviceVersion, staticMeta);
6411     ret = device3_x->open(
6412         cb,
6413         [&](auto status, const auto& newSession) {
6414             ALOGI("device::open returns status:%d", (int)status);
6415             ASSERT_EQ(Status::OK, status);
6416             ASSERT_NE(newSession, nullptr);
6417             *session = newSession;
6418         });
6419     ASSERT_TRUE(ret.isOk());
6420     *outCb = cb;
6421 
6422     sp<device::V3_3::ICameraDeviceSession> session3_3;
6423     sp<device::V3_4::ICameraDeviceSession> session3_4;
6424     sp<device::V3_5::ICameraDeviceSession> session3_5;
6425     sp<device::V3_6::ICameraDeviceSession> session3_6;
6426     castSession(*session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
6427 
6428     *useHalBufManager = false;
6429     status = find_camera_metadata_ro_entry(staticMeta,
6430             ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION, &entry);
6431     if ((0 == status) && (entry.count == 1)) {
6432         *useHalBufManager = (entry.data.u8[0] ==
6433             ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION_HIDL_DEVICE_3_5);
6434     }
6435 
6436     outputPreviewStreams.clear();
6437     auto rc = getAvailableOutputStreams(staticMeta,
6438             outputPreviewStreams, previewThreshold);
6439 
6440     uint32_t jpegBufferSize = 0;
6441     ASSERT_EQ(Status::OK, getJpegBufferSize(staticMeta, &jpegBufferSize));
6442     ASSERT_NE(0u, jpegBufferSize);
6443 
6444     free_camera_metadata(staticMeta);
6445     ASSERT_EQ(Status::OK, rc);
6446     ASSERT_FALSE(outputPreviewStreams.empty());
6447 
6448     V3_2::DataspaceFlags dataspaceFlag = 0;
6449     switch (static_cast<PixelFormat>(outputPreviewStreams[0].format)) {
6450         case PixelFormat::Y16:
6451             dataspaceFlag = static_cast<V3_2::DataspaceFlags>(Dataspace::DEPTH);
6452             break;
6453         default:
6454             dataspaceFlag = static_cast<V3_2::DataspaceFlags>(Dataspace::UNKNOWN);
6455     }
6456 
6457     V3_2::Stream stream3_2 = {0,
6458                               StreamType::OUTPUT,
6459                               static_cast<uint32_t>(outputPreviewStreams[0].width),
6460                               static_cast<uint32_t>(outputPreviewStreams[0].height),
6461                               static_cast<PixelFormat>(outputPreviewStreams[0].format),
6462                               bufferUsage,
6463                               dataspaceFlag,
6464                               StreamRotation::ROTATION_0};
6465     ::android::hardware::hidl_vec<V3_2::Stream> streams3_2 = {stream3_2};
6466     ::android::hardware::camera::device::V3_2::StreamConfiguration config3_2;
6467     ::android::hardware::camera::device::V3_4::StreamConfiguration config3_4;
6468     ::android::hardware::camera::device::V3_5::StreamConfiguration config3_5;
6469     createStreamConfiguration(streams3_2, StreamConfigurationMode::NORMAL_MODE,
6470                               &config3_2, &config3_4, &config3_5, jpegBufferSize);
6471     if (session3_5 != nullptr) {
6472         ret = session3_5->constructDefaultRequestSettings(reqTemplate,
6473                                                        [&config3_5](auto status, const auto& req) {
6474                                                            ASSERT_EQ(Status::OK, status);
6475                                                            config3_5.v3_4.sessionParams = req;
6476                                                        });
6477         ASSERT_TRUE(ret.isOk());
6478         config3_5.streamConfigCounter = streamConfigCounter;
6479         ret = session3_5->configureStreams_3_5(config3_5,
6480                 [&] (Status s, device::V3_4::HalStreamConfiguration halConfig) {
6481                     ASSERT_EQ(Status::OK, s);
6482                     ASSERT_EQ(1u, halConfig.streams.size());
6483                     halStreamConfig->streams.resize(1);
6484                     halStreamConfig->streams[0] = halConfig.streams[0].v3_3.v3_2;
6485                     if (*useHalBufManager) {
6486                         hidl_vec<V3_4::Stream> streams(1);
6487                         hidl_vec<V3_2::HalStream> halStreams(1);
6488                         streams[0] = config3_4.streams[0];
6489                         halStreams[0] = halConfig.streams[0].v3_3.v3_2;
6490                         cb->setCurrentStreamConfig(streams, halStreams);
6491                     }
6492                 });
6493     } else if (session3_4 != nullptr) {
6494         ret = session3_4->constructDefaultRequestSettings(reqTemplate,
6495                                                        [&config3_4](auto status, const auto& req) {
6496                                                            ASSERT_EQ(Status::OK, status);
6497                                                            config3_4.sessionParams = req;
6498                                                        });
6499         ASSERT_TRUE(ret.isOk());
6500         ret = session3_4->configureStreams_3_4(config3_4,
6501                 [&] (Status s, device::V3_4::HalStreamConfiguration halConfig) {
6502                     ASSERT_EQ(Status::OK, s);
6503                     ASSERT_EQ(1u, halConfig.streams.size());
6504                     halStreamConfig->streams.resize(halConfig.streams.size());
6505                     for (size_t i = 0; i < halConfig.streams.size(); i++) {
6506                         halStreamConfig->streams[i] = halConfig.streams[i].v3_3.v3_2;
6507                     }
6508                 });
6509     } else if (session3_3 != nullptr) {
6510         ret = session3_3->configureStreams_3_3(config3_2,
6511                 [&] (Status s, device::V3_3::HalStreamConfiguration halConfig) {
6512                     ASSERT_EQ(Status::OK, s);
6513                     ASSERT_EQ(1u, halConfig.streams.size());
6514                     halStreamConfig->streams.resize(halConfig.streams.size());
6515                     for (size_t i = 0; i < halConfig.streams.size(); i++) {
6516                         halStreamConfig->streams[i] = halConfig.streams[i].v3_2;
6517                     }
6518                 });
6519     } else {
6520         ret = (*session)->configureStreams(config3_2,
6521                 [&] (Status s, HalStreamConfiguration halConfig) {
6522                     ASSERT_EQ(Status::OK, s);
6523                     ASSERT_EQ(1u, halConfig.streams.size());
6524                     *halStreamConfig = halConfig;
6525                 });
6526     }
6527     *previewStream = stream3_2;
6528     ASSERT_TRUE(ret.isOk());
6529 }
6530 
castDevice(const sp<device::V3_2::ICameraDevice> & device,int32_t deviceVersion,sp<device::V3_5::ICameraDevice> * device3_5)6531 void CameraHidlTest::castDevice(const sp<device::V3_2::ICameraDevice> &device,
6532         int32_t deviceVersion, sp<device::V3_5::ICameraDevice> *device3_5/*out*/) {
6533     ASSERT_NE(nullptr, device3_5);
6534     if (deviceVersion == CAMERA_DEVICE_API_VERSION_3_5) {
6535         auto castResult = device::V3_5::ICameraDevice::castFrom(device);
6536         ASSERT_TRUE(castResult.isOk());
6537         *device3_5 = castResult;
6538     }
6539 }
6540 
6541 //Cast camera provider to corresponding version if available
castProvider(const sp<ICameraProvider> & provider,sp<provider::V2_5::ICameraProvider> * provider2_5,sp<provider::V2_6::ICameraProvider> * provider2_6)6542 void CameraHidlTest::castProvider(const sp<ICameraProvider>& provider,
6543                                   sp<provider::V2_5::ICameraProvider>* provider2_5 /*out*/,
6544                                   sp<provider::V2_6::ICameraProvider>* provider2_6 /*out*/) {
6545     ASSERT_NE(nullptr, provider2_5);
6546     auto castResult2_5 = provider::V2_5::ICameraProvider::castFrom(provider);
6547     if (castResult2_5.isOk()) {
6548         *provider2_5 = castResult2_5;
6549     }
6550 
6551     ASSERT_NE(nullptr, provider2_6);
6552     auto castResult2_6 = provider::V2_6::ICameraProvider::castFrom(provider);
6553     if (castResult2_6.isOk()) {
6554         *provider2_6 = castResult2_6;
6555     }
6556 }
6557 
6558 //Cast camera device session to corresponding version
castSession(const sp<ICameraDeviceSession> & session,int32_t deviceVersion,sp<device::V3_3::ICameraDeviceSession> * session3_3,sp<device::V3_4::ICameraDeviceSession> * session3_4,sp<device::V3_5::ICameraDeviceSession> * session3_5,sp<device::V3_6::ICameraDeviceSession> * session3_6)6559 void CameraHidlTest::castSession(const sp<ICameraDeviceSession> &session, int32_t deviceVersion,
6560         sp<device::V3_3::ICameraDeviceSession> *session3_3 /*out*/,
6561         sp<device::V3_4::ICameraDeviceSession> *session3_4 /*out*/,
6562         sp<device::V3_5::ICameraDeviceSession> *session3_5 /*out*/,
6563         sp<device::V3_6::ICameraDeviceSession> *session3_6 /*out*/) {
6564     ASSERT_NE(nullptr, session3_3);
6565     ASSERT_NE(nullptr, session3_4);
6566     ASSERT_NE(nullptr, session3_5);
6567     ASSERT_NE(nullptr, session3_6);
6568 
6569     switch (deviceVersion) {
6570         case CAMERA_DEVICE_API_VERSION_3_6: {
6571             auto castResult = device::V3_6::ICameraDeviceSession::castFrom(session);
6572             ASSERT_TRUE(castResult.isOk());
6573             *session3_6 = castResult;
6574         }
6575         [[fallthrough]];
6576         case CAMERA_DEVICE_API_VERSION_3_5: {
6577             auto castResult = device::V3_5::ICameraDeviceSession::castFrom(session);
6578             ASSERT_TRUE(castResult.isOk());
6579             *session3_5 = castResult;
6580         }
6581         [[fallthrough]];
6582         case CAMERA_DEVICE_API_VERSION_3_4: {
6583             auto castResult = device::V3_4::ICameraDeviceSession::castFrom(session);
6584             ASSERT_TRUE(castResult.isOk());
6585             *session3_4 = castResult;
6586         }
6587         [[fallthrough]];
6588         case CAMERA_DEVICE_API_VERSION_3_3: {
6589             auto castResult = device::V3_3::ICameraDeviceSession::castFrom(session);
6590             ASSERT_TRUE(castResult.isOk());
6591             *session3_3 = castResult;
6592             break;
6593         }
6594         default:
6595             //no-op
6596             return;
6597     }
6598 }
6599 
verifyStreamCombination(sp<device::V3_5::ICameraDevice> cameraDevice3_5,const::android::hardware::camera::device::V3_4::StreamConfiguration & config3_4,bool expectedStatus,bool expectMethodSupported)6600 void CameraHidlTest::verifyStreamCombination(sp<device::V3_5::ICameraDevice> cameraDevice3_5,
6601         const ::android::hardware::camera::device::V3_4::StreamConfiguration &config3_4,
6602         bool expectedStatus, bool expectMethodSupported) {
6603     if (cameraDevice3_5.get() != nullptr) {
6604         auto ret = cameraDevice3_5->isStreamCombinationSupported(config3_4,
6605                 [expectedStatus, expectMethodSupported] (Status s, bool combStatus) {
6606                     ASSERT_TRUE((Status::OK == s) ||
6607                             (!expectMethodSupported && Status::METHOD_NOT_SUPPORTED == s));
6608                     if (Status::OK == s) {
6609                         ASSERT_TRUE(combStatus == expectedStatus);
6610                     }
6611                 });
6612         ASSERT_TRUE(ret.isOk());
6613     }
6614 }
6615 
6616 // Verify logical camera static metadata
verifyLogicalCameraMetadata(const std::string & cameraName,const::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> & device,const CameraMetadata & chars,int deviceVersion,const hidl_vec<hidl_string> & deviceNames)6617 void CameraHidlTest::verifyLogicalCameraMetadata(const std::string& cameraName,
6618         const ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice>& device,
6619         const CameraMetadata &chars, int deviceVersion,
6620         const hidl_vec<hidl_string>& deviceNames) {
6621     const camera_metadata_t* metadata = (camera_metadata_t*)chars.data();
6622     ASSERT_NE(nullptr, metadata);
6623     SystemCameraKind systemCameraKind = SystemCameraKind::PUBLIC;
6624     Status rc = getSystemCameraKind(metadata, &systemCameraKind);
6625     ASSERT_EQ(rc, Status::OK);
6626     rc = isLogicalMultiCamera(metadata);
6627     ASSERT_TRUE(Status::OK == rc || Status::METHOD_NOT_SUPPORTED == rc);
6628     if (Status::METHOD_NOT_SUPPORTED == rc) {
6629         return;
6630     }
6631 
6632     camera_metadata_ro_entry entry;
6633     int retcode = find_camera_metadata_ro_entry(metadata,
6634             ANDROID_CONTROL_ZOOM_RATIO_RANGE, &entry);
6635     bool hasZoomRatioRange = (0 == retcode && entry.count == 2);
6636 
6637     std::string version, cameraId;
6638     ASSERT_TRUE(::matchDeviceName(cameraName, mProviderType, &version, &cameraId));
6639     std::unordered_set<std::string> physicalIds;
6640     ASSERT_TRUE(Status::OK == getPhysicalCameraIds(metadata, &physicalIds));
6641     for (auto physicalId : physicalIds) {
6642         ASSERT_NE(physicalId, cameraId);
6643         bool isPublicId = false;
6644         std::string fullPublicId;
6645         SystemCameraKind physSystemCameraKind = SystemCameraKind::PUBLIC;
6646         for (auto& deviceName : deviceNames) {
6647             std::string publicVersion, publicId;
6648             ASSERT_TRUE(::matchDeviceName(deviceName, mProviderType, &publicVersion, &publicId));
6649             if (physicalId == publicId) {
6650                 isPublicId = true;
6651                 fullPublicId = deviceName;
6652                 break;
6653             }
6654         }
6655         if (isPublicId) {
6656             ::android::sp<::android::hardware::camera::device::V3_2::ICameraDevice> subDevice;
6657             Return<void> ret;
6658             ret = mProvider->getCameraDeviceInterface_V3_x(
6659                 fullPublicId, [&](auto status, const auto& device) {
6660                     ASSERT_EQ(Status::OK, status);
6661                     ASSERT_NE(device, nullptr);
6662                     subDevice = device;
6663                 });
6664             ASSERT_TRUE(ret.isOk());
6665 
6666             ret = subDevice->getCameraCharacteristics(
6667                     [&](auto status, const auto& chars) {
6668                 ASSERT_EQ(Status::OK, status);
6669                 const camera_metadata_t* staticMeta =
6670                         reinterpret_cast<const camera_metadata_t*>(chars.data());
6671                 rc = getSystemCameraKind(staticMeta, &physSystemCameraKind);
6672                 ASSERT_EQ(rc, Status::OK);
6673                 // Make sure that the system camera kind of a non-hidden
6674                 // physical cameras is the same as the logical camera associated
6675                 // with it.
6676                 ASSERT_EQ(physSystemCameraKind, systemCameraKind);
6677                 retcode = find_camera_metadata_ro_entry(staticMeta,
6678                                                         ANDROID_CONTROL_ZOOM_RATIO_RANGE, &entry);
6679                 bool subCameraHasZoomRatioRange = (0 == retcode && entry.count == 2);
6680                 ASSERT_EQ(hasZoomRatioRange, subCameraHasZoomRatioRange);
6681             });
6682             ASSERT_TRUE(ret.isOk());
6683             continue;
6684         }
6685 
6686         ASSERT_TRUE(deviceVersion >= CAMERA_DEVICE_API_VERSION_3_5);
6687         auto castResult = device::V3_5::ICameraDevice::castFrom(device);
6688         ASSERT_TRUE(castResult.isOk());
6689         ::android::sp<::android::hardware::camera::device::V3_5::ICameraDevice> device3_5 =
6690                 castResult;
6691         ASSERT_NE(device3_5, nullptr);
6692 
6693         // Check camera characteristics for hidden camera id
6694         Return<void> ret = device3_5->getPhysicalCameraCharacteristics(
6695                 physicalId, [&](auto status, const auto& chars) {
6696                     verifyCameraCharacteristics(status, chars);
6697                     verifyMonochromeCharacteristics(chars, deviceVersion);
6698                     retcode =
6699                             find_camera_metadata_ro_entry((const camera_metadata_t*)chars.data(),
6700                                                           ANDROID_CONTROL_ZOOM_RATIO_RANGE, &entry);
6701                     bool subCameraHasZoomRatioRange = (0 == retcode && entry.count == 2);
6702                     ASSERT_EQ(hasZoomRatioRange, subCameraHasZoomRatioRange);
6703                 });
6704         ASSERT_TRUE(ret.isOk());
6705 
6706         // Check calling getCameraDeviceInterface_V3_x() on hidden camera id returns
6707         // ILLEGAL_ARGUMENT.
6708         std::stringstream s;
6709         s << "device@" << version << "/" << mProviderType << "/" << physicalId;
6710         hidl_string fullPhysicalId(s.str());
6711         ret = mProvider->getCameraDeviceInterface_V3_x(fullPhysicalId,
6712                 [&](auto status, const auto& device3_x) {
6713             ASSERT_EQ(Status::ILLEGAL_ARGUMENT, status);
6714             ASSERT_EQ(device3_x, nullptr);
6715         });
6716         ASSERT_TRUE(ret.isOk());
6717     }
6718 
6719     // Make sure ANDROID_LOGICAL_MULTI_CAMERA_ACTIVE_PHYSICAL_ID is available in
6720     // result keys.
6721     if (deviceVersion >= CAMERA_DEVICE_API_VERSION_3_5) {
6722         retcode = find_camera_metadata_ro_entry(metadata,
6723                 ANDROID_REQUEST_AVAILABLE_RESULT_KEYS, &entry);
6724         if ((0 == retcode) && (entry.count > 0)) {
6725                 ASSERT_NE(std::find(entry.data.i32, entry.data.i32 + entry.count,
6726                     static_cast<int32_t>(
6727                             CameraMetadataTag::ANDROID_LOGICAL_MULTI_CAMERA_ACTIVE_PHYSICAL_ID)),
6728                     entry.data.i32 + entry.count);
6729         } else {
6730             ADD_FAILURE() << "Get camera availableResultKeys failed!";
6731         }
6732     }
6733 }
6734 
verifyCameraCharacteristics(Status status,const CameraMetadata & chars)6735 void CameraHidlTest::verifyCameraCharacteristics(Status status, const CameraMetadata& chars) {
6736     ASSERT_EQ(Status::OK, status);
6737     const camera_metadata_t* metadata = (camera_metadata_t*)chars.data();
6738     size_t expectedSize = chars.size();
6739     int result = validate_camera_metadata_structure(metadata, &expectedSize);
6740     ASSERT_TRUE((result == 0) || (result == CAMERA_METADATA_VALIDATION_SHIFTED));
6741     size_t entryCount = get_camera_metadata_entry_count(metadata);
6742     // TODO: we can do better than 0 here. Need to check how many required
6743     // characteristics keys we've defined.
6744     ASSERT_GT(entryCount, 0u);
6745 
6746     camera_metadata_ro_entry entry;
6747     int retcode = find_camera_metadata_ro_entry(metadata,
6748             ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL, &entry);
6749     if ((0 == retcode) && (entry.count > 0)) {
6750         uint8_t hardwareLevel = entry.data.u8[0];
6751         ASSERT_TRUE(
6752                 hardwareLevel == ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL_LIMITED ||
6753                 hardwareLevel == ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL_FULL ||
6754                 hardwareLevel == ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL_3 ||
6755                 hardwareLevel == ANDROID_INFO_SUPPORTED_HARDWARE_LEVEL_EXTERNAL);
6756     } else {
6757         ADD_FAILURE() << "Get camera hardware level failed!";
6758     }
6759 
6760     entry.count = 0;
6761     retcode = find_camera_metadata_ro_entry(metadata,
6762             ANDROID_REQUEST_CHARACTERISTIC_KEYS_NEEDING_PERMISSION, &entry);
6763     if ((0 == retcode) || (entry.count > 0)) {
6764         ADD_FAILURE() << "ANDROID_REQUEST_CHARACTERISTIC_KEYS_NEEDING_PERMISSION "
6765             << " per API contract should never be set by Hal!";
6766     }
6767     retcode = find_camera_metadata_ro_entry(metadata,
6768             ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS, &entry);
6769     if ((0 == retcode) || (entry.count > 0)) {
6770         ADD_FAILURE() << "ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS"
6771             << " per API contract should never be set by Hal!";
6772     }
6773     retcode = find_camera_metadata_ro_entry(metadata,
6774             ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS, &entry);
6775     if ((0 == retcode) || (entry.count > 0)) {
6776         ADD_FAILURE() << "ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS"
6777             << " per API contract should never be set by Hal!";
6778     }
6779     retcode = find_camera_metadata_ro_entry(metadata,
6780             ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS, &entry);
6781     if ((0 == retcode) || (entry.count > 0)) {
6782         ADD_FAILURE() << "ANDROID_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS"
6783             << " per API contract should never be set by Hal!";
6784     }
6785 
6786     retcode = find_camera_metadata_ro_entry(metadata,
6787             ANDROID_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS, &entry);
6788     if (0 == retcode || entry.count > 0) {
6789         ADD_FAILURE() << "ANDROID_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS "
6790             << " per API contract should never be set by Hal!";
6791     }
6792 
6793     retcode = find_camera_metadata_ro_entry(metadata,
6794             ANDROID_HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS, &entry);
6795     if (0 == retcode || entry.count > 0) {
6796         ADD_FAILURE() << "ANDROID_HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS "
6797             << " per API contract should never be set by Hal!";
6798     }
6799 
6800     retcode = find_camera_metadata_ro_entry(metadata,
6801             ANDROID_HEIC_AVAILABLE_HEIC_STALL_DURATIONS, &entry);
6802     if (0 == retcode || entry.count > 0) {
6803         ADD_FAILURE() << "ANDROID_HEIC_AVAILABLE_HEIC_STALL_DURATIONS "
6804             << " per API contract should never be set by Hal!";
6805     }
6806 
6807     retcode = find_camera_metadata_ro_entry(metadata,
6808             ANDROID_HEIC_INFO_SUPPORTED, &entry);
6809     if (0 == retcode && entry.count > 0) {
6810         retcode = find_camera_metadata_ro_entry(metadata,
6811             ANDROID_HEIC_INFO_MAX_JPEG_APP_SEGMENTS_COUNT, &entry);
6812         if (0 == retcode && entry.count > 0) {
6813             uint8_t maxJpegAppSegmentsCount = entry.data.u8[0];
6814             ASSERT_TRUE(maxJpegAppSegmentsCount >= 1 &&
6815                     maxJpegAppSegmentsCount <= 16);
6816         } else {
6817             ADD_FAILURE() << "Get Heic maxJpegAppSegmentsCount failed!";
6818         }
6819     }
6820 
6821     retcode = find_camera_metadata_ro_entry(metadata,
6822             ANDROID_LENS_POSE_REFERENCE, &entry);
6823     if (0 == retcode && entry.count > 0) {
6824         uint8_t poseReference = entry.data.u8[0];
6825         ASSERT_TRUE(poseReference <= ANDROID_LENS_POSE_REFERENCE_UNDEFINED &&
6826                 poseReference >= ANDROID_LENS_POSE_REFERENCE_PRIMARY_CAMERA);
6827     }
6828 
6829     verifyExtendedSceneModeCharacteristics(metadata);
6830     verifyZoomCharacteristics(metadata);
6831 }
6832 
verifyExtendedSceneModeCharacteristics(const camera_metadata_t * metadata)6833 void CameraHidlTest::verifyExtendedSceneModeCharacteristics(const camera_metadata_t* metadata) {
6834     camera_metadata_ro_entry entry;
6835     int retcode = 0;
6836 
6837     retcode = find_camera_metadata_ro_entry(metadata, ANDROID_CONTROL_AVAILABLE_MODES, &entry);
6838     if ((0 == retcode) && (entry.count > 0)) {
6839         for (auto i = 0; i < entry.count; i++) {
6840             ASSERT_TRUE(entry.data.u8[i] >= ANDROID_CONTROL_MODE_OFF &&
6841                         entry.data.u8[i] <= ANDROID_CONTROL_MODE_USE_EXTENDED_SCENE_MODE);
6842         }
6843     } else {
6844         ADD_FAILURE() << "Get camera controlAvailableModes failed!";
6845     }
6846 
6847     // Check key availability in capabilities, request and result.
6848 
6849     retcode = find_camera_metadata_ro_entry(metadata,
6850             ANDROID_REQUEST_AVAILABLE_REQUEST_KEYS, &entry);
6851     bool hasExtendedSceneModeRequestKey = false;
6852     if ((0 == retcode) && (entry.count > 0)) {
6853         hasExtendedSceneModeRequestKey =
6854                 std::find(entry.data.i32, entry.data.i32 + entry.count,
6855                           ANDROID_CONTROL_EXTENDED_SCENE_MODE) != entry.data.i32 + entry.count;
6856     } else {
6857         ADD_FAILURE() << "Get camera availableRequestKeys failed!";
6858     }
6859 
6860     retcode = find_camera_metadata_ro_entry(metadata,
6861             ANDROID_REQUEST_AVAILABLE_RESULT_KEYS, &entry);
6862     bool hasExtendedSceneModeResultKey = false;
6863     if ((0 == retcode) && (entry.count > 0)) {
6864         hasExtendedSceneModeResultKey =
6865                 std::find(entry.data.i32, entry.data.i32 + entry.count,
6866                           ANDROID_CONTROL_EXTENDED_SCENE_MODE) != entry.data.i32 + entry.count;
6867     } else {
6868         ADD_FAILURE() << "Get camera availableResultKeys failed!";
6869     }
6870 
6871     retcode = find_camera_metadata_ro_entry(metadata,
6872             ANDROID_REQUEST_AVAILABLE_CHARACTERISTICS_KEYS, &entry);
6873     bool hasExtendedSceneModeMaxSizesKey = false;
6874     bool hasExtendedSceneModeZoomRatioRangesKey = false;
6875     if ((0 == retcode) && (entry.count > 0)) {
6876         hasExtendedSceneModeMaxSizesKey =
6877                 std::find(entry.data.i32, entry.data.i32 + entry.count,
6878                           ANDROID_CONTROL_AVAILABLE_EXTENDED_SCENE_MODE_MAX_SIZES) !=
6879                 entry.data.i32 + entry.count;
6880         hasExtendedSceneModeZoomRatioRangesKey =
6881                 std::find(entry.data.i32, entry.data.i32 + entry.count,
6882                           ANDROID_CONTROL_AVAILABLE_EXTENDED_SCENE_MODE_ZOOM_RATIO_RANGES) !=
6883                 entry.data.i32 + entry.count;
6884     } else {
6885         ADD_FAILURE() << "Get camera availableCharacteristicsKeys failed!";
6886     }
6887 
6888     camera_metadata_ro_entry maxSizesEntry;
6889     retcode = find_camera_metadata_ro_entry(
6890             metadata, ANDROID_CONTROL_AVAILABLE_EXTENDED_SCENE_MODE_MAX_SIZES, &maxSizesEntry);
6891     bool hasExtendedSceneModeMaxSizes = (0 == retcode && maxSizesEntry.count > 0);
6892 
6893     camera_metadata_ro_entry zoomRatioRangesEntry;
6894     retcode = find_camera_metadata_ro_entry(
6895             metadata, ANDROID_CONTROL_AVAILABLE_EXTENDED_SCENE_MODE_ZOOM_RATIO_RANGES,
6896             &zoomRatioRangesEntry);
6897     bool hasExtendedSceneModeZoomRatioRanges = (0 == retcode && zoomRatioRangesEntry.count > 0);
6898 
6899     // Extended scene mode keys must all be available, or all be unavailable.
6900     bool noExtendedSceneMode =
6901             !hasExtendedSceneModeRequestKey && !hasExtendedSceneModeResultKey &&
6902             !hasExtendedSceneModeMaxSizesKey && !hasExtendedSceneModeZoomRatioRangesKey &&
6903             !hasExtendedSceneModeMaxSizes && !hasExtendedSceneModeZoomRatioRanges;
6904     if (noExtendedSceneMode) {
6905         return;
6906     }
6907     bool hasExtendedSceneMode = hasExtendedSceneModeRequestKey && hasExtendedSceneModeResultKey &&
6908                                 hasExtendedSceneModeMaxSizesKey &&
6909                                 hasExtendedSceneModeZoomRatioRangesKey &&
6910                                 hasExtendedSceneModeMaxSizes && hasExtendedSceneModeZoomRatioRanges;
6911     ASSERT_TRUE(hasExtendedSceneMode);
6912 
6913     // Must have DISABLED, and must have one of BOKEH_STILL_CAPTURE, BOKEH_CONTINUOUS, or a VENDOR
6914     // mode.
6915     ASSERT_TRUE((maxSizesEntry.count == 6 && zoomRatioRangesEntry.count == 2) ||
6916             (maxSizesEntry.count == 9 && zoomRatioRangesEntry.count == 4));
6917     bool hasDisabledMode = false;
6918     bool hasBokehStillCaptureMode = false;
6919     bool hasBokehContinuousMode = false;
6920     bool hasVendorMode = false;
6921     std::vector<AvailableStream> outputStreams;
6922     ASSERT_EQ(Status::OK, getAvailableOutputStreams(metadata, outputStreams));
6923     for (int i = 0, j = 0; i < maxSizesEntry.count && j < zoomRatioRangesEntry.count; i += 3) {
6924         int32_t mode = maxSizesEntry.data.i32[i];
6925         int32_t maxWidth = maxSizesEntry.data.i32[i+1];
6926         int32_t maxHeight = maxSizesEntry.data.i32[i+2];
6927         switch (mode) {
6928             case ANDROID_CONTROL_EXTENDED_SCENE_MODE_DISABLED:
6929                 hasDisabledMode = true;
6930                 ASSERT_TRUE(maxWidth == 0 && maxHeight == 0);
6931                 break;
6932             case ANDROID_CONTROL_EXTENDED_SCENE_MODE_BOKEH_STILL_CAPTURE:
6933                 hasBokehStillCaptureMode = true;
6934                 j += 2;
6935                 break;
6936             case ANDROID_CONTROL_EXTENDED_SCENE_MODE_BOKEH_CONTINUOUS:
6937                 hasBokehContinuousMode = true;
6938                 j += 2;
6939                 break;
6940             default:
6941                 if (mode < ANDROID_CONTROL_EXTENDED_SCENE_MODE_VENDOR_START) {
6942                     ADD_FAILURE() << "Invalid extended scene mode advertised: " << mode;
6943                 } else {
6944                     hasVendorMode = true;
6945                     j += 2;
6946                 }
6947                 break;
6948         }
6949 
6950         if (mode != ANDROID_CONTROL_EXTENDED_SCENE_MODE_DISABLED) {
6951             // Make sure size is supported.
6952             bool sizeSupported = false;
6953             for (const auto& stream : outputStreams) {
6954                 if ((stream.format == static_cast<int32_t>(PixelFormat::YCBCR_420_888) ||
6955                         stream.format == static_cast<int32_t>(PixelFormat::IMPLEMENTATION_DEFINED))
6956                         && stream.width == maxWidth && stream.height == maxHeight) {
6957                     sizeSupported = true;
6958                     break;
6959                 }
6960             }
6961             ASSERT_TRUE(sizeSupported);
6962 
6963             // Make sure zoom range is valid
6964             float minZoomRatio = zoomRatioRangesEntry.data.f[0];
6965             float maxZoomRatio = zoomRatioRangesEntry.data.f[1];
6966             ASSERT_GT(minZoomRatio, 0.0f);
6967             ASSERT_LE(minZoomRatio, maxZoomRatio);
6968         }
6969     }
6970     ASSERT_TRUE(hasDisabledMode);
6971     ASSERT_TRUE(hasBokehStillCaptureMode || hasBokehContinuousMode || hasVendorMode);
6972 }
6973 
verifyZoomCharacteristics(const camera_metadata_t * metadata)6974 void CameraHidlTest::verifyZoomCharacteristics(const camera_metadata_t* metadata) {
6975     camera_metadata_ro_entry entry;
6976     int retcode = 0;
6977 
6978     // Check key availability in capabilities, request and result.
6979     retcode = find_camera_metadata_ro_entry(metadata,
6980             ANDROID_SCALER_AVAILABLE_MAX_DIGITAL_ZOOM, &entry);
6981     float maxDigitalZoom = 1.0;
6982     if ((0 == retcode) && (entry.count == 1)) {
6983         maxDigitalZoom = entry.data.f[0];
6984     } else {
6985         ADD_FAILURE() << "Get camera scalerAvailableMaxDigitalZoom failed!";
6986     }
6987 
6988     retcode = find_camera_metadata_ro_entry(metadata,
6989             ANDROID_REQUEST_AVAILABLE_REQUEST_KEYS, &entry);
6990     bool hasZoomRequestKey = false;
6991     if ((0 == retcode) && (entry.count > 0)) {
6992         hasZoomRequestKey = std::find(entry.data.i32, entry.data.i32+entry.count,
6993                 ANDROID_CONTROL_ZOOM_RATIO) != entry.data.i32+entry.count;
6994     } else {
6995         ADD_FAILURE() << "Get camera availableRequestKeys failed!";
6996     }
6997 
6998     retcode = find_camera_metadata_ro_entry(metadata,
6999             ANDROID_REQUEST_AVAILABLE_RESULT_KEYS, &entry);
7000     bool hasZoomResultKey = false;
7001     if ((0 == retcode) && (entry.count > 0)) {
7002         hasZoomResultKey = std::find(entry.data.i32, entry.data.i32+entry.count,
7003                 ANDROID_CONTROL_ZOOM_RATIO) != entry.data.i32+entry.count;
7004     } else {
7005         ADD_FAILURE() << "Get camera availableResultKeys failed!";
7006     }
7007 
7008     retcode = find_camera_metadata_ro_entry(metadata,
7009             ANDROID_REQUEST_AVAILABLE_CHARACTERISTICS_KEYS, &entry);
7010     bool hasZoomCharacteristicsKey = false;
7011     if ((0 == retcode) && (entry.count > 0)) {
7012         hasZoomCharacteristicsKey = std::find(entry.data.i32, entry.data.i32+entry.count,
7013                 ANDROID_CONTROL_ZOOM_RATIO_RANGE) != entry.data.i32+entry.count;
7014     } else {
7015         ADD_FAILURE() << "Get camera availableCharacteristicsKeys failed!";
7016     }
7017 
7018     retcode = find_camera_metadata_ro_entry(metadata,
7019             ANDROID_CONTROL_ZOOM_RATIO_RANGE, &entry);
7020     bool hasZoomRatioRange = (0 == retcode && entry.count == 2);
7021 
7022     // Zoom keys must all be available, or all be unavailable.
7023     bool noZoomRatio = !hasZoomRequestKey && !hasZoomResultKey && !hasZoomCharacteristicsKey &&
7024             !hasZoomRatioRange;
7025     if (noZoomRatio) {
7026         return;
7027     }
7028     bool hasZoomRatio = hasZoomRequestKey && hasZoomResultKey && hasZoomCharacteristicsKey &&
7029             hasZoomRatioRange;
7030     ASSERT_TRUE(hasZoomRatio);
7031 
7032     float minZoomRatio = entry.data.f[0];
7033     float maxZoomRatio = entry.data.f[1];
7034     constexpr float FLOATING_POINT_THRESHOLD = 0.00001f;
7035     if (maxDigitalZoom > maxZoomRatio + FLOATING_POINT_THRESHOLD) {
7036         ADD_FAILURE() << "Maximum digital zoom " << maxDigitalZoom
7037                       << " is larger than maximum zoom ratio " << maxZoomRatio << " + threshold "
7038                       << FLOATING_POINT_THRESHOLD << "!";
7039     }
7040     if (minZoomRatio > maxZoomRatio) {
7041         ADD_FAILURE() << "Maximum zoom ratio is less than minimum zoom ratio!";
7042     }
7043     if (minZoomRatio > 1.0f) {
7044         ADD_FAILURE() << "Minimum zoom ratio is more than 1.0!";
7045     }
7046     if (maxZoomRatio < 1.0f) {
7047         ADD_FAILURE() << "Maximum zoom ratio is less than 1.0!";
7048     }
7049 
7050     // Make sure CROPPING_TYPE is CENTER_ONLY
7051     retcode = find_camera_metadata_ro_entry(metadata,
7052             ANDROID_SCALER_CROPPING_TYPE, &entry);
7053     if ((0 == retcode) && (entry.count == 1)) {
7054         int8_t croppingType = entry.data.u8[0];
7055         ASSERT_EQ(croppingType, ANDROID_SCALER_CROPPING_TYPE_CENTER_ONLY);
7056     } else {
7057         ADD_FAILURE() << "Get camera scalerCroppingType failed!";
7058     }
7059 }
7060 
verifyMonochromeCharacteristics(const CameraMetadata & chars,int deviceVersion)7061 void CameraHidlTest::verifyMonochromeCharacteristics(const CameraMetadata& chars,
7062         int deviceVersion) {
7063     const camera_metadata_t* metadata = (camera_metadata_t*)chars.data();
7064     Status rc = isMonochromeCamera(metadata);
7065     if (Status::METHOD_NOT_SUPPORTED == rc) {
7066         return;
7067     }
7068     ASSERT_EQ(Status::OK, rc);
7069 
7070     camera_metadata_ro_entry entry;
7071     // Check capabilities
7072     int retcode = find_camera_metadata_ro_entry(metadata,
7073                 ANDROID_REQUEST_AVAILABLE_CAPABILITIES, &entry);
7074     if ((0 == retcode) && (entry.count > 0)) {
7075         ASSERT_EQ(std::find(entry.data.u8, entry.data.u8 + entry.count,
7076                 ANDROID_REQUEST_AVAILABLE_CAPABILITIES_MANUAL_POST_PROCESSING),
7077                 entry.data.u8 + entry.count);
7078         if (deviceVersion < CAMERA_DEVICE_API_VERSION_3_5) {
7079             ASSERT_EQ(std::find(entry.data.u8, entry.data.u8 + entry.count,
7080                     ANDROID_REQUEST_AVAILABLE_CAPABILITIES_RAW),
7081                     entry.data.u8 + entry.count);
7082         }
7083     }
7084 
7085     if (deviceVersion >= CAMERA_DEVICE_API_VERSION_3_5) {
7086         // Check Cfa
7087         retcode = find_camera_metadata_ro_entry(metadata,
7088                 ANDROID_SENSOR_INFO_COLOR_FILTER_ARRANGEMENT, &entry);
7089         if ((0 == retcode) && (entry.count == 1)) {
7090             ASSERT_TRUE(entry.data.i32[0] == static_cast<int32_t>(
7091                     CameraMetadataEnumAndroidSensorInfoColorFilterArrangement::ANDROID_SENSOR_INFO_COLOR_FILTER_ARRANGEMENT_MONO)
7092                     || entry.data.i32[0] == static_cast<int32_t>(
7093                     CameraMetadataEnumAndroidSensorInfoColorFilterArrangement::ANDROID_SENSOR_INFO_COLOR_FILTER_ARRANGEMENT_NIR));
7094         }
7095 
7096         // Check availableRequestKeys
7097         retcode = find_camera_metadata_ro_entry(metadata,
7098                 ANDROID_REQUEST_AVAILABLE_REQUEST_KEYS, &entry);
7099         if ((0 == retcode) && (entry.count > 0)) {
7100             for (size_t i = 0; i < entry.count; i++) {
7101                 ASSERT_NE(entry.data.i32[i], ANDROID_COLOR_CORRECTION_MODE);
7102                 ASSERT_NE(entry.data.i32[i], ANDROID_COLOR_CORRECTION_TRANSFORM);
7103                 ASSERT_NE(entry.data.i32[i], ANDROID_COLOR_CORRECTION_GAINS);
7104             }
7105         } else {
7106             ADD_FAILURE() << "Get camera availableRequestKeys failed!";
7107         }
7108 
7109         // Check availableResultKeys
7110         retcode = find_camera_metadata_ro_entry(metadata,
7111                 ANDROID_REQUEST_AVAILABLE_RESULT_KEYS, &entry);
7112         if ((0 == retcode) && (entry.count > 0)) {
7113             for (size_t i = 0; i < entry.count; i++) {
7114                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_GREEN_SPLIT);
7115                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_NEUTRAL_COLOR_POINT);
7116                 ASSERT_NE(entry.data.i32[i], ANDROID_COLOR_CORRECTION_MODE);
7117                 ASSERT_NE(entry.data.i32[i], ANDROID_COLOR_CORRECTION_TRANSFORM);
7118                 ASSERT_NE(entry.data.i32[i], ANDROID_COLOR_CORRECTION_GAINS);
7119             }
7120         } else {
7121             ADD_FAILURE() << "Get camera availableResultKeys failed!";
7122         }
7123 
7124         // Check availableCharacteristicKeys
7125         retcode = find_camera_metadata_ro_entry(metadata,
7126                 ANDROID_REQUEST_AVAILABLE_CHARACTERISTICS_KEYS, &entry);
7127         if ((0 == retcode) && (entry.count > 0)) {
7128             for (size_t i = 0; i < entry.count; i++) {
7129                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_REFERENCE_ILLUMINANT1);
7130                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_REFERENCE_ILLUMINANT2);
7131                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_CALIBRATION_TRANSFORM1);
7132                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_CALIBRATION_TRANSFORM2);
7133                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_COLOR_TRANSFORM1);
7134                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_COLOR_TRANSFORM2);
7135                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_FORWARD_MATRIX1);
7136                 ASSERT_NE(entry.data.i32[i], ANDROID_SENSOR_FORWARD_MATRIX2);
7137             }
7138         } else {
7139             ADD_FAILURE() << "Get camera availableResultKeys failed!";
7140         }
7141 
7142         // Check blackLevelPattern
7143         retcode = find_camera_metadata_ro_entry(metadata,
7144                 ANDROID_SENSOR_BLACK_LEVEL_PATTERN, &entry);
7145         if ((0 == retcode) && (entry.count > 0)) {
7146             ASSERT_EQ(entry.count, 4);
7147             for (size_t i = 1; i < entry.count; i++) {
7148                 ASSERT_EQ(entry.data.i32[i], entry.data.i32[0]);
7149             }
7150         }
7151     }
7152 }
7153 
verifyMonochromeCameraResult(const::android::hardware::camera::common::V1_0::helper::CameraMetadata & metadata)7154 void CameraHidlTest::verifyMonochromeCameraResult(
7155         const ::android::hardware::camera::common::V1_0::helper::CameraMetadata& metadata) {
7156     camera_metadata_ro_entry entry;
7157 
7158     // Check tags that are not applicable for monochrome camera
7159     ASSERT_FALSE(metadata.exists(ANDROID_SENSOR_GREEN_SPLIT));
7160     ASSERT_FALSE(metadata.exists(ANDROID_SENSOR_NEUTRAL_COLOR_POINT));
7161     ASSERT_FALSE(metadata.exists(ANDROID_COLOR_CORRECTION_MODE));
7162     ASSERT_FALSE(metadata.exists(ANDROID_COLOR_CORRECTION_TRANSFORM));
7163     ASSERT_FALSE(metadata.exists(ANDROID_COLOR_CORRECTION_GAINS));
7164 
7165     // Check dynamicBlackLevel
7166     entry = metadata.find(ANDROID_SENSOR_DYNAMIC_BLACK_LEVEL);
7167     if (entry.count > 0) {
7168         ASSERT_EQ(entry.count, 4);
7169         for (size_t i = 1; i < entry.count; i++) {
7170             ASSERT_FLOAT_EQ(entry.data.f[i], entry.data.f[0]);
7171         }
7172     }
7173 
7174     // Check noiseProfile
7175     entry = metadata.find(ANDROID_SENSOR_NOISE_PROFILE);
7176     if (entry.count > 0) {
7177         ASSERT_EQ(entry.count, 2);
7178     }
7179 
7180     // Check lensShadingMap
7181     entry = metadata.find(ANDROID_STATISTICS_LENS_SHADING_MAP);
7182     if (entry.count > 0) {
7183         ASSERT_EQ(entry.count % 4, 0);
7184         for (size_t i = 0; i < entry.count/4; i++) {
7185             ASSERT_FLOAT_EQ(entry.data.f[i*4+1], entry.data.f[i*4]);
7186             ASSERT_FLOAT_EQ(entry.data.f[i*4+2], entry.data.f[i*4]);
7187             ASSERT_FLOAT_EQ(entry.data.f[i*4+3], entry.data.f[i*4]);
7188         }
7189     }
7190 
7191     // Check tonemapCurve
7192     camera_metadata_ro_entry curveRed = metadata.find(ANDROID_TONEMAP_CURVE_RED);
7193     camera_metadata_ro_entry curveGreen = metadata.find(ANDROID_TONEMAP_CURVE_GREEN);
7194     camera_metadata_ro_entry curveBlue = metadata.find(ANDROID_TONEMAP_CURVE_BLUE);
7195     if (curveRed.count > 0 && curveGreen.count > 0 && curveBlue.count > 0) {
7196         ASSERT_EQ(curveRed.count, curveGreen.count);
7197         ASSERT_EQ(curveRed.count, curveBlue.count);
7198         for (size_t i = 0; i < curveRed.count; i++) {
7199             ASSERT_FLOAT_EQ(curveGreen.data.f[i], curveRed.data.f[i]);
7200             ASSERT_FLOAT_EQ(curveBlue.data.f[i], curveRed.data.f[i]);
7201         }
7202     }
7203 }
7204 
verifyBuffersReturned(sp<device::V3_2::ICameraDeviceSession> session,int deviceVersion,int32_t streamId,sp<DeviceCb> cb,uint32_t streamConfigCounter)7205 void CameraHidlTest::verifyBuffersReturned(
7206         sp<device::V3_2::ICameraDeviceSession> session,
7207         int deviceVersion, int32_t streamId,
7208         sp<DeviceCb> cb, uint32_t streamConfigCounter) {
7209     sp<device::V3_3::ICameraDeviceSession> session3_3;
7210     sp<device::V3_4::ICameraDeviceSession> session3_4;
7211     sp<device::V3_5::ICameraDeviceSession> session3_5;
7212     sp<device::V3_6::ICameraDeviceSession> session3_6;
7213     castSession(session, deviceVersion, &session3_3, &session3_4, &session3_5, &session3_6);
7214     ASSERT_NE(nullptr, session3_5.get());
7215 
7216     hidl_vec<int32_t> streamIds(1);
7217     streamIds[0] = streamId;
7218     session3_5->signalStreamFlush(streamIds, /*streamConfigCounter*/streamConfigCounter);
7219     cb->waitForBuffersReturned();
7220 }
7221 
verifyBuffersReturned(sp<device::V3_4::ICameraDeviceSession> session3_4,hidl_vec<int32_t> streamIds,sp<DeviceCb> cb,uint32_t streamConfigCounter)7222 void CameraHidlTest::verifyBuffersReturned(
7223         sp<device::V3_4::ICameraDeviceSession> session3_4,
7224         hidl_vec<int32_t> streamIds, sp<DeviceCb> cb, uint32_t streamConfigCounter) {
7225     auto castResult = device::V3_5::ICameraDeviceSession::castFrom(session3_4);
7226     ASSERT_TRUE(castResult.isOk());
7227     sp<device::V3_5::ICameraDeviceSession> session3_5 = castResult;
7228     ASSERT_NE(nullptr, session3_5.get());
7229 
7230     session3_5->signalStreamFlush(streamIds, /*streamConfigCounter*/streamConfigCounter);
7231     cb->waitForBuffersReturned();
7232 }
7233 
verifyLogicalCameraResult(const camera_metadata_t * staticMetadata,const::android::hardware::camera::common::V1_0::helper::CameraMetadata & resultMetadata)7234 void CameraHidlTest::verifyLogicalCameraResult(const camera_metadata_t* staticMetadata,
7235         const ::android::hardware::camera::common::V1_0::helper::CameraMetadata& resultMetadata) {
7236     std::unordered_set<std::string> physicalIds;
7237     Status rc = getPhysicalCameraIds(staticMetadata, &physicalIds);
7238     ASSERT_TRUE(Status::OK == rc);
7239     ASSERT_TRUE(physicalIds.size() > 1);
7240 
7241     camera_metadata_ro_entry entry;
7242     // Check mainPhysicalId
7243     entry = resultMetadata.find(ANDROID_LOGICAL_MULTI_CAMERA_ACTIVE_PHYSICAL_ID);
7244     if (entry.count > 0) {
7245         std::string mainPhysicalId(reinterpret_cast<const char *>(entry.data.u8));
7246         ASSERT_NE(physicalIds.find(mainPhysicalId), physicalIds.end());
7247     } else {
7248         ADD_FAILURE() << "Get LOGICAL_MULTI_CAMERA_ACTIVE_PHYSICAL_ID failed!";
7249     }
7250 }
7251 
7252 // Open a device session with empty callbacks and return static metadata.
openEmptyDeviceSession(const std::string & name,sp<ICameraProvider> provider,sp<ICameraDeviceSession> * session,camera_metadata_t ** staticMeta,::android::sp<ICameraDevice> * cameraDevice)7253 void CameraHidlTest::openEmptyDeviceSession(const std::string &name, sp<ICameraProvider> provider,
7254         sp<ICameraDeviceSession> *session /*out*/, camera_metadata_t **staticMeta /*out*/,
7255         ::android::sp<ICameraDevice> *cameraDevice /*out*/) {
7256     ASSERT_NE(nullptr, session);
7257     ASSERT_NE(nullptr, staticMeta);
7258 
7259     ::android::sp<ICameraDevice> device3_x;
7260     ALOGI("configureStreams: Testing camera device %s", name.c_str());
7261     Return<void> ret;
7262     ret = provider->getCameraDeviceInterface_V3_x(
7263         name,
7264         [&](auto status, const auto& device) {
7265             ALOGI("getCameraDeviceInterface_V3_x returns status:%d",
7266                   (int)status);
7267             ASSERT_EQ(Status::OK, status);
7268             ASSERT_NE(device, nullptr);
7269             device3_x = device;
7270         });
7271     ASSERT_TRUE(ret.isOk());
7272     if (cameraDevice != nullptr) {
7273         *cameraDevice = device3_x;
7274     }
7275 
7276     sp<EmptyDeviceCb> cb = new EmptyDeviceCb();
7277     ret = device3_x->open(cb, [&](auto status, const auto& newSession) {
7278             ALOGI("device::open returns status:%d", (int)status);
7279             ASSERT_EQ(Status::OK, status);
7280             ASSERT_NE(newSession, nullptr);
7281             *session = newSession;
7282         });
7283     ASSERT_TRUE(ret.isOk());
7284 
7285     ret = device3_x->getCameraCharacteristics([&] (Status s,
7286             CameraMetadata metadata) {
7287         ASSERT_EQ(Status::OK, s);
7288         *staticMeta = clone_camera_metadata(
7289                 reinterpret_cast<const camera_metadata_t*>(metadata.data()));
7290         ASSERT_NE(nullptr, *staticMeta);
7291     });
7292     ASSERT_TRUE(ret.isOk());
7293 }
7294 
notifyDeviceState(provider::V2_5::DeviceState newState)7295 void CameraHidlTest::notifyDeviceState(provider::V2_5::DeviceState newState) {
7296     if (mProvider2_5.get() == nullptr) return;
7297 
7298     mProvider2_5->notifyDeviceStateChange(
7299             static_cast<hidl_bitfield<provider::V2_5::DeviceState>>(newState));
7300 }
7301 
7302 // Open a particular camera device.
openCameraDevice(const std::string & name,sp<ICameraProvider> provider,sp<::android::hardware::camera::device::V1_0::ICameraDevice> * device1)7303 void CameraHidlTest::openCameraDevice(const std::string &name,
7304         sp<ICameraProvider> provider,
7305         sp<::android::hardware::camera::device::V1_0::ICameraDevice> *device1 /*out*/) {
7306     ASSERT_TRUE(nullptr != device1);
7307 
7308     Return<void> ret;
7309     ret = provider->getCameraDeviceInterface_V1_x(
7310             name,
7311             [&](auto status, const auto& device) {
7312             ALOGI("getCameraDeviceInterface_V1_x returns status:%d",
7313                   (int)status);
7314             ASSERT_EQ(Status::OK, status);
7315             ASSERT_NE(device, nullptr);
7316             *device1 = device;
7317         });
7318     ASSERT_TRUE(ret.isOk());
7319 
7320     sp<Camera1DeviceCb> deviceCb = new Camera1DeviceCb(this);
7321     Return<Status> returnStatus = (*device1)->open(deviceCb);
7322     ASSERT_TRUE(returnStatus.isOk());
7323     ASSERT_EQ(Status::OK, returnStatus);
7324 }
7325 
7326 // Initialize and configure a preview window.
setupPreviewWindow(const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device,sp<BufferItemConsumer> * bufferItemConsumer,sp<BufferItemHander> * bufferHandler)7327 void CameraHidlTest::setupPreviewWindow(
7328         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device,
7329         sp<BufferItemConsumer> *bufferItemConsumer /*out*/,
7330         sp<BufferItemHander> *bufferHandler /*out*/) {
7331     ASSERT_NE(nullptr, device.get());
7332     ASSERT_NE(nullptr, bufferItemConsumer);
7333     ASSERT_NE(nullptr, bufferHandler);
7334 
7335     sp<IGraphicBufferProducer> producer;
7336     sp<IGraphicBufferConsumer> consumer;
7337     BufferQueue::createBufferQueue(&producer, &consumer);
7338     *bufferItemConsumer = new BufferItemConsumer(consumer,
7339             GraphicBuffer::USAGE_HW_TEXTURE); //Use GLConsumer default usage flags
7340     ASSERT_NE(nullptr, (*bufferItemConsumer).get());
7341     *bufferHandler = new BufferItemHander(*bufferItemConsumer);
7342     ASSERT_NE(nullptr, (*bufferHandler).get());
7343     (*bufferItemConsumer)->setFrameAvailableListener(*bufferHandler);
7344     sp<Surface> surface = new Surface(producer);
7345     sp<PreviewWindowCb> previewCb = new PreviewWindowCb(surface);
7346 
7347     auto rc = device->setPreviewWindow(previewCb);
7348     ASSERT_TRUE(rc.isOk());
7349     ASSERT_EQ(Status::OK, rc);
7350 }
7351 
7352 // Stop camera preview and close camera.
stopPreviewAndClose(const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device)7353 void CameraHidlTest::stopPreviewAndClose(
7354         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device) {
7355     Return<void> ret = device->stopPreview();
7356     ASSERT_TRUE(ret.isOk());
7357 
7358     ret = device->close();
7359     ASSERT_TRUE(ret.isOk());
7360 }
7361 
7362 // Enable a specific camera message type.
enableMsgType(unsigned int msgType,const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device)7363 void CameraHidlTest::enableMsgType(unsigned int msgType,
7364         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device) {
7365     Return<void> ret = device->enableMsgType(msgType);
7366     ASSERT_TRUE(ret.isOk());
7367 
7368     Return<bool> returnBoolStatus = device->msgTypeEnabled(msgType);
7369     ASSERT_TRUE(returnBoolStatus.isOk());
7370     ASSERT_TRUE(returnBoolStatus);
7371 }
7372 
7373 // Disable a specific camera message type.
disableMsgType(unsigned int msgType,const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device)7374 void CameraHidlTest::disableMsgType(unsigned int msgType,
7375         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device) {
7376     Return<void> ret = device->disableMsgType(msgType);
7377     ASSERT_TRUE(ret.isOk());
7378 
7379     Return<bool> returnBoolStatus = device->msgTypeEnabled(msgType);
7380     ASSERT_TRUE(returnBoolStatus.isOk());
7381     ASSERT_FALSE(returnBoolStatus);
7382 }
7383 
7384 // Wait until a specific frame notification arrives.
waitForFrameLocked(DataCallbackMsg msgFrame,std::unique_lock<std::mutex> & l)7385 void CameraHidlTest::waitForFrameLocked(DataCallbackMsg msgFrame,
7386         std::unique_lock<std::mutex> &l) {
7387     while (msgFrame != mDataMessageTypeReceived) {
7388         auto timeout = std::chrono::system_clock::now() +
7389                 std::chrono::seconds(kStreamBufferTimeoutSec);
7390         ASSERT_NE(std::cv_status::timeout,
7391                 mResultCondition.wait_until(l, timeout));
7392     }
7393 }
7394 
7395 // Start preview on a particular camera device
startPreview(const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device)7396 void CameraHidlTest::startPreview(
7397         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device) {
7398     Return<Status> returnStatus = device->startPreview();
7399     ASSERT_TRUE(returnStatus.isOk());
7400     ASSERT_EQ(Status::OK, returnStatus);
7401 }
7402 
7403 // Retrieve camera parameters.
getParameters(const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device,CameraParameters * cameraParams)7404 void CameraHidlTest::getParameters(
7405         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device,
7406         CameraParameters *cameraParams /*out*/) {
7407     ASSERT_NE(nullptr, cameraParams);
7408 
7409     Return<void> ret;
7410     ret = device->getParameters([&] (const ::android::hardware::hidl_string& params) {
7411         ASSERT_FALSE(params.empty());
7412         ::android::String8 paramString(params.c_str());
7413         (*cameraParams).unflatten(paramString);
7414     });
7415     ASSERT_TRUE(ret.isOk());
7416 }
7417 
7418 // Set camera parameters.
setParameters(const sp<::android::hardware::camera::device::V1_0::ICameraDevice> & device,const CameraParameters & cameraParams)7419 void CameraHidlTest::setParameters(
7420         const sp<::android::hardware::camera::device::V1_0::ICameraDevice> &device,
7421         const CameraParameters &cameraParams) {
7422     Return<Status> returnStatus = device->setParameters(
7423             cameraParams.flatten().string());
7424     ASSERT_TRUE(returnStatus.isOk());
7425     ASSERT_EQ(Status::OK, returnStatus);
7426 }
7427 
allocateGraphicBuffer(uint32_t width,uint32_t height,uint64_t usage,PixelFormat format,hidl_handle * buffer_handle)7428 void CameraHidlTest::allocateGraphicBuffer(uint32_t width, uint32_t height, uint64_t usage,
7429         PixelFormat format, hidl_handle *buffer_handle /*out*/) {
7430     ASSERT_NE(buffer_handle, nullptr);
7431 
7432     buffer_handle_t buffer;
7433     uint32_t stride;
7434 
7435     android::status_t err = android::GraphicBufferAllocator::get().allocateRawHandle(
7436             width, height, static_cast<int32_t>(format), 1u /*layerCount*/, usage, &buffer, &stride,
7437             "VtsHalCameraProviderV2_4");
7438     ASSERT_EQ(err, android::NO_ERROR);
7439 
7440     buffer_handle->setTo(const_cast<native_handle_t*>(buffer), true /*shouldOwn*/);
7441 }
7442 
verifyRecommendedConfigs(const CameraMetadata & chars)7443 void CameraHidlTest::verifyRecommendedConfigs(const CameraMetadata& chars) {
7444     size_t CONFIG_ENTRY_SIZE = 5;
7445     size_t CONFIG_ENTRY_TYPE_OFFSET = 3;
7446     size_t CONFIG_ENTRY_BITFIELD_OFFSET = 4;
7447     uint32_t maxPublicUsecase =
7448             ANDROID_SCALER_AVAILABLE_RECOMMENDED_STREAM_CONFIGURATIONS_PUBLIC_END;
7449     uint32_t vendorUsecaseStart =
7450             ANDROID_SCALER_AVAILABLE_RECOMMENDED_STREAM_CONFIGURATIONS_VENDOR_START;
7451     uint32_t usecaseMask = (1 << vendorUsecaseStart) - 1;
7452     usecaseMask &= ~((1 << maxPublicUsecase) - 1);
7453 
7454     const camera_metadata_t* metadata = reinterpret_cast<const camera_metadata_t*> (chars.data());
7455 
7456     camera_metadata_ro_entry recommendedConfigsEntry, recommendedDepthConfigsEntry, ioMapEntry;
7457     recommendedConfigsEntry.count = recommendedDepthConfigsEntry.count = ioMapEntry.count = 0;
7458     int retCode = find_camera_metadata_ro_entry(metadata,
7459             ANDROID_SCALER_AVAILABLE_RECOMMENDED_STREAM_CONFIGURATIONS, &recommendedConfigsEntry);
7460     int depthRetCode = find_camera_metadata_ro_entry(metadata,
7461             ANDROID_DEPTH_AVAILABLE_RECOMMENDED_DEPTH_STREAM_CONFIGURATIONS,
7462             &recommendedDepthConfigsEntry);
7463     int ioRetCode = find_camera_metadata_ro_entry(metadata,
7464             ANDROID_SCALER_AVAILABLE_RECOMMENDED_INPUT_OUTPUT_FORMATS_MAP, &ioMapEntry);
7465     if ((0 != retCode) && (0 != depthRetCode)) {
7466         //In case both regular and depth recommended configurations are absent,
7467         //I/O should be absent as well.
7468         ASSERT_NE(ioRetCode, 0);
7469         return;
7470     }
7471 
7472     camera_metadata_ro_entry availableKeysEntry;
7473     retCode = find_camera_metadata_ro_entry(metadata,
7474             ANDROID_REQUEST_AVAILABLE_CHARACTERISTICS_KEYS, &availableKeysEntry);
7475     ASSERT_TRUE((0 == retCode) && (availableKeysEntry.count > 0));
7476     std::vector<int32_t> availableKeys;
7477     availableKeys.reserve(availableKeysEntry.count);
7478     availableKeys.insert(availableKeys.end(), availableKeysEntry.data.i32,
7479             availableKeysEntry.data.i32 + availableKeysEntry.count);
7480 
7481     if (recommendedConfigsEntry.count > 0) {
7482         ASSERT_NE(std::find(availableKeys.begin(), availableKeys.end(),
7483                     ANDROID_SCALER_AVAILABLE_RECOMMENDED_STREAM_CONFIGURATIONS),
7484                 availableKeys.end());
7485         ASSERT_EQ((recommendedConfigsEntry.count % CONFIG_ENTRY_SIZE), 0);
7486         for (size_t i = 0; i < recommendedConfigsEntry.count; i += CONFIG_ENTRY_SIZE) {
7487             int32_t entryType =
7488                 recommendedConfigsEntry.data.i32[i + CONFIG_ENTRY_TYPE_OFFSET];
7489             uint32_t bitfield =
7490                 recommendedConfigsEntry.data.i32[i + CONFIG_ENTRY_BITFIELD_OFFSET];
7491             ASSERT_TRUE((entryType ==
7492                      ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT) ||
7493                     (entryType ==
7494                      ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_INPUT));
7495             ASSERT_TRUE((bitfield & usecaseMask) == 0);
7496         }
7497     }
7498 
7499     if (recommendedDepthConfigsEntry.count > 0) {
7500         ASSERT_NE(std::find(availableKeys.begin(), availableKeys.end(),
7501                     ANDROID_DEPTH_AVAILABLE_RECOMMENDED_DEPTH_STREAM_CONFIGURATIONS),
7502                 availableKeys.end());
7503         ASSERT_EQ((recommendedDepthConfigsEntry.count % CONFIG_ENTRY_SIZE), 0);
7504         for (size_t i = 0; i < recommendedDepthConfigsEntry.count; i += CONFIG_ENTRY_SIZE) {
7505             int32_t entryType =
7506                 recommendedDepthConfigsEntry.data.i32[i + CONFIG_ENTRY_TYPE_OFFSET];
7507             uint32_t bitfield =
7508                 recommendedDepthConfigsEntry.data.i32[i + CONFIG_ENTRY_BITFIELD_OFFSET];
7509             ASSERT_TRUE((entryType ==
7510                      ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT) ||
7511                     (entryType ==
7512                      ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_INPUT));
7513             ASSERT_TRUE((bitfield & usecaseMask) == 0);
7514         }
7515 
7516         if (recommendedConfigsEntry.count == 0) {
7517             //In case regular recommended configurations are absent but suggested depth
7518             //configurations are present, I/O should be absent.
7519             ASSERT_NE(ioRetCode, 0);
7520         }
7521     }
7522 
7523     if ((ioRetCode == 0) && (ioMapEntry.count > 0)) {
7524         ASSERT_NE(std::find(availableKeys.begin(), availableKeys.end(),
7525                     ANDROID_SCALER_AVAILABLE_RECOMMENDED_INPUT_OUTPUT_FORMATS_MAP),
7526                 availableKeys.end());
7527         ASSERT_EQ(isZSLModeAvailable(metadata), Status::OK);
7528     }
7529 }
7530 
verifySessionReconfigurationQuery(sp<device::V3_5::ICameraDeviceSession> session3_5,camera_metadata * oldSessionParams,camera_metadata * newSessionParams)7531 void CameraHidlTest::verifySessionReconfigurationQuery(
7532         sp<device::V3_5::ICameraDeviceSession> session3_5, camera_metadata* oldSessionParams,
7533         camera_metadata* newSessionParams) {
7534     ASSERT_NE(nullptr, session3_5.get());
7535     ASSERT_NE(nullptr, oldSessionParams);
7536     ASSERT_NE(nullptr, newSessionParams);
7537 
7538     android::hardware::hidl_vec<uint8_t> oldParams, newParams;
7539     oldParams.setToExternal(reinterpret_cast<uint8_t*>(oldSessionParams),
7540             get_camera_metadata_size(oldSessionParams));
7541     newParams.setToExternal(reinterpret_cast<uint8_t*>(newSessionParams),
7542             get_camera_metadata_size(newSessionParams));
7543     android::hardware::camera::common::V1_0::Status callStatus;
7544     auto hidlCb = [&callStatus] (android::hardware::camera::common::V1_0::Status s,
7545             bool /*requiredFlag*/) {
7546         callStatus = s;
7547     };
7548     auto ret = session3_5->isReconfigurationRequired(oldParams, newParams, hidlCb);
7549     ASSERT_TRUE(ret.isOk());
7550     switch (callStatus) {
7551         case android::hardware::camera::common::V1_0::Status::OK:
7552         case android::hardware::camera::common::V1_0::Status::METHOD_NOT_SUPPORTED:
7553             break;
7554         case android::hardware::camera::common::V1_0::Status::INTERNAL_ERROR:
7555         default:
7556             ADD_FAILURE() << "Query calllback failed";
7557     }
7558 }
7559 
verifyRequestTemplate(const camera_metadata_t * metadata,RequestTemplate requestTemplate)7560 void CameraHidlTest::verifyRequestTemplate(const camera_metadata_t* metadata,
7561         RequestTemplate requestTemplate) {
7562     ASSERT_NE(nullptr, metadata);
7563     size_t entryCount =
7564             get_camera_metadata_entry_count(metadata);
7565     ALOGI("template %u metadata entry count is %zu", (int32_t)requestTemplate, entryCount);
7566     // TODO: we can do better than 0 here. Need to check how many required
7567     // request keys we've defined for each template
7568     ASSERT_GT(entryCount, 0u);
7569 
7570     // Check zoomRatio
7571     camera_metadata_ro_entry zoomRatioEntry;
7572     int foundZoomRatio = find_camera_metadata_ro_entry(metadata,
7573             ANDROID_CONTROL_ZOOM_RATIO, &zoomRatioEntry);
7574     if (foundZoomRatio == 0) {
7575         ASSERT_EQ(zoomRatioEntry.count, 1);
7576         ASSERT_EQ(zoomRatioEntry.data.f[0], 1.0f);
7577     }
7578 }
7579 
7580 INSTANTIATE_TEST_SUITE_P(
7581         PerInstance, CameraHidlTest,
7582         testing::ValuesIn(android::hardware::getAllHalInstanceNames(ICameraProvider::descriptor)),
7583         android::hardware::PrintInstanceNameToString);
7584