1 /*
2 * Copyright (C) 2024 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
18 #define LOG_TAG "CameraOpenerJni"
19 #define LOG_NDEBUG 0
20
21 #include <android/log.h>
22 #include <log/log.h>
23
24 #include <chrono>
25 #include <condition_variable>
26 #include <memory>
27 #include <mutex>
28 #include <thread>
29
30 #include "camera/NdkCameraManager.h"
31 #include "media/NdkImage.h"
32 #include "media/NdkImageReader.h"
33
34 namespace {
35
36 template <typename T, void (*free_ptr)(T*)>
37 class Auto : public std::unique_ptr<T, void (*)(T*)> {
38 public:
Auto()39 Auto() : std::unique_ptr<T, void (*)(T*)>(nullptr, free_ptr) {}
Auto(T * t)40 Auto(T* t) : std::unique_ptr<T, void (*)(T*)>(t, free_ptr) {}
41 };
42
43 class CameraOpenerJni {
44 public:
CameraOpenerJni()45 CameraOpenerJni()
46 : mCameraManager(ACameraManager_create()),
47 mCameraDeviceListener(*this),
48 mCameraDeviceCb(&mCameraDeviceListener, CameraDeviceListener::onDisconnectedStatic,
49 CameraDeviceListener::onErrorStatic),
50 mImgReaderAnw(nullptr),
51 mImgReaderListener(),
52 mImgReaderCb(&mImgReaderListener, ImageReaderListener::signalImageStatic),
53 mCaptureSessionListener(),
54 mCaptureSessionCb(&mCaptureSessionListener, CaptureSessionListener::onClosed,
55 CaptureSessionListener::onReady, CaptureSessionListener::onActive),
56 mCaptureResultListener(*this),
57 mCaptureResultCb(&mCaptureResultListener, CaptureResultListener::onCaptureStart,
58 CaptureResultListener::onCaptureProgressed,
59 CaptureResultListener::onCaptureCompletedStatic,
60 CaptureResultListener::onCaptureFailedStatic,
61 CaptureResultListener::onCaptureSequenceCompleted,
62 CaptureResultListener::onCaptureSequenceAborted,
63 CaptureResultListener::onCaptureBufferLost) {}
64
hasCamera()65 bool hasCamera() {
66 ACameraIdList* cameraIdList = nullptr;
67 auto rc = ACameraManager_getCameraIdList(mCameraManager.get(), &cameraIdList);
68 if (rc != ACAMERA_OK) {
69 ALOGE("Get camera id list failed: ret %d", rc);
70 return false;
71 }
72 jboolean result = cameraIdList->numCameras > 0;
73 mCameraIdList.reset(cameraIdList);
74 return result;
75 }
76
openCamera()77 int openCamera() {
78 const char* cameraId = mCameraIdList->cameraIds[0];
79
80 ACameraDevice* device = nullptr;
81 auto rc = ACameraManager_openCamera(mCameraManager.get(), cameraId, &mCameraDeviceCb,
82 &device);
83 if (rc != ACAMERA_OK) {
84 ALOGE("Open camera failed: ret %d", rc);
85 return rc;
86 }
87
88 mCameraDevice.reset(device);
89
90 return ACAMERA_OK;
91 }
92
openCameraStream(bool shouldRepeat)93 int openCameraStream(bool shouldRepeat) {
94 const char* cameraId = mCameraIdList->cameraIds[0];
95 ACameraMetadata* chars = nullptr;
96
97 auto rc = ACameraManager_getCameraCharacteristics(mCameraManager.get(), cameraId, &chars);
98 if (rc != ACAMERA_OK || chars == nullptr) {
99 ALOGE("Get camera %s characteristics failure. ret %d, chars %p", cameraId, rc, chars);
100 return rc;
101 }
102
103 mCameraCharacteristics.reset(chars);
104 int width = 0, height = 0;
105 rc = getPreviewSize(width, height);
106 if (rc != ACAMERA_OK) {
107 return rc;
108 }
109
110 media_status_t mediaRc = createImageReader(width, height);
111 if (mediaRc != AMEDIA_OK) {
112 return mediaRc;
113 }
114
115 rc = createCaptureSessionOutputContainer();
116 if (rc != ACAMERA_OK) {
117 return rc;
118 }
119
120 rc = ACameraDevice_isSessionConfigurationSupported(mCameraDevice.get(),
121 mOutputContainer.get());
122 if (rc != ACAMERA_OK) {
123 ALOGE("isSessionConfigurationSupported returned %d, device %p outputContainer %p", rc,
124 mCameraDevice.get(), mOutputContainer.get());
125 return rc;
126 }
127
128 ACameraCaptureSession* captureSession = nullptr;
129 rc = ACameraDevice_createCaptureSessionWithSessionParameters(mCameraDevice.get(),
130 mOutputContainer.get(),
131 /*sessionParameters=*/nullptr,
132 &mCaptureSessionCb,
133 &captureSession);
134 if (rc != ACAMERA_OK || captureSession == nullptr) {
135 ALOGE("Create session for camera %s failed. ret %d session %p", cameraId, rc,
136 captureSession);
137 if (rc == ACAMERA_OK) {
138 rc = ACAMERA_ERROR_UNKNOWN; // ret OK but session is null
139 }
140 return rc;
141 }
142
143 mCaptureSession.reset(captureSession);
144
145 rc = createCaptureRequest(shouldRepeat ? TEMPLATE_PREVIEW : TEMPLATE_STILL_CAPTURE);
146 if (rc != ACAMERA_OK) {
147 return rc;
148 }
149
150 ACaptureRequest* requests[] = {mCaptureRequest.get()};
151
152 if (shouldRepeat) {
153 rc = ACameraCaptureSession_setRepeatingRequest(mCaptureSession.get(), &mCaptureResultCb,
154 /*numRequests=*/1, requests,
155 /*captureSequenceId=*/nullptr);
156 if (rc != ACAMERA_OK) {
157 ALOGE("%s: Failed to setRepeatingRequest %d", __FUNCTION__, rc);
158 return rc;
159 }
160 } else {
161 rc = ACameraCaptureSession_capture(mCaptureSession.get(), &mCaptureResultCb,
162 /*numRequests=*/1, requests,
163 /*captureSequenceId=*/nullptr);
164 if (rc != ACAMERA_OK) {
165 ALOGE("%s: Failed to capture %d", __FUNCTION__, rc);
166 return rc;
167 }
168 }
169
170 {
171 std::unique_lock<std::mutex> l(mMutex);
172 if (!mFirstCaptureCompleted && !mStoppedRepeating) {
173 ALOGV("%s: %p waiting for first capture", __FUNCTION__, this);
174 auto timeout = std::chrono::seconds(10);
175 if (!mStateChanged.wait_for(l, timeout, [this]() {
176 ALOGV("%s: wakeup mFirstCaptureCompleted %d mStoppedRepeating %d",
177 __FUNCTION__, mFirstCaptureCompleted, mStoppedRepeating);
178 return mFirstCaptureCompleted || mStoppedRepeating;
179 })) {
180 ALOGE("Timed out waiting for capture to complete.");
181 return ACAMERA_ERROR_UNKNOWN;
182 }
183 }
184
185 if (mStoppedRepeating) {
186 if (mErrorCode != 0) {
187 ALOGE("%s: Stopped repeating (error %d)", __FUNCTION__, mErrorCode);
188 return mErrorCode;
189 } else {
190 ALOGE("%s: Stopped repeating for unknown reason", __FUNCTION__);
191 return ACAMERA_ERROR_UNKNOWN;
192 }
193 }
194 }
195
196 ALOGV("%s: exit", __FUNCTION__);
197 return ACAMERA_OK;
198 }
199
waitStopRepeating()200 int waitStopRepeating() {
201 std::unique_lock<std::mutex> l(mMutex);
202 if (!mStoppedRepeating) {
203 auto timeout = std::chrono::seconds(30);
204 if (!mStateChanged.wait_for(l, timeout, [this]() {
205 ALOGV("%s: wakeup %d", __FUNCTION__, mStoppedRepeating);
206 return mStoppedRepeating;
207 })) {
208 ALOGE("Timed out waiting for stream to stop.");
209 return ACAMERA_ERROR_UNKNOWN;
210 }
211 }
212 return mErrorCode;
213 }
214
stopRepeating()215 int stopRepeating() {
216 ALOGV("Enter %s", __FUNCTION__);
217 int rc = ACAMERA_OK;
218 {
219 std::unique_lock<std::mutex> l(mMutex);
220 ALOGV("%s: mStoppedRepeating %d", __FUNCTION__, mStoppedRepeating);
221 if (!mStoppedRepeating) {
222 mStoppedRepeating = true;
223 rc = ACameraCaptureSession_stopRepeating(mCaptureSession.get());
224 }
225 }
226
227 ALOGV("%s: notifying", __FUNCTION__);
228 mStateChanged.notify_all();
229 return rc;
230 }
231
signalStoppedRepeating(int errorCode)232 void signalStoppedRepeating(int errorCode) {
233 {
234 std::lock_guard<std::mutex> l(mMutex);
235 mStoppedRepeating = true;
236 if (mErrorCode == 0) {
237 mErrorCode = errorCode;
238 }
239 }
240
241 ALOGV("%s: notifying", __FUNCTION__);
242 mStateChanged.notify_all();
243 }
244
onCaptureCompleted()245 void onCaptureCompleted() {
246 {
247 std::lock_guard<std::mutex> l(mMutex);
248 mFirstCaptureCompleted = true;
249 }
250
251 ALOGV("%s: %p notifying", __FUNCTION__, this);
252 mStateChanged.notify_all();
253 }
254
onCaptureFailed(ACameraCaptureFailure * failure)255 void onCaptureFailed(ACameraCaptureFailure* failure) {
256 if (failure == nullptr) {
257 ALOGE("%s: null failure", __FUNCTION__);
258 return;
259 }
260 ALOGV("%s: frameNumber %" PRId64 " reason %d sequenceId %d wasImageCaptured %d",
261 __FUNCTION__, failure->frameNumber, failure->reason, failure->sequenceId,
262 failure->wasImageCaptured);
263 }
264
checkNullObj(void * obj,const char * func)265 static bool checkNullObj(void* obj, const char* func) {
266 if (obj == nullptr) {
267 ALOGE("%s: null obj", func);
268 return true;
269 }
270 return false;
271 }
272
273 class CameraDeviceListener {
274 public:
CameraDeviceListener(CameraOpenerJni & parent)275 CameraDeviceListener(CameraOpenerJni& parent) : mParent(parent) {}
276
onDisconnectedStatic(void * obj,ACameraDevice * device)277 static void onDisconnectedStatic(void* obj, ACameraDevice* device) {
278 if (checkNullObj(obj, __FUNCTION__)) return;
279 reinterpret_cast<CameraDeviceListener*>(obj)->onDisconnected(device);
280 }
281
onErrorStatic(void * obj,ACameraDevice * device,int errorCode)282 static void onErrorStatic(void* obj, ACameraDevice* device, int errorCode) {
283 if (checkNullObj(obj, __FUNCTION__)) return;
284 reinterpret_cast<CameraDeviceListener*>(obj)->onError(device, errorCode);
285 }
286
closeDevice(ACameraDevice * device)287 static void closeDevice(ACameraDevice* device) {
288 auto rc = ACameraDevice_close(device);
289 if (rc != ACAMERA_OK) {
290 ALOGE("Close camera failed: ret %d", rc);
291 }
292 }
293
onDisconnected(ACameraDevice *)294 void onDisconnected(ACameraDevice* /*device*/) {
295 ALOGV("%s", __FUNCTION__);
296 mParent.signalStoppedRepeating(0);
297 }
298
onError(ACameraDevice *,int errorCode)299 void onError(ACameraDevice* /*device*/, int errorCode) {
300 ALOGV("%s: %d", __FUNCTION__, errorCode);
301 mParent.signalStoppedRepeating(errorCode);
302 }
303
304 private:
305 CameraOpenerJni& mParent;
306 };
307
308 class ImageReaderListener {
309 public:
signalImageStatic(void * obj,AImageReader * reader)310 static void signalImageStatic(void* obj, AImageReader* reader) {
311 if (checkNullObj(obj, __FUNCTION__)) return;
312 reinterpret_cast<ImageReaderListener*>(obj)->signalImage(reader);
313 }
314
signalImage(AImageReader * reader)315 void signalImage(AImageReader* reader) {
316 AImage* img = nullptr;
317 media_status_t rc = AImageReader_acquireNextImage(reader, &img);
318 if (rc != AMEDIA_OK || img == nullptr) {
319 ALOGE("%s: acquire image from reader %p failed! ret: %d, img %p", __FUNCTION__,
320 reader, rc, img);
321 return;
322 }
323 AImage_delete(img);
324 }
325 };
326
327 class CaptureSessionListener {
328 public:
onClosed(void * obj,ACameraCaptureSession * session)329 static void onClosed([[maybe_unused]] void* obj, ACameraCaptureSession* session) {
330 ALOGV("%s: %p", __FUNCTION__, session);
331 }
332
onReady(void * obj,ACameraCaptureSession * session)333 static void onReady([[maybe_unused]] void* obj, ACameraCaptureSession* session) {
334 ALOGV("%s: %p", __FUNCTION__, session);
335 }
336
onActive(void * obj,ACameraCaptureSession * session)337 static void onActive([[maybe_unused]] void* obj, ACameraCaptureSession* session) {
338 ALOGV("%s: %p", __FUNCTION__, session);
339 }
340 };
341
342 class CaptureResultListener {
343 public:
CaptureResultListener(CameraOpenerJni & parent)344 CaptureResultListener(CameraOpenerJni& parent) : mParent(parent) {}
345
onCaptureStart(void *,ACameraCaptureSession *,const ACaptureRequest *,int64_t)346 static void onCaptureStart(void* /*obj*/, ACameraCaptureSession* /*session*/,
347 const ACaptureRequest* /*request*/, int64_t /*timestamp*/) {
348 ALOGV("%s", __FUNCTION__);
349 }
350
onCaptureProgressed(void *,ACameraCaptureSession *,ACaptureRequest *,const ACameraMetadata *)351 static void onCaptureProgressed(void* /*obj*/, ACameraCaptureSession* /*session*/,
352 ACaptureRequest* /*request*/,
353 const ACameraMetadata* /*result*/) {
354 ALOGV("%s", __FUNCTION__);
355 }
356
onCaptureCompletedStatic(void * obj,ACameraCaptureSession *,ACaptureRequest *,const ACameraMetadata *)357 static void onCaptureCompletedStatic(void* obj, ACameraCaptureSession* /*session*/,
358 ACaptureRequest* /*request*/,
359 const ACameraMetadata* /*result*/) {
360 ALOGV("%s", __FUNCTION__);
361 if (checkNullObj(obj, __FUNCTION__)) return;
362 reinterpret_cast<CaptureResultListener*>(obj)->onCaptureCompleted();
363 }
364
onCaptureFailedStatic(void * obj,ACameraCaptureSession *,ACaptureRequest *,ACameraCaptureFailure * failure)365 static void onCaptureFailedStatic(void* obj, ACameraCaptureSession* /*session*/,
366 ACaptureRequest* /*request*/,
367 ACameraCaptureFailure* failure) {
368 ALOGV("%s", __FUNCTION__);
369 if (checkNullObj(obj, __FUNCTION__)) return;
370 reinterpret_cast<CaptureResultListener*>(obj)->onCaptureFailed(failure);
371 }
372
onCaptureSequenceCompleted(void *,ACameraCaptureSession *,int,int64_t frameNumber)373 static void onCaptureSequenceCompleted(void* /*obj*/, ACameraCaptureSession* /*session*/,
374 int /*sequenceId*/, int64_t frameNumber) {
375 ALOGV("%s: frameNumber %" PRId64, __FUNCTION__, frameNumber);
376 }
377
onCaptureSequenceAborted(void *,ACameraCaptureSession *,int)378 static void onCaptureSequenceAborted(void* /*obj*/, ACameraCaptureSession* /*session*/,
379 int /*sequenceId*/) {
380 ALOGV("%s", __FUNCTION__);
381 }
382
onCaptureBufferLost(void *,ACameraCaptureSession *,ACaptureRequest *,ANativeWindow *,int64_t frameNumber)383 static void onCaptureBufferLost(void* /*obj*/, ACameraCaptureSession* /*session*/,
384 ACaptureRequest* /*request*/, ANativeWindow* /*window*/,
385 int64_t frameNumber) {
386 ALOGV("%s: frameNumber %" PRId64, __FUNCTION__, frameNumber);
387 }
388
onCaptureCompleted()389 void onCaptureCompleted() { mParent.onCaptureCompleted(); }
390
onCaptureFailed(ACameraCaptureFailure * failure)391 void onCaptureFailed(ACameraCaptureFailure* failure) { mParent.onCaptureFailed(failure); }
392
393 private:
394 CameraOpenerJni& mParent;
395 };
396
397 private:
getPreviewSize(int & w,int & h)398 camera_status_t getPreviewSize(int& w, int& h) {
399 ACameraMetadata_const_entry entry;
400 auto rc = ACameraMetadata_getConstEntry(mCameraCharacteristics.get(),
401 ACAMERA_SCALER_AVAILABLE_STREAM_CONFIGURATIONS,
402 &entry);
403 if (rc != ACAMERA_OK) {
404 ALOGE("Failed to get available stream configurations: %d", rc);
405 return rc;
406 }
407
408 for (uint32_t i = 0; i < entry.count; i += 4) {
409 if (entry.data.i32[i] == AIMAGE_FORMAT_JPEG &&
410 entry.data.i32[i + 3] == ACAMERA_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT) {
411 w = entry.data.i32[i + 1];
412 h = entry.data.i32[i + 2];
413 return ACAMERA_OK;
414 }
415 }
416
417 ALOGE("Could not find preview size for JPEG format");
418 return ACAMERA_ERROR_METADATA_NOT_FOUND;
419 }
420
createImageReader(int width,int height)421 media_status_t createImageReader(int width, int height) {
422 AImageReader* reader = nullptr;
423
424 auto rc = AImageReader_new(width, height, AIMAGE_FORMAT_JPEG, /*maxImages=*/1, &reader);
425 if (rc != AMEDIA_OK) {
426 ALOGE("Failed to create image reader: %d", rc);
427 return rc;
428 }
429 if (reader == nullptr) {
430 ALOGE("Null image reader created.");
431 return AMEDIA_ERROR_UNKNOWN;
432 }
433
434 mImgReader.reset(reader);
435 rc = AImageReader_setImageListener(reader, &mImgReaderCb);
436 if (rc != AMEDIA_OK) {
437 ALOGE("Set AImageReader listener failed. ret %d", rc);
438 return rc;
439 }
440
441 rc = AImageReader_getWindow(reader, &mImgReaderAnw);
442 if (rc != AMEDIA_OK) {
443 ALOGE("AImageReader_getWindow failed. ret %d", rc);
444 return rc;
445 }
446 if (mImgReaderAnw == nullptr) {
447 ALOGE("Null ANW from AImageReader!");
448 return AMEDIA_ERROR_UNKNOWN;
449 }
450
451 return AMEDIA_OK;
452 }
453
createCaptureSessionOutputContainer()454 camera_status_t createCaptureSessionOutputContainer() {
455 ACaptureSessionOutputContainer* outputContainer = nullptr;
456 auto rc = ACaptureSessionOutputContainer_create(&outputContainer);
457 if (rc != ACAMERA_OK) {
458 ALOGE("Create capture session output container failed. ret %d", rc);
459 return rc;
460 }
461
462 mOutputContainer.reset(outputContainer);
463
464 ACaptureSessionOutput* output = nullptr;
465 rc = ACaptureSessionOutput_create(mImgReaderAnw, &output);
466 if (rc != ACAMERA_OK || output == nullptr) {
467 ALOGE("Session image reader output create fail! ret %d output %p", rc, output);
468 if (rc == ACAMERA_OK) {
469 rc = ACAMERA_ERROR_UNKNOWN; // ret OK but output is null
470 }
471 return rc;
472 }
473
474 mOutput.reset(output);
475
476 rc = ACaptureSessionOutputContainer_add(outputContainer, output);
477 if (rc != ACAMERA_OK) {
478 ALOGE("Session image reader output add failed! ret %d", rc);
479 return rc;
480 }
481
482 return ACAMERA_OK;
483 }
484
createCaptureRequest(ACameraDevice_request_template requestTemplate)485 camera_status_t createCaptureRequest(ACameraDevice_request_template requestTemplate) {
486 ACaptureRequest* request = nullptr;
487 auto rc =
488 ACameraDevice_createCaptureRequest(mCameraDevice.get(), requestTemplate, &request);
489 if (rc != ACAMERA_OK) {
490 ALOGE("Create capture request failed. ret %d", rc);
491 return rc;
492 }
493
494 mCaptureRequest.reset(request);
495
496 ACameraOutputTarget* outputTarget = nullptr;
497 rc = ACameraOutputTarget_create(mImgReaderAnw, &outputTarget);
498 if (rc != ACAMERA_OK) {
499 ALOGE("Create request reader output target failed. ret %d", rc);
500 return rc;
501 }
502
503 mOutputTarget.reset(outputTarget);
504
505 rc = ACaptureRequest_addTarget(request, outputTarget);
506 if (rc != ACAMERA_OK) {
507 ALOGE("Add capture request output failed. ret %d", rc);
508 return rc;
509 }
510
511 return ACAMERA_OK;
512 }
513
514 Auto<ACameraManager, ACameraManager_delete> mCameraManager;
515 Auto<ACameraIdList, ACameraManager_deleteCameraIdList> mCameraIdList;
516 CameraDeviceListener mCameraDeviceListener;
517 ACameraDevice_StateCallbacks mCameraDeviceCb;
518 Auto<ACameraDevice, CameraDeviceListener::closeDevice> mCameraDevice;
519 Auto<ACameraMetadata, ACameraMetadata_free> mCameraCharacteristics;
520 Auto<AImageReader, AImageReader_delete> mImgReader;
521 ANativeWindow* mImgReaderAnw;
522 ImageReaderListener mImgReaderListener;
523 AImageReader_ImageListener mImgReaderCb;
524 Auto<ACaptureSessionOutputContainer, ACaptureSessionOutputContainer_free> mOutputContainer;
525 Auto<ACaptureSessionOutput, ACaptureSessionOutput_free> mOutput;
526 Auto<ACameraCaptureSession, ACameraCaptureSession_close> mCaptureSession;
527 CaptureSessionListener mCaptureSessionListener;
528 ACameraCaptureSession_stateCallbacks mCaptureSessionCb;
529 Auto<ACaptureRequest, ACaptureRequest_free> mCaptureRequest;
530 Auto<ACameraOutputTarget, ACameraOutputTarget_free> mOutputTarget;
531 CaptureResultListener mCaptureResultListener;
532 ACameraCaptureSession_captureCallbacks mCaptureResultCb;
533 std::mutex mMutex;
534 std::condition_variable mStateChanged;
535 bool mFirstCaptureCompleted = false;
536 bool mStoppedRepeating = false;
537 int mErrorCode = 0;
538 };
539
540 static std::unique_ptr<CameraOpenerJni> sThis = nullptr;
541
checkNullThis(const char * func)542 static bool checkNullThis(const char* func) {
543 if (sThis == nullptr) {
544 ALOGE("%s: sThis is null", func);
545 return true;
546 }
547 return false;
548 }
549
550 } // namespace
551
552 extern "C" {
553
Java_android_security_cts_camera_open_CameraOpener_nativeInit()554 void Java_android_security_cts_camera_open_CameraOpener_nativeInit() {
555 ALOGV("Enter %s", __FUNCTION__);
556 sThis = std::make_unique<CameraOpenerJni>();
557 }
558
Java_android_security_cts_camera_open_CameraOpener_nativeCleanup()559 void Java_android_security_cts_camera_open_CameraOpener_nativeCleanup() {
560 ALOGV("Enter %s", __FUNCTION__);
561 sThis = nullptr;
562 }
563
Java_android_security_cts_camera_open_CameraOpener_nativeHasCamera()564 jboolean Java_android_security_cts_camera_open_CameraOpener_nativeHasCamera() {
565 if (checkNullThis(__FUNCTION__)) return false;
566 return sThis->hasCamera();
567 }
568
Java_android_security_cts_camera_open_CameraOpener_nativeOpenCamera()569 jint Java_android_security_cts_camera_open_CameraOpener_nativeOpenCamera() {
570 if (checkNullThis(__FUNCTION__)) return ACAMERA_ERROR_UNKNOWN;
571 return sThis->openCamera();
572 }
573
Java_android_security_cts_camera_open_CameraOpener_nativeOpenCameraStream(jboolean shouldRepeat)574 jint Java_android_security_cts_camera_open_CameraOpener_nativeOpenCameraStream(
575 jboolean shouldRepeat) {
576 if (checkNullThis(__FUNCTION__)) return ACAMERA_ERROR_UNKNOWN;
577 return sThis->openCameraStream(shouldRepeat);
578 }
579
Java_android_security_cts_camera_open_CameraOpener_nativeWaitStopRepeating()580 jint Java_android_security_cts_camera_open_CameraOpener_nativeWaitStopRepeating() {
581 if (checkNullThis(__FUNCTION__)) return ACAMERA_ERROR_UNKNOWN;
582 return sThis->waitStopRepeating();
583 }
584
Java_android_security_cts_camera_open_CameraOpener_nativeStopRepeating()585 jint Java_android_security_cts_camera_open_CameraOpener_nativeStopRepeating() {
586 if (checkNullThis(__FUNCTION__)) return ACAMERA_ERROR_UNKNOWN;
587 return sThis->stopRepeating();
588 }
589 }
590