blob: 8bdb6d4e416dd749a0c879ca70af156b429d5034 [file] [log] [blame]
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001/*
2 * Copyright (C) 2015 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_NDEBUG 0
18#define LOG_TAG "ACameraDevice"
19
Yin-Chia Yehead91462016-01-06 16:45:08 -080020#include <vector>
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080021#include <inttypes.h>
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -080022#include <android/hardware/ICameraService.h>
Yin-Chia Yehead91462016-01-06 16:45:08 -080023#include <gui/Surface.h>
Austin Borger1c1bee02023-06-01 16:51:35 -070024#include <camera/StringUtils.h>
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080025#include "ACameraDevice.h"
26#include "ACameraMetadata.h"
27#include "ACaptureRequest.h"
Yin-Chia Yehead91462016-01-06 16:45:08 -080028#include "ACameraCaptureSession.h"
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080029
Jayant Chowdharya8488c92019-06-21 12:45:34 -070030ACameraDevice::~ACameraDevice() {
Jayant Chowdharya8bf1c62019-09-26 08:50:17 -070031 mDevice->stopLooperAndDisconnect();
Jayant Chowdharya8488c92019-06-21 12:45:34 -070032}
33
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080034namespace android {
Jayant Chowdhary6df26072018-11-06 23:55:12 -080035namespace acam {
36
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080037// Static member definitions
Yin-Chia Yehead91462016-01-06 16:45:08 -080038const char* CameraDevice::kContextKey = "Context";
39const char* CameraDevice::kDeviceKey = "Device";
40const char* CameraDevice::kErrorCodeKey = "ErrorCode";
41const char* CameraDevice::kCallbackFpKey = "Callback";
42const char* CameraDevice::kSessionSpKey = "SessionSp";
43const char* CameraDevice::kCaptureRequestKey = "CaptureRequest";
44const char* CameraDevice::kTimeStampKey = "TimeStamp";
45const char* CameraDevice::kCaptureResultKey = "CaptureResult";
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -080046const char* CameraDevice::kPhysicalCaptureResultKey = "PhysicalCaptureResult";
Yin-Chia Yehead91462016-01-06 16:45:08 -080047const char* CameraDevice::kCaptureFailureKey = "CaptureFailure";
48const char* CameraDevice::kSequenceIdKey = "SequenceId";
49const char* CameraDevice::kFrameNumberKey = "FrameNumber";
Yin-Chia Yehe081c592016-03-29 18:26:44 -070050const char* CameraDevice::kAnwKey = "Anw";
Emilian Peevedec62d2019-03-19 17:59:24 -070051const char* CameraDevice::kFailingPhysicalCameraId= "FailingPhysicalCameraId";
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080052
53/**
54 * CameraDevice Implementation
55 */
56CameraDevice::CameraDevice(
57 const char* id,
58 ACameraDevice_StateCallbacks* cb,
Yin-Chia Yehdd045bf2018-08-20 12:39:19 -070059 sp<ACameraMetadata> chars,
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080060 ACameraDevice* wrapper) :
61 mCameraId(id),
62 mAppCallbacks(*cb),
Yin-Chia Yehdd045bf2018-08-20 12:39:19 -070063 mChars(chars),
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080064 mServiceCallback(new ServiceCallback(this)),
65 mWrapper(wrapper),
66 mInError(false),
67 mError(ACAMERA_OK),
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -070068 mIdle(true),
69 mCurrentSession(nullptr) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080070 mClosing = false;
71 // Setup looper thread to perfrom device callbacks to app
72 mCbLooper = new ALooper;
73 mCbLooper->setName("C2N-dev-looper");
Eino-Ville Talvala02bf0322016-02-18 12:41:10 -080074 status_t err = mCbLooper->start(
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080075 /*runOnCallingThread*/false,
76 /*canCallJava*/ true,
Yin-Chia Yehead91462016-01-06 16:45:08 -080077 PRIORITY_DEFAULT);
Eino-Ville Talvala02bf0322016-02-18 12:41:10 -080078 if (err != OK) {
79 ALOGE("%s: Unable to start camera device callback looper: %s (%d)",
80 __FUNCTION__, strerror(-err), err);
81 setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_DEVICE);
82 }
Shuzhen Wang6c17e212019-02-19 14:51:47 -080083 mHandler = new CallbackHandler(id);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -080084 mCbLooper->registerHandler(mHandler);
Yin-Chia Yehead91462016-01-06 16:45:08 -080085
Yin-Chia Yeh8aac03f2016-03-03 15:45:23 -080086 const CameraMetadata& metadata = mChars->getInternalData();
87 camera_metadata_ro_entry entry = metadata.find(ANDROID_REQUEST_PARTIAL_RESULT_COUNT);
Yin-Chia Yehead91462016-01-06 16:45:08 -080088 if (entry.count != 1) {
89 ALOGW("%s: bad count %zu for partial result count", __FUNCTION__, entry.count);
90 mPartialResultCount = 1;
91 } else {
92 mPartialResultCount = entry.data.i32[0];
93 }
94
95 entry = metadata.find(ANDROID_LENS_INFO_SHADING_MAP_SIZE);
96 if (entry.count != 2) {
97 ALOGW("%s: bad count %zu for shading map size", __FUNCTION__, entry.count);
98 mShadingMapSize[0] = 0;
99 mShadingMapSize[1] = 0;
100 } else {
101 mShadingMapSize[0] = entry.data.i32[0];
102 mShadingMapSize[1] = entry.data.i32[1];
103 }
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800104
105 size_t physicalIdCnt = 0;
106 const char*const* physicalCameraIds;
107 if (mChars->isLogicalMultiCamera(&physicalIdCnt, &physicalCameraIds)) {
108 for (size_t i = 0; i < physicalIdCnt; i++) {
109 mPhysicalIds.push_back(physicalCameraIds[i]);
110 }
111 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800112}
113
Jayant Chowdharya8bf1c62019-09-26 08:50:17 -0700114CameraDevice::~CameraDevice() { }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800115
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700116void
117CameraDevice::postSessionMsgAndCleanup(sp<AMessage>& msg) {
118 msg->post();
119 msg.clear();
120 sp<AMessage> cleanupMsg = new AMessage(kWhatCleanUpSessions, mHandler);
121 cleanupMsg->post();
122}
123
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800124// TODO: cached created request?
125camera_status_t
126CameraDevice::createCaptureRequest(
127 ACameraDevice_request_template templateId,
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800128 const ACameraIdList* physicalIdList,
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800129 ACaptureRequest** request) const {
130 Mutex::Autolock _l(mDeviceLock);
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800131
132 if (physicalIdList != nullptr) {
133 if (physicalIdList->numCameras > static_cast<int>(mPhysicalIds.size())) {
134 ALOGE("%s: physicalIdList size %d exceeds number of available physical cameras %zu",
135 __FUNCTION__, physicalIdList->numCameras, mPhysicalIds.size());
136 return ACAMERA_ERROR_INVALID_PARAMETER;
137 }
138 for (auto i = 0; i < physicalIdList->numCameras; i++) {
139 if (physicalIdList->cameraIds[i] == nullptr) {
140 ALOGE("%s: physicalId is null!", __FUNCTION__);
141 return ACAMERA_ERROR_INVALID_PARAMETER;
142 }
143 if (mPhysicalIds.end() == std::find(
144 mPhysicalIds.begin(), mPhysicalIds.end(), physicalIdList->cameraIds[i])) {
145 ALOGE("%s: Invalid physicalId %s!", __FUNCTION__, physicalIdList->cameraIds[i]);
146 return ACAMERA_ERROR_INVALID_PARAMETER;
147 }
148 }
149 }
150
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800151 camera_status_t ret = checkCameraClosedOrErrorLocked();
152 if (ret != ACAMERA_OK) {
153 return ret;
154 }
155 if (mRemote == nullptr) {
156 return ACAMERA_ERROR_CAMERA_DISCONNECTED;
157 }
158 CameraMetadata rawRequest;
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800159 binder::Status remoteRet = mRemote->createDefaultRequest(templateId, &rawRequest);
160 if (remoteRet.serviceSpecificErrorCode() ==
161 hardware::ICameraService::ERROR_ILLEGAL_ARGUMENT) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800162 ALOGW("Create capture request failed! template %d is not supported on this device",
163 templateId);
Yin-Chia Yeha22528a2016-05-12 14:03:11 -0700164 return ACAMERA_ERROR_INVALID_PARAMETER;
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800165 } else if (!remoteRet.isOk()) {
166 ALOGE("Create capture request failed: %s", remoteRet.toString8().string());
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800167 return ACAMERA_ERROR_UNKNOWN;
168 }
169 ACaptureRequest* outReq = new ACaptureRequest();
170 outReq->settings = new ACameraMetadata(rawRequest.release(), ACameraMetadata::ACM_REQUEST);
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800171 if (physicalIdList != nullptr) {
172 for (auto i = 0; i < physicalIdList->numCameras; i++) {
173 outReq->physicalSettings.emplace(physicalIdList->cameraIds[i],
174 new ACameraMetadata(*(outReq->settings)));
175 }
176 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800177 outReq->targets = new ACameraOutputTargets();
178 *request = outReq;
179 return ACAMERA_OK;
180}
181
Yin-Chia Yehead91462016-01-06 16:45:08 -0800182camera_status_t
183CameraDevice::createCaptureSession(
184 const ACaptureSessionOutputContainer* outputs,
Emilian Peev5fbe0ba2017-10-20 15:45:45 +0100185 const ACaptureRequest* sessionParameters,
Yin-Chia Yehead91462016-01-06 16:45:08 -0800186 const ACameraCaptureSession_stateCallbacks* callbacks,
187 /*out*/ACameraCaptureSession** session) {
Shuzhen Wang316781a2020-08-18 18:11:01 -0700188 nsecs_t startTimeNs = systemTime();
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700189 sp<ACameraCaptureSession> currentSession = mCurrentSession.promote();
Yin-Chia Yehead91462016-01-06 16:45:08 -0800190 Mutex::Autolock _l(mDeviceLock);
191 camera_status_t ret = checkCameraClosedOrErrorLocked();
192 if (ret != ACAMERA_OK) {
193 return ret;
194 }
195
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700196 if (currentSession != nullptr) {
197 currentSession->closeByDevice();
Yin-Chia Yehead91462016-01-06 16:45:08 -0800198 stopRepeatingLocked();
199 }
200
201 // Create new session
Shuzhen Wang316781a2020-08-18 18:11:01 -0700202 ret = configureStreamsLocked(outputs, sessionParameters, startTimeNs);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800203 if (ret != ACAMERA_OK) {
204 ALOGE("Fail to create new session. cannot configure streams");
205 return ret;
206 }
207
208 ACameraCaptureSession* newSession = new ACameraCaptureSession(
209 mNextSessionId++, outputs, callbacks, this);
210
Yin-Chia Yehead91462016-01-06 16:45:08 -0800211 // set new session as current session
212 newSession->incStrong((void *) ACameraDevice_createCaptureSession);
213 mCurrentSession = newSession;
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -0700214 mFlushing = false;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800215 *session = newSession;
216 return ACAMERA_OK;
217}
218
Shuzhen Wang24810e72019-03-18 10:55:01 -0700219camera_status_t CameraDevice::isSessionConfigurationSupported(
220 const ACaptureSessionOutputContainer* sessionOutputContainer) const {
221 Mutex::Autolock _l(mDeviceLock);
222 camera_status_t ret = checkCameraClosedOrErrorLocked();
223 if (ret != ACAMERA_OK) {
224 return ret;
225 }
226
227 SessionConfiguration sessionConfiguration(0 /*inputWidth*/, 0 /*inputHeight*/,
228 -1 /*inputFormat*/, CAMERA3_STREAM_CONFIGURATION_NORMAL_MODE);
229 for (const auto& output : sessionOutputContainer->mOutputs) {
230 sp<IGraphicBufferProducer> iGBP(nullptr);
231 ret = getIGBPfromAnw(output.mWindow, iGBP);
232 if (ret != ACAMERA_OK) {
233 ALOGE("Camera device %s failed to extract graphic producer from native window",
234 getId());
235 return ret;
236 }
237
Austin Borger1c1bee02023-06-01 16:51:35 -0700238 OutputConfiguration outConfig(iGBP, output.mRotation, output.mPhysicalCameraId,
Shuzhen Wang24810e72019-03-18 10:55:01 -0700239 OutputConfiguration::INVALID_SET_ID, true);
240
241 for (auto& anw : output.mSharedWindows) {
242 ret = getIGBPfromAnw(anw, iGBP);
243 if (ret != ACAMERA_OK) {
244 ALOGE("Camera device %s failed to extract graphic producer from native window",
245 getId());
246 return ret;
247 }
248 outConfig.addGraphicProducer(iGBP);
249 }
250
251 sessionConfiguration.addOutputConfiguration(outConfig);
252 }
253
254 bool supported = false;
255 binder::Status remoteRet = mRemote->isSessionConfigurationSupported(
256 sessionConfiguration, &supported);
257 if (remoteRet.serviceSpecificErrorCode() ==
258 hardware::ICameraService::ERROR_INVALID_OPERATION) {
259 return ACAMERA_ERROR_UNSUPPORTED_OPERATION;
260 } else if (!remoteRet.isOk()) {
261 return ACAMERA_ERROR_UNKNOWN;
262 } else {
263 return supported ? ACAMERA_OK : ACAMERA_ERROR_STREAM_CONFIGURE_FAIL;
264 }
265}
266
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800267camera_status_t CameraDevice::updateOutputConfigurationLocked(ACaptureSessionOutput *output) {
Emilian Peev40ead602017-09-26 15:46:36 +0100268 camera_status_t ret = checkCameraClosedOrErrorLocked();
269 if (ret != ACAMERA_OK) {
270 return ret;
271 }
272
273 if (output == nullptr) {
274 return ACAMERA_ERROR_INVALID_PARAMETER;
275 }
276
277 if (!output->mIsShared) {
278 ALOGE("Error output configuration is not shared");
279 return ACAMERA_ERROR_INVALID_OPERATION;
280 }
281
282 int32_t streamId = -1;
283 for (auto& kvPair : mConfiguredOutputs) {
284 if (kvPair.second.first == output->mWindow) {
285 streamId = kvPair.first;
286 break;
287 }
288 }
289 if (streamId < 0) {
290 ALOGE("Error: Invalid output configuration");
291 return ACAMERA_ERROR_INVALID_PARAMETER;
292 }
293
294 sp<IGraphicBufferProducer> iGBP(nullptr);
295 ret = getIGBPfromAnw(output->mWindow, iGBP);
296 if (ret != ACAMERA_OK) {
297 ALOGE("Camera device %s failed to extract graphic producer from native window",
298 getId());
299 return ret;
300 }
301
Austin Borger1c1bee02023-06-01 16:51:35 -0700302 OutputConfiguration outConfig(iGBP, output->mRotation, output->mPhysicalCameraId,
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800303 OutputConfiguration::INVALID_SET_ID, true);
Emilian Peev40ead602017-09-26 15:46:36 +0100304
305 for (auto& anw : output->mSharedWindows) {
306 ret = getIGBPfromAnw(anw, iGBP);
307 if (ret != ACAMERA_OK) {
308 ALOGE("Camera device %s failed to extract graphic producer from native window",
309 getId());
310 return ret;
311 }
312 outConfig.addGraphicProducer(iGBP);
313 }
314
315 auto remoteRet = mRemote->updateOutputConfiguration(streamId, outConfig);
316 if (!remoteRet.isOk()) {
317 switch (remoteRet.serviceSpecificErrorCode()) {
318 case hardware::ICameraService::ERROR_INVALID_OPERATION:
319 ALOGE("Camera device %s invalid operation: %s", getId(),
320 remoteRet.toString8().string());
321 return ACAMERA_ERROR_INVALID_OPERATION;
322 break;
323 case hardware::ICameraService::ERROR_ALREADY_EXISTS:
324 ALOGE("Camera device %s output surface already exists: %s", getId(),
325 remoteRet.toString8().string());
326 return ACAMERA_ERROR_INVALID_PARAMETER;
327 break;
328 case hardware::ICameraService::ERROR_ILLEGAL_ARGUMENT:
329 ALOGE("Camera device %s invalid input argument: %s", getId(),
330 remoteRet.toString8().string());
331 return ACAMERA_ERROR_INVALID_PARAMETER;
332 break;
333 default:
334 ALOGE("Camera device %s failed to add shared output: %s", getId(),
335 remoteRet.toString8().string());
336 return ACAMERA_ERROR_UNKNOWN;
337 }
338 }
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800339 mConfiguredOutputs[streamId] = std::make_pair(output->mWindow, outConfig);
Emilian Peev40ead602017-09-26 15:46:36 +0100340
341 return ACAMERA_OK;
342}
343
Jayant Chowdhary09b368b2023-02-13 06:53:05 +0000344camera_status_t CameraDevice::prepareLocked(ACameraWindowType *window) {
345 camera_status_t ret = checkCameraClosedOrErrorLocked();
346 if (ret != ACAMERA_OK) {
347 return ret;
348 }
349
350 if (window == nullptr) {
351 return ACAMERA_ERROR_INVALID_PARAMETER;
352 }
353
354 int32_t streamId = -1;
355 for (auto& kvPair : mConfiguredOutputs) {
356 if (window == kvPair.second.first) {
357 streamId = kvPair.first;
358 break;
359 }
360 }
361 if (streamId < 0) {
362 ALOGE("Error: Invalid output configuration");
363 return ACAMERA_ERROR_INVALID_PARAMETER;
364 }
365 auto remoteRet = mRemote->prepare(streamId);
366 if (!remoteRet.isOk()) {
367 // TODO:(b/259735869) Do this check for all other binder calls in the
368 // ndk as well.
369 if (remoteRet.exceptionCode() != EX_SERVICE_SPECIFIC) {
370 ALOGE("Camera device %s failed to prepare output window %p: %s", getId(), window,
371 remoteRet.toString8().string());
372 return ACAMERA_ERROR_UNKNOWN;
373
374 }
375 switch (remoteRet.serviceSpecificErrorCode()) {
376 case hardware::ICameraService::ERROR_INVALID_OPERATION:
377 ALOGE("Camera device %s invalid operation: %s", getId(),
378 remoteRet.toString8().string());
379 return ACAMERA_ERROR_INVALID_OPERATION;
380 break;
381 case hardware::ICameraService::ERROR_ILLEGAL_ARGUMENT:
382 ALOGE("Camera device %s invalid input argument: %s", getId(),
383 remoteRet.toString8().string());
384 return ACAMERA_ERROR_INVALID_PARAMETER;
385 break;
386 default:
387 ALOGE("Camera device %s failed to prepare output window %p: %s", getId(), window,
388 remoteRet.toString8().string());
389 return ACAMERA_ERROR_UNKNOWN;
390 }
391 }
392
393 return ACAMERA_OK;
394}
395
Yin-Chia Yehead91462016-01-06 16:45:08 -0800396camera_status_t
397CameraDevice::allocateCaptureRequest(
398 const ACaptureRequest* request, /*out*/sp<CaptureRequest>& outReq) {
399 camera_status_t ret;
400 sp<CaptureRequest> req(new CaptureRequest());
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800401 req->mPhysicalCameraSettings.push_back({getId(),
Emilian Peevaebbe412018-01-15 13:53:24 +0000402 request->settings->getInternalData()});
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800403 for (auto& entry : request->physicalSettings) {
404 req->mPhysicalCameraSettings.push_back({entry.first,
405 entry.second->getInternalData()});
406 }
Yin-Chia Yehead91462016-01-06 16:45:08 -0800407 req->mIsReprocess = false; // NDK does not support reprocessing yet
Yin-Chia Yehd39b9e32017-10-30 17:39:23 -0700408 req->mContext = request->context;
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800409 req->mSurfaceConverted = true; // set to true, and fill in stream/surface idx to speed up IPC
Yin-Chia Yehead91462016-01-06 16:45:08 -0800410
411 for (auto outputTarget : request->targets->mOutputs) {
412 ANativeWindow* anw = outputTarget.mWindow;
413 sp<Surface> surface;
414 ret = getSurfaceFromANativeWindow(anw, surface);
415 if (ret != ACAMERA_OK) {
416 ALOGE("Bad output target in capture request! ret %d", ret);
417 return ret;
418 }
419 req->mSurfaceList.push_back(surface);
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800420
421 bool found = false;
422 // lookup stream/surface ID
423 for (const auto& kvPair : mConfiguredOutputs) {
424 int streamId = kvPair.first;
425 const OutputConfiguration& outConfig = kvPair.second.second;
426 const auto& gbps = outConfig.getGraphicBufferProducers();
427 for (int surfaceId = 0; surfaceId < (int) gbps.size(); surfaceId++) {
428 if (gbps[surfaceId] == surface->getIGraphicBufferProducer()) {
429 found = true;
430 req->mStreamIdxList.push_back(streamId);
431 req->mSurfaceIdxList.push_back(surfaceId);
432 break;
433 }
434 }
435 if (found) {
436 break;
437 }
438 }
439 if (!found) {
440 ALOGE("Unconfigured output target %p in capture request!", anw);
441 return ret;
442 }
Yin-Chia Yehead91462016-01-06 16:45:08 -0800443 }
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800444
Yin-Chia Yehead91462016-01-06 16:45:08 -0800445 outReq = req;
446 return ACAMERA_OK;
447}
448
449ACaptureRequest*
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800450CameraDevice::allocateACaptureRequest(sp<CaptureRequest>& req, const std::string& deviceId) {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800451 ACaptureRequest* pRequest = new ACaptureRequest();
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800452 for (auto& entry : req->mPhysicalCameraSettings) {
453 CameraMetadata clone = entry.settings;
454 if (entry.id == deviceId) {
455 pRequest->settings = new ACameraMetadata(clone.release(), ACameraMetadata::ACM_REQUEST);
456 } else {
457 pRequest->physicalSettings.emplace(entry.id,
458 new ACameraMetadata(clone.release(), ACameraMetadata::ACM_REQUEST));
459 }
460 }
Yin-Chia Yehead91462016-01-06 16:45:08 -0800461 pRequest->targets = new ACameraOutputTargets();
462 for (size_t i = 0; i < req->mSurfaceList.size(); i++) {
463 ANativeWindow* anw = static_cast<ANativeWindow*>(req->mSurfaceList[i].get());
464 ACameraOutputTarget outputTarget(anw);
465 pRequest->targets->mOutputs.insert(outputTarget);
466 }
Yin-Chia Yehd39b9e32017-10-30 17:39:23 -0700467 pRequest->context = req->mContext;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800468 return pRequest;
469}
470
471void
472CameraDevice::freeACaptureRequest(ACaptureRequest* req) {
473 if (req == nullptr) {
474 return;
475 }
Yin-Chia Yehdd045bf2018-08-20 12:39:19 -0700476 req->settings.clear();
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800477 req->physicalSettings.clear();
Yin-Chia Yehead91462016-01-06 16:45:08 -0800478 delete req->targets;
479 delete req;
480}
481
482void
483CameraDevice::notifySessionEndOfLifeLocked(ACameraCaptureSession* session) {
484 if (isClosed()) {
485 // Device is closing already. do nothing
486 return;
487 }
488
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700489 if (mCurrentSession != session) {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800490 // Session has been replaced by other seesion or device is closed
491 return;
492 }
493 mCurrentSession = nullptr;
494
495 // Should not happen
496 if (!session->mIsClosed) {
497 ALOGE("Error: unclosed session %p reaches end of life!", session);
498 setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_DEVICE);
499 return;
500 }
501
502 // No new session, unconfigure now
Shuzhen Wang316781a2020-08-18 18:11:01 -0700503 // Note: The unconfiguration of session won't be accounted for session
504 // latency because a stream configuration with 0 streams won't ever become
505 // active.
506 nsecs_t startTimeNs = systemTime();
507 camera_status_t ret = configureStreamsLocked(nullptr, nullptr, startTimeNs);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800508 if (ret != ACAMERA_OK) {
509 ALOGE("Unconfigure stream failed. Device might still be configured! ret %d", ret);
510 }
511}
512
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800513void
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700514CameraDevice::disconnectLocked(sp<ACameraCaptureSession>& session) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800515 if (mClosing.exchange(true)) {
516 // Already closing, just return
517 ALOGW("Camera device %s is already closing.", getId());
518 return;
519 }
520
521 if (mRemote != nullptr) {
522 mRemote->disconnect();
523 }
524 mRemote = nullptr;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800525
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700526 if (session != nullptr) {
527 session->closeByDevice();
Yin-Chia Yehead91462016-01-06 16:45:08 -0800528 }
529}
530
531camera_status_t
532CameraDevice::stopRepeatingLocked() {
533 camera_status_t ret = checkCameraClosedOrErrorLocked();
534 if (ret != ACAMERA_OK) {
535 ALOGE("Camera %s stop repeating failed! ret %d", getId(), ret);
536 return ret;
537 }
538 if (mRepeatingSequenceId != REQUEST_ID_NONE) {
539 int repeatingSequenceId = mRepeatingSequenceId;
540 mRepeatingSequenceId = REQUEST_ID_NONE;
541
542 int64_t lastFrameNumber;
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800543 binder::Status remoteRet = mRemote->cancelRequest(repeatingSequenceId, &lastFrameNumber);
Chien-Yu Chene8c535e2016-04-14 12:18:26 -0700544 if (remoteRet.serviceSpecificErrorCode() ==
545 hardware::ICameraService::ERROR_ILLEGAL_ARGUMENT) {
546 ALOGV("Repeating request is already stopped.");
547 return ACAMERA_OK;
548 } else if (!remoteRet.isOk()) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800549 ALOGE("Stop repeating request fails in remote: %s", remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800550 return ACAMERA_ERROR_UNKNOWN;
551 }
552 checkRepeatingSequenceCompleteLocked(repeatingSequenceId, lastFrameNumber);
553 }
554 return ACAMERA_OK;
555}
556
557camera_status_t
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -0700558CameraDevice::flushLocked(ACameraCaptureSession* session) {
559 camera_status_t ret = checkCameraClosedOrErrorLocked();
560 if (ret != ACAMERA_OK) {
561 ALOGE("Camera %s abort captures failed! ret %d", getId(), ret);
562 return ret;
563 }
564
565 // This should never happen because creating a new session will close
566 // previous one and thus reject any API call from previous session.
567 // But still good to check here in case something unexpected happen.
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700568 if (mCurrentSession != session) {
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -0700569 ALOGE("Camera %s session %p is not current active session!", getId(), session);
570 return ACAMERA_ERROR_INVALID_OPERATION;
571 }
572
573 if (mFlushing) {
574 ALOGW("Camera %s is already aborting captures", getId());
575 return ACAMERA_OK;
576 }
577
578 mFlushing = true;
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700579
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -0700580 // Send onActive callback to guarantee there is always active->ready transition
581 sp<AMessage> msg = new AMessage(kWhatSessionStateCb, mHandler);
582 msg->setPointer(kContextKey, session->mUserSessionCallback.context);
583 msg->setObject(kSessionSpKey, session);
584 msg->setPointer(kCallbackFpKey, (void*) session->mUserSessionCallback.onActive);
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700585 postSessionMsgAndCleanup(msg);
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -0700586
587 // If device is already idling, send callback and exit early
588 if (mIdle) {
589 sp<AMessage> msg = new AMessage(kWhatSessionStateCb, mHandler);
590 msg->setPointer(kContextKey, session->mUserSessionCallback.context);
591 msg->setObject(kSessionSpKey, session);
592 msg->setPointer(kCallbackFpKey, (void*) session->mUserSessionCallback.onReady);
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700593 postSessionMsgAndCleanup(msg);
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -0700594 mFlushing = false;
595 return ACAMERA_OK;
596 }
597
598 int64_t lastFrameNumber;
599 binder::Status remoteRet = mRemote->flush(&lastFrameNumber);
600 if (!remoteRet.isOk()) {
601 ALOGE("Abort captures fails in remote: %s", remoteRet.toString8().string());
602 return ACAMERA_ERROR_UNKNOWN;
603 }
604 if (mRepeatingSequenceId != REQUEST_ID_NONE) {
605 checkRepeatingSequenceCompleteLocked(mRepeatingSequenceId, lastFrameNumber);
606 }
607 return ACAMERA_OK;
608}
609
610camera_status_t
Yin-Chia Yehead91462016-01-06 16:45:08 -0800611CameraDevice::waitUntilIdleLocked() {
612 camera_status_t ret = checkCameraClosedOrErrorLocked();
613 if (ret != ACAMERA_OK) {
614 ALOGE("Wait until camera %s idle failed! ret %d", getId(), ret);
615 return ret;
616 }
617
618 if (mRepeatingSequenceId != REQUEST_ID_NONE) {
619 ALOGE("Camera device %s won't go to idle when there is repeating request!", getId());
620 return ACAMERA_ERROR_INVALID_OPERATION;
621 }
622
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800623 binder::Status remoteRet = mRemote->waitUntilIdle();
624 if (!remoteRet.isOk()) {
625 ALOGE("Camera device %s waitUntilIdle failed: %s", getId(), remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800626 // TODO: define a function to convert status_t -> camera_status_t
627 return ACAMERA_ERROR_UNKNOWN;
628 }
629
630 return ACAMERA_OK;
631}
632
633camera_status_t
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700634CameraDevice::getIGBPfromAnw(
635 ANativeWindow* anw,
Yin-Chia Yehead91462016-01-06 16:45:08 -0800636 sp<IGraphicBufferProducer>& out) {
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800637 sp<Surface> surface;
638 camera_status_t ret = getSurfaceFromANativeWindow(anw, surface);
639 if (ret != ACAMERA_OK) {
640 return ret;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800641 }
Yin-Chia Yehead91462016-01-06 16:45:08 -0800642 out = surface->getIGraphicBufferProducer();
643 return ACAMERA_OK;
644}
645
646camera_status_t
647CameraDevice::getSurfaceFromANativeWindow(
648 ANativeWindow* anw, sp<Surface>& out) {
649 if (anw == nullptr) {
650 ALOGE("Error: output ANativeWindow is null");
651 return ACAMERA_ERROR_INVALID_PARAMETER;
652 }
653 int value;
654 int err = (*anw->query)(anw, NATIVE_WINDOW_CONCRETE_TYPE, &value);
Eino-Ville Talvala02bf0322016-02-18 12:41:10 -0800655 if (err != OK || value != NATIVE_WINDOW_SURFACE) {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800656 ALOGE("Error: ANativeWindow is not backed by Surface!");
657 return ACAMERA_ERROR_INVALID_PARAMETER;
658 }
659 sp<Surface> surface(static_cast<Surface*>(anw));
660 out = surface;
661 return ACAMERA_OK;
662}
663
664camera_status_t
Emilian Peev5fbe0ba2017-10-20 15:45:45 +0100665CameraDevice::configureStreamsLocked(const ACaptureSessionOutputContainer* outputs,
Shuzhen Wang316781a2020-08-18 18:11:01 -0700666 const ACaptureRequest* sessionParameters, nsecs_t startTimeNs) {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800667 ACaptureSessionOutputContainer emptyOutput;
668 if (outputs == nullptr) {
669 outputs = &emptyOutput;
670 }
671
Yin-Chia Yehead91462016-01-06 16:45:08 -0800672 camera_status_t ret = checkCameraClosedOrErrorLocked();
673 if (ret != ACAMERA_OK) {
674 return ret;
675 }
676
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700677 std::set<std::pair<ANativeWindow*, OutputConfiguration>> outputSet;
Chih-Hung Hsieh3ef324d2018-12-11 11:48:12 -0800678 for (const auto& outConfig : outputs->mOutputs) {
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700679 ANativeWindow* anw = outConfig.mWindow;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800680 sp<IGraphicBufferProducer> iGBP(nullptr);
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700681 ret = getIGBPfromAnw(anw, iGBP);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800682 if (ret != ACAMERA_OK) {
683 return ret;
684 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700685 outputSet.insert(std::make_pair(
Austin Borger1c1bee02023-06-01 16:51:35 -0700686 anw, OutputConfiguration(iGBP, outConfig.mRotation, outConfig.mPhysicalCameraId,
Emilian Peev40ead602017-09-26 15:46:36 +0100687 OutputConfiguration::INVALID_SET_ID, outConfig.mIsShared)));
Yin-Chia Yehead91462016-01-06 16:45:08 -0800688 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700689 auto addSet = outputSet;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800690 std::vector<int> deleteList;
691
692 // Determine which streams need to be created, which to be deleted
693 for (auto& kvPair : mConfiguredOutputs) {
694 int streamId = kvPair.first;
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700695 auto& outputPair = kvPair.second;
696 if (outputSet.count(outputPair) == 0) {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800697 deleteList.push_back(streamId); // Need to delete a no longer needed stream
698 } else {
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700699 addSet.erase(outputPair); // No need to add already existing stream
Yin-Chia Yehead91462016-01-06 16:45:08 -0800700 }
701 }
702
703 ret = stopRepeatingLocked();
704 if (ret != ACAMERA_OK) {
705 ALOGE("Camera device %s stop repeating failed, ret %d", getId(), ret);
706 return ret;
707 }
708
709 ret = waitUntilIdleLocked();
710 if (ret != ACAMERA_OK) {
711 ALOGE("Camera device %s wait until idle failed, ret %d", getId(), ret);
712 return ret;
713 }
714
715 // Send onReady to previous session
716 // CurrentSession will be updated after configureStreamLocked, so here
717 // mCurrentSession is the session to be replaced by a new session
718 if (!mIdle && mCurrentSession != nullptr) {
719 if (mBusySession != mCurrentSession) {
720 ALOGE("Current session != busy session");
721 setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_DEVICE);
722 return ACAMERA_ERROR_CAMERA_DEVICE;
723 }
724 sp<AMessage> msg = new AMessage(kWhatSessionStateCb, mHandler);
725 msg->setPointer(kContextKey, mBusySession->mUserSessionCallback.context);
726 msg->setObject(kSessionSpKey, mBusySession);
727 msg->setPointer(kCallbackFpKey, (void*) mBusySession->mUserSessionCallback.onReady);
728 mBusySession.clear();
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700729 postSessionMsgAndCleanup(msg);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800730 }
731 mIdle = true;
732
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800733 binder::Status remoteRet = mRemote->beginConfigure();
734 if (!remoteRet.isOk()) {
735 ALOGE("Camera device %s begin configure failed: %s", getId(), remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800736 return ACAMERA_ERROR_UNKNOWN;
737 }
738
739 // delete to-be-deleted streams
740 for (auto streamId : deleteList) {
741 remoteRet = mRemote->deleteStream(streamId);
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800742 if (!remoteRet.isOk()) {
743 ALOGE("Camera device %s failed to remove stream %d: %s", getId(), streamId,
744 remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800745 return ACAMERA_ERROR_UNKNOWN;
746 }
747 mConfiguredOutputs.erase(streamId);
748 }
749
750 // add new streams
Chih-Hung Hsieh3ef324d2018-12-11 11:48:12 -0800751 for (const auto& outputPair : addSet) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800752 int streamId;
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700753 remoteRet = mRemote->createStream(outputPair.second, &streamId);
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800754 if (!remoteRet.isOk()) {
755 ALOGE("Camera device %s failed to create stream: %s", getId(),
756 remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800757 return ACAMERA_ERROR_UNKNOWN;
758 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700759 mConfiguredOutputs.insert(std::make_pair(streamId, outputPair));
Yin-Chia Yehead91462016-01-06 16:45:08 -0800760 }
761
Emilian Peev5fbe0ba2017-10-20 15:45:45 +0100762 CameraMetadata params;
763 if ((sessionParameters != nullptr) && (sessionParameters->settings != nullptr)) {
764 params.append(sessionParameters->settings->getInternalData());
765 }
Emilian Peevcc0b7952020-01-07 13:54:47 -0800766 std::vector<int> offlineStreamIds;
Shuzhen Wang316781a2020-08-18 18:11:01 -0700767 remoteRet = mRemote->endConfigure(/*isConstrainedHighSpeed*/ false, params,
768 ns2ms(startTimeNs), &offlineStreamIds);
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800769 if (remoteRet.serviceSpecificErrorCode() == hardware::ICameraService::ERROR_ILLEGAL_ARGUMENT) {
770 ALOGE("Camera device %s cannnot support app output configuration: %s", getId(),
771 remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800772 return ACAMERA_ERROR_STREAM_CONFIGURE_FAIL;
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800773 } else if (!remoteRet.isOk()) {
774 ALOGE("Camera device %s end configure failed: %s", getId(), remoteRet.toString8().string());
Yin-Chia Yehead91462016-01-06 16:45:08 -0800775 return ACAMERA_ERROR_UNKNOWN;
776 }
777
778 return ACAMERA_OK;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800779}
780
781void
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800782CameraDevice::setRemoteDevice(sp<hardware::camera2::ICameraDeviceUser> remote) {
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800783 Mutex::Autolock _l(mDeviceLock);
784 mRemote = remote;
785}
786
787camera_status_t
788CameraDevice::checkCameraClosedOrErrorLocked() const {
789 if (mRemote == nullptr) {
790 ALOGE("%s: camera device already closed", __FUNCTION__);
791 return ACAMERA_ERROR_CAMERA_DISCONNECTED;
792 }
793 if (mInError) {// triggered by onDeviceError
794 ALOGE("%s: camera device has encountered a serious error", __FUNCTION__);
795 return mError;
796 }
797 return ACAMERA_OK;
798}
799
800void
Yin-Chia Yehead91462016-01-06 16:45:08 -0800801CameraDevice::setCameraDeviceErrorLocked(camera_status_t error) {
802 mInError = true;
803 mError = error;
804 return;
805}
806
807void
808CameraDevice::FrameNumberTracker::updateTracker(int64_t frameNumber, bool isError) {
809 ALOGV("updateTracker frame %" PRId64 " isError %d", frameNumber, isError);
810 if (isError) {
811 mFutureErrorSet.insert(frameNumber);
812 } else if (frameNumber <= mCompletedFrameNumber) {
813 ALOGE("Frame number %" PRId64 " decreased! current fn %" PRId64,
814 frameNumber, mCompletedFrameNumber);
815 return;
816 } else {
817 if (frameNumber != mCompletedFrameNumber + 1) {
818 ALOGE("Frame number out of order. Expect %" PRId64 " but get %" PRId64,
819 mCompletedFrameNumber + 1, frameNumber);
820 // Do not assert as in java implementation
821 }
822 mCompletedFrameNumber = frameNumber;
823 }
824 update();
825}
826
827void
828CameraDevice::FrameNumberTracker::update() {
829 for (auto it = mFutureErrorSet.begin(); it != mFutureErrorSet.end();) {
830 int64_t errorFrameNumber = *it;
831 if (errorFrameNumber == mCompletedFrameNumber + 1) {
832 mCompletedFrameNumber++;
833 it = mFutureErrorSet.erase(it);
834 } else if (errorFrameNumber <= mCompletedFrameNumber) {
835 // This should not happen, but deal with it anyway
836 ALOGE("Completd frame number passed through current frame number!");
837 // erase the old error since it's no longer useful
838 it = mFutureErrorSet.erase(it);
839 } else {
840 // Normal requests hasn't catched up error frames, just break
841 break;
842 }
843 }
844 ALOGV("Update complete frame %" PRId64, mCompletedFrameNumber);
845}
846
847void
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800848CameraDevice::onCaptureErrorLocked(
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800849 int32_t errorCode,
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800850 const CaptureResultExtras& resultExtras) {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800851 int sequenceId = resultExtras.requestId;
852 int64_t frameNumber = resultExtras.frameNumber;
853 int32_t burstId = resultExtras.burstId;
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700854 auto it = mSequenceCallbackMap.find(sequenceId);
855 if (it == mSequenceCallbackMap.end()) {
856 ALOGE("%s: Error: capture sequence index %d not found!",
857 __FUNCTION__, sequenceId);
858 setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_SERVICE);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800859 return;
860 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700861
862 CallbackHolder cbh = (*it).second;
863 sp<ACameraCaptureSession> session = cbh.mSession;
864 if ((size_t) burstId >= cbh.mRequests.size()) {
865 ALOGE("%s: Error: request index %d out of bound (size %zu)",
866 __FUNCTION__, burstId, cbh.mRequests.size());
867 setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_SERVICE);
868 return;
869 }
870 sp<CaptureRequest> request = cbh.mRequests[burstId];
871
872 // Handle buffer error
873 if (errorCode == hardware::camera2::ICameraDeviceCallbacks::ERROR_CAMERA_BUFFER) {
874 int32_t streamId = resultExtras.errorStreamId;
875 ACameraCaptureSession_captureCallback_bufferLost onBufferLost =
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800876 cbh.mOnCaptureBufferLost;
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700877 auto outputPairIt = mConfiguredOutputs.find(streamId);
878 if (outputPairIt == mConfiguredOutputs.end()) {
879 ALOGE("%s: Error: stream id %d does not exist", __FUNCTION__, streamId);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800880 setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_SERVICE);
881 return;
882 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700883
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800884 const auto& gbps = outputPairIt->second.second.getGraphicBufferProducers();
885 for (const auto& outGbp : gbps) {
Chih-Hung Hsieh3ef324d2018-12-11 11:48:12 -0800886 for (const auto& surface : request->mSurfaceList) {
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800887 if (surface->getIGraphicBufferProducer() == outGbp) {
888 ANativeWindow* anw = static_cast<ANativeWindow*>(surface.get());
889 ALOGV("Camera %s Lost output buffer for ANW %p frame %" PRId64,
890 getId(), anw, frameNumber);
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700891
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800892 sp<AMessage> msg = new AMessage(kWhatCaptureBufferLost, mHandler);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800893 msg->setPointer(kContextKey, cbh.mContext);
Yin-Chia Yeh4dfa4cc2017-11-10 20:00:09 -0800894 msg->setObject(kSessionSpKey, session);
895 msg->setPointer(kCallbackFpKey, (void*) onBufferLost);
896 msg->setObject(kCaptureRequestKey, request);
897 msg->setPointer(kAnwKey, (void*) anw);
898 msg->setInt64(kFrameNumberKey, frameNumber);
899 postSessionMsgAndCleanup(msg);
900 }
901 }
902 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700903 } else { // Handle other capture failures
904 // Fire capture failure callback if there is one registered
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800905 ACameraCaptureSession_captureCallback_failed onError = cbh.mOnCaptureFailed;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800906 sp<CameraCaptureFailure> failure(new CameraCaptureFailure());
907 failure->frameNumber = frameNumber;
908 // TODO: refine this when implementing flush
909 failure->reason = CAPTURE_FAILURE_REASON_ERROR;
910 failure->sequenceId = sequenceId;
911 failure->wasImageCaptured = (errorCode ==
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -0800912 hardware::camera2::ICameraDeviceCallbacks::ERROR_CAMERA_RESULT);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800913
Emilian Peevedec62d2019-03-19 17:59:24 -0700914 sp<AMessage> msg = new AMessage(cbh.mIsLogicalCameraCallback ? kWhatLogicalCaptureFail :
915 kWhatCaptureFail, mHandler);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800916 msg->setPointer(kContextKey, cbh.mContext);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800917 msg->setObject(kSessionSpKey, session);
Emilian Peevedec62d2019-03-19 17:59:24 -0700918 if (cbh.mIsLogicalCameraCallback) {
919 if (resultExtras.errorPhysicalCameraId.size() > 0) {
Austin Borger1c1bee02023-06-01 16:51:35 -0700920 String8 cameraId = toString8(resultExtras.errorPhysicalCameraId);
Emilian Peevedec62d2019-03-19 17:59:24 -0700921 msg->setString(kFailingPhysicalCameraId, cameraId.string(), cameraId.size());
922 }
923 msg->setPointer(kCallbackFpKey, (void*) cbh.mOnLogicalCameraCaptureFailed);
924 } else {
925 msg->setPointer(kCallbackFpKey, (void*) onError);
926 }
Yin-Chia Yehead91462016-01-06 16:45:08 -0800927 msg->setObject(kCaptureRequestKey, request);
928 msg->setObject(kCaptureFailureKey, failure);
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700929 postSessionMsgAndCleanup(msg);
Yin-Chia Yehead91462016-01-06 16:45:08 -0800930
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700931 // Update tracker
932 mFrameNumberTracker.updateTracker(frameNumber, /*isError*/true);
933 checkAndFireSequenceCompleteLocked();
934 }
935 return;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800936}
937
Jayant Chowdharya8bf1c62019-09-26 08:50:17 -0700938void CameraDevice::stopLooperAndDisconnect() {
Jayant Chowdharya8488c92019-06-21 12:45:34 -0700939 Mutex::Autolock _l(mDeviceLock);
Jayant Chowdharya8bf1c62019-09-26 08:50:17 -0700940 sp<ACameraCaptureSession> session = mCurrentSession.promote();
941 if (!isClosed()) {
942 disconnectLocked(session);
943 }
944 mCurrentSession = nullptr;
945
Jayant Chowdharya8488c92019-06-21 12:45:34 -0700946 if (mCbLooper != nullptr) {
947 mCbLooper->unregisterHandler(mHandler->id());
948 mCbLooper->stop();
949 }
950 mCbLooper.clear();
951 mHandler.clear();
952}
953
Shuzhen Wang6c17e212019-02-19 14:51:47 -0800954CameraDevice::CallbackHandler::CallbackHandler(const char* id) : mId(id) {
955}
956
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800957void CameraDevice::CallbackHandler::onMessageReceived(
958 const sp<AMessage> &msg) {
959 switch (msg->what()) {
960 case kWhatOnDisconnected:
961 case kWhatOnError:
Yin-Chia Yehead91462016-01-06 16:45:08 -0800962 case kWhatSessionStateCb:
963 case kWhatCaptureStart:
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +0000964 case kWhatCaptureStart2:
Yin-Chia Yehead91462016-01-06 16:45:08 -0800965 case kWhatCaptureResult:
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -0800966 case kWhatLogicalCaptureResult:
Yin-Chia Yehead91462016-01-06 16:45:08 -0800967 case kWhatCaptureFail:
Emilian Peevedec62d2019-03-19 17:59:24 -0700968 case kWhatLogicalCaptureFail:
Yin-Chia Yehead91462016-01-06 16:45:08 -0800969 case kWhatCaptureSeqEnd:
970 case kWhatCaptureSeqAbort:
Yin-Chia Yehe081c592016-03-29 18:26:44 -0700971 case kWhatCaptureBufferLost:
Jayant Chowdhary09b368b2023-02-13 06:53:05 +0000972 case kWhatPreparedCb:
Yin-Chia Yehead91462016-01-06 16:45:08 -0800973 ALOGV("%s: Received msg %d", __FUNCTION__, msg->what());
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800974 break;
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -0700975 case kWhatCleanUpSessions:
976 mCachedSessions.clear();
977 return;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800978 default:
979 ALOGE("%s:Error: unknown device callback %d", __FUNCTION__, msg->what());
980 return;
981 }
982 // Check the common part of all message
983 void* context;
984 bool found = msg->findPointer(kContextKey, &context);
985 if (!found) {
986 ALOGE("%s: Cannot find callback context!", __FUNCTION__);
987 return;
988 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800989 switch (msg->what()) {
990 case kWhatOnDisconnected:
991 {
Yin-Chia Yehead91462016-01-06 16:45:08 -0800992 ACameraDevice* dev;
993 found = msg->findPointer(kDeviceKey, (void**) &dev);
994 if (!found || dev == nullptr) {
995 ALOGE("%s: Cannot find device pointer!", __FUNCTION__);
996 return;
997 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -0800998 ACameraDevice_StateCallback onDisconnected;
Yin-Chia Yehead91462016-01-06 16:45:08 -0800999 found = msg->findPointer(kCallbackFpKey, (void**) &onDisconnected);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001000 if (!found) {
1001 ALOGE("%s: Cannot find onDisconnected!", __FUNCTION__);
1002 return;
1003 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001004 if (onDisconnected == nullptr) {
1005 return;
1006 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001007 (*onDisconnected)(context, dev);
1008 break;
1009 }
1010 case kWhatOnError:
1011 {
Yin-Chia Yehead91462016-01-06 16:45:08 -08001012 ACameraDevice* dev;
1013 found = msg->findPointer(kDeviceKey, (void**) &dev);
1014 if (!found || dev == nullptr) {
1015 ALOGE("%s: Cannot find device pointer!", __FUNCTION__);
1016 return;
1017 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001018 ACameraDevice_ErrorStateCallback onError;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001019 found = msg->findPointer(kCallbackFpKey, (void**) &onError);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001020 if (!found) {
1021 ALOGE("%s: Cannot find onError!", __FUNCTION__);
1022 return;
1023 }
1024 int errorCode;
1025 found = msg->findInt32(kErrorCodeKey, &errorCode);
1026 if (!found) {
1027 ALOGE("%s: Cannot find error code!", __FUNCTION__);
1028 return;
1029 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001030 if (onError == nullptr) {
1031 return;
1032 }
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001033 (*onError)(context, dev, errorCode);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001034 break;
1035 }
1036 case kWhatSessionStateCb:
1037 case kWhatCaptureStart:
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001038 case kWhatCaptureStart2:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001039 case kWhatCaptureResult:
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001040 case kWhatLogicalCaptureResult:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001041 case kWhatCaptureFail:
Emilian Peevedec62d2019-03-19 17:59:24 -07001042 case kWhatLogicalCaptureFail:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001043 case kWhatCaptureSeqEnd:
1044 case kWhatCaptureSeqAbort:
Yin-Chia Yehe081c592016-03-29 18:26:44 -07001045 case kWhatCaptureBufferLost:
Jayant Chowdhary09b368b2023-02-13 06:53:05 +00001046 case kWhatPreparedCb:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001047 {
1048 sp<RefBase> obj;
1049 found = msg->findObject(kSessionSpKey, &obj);
1050 if (!found || obj == nullptr) {
1051 ALOGE("%s: Cannot find session pointer!", __FUNCTION__);
1052 return;
1053 }
1054 sp<ACameraCaptureSession> session(static_cast<ACameraCaptureSession*>(obj.get()));
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001055 mCachedSessions.push(session);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001056 sp<CaptureRequest> requestSp = nullptr;
1057 switch (msg->what()) {
1058 case kWhatCaptureStart:
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001059 case kWhatCaptureStart2:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001060 case kWhatCaptureResult:
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001061 case kWhatLogicalCaptureResult:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001062 case kWhatCaptureFail:
Emilian Peevedec62d2019-03-19 17:59:24 -07001063 case kWhatLogicalCaptureFail:
Yin-Chia Yehe081c592016-03-29 18:26:44 -07001064 case kWhatCaptureBufferLost:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001065 found = msg->findObject(kCaptureRequestKey, &obj);
1066 if (!found) {
1067 ALOGE("%s: Cannot find capture request!", __FUNCTION__);
1068 return;
1069 }
1070 requestSp = static_cast<CaptureRequest*>(obj.get());
1071 break;
1072 }
1073
1074 switch (msg->what()) {
1075 case kWhatSessionStateCb:
1076 {
1077 ACameraCaptureSession_stateCallback onState;
1078 found = msg->findPointer(kCallbackFpKey, (void**) &onState);
1079 if (!found) {
1080 ALOGE("%s: Cannot find state callback!", __FUNCTION__);
1081 return;
1082 }
1083 if (onState == nullptr) {
1084 return;
1085 }
1086 (*onState)(context, session.get());
1087 break;
1088 }
Jayant Chowdhary09b368b2023-02-13 06:53:05 +00001089 case kWhatPreparedCb:
1090 {
1091 ACameraCaptureSession_prepareCallback onWindowPrepared;
1092 found = msg->findPointer(kCallbackFpKey, (void**) &onWindowPrepared);
1093 if (!found) {
Jayant Chowdhary0f2cb992023-02-17 18:25:53 +00001094 ALOGE("%s: Cannot find window prepared callback!", __FUNCTION__);
Jayant Chowdhary09b368b2023-02-13 06:53:05 +00001095 return;
1096 }
1097 if (onWindowPrepared == nullptr) {
1098 return;
1099 }
1100 ACameraWindowType* anw;
1101 found = msg->findPointer(kAnwKey, (void**) &anw);
1102 if (!found) {
1103 ALOGE("%s: Cannot find ANativeWindow: %d!", __FUNCTION__, __LINE__);
1104 return;
1105 }
1106 (*onWindowPrepared)(context, anw, session.get());
1107 break;
1108 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001109 case kWhatCaptureStart:
1110 {
1111 ACameraCaptureSession_captureCallback_start onStart;
1112 found = msg->findPointer(kCallbackFpKey, (void**) &onStart);
1113 if (!found) {
1114 ALOGE("%s: Cannot find capture start callback!", __FUNCTION__);
1115 return;
1116 }
1117 if (onStart == nullptr) {
1118 return;
1119 }
1120 int64_t timestamp;
1121 found = msg->findInt64(kTimeStampKey, &timestamp);
1122 if (!found) {
1123 ALOGE("%s: Cannot find timestamp!", __FUNCTION__);
1124 return;
1125 }
Shuzhen Wang6c17e212019-02-19 14:51:47 -08001126 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001127 (*onStart)(context, session.get(), request, timestamp);
1128 freeACaptureRequest(request);
1129 break;
1130 }
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001131 case kWhatCaptureStart2:
1132 {
1133 ACameraCaptureSession_captureCallback_startV2 onStart2;
1134 found = msg->findPointer(kCallbackFpKey, (void**) &onStart2);
1135 if (!found) {
1136 ALOGE("%s: Cannot find capture startV2 callback!", __FUNCTION__);
1137 return;
1138 }
1139 if (onStart2 == nullptr) {
1140 return;
1141 }
1142 int64_t timestamp;
1143 found = msg->findInt64(kTimeStampKey, &timestamp);
1144 if (!found) {
1145 ALOGE("%s: Cannot find timestamp!", __FUNCTION__);
1146 return;
1147 }
1148 int64_t frameNumber;
1149 found = msg->findInt64(kFrameNumberKey, &frameNumber);
1150 if (!found) {
1151 ALOGE("%s: Cannot find frame number!", __FUNCTION__);
1152 return;
1153 }
1154
1155 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
1156 (*onStart2)(context, session.get(), request, timestamp, frameNumber);
1157 freeACaptureRequest(request);
1158 break;
1159 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001160 case kWhatCaptureResult:
1161 {
1162 ACameraCaptureSession_captureCallback_result onResult;
1163 found = msg->findPointer(kCallbackFpKey, (void**) &onResult);
1164 if (!found) {
1165 ALOGE("%s: Cannot find capture result callback!", __FUNCTION__);
1166 return;
1167 }
1168 if (onResult == nullptr) {
1169 return;
1170 }
1171
1172 found = msg->findObject(kCaptureResultKey, &obj);
1173 if (!found) {
1174 ALOGE("%s: Cannot find capture result!", __FUNCTION__);
1175 return;
1176 }
1177 sp<ACameraMetadata> result(static_cast<ACameraMetadata*>(obj.get()));
Shuzhen Wang6c17e212019-02-19 14:51:47 -08001178 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001179 (*onResult)(context, session.get(), request, result.get());
1180 freeACaptureRequest(request);
1181 break;
1182 }
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001183 case kWhatLogicalCaptureResult:
1184 {
1185 ACameraCaptureSession_logicalCamera_captureCallback_result onResult;
1186 found = msg->findPointer(kCallbackFpKey, (void**) &onResult);
1187 if (!found) {
1188 ALOGE("%s: Cannot find logicalCamera capture result callback!",
1189 __FUNCTION__);
1190 return;
1191 }
1192 if (onResult == nullptr) {
1193 return;
1194 }
1195
1196 found = msg->findObject(kCaptureResultKey, &obj);
1197 if (!found) {
1198 ALOGE("%s: Cannot find capture result!", __FUNCTION__);
1199 return;
1200 }
1201 sp<ACameraMetadata> result(static_cast<ACameraMetadata*>(obj.get()));
1202
1203 found = msg->findObject(kPhysicalCaptureResultKey, &obj);
1204 if (!found) {
1205 ALOGE("%s: Cannot find physical capture result!", __FUNCTION__);
1206 return;
1207 }
1208 sp<ACameraPhysicalCaptureResultInfo> physicalResult(
1209 static_cast<ACameraPhysicalCaptureResultInfo*>(obj.get()));
1210 std::vector<PhysicalCaptureResultInfo>& physicalResultInfo =
1211 physicalResult->mPhysicalResultInfo;
1212
1213 std::vector<std::string> physicalCameraIds;
1214 std::vector<sp<ACameraMetadata>> physicalMetadataCopy;
1215 for (size_t i = 0; i < physicalResultInfo.size(); i++) {
Austin Borger1c1bee02023-06-01 16:51:35 -07001216 String8 physicalId8 = toString8(physicalResultInfo[i].mPhysicalCameraId);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001217 physicalCameraIds.push_back(physicalId8.c_str());
1218
1219 CameraMetadata clone = physicalResultInfo[i].mPhysicalCameraMetadata;
1220 clone.update(ANDROID_SYNC_FRAME_NUMBER,
1221 &physicalResult->mFrameNumber, /*data_count*/1);
1222 sp<ACameraMetadata> metadata =
1223 new ACameraMetadata(clone.release(), ACameraMetadata::ACM_RESULT);
1224 physicalMetadataCopy.push_back(metadata);
1225 }
1226
1227 std::vector<const char*> physicalCameraIdPtrs;
1228 std::vector<const ACameraMetadata*> physicalMetadataCopyPtrs;
1229 for (size_t i = 0; i < physicalResultInfo.size(); i++) {
1230 physicalCameraIdPtrs.push_back(physicalCameraIds[i].c_str());
1231 physicalMetadataCopyPtrs.push_back(physicalMetadataCopy[i].get());
1232 }
1233
Shuzhen Wang6c17e212019-02-19 14:51:47 -08001234 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001235 (*onResult)(context, session.get(), request, result.get(),
1236 physicalResultInfo.size(), physicalCameraIdPtrs.data(),
1237 physicalMetadataCopyPtrs.data());
1238 freeACaptureRequest(request);
1239 break;
1240 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001241 case kWhatCaptureFail:
1242 {
1243 ACameraCaptureSession_captureCallback_failed onFail;
1244 found = msg->findPointer(kCallbackFpKey, (void**) &onFail);
1245 if (!found) {
1246 ALOGE("%s: Cannot find capture fail callback!", __FUNCTION__);
1247 return;
1248 }
1249 if (onFail == nullptr) {
1250 return;
1251 }
1252
1253 found = msg->findObject(kCaptureFailureKey, &obj);
1254 if (!found) {
1255 ALOGE("%s: Cannot find capture failure!", __FUNCTION__);
1256 return;
1257 }
1258 sp<CameraCaptureFailure> failureSp(
1259 static_cast<CameraCaptureFailure*>(obj.get()));
1260 ACameraCaptureFailure* failure =
1261 static_cast<ACameraCaptureFailure*>(failureSp.get());
Shuzhen Wang6c17e212019-02-19 14:51:47 -08001262 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001263 (*onFail)(context, session.get(), request, failure);
1264 freeACaptureRequest(request);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001265 break;
1266 }
Emilian Peevedec62d2019-03-19 17:59:24 -07001267 case kWhatLogicalCaptureFail:
1268 {
1269 ACameraCaptureSession_logicalCamera_captureCallback_failed onFail;
1270 found = msg->findPointer(kCallbackFpKey, (void**) &onFail);
1271 if (!found) {
1272 ALOGE("%s: Cannot find capture fail callback!", __FUNCTION__);
1273 return;
1274 }
1275 if (onFail == nullptr) {
1276 return;
1277 }
1278
1279 found = msg->findObject(kCaptureFailureKey, &obj);
1280 if (!found) {
1281 ALOGE("%s: Cannot find capture failure!", __FUNCTION__);
1282 return;
1283 }
1284 sp<CameraCaptureFailure> failureSp(
1285 static_cast<CameraCaptureFailure*>(obj.get()));
1286 ALogicalCameraCaptureFailure failure;
1287 AString physicalCameraId;
1288 found = msg->findString(kFailingPhysicalCameraId, &physicalCameraId);
1289 if (found && !physicalCameraId.empty()) {
1290 failure.physicalCameraId = physicalCameraId.c_str();
1291 } else {
1292 failure.physicalCameraId = nullptr;
1293 }
1294 failure.captureFailure = *failureSp;
1295 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
1296 (*onFail)(context, session.get(), request, &failure);
1297 freeACaptureRequest(request);
1298 break;
1299 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001300 case kWhatCaptureSeqEnd:
1301 {
1302 ACameraCaptureSession_captureCallback_sequenceEnd onSeqEnd;
1303 found = msg->findPointer(kCallbackFpKey, (void**) &onSeqEnd);
1304 if (!found) {
1305 ALOGE("%s: Cannot find sequence end callback!", __FUNCTION__);
1306 return;
1307 }
1308 if (onSeqEnd == nullptr) {
1309 return;
1310 }
1311 int seqId;
1312 found = msg->findInt32(kSequenceIdKey, &seqId);
1313 if (!found) {
1314 ALOGE("%s: Cannot find frame number!", __FUNCTION__);
1315 return;
1316 }
1317 int64_t frameNumber;
1318 found = msg->findInt64(kFrameNumberKey, &frameNumber);
1319 if (!found) {
1320 ALOGE("%s: Cannot find frame number!", __FUNCTION__);
1321 return;
1322 }
1323 (*onSeqEnd)(context, session.get(), seqId, frameNumber);
1324 break;
1325 }
1326 case kWhatCaptureSeqAbort:
1327 {
1328 ACameraCaptureSession_captureCallback_sequenceAbort onSeqAbort;
1329 found = msg->findPointer(kCallbackFpKey, (void**) &onSeqAbort);
1330 if (!found) {
1331 ALOGE("%s: Cannot find sequence end callback!", __FUNCTION__);
1332 return;
1333 }
1334 if (onSeqAbort == nullptr) {
1335 return;
1336 }
1337 int seqId;
1338 found = msg->findInt32(kSequenceIdKey, &seqId);
1339 if (!found) {
1340 ALOGE("%s: Cannot find frame number!", __FUNCTION__);
1341 return;
1342 }
1343 (*onSeqAbort)(context, session.get(), seqId);
1344 break;
1345 }
Yin-Chia Yehe081c592016-03-29 18:26:44 -07001346 case kWhatCaptureBufferLost:
1347 {
1348 ACameraCaptureSession_captureCallback_bufferLost onBufferLost;
1349 found = msg->findPointer(kCallbackFpKey, (void**) &onBufferLost);
1350 if (!found) {
1351 ALOGE("%s: Cannot find buffer lost callback!", __FUNCTION__);
1352 return;
1353 }
1354 if (onBufferLost == nullptr) {
1355 return;
1356 }
1357
1358 ANativeWindow* anw;
1359 found = msg->findPointer(kAnwKey, (void**) &anw);
1360 if (!found) {
1361 ALOGE("%s: Cannot find ANativeWindow!", __FUNCTION__);
1362 return;
1363 }
1364
1365 int64_t frameNumber;
1366 found = msg->findInt64(kFrameNumberKey, &frameNumber);
1367 if (!found) {
1368 ALOGE("%s: Cannot find frame number!", __FUNCTION__);
1369 return;
1370 }
1371
Shuzhen Wang6c17e212019-02-19 14:51:47 -08001372 ACaptureRequest* request = allocateACaptureRequest(requestSp, mId);
Yin-Chia Yehe081c592016-03-29 18:26:44 -07001373 (*onBufferLost)(context, session.get(), request, anw, frameNumber);
1374 freeACaptureRequest(request);
1375 break;
1376 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001377 }
1378 break;
1379 }
1380 }
1381}
1382
1383CameraDevice::CallbackHolder::CallbackHolder(
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001384 sp<ACameraCaptureSession> session,
1385 const Vector<sp<CaptureRequest> >& requests,
1386 bool isRepeating,
1387 ACameraCaptureSession_captureCallbacks* cbs) :
1388 mSession(session), mRequests(requests),
1389 mIsRepeating(isRepeating),
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001390 mIsLogicalCameraCallback(false),
1391 mIs2Callback(false) {
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001392 initCaptureCallbacks(cbs);
1393
1394 if (cbs != nullptr) {
1395 mOnCaptureCompleted = cbs->onCaptureCompleted;
Emilian Peevedec62d2019-03-19 17:59:24 -07001396 mOnCaptureFailed = cbs->onCaptureFailed;
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001397 }
1398}
1399
1400CameraDevice::CallbackHolder::CallbackHolder(
1401 sp<ACameraCaptureSession> session,
1402 const Vector<sp<CaptureRequest> >& requests,
1403 bool isRepeating,
1404 ACameraCaptureSession_logicalCamera_captureCallbacks* lcbs) :
1405 mSession(session), mRequests(requests),
1406 mIsRepeating(isRepeating),
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001407 mIsLogicalCameraCallback(true),
1408 mIs2Callback(false) {
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001409 initCaptureCallbacks(lcbs);
1410
1411 if (lcbs != nullptr) {
1412 mOnLogicalCameraCaptureCompleted = lcbs->onLogicalCameraCaptureCompleted;
Emilian Peevedec62d2019-03-19 17:59:24 -07001413 mOnLogicalCameraCaptureFailed = lcbs->onLogicalCameraCaptureFailed;
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001414 }
1415}
Yin-Chia Yehead91462016-01-06 16:45:08 -08001416
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001417CameraDevice::CallbackHolder::CallbackHolder(
1418 sp<ACameraCaptureSession> session,
1419 const Vector<sp<CaptureRequest> >& requests,
1420 bool isRepeating,
1421 ACameraCaptureSession_captureCallbacksV2* cbs) :
1422 mSession(session), mRequests(requests),
1423 mIsRepeating(isRepeating),
1424 mIsLogicalCameraCallback(false),
1425 mIs2Callback(true) {
1426 initCaptureCallbacksV2(cbs);
1427
1428 if (cbs != nullptr) {
1429 mOnCaptureCompleted = cbs->onCaptureCompleted;
1430 mOnCaptureFailed = cbs->onCaptureFailed;
1431 }
1432}
1433
1434CameraDevice::CallbackHolder::CallbackHolder(
1435 sp<ACameraCaptureSession> session,
1436 const Vector<sp<CaptureRequest> >& requests,
1437 bool isRepeating,
1438 ACameraCaptureSession_logicalCamera_captureCallbacksV2* lcbs) :
1439 mSession(session), mRequests(requests),
1440 mIsRepeating(isRepeating),
1441 mIsLogicalCameraCallback(true),
1442 mIs2Callback(true) {
1443 initCaptureCallbacksV2(lcbs);
1444
1445 if (lcbs != nullptr) {
1446 mOnLogicalCameraCaptureCompleted = lcbs->onLogicalCameraCaptureCompleted;
1447 mOnLogicalCameraCaptureFailed = lcbs->onLogicalCameraCaptureFailed;
1448 }
1449}
1450
Yin-Chia Yehead91462016-01-06 16:45:08 -08001451void
1452CameraDevice::checkRepeatingSequenceCompleteLocked(
1453 const int sequenceId, const int64_t lastFrameNumber) {
1454 ALOGV("Repeating seqId %d lastFrameNumer %" PRId64, sequenceId, lastFrameNumber);
1455 if (lastFrameNumber == NO_FRAMES_CAPTURED) {
1456 if (mSequenceCallbackMap.count(sequenceId) == 0) {
1457 ALOGW("No callback found for sequenceId %d", sequenceId);
1458 return;
1459 }
1460 // remove callback holder from callback map
1461 auto cbIt = mSequenceCallbackMap.find(sequenceId);
1462 CallbackHolder cbh = cbIt->second;
1463 mSequenceCallbackMap.erase(cbIt);
1464 // send seq aborted callback
1465 sp<AMessage> msg = new AMessage(kWhatCaptureSeqAbort, mHandler);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001466 msg->setPointer(kContextKey, cbh.mContext);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001467 msg->setObject(kSessionSpKey, cbh.mSession);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001468 msg->setPointer(kCallbackFpKey, (void*) cbh.mOnCaptureSequenceAborted);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001469 msg->setInt32(kSequenceIdKey, sequenceId);
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001470 postSessionMsgAndCleanup(msg);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001471 } else {
1472 // Use mSequenceLastFrameNumberMap to track
1473 mSequenceLastFrameNumberMap.insert(std::make_pair(sequenceId, lastFrameNumber));
1474
1475 // Last frame might have arrived. Check now
1476 checkAndFireSequenceCompleteLocked();
1477 }
1478}
1479
1480void
1481CameraDevice::checkAndFireSequenceCompleteLocked() {
1482 int64_t completedFrameNumber = mFrameNumberTracker.getCompletedFrameNumber();
Yin-Chia Yehead91462016-01-06 16:45:08 -08001483 auto it = mSequenceLastFrameNumberMap.begin();
1484 while (it != mSequenceLastFrameNumberMap.end()) {
1485 int sequenceId = it->first;
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001486 int64_t lastFrameNumber = it->second.lastFrameNumber;
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001487
1488 if (mRemote == nullptr) {
1489 ALOGW("Camera %s closed while checking sequence complete", getId());
1490 return;
1491 }
1492 ALOGV("%s: seq %d's last frame number %" PRId64 ", completed %" PRId64,
1493 __FUNCTION__, sequenceId, lastFrameNumber, completedFrameNumber);
1494 if (!it->second.isSequenceCompleted) {
1495 // Check if there is callback for this sequence
1496 // This should not happen because we always register callback (with nullptr inside)
1497 if (mSequenceCallbackMap.count(sequenceId) == 0) {
1498 ALOGW("No callback found for sequenceId %d", sequenceId);
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001499 }
1500
1501 if (lastFrameNumber <= completedFrameNumber) {
1502 ALOGV("Mark sequenceId %d as sequence completed", sequenceId);
1503 it->second.isSequenceCompleted = true;
1504 }
1505
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001506 }
1507
1508 if (it->second.isSequenceCompleted && it->second.isInflightCompleted) {
Shuzhen Wangacae2642020-12-21 17:11:37 -08001509 sendCaptureSequenceCompletedLocked(sequenceId, lastFrameNumber);
1510
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001511 it = mSequenceLastFrameNumberMap.erase(it);
1512 ALOGV("%s: Remove holder for sequenceId %d", __FUNCTION__, sequenceId);
1513 } else {
1514 ++it;
1515 }
1516 }
1517}
1518
1519void
1520CameraDevice::removeCompletedCallbackHolderLocked(int64_t lastCompletedRegularFrameNumber) {
1521 auto it = mSequenceLastFrameNumberMap.begin();
1522 while (it != mSequenceLastFrameNumberMap.end()) {
1523 int sequenceId = it->first;
1524 int64_t lastFrameNumber = it->second.lastFrameNumber;
Shuzhen Wang730a7912020-05-07 11:59:02 -07001525
1526 if (mRemote == nullptr) {
1527 ALOGW("Camera %s closed while checking sequence complete", getId());
1528 return;
1529 }
Shuzhen Wang730a7912020-05-07 11:59:02 -07001530
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001531 ALOGV("%s: seq %d's last frame number %" PRId64
1532 ", completed inflight frame number %" PRId64,
1533 __FUNCTION__, sequenceId, lastFrameNumber,
1534 lastCompletedRegularFrameNumber);
1535 if (lastFrameNumber <= lastCompletedRegularFrameNumber) {
1536 if (it->second.isSequenceCompleted) {
Shuzhen Wangacae2642020-12-21 17:11:37 -08001537 sendCaptureSequenceCompletedLocked(sequenceId, lastFrameNumber);
Shuzhen Wang730a7912020-05-07 11:59:02 -07001538
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001539 it = mSequenceLastFrameNumberMap.erase(it);
1540 ALOGV("%s: Remove holder for sequenceId %d", __FUNCTION__, sequenceId);
1541 } else {
1542 ALOGV("Mark sequenceId %d as inflight completed", sequenceId);
1543 it->second.isInflightCompleted = true;
1544 ++it;
1545 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001546 } else {
1547 ++it;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001548 }
1549 }
1550}
1551
1552/**
1553 * Camera service callback implementation
1554 */
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001555binder::Status
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001556CameraDevice::ServiceCallback::onDeviceError(
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001557 int32_t errorCode,
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001558 const CaptureResultExtras& resultExtras) {
1559 ALOGD("Device error received, code %d, frame number %" PRId64 ", request ID %d, subseq ID %d",
1560 errorCode, resultExtras.frameNumber, resultExtras.requestId, resultExtras.burstId);
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001561 binder::Status ret = binder::Status::ok();
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001562 sp<CameraDevice> dev = mDevice.promote();
1563 if (dev == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001564 return ret; // device has been closed
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001565 }
1566
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001567 sp<ACameraCaptureSession> session = dev->mCurrentSession.promote();
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001568 Mutex::Autolock _l(dev->mDeviceLock);
1569 if (dev->mRemote == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001570 return ret; // device has been closed
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001571 }
1572 switch (errorCode) {
1573 case ERROR_CAMERA_DISCONNECTED:
1574 {
Yin-Chia Yehead91462016-01-06 16:45:08 -08001575 // Camera is disconnected, close the session and expect no more callbacks
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001576 if (session != nullptr) {
1577 session->closeByDevice();
Yin-Chia Yehead91462016-01-06 16:45:08 -08001578 }
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001579 dev->mCurrentSession = nullptr;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001580 sp<AMessage> msg = new AMessage(kWhatOnDisconnected, dev->mHandler);
1581 msg->setPointer(kContextKey, dev->mAppCallbacks.context);
1582 msg->setPointer(kDeviceKey, (void*) dev->getWrapper());
Yin-Chia Yehead91462016-01-06 16:45:08 -08001583 msg->setPointer(kCallbackFpKey, (void*) dev->mAppCallbacks.onDisconnected);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001584 msg->post();
1585 break;
1586 }
1587 default:
1588 ALOGE("Unknown error from camera device: %d", errorCode);
Chih-Hung Hsiehe6a2f212018-10-16 12:16:31 -07001589 [[fallthrough]];
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001590 case ERROR_CAMERA_DEVICE:
1591 case ERROR_CAMERA_SERVICE:
1592 {
Jayant Chowdhary694cd472018-10-16 12:44:58 -07001593 int32_t errorVal = ::ERROR_CAMERA_DEVICE;
1594 // We keep this switch since this block might be encountered with
1595 // more than just 2 states. The default fallthrough could have us
1596 // handling more unmatched error cases.
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001597 switch (errorCode) {
1598 case ERROR_CAMERA_DEVICE:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001599 dev->setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_DEVICE);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001600 break;
1601 case ERROR_CAMERA_SERVICE:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001602 dev->setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_SERVICE);
Jayant Chowdhary694cd472018-10-16 12:44:58 -07001603 errorVal = ::ERROR_CAMERA_SERVICE;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001604 break;
1605 default:
Yin-Chia Yehead91462016-01-06 16:45:08 -08001606 dev->setCameraDeviceErrorLocked(ACAMERA_ERROR_UNKNOWN);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001607 break;
1608 }
1609 sp<AMessage> msg = new AMessage(kWhatOnError, dev->mHandler);
1610 msg->setPointer(kContextKey, dev->mAppCallbacks.context);
1611 msg->setPointer(kDeviceKey, (void*) dev->getWrapper());
Yin-Chia Yehead91462016-01-06 16:45:08 -08001612 msg->setPointer(kCallbackFpKey, (void*) dev->mAppCallbacks.onError);
Jayant Chowdhary694cd472018-10-16 12:44:58 -07001613 msg->setInt32(kErrorCodeKey, errorVal);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001614 msg->post();
1615 break;
1616 }
1617 case ERROR_CAMERA_REQUEST:
1618 case ERROR_CAMERA_RESULT:
1619 case ERROR_CAMERA_BUFFER:
1620 dev->onCaptureErrorLocked(errorCode, resultExtras);
1621 break;
1622 }
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001623 return ret;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001624}
1625
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001626binder::Status
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001627CameraDevice::ServiceCallback::onDeviceIdle() {
1628 ALOGV("Camera is now idle");
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001629 binder::Status ret = binder::Status::ok();
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001630 sp<CameraDevice> dev = mDevice.promote();
1631 if (dev == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001632 return ret; // device has been closed
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001633 }
1634
1635 Mutex::Autolock _l(dev->mDeviceLock);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001636 if (dev->isClosed() || dev->mRemote == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001637 return ret;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001638 }
Yin-Chia Yehead91462016-01-06 16:45:08 -08001639
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001640 dev->removeCompletedCallbackHolderLocked(
1641 std::numeric_limits<int64_t>::max()/*lastCompletedRegularFrameNumber*/);
1642
Yin-Chia Yehead91462016-01-06 16:45:08 -08001643 if (dev->mIdle) {
1644 // Already in idle state. Possibly other thread did waitUntilIdle
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001645 return ret;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001646 }
1647
1648 if (dev->mCurrentSession != nullptr) {
1649 ALOGE("onDeviceIdle sending state cb");
1650 if (dev->mBusySession != dev->mCurrentSession) {
1651 ALOGE("Current session != busy session");
1652 dev->setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_DEVICE);
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001653 return ret;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001654 }
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001655
Yin-Chia Yehead91462016-01-06 16:45:08 -08001656 sp<AMessage> msg = new AMessage(kWhatSessionStateCb, dev->mHandler);
1657 msg->setPointer(kContextKey, dev->mBusySession->mUserSessionCallback.context);
1658 msg->setObject(kSessionSpKey, dev->mBusySession);
1659 msg->setPointer(kCallbackFpKey, (void*) dev->mBusySession->mUserSessionCallback.onReady);
1660 // Make sure we clear the sp first so the session destructor can
1661 // only happen on handler thread (where we don't hold device/session lock)
1662 dev->mBusySession.clear();
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001663 dev->postSessionMsgAndCleanup(msg);
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001664 }
1665 dev->mIdle = true;
Yin-Chia Yeh309d05d2016-03-28 10:15:31 -07001666 dev->mFlushing = false;
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001667 return ret;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001668}
1669
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001670binder::Status
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001671CameraDevice::ServiceCallback::onCaptureStarted(
1672 const CaptureResultExtras& resultExtras,
1673 int64_t timestamp) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001674 binder::Status ret = binder::Status::ok();
Yin-Chia Yehead91462016-01-06 16:45:08 -08001675 sp<CameraDevice> dev = mDevice.promote();
1676 if (dev == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001677 return ret; // device has been closed
Yin-Chia Yehead91462016-01-06 16:45:08 -08001678 }
1679 Mutex::Autolock _l(dev->mDeviceLock);
1680 if (dev->isClosed() || dev->mRemote == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001681 return ret;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001682 }
1683
Shuzhen Wangb7b42652020-05-07 11:59:02 -07001684 dev->removeCompletedCallbackHolderLocked(
1685 resultExtras.lastCompletedRegularFrameNumber);
1686
Yin-Chia Yehead91462016-01-06 16:45:08 -08001687 int sequenceId = resultExtras.requestId;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001688 int32_t burstId = resultExtras.burstId;
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001689 int64_t frameNumber = resultExtras.frameNumber;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001690
1691 auto it = dev->mSequenceCallbackMap.find(sequenceId);
1692 if (it != dev->mSequenceCallbackMap.end()) {
1693 CallbackHolder cbh = (*it).second;
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001694 bool v2Callback = cbh.mIs2Callback;
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001695 ACameraCaptureSession_captureCallback_start onStart = cbh.mOnCaptureStarted;
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001696 ACameraCaptureSession_captureCallback_startV2 onStart2 = cbh.mOnCaptureStarted2;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001697 sp<ACameraCaptureSession> session = cbh.mSession;
1698 if ((size_t) burstId >= cbh.mRequests.size()) {
1699 ALOGE("%s: Error: request index %d out of bound (size %zu)",
1700 __FUNCTION__, burstId, cbh.mRequests.size());
1701 dev->setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_SERVICE);
1702 }
1703 sp<CaptureRequest> request = cbh.mRequests[burstId];
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001704 sp<AMessage> msg = nullptr;
1705 if (v2Callback) {
1706 msg = new AMessage(kWhatCaptureStart2, dev->mHandler);
1707 msg->setPointer(kCallbackFpKey, (void*) onStart2);
1708 } else {
1709 msg = new AMessage(kWhatCaptureStart, dev->mHandler);
1710 msg->setPointer(kCallbackFpKey, (void *)onStart);
1711 }
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001712 msg->setPointer(kContextKey, cbh.mContext);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001713 msg->setObject(kSessionSpKey, session);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001714 msg->setObject(kCaptureRequestKey, request);
1715 msg->setInt64(kTimeStampKey, timestamp);
Jayant Chowdhary04ba13f2022-01-14 00:21:19 +00001716 msg->setInt64(kFrameNumberKey, frameNumber);
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001717 dev->postSessionMsgAndCleanup(msg);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001718 }
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001719 return ret;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001720}
1721
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001722binder::Status
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001723CameraDevice::ServiceCallback::onResultReceived(
1724 const CameraMetadata& metadata,
Shuzhen Wang5c22c152017-12-31 17:12:25 -08001725 const CaptureResultExtras& resultExtras,
1726 const std::vector<PhysicalCaptureResultInfo>& physicalResultInfos) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001727 binder::Status ret = binder::Status::ok();
1728
Yin-Chia Yehead91462016-01-06 16:45:08 -08001729 sp<CameraDevice> dev = mDevice.promote();
1730 if (dev == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001731 return ret; // device has been closed
Yin-Chia Yehead91462016-01-06 16:45:08 -08001732 }
1733 int sequenceId = resultExtras.requestId;
1734 int64_t frameNumber = resultExtras.frameNumber;
1735 int32_t burstId = resultExtras.burstId;
1736 bool isPartialResult = (resultExtras.partialResultCount < dev->mPartialResultCount);
1737
1738 if (!isPartialResult) {
1739 ALOGV("SeqId %d frame %" PRId64 " result arrive.", sequenceId, frameNumber);
1740 }
1741
1742 Mutex::Autolock _l(dev->mDeviceLock);
1743 if (dev->mRemote == nullptr) {
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001744 return ret; // device has been disconnected
Yin-Chia Yehead91462016-01-06 16:45:08 -08001745 }
1746
1747 if (dev->isClosed()) {
1748 if (!isPartialResult) {
1749 dev->mFrameNumberTracker.updateTracker(frameNumber, /*isError*/false);
1750 }
1751 // early return to avoid callback sent to closed devices
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001752 return ret;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001753 }
1754
1755 CameraMetadata metadataCopy = metadata;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001756 metadataCopy.update(ANDROID_LENS_INFO_SHADING_MAP_SIZE, dev->mShadingMapSize, /*data_count*/2);
Yin-Chia Yehff2a4952016-04-02 16:31:57 -07001757 metadataCopy.update(ANDROID_SYNC_FRAME_NUMBER, &frameNumber, /*data_count*/1);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001758
1759 auto it = dev->mSequenceCallbackMap.find(sequenceId);
1760 if (it != dev->mSequenceCallbackMap.end()) {
1761 CallbackHolder cbh = (*it).second;
Yin-Chia Yehead91462016-01-06 16:45:08 -08001762 sp<ACameraCaptureSession> session = cbh.mSession;
1763 if ((size_t) burstId >= cbh.mRequests.size()) {
1764 ALOGE("%s: Error: request index %d out of bound (size %zu)",
1765 __FUNCTION__, burstId, cbh.mRequests.size());
1766 dev->setCameraDeviceErrorLocked(ACAMERA_ERROR_CAMERA_SERVICE);
1767 }
1768 sp<CaptureRequest> request = cbh.mRequests[burstId];
1769 sp<ACameraMetadata> result(new ACameraMetadata(
1770 metadataCopy.release(), ACameraMetadata::ACM_RESULT));
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001771 sp<ACameraPhysicalCaptureResultInfo> physicalResult(
1772 new ACameraPhysicalCaptureResultInfo(physicalResultInfos, frameNumber));
Yin-Chia Yehead91462016-01-06 16:45:08 -08001773
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001774 sp<AMessage> msg = new AMessage(
1775 cbh.mIsLogicalCameraCallback ? kWhatLogicalCaptureResult : kWhatCaptureResult,
1776 dev->mHandler);
1777 msg->setPointer(kContextKey, cbh.mContext);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001778 msg->setObject(kSessionSpKey, session);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001779 msg->setObject(kCaptureRequestKey, request);
1780 msg->setObject(kCaptureResultKey, result);
Shuzhen Wang0ff9ae32018-12-05 18:06:12 -08001781 if (isPartialResult) {
1782 msg->setPointer(kCallbackFpKey,
1783 (void *)cbh.mOnCaptureProgressed);
1784 } else if (cbh.mIsLogicalCameraCallback) {
1785 msg->setPointer(kCallbackFpKey,
1786 (void *)cbh.mOnLogicalCameraCaptureCompleted);
1787 msg->setObject(kPhysicalCaptureResultKey, physicalResult);
1788 } else {
1789 msg->setPointer(kCallbackFpKey,
1790 (void *)cbh.mOnCaptureCompleted);
1791 }
Yin-Chia Yeh6e2353b2017-10-24 16:35:20 -07001792 dev->postSessionMsgAndCleanup(msg);
Yin-Chia Yehead91462016-01-06 16:45:08 -08001793 }
1794
1795 if (!isPartialResult) {
1796 dev->mFrameNumberTracker.updateTracker(frameNumber, /*isError*/false);
1797 dev->checkAndFireSequenceCompleteLocked();
1798 }
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001799
1800 return ret;
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001801}
1802
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001803binder::Status
Jayant Chowdhary09b368b2023-02-13 06:53:05 +00001804CameraDevice::ServiceCallback::onPrepared(int streamId) {
1805 ALOGV("%s: callback for stream id %d", __FUNCTION__, streamId);
1806 binder::Status ret = binder::Status::ok();
1807 sp<CameraDevice> dev = mDevice.promote();
1808 if (dev == nullptr) {
1809 return ret; // device has been closed
1810 }
1811 Mutex::Autolock _l(dev->mDeviceLock);
1812 if (dev->isClosed() || dev->mRemote == nullptr) {
1813 return ret;
1814 }
1815 auto it = dev->mConfiguredOutputs.find(streamId);
1816 if (it == dev->mConfiguredOutputs.end()) {
1817 ALOGE("%s: stream id %d does not exist", __FUNCTION__ , streamId);
1818 return ret;
1819 }
1820 sp<ACameraCaptureSession> session = dev->mCurrentSession.promote();
1821 if (session == nullptr) {
1822 ALOGE("%s: Session is dead already", __FUNCTION__ );
1823 return ret;
1824 }
1825 // We've found the window corresponding to the surface id.
1826 ACameraWindowType *window = it->second.first;
1827 sp<AMessage> msg = new AMessage(kWhatPreparedCb, dev->mHandler);
1828 msg->setPointer(kContextKey, session->mPreparedCb.context);
1829 msg->setPointer(kAnwKey, window);
1830 msg->setObject(kSessionSpKey, session);
1831 msg->setPointer(kCallbackFpKey, (void *)session->mPreparedCb.onWindowPrepared);
1832 dev->postSessionMsgAndCleanup(msg);
1833
Eino-Ville Talvalad56db1d2015-12-17 16:50:35 -08001834 return binder::Status::ok();
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001835}
1836
Chien-Yu Chene8c535e2016-04-14 12:18:26 -07001837binder::Status
Shuzhen Wang9d066012016-09-30 11:30:20 -07001838CameraDevice::ServiceCallback::onRequestQueueEmpty() {
1839 // onRequestQueueEmpty not yet implemented in NDK
1840 return binder::Status::ok();
1841}
1842
1843binder::Status
Yin-Chia Yeh8ca23dc2017-09-05 18:15:56 -07001844CameraDevice::ServiceCallback::onRepeatingRequestError(
1845 int64_t lastFrameNumber, int32_t stoppedSequenceId) {
Chien-Yu Chene8c535e2016-04-14 12:18:26 -07001846 binder::Status ret = binder::Status::ok();
1847
1848 sp<CameraDevice> dev = mDevice.promote();
1849 if (dev == nullptr) {
1850 return ret; // device has been closed
1851 }
1852
1853 Mutex::Autolock _l(dev->mDeviceLock);
1854
1855 int repeatingSequenceId = dev->mRepeatingSequenceId;
Yin-Chia Yeh8ca23dc2017-09-05 18:15:56 -07001856 if (stoppedSequenceId == repeatingSequenceId) {
1857 dev->mRepeatingSequenceId = REQUEST_ID_NONE;
1858 }
Chien-Yu Chene8c535e2016-04-14 12:18:26 -07001859
1860 dev->checkRepeatingSequenceCompleteLocked(repeatingSequenceId, lastFrameNumber);
1861
1862 return ret;
1863}
1864
Shuzhen Wangacae2642020-12-21 17:11:37 -08001865void
1866CameraDevice::sendCaptureSequenceCompletedLocked(int sequenceId, int64_t lastFrameNumber) {
1867 auto cbIt = mSequenceCallbackMap.find(sequenceId);
1868 if (cbIt != mSequenceCallbackMap.end()) {
1869 CallbackHolder cbh = cbIt->second;
1870 mSequenceCallbackMap.erase(cbIt);
1871
1872 // send seq complete callback
1873 sp<AMessage> msg = new AMessage(kWhatCaptureSeqEnd, mHandler);
1874 msg->setPointer(kContextKey, cbh.mContext);
1875 msg->setObject(kSessionSpKey, cbh.mSession);
1876 msg->setPointer(kCallbackFpKey, (void*) cbh.mOnCaptureSequenceCompleted);
1877 msg->setInt32(kSequenceIdKey, sequenceId);
1878 msg->setInt64(kFrameNumberKey, lastFrameNumber);
1879
1880 // Clear the session sp before we send out the message
1881 // This will guarantee the rare case where the message is processed
1882 // before cbh goes out of scope and causing we call the session
1883 // destructor while holding device lock
1884 cbh.mSession.clear();
1885 postSessionMsgAndCleanup(msg);
1886 } else {
1887 // Check if there is callback for this sequence
1888 // This should not happen because we always register callback (with nullptr inside)
1889 ALOGW("No callback found for sequenceId %d", sequenceId);
1890 }
1891}
1892
Jayant Chowdhary6df26072018-11-06 23:55:12 -08001893} // namespace acam
Yin-Chia Yeh0dea57f2015-12-09 16:46:07 -08001894} // namespace android