• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2015 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 //#define LOG_NDEBUG 0
18 #define LOG_TAG "NativeCamera"
19 #include <log/log.h>
20 
21 #include <chrono>
22 #include <cinttypes>
23 #include <condition_variable>
24 #include <map>
25 #include <mutex>
26 #include <string>
27 #include <vector>
28 #include <unistd.h>
29 #include <assert.h>
30 #include <jni.h>
31 #include <stdio.h>
32 #include <string.h>
33 #include <unordered_map>
34 #include <set>
35 
36 #include <android/native_window_jni.h>
37 
38 #include "camera/NdkCameraError.h"
39 #include "camera/NdkCameraManager.h"
40 #include "camera/NdkCameraMetadata.h"
41 #include "camera/NdkCameraDevice.h"
42 #include "camera/NdkCameraCaptureSession.h"
43 #include "media/NdkImage.h"
44 #include "media/NdkImageReader.h"
45 
46 #define LOG_ERROR(buf, ...) sprintf(buf, __VA_ARGS__); \
47                             ALOGE("%s", buf);
48 
49 namespace {
50     const int MAX_ERROR_STRING_LEN = 512;
51     char errorString[MAX_ERROR_STRING_LEN];
52 }
53 
54 template <>
55 struct std::default_delete<ACameraMetadata> {
operator ()std::default_delete56     inline void operator()(ACameraMetadata* chars) const { ACameraMetadata_free(chars); }
57 };
58 
59 class CameraServiceListener {
60   public:
61     typedef std::set<std::pair<std::string, std::string>> StringPairSet;
62 
onAvailable(void * obj,const char * cameraId)63     static void onAvailable(void* obj, const char* cameraId) {
64         ALOGV("Camera %s onAvailable", cameraId);
65         if (obj == nullptr) {
66             return;
67         }
68         CameraServiceListener* thiz = reinterpret_cast<CameraServiceListener*>(obj);
69         std::lock_guard<std::mutex> lock(thiz->mMutex);
70         thiz->mOnAvailableCount++;
71         thiz->mAvailableMap[cameraId] = true;
72         return;
73     }
74 
onUnavailable(void * obj,const char * cameraId)75     static void onUnavailable(void* obj, const char* cameraId) {
76         ALOGV("Camera %s onUnavailable", cameraId);
77         if (obj == nullptr) {
78             return;
79         }
80         CameraServiceListener* thiz = reinterpret_cast<CameraServiceListener*>(obj);
81         std::lock_guard<std::mutex> lock(thiz->mMutex);
82         thiz->mOnUnavailableCount++;
83         thiz->mAvailableMap[cameraId] = false;
84         return;
85     }
86 
87 
onCameraAccessPrioritiesChanged(void * obj)88     static void onCameraAccessPrioritiesChanged(void* obj) {
89         ALOGV("onCameraAccessPrioritiesChanged");
90         if (obj == nullptr) {
91             return;
92         }
93         CameraServiceListener* thiz = reinterpret_cast<CameraServiceListener*>(obj);
94         std::lock_guard<std::mutex> lock(thiz->mMutex);
95         thiz->mOnCameraAccessPrioritiesChangedCount++;
96         return;
97     }
98 
onPhysicalCameraAvailable(void * obj,const char * cameraId,const char * physicalCameraId)99     static void onPhysicalCameraAvailable(void* obj, const char* cameraId,
100             const char* physicalCameraId) {
101         ALOGV("Camera %s : %s onAvailable", cameraId, physicalCameraId);
102         if (obj == nullptr) {
103             return;
104         }
105         CameraServiceListener* thiz = reinterpret_cast<CameraServiceListener*>(obj);
106         std::lock_guard<std::mutex> lock(thiz->mMutex);
107         thiz->mOnPhysicalCameraAvailableCount++;
108         return;
109     }
110 
onPhysicalCameraUnavailable(void * obj,const char * cameraId,const char * physicalCameraId)111     static void onPhysicalCameraUnavailable(void* obj, const char* cameraId,
112             const char* physicalCameraId) {
113         ALOGV("Camera %s : %s onUnavailable", cameraId, physicalCameraId);
114         if (obj == nullptr) {
115             return;
116         }
117         CameraServiceListener* thiz = reinterpret_cast<CameraServiceListener*>(obj);
118         std::lock_guard<std::mutex> lock(thiz->mMutex);
119         thiz->mUnavailablePhysicalCameras.emplace(cameraId, physicalCameraId);
120         return;
121     }
122 
123 
resetCount()124     void resetCount() {
125         std::lock_guard<std::mutex> lock(mMutex);
126         mOnAvailableCount = 0;
127         mOnUnavailableCount = 0;
128         mOnCameraAccessPrioritiesChangedCount = 0;
129         mOnPhysicalCameraAvailableCount = 0;
130         mUnavailablePhysicalCameras.clear();
131         return;
132     }
133 
getAvailableCount()134     int getAvailableCount() {
135         std::lock_guard<std::mutex> lock(mMutex);
136         return mOnAvailableCount;
137     }
138 
getUnavailableCount()139     int getUnavailableCount() {
140         std::lock_guard<std::mutex> lock(mMutex);
141         return mOnUnavailableCount;
142     }
143 
getCameraAccessPrioritiesChangedCount()144     int getCameraAccessPrioritiesChangedCount() {
145         std::lock_guard<std::mutex> lock(mMutex);
146         return mOnCameraAccessPrioritiesChangedCount;
147     }
148 
getPhysicalCameraAvailableCount()149     int getPhysicalCameraAvailableCount() {
150         std::lock_guard<std::mutex> lock(mMutex);
151         return mOnPhysicalCameraAvailableCount;
152     }
153 
getUnavailablePhysicalCameras()154     StringPairSet getUnavailablePhysicalCameras() {
155         std::lock_guard<std::mutex> lock(mMutex);
156         return mUnavailablePhysicalCameras;
157     }
158 
isAvailable(const char * cameraId)159     bool isAvailable(const char* cameraId) {
160         std::lock_guard<std::mutex> lock(mMutex);
161         if (mAvailableMap.count(cameraId) == 0) {
162             return false;
163         }
164         return mAvailableMap[cameraId];
165     }
166 
167   private:
168     std::mutex mMutex;
169     int mOnAvailableCount = 0;
170     int mOnUnavailableCount = 0;
171     int mOnCameraAccessPrioritiesChangedCount = 0;
172     int mOnPhysicalCameraAvailableCount = 0;
173     std::map<std::string, bool> mAvailableMap;
174     StringPairSet mUnavailablePhysicalCameras;
175 };
176 
177 class CameraDeviceListener {
178   public:
onDisconnected(void * obj,ACameraDevice * device)179     static void onDisconnected(void* obj, ACameraDevice* device) {
180         ALOGV("Camera %s is disconnected!", ACameraDevice_getId(device));
181         if (obj == nullptr) {
182             return;
183         }
184         CameraDeviceListener* thiz = reinterpret_cast<CameraDeviceListener*>(obj);
185         std::lock_guard<std::mutex> lock(thiz->mMutex);
186         thiz->mOnDisconnect++;
187         return;
188     }
189 
onError(void * obj,ACameraDevice * device,int errorCode)190     static void onError(void* obj, ACameraDevice* device, int errorCode) {
191         ALOGV("Camera %s receive error %d!", ACameraDevice_getId(device), errorCode);
192         if (obj == nullptr) {
193             return;
194         }
195         CameraDeviceListener* thiz = reinterpret_cast<CameraDeviceListener*>(obj);
196         std::lock_guard<std::mutex> lock(thiz->mMutex);
197         thiz->mOnError++;
198         thiz->mLatestError = errorCode;
199         return;
200     }
201 
202   private:
203     std::mutex mMutex;
204     int mOnDisconnect = 0;
205     int mOnError = 0;
206     int mLatestError = 0;
207 };
208 
209 class CaptureSessionListener {
210 
211   public:
onClosed(void * obj,ACameraCaptureSession * session)212     static void onClosed(void* obj, ACameraCaptureSession *session) {
213         // TODO: might want an API to query cameraId even session is closed?
214         ALOGV("Session %p is closed!", session);
215         if (obj == nullptr) {
216             return;
217         }
218         CaptureSessionListener* thiz = reinterpret_cast<CaptureSessionListener*>(obj);
219         std::lock_guard<std::mutex> lock(thiz->mMutex);
220         thiz->mIsClosed = true;
221         thiz->mOnClosed++; // Should never > 1
222     }
223 
onReady(void * obj,ACameraCaptureSession * session)224     static void onReady(void* obj, ACameraCaptureSession *session) {
225         ALOGV("%s", __FUNCTION__);
226         if (obj == nullptr) {
227             return;
228         }
229         CaptureSessionListener* thiz = reinterpret_cast<CaptureSessionListener*>(obj);
230         std::lock_guard<std::mutex> lock(thiz->mMutex);
231         ACameraDevice* device = nullptr;
232         camera_status_t ret = ACameraCaptureSession_getDevice(session, &device);
233         // There will be one onReady fired after session closed
234         if (ret != ACAMERA_OK && !thiz->mIsClosed) {
235             ALOGE("%s Getting camera device from session callback failed!",
236                     __FUNCTION__);
237             thiz->mInError = true;
238         }
239         ALOGV("Session for camera %s is ready!", ACameraDevice_getId(device));
240         thiz->mIsIdle = true;
241         thiz->mOnReady++;
242     }
243 
onWindowPrepared(void * obj,ACameraWindowType * anw,ACameraCaptureSession * session)244     static void onWindowPrepared(
245             void* obj, ACameraWindowType* anw, ACameraCaptureSession* session) {
246         ALOGV("%s", __FUNCTION__);
247         if (obj == nullptr) {
248             ALOGE("%s ctx ptr is null ?", __FUNCTION__);
249             return;
250         }
251         CaptureSessionListener* thiz = reinterpret_cast<CaptureSessionListener*>(obj);
252         std::lock_guard<std::mutex> lock(thiz->mMutex);
253         // Reduce the pending prepared count of anw by 1. If count is  0, remove the key.
254         if(thiz->mPendingPreparedCbs.find(anw) == thiz->mPendingPreparedCbs.end()) {
255             ALOGE("%s: ANW %p was not being prepared at all ?", __FUNCTION__, anw);
256             return;
257         }
258         if (thiz->mPendingPreparedCbs[anw] == 0) {
259             ALOGE("%s: ANW %p pending prepared cbs is already 0", __FUNCTION__, anw);
260             return;
261         }
262         thiz->mPendingPreparedCbs[anw]--;
263         if (thiz->mPendingPreparedCbs[anw] == 0) {
264             thiz->mPendingPreparedCbs.erase(anw);
265         }
266     }
onActive(void * obj,ACameraCaptureSession * session)267     static void onActive(void* obj, ACameraCaptureSession* session) {
268         ALOGV("%s", __FUNCTION__);
269         if (obj == nullptr) {
270             return;
271         }
272         CaptureSessionListener* thiz = reinterpret_cast<CaptureSessionListener*>(obj);
273         std::lock_guard<std::mutex> lock(thiz->mMutex);
274         ACameraDevice* device = nullptr;
275         camera_status_t ret = ACameraCaptureSession_getDevice(session, &device);
276         if (ret != ACAMERA_OK) {
277             ALOGE("%s Getting camera device from session callback failed!",
278                     __FUNCTION__);
279             thiz->mInError = true;
280         }
281         ALOGV("Session for camera %s is busy!", ACameraDevice_getId(device));
282         thiz->mIsIdle = false;
283         thiz->mOnActive;
284     }
gotAllPreparedCallbacksWithErrorLog()285     bool gotAllPreparedCallbacksWithErrorLog() {
286         std::lock_guard<std::mutex> lock(mMutex);
287         bool ret = (mPendingPreparedCbs.size() == 0);
288         if (!ret) {
289             ALOGE("%s: mPendingPreparedCbs has the following expected callbacks", __FUNCTION__);
290             for (auto pair : mPendingPreparedCbs) {
291                 ALOGE("%s: ANW: %p : pending callbacks %d", __FUNCTION__, pair.first, pair.second);
292             }
293         }
294         return ret;
295     }
296 
incPendingPrepared(ANativeWindow * anw)297     void incPendingPrepared(ANativeWindow *anw) {
298         std::lock_guard<std::mutex> lock(mMutex);
299         if ((mPendingPreparedCbs.find(anw) == mPendingPreparedCbs.end())) {
300             mPendingPreparedCbs[anw] = 1;
301             return;
302         }
303         mPendingPreparedCbs[anw]++;
304     }
isClosed()305     bool isClosed() {
306         std::lock_guard<std::mutex> lock(mMutex);
307         return mIsClosed;
308     }
309 
isIdle()310     bool isIdle() {
311         std::lock_guard<std::mutex> lock(mMutex);
312         return mIsIdle;
313     }
314 
isInError()315     bool isInError() {
316         std::lock_guard<std::mutex> lock(mMutex);
317         return mInError;
318     }
319 
onClosedCount()320     int onClosedCount()  {
321         std::lock_guard<std::mutex> lock(mMutex);
322         return mOnClosed;
323     }
324 
onReadyCount()325     int onReadyCount()  {
326         std::lock_guard<std::mutex> lock(mMutex);
327         return mOnReady;
328     }
329 
onActiveCount()330     int onActiveCount()  {
331         std::lock_guard<std::mutex> lock(mMutex);
332         return mOnActive;
333     }
334 
reset()335     void reset() {
336         std::lock_guard<std::mutex> lock(mMutex);
337         mIsClosed = false;
338         mIsIdle = true;
339         mInError = false;
340         mOnClosed = 0;
341         mOnReady = 0;
342         mOnActive = 0;
343     }
344 
345   private:
346     std::mutex mMutex;
347     bool mIsClosed = false;
348     bool mIsIdle = true;
349     bool mInError = false; // should always stay false
350     int mOnClosed = 0;
351     int mOnReady = 0;
352     int mOnActive = 0;
353     // ANativeWindow -> # expected callbacks
354     std::unordered_map<ANativeWindow *, int> mPendingPreparedCbs;
355 };
356 
357 class CaptureResultListener {
358   public:
~CaptureResultListener()359     ~CaptureResultListener() {
360         std::unique_lock<std::mutex> l(mMutex);
361         clearSavedRequestsLocked();
362         mCompletedFrameNumbers.clear();
363         mStartedFrameNumbers.clear();
364         clearFailedLostFrameNumbersLocked();
365     }
366 
onCaptureStart(void *,ACameraCaptureSession *,const ACaptureRequest *,int64_t)367     static void onCaptureStart(void* /*obj*/, ACameraCaptureSession* /*session*/,
368             const ACaptureRequest* /*request*/, int64_t /*timestamp*/) {
369         //Not used for now
370     }
371 
onCaptureStartV2(void * obj,ACameraCaptureSession *,const ACaptureRequest *,int64_t,int64_t frameNumber)372     static void onCaptureStartV2(void* obj, ACameraCaptureSession* /*session*/,
373             const ACaptureRequest* /*request*/, int64_t /*timestamp*/, int64_t frameNumber) {
374         if ((obj == nullptr) || (frameNumber < 0)) {
375             return;
376         }
377         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
378         std::lock_guard<std::mutex> lock(thiz->mMutex);
379 
380         thiz->mStartedFrameNumbers.insert(frameNumber);
381         thiz->mStartCondition.notify_one();
382     }
383 
onCaptureProgressed(void *,ACameraCaptureSession *,ACaptureRequest *,const ACameraMetadata *)384     static void onCaptureProgressed(void* /*obj*/, ACameraCaptureSession* /*session*/,
385             ACaptureRequest* /*request*/, const ACameraMetadata* /*result*/) {
386         //Not used for now
387     }
388 
onCaptureCompleted(void * obj,ACameraCaptureSession *,ACaptureRequest * request,const ACameraMetadata * result)389     static void onCaptureCompleted(void* obj, ACameraCaptureSession* /*session*/,
390             ACaptureRequest* request, const ACameraMetadata* result) {
391         ALOGV("%s", __FUNCTION__);
392         if ((obj == nullptr) || (result == nullptr)) {
393             return;
394         }
395         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
396         std::lock_guard<std::mutex> lock(thiz->mMutex);
397         ACameraMetadata_const_entry entry;
398         auto ret = ACameraMetadata_getConstEntry(result, ACAMERA_SYNC_FRAME_NUMBER, &entry);
399         if (ret != ACAMERA_OK) {
400             ALOGE("Error: Sync frame number missing from result!");
401             return;
402         }
403 
404         ACameraMetadata* copy = ACameraMetadata_copy(result);
405         ACameraMetadata_const_entry entryCopy;
406         ret = ACameraMetadata_getConstEntry(copy, ACAMERA_SYNC_FRAME_NUMBER, &entryCopy);
407         if (ret != ACAMERA_OK) {
408             ALOGE("Error: Sync frame number missing from result copy!");
409             return;
410         }
411 
412         if (entry.data.i64[0] != entryCopy.data.i64[0]) {
413             ALOGE("Error: Sync frame number %" PRId64 " mismatch result copy %" PRId64,
414                     entry.data.i64[0], entryCopy.data.i64[0]);
415             return;
416         }
417         ACameraMetadata_free(copy);
418 
419         if (thiz->mSaveCompletedRequests) {
420             thiz->mCompletedRequests.push_back(ACaptureRequest_copy(request));
421         }
422 
423         thiz->mCompletedFrameNumbers.insert(entry.data.i64[0]);
424         thiz->mResultCondition.notify_one();
425     }
426 
onLogicalCameraCaptureCompleted(void * obj,ACameraCaptureSession *,ACaptureRequest * request,const ACameraMetadata * result,size_t physicalResultCount,const char ** physicalCameraIds,const ACameraMetadata ** physicalResults)427     static void onLogicalCameraCaptureCompleted(void* obj, ACameraCaptureSession* /*session*/,
428             ACaptureRequest* request, const ACameraMetadata* result,
429             size_t physicalResultCount, const char** physicalCameraIds,
430             const ACameraMetadata** physicalResults) {
431         ALOGV("%s", __FUNCTION__);
432         if ((obj == nullptr) || (result == nullptr)) {
433             return;
434         }
435         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
436         std::lock_guard<std::mutex> lock(thiz->mMutex);
437         ACameraMetadata_const_entry entry;
438         auto ret = ACameraMetadata_getConstEntry(result, ACAMERA_SYNC_FRAME_NUMBER, &entry);
439         if (ret != ACAMERA_OK) {
440             ALOGE("Error: Sync frame number missing from result!");
441             return;
442         }
443 
444         ACameraMetadata* copy = ACameraMetadata_copy(result);
445         ACameraMetadata_const_entry entryCopy;
446         ret = ACameraMetadata_getConstEntry(copy, ACAMERA_SYNC_FRAME_NUMBER, &entryCopy);
447         if (ret != ACAMERA_OK) {
448             ALOGE("Error: Sync frame number missing from result copy!");
449             return;
450         }
451 
452         if (entry.data.i64[0] != entryCopy.data.i64[0]) {
453             ALOGE("Error: Sync frame number %" PRId64 " mismatch result copy %" PRId64,
454                     entry.data.i64[0], entryCopy.data.i64[0]);
455             return;
456         }
457 
458         if (thiz->mRegisteredPhysicalIds.size() != physicalResultCount) {
459             ALOGE("Error: Number of registered physical camera Ids %zu is different than received"
460                     " physical camera Ids %zu", thiz->mRegisteredPhysicalIds.size(),
461                     physicalResultCount);
462             return;
463         }
464         for (size_t i = 0; i < physicalResultCount; i++) {
465             if (physicalCameraIds[i] == nullptr) {
466                 ALOGE("Error: Invalid physical camera id in capture result");
467                 return;
468             }
469             if (physicalResults[i] == nullptr) {
470                 ALOGE("Error: Invalid physical camera metadata in capture result");
471                 return;
472             }
473             ACameraMetadata_const_entry physicalEntry;
474             auto ret = ACameraMetadata_getConstEntry(physicalResults[i], ACAMERA_SYNC_FRAME_NUMBER,
475                     &physicalEntry);
476             if (ret != ACAMERA_OK) {
477                 ALOGE("Error: Sync frame number missing from physical camera result metadata!");
478                 return;
479             }
480             if (physicalEntry.data.i64[0] != entryCopy.data.i64[0]) {
481                 ALOGE("Error: Physical camera sync frame number %" PRId64
482                         " mismatch result copy %" PRId64,
483                         physicalEntry.data.i64[0], entryCopy.data.i64[0]);
484                 return;
485             }
486 
487             auto foundId = std::find(thiz->mRegisteredPhysicalIds.begin(),
488                     thiz->mRegisteredPhysicalIds.end(), physicalCameraIds[i]);
489             if (foundId == thiz->mRegisteredPhysicalIds.end()) {
490                 ALOGE("Error: Returned physical camera Id %s is not registered",
491                         physicalCameraIds[i]);
492                 return;
493             }
494         }
495         ACameraMetadata_free(copy);
496 
497         if (thiz->mSaveCompletedRequests) {
498             thiz->mCompletedRequests.push_back(ACaptureRequest_copy(request));
499         }
500 
501         thiz->mCompletedFrameNumbers.insert(entry.data.i64[0]);
502         thiz->mResultCondition.notify_one();
503     }
504 
onCaptureFailed(void * obj,ACameraCaptureSession *,ACaptureRequest *,ACameraCaptureFailure * failure)505     static void onCaptureFailed(void* obj, ACameraCaptureSession* /*session*/,
506             ACaptureRequest* /*request*/, ACameraCaptureFailure* failure) {
507         ALOGV("%s", __FUNCTION__);
508         if ((obj == nullptr) || (failure == nullptr)) {
509             return;
510         }
511         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
512         std::lock_guard<std::mutex> lock(thiz->mMutex);
513         thiz->mFailedFrameNumbers.insert(failure->frameNumber);
514         thiz->mResultCondition.notify_one();
515     }
516 
onLogicalCameraCaptureFailed(void * obj,ACameraCaptureSession *,ACaptureRequest *,ALogicalCameraCaptureFailure * failure)517     static void onLogicalCameraCaptureFailed(void* obj, ACameraCaptureSession* /*session*/,
518             ACaptureRequest* /*request*/, ALogicalCameraCaptureFailure* failure) {
519         ALOGV("%s", __FUNCTION__);
520         if ((obj == nullptr) || (failure == nullptr)) {
521             return;
522         }
523         if (failure->physicalCameraId != nullptr) {
524             ALOGV("%s: physicalCameraId: %s", __FUNCTION__, failure->physicalCameraId);
525         }
526         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
527         std::lock_guard<std::mutex> lock(thiz->mMutex);
528         thiz->mFailedFrameNumbers.insert(failure->captureFailure.frameNumber);
529         thiz->mResultCondition.notify_one();
530     }
531 
onCaptureSequenceCompleted(void * obj,ACameraCaptureSession *,int sequenceId,int64_t frameNumber)532     static void onCaptureSequenceCompleted(void* obj, ACameraCaptureSession* /*session*/,
533             int sequenceId, int64_t frameNumber) {
534         ALOGV("%s", __FUNCTION__);
535         if (obj == nullptr) {
536             return;
537         }
538         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
539         std::lock_guard<std::mutex> lock(thiz->mMutex);
540         thiz->mLastSequenceIdCompleted = sequenceId;
541         thiz->mLastSequenceFrameNumber = frameNumber;
542         thiz->mResultCondition.notify_one();
543     }
544 
onCaptureSequenceAborted(void *,ACameraCaptureSession *,int)545     static void onCaptureSequenceAborted(void* /*obj*/, ACameraCaptureSession* /*session*/,
546             int /*sequenceId*/) {
547         //Not used for now
548     }
549 
onCaptureBufferLost(void * obj,ACameraCaptureSession *,ACaptureRequest *,ANativeWindow *,int64_t frameNumber)550     static void onCaptureBufferLost(void* obj, ACameraCaptureSession* /*session*/,
551             ACaptureRequest* /*request*/, ANativeWindow* /*window*/, int64_t frameNumber) {
552         ALOGV("%s", __FUNCTION__);
553         if (obj == nullptr) {
554             return;
555         }
556         CaptureResultListener* thiz = reinterpret_cast<CaptureResultListener*>(obj);
557         std::lock_guard<std::mutex> lock(thiz->mMutex);
558         thiz->mBufferLostFrameNumbers.insert(frameNumber);
559         thiz->mResultCondition.notify_one();
560     }
561 
getCaptureSequenceLastFrameNumber(int64_t sequenceId,uint32_t timeoutSec)562     int64_t getCaptureSequenceLastFrameNumber(int64_t sequenceId, uint32_t timeoutSec) {
563         int64_t ret = -1;
564         std::unique_lock<std::mutex> l(mMutex);
565 
566         while (mLastSequenceIdCompleted != sequenceId) {
567             auto timeout = std::chrono::system_clock::now() +
568                            std::chrono::seconds(timeoutSec);
569             if (std::cv_status::timeout == mResultCondition.wait_until(l, timeout)) {
570                 break;
571             }
572         }
573 
574         if (mLastSequenceIdCompleted == sequenceId) {
575             ret = mLastSequenceFrameNumber;
576         }
577 
578         return ret;
579     }
580 
waitForFrameNumber(int64_t frameNumber,uint32_t timeoutSec)581     bool waitForFrameNumber(int64_t frameNumber, uint32_t timeoutSec) {
582         bool ret = false;
583         std::unique_lock<std::mutex> l(mMutex);
584 
585         while ((mCompletedFrameNumbers.find(frameNumber) == mCompletedFrameNumbers.end()) &&
586                 !checkForFailureOrLossLocked(frameNumber)) {
587             auto timeout = std::chrono::system_clock::now() +
588                            std::chrono::seconds(timeoutSec);
589             if (std::cv_status::timeout == mResultCondition.wait_until(l, timeout)) {
590                 break;
591             }
592         }
593 
594         if ((mCompletedFrameNumbers.find(frameNumber) != mCompletedFrameNumbers.end()) ||
595                 checkForFailureOrLossLocked(frameNumber)) {
596             ret = true;
597         }
598 
599         return ret;
600     }
601 
waitForFrameNumberStarted(int64_t frameNumber,uint32_t timeoutSec)602     bool waitForFrameNumberStarted(int64_t frameNumber, uint32_t timeoutSec) {
603         bool ret = false;
604         std::unique_lock<std::mutex> l(mMutex);
605 
606         while ((mStartedFrameNumbers.find(frameNumber) == mStartedFrameNumbers.end())) {
607             auto timeout = std::chrono::system_clock::now() +
608                            std::chrono::seconds(timeoutSec);
609             if (std::cv_status::timeout == mStartCondition.wait_until(l, timeout)) {
610                 break;
611             }
612         }
613 
614         if ((mStartedFrameNumbers.find(frameNumber) != mStartedFrameNumbers.end())) {
615             ret = true;
616         }
617 
618         return ret;
619     }
620 
setRequestSave(bool enable)621     void setRequestSave(bool enable) {
622         std::unique_lock<std::mutex> l(mMutex);
623         if (!enable) {
624             clearSavedRequestsLocked();
625         }
626         mSaveCompletedRequests = enable;
627     }
628 
629     // The lifecycle of returned ACaptureRequest* is still managed by CaptureResultListener
getCompletedRequests(std::vector<ACaptureRequest * > * out)630     void getCompletedRequests(std::vector<ACaptureRequest*>* out) {
631         std::unique_lock<std::mutex> l(mMutex);
632         *out = mCompletedRequests;
633     }
634 
registerPhysicalResults(size_t physicalIdCnt,const char * const * physicalOutputs)635     void registerPhysicalResults(size_t physicalIdCnt, const char*const* physicalOutputs) {
636         std::unique_lock<std::mutex> l(mMutex);
637         mRegisteredPhysicalIds.clear();
638         for (size_t i = 0; i < physicalIdCnt; i++) {
639             mRegisteredPhysicalIds.push_back(physicalOutputs[i]);
640         }
641     }
642 
checkForFailureOrLoss(int64_t frameNumber)643     bool checkForFailureOrLoss(int64_t frameNumber) {
644         std::lock_guard<std::mutex> lock(mMutex);
645         return checkForFailureOrLossLocked(frameNumber);
646     }
647 
reset()648     void reset() {
649         std::lock_guard<std::mutex> lock(mMutex);
650         mLastSequenceIdCompleted = -1;
651         mLastSequenceFrameNumber = -1;
652         mSaveCompletedRequests = false;
653         clearSavedRequestsLocked();
654         mCompletedFrameNumbers.clear();
655         clearFailedLostFrameNumbersLocked();
656     }
657 
658   private:
659     std::mutex mMutex;
660     std::condition_variable mResultCondition;
661     std::condition_variable mStartCondition;
662     int mLastSequenceIdCompleted = -1;
663     int64_t mLastSequenceFrameNumber = -1;
664     std::set<int64_t> mCompletedFrameNumbers;
665     std::set<int64_t> mStartedFrameNumbers;
666     std::set<int64_t> mFailedFrameNumbers, mBufferLostFrameNumbers;
667     bool    mSaveCompletedRequests = false;
668     std::vector<ACaptureRequest*> mCompletedRequests;
669     // Registered physical camera Ids that are being requested upon.
670     std::vector<std::string> mRegisteredPhysicalIds;
671 
clearSavedRequestsLocked()672     void clearSavedRequestsLocked() {
673         for (ACaptureRequest* req : mCompletedRequests) {
674             ACaptureRequest_free(req);
675         }
676         mCompletedRequests.clear();
677     }
678 
clearFailedLostFrameNumbersLocked()679     void clearFailedLostFrameNumbersLocked() {
680         mFailedFrameNumbers.clear();
681         mBufferLostFrameNumbers.clear();
682     }
683 
checkForFailureOrLossLocked(int64_t frameNumber)684     bool checkForFailureOrLossLocked(int64_t frameNumber) {
685         return (mFailedFrameNumbers.find(frameNumber) != mFailedFrameNumbers.end()) ||
686                 (mBufferLostFrameNumbers.find(frameNumber) != mBufferLostFrameNumbers.end());
687     }
688 };
689 
690 class ImageReaderListener {
691   public:
ImageReaderListener()692     ImageReaderListener() {
693         mBufferTs.insert(mLastBufferTs);
694     }
695 
696     // count, acquire, validate, and delete AImage when a new image is available
validateImageCb(void * obj,AImageReader * reader)697     static void validateImageCb(void* obj, AImageReader* reader) {
698         ALOGV("%s", __FUNCTION__);
699         if (obj == nullptr) {
700             return;
701         }
702         ImageReaderListener* thiz = reinterpret_cast<ImageReaderListener*>(obj);
703         std::lock_guard<std::mutex> lock(thiz->mMutex);
704         thiz->mOnImageAvailableCount++;
705 
706         AImage* img = nullptr;
707         media_status_t ret = AImageReader_acquireNextImage(reader, &img);
708         if (ret != AMEDIA_OK || img == nullptr) {
709             ALOGE("%s: acquire image from reader %p failed! ret: %d, img %p",
710                     __FUNCTION__, reader, ret, img);
711             return;
712         }
713 
714         // TODO: validate image content
715         int32_t format = -1;
716         ret = AImage_getFormat(img, &format);
717         if (ret != AMEDIA_OK || format == -1) {
718             ALOGE("%s: get format for image %p failed! ret: %d, format %d",
719                     __FUNCTION__, img, ret, format);
720         }
721 
722         // Save jpeg to SD card
723         if (thiz->mDumpFilePathBase && format == AIMAGE_FORMAT_JPEG) {
724             int32_t numPlanes = 0;
725             ret = AImage_getNumberOfPlanes(img, &numPlanes);
726             if (ret != AMEDIA_OK || numPlanes != 1) {
727                 ALOGE("%s: get numPlanes for image %p failed! ret: %d, numPlanes %d",
728                         __FUNCTION__, img, ret, numPlanes);
729                 AImage_delete(img);
730                 return;
731             }
732 
733             int32_t width = -1, height = -1;
734             ret = AImage_getWidth(img, &width);
735             if (ret != AMEDIA_OK || width <= 0) {
736                 ALOGE("%s: get width for image %p failed! ret: %d, width %d",
737                         __FUNCTION__, img, ret, width);
738                 AImage_delete(img);
739                 return;
740             }
741 
742             ret = AImage_getHeight(img, &height);
743             if (ret != AMEDIA_OK || height <= 0) {
744                 ALOGE("%s: get height for image %p failed! ret: %d, height %d",
745                         __FUNCTION__, img, ret, height);
746                 AImage_delete(img);
747                 return;
748             }
749 
750             uint8_t* data = nullptr;
751             int dataLength = 0;
752             ret =  AImage_getPlaneData(img, /*planeIdx*/0, &data, &dataLength);
753             if (ret != AMEDIA_OK || data == nullptr || dataLength <= 0) {
754                 ALOGE("%s: get jpeg data for image %p failed! ret: %d, data %p, len %d",
755                         __FUNCTION__, img, ret, data, dataLength);
756                 AImage_delete(img);
757                 return;
758             }
759 
760 #if 0
761             char dumpFilePath[512];
762             sprintf(dumpFilePath, "%s/%dx%d.jpg", thiz->mDumpFilePathBase, width, height);
763             ALOGI("Writing jpeg file to %s", dumpFilePath);
764             FILE* file = fopen(dumpFilePath,"w+");
765 
766             if (file != nullptr) {
767                 fwrite(data, 1, dataLength, file);
768                 fflush(file);
769                 fclose(file);
770             }
771 #endif
772         }
773 
774         AImage_delete(img);
775     }
776 
777     // count, acquire image but not delete the image
acquireImageCb(void * obj,AImageReader * reader)778     static void acquireImageCb(void* obj, AImageReader* reader) {
779         ALOGV("%s", __FUNCTION__);
780         if (obj == nullptr) {
781             return;
782         }
783         ImageReaderListener* thiz = reinterpret_cast<ImageReaderListener*>(obj);
784         std::lock_guard<std::mutex> lock(thiz->mMutex);
785         thiz->mOnImageAvailableCount++;
786 
787         // Acquire, but not closing.
788         AImage* img = nullptr;
789         media_status_t ret = AImageReader_acquireNextImage(reader, &img);
790         if (ret != AMEDIA_OK || img == nullptr) {
791             ALOGE("%s: acquire image from reader %p failed! ret: %d, img %p",
792                     __FUNCTION__, reader, ret, img);
793             return;
794         }
795         return;
796     }
797 
onImageAvailableCount()798     int onImageAvailableCount() {
799         std::lock_guard<std::mutex> lock(mMutex);
800         return mOnImageAvailableCount;
801     }
802 
setDumpFilePathBase(const char * path)803     void setDumpFilePathBase(const char* path) {
804         std::lock_guard<std::mutex> lock(mMutex);
805         mDumpFilePathBase = path;
806     }
807 
808     // acquire image, query the corresponding timestamp but not delete the image
signalImageCb(void * obj,AImageReader * reader)809     static void signalImageCb(void* obj, AImageReader* reader) {
810         ALOGV("%s", __FUNCTION__);
811         if (obj == nullptr) {
812             return;
813         }
814         ImageReaderListener* thiz = reinterpret_cast<ImageReaderListener*>(obj);
815         std::lock_guard<std::mutex> lock(thiz->mMutex);
816 
817         AImage* img = nullptr;
818         media_status_t ret = AImageReader_acquireNextImage(reader, &img);
819         if (ret != AMEDIA_OK || img == nullptr) {
820             ALOGE("%s: acquire image from reader %p failed! ret: %d, img %p",
821                     __FUNCTION__, reader, ret, img);
822             thiz->mBufferCondition.notify_one();
823             return;
824         }
825 
826         int64_t currentTs = -1;
827         ret = AImage_getTimestamp(img, &currentTs);
828         if (ret != AMEDIA_OK || currentTs == -1) {
829             ALOGE("%s: acquire image from reader %p failed! ret: %d", __FUNCTION__, reader, ret);
830             AImage_delete(img);
831             thiz->mBufferCondition.notify_one();
832             return;
833         }
834 
835         thiz->mBufferTs.insert(currentTs);
836         thiz->mBufferCondition.notify_one();
837         return;
838     }
839 
waitForNextBuffer(uint32_t timeoutSec)840     bool waitForNextBuffer(uint32_t timeoutSec) {
841         bool ret = false;
842         std::unique_lock<std::mutex> l(mMutex);
843 
844         auto it = mBufferTs.find(mLastBufferTs);
845         if (it == mBufferTs.end()) {
846             ALOGE("%s: Last buffer timestamp: %" PRId64 " not found!", __FUNCTION__, mLastBufferTs);
847             return false;
848         }
849         it++;
850 
851         if (it == mBufferTs.end()) {
852             auto timeout = std::chrono::system_clock::now() + std::chrono::seconds(timeoutSec);
853             if (std::cv_status::no_timeout == mBufferCondition.wait_until(l, timeout)) {
854                 it = mBufferTs.find(mLastBufferTs);
855                 it++;
856             }
857         }
858 
859         if (it != mBufferTs.end()) {
860             mLastBufferTs = *it;
861             ret = true;
862         }
863 
864         return ret;
865     }
866 
867   private:
868     // TODO: add mReader to make sure each listener is associated to one reader?
869     std::mutex mMutex;
870     int mOnImageAvailableCount = 0;
871     const char* mDumpFilePathBase = nullptr;
872     std::condition_variable mBufferCondition;
873     int64_t mLastBufferTs = -1;
874     std::set<int64_t> mBufferTs;
875 };
876 
877 class StaticInfo {
878   public:
StaticInfo(ACameraMetadata * chars)879     explicit StaticInfo(ACameraMetadata* chars) : mChars(chars) {}
880 
isColorOutputSupported()881     bool isColorOutputSupported() {
882         return isCapabilitySupported(ACAMERA_REQUEST_AVAILABLE_CAPABILITIES_BACKWARD_COMPATIBLE);
883     }
884 
isCapabilitySupported(acamera_metadata_enum_android_request_available_capabilities_t cap)885     bool isCapabilitySupported(acamera_metadata_enum_android_request_available_capabilities_t cap) {
886         ACameraMetadata_const_entry entry;
887         ACameraMetadata_getConstEntry(mChars, ACAMERA_REQUEST_AVAILABLE_CAPABILITIES, &entry);
888         for (uint32_t i = 0; i < entry.count; i++) {
889             if (entry.data.u8[i] == cap) {
890                 return true;
891             }
892         }
893         return false;
894     }
895 
getMinFrameDurationFor(int64_t format,int64_t width,int64_t height)896     int64_t getMinFrameDurationFor(int64_t format, int64_t width, int64_t height) {
897         int32_t minFrameDurationTag = (format == AIMAGE_FORMAT_HEIC) ?
898                 ACAMERA_HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS :
899                 (format == AIMAGE_FORMAT_DEPTH_JPEG) ?
900                 ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS :
901                 ACAMERA_SCALER_AVAILABLE_MIN_FRAME_DURATIONS;
902         return getDurationFor(minFrameDurationTag, format, width, height);
903     }
904 
getStallDurationFor(int64_t format,int64_t width,int64_t height)905     int64_t getStallDurationFor(int64_t format, int64_t width, int64_t height) {
906         int32_t stallDurationTag = (format == AIMAGE_FORMAT_HEIC) ?
907                 ACAMERA_HEIC_AVAILABLE_HEIC_STALL_DURATIONS : (format == AIMAGE_FORMAT_DEPTH_JPEG) ?
908                 ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS :
909                 ACAMERA_SCALER_AVAILABLE_STALL_DURATIONS;
910         return getDurationFor(stallDurationTag, format, width, height);
911     }
912 
getMaxSizeForFormat(int32_t format,int32_t * width,int32_t * height)913     bool getMaxSizeForFormat(int32_t format, int32_t *width, int32_t *height) {
914         ACameraMetadata_const_entry entry;
915 
916         int32_t streamConfigTag, streamConfigOutputTag;
917         switch (format) {
918             case AIMAGE_FORMAT_HEIC:
919                 streamConfigTag = ACAMERA_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS;
920                 streamConfigOutputTag = ACAMERA_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS_OUTPUT;
921                 break;
922             case AIMAGE_FORMAT_DEPTH_JPEG:
923                 streamConfigTag = ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS;
924                 streamConfigOutputTag =
925                         ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STREAM_CONFIGURATIONS_OUTPUT;
926                 break;
927             case AIMAGE_FORMAT_JPEG:
928             case AIMAGE_FORMAT_Y8:
929             default:
930                 streamConfigTag = ACAMERA_SCALER_AVAILABLE_STREAM_CONFIGURATIONS;
931                 streamConfigOutputTag = ACAMERA_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT;
932                 break;
933         }
934 
935         bool supported = false;
936         camera_status_t status = ACameraMetadata_getConstEntry(mChars, streamConfigTag, &entry);
937         if (status == ACAMERA_ERROR_METADATA_NOT_FOUND) {
938             return supported;
939         }
940 
941        int32_t w = 0, h = 0;
942         for (uint32_t i = 0; i < entry.count; i += 4) {
943             if (entry.data.i32[i] == format &&
944                     entry.data.i32[i+3] == streamConfigOutputTag &&
945                     entry.data.i32[i+1] * entry.data.i32[i+2] > w * h) {
946                 w = entry.data.i32[i+1];
947                 h = entry.data.i32[i+2];
948                 supported = true;
949             }
950         }
951 
952         if (supported) {
953             *width = w;
954             *height = h;
955         }
956         return supported;
957     }
958 
isSizeSupportedForFormat(int32_t format,int32_t width,int32_t height)959     bool isSizeSupportedForFormat(int32_t format, int32_t width, int32_t height) {
960         ACameraMetadata_const_entry entry;
961 
962         int32_t streamConfigTag, streamConfigOutputTag;
963         switch (format) {
964             case AIMAGE_FORMAT_HEIC:
965                 streamConfigTag = ACAMERA_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS;
966                 streamConfigOutputTag = ACAMERA_HEIC_AVAILABLE_HEIC_STREAM_CONFIGURATIONS_OUTPUT;
967                 break;
968             case AIMAGE_FORMAT_JPEG:
969             case AIMAGE_FORMAT_Y8:
970             default:
971                 streamConfigTag = ACAMERA_SCALER_AVAILABLE_STREAM_CONFIGURATIONS;
972                 streamConfigOutputTag = ACAMERA_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT;
973                 break;
974         }
975 
976         auto ret = ACameraMetadata_getConstEntry(mChars, streamConfigTag, &entry);
977         if (ret != ACAMERA_OK) {
978             return false;
979         }
980         for (uint32_t i = 0; i < entry.count; i += 4) {
981             if (entry.data.i32[i] == format &&
982                     entry.data.i32[i+3] == streamConfigOutputTag &&
983                     entry.data.i32[i+1] == width &&
984                     entry.data.i32[i+2] == height) {
985                 return true;
986             }
987         }
988         return false;
989     }
990   private:
getDurationFor(uint32_t tag,int64_t format,int64_t width,int64_t height)991     int64_t getDurationFor(uint32_t tag, int64_t format, int64_t width, int64_t height) {
992         if (tag != ACAMERA_SCALER_AVAILABLE_MIN_FRAME_DURATIONS &&
993                 tag != ACAMERA_SCALER_AVAILABLE_STALL_DURATIONS &&
994                 tag != ACAMERA_DEPTH_AVAILABLE_DEPTH_MIN_FRAME_DURATIONS &&
995                 tag != ACAMERA_DEPTH_AVAILABLE_DEPTH_STALL_DURATIONS &&
996                 tag != ACAMERA_HEIC_AVAILABLE_HEIC_MIN_FRAME_DURATIONS &&
997                 tag != ACAMERA_HEIC_AVAILABLE_HEIC_STALL_DURATIONS &&
998                 tag != ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_MIN_FRAME_DURATIONS &&
999                 tag != ACAMERA_DEPTH_AVAILABLE_DYNAMIC_DEPTH_STALL_DURATIONS) {
1000             return -1;
1001         }
1002         ACameraMetadata_const_entry entry;
1003         ACameraMetadata_getConstEntry(mChars, tag, &entry);
1004         for (uint32_t i = 0; i < entry.count; i += 4) {
1005             if (entry.data.i64[i] == format &&
1006                     entry.data.i64[i+1] == width &&
1007                     entry.data.i64[i+2] == height) {
1008                 return entry.data.i64[i+3];
1009             }
1010         }
1011         return -1;
1012     }
1013     const ACameraMetadata* mChars;
1014 };
1015 
1016 class PreviewTestCase {
1017   public:
~PreviewTestCase()1018     ~PreviewTestCase() {
1019         resetCamera();
1020         deInit();
1021         if (mCameraManager) {
1022             ACameraManager_delete(mCameraManager);
1023             mCameraManager = nullptr;
1024         }
1025     }
1026 
PreviewTestCase()1027     PreviewTestCase() {
1028         // create is guaranteed to succeed;
1029         createManager();
1030     }
1031 
1032     // Free all resources except camera manager
resetCamera()1033     void resetCamera() {
1034         mSessionListener.reset();
1035         mResultListener.reset();
1036         if (mSession) {
1037             ACameraCaptureSession_close(mSession);
1038             mSession = nullptr;
1039         }
1040         if (mDevice) {
1041             ACameraDevice_close(mDevice);
1042             mDevice = nullptr;
1043         }
1044         if (mImgReader) {
1045             AImageReader_delete(mImgReader);
1046             // No need to call ANativeWindow_release on imageReaderAnw
1047             mImgReaderAnw = nullptr;
1048             mImgReader = nullptr;
1049         }
1050         if (mPreviewAnw) {
1051             ANativeWindow_release(mPreviewAnw);
1052             mPreviewAnw = nullptr;
1053         }
1054         if (mOutputs) {
1055             ACaptureSessionOutputContainer_free(mOutputs);
1056             mOutputs = nullptr;
1057         }
1058         if (mPreviewOutput) {
1059             ACaptureSessionOutput_free(mPreviewOutput);
1060             mPreviewOutput = nullptr;
1061         }
1062         if (mImgReaderOutput) {
1063             ACaptureSessionOutput_free(mImgReaderOutput);
1064             mImgReaderOutput = nullptr;
1065         }
1066         if (mPreviewRequest) {
1067             ACaptureRequest_free(mPreviewRequest);
1068             mPreviewRequest = nullptr;
1069         }
1070         if (mStillRequest) {
1071             ACaptureRequest_free(mStillRequest);
1072             mStillRequest = nullptr;
1073         }
1074         if (mReqPreviewOutput) {
1075             ACameraOutputTarget_free(mReqPreviewOutput);
1076             mReqPreviewOutput = nullptr;
1077         }
1078         if (mReqImgReaderOutput) {
1079             ACameraOutputTarget_free(mReqImgReaderOutput);
1080             mReqImgReaderOutput = nullptr;
1081         }
1082 
1083         mImgReaderInited = false;
1084         mPreviewInited = false;
1085     }
1086 
initWithErrorLog()1087     camera_status_t initWithErrorLog() {
1088         return initWithErrorLog(nullptr /*env*/, nullptr /*jOverrideCameraId*/);
1089     }
1090 
initWithErrorLog(JNIEnv * env,jstring jOverrideCameraId)1091     camera_status_t initWithErrorLog(JNIEnv* env, jstring jOverrideCameraId) {
1092         camera_status_t ret = ACameraManager_getCameraIdList(
1093                 mCameraManager, &mCameraIdList);
1094         if (ret != ACAMERA_OK) {
1095             LOG_ERROR(errorString, "Get camera id list failed: ret %d", ret);
1096             return ret;
1097         }
1098 
1099         if (env != nullptr && jOverrideCameraId != nullptr) {
1100             mOverrideCameraId = env->GetStringUTFChars(jOverrideCameraId, 0);
1101         }
1102         ret = ACameraManager_registerAvailabilityCallback(mCameraManager, &mServiceCb);
1103         if (ret != ACAMERA_OK) {
1104             LOG_ERROR(errorString, "Register availability callback failed: ret %d", ret);
1105             return ret;
1106         }
1107         mMgrInited = true;
1108         mJOverrideCameraId = jOverrideCameraId;
1109         mJNIEnv = env;
1110         return ACAMERA_OK;
1111     }
1112 
deInit()1113     camera_status_t deInit () {
1114         if (!mMgrInited) {
1115             return ACAMERA_OK;
1116         }
1117 
1118         camera_status_t ret = ACameraManager_unregisterAvailabilityCallback(
1119                 mCameraManager, &mServiceCb);
1120         if (ret != ACAMERA_OK) {
1121             ALOGE("Unregister availability callback failed: ret %d", ret);
1122             return ret;
1123         }
1124 
1125         if (mCameraIdList) {
1126             ACameraManager_deleteCameraIdList(mCameraIdList);
1127             mCameraIdList = nullptr;
1128         }
1129         mMgrInited = false;
1130         if (mOverrideCameraId != nullptr && mJNIEnv != nullptr) {
1131             mJNIEnv->ReleaseStringUTFChars(mJOverrideCameraId, mOverrideCameraId);
1132             mOverrideCameraId = nullptr;
1133             mJOverrideCameraId = nullptr;
1134             mJNIEnv = nullptr;
1135         }
1136         return ACAMERA_OK;
1137     }
1138 
getNumCameras()1139     int getNumCameras() {
1140         if (!mMgrInited || !mCameraIdList) {
1141             ALOGE("%s CameraManager not inited yet.", __FUNCTION__);
1142             return -1;
1143         }
1144         if (mOverrideCameraId != nullptr) {
1145             return 1;
1146         }
1147         return mCameraIdList->numCameras;
1148     }
1149 
getCameraId(int idx)1150     const char* getCameraId(int idx) {
1151         if (!mMgrInited || !mCameraIdList || idx < 0 || idx >= mCameraIdList->numCameras) {
1152             return nullptr;
1153         }
1154         if (mOverrideCameraId != nullptr) {
1155             if (idx >= 1) {
1156                 return nullptr;
1157             } else {
1158                 return mOverrideCameraId;
1159             }
1160         }
1161         return mCameraIdList->cameraIds[idx];
1162     }
1163 
1164     // Caller is responsible to free returned characteristics metadata
getCameraChars(int idx)1165     ACameraMetadata* getCameraChars(int idx) {
1166         if (!mMgrInited || !mCameraIdList || idx < 0 || idx >= mCameraIdList->numCameras) {
1167             return nullptr;
1168         }
1169         const char* cameraId = mCameraIdList->cameraIds[idx];
1170         if (mOverrideCameraId != nullptr) {
1171             if (idx >= 1) {
1172                 return nullptr;
1173             } else {
1174                 cameraId = mOverrideCameraId;
1175             }
1176         }
1177 
1178         ACameraMetadata* chars;
1179         camera_status_t ret = ACameraManager_getCameraCharacteristics(
1180                 mCameraManager, cameraId, &chars);
1181         if (ret != ACAMERA_OK) {
1182             LOG_ERROR(errorString, "Get camera characteristics failed: ret %d", ret);
1183             return nullptr;
1184         }
1185         return chars;
1186     }
1187 
1188     // Caller is responsible to free returned characteristics metadata.
getCameraChars(const char * id)1189     ACameraMetadata* getCameraChars(const char* id) {
1190         if (!mMgrInited || id == nullptr) {
1191             return nullptr;
1192         }
1193 
1194         ACameraMetadata* chars;
1195         camera_status_t ret = ACameraManager_getCameraCharacteristics(mCameraManager, id, &chars);
1196         if (ret != ACAMERA_OK) {
1197             LOG_ERROR(errorString, "Get camera characteristics failed: ret %d", ret);
1198             return nullptr;
1199         }
1200         return chars;
1201     }
1202 
updateOutput(JNIEnv * env,ACaptureSessionOutput * output)1203     camera_status_t updateOutput(JNIEnv* env, ACaptureSessionOutput *output) {
1204         if (mSession == nullptr) {
1205             ALOGE("Testcase cannot update output configuration session %p",
1206                     mSession);
1207             return ACAMERA_ERROR_UNKNOWN;
1208         }
1209 
1210         return ACameraCaptureSession_updateSharedOutput(mSession, output);
1211     }
1212 
openCamera(const char * cameraId)1213     camera_status_t openCamera(const char* cameraId) {
1214         if (mDevice) {
1215             ALOGE("Cannot open camera before closing previously open one");
1216             return ACAMERA_ERROR_INVALID_PARAMETER;
1217         }
1218         mCameraId = cameraId;
1219         return ACameraManager_openCamera(mCameraManager, cameraId, &mDeviceCb, &mDevice);
1220     }
1221 
closeCamera()1222     camera_status_t closeCamera() {
1223         camera_status_t ret = ACameraDevice_close(mDevice);
1224         mDevice = nullptr;
1225         return ret;
1226     }
1227 
isCameraAvailable(const char * cameraId)1228     bool isCameraAvailable(const char* cameraId) {
1229         if (!mMgrInited) {
1230             ALOGE("Camera service listener has not been registered!");
1231         }
1232         return mServiceListener.isAvailable(cameraId);
1233     }
1234 
initImageReaderWithErrorLog(int32_t width,int32_t height,int32_t format,int32_t maxImages,AImageReader_ImageListener * listener)1235     media_status_t initImageReaderWithErrorLog(
1236             int32_t width, int32_t height, int32_t format, int32_t maxImages,
1237             AImageReader_ImageListener* listener) {
1238         if (mImgReader || mImgReaderAnw) {
1239             LOG_ERROR(errorString, "Cannot init image reader before closing existing one");
1240             return AMEDIA_ERROR_UNKNOWN;
1241         }
1242 
1243         media_status_t ret = initImageReaderWithErrorLog(
1244                 width, height, format, maxImages, listener, &mImgReader,
1245                 &mImgReaderAnw);
1246         if (ret != AMEDIA_OK) {
1247             return ret;
1248         }
1249 
1250         mImgReaderInited = true;
1251         return AMEDIA_OK;
1252     }
1253 
initImageReaderWithErrorLog(int32_t width,int32_t height,int32_t format,int32_t maxImages,AImageReader_ImageListener * listener,AImageReader ** imgReader,ANativeWindow ** imgReaderAnw)1254     media_status_t initImageReaderWithErrorLog(
1255             int32_t width, int32_t height, int32_t format, int32_t maxImages,
1256             AImageReader_ImageListener* listener, AImageReader **imgReader,
1257             ANativeWindow **imgReaderAnw) {
1258 
1259         media_status_t ret = AImageReader_new(
1260                 width, height, format,
1261                 maxImages, imgReader);
1262         if (ret != AMEDIA_OK) {
1263             LOG_ERROR(errorString, "Create image reader. ret %d", ret);
1264             return ret;
1265         }
1266         if (*imgReader == nullptr) {
1267             LOG_ERROR(errorString, "null image reader created");
1268             return AMEDIA_ERROR_UNKNOWN;
1269         }
1270 
1271         ret = AImageReader_setImageListener(*imgReader, listener);
1272         if (ret != AMEDIA_OK) {
1273             LOG_ERROR(errorString, "Set AImageReader listener failed. ret %d", ret);
1274             return ret;
1275         }
1276 
1277         ret = AImageReader_getWindow(*imgReader, imgReaderAnw);
1278         if (ret != AMEDIA_OK) {
1279             LOG_ERROR(errorString, "AImageReader_getWindow failed. ret %d", ret);
1280             return ret;
1281         }
1282         if (*imgReaderAnw == nullptr) {
1283             LOG_ERROR(errorString, "Null ANW from AImageReader!");
1284             return AMEDIA_ERROR_UNKNOWN;
1285         }
1286         return AMEDIA_OK;
1287     }
1288 
initPreviewAnw(JNIEnv * env,jobject jSurface)1289     ANativeWindow* initPreviewAnw(JNIEnv* env, jobject jSurface) {
1290         if (mPreviewAnw) {
1291             ALOGE("Cannot init preview twice!");
1292             return nullptr;
1293         }
1294         mPreviewAnw =  ANativeWindow_fromSurface(env, jSurface);
1295         mPreviewInited = true;
1296         return mPreviewAnw;
1297     }
1298 
createCaptureSessionWithLog(bool isPreviewShared=false,ACaptureRequest * sessionParameters=nullptr)1299     camera_status_t createCaptureSessionWithLog(bool isPreviewShared = false,
1300             ACaptureRequest *sessionParameters = nullptr) {
1301         std::vector<ACaptureSessionOutput*> extraOutputs;
1302         return createCaptureSessionWithLog(extraOutputs, isPreviewShared, sessionParameters);
1303     }
1304 
createCaptureSessionOutputContainer(const std::vector<ACaptureSessionOutput * > extraOutputs,ACaptureSessionOutputContainer ** outputs,bool isPreviewShared=false,ACaptureRequest * sessionParameters=nullptr)1305     camera_status_t createCaptureSessionOutputContainer(
1306             const std::vector<ACaptureSessionOutput*> extraOutputs,
1307             ACaptureSessionOutputContainer** outputs,
1308             bool isPreviewShared = false, ACaptureRequest *sessionParameters = nullptr) {
1309         if (!mMgrInited || (!mImgReaderInited && !mPreviewInited) || !outputs) {
1310             LOG_ERROR(errorString, "Cannot create session output container. mgrInit %d "
1311                     "readerInit %d previewInit %d outputs %p",
1312                     mMgrInited, mImgReaderInited, mPreviewInited, outputs);
1313             return ACAMERA_ERROR_UNKNOWN;
1314         }
1315 
1316         camera_status_t ret = ACaptureSessionOutputContainer_create(outputs);
1317         if (ret != ACAMERA_OK) {
1318             LOG_ERROR(errorString, "Create capture session output container failed. ret %d", ret);
1319             return ret;
1320         }
1321 
1322         if (mImgReaderInited) {
1323             ret = ACaptureSessionOutput_create(mImgReaderAnw, &mImgReaderOutput);
1324             if (ret != ACAMERA_OK || mImgReaderOutput == nullptr) {
1325                 LOG_ERROR(errorString,
1326                         "Session image reader output create fail! ret %d output %p",
1327                         ret, mImgReaderOutput);
1328                 if (ret == ACAMERA_OK) {
1329                     ret = ACAMERA_ERROR_UNKNOWN; // ret OK but output is null
1330                 }
1331                 return ret;
1332             }
1333 
1334             ret = ACaptureSessionOutputContainer_add(*outputs, mImgReaderOutput);
1335             if (ret != ACAMERA_OK) {
1336                 LOG_ERROR(errorString, "Session image reader output add failed! ret %d", ret);
1337                 return ret;
1338             }
1339         }
1340 
1341         for (auto extraOutput : extraOutputs) {
1342             ret = ACaptureSessionOutputContainer_add(*outputs, extraOutput);
1343             if (ret != ACAMERA_OK) {
1344                 LOG_ERROR(errorString, "Session image reader output add failed! ret %d", ret);
1345                 return ret;
1346             }
1347         }
1348 
1349         if (mPreviewInited) {
1350             if (isPreviewShared) {
1351                 ret = ACaptureSessionSharedOutput_create(mPreviewAnw, &mPreviewOutput);
1352             } else {
1353                 ret = ACaptureSessionOutput_create(mPreviewAnw, &mPreviewOutput);
1354             }
1355             if (ret != ACAMERA_OK || mPreviewOutput == nullptr) {
1356                 LOG_ERROR(errorString,
1357                         "Session preview output create fail! ret %d output %p",
1358                         ret, mPreviewOutput);
1359                 if (ret == ACAMERA_OK) {
1360                     ret = ACAMERA_ERROR_UNKNOWN; // ret OK but output is null
1361                 }
1362                 return ret;
1363             }
1364 
1365             ret = ACaptureSessionOutputContainer_add(*outputs, mPreviewOutput);
1366             if (ret != ACAMERA_OK) {
1367                 LOG_ERROR(errorString, "Session preview output add failed! ret %d", ret);
1368                 return ret;
1369             }
1370         }
1371         return ret;
1372     }
1373 
createCaptureSessionWithLog(const std::vector<ACaptureSessionOutput * > extraOutputs,bool isPreviewShared=false,ACaptureRequest * sessionParameters=nullptr,bool sessionConfigurationDefault=true)1374     camera_status_t createCaptureSessionWithLog(
1375             const std::vector<ACaptureSessionOutput*> extraOutputs,
1376             bool isPreviewShared = false, ACaptureRequest *sessionParameters = nullptr,
1377             bool sessionConfigurationDefault = true) {
1378         if (mSession) {
1379             LOG_ERROR(errorString, "Cannot create session before closing existing one");
1380             return ACAMERA_ERROR_UNKNOWN;
1381         }
1382 
1383         camera_status_t ret = createCaptureSessionOutputContainer(
1384                 extraOutputs, &mOutputs, isPreviewShared, sessionParameters);
1385         if (ret != ACAMERA_OK) {
1386             LOG_ERROR(errorString, "Failed to create session output container! ret %d", ret);
1387             return ret;
1388         }
1389 
1390         ret = ACameraDevice_isSessionConfigurationSupported(mDevice, mOutputs);
1391         if (ret != ACAMERA_OK && ret != ACAMERA_ERROR_UNSUPPORTED_OPERATION &&
1392                 ret != ACAMERA_ERROR_STREAM_CONFIGURE_FAIL) {
1393             LOG_ERROR(errorString, "isSessionConfigurationSupported must return either OK "
1394                     ", UNSUPPORTED_OPERATION, or STREAM_CONFIGURE_FAIL, but returns %d", ret);
1395             return ret;
1396         }
1397 
1398         // If session configuration is not supported by default, return early
1399         // when camera device doesn't explicitly claim support.
1400         if (ret != ACAMERA_OK && !sessionConfigurationDefault) {
1401             return ret;
1402         }
1403 
1404         ret = ACameraDevice_createCaptureSessionWithSessionParameters(
1405                 mDevice, mOutputs, sessionParameters, &mSessionCb, &mSession);
1406         if (ret != ACAMERA_OK || mSession == nullptr) {
1407             LOG_ERROR(errorString, "Create session for camera %s failed. ret %d session %p",
1408                     mCameraId, ret, mSession);
1409             if (ret == ACAMERA_OK) {
1410                 ret = ACAMERA_ERROR_UNKNOWN; // ret OK but session is null
1411             }
1412             return ret;
1413         }
1414 
1415         return ACAMERA_OK;
1416     }
1417 
prepareWindow(ANativeWindow * window)1418     camera_status_t prepareWindow(ANativeWindow *window) {
1419         if (mSession == nullptr) {
1420             ALOGE("%s: Called when session hasn't been configured", __FUNCTION__);
1421             return ACAMERA_ERROR_INVALID_OPERATION;
1422         }
1423         mSessionListener.incPendingPrepared(window);
1424         return ACameraCaptureSession_prepareWindow(mSession, window);
1425     }
1426 
setWindowPreparedCallback()1427     camera_status_t setWindowPreparedCallback() {
1428         if (mSession == nullptr) {
1429             ALOGE("%s: Called when session hasn't been configured", __FUNCTION__);
1430             return ACAMERA_ERROR_INVALID_OPERATION;
1431         }
1432         return ACameraCaptureSession_setWindowPreparedCallback(mSession, &mSessionListener,
1433                                                                mPreparedCb);
1434     }
1435 
gotAllPreparedCallbacksWithErrorLog()1436     bool gotAllPreparedCallbacksWithErrorLog() {
1437         return mSessionListener.gotAllPreparedCallbacksWithErrorLog();
1438     }
closeSession()1439     void closeSession() {
1440         if (mSession != nullptr) {
1441             ACameraCaptureSession_close(mSession);
1442         }
1443         if (mOutputs) {
1444             ACaptureSessionOutputContainer_free(mOutputs);
1445             mOutputs = nullptr;
1446         }
1447         if (mPreviewOutput) {
1448             ACaptureSessionOutput_free(mPreviewOutput);
1449             mPreviewOutput = nullptr;
1450         }
1451         if (mImgReaderOutput) {
1452             ACaptureSessionOutput_free(mImgReaderOutput);
1453             mImgReaderOutput = nullptr;
1454         }
1455         mSession = nullptr;
1456     }
1457 
createRequestsWithErrorLog()1458     camera_status_t createRequestsWithErrorLog() {
1459         std::vector<ACameraOutputTarget*> extraOutputs;
1460         return createRequestsWithErrorLog(extraOutputs);
1461     }
1462 
createRequestsWithErrorLog(const std::vector<ACameraOutputTarget * > extraOutputs,const ACameraIdList * physicalCameraIdList=nullptr)1463     camera_status_t createRequestsWithErrorLog(
1464                 const std::vector<ACameraOutputTarget*> extraOutputs,
1465                 const ACameraIdList* physicalCameraIdList = nullptr) {
1466         if (mPreviewRequest || mStillRequest) {
1467             LOG_ERROR(errorString, "Cannot create requests before deleteing existing one");
1468             return ACAMERA_ERROR_UNKNOWN;
1469         }
1470 
1471         if (mDevice == nullptr || (!mPreviewInited && !mImgReaderInited)) {
1472             LOG_ERROR(errorString,
1473                     "Cannot create request. device %p previewInit %d readeInit %d",
1474                     mDevice, mPreviewInited, mImgReaderInited);
1475             return ACAMERA_ERROR_UNKNOWN;
1476         }
1477 
1478         camera_status_t ret;
1479         bool usePhysicalSettings = (physicalCameraIdList != nullptr);
1480         if (mPreviewInited) {
1481             if (!usePhysicalSettings) {
1482                 ret = ACameraDevice_createCaptureRequest(
1483                         mDevice, TEMPLATE_PREVIEW, &mPreviewRequest);
1484             } else {
1485                 ret = ACameraDevice_createCaptureRequest_withPhysicalIds(
1486                         mDevice, TEMPLATE_PREVIEW, physicalCameraIdList, &mPreviewRequest);
1487             }
1488             if (ret != ACAMERA_OK) {
1489                 LOG_ERROR(errorString, "Camera %s create preview request failed. ret %d",
1490                         mCameraId, ret);
1491                 return ret;
1492             }
1493 
1494             if (usePhysicalSettings) {
1495                 for (int i = 0; i < physicalCameraIdList->numCameras; i++) {
1496                     // Check physical camera specific metadata functions.
1497                     uint8_t aeMode = ACAMERA_CONTROL_AE_MODE_ON;
1498                     ret = ACaptureRequest_setEntry_physicalCamera_u8(mPreviewRequest,
1499                             physicalCameraIdList->cameraIds[i], ACAMERA_CONTROL_AE_MODE,
1500                             1 /*count*/, &aeMode);
1501                     if (ret != ACAMERA_OK) {
1502                         LOG_ERROR(errorString,
1503                             "Error: Camera %s update AE mode key fail. ret %d",
1504                             physicalCameraIdList->cameraIds[i], ret);
1505                         return ret;
1506                     }
1507 
1508                     ACameraMetadata_const_entry entry;
1509                     ret = ACaptureRequest_getConstEntry_physicalCamera(mPreviewRequest,
1510                                 physicalCameraIdList->cameraIds[i],
1511                                 ACAMERA_CONTROL_AE_MODE, &entry);
1512                     if (ret != ACAMERA_OK) {
1513                         LOG_ERROR(errorString, "Get AE mode key for physicalCamera %s failed."
1514                                 " ret %d", physicalCameraIdList->cameraIds[i], ret);
1515                         return ret;
1516                     }
1517                     if (entry.data.u8[0] != aeMode) {
1518                         LOG_ERROR(errorString,
1519                             "Error: AE mode key is not updated. expect %d but get %d",
1520                             aeMode, entry.data.u8[0]);
1521                         return ACAMERA_ERROR_UNKNOWN;
1522                     }
1523                 }
1524             }
1525 
1526             ret = ACameraOutputTarget_create(mPreviewAnw, &mReqPreviewOutput);
1527             if (ret != ACAMERA_OK) {
1528                 LOG_ERROR(errorString,
1529                         "Camera %s create request preview output target failed. ret %d",
1530                         mCameraId, ret);
1531                 return ret;
1532             }
1533 
1534             ret = ACaptureRequest_addTarget(mPreviewRequest, mReqPreviewOutput);
1535             if (ret != ACAMERA_OK) {
1536                 LOG_ERROR(errorString, "Camera %s add preview request output failed. ret %d",
1537                         mCameraId, ret);
1538                 return ret;
1539             }
1540 
1541             // Add extraOutputs to the request
1542             for (auto extraOutput : extraOutputs) {
1543                 ret = ACaptureRequest_addTarget(mPreviewRequest, extraOutput);
1544                 if (ret != ACAMERA_OK) {
1545                     LOG_ERROR(errorString, "Camera %s add extra request output failed. ret %d",
1546                             mCameraId, ret);
1547                     return ret;
1548                 }
1549             }
1550         } else {
1551             ALOGI("Preview not inited. Will not create preview request!");
1552         }
1553 
1554         if (mImgReaderInited) {
1555             ret = ACameraDevice_createCaptureRequest(
1556                     mDevice, TEMPLATE_STILL_CAPTURE, &mStillRequest);
1557             if (ret != ACAMERA_OK) {
1558                 LOG_ERROR(errorString, "Camera %s create still request failed. ret %d",
1559                         mCameraId, ret);
1560                 return ret;
1561             }
1562 
1563             ret = ACameraOutputTarget_create(mImgReaderAnw, &mReqImgReaderOutput);
1564             if (ret != ACAMERA_OK) {
1565                 LOG_ERROR(errorString,
1566                         "Camera %s create request reader output target failed. ret %d",
1567                         mCameraId, ret);
1568                 return ret;
1569             }
1570 
1571             ret = ACaptureRequest_addTarget(mStillRequest, mReqImgReaderOutput);
1572             if (ret != ACAMERA_OK) {
1573                 LOG_ERROR(errorString, "Camera %s add still request output failed. ret %d",
1574                         mCameraId, ret);
1575                 return ret;
1576             }
1577 
1578             if (mPreviewInited) {
1579                 ret = ACaptureRequest_addTarget(mStillRequest, mReqPreviewOutput);
1580                 if (ret != ACAMERA_OK) {
1581                     LOG_ERROR(errorString,
1582                             "Camera %s add still request preview output failed. ret %d",
1583                             mCameraId, ret);
1584                     return ret;
1585                 }
1586             }
1587         } else {
1588             ALOGI("AImageReader not inited. Will not create still request!");
1589         }
1590 
1591         return ACAMERA_OK;
1592     }
1593 
1594     // The output ACaptureRequest* is still managed by testcase class
getStillRequest(ACaptureRequest ** out)1595     camera_status_t getStillRequest(ACaptureRequest** out) {
1596         if (mStillRequest == nullptr) {
1597             ALOGE("Camera %s Still capture request hasn't been created", mCameraId);
1598             return ACAMERA_ERROR_INVALID_PARAMETER;
1599         }
1600         *out = mStillRequest;
1601         return ACAMERA_OK;
1602     }
1603 
getPreviewRequest(ACaptureRequest ** out)1604     camera_status_t getPreviewRequest(ACaptureRequest** out) {
1605         if (mPreviewRequest == nullptr) {
1606             ALOGE("Camera %s Preview capture request hasn't been created", mCameraId);
1607             return ACAMERA_ERROR_INVALID_PARAMETER;
1608         }
1609         *out = mPreviewRequest;
1610         return ACAMERA_OK;
1611     }
1612 
startPreview(int * sequenceId=nullptr,size_t physicalIdCnt=0,const char * const * extraPhysicalOutputs=nullptr,bool v2Callbacks=false)1613     camera_status_t startPreview(int *sequenceId = nullptr, size_t physicalIdCnt = 0,
1614             const char*const* extraPhysicalOutputs = nullptr, bool v2Callbacks = false) {
1615         if (mSession == nullptr || mPreviewRequest == nullptr) {
1616             ALOGE("Testcase cannot start preview: session %p, preview request %p",
1617                     mSession, mPreviewRequest);
1618             return ACAMERA_ERROR_UNKNOWN;
1619         }
1620         int previewSeqId;
1621         camera_status_t ret;
1622         if (sequenceId == nullptr) {
1623             ret = ACameraCaptureSession_setRepeatingRequest(
1624                    mSession, nullptr, 1, &mPreviewRequest, &previewSeqId);
1625         } else if (physicalIdCnt == 0) {
1626             if (v2Callbacks) {
1627                 ret = ACameraCaptureSession_setRepeatingRequestV2(
1628                       mSession, &mResultCb2, 1, &mPreviewRequest, sequenceId);
1629             } else {
1630                 ret = ACameraCaptureSession_setRepeatingRequest(
1631                       mSession, &mResultCb, 1, &mPreviewRequest, sequenceId);
1632             }
1633         } else {
1634             if (extraPhysicalOutputs == nullptr) {
1635                 ALOGE("Testcase missing valid physical camera Ids for logical camera");
1636                 return ACAMERA_ERROR_INVALID_PARAMETER;
1637             }
1638             CaptureResultListener* resultListener =
1639                     static_cast<CaptureResultListener*>(mLogicalCameraResultCb.context);
1640             resultListener->registerPhysicalResults(physicalIdCnt, extraPhysicalOutputs);
1641             if (v2Callbacks) {
1642                 ret = ACameraCaptureSession_logicalCamera_setRepeatingRequestV2(
1643                         mSession, &mLogicalCameraResultCb2, 1, &mPreviewRequest, sequenceId);
1644             } else {
1645                 ret = ACameraCaptureSession_logicalCamera_setRepeatingRequest(
1646                         mSession, &mLogicalCameraResultCb, 1, &mPreviewRequest, sequenceId);
1647             }
1648         }
1649         return ret;
1650     }
1651 
startRepeatingRequest(int * sequenceId,ACaptureRequest * request,ACameraCaptureSession_captureCallbacks * resultCb)1652     camera_status_t startRepeatingRequest(int *sequenceId, ACaptureRequest *request,
1653             ACameraCaptureSession_captureCallbacks *resultCb) {
1654         if (mSession == nullptr || request == nullptr || resultCb == nullptr) {
1655             ALOGE("Testcase cannot start repeating request: session %p, request %p resultCb %p",
1656                     mSession, request, resultCb);
1657             return ACAMERA_ERROR_UNKNOWN;
1658         }
1659 
1660         return ACameraCaptureSession_setRepeatingRequest(mSession, resultCb, 1, &request,
1661                 sequenceId);
1662     }
1663 
stopPreview()1664     camera_status_t stopPreview() {
1665         if (mSession == nullptr) {
1666             ALOGE("Testcase cannot stop preview: session %p", mSession);
1667             return ACAMERA_ERROR_UNKNOWN;
1668         }
1669         return ACameraCaptureSession_stopRepeating(mSession);
1670     }
1671 
abortCaptures()1672     camera_status_t abortCaptures() {
1673         if (mSession == nullptr) {
1674             ALOGE("Testcase cannot abort session %p", mSession);
1675             return ACAMERA_ERROR_UNKNOWN;
1676         }
1677         return ACameraCaptureSession_abortCaptures(mSession);
1678     }
1679 
updateRepeatingRequest(ACaptureRequest * updatedRequest,int * sequenceId=nullptr)1680     camera_status_t updateRepeatingRequest(ACaptureRequest *updatedRequest,
1681             int *sequenceId = nullptr) {
1682         if (mSession == nullptr || updatedRequest == nullptr) {
1683             ALOGE("Testcase cannot update repeating request: session %p, updated request %p",
1684                     mSession, updatedRequest);
1685             return ACAMERA_ERROR_UNKNOWN;
1686         }
1687 
1688         int previewSeqId;
1689         camera_status_t ret;
1690         if (sequenceId == nullptr) {
1691             ret = ACameraCaptureSession_setRepeatingRequest(
1692                     mSession, nullptr, 1, &updatedRequest, &previewSeqId);
1693         } else {
1694             ret = ACameraCaptureSession_setRepeatingRequest(
1695                     mSession, &mResultCb, 1, &updatedRequest, sequenceId);
1696         }
1697         return ret;
1698     }
1699 
getCaptureSequenceLastFrameNumber(int64_t sequenceId,uint32_t timeoutSec)1700     int64_t getCaptureSequenceLastFrameNumber(int64_t sequenceId, uint32_t timeoutSec) {
1701         return mResultListener.getCaptureSequenceLastFrameNumber(sequenceId, timeoutSec);
1702     }
1703 
waitForFrameNumber(int64_t frameNumber,uint32_t timeoutSec)1704     bool waitForFrameNumber(int64_t frameNumber, uint32_t timeoutSec) {
1705         return mResultListener.waitForFrameNumber(frameNumber, timeoutSec);
1706     }
1707 
waitForFrameNumberStarted(int64_t frameNumber,uint32_t timeoutSec)1708     bool waitForFrameNumberStarted(int64_t frameNumber, uint32_t timeoutSec) {
1709         return mResultListener.waitForFrameNumberStarted(frameNumber, timeoutSec);
1710     }
1711 
takePicture()1712     camera_status_t takePicture() {
1713         if (mSession == nullptr || mStillRequest == nullptr) {
1714             ALOGE("Testcase cannot take picture: session %p, still request %p",
1715                     mSession, mStillRequest);
1716             return ACAMERA_ERROR_UNKNOWN;
1717         }
1718         int seqId;
1719         return ACameraCaptureSession_capture(
1720                 mSession, nullptr, 1, &mStillRequest, &seqId);
1721     }
1722 
capture(ACaptureRequest * request,ACameraCaptureSession_captureCallbacks * listener,int * seqId)1723     camera_status_t capture(ACaptureRequest* request,
1724             ACameraCaptureSession_captureCallbacks* listener,
1725             /*out*/int* seqId) {
1726         if (mSession == nullptr || request == nullptr) {
1727             ALOGE("Testcase cannot capture session: session %p, request %p",
1728                     mSession, request);
1729             return ACAMERA_ERROR_UNKNOWN;
1730         }
1731         return ACameraCaptureSession_capture(
1732                 mSession, listener, 1, &request, seqId);
1733     }
1734 
resetWithErrorLog()1735     camera_status_t resetWithErrorLog() {
1736         camera_status_t ret;
1737 
1738         closeSession();
1739 
1740         for (int i = 0; i < 50; i++) {
1741             usleep(100000); // sleep 100ms
1742             if (mSessionListener.isClosed()) {
1743                 ALOGI("Session take ~%d ms to close", i*100);
1744                 break;
1745             }
1746         }
1747 
1748         if (!mSessionListener.isClosed() || mSessionListener.onClosedCount() != 1) {
1749             LOG_ERROR(errorString,
1750                     "Session for camera %s close error. isClosde %d close count %d",
1751                     mCameraId, mSessionListener.isClosed(), mSessionListener.onClosedCount());
1752             return ACAMERA_ERROR_UNKNOWN;
1753         }
1754         mSessionListener.reset();
1755         mResultListener.reset();
1756 
1757         ret = closeCamera();
1758         if (ret != ACAMERA_OK) {
1759             LOG_ERROR(errorString, "Close camera device %s failure. ret %d", mCameraId, ret);
1760             return ret;
1761         }
1762 
1763         resetCamera();
1764         return ACAMERA_OK;
1765     }
1766 
getSessionListener()1767     CaptureSessionListener* getSessionListener() {
1768         return &mSessionListener;
1769     }
1770 
getCameraDevice()1771     ACameraDevice* getCameraDevice() {
1772         return mDevice;
1773     }
1774 
getPreviewOutput()1775     ACaptureSessionOutput *getPreviewOutput() {
1776         return mPreviewOutput;
1777     }
1778 
1779   private:
createManager()1780     ACameraManager* createManager() {
1781         if (!mCameraManager) {
1782             mCameraManager = ACameraManager_create();
1783         }
1784         return mCameraManager;
1785     }
1786 
1787     CameraServiceListener mServiceListener;
1788     ACameraManager_AvailabilityCallbacks mServiceCb {
1789         &mServiceListener,
1790         CameraServiceListener::onAvailable,
1791         CameraServiceListener::onUnavailable
1792     };
1793     CameraDeviceListener mDeviceListener;
1794     ACameraDevice_StateCallbacks mDeviceCb {
1795         &mDeviceListener,
1796         CameraDeviceListener::onDisconnected,
1797         CameraDeviceListener::onError
1798     };
1799     CaptureSessionListener mSessionListener;
1800     ACameraCaptureSession_stateCallbacks mSessionCb {
1801         &mSessionListener,
1802         CaptureSessionListener::onClosed,
1803         CaptureSessionListener::onReady,
1804         CaptureSessionListener::onActive
1805     };
1806 
1807     ACameraCaptureSession_prepareCallback mPreparedCb  = &CaptureSessionListener::onWindowPrepared;
1808 
1809     CaptureResultListener mResultListener;
1810     ACameraCaptureSession_captureCallbacks mResultCb {
1811         &mResultListener,
1812         CaptureResultListener::onCaptureStart,
1813         CaptureResultListener::onCaptureProgressed,
1814         CaptureResultListener::onCaptureCompleted,
1815         CaptureResultListener::onCaptureFailed,
1816         CaptureResultListener::onCaptureSequenceCompleted,
1817         CaptureResultListener::onCaptureSequenceAborted,
1818         CaptureResultListener::onCaptureBufferLost
1819     };
1820 
1821     ACameraCaptureSession_captureCallbacksV2 mResultCb2 {
1822         &mResultListener,
1823         CaptureResultListener::onCaptureStartV2,
1824         CaptureResultListener::onCaptureProgressed,
1825         CaptureResultListener::onCaptureCompleted,
1826         CaptureResultListener::onCaptureFailed,
1827         CaptureResultListener::onCaptureSequenceCompleted,
1828         CaptureResultListener::onCaptureSequenceAborted,
1829         CaptureResultListener::onCaptureBufferLost
1830     };
1831 
1832     ACameraCaptureSession_logicalCamera_captureCallbacksV2 mLogicalCameraResultCb2 {
1833         &mResultListener,
1834         CaptureResultListener::onCaptureStartV2,
1835         CaptureResultListener::onCaptureProgressed,
1836         CaptureResultListener::onLogicalCameraCaptureCompleted,
1837         CaptureResultListener::onLogicalCameraCaptureFailed,
1838         CaptureResultListener::onCaptureSequenceCompleted,
1839         CaptureResultListener::onCaptureSequenceAborted,
1840         CaptureResultListener::onCaptureBufferLost
1841     };
1842 
1843     ACameraCaptureSession_logicalCamera_captureCallbacks mLogicalCameraResultCb {
1844         &mResultListener,
1845         CaptureResultListener::onCaptureStart,
1846         CaptureResultListener::onCaptureProgressed,
1847         CaptureResultListener::onLogicalCameraCaptureCompleted,
1848         CaptureResultListener::onLogicalCameraCaptureFailed,
1849         CaptureResultListener::onCaptureSequenceCompleted,
1850         CaptureResultListener::onCaptureSequenceAborted,
1851         CaptureResultListener::onCaptureBufferLost
1852     };
1853 
1854     ACameraIdList* mCameraIdList = nullptr;
1855     ACameraDevice* mDevice = nullptr;
1856     AImageReader* mImgReader = nullptr;
1857     ANativeWindow* mImgReaderAnw = nullptr;
1858     ANativeWindow* mPreviewAnw = nullptr;
1859     ACameraManager* mCameraManager = nullptr;
1860     ACaptureSessionOutputContainer* mOutputs = nullptr;
1861     ACaptureSessionOutput* mPreviewOutput = nullptr;
1862     ACaptureSessionOutput* mImgReaderOutput = nullptr;
1863     ACameraCaptureSession* mSession = nullptr;
1864     ACaptureRequest* mPreviewRequest = nullptr;
1865     ACaptureRequest* mStillRequest = nullptr;
1866     ACameraOutputTarget* mReqPreviewOutput = nullptr;
1867     ACameraOutputTarget* mReqImgReaderOutput = nullptr;
1868     const char* mCameraId;
1869     JNIEnv* mJNIEnv = nullptr;
1870     jstring mJOverrideCameraId;
1871     const char* mOverrideCameraId = nullptr;
1872 
1873     bool mMgrInited = false; // cameraId, serviceListener
1874     bool mImgReaderInited = false;
1875     bool mPreviewInited = false;
1876 };
1877 
throwAssertionError(JNIEnv * env,const char * message)1878 jint throwAssertionError(JNIEnv* env, const char* message)
1879 {
1880     jclass assertionClass;
1881     const char* className = "junit/framework/AssertionFailedError";
1882 
1883     assertionClass = env->FindClass(className);
1884     if (assertionClass == nullptr) {
1885         ALOGE("Native throw error: cannot find class %s", className);
1886         return -1;
1887     }
1888     return env->ThrowNew(assertionClass, message);
1889 }
1890 
1891 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraManagerTest_testCameraManagerGetAndCloseNative(JNIEnv * env,jclass)1892 Java_android_hardware_camera2_cts_NativeCameraManagerTest_\
1893 testCameraManagerGetAndCloseNative(
1894         JNIEnv* env, jclass /*clazz*/) {
1895     bool pass = false;
1896     ALOGV("%s", __FUNCTION__);
1897     ACameraManager* cameraManager2 = nullptr;
1898     ACameraManager* cameraManager3 = nullptr;
1899     ACameraManager* cameraManager4 = nullptr;
1900     camera_status_t ret = ACAMERA_OK;
1901     ACameraManager* cameraManager = ACameraManager_create();
1902     if (cameraManager == nullptr) {
1903         LOG_ERROR(errorString, "ACameraManager_create returns nullptr");
1904         goto cleanup;
1905     }
1906     ACameraManager_delete(cameraManager);
1907     cameraManager = nullptr;
1908 
1909     // Test get/close multiple instances
1910     cameraManager = ACameraManager_create();
1911     cameraManager2 = ACameraManager_create();
1912     if (cameraManager2 == nullptr) {
1913         LOG_ERROR(errorString, "ACameraManager_create 2 returns nullptr");
1914         goto cleanup;
1915     }
1916     ACameraManager_delete(cameraManager);
1917     cameraManager = nullptr;
1918     cameraManager3 = ACameraManager_create();
1919     if (cameraManager3 == nullptr) {
1920         LOG_ERROR(errorString, "ACameraManager_create 3 returns nullptr");
1921         goto cleanup;
1922     }
1923     cameraManager4 = ACameraManager_create();
1924         if (cameraManager4 == nullptr) {
1925         LOG_ERROR(errorString, "ACameraManager_create 4 returns nullptr");
1926         goto cleanup;
1927     }
1928     ACameraManager_delete(cameraManager3);
1929     ACameraManager_delete(cameraManager2);
1930     ACameraManager_delete(cameraManager4);
1931 
1932     pass = true;
1933 cleanup:
1934     if (cameraManager) {
1935         ACameraManager_delete(cameraManager);
1936     }
1937     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "fail");
1938     if (!pass) {
1939         throwAssertionError(env, errorString);
1940     }
1941     return pass;
1942 }
1943 
1944 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraManagerTest_testCameraManagerGetCameraIdsNative(JNIEnv * env,jclass)1945 Java_android_hardware_camera2_cts_NativeCameraManagerTest_\
1946 testCameraManagerGetCameraIdsNative(
1947         JNIEnv* env, jclass /*clazz*/) {
1948     ALOGV("%s", __FUNCTION__);
1949     bool pass = false;
1950     ACameraManager* mgr = ACameraManager_create();
1951     ACameraIdList *cameraIdList = nullptr;
1952     camera_status_t ret = ACameraManager_getCameraIdList(mgr, &cameraIdList);
1953     if (ret != ACAMERA_OK || cameraIdList == nullptr) {
1954         LOG_ERROR(errorString, "Get camera id list failed: ret %d, cameraIdList %p",
1955                 ret, cameraIdList);
1956         goto cleanup;
1957     }
1958     ALOGI("Number of cameras: %d", cameraIdList->numCameras);
1959     for (int i = 0; i < cameraIdList->numCameras; i++) {
1960         ALOGI("Camera ID: %s", cameraIdList->cameraIds[i]);
1961     }
1962     ACameraManager_deleteCameraIdList(cameraIdList);
1963     cameraIdList = nullptr;
1964 
1965     pass = true;
1966 cleanup:
1967     if (mgr) {
1968         ACameraManager_delete(mgr);
1969     }
1970     if (cameraIdList) {
1971         ACameraManager_deleteCameraIdList(cameraIdList);
1972     }
1973     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "fail");
1974     if (!pass) {
1975         throwAssertionError(env, errorString);
1976     }
1977     return pass;
1978 }
1979 
1980 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraManagerTest_testCameraManagerExtendedAvailabilityCallbackNative(JNIEnv * env,jclass)1981 Java_android_hardware_camera2_cts_NativeCameraManagerTest_\
1982 testCameraManagerExtendedAvailabilityCallbackNative(
1983         JNIEnv* env, jclass /*clazz*/) {
1984     ALOGV("%s", __FUNCTION__);
1985     bool pass = false;
1986     ACameraManager* mgr = ACameraManager_create();
1987     ACameraIdList *cameraIdList = nullptr;
1988     camera_status_t ret = ACameraManager_getCameraIdList(mgr, &cameraIdList);
1989     int numCameras = cameraIdList->numCameras;
1990     CameraServiceListener listener;
1991     CameraServiceListener::StringPairSet unavailablePhysicalCameras;
1992     CameraServiceListener::StringPairSet physicalCameraIdPairs;
1993     ACameraManager_ExtendedAvailabilityCallbacks cbs {
1994             {
1995                 &listener,
1996                 CameraServiceListener::onAvailable,
1997                 CameraServiceListener::onUnavailable
1998             },
1999             CameraServiceListener::onCameraAccessPrioritiesChanged,
2000             CameraServiceListener::onPhysicalCameraAvailable,
2001             CameraServiceListener::onPhysicalCameraUnavailable,
2002             {}
2003     };
2004 
2005     ret = ACameraManager_registerExtendedAvailabilityCallback(mgr, &cbs);
2006     if (ret != ACAMERA_OK) {
2007         LOG_ERROR(errorString, "Register extended availability callback failed: ret %d", ret);
2008         goto cleanup;
2009     }
2010     sleep(1); // sleep a second to give some time for callbacks to happen
2011 
2012     // Should at least get onAvailable for each camera once
2013     if (listener.getAvailableCount() < numCameras) {
2014         LOG_ERROR(errorString, "Expect at least %d available callback but only got %d",
2015                 numCameras, listener.getAvailableCount());
2016         goto cleanup;
2017     }
2018 
2019     {
2020         int availablePhysicalCamera = listener.getPhysicalCameraAvailableCount();
2021         if (availablePhysicalCamera > 0) {
2022             LOG_ERROR(errorString, "Expect no available callback, but got %d",
2023                     availablePhysicalCamera);
2024         }
2025     }
2026 
2027     unavailablePhysicalCameras = listener.getUnavailablePhysicalCameras();
2028     for (int i = 0; i < numCameras; i++) {
2029         const char* cameraId = cameraIdList->cameraIds[i];
2030         if (cameraId == nullptr) {
2031             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
2032             goto cleanup;
2033         }
2034         ACameraMetadata* c;
2035         ret = ACameraManager_getCameraCharacteristics(mgr, cameraId, &c);
2036         if (ret != ACAMERA_OK || c == nullptr) {
2037             LOG_ERROR(errorString, "Get camera %s characteristics failure", cameraId);
2038             goto cleanup;
2039         }
2040         std::unique_ptr<ACameraMetadata> chars(c);
2041 
2042         size_t physicalCameraCnt = 0;
2043         const char *const* physicalCameraIds = nullptr;
2044         if (!ACameraMetadata_isLogicalMultiCamera(
2045                 chars.get(), &physicalCameraCnt, &physicalCameraIds)) {
2046             continue;
2047         }
2048         for (size_t j = 0; j < physicalCameraCnt; j++) {
2049             physicalCameraIdPairs.emplace(cameraId, physicalCameraIds[j]);
2050         }
2051     }
2052     for (const auto& unavailIdPair : unavailablePhysicalCameras) {
2053         bool validPair = false;
2054         for (const auto& idPair : physicalCameraIdPairs) {
2055             if (idPair.first == unavailIdPair.first && idPair.second == unavailIdPair.second) {
2056                 validPair = true;
2057                 break;
2058             }
2059         }
2060         if (!validPair) {
2061             LOG_ERROR(errorString, "Expect valid unavailable physical cameras, but got %s : %s",
2062                     unavailIdPair.first.c_str(), unavailIdPair.second.c_str());
2063             goto cleanup;
2064         }
2065     }
2066 
2067     ret = ACameraManager_unregisterExtendedAvailabilityCallback(mgr, &cbs);
2068     if (ret != ACAMERA_OK) {
2069         LOG_ERROR(errorString, "Unregister extended availability callback failed: ret %d", ret);
2070         goto cleanup;
2071     }
2072     pass = true;
2073 cleanup:
2074     if (cameraIdList) {
2075         ACameraManager_deleteCameraIdList(cameraIdList);
2076     }
2077     if (mgr) {
2078         ACameraManager_delete(mgr);
2079     }
2080     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2081     if (!pass) {
2082         throwAssertionError(env, errorString);
2083     }
2084     return pass;
2085 }
2086 
2087 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraManagerTest_testCameraManagerAvailabilityCallbackNative(JNIEnv * env,jclass)2088 Java_android_hardware_camera2_cts_NativeCameraManagerTest_\
2089 testCameraManagerAvailabilityCallbackNative(
2090         JNIEnv* env, jclass /*clazz*/) {
2091     ALOGV("%s", __FUNCTION__);
2092     bool pass = false;
2093     ACameraManager* mgr = ACameraManager_create();
2094     ACameraIdList *cameraIdList = nullptr;
2095     camera_status_t ret = ACameraManager_getCameraIdList(mgr, &cameraIdList);
2096     int numCameras = cameraIdList->numCameras;
2097     CameraServiceListener listener;
2098     ACameraManager_AvailabilityCallbacks cbs {
2099             &listener,
2100             CameraServiceListener::onAvailable,
2101             CameraServiceListener::onUnavailable};
2102     ret = ACameraManager_registerAvailabilityCallback(mgr, &cbs);
2103     if (ret != ACAMERA_OK) {
2104         LOG_ERROR(errorString, "Register availability callback failed: ret %d", ret);
2105         goto cleanup;
2106     }
2107     sleep(1); // sleep a second to give some time for callbacks to happen
2108 
2109     // Should at least get onAvailable for each camera once
2110     if (listener.getAvailableCount() < numCameras) {
2111         LOG_ERROR(errorString, "Expect at least %d available callback but only got %d",
2112                 numCameras, listener.getAvailableCount());
2113         goto cleanup;
2114     }
2115 
2116     ret = ACameraManager_unregisterAvailabilityCallback(mgr, &cbs);
2117     if (ret != ACAMERA_OK) {
2118         LOG_ERROR(errorString, "Unregister availability callback failed: ret %d", ret);
2119         goto cleanup;
2120     }
2121     pass = true;
2122 cleanup:
2123     if (cameraIdList) {
2124         ACameraManager_deleteCameraIdList(cameraIdList);
2125     }
2126     if (mgr) {
2127         ACameraManager_delete(mgr);
2128     }
2129     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2130     if (!pass) {
2131         throwAssertionError(env, errorString);
2132     }
2133     return pass;
2134 }
2135 
2136 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraManagerTest_testCameraManagerCharacteristicsNative(JNIEnv * env,jclass)2137 Java_android_hardware_camera2_cts_NativeCameraManagerTest_\
2138 testCameraManagerCharacteristicsNative(
2139         JNIEnv* env, jclass /*clazz*/) {
2140     ALOGV("%s", __FUNCTION__);
2141     bool pass = false;
2142     ACameraManager* mgr = ACameraManager_create();
2143     ACameraIdList *cameraIdList = nullptr;
2144     ACameraMetadata* chars = nullptr;
2145     ACameraMetadata* copy = nullptr;
2146     int numCameras = 0;
2147     camera_status_t ret = ACameraManager_getCameraIdList(mgr, &cameraIdList);
2148     if (ret != ACAMERA_OK || cameraIdList == nullptr) {
2149         LOG_ERROR(errorString, "Get camera id list failed: ret %d, cameraIdList %p",
2150                 ret, cameraIdList);
2151         goto cleanup;
2152     }
2153     numCameras = cameraIdList->numCameras;
2154 
2155     for (int i = 0; i < numCameras; i++) {
2156         ret = ACameraManager_getCameraCharacteristics(
2157                 mgr, cameraIdList->cameraIds[i], &chars);
2158         if (ret != ACAMERA_OK) {
2159             LOG_ERROR(errorString, "Get camera characteristics failed: ret %d", ret);
2160             goto cleanup;
2161         }
2162 
2163         int32_t numTags = 0;
2164         const uint32_t* tags = nullptr;
2165         ret = ACameraMetadata_getAllTags(chars, &numTags, &tags);
2166         if (ret != ACAMERA_OK) {
2167             LOG_ERROR(errorString, "Get camera characteristics tags failed: ret %d", ret);
2168             goto cleanup;
2169         }
2170 
2171         for (int tid = 0; tid < numTags; tid++) {
2172             uint32_t tagId = tags[tid];
2173             ALOGV("%s camera characteristics contains key %u", __FUNCTION__, tagId);
2174             uint32_t sectionId = tagId >> 16;
2175             if (sectionId >= ACAMERA_SECTION_COUNT && sectionId < ACAMERA_VENDOR) {
2176                 LOG_ERROR(errorString, "Unknown tagId %u, sectionId %u", tagId, sectionId);
2177                 goto cleanup;
2178             }
2179         }
2180 
2181         ACameraMetadata_const_entry entry;
2182         ret = ACameraMetadata_getConstEntry(chars, ACAMERA_REQUEST_AVAILABLE_CAPABILITIES, &entry);
2183         if (ret != ACAMERA_OK) {
2184             LOG_ERROR(errorString, "Get const available capabilities key failed. ret %d", ret);
2185             goto cleanup;
2186         }
2187 
2188         // Check the entry is actually legit
2189         if (entry.tag != ACAMERA_REQUEST_AVAILABLE_CAPABILITIES ||
2190                 entry.count == 0 || entry.type != ACAMERA_TYPE_BYTE || entry.data.i32 == nullptr) {
2191             LOG_ERROR(errorString,
2192                     "Bad available capabilities key: tag: %d (expected %d), count %u (expect > 0), "
2193                     "type %d (expected %d), data %p (expected not null)",
2194                     entry.tag, ACAMERA_REQUEST_AVAILABLE_CAPABILITIES, entry.count,
2195                     entry.type, ACAMERA_TYPE_BYTE, entry.data.i32);
2196             goto cleanup;
2197         }
2198         // All camera supports BC except depth only cameras
2199         bool supportBC = false, supportDepth = false;
2200         for (uint32_t i = 0; i < entry.count; i++) {
2201             if (entry.data.u8[i] == ACAMERA_REQUEST_AVAILABLE_CAPABILITIES_BACKWARD_COMPATIBLE) {
2202                 supportBC = true;
2203             }
2204             if (entry.data.u8[i] == ACAMERA_REQUEST_AVAILABLE_CAPABILITIES_DEPTH_OUTPUT) {
2205                 supportDepth = true;
2206             }
2207         }
2208         if (!(supportBC || supportDepth)) {
2209             LOG_ERROR(errorString, "Error: camera device %s does not support either BC or DEPTH",
2210                     cameraIdList->cameraIds[i]);
2211             goto cleanup;
2212         }
2213 
2214         // Check copy works
2215         copy = ACameraMetadata_copy(chars);
2216 
2217         // Compare copy with original
2218         ACameraMetadata_const_entry entryCopy;
2219         ret = ACameraMetadata_getConstEntry(
2220                 copy, ACAMERA_REQUEST_AVAILABLE_CAPABILITIES, &entryCopy);
2221         if (ret != ACAMERA_OK) {
2222             LOG_ERROR(errorString, "Get const available capabilities key failed. ret %d", ret);
2223             goto cleanup;
2224         }
2225         for (uint32_t i = 0; i < entry.count; i++) {
2226             if (entry.data.u8[i] != entryCopy.data.u8[i]) {
2227                 LOG_ERROR(errorString,
2228                     "Copy of available capability key[%d]: %d mismatches original %d",
2229                     i, entryCopy.data.u8[i], entry.data.u8[i]);
2230                 goto cleanup;
2231             }
2232         }
2233 
2234         // Check get unknown value fails
2235         uint32_t badTag = (uint32_t) ACAMERA_VENDOR_START - 1;
2236         ret = ACameraMetadata_getConstEntry(chars, badTag, &entry);
2237         if (ret == ACAMERA_OK) {
2238             LOG_ERROR(errorString, "Error: get unknown tag should fail!");
2239             goto cleanup;
2240         }
2241 
2242         ACameraMetadata_free(chars);
2243         ACameraMetadata_free(copy);
2244         chars = nullptr;
2245         copy = nullptr;
2246     }
2247 
2248     pass = true;
2249 cleanup:
2250     if (chars) {
2251         ACameraMetadata_free(chars);
2252     }
2253     if (copy) {
2254         ACameraMetadata_free(copy);
2255     }
2256     ACameraManager_deleteCameraIdList(cameraIdList);
2257     ACameraManager_delete(mgr);
2258     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2259     if (!pass) {
2260         throwAssertionError(env, errorString);
2261     }
2262     return pass;
2263 }
2264 
2265 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceOpenAndCloseNative(JNIEnv * env,jclass,jstring jOverrideCameraId)2266 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
2267 testCameraDeviceOpenAndCloseNative(
2268         JNIEnv* env, jclass /*clazz*/, jstring jOverrideCameraId) {
2269     ALOGV("%s", __FUNCTION__);
2270     int numCameras = 0;
2271     bool pass = false;
2272     PreviewTestCase testCase;
2273 
2274     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
2275     if (ret != ACAMERA_OK) {
2276         // Don't log error here. testcase did it
2277         goto cleanup;
2278     }
2279 
2280     numCameras = testCase.getNumCameras();
2281     if (numCameras < 0) {
2282         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
2283         goto cleanup;
2284     }
2285 
2286     for (int i = 0; i < numCameras; i++) {
2287         const char* cameraId = testCase.getCameraId(i);
2288         if (cameraId == nullptr) {
2289             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
2290             goto cleanup;
2291         }
2292 
2293         ret = testCase.openCamera(cameraId);
2294         if (ret != ACAMERA_OK) {
2295             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
2296             goto cleanup;
2297         }
2298 
2299         usleep(100000); // sleep to give some time for callbacks to happen
2300 
2301         if (testCase.isCameraAvailable(cameraId)) {
2302             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
2303             goto cleanup;
2304         }
2305 
2306         ret = testCase.closeCamera();
2307         if (ret != ACAMERA_OK) {
2308             LOG_ERROR(errorString, "Close camera device %s failure. ret %d", cameraId, ret);
2309             goto cleanup;
2310         }
2311 
2312         usleep(100000); // sleep to give some time for callbacks to happen
2313 
2314         if (!testCase.isCameraAvailable(cameraId)) {
2315             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
2316             goto cleanup;
2317         }
2318     }
2319 
2320     ret = testCase.deInit();
2321     if (ret != ACAMERA_OK) {
2322         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
2323         goto cleanup;
2324     }
2325 
2326     pass = true;
2327 cleanup:
2328     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2329     if (!pass) {
2330         throwAssertionError(env, errorString);
2331     }
2332     return pass;
2333 }
2334 
2335 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceCreateCaptureRequestNative(JNIEnv * env,jclass,jstring jOverrideCameraId)2336 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
2337 testCameraDeviceCreateCaptureRequestNative(
2338         JNIEnv* env, jclass /*clazz*/, jstring jOverrideCameraId) {
2339     ALOGV("%s", __FUNCTION__);
2340     bool pass = false;
2341     ACameraManager* mgr = ACameraManager_create();
2342     ACameraIdList* cameraIdList = nullptr;
2343     ACameraDevice* device = nullptr;
2344     ACaptureRequest* request = nullptr;
2345     ACameraMetadata* chars = nullptr;
2346     camera_status_t ret = ACameraManager_getCameraIdList(mgr, &cameraIdList);
2347 
2348     int numCameras = cameraIdList->numCameras;
2349     const char* overrideCameraId = nullptr;
2350     if (jOverrideCameraId != nullptr) {
2351         overrideCameraId = env->GetStringUTFChars(jOverrideCameraId, nullptr);
2352     }
2353 
2354     for (int i = 0; i < numCameras; i++) {
2355         CameraDeviceListener deviceListener;
2356         const char* cameraId = cameraIdList->cameraIds[i];
2357         if (overrideCameraId != nullptr && strcmp(overrideCameraId, cameraId)) {
2358             // Skip other cameras if overriding camera id to be tested.
2359             continue;
2360         }
2361         ACameraDevice_StateCallbacks deviceCb {
2362             &deviceListener,
2363             CameraDeviceListener::onDisconnected,
2364             CameraDeviceListener::onError
2365         };
2366         ret = ACameraManager_openCamera(mgr, cameraId, &deviceCb, &device);
2367         if (ret != ACAMERA_OK) {
2368             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
2369             goto cleanup;
2370         }
2371 
2372         ret = ACameraManager_getCameraCharacteristics(mgr, cameraId, &chars);
2373         if (ret != ACAMERA_OK || chars == nullptr) {
2374             LOG_ERROR(errorString, "Get camera %s characteristics failure. ret %d, chars %p",
2375                     cameraId, ret, chars);
2376             goto cleanup;
2377         }
2378         StaticInfo staticInfo(chars);
2379 
2380         for (int t = TEMPLATE_PREVIEW; t <= TEMPLATE_MANUAL; t++) {
2381             ACameraDevice_request_template templateId =
2382                     static_cast<ACameraDevice_request_template>(t);
2383             ret = ACameraDevice_createCaptureRequest(device, templateId, &request);
2384             if (ret == ACAMERA_ERROR_INVALID_PARAMETER) {
2385                 // template not supported. skip
2386                 continue;
2387             }
2388 
2389             if (ret != ACAMERA_OK) {
2390                 LOG_ERROR(errorString, "Create capture request failed!: ret %d", ret);
2391                 goto cleanup;
2392             }
2393 
2394             int32_t numTags = 0;
2395             const uint32_t* tags = nullptr;
2396             ret = ACaptureRequest_getAllTags(request, &numTags, &tags);
2397             if (ret != ACAMERA_OK) {
2398                 LOG_ERROR(errorString, "Get capture request tags failed: ret %d", ret);
2399                 goto cleanup;
2400             }
2401 
2402             for (int tid = 0; tid < numTags; tid++) {
2403                 uint32_t tagId = tags[tid];
2404                 ALOGV("%s capture request contains key %u", __FUNCTION__, tagId);
2405                 uint32_t sectionId = tagId >> 16;
2406                 if (sectionId >= ACAMERA_SECTION_COUNT && sectionId < ACAMERA_VENDOR) {
2407                     LOG_ERROR(errorString, "Unknown tagId %u, sectionId %u", tagId, sectionId);
2408                     goto cleanup;
2409                 }
2410             }
2411 
2412             void* context = nullptr;
2413             ret = ACaptureRequest_getUserContext(request, &context);
2414             if (ret != ACAMERA_OK) {
2415                 LOG_ERROR(errorString, "Get capture request context failed: ret %d", ret);
2416                 goto cleanup;
2417             }
2418             if (context != nullptr) {
2419                 LOG_ERROR(errorString, "Capture request context is not null: %p", context);
2420                 goto cleanup;
2421             }
2422 
2423             intptr_t magic_num = 0xBEEF;
2424             ret = ACaptureRequest_setUserContext(request, (void*) magic_num);
2425             if (ret != ACAMERA_OK) {
2426                 LOG_ERROR(errorString, "Set capture request context failed: ret %d", ret);
2427                 goto cleanup;
2428             }
2429 
2430             ret = ACaptureRequest_getUserContext(request, &context);
2431             if (ret != ACAMERA_OK) {
2432                 LOG_ERROR(errorString, "Get capture request context failed: ret %d", ret);
2433                 goto cleanup;
2434             }
2435             if (context != (void*) magic_num) {
2436                 LOG_ERROR(errorString, "Capture request context is wrong: %p", context);
2437                 goto cleanup;
2438             }
2439 
2440             // try get/set capture request fields
2441             ACameraMetadata_const_entry entry;
2442             ret = ACaptureRequest_getConstEntry_physicalCamera(request, nullptr,
2443                     ACAMERA_CONTROL_AE_MODE, &entry);
2444             if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2445                 LOG_ERROR(errorString, "Get AE mode key for null physical id should fail. ret %d",
2446                         ret);
2447                 goto cleanup;
2448             }
2449             ret = ACaptureRequest_getConstEntry_physicalCamera(request, cameraId,
2450                     ACAMERA_CONTROL_AE_MODE, &entry);
2451             if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2452                 LOG_ERROR(errorString, "Get AE mode key for physical id should fail. ret %d",
2453                         ret);
2454                 goto cleanup;
2455             }
2456             ret = ACaptureRequest_getConstEntry(request, ACAMERA_CONTROL_AE_MODE, &entry);
2457             if (ret != ACAMERA_OK) {
2458                 LOG_ERROR(errorString, "Get AE mode key failed. ret %d", ret);
2459                 goto cleanup;
2460             }
2461 
2462             if (entry.tag != ACAMERA_CONTROL_AE_MODE || entry.type != ACAMERA_TYPE_BYTE ||\
2463                     entry.count != 1) {
2464                 LOG_ERROR(errorString,
2465                         "Bad AE mode key. tag 0x%x (expect 0x%x), type %d (expect %d), "
2466                         "count %d (expect %d)",
2467                         entry.tag, ACAMERA_CONTROL_AE_MODE, entry.type, ACAMERA_TYPE_BYTE,
2468                         entry.count, 1);
2469                 goto cleanup;
2470             }
2471             if (t == TEMPLATE_MANUAL) {
2472                 if (entry.data.u8[0] != ACAMERA_CONTROL_AE_MODE_OFF) {
2473                     LOG_ERROR(errorString, "Error: MANUAL template AE mode %d (expect %d)",
2474                             entry.data.u8[0], ACAMERA_CONTROL_AE_MODE_OFF);
2475                     goto cleanup;
2476                 }
2477                 // try set AE_MODE_ON
2478                 uint8_t aeMode = ACAMERA_CONTROL_AE_MODE_ON;
2479                 ret = ACaptureRequest_setEntry_physicalCamera_u8(
2480                         request, nullptr, ACAMERA_CONTROL_AE_MODE, /*count*/ 1, &aeMode);
2481                 if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2482                     LOG_ERROR(errorString, "Error: camera %s setEntry_physicalCamera_u8 should "
2483                             "fail. ret %d", cameraId, ret);
2484                     goto cleanup;
2485                 }
2486                 ret = ACaptureRequest_setEntry_physicalCamera_u8(
2487                         request, cameraId, ACAMERA_CONTROL_AE_MODE, /*count*/ 1, &aeMode);
2488                 if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2489                     LOG_ERROR(errorString, "Error: camera %s setEntry_physicalCamera_u8 should "
2490                             "fail. ret %d", cameraId, ret);
2491                     goto cleanup;
2492                 }
2493                 ret = ACaptureRequest_setEntry_u8(
2494                         request, ACAMERA_CONTROL_AE_MODE, /*count*/ 1, &aeMode);
2495                 if (ret != ACAMERA_OK) {
2496                     LOG_ERROR(errorString,
2497                             "Error: Camera %s template %d: update AE mode key fail. ret %d",
2498                             cameraId, t, ret);
2499                     goto cleanup;
2500                 }
2501                 ret = ACaptureRequest_getConstEntry(
2502                         request, ACAMERA_CONTROL_AE_MODE, &entry);
2503                 if (ret != ACAMERA_OK) {
2504                     LOG_ERROR(errorString, "Get AE mode key failed. ret %d", ret);
2505                     goto cleanup;
2506                 }
2507                 if (entry.data.u8[0] != aeMode) {
2508                     LOG_ERROR(errorString,
2509                             "Error: AE mode key is not updated. expect %d but get %d",
2510                             aeMode, entry.data.u8[0]);
2511                     goto cleanup;
2512                 }
2513             } else {
2514                 if (staticInfo.isColorOutputSupported()) {
2515                     if (entry.data.u8[0] != ACAMERA_CONTROL_AE_MODE_ON) {
2516                         LOG_ERROR(errorString,
2517                                 "Error: Template %d has wrong AE mode %d (expect %d)",
2518                                 t, entry.data.u8[0], ACAMERA_CONTROL_AE_MODE_ON);
2519                         goto cleanup;
2520                     }
2521                     // try set AE_MODE_OFF
2522                     if (staticInfo.isCapabilitySupported(
2523                             ACAMERA_REQUEST_AVAILABLE_CAPABILITIES_MANUAL_SENSOR)) {
2524                         uint8_t aeMode = ACAMERA_CONTROL_AE_MODE_OFF;
2525                         ret = ACaptureRequest_setEntry_u8(
2526                                 request, ACAMERA_CONTROL_AE_MODE, /*count*/ 1, &aeMode);
2527                         if (ret != ACAMERA_OK) {
2528                             LOG_ERROR(errorString,
2529                                     "Error: Camera %s template %d: update AE mode key fail. ret %d",
2530                                     cameraId, t, ret);
2531                             goto cleanup;
2532                         }
2533                         ret = ACaptureRequest_getConstEntry(
2534                                 request, ACAMERA_CONTROL_AE_MODE, &entry);
2535                         if (ret != ACAMERA_OK) {
2536                             LOG_ERROR(errorString, "Get AE mode key failed. ret %d", ret);
2537                             goto cleanup;
2538                         }
2539                         if (entry.data.u8[0] != aeMode) {
2540                             LOG_ERROR(errorString,
2541                                     "Error: AE mode key is not updated. expect %d but get %d",
2542                                     aeMode, entry.data.u8[0]);
2543                             goto cleanup;
2544                         }
2545                     }
2546                 }
2547             }
2548             ACaptureRequest_free(request);
2549             request = nullptr;
2550         }
2551 
2552         ACameraMetadata_free(chars);
2553         chars = nullptr;
2554         ACameraDevice_close(device);
2555         device = nullptr;
2556     }
2557 
2558     pass = true;
2559 cleanup:
2560     if (cameraIdList) {
2561         ACameraManager_deleteCameraIdList(cameraIdList);
2562     }
2563     if (request) {
2564         ACaptureRequest_free(request);
2565     }
2566     if (chars) {
2567         ACameraMetadata_free(chars);
2568     }
2569     if (device) {
2570         ACameraDevice_close(device);
2571     }
2572     if (mgr) {
2573         ACameraManager_delete(mgr);
2574     }
2575     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2576     if (!pass) {
2577         throwAssertionError(env, errorString);
2578     }
2579     return pass;
2580 }
2581 
2582 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceSessionOpenAndCloseNative(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)2583 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
2584 testCameraDeviceSessionOpenAndCloseNative(
2585         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
2586         jstring jOverrideCameraId) {
2587     ALOGV("%s", __FUNCTION__);
2588     int numCameras = 0;
2589     bool pass = false;
2590     PreviewTestCase testCase;
2591 
2592     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
2593     if (ret != ACAMERA_OK) {
2594         // Don't log error here. testcase did it
2595         goto cleanup;
2596     }
2597 
2598     numCameras = testCase.getNumCameras();
2599     if (numCameras < 0) {
2600         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
2601         goto cleanup;
2602     }
2603 
2604     for (int i = 0; i < numCameras; i++) {
2605         const char* cameraId = testCase.getCameraId(i);
2606         if (cameraId == nullptr) {
2607             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
2608             goto cleanup;
2609         }
2610 
2611         {
2612             ACameraMetadata* chars = testCase.getCameraChars(cameraId);
2613             StaticInfo staticInfo(chars);
2614             if (!staticInfo.isColorOutputSupported()) {
2615                 ALOGI("%s: camera %s does not support color output. skipping",
2616                         __FUNCTION__, cameraId);
2617                 ACameraMetadata_free(chars);
2618                 continue;
2619             }
2620             ACameraMetadata_free(chars);
2621         }
2622 
2623         ret = testCase.openCamera(cameraId);
2624         if (ret != ACAMERA_OK) {
2625             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
2626             goto cleanup;
2627         }
2628 
2629         usleep(100000); // sleep to give some time for callbacks to happen
2630 
2631         if (testCase.isCameraAvailable(cameraId)) {
2632             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
2633             goto cleanup;
2634         }
2635 
2636         ANativeWindow* previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
2637         if (previewAnw == nullptr) {
2638             LOG_ERROR(errorString, "Null ANW from preview surface!");
2639             goto cleanup;
2640         }
2641 
2642         CaptureSessionListener* sessionListener = testCase.getSessionListener();
2643         if (sessionListener == nullptr) {
2644             LOG_ERROR(errorString, "Session listener camera %s is null", cameraId);
2645             goto cleanup;
2646         }
2647 
2648         // Try open/close session multiple times
2649         for (int j = 0; j < 5; j++) {
2650             ret = testCase.createCaptureSessionWithLog();
2651             if (ret != ACAMERA_OK) {
2652                 // Don't log error here. testcase did it
2653                 goto cleanup;
2654             }
2655 
2656             usleep(100000); // sleep to give some time for callbacks to happen
2657 
2658             if (!sessionListener->isIdle()) {
2659                 LOG_ERROR(errorString, "Session for camera %s should be idle right after creation",
2660                         cameraId);
2661                 goto cleanup;
2662             }
2663 
2664             testCase.closeSession();
2665 
2666             usleep(100000); // sleep to give some time for callbacks to happen
2667             if (!sessionListener->isClosed() || sessionListener->onClosedCount() != 1) {
2668                 LOG_ERROR(errorString,
2669                         "Session for camera %s close error. isClosde %d close count %d",
2670                         cameraId, sessionListener->isClosed(), sessionListener->onClosedCount());
2671                 goto cleanup;
2672             }
2673             sessionListener->reset();
2674         }
2675 
2676         // Try open/close really fast
2677         ret = testCase.createCaptureSessionWithLog();
2678         if (ret != ACAMERA_OK) {
2679             LOG_ERROR(errorString, "Create session for camera %s failed. ret %d",
2680                     cameraId, ret);
2681             goto cleanup;
2682         }
2683         testCase.closeSession();
2684         usleep(100000); // sleep to give some time for callbacks to happen
2685         if (!sessionListener->isClosed() || sessionListener->onClosedCount() != 1) {
2686             LOG_ERROR(errorString,
2687                     "Session for camera %s close error. isClosde %d close count %d",
2688                     cameraId, sessionListener->isClosed(), sessionListener->onClosedCount());
2689             goto cleanup;
2690         }
2691 
2692         ret = testCase.resetWithErrorLog();
2693         if (ret != ACAMERA_OK) {
2694             // Don't log error here. testcase did it
2695             goto cleanup;
2696         }
2697 
2698         usleep(100000); // sleep to give some time for callbacks to happen
2699 
2700         if (!testCase.isCameraAvailable(cameraId)) {
2701             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
2702             goto cleanup;
2703         }
2704     }
2705 
2706     ret = testCase.deInit();
2707     if (ret != ACAMERA_OK) {
2708         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
2709         goto cleanup;
2710     }
2711 
2712     pass = true;
2713 cleanup:
2714     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2715     if (!pass) {
2716         throwAssertionError(env, errorString);
2717     }
2718     return pass;
2719 }
2720 
2721 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceSharedOutputUpdate(JNIEnv * env,jclass,jobject jPreviewSurface,jobject jSharedSurface,jstring jOverrideCameraId)2722 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
2723 testCameraDeviceSharedOutputUpdate(
2724         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface, jobject jSharedSurface,
2725         jstring jOverrideCameraId) {
2726     ALOGV("%s", __FUNCTION__);
2727     int numCameras = 0;
2728     bool pass = false;
2729     PreviewTestCase testCase;
2730     int sequenceId = -1;
2731     int64_t lastFrameNumber = 0;
2732     bool frameArrived = false;
2733     ANativeWindow* previewAnw = nullptr;
2734     ANativeWindow* sharedAnw = ANativeWindow_fromSurface(env, jSharedSurface);
2735     ACaptureRequest* updatedRequest = nullptr;
2736     ACameraOutputTarget* reqPreviewOutput = nullptr;
2737     ACameraOutputTarget* reqSharedOutput = nullptr;
2738     ACaptureSessionOutput *previewOutput = nullptr;
2739     uint32_t timeoutSec = 1;
2740     uint32_t runPreviewSec = 2;
2741 
2742     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
2743     if (ret != ACAMERA_OK) {
2744         // Don't log error here. testcase did it
2745         goto cleanup;
2746     }
2747 
2748     numCameras = testCase.getNumCameras();
2749     if (numCameras < 0) {
2750         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
2751         goto cleanup;
2752     }
2753 
2754     for (int i = 0; i < numCameras; i++) {
2755         const char* cameraId = testCase.getCameraId(i);
2756         if (cameraId == nullptr) {
2757             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
2758             goto cleanup;
2759         }
2760 
2761         {
2762             ACameraMetadata* chars = testCase.getCameraChars(cameraId);
2763             StaticInfo staticInfo(chars);
2764             if (!staticInfo.isColorOutputSupported()) {
2765                 ALOGI("%s: camera %s does not support color output. skipping",
2766                         __FUNCTION__, cameraId);
2767                 ACameraMetadata_free(chars);
2768                 continue;
2769             }
2770             ACameraMetadata_free(chars);
2771         }
2772 
2773         ret = testCase.openCamera(cameraId);
2774         if (ret != ACAMERA_OK) {
2775             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
2776             goto cleanup;
2777         }
2778 
2779         usleep(100000); // sleep to give some time for callbacks to happen
2780 
2781         if (testCase.isCameraAvailable(cameraId)) {
2782             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
2783             goto cleanup;
2784         }
2785 
2786         previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
2787         if (previewAnw == nullptr) {
2788             LOG_ERROR(errorString, "Null ANW from preview surface!");
2789             goto cleanup;
2790         }
2791 
2792         ret = testCase.createCaptureSessionWithLog(true);
2793         if (ret != ACAMERA_OK) {
2794             // Don't log error here. testcase did it
2795             goto cleanup;
2796         }
2797 
2798         ret = testCase.createRequestsWithErrorLog();
2799         if (ret != ACAMERA_OK) {
2800             // Don't log error here. testcase did it
2801             goto cleanup;
2802         }
2803 
2804         ret = testCase.startPreview();
2805         if (ret != ACAMERA_OK) {
2806             LOG_ERROR(errorString, "Start preview failed!");
2807             goto cleanup;
2808         }
2809 
2810         sleep(runPreviewSec);
2811 
2812         previewOutput = testCase.getPreviewOutput();
2813         //Try some bad input
2814         ret = ACaptureSessionSharedOutput_add(previewOutput, previewAnw);
2815         if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2816             LOG_ERROR(errorString, "ACaptureSessionSharedOutput_add should return invalid "
2817                     "parameter! %d", ret);
2818             goto cleanup;
2819         }
2820 
2821         ret = ACaptureSessionSharedOutput_remove(previewOutput, previewAnw);
2822         if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2823             LOG_ERROR(errorString, "ACaptureSessionSharedOutput_remove should return invalid "
2824                     "parameter! %d", ret);
2825             goto cleanup;
2826         }
2827 
2828         //Now try with valid input
2829         ret = ACaptureSessionSharedOutput_add(previewOutput, sharedAnw);
2830         if (ret != ACAMERA_OK) {
2831             LOG_ERROR(errorString, "ACaptureSessionSharedOutput_add failed!")
2832             goto cleanup;
2833         }
2834 
2835         ret = testCase.updateOutput(env, previewOutput);
2836         if (ret != ACAMERA_OK) {
2837             LOG_ERROR(errorString, "Failed to update output configuration!")
2838             goto cleanup;
2839         }
2840 
2841         ret = ACameraDevice_createCaptureRequest(
2842                 testCase.getCameraDevice(), TEMPLATE_PREVIEW, &updatedRequest);
2843         if (ret != ACAMERA_OK) {
2844             LOG_ERROR(errorString, "Camera %s create preview request failed. ret %d",
2845                     cameraId, ret);
2846             goto cleanup;
2847         }
2848 
2849         ret = ACameraOutputTarget_create(previewAnw, &reqPreviewOutput);
2850         if (ret != ACAMERA_OK) {
2851             LOG_ERROR(errorString,
2852                     "Camera %s create request preview output target failed. ret %d",
2853                     cameraId, ret);
2854             goto cleanup;
2855         }
2856 
2857         ret = ACaptureRequest_addTarget(updatedRequest, reqPreviewOutput);
2858         if (ret != ACAMERA_OK) {
2859             LOG_ERROR(errorString, "Camera %s add preview request output failed. ret %d",
2860                     cameraId, ret);
2861             goto cleanup;
2862         }
2863 
2864         ret = ACameraOutputTarget_create(sharedAnw, &reqSharedOutput);
2865         if (ret != ACAMERA_OK) {
2866             LOG_ERROR(errorString,
2867                     "Camera %s create request preview output target failed. ret %d",
2868                     cameraId, ret);
2869             goto cleanup;
2870         }
2871 
2872         ret = ACaptureRequest_addTarget(updatedRequest, reqSharedOutput);
2873         if (ret != ACAMERA_OK) {
2874             LOG_ERROR(errorString, "Camera %s add preview request output failed. ret %d",
2875                     cameraId, ret);
2876             goto cleanup;
2877         }
2878 
2879         ret = testCase.updateRepeatingRequest(updatedRequest, &sequenceId);
2880         if (ret != ACAMERA_OK) {
2881             LOG_ERROR(errorString, "Camera %s failed to update repeated request. ret %d",
2882                     cameraId, ret);
2883             goto cleanup;
2884         }
2885 
2886         sleep(runPreviewSec);
2887 
2888         ret = ACaptureSessionSharedOutput_remove(previewOutput, sharedAnw);
2889         if (ret != ACAMERA_OK) {
2890             LOG_ERROR(errorString, "ACaptureSessionSharedOutput_remove failed!");
2891             goto cleanup;
2892         }
2893 
2894         //Try removing shared output which still has pending camera requests
2895         ret = testCase.updateOutput(env, previewOutput);
2896         if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
2897             LOG_ERROR(errorString, "updateOutput should fail!");
2898             goto cleanup;
2899         }
2900 
2901         //Remove the shared output correctly by updating the repeating request
2902         //first
2903         ret = ACaptureRequest_removeTarget(updatedRequest, reqSharedOutput);
2904         if (ret != ACAMERA_OK) {
2905             LOG_ERROR(errorString, "Camera %s remove target output failed. ret %d",
2906                     cameraId, ret);
2907             goto cleanup;
2908         }
2909 
2910         ret = testCase.updateRepeatingRequest(updatedRequest);
2911         if (ret != ACAMERA_OK) {
2912             LOG_ERROR(errorString, "Camera %s failed to update repeated request. ret %d",
2913                     cameraId, ret);
2914             goto cleanup;
2915         }
2916 
2917         //Then wait for all old requests to flush
2918         lastFrameNumber = testCase.getCaptureSequenceLastFrameNumber(sequenceId, timeoutSec);
2919         if (lastFrameNumber < 0) {
2920             LOG_ERROR(errorString, "Camera %s failed to acquire last frame number!",
2921                     cameraId);
2922             goto cleanup;
2923         }
2924 
2925         frameArrived = testCase.waitForFrameNumber(lastFrameNumber, timeoutSec);
2926         if (!frameArrived) {
2927             LOG_ERROR(errorString, "Camera %s timed out waiting on last frame number!",
2928                     cameraId);
2929             goto cleanup;
2930         }
2931 
2932         ret = testCase.updateOutput(env, previewOutput);
2933         if (ret != ACAMERA_OK) {
2934             LOG_ERROR(errorString, "updateOutput failed!");
2935             goto cleanup;
2936         }
2937 
2938         sleep(runPreviewSec);
2939 
2940         ret = testCase.resetWithErrorLog();
2941         if (ret != ACAMERA_OK) {
2942             // Don't log error here. testcase did it
2943             goto cleanup;
2944         }
2945 
2946         usleep(100000); // sleep to give some time for callbacks to happen
2947 
2948         if (!testCase.isCameraAvailable(cameraId)) {
2949             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
2950             goto cleanup;
2951         }
2952     }
2953 
2954     ret = testCase.deInit();
2955     if (ret != ACAMERA_OK) {
2956         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
2957         goto cleanup;
2958     }
2959 
2960     pass = true;
2961 
2962 cleanup:
2963 
2964     if (updatedRequest != nullptr) {
2965         ACaptureRequest_free(updatedRequest);
2966         updatedRequest = nullptr;
2967     }
2968 
2969     if (reqPreviewOutput != nullptr) {
2970         ACameraOutputTarget_free(reqPreviewOutput);
2971         reqPreviewOutput = nullptr;
2972     }
2973 
2974     if (reqSharedOutput != nullptr) {
2975         ACameraOutputTarget_free(reqSharedOutput);
2976         reqSharedOutput = nullptr;
2977     }
2978 
2979     if (sharedAnw) {
2980         ANativeWindow_release(sharedAnw);
2981         sharedAnw = nullptr;
2982     }
2983 
2984     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
2985     if (!pass) {
2986         throwAssertionError(env, errorString);
2987     }
2988     return pass;
2989 }
2990 
testCameraDeviceSimplePreviewNativeInternal(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId,bool v2Callbacks)2991 bool testCameraDeviceSimplePreviewNativeInternal(
2992         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
2993         jstring jOverrideCameraId, bool v2Callbacks) {
2994     ALOGV("%s", __FUNCTION__);
2995     int numCameras = 0;
2996     bool pass = false;
2997     const int timeoutSec = 1;
2998     PreviewTestCase testCase;
2999 
3000     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
3001     if (ret != ACAMERA_OK) {
3002         // Don't log error here. testcase did it
3003         goto cleanup;
3004     }
3005 
3006     numCameras = testCase.getNumCameras();
3007     if (numCameras < 0) {
3008         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
3009         goto cleanup;
3010     }
3011 
3012     for (int i = 0; i < numCameras; i++) {
3013         const char* cameraId = testCase.getCameraId(i);
3014         if (cameraId == nullptr) {
3015             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
3016             goto cleanup;
3017         }
3018 
3019         {
3020             ACameraMetadata* chars = testCase.getCameraChars(cameraId);
3021             StaticInfo staticInfo(chars);
3022             if (!staticInfo.isColorOutputSupported()) {
3023                 ALOGI("%s: camera %s does not support color output. skipping",
3024                         __FUNCTION__, cameraId);
3025                 ACameraMetadata_free(chars);
3026                 continue;
3027             }
3028             ACameraMetadata_free(chars);
3029         }
3030 
3031         ret = testCase.openCamera(cameraId);
3032         if (ret != ACAMERA_OK) {
3033             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
3034             goto cleanup;
3035         }
3036 
3037         usleep(100000); // sleep to give some time for callbacks to happen
3038 
3039         if (testCase.isCameraAvailable(cameraId)) {
3040             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
3041             goto cleanup;
3042         }
3043 
3044         ANativeWindow* previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
3045         if (previewAnw == nullptr) {
3046             LOG_ERROR(errorString, "Null ANW from preview surface!");
3047             goto cleanup;
3048         }
3049 
3050         ret = testCase.createCaptureSessionWithLog();
3051         if (ret != ACAMERA_OK) {
3052             // Don't log error here. testcase did it
3053             goto cleanup;
3054         }
3055 
3056         ret = testCase.createRequestsWithErrorLog();
3057         if (ret != ACAMERA_OK) {
3058             // Don't log error here. testcase did it
3059             goto cleanup;
3060         }
3061         int sequenceId = 0;
3062         ret = testCase.startPreview(&sequenceId, 0, nullptr, v2Callbacks);
3063         if (ret != ACAMERA_OK) {
3064             LOG_ERROR(errorString, "Start preview failed!");
3065             goto cleanup;
3066         }
3067 
3068         sleep(3);
3069 
3070         ret = testCase.stopPreview();
3071         if (ret != ACAMERA_OK) {
3072             ALOGE("%s: stopPreview failed", __FUNCTION__);
3073             LOG_ERROR(errorString, "stopPreview failed!");
3074             goto cleanup;
3075         }
3076 
3077         //Then wait for all old requests to flush
3078         int64_t lastFrameNumber =
3079                 testCase.getCaptureSequenceLastFrameNumber(sequenceId, timeoutSec);
3080         if (lastFrameNumber < 0) {
3081             LOG_ERROR(errorString, "Camera %s failed to acquire last frame number!",
3082                     cameraId);
3083             goto cleanup;
3084         }
3085         if (v2Callbacks) {
3086               bool frameStarted = testCase.waitForFrameNumberStarted(lastFrameNumber, timeoutSec);
3087             if (!frameStarted) {
3088                 LOG_ERROR(errorString, "Camera %s timed out waiting on onCaptureStart for last"
3089                         "frame number!", cameraId);
3090                 goto cleanup;
3091             }
3092 
3093         }
3094 
3095         ret = testCase.resetWithErrorLog();
3096         if (ret != ACAMERA_OK) {
3097             // Don't log error here. testcase did it
3098             goto cleanup;
3099         }
3100 
3101         usleep(100000); // sleep to give some time for callbacks to happen
3102 
3103         if (!testCase.isCameraAvailable(cameraId)) {
3104             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
3105             goto cleanup;
3106         }
3107     }
3108 
3109     ret = testCase.deInit();
3110     if (ret != ACAMERA_OK) {
3111         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
3112         goto cleanup;
3113     }
3114 
3115     pass = true;
3116 cleanup:
3117     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
3118     if (!pass) {
3119         throwAssertionError(env, errorString);
3120     }
3121     return pass;
3122 }
3123 
3124 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceSimplePreviewNative(JNIEnv * env,jclass clazz,jobject jPreviewSurface,jstring jOverrideCameraId)3125 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3126 testCameraDeviceSimplePreviewNative(
3127         JNIEnv* env, jclass clazz, jobject jPreviewSurface,
3128         jstring jOverrideCameraId) {
3129     return testCameraDeviceSimplePreviewNativeInternal(env, clazz, jPreviewSurface,
3130             jOverrideCameraId, /*v2Callbacks*/false);
3131 }
3132 
3133 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceSimplePreviewNative2(JNIEnv * env,jclass clazz,jobject jPreviewSurface,jstring jOverrideCameraId)3134 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3135 testCameraDeviceSimplePreviewNative2(
3136         JNIEnv* env, jclass clazz, jobject jPreviewSurface,
3137         jstring jOverrideCameraId) {
3138     return testCameraDeviceSimplePreviewNativeInternal(env, clazz, jPreviewSurface,
3139             jOverrideCameraId, /*v2Callbacks*/true);
3140 }
3141 
3142 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDevicePreviewWithSessionParametersNative(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)3143 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3144 testCameraDevicePreviewWithSessionParametersNative(
3145         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
3146         jstring jOverrideCameraId) {
3147     ALOGV("%s", __FUNCTION__);
3148     int numCameras = 0;
3149     bool pass = false;
3150     ACameraManager* mgr = ACameraManager_create();
3151     ACameraMetadata* chars = nullptr;
3152     PreviewTestCase testCase;
3153 
3154     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
3155     if (ret != ACAMERA_OK) {
3156         // Don't log error here. testcase did it
3157         goto cleanup;
3158     }
3159 
3160     numCameras = testCase.getNumCameras();
3161     if (numCameras < 0) {
3162         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
3163         goto cleanup;
3164     }
3165 
3166     for (int i = 0; i < numCameras; i++) {
3167         const char* cameraId = testCase.getCameraId(i);
3168         if (cameraId == nullptr) {
3169             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
3170             goto cleanup;
3171         }
3172 
3173         ret = ACameraManager_getCameraCharacteristics(
3174                 mgr, cameraId, &chars);
3175         if (ret != ACAMERA_OK) {
3176             LOG_ERROR(errorString, "Get camera characteristics failed: ret %d", ret);
3177             goto cleanup;
3178         }
3179 
3180         StaticInfo staticInfo(chars);
3181         ACameraMetadata_const_entry sessionParamKeys{};
3182         ret = ACameraMetadata_getConstEntry(chars, ACAMERA_REQUEST_AVAILABLE_SESSION_KEYS,
3183                 &sessionParamKeys);
3184         if ((ret != ACAMERA_OK) || (sessionParamKeys.count == 0) ||
3185                 !staticInfo.isColorOutputSupported()) {
3186             ACameraMetadata_free(chars);
3187             chars = nullptr;
3188             continue;
3189         }
3190 
3191         ret = testCase.openCamera(cameraId);
3192         if (ret != ACAMERA_OK) {
3193             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
3194             goto cleanup;
3195         }
3196 
3197         usleep(100000); // sleep to give some time for callbacks to happen
3198 
3199         if (testCase.isCameraAvailable(cameraId)) {
3200             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
3201             goto cleanup;
3202         }
3203 
3204         ANativeWindow* previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
3205         if (previewAnw == nullptr) {
3206             LOG_ERROR(errorString, "Null ANW from preview surface!");
3207             goto cleanup;
3208         }
3209 
3210         ret = testCase.createRequestsWithErrorLog();
3211         if (ret != ACAMERA_OK) {
3212             // Don't log error here. testcase did it
3213             goto cleanup;
3214         }
3215 
3216         ACaptureRequest *previewRequest = nullptr;
3217         ret = testCase.getPreviewRequest(&previewRequest);
3218         if ((ret != ACAMERA_OK) || (previewRequest == nullptr)) {
3219             LOG_ERROR(errorString, "Preview request query failed!");
3220             goto cleanup;
3221         }
3222 
3223         ret = testCase.createCaptureSessionWithLog(/*isPreviewShared*/ false, previewRequest);
3224         if (ret != ACAMERA_OK) {
3225             // Don't log error here. testcase did it
3226             goto cleanup;
3227         }
3228 
3229         ret = testCase.startPreview();
3230         if (ret != ACAMERA_OK) {
3231             LOG_ERROR(errorString, "Start preview failed!");
3232             goto cleanup;
3233         }
3234 
3235         sleep(3);
3236 
3237         ret = testCase.resetWithErrorLog();
3238         if (ret != ACAMERA_OK) {
3239             // Don't log error here. testcase did it
3240             goto cleanup;
3241         }
3242 
3243         usleep(100000); // sleep to give some time for callbacks to happen
3244 
3245         if (!testCase.isCameraAvailable(cameraId)) {
3246             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
3247             goto cleanup;
3248         }
3249 
3250         ACameraMetadata_free(chars);
3251         chars = nullptr;
3252     }
3253 
3254     ret = testCase.deInit();
3255     if (ret != ACAMERA_OK) {
3256         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
3257         goto cleanup;
3258     }
3259 
3260     pass = true;
3261 cleanup:
3262     if (chars) {
3263         ACameraMetadata_free(chars);
3264     }
3265     ACameraManager_delete(mgr);
3266     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
3267     if (!pass) {
3268         throwAssertionError(env, errorString);
3269     }
3270     return pass;
3271 }
3272 
nativeCameraDeviceTestPrepareSurface(JNIEnv * env,jobject jPreviewSurface,jstring jOverrideCameraId)3273 bool nativeCameraDeviceTestPrepareSurface(
3274         JNIEnv* env, jobject jPreviewSurface,
3275         jstring jOverrideCameraId) {
3276     const int NUM_TEST_IMAGES = 10;
3277     const int TEST_WIDTH  = 640;
3278     const int TEST_HEIGHT = 480;
3279     ALOGV("%s", __FUNCTION__);
3280     int numCameras = 0;
3281     bool pass = false;
3282     ACameraManager* mgr = ACameraManager_create();
3283     ACameraMetadata* chars = nullptr;
3284     media_status_t mediaRet = AMEDIA_ERROR_UNKNOWN;
3285     PreviewTestCase testCase;
3286     int64_t lastFrameNumber = 0;
3287     bool frameStarted = false;
3288     bool frameArrived = false;
3289     uint32_t timeoutSec = 1;
3290     uint32_t runPreviewSec = 2;
3291 
3292     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
3293     if (ret != ACAMERA_OK) {
3294         // Don't log error here. testcase did it
3295         goto cleanup;
3296     }
3297 
3298     numCameras = testCase.getNumCameras();
3299     if (numCameras < 0) {
3300         LOG_ERROR(errorString, "Testcase returned negative number of cameras: %d", numCameras);
3301         goto cleanup;
3302     }
3303 
3304     for (int i = 0; i < numCameras; i++) {
3305         const char* cameraId = testCase.getCameraId(i);
3306         if (cameraId == nullptr) {
3307             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
3308             goto cleanup;
3309         }
3310 
3311         chars = testCase.getCameraChars(cameraId);
3312         if (chars == nullptr) {
3313             LOG_ERROR(errorString, "Get camera %s characteristics failure", cameraId);
3314             goto cleanup;
3315         }
3316         StaticInfo staticInfo(chars);
3317         if (!staticInfo.isColorOutputSupported()) {
3318             ALOGI("%s: camera %s does not support color output. skipping",
3319                     __FUNCTION__, cameraId);
3320             ACameraMetadata_free(chars);
3321             chars = nullptr;
3322             continue;
3323         }
3324         ACameraMetadata_free(chars);
3325         chars = nullptr;
3326 
3327         ret = testCase.openCamera(cameraId);
3328         if (ret != ACAMERA_OK) {
3329             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
3330             goto cleanup;
3331         }
3332 
3333         usleep(1000000); // sleep to give some time for callbacks to happen
3334 
3335         if (testCase.isCameraAvailable(cameraId)) {
3336             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
3337             goto cleanup;
3338         }
3339         ImageReaderListener readerListener;
3340         AImageReader* reader = nullptr;
3341         ANativeWindow* readerAnw = nullptr;
3342         ACaptureSessionOutput* readerSessionOutput = nullptr;
3343         ACameraOutputTarget* readerOutput = nullptr;
3344         AImageReader_ImageListener readerCb {
3345             &readerListener,
3346             ImageReaderListener::validateImageCb
3347         };
3348 
3349         mediaRet = testCase.initImageReaderWithErrorLog(
3350                 TEST_WIDTH, TEST_HEIGHT, AIMAGE_FORMAT_YUV_420_888, NUM_TEST_IMAGES,
3351                 &readerCb, &reader, &readerAnw);
3352         if (mediaRet != AMEDIA_OK) {
3353             // Don't log error here. testcase did it
3354             goto cleanup;
3355         }
3356 
3357         ret = ACaptureSessionOutput_create(readerAnw,
3358                 &readerSessionOutput);
3359         if (ret != ACAMERA_OK || readerSessionOutput == nullptr) {
3360             // Don't log error here. testcase did it
3361             goto cleanup;
3362         }
3363 
3364         ret = ACameraOutputTarget_create(readerAnw, &readerOutput);
3365         if (ret != ACAMERA_OK) {
3366             // Don't log error here. testcase did it
3367             goto cleanup;
3368         }
3369 
3370         ANativeWindow* previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
3371         if (previewAnw == nullptr) {
3372             LOG_ERROR(errorString, "Null ANW from preview surface!");
3373             goto cleanup;
3374         }
3375         std::vector<ACaptureSessionOutput *> readerSessionOutputs = {readerSessionOutput};
3376         ret = testCase.createCaptureSessionWithLog(readerSessionOutputs, false /*isPreviewShared*/,
3377                 nullptr /*sessionParameters*/, false /*sessionConfigurationDefault*/);
3378         if (ret == ACAMERA_ERROR_UNSUPPORTED_OPERATION ||
3379                 ret == ACAMERA_ERROR_STREAM_CONFIGURE_FAIL) {
3380             // Camera device doesn't support the stream combination, skip the
3381             // current camera.
3382             testCase.closeCamera();
3383             testCase.resetCamera();
3384             continue;
3385         } else if (ret != ACAMERA_OK) {
3386             // Don't log error here. testcase did it
3387             goto cleanup;
3388         }
3389         // Set the callback on the created capture session and prepare all the surfaces
3390         if (testCase.setWindowPreparedCallback() != ACAMERA_OK ||
3391                 testCase.prepareWindow(previewAnw) != ACAMERA_OK) {
3392             goto cleanup;
3393         }
3394         if (testCase.prepareWindow(readerAnw) != ACAMERA_OK) {
3395             goto cleanup;
3396         }
3397         // Wait for some time - we should've gotten onWindowPrepared callbacks for all the
3398         // ANativeWindows.
3399         usleep(200000);
3400         if (!testCase.gotAllPreparedCallbacksWithErrorLog()) {
3401             goto cleanup;
3402         }
3403         std::vector<ACameraOutputTarget* > readerOutputs = {readerOutput};
3404         ret = testCase.createRequestsWithErrorLog(readerOutputs);
3405         if (ret != ACAMERA_OK) {
3406             // Don't log error here. testcase did it
3407             goto cleanup;
3408         }
3409 
3410         ACaptureRequest *previewRequest = nullptr;
3411         ret = testCase.getPreviewRequest(&previewRequest);
3412         if ((ret != ACAMERA_OK) || (previewRequest == nullptr)) {
3413             LOG_ERROR(errorString, "Preview request query failed!");
3414             goto cleanup;
3415         }
3416 
3417         int sequenceId = 0;
3418         ret = testCase.startPreview(&sequenceId);
3419         if (ret != ACAMERA_OK) {
3420             LOG_ERROR(errorString, "Start preview failed!");
3421             goto cleanup;
3422         }
3423 
3424         sleep(runPreviewSec);
3425 
3426         ret = testCase.stopPreview();
3427         if (ret != ACAMERA_OK) {
3428             ALOGE("%s: stopPreview failed", __FUNCTION__);
3429             LOG_ERROR(errorString, "stopPreview failed!");
3430             goto cleanup;
3431         }
3432 
3433         //Then wait for all old requests to flush
3434         lastFrameNumber = testCase.getCaptureSequenceLastFrameNumber(sequenceId, timeoutSec);
3435         if (lastFrameNumber < 0) {
3436             LOG_ERROR(errorString, "Camera %s failed to acquire last frame number!",
3437                     cameraId);
3438             goto cleanup;
3439         }
3440         frameArrived = testCase.waitForFrameNumber(lastFrameNumber, timeoutSec);
3441         if (!frameArrived) {
3442             LOG_ERROR(errorString, "Camera %s timed out waiting on last frame number!",
3443                     cameraId);
3444             goto cleanup;
3445         }
3446 
3447         ret = testCase.resetWithErrorLog();
3448         if (ret != ACAMERA_OK) {
3449             // Don't log error here. testcase did it
3450             goto cleanup;
3451         }
3452 
3453         usleep(100000); // sleep to give some time for callbacks to happen
3454 
3455         if (!testCase.isCameraAvailable(cameraId)) {
3456             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
3457             goto cleanup;
3458         }
3459     }
3460 
3461     ret = testCase.deInit();
3462     if (ret != ACAMERA_OK) {
3463         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
3464         goto cleanup;
3465     }
3466 
3467     pass = true;
3468 cleanup:
3469     if (chars) {
3470         ACameraMetadata_free(chars);
3471     }
3472     ACameraManager_delete(mgr);
3473     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
3474     if (!pass) {
3475         throwAssertionError(env, errorString);
3476     }
3477     return pass;
3478 }
3479 
3480 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDevicePrepareSurface(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)3481 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3482 testCameraDevicePrepareSurface(
3483         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
3484         jstring jOverrideCameraId) {
3485     return nativeCameraDeviceTestPrepareSurface(env,
3486             jPreviewSurface, jOverrideCameraId);
3487 }
3488 
nativeCameraDeviceLogicalPhysicalStreaming(JNIEnv * env,jobject jPreviewSurface,bool usePhysicalSettings,jstring jOverrideCameraId,bool v2Callbacks)3489 bool nativeCameraDeviceLogicalPhysicalStreaming(
3490         JNIEnv* env, jobject jPreviewSurface, bool usePhysicalSettings,
3491         jstring jOverrideCameraId, bool v2Callbacks) {
3492     const int NUM_TEST_IMAGES = 10;
3493     const int TEST_WIDTH  = 640;
3494     const int TEST_HEIGHT = 480;
3495     ALOGV("%s", __FUNCTION__);
3496     int numCameras = 0;
3497     bool pass = false;
3498     ACameraManager* mgr = ACameraManager_create();
3499     ACameraMetadata* chars = nullptr;
3500     media_status_t mediaRet = AMEDIA_ERROR_UNKNOWN;
3501     PreviewTestCase testCase;
3502     int64_t lastFrameNumber = 0;
3503     bool frameStarted = false;
3504     bool frameArrived = false;
3505     uint32_t timeoutSec = 1;
3506     uint32_t runPreviewSec = 2;
3507 
3508     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
3509     if (ret != ACAMERA_OK) {
3510         // Don't log error here. testcase did it
3511         goto cleanup;
3512     }
3513 
3514     numCameras = testCase.getNumCameras();
3515     if (numCameras < 0) {
3516         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
3517         goto cleanup;
3518     }
3519 
3520     for (int i = 0; i < numCameras; i++) {
3521         const char* cameraId = testCase.getCameraId(i);
3522         if (cameraId == nullptr) {
3523             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
3524             goto cleanup;
3525         }
3526 
3527         if (chars != nullptr) {
3528             ACameraMetadata_free(chars);
3529             chars = nullptr;
3530         }
3531         chars = testCase.getCameraChars(i);
3532         if (chars == nullptr) {
3533             LOG_ERROR(errorString, "Get camera %s characteristics failure", cameraId);
3534             goto cleanup;
3535         }
3536 
3537         size_t physicalCameraCnt = 0;
3538         const char *const* physicalCameraIds = nullptr;
3539         if (!ACameraMetadata_isLogicalMultiCamera(
3540                 chars, &physicalCameraCnt, &physicalCameraIds)) {
3541             continue;
3542         }
3543         if (physicalCameraCnt < 2) {
3544             LOG_ERROR(errorString, "Logical camera device %s only has %zu physical cameras",
3545                    cameraId, physicalCameraCnt);
3546             goto cleanup;
3547         }
3548 
3549         std::vector<const char*> candidateIds;
3550         for (size_t i = 0; i < physicalCameraCnt && candidateIds.size() < 2; i++) {
3551             ACameraMetadata* physicalChars = testCase.getCameraChars(physicalCameraIds[i]);
3552             if (physicalChars == nullptr) {
3553                 LOG_ERROR(errorString,
3554                         "Get camera %s characteristics failure", physicalCameraIds[i]);
3555                 goto cleanup;
3556             }
3557             StaticInfo info(physicalChars);
3558             bool testSizeSupported = info.isSizeSupportedForFormat(AIMAGE_FORMAT_YUV_420_888,
3559                     TEST_WIDTH, TEST_HEIGHT);
3560             ACameraMetadata_free(physicalChars);
3561             if (!testSizeSupported) {
3562                 continue;
3563             }
3564             candidateIds.push_back(physicalCameraIds[i]);
3565         }
3566         if (candidateIds.size() < 2) {
3567             continue;
3568         }
3569 
3570         // Check physical camera request keys
3571         if (usePhysicalSettings) {
3572             ACameraMetadata_const_entry entry;
3573             camera_status_t status = ACameraMetadata_getConstEntry(
3574                     chars, ACAMERA_REQUEST_AVAILABLE_PHYSICAL_CAMERA_REQUEST_KEYS, &entry);
3575             if (status == ACAMERA_ERROR_METADATA_NOT_FOUND) {
3576                 // No supported PHYSICAL_CAMERA_REQUEST_KEYS, skip test
3577                 ALOGI("%s camera id %s physical request keys not reported, skipping",
3578                         __FUNCTION__, cameraId);
3579                 continue;
3580             } else if (status != ACAMERA_OK) {
3581                 // Do not log error here. testcase did it.
3582                 goto cleanup;
3583             } else if (entry.count == 0) {
3584                 // No supported PHYSICAL_CAMERA_REQUEST_KEYS, skip test
3585                 continue;
3586             }
3587         }
3588 
3589         ret = testCase.openCamera(cameraId);
3590         if (ret != ACAMERA_OK) {
3591             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
3592             goto cleanup;
3593         }
3594 
3595         usleep(100000); // sleep to give some time for callbacks to happen
3596 
3597         if (testCase.isCameraAvailable(cameraId)) {
3598             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
3599             goto cleanup;
3600         }
3601 
3602         std::vector<ImageReaderListener> readerListeners(2);
3603         std::vector<AImageReader_ImageListener> readerCbs;
3604         std::vector<AImageReader*> readers;
3605         std::vector<ANativeWindow*> readerAnws;
3606         std::vector<ACaptureSessionOutput*> readerSessionOutputs;
3607         std::vector<ACameraOutputTarget*> readerOutputs;
3608         for (size_t i = 0; i < 2; i++) {
3609             AImageReader_ImageListener readerCb {
3610                 &readerListeners[i],
3611                 ImageReaderListener::validateImageCb
3612             };
3613             readerCbs.push_back(readerCb);
3614 
3615             AImageReader* reader = nullptr;
3616             ANativeWindow* readerAnw = nullptr;
3617             ACaptureSessionOutput* readerSessionOutput = nullptr;
3618             ACameraOutputTarget* readerOutput = nullptr;
3619             mediaRet = testCase.initImageReaderWithErrorLog(
3620                     TEST_WIDTH, TEST_HEIGHT, AIMAGE_FORMAT_YUV_420_888, NUM_TEST_IMAGES,
3621                     &readerCb, &reader, &readerAnw);
3622             if (mediaRet != AMEDIA_OK) {
3623                 // Don't log error here. testcase did it
3624                 goto cleanup;
3625             }
3626 
3627             camera_status_t ret = ACaptureSessionPhysicalOutput_create(readerAnw,
3628                     candidateIds[i], &readerSessionOutput);
3629             if (ret != ACAMERA_OK || readerSessionOutput == nullptr) {
3630                 if (ret == ACAMERA_OK) {
3631                     ret = ACAMERA_ERROR_UNKNOWN; // ret OK but output is null
3632                 }
3633                 // Don't log error here. testcase did it
3634                 goto cleanup;
3635             }
3636 
3637             ret = ACameraOutputTarget_create(readerAnw, &readerOutput);
3638             if (ret != ACAMERA_OK) {
3639                 // Don't log error here. testcase did it
3640                 goto cleanup;
3641             }
3642 
3643             readers.push_back(reader);
3644             readerAnws.push_back(readerAnw);
3645             readerSessionOutputs.push_back(readerSessionOutput);
3646             readerOutputs.push_back(readerOutput);
3647         }
3648 
3649         ANativeWindow* previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
3650         if (previewAnw == nullptr) {
3651             LOG_ERROR(errorString, "Null ANW from preview surface!");
3652             goto cleanup;
3653         }
3654 
3655         ret = testCase.createCaptureSessionWithLog(readerSessionOutputs, false /*isPreviewShared*/,
3656                 nullptr /*sessionParameters*/, false /*sessionConfigurationDefault*/);
3657         if (ret == ACAMERA_ERROR_UNSUPPORTED_OPERATION ||
3658                 ret == ACAMERA_ERROR_STREAM_CONFIGURE_FAIL) {
3659             // Camera device doesn't support the stream combination, skip the
3660             // current camera.
3661             testCase.closeCamera();
3662             testCase.resetCamera();
3663             continue;
3664         } else if (ret != ACAMERA_OK) {
3665             // Don't log error here. testcase did it
3666             goto cleanup;
3667         }
3668 
3669         if (usePhysicalSettings) {
3670             std::vector<const char*> twoNullStr = {nullptr, nullptr};
3671             ACameraIdList nullCameraIdList = {2, twoNullStr.data()};
3672             ret = testCase.createRequestsWithErrorLog(readerOutputs, &nullCameraIdList);
3673             if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
3674                 LOG_ERROR(errorString, "Null physical camera ids must fail createCaptureRequest. "
3675                         "ret %d", ret);
3676                 goto cleanup;
3677             }
3678 
3679             std::string invalidId = "";
3680             std::vector<const char*> one0LengthStr = {invalidId.c_str()};
3681             ACameraIdList invalidCameraIdList = {1, one0LengthStr.data()};
3682             ret = testCase.createRequestsWithErrorLog(readerOutputs, &invalidCameraIdList);
3683             if (ret != ACAMERA_ERROR_INVALID_PARAMETER) {
3684                 LOG_ERROR(errorString, "zero-length physical camera ids must fail "
3685                         "createCaptureRequest. ret %d", ret);
3686                 goto cleanup;
3687             }
3688 
3689             ACameraIdList physicalCameraIdList = {2, candidateIds.data()};
3690             ret = testCase.createRequestsWithErrorLog(readerOutputs, &physicalCameraIdList);
3691         } else {
3692             ret = testCase.createRequestsWithErrorLog(readerOutputs);
3693         }
3694         if (ret != ACAMERA_OK) {
3695             // Don't log error here. testcase did it
3696             goto cleanup;
3697         }
3698 
3699         ACaptureRequest *previewRequest = nullptr;
3700         ret = testCase.getPreviewRequest(&previewRequest);
3701         if ((ret != ACAMERA_OK) || (previewRequest == nullptr)) {
3702             LOG_ERROR(errorString, "Preview request query failed!");
3703             goto cleanup;
3704         }
3705 
3706         int sequenceId = 0;
3707         ret = testCase.startPreview(&sequenceId, 2, candidateIds.data(), v2Callbacks);
3708         if (ret != ACAMERA_OK) {
3709             LOG_ERROR(errorString, "Start preview failed!");
3710             goto cleanup;
3711         }
3712 
3713         sleep(runPreviewSec);
3714 
3715         ret = testCase.stopPreview();
3716         if (ret != ACAMERA_OK) {
3717             ALOGE("%s: stopPreview failed", __FUNCTION__);
3718             LOG_ERROR(errorString, "stopPreview failed!");
3719             goto cleanup;
3720         }
3721 
3722         //Then wait for all old requests to flush
3723         lastFrameNumber = testCase.getCaptureSequenceLastFrameNumber(sequenceId, timeoutSec);
3724         if (lastFrameNumber < 0) {
3725             LOG_ERROR(errorString, "Camera %s failed to acquire last frame number!",
3726                     cameraId);
3727             goto cleanup;
3728         }
3729         if (v2Callbacks) {
3730               frameStarted = testCase.waitForFrameNumberStarted(lastFrameNumber, timeoutSec);
3731             if (!frameStarted) {
3732                 LOG_ERROR(errorString, "Camera %s timed out waiting on onCaptureStart for last"
3733                         "frame number!", cameraId);
3734                 goto cleanup;
3735             }
3736 
3737         }
3738 
3739         frameArrived = testCase.waitForFrameNumber(lastFrameNumber, timeoutSec);
3740         if (!frameArrived) {
3741             LOG_ERROR(errorString, "Camera %s timed out waiting on last frame number!",
3742                     cameraId);
3743             goto cleanup;
3744         }
3745 
3746         ret = testCase.resetWithErrorLog();
3747         if (ret != ACAMERA_OK) {
3748             // Don't log error here. testcase did it
3749             goto cleanup;
3750         }
3751 
3752         usleep(100000); // sleep to give some time for callbacks to happen
3753 
3754         if (!testCase.isCameraAvailable(cameraId)) {
3755             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
3756             goto cleanup;
3757         }
3758     }
3759 
3760     ret = testCase.deInit();
3761     if (ret != ACAMERA_OK) {
3762         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
3763         goto cleanup;
3764     }
3765 
3766     pass = true;
3767 cleanup:
3768     if (chars) {
3769         ACameraMetadata_free(chars);
3770     }
3771     ACameraManager_delete(mgr);
3772     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
3773     if (!pass) {
3774         throwAssertionError(env, errorString);
3775     }
3776     return pass;
3777 }
3778 
3779 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceLogicalPhysicalStreamingNative(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)3780 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3781 testCameraDeviceLogicalPhysicalStreamingNative(
3782         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
3783         jstring jOverrideCameraId) {
3784     return nativeCameraDeviceLogicalPhysicalStreaming(env,
3785             jPreviewSurface, false /*usePhysicalSettings*/,
3786             jOverrideCameraId, /*v2Callbacks*/false);
3787 }
3788 
3789 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceLogicalPhysicalStreamingNative2(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)3790 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3791 testCameraDeviceLogicalPhysicalStreamingNative2(
3792         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
3793         jstring jOverrideCameraId) {
3794     return nativeCameraDeviceLogicalPhysicalStreaming(env,
3795             jPreviewSurface, false /*usePhysicalSettings*/,
3796             jOverrideCameraId, /*v2Callbacks*/true);
3797 }
3798 
3799 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceLogicalPhysicalSettingsNative(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)3800 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3801 testCameraDeviceLogicalPhysicalSettingsNative(
3802         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
3803         jstring jOverrideCameraId) {
3804     return nativeCameraDeviceLogicalPhysicalStreaming(env,
3805             jPreviewSurface, true /*usePhysicalSettings*/,
3806             jOverrideCameraId, /*v2Callbacks*/false);
3807 }
3808 
3809 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceLogicalPhysicalSettingsNative2(JNIEnv * env,jclass,jobject jPreviewSurface,jstring jOverrideCameraId)3810 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
3811 testCameraDeviceLogicalPhysicalSettingsNative2(
3812         JNIEnv* env, jclass /*clazz*/, jobject jPreviewSurface,
3813         jstring jOverrideCameraId) {
3814     return nativeCameraDeviceLogicalPhysicalStreaming(env,
3815             jPreviewSurface, true /*usePhysicalSettings*/,
3816             jOverrideCameraId, /*v2Callbacks*/ true);
3817 }
3818 
nativeImageReaderTestBase(JNIEnv * env,jstring jOutPath,jint format,AImageReader_ImageCallback cb,jstring jOverrideCameraId)3819 bool nativeImageReaderTestBase(
3820         JNIEnv* env, jstring jOutPath, jint format, AImageReader_ImageCallback cb,
3821         jstring jOverrideCameraId) {
3822     const int NUM_TEST_IMAGES = 10;
3823     media_status_t mediaRet = AMEDIA_ERROR_UNKNOWN;
3824     int numCameras = 0;
3825     bool pass = false;
3826     PreviewTestCase testCase;
3827     ACameraMetadata* chars = nullptr;
3828 
3829     const char* outPath = (jOutPath == nullptr) ? nullptr :
3830             env->GetStringUTFChars(jOutPath, nullptr);
3831     if (outPath != nullptr) {
3832         ALOGI("%s: out path is %s", __FUNCTION__, outPath);
3833     }
3834 
3835     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
3836     if (ret != ACAMERA_OK) {
3837         // Don't log error here. testcase did it
3838         goto cleanup;
3839     }
3840 
3841     numCameras = testCase.getNumCameras();
3842     if (numCameras < 0) {
3843         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
3844         goto cleanup;
3845     }
3846 
3847     for (int i = 0; i < numCameras; i++) {
3848         const char* cameraId = testCase.getCameraId(i);
3849         if (cameraId == nullptr) {
3850             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
3851             goto cleanup;
3852         }
3853 
3854         {
3855             ACameraMetadata* chars = testCase.getCameraChars(cameraId);
3856             StaticInfo staticInfo(chars);
3857             if (!staticInfo.isColorOutputSupported()) {
3858                 ALOGI("%s: camera %s does not support color output. skipping",
3859                         __FUNCTION__, cameraId);
3860                 ACameraMetadata_free(chars);
3861                 continue;
3862             }
3863             ACameraMetadata_free(chars);
3864         }
3865 
3866         ret = testCase.openCamera(cameraId);
3867         if (ret != ACAMERA_OK) {
3868             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
3869             goto cleanup;
3870         }
3871 
3872         chars = testCase.getCameraChars(i);
3873         if (chars == nullptr) {
3874             LOG_ERROR(errorString, "Get camera %s characteristics failure", cameraId);
3875             goto cleanup;
3876         }
3877         StaticInfo staticInfo(chars);
3878 
3879         usleep(200000); // sleep to give some time for callbacks to happen
3880 
3881         if (testCase.isCameraAvailable(cameraId)) {
3882             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
3883             goto cleanup;
3884         }
3885 
3886         ImageReaderListener readerListener;
3887         AImageReader_ImageListener readerCb { &readerListener, cb };
3888         readerListener.setDumpFilePathBase(outPath);
3889 
3890         int32_t testWidth, testHeight;
3891         switch (format) {
3892             case AIMAGE_FORMAT_JPEG:
3893             case AIMAGE_FORMAT_Y8:
3894             case AIMAGE_FORMAT_HEIC:
3895             case AIMAGE_FORMAT_DEPTH_JPEG:
3896                 if (!staticInfo.getMaxSizeForFormat(format, &testWidth, &testHeight)) {
3897                     // No corresponding format support, skip this device.
3898                     ACameraMetadata_free(chars);
3899                     chars = nullptr;
3900                     ret = testCase.closeCamera();
3901                     if (ret != ACAMERA_OK) {
3902                         LOG_ERROR(errorString, "Camera %s failed to close. ret %d ", cameraId, ret);
3903                         goto cleanup;
3904                     }
3905 
3906                     continue;
3907                 }
3908                 break;
3909             default:
3910                 LOG_ERROR(errorString, "Testcase doesn't yet support format %d", format);
3911                 goto cleanup;
3912         }
3913         mediaRet = testCase.initImageReaderWithErrorLog(
3914                 testWidth, testHeight, format, NUM_TEST_IMAGES,
3915                 &readerCb);
3916         if (mediaRet != AMEDIA_OK) {
3917             // Don't log error here. testcase did it
3918             goto cleanup;
3919         }
3920 
3921         ret = testCase.createCaptureSessionWithLog();
3922         if (ret != ACAMERA_OK) {
3923             // Don't log error here. testcase did it
3924             goto cleanup;
3925         }
3926 
3927         ret = testCase.createRequestsWithErrorLog();
3928         if (ret != ACAMERA_OK) {
3929             // Don't log error here. testcase did it
3930             goto cleanup;
3931         }
3932 
3933         CaptureResultListener resultListener;
3934         ACameraCaptureSession_captureCallbacks resultCb {
3935             &resultListener,
3936             CaptureResultListener::onCaptureStart,
3937             CaptureResultListener::onCaptureProgressed,
3938             CaptureResultListener::onCaptureCompleted,
3939             CaptureResultListener::onCaptureFailed,
3940             CaptureResultListener::onCaptureSequenceCompleted,
3941             CaptureResultListener::onCaptureSequenceAborted,
3942             CaptureResultListener::onCaptureBufferLost
3943         };
3944         resultListener.setRequestSave(true);
3945         ACaptureRequest* requestTemplate = nullptr;
3946         ret = testCase.getStillRequest(&requestTemplate);
3947         if (ret != ACAMERA_OK || requestTemplate == nullptr) {
3948             // Don't log error here. testcase did it
3949             goto cleanup;
3950         }
3951 
3952         // Do some still capture
3953         int lastSeqId = -1;
3954         for (intptr_t capture = 0; capture < NUM_TEST_IMAGES; capture++) {
3955             ACaptureRequest* req = ACaptureRequest_copy(requestTemplate);
3956             ACaptureRequest_setUserContext(req, (void*) capture);
3957             int seqId;
3958             ret = testCase.capture(req, &resultCb, &seqId);
3959             if (ret != ACAMERA_OK) {
3960                 LOG_ERROR(errorString, "Camera %s capture(%" PRIdPTR ") failed. ret %d",
3961                         cameraId, capture, ret);
3962                 goto cleanup;
3963             }
3964             if (capture == NUM_TEST_IMAGES - 1) {
3965                 lastSeqId = seqId;
3966             }
3967             ACaptureRequest_free(req);
3968         }
3969 
3970         // wait until last sequence complete
3971         resultListener.getCaptureSequenceLastFrameNumber(lastSeqId, /*timeoutSec*/ 5);
3972 
3973         std::vector<ACaptureRequest*> completedRequests;
3974         resultListener.getCompletedRequests(&completedRequests);
3975 
3976         if (completedRequests.size() != NUM_TEST_IMAGES) {
3977             LOG_ERROR(errorString, "Camera %s fails to capture %d capture results. Got %zu",
3978                     cameraId, NUM_TEST_IMAGES, completedRequests.size());
3979             goto cleanup;
3980         }
3981 
3982         for (intptr_t i = 0; i < NUM_TEST_IMAGES; i++) {
3983             intptr_t userContext = -1;
3984             ret = ACaptureRequest_getUserContext(completedRequests[i], (void**) &userContext);
3985             if (ret != ACAMERA_OK) {
3986                 LOG_ERROR(errorString, "Camera %s fails to get request user context", cameraId);
3987                 goto cleanup;
3988             }
3989 
3990             if (userContext != i) {
3991                 LOG_ERROR(errorString, "Camera %s fails to return matching user context. "
3992                         "Expect %" PRIdPTR ", got %" PRIdPTR, cameraId, i, userContext);
3993                 goto cleanup;
3994             }
3995         }
3996 
3997         int64_t minFrameDurationNs = staticInfo.getMinFrameDurationFor(
3998                 format, testWidth, testHeight);
3999         if (minFrameDurationNs < 0) {
4000             LOG_ERROR(errorString, "Get camera %s minFrameDuration failed", cameraId);
4001             goto cleanup;
4002         }
4003         int64_t stallDurationNs = (format == AIMAGE_FORMAT_Y8) ? 0 :
4004                 staticInfo.getStallDurationFor(format, testWidth, testHeight);
4005         if (stallDurationNs < 0) {
4006             LOG_ERROR(errorString, "Get camera %s stallDuration failed", cameraId);
4007             goto cleanup;
4008         }
4009 
4010         int64_t expectedDurationNs = (minFrameDurationNs + stallDurationNs) * NUM_TEST_IMAGES;
4011         constexpr int64_t waitPerIterationUs = 100000;
4012         constexpr int64_t usToNs = 1000;
4013         int totalWaitIteration = 50;
4014 
4015         // Allow 1.5x margin
4016         if (expectedDurationNs * 3 / 2 > totalWaitIteration * waitPerIterationUs * usToNs) {
4017             totalWaitIteration = expectedDurationNs * 3 / 2 / waitPerIterationUs / usToNs;
4018         }
4019 
4020         // wait until all capture finished
4021         for (int i = 0; i < totalWaitIteration; i++) {
4022             usleep(waitPerIterationUs);
4023             if (readerListener.onImageAvailableCount() == NUM_TEST_IMAGES) {
4024                 ALOGI("Session take ~%d ms to capture %d images",
4025                         i*100, NUM_TEST_IMAGES);
4026                 break;
4027             }
4028         }
4029 
4030         if (readerListener.onImageAvailableCount() != NUM_TEST_IMAGES) {
4031             LOG_ERROR(errorString, "Camera %s timeout capturing %d images. Got %d",
4032                     cameraId, NUM_TEST_IMAGES, readerListener.onImageAvailableCount());
4033             goto cleanup;
4034         }
4035 
4036         ret = testCase.resetWithErrorLog();
4037         if (ret != ACAMERA_OK) {
4038             // Don't log error here. testcase did it
4039             goto cleanup;
4040         }
4041 
4042         usleep(200000); // sleep to give some time for callbacks to happen
4043 
4044         if (!testCase.isCameraAvailable(cameraId)) {
4045             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
4046             goto cleanup;
4047         }
4048     }
4049 
4050     ret = testCase.deInit();
4051     if (ret != ACAMERA_OK) {
4052         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
4053         goto cleanup;
4054     }
4055 
4056     pass = true;
4057 
4058 cleanup:
4059     if (outPath != nullptr) {
4060         env->ReleaseStringUTFChars(jOutPath, outPath);
4061     }
4062 
4063     if (chars != nullptr) {
4064         ACameraMetadata_free(chars);
4065         chars = nullptr;
4066     }
4067 
4068     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
4069     if (!pass) {
4070         throwAssertionError(env, errorString);
4071     }
4072     return pass;
4073 }
4074 
4075 // Test the camera NDK capture failure path by acquiring the maximum amount of
4076 // ImageReader buffers available. Since there is no circulation of camera
4077 // images, the registered output surface will eventually run out of free buffers
4078 // and start reporting capture errors or lost buffers.
4079 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeCameraDeviceTest_testCameraDeviceCaptureFailureNative(JNIEnv * env,jclass,jstring jOverrideCameraId)4080 Java_android_hardware_camera2_cts_NativeCameraDeviceTest_\
4081 testCameraDeviceCaptureFailureNative(JNIEnv* env, jclass /*clazz*/, jstring jOverrideCameraId) {
4082     const size_t NUM_TEST_IMAGES = 10;
4083     const size_t NUM_FAILED_FRAMES = 3; // Wait for at least 3 consecutive failed capture requests
4084     const int64_t NUM_TOTAL_FRAMES = 60; // Avoid waiting for more than 60 frames
4085     const size_t TEST_WIDTH  = 640;
4086     const size_t TEST_HEIGHT = 480;
4087     media_status_t mediaRet = AMEDIA_ERROR_UNKNOWN;
4088     int numCameras = 0;
4089     bool pass = false;
4090     PreviewTestCase testCase;
4091     uint32_t bufferTimeoutSec = 1;
4092     uint32_t timeoutSec = 10; // It is important to keep this timeout bigger than the framework
4093                               // timeout
4094 
4095     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
4096     if (ret != ACAMERA_OK) {
4097         // Don't log error here. testcase did it
4098         goto exit;
4099     }
4100 
4101     numCameras = testCase.getNumCameras();
4102     if (numCameras < 0) {
4103         LOG_ERROR(errorString, "Testcase returned negative number of cameras: %d", numCameras);
4104         goto exit;
4105     }
4106 
4107     for (int i = 0; i < numCameras; i++) {
4108         const char* cameraId = testCase.getCameraId(i);
4109         if (cameraId == nullptr) {
4110             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
4111             goto exit;
4112         }
4113 
4114         std::unique_ptr<ACameraMetadata> chars(testCase.getCameraChars(i));
4115         if (chars.get() == nullptr) {
4116             LOG_ERROR(errorString, "Get camera %s characteristics failure", cameraId);
4117             goto exit;
4118         }
4119         StaticInfo staticInfo(chars.get());
4120 
4121         if (!staticInfo.isColorOutputSupported()) {
4122             continue;
4123         }
4124 
4125         ret = testCase.openCamera(cameraId);
4126         if (ret != ACAMERA_OK) {
4127             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
4128             goto exit;
4129         }
4130 
4131         usleep(100000); // sleep to give some time for callbacks to happen
4132 
4133         if (testCase.isCameraAvailable(cameraId)) {
4134             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
4135             goto exit;
4136         }
4137 
4138         ImageReaderListener readerListener;
4139         AImageReader_ImageListener readerCb =
4140                 { &readerListener, ImageReaderListener::signalImageCb };
4141         mediaRet = testCase.initImageReaderWithErrorLog(TEST_WIDTH, TEST_HEIGHT,
4142                 AIMAGE_FORMAT_YUV_420_888, NUM_TEST_IMAGES, &readerCb);
4143         if (mediaRet != AMEDIA_OK) {
4144             // Don't log error here. testcase did it
4145             goto exit;
4146         }
4147 
4148         ret = testCase.createCaptureSessionWithLog();
4149         if (ret != ACAMERA_OK) {
4150             // Don't log error here. testcase did it
4151             goto exit;
4152         }
4153 
4154         ret = testCase.createRequestsWithErrorLog();
4155         if (ret != ACAMERA_OK) {
4156             // Don't log error here. testcase did it
4157             goto exit;
4158         }
4159 
4160         CaptureResultListener resultListener;
4161         ACameraCaptureSession_captureCallbacks resultCb {
4162             &resultListener,
4163             CaptureResultListener::onCaptureStart,
4164             CaptureResultListener::onCaptureProgressed,
4165             CaptureResultListener::onCaptureCompleted,
4166             CaptureResultListener::onCaptureFailed,
4167             CaptureResultListener::onCaptureSequenceCompleted,
4168             CaptureResultListener::onCaptureSequenceAborted,
4169             CaptureResultListener::onCaptureBufferLost
4170         };
4171         ACaptureRequest* requestTemplate = nullptr;
4172         ret = testCase.getStillRequest(&requestTemplate);
4173         if (ret != ACAMERA_OK || requestTemplate == nullptr) {
4174             // Don't log error here. testcase did it
4175             goto exit;
4176         }
4177 
4178         int seqId;
4179         ret = testCase.startRepeatingRequest(&seqId, requestTemplate, &resultCb);
4180         if (ret != ACAMERA_OK) {
4181             // Don't log error here. testcase did it
4182             goto exit;
4183         }
4184 
4185         size_t failedRequestCount;
4186         int64_t lastFrameNumber;
4187         int64_t lastFailedRequestNumber = -1;
4188         failedRequestCount = lastFrameNumber = 0;
4189         while ((failedRequestCount < NUM_FAILED_FRAMES) && (lastFrameNumber < NUM_TOTAL_FRAMES)) {
4190             auto frameArrived = resultListener.waitForFrameNumber(lastFrameNumber, timeoutSec);
4191             if (!frameArrived) {
4192                 LOG_ERROR(errorString, "Camera %s timed out waiting on last frame number!",
4193                         cameraId);
4194                 goto exit;
4195             }
4196             readerListener.waitForNextBuffer(bufferTimeoutSec);
4197             auto failedFrameNumber = resultListener.checkForFailureOrLoss(lastFrameNumber) ?
4198                     lastFrameNumber : -1;
4199             if (lastFailedRequestNumber != failedFrameNumber) {
4200                 if ((lastFailedRequestNumber + 1) == failedFrameNumber) {
4201                     failedRequestCount++;
4202                 } else {
4203                     failedRequestCount = 1;
4204                 }
4205                 lastFailedRequestNumber = failedFrameNumber;
4206             }
4207             lastFrameNumber++;
4208         }
4209 
4210         ret = testCase.abortCaptures();
4211         if (ret != ACAMERA_OK) {
4212             LOG_ERROR(errorString, "abort captures failed!");
4213             goto exit;
4214         }
4215 
4216         ret = testCase.resetWithErrorLog();
4217         if (ret != ACAMERA_OK) {
4218             // Don't log error here. testcase did it
4219             goto exit;
4220         }
4221 
4222         usleep(100000); // sleep to give some time for callbacks to happen
4223 
4224         if (!testCase.isCameraAvailable(cameraId)) {
4225             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
4226             goto exit;
4227         }
4228 
4229         if (failedRequestCount < NUM_FAILED_FRAMES) {
4230             LOG_ERROR(errorString, "Unable to receive %zu consecutive capture failures within"
4231                     " %" PRId64 " capture requests", NUM_FAILED_FRAMES, NUM_TOTAL_FRAMES);
4232             goto exit;
4233         }
4234     }
4235 
4236     ret = testCase.deInit();
4237     if (ret != ACAMERA_OK) {
4238         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
4239         goto exit;
4240     }
4241 
4242     pass = true;
4243 
4244 exit:
4245 
4246     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
4247     if (!pass) {
4248         throwAssertionError(env, errorString);
4249     }
4250 
4251     return pass;
4252 }
4253 
4254 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeImageReaderTest_testJpegNative(JNIEnv * env,jclass,jstring jOutPath,jstring jOverrideCameraId)4255 Java_android_hardware_camera2_cts_NativeImageReaderTest_\
4256 testJpegNative(
4257         JNIEnv* env, jclass /*clazz*/, jstring jOutPath,
4258         jstring jOverrideCameraId) {
4259     ALOGV("%s", __FUNCTION__);
4260     return nativeImageReaderTestBase(env, jOutPath, AIMAGE_FORMAT_JPEG,
4261             ImageReaderListener::validateImageCb, jOverrideCameraId);
4262 }
4263 
4264 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeImageReaderTest_testY8Native(JNIEnv * env,jclass,jstring jOutPath,jstring jOverrideCameraId)4265 Java_android_hardware_camera2_cts_NativeImageReaderTest_\
4266 testY8Native(
4267         JNIEnv* env, jclass /*clazz*/, jstring jOutPath,
4268         jstring jOverrideCameraId) {
4269     ALOGV("%s", __FUNCTION__);
4270     return nativeImageReaderTestBase(env, jOutPath, AIMAGE_FORMAT_Y8,
4271             ImageReaderListener::validateImageCb, jOverrideCameraId);
4272 }
4273 
4274 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeImageReaderTest_testHeicNative(JNIEnv * env,jclass,jstring jOutPath,jstring jOverrideCameraId)4275 Java_android_hardware_camera2_cts_NativeImageReaderTest_\
4276 testHeicNative(
4277         JNIEnv* env, jclass /*clazz*/, jstring jOutPath,
4278         jstring jOverrideCameraId) {
4279     ALOGV("%s", __FUNCTION__);
4280     return nativeImageReaderTestBase(env, jOutPath, AIMAGE_FORMAT_HEIC,
4281             ImageReaderListener::validateImageCb, jOverrideCameraId);
4282 }
4283 
4284 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeImageReaderTest_testDepthJpegNative(JNIEnv * env,jclass,jstring jOutPath,jstring jOverrideCameraId)4285 Java_android_hardware_camera2_cts_NativeImageReaderTest_\
4286 testDepthJpegNative(
4287         JNIEnv* env, jclass /*clazz*/, jstring jOutPath,
4288         jstring jOverrideCameraId) {
4289     ALOGV("%s", __FUNCTION__);
4290     return nativeImageReaderTestBase(env, jOutPath, AIMAGE_FORMAT_DEPTH_JPEG,
4291             ImageReaderListener::validateImageCb, jOverrideCameraId);
4292 }
4293 
4294 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeImageReaderTest_testImageReaderCloseAcquiredImagesNative(JNIEnv * env,jclass,jstring jOverrideCameraId)4295 Java_android_hardware_camera2_cts_NativeImageReaderTest_\
4296 testImageReaderCloseAcquiredImagesNative(
4297         JNIEnv* env, jclass /*clazz*/,
4298         jstring jOverrideCameraId) {
4299     ALOGV("%s", __FUNCTION__);
4300     return nativeImageReaderTestBase(env, nullptr, AIMAGE_FORMAT_JPEG,
4301             ImageReaderListener::acquireImageCb, jOverrideCameraId);
4302 }
4303 
4304 template <>
4305 struct std::default_delete<ACameraManager> {
operator ()std::default_delete4306     inline void operator()(ACameraManager* manager) const { ACameraManager_delete(manager); }
4307 };
4308 
4309 class AvailabilityContext {
4310     public:
4311         AvailabilityContext();
4312         ~AvailabilityContext();
4313 
4314         camera_status_t initialize();
4315         int getAcessCallbackCountAndReset();
4316 
4317     private:
4318         std::unique_ptr<ACameraManager> mCameraManager;
4319         std::unique_ptr<CameraServiceListener> mServiceListener;
4320         std::unique_ptr<ACameraManager_ExtendedAvailabilityCallbacks> mServiceCb;
4321 };
4322 
AvailabilityContext()4323 AvailabilityContext::AvailabilityContext() :
4324     mCameraManager(ACameraManager_create()),
4325     mServiceListener(std::make_unique<CameraServiceListener>()),
4326     mServiceCb(std::make_unique<ACameraManager_ExtendedAvailabilityCallbacks>()) {
4327         mServiceCb->availabilityCallbacks.context = mServiceListener.get();
4328         mServiceCb->availabilityCallbacks.onCameraAvailable = CameraServiceListener::onAvailable;
4329         mServiceCb->availabilityCallbacks.onCameraUnavailable =
4330                 CameraServiceListener::onUnavailable;
4331         mServiceCb->onCameraAccessPrioritiesChanged =
4332                 CameraServiceListener::onCameraAccessPrioritiesChanged;
4333         mServiceCb->onPhysicalCameraAvailable =
4334                 CameraServiceListener::onPhysicalCameraAvailable;
4335         mServiceCb->onPhysicalCameraUnavailable =
4336                 CameraServiceListener::onPhysicalCameraUnavailable;
4337 }
4338 
initialize()4339 camera_status_t AvailabilityContext::initialize() {
4340     auto rc = ACameraManager_registerExtendedAvailabilityCallback(mCameraManager.get(),
4341             mServiceCb.get());
4342     if (rc != ACAMERA_OK) {
4343         LOG_ERROR(errorString, "Register availability callback failed: rc %d", rc);
4344         return rc;
4345     }
4346 
4347     ACameraIdList* cameraIdList = nullptr;
4348     rc = ACameraManager_getCameraIdList(mCameraManager.get(), &cameraIdList);
4349     if (rc != ACAMERA_OK) {
4350         LOG_ERROR(errorString, "Get camera id list failed: ret %d", rc);
4351         return rc;
4352     }
4353     ACameraManager_deleteCameraIdList(cameraIdList);
4354 
4355     return rc;
4356 }
4357 
getAcessCallbackCountAndReset()4358 int AvailabilityContext::getAcessCallbackCountAndReset() {
4359     auto ret = mServiceListener->getCameraAccessPrioritiesChangedCount();
4360     mServiceListener->resetCount();
4361     return ret;
4362 }
4363 
~AvailabilityContext()4364 AvailabilityContext::~AvailabilityContext() {
4365     if (mServiceCb != nullptr) {
4366         camera_status_t ret = ACameraManager_unregisterExtendedAvailabilityCallback(
4367                 mCameraManager.get(), mServiceCb.get());
4368         if (ret != ACAMERA_OK) {
4369             ALOGE("Unregister availability callback failed: ret %d", ret);
4370         }
4371     }
4372 }
4373 
4374 extern "C" jlong
Java_android_hardware_multiprocess_camera_cts_CameraEvictionTest_initializeAvailabilityCallbacksNative(JNIEnv * env,jclass)4375 Java_android_hardware_multiprocess_camera_cts_CameraEvictionTest_\
4376 initializeAvailabilityCallbacksNative(
4377         JNIEnv* env, jclass /*clazz*/) {
4378     ALOGV("%s", __FUNCTION__);
4379 
4380     AvailabilityContext *ctx = new AvailabilityContext();
4381 
4382     auto rc = ctx->initialize();
4383     if (rc != ACAMERA_OK) {
4384         delete ctx;
4385         LOG_ERROR(errorString, "Availability context initialization failed: %d", rc);
4386         return 0;
4387     }
4388 
4389     return (jlong) ctx;
4390 }
4391 
4392 extern "C" jint
Java_android_hardware_multiprocess_camera_cts_CameraEvictionTest_getAccessCallbacksCountAndResetNative(JNIEnv * env,jclass,jlong context)4393 Java_android_hardware_multiprocess_camera_cts_CameraEvictionTest_\
4394 getAccessCallbacksCountAndResetNative(
4395         JNIEnv* env, jclass /*clazz*/, jlong context) {
4396     ALOGV("%s", __FUNCTION__);
4397 
4398     if (context == 0) {
4399         LOG_ERROR(errorString, "Invalid availability context");
4400         return 0;
4401     }
4402 
4403     AvailabilityContext* ctx = reinterpret_cast<AvailabilityContext*>(context);
4404     return ctx->getAcessCallbackCountAndReset();
4405 }
4406 
4407 extern "C" void
Java_android_hardware_multiprocess_camera_cts_CameraEvictionTest_releaseAvailabilityCallbacksNative(JNIEnv * env,jclass,jlong context)4408 Java_android_hardware_multiprocess_camera_cts_CameraEvictionTest_\
4409 releaseAvailabilityCallbacksNative(
4410         JNIEnv* env, jclass /*clazz*/, jlong context) {
4411     ALOGV("%s", __FUNCTION__);
4412 
4413     if (context == 0) {
4414         return;
4415     }
4416 
4417     AvailabilityContext* ctx = reinterpret_cast<AvailabilityContext*>(context);
4418     delete ctx;
4419 }
4420 
4421 extern "C" jboolean
Java_android_hardware_camera2_cts_NativeStillCaptureTest_testStillCaptureNative(JNIEnv * env,jclass,jstring jOutPath,jobject jPreviewSurface,jstring jOverrideCameraId)4422 Java_android_hardware_camera2_cts_NativeStillCaptureTest_\
4423 testStillCaptureNative(
4424         JNIEnv* env, jclass /*clazz*/, jstring jOutPath, jobject jPreviewSurface,
4425         jstring jOverrideCameraId) {
4426     ALOGV("%s", __FUNCTION__);
4427     const int NUM_TEST_IMAGES = 10;
4428     media_status_t mediaRet = AMEDIA_ERROR_UNKNOWN;
4429     int numCameras = 0;
4430     bool pass = false;
4431     PreviewTestCase testCase;
4432     ACameraMetadata* chars = nullptr;
4433 
4434     const char* outPath = env->GetStringUTFChars(jOutPath, nullptr);
4435     ALOGI("%s: out path is %s", __FUNCTION__, outPath);
4436 
4437     camera_status_t ret = testCase.initWithErrorLog(env, jOverrideCameraId);
4438     if (ret != ACAMERA_OK) {
4439         // Don't log error here. testcase did it
4440         goto cleanup;
4441     }
4442 
4443     numCameras = testCase.getNumCameras();
4444     if (numCameras < 0) {
4445         LOG_ERROR(errorString, "Testcase returned negavtive number of cameras: %d", numCameras);
4446         goto cleanup;
4447     }
4448 
4449     for (int i = 0; i < numCameras; i++) {
4450         const char* cameraId = testCase.getCameraId(i);
4451         if (cameraId == nullptr) {
4452             LOG_ERROR(errorString, "Testcase returned null camera id for camera %d", i);
4453             goto cleanup;
4454         }
4455 
4456         {
4457             ACameraMetadata* chars = testCase.getCameraChars(cameraId);
4458             StaticInfo staticInfo(chars);
4459             if (!staticInfo.isColorOutputSupported()) {
4460                 ALOGI("%s: camera %s does not support color output. skipping",
4461                         __FUNCTION__, cameraId);
4462                 ACameraMetadata_free(chars);
4463                 continue;
4464             }
4465             ACameraMetadata_free(chars);
4466         }
4467 
4468         ret = testCase.openCamera(cameraId);
4469         if (ret != ACAMERA_OK) {
4470             LOG_ERROR(errorString, "Open camera device %s failure. ret %d", cameraId, ret);
4471             goto cleanup;
4472         }
4473 
4474         chars = testCase.getCameraChars(i);
4475         if (chars == nullptr) {
4476             LOG_ERROR(errorString, "Get camera %s characteristics failure", cameraId);
4477             goto cleanup;
4478         }
4479         StaticInfo staticInfo(chars);
4480 
4481         usleep(100000); // sleep to give some time for callbacks to happen
4482 
4483         if (testCase.isCameraAvailable(cameraId)) {
4484             LOG_ERROR(errorString, "Camera %s should be unavailable now", cameraId);
4485             goto cleanup;
4486         }
4487 
4488         ImageReaderListener readerListener;
4489         AImageReader_ImageListener readerCb {
4490             &readerListener,
4491             ImageReaderListener::validateImageCb
4492         };
4493         readerListener.setDumpFilePathBase(outPath);
4494         int32_t testWidth, testHeight;
4495         if (!staticInfo.getMaxSizeForFormat(AIMAGE_FORMAT_JPEG, &testWidth, &testHeight)) {
4496             goto cleanup;
4497         }
4498         mediaRet = testCase.initImageReaderWithErrorLog(
4499                 testWidth, testHeight, AIMAGE_FORMAT_JPEG, NUM_TEST_IMAGES,
4500                 &readerCb);
4501         if (mediaRet != AMEDIA_OK) {
4502             // Don't log error here. testcase did it
4503             goto cleanup;
4504         }
4505 
4506         ANativeWindow* previewAnw = testCase.initPreviewAnw(env, jPreviewSurface);
4507         if (previewAnw == nullptr) {
4508             LOG_ERROR(errorString, "Null ANW from preview surface!");
4509             goto cleanup;
4510         }
4511 
4512         ret = testCase.createCaptureSessionWithLog();
4513         if (ret != ACAMERA_OK) {
4514             // Don't log error here. testcase did it
4515             goto cleanup;
4516         }
4517 
4518         ret = testCase.createRequestsWithErrorLog();
4519         if (ret != ACAMERA_OK) {
4520             // Don't log error here. testcase did it
4521             goto cleanup;
4522         }
4523 
4524         ret = testCase.startPreview();
4525         if (ret != ACAMERA_OK) {
4526             LOG_ERROR(errorString, "Start preview failed!");
4527             goto cleanup;
4528         }
4529 
4530         // Let preview run some time
4531         sleep(3);
4532 
4533         // Do some still capture
4534         for (int capture = 0; capture < NUM_TEST_IMAGES; capture++) {
4535             ret = testCase.takePicture();
4536             if (ret != ACAMERA_OK) {
4537                 LOG_ERROR(errorString, "Camera %s capture(%d) failed. ret %d",
4538                         cameraId, capture, ret);
4539                 goto cleanup;
4540             }
4541         }
4542 
4543         int64_t minFrameDurationNs = staticInfo.getMinFrameDurationFor(
4544                 AIMAGE_FORMAT_JPEG, testWidth, testHeight);
4545         if (minFrameDurationNs < 0) {
4546             LOG_ERROR(errorString, "Get camera %s minFrameDuration failed", cameraId);
4547             goto cleanup;
4548         }
4549         int64_t stallDurationNs = staticInfo.getStallDurationFor(
4550                 AIMAGE_FORMAT_JPEG, testWidth, testHeight);
4551         if (stallDurationNs < 0) {
4552             LOG_ERROR(errorString, "Get camera %s stallDuration failed", cameraId);
4553             goto cleanup;
4554         }
4555 
4556         int64_t expectedDurationNs = (minFrameDurationNs + stallDurationNs) * NUM_TEST_IMAGES;
4557         constexpr int64_t waitPerIterationUs = 100000;
4558         constexpr int64_t usToNs = 1000;
4559         int totalWaitIteration = 60;
4560 
4561         // Allow 1.5x margin
4562         if (expectedDurationNs * 3 / 2 > totalWaitIteration * waitPerIterationUs * usToNs) {
4563             totalWaitIteration = expectedDurationNs * 3 / 2 / waitPerIterationUs / usToNs;
4564         }
4565 
4566         // wait until all capture finished
4567         for (int i = 0; i < totalWaitIteration; i++) {
4568             usleep(waitPerIterationUs);
4569             if (readerListener.onImageAvailableCount() == NUM_TEST_IMAGES) {
4570                 ALOGI("Session take ~%d ms to capture %d images",
4571                         i*100, NUM_TEST_IMAGES);
4572                 break;
4573             }
4574         }
4575 
4576         if (readerListener.onImageAvailableCount() != NUM_TEST_IMAGES) {
4577             LOG_ERROR(errorString, "Camera %s timeout capturing %d images. Got %d",
4578                     cameraId, NUM_TEST_IMAGES, readerListener.onImageAvailableCount());
4579             testCase.resetWithErrorLog();
4580             goto cleanup;
4581         }
4582 
4583         ret = testCase.resetWithErrorLog();
4584         if (ret != ACAMERA_OK) {
4585             // Don't log error here. testcase did it
4586             goto cleanup;
4587         }
4588 
4589         usleep(100000); // sleep to give some time for callbacks to happen
4590 
4591         if (!testCase.isCameraAvailable(cameraId)) {
4592             LOG_ERROR(errorString, "Camera %s should be available now", cameraId);
4593             goto cleanup;
4594         }
4595     }
4596 
4597     ret = testCase.deInit();
4598     if (ret != ACAMERA_OK) {
4599         LOG_ERROR(errorString, "Testcase deInit failed: ret %d", ret);
4600         goto cleanup;
4601     }
4602 
4603     pass = true;
4604 cleanup:
4605     env->ReleaseStringUTFChars(jOutPath, outPath);
4606 
4607     if (chars != nullptr) {
4608         ACameraMetadata_free(chars);
4609         chars = nullptr;
4610     }
4611 
4612     ALOGI("%s %s", __FUNCTION__, pass ? "pass" : "failed");
4613     if (!pass) {
4614         throwAssertionError(env, errorString);
4615     }
4616     return pass;
4617 }
4618 
4619 extern "C" jboolean
Java_android_hardware_camera2_cts_CaptureResultTest_validateACameraMetadataFromCameraMetadataCriticalTagsNative(JNIEnv * env,jclass,jobject captureResult,jlong javaTimestamp)4620 Java_android_hardware_camera2_cts_CaptureResultTest_\
4621 validateACameraMetadataFromCameraMetadataCriticalTagsNative(
4622         JNIEnv* env, jclass /*clazz*/, jobject captureResult,
4623         jlong javaTimestamp) {
4624     ALOGV("%s", __FUNCTION__);
4625     ACameraMetadata* ndkResult =
4626         ACameraMetadata_fromCameraMetadata(env, captureResult);
4627     if (!ndkResult) {
4628         ALOGE("validateCriticalTags failed: "
4629               "ACameraMetadata_fromCameraMetadata returned nullptr.");
4630         return false;
4631     }
4632 
4633     camera_status_t ret;
4634     ACameraMetadata_const_entry entry;
4635 
4636     ret = ACameraMetadata_getConstEntry(ndkResult, ACAMERA_SENSOR_TIMESTAMP,
4637         &entry);
4638 
4639     if (ret != ACAMERA_OK) {
4640         ALOGE("validateCriticalTags failed: "
4641               "ACameraMetadata_getConstEntry returned %d.", ret);
4642         ACameraMetadata_free(ndkResult);
4643         return false;
4644     }
4645     if (entry.type != ACAMERA_TYPE_INT64) {
4646         ALOGE("validateCriticalTags failed: entry.type is %u but should be %u.",
4647               entry.type, ACAMERA_TYPE_INT64);
4648         ACameraMetadata_free(ndkResult);
4649         return false;
4650     }
4651     if (entry.count != 1) {
4652         ALOGE("validateCriticalTags failed: entry.count is %u but should be %u.",
4653               entry.count, 1);
4654         ACameraMetadata_free(ndkResult);
4655         return false;
4656     }
4657     if (entry.data.i64 == nullptr) {
4658         ALOGE("validateCriticalTags failed: entry.data.i64 is nullptr.");
4659         ACameraMetadata_free(ndkResult);
4660         return false;
4661     }
4662 
4663     const int64_t javaTimestampI64 = static_cast<int64_t>(javaTimestamp);
4664     const int64_t ndkTimestampI64 = *(entry.data.i64);
4665     ALOGV("javaTimestampI64 = %" PRId64 ", ndkTimestampI64 = %" PRId64,
4666           javaTimestampI64, ndkTimestampI64);
4667 
4668     ACameraMetadata_free(ndkResult);
4669 
4670     return (javaTimestampI64 == ndkTimestampI64);
4671 }
4672 
4673 static ACameraMetadata *sStashedMetadata = nullptr;
4674 
4675 // Test holding on to a ACameraMetadata past a single local JNI call
4676 extern "C" jboolean
Java_android_hardware_camera2_cts_CaptureResultTest_stashACameraMetadataFromCameraMetadataNative(JNIEnv * env,jclass,jobject captureResult)4677 Java_android_hardware_camera2_cts_CaptureResultTest_\
4678 stashACameraMetadataFromCameraMetadataNative(
4679         JNIEnv* env, jclass /*clazz*/, jobject captureResult) {
4680     ALOGV("%s", __FUNCTION__);
4681     ACameraMetadata* ndkResult =
4682         ACameraMetadata_fromCameraMetadata(env, captureResult);
4683     if (ndkResult == nullptr) return false;
4684     sStashedMetadata = ndkResult;
4685 
4686     return true;
4687 }
4688 
4689 extern "C" jboolean
Java_android_hardware_camera2_cts_CaptureResultTest_validateStashedACameraMetadataFromCameraMetadataNative(JNIEnv * env,jclass,jlong timestamp)4690 Java_android_hardware_camera2_cts_CaptureResultTest_\
4691 validateStashedACameraMetadataFromCameraMetadataNative(
4692         JNIEnv* env, jclass /*clazz*/, jlong timestamp) {
4693     ALOGV("%s", __FUNCTION__);
4694     if (sStashedMetadata == nullptr) return false;
4695 
4696     camera_status_t ret;
4697     ACameraMetadata_const_entry entry;
4698 
4699     ret = ACameraMetadata_getConstEntry(sStashedMetadata, ACAMERA_SENSOR_TIMESTAMP,
4700         &entry);
4701 
4702     if (ret != ACAMERA_OK) {
4703         ALOGE("validateStashed failed: "
4704               "ACameraMetadata_getConstEntry returned %d.", ret);
4705         ACameraMetadata_free(sStashedMetadata);
4706         sStashedMetadata = nullptr;
4707         return false;
4708     }
4709     if (entry.type != ACAMERA_TYPE_INT64) {
4710         ALOGE("validateStashed failed: entry.type is %u but should be %u.",
4711               entry.type, ACAMERA_TYPE_INT64);
4712         ACameraMetadata_free(sStashedMetadata);
4713         sStashedMetadata = nullptr;
4714         return false;
4715     }
4716     if (entry.count != 1) {
4717         ALOGE("validateStashed failed: entry.count is %u but should be %u.",
4718               entry.count, 1);
4719         ACameraMetadata_free(sStashedMetadata);
4720         sStashedMetadata = nullptr;
4721         return false;
4722     }
4723     if (entry.data.i64 == nullptr) {
4724         ALOGE("validateStashed failed: entry.data.i64 is nullptr.");
4725         ACameraMetadata_free(sStashedMetadata);
4726         sStashedMetadata = nullptr;
4727         return false;
4728     }
4729 
4730     const int64_t javaTimestampI64 = static_cast<int64_t>(timestamp);
4731     const int64_t ndkTimestampI64 = *(entry.data.i64);
4732 
4733     ACameraMetadata_free(sStashedMetadata);
4734     sStashedMetadata = nullptr;
4735     ALOGV("javaTimestampI64 = %" PRId64 ", ndkTimestampI64 = %" PRId64,
4736           javaTimestampI64, ndkTimestampI64);
4737     return (javaTimestampI64 == ndkTimestampI64);
4738 
4739 }
4740 
4741 
4742 
4743 extern "C" jboolean
Java_android_hardware_camera2_cts_CameraManagerTest_validateACameraMetadataFromCameraMetadataCriticalTagsNative(JNIEnv * env,jclass,jobject cameraCharacteristics,jint javaLensFacing)4744 Java_android_hardware_camera2_cts_CameraManagerTest_\
4745 validateACameraMetadataFromCameraMetadataCriticalTagsNative(
4746         JNIEnv* env, jclass /*clazz*/, jobject cameraCharacteristics,
4747         jint javaLensFacing) {
4748     ALOGV("%s", __FUNCTION__);
4749     ACameraMetadata* ndkCharacteristics =
4750         ACameraMetadata_fromCameraMetadata(env, cameraCharacteristics);
4751     if (!ndkCharacteristics) {
4752         ALOGE("validateCriticalTags failed: "
4753               "ACameraMetadata_fromCameraMetadata returned nullptr.");
4754         return false;
4755     }
4756 
4757     camera_status_t ret;
4758     ACameraMetadata_const_entry entry;
4759 
4760     ret = ACameraMetadata_getConstEntry(ndkCharacteristics,
4761         ACAMERA_LENS_FACING, &entry);
4762     ACameraMetadata_free(ndkCharacteristics);
4763 
4764     if (ret != ACAMERA_OK) {
4765         ALOGE("validateCriticalTags failed: "
4766               "ACameraMetadata_getConstEntry returned %d", ret);
4767         return false;
4768     }
4769     if (entry.type != ACAMERA_TYPE_BYTE) {
4770         ALOGE("validateCriticalTags failed: entry.type is %u but should be %u.",
4771               entry.type, ACAMERA_TYPE_BYTE);
4772         return false;
4773     }
4774     if (entry.count != 1) {
4775         ALOGE("validateCriticalTags failed: entry.count is %u but should be %u.",
4776               entry.count, 1);
4777         return false;
4778     }
4779     if (entry.data.u8 == nullptr) {
4780         ALOGE("validateCriticalTags failed: entry.data.u8 is nullptr.");
4781         return false;
4782     }
4783 
4784     const uint8_t javaLensFacingU8 = static_cast<uint8_t>(javaLensFacing);
4785     const uint8_t ndkLensFacingU8 = *(entry.data.u8);
4786     ALOGV("javaLensFacingU8 = %d, ndkLensFacingU8 = %d",
4787           javaLensFacingU8, ndkLensFacingU8);
4788     return (javaLensFacingU8 == ndkLensFacingU8);
4789 }
4790