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 #define LOG_TAG "Camera3-Stream"
18 #define ATRACE_TAG ATRACE_TAG_CAMERA
19 //#define LOG_NDEBUG 0
20 
21 #include <utils/Log.h>
22 #include <utils/Trace.h>
23 #include "device3/Camera3Stream.h"
24 #include "device3/StatusTracker.h"
25 
26 #include <cutils/properties.h>
27 
28 namespace android {
29 
30 namespace camera3 {
31 
~Camera3Stream()32 Camera3Stream::~Camera3Stream() {
33     sp<StatusTracker> statusTracker = mStatusTracker.promote();
34     if (statusTracker != 0 && mStatusId != StatusTracker::NO_STATUS_ID) {
35         statusTracker->removeComponent(mStatusId);
36     }
37 }
38 
cast(camera3_stream * stream)39 Camera3Stream* Camera3Stream::cast(camera3_stream *stream) {
40     return static_cast<Camera3Stream*>(stream);
41 }
42 
cast(const camera3_stream * stream)43 const Camera3Stream* Camera3Stream::cast(const camera3_stream *stream) {
44     return static_cast<const Camera3Stream*>(stream);
45 }
46 
Camera3Stream(int id,camera3_stream_type type,uint32_t width,uint32_t height,size_t maxSize,int format,android_dataspace dataSpace,camera3_stream_rotation_t rotation,const String8 & physicalCameraId,int setId)47 Camera3Stream::Camera3Stream(int id,
48         camera3_stream_type type,
49         uint32_t width, uint32_t height, size_t maxSize, int format,
50         android_dataspace dataSpace, camera3_stream_rotation_t rotation,
51         const String8& physicalCameraId, int setId) :
52     camera3_stream(),
53     mId(id),
54     mSetId(setId),
55     mName(String8::format("Camera3Stream[%d]", id)),
56     mMaxSize(maxSize),
57     mState(STATE_CONSTRUCTED),
58     mStatusId(StatusTracker::NO_STATUS_ID),
59     mStreamUnpreparable(true),
60     mUsage(0),
61     mOldUsage(0),
62     mOldMaxBuffers(0),
63     mOldFormat(-1),
64     mOldDataSpace(HAL_DATASPACE_UNKNOWN),
65     mPrepared(false),
66     mPrepareBlockRequest(true),
67     mPreparedBufferIdx(0),
68     mLastMaxCount(Camera3StreamInterface::ALLOCATE_PIPELINE_MAX),
69     mBufferLimitLatency(kBufferLimitLatencyBinSize),
70     mFormatOverridden(false),
71     mOriginalFormat(format),
72     mDataSpaceOverridden(false),
73     mOriginalDataSpace(dataSpace),
74     mPhysicalCameraId(physicalCameraId),
75     mLastTimestamp(0) {
76 
77     camera3_stream::stream_type = type;
78     camera3_stream::width = width;
79     camera3_stream::height = height;
80     camera3_stream::format = format;
81     camera3_stream::data_space = dataSpace;
82     camera3_stream::rotation = rotation;
83     camera3_stream::max_buffers = 0;
84     camera3_stream::priv = NULL;
85     camera3_stream::physical_camera_id = mPhysicalCameraId.string();
86 
87     if ((format == HAL_PIXEL_FORMAT_BLOB || format == HAL_PIXEL_FORMAT_RAW_OPAQUE) &&
88             maxSize == 0) {
89         ALOGE("%s: BLOB or RAW_OPAQUE format with size == 0", __FUNCTION__);
90         mState = STATE_ERROR;
91     }
92 }
93 
getId() const94 int Camera3Stream::getId() const {
95     return mId;
96 }
97 
getStreamSetId() const98 int Camera3Stream::getStreamSetId() const {
99     return mSetId;
100 }
101 
getWidth() const102 uint32_t Camera3Stream::getWidth() const {
103     return camera3_stream::width;
104 }
105 
getHeight() const106 uint32_t Camera3Stream::getHeight() const {
107     return camera3_stream::height;
108 }
109 
getFormat() const110 int Camera3Stream::getFormat() const {
111     return camera3_stream::format;
112 }
113 
getDataSpace() const114 android_dataspace Camera3Stream::getDataSpace() const {
115     return camera3_stream::data_space;
116 }
117 
getUsage() const118 uint64_t Camera3Stream::getUsage() const {
119     return mUsage;
120 }
121 
setUsage(uint64_t usage)122 void Camera3Stream::setUsage(uint64_t usage) {
123     mUsage = usage;
124 }
125 
setFormatOverride(bool formatOverridden)126 void Camera3Stream::setFormatOverride(bool formatOverridden) {
127     mFormatOverridden = formatOverridden;
128 }
129 
isFormatOverridden() const130 bool Camera3Stream::isFormatOverridden() const {
131     return mFormatOverridden;
132 }
133 
getOriginalFormat() const134 int Camera3Stream::getOriginalFormat() const {
135     return mOriginalFormat;
136 }
137 
setDataSpaceOverride(bool dataSpaceOverridden)138 void Camera3Stream::setDataSpaceOverride(bool dataSpaceOverridden) {
139     mDataSpaceOverridden = dataSpaceOverridden;
140 }
141 
isDataSpaceOverridden() const142 bool Camera3Stream::isDataSpaceOverridden() const {
143     return mDataSpaceOverridden;
144 }
145 
getOriginalDataSpace() const146 android_dataspace Camera3Stream::getOriginalDataSpace() const {
147     return mOriginalDataSpace;
148 }
149 
physicalCameraId() const150 const String8& Camera3Stream::physicalCameraId() const {
151     return mPhysicalCameraId;
152 }
153 
forceToIdle()154 status_t Camera3Stream::forceToIdle() {
155     ATRACE_CALL();
156     Mutex::Autolock l(mLock);
157     status_t res;
158 
159     switch (mState) {
160         case STATE_ERROR:
161         case STATE_CONSTRUCTED:
162         case STATE_IN_CONFIG:
163         case STATE_PREPARING:
164         case STATE_IN_RECONFIG:
165             ALOGE("%s: Invalid state: %d", __FUNCTION__, mState);
166             res = NO_INIT;
167             break;
168         case STATE_CONFIGURED:
169             if (hasOutstandingBuffersLocked()) {
170                 sp<StatusTracker> statusTracker = mStatusTracker.promote();
171                 if (statusTracker != 0) {
172                     statusTracker->markComponentIdle(mStatusId, Fence::NO_FENCE);
173                 }
174             }
175 
176             mState = STATE_IN_IDLE;
177             res = OK;
178 
179             break;
180         default:
181             ALOGE("%s: Unknown state %d", __FUNCTION__, mState);
182             res = NO_INIT;
183     }
184 
185     return res;
186 }
187 
restoreConfiguredState()188 status_t Camera3Stream::restoreConfiguredState() {
189     ATRACE_CALL();
190     Mutex::Autolock l(mLock);
191     status_t res;
192 
193     switch (mState) {
194         case STATE_ERROR:
195         case STATE_CONSTRUCTED:
196         case STATE_IN_CONFIG:
197         case STATE_PREPARING:
198         case STATE_IN_RECONFIG:
199         case STATE_CONFIGURED:
200             ALOGE("%s: Invalid state: %d", __FUNCTION__, mState);
201             res = NO_INIT;
202             break;
203         case STATE_IN_IDLE:
204             if (hasOutstandingBuffersLocked()) {
205                 sp<StatusTracker> statusTracker = mStatusTracker.promote();
206                 if (statusTracker != 0) {
207                     statusTracker->markComponentActive(mStatusId);
208                 }
209             }
210 
211             mState = STATE_CONFIGURED;
212             res = OK;
213 
214             break;
215         default:
216             ALOGE("%s: Unknown state %d", __FUNCTION__, mState);
217             res = NO_INIT;
218     }
219 
220     return res;
221 }
222 
startConfiguration()223 camera3_stream* Camera3Stream::startConfiguration() {
224     ATRACE_CALL();
225     Mutex::Autolock l(mLock);
226     status_t res;
227 
228     switch (mState) {
229         case STATE_ERROR:
230             ALOGE("%s: In error state", __FUNCTION__);
231             return NULL;
232         case STATE_CONSTRUCTED:
233         case STATE_IN_IDLE:
234             // OK
235             break;
236         case STATE_IN_CONFIG:
237         case STATE_IN_RECONFIG:
238             // Can start config again with no trouble; but don't redo
239             // mOldUsage/mOldMaxBuffers
240             return this;
241         case STATE_CONFIGURED:
242             if (hasOutstandingBuffersLocked()) {
243                 ALOGE("%s: Cannot configure stream; has outstanding buffers",
244                         __FUNCTION__);
245                 return NULL;
246             }
247             break;
248         default:
249             ALOGE("%s: Unknown state %d", __FUNCTION__, mState);
250             return NULL;
251     }
252 
253     mOldUsage = mUsage;
254     mOldMaxBuffers = camera3_stream::max_buffers;
255     mOldFormat = camera3_stream::format;
256     mOldDataSpace = camera3_stream::data_space;
257 
258     res = getEndpointUsage(&mUsage);
259     if (res != OK) {
260         ALOGE("%s: Cannot query consumer endpoint usage!",
261                 __FUNCTION__);
262         return NULL;
263     }
264 
265     if (mState == STATE_IN_IDLE) {
266         // Skip configuration.
267         return this;
268     }
269 
270     // Stop tracking if currently doing so
271     if (mStatusId != StatusTracker::NO_STATUS_ID) {
272         sp<StatusTracker> statusTracker = mStatusTracker.promote();
273         if (statusTracker != 0) {
274             statusTracker->removeComponent(mStatusId);
275         }
276         mStatusId = StatusTracker::NO_STATUS_ID;
277     }
278 
279     if (mState == STATE_CONSTRUCTED) {
280         mState = STATE_IN_CONFIG;
281     } else { // mState == STATE_CONFIGURED
282         LOG_ALWAYS_FATAL_IF(mState != STATE_CONFIGURED, "Invalid state: 0x%x", mState);
283         mState = STATE_IN_RECONFIG;
284     }
285 
286     return this;
287 }
288 
isConfiguring() const289 bool Camera3Stream::isConfiguring() const {
290     Mutex::Autolock l(mLock);
291     return (mState == STATE_IN_CONFIG) || (mState == STATE_IN_RECONFIG);
292 }
293 
finishConfiguration(bool * streamReconfigured)294 status_t Camera3Stream::finishConfiguration(/*out*/bool* streamReconfigured) {
295     ATRACE_CALL();
296     if (streamReconfigured != nullptr) {
297         *streamReconfigured = false;
298     }
299     Mutex::Autolock l(mLock);
300     switch (mState) {
301         case STATE_ERROR:
302             ALOGE("%s: In error state", __FUNCTION__);
303             return INVALID_OPERATION;
304         case STATE_IN_CONFIG:
305         case STATE_IN_RECONFIG:
306             // OK
307             break;
308         case STATE_CONSTRUCTED:
309         case STATE_CONFIGURED:
310             ALOGE("%s: Cannot finish configuration that hasn't been started",
311                     __FUNCTION__);
312             return INVALID_OPERATION;
313         case STATE_IN_IDLE:
314             //Skip configuration in this state
315             return OK;
316         default:
317             ALOGE("%s: Unknown state", __FUNCTION__);
318             return INVALID_OPERATION;
319     }
320 
321     // Register for idle tracking
322     sp<StatusTracker> statusTracker = mStatusTracker.promote();
323     if (statusTracker != 0 && mStatusId == StatusTracker::NO_STATUS_ID) {
324         mStatusId = statusTracker->addComponent();
325     }
326 
327     // Check if the stream configuration is unchanged, and skip reallocation if
328     // so. As documented in hardware/camera3.h:configure_streams().
329     if (mState == STATE_IN_RECONFIG &&
330             mOldUsage == mUsage &&
331             mOldMaxBuffers == camera3_stream::max_buffers &&
332             mOldDataSpace == camera3_stream::data_space &&
333             mOldFormat == camera3_stream::format) {
334         mState = STATE_CONFIGURED;
335         return OK;
336     }
337 
338     // Reset prepared state, since buffer config has changed, and existing
339     // allocations are no longer valid
340     mPrepared = false;
341     mPrepareBlockRequest = true;
342     mStreamUnpreparable = false;
343 
344     bool reconfiguring = (mState == STATE_IN_RECONFIG);
345     status_t res;
346     res = configureQueueLocked();
347     // configureQueueLocked could return error in case of abandoned surface.
348     // Treat as non-fatal error.
349     if (res == NO_INIT || res == DEAD_OBJECT) {
350         ALOGE("%s: Unable to configure stream %d queue (non-fatal): %s (%d)",
351                 __FUNCTION__, mId, strerror(-res), res);
352         mState = STATE_ABANDONED;
353         return res;
354     } else if (res != OK) {
355         ALOGE("%s: Unable to configure stream %d queue: %s (%d)",
356                 __FUNCTION__, mId, strerror(-res), res);
357         mState = STATE_ERROR;
358         return res;
359     }
360 
361     if (reconfiguring && streamReconfigured != nullptr) {
362         *streamReconfigured = true;
363     }
364     mState = STATE_CONFIGURED;
365 
366     return res;
367 }
368 
cancelConfiguration()369 status_t Camera3Stream::cancelConfiguration() {
370     ATRACE_CALL();
371     Mutex::Autolock l(mLock);
372     switch (mState) {
373         case STATE_ERROR:
374             ALOGE("%s: In error state", __FUNCTION__);
375             return INVALID_OPERATION;
376         case STATE_IN_CONFIG:
377         case STATE_IN_RECONFIG:
378         case STATE_IN_IDLE:
379             // OK
380             break;
381         case STATE_CONSTRUCTED:
382         case STATE_CONFIGURED:
383             ALOGE("%s: Cannot cancel configuration that hasn't been started",
384                     __FUNCTION__);
385             return INVALID_OPERATION;
386         default:
387             ALOGE("%s: Unknown state", __FUNCTION__);
388             return INVALID_OPERATION;
389     }
390 
391     mUsage = mOldUsage;
392     camera3_stream::max_buffers = mOldMaxBuffers;
393 
394     mState = ((mState == STATE_IN_RECONFIG) || (mState == STATE_IN_IDLE)) ? STATE_CONFIGURED :
395             STATE_CONSTRUCTED;
396 
397     return OK;
398 }
399 
isUnpreparable()400 bool Camera3Stream::isUnpreparable() {
401     ATRACE_CALL();
402 
403     Mutex::Autolock l(mLock);
404     return mStreamUnpreparable;
405 }
406 
startPrepare(int maxCount,bool blockRequest)407 status_t Camera3Stream::startPrepare(int maxCount, bool blockRequest) {
408     ATRACE_CALL();
409 
410     Mutex::Autolock l(mLock);
411 
412     if (maxCount < 0) {
413         ALOGE("%s: Stream %d: Can't prepare stream if max buffer count (%d) is < 0",
414                 __FUNCTION__, mId, maxCount);
415         return BAD_VALUE;
416     }
417 
418     // This function should be only called when the stream is configured already.
419     if (mState != STATE_CONFIGURED) {
420         ALOGE("%s: Stream %d: Can't prepare stream if stream is not in CONFIGURED "
421                 "state %d", __FUNCTION__, mId, mState);
422         return INVALID_OPERATION;
423     }
424 
425     // This function can't be called if the stream has already received filled
426     // buffers
427     if (mStreamUnpreparable) {
428         ALOGE("%s: Stream %d: Can't prepare stream that's already in use",
429                 __FUNCTION__, mId);
430         return INVALID_OPERATION;
431     }
432 
433     if (getHandoutOutputBufferCountLocked() > 0) {
434         ALOGE("%s: Stream %d: Can't prepare stream that has outstanding buffers",
435                 __FUNCTION__, mId);
436         return INVALID_OPERATION;
437     }
438 
439     size_t pipelineMax = getBufferCountLocked();
440     size_t clampedCount = (pipelineMax < static_cast<size_t>(maxCount)) ?
441             pipelineMax : static_cast<size_t>(maxCount);
442     size_t bufferCount = (maxCount == Camera3StreamInterface::ALLOCATE_PIPELINE_MAX) ?
443             pipelineMax : clampedCount;
444 
445     mPrepared = bufferCount <= mLastMaxCount;
446     mPrepareBlockRequest = blockRequest;
447 
448     if (mPrepared) return OK;
449 
450     mLastMaxCount = bufferCount;
451 
452     mPreparedBuffers.insertAt(camera3_stream_buffer_t(), /*index*/0, bufferCount);
453     mPreparedBufferIdx = 0;
454 
455     mState = STATE_PREPARING;
456 
457     return NOT_ENOUGH_DATA;
458 }
459 
isBlockedByPrepare() const460 bool Camera3Stream::isBlockedByPrepare() const {
461     Mutex::Autolock l(mLock);
462     return mState == STATE_PREPARING && mPrepareBlockRequest;
463 }
464 
isAbandoned() const465 bool Camera3Stream::isAbandoned() const {
466     Mutex::Autolock l(mLock);
467     return mState == STATE_ABANDONED;
468 }
469 
prepareNextBuffer()470 status_t Camera3Stream::prepareNextBuffer() {
471     ATRACE_CALL();
472 
473     Mutex::Autolock l(mLock);
474     status_t res = OK;
475 
476     // This function should be only called when the stream is preparing
477     if (mState != STATE_PREPARING) {
478         ALOGE("%s: Stream %d: Can't prepare buffer if stream is not in PREPARING "
479                 "state %d", __FUNCTION__, mId, mState);
480         return INVALID_OPERATION;
481     }
482 
483     // Get next buffer - this may allocate, and take a while for large buffers
484     res = getBufferLocked( &mPreparedBuffers.editItemAt(mPreparedBufferIdx) );
485     if (res != OK) {
486         ALOGE("%s: Stream %d: Unable to allocate buffer %zu during preparation",
487                 __FUNCTION__, mId, mPreparedBufferIdx);
488         return NO_INIT;
489     }
490 
491     mPreparedBufferIdx++;
492 
493     // Check if we still have buffers left to allocate
494     if (mPreparedBufferIdx < mPreparedBuffers.size()) {
495         return NOT_ENOUGH_DATA;
496     }
497 
498     // Done with prepare - mark stream as such, and return all buffers
499     // via cancelPrepare
500     mPrepared = true;
501 
502     return cancelPrepareLocked();
503 }
504 
cancelPrepare()505 status_t Camera3Stream::cancelPrepare() {
506     ATRACE_CALL();
507 
508     Mutex::Autolock l(mLock);
509 
510     return cancelPrepareLocked();
511 }
512 
cancelPrepareLocked()513 status_t Camera3Stream::cancelPrepareLocked() {
514     status_t res = OK;
515 
516     // This function should be only called when the stream is mid-preparing.
517     if (mState != STATE_PREPARING) {
518         ALOGE("%s: Stream %d: Can't cancel prepare stream if stream is not in "
519                 "PREPARING state %d", __FUNCTION__, mId, mState);
520         return INVALID_OPERATION;
521     }
522 
523     // Return all valid buffers to stream, in ERROR state to indicate
524     // they weren't filled.
525     for (size_t i = 0; i < mPreparedBufferIdx; i++) {
526         mPreparedBuffers.editItemAt(i).release_fence = -1;
527         mPreparedBuffers.editItemAt(i).status = CAMERA3_BUFFER_STATUS_ERROR;
528         returnBufferLocked(mPreparedBuffers[i], 0);
529     }
530     mPreparedBuffers.clear();
531     mPreparedBufferIdx = 0;
532 
533     mState = STATE_CONFIGURED;
534 
535     return res;
536 }
537 
tearDown()538 status_t Camera3Stream::tearDown() {
539     ATRACE_CALL();
540     Mutex::Autolock l(mLock);
541 
542     status_t res = OK;
543 
544     // This function should be only called when the stream is configured.
545     if (mState != STATE_CONFIGURED) {
546         ALOGE("%s: Stream %d: Can't tear down stream if stream is not in "
547                 "CONFIGURED state %d", __FUNCTION__, mId, mState);
548         return INVALID_OPERATION;
549     }
550 
551     // If any buffers have been handed to the HAL, the stream cannot be torn down.
552     if (getHandoutOutputBufferCountLocked() > 0) {
553         ALOGE("%s: Stream %d: Can't tear down a stream that has outstanding buffers",
554                 __FUNCTION__, mId);
555         return INVALID_OPERATION;
556     }
557 
558     // Free buffers by disconnecting and then reconnecting to the buffer queue
559     // Only unused buffers will be dropped immediately; buffers that have been filled
560     // and are waiting to be acquired by the consumer and buffers that are currently
561     // acquired will be freed once they are released by the consumer.
562 
563     res = disconnectLocked();
564     if (res != OK) {
565         if (res == -ENOTCONN) {
566             // queue has been disconnected, nothing left to do, so exit with success
567             return OK;
568         }
569         ALOGE("%s: Stream %d: Unable to disconnect to tear down buffers: %s (%d)",
570                 __FUNCTION__, mId, strerror(-res), res);
571         return res;
572     }
573 
574     mState = STATE_IN_CONFIG;
575 
576     res = configureQueueLocked();
577     if (res != OK) {
578         ALOGE("%s: Unable to configure stream %d queue: %s (%d)",
579                 __FUNCTION__, mId, strerror(-res), res);
580         mState = STATE_ERROR;
581         return res;
582     }
583 
584     // Reset prepared state, since we've reconnected to the queue and can prepare again.
585     mPrepared = false;
586     mStreamUnpreparable = false;
587 
588     mState = STATE_CONFIGURED;
589 
590     return OK;
591 }
592 
getBuffer(camera3_stream_buffer * buffer,nsecs_t waitBufferTimeout,const std::vector<size_t> & surface_ids)593 status_t Camera3Stream::getBuffer(camera3_stream_buffer *buffer,
594         nsecs_t waitBufferTimeout,
595         const std::vector<size_t>& surface_ids) {
596     ATRACE_CALL();
597     Mutex::Autolock l(mLock);
598     status_t res = OK;
599 
600     // This function should be only called when the stream is configured already.
601     if (mState != STATE_CONFIGURED) {
602         ALOGE("%s: Stream %d: Can't get buffers if stream is not in CONFIGURED state %d",
603                 __FUNCTION__, mId, mState);
604         if (mState == STATE_ABANDONED) {
605             return DEAD_OBJECT;
606         } else {
607             return INVALID_OPERATION;
608         }
609     }
610 
611     // Wait for new buffer returned back if we are running into the limit.
612     if (getHandoutOutputBufferCountLocked() == camera3_stream::max_buffers) {
613         ALOGV("%s: Already dequeued max output buffers (%d), wait for next returned one.",
614                         __FUNCTION__, camera3_stream::max_buffers);
615         nsecs_t waitStart = systemTime(SYSTEM_TIME_MONOTONIC);
616         if (waitBufferTimeout < kWaitForBufferDuration) {
617             waitBufferTimeout = kWaitForBufferDuration;
618         }
619         res = mOutputBufferReturnedSignal.waitRelative(mLock, waitBufferTimeout);
620         nsecs_t waitEnd = systemTime(SYSTEM_TIME_MONOTONIC);
621         mBufferLimitLatency.add(waitStart, waitEnd);
622         if (res != OK) {
623             if (res == TIMED_OUT) {
624                 ALOGE("%s: wait for output buffer return timed out after %lldms (max_buffers %d)",
625                         __FUNCTION__, waitBufferTimeout / 1000000LL,
626                         camera3_stream::max_buffers);
627             }
628             return res;
629         }
630     }
631 
632     res = getBufferLocked(buffer, surface_ids);
633     if (res == OK) {
634         fireBufferListenersLocked(*buffer, /*acquired*/true, /*output*/true);
635         if (buffer->buffer) {
636             Mutex::Autolock l(mOutstandingBuffersLock);
637             mOutstandingBuffers.push_back(*buffer->buffer);
638         }
639     }
640 
641     return res;
642 }
643 
isOutstandingBuffer(const camera3_stream_buffer & buffer) const644 bool Camera3Stream::isOutstandingBuffer(const camera3_stream_buffer &buffer) const{
645     if (buffer.buffer == nullptr) {
646         return false;
647     }
648 
649     Mutex::Autolock l(mOutstandingBuffersLock);
650 
651     for (auto b : mOutstandingBuffers) {
652         if (b == *buffer.buffer) {
653             return true;
654         }
655     }
656     return false;
657 }
658 
removeOutstandingBuffer(const camera3_stream_buffer & buffer)659 void Camera3Stream::removeOutstandingBuffer(const camera3_stream_buffer &buffer) {
660     if (buffer.buffer == nullptr) {
661         return;
662     }
663 
664     Mutex::Autolock l(mOutstandingBuffersLock);
665 
666     for (auto b = mOutstandingBuffers.begin(); b != mOutstandingBuffers.end(); b++) {
667         if (*b == *buffer.buffer) {
668             mOutstandingBuffers.erase(b);
669             return;
670         }
671     }
672 }
673 
returnBuffer(const camera3_stream_buffer & buffer,nsecs_t timestamp,bool timestampIncreasing,const std::vector<size_t> & surface_ids,uint64_t frameNumber)674 status_t Camera3Stream::returnBuffer(const camera3_stream_buffer &buffer,
675         nsecs_t timestamp, bool timestampIncreasing,
676          const std::vector<size_t>& surface_ids, uint64_t frameNumber) {
677     ATRACE_CALL();
678     Mutex::Autolock l(mLock);
679 
680     // Check if this buffer is outstanding.
681     if (!isOutstandingBuffer(buffer)) {
682         ALOGE("%s: Stream %d: Returning an unknown buffer.", __FUNCTION__, mId);
683         return BAD_VALUE;
684     }
685 
686     removeOutstandingBuffer(buffer);
687 
688     // Buffer status may be changed, so make a copy of the stream_buffer struct.
689     camera3_stream_buffer b = buffer;
690     if (timestampIncreasing && timestamp != 0 && timestamp <= mLastTimestamp) {
691         ALOGE("%s: Stream %d: timestamp %" PRId64 " is not increasing. Prev timestamp %" PRId64,
692                 __FUNCTION__, mId, timestamp, mLastTimestamp);
693         b.status = CAMERA3_BUFFER_STATUS_ERROR;
694     }
695     mLastTimestamp = timestamp;
696 
697     /**
698      * TODO: Check that the state is valid first.
699      *
700      * <HAL3.2 IN_CONFIG and IN_RECONFIG in addition to CONFIGURED.
701      * >= HAL3.2 CONFIGURED only
702      *
703      * Do this for getBuffer as well.
704      */
705     status_t res = returnBufferLocked(b, timestamp, surface_ids);
706     if (res == OK) {
707         fireBufferListenersLocked(b, /*acquired*/false, /*output*/true, timestamp, frameNumber);
708     }
709 
710     // Even if returning the buffer failed, we still want to signal whoever is waiting for the
711     // buffer to be returned.
712     mOutputBufferReturnedSignal.signal();
713 
714     return res;
715 }
716 
getInputBuffer(camera3_stream_buffer * buffer,bool respectHalLimit)717 status_t Camera3Stream::getInputBuffer(camera3_stream_buffer *buffer, bool respectHalLimit) {
718     ATRACE_CALL();
719     Mutex::Autolock l(mLock);
720     status_t res = OK;
721 
722     // This function should be only called when the stream is configured already.
723     if (mState != STATE_CONFIGURED) {
724         ALOGE("%s: Stream %d: Can't get input buffers if stream is not in CONFIGURED state %d",
725                 __FUNCTION__, mId, mState);
726         return INVALID_OPERATION;
727     }
728 
729     // Wait for new buffer returned back if we are running into the limit.
730     if (getHandoutInputBufferCountLocked() == camera3_stream::max_buffers && respectHalLimit) {
731         ALOGV("%s: Already dequeued max input buffers (%d), wait for next returned one.",
732                 __FUNCTION__, camera3_stream::max_buffers);
733         res = mInputBufferReturnedSignal.waitRelative(mLock, kWaitForBufferDuration);
734         if (res != OK) {
735             if (res == TIMED_OUT) {
736                 ALOGE("%s: wait for input buffer return timed out after %lldms", __FUNCTION__,
737                         kWaitForBufferDuration / 1000000LL);
738             }
739             return res;
740         }
741     }
742 
743     res = getInputBufferLocked(buffer);
744     if (res == OK) {
745         fireBufferListenersLocked(*buffer, /*acquired*/true, /*output*/false);
746         if (buffer->buffer) {
747             Mutex::Autolock l(mOutstandingBuffersLock);
748             mOutstandingBuffers.push_back(*buffer->buffer);
749         }
750     }
751 
752     return res;
753 }
754 
returnInputBuffer(const camera3_stream_buffer & buffer)755 status_t Camera3Stream::returnInputBuffer(const camera3_stream_buffer &buffer) {
756     ATRACE_CALL();
757     Mutex::Autolock l(mLock);
758 
759     // Check if this buffer is outstanding.
760     if (!isOutstandingBuffer(buffer)) {
761         ALOGE("%s: Stream %d: Returning an unknown buffer.", __FUNCTION__, mId);
762         return BAD_VALUE;
763     }
764 
765     removeOutstandingBuffer(buffer);
766 
767     status_t res = returnInputBufferLocked(buffer);
768     if (res == OK) {
769         fireBufferListenersLocked(buffer, /*acquired*/false, /*output*/false);
770         mInputBufferReturnedSignal.signal();
771     }
772 
773     return res;
774 }
775 
getInputBufferProducer(sp<IGraphicBufferProducer> * producer)776 status_t Camera3Stream::getInputBufferProducer(sp<IGraphicBufferProducer> *producer) {
777     ATRACE_CALL();
778     Mutex::Autolock l(mLock);
779 
780     return getInputBufferProducerLocked(producer);
781 }
782 
fireBufferRequestForFrameNumber(uint64_t frameNumber,const CameraMetadata & settings)783 void Camera3Stream::fireBufferRequestForFrameNumber(uint64_t frameNumber,
784         const CameraMetadata& settings) {
785     ATRACE_CALL();
786     Mutex::Autolock l(mLock);
787 
788     for (auto &it : mBufferListenerList) {
789         sp<Camera3StreamBufferListener> listener = it.promote();
790         if (listener.get() != nullptr) {
791             listener->onBufferRequestForFrameNumber(frameNumber, getId(), settings);
792         }
793     }
794 }
795 
fireBufferListenersLocked(const camera3_stream_buffer & buffer,bool acquired,bool output,nsecs_t timestamp,uint64_t frameNumber)796 void Camera3Stream::fireBufferListenersLocked(
797         const camera3_stream_buffer& buffer, bool acquired, bool output, nsecs_t timestamp,
798         uint64_t frameNumber) {
799     List<wp<Camera3StreamBufferListener> >::iterator it, end;
800 
801     // TODO: finish implementing
802 
803     Camera3StreamBufferListener::BufferInfo info =
804         Camera3StreamBufferListener::BufferInfo();
805     info.mOutput = output;
806     info.mError = (buffer.status == CAMERA3_BUFFER_STATUS_ERROR);
807     info.mFrameNumber = frameNumber;
808     info.mTimestamp = timestamp;
809     // TODO: rest of fields
810 
811     for (it = mBufferListenerList.begin(), end = mBufferListenerList.end();
812          it != end;
813          ++it) {
814 
815         sp<Camera3StreamBufferListener> listener = it->promote();
816         if (listener != 0) {
817             if (acquired) {
818                 listener->onBufferAcquired(info);
819             } else {
820                 listener->onBufferReleased(info);
821             }
822         }
823     }
824 }
825 
hasOutstandingBuffers() const826 bool Camera3Stream::hasOutstandingBuffers() const {
827     ATRACE_CALL();
828     Mutex::Autolock l(mLock);
829     return hasOutstandingBuffersLocked();
830 }
831 
getOutstandingBuffersCount() const832 size_t Camera3Stream::getOutstandingBuffersCount() const {
833     ATRACE_CALL();
834     Mutex::Autolock l(mLock);
835     return getHandoutOutputBufferCountLocked();
836 }
837 
setStatusTracker(sp<StatusTracker> statusTracker)838 status_t Camera3Stream::setStatusTracker(sp<StatusTracker> statusTracker) {
839     Mutex::Autolock l(mLock);
840     sp<StatusTracker> oldTracker = mStatusTracker.promote();
841     if (oldTracker != 0 && mStatusId != StatusTracker::NO_STATUS_ID) {
842         oldTracker->removeComponent(mStatusId);
843     }
844     mStatusId = StatusTracker::NO_STATUS_ID;
845     mStatusTracker = statusTracker;
846 
847     return OK;
848 }
849 
disconnect()850 status_t Camera3Stream::disconnect() {
851     ATRACE_CALL();
852     Mutex::Autolock l(mLock);
853     ALOGV("%s: Stream %d: Disconnecting...", __FUNCTION__, mId);
854     status_t res = disconnectLocked();
855 
856     mBufferLimitLatency.log("Stream %d latency histogram for wait on max_buffers", mId);
857     mBufferLimitLatency.reset();
858 
859     if (res == -ENOTCONN) {
860         // "Already disconnected" -- not an error
861         return OK;
862     } else {
863         return res;
864     }
865 }
866 
dump(int fd,const Vector<String16> & args) const867 void Camera3Stream::dump(int fd, const Vector<String16> &args) const
868 {
869     (void)args;
870     mBufferLimitLatency.dump(fd,
871             "      Latency histogram for wait on max_buffers");
872 }
873 
getBufferLocked(camera3_stream_buffer *,const std::vector<size_t> &)874 status_t Camera3Stream::getBufferLocked(camera3_stream_buffer *,
875         const std::vector<size_t>&) {
876     ALOGE("%s: This type of stream does not support output", __FUNCTION__);
877     return INVALID_OPERATION;
878 }
returnBufferLocked(const camera3_stream_buffer &,nsecs_t,const std::vector<size_t> &)879 status_t Camera3Stream::returnBufferLocked(const camera3_stream_buffer &,
880                                            nsecs_t, const std::vector<size_t>&) {
881     ALOGE("%s: This type of stream does not support output", __FUNCTION__);
882     return INVALID_OPERATION;
883 }
getInputBufferLocked(camera3_stream_buffer *)884 status_t Camera3Stream::getInputBufferLocked(camera3_stream_buffer *) {
885     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
886     return INVALID_OPERATION;
887 }
returnInputBufferLocked(const camera3_stream_buffer &)888 status_t Camera3Stream::returnInputBufferLocked(
889         const camera3_stream_buffer &) {
890     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
891     return INVALID_OPERATION;
892 }
getInputBufferProducerLocked(sp<IGraphicBufferProducer> *)893 status_t Camera3Stream::getInputBufferProducerLocked(sp<IGraphicBufferProducer>*) {
894     ALOGE("%s: This type of stream does not support input", __FUNCTION__);
895     return INVALID_OPERATION;
896 }
897 
addBufferListener(wp<Camera3StreamBufferListener> listener)898 void Camera3Stream::addBufferListener(
899         wp<Camera3StreamBufferListener> listener) {
900     Mutex::Autolock l(mLock);
901 
902     List<wp<Camera3StreamBufferListener> >::iterator it, end;
903     for (it = mBufferListenerList.begin(), end = mBufferListenerList.end();
904          it != end;
905          ) {
906         if (*it == listener) {
907             ALOGE("%s: Try to add the same listener twice, ignoring...", __FUNCTION__);
908             return;
909         }
910         it++;
911     }
912 
913     mBufferListenerList.push_back(listener);
914 }
915 
removeBufferListener(const sp<Camera3StreamBufferListener> & listener)916 void Camera3Stream::removeBufferListener(
917         const sp<Camera3StreamBufferListener>& listener) {
918     Mutex::Autolock l(mLock);
919 
920     bool erased = true;
921     List<wp<Camera3StreamBufferListener> >::iterator it, end;
922     for (it = mBufferListenerList.begin(), end = mBufferListenerList.end();
923          it != end;
924          ) {
925 
926         if (*it == listener) {
927             it = mBufferListenerList.erase(it);
928             erased = true;
929         } else {
930             ++it;
931         }
932     }
933 
934     if (!erased) {
935         ALOGW("%s: Could not find listener to remove, already removed",
936               __FUNCTION__);
937     }
938 }
939 
setBufferFreedListener(wp<Camera3StreamBufferFreedListener> listener)940 void Camera3Stream::setBufferFreedListener(
941         wp<Camera3StreamBufferFreedListener> listener) {
942     Mutex::Autolock l(mLock);
943     // Only allow set listener during stream configuration because stream is guaranteed to be IDLE
944     // at this state, so setBufferFreedListener won't collide with onBufferFreed callbacks
945     if (mState != STATE_IN_CONFIG && mState != STATE_IN_RECONFIG) {
946         ALOGE("%s: listener must be set during stream configuration!",__FUNCTION__);
947         return;
948     }
949     mBufferFreedListener = listener;
950 }
951 
952 }; // namespace camera3
953 
954 }; // namespace android
955