• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2013 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #define LOG_TAG "Camera3-Device"
18 #define ATRACE_TAG ATRACE_TAG_CAMERA
19 //#define LOG_NDEBUG 0
20 //#define LOG_NNDEBUG 0  // Per-frame verbose logging
21 
22 #ifdef LOG_NNDEBUG
23 #define ALOGVV(...) ALOGV(__VA_ARGS__)
24 #else
25 #define ALOGVV(...) ((void)0)
26 #endif
27 
28 // Convenience macro for transient errors
29 #define CLOGE(fmt, ...) ALOGE("Camera %d: %s: " fmt, mId, __FUNCTION__, \
30             ##__VA_ARGS__)
31 
32 // Convenience macros for transitioning to the error state
33 #define SET_ERR(fmt, ...) setErrorState(   \
34     "%s: " fmt, __FUNCTION__,              \
35     ##__VA_ARGS__)
36 #define SET_ERR_L(fmt, ...) setErrorStateLocked( \
37     "%s: " fmt, __FUNCTION__,                    \
38     ##__VA_ARGS__)
39 
40 #include <inttypes.h>
41 
42 #include <utils/Log.h>
43 #include <utils/Trace.h>
44 #include <utils/Timers.h>
45 
46 #include "CameraService.h"
47 #include "utils/CameraTraces.h"
48 #include "mediautils/SchedulingPolicyService.h"
49 #include "device3/Camera3Device.h"
50 #include "device3/Camera3OutputStream.h"
51 #include "device3/Camera3InputStream.h"
52 #include "device3/Camera3ZslStream.h"
53 #include "device3/Camera3DummyStream.h"
54 #include "CameraService.h"
55 
56 using namespace android::camera3;
57 
58 namespace android {
59 
Camera3Device(int id)60 Camera3Device::Camera3Device(int id):
61         mId(id),
62         mIsConstrainedHighSpeedConfiguration(false),
63         mHal3Device(NULL),
64         mStatus(STATUS_UNINITIALIZED),
65         mStatusWaiters(0),
66         mUsePartialResult(false),
67         mNumPartialResults(1),
68         mNextResultFrameNumber(0),
69         mNextReprocessResultFrameNumber(0),
70         mNextShutterFrameNumber(0),
71         mNextReprocessShutterFrameNumber(0),
72         mListener(NULL)
73 {
74     ATRACE_CALL();
75     camera3_callback_ops::notify = &sNotify;
76     camera3_callback_ops::process_capture_result = &sProcessCaptureResult;
77     ALOGV("%s: Created device for camera %d", __FUNCTION__, id);
78 }
79 
~Camera3Device()80 Camera3Device::~Camera3Device()
81 {
82     ATRACE_CALL();
83     ALOGV("%s: Tearing down for camera id %d", __FUNCTION__, mId);
84     disconnect();
85 }
86 
getId() const87 int Camera3Device::getId() const {
88     return mId;
89 }
90 
91 /**
92  * CameraDeviceBase interface
93  */
94 
initialize(CameraModule * module)95 status_t Camera3Device::initialize(CameraModule *module)
96 {
97     ATRACE_CALL();
98     Mutex::Autolock il(mInterfaceLock);
99     Mutex::Autolock l(mLock);
100 
101     ALOGV("%s: Initializing device for camera %d", __FUNCTION__, mId);
102     if (mStatus != STATUS_UNINITIALIZED) {
103         CLOGE("Already initialized!");
104         return INVALID_OPERATION;
105     }
106 
107     /** Open HAL device */
108 
109     status_t res;
110     String8 deviceName = String8::format("%d", mId);
111 
112     camera3_device_t *device;
113 
114     ATRACE_BEGIN("camera3->open");
115     res = module->open(deviceName.string(),
116             reinterpret_cast<hw_device_t**>(&device));
117     ATRACE_END();
118 
119     if (res != OK) {
120         SET_ERR_L("Could not open camera: %s (%d)", strerror(-res), res);
121         return res;
122     }
123 
124     /** Cross-check device version */
125     if (device->common.version < CAMERA_DEVICE_API_VERSION_3_0) {
126         SET_ERR_L("Could not open camera: "
127                 "Camera device should be at least %x, reports %x instead",
128                 CAMERA_DEVICE_API_VERSION_3_0,
129                 device->common.version);
130         device->common.close(&device->common);
131         return BAD_VALUE;
132     }
133 
134     camera_info info;
135     res = CameraService::filterGetInfoErrorCode(module->getCameraInfo(
136         mId, &info));
137     if (res != OK) return res;
138 
139     if (info.device_version != device->common.version) {
140         SET_ERR_L("HAL reporting mismatched camera_info version (%x)"
141                 " and device version (%x).",
142                 info.device_version, device->common.version);
143         device->common.close(&device->common);
144         return BAD_VALUE;
145     }
146 
147     /** Initialize device with callback functions */
148 
149     ATRACE_BEGIN("camera3->initialize");
150     res = device->ops->initialize(device, this);
151     ATRACE_END();
152 
153     if (res != OK) {
154         SET_ERR_L("Unable to initialize HAL device: %s (%d)",
155                 strerror(-res), res);
156         device->common.close(&device->common);
157         return BAD_VALUE;
158     }
159 
160     /** Start up status tracker thread */
161     mStatusTracker = new StatusTracker(this);
162     res = mStatusTracker->run(String8::format("C3Dev-%d-Status", mId).string());
163     if (res != OK) {
164         SET_ERR_L("Unable to start status tracking thread: %s (%d)",
165                 strerror(-res), res);
166         device->common.close(&device->common);
167         mStatusTracker.clear();
168         return res;
169     }
170 
171     bool aeLockAvailable = false;
172     camera_metadata_ro_entry aeLockAvailableEntry;
173     res = find_camera_metadata_ro_entry(info.static_camera_characteristics,
174             ANDROID_CONTROL_AE_LOCK_AVAILABLE, &aeLockAvailableEntry);
175     if (res == OK && aeLockAvailableEntry.count > 0) {
176         aeLockAvailable = (aeLockAvailableEntry.data.u8[0] ==
177                 ANDROID_CONTROL_AE_LOCK_AVAILABLE_TRUE);
178     }
179 
180     /** Start up request queue thread */
181     mRequestThread = new RequestThread(this, mStatusTracker, device, aeLockAvailable);
182     res = mRequestThread->run(String8::format("C3Dev-%d-ReqQueue", mId).string());
183     if (res != OK) {
184         SET_ERR_L("Unable to start request queue thread: %s (%d)",
185                 strerror(-res), res);
186         device->common.close(&device->common);
187         mRequestThread.clear();
188         return res;
189     }
190 
191     mPreparerThread = new PreparerThread();
192 
193     /** Everything is good to go */
194 
195     mDeviceVersion = device->common.version;
196     mDeviceInfo = info.static_camera_characteristics;
197     mHal3Device = device;
198 
199     internalUpdateStatusLocked(STATUS_UNCONFIGURED);
200     mNextStreamId = 0;
201     mDummyStreamId = NO_STREAM;
202     mNeedConfig = true;
203     mPauseStateNotify = false;
204 
205     // Will the HAL be sending in early partial result metadata?
206     if (mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
207         camera_metadata_entry partialResultsCount =
208                 mDeviceInfo.find(ANDROID_REQUEST_PARTIAL_RESULT_COUNT);
209         if (partialResultsCount.count > 0) {
210             mNumPartialResults = partialResultsCount.data.i32[0];
211             mUsePartialResult = (mNumPartialResults > 1);
212         }
213     } else {
214         camera_metadata_entry partialResultsQuirk =
215                 mDeviceInfo.find(ANDROID_QUIRKS_USE_PARTIAL_RESULT);
216         if (partialResultsQuirk.count > 0 && partialResultsQuirk.data.u8[0] == 1) {
217             mUsePartialResult = true;
218         }
219     }
220 
221     camera_metadata_entry configs =
222             mDeviceInfo.find(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS);
223     for (uint32_t i = 0; i < configs.count; i += 4) {
224         if (configs.data.i32[i] == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED &&
225                 configs.data.i32[i + 3] ==
226                 ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_INPUT) {
227             mSupportedOpaqueInputSizes.add(Size(configs.data.i32[i + 1],
228                     configs.data.i32[i + 2]));
229         }
230     }
231 
232     return OK;
233 }
234 
disconnect()235 status_t Camera3Device::disconnect() {
236     ATRACE_CALL();
237     Mutex::Autolock il(mInterfaceLock);
238 
239     ALOGV("%s: E", __FUNCTION__);
240 
241     status_t res = OK;
242 
243     {
244         Mutex::Autolock l(mLock);
245         if (mStatus == STATUS_UNINITIALIZED) return res;
246 
247         if (mStatus == STATUS_ACTIVE ||
248                 (mStatus == STATUS_ERROR && mRequestThread != NULL)) {
249             res = mRequestThread->clearRepeatingRequests();
250             if (res != OK) {
251                 SET_ERR_L("Can't stop streaming");
252                 // Continue to close device even in case of error
253             } else {
254                 res = waitUntilStateThenRelock(/*active*/ false, kShutdownTimeout);
255                 if (res != OK) {
256                     SET_ERR_L("Timeout waiting for HAL to drain");
257                     // Continue to close device even in case of error
258                 }
259             }
260         }
261 
262         if (mStatus == STATUS_ERROR) {
263             CLOGE("Shutting down in an error state");
264         }
265 
266         if (mStatusTracker != NULL) {
267             mStatusTracker->requestExit();
268         }
269 
270         if (mRequestThread != NULL) {
271             mRequestThread->requestExit();
272         }
273 
274         mOutputStreams.clear();
275         mInputStream.clear();
276     }
277 
278     // Joining done without holding mLock, otherwise deadlocks may ensue
279     // as the threads try to access parent state
280     if (mRequestThread != NULL && mStatus != STATUS_ERROR) {
281         // HAL may be in a bad state, so waiting for request thread
282         // (which may be stuck in the HAL processCaptureRequest call)
283         // could be dangerous.
284         mRequestThread->join();
285     }
286 
287     if (mStatusTracker != NULL) {
288         mStatusTracker->join();
289     }
290 
291     camera3_device_t *hal3Device;
292     {
293         Mutex::Autolock l(mLock);
294 
295         mRequestThread.clear();
296         mStatusTracker.clear();
297 
298         hal3Device = mHal3Device;
299     }
300 
301     // Call close without internal mutex held, as the HAL close may need to
302     // wait on assorted callbacks,etc, to complete before it can return.
303     if (hal3Device != NULL) {
304         ATRACE_BEGIN("camera3->close");
305         hal3Device->common.close(&hal3Device->common);
306         ATRACE_END();
307     }
308 
309     {
310         Mutex::Autolock l(mLock);
311         mHal3Device = NULL;
312         internalUpdateStatusLocked(STATUS_UNINITIALIZED);
313     }
314 
315     ALOGV("%s: X", __FUNCTION__);
316     return res;
317 }
318 
319 // For dumping/debugging only -
320 // try to acquire a lock a few times, eventually give up to proceed with
321 // debug/dump operations
tryLockSpinRightRound(Mutex & lock)322 bool Camera3Device::tryLockSpinRightRound(Mutex& lock) {
323     bool gotLock = false;
324     for (size_t i = 0; i < kDumpLockAttempts; ++i) {
325         if (lock.tryLock() == NO_ERROR) {
326             gotLock = true;
327             break;
328         } else {
329             usleep(kDumpSleepDuration);
330         }
331     }
332     return gotLock;
333 }
334 
getMaxJpegResolution() const335 Camera3Device::Size Camera3Device::getMaxJpegResolution() const {
336     int32_t maxJpegWidth = 0, maxJpegHeight = 0;
337     if (mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
338         const int STREAM_CONFIGURATION_SIZE = 4;
339         const int STREAM_FORMAT_OFFSET = 0;
340         const int STREAM_WIDTH_OFFSET = 1;
341         const int STREAM_HEIGHT_OFFSET = 2;
342         const int STREAM_IS_INPUT_OFFSET = 3;
343         camera_metadata_ro_entry_t availableStreamConfigs =
344                 mDeviceInfo.find(ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS);
345         if (availableStreamConfigs.count == 0 ||
346                 availableStreamConfigs.count % STREAM_CONFIGURATION_SIZE != 0) {
347             return Size(0, 0);
348         }
349 
350         // Get max jpeg size (area-wise).
351         for (size_t i=0; i < availableStreamConfigs.count; i+= STREAM_CONFIGURATION_SIZE) {
352             int32_t format = availableStreamConfigs.data.i32[i + STREAM_FORMAT_OFFSET];
353             int32_t width = availableStreamConfigs.data.i32[i + STREAM_WIDTH_OFFSET];
354             int32_t height = availableStreamConfigs.data.i32[i + STREAM_HEIGHT_OFFSET];
355             int32_t isInput = availableStreamConfigs.data.i32[i + STREAM_IS_INPUT_OFFSET];
356             if (isInput == ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT
357                     && format == HAL_PIXEL_FORMAT_BLOB &&
358                     (width * height > maxJpegWidth * maxJpegHeight)) {
359                 maxJpegWidth = width;
360                 maxJpegHeight = height;
361             }
362         }
363     } else {
364         camera_metadata_ro_entry availableJpegSizes =
365                 mDeviceInfo.find(ANDROID_SCALER_AVAILABLE_JPEG_SIZES);
366         if (availableJpegSizes.count == 0 || availableJpegSizes.count % 2 != 0) {
367             return Size(0, 0);
368         }
369 
370         // Get max jpeg size (area-wise).
371         for (size_t i = 0; i < availableJpegSizes.count; i += 2) {
372             if ((availableJpegSizes.data.i32[i] * availableJpegSizes.data.i32[i + 1])
373                     > (maxJpegWidth * maxJpegHeight)) {
374                 maxJpegWidth = availableJpegSizes.data.i32[i];
375                 maxJpegHeight = availableJpegSizes.data.i32[i + 1];
376             }
377         }
378     }
379     return Size(maxJpegWidth, maxJpegHeight);
380 }
381 
getJpegBufferSize(uint32_t width,uint32_t height) const382 ssize_t Camera3Device::getJpegBufferSize(uint32_t width, uint32_t height) const {
383     // Get max jpeg size (area-wise).
384     Size maxJpegResolution = getMaxJpegResolution();
385     if (maxJpegResolution.width == 0) {
386         ALOGE("%s: Camera %d: Can't find valid available jpeg sizes in static metadata!",
387                 __FUNCTION__, mId);
388         return BAD_VALUE;
389     }
390 
391     // Get max jpeg buffer size
392     ssize_t maxJpegBufferSize = 0;
393     camera_metadata_ro_entry jpegBufMaxSize = mDeviceInfo.find(ANDROID_JPEG_MAX_SIZE);
394     if (jpegBufMaxSize.count == 0) {
395         ALOGE("%s: Camera %d: Can't find maximum JPEG size in static metadata!", __FUNCTION__, mId);
396         return BAD_VALUE;
397     }
398     maxJpegBufferSize = jpegBufMaxSize.data.i32[0];
399     assert(kMinJpegBufferSize < maxJpegBufferSize);
400 
401     // Calculate final jpeg buffer size for the given resolution.
402     float scaleFactor = ((float) (width * height)) /
403             (maxJpegResolution.width * maxJpegResolution.height);
404     ssize_t jpegBufferSize = scaleFactor * (maxJpegBufferSize - kMinJpegBufferSize) +
405             kMinJpegBufferSize;
406     if (jpegBufferSize > maxJpegBufferSize) {
407         jpegBufferSize = maxJpegBufferSize;
408     }
409 
410     return jpegBufferSize;
411 }
412 
getPointCloudBufferSize() const413 ssize_t Camera3Device::getPointCloudBufferSize() const {
414     const int FLOATS_PER_POINT=4;
415     camera_metadata_ro_entry maxPointCount = mDeviceInfo.find(ANDROID_DEPTH_MAX_DEPTH_SAMPLES);
416     if (maxPointCount.count == 0) {
417         ALOGE("%s: Camera %d: Can't find maximum depth point cloud size in static metadata!",
418                 __FUNCTION__, mId);
419         return BAD_VALUE;
420     }
421     ssize_t maxBytesForPointCloud = sizeof(android_depth_points) +
422             maxPointCount.data.i32[0] * sizeof(float) * FLOATS_PER_POINT;
423     return maxBytesForPointCloud;
424 }
425 
426 
427 
dump(int fd,const Vector<String16> & args)428 status_t Camera3Device::dump(int fd, const Vector<String16> &args) {
429     ATRACE_CALL();
430     (void)args;
431 
432     // Try to lock, but continue in case of failure (to avoid blocking in
433     // deadlocks)
434     bool gotInterfaceLock = tryLockSpinRightRound(mInterfaceLock);
435     bool gotLock = tryLockSpinRightRound(mLock);
436 
437     ALOGW_IF(!gotInterfaceLock,
438             "Camera %d: %s: Unable to lock interface lock, proceeding anyway",
439             mId, __FUNCTION__);
440     ALOGW_IF(!gotLock,
441             "Camera %d: %s: Unable to lock main lock, proceeding anyway",
442             mId, __FUNCTION__);
443 
444     String8 lines;
445 
446     const char *status =
447             mStatus == STATUS_ERROR         ? "ERROR" :
448             mStatus == STATUS_UNINITIALIZED ? "UNINITIALIZED" :
449             mStatus == STATUS_UNCONFIGURED  ? "UNCONFIGURED" :
450             mStatus == STATUS_CONFIGURED    ? "CONFIGURED" :
451             mStatus == STATUS_ACTIVE        ? "ACTIVE" :
452             "Unknown";
453 
454     lines.appendFormat("    Device status: %s\n", status);
455     if (mStatus == STATUS_ERROR) {
456         lines.appendFormat("    Error cause: %s\n", mErrorCause.string());
457     }
458     lines.appendFormat("    Stream configuration:\n");
459     lines.appendFormat("    Operation mode: %s \n", mIsConstrainedHighSpeedConfiguration ?
460             "CONSTRAINED HIGH SPEED VIDEO" : "NORMAL");
461 
462     if (mInputStream != NULL) {
463         write(fd, lines.string(), lines.size());
464         mInputStream->dump(fd, args);
465     } else {
466         lines.appendFormat("      No input stream.\n");
467         write(fd, lines.string(), lines.size());
468     }
469     for (size_t i = 0; i < mOutputStreams.size(); i++) {
470         mOutputStreams[i]->dump(fd,args);
471     }
472 
473     lines = String8("    In-flight requests:\n");
474     if (mInFlightMap.size() == 0) {
475         lines.append("      None\n");
476     } else {
477         for (size_t i = 0; i < mInFlightMap.size(); i++) {
478             InFlightRequest r = mInFlightMap.valueAt(i);
479             lines.appendFormat("      Frame %d |  Timestamp: %" PRId64 ", metadata"
480                     " arrived: %s, buffers left: %d\n", mInFlightMap.keyAt(i),
481                     r.shutterTimestamp, r.haveResultMetadata ? "true" : "false",
482                     r.numBuffersLeft);
483         }
484     }
485     write(fd, lines.string(), lines.size());
486 
487     {
488         lines = String8("    Last request sent:\n");
489         write(fd, lines.string(), lines.size());
490 
491         CameraMetadata lastRequest = getLatestRequestLocked();
492         lastRequest.dump(fd, /*verbosity*/2, /*indentation*/6);
493     }
494 
495     if (mHal3Device != NULL) {
496         lines = String8("    HAL device dump:\n");
497         write(fd, lines.string(), lines.size());
498         mHal3Device->ops->dump(mHal3Device, fd);
499     }
500 
501     if (gotLock) mLock.unlock();
502     if (gotInterfaceLock) mInterfaceLock.unlock();
503 
504     return OK;
505 }
506 
info() const507 const CameraMetadata& Camera3Device::info() const {
508     ALOGVV("%s: E", __FUNCTION__);
509     if (CC_UNLIKELY(mStatus == STATUS_UNINITIALIZED ||
510                     mStatus == STATUS_ERROR)) {
511         ALOGW("%s: Access to static info %s!", __FUNCTION__,
512                 mStatus == STATUS_ERROR ?
513                 "when in error state" : "before init");
514     }
515     return mDeviceInfo;
516 }
517 
checkStatusOkToCaptureLocked()518 status_t Camera3Device::checkStatusOkToCaptureLocked() {
519     switch (mStatus) {
520         case STATUS_ERROR:
521             CLOGE("Device has encountered a serious error");
522             return INVALID_OPERATION;
523         case STATUS_UNINITIALIZED:
524             CLOGE("Device not initialized");
525             return INVALID_OPERATION;
526         case STATUS_UNCONFIGURED:
527         case STATUS_CONFIGURED:
528         case STATUS_ACTIVE:
529             // OK
530             break;
531         default:
532             SET_ERR_L("Unexpected status: %d", mStatus);
533             return INVALID_OPERATION;
534     }
535     return OK;
536 }
537 
convertMetadataListToRequestListLocked(const List<const CameraMetadata> & metadataList,RequestList * requestList)538 status_t Camera3Device::convertMetadataListToRequestListLocked(
539         const List<const CameraMetadata> &metadataList, RequestList *requestList) {
540     if (requestList == NULL) {
541         CLOGE("requestList cannot be NULL.");
542         return BAD_VALUE;
543     }
544 
545     int32_t burstId = 0;
546     for (List<const CameraMetadata>::const_iterator it = metadataList.begin();
547             it != metadataList.end(); ++it) {
548         sp<CaptureRequest> newRequest = setUpRequestLocked(*it);
549         if (newRequest == 0) {
550             CLOGE("Can't create capture request");
551             return BAD_VALUE;
552         }
553 
554         // Setup burst Id and request Id
555         newRequest->mResultExtras.burstId = burstId++;
556         if (it->exists(ANDROID_REQUEST_ID)) {
557             if (it->find(ANDROID_REQUEST_ID).count == 0) {
558                 CLOGE("RequestID entry exists; but must not be empty in metadata");
559                 return BAD_VALUE;
560             }
561             newRequest->mResultExtras.requestId = it->find(ANDROID_REQUEST_ID).data.i32[0];
562         } else {
563             CLOGE("RequestID does not exist in metadata");
564             return BAD_VALUE;
565         }
566 
567         requestList->push_back(newRequest);
568 
569         ALOGV("%s: requestId = %" PRId32, __FUNCTION__, newRequest->mResultExtras.requestId);
570     }
571 
572     // Setup batch size if this is a high speed video recording request.
573     if (mIsConstrainedHighSpeedConfiguration && requestList->size() > 0) {
574         auto firstRequest = requestList->begin();
575         for (auto& outputStream : (*firstRequest)->mOutputStreams) {
576             if (outputStream->isVideoStream()) {
577                 (*firstRequest)->mBatchSize = requestList->size();
578                 break;
579             }
580         }
581     }
582 
583     return OK;
584 }
585 
capture(CameraMetadata & request,int64_t *)586 status_t Camera3Device::capture(CameraMetadata &request, int64_t* /*lastFrameNumber*/) {
587     ATRACE_CALL();
588 
589     List<const CameraMetadata> requests;
590     requests.push_back(request);
591     return captureList(requests, /*lastFrameNumber*/NULL);
592 }
593 
submitRequestsHelper(const List<const CameraMetadata> & requests,bool repeating,int64_t * lastFrameNumber)594 status_t Camera3Device::submitRequestsHelper(
595         const List<const CameraMetadata> &requests, bool repeating,
596         /*out*/
597         int64_t *lastFrameNumber) {
598     ATRACE_CALL();
599     Mutex::Autolock il(mInterfaceLock);
600     Mutex::Autolock l(mLock);
601 
602     status_t res = checkStatusOkToCaptureLocked();
603     if (res != OK) {
604         // error logged by previous call
605         return res;
606     }
607 
608     RequestList requestList;
609 
610     res = convertMetadataListToRequestListLocked(requests, /*out*/&requestList);
611     if (res != OK) {
612         // error logged by previous call
613         return res;
614     }
615 
616     if (repeating) {
617         res = mRequestThread->setRepeatingRequests(requestList, lastFrameNumber);
618     } else {
619         res = mRequestThread->queueRequestList(requestList, lastFrameNumber);
620     }
621 
622     if (res == OK) {
623         waitUntilStateThenRelock(/*active*/true, kActiveTimeout);
624         if (res != OK) {
625             SET_ERR_L("Can't transition to active in %f seconds!",
626                     kActiveTimeout/1e9);
627         }
628         ALOGV("Camera %d: Capture request %" PRId32 " enqueued", mId,
629               (*(requestList.begin()))->mResultExtras.requestId);
630     } else {
631         CLOGE("Cannot queue request. Impossible.");
632         return BAD_VALUE;
633     }
634 
635     return res;
636 }
637 
captureList(const List<const CameraMetadata> & requests,int64_t * lastFrameNumber)638 status_t Camera3Device::captureList(const List<const CameraMetadata> &requests,
639                                     int64_t *lastFrameNumber) {
640     ATRACE_CALL();
641 
642     return submitRequestsHelper(requests, /*repeating*/false, lastFrameNumber);
643 }
644 
setStreamingRequest(const CameraMetadata & request,int64_t *)645 status_t Camera3Device::setStreamingRequest(const CameraMetadata &request,
646                                             int64_t* /*lastFrameNumber*/) {
647     ATRACE_CALL();
648 
649     List<const CameraMetadata> requests;
650     requests.push_back(request);
651     return setStreamingRequestList(requests, /*lastFrameNumber*/NULL);
652 }
653 
setStreamingRequestList(const List<const CameraMetadata> & requests,int64_t * lastFrameNumber)654 status_t Camera3Device::setStreamingRequestList(const List<const CameraMetadata> &requests,
655                                                 int64_t *lastFrameNumber) {
656     ATRACE_CALL();
657 
658     return submitRequestsHelper(requests, /*repeating*/true, lastFrameNumber);
659 }
660 
setUpRequestLocked(const CameraMetadata & request)661 sp<Camera3Device::CaptureRequest> Camera3Device::setUpRequestLocked(
662         const CameraMetadata &request) {
663     status_t res;
664 
665     if (mStatus == STATUS_UNCONFIGURED || mNeedConfig) {
666         res = configureStreamsLocked();
667         // Stream configuration failed due to unsupported configuration.
668         // Device back to unconfigured state. Client might try other configuraitons
669         if (res == BAD_VALUE && mStatus == STATUS_UNCONFIGURED) {
670             CLOGE("No streams configured");
671             return NULL;
672         }
673         // Stream configuration failed for other reason. Fatal.
674         if (res != OK) {
675             SET_ERR_L("Can't set up streams: %s (%d)", strerror(-res), res);
676             return NULL;
677         }
678         // Stream configuration successfully configure to empty stream configuration.
679         if (mStatus == STATUS_UNCONFIGURED) {
680             CLOGE("No streams configured");
681             return NULL;
682         }
683     }
684 
685     sp<CaptureRequest> newRequest = createCaptureRequest(request);
686     return newRequest;
687 }
688 
clearStreamingRequest(int64_t * lastFrameNumber)689 status_t Camera3Device::clearStreamingRequest(int64_t *lastFrameNumber) {
690     ATRACE_CALL();
691     Mutex::Autolock il(mInterfaceLock);
692     Mutex::Autolock l(mLock);
693 
694     switch (mStatus) {
695         case STATUS_ERROR:
696             CLOGE("Device has encountered a serious error");
697             return INVALID_OPERATION;
698         case STATUS_UNINITIALIZED:
699             CLOGE("Device not initialized");
700             return INVALID_OPERATION;
701         case STATUS_UNCONFIGURED:
702         case STATUS_CONFIGURED:
703         case STATUS_ACTIVE:
704             // OK
705             break;
706         default:
707             SET_ERR_L("Unexpected status: %d", mStatus);
708             return INVALID_OPERATION;
709     }
710     ALOGV("Camera %d: Clearing repeating request", mId);
711 
712     return mRequestThread->clearRepeatingRequests(lastFrameNumber);
713 }
714 
waitUntilRequestReceived(int32_t requestId,nsecs_t timeout)715 status_t Camera3Device::waitUntilRequestReceived(int32_t requestId, nsecs_t timeout) {
716     ATRACE_CALL();
717     Mutex::Autolock il(mInterfaceLock);
718 
719     return mRequestThread->waitUntilRequestProcessed(requestId, timeout);
720 }
721 
createInputStream(uint32_t width,uint32_t height,int format,int * id)722 status_t Camera3Device::createInputStream(
723         uint32_t width, uint32_t height, int format, int *id) {
724     ATRACE_CALL();
725     Mutex::Autolock il(mInterfaceLock);
726     Mutex::Autolock l(mLock);
727     ALOGV("Camera %d: Creating new input stream %d: %d x %d, format %d",
728             mId, mNextStreamId, width, height, format);
729 
730     status_t res;
731     bool wasActive = false;
732 
733     switch (mStatus) {
734         case STATUS_ERROR:
735             ALOGE("%s: Device has encountered a serious error", __FUNCTION__);
736             return INVALID_OPERATION;
737         case STATUS_UNINITIALIZED:
738             ALOGE("%s: Device not initialized", __FUNCTION__);
739             return INVALID_OPERATION;
740         case STATUS_UNCONFIGURED:
741         case STATUS_CONFIGURED:
742             // OK
743             break;
744         case STATUS_ACTIVE:
745             ALOGV("%s: Stopping activity to reconfigure streams", __FUNCTION__);
746             res = internalPauseAndWaitLocked();
747             if (res != OK) {
748                 SET_ERR_L("Can't pause captures to reconfigure streams!");
749                 return res;
750             }
751             wasActive = true;
752             break;
753         default:
754             SET_ERR_L("%s: Unexpected status: %d", mStatus);
755             return INVALID_OPERATION;
756     }
757     assert(mStatus != STATUS_ACTIVE);
758 
759     if (mInputStream != 0) {
760         ALOGE("%s: Cannot create more than 1 input stream", __FUNCTION__);
761         return INVALID_OPERATION;
762     }
763 
764     sp<Camera3InputStream> newStream = new Camera3InputStream(mNextStreamId,
765                 width, height, format);
766     newStream->setStatusTracker(mStatusTracker);
767 
768     mInputStream = newStream;
769 
770     *id = mNextStreamId++;
771 
772     // Continue captures if active at start
773     if (wasActive) {
774         ALOGV("%s: Restarting activity to reconfigure streams", __FUNCTION__);
775         res = configureStreamsLocked();
776         if (res != OK) {
777             ALOGE("%s: Can't reconfigure device for new stream %d: %s (%d)",
778                     __FUNCTION__, mNextStreamId, strerror(-res), res);
779             return res;
780         }
781         internalResumeLocked();
782     }
783 
784     ALOGV("Camera %d: Created input stream", mId);
785     return OK;
786 }
787 
788 
createZslStream(uint32_t width,uint32_t height,int depth,int * id,sp<Camera3ZslStream> * zslStream)789 status_t Camera3Device::createZslStream(
790             uint32_t width, uint32_t height,
791             int depth,
792             /*out*/
793             int *id,
794             sp<Camera3ZslStream>* zslStream) {
795     ATRACE_CALL();
796     Mutex::Autolock il(mInterfaceLock);
797     Mutex::Autolock l(mLock);
798     ALOGV("Camera %d: Creating ZSL stream %d: %d x %d, depth %d",
799             mId, mNextStreamId, width, height, depth);
800 
801     status_t res;
802     bool wasActive = false;
803 
804     switch (mStatus) {
805         case STATUS_ERROR:
806             ALOGE("%s: Device has encountered a serious error", __FUNCTION__);
807             return INVALID_OPERATION;
808         case STATUS_UNINITIALIZED:
809             ALOGE("%s: Device not initialized", __FUNCTION__);
810             return INVALID_OPERATION;
811         case STATUS_UNCONFIGURED:
812         case STATUS_CONFIGURED:
813             // OK
814             break;
815         case STATUS_ACTIVE:
816             ALOGV("%s: Stopping activity to reconfigure streams", __FUNCTION__);
817             res = internalPauseAndWaitLocked();
818             if (res != OK) {
819                 SET_ERR_L("Can't pause captures to reconfigure streams!");
820                 return res;
821             }
822             wasActive = true;
823             break;
824         default:
825             SET_ERR_L("Unexpected status: %d", mStatus);
826             return INVALID_OPERATION;
827     }
828     assert(mStatus != STATUS_ACTIVE);
829 
830     if (mInputStream != 0) {
831         ALOGE("%s: Cannot create more than 1 input stream", __FUNCTION__);
832         return INVALID_OPERATION;
833     }
834 
835     sp<Camera3ZslStream> newStream = new Camera3ZslStream(mNextStreamId,
836                 width, height, depth);
837     newStream->setStatusTracker(mStatusTracker);
838 
839     res = mOutputStreams.add(mNextStreamId, newStream);
840     if (res < 0) {
841         ALOGE("%s: Can't add new stream to set: %s (%d)",
842                 __FUNCTION__, strerror(-res), res);
843         return res;
844     }
845     mInputStream = newStream;
846 
847     mNeedConfig = true;
848 
849     *id = mNextStreamId++;
850     *zslStream = newStream;
851 
852     // Continue captures if active at start
853     if (wasActive) {
854         ALOGV("%s: Restarting activity to reconfigure streams", __FUNCTION__);
855         res = configureStreamsLocked();
856         if (res != OK) {
857             ALOGE("%s: Can't reconfigure device for new stream %d: %s (%d)",
858                     __FUNCTION__, mNextStreamId, strerror(-res), res);
859             return res;
860         }
861         internalResumeLocked();
862     }
863 
864     ALOGV("Camera %d: Created ZSL stream", mId);
865     return OK;
866 }
867 
createStream(sp<Surface> consumer,uint32_t width,uint32_t height,int format,android_dataspace dataSpace,camera3_stream_rotation_t rotation,int * id)868 status_t Camera3Device::createStream(sp<Surface> consumer,
869         uint32_t width, uint32_t height, int format, android_dataspace dataSpace,
870         camera3_stream_rotation_t rotation, int *id) {
871     ATRACE_CALL();
872     Mutex::Autolock il(mInterfaceLock);
873     Mutex::Autolock l(mLock);
874     ALOGV("Camera %d: Creating new stream %d: %d x %d, format %d, dataspace %d rotation %d",
875             mId, mNextStreamId, width, height, format, dataSpace, rotation);
876 
877     status_t res;
878     bool wasActive = false;
879 
880     switch (mStatus) {
881         case STATUS_ERROR:
882             CLOGE("Device has encountered a serious error");
883             return INVALID_OPERATION;
884         case STATUS_UNINITIALIZED:
885             CLOGE("Device not initialized");
886             return INVALID_OPERATION;
887         case STATUS_UNCONFIGURED:
888         case STATUS_CONFIGURED:
889             // OK
890             break;
891         case STATUS_ACTIVE:
892             ALOGV("%s: Stopping activity to reconfigure streams", __FUNCTION__);
893             res = internalPauseAndWaitLocked();
894             if (res != OK) {
895                 SET_ERR_L("Can't pause captures to reconfigure streams!");
896                 return res;
897             }
898             wasActive = true;
899             break;
900         default:
901             SET_ERR_L("Unexpected status: %d", mStatus);
902             return INVALID_OPERATION;
903     }
904     assert(mStatus != STATUS_ACTIVE);
905 
906     sp<Camera3OutputStream> newStream;
907     if (format == HAL_PIXEL_FORMAT_BLOB) {
908         ssize_t blobBufferSize;
909         if (dataSpace != HAL_DATASPACE_DEPTH) {
910             blobBufferSize = getJpegBufferSize(width, height);
911             if (blobBufferSize <= 0) {
912                 SET_ERR_L("Invalid jpeg buffer size %zd", blobBufferSize);
913                 return BAD_VALUE;
914             }
915         } else {
916             blobBufferSize = getPointCloudBufferSize();
917             if (blobBufferSize <= 0) {
918                 SET_ERR_L("Invalid point cloud buffer size %zd", blobBufferSize);
919                 return BAD_VALUE;
920             }
921         }
922         newStream = new Camera3OutputStream(mNextStreamId, consumer,
923                 width, height, blobBufferSize, format, dataSpace, rotation);
924     } else {
925         newStream = new Camera3OutputStream(mNextStreamId, consumer,
926                 width, height, format, dataSpace, rotation);
927     }
928     newStream->setStatusTracker(mStatusTracker);
929 
930     res = mOutputStreams.add(mNextStreamId, newStream);
931     if (res < 0) {
932         SET_ERR_L("Can't add new stream to set: %s (%d)", strerror(-res), res);
933         return res;
934     }
935 
936     *id = mNextStreamId++;
937     mNeedConfig = true;
938 
939     // Continue captures if active at start
940     if (wasActive) {
941         ALOGV("%s: Restarting activity to reconfigure streams", __FUNCTION__);
942         res = configureStreamsLocked();
943         if (res != OK) {
944             CLOGE("Can't reconfigure device for new stream %d: %s (%d)",
945                     mNextStreamId, strerror(-res), res);
946             return res;
947         }
948         internalResumeLocked();
949     }
950     ALOGV("Camera %d: Created new stream", mId);
951     return OK;
952 }
953 
createReprocessStreamFromStream(int outputId,int * id)954 status_t Camera3Device::createReprocessStreamFromStream(int outputId, int *id) {
955     ATRACE_CALL();
956     (void)outputId; (void)id;
957 
958     CLOGE("Unimplemented");
959     return INVALID_OPERATION;
960 }
961 
962 
getStreamInfo(int id,uint32_t * width,uint32_t * height,uint32_t * format,android_dataspace * dataSpace)963 status_t Camera3Device::getStreamInfo(int id,
964         uint32_t *width, uint32_t *height,
965         uint32_t *format, android_dataspace *dataSpace) {
966     ATRACE_CALL();
967     Mutex::Autolock il(mInterfaceLock);
968     Mutex::Autolock l(mLock);
969 
970     switch (mStatus) {
971         case STATUS_ERROR:
972             CLOGE("Device has encountered a serious error");
973             return INVALID_OPERATION;
974         case STATUS_UNINITIALIZED:
975             CLOGE("Device not initialized!");
976             return INVALID_OPERATION;
977         case STATUS_UNCONFIGURED:
978         case STATUS_CONFIGURED:
979         case STATUS_ACTIVE:
980             // OK
981             break;
982         default:
983             SET_ERR_L("Unexpected status: %d", mStatus);
984             return INVALID_OPERATION;
985     }
986 
987     ssize_t idx = mOutputStreams.indexOfKey(id);
988     if (idx == NAME_NOT_FOUND) {
989         CLOGE("Stream %d is unknown", id);
990         return idx;
991     }
992 
993     if (width) *width  = mOutputStreams[idx]->getWidth();
994     if (height) *height = mOutputStreams[idx]->getHeight();
995     if (format) *format = mOutputStreams[idx]->getFormat();
996     if (dataSpace) *dataSpace = mOutputStreams[idx]->getDataSpace();
997     return OK;
998 }
999 
setStreamTransform(int id,int transform)1000 status_t Camera3Device::setStreamTransform(int id,
1001         int transform) {
1002     ATRACE_CALL();
1003     Mutex::Autolock il(mInterfaceLock);
1004     Mutex::Autolock l(mLock);
1005 
1006     switch (mStatus) {
1007         case STATUS_ERROR:
1008             CLOGE("Device has encountered a serious error");
1009             return INVALID_OPERATION;
1010         case STATUS_UNINITIALIZED:
1011             CLOGE("Device not initialized");
1012             return INVALID_OPERATION;
1013         case STATUS_UNCONFIGURED:
1014         case STATUS_CONFIGURED:
1015         case STATUS_ACTIVE:
1016             // OK
1017             break;
1018         default:
1019             SET_ERR_L("Unexpected status: %d", mStatus);
1020             return INVALID_OPERATION;
1021     }
1022 
1023     ssize_t idx = mOutputStreams.indexOfKey(id);
1024     if (idx == NAME_NOT_FOUND) {
1025         CLOGE("Stream %d does not exist",
1026                 id);
1027         return BAD_VALUE;
1028     }
1029 
1030     return mOutputStreams.editValueAt(idx)->setTransform(transform);
1031 }
1032 
deleteStream(int id)1033 status_t Camera3Device::deleteStream(int id) {
1034     ATRACE_CALL();
1035     Mutex::Autolock il(mInterfaceLock);
1036     Mutex::Autolock l(mLock);
1037     status_t res;
1038 
1039     ALOGV("%s: Camera %d: Deleting stream %d", __FUNCTION__, mId, id);
1040 
1041     // CameraDevice semantics require device to already be idle before
1042     // deleteStream is called, unlike for createStream.
1043     if (mStatus == STATUS_ACTIVE) {
1044         ALOGV("%s: Camera %d: Device not idle", __FUNCTION__, mId);
1045         return -EBUSY;
1046     }
1047 
1048     sp<Camera3StreamInterface> deletedStream;
1049     ssize_t outputStreamIdx = mOutputStreams.indexOfKey(id);
1050     if (mInputStream != NULL && id == mInputStream->getId()) {
1051         deletedStream = mInputStream;
1052         mInputStream.clear();
1053     } else {
1054         if (outputStreamIdx == NAME_NOT_FOUND) {
1055             CLOGE("Stream %d does not exist", id);
1056             return BAD_VALUE;
1057         }
1058     }
1059 
1060     // Delete output stream or the output part of a bi-directional stream.
1061     if (outputStreamIdx != NAME_NOT_FOUND) {
1062         deletedStream = mOutputStreams.editValueAt(outputStreamIdx);
1063         mOutputStreams.removeItem(id);
1064     }
1065 
1066     // Free up the stream endpoint so that it can be used by some other stream
1067     res = deletedStream->disconnect();
1068     if (res != OK) {
1069         SET_ERR_L("Can't disconnect deleted stream %d", id);
1070         // fall through since we want to still list the stream as deleted.
1071     }
1072     mDeletedStreams.add(deletedStream);
1073     mNeedConfig = true;
1074 
1075     return res;
1076 }
1077 
deleteReprocessStream(int id)1078 status_t Camera3Device::deleteReprocessStream(int id) {
1079     ATRACE_CALL();
1080     (void)id;
1081 
1082     CLOGE("Unimplemented");
1083     return INVALID_OPERATION;
1084 }
1085 
configureStreams(bool isConstrainedHighSpeed)1086 status_t Camera3Device::configureStreams(bool isConstrainedHighSpeed) {
1087     ATRACE_CALL();
1088     ALOGV("%s: E", __FUNCTION__);
1089 
1090     Mutex::Autolock il(mInterfaceLock);
1091     Mutex::Autolock l(mLock);
1092 
1093     if (mIsConstrainedHighSpeedConfiguration != isConstrainedHighSpeed) {
1094         mNeedConfig = true;
1095         mIsConstrainedHighSpeedConfiguration = isConstrainedHighSpeed;
1096     }
1097 
1098     return configureStreamsLocked();
1099 }
1100 
getInputBufferProducer(sp<IGraphicBufferProducer> * producer)1101 status_t Camera3Device::getInputBufferProducer(
1102         sp<IGraphicBufferProducer> *producer) {
1103     Mutex::Autolock il(mInterfaceLock);
1104     Mutex::Autolock l(mLock);
1105 
1106     if (producer == NULL) {
1107         return BAD_VALUE;
1108     } else if (mInputStream == NULL) {
1109         return INVALID_OPERATION;
1110     }
1111 
1112     return mInputStream->getInputBufferProducer(producer);
1113 }
1114 
createDefaultRequest(int templateId,CameraMetadata * request)1115 status_t Camera3Device::createDefaultRequest(int templateId,
1116         CameraMetadata *request) {
1117     ATRACE_CALL();
1118     ALOGV("%s: for template %d", __FUNCTION__, templateId);
1119 
1120     if (templateId <= 0 || templateId >= CAMERA3_TEMPLATE_COUNT) {
1121         android_errorWriteWithInfoLog(CameraService::SN_EVENT_LOG_ID, "26866110",
1122                 IPCThreadState::self()->getCallingUid(), NULL, 0);
1123         return BAD_VALUE;
1124     }
1125 
1126     Mutex::Autolock il(mInterfaceLock);
1127     Mutex::Autolock l(mLock);
1128 
1129     switch (mStatus) {
1130         case STATUS_ERROR:
1131             CLOGE("Device has encountered a serious error");
1132             return INVALID_OPERATION;
1133         case STATUS_UNINITIALIZED:
1134             CLOGE("Device is not initialized!");
1135             return INVALID_OPERATION;
1136         case STATUS_UNCONFIGURED:
1137         case STATUS_CONFIGURED:
1138         case STATUS_ACTIVE:
1139             // OK
1140             break;
1141         default:
1142             SET_ERR_L("Unexpected status: %d", mStatus);
1143             return INVALID_OPERATION;
1144     }
1145 
1146     if (!mRequestTemplateCache[templateId].isEmpty()) {
1147         *request = mRequestTemplateCache[templateId];
1148         return OK;
1149     }
1150 
1151     const camera_metadata_t *rawRequest;
1152     ATRACE_BEGIN("camera3->construct_default_request_settings");
1153     rawRequest = mHal3Device->ops->construct_default_request_settings(
1154         mHal3Device, templateId);
1155     ATRACE_END();
1156     if (rawRequest == NULL) {
1157         ALOGI("%s: template %d is not supported on this camera device",
1158               __FUNCTION__, templateId);
1159         return BAD_VALUE;
1160     }
1161     *request = rawRequest;
1162     mRequestTemplateCache[templateId] = rawRequest;
1163 
1164     return OK;
1165 }
1166 
waitUntilDrained()1167 status_t Camera3Device::waitUntilDrained() {
1168     ATRACE_CALL();
1169     Mutex::Autolock il(mInterfaceLock);
1170     Mutex::Autolock l(mLock);
1171 
1172     return waitUntilDrainedLocked();
1173 }
1174 
waitUntilDrainedLocked()1175 status_t Camera3Device::waitUntilDrainedLocked() {
1176     switch (mStatus) {
1177         case STATUS_UNINITIALIZED:
1178         case STATUS_UNCONFIGURED:
1179             ALOGV("%s: Already idle", __FUNCTION__);
1180             return OK;
1181         case STATUS_CONFIGURED:
1182             // To avoid race conditions, check with tracker to be sure
1183         case STATUS_ERROR:
1184         case STATUS_ACTIVE:
1185             // Need to verify shut down
1186             break;
1187         default:
1188             SET_ERR_L("Unexpected status: %d",mStatus);
1189             return INVALID_OPERATION;
1190     }
1191 
1192     ALOGV("%s: Camera %d: Waiting until idle", __FUNCTION__, mId);
1193     status_t res = waitUntilStateThenRelock(/*active*/ false, kShutdownTimeout);
1194     if (res != OK) {
1195         SET_ERR_L("Error waiting for HAL to drain: %s (%d)", strerror(-res),
1196                 res);
1197     }
1198     return res;
1199 }
1200 
1201 
internalUpdateStatusLocked(Status status)1202 void Camera3Device::internalUpdateStatusLocked(Status status) {
1203     mStatus = status;
1204     mRecentStatusUpdates.add(mStatus);
1205     mStatusChanged.broadcast();
1206 }
1207 
1208 // Pause to reconfigure
internalPauseAndWaitLocked()1209 status_t Camera3Device::internalPauseAndWaitLocked() {
1210     mRequestThread->setPaused(true);
1211     mPauseStateNotify = true;
1212 
1213     ALOGV("%s: Camera %d: Internal wait until idle", __FUNCTION__, mId);
1214     status_t res = waitUntilStateThenRelock(/*active*/ false, kShutdownTimeout);
1215     if (res != OK) {
1216         SET_ERR_L("Can't idle device in %f seconds!",
1217                 kShutdownTimeout/1e9);
1218     }
1219 
1220     return res;
1221 }
1222 
1223 // Resume after internalPauseAndWaitLocked
internalResumeLocked()1224 status_t Camera3Device::internalResumeLocked() {
1225     status_t res;
1226 
1227     mRequestThread->setPaused(false);
1228 
1229     res = waitUntilStateThenRelock(/*active*/ true, kActiveTimeout);
1230     if (res != OK) {
1231         SET_ERR_L("Can't transition to active in %f seconds!",
1232                 kActiveTimeout/1e9);
1233     }
1234     mPauseStateNotify = false;
1235     return OK;
1236 }
1237 
waitUntilStateThenRelock(bool active,nsecs_t timeout)1238 status_t Camera3Device::waitUntilStateThenRelock(bool active, nsecs_t timeout) {
1239     status_t res = OK;
1240 
1241     size_t startIndex = 0;
1242     if (mStatusWaiters == 0) {
1243         // Clear the list of recent statuses if there are no existing threads waiting on updates to
1244         // this status list
1245         mRecentStatusUpdates.clear();
1246     } else {
1247         // If other threads are waiting on updates to this status list, set the position of the
1248         // first element that this list will check rather than clearing the list.
1249         startIndex = mRecentStatusUpdates.size();
1250     }
1251 
1252     mStatusWaiters++;
1253 
1254     bool stateSeen = false;
1255     do {
1256         if (active == (mStatus == STATUS_ACTIVE)) {
1257             // Desired state is current
1258             break;
1259         }
1260 
1261         res = mStatusChanged.waitRelative(mLock, timeout);
1262         if (res != OK) break;
1263 
1264         // This is impossible, but if not, could result in subtle deadlocks and invalid state
1265         // transitions.
1266         LOG_ALWAYS_FATAL_IF(startIndex > mRecentStatusUpdates.size(),
1267                 "%s: Skipping status updates in Camera3Device, may result in deadlock.",
1268                 __FUNCTION__);
1269 
1270         // Encountered desired state since we began waiting
1271         for (size_t i = startIndex; i < mRecentStatusUpdates.size(); i++) {
1272             if (active == (mRecentStatusUpdates[i] == STATUS_ACTIVE) ) {
1273                 stateSeen = true;
1274                 break;
1275             }
1276         }
1277     } while (!stateSeen);
1278 
1279     mStatusWaiters--;
1280 
1281     return res;
1282 }
1283 
1284 
setNotifyCallback(NotificationListener * listener)1285 status_t Camera3Device::setNotifyCallback(NotificationListener *listener) {
1286     ATRACE_CALL();
1287     Mutex::Autolock l(mOutputLock);
1288 
1289     if (listener != NULL && mListener != NULL) {
1290         ALOGW("%s: Replacing old callback listener", __FUNCTION__);
1291     }
1292     mListener = listener;
1293     mRequestThread->setNotificationListener(listener);
1294     mPreparerThread->setNotificationListener(listener);
1295 
1296     return OK;
1297 }
1298 
willNotify3A()1299 bool Camera3Device::willNotify3A() {
1300     return false;
1301 }
1302 
waitForNextFrame(nsecs_t timeout)1303 status_t Camera3Device::waitForNextFrame(nsecs_t timeout) {
1304     status_t res;
1305     Mutex::Autolock l(mOutputLock);
1306 
1307     while (mResultQueue.empty()) {
1308         res = mResultSignal.waitRelative(mOutputLock, timeout);
1309         if (res == TIMED_OUT) {
1310             return res;
1311         } else if (res != OK) {
1312             ALOGW("%s: Camera %d: No frame in %" PRId64 " ns: %s (%d)",
1313                     __FUNCTION__, mId, timeout, strerror(-res), res);
1314             return res;
1315         }
1316     }
1317     return OK;
1318 }
1319 
getNextResult(CaptureResult * frame)1320 status_t Camera3Device::getNextResult(CaptureResult *frame) {
1321     ATRACE_CALL();
1322     Mutex::Autolock l(mOutputLock);
1323 
1324     if (mResultQueue.empty()) {
1325         return NOT_ENOUGH_DATA;
1326     }
1327 
1328     if (frame == NULL) {
1329         ALOGE("%s: argument cannot be NULL", __FUNCTION__);
1330         return BAD_VALUE;
1331     }
1332 
1333     CaptureResult &result = *(mResultQueue.begin());
1334     frame->mResultExtras = result.mResultExtras;
1335     frame->mMetadata.acquire(result.mMetadata);
1336     mResultQueue.erase(mResultQueue.begin());
1337 
1338     return OK;
1339 }
1340 
triggerAutofocus(uint32_t id)1341 status_t Camera3Device::triggerAutofocus(uint32_t id) {
1342     ATRACE_CALL();
1343     Mutex::Autolock il(mInterfaceLock);
1344 
1345     ALOGV("%s: Triggering autofocus, id %d", __FUNCTION__, id);
1346     // Mix-in this trigger into the next request and only the next request.
1347     RequestTrigger trigger[] = {
1348         {
1349             ANDROID_CONTROL_AF_TRIGGER,
1350             ANDROID_CONTROL_AF_TRIGGER_START
1351         },
1352         {
1353             ANDROID_CONTROL_AF_TRIGGER_ID,
1354             static_cast<int32_t>(id)
1355         }
1356     };
1357 
1358     return mRequestThread->queueTrigger(trigger,
1359                                         sizeof(trigger)/sizeof(trigger[0]));
1360 }
1361 
triggerCancelAutofocus(uint32_t id)1362 status_t Camera3Device::triggerCancelAutofocus(uint32_t id) {
1363     ATRACE_CALL();
1364     Mutex::Autolock il(mInterfaceLock);
1365 
1366     ALOGV("%s: Triggering cancel autofocus, id %d", __FUNCTION__, id);
1367     // Mix-in this trigger into the next request and only the next request.
1368     RequestTrigger trigger[] = {
1369         {
1370             ANDROID_CONTROL_AF_TRIGGER,
1371             ANDROID_CONTROL_AF_TRIGGER_CANCEL
1372         },
1373         {
1374             ANDROID_CONTROL_AF_TRIGGER_ID,
1375             static_cast<int32_t>(id)
1376         }
1377     };
1378 
1379     return mRequestThread->queueTrigger(trigger,
1380                                         sizeof(trigger)/sizeof(trigger[0]));
1381 }
1382 
triggerPrecaptureMetering(uint32_t id)1383 status_t Camera3Device::triggerPrecaptureMetering(uint32_t id) {
1384     ATRACE_CALL();
1385     Mutex::Autolock il(mInterfaceLock);
1386 
1387     ALOGV("%s: Triggering precapture metering, id %d", __FUNCTION__, id);
1388     // Mix-in this trigger into the next request and only the next request.
1389     RequestTrigger trigger[] = {
1390         {
1391             ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER,
1392             ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_START
1393         },
1394         {
1395             ANDROID_CONTROL_AE_PRECAPTURE_ID,
1396             static_cast<int32_t>(id)
1397         }
1398     };
1399 
1400     return mRequestThread->queueTrigger(trigger,
1401                                         sizeof(trigger)/sizeof(trigger[0]));
1402 }
1403 
pushReprocessBuffer(int reprocessStreamId,buffer_handle_t * buffer,wp<BufferReleasedListener> listener)1404 status_t Camera3Device::pushReprocessBuffer(int reprocessStreamId,
1405         buffer_handle_t *buffer, wp<BufferReleasedListener> listener) {
1406     ATRACE_CALL();
1407     (void)reprocessStreamId; (void)buffer; (void)listener;
1408 
1409     CLOGE("Unimplemented");
1410     return INVALID_OPERATION;
1411 }
1412 
flush(int64_t * frameNumber)1413 status_t Camera3Device::flush(int64_t *frameNumber) {
1414     ATRACE_CALL();
1415     ALOGV("%s: Camera %d: Flushing all requests", __FUNCTION__, mId);
1416     Mutex::Autolock il(mInterfaceLock);
1417 
1418     NotificationListener* listener;
1419     {
1420         Mutex::Autolock l(mOutputLock);
1421         listener = mListener;
1422     }
1423 
1424     {
1425         Mutex::Autolock l(mLock);
1426         mRequestThread->clear(listener, /*out*/frameNumber);
1427     }
1428 
1429     status_t res;
1430     if (mHal3Device->common.version >= CAMERA_DEVICE_API_VERSION_3_1) {
1431         res = mRequestThread->flush();
1432     } else {
1433         Mutex::Autolock l(mLock);
1434         res = waitUntilDrainedLocked();
1435     }
1436 
1437     return res;
1438 }
1439 
prepare(int streamId)1440 status_t Camera3Device::prepare(int streamId) {
1441     return prepare(camera3::Camera3StreamInterface::ALLOCATE_PIPELINE_MAX, streamId);
1442 }
1443 
prepare(int maxCount,int streamId)1444 status_t Camera3Device::prepare(int maxCount, int streamId) {
1445     ATRACE_CALL();
1446     ALOGV("%s: Camera %d: Preparing stream %d", __FUNCTION__, mId, streamId);
1447     Mutex::Autolock il(mInterfaceLock);
1448     Mutex::Autolock l(mLock);
1449 
1450     sp<Camera3StreamInterface> stream;
1451     ssize_t outputStreamIdx = mOutputStreams.indexOfKey(streamId);
1452     if (outputStreamIdx == NAME_NOT_FOUND) {
1453         CLOGE("Stream %d does not exist", streamId);
1454         return BAD_VALUE;
1455     }
1456 
1457     stream = mOutputStreams.editValueAt(outputStreamIdx);
1458 
1459     if (stream->isUnpreparable() || stream->hasOutstandingBuffers() ) {
1460         CLOGE("Stream %d has already been a request target", streamId);
1461         return BAD_VALUE;
1462     }
1463 
1464     if (mRequestThread->isStreamPending(stream)) {
1465         CLOGE("Stream %d is already a target in a pending request", streamId);
1466         return BAD_VALUE;
1467     }
1468 
1469     return mPreparerThread->prepare(maxCount, stream);
1470 }
1471 
tearDown(int streamId)1472 status_t Camera3Device::tearDown(int streamId) {
1473     ATRACE_CALL();
1474     ALOGV("%s: Camera %d: Tearing down stream %d", __FUNCTION__, mId, streamId);
1475     Mutex::Autolock il(mInterfaceLock);
1476     Mutex::Autolock l(mLock);
1477 
1478     // Teardown can only be accomplished on devices that don't require register_stream_buffers,
1479     // since we cannot call register_stream_buffers except right after configure_streams.
1480     if (mHal3Device->common.version < CAMERA_DEVICE_API_VERSION_3_2) {
1481         ALOGE("%s: Unable to tear down streams on device HAL v%x",
1482                 __FUNCTION__, mHal3Device->common.version);
1483         return NO_INIT;
1484     }
1485 
1486     sp<Camera3StreamInterface> stream;
1487     ssize_t outputStreamIdx = mOutputStreams.indexOfKey(streamId);
1488     if (outputStreamIdx == NAME_NOT_FOUND) {
1489         CLOGE("Stream %d does not exist", streamId);
1490         return BAD_VALUE;
1491     }
1492 
1493     stream = mOutputStreams.editValueAt(outputStreamIdx);
1494 
1495     if (stream->hasOutstandingBuffers() || mRequestThread->isStreamPending(stream)) {
1496         CLOGE("Stream %d is a target of a in-progress request", streamId);
1497         return BAD_VALUE;
1498     }
1499 
1500     return stream->tearDown();
1501 }
1502 
getDeviceVersion()1503 uint32_t Camera3Device::getDeviceVersion() {
1504     ATRACE_CALL();
1505     Mutex::Autolock il(mInterfaceLock);
1506     return mDeviceVersion;
1507 }
1508 
1509 /**
1510  * Methods called by subclasses
1511  */
1512 
notifyStatus(bool idle)1513 void Camera3Device::notifyStatus(bool idle) {
1514     {
1515         // Need mLock to safely update state and synchronize to current
1516         // state of methods in flight.
1517         Mutex::Autolock l(mLock);
1518         // We can get various system-idle notices from the status tracker
1519         // while starting up. Only care about them if we've actually sent
1520         // in some requests recently.
1521         if (mStatus != STATUS_ACTIVE && mStatus != STATUS_CONFIGURED) {
1522             return;
1523         }
1524         ALOGV("%s: Camera %d: Now %s", __FUNCTION__, mId,
1525                 idle ? "idle" : "active");
1526         internalUpdateStatusLocked(idle ? STATUS_CONFIGURED : STATUS_ACTIVE);
1527 
1528         // Skip notifying listener if we're doing some user-transparent
1529         // state changes
1530         if (mPauseStateNotify) return;
1531     }
1532     NotificationListener *listener;
1533     {
1534         Mutex::Autolock l(mOutputLock);
1535         listener = mListener;
1536     }
1537     if (idle && listener != NULL) {
1538         listener->notifyIdle();
1539     }
1540 }
1541 
1542 /**
1543  * Camera3Device private methods
1544  */
1545 
createCaptureRequest(const CameraMetadata & request)1546 sp<Camera3Device::CaptureRequest> Camera3Device::createCaptureRequest(
1547         const CameraMetadata &request) {
1548     ATRACE_CALL();
1549     status_t res;
1550 
1551     sp<CaptureRequest> newRequest = new CaptureRequest;
1552     newRequest->mSettings = request;
1553 
1554     camera_metadata_entry_t inputStreams =
1555             newRequest->mSettings.find(ANDROID_REQUEST_INPUT_STREAMS);
1556     if (inputStreams.count > 0) {
1557         if (mInputStream == NULL ||
1558                 mInputStream->getId() != inputStreams.data.i32[0]) {
1559             CLOGE("Request references unknown input stream %d",
1560                     inputStreams.data.u8[0]);
1561             return NULL;
1562         }
1563         // Lazy completion of stream configuration (allocation/registration)
1564         // on first use
1565         if (mInputStream->isConfiguring()) {
1566             res = mInputStream->finishConfiguration(mHal3Device);
1567             if (res != OK) {
1568                 SET_ERR_L("Unable to finish configuring input stream %d:"
1569                         " %s (%d)",
1570                         mInputStream->getId(), strerror(-res), res);
1571                 return NULL;
1572             }
1573         }
1574         // Check if stream is being prepared
1575         if (mInputStream->isPreparing()) {
1576             CLOGE("Request references an input stream that's being prepared!");
1577             return NULL;
1578         }
1579 
1580         newRequest->mInputStream = mInputStream;
1581         newRequest->mSettings.erase(ANDROID_REQUEST_INPUT_STREAMS);
1582     }
1583 
1584     camera_metadata_entry_t streams =
1585             newRequest->mSettings.find(ANDROID_REQUEST_OUTPUT_STREAMS);
1586     if (streams.count == 0) {
1587         CLOGE("Zero output streams specified!");
1588         return NULL;
1589     }
1590 
1591     for (size_t i = 0; i < streams.count; i++) {
1592         int idx = mOutputStreams.indexOfKey(streams.data.i32[i]);
1593         if (idx == NAME_NOT_FOUND) {
1594             CLOGE("Request references unknown stream %d",
1595                     streams.data.u8[i]);
1596             return NULL;
1597         }
1598         sp<Camera3OutputStreamInterface> stream =
1599                 mOutputStreams.editValueAt(idx);
1600 
1601         // Lazy completion of stream configuration (allocation/registration)
1602         // on first use
1603         if (stream->isConfiguring()) {
1604             res = stream->finishConfiguration(mHal3Device);
1605             if (res != OK) {
1606                 SET_ERR_L("Unable to finish configuring stream %d: %s (%d)",
1607                         stream->getId(), strerror(-res), res);
1608                 return NULL;
1609             }
1610         }
1611         // Check if stream is being prepared
1612         if (stream->isPreparing()) {
1613             CLOGE("Request references an output stream that's being prepared!");
1614             return NULL;
1615         }
1616 
1617         newRequest->mOutputStreams.push(stream);
1618     }
1619     newRequest->mSettings.erase(ANDROID_REQUEST_OUTPUT_STREAMS);
1620     newRequest->mBatchSize = 1;
1621 
1622     return newRequest;
1623 }
1624 
isOpaqueInputSizeSupported(uint32_t width,uint32_t height)1625 bool Camera3Device::isOpaqueInputSizeSupported(uint32_t width, uint32_t height) {
1626     for (uint32_t i = 0; i < mSupportedOpaqueInputSizes.size(); i++) {
1627         Size size = mSupportedOpaqueInputSizes[i];
1628         if (size.width == width && size.height == height) {
1629             return true;
1630         }
1631     }
1632 
1633     return false;
1634 }
1635 
configureStreamsLocked()1636 status_t Camera3Device::configureStreamsLocked() {
1637     ATRACE_CALL();
1638     status_t res;
1639 
1640     if (mStatus != STATUS_UNCONFIGURED && mStatus != STATUS_CONFIGURED) {
1641         CLOGE("Not idle");
1642         return INVALID_OPERATION;
1643     }
1644 
1645     if (!mNeedConfig) {
1646         ALOGV("%s: Skipping config, no stream changes", __FUNCTION__);
1647         return OK;
1648     }
1649 
1650     // Workaround for device HALv3.2 or older spec bug - zero streams requires
1651     // adding a dummy stream instead.
1652     // TODO: Bug: 17321404 for fixing the HAL spec and removing this workaround.
1653     if (mOutputStreams.size() == 0) {
1654         addDummyStreamLocked();
1655     } else {
1656         tryRemoveDummyStreamLocked();
1657     }
1658 
1659     // Start configuring the streams
1660     ALOGV("%s: Camera %d: Starting stream configuration", __FUNCTION__, mId);
1661 
1662     camera3_stream_configuration config;
1663     config.operation_mode = mIsConstrainedHighSpeedConfiguration ?
1664             CAMERA3_STREAM_CONFIGURATION_CONSTRAINED_HIGH_SPEED_MODE :
1665             CAMERA3_STREAM_CONFIGURATION_NORMAL_MODE;
1666     config.num_streams = (mInputStream != NULL) + mOutputStreams.size();
1667 
1668     Vector<camera3_stream_t*> streams;
1669     streams.setCapacity(config.num_streams);
1670 
1671     if (mInputStream != NULL) {
1672         camera3_stream_t *inputStream;
1673         inputStream = mInputStream->startConfiguration();
1674         if (inputStream == NULL) {
1675             SET_ERR_L("Can't start input stream configuration");
1676             return INVALID_OPERATION;
1677         }
1678         streams.add(inputStream);
1679     }
1680 
1681     for (size_t i = 0; i < mOutputStreams.size(); i++) {
1682 
1683         // Don't configure bidi streams twice, nor add them twice to the list
1684         if (mOutputStreams[i].get() ==
1685             static_cast<Camera3StreamInterface*>(mInputStream.get())) {
1686 
1687             config.num_streams--;
1688             continue;
1689         }
1690 
1691         camera3_stream_t *outputStream;
1692         outputStream = mOutputStreams.editValueAt(i)->startConfiguration();
1693         if (outputStream == NULL) {
1694             SET_ERR_L("Can't start output stream configuration");
1695             return INVALID_OPERATION;
1696         }
1697         streams.add(outputStream);
1698     }
1699 
1700     config.streams = streams.editArray();
1701 
1702     // Do the HAL configuration; will potentially touch stream
1703     // max_buffers, usage, priv fields.
1704     ATRACE_BEGIN("camera3->configure_streams");
1705     res = mHal3Device->ops->configure_streams(mHal3Device, &config);
1706     ATRACE_END();
1707 
1708     if (res == BAD_VALUE) {
1709         // HAL rejected this set of streams as unsupported, clean up config
1710         // attempt and return to unconfigured state
1711         if (mInputStream != NULL && mInputStream->isConfiguring()) {
1712             res = mInputStream->cancelConfiguration();
1713             if (res != OK) {
1714                 SET_ERR_L("Can't cancel configuring input stream %d: %s (%d)",
1715                         mInputStream->getId(), strerror(-res), res);
1716                 return res;
1717             }
1718         }
1719 
1720         for (size_t i = 0; i < mOutputStreams.size(); i++) {
1721             sp<Camera3OutputStreamInterface> outputStream =
1722                     mOutputStreams.editValueAt(i);
1723             if (outputStream->isConfiguring()) {
1724                 res = outputStream->cancelConfiguration();
1725                 if (res != OK) {
1726                     SET_ERR_L(
1727                         "Can't cancel configuring output stream %d: %s (%d)",
1728                         outputStream->getId(), strerror(-res), res);
1729                     return res;
1730                 }
1731             }
1732         }
1733 
1734         // Return state to that at start of call, so that future configures
1735         // properly clean things up
1736         internalUpdateStatusLocked(STATUS_UNCONFIGURED);
1737         mNeedConfig = true;
1738 
1739         ALOGV("%s: Camera %d: Stream configuration failed", __FUNCTION__, mId);
1740         return BAD_VALUE;
1741     } else if (res != OK) {
1742         // Some other kind of error from configure_streams - this is not
1743         // expected
1744         SET_ERR_L("Unable to configure streams with HAL: %s (%d)",
1745                 strerror(-res), res);
1746         return res;
1747     }
1748 
1749     // Finish all stream configuration immediately.
1750     // TODO: Try to relax this later back to lazy completion, which should be
1751     // faster
1752 
1753     if (mInputStream != NULL && mInputStream->isConfiguring()) {
1754         res = mInputStream->finishConfiguration(mHal3Device);
1755         if (res != OK) {
1756             SET_ERR_L("Can't finish configuring input stream %d: %s (%d)",
1757                     mInputStream->getId(), strerror(-res), res);
1758             return res;
1759         }
1760     }
1761 
1762     for (size_t i = 0; i < mOutputStreams.size(); i++) {
1763         sp<Camera3OutputStreamInterface> outputStream =
1764             mOutputStreams.editValueAt(i);
1765         if (outputStream->isConfiguring()) {
1766             res = outputStream->finishConfiguration(mHal3Device);
1767             if (res != OK) {
1768                 SET_ERR_L("Can't finish configuring output stream %d: %s (%d)",
1769                         outputStream->getId(), strerror(-res), res);
1770                 return res;
1771             }
1772         }
1773     }
1774 
1775     // Request thread needs to know to avoid using repeat-last-settings protocol
1776     // across configure_streams() calls
1777     mRequestThread->configurationComplete();
1778 
1779     // Boost priority of request thread for high speed recording to SCHED_FIFO
1780     if (mIsConstrainedHighSpeedConfiguration) {
1781         pid_t requestThreadTid = mRequestThread->getTid();
1782         res = requestPriority(getpid(), requestThreadTid,
1783                 kConstrainedHighSpeedThreadPriority, true);
1784         if (res != OK) {
1785             ALOGW("Can't set realtime priority for request processing thread: %s (%d)",
1786                     strerror(-res), res);
1787         } else {
1788             ALOGD("Set real time priority for request queue thread (tid %d)", requestThreadTid);
1789         }
1790     } else {
1791         // TODO: Set/restore normal priority for normal use cases
1792     }
1793 
1794     // Update device state
1795 
1796     mNeedConfig = false;
1797 
1798     internalUpdateStatusLocked((mDummyStreamId == NO_STREAM) ?
1799             STATUS_CONFIGURED : STATUS_UNCONFIGURED);
1800 
1801     ALOGV("%s: Camera %d: Stream configuration complete", __FUNCTION__, mId);
1802 
1803     // tear down the deleted streams after configure streams.
1804     mDeletedStreams.clear();
1805 
1806     return OK;
1807 }
1808 
addDummyStreamLocked()1809 status_t Camera3Device::addDummyStreamLocked() {
1810     ATRACE_CALL();
1811     status_t res;
1812 
1813     if (mDummyStreamId != NO_STREAM) {
1814         // Should never be adding a second dummy stream when one is already
1815         // active
1816         SET_ERR_L("%s: Camera %d: A dummy stream already exists!",
1817                 __FUNCTION__, mId);
1818         return INVALID_OPERATION;
1819     }
1820 
1821     ALOGV("%s: Camera %d: Adding a dummy stream", __FUNCTION__, mId);
1822 
1823     sp<Camera3OutputStreamInterface> dummyStream =
1824             new Camera3DummyStream(mNextStreamId);
1825 
1826     res = mOutputStreams.add(mNextStreamId, dummyStream);
1827     if (res < 0) {
1828         SET_ERR_L("Can't add dummy stream to set: %s (%d)", strerror(-res), res);
1829         return res;
1830     }
1831 
1832     mDummyStreamId = mNextStreamId;
1833     mNextStreamId++;
1834 
1835     return OK;
1836 }
1837 
tryRemoveDummyStreamLocked()1838 status_t Camera3Device::tryRemoveDummyStreamLocked() {
1839     ATRACE_CALL();
1840     status_t res;
1841 
1842     if (mDummyStreamId == NO_STREAM) return OK;
1843     if (mOutputStreams.size() == 1) return OK;
1844 
1845     ALOGV("%s: Camera %d: Removing the dummy stream", __FUNCTION__, mId);
1846 
1847     // Ok, have a dummy stream and there's at least one other output stream,
1848     // so remove the dummy
1849 
1850     sp<Camera3StreamInterface> deletedStream;
1851     ssize_t outputStreamIdx = mOutputStreams.indexOfKey(mDummyStreamId);
1852     if (outputStreamIdx == NAME_NOT_FOUND) {
1853         SET_ERR_L("Dummy stream %d does not appear to exist", mDummyStreamId);
1854         return INVALID_OPERATION;
1855     }
1856 
1857     deletedStream = mOutputStreams.editValueAt(outputStreamIdx);
1858     mOutputStreams.removeItemsAt(outputStreamIdx);
1859 
1860     // Free up the stream endpoint so that it can be used by some other stream
1861     res = deletedStream->disconnect();
1862     if (res != OK) {
1863         SET_ERR_L("Can't disconnect deleted dummy stream %d", mDummyStreamId);
1864         // fall through since we want to still list the stream as deleted.
1865     }
1866     mDeletedStreams.add(deletedStream);
1867     mDummyStreamId = NO_STREAM;
1868 
1869     return res;
1870 }
1871 
setErrorState(const char * fmt,...)1872 void Camera3Device::setErrorState(const char *fmt, ...) {
1873     Mutex::Autolock l(mLock);
1874     va_list args;
1875     va_start(args, fmt);
1876 
1877     setErrorStateLockedV(fmt, args);
1878 
1879     va_end(args);
1880 }
1881 
setErrorStateV(const char * fmt,va_list args)1882 void Camera3Device::setErrorStateV(const char *fmt, va_list args) {
1883     Mutex::Autolock l(mLock);
1884     setErrorStateLockedV(fmt, args);
1885 }
1886 
setErrorStateLocked(const char * fmt,...)1887 void Camera3Device::setErrorStateLocked(const char *fmt, ...) {
1888     va_list args;
1889     va_start(args, fmt);
1890 
1891     setErrorStateLockedV(fmt, args);
1892 
1893     va_end(args);
1894 }
1895 
setErrorStateLockedV(const char * fmt,va_list args)1896 void Camera3Device::setErrorStateLockedV(const char *fmt, va_list args) {
1897     // Print out all error messages to log
1898     String8 errorCause = String8::formatV(fmt, args);
1899     ALOGE("Camera %d: %s", mId, errorCause.string());
1900 
1901     // But only do error state transition steps for the first error
1902     if (mStatus == STATUS_ERROR || mStatus == STATUS_UNINITIALIZED) return;
1903 
1904     mErrorCause = errorCause;
1905 
1906     mRequestThread->setPaused(true);
1907     internalUpdateStatusLocked(STATUS_ERROR);
1908 
1909     // Notify upstream about a device error
1910     if (mListener != NULL) {
1911         mListener->notifyError(ICameraDeviceCallbacks::ERROR_CAMERA_DEVICE,
1912                 CaptureResultExtras());
1913     }
1914 
1915     // Save stack trace. View by dumping it later.
1916     CameraTraces::saveTrace();
1917     // TODO: consider adding errorCause and client pid/procname
1918 }
1919 
1920 /**
1921  * In-flight request management
1922  */
1923 
registerInFlight(uint32_t frameNumber,int32_t numBuffers,CaptureResultExtras resultExtras,bool hasInput,const AeTriggerCancelOverride_t & aeTriggerCancelOverride)1924 status_t Camera3Device::registerInFlight(uint32_t frameNumber,
1925         int32_t numBuffers, CaptureResultExtras resultExtras, bool hasInput,
1926         const AeTriggerCancelOverride_t &aeTriggerCancelOverride) {
1927     ATRACE_CALL();
1928     Mutex::Autolock l(mInFlightLock);
1929 
1930     ssize_t res;
1931     res = mInFlightMap.add(frameNumber, InFlightRequest(numBuffers, resultExtras, hasInput,
1932             aeTriggerCancelOverride));
1933     if (res < 0) return res;
1934 
1935     return OK;
1936 }
1937 
1938 /**
1939  * Check if all 3A fields are ready, and send off a partial 3A-only result
1940  * to the output frame queue
1941  */
processPartial3AResult(uint32_t frameNumber,const CameraMetadata & partial,const CaptureResultExtras & resultExtras)1942 bool Camera3Device::processPartial3AResult(
1943         uint32_t frameNumber,
1944         const CameraMetadata& partial, const CaptureResultExtras& resultExtras) {
1945 
1946     // Check if all 3A states are present
1947     // The full list of fields is
1948     //   android.control.afMode
1949     //   android.control.awbMode
1950     //   android.control.aeState
1951     //   android.control.awbState
1952     //   android.control.afState
1953     //   android.control.afTriggerID
1954     //   android.control.aePrecaptureID
1955     // TODO: Add android.control.aeMode
1956 
1957     bool gotAllStates = true;
1958 
1959     uint8_t afMode;
1960     uint8_t awbMode;
1961     uint8_t aeState;
1962     uint8_t afState;
1963     uint8_t awbState;
1964 
1965     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AF_MODE,
1966         &afMode, frameNumber);
1967 
1968     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AWB_MODE,
1969         &awbMode, frameNumber);
1970 
1971     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AE_STATE,
1972         &aeState, frameNumber);
1973 
1974     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AF_STATE,
1975         &afState, frameNumber);
1976 
1977     gotAllStates &= get3AResult(partial, ANDROID_CONTROL_AWB_STATE,
1978         &awbState, frameNumber);
1979 
1980     if (!gotAllStates) return false;
1981 
1982     ALOGVV("%s: Camera %d: Frame %d, Request ID %d: AF mode %d, AWB mode %d, "
1983         "AF state %d, AE state %d, AWB state %d, "
1984         "AF trigger %d, AE precapture trigger %d",
1985         __FUNCTION__, mId, frameNumber, resultExtras.requestId,
1986         afMode, awbMode,
1987         afState, aeState, awbState,
1988         resultExtras.afTriggerId, resultExtras.precaptureTriggerId);
1989 
1990     // Got all states, so construct a minimal result to send
1991     // In addition to the above fields, this means adding in
1992     //   android.request.frameCount
1993     //   android.request.requestId
1994     //   android.quirks.partialResult (for HAL version below HAL3.2)
1995 
1996     const size_t kMinimal3AResultEntries = 10;
1997 
1998     Mutex::Autolock l(mOutputLock);
1999 
2000     CaptureResult captureResult;
2001     captureResult.mResultExtras = resultExtras;
2002     captureResult.mMetadata = CameraMetadata(kMinimal3AResultEntries, /*dataCapacity*/ 0);
2003     // TODO: change this to sp<CaptureResult>. This will need other changes, including,
2004     // but not limited to CameraDeviceBase::getNextResult
2005     CaptureResult& min3AResult =
2006             *mResultQueue.insert(mResultQueue.end(), captureResult);
2007 
2008     if (!insert3AResult(min3AResult.mMetadata, ANDROID_REQUEST_FRAME_COUNT,
2009             // TODO: This is problematic casting. Need to fix CameraMetadata.
2010             reinterpret_cast<int32_t*>(&frameNumber), frameNumber)) {
2011         return false;
2012     }
2013 
2014     int32_t requestId = resultExtras.requestId;
2015     if (!insert3AResult(min3AResult.mMetadata, ANDROID_REQUEST_ID,
2016             &requestId, frameNumber)) {
2017         return false;
2018     }
2019 
2020     if (mDeviceVersion < CAMERA_DEVICE_API_VERSION_3_2) {
2021         static const uint8_t partialResult = ANDROID_QUIRKS_PARTIAL_RESULT_PARTIAL;
2022         if (!insert3AResult(min3AResult.mMetadata, ANDROID_QUIRKS_PARTIAL_RESULT,
2023                 &partialResult, frameNumber)) {
2024             return false;
2025         }
2026     }
2027 
2028     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AF_MODE,
2029             &afMode, frameNumber)) {
2030         return false;
2031     }
2032 
2033     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AWB_MODE,
2034             &awbMode, frameNumber)) {
2035         return false;
2036     }
2037 
2038     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AE_STATE,
2039             &aeState, frameNumber)) {
2040         return false;
2041     }
2042 
2043     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AF_STATE,
2044             &afState, frameNumber)) {
2045         return false;
2046     }
2047 
2048     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AWB_STATE,
2049             &awbState, frameNumber)) {
2050         return false;
2051     }
2052 
2053     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AF_TRIGGER_ID,
2054             &resultExtras.afTriggerId, frameNumber)) {
2055         return false;
2056     }
2057 
2058     if (!insert3AResult(min3AResult.mMetadata, ANDROID_CONTROL_AE_PRECAPTURE_ID,
2059             &resultExtras.precaptureTriggerId, frameNumber)) {
2060         return false;
2061     }
2062 
2063     // We only send the aggregated partial when all 3A related metadata are available
2064     // For both API1 and API2.
2065     // TODO: we probably should pass through all partials to API2 unconditionally.
2066     mResultSignal.signal();
2067 
2068     return true;
2069 }
2070 
2071 template<typename T>
get3AResult(const CameraMetadata & result,int32_t tag,T * value,uint32_t frameNumber)2072 bool Camera3Device::get3AResult(const CameraMetadata& result, int32_t tag,
2073         T* value, uint32_t frameNumber) {
2074     (void) frameNumber;
2075 
2076     camera_metadata_ro_entry_t entry;
2077 
2078     entry = result.find(tag);
2079     if (entry.count == 0) {
2080         ALOGVV("%s: Camera %d: Frame %d: No %s provided by HAL!", __FUNCTION__,
2081             mId, frameNumber, get_camera_metadata_tag_name(tag));
2082         return false;
2083     }
2084 
2085     if (sizeof(T) == sizeof(uint8_t)) {
2086         *value = entry.data.u8[0];
2087     } else if (sizeof(T) == sizeof(int32_t)) {
2088         *value = entry.data.i32[0];
2089     } else {
2090         ALOGE("%s: Unexpected type", __FUNCTION__);
2091         return false;
2092     }
2093     return true;
2094 }
2095 
2096 template<typename T>
insert3AResult(CameraMetadata & result,int32_t tag,const T * value,uint32_t frameNumber)2097 bool Camera3Device::insert3AResult(CameraMetadata& result, int32_t tag,
2098         const T* value, uint32_t frameNumber) {
2099     if (result.update(tag, value, 1) != NO_ERROR) {
2100         mResultQueue.erase(--mResultQueue.end(), mResultQueue.end());
2101         SET_ERR("Frame %d: Failed to set %s in partial metadata",
2102                 frameNumber, get_camera_metadata_tag_name(tag));
2103         return false;
2104     }
2105     return true;
2106 }
2107 
returnOutputBuffers(const camera3_stream_buffer_t * outputBuffers,size_t numBuffers,nsecs_t timestamp)2108 void Camera3Device::returnOutputBuffers(
2109         const camera3_stream_buffer_t *outputBuffers, size_t numBuffers,
2110         nsecs_t timestamp) {
2111     for (size_t i = 0; i < numBuffers; i++)
2112     {
2113         Camera3Stream *stream = Camera3Stream::cast(outputBuffers[i].stream);
2114         status_t res = stream->returnBuffer(outputBuffers[i], timestamp);
2115         // Note: stream may be deallocated at this point, if this buffer was
2116         // the last reference to it.
2117         if (res != OK) {
2118             ALOGE("Can't return buffer to its stream: %s (%d)",
2119                 strerror(-res), res);
2120         }
2121     }
2122 }
2123 
2124 
removeInFlightRequestIfReadyLocked(int idx)2125 void Camera3Device::removeInFlightRequestIfReadyLocked(int idx) {
2126 
2127     const InFlightRequest &request = mInFlightMap.valueAt(idx);
2128     const uint32_t frameNumber = mInFlightMap.keyAt(idx);
2129 
2130     nsecs_t sensorTimestamp = request.sensorTimestamp;
2131     nsecs_t shutterTimestamp = request.shutterTimestamp;
2132 
2133     // Check if it's okay to remove the request from InFlightMap:
2134     // In the case of a successful request:
2135     //      all input and output buffers, all result metadata, shutter callback
2136     //      arrived.
2137     // In the case of a unsuccessful request:
2138     //      all input and output buffers arrived.
2139     if (request.numBuffersLeft == 0 &&
2140             (request.requestStatus != OK ||
2141             (request.haveResultMetadata && shutterTimestamp != 0))) {
2142         ATRACE_ASYNC_END("frame capture", frameNumber);
2143 
2144         // Sanity check - if sensor timestamp matches shutter timestamp
2145         if (request.requestStatus == OK &&
2146                 sensorTimestamp != shutterTimestamp) {
2147             SET_ERR("sensor timestamp (%" PRId64
2148                 ") for frame %d doesn't match shutter timestamp (%" PRId64 ")",
2149                 sensorTimestamp, frameNumber, shutterTimestamp);
2150         }
2151 
2152         // for an unsuccessful request, it may have pending output buffers to
2153         // return.
2154         assert(request.requestStatus != OK ||
2155                request.pendingOutputBuffers.size() == 0);
2156         returnOutputBuffers(request.pendingOutputBuffers.array(),
2157             request.pendingOutputBuffers.size(), 0);
2158 
2159         mInFlightMap.removeItemsAt(idx, 1);
2160 
2161         ALOGVV("%s: removed frame %d from InFlightMap", __FUNCTION__, frameNumber);
2162      }
2163 
2164     // Sanity check - if we have too many in-flight frames, something has
2165     // likely gone wrong
2166     if (!mIsConstrainedHighSpeedConfiguration && mInFlightMap.size() > kInFlightWarnLimit) {
2167         CLOGE("In-flight list too large: %zu", mInFlightMap.size());
2168     } else if (mIsConstrainedHighSpeedConfiguration && mInFlightMap.size() >
2169             kInFlightWarnLimitHighSpeed) {
2170         CLOGE("In-flight list too large for high speed configuration: %zu",
2171                 mInFlightMap.size());
2172     }
2173 }
2174 
2175 
sendCaptureResult(CameraMetadata & pendingMetadata,CaptureResultExtras & resultExtras,CameraMetadata & collectedPartialResult,uint32_t frameNumber,bool reprocess,const AeTriggerCancelOverride_t & aeTriggerCancelOverride)2176 void Camera3Device::sendCaptureResult(CameraMetadata &pendingMetadata,
2177         CaptureResultExtras &resultExtras,
2178         CameraMetadata &collectedPartialResult,
2179         uint32_t frameNumber,
2180         bool reprocess,
2181         const AeTriggerCancelOverride_t &aeTriggerCancelOverride) {
2182     if (pendingMetadata.isEmpty())
2183         return;
2184 
2185     Mutex::Autolock l(mOutputLock);
2186 
2187     // TODO: need to track errors for tighter bounds on expected frame number
2188     if (reprocess) {
2189         if (frameNumber < mNextReprocessResultFrameNumber) {
2190             SET_ERR("Out-of-order reprocess capture result metadata submitted! "
2191                 "(got frame number %d, expecting %d)",
2192                 frameNumber, mNextReprocessResultFrameNumber);
2193             return;
2194         }
2195         mNextReprocessResultFrameNumber = frameNumber + 1;
2196     } else {
2197         if (frameNumber < mNextResultFrameNumber) {
2198             SET_ERR("Out-of-order capture result metadata submitted! "
2199                     "(got frame number %d, expecting %d)",
2200                     frameNumber, mNextResultFrameNumber);
2201             return;
2202         }
2203         mNextResultFrameNumber = frameNumber + 1;
2204     }
2205 
2206     CaptureResult captureResult;
2207     captureResult.mResultExtras = resultExtras;
2208     captureResult.mMetadata = pendingMetadata;
2209 
2210     if (captureResult.mMetadata.update(ANDROID_REQUEST_FRAME_COUNT,
2211             (int32_t*)&frameNumber, 1) != OK) {
2212         SET_ERR("Failed to set frame# in metadata (%d)",
2213                 frameNumber);
2214         return;
2215     } else {
2216         ALOGVV("%s: Camera %d: Set frame# in metadata (%d)",
2217                 __FUNCTION__, mId, frameNumber);
2218     }
2219 
2220     // Append any previous partials to form a complete result
2221     if (mUsePartialResult && !collectedPartialResult.isEmpty()) {
2222         captureResult.mMetadata.append(collectedPartialResult);
2223     }
2224 
2225     captureResult.mMetadata.sort();
2226 
2227     // Check that there's a timestamp in the result metadata
2228     camera_metadata_entry entry =
2229             captureResult.mMetadata.find(ANDROID_SENSOR_TIMESTAMP);
2230     if (entry.count == 0) {
2231         SET_ERR("No timestamp provided by HAL for frame %d!",
2232                 frameNumber);
2233         return;
2234     }
2235 
2236     overrideResultForPrecaptureCancel(&captureResult.mMetadata, aeTriggerCancelOverride);
2237 
2238     // Valid result, insert into queue
2239     List<CaptureResult>::iterator queuedResult =
2240             mResultQueue.insert(mResultQueue.end(), CaptureResult(captureResult));
2241     ALOGVV("%s: result requestId = %" PRId32 ", frameNumber = %" PRId64
2242            ", burstId = %" PRId32, __FUNCTION__,
2243            queuedResult->mResultExtras.requestId,
2244            queuedResult->mResultExtras.frameNumber,
2245            queuedResult->mResultExtras.burstId);
2246 
2247     mResultSignal.signal();
2248 }
2249 
2250 /**
2251  * Camera HAL device callback methods
2252  */
2253 
processCaptureResult(const camera3_capture_result * result)2254 void Camera3Device::processCaptureResult(const camera3_capture_result *result) {
2255     ATRACE_CALL();
2256 
2257     status_t res;
2258 
2259     uint32_t frameNumber = result->frame_number;
2260     if (result->result == NULL && result->num_output_buffers == 0 &&
2261             result->input_buffer == NULL) {
2262         SET_ERR("No result data provided by HAL for frame %d",
2263                 frameNumber);
2264         return;
2265     }
2266 
2267     // For HAL3.2 or above, If HAL doesn't support partial, it must always set
2268     // partial_result to 1 when metadata is included in this result.
2269     if (!mUsePartialResult &&
2270             mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2 &&
2271             result->result != NULL &&
2272             result->partial_result != 1) {
2273         SET_ERR("Result is malformed for frame %d: partial_result %u must be 1"
2274                 " if partial result is not supported",
2275                 frameNumber, result->partial_result);
2276         return;
2277     }
2278 
2279     bool isPartialResult = false;
2280     CameraMetadata collectedPartialResult;
2281     CaptureResultExtras resultExtras;
2282     bool hasInputBufferInRequest = false;
2283 
2284     // Get shutter timestamp and resultExtras from list of in-flight requests,
2285     // where it was added by the shutter notification for this frame. If the
2286     // shutter timestamp isn't received yet, append the output buffers to the
2287     // in-flight request and they will be returned when the shutter timestamp
2288     // arrives. Update the in-flight status and remove the in-flight entry if
2289     // all result data and shutter timestamp have been received.
2290     nsecs_t shutterTimestamp = 0;
2291 
2292     {
2293         Mutex::Autolock l(mInFlightLock);
2294         ssize_t idx = mInFlightMap.indexOfKey(frameNumber);
2295         if (idx == NAME_NOT_FOUND) {
2296             SET_ERR("Unknown frame number for capture result: %d",
2297                     frameNumber);
2298             return;
2299         }
2300         InFlightRequest &request = mInFlightMap.editValueAt(idx);
2301         ALOGVV("%s: got InFlightRequest requestId = %" PRId32
2302                 ", frameNumber = %" PRId64 ", burstId = %" PRId32
2303                 ", partialResultCount = %d",
2304                 __FUNCTION__, request.resultExtras.requestId,
2305                 request.resultExtras.frameNumber, request.resultExtras.burstId,
2306                 result->partial_result);
2307         // Always update the partial count to the latest one if it's not 0
2308         // (buffers only). When framework aggregates adjacent partial results
2309         // into one, the latest partial count will be used.
2310         if (result->partial_result != 0)
2311             request.resultExtras.partialResultCount = result->partial_result;
2312 
2313         // Check if this result carries only partial metadata
2314         if (mUsePartialResult && result->result != NULL) {
2315             if (mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
2316                 if (result->partial_result > mNumPartialResults || result->partial_result < 1) {
2317                     SET_ERR("Result is malformed for frame %d: partial_result %u must be  in"
2318                             " the range of [1, %d] when metadata is included in the result",
2319                             frameNumber, result->partial_result, mNumPartialResults);
2320                     return;
2321                 }
2322                 isPartialResult = (result->partial_result < mNumPartialResults);
2323                 if (isPartialResult) {
2324                     request.partialResult.collectedResult.append(result->result);
2325                 }
2326             } else {
2327                 camera_metadata_ro_entry_t partialResultEntry;
2328                 res = find_camera_metadata_ro_entry(result->result,
2329                         ANDROID_QUIRKS_PARTIAL_RESULT, &partialResultEntry);
2330                 if (res != NAME_NOT_FOUND &&
2331                         partialResultEntry.count > 0 &&
2332                         partialResultEntry.data.u8[0] ==
2333                         ANDROID_QUIRKS_PARTIAL_RESULT_PARTIAL) {
2334                     // A partial result. Flag this as such, and collect this
2335                     // set of metadata into the in-flight entry.
2336                     isPartialResult = true;
2337                     request.partialResult.collectedResult.append(
2338                         result->result);
2339                     request.partialResult.collectedResult.erase(
2340                         ANDROID_QUIRKS_PARTIAL_RESULT);
2341                 }
2342             }
2343 
2344             if (isPartialResult) {
2345                 // Fire off a 3A-only result if possible
2346                 if (!request.partialResult.haveSent3A) {
2347                     request.partialResult.haveSent3A =
2348                             processPartial3AResult(frameNumber,
2349                                     request.partialResult.collectedResult,
2350                                     request.resultExtras);
2351                 }
2352             }
2353         }
2354 
2355         shutterTimestamp = request.shutterTimestamp;
2356         hasInputBufferInRequest = request.hasInputBuffer;
2357 
2358         // Did we get the (final) result metadata for this capture?
2359         if (result->result != NULL && !isPartialResult) {
2360             if (request.haveResultMetadata) {
2361                 SET_ERR("Called multiple times with metadata for frame %d",
2362                         frameNumber);
2363                 return;
2364             }
2365             if (mUsePartialResult &&
2366                     !request.partialResult.collectedResult.isEmpty()) {
2367                 collectedPartialResult.acquire(
2368                     request.partialResult.collectedResult);
2369             }
2370             request.haveResultMetadata = true;
2371         }
2372 
2373         uint32_t numBuffersReturned = result->num_output_buffers;
2374         if (result->input_buffer != NULL) {
2375             if (hasInputBufferInRequest) {
2376                 numBuffersReturned += 1;
2377             } else {
2378                 ALOGW("%s: Input buffer should be NULL if there is no input"
2379                         " buffer sent in the request",
2380                         __FUNCTION__);
2381             }
2382         }
2383         request.numBuffersLeft -= numBuffersReturned;
2384         if (request.numBuffersLeft < 0) {
2385             SET_ERR("Too many buffers returned for frame %d",
2386                     frameNumber);
2387             return;
2388         }
2389 
2390         camera_metadata_ro_entry_t entry;
2391         res = find_camera_metadata_ro_entry(result->result,
2392                 ANDROID_SENSOR_TIMESTAMP, &entry);
2393         if (res == OK && entry.count == 1) {
2394             request.sensorTimestamp = entry.data.i64[0];
2395         }
2396 
2397         // If shutter event isn't received yet, append the output buffers to
2398         // the in-flight request. Otherwise, return the output buffers to
2399         // streams.
2400         if (shutterTimestamp == 0) {
2401             request.pendingOutputBuffers.appendArray(result->output_buffers,
2402                 result->num_output_buffers);
2403         } else {
2404             returnOutputBuffers(result->output_buffers,
2405                 result->num_output_buffers, shutterTimestamp);
2406         }
2407 
2408         if (result->result != NULL && !isPartialResult) {
2409             if (shutterTimestamp == 0) {
2410                 request.pendingMetadata = result->result;
2411                 request.partialResult.collectedResult = collectedPartialResult;
2412             } else {
2413                 CameraMetadata metadata;
2414                 metadata = result->result;
2415                 sendCaptureResult(metadata, request.resultExtras,
2416                     collectedPartialResult, frameNumber, hasInputBufferInRequest,
2417                     request.aeTriggerCancelOverride);
2418             }
2419         }
2420 
2421         removeInFlightRequestIfReadyLocked(idx);
2422     } // scope for mInFlightLock
2423 
2424     if (result->input_buffer != NULL) {
2425         if (hasInputBufferInRequest) {
2426             Camera3Stream *stream =
2427                 Camera3Stream::cast(result->input_buffer->stream);
2428             res = stream->returnInputBuffer(*(result->input_buffer));
2429             // Note: stream may be deallocated at this point, if this buffer was the
2430             // last reference to it.
2431             if (res != OK) {
2432                 ALOGE("%s: RequestThread: Can't return input buffer for frame %d to"
2433                       "  its stream:%s (%d)",  __FUNCTION__,
2434                       frameNumber, strerror(-res), res);
2435             }
2436         } else {
2437             ALOGW("%s: Input buffer should be NULL if there is no input"
2438                     " buffer sent in the request, skipping input buffer return.",
2439                     __FUNCTION__);
2440         }
2441     }
2442 }
2443 
notify(const camera3_notify_msg * msg)2444 void Camera3Device::notify(const camera3_notify_msg *msg) {
2445     ATRACE_CALL();
2446     NotificationListener *listener;
2447     {
2448         Mutex::Autolock l(mOutputLock);
2449         listener = mListener;
2450     }
2451 
2452     if (msg == NULL) {
2453         SET_ERR("HAL sent NULL notify message!");
2454         return;
2455     }
2456 
2457     switch (msg->type) {
2458         case CAMERA3_MSG_ERROR: {
2459             notifyError(msg->message.error, listener);
2460             break;
2461         }
2462         case CAMERA3_MSG_SHUTTER: {
2463             notifyShutter(msg->message.shutter, listener);
2464             break;
2465         }
2466         default:
2467             SET_ERR("Unknown notify message from HAL: %d",
2468                     msg->type);
2469     }
2470 }
2471 
notifyError(const camera3_error_msg_t & msg,NotificationListener * listener)2472 void Camera3Device::notifyError(const camera3_error_msg_t &msg,
2473         NotificationListener *listener) {
2474 
2475     // Map camera HAL error codes to ICameraDeviceCallback error codes
2476     // Index into this with the HAL error code
2477     static const ICameraDeviceCallbacks::CameraErrorCode
2478             halErrorMap[CAMERA3_MSG_NUM_ERRORS] = {
2479         // 0 = Unused error code
2480         ICameraDeviceCallbacks::ERROR_CAMERA_INVALID_ERROR,
2481         // 1 = CAMERA3_MSG_ERROR_DEVICE
2482         ICameraDeviceCallbacks::ERROR_CAMERA_DEVICE,
2483         // 2 = CAMERA3_MSG_ERROR_REQUEST
2484         ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
2485         // 3 = CAMERA3_MSG_ERROR_RESULT
2486         ICameraDeviceCallbacks::ERROR_CAMERA_RESULT,
2487         // 4 = CAMERA3_MSG_ERROR_BUFFER
2488         ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER
2489     };
2490 
2491     ICameraDeviceCallbacks::CameraErrorCode errorCode =
2492             ((msg.error_code >= 0) &&
2493                     (msg.error_code < CAMERA3_MSG_NUM_ERRORS)) ?
2494             halErrorMap[msg.error_code] :
2495             ICameraDeviceCallbacks::ERROR_CAMERA_INVALID_ERROR;
2496 
2497     int streamId = 0;
2498     if (msg.error_stream != NULL) {
2499         Camera3Stream *stream =
2500                 Camera3Stream::cast(msg.error_stream);
2501         streamId = stream->getId();
2502     }
2503     ALOGV("Camera %d: %s: HAL error, frame %d, stream %d: %d",
2504             mId, __FUNCTION__, msg.frame_number,
2505             streamId, msg.error_code);
2506 
2507     CaptureResultExtras resultExtras;
2508     switch (errorCode) {
2509         case ICameraDeviceCallbacks::ERROR_CAMERA_DEVICE:
2510             // SET_ERR calls notifyError
2511             SET_ERR("Camera HAL reported serious device error");
2512             break;
2513         case ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST:
2514         case ICameraDeviceCallbacks::ERROR_CAMERA_RESULT:
2515         case ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER:
2516             {
2517                 Mutex::Autolock l(mInFlightLock);
2518                 ssize_t idx = mInFlightMap.indexOfKey(msg.frame_number);
2519                 if (idx >= 0) {
2520                     InFlightRequest &r = mInFlightMap.editValueAt(idx);
2521                     r.requestStatus = msg.error_code;
2522                     resultExtras = r.resultExtras;
2523                 } else {
2524                     resultExtras.frameNumber = msg.frame_number;
2525                     ALOGE("Camera %d: %s: cannot find in-flight request on "
2526                             "frame %" PRId64 " error", mId, __FUNCTION__,
2527                             resultExtras.frameNumber);
2528                 }
2529             }
2530             if (listener != NULL) {
2531                 listener->notifyError(errorCode, resultExtras);
2532             } else {
2533                 ALOGE("Camera %d: %s: no listener available", mId, __FUNCTION__);
2534             }
2535             break;
2536         default:
2537             // SET_ERR calls notifyError
2538             SET_ERR("Unknown error message from HAL: %d", msg.error_code);
2539             break;
2540     }
2541 }
2542 
notifyShutter(const camera3_shutter_msg_t & msg,NotificationListener * listener)2543 void Camera3Device::notifyShutter(const camera3_shutter_msg_t &msg,
2544         NotificationListener *listener) {
2545     ssize_t idx;
2546 
2547     // Set timestamp for the request in the in-flight tracking
2548     // and get the request ID to send upstream
2549     {
2550         Mutex::Autolock l(mInFlightLock);
2551         idx = mInFlightMap.indexOfKey(msg.frame_number);
2552         if (idx >= 0) {
2553             InFlightRequest &r = mInFlightMap.editValueAt(idx);
2554 
2555             // Verify ordering of shutter notifications
2556             {
2557                 Mutex::Autolock l(mOutputLock);
2558                 // TODO: need to track errors for tighter bounds on expected frame number.
2559                 if (r.hasInputBuffer) {
2560                     if (msg.frame_number < mNextReprocessShutterFrameNumber) {
2561                         SET_ERR("Shutter notification out-of-order. Expected "
2562                                 "notification for frame %d, got frame %d",
2563                                 mNextReprocessShutterFrameNumber, msg.frame_number);
2564                         return;
2565                     }
2566                     mNextReprocessShutterFrameNumber = msg.frame_number + 1;
2567                 } else {
2568                     if (msg.frame_number < mNextShutterFrameNumber) {
2569                         SET_ERR("Shutter notification out-of-order. Expected "
2570                                 "notification for frame %d, got frame %d",
2571                                 mNextShutterFrameNumber, msg.frame_number);
2572                         return;
2573                     }
2574                     mNextShutterFrameNumber = msg.frame_number + 1;
2575                 }
2576             }
2577 
2578             ALOGVV("Camera %d: %s: Shutter fired for frame %d (id %d) at %" PRId64,
2579                     mId, __FUNCTION__,
2580                     msg.frame_number, r.resultExtras.requestId, msg.timestamp);
2581             // Call listener, if any
2582             if (listener != NULL) {
2583                 listener->notifyShutter(r.resultExtras, msg.timestamp);
2584             }
2585 
2586             r.shutterTimestamp = msg.timestamp;
2587 
2588             // send pending result and buffers
2589             sendCaptureResult(r.pendingMetadata, r.resultExtras,
2590                 r.partialResult.collectedResult, msg.frame_number,
2591                 r.hasInputBuffer, r.aeTriggerCancelOverride);
2592             returnOutputBuffers(r.pendingOutputBuffers.array(),
2593                 r.pendingOutputBuffers.size(), r.shutterTimestamp);
2594             r.pendingOutputBuffers.clear();
2595 
2596             removeInFlightRequestIfReadyLocked(idx);
2597         }
2598     }
2599     if (idx < 0) {
2600         SET_ERR("Shutter notification for non-existent frame number %d",
2601                 msg.frame_number);
2602     }
2603 }
2604 
2605 
getLatestRequestLocked()2606 CameraMetadata Camera3Device::getLatestRequestLocked() {
2607     ALOGV("%s", __FUNCTION__);
2608 
2609     CameraMetadata retVal;
2610 
2611     if (mRequestThread != NULL) {
2612         retVal = mRequestThread->getLatestRequest();
2613     }
2614 
2615     return retVal;
2616 }
2617 
2618 
2619 /**
2620  * RequestThread inner class methods
2621  */
2622 
RequestThread(wp<Camera3Device> parent,sp<StatusTracker> statusTracker,camera3_device_t * hal3Device,bool aeLockAvailable)2623 Camera3Device::RequestThread::RequestThread(wp<Camera3Device> parent,
2624         sp<StatusTracker> statusTracker,
2625         camera3_device_t *hal3Device,
2626         bool aeLockAvailable) :
2627         Thread(/*canCallJava*/false),
2628         mParent(parent),
2629         mStatusTracker(statusTracker),
2630         mHal3Device(hal3Device),
2631         mId(getId(parent)),
2632         mReconfigured(false),
2633         mDoPause(false),
2634         mPaused(true),
2635         mFrameNumber(0),
2636         mLatestRequestId(NAME_NOT_FOUND),
2637         mCurrentAfTriggerId(0),
2638         mCurrentPreCaptureTriggerId(0),
2639         mRepeatingLastFrameNumber(NO_IN_FLIGHT_REPEATING_FRAMES),
2640         mAeLockAvailable(aeLockAvailable) {
2641     mStatusId = statusTracker->addComponent();
2642 }
2643 
setNotificationListener(NotificationListener * listener)2644 void Camera3Device::RequestThread::setNotificationListener(
2645         NotificationListener *listener) {
2646     Mutex::Autolock l(mRequestLock);
2647     mListener = listener;
2648 }
2649 
configurationComplete()2650 void Camera3Device::RequestThread::configurationComplete() {
2651     Mutex::Autolock l(mRequestLock);
2652     mReconfigured = true;
2653 }
2654 
queueRequestList(List<sp<CaptureRequest>> & requests,int64_t * lastFrameNumber)2655 status_t Camera3Device::RequestThread::queueRequestList(
2656         List<sp<CaptureRequest> > &requests,
2657         /*out*/
2658         int64_t *lastFrameNumber) {
2659     Mutex::Autolock l(mRequestLock);
2660     for (List<sp<CaptureRequest> >::iterator it = requests.begin(); it != requests.end();
2661             ++it) {
2662         mRequestQueue.push_back(*it);
2663     }
2664 
2665     if (lastFrameNumber != NULL) {
2666         *lastFrameNumber = mFrameNumber + mRequestQueue.size() - 1;
2667         ALOGV("%s: requestId %d, mFrameNumber %" PRId32 ", lastFrameNumber %" PRId64 ".",
2668               __FUNCTION__, (*(requests.begin()))->mResultExtras.requestId, mFrameNumber,
2669               *lastFrameNumber);
2670     }
2671 
2672     unpauseForNewRequests();
2673 
2674     return OK;
2675 }
2676 
2677 
queueTrigger(RequestTrigger trigger[],size_t count)2678 status_t Camera3Device::RequestThread::queueTrigger(
2679         RequestTrigger trigger[],
2680         size_t count) {
2681 
2682     Mutex::Autolock l(mTriggerMutex);
2683     status_t ret;
2684 
2685     for (size_t i = 0; i < count; ++i) {
2686         ret = queueTriggerLocked(trigger[i]);
2687 
2688         if (ret != OK) {
2689             return ret;
2690         }
2691     }
2692 
2693     return OK;
2694 }
2695 
getId(const wp<Camera3Device> & device)2696 int Camera3Device::RequestThread::getId(const wp<Camera3Device> &device) {
2697     sp<Camera3Device> d = device.promote();
2698     if (d != NULL) return d->mId;
2699     return 0;
2700 }
2701 
queueTriggerLocked(RequestTrigger trigger)2702 status_t Camera3Device::RequestThread::queueTriggerLocked(
2703         RequestTrigger trigger) {
2704 
2705     uint32_t tag = trigger.metadataTag;
2706     ssize_t index = mTriggerMap.indexOfKey(tag);
2707 
2708     switch (trigger.getTagType()) {
2709         case TYPE_BYTE:
2710         // fall-through
2711         case TYPE_INT32:
2712             break;
2713         default:
2714             ALOGE("%s: Type not supported: 0x%x", __FUNCTION__,
2715                     trigger.getTagType());
2716             return INVALID_OPERATION;
2717     }
2718 
2719     /**
2720      * Collect only the latest trigger, since we only have 1 field
2721      * in the request settings per trigger tag, and can't send more than 1
2722      * trigger per request.
2723      */
2724     if (index != NAME_NOT_FOUND) {
2725         mTriggerMap.editValueAt(index) = trigger;
2726     } else {
2727         mTriggerMap.add(tag, trigger);
2728     }
2729 
2730     return OK;
2731 }
2732 
setRepeatingRequests(const RequestList & requests,int64_t * lastFrameNumber)2733 status_t Camera3Device::RequestThread::setRepeatingRequests(
2734         const RequestList &requests,
2735         /*out*/
2736         int64_t *lastFrameNumber) {
2737     Mutex::Autolock l(mRequestLock);
2738     if (lastFrameNumber != NULL) {
2739         *lastFrameNumber = mRepeatingLastFrameNumber;
2740     }
2741     mRepeatingRequests.clear();
2742     mRepeatingRequests.insert(mRepeatingRequests.begin(),
2743             requests.begin(), requests.end());
2744 
2745     unpauseForNewRequests();
2746 
2747     mRepeatingLastFrameNumber = NO_IN_FLIGHT_REPEATING_FRAMES;
2748     return OK;
2749 }
2750 
isRepeatingRequestLocked(const sp<CaptureRequest> requestIn)2751 bool Camera3Device::RequestThread::isRepeatingRequestLocked(const sp<CaptureRequest> requestIn) {
2752     if (mRepeatingRequests.empty()) {
2753         return false;
2754     }
2755     int32_t requestId = requestIn->mResultExtras.requestId;
2756     const RequestList &repeatRequests = mRepeatingRequests;
2757     // All repeating requests are guaranteed to have same id so only check first quest
2758     const sp<CaptureRequest> firstRequest = *repeatRequests.begin();
2759     return (firstRequest->mResultExtras.requestId == requestId);
2760 }
2761 
clearRepeatingRequests(int64_t * lastFrameNumber)2762 status_t Camera3Device::RequestThread::clearRepeatingRequests(/*out*/int64_t *lastFrameNumber) {
2763     Mutex::Autolock l(mRequestLock);
2764     mRepeatingRequests.clear();
2765     if (lastFrameNumber != NULL) {
2766         *lastFrameNumber = mRepeatingLastFrameNumber;
2767     }
2768     mRepeatingLastFrameNumber = NO_IN_FLIGHT_REPEATING_FRAMES;
2769     return OK;
2770 }
2771 
clear(NotificationListener * listener,int64_t * lastFrameNumber)2772 status_t Camera3Device::RequestThread::clear(
2773         NotificationListener *listener,
2774         /*out*/int64_t *lastFrameNumber) {
2775     Mutex::Autolock l(mRequestLock);
2776     ALOGV("RequestThread::%s:", __FUNCTION__);
2777 
2778     mRepeatingRequests.clear();
2779 
2780     // Send errors for all requests pending in the request queue, including
2781     // pending repeating requests
2782     if (listener != NULL) {
2783         for (RequestList::iterator it = mRequestQueue.begin();
2784                  it != mRequestQueue.end(); ++it) {
2785             // Abort the input buffers for reprocess requests.
2786             if ((*it)->mInputStream != NULL) {
2787                 camera3_stream_buffer_t inputBuffer;
2788                 status_t res = (*it)->mInputStream->getInputBuffer(&inputBuffer);
2789                 if (res != OK) {
2790                     ALOGW("%s: %d: couldn't get input buffer while clearing the request "
2791                             "list: %s (%d)", __FUNCTION__, __LINE__, strerror(-res), res);
2792                 } else {
2793                     res = (*it)->mInputStream->returnInputBuffer(inputBuffer);
2794                     if (res != OK) {
2795                         ALOGE("%s: %d: couldn't return input buffer while clearing the request "
2796                                 "list: %s (%d)", __FUNCTION__, __LINE__, strerror(-res), res);
2797                     }
2798                 }
2799             }
2800             // Set the frame number this request would have had, if it
2801             // had been submitted; this frame number will not be reused.
2802             // The requestId and burstId fields were set when the request was
2803             // submitted originally (in convertMetadataListToRequestListLocked)
2804             (*it)->mResultExtras.frameNumber = mFrameNumber++;
2805             listener->notifyError(ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
2806                     (*it)->mResultExtras);
2807         }
2808     }
2809     mRequestQueue.clear();
2810     mTriggerMap.clear();
2811     if (lastFrameNumber != NULL) {
2812         *lastFrameNumber = mRepeatingLastFrameNumber;
2813     }
2814     mRepeatingLastFrameNumber = NO_IN_FLIGHT_REPEATING_FRAMES;
2815     return OK;
2816 }
2817 
flush()2818 status_t Camera3Device::RequestThread::flush() {
2819     ATRACE_CALL();
2820     Mutex::Autolock l(mFlushLock);
2821 
2822     if (mHal3Device->common.version >= CAMERA_DEVICE_API_VERSION_3_1) {
2823         return mHal3Device->ops->flush(mHal3Device);
2824     }
2825 
2826     return -ENOTSUP;
2827 }
2828 
setPaused(bool paused)2829 void Camera3Device::RequestThread::setPaused(bool paused) {
2830     Mutex::Autolock l(mPauseLock);
2831     mDoPause = paused;
2832     mDoPauseSignal.signal();
2833 }
2834 
waitUntilRequestProcessed(int32_t requestId,nsecs_t timeout)2835 status_t Camera3Device::RequestThread::waitUntilRequestProcessed(
2836         int32_t requestId, nsecs_t timeout) {
2837     Mutex::Autolock l(mLatestRequestMutex);
2838     status_t res;
2839     while (mLatestRequestId != requestId) {
2840         nsecs_t startTime = systemTime();
2841 
2842         res = mLatestRequestSignal.waitRelative(mLatestRequestMutex, timeout);
2843         if (res != OK) return res;
2844 
2845         timeout -= (systemTime() - startTime);
2846     }
2847 
2848     return OK;
2849 }
2850 
requestExit()2851 void Camera3Device::RequestThread::requestExit() {
2852     // Call parent to set up shutdown
2853     Thread::requestExit();
2854     // The exit from any possible waits
2855     mDoPauseSignal.signal();
2856     mRequestSignal.signal();
2857 }
2858 
2859 
2860 /**
2861  * For devices <= CAMERA_DEVICE_API_VERSION_3_2, AE_PRECAPTURE_TRIGGER_CANCEL is not supported so
2862  * we need to override AE_PRECAPTURE_TRIGGER_CANCEL to AE_PRECAPTURE_TRIGGER_IDLE and AE_LOCK_OFF
2863  * to AE_LOCK_ON to start cancelling AE precapture. If AE lock is not available, it still overrides
2864  * AE_PRECAPTURE_TRIGGER_CANCEL to AE_PRECAPTURE_TRIGGER_IDLE but doesn't add AE_LOCK_ON to the
2865  * request.
2866  */
handleAePrecaptureCancelRequest(sp<CaptureRequest> request)2867 void Camera3Device::RequestThread::handleAePrecaptureCancelRequest(sp<CaptureRequest> request) {
2868     request->mAeTriggerCancelOverride.applyAeLock = false;
2869     request->mAeTriggerCancelOverride.applyAePrecaptureTrigger = false;
2870 
2871     if (mHal3Device->common.version > CAMERA_DEVICE_API_VERSION_3_2) {
2872         return;
2873     }
2874 
2875     camera_metadata_entry_t aePrecaptureTrigger =
2876             request->mSettings.find(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER);
2877     if (aePrecaptureTrigger.count > 0 &&
2878             aePrecaptureTrigger.data.u8[0] == ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_CANCEL) {
2879         // Always override CANCEL to IDLE
2880         uint8_t aePrecaptureTrigger = ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_IDLE;
2881         request->mSettings.update(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER, &aePrecaptureTrigger, 1);
2882         request->mAeTriggerCancelOverride.applyAePrecaptureTrigger = true;
2883         request->mAeTriggerCancelOverride.aePrecaptureTrigger =
2884                 ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_CANCEL;
2885 
2886         if (mAeLockAvailable == true) {
2887             camera_metadata_entry_t aeLock = request->mSettings.find(ANDROID_CONTROL_AE_LOCK);
2888             if (aeLock.count == 0 ||  aeLock.data.u8[0] == ANDROID_CONTROL_AE_LOCK_OFF) {
2889                 uint8_t aeLock = ANDROID_CONTROL_AE_LOCK_ON;
2890                 request->mSettings.update(ANDROID_CONTROL_AE_LOCK, &aeLock, 1);
2891                 request->mAeTriggerCancelOverride.applyAeLock = true;
2892                 request->mAeTriggerCancelOverride.aeLock = ANDROID_CONTROL_AE_LOCK_OFF;
2893             }
2894         }
2895     }
2896 }
2897 
2898 /**
2899  * Override result metadata for cancelling AE precapture trigger applied in
2900  * handleAePrecaptureCancelRequest().
2901  */
overrideResultForPrecaptureCancel(CameraMetadata * result,const AeTriggerCancelOverride_t & aeTriggerCancelOverride)2902 void Camera3Device::overrideResultForPrecaptureCancel(
2903         CameraMetadata *result, const AeTriggerCancelOverride_t &aeTriggerCancelOverride) {
2904     if (aeTriggerCancelOverride.applyAeLock) {
2905         // Only devices <= v3.2 should have this override
2906         assert(mDeviceVersion <= CAMERA_DEVICE_API_VERSION_3_2);
2907         result->update(ANDROID_CONTROL_AE_LOCK, &aeTriggerCancelOverride.aeLock, 1);
2908     }
2909 
2910     if (aeTriggerCancelOverride.applyAePrecaptureTrigger) {
2911         // Only devices <= v3.2 should have this override
2912         assert(mDeviceVersion <= CAMERA_DEVICE_API_VERSION_3_2);
2913         result->update(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER,
2914                 &aeTriggerCancelOverride.aePrecaptureTrigger, 1);
2915     }
2916 }
2917 
threadLoop()2918 bool Camera3Device::RequestThread::threadLoop() {
2919     ATRACE_CALL();
2920     status_t res;
2921 
2922     // Handle paused state.
2923     if (waitIfPaused()) {
2924         return true;
2925     }
2926 
2927     // Wait for the next batch of requests.
2928     waitForNextRequestBatch();
2929     if (mNextRequests.size() == 0) {
2930         return true;
2931     }
2932 
2933     // Get the latest request ID, if any
2934     int latestRequestId;
2935     camera_metadata_entry_t requestIdEntry = mNextRequests[mNextRequests.size() - 1].
2936             captureRequest->mSettings.find(ANDROID_REQUEST_ID);
2937     if (requestIdEntry.count > 0) {
2938         latestRequestId = requestIdEntry.data.i32[0];
2939     } else {
2940         ALOGW("%s: Did not have android.request.id set in the request.", __FUNCTION__);
2941         latestRequestId = NAME_NOT_FOUND;
2942     }
2943 
2944     // Prepare a batch of HAL requests and output buffers.
2945     res = prepareHalRequests();
2946     if (res == TIMED_OUT) {
2947         // Not a fatal error if getting output buffers time out.
2948         cleanUpFailedRequests(/*sendRequestError*/ true);
2949         return true;
2950     } else if (res != OK) {
2951         cleanUpFailedRequests(/*sendRequestError*/ false);
2952         return false;
2953     }
2954 
2955     // Inform waitUntilRequestProcessed thread of a new request ID
2956     {
2957         Mutex::Autolock al(mLatestRequestMutex);
2958 
2959         mLatestRequestId = latestRequestId;
2960         mLatestRequestSignal.signal();
2961     }
2962 
2963     // Submit a batch of requests to HAL.
2964     // Use flush lock only when submitting multilple requests in a batch.
2965     // TODO: The problem with flush lock is flush() will be blocked by process_capture_request()
2966     // which may take a long time to finish so synchronizing flush() and
2967     // process_capture_request() defeats the purpose of cancelling requests ASAP with flush().
2968     // For now, only synchronize for high speed recording and we should figure something out for
2969     // removing the synchronization.
2970     bool useFlushLock = mNextRequests.size() > 1;
2971 
2972     if (useFlushLock) {
2973         mFlushLock.lock();
2974     }
2975 
2976     ALOGVV("%s: %d: submitting %d requests in a batch.", __FUNCTION__, __LINE__,
2977             mNextRequests.size());
2978     for (auto& nextRequest : mNextRequests) {
2979         // Submit request and block until ready for next one
2980         ATRACE_ASYNC_BEGIN("frame capture", nextRequest.halRequest.frame_number);
2981         ATRACE_BEGIN("camera3->process_capture_request");
2982         res = mHal3Device->ops->process_capture_request(mHal3Device, &nextRequest.halRequest);
2983         ATRACE_END();
2984 
2985         if (res != OK) {
2986             // Should only get a failure here for malformed requests or device-level
2987             // errors, so consider all errors fatal.  Bad metadata failures should
2988             // come through notify.
2989             SET_ERR("RequestThread: Unable to submit capture request %d to HAL"
2990                     " device: %s (%d)", nextRequest.halRequest.frame_number, strerror(-res),
2991                     res);
2992             cleanUpFailedRequests(/*sendRequestError*/ false);
2993             if (useFlushLock) {
2994                 mFlushLock.unlock();
2995             }
2996             return false;
2997         }
2998 
2999         // Mark that the request has be submitted successfully.
3000         nextRequest.submitted = true;
3001 
3002         // Update the latest request sent to HAL
3003         if (nextRequest.halRequest.settings != NULL) { // Don't update if they were unchanged
3004             Mutex::Autolock al(mLatestRequestMutex);
3005 
3006             camera_metadata_t* cloned = clone_camera_metadata(nextRequest.halRequest.settings);
3007             mLatestRequest.acquire(cloned);
3008         }
3009 
3010         if (nextRequest.halRequest.settings != NULL) {
3011             nextRequest.captureRequest->mSettings.unlock(nextRequest.halRequest.settings);
3012         }
3013 
3014         // Remove any previously queued triggers (after unlock)
3015         res = removeTriggers(mPrevRequest);
3016         if (res != OK) {
3017             SET_ERR("RequestThread: Unable to remove triggers "
3018                   "(capture request %d, HAL device: %s (%d)",
3019                   nextRequest.halRequest.frame_number, strerror(-res), res);
3020             cleanUpFailedRequests(/*sendRequestError*/ false);
3021             if (useFlushLock) {
3022                 mFlushLock.unlock();
3023             }
3024             return false;
3025         }
3026     }
3027 
3028     if (useFlushLock) {
3029         mFlushLock.unlock();
3030     }
3031 
3032     // Unset as current request
3033     {
3034         Mutex::Autolock l(mRequestLock);
3035         mNextRequests.clear();
3036     }
3037 
3038     return true;
3039 }
3040 
prepareHalRequests()3041 status_t Camera3Device::RequestThread::prepareHalRequests() {
3042     ATRACE_CALL();
3043 
3044     for (auto& nextRequest : mNextRequests) {
3045         sp<CaptureRequest> captureRequest = nextRequest.captureRequest;
3046         camera3_capture_request_t* halRequest = &nextRequest.halRequest;
3047         Vector<camera3_stream_buffer_t>* outputBuffers = &nextRequest.outputBuffers;
3048 
3049         // Prepare a request to HAL
3050         halRequest->frame_number = captureRequest->mResultExtras.frameNumber;
3051 
3052         // Insert any queued triggers (before metadata is locked)
3053         status_t res = insertTriggers(captureRequest);
3054 
3055         if (res < 0) {
3056             SET_ERR("RequestThread: Unable to insert triggers "
3057                     "(capture request %d, HAL device: %s (%d)",
3058                     halRequest->frame_number, strerror(-res), res);
3059             return INVALID_OPERATION;
3060         }
3061         int triggerCount = res;
3062         bool triggersMixedIn = (triggerCount > 0 || mPrevTriggers > 0);
3063         mPrevTriggers = triggerCount;
3064 
3065         // If the request is the same as last, or we had triggers last time
3066         if (mPrevRequest != captureRequest || triggersMixedIn) {
3067             /**
3068              * HAL workaround:
3069              * Insert a dummy trigger ID if a trigger is set but no trigger ID is
3070              */
3071             res = addDummyTriggerIds(captureRequest);
3072             if (res != OK) {
3073                 SET_ERR("RequestThread: Unable to insert dummy trigger IDs "
3074                         "(capture request %d, HAL device: %s (%d)",
3075                         halRequest->frame_number, strerror(-res), res);
3076                 return INVALID_OPERATION;
3077             }
3078 
3079             /**
3080              * The request should be presorted so accesses in HAL
3081              *   are O(logn). Sidenote, sorting a sorted metadata is nop.
3082              */
3083             captureRequest->mSettings.sort();
3084             halRequest->settings = captureRequest->mSettings.getAndLock();
3085             mPrevRequest = captureRequest;
3086             ALOGVV("%s: Request settings are NEW", __FUNCTION__);
3087 
3088             IF_ALOGV() {
3089                 camera_metadata_ro_entry_t e = camera_metadata_ro_entry_t();
3090                 find_camera_metadata_ro_entry(
3091                         halRequest->settings,
3092                         ANDROID_CONTROL_AF_TRIGGER,
3093                         &e
3094                 );
3095                 if (e.count > 0) {
3096                     ALOGV("%s: Request (frame num %d) had AF trigger 0x%x",
3097                           __FUNCTION__,
3098                           halRequest->frame_number,
3099                           e.data.u8[0]);
3100                 }
3101             }
3102         } else {
3103             // leave request.settings NULL to indicate 'reuse latest given'
3104             ALOGVV("%s: Request settings are REUSED",
3105                    __FUNCTION__);
3106         }
3107 
3108         uint32_t totalNumBuffers = 0;
3109 
3110         // Fill in buffers
3111         if (captureRequest->mInputStream != NULL) {
3112             halRequest->input_buffer = &captureRequest->mInputBuffer;
3113             totalNumBuffers += 1;
3114         } else {
3115             halRequest->input_buffer = NULL;
3116         }
3117 
3118         outputBuffers->insertAt(camera3_stream_buffer_t(), 0,
3119                 captureRequest->mOutputStreams.size());
3120         halRequest->output_buffers = outputBuffers->array();
3121         for (size_t i = 0; i < captureRequest->mOutputStreams.size(); i++) {
3122             res = captureRequest->mOutputStreams.editItemAt(i)->
3123                     getBuffer(&outputBuffers->editItemAt(i));
3124             if (res != OK) {
3125                 // Can't get output buffer from gralloc queue - this could be due to
3126                 // abandoned queue or other consumer misbehavior, so not a fatal
3127                 // error
3128                 ALOGE("RequestThread: Can't get output buffer, skipping request:"
3129                         " %s (%d)", strerror(-res), res);
3130 
3131                 return TIMED_OUT;
3132             }
3133             halRequest->num_output_buffers++;
3134         }
3135         totalNumBuffers += halRequest->num_output_buffers;
3136 
3137         // Log request in the in-flight queue
3138         sp<Camera3Device> parent = mParent.promote();
3139         if (parent == NULL) {
3140             // Should not happen, and nowhere to send errors to, so just log it
3141             CLOGE("RequestThread: Parent is gone");
3142             return INVALID_OPERATION;
3143         }
3144         res = parent->registerInFlight(halRequest->frame_number,
3145                 totalNumBuffers, captureRequest->mResultExtras,
3146                 /*hasInput*/halRequest->input_buffer != NULL,
3147                 captureRequest->mAeTriggerCancelOverride);
3148         ALOGVV("%s: registered in flight requestId = %" PRId32 ", frameNumber = %" PRId64
3149                ", burstId = %" PRId32 ".",
3150                 __FUNCTION__,
3151                 captureRequest->mResultExtras.requestId, captureRequest->mResultExtras.frameNumber,
3152                 captureRequest->mResultExtras.burstId);
3153         if (res != OK) {
3154             SET_ERR("RequestThread: Unable to register new in-flight request:"
3155                     " %s (%d)", strerror(-res), res);
3156             return INVALID_OPERATION;
3157         }
3158     }
3159 
3160     return OK;
3161 }
3162 
getLatestRequest() const3163 CameraMetadata Camera3Device::RequestThread::getLatestRequest() const {
3164     Mutex::Autolock al(mLatestRequestMutex);
3165 
3166     ALOGV("RequestThread::%s", __FUNCTION__);
3167 
3168     return mLatestRequest;
3169 }
3170 
isStreamPending(sp<Camera3StreamInterface> & stream)3171 bool Camera3Device::RequestThread::isStreamPending(
3172         sp<Camera3StreamInterface>& stream) {
3173     Mutex::Autolock l(mRequestLock);
3174 
3175     for (const auto& nextRequest : mNextRequests) {
3176         if (!nextRequest.submitted) {
3177             for (const auto& s : nextRequest.captureRequest->mOutputStreams) {
3178                 if (stream == s) return true;
3179             }
3180             if (stream == nextRequest.captureRequest->mInputStream) return true;
3181         }
3182     }
3183 
3184     for (const auto& request : mRequestQueue) {
3185         for (const auto& s : request->mOutputStreams) {
3186             if (stream == s) return true;
3187         }
3188         if (stream == request->mInputStream) return true;
3189     }
3190 
3191     for (const auto& request : mRepeatingRequests) {
3192         for (const auto& s : request->mOutputStreams) {
3193             if (stream == s) return true;
3194         }
3195         if (stream == request->mInputStream) return true;
3196     }
3197 
3198     return false;
3199 }
3200 
cleanUpFailedRequests(bool sendRequestError)3201 void Camera3Device::RequestThread::cleanUpFailedRequests(bool sendRequestError) {
3202     if (mNextRequests.empty()) {
3203         return;
3204     }
3205 
3206     for (auto& nextRequest : mNextRequests) {
3207         // Skip the ones that have been submitted successfully.
3208         if (nextRequest.submitted) {
3209             continue;
3210         }
3211 
3212         sp<CaptureRequest> captureRequest = nextRequest.captureRequest;
3213         camera3_capture_request_t* halRequest = &nextRequest.halRequest;
3214         Vector<camera3_stream_buffer_t>* outputBuffers = &nextRequest.outputBuffers;
3215 
3216         if (halRequest->settings != NULL) {
3217             captureRequest->mSettings.unlock(halRequest->settings);
3218         }
3219 
3220         if (captureRequest->mInputStream != NULL) {
3221             captureRequest->mInputBuffer.status = CAMERA3_BUFFER_STATUS_ERROR;
3222             captureRequest->mInputStream->returnInputBuffer(captureRequest->mInputBuffer);
3223         }
3224 
3225         for (size_t i = 0; i < halRequest->num_output_buffers; i++) {
3226             outputBuffers->editItemAt(i).status = CAMERA3_BUFFER_STATUS_ERROR;
3227             captureRequest->mOutputStreams.editItemAt(i)->returnBuffer((*outputBuffers)[i], 0);
3228         }
3229 
3230         if (sendRequestError) {
3231             Mutex::Autolock l(mRequestLock);
3232             if (mListener != NULL) {
3233                 mListener->notifyError(
3234                         ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
3235                         captureRequest->mResultExtras);
3236             }
3237         }
3238     }
3239 
3240     Mutex::Autolock l(mRequestLock);
3241     mNextRequests.clear();
3242 }
3243 
waitForNextRequestBatch()3244 void Camera3Device::RequestThread::waitForNextRequestBatch() {
3245     // Optimized a bit for the simple steady-state case (single repeating
3246     // request), to avoid putting that request in the queue temporarily.
3247     Mutex::Autolock l(mRequestLock);
3248 
3249     assert(mNextRequests.empty());
3250 
3251     NextRequest nextRequest;
3252     nextRequest.captureRequest = waitForNextRequestLocked();
3253     if (nextRequest.captureRequest == nullptr) {
3254         return;
3255     }
3256 
3257     nextRequest.halRequest = camera3_capture_request_t();
3258     nextRequest.submitted = false;
3259     mNextRequests.add(nextRequest);
3260 
3261     // Wait for additional requests
3262     const size_t batchSize = nextRequest.captureRequest->mBatchSize;
3263 
3264     for (size_t i = 1; i < batchSize; i++) {
3265         NextRequest additionalRequest;
3266         additionalRequest.captureRequest = waitForNextRequestLocked();
3267         if (additionalRequest.captureRequest == nullptr) {
3268             break;
3269         }
3270 
3271         additionalRequest.halRequest = camera3_capture_request_t();
3272         additionalRequest.submitted = false;
3273         mNextRequests.add(additionalRequest);
3274     }
3275 
3276     if (mNextRequests.size() < batchSize) {
3277         ALOGE("RequestThread: only get %d out of %d requests. Skipping requests.",
3278                 mNextRequests.size(), batchSize);
3279         cleanUpFailedRequests(/*sendRequestError*/true);
3280     }
3281 
3282     return;
3283 }
3284 
3285 sp<Camera3Device::CaptureRequest>
waitForNextRequestLocked()3286         Camera3Device::RequestThread::waitForNextRequestLocked() {
3287     status_t res;
3288     sp<CaptureRequest> nextRequest;
3289 
3290     while (mRequestQueue.empty()) {
3291         if (!mRepeatingRequests.empty()) {
3292             // Always atomically enqueue all requests in a repeating request
3293             // list. Guarantees a complete in-sequence set of captures to
3294             // application.
3295             const RequestList &requests = mRepeatingRequests;
3296             RequestList::const_iterator firstRequest =
3297                     requests.begin();
3298             nextRequest = *firstRequest;
3299             mRequestQueue.insert(mRequestQueue.end(),
3300                     ++firstRequest,
3301                     requests.end());
3302             // No need to wait any longer
3303 
3304             mRepeatingLastFrameNumber = mFrameNumber + requests.size() - 1;
3305 
3306             break;
3307         }
3308 
3309         res = mRequestSignal.waitRelative(mRequestLock, kRequestTimeout);
3310 
3311         if ((mRequestQueue.empty() && mRepeatingRequests.empty()) ||
3312                 exitPending()) {
3313             Mutex::Autolock pl(mPauseLock);
3314             if (mPaused == false) {
3315                 ALOGV("%s: RequestThread: Going idle", __FUNCTION__);
3316                 mPaused = true;
3317                 // Let the tracker know
3318                 sp<StatusTracker> statusTracker = mStatusTracker.promote();
3319                 if (statusTracker != 0) {
3320                     statusTracker->markComponentIdle(mStatusId, Fence::NO_FENCE);
3321                 }
3322             }
3323             // Stop waiting for now and let thread management happen
3324             return NULL;
3325         }
3326     }
3327 
3328     if (nextRequest == NULL) {
3329         // Don't have a repeating request already in hand, so queue
3330         // must have an entry now.
3331         RequestList::iterator firstRequest =
3332                 mRequestQueue.begin();
3333         nextRequest = *firstRequest;
3334         mRequestQueue.erase(firstRequest);
3335     }
3336 
3337     // In case we've been unpaused by setPaused clearing mDoPause, need to
3338     // update internal pause state (capture/setRepeatingRequest unpause
3339     // directly).
3340     Mutex::Autolock pl(mPauseLock);
3341     if (mPaused) {
3342         ALOGV("%s: RequestThread: Unpaused", __FUNCTION__);
3343         sp<StatusTracker> statusTracker = mStatusTracker.promote();
3344         if (statusTracker != 0) {
3345             statusTracker->markComponentActive(mStatusId);
3346         }
3347     }
3348     mPaused = false;
3349 
3350     // Check if we've reconfigured since last time, and reset the preview
3351     // request if so. Can't use 'NULL request == repeat' across configure calls.
3352     if (mReconfigured) {
3353         mPrevRequest.clear();
3354         mReconfigured = false;
3355     }
3356 
3357     if (nextRequest != NULL) {
3358         nextRequest->mResultExtras.frameNumber = mFrameNumber++;
3359         nextRequest->mResultExtras.afTriggerId = mCurrentAfTriggerId;
3360         nextRequest->mResultExtras.precaptureTriggerId = mCurrentPreCaptureTriggerId;
3361 
3362         // Since RequestThread::clear() removes buffers from the input stream,
3363         // get the right buffer here before unlocking mRequestLock
3364         if (nextRequest->mInputStream != NULL) {
3365             res = nextRequest->mInputStream->getInputBuffer(&nextRequest->mInputBuffer);
3366             if (res != OK) {
3367                 // Can't get input buffer from gralloc queue - this could be due to
3368                 // disconnected queue or other producer misbehavior, so not a fatal
3369                 // error
3370                 ALOGE("%s: Can't get input buffer, skipping request:"
3371                         " %s (%d)", __FUNCTION__, strerror(-res), res);
3372                 if (mListener != NULL) {
3373                     mListener->notifyError(
3374                             ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST,
3375                             nextRequest->mResultExtras);
3376                 }
3377                 return NULL;
3378             }
3379         }
3380     }
3381 
3382     handleAePrecaptureCancelRequest(nextRequest);
3383 
3384     return nextRequest;
3385 }
3386 
waitIfPaused()3387 bool Camera3Device::RequestThread::waitIfPaused() {
3388     status_t res;
3389     Mutex::Autolock l(mPauseLock);
3390     while (mDoPause) {
3391         if (mPaused == false) {
3392             mPaused = true;
3393             ALOGV("%s: RequestThread: Paused", __FUNCTION__);
3394             // Let the tracker know
3395             sp<StatusTracker> statusTracker = mStatusTracker.promote();
3396             if (statusTracker != 0) {
3397                 statusTracker->markComponentIdle(mStatusId, Fence::NO_FENCE);
3398             }
3399         }
3400 
3401         res = mDoPauseSignal.waitRelative(mPauseLock, kRequestTimeout);
3402         if (res == TIMED_OUT || exitPending()) {
3403             return true;
3404         }
3405     }
3406     // We don't set mPaused to false here, because waitForNextRequest needs
3407     // to further manage the paused state in case of starvation.
3408     return false;
3409 }
3410 
unpauseForNewRequests()3411 void Camera3Device::RequestThread::unpauseForNewRequests() {
3412     // With work to do, mark thread as unpaused.
3413     // If paused by request (setPaused), don't resume, to avoid
3414     // extra signaling/waiting overhead to waitUntilPaused
3415     mRequestSignal.signal();
3416     Mutex::Autolock p(mPauseLock);
3417     if (!mDoPause) {
3418         ALOGV("%s: RequestThread: Going active", __FUNCTION__);
3419         if (mPaused) {
3420             sp<StatusTracker> statusTracker = mStatusTracker.promote();
3421             if (statusTracker != 0) {
3422                 statusTracker->markComponentActive(mStatusId);
3423             }
3424         }
3425         mPaused = false;
3426     }
3427 }
3428 
setErrorState(const char * fmt,...)3429 void Camera3Device::RequestThread::setErrorState(const char *fmt, ...) {
3430     sp<Camera3Device> parent = mParent.promote();
3431     if (parent != NULL) {
3432         va_list args;
3433         va_start(args, fmt);
3434 
3435         parent->setErrorStateV(fmt, args);
3436 
3437         va_end(args);
3438     }
3439 }
3440 
insertTriggers(const sp<CaptureRequest> & request)3441 status_t Camera3Device::RequestThread::insertTriggers(
3442         const sp<CaptureRequest> &request) {
3443 
3444     Mutex::Autolock al(mTriggerMutex);
3445 
3446     sp<Camera3Device> parent = mParent.promote();
3447     if (parent == NULL) {
3448         CLOGE("RequestThread: Parent is gone");
3449         return DEAD_OBJECT;
3450     }
3451 
3452     CameraMetadata &metadata = request->mSettings;
3453     size_t count = mTriggerMap.size();
3454 
3455     for (size_t i = 0; i < count; ++i) {
3456         RequestTrigger trigger = mTriggerMap.valueAt(i);
3457         uint32_t tag = trigger.metadataTag;
3458 
3459         if (tag == ANDROID_CONTROL_AF_TRIGGER_ID || tag == ANDROID_CONTROL_AE_PRECAPTURE_ID) {
3460             bool isAeTrigger = (trigger.metadataTag == ANDROID_CONTROL_AE_PRECAPTURE_ID);
3461             uint32_t triggerId = static_cast<uint32_t>(trigger.entryValue);
3462             if (isAeTrigger) {
3463                 request->mResultExtras.precaptureTriggerId = triggerId;
3464                 mCurrentPreCaptureTriggerId = triggerId;
3465             } else {
3466                 request->mResultExtras.afTriggerId = triggerId;
3467                 mCurrentAfTriggerId = triggerId;
3468             }
3469             if (parent->mDeviceVersion >= CAMERA_DEVICE_API_VERSION_3_2) {
3470                 continue; // Trigger ID tag is deprecated since device HAL 3.2
3471             }
3472         }
3473 
3474         camera_metadata_entry entry = metadata.find(tag);
3475 
3476         if (entry.count > 0) {
3477             /**
3478              * Already has an entry for this trigger in the request.
3479              * Rewrite it with our requested trigger value.
3480              */
3481             RequestTrigger oldTrigger = trigger;
3482 
3483             oldTrigger.entryValue = entry.data.u8[0];
3484 
3485             mTriggerReplacedMap.add(tag, oldTrigger);
3486         } else {
3487             /**
3488              * More typical, no trigger entry, so we just add it
3489              */
3490             mTriggerRemovedMap.add(tag, trigger);
3491         }
3492 
3493         status_t res;
3494 
3495         switch (trigger.getTagType()) {
3496             case TYPE_BYTE: {
3497                 uint8_t entryValue = static_cast<uint8_t>(trigger.entryValue);
3498                 res = metadata.update(tag,
3499                                       &entryValue,
3500                                       /*count*/1);
3501                 break;
3502             }
3503             case TYPE_INT32:
3504                 res = metadata.update(tag,
3505                                       &trigger.entryValue,
3506                                       /*count*/1);
3507                 break;
3508             default:
3509                 ALOGE("%s: Type not supported: 0x%x",
3510                       __FUNCTION__,
3511                       trigger.getTagType());
3512                 return INVALID_OPERATION;
3513         }
3514 
3515         if (res != OK) {
3516             ALOGE("%s: Failed to update request metadata with trigger tag %s"
3517                   ", value %d", __FUNCTION__, trigger.getTagName(),
3518                   trigger.entryValue);
3519             return res;
3520         }
3521 
3522         ALOGV("%s: Mixed in trigger %s, value %d", __FUNCTION__,
3523               trigger.getTagName(),
3524               trigger.entryValue);
3525     }
3526 
3527     mTriggerMap.clear();
3528 
3529     return count;
3530 }
3531 
removeTriggers(const sp<CaptureRequest> & request)3532 status_t Camera3Device::RequestThread::removeTriggers(
3533         const sp<CaptureRequest> &request) {
3534     Mutex::Autolock al(mTriggerMutex);
3535 
3536     CameraMetadata &metadata = request->mSettings;
3537 
3538     /**
3539      * Replace all old entries with their old values.
3540      */
3541     for (size_t i = 0; i < mTriggerReplacedMap.size(); ++i) {
3542         RequestTrigger trigger = mTriggerReplacedMap.valueAt(i);
3543 
3544         status_t res;
3545 
3546         uint32_t tag = trigger.metadataTag;
3547         switch (trigger.getTagType()) {
3548             case TYPE_BYTE: {
3549                 uint8_t entryValue = static_cast<uint8_t>(trigger.entryValue);
3550                 res = metadata.update(tag,
3551                                       &entryValue,
3552                                       /*count*/1);
3553                 break;
3554             }
3555             case TYPE_INT32:
3556                 res = metadata.update(tag,
3557                                       &trigger.entryValue,
3558                                       /*count*/1);
3559                 break;
3560             default:
3561                 ALOGE("%s: Type not supported: 0x%x",
3562                       __FUNCTION__,
3563                       trigger.getTagType());
3564                 return INVALID_OPERATION;
3565         }
3566 
3567         if (res != OK) {
3568             ALOGE("%s: Failed to restore request metadata with trigger tag %s"
3569                   ", trigger value %d", __FUNCTION__,
3570                   trigger.getTagName(), trigger.entryValue);
3571             return res;
3572         }
3573     }
3574     mTriggerReplacedMap.clear();
3575 
3576     /**
3577      * Remove all new entries.
3578      */
3579     for (size_t i = 0; i < mTriggerRemovedMap.size(); ++i) {
3580         RequestTrigger trigger = mTriggerRemovedMap.valueAt(i);
3581         status_t res = metadata.erase(trigger.metadataTag);
3582 
3583         if (res != OK) {
3584             ALOGE("%s: Failed to erase metadata with trigger tag %s"
3585                   ", trigger value %d", __FUNCTION__,
3586                   trigger.getTagName(), trigger.entryValue);
3587             return res;
3588         }
3589     }
3590     mTriggerRemovedMap.clear();
3591 
3592     return OK;
3593 }
3594 
addDummyTriggerIds(const sp<CaptureRequest> & request)3595 status_t Camera3Device::RequestThread::addDummyTriggerIds(
3596         const sp<CaptureRequest> &request) {
3597     // Trigger ID 0 has special meaning in the HAL2 spec, so avoid it here
3598     static const int32_t dummyTriggerId = 1;
3599     status_t res;
3600 
3601     CameraMetadata &metadata = request->mSettings;
3602 
3603     // If AF trigger is active, insert a dummy AF trigger ID if none already
3604     // exists
3605     camera_metadata_entry afTrigger = metadata.find(ANDROID_CONTROL_AF_TRIGGER);
3606     camera_metadata_entry afId = metadata.find(ANDROID_CONTROL_AF_TRIGGER_ID);
3607     if (afTrigger.count > 0 &&
3608             afTrigger.data.u8[0] != ANDROID_CONTROL_AF_TRIGGER_IDLE &&
3609             afId.count == 0) {
3610         res = metadata.update(ANDROID_CONTROL_AF_TRIGGER_ID, &dummyTriggerId, 1);
3611         if (res != OK) return res;
3612     }
3613 
3614     // If AE precapture trigger is active, insert a dummy precapture trigger ID
3615     // if none already exists
3616     camera_metadata_entry pcTrigger =
3617             metadata.find(ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER);
3618     camera_metadata_entry pcId = metadata.find(ANDROID_CONTROL_AE_PRECAPTURE_ID);
3619     if (pcTrigger.count > 0 &&
3620             pcTrigger.data.u8[0] != ANDROID_CONTROL_AE_PRECAPTURE_TRIGGER_IDLE &&
3621             pcId.count == 0) {
3622         res = metadata.update(ANDROID_CONTROL_AE_PRECAPTURE_ID,
3623                 &dummyTriggerId, 1);
3624         if (res != OK) return res;
3625     }
3626 
3627     return OK;
3628 }
3629 
3630 /**
3631  * PreparerThread inner class methods
3632  */
3633 
PreparerThread()3634 Camera3Device::PreparerThread::PreparerThread() :
3635         Thread(/*canCallJava*/false), mActive(false), mCancelNow(false) {
3636 }
3637 
~PreparerThread()3638 Camera3Device::PreparerThread::~PreparerThread() {
3639     Thread::requestExitAndWait();
3640     if (mCurrentStream != nullptr) {
3641         mCurrentStream->cancelPrepare();
3642         ATRACE_ASYNC_END("stream prepare", mCurrentStream->getId());
3643         mCurrentStream.clear();
3644     }
3645     clear();
3646 }
3647 
prepare(int maxCount,sp<Camera3StreamInterface> & stream)3648 status_t Camera3Device::PreparerThread::prepare(int maxCount, sp<Camera3StreamInterface>& stream) {
3649     status_t res;
3650 
3651     Mutex::Autolock l(mLock);
3652 
3653     res = stream->startPrepare(maxCount);
3654     if (res == OK) {
3655         // No preparation needed, fire listener right off
3656         ALOGV("%s: Stream %d already prepared", __FUNCTION__, stream->getId());
3657         if (mListener) {
3658             mListener->notifyPrepared(stream->getId());
3659         }
3660         return OK;
3661     } else if (res != NOT_ENOUGH_DATA) {
3662         return res;
3663     }
3664 
3665     // Need to prepare, start up thread if necessary
3666     if (!mActive) {
3667         // mRunning will change to false before the thread fully shuts down, so wait to be sure it
3668         // isn't running
3669         Thread::requestExitAndWait();
3670         res = Thread::run("C3PrepThread", PRIORITY_BACKGROUND);
3671         if (res != OK) {
3672             ALOGE("%s: Unable to start preparer stream: %d (%s)", __FUNCTION__, res, strerror(-res));
3673             if (mListener) {
3674                 mListener->notifyPrepared(stream->getId());
3675             }
3676             return res;
3677         }
3678         mCancelNow = false;
3679         mActive = true;
3680         ALOGV("%s: Preparer stream started", __FUNCTION__);
3681     }
3682 
3683     // queue up the work
3684     mPendingStreams.push_back(stream);
3685     ALOGV("%s: Stream %d queued for preparing", __FUNCTION__, stream->getId());
3686 
3687     return OK;
3688 }
3689 
clear()3690 status_t Camera3Device::PreparerThread::clear() {
3691     status_t res;
3692 
3693     Mutex::Autolock l(mLock);
3694 
3695     for (const auto& stream : mPendingStreams) {
3696         stream->cancelPrepare();
3697     }
3698     mPendingStreams.clear();
3699     mCancelNow = true;
3700 
3701     return OK;
3702 }
3703 
setNotificationListener(NotificationListener * listener)3704 void Camera3Device::PreparerThread::setNotificationListener(NotificationListener *listener) {
3705     Mutex::Autolock l(mLock);
3706     mListener = listener;
3707 }
3708 
threadLoop()3709 bool Camera3Device::PreparerThread::threadLoop() {
3710     status_t res;
3711     {
3712         Mutex::Autolock l(mLock);
3713         if (mCurrentStream == nullptr) {
3714             // End thread if done with work
3715             if (mPendingStreams.empty()) {
3716                 ALOGV("%s: Preparer stream out of work", __FUNCTION__);
3717                 // threadLoop _must not_ re-acquire mLock after it sets mActive to false; would
3718                 // cause deadlock with prepare()'s requestExitAndWait triggered by !mActive.
3719                 mActive = false;
3720                 return false;
3721             }
3722 
3723             // Get next stream to prepare
3724             auto it = mPendingStreams.begin();
3725             mCurrentStream = *it;
3726             mPendingStreams.erase(it);
3727             ATRACE_ASYNC_BEGIN("stream prepare", mCurrentStream->getId());
3728             ALOGV("%s: Preparing stream %d", __FUNCTION__, mCurrentStream->getId());
3729         } else if (mCancelNow) {
3730             mCurrentStream->cancelPrepare();
3731             ATRACE_ASYNC_END("stream prepare", mCurrentStream->getId());
3732             ALOGV("%s: Cancelling stream %d prepare", __FUNCTION__, mCurrentStream->getId());
3733             mCurrentStream.clear();
3734             mCancelNow = false;
3735             return true;
3736         }
3737     }
3738 
3739     res = mCurrentStream->prepareNextBuffer();
3740     if (res == NOT_ENOUGH_DATA) return true;
3741     if (res != OK) {
3742         // Something bad happened; try to recover by cancelling prepare and
3743         // signalling listener anyway
3744         ALOGE("%s: Stream %d returned error %d (%s) during prepare", __FUNCTION__,
3745                 mCurrentStream->getId(), res, strerror(-res));
3746         mCurrentStream->cancelPrepare();
3747     }
3748 
3749     // This stream has finished, notify listener
3750     Mutex::Autolock l(mLock);
3751     if (mListener) {
3752         ALOGV("%s: Stream %d prepare done, signaling listener", __FUNCTION__,
3753                 mCurrentStream->getId());
3754         mListener->notifyPrepared(mCurrentStream->getId());
3755     }
3756 
3757     ATRACE_ASYNC_END("stream prepare", mCurrentStream->getId());
3758     mCurrentStream.clear();
3759 
3760     return true;
3761 }
3762 
3763 /**
3764  * Static callback forwarding methods from HAL to instance
3765  */
3766 
sProcessCaptureResult(const camera3_callback_ops * cb,const camera3_capture_result * result)3767 void Camera3Device::sProcessCaptureResult(const camera3_callback_ops *cb,
3768         const camera3_capture_result *result) {
3769     Camera3Device *d =
3770             const_cast<Camera3Device*>(static_cast<const Camera3Device*>(cb));
3771 
3772     d->processCaptureResult(result);
3773 }
3774 
sNotify(const camera3_callback_ops * cb,const camera3_notify_msg * msg)3775 void Camera3Device::sNotify(const camera3_callback_ops *cb,
3776         const camera3_notify_msg *msg) {
3777     Camera3Device *d =
3778             const_cast<Camera3Device*>(static_cast<const Camera3Device*>(cb));
3779     d->notify(msg);
3780 }
3781 
3782 }; // namespace android
3783