1 /* 2 * Copyright (C) 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-CompositeStream" 18 #define ATRACE_TAG ATRACE_TAG_CAMERA 19 //#define LOG_NDEBUG 0 20 21 #include <utils/Log.h> 22 #include <utils/Trace.h> 23 24 #include "common/CameraDeviceBase.h" 25 #include "CameraDeviceClient.h" 26 #include "CompositeStream.h" 27 28 namespace android { 29 namespace camera3 { 30 31 CompositeStream::CompositeStream(wp<CameraDeviceBase> device, 32 wp<hardware::camera2::ICameraDeviceCallbacks> cb) : 33 mDevice(device), 34 mRemoteCallback(cb), 35 mNumPartialResults(1), 36 mErrorState(false) { 37 sp<CameraDeviceBase> cameraDevice = device.promote(); 38 if (cameraDevice.get() != nullptr) { 39 CameraMetadata staticInfo = cameraDevice->info(); 40 camera_metadata_entry_t entry = staticInfo.find(ANDROID_REQUEST_PARTIAL_RESULT_COUNT); 41 if (entry.count > 0) { 42 mNumPartialResults = entry.data.i32[0]; 43 } 44 } 45 } 46 47 status_t CompositeStream::createStream(const std::vector<sp<Surface>>& consumers, 48 bool hasDeferredConsumer, uint32_t width, uint32_t height, int format, 49 camera3_stream_rotation_t rotation, int * id, const String8& physicalCameraId, 50 std::vector<int> * surfaceIds, int streamSetId, bool isShared) { 51 if (hasDeferredConsumer) { 52 ALOGE("%s: Deferred consumers not supported in case of composite streams!", 53 __FUNCTION__); 54 return BAD_VALUE; 55 } 56 57 if (streamSetId != camera3::CAMERA3_STREAM_ID_INVALID) { 58 ALOGE("%s: Surface groups not supported in case of composite streams!", 59 __FUNCTION__); 60 return BAD_VALUE; 61 } 62 63 if (isShared) { 64 ALOGE("%s: Shared surfaces not supported in case of composite streams!", 65 __FUNCTION__); 66 return BAD_VALUE; 67 } 68 69 return createInternalStreams(consumers, hasDeferredConsumer, width, height, format, rotation, id, 70 physicalCameraId, surfaceIds, streamSetId, isShared); 71 } 72 73 status_t CompositeStream::deleteStream() { 74 { 75 Mutex::Autolock l(mMutex); 76 mPendingCaptureResults.clear(); 77 mCaptureResults.clear(); 78 mFrameNumberMap.clear(); 79 mErrorFrameNumbers.clear(); 80 } 81 82 return deleteInternalStreams(); 83 } 84 85 void CompositeStream::onBufferRequestForFrameNumber(uint64_t frameNumber, int streamId, 86 const CameraMetadata& /*settings*/) { 87 Mutex::Autolock l(mMutex); 88 if (!mErrorState && (streamId == getStreamId())) { 89 mPendingCaptureResults.emplace(frameNumber, CameraMetadata()); 90 } 91 } 92 93 void CompositeStream::onBufferReleased(const BufferInfo& bufferInfo) { 94 Mutex::Autolock l(mMutex); 95 if (!mErrorState && !bufferInfo.mError) { 96 mFrameNumberMap.emplace(bufferInfo.mFrameNumber, bufferInfo.mTimestamp); 97 mInputReadyCondition.signal(); 98 } 99 } 100 101 void CompositeStream::eraseResult(int64_t frameNumber) { 102 Mutex::Autolock l(mMutex); 103 104 auto it = mPendingCaptureResults.find(frameNumber); 105 if (it == mPendingCaptureResults.end()) { 106 return; 107 } 108 109 it = mPendingCaptureResults.erase(it); 110 } 111 112 void CompositeStream::onResultAvailable(const CaptureResult& result) { 113 bool resultError = false; 114 { 115 Mutex::Autolock l(mMutex); 116 117 uint64_t frameNumber = result.mResultExtras.frameNumber; 118 bool resultReady = false; 119 auto it = mPendingCaptureResults.find(frameNumber); 120 if (it != mPendingCaptureResults.end()) { 121 it->second.append(result.mMetadata); 122 if (result.mResultExtras.partialResultCount >= mNumPartialResults) { 123 auto entry = it->second.find(ANDROID_SENSOR_TIMESTAMP); 124 if (entry.count == 1) { 125 auto ts = entry.data.i64[0]; 126 mCaptureResults.emplace(ts, std::make_tuple(frameNumber, it->second)); 127 resultReady = true; 128 } else { 129 ALOGE("%s: Timestamp metadata entry missing for frameNumber: %" PRIu64, 130 __FUNCTION__, frameNumber); 131 resultError = true; 132 } 133 mPendingCaptureResults.erase(it); 134 } 135 } 136 137 if (resultReady) { 138 mInputReadyCondition.signal(); 139 } 140 } 141 142 if (resultError) { 143 onResultError(result.mResultExtras); 144 } 145 } 146 147 void CompositeStream::flagAnErrorFrameNumber(int64_t frameNumber) { 148 Mutex::Autolock l(mMutex); 149 mErrorFrameNumbers.emplace(frameNumber); 150 mInputReadyCondition.signal(); 151 } 152 153 status_t CompositeStream::registerCompositeStreamListener(int32_t streamId) { 154 sp<CameraDeviceBase> device = mDevice.promote(); 155 if (device.get() == nullptr) { 156 return NO_INIT; 157 } 158 159 auto ret = device->addBufferListenerForStream(streamId, this); 160 if (ret != OK) { 161 ALOGE("%s: Failed to register composite stream listener!", __FUNCTION__); 162 } 163 164 return ret; 165 } 166 167 bool CompositeStream::onError(int32_t errorCode, const CaptureResultExtras& resultExtras) { 168 auto ret = false; 169 switch (errorCode) { 170 case hardware::camera2::ICameraDeviceCallbacks::ERROR_CAMERA_RESULT: 171 onResultError(resultExtras); 172 break; 173 case hardware::camera2::ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER: 174 ret = onStreamBufferError(resultExtras); 175 break; 176 case hardware::camera2::ICameraDeviceCallbacks::ERROR_CAMERA_REQUEST: 177 // Invalid request, this shouldn't affect composite streams. 178 break; 179 default: 180 ALOGE("%s: Unrecoverable error: %d detected!", __FUNCTION__, errorCode); 181 Mutex::Autolock l(mMutex); 182 mErrorState = true; 183 break; 184 } 185 186 return ret; 187 } 188 189 void CompositeStream::notifyError(int64_t frameNumber) { 190 sp<hardware::camera2::ICameraDeviceCallbacks> remoteCb = 191 mRemoteCallback.promote(); 192 193 if ((frameNumber >= 0) && (remoteCb.get() != nullptr)) { 194 CaptureResultExtras extras; 195 extras.errorStreamId = getStreamId(); 196 extras.frameNumber = frameNumber; 197 remoteCb->onDeviceError( 198 hardware::camera2::ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER, 199 extras); 200 } 201 } 202 203 }; // namespace camera3 204 }; // namespace android 205