xref: /aosp_15_r20/frameworks/av/services/camera/libcameraservice/device3/Camera3Stream.cpp (revision ec779b8e0859a360c3d303172224686826e6e0e1)
1 /*
2  * Copyright (C) 2013-2018 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include <vector>
18 #include "system/window.h"
19 #define LOG_TAG "Camera3-Stream"
20 #define ATRACE_TAG ATRACE_TAG_CAMERA
21 //#define LOG_NDEBUG 0
22 
23 #include <utils/Log.h>
24 #include <utils/Trace.h>
25 #include <camera/StringUtils.h>
26 #include "device3/Camera3Stream.h"
27 #include "device3/StatusTracker.h"
28 #include "utils/TraceHFR.h"
29 #include "ui/GraphicBufferMapper.h"
30 
31 #include <cutils/properties.h>
32 #include <com_android_internal_camera_flags.h>
33 
34 namespace flags = com::android::internal::camera::flags;
35 
36 namespace android {
37 
38 namespace camera3 {
39 
~Camera3Stream()40 Camera3Stream::~Camera3Stream() {
41     sp<StatusTracker> statusTracker = mStatusTracker.promote();
42     if (statusTracker != 0 && mStatusId != StatusTracker::NO_STATUS_ID) {
43         statusTracker->removeComponent(mStatusId);
44     }
45 }
46 
cast(camera_stream * stream)47 Camera3Stream* Camera3Stream::cast(camera_stream *stream) {
48     return static_cast<Camera3Stream*>(stream);
49 }
50 
cast(const camera_stream * stream)51 const Camera3Stream* Camera3Stream::cast(const camera_stream *stream) {
52     return static_cast<const Camera3Stream*>(stream);
53 }
54 
Camera3Stream(int id,camera_stream_type type,uint32_t width,uint32_t height,size_t maxSize,int format,android_dataspace dataSpace,camera_stream_rotation_t rotation,const std::string & physicalCameraId,const std::unordered_set<int32_t> & sensorPixelModesUsed,int setId,bool isMultiResolution,int64_t dynamicRangeProfile,int64_t streamUseCase,bool deviceTimeBaseIsRealtime,int timestampBase,int32_t colorSpace)55 Camera3Stream::Camera3Stream(int id,
56         camera_stream_type type,
57         uint32_t width, uint32_t height, size_t maxSize, int format,
58         android_dataspace dataSpace, camera_stream_rotation_t rotation,
59         const std::string& physicalCameraId,
60         const std::unordered_set<int32_t> &sensorPixelModesUsed,
61         int setId, bool isMultiResolution, int64_t dynamicRangeProfile,
62         int64_t streamUseCase, bool deviceTimeBaseIsRealtime, int timestampBase,
63         int32_t colorSpace) :
64     camera_stream(),
65     mId(id),
66     mSetId(setId),
67     mName(fmt::sprintf("Camera3Stream[%d]", id)),
68     mMaxSize(maxSize),
69     mState(STATE_CONSTRUCTED),
70     mStatusId(StatusTracker::NO_STATUS_ID),
71     mStreamUnpreparable(true),
72     mUsage(0),
73     mOldUsage(0),
74     mOldMaxBuffers(0),
75     mOldFormat(-1),
76     mOldDataSpace(HAL_DATASPACE_UNKNOWN),
77     mPrepared(false),
78     mPrepareBlockRequest(true),
79     mPreparedBufferIdx(0),
80     mLastMaxCount(Camera3StreamInterface::ALLOCATE_PIPELINE_MAX),
81     mBufferLimitLatency(kBufferLimitLatencyBinSize),
82     mFormatOverridden(false),
83     mOriginalFormat(format),
84     mDataSpaceOverridden(false),
85     mOriginalDataSpace(dataSpace),
86     mPhysicalCameraId(physicalCameraId),
87     mLastTimestamp(0),
88     mIsMultiResolution(isMultiResolution),
89     mDeviceTimeBaseIsRealtime(deviceTimeBaseIsRealtime),
90     mTimestampBase(timestampBase) {
91 
92     camera_stream::stream_type = type;
93     camera_stream::width = width;
94     camera_stream::height = height;
95     camera_stream::format = format;
96     camera_stream::data_space = dataSpace;
97     camera_stream::rotation = rotation;
98     camera_stream::max_buffers = 0;
99     camera_stream::physical_camera_id = mPhysicalCameraId;
100     camera_stream::sensor_pixel_modes_used = sensorPixelModesUsed;
101     camera_stream::dynamic_range_profile = dynamicRangeProfile;
102     camera_stream::use_case = streamUseCase;
103     camera_stream::color_space = colorSpace;
104 
105     if ((format == HAL_PIXEL_FORMAT_BLOB || format == HAL_PIXEL_FORMAT_RAW_OPAQUE) &&
106             maxSize == 0) {
107         ALOGE("%s: BLOB or RAW_OPAQUE format with size == 0", __FUNCTION__);
108         mState = STATE_ERROR;
109     }
110 }
111 
getId() const112 int Camera3Stream::getId() const {
113     return mId;
114 }
115 
getStreamSetId() const116 int Camera3Stream::getStreamSetId() const {
117     return mSetId;
118 }
119 
getHalStreamGroupId() const120 int Camera3Stream::getHalStreamGroupId() const {
121     return mIsMultiResolution ? mSetId : -1;
122 }
123 
isMultiResolution() const124 bool Camera3Stream::isMultiResolution() const {
125     return mIsMultiResolution;
126 }
127 
getWidth() const128 uint32_t Camera3Stream::getWidth() const {
129     return camera_stream::width;
130 }
131 
getHeight() const132 uint32_t Camera3Stream::getHeight() const {
133     return camera_stream::height;
134 }
135 
getFormat() const136 int Camera3Stream::getFormat() const {
137     return camera_stream::format;
138 }
139 
getDataSpace() const140 android_dataspace Camera3Stream::getDataSpace() const {
141     return camera_stream::data_space;
142 }
143 
getColorSpace() const144 int32_t Camera3Stream::getColorSpace() const {
145     return camera_stream::color_space;
146 }
147 
getUsage() const148 uint64_t Camera3Stream::getUsage() const {
149     return mUsage;
150 }
151 
setUsage(uint64_t usage)152 void Camera3Stream::setUsage(uint64_t usage) {
153     mUsage = usage;
154 }
155 
setFormatOverride(bool formatOverridden)156 void Camera3Stream::setFormatOverride(bool formatOverridden) {
157     mFormatOverridden = formatOverridden;
158 }
159 
isFormatOverridden() const160 bool Camera3Stream::isFormatOverridden() const {
161     return mFormatOverridden;
162 }
163 
getOriginalFormat() const164 int Camera3Stream::getOriginalFormat() const {
165     return mOriginalFormat;
166 }
167 
getDynamicRangeProfile() const168 int64_t Camera3Stream::getDynamicRangeProfile() const {
169     return camera_stream::dynamic_range_profile;
170 }
171 
setDataSpaceOverride(bool dataSpaceOverridden)172 void Camera3Stream::setDataSpaceOverride(bool dataSpaceOverridden) {
173     mDataSpaceOverridden = dataSpaceOverridden;
174 }
175 
isDataSpaceOverridden() const176 bool Camera3Stream::isDataSpaceOverridden() const {
177     return mDataSpaceOverridden;
178 }
179 
getOriginalDataSpace() const180 android_dataspace Camera3Stream::getOriginalDataSpace() const {
181     return mOriginalDataSpace;
182 }
183 
physicalCameraId() const184 const std::string& Camera3Stream::physicalCameraId() const {
185     return mPhysicalCameraId;
186 }
187 
getMaxHalBuffers() const188 int Camera3Stream::getMaxHalBuffers() const {
189     return camera_stream::max_buffers;
190 }
191 
getStreamUseCase() const192 int64_t Camera3Stream::getStreamUseCase() const {
193     return camera_stream::use_case;
194 }
195 
getTimestampBase() const196 int Camera3Stream::getTimestampBase() const {
197     return mTimestampBase;
198 }
199 
isDeviceTimeBaseRealtime() const200 bool Camera3Stream::isDeviceTimeBaseRealtime() const {
201     return mDeviceTimeBaseIsRealtime;
202 }
203 
setOfflineProcessingSupport(bool support)204 void Camera3Stream::setOfflineProcessingSupport(bool support) {
205     mSupportOfflineProcessing = support;
206 }
207 
getOfflineProcessingSupport() const208 bool Camera3Stream::getOfflineProcessingSupport() const {
209     return mSupportOfflineProcessing;
210 }
211 
forceToIdle()212 status_t Camera3Stream::forceToIdle() {
213     ATRACE_CALL();
214     Mutex::Autolock l(mLock);
215     status_t res;
216 
217     switch (mState) {
218         case STATE_ERROR:
219         case STATE_CONSTRUCTED:
220         case STATE_IN_CONFIG:
221         case STATE_PREPARING:
222         case STATE_IN_RECONFIG:
223             ALOGE("%s: Invalid state: %d", __FUNCTION__, mState);
224             res = NO_INIT;
225             break;
226         case STATE_CONFIGURED:
227             if (hasOutstandingBuffersLocked()) {
228                 sp<StatusTracker> statusTracker = mStatusTracker.promote();
229                 if (statusTracker != 0) {
230                     statusTracker->markComponentIdle(mStatusId, Fence::NO_FENCE);
231                 }
232             }
233 
234             mState = STATE_IN_IDLE;
235             res = OK;
236 
237             break;
238         default:
239             ALOGE("%s: Unknown state %d", __FUNCTION__, mState);
240             res = NO_INIT;
241     }
242 
243     return res;
244 }
245 
restoreConfiguredState()246 status_t Camera3Stream::restoreConfiguredState() {
247     ATRACE_CALL();
248     Mutex::Autolock l(mLock);
249     status_t res;
250 
251     switch (mState) {
252         case STATE_ERROR:
253         case STATE_CONSTRUCTED:
254         case STATE_IN_CONFIG:
255         case STATE_PREPARING:
256         case STATE_IN_RECONFIG:
257         case STATE_CONFIGURED:
258             ALOGE("%s: Invalid state: %d", __FUNCTION__, mState);
259             res = NO_INIT;
260             break;
261         case STATE_IN_IDLE:
262             if (hasOutstandingBuffersLocked()) {
263                 sp<StatusTracker> statusTracker = mStatusTracker.promote();
264                 if (statusTracker != 0) {
265                     statusTracker->markComponentActive(mStatusId);
266                 }
267             }
268 
269             mState = STATE_CONFIGURED;
270             res = OK;
271 
272             break;
273         default:
274             ALOGE("%s: Unknown state %d", __FUNCTION__, mState);
275             res = NO_INIT;
276     }
277 
278     return res;
279 }
280 
startConfiguration()281 camera_stream* Camera3Stream::startConfiguration() {
282     ATRACE_CALL();
283     Mutex::Autolock l(mLock);
284     status_t res;
285 
286     switch (mState) {
287         case STATE_ERROR:
288             ALOGE("%s: In error state", __FUNCTION__);
289             return NULL;
290         case STATE_CONSTRUCTED:
291         case STATE_IN_IDLE:
292             // OK
293             break;
294         case STATE_IN_CONFIG:
295         case STATE_IN_RECONFIG:
296             // Can start config again with no trouble; but don't redo
297             // mOldUsage/mOldMaxBuffers
298             return this;
299         case STATE_CONFIGURED:
300             if (hasOutstandingBuffersLocked()) {
301                 ALOGE("%s: Cannot configure stream; has outstanding buffers",
302                         __FUNCTION__);
303                 return NULL;
304             }
305             break;
306         default:
307             ALOGE("%s: Unknown state %d", __FUNCTION__, mState);
308             return NULL;
309     }
310 
311     mOldUsage = mUsage;
312     mOldMaxBuffers = camera_stream::max_buffers;
313     mOldFormat = camera_stream::format;
314     mOldDataSpace = camera_stream::data_space;
315 
316     res = getEndpointUsage(&mUsage);
317     if (res != OK) {
318         ALOGE("%s: Cannot query consumer endpoint usage!",
319                 __FUNCTION__);
320         return NULL;
321     }
322 
323     if (mState == STATE_IN_IDLE) {
324         // Skip configuration.
325         return this;
326     }
327 
328     // Stop tracking if currently doing so
329     if (mStatusId != StatusTracker::NO_STATUS_ID) {
330         sp<StatusTracker> statusTracker = mStatusTracker.promote();
331         if (statusTracker != 0) {
332             statusTracker->removeComponent(mStatusId);
333         }
334         mStatusId = StatusTracker::NO_STATUS_ID;
335     }
336 
337     if (mState == STATE_CONSTRUCTED) {
338         mState = STATE_IN_CONFIG;
339     } else { // mState == STATE_CONFIGURED
340         LOG_ALWAYS_FATAL_IF(mState != STATE_CONFIGURED, "Invalid state: 0x%x", mState);
341         mState = STATE_IN_RECONFIG;
342     }
343 
344     return this;
345 }
346 
isConfiguring() const347 bool Camera3Stream::isConfiguring() const {
348     Mutex::Autolock l(mLock);
349     return (mState == STATE_IN_CONFIG) || (mState == STATE_IN_RECONFIG);
350 }
351 
finishConfiguration(bool * streamReconfigured)352 status_t Camera3Stream::finishConfiguration(/*out*/bool* streamReconfigured) {
353     ATRACE_CALL();
354     if (streamReconfigured != nullptr) {
355         *streamReconfigured = false;
356     }
357     Mutex::Autolock l(mLock);
358     switch (mState) {
359         case STATE_ERROR:
360             ALOGE("%s: In error state", __FUNCTION__);
361             return INVALID_OPERATION;
362         case STATE_IN_CONFIG:
363         case STATE_IN_RECONFIG:
364             // OK
365             break;
366         case STATE_CONSTRUCTED:
367         case STATE_CONFIGURED:
368             ALOGE("%s: Cannot finish configuration that hasn't been started",
369                     __FUNCTION__);
370             return INVALID_OPERATION;
371         case STATE_IN_IDLE:
372             //Skip configuration in this state
373             return OK;
374         default:
375             ALOGE("%s: Unknown state", __FUNCTION__);
376             return INVALID_OPERATION;
377     }
378 
379     // Register for idle tracking
380     sp<StatusTracker> statusTracker = mStatusTracker.promote();
381     if (statusTracker != 0 && mStatusId == StatusTracker::NO_STATUS_ID) {
382         std::string name = std::string("Stream ") + std::to_string(mId);
383         mStatusId = statusTracker->addComponent(name);
384     }
385 
386     // Check if the stream configuration is unchanged, and skip reallocation if
387     // so.
388     if (mState == STATE_IN_RECONFIG &&
389             mOldUsage == mUsage &&
390             mOldMaxBuffers == camera_stream::max_buffers &&
391             mOldDataSpace == camera_stream::data_space &&
392             mOldFormat == camera_stream::format) {
393         mState = STATE_CONFIGURED;
394         if (flags::enable_stream_reconfiguration_for_unchanged_streams()
395                 && streamReconfigured != nullptr) {
396             *streamReconfigured = true;
397         }
398         return OK;
399     }
400 
401     // Reset prepared state, since buffer config has changed, and existing
402     // allocations are no longer valid
403     mPrepared = false;
404     mPrepareBlockRequest = true;
405     mStreamUnpreparable = false;
406 
407     bool reconfiguring = (mState == STATE_IN_RECONFIG);
408     status_t res;
409     res = configureQueueLocked();
410     // configureQueueLocked could return error in case of abandoned surface.
411     // Treat as non-fatal error.
412     if (res == NO_INIT || res == DEAD_OBJECT) {
413         ALOGE("%s: Unable to configure stream %d queue (non-fatal): %s (%d)",
414                 __FUNCTION__, mId, strerror(-res), res);
415         mState = STATE_ABANDONED;
416         return res;
417     } else if (res != OK) {
418         ALOGE("%s: Unable to configure stream %d queue: %s (%d)",
419                 __FUNCTION__, mId, strerror(-res), res);
420         mState = STATE_ERROR;
421         return res;
422     }
423 
424     if (reconfiguring && streamReconfigured != nullptr) {
425         *streamReconfigured = true;
426     }
427     mState = STATE_CONFIGURED;
428 
429     return res;
430 }
431 
cancelConfiguration()432 status_t Camera3Stream::cancelConfiguration() {
433     ATRACE_CALL();
434     Mutex::Autolock l(mLock);
435     switch (mState) {
436         case STATE_ERROR:
437             ALOGE("%s: In error state", __FUNCTION__);
438             return INVALID_OPERATION;
439         case STATE_IN_CONFIG:
440         case STATE_IN_RECONFIG:
441         case STATE_IN_IDLE:
442             // OK
443             break;
444         case STATE_CONSTRUCTED:
445         case STATE_CONFIGURED:
446             ALOGE("%s: Cannot cancel configuration that hasn't been started",
447                     __FUNCTION__);
448             return INVALID_OPERATION;
449         default:
450             ALOGE("%s: Unknown state", __FUNCTION__);
451             return INVALID_OPERATION;
452     }
453 
454     mUsage = mOldUsage;
455     camera_stream::max_buffers = mOldMaxBuffers;
456 
457     mState = ((mState == STATE_IN_RECONFIG) || (mState == STATE_IN_IDLE)) ? STATE_CONFIGURED :
458             STATE_CONSTRUCTED;
459 
460     return OK;
461 }
462 
isUnpreparable()463 bool Camera3Stream::isUnpreparable() {
464     ATRACE_CALL();
465 
466     Mutex::Autolock l(mLock);
467     return mStreamUnpreparable;
468 }
469 
markUnpreparable()470 void Camera3Stream::markUnpreparable() {
471     ATRACE_CALL();
472 
473     Mutex::Autolock l(mLock);
474     mStreamUnpreparable = true;
475 }
476 
startPrepare(int maxCount,bool blockRequest)477 status_t Camera3Stream::startPrepare(int maxCount, bool blockRequest) {
478     ATRACE_CALL();
479 
480     Mutex::Autolock l(mLock);
481 
482     if (maxCount < 0) {
483         ALOGE("%s: Stream %d: Can't prepare stream if max buffer count (%d) is < 0",
484                 __FUNCTION__, mId, maxCount);
485         return BAD_VALUE;
486     }
487 
488     // This function should be only called when the stream is configured already.
489     if (mState != STATE_CONFIGURED) {
490         ALOGE("%s: Stream %d: Can't prepare stream if stream is not in CONFIGURED "
491                 "state %d", __FUNCTION__, mId, mState);
492         return INVALID_OPERATION;
493     }
494 
495     // This function can't be called if the stream has already received filled
496     // buffers
497     if (mStreamUnpreparable) {
498         ALOGE("%s: Stream %d: Can't prepare stream that's already in use",
499                 __FUNCTION__, mId);
500         return INVALID_OPERATION;
501     }
502 
503     if (getHandoutOutputBufferCountLocked() > 0) {
504         ALOGE("%s: Stream %d: Can't prepare stream that has outstanding buffers",
505                 __FUNCTION__, mId);
506         return INVALID_OPERATION;
507     }
508 
509     size_t pipelineMax = getBufferCountLocked();
510     size_t clampedCount = (pipelineMax < static_cast<size_t>(maxCount)) ?
511             pipelineMax : static_cast<size_t>(maxCount);
512     size_t bufferCount = (maxCount == Camera3StreamInterface::ALLOCATE_PIPELINE_MAX) ?
513             pipelineMax : clampedCount;
514 
515     mPrepared = bufferCount <= mLastMaxCount;
516     mPrepareBlockRequest = blockRequest;
517 
518     if (mPrepared) return OK;
519 
520     mLastMaxCount = bufferCount;
521 
522     mPreparedBuffers.insertAt(camera_stream_buffer_t(), /*index*/0, bufferCount);
523     mPreparedBufferIdx = 0;
524 
525     mState = STATE_PREPARING;
526 
527     return NOT_ENOUGH_DATA;
528 }
529 
isBlockedByPrepare() const530 bool Camera3Stream::isBlockedByPrepare() const {
531     Mutex::Autolock l(mLock);
532     return mState == STATE_PREPARING && mPrepareBlockRequest;
533 }
534 
isAbandoned() const535 bool Camera3Stream::isAbandoned() const {
536     Mutex::Autolock l(mLock);
537     return mState == STATE_ABANDONED;
538 }
539 
prepareNextBuffer()540 status_t Camera3Stream::prepareNextBuffer() {
541     ATRACE_CALL();
542 
543     Mutex::Autolock l(mLock);
544     status_t res = OK;
545 
546     // This function should be only called when the stream is preparing
547     if (mState != STATE_PREPARING) {
548         ALOGE("%s: Stream %d: Can't prepare buffer if stream is not in PREPARING "
549                 "state %d", __FUNCTION__, mId, mState);
550         return INVALID_OPERATION;
551     }
552 
553     // Get next buffer - this may allocate, and take a while for large buffers
554     res = getBufferLocked( &mPreparedBuffers.editItemAt(mPreparedBufferIdx) );
555     if (res != OK) {
556         ALOGE("%s: Stream %d: Unable to allocate buffer %zu during preparation",
557                 __FUNCTION__, mId, mPreparedBufferIdx);
558         return NO_INIT;
559     }
560 
561     mPreparedBufferIdx++;
562 
563     // Check if we still have buffers left to allocate
564     if (mPreparedBufferIdx < mPreparedBuffers.size()) {
565         return NOT_ENOUGH_DATA;
566     }
567 
568     // Done with prepare - mark stream as such, and return all buffers
569     // via cancelPrepare
570     mPrepared = true;
571 
572     return cancelPrepareLocked();
573 }
574 
cancelPrepare()575 status_t Camera3Stream::cancelPrepare() {
576     ATRACE_CALL();
577 
578     Mutex::Autolock l(mLock);
579 
580     return cancelPrepareLocked();
581 }
582 
cancelPrepareLocked()583 status_t Camera3Stream::cancelPrepareLocked() {
584     status_t res = OK;
585 
586     // This function should be only called when the stream is mid-preparing.
587     if (mState != STATE_PREPARING) {
588         ALOGE("%s: Stream %d: Can't cancel prepare stream if stream is not in "
589                 "PREPARING state %d", __FUNCTION__, mId, mState);
590         return INVALID_OPERATION;
591     }
592 
593     // Return all valid buffers to stream, in ERROR state to indicate
594     // they weren't filled.
595     for (size_t i = 0; i < mPreparedBufferIdx; i++) {
596         mPreparedBuffers.editItemAt(i).release_fence = -1;
597         mPreparedBuffers.editItemAt(i).status = CAMERA_BUFFER_STATUS_ERROR;
598         returnBufferLocked(mPreparedBuffers[i], /*timestamp*/0, /*readoutTimestamp*/0,
599                 /*transform*/ -1);
600     }
601     mPreparedBuffers.clear();
602     mPreparedBufferIdx = 0;
603 
604     mState = STATE_CONFIGURED;
605 
606     return res;
607 }
608 
tearDown()609 status_t Camera3Stream::tearDown() {
610     ATRACE_CALL();
611     Mutex::Autolock l(mLock);
612 
613     status_t res = OK;
614 
615     // This function should be only called when the stream is configured.
616     if (mState != STATE_CONFIGURED) {
617         ALOGE("%s: Stream %d: Can't tear down stream if stream is not in "
618                 "CONFIGURED state %d", __FUNCTION__, mId, mState);
619         return INVALID_OPERATION;
620     }
621 
622     // If any buffers have been handed to the HAL, the stream cannot be torn down.
623     if (getHandoutOutputBufferCountLocked() > 0) {
624         ALOGE("%s: Stream %d: Can't tear down a stream that has outstanding buffers",
625                 __FUNCTION__, mId);
626         return INVALID_OPERATION;
627     }
628 
629     // Free buffers by disconnecting and then reconnecting to the buffer queue
630     // Only unused buffers will be dropped immediately; buffers that have been filled
631     // and are waiting to be acquired by the consumer and buffers that are currently
632     // acquired will be freed once they are released by the consumer.
633 
634     res = disconnectLocked();
635     if (res != OK) {
636         if (res == -ENOTCONN) {
637             // queue has been disconnected, nothing left to do, so exit with success
638             return OK;
639         }
640         ALOGE("%s: Stream %d: Unable to disconnect to tear down buffers: %s (%d)",
641                 __FUNCTION__, mId, strerror(-res), res);
642         return res;
643     }
644 
645     mState = STATE_IN_CONFIG;
646 
647     res = configureQueueLocked();
648     if (res != OK) {
649         ALOGE("%s: Unable to configure stream %d queue: %s (%d)",
650                 __FUNCTION__, mId, strerror(-res), res);
651         mState = STATE_ERROR;
652         return res;
653     }
654 
655     // Reset prepared state, since we've reconnected to the queue and can prepare again.
656     mPrepared = false;
657     mStreamUnpreparable = false;
658 
659     mState = STATE_CONFIGURED;
660 
661     return OK;
662 }
663 
getBuffer(camera_stream_buffer * buffer,nsecs_t waitBufferTimeout,const std::vector<size_t> & surface_ids)664 status_t Camera3Stream::getBuffer(camera_stream_buffer *buffer,
665         nsecs_t waitBufferTimeout,
666         const std::vector<size_t>& surface_ids) {
667     ATRACE_HFR_CALL();
668     Mutex::Autolock l(mLock);
669     status_t res = OK;
670 
671     // This function should be only called when the stream is configured already.
672     if (mState != STATE_CONFIGURED) {
673         ALOGE("%s: Stream %d: Can't get buffers if stream is not in CONFIGURED state %d",
674                 __FUNCTION__, mId, mState);
675         if (mState == STATE_ABANDONED) {
676             return DEAD_OBJECT;
677         } else {
678             return INVALID_OPERATION;
679         }
680     }
681 
682     // Wait for new buffer returned back if we are running into the limit. There
683     // are 2 limits:
684     // 1. The number of HAL buffers is greater than max_buffers
685     // 2. The number of HAL buffers + cached buffers is greater than max_buffers
686     //    + maxCachedBuffers
687     size_t numOutstandingBuffers = getHandoutOutputBufferCountLocked();
688     size_t numCachedBuffers = getCachedOutputBufferCountLocked();
689     size_t maxNumCachedBuffers = getMaxCachedOutputBuffersLocked();
690     while (numOutstandingBuffers == camera_stream::max_buffers ||
691             numOutstandingBuffers + numCachedBuffers ==
692             camera_stream::max_buffers + maxNumCachedBuffers) {
693         ALOGV("%s: Already dequeued max output buffers (%d(+%zu)), wait for next returned one.",
694                         __FUNCTION__, camera_stream::max_buffers, maxNumCachedBuffers);
695         nsecs_t waitStart = systemTime(SYSTEM_TIME_MONOTONIC);
696         if (waitBufferTimeout < kWaitForBufferDuration) {
697             waitBufferTimeout = kWaitForBufferDuration;
698         }
699         res = mOutputBufferReturnedSignal.waitRelative(mLock, waitBufferTimeout);
700         nsecs_t waitEnd = systemTime(SYSTEM_TIME_MONOTONIC);
701         mBufferLimitLatency.add(waitStart, waitEnd);
702         if (res != OK) {
703             if (res == TIMED_OUT) {
704                 ALOGE("%s: wait for output buffer return timed out after %lldms (max_buffers %d)",
705                         __FUNCTION__, waitBufferTimeout / 1000000LL,
706                         camera_stream::max_buffers);
707             }
708             return res;
709         }
710 
711         size_t updatedNumOutstandingBuffers = getHandoutOutputBufferCountLocked();
712         size_t updatedNumCachedBuffers = getCachedOutputBufferCountLocked();
713         if (updatedNumOutstandingBuffers >= numOutstandingBuffers &&
714                 updatedNumCachedBuffers == numCachedBuffers) {
715             ALOGE("%s: outstanding buffer count goes from %zu to %zu, "
716                     "getBuffer(s) call must not run in parallel!", __FUNCTION__,
717                     numOutstandingBuffers, updatedNumOutstandingBuffers);
718             return INVALID_OPERATION;
719         }
720         numOutstandingBuffers = updatedNumOutstandingBuffers;
721         numCachedBuffers = updatedNumCachedBuffers;
722     }
723 
724     res = getBufferLocked(buffer, surface_ids);
725     if (res == OK) {
726         fireBufferListenersLocked(*buffer, /*acquired*/true, /*output*/true);
727         if (buffer->buffer) {
728             Mutex::Autolock l(mOutstandingBuffersLock);
729             mOutstandingBuffers.push_back(*buffer->buffer);
730         }
731     }
732 
733     return res;
734 }
735 
isOutstandingBuffer(const camera_stream_buffer & buffer) const736 bool Camera3Stream::isOutstandingBuffer(const camera_stream_buffer &buffer) const{
737     if (buffer.buffer == nullptr) {
738         return false;
739     }
740 
741     Mutex::Autolock l(mOutstandingBuffersLock);
742 
743     for (auto b : mOutstandingBuffers) {
744         if (b == *buffer.buffer) {
745             return true;
746         }
747     }
748     return false;
749 }
750 
removeOutstandingBuffer(const camera_stream_buffer & buffer)751 void Camera3Stream::removeOutstandingBuffer(const camera_stream_buffer &buffer) {
752     if (buffer.buffer == nullptr) {
753         return;
754     }
755 
756     Mutex::Autolock l(mOutstandingBuffersLock);
757 
758     for (auto b = mOutstandingBuffers.begin(); b != mOutstandingBuffers.end(); b++) {
759         if (*b == *buffer.buffer) {
760             mOutstandingBuffers.erase(b);
761             return;
762         }
763     }
764 }
765 
returnBuffer(const camera_stream_buffer & buffer,nsecs_t timestamp,nsecs_t readoutTimestamp,bool timestampIncreasing,const std::vector<size_t> & surface_ids,uint64_t frameNumber,int32_t transform)766 status_t Camera3Stream::returnBuffer(const camera_stream_buffer &buffer,
767         nsecs_t timestamp, nsecs_t readoutTimestamp, bool timestampIncreasing,
768          const std::vector<size_t>& surface_ids, uint64_t frameNumber, int32_t transform) {
769     ATRACE_HFR_CALL();
770     Mutex::Autolock l(mLock);
771 
772     // Check if this buffer is outstanding.
773     if (!isOutstandingBuffer(buffer)) {
774         ALOGE("%s: Stream %d: Returning an unknown buffer.", __FUNCTION__, mId);
775         return BAD_VALUE;
776     }
777 
778     removeOutstandingBuffer(buffer);
779 
780     // Buffer status may be changed, so make a copy of the stream_buffer struct.
781     camera_stream_buffer b = buffer;
782     if (timestampIncreasing && timestamp != 0 && timestamp <= mLastTimestamp
783             && b.status != CAMERA_BUFFER_STATUS_ERROR) {
784         ALOGE("%s: Stream %d: timestamp %" PRId64 " is not increasing. Prev timestamp %" PRId64,
785                 __FUNCTION__, mId, timestamp, mLastTimestamp);
786         b.status = CAMERA_BUFFER_STATUS_ERROR;
787     }
788     mLastTimestamp = timestamp;
789 
790     /**
791      * TODO: Check that the state is valid first.
792      *
793      * <HAL3.2 IN_CONFIG and IN_RECONFIG in addition to CONFIGURED.
794      * >= HAL3.2 CONFIGURED only
795      *
796      * Do this for getBuffer as well.
797      */
798     status_t res = returnBufferLocked(b, timestamp, readoutTimestamp, transform, surface_ids);
799     if (res == OK) {
800         fireBufferListenersLocked(b, /*acquired*/false, /*output*/true, timestamp, frameNumber);
801     }
802 
803     // Even if returning the buffer failed, we still want to signal whoever is waiting for the
804     // buffer to be returned.
805     mOutputBufferReturnedSignal.signal();
806 
807     return res;
808 }
809 
getInputBuffer(camera_stream_buffer * buffer,Size * size,bool respectHalLimit)810 status_t Camera3Stream::getInputBuffer(camera_stream_buffer *buffer,
811         Size* size, bool respectHalLimit) {
812     ATRACE_CALL();
813     Mutex::Autolock l(mLock);
814     status_t res = OK;
815 
816     if (size == nullptr) {
817         ALOGE("%s: size must not be null", __FUNCTION__);
818         return BAD_VALUE;
819     }
820     // This function should be only called when the stream is configured already.
821     if (mState != STATE_CONFIGURED) {
822         ALOGE("%s: Stream %d: Can't get input buffers if stream is not in CONFIGURED state %d",
823                 __FUNCTION__, mId, mState);
824         return INVALID_OPERATION;
825     }
826 
827     // Wait for new buffer returned back if we are running into the limit.
828     if (getHandoutInputBufferCountLocked() == camera_stream::max_buffers && respectHalLimit) {
829         ALOGV("%s: Already dequeued max input buffers (%d), wait for next returned one.",
830                 __FUNCTION__, camera_stream::max_buffers);
831         res = mInputBufferReturnedSignal.waitRelative(mLock, kWaitForBufferDuration);
832         if (res != OK) {
833             if (res == TIMED_OUT) {
834                 ALOGE("%s: wait for input buffer return timed out after %lldms", __FUNCTION__,
835                         kWaitForBufferDuration / 1000000LL);
836             }
837             return res;
838         }
839     }
840 
841     res = getInputBufferLocked(buffer, size);
842     if (res == OK) {
843         fireBufferListenersLocked(*buffer, /*acquired*/true, /*output*/false);
844         if (buffer->buffer) {
845             Mutex::Autolock l(mOutstandingBuffersLock);
846             mOutstandingBuffers.push_back(*buffer->buffer);
847         }
848     }
849 
850     return res;
851 }
852 
returnInputBuffer(const camera_stream_buffer & buffer)853 status_t Camera3Stream::returnInputBuffer(const camera_stream_buffer &buffer) {
854     ATRACE_CALL();
855     Mutex::Autolock l(mLock);
856 
857     // Check if this buffer is outstanding.
858     if (!isOutstandingBuffer(buffer)) {
859         ALOGE("%s: Stream %d: Returning an unknown buffer.", __FUNCTION__, mId);
860         return BAD_VALUE;
861     }
862 
863     removeOutstandingBuffer(buffer);
864 
865     status_t res = returnInputBufferLocked(buffer);
866     if (res == OK) {
867         fireBufferListenersLocked(buffer, /*acquired*/false, /*output*/false);
868         mInputBufferReturnedSignal.signal();
869     }
870 
871     return res;
872 }
873 
874 #if WB_CAMERA3_AND_PROCESSORS_WITH_DEPENDENCIES
getInputSurface(sp<Surface> * surface)875 status_t Camera3Stream::getInputSurface(sp<Surface> *surface) {
876     ATRACE_CALL();
877     Mutex::Autolock l(mLock);
878 
879     return getInputSurfaceLocked(surface);
880 }
881 #else
getInputBufferProducer(sp<IGraphicBufferProducer> * producer)882 status_t Camera3Stream::getInputBufferProducer(sp<IGraphicBufferProducer> *producer) {
883     ATRACE_CALL();
884     Mutex::Autolock l(mLock);
885 
886     return getInputBufferProducerLocked(producer);
887 }
888 #endif
889 
fireBufferRequestForFrameNumber(uint64_t frameNumber,const CameraMetadata & settings)890 void Camera3Stream::fireBufferRequestForFrameNumber(uint64_t frameNumber,
891         const CameraMetadata& settings) {
892     ATRACE_CALL();
893     Mutex::Autolock l(mLock);
894 
895     for (auto &it : mBufferListenerList) {
896         sp<Camera3StreamBufferListener> listener = it.promote();
897         if (listener.get() != nullptr) {
898             listener->onBufferRequestForFrameNumber(frameNumber, getId(), settings);
899         }
900     }
901 }
902 
fireBufferListenersLocked(const camera_stream_buffer & buffer,bool acquired,bool output,nsecs_t timestamp,uint64_t frameNumber)903 void Camera3Stream::fireBufferListenersLocked(
904         const camera_stream_buffer& buffer, bool acquired, bool output, nsecs_t timestamp,
905         uint64_t frameNumber) {
906     List<wp<Camera3StreamBufferListener> >::iterator it, end;
907 
908     // TODO: finish implementing
909 
910     Camera3StreamBufferListener::BufferInfo info =
911         Camera3StreamBufferListener::BufferInfo();
912     info.mOutput = output;
913     info.mError = (buffer.status == CAMERA_BUFFER_STATUS_ERROR);
914     info.mFrameNumber = frameNumber;
915     info.mTimestamp = timestamp;
916     info.mStreamId = getId();
917 
918     // TODO: rest of fields
919 
920     for (it = mBufferListenerList.begin(), end = mBufferListenerList.end();
921          it != end;
922          ++it) {
923 
924         sp<Camera3StreamBufferListener> listener = it->promote();
925         if (listener != 0) {
926             if (acquired) {
927                 listener->onBufferAcquired(info);
928             } else {
929                 listener->onBufferReleased(info);
930             }
931         }
932     }
933 }
934 
hasOutstandingBuffers() const935 bool Camera3Stream::hasOutstandingBuffers() const {
936     ATRACE_CALL();
937     Mutex::Autolock l(mLock);
938     return hasOutstandingBuffersLocked();
939 }
940 
getOutstandingBuffersCount() const941 size_t Camera3Stream::getOutstandingBuffersCount() const {
942     ATRACE_CALL();
943     Mutex::Autolock l(mLock);
944     return getHandoutOutputBufferCountLocked();
945 }
946 
setStatusTracker(sp<StatusTracker> statusTracker)947 status_t Camera3Stream::setStatusTracker(sp<StatusTracker> statusTracker) {
948     Mutex::Autolock l(mLock);
949     sp<StatusTracker> oldTracker = mStatusTracker.promote();
950     if (oldTracker != 0 && mStatusId != StatusTracker::NO_STATUS_ID) {
951         oldTracker->removeComponent(mStatusId);
952     }
953     mStatusId = StatusTracker::NO_STATUS_ID;
954     mStatusTracker = statusTracker;
955 
956     return OK;
957 }
958 
disconnect()959 status_t Camera3Stream::disconnect() {
960     ATRACE_CALL();
961     Mutex::Autolock l(mLock);
962     ALOGV("%s: Stream %d: Disconnecting...", __FUNCTION__, mId);
963     status_t res = disconnectLocked();
964 
965     mBufferLimitLatency.log("Stream %d latency histogram for wait on max_buffers", mId);
966     mBufferLimitLatency.reset();
967 
968     if (res == -ENOTCONN) {
969         // "Already disconnected" -- not an error
970         return OK;
971     } else {
972         return res;
973     }
974 }
975 
dump(int fd,const Vector<String16> & args)976 void Camera3Stream::dump(int fd, [[maybe_unused]] const Vector<String16> &args)
977 {
978     mBufferLimitLatency.dump(fd,
979             "      Latency histogram for wait on max_buffers");
980 }
981 
getBufferLocked(camera_stream_buffer *,const std::vector<size_t> &)982 status_t Camera3Stream::getBufferLocked(camera_stream_buffer *,
983         const std::vector<size_t>&) {
984     ALOGE("%s: This type of stream does not support output", __FUNCTION__);
985     return INVALID_OPERATION;
986 }
987 
returnBufferLocked(const camera_stream_buffer &,nsecs_t,nsecs_t,int32_t,const std::vector<size_t> &)988 status_t Camera3Stream::returnBufferLocked(const camera_stream_buffer &,
989                                            nsecs_t, nsecs_t, int32_t, const std::vector<size_t>&) {
990     ALOGE("%s: This type of stream does not support output", __FUNCTION__);
991     return INVALID_OPERATION;
992 }
getInputBufferLocked(camera_stream_buffer *,Size *)993 status_t Camera3Stream::getInputBufferLocked(camera_stream_buffer *, Size *) {
994     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
995     return INVALID_OPERATION;
996 }
returnInputBufferLocked(const camera_stream_buffer &)997 status_t Camera3Stream::returnInputBufferLocked(
998         const camera_stream_buffer &) {
999     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
1000     return INVALID_OPERATION;
1001 }
1002 #if WB_CAMERA3_AND_PROCESSORS_WITH_DEPENDENCIES
getInputSurfaceLocked(sp<Surface> *)1003 status_t Camera3Stream::getInputSurfaceLocked(sp<Surface>*) {
1004     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
1005     return INVALID_OPERATION;
1006 }
1007 #else
getInputBufferProducerLocked(sp<IGraphicBufferProducer> *)1008 status_t Camera3Stream::getInputBufferProducerLocked(sp<IGraphicBufferProducer>*) {
1009     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
1010     return INVALID_OPERATION;
1011 }
1012 #endif
1013 
addBufferListener(wp<Camera3StreamBufferListener> listener)1014 void Camera3Stream::addBufferListener(
1015         wp<Camera3StreamBufferListener> listener) {
1016     Mutex::Autolock l(mLock);
1017 
1018     List<wp<Camera3StreamBufferListener> >::iterator it, end;
1019     for (it = mBufferListenerList.begin(), end = mBufferListenerList.end();
1020          it != end;
1021          ) {
1022         if (*it == listener) {
1023             ALOGE("%s: Try to add the same listener twice, ignoring...", __FUNCTION__);
1024             return;
1025         }
1026         it++;
1027     }
1028 
1029     mBufferListenerList.push_back(listener);
1030 }
1031 
removeBufferListener(const sp<Camera3StreamBufferListener> & listener)1032 void Camera3Stream::removeBufferListener(
1033         const sp<Camera3StreamBufferListener>& listener) {
1034     Mutex::Autolock l(mLock);
1035 
1036     bool erased = true;
1037     List<wp<Camera3StreamBufferListener> >::iterator it, end;
1038     for (it = mBufferListenerList.begin(), end = mBufferListenerList.end();
1039          it != end;
1040          ) {
1041 
1042         if (*it == listener) {
1043             it = mBufferListenerList.erase(it);
1044             erased = true;
1045         } else {
1046             ++it;
1047         }
1048     }
1049 
1050     if (!erased) {
1051         ALOGW("%s: Could not find listener to remove, already removed",
1052               __FUNCTION__);
1053     }
1054 }
1055 
setBufferFreedListener(wp<Camera3StreamBufferFreedListener> listener)1056 void Camera3Stream::setBufferFreedListener(
1057         wp<Camera3StreamBufferFreedListener> listener) {
1058     Mutex::Autolock l(mLock);
1059     // Only allow set listener during stream configuration because stream is guaranteed to be IDLE
1060     // at this state, so setBufferFreedListener won't collide with onBufferFreed callbacks
1061     if (mState != STATE_IN_CONFIG && mState != STATE_IN_RECONFIG) {
1062         ALOGE("%s: listener must be set during stream configuration!",__FUNCTION__);
1063         return;
1064     }
1065     mBufferFreedListener = listener;
1066 }
1067 
queueHDRMetadata(buffer_handle_t buffer,sp<ANativeWindow> & anw,int64_t dynamicRangeProfile)1068 void Camera3Stream::queueHDRMetadata(buffer_handle_t buffer, sp<ANativeWindow>& anw,
1069         int64_t dynamicRangeProfile) {
1070     auto& mapper = GraphicBufferMapper::get();
1071     switch (dynamicRangeProfile) {
1072         case ANDROID_REQUEST_AVAILABLE_DYNAMIC_RANGE_PROFILES_MAP_HDR10: {
1073             std::optional<ui::Smpte2086> smpte2086;
1074             auto res = mapper.getSmpte2086(buffer, &smpte2086);
1075             if ((res == OK) && smpte2086.has_value()) {
1076                 const auto& metaValue = smpte2086.value();
1077                 android_smpte2086_metadata meta = {
1078                     .displayPrimaryRed.x = metaValue.primaryRed.x,
1079                     .displayPrimaryRed.y = metaValue.primaryRed.y,
1080                     .displayPrimaryGreen.x = metaValue.primaryGreen.x,
1081                     .displayPrimaryGreen.y = metaValue.primaryGreen.y,
1082                     .displayPrimaryBlue.x = metaValue.primaryBlue.x,
1083                     .displayPrimaryBlue.y = metaValue.primaryBlue.y,
1084                     .whitePoint.x = metaValue.whitePoint.x,
1085                     .whitePoint.y = metaValue.whitePoint.y,
1086                     .maxLuminance = metaValue.maxLuminance,
1087                     .minLuminance = metaValue.minLuminance};
1088                 native_window_set_buffers_smpte2086_metadata(anw.get(), &meta);
1089             } else {
1090                 ALOGE("%s Couldn't retrieve Smpte2086 metadata %s (%d)",
1091                         __FUNCTION__, strerror(-res), res);
1092             }
1093             break;
1094         }
1095         case ANDROID_REQUEST_AVAILABLE_DYNAMIC_RANGE_PROFILES_MAP_HDR10_PLUS: {
1096             std::optional<std::vector<uint8_t>> smpte2094_40;
1097             auto res = mapper.getSmpte2094_40(buffer, &smpte2094_40);
1098             if ((res == OK) && smpte2094_40.has_value()) {
1099                 native_window_set_buffers_hdr10_plus_metadata(anw.get(),
1100                         smpte2094_40.value().size(), smpte2094_40.value().data());
1101             } else {
1102                 ALOGE("%s Couldn't retrieve Smpte2094_40 metadata %s (%d)",
1103                         __FUNCTION__, strerror(-res), res);
1104             }
1105             break;
1106         }
1107         default:
1108             // No-op
1109             break;
1110     }
1111 }
1112 
1113 
1114 }; // namespace camera3
1115 
1116 }; // namespace android
1117