1 /*
2 * Copyright (C) 2019 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 "GCH_CameraDeviceSession"
19 #define ATRACE_TAG ATRACE_TAG_CAMERA
20 #include "camera_device_session.h"
21
22 #include <inttypes.h>
23 #include <log/log.h>
24 #include <utils/Trace.h>
25
26 #include "basic_capture_session.h"
27 #include "capture_session_utils.h"
28 #include "dual_ir_capture_session.h"
29 #include "hal_types.h"
30 #include "hal_utils.h"
31 #include "hdrplus_capture_session.h"
32 #include "rgbird_capture_session.h"
33 #include "system/camera_metadata.h"
34 #include "ui/GraphicBufferMapper.h"
35 #include "vendor_tag_defs.h"
36 #include "vendor_tag_types.h"
37 #include "vendor_tags.h"
38 #include "zsl_snapshot_capture_session.h"
39
40 namespace android {
41 namespace google_camera_hal {
42
43 constexpr char kMeasureBufferAllocationProp[] =
44 "persist.vendor.camera.measure_buffer_allocation";
45
46 static constexpr int64_t kNsPerSec = 1000000000;
47 static constexpr int64_t kAllocationThreshold = 33000000; // 33ms
48
49 std::vector<CaptureSessionEntryFuncs>
50 CameraDeviceSession::kCaptureSessionEntries = {
51 {.IsStreamConfigurationSupported =
52 HdrplusCaptureSession::IsStreamConfigurationSupported,
53 .CreateSession = HdrplusCaptureSession::Create},
54 {.IsStreamConfigurationSupported =
55 RgbirdCaptureSession::IsStreamConfigurationSupported,
56 .CreateSession = RgbirdCaptureSession::Create},
57 {.IsStreamConfigurationSupported =
58 DualIrCaptureSession::IsStreamConfigurationSupported,
59 .CreateSession = DualIrCaptureSession::Create},
60 // BasicCaptureSession is supposed to be the last resort.
61 {.IsStreamConfigurationSupported =
62 BasicCaptureSession::IsStreamConfigurationSupported,
63 .CreateSession = BasicCaptureSession::Create}};
64
65 std::vector<WrapperCaptureSessionEntryFuncs>
66 CameraDeviceSession::kWrapperCaptureSessionEntries = {
67 {.IsStreamConfigurationSupported =
68 ZslSnapshotCaptureSession::IsStreamConfigurationSupported,
69 .CreateSession = ZslSnapshotCaptureSession::Create}};
70
Create(std::unique_ptr<CameraDeviceSessionHwl> device_session_hwl,std::vector<GetCaptureSessionFactoryFunc> external_session_factory_entries,CameraBufferAllocatorHwl * camera_allocator_hwl)71 std::unique_ptr<CameraDeviceSession> CameraDeviceSession::Create(
72 std::unique_ptr<CameraDeviceSessionHwl> device_session_hwl,
73 std::vector<GetCaptureSessionFactoryFunc> external_session_factory_entries,
74 CameraBufferAllocatorHwl* camera_allocator_hwl) {
75 ATRACE_CALL();
76 if (device_session_hwl == nullptr) {
77 ALOGE("%s: device_session_hwl is nullptr", __FUNCTION__);
78 return nullptr;
79 }
80
81 uint32_t camera_id = device_session_hwl->GetCameraId();
82 std::vector<uint32_t> physical_camera_ids =
83 device_session_hwl->GetPhysicalCameraIds();
84
85 auto session = std::unique_ptr<CameraDeviceSession>(new CameraDeviceSession());
86 if (session == nullptr) {
87 ALOGE("%s: Creating CameraDeviceSession failed.", __FUNCTION__);
88 return nullptr;
89 }
90
91 status_t res =
92 session->Initialize(std::move(device_session_hwl), camera_allocator_hwl,
93 external_session_factory_entries);
94 if (res != OK) {
95 ALOGE("%s: Initializing CameraDeviceSession failed: %s (%d).", __FUNCTION__,
96 strerror(-res), res);
97 return nullptr;
98 }
99
100 // Construct a string of physical camera IDs.
101 std::string physical_camera_ids_string;
102 if (physical_camera_ids.size() > 0) {
103 physical_camera_ids_string += ": ";
104
105 for (auto& id : physical_camera_ids) {
106 physical_camera_ids_string += std::to_string(id) + " ";
107 }
108 }
109
110 ALOGI(
111 "%s: Created a device session for camera %d with %zu physical cameras%s",
112 __FUNCTION__, camera_id, physical_camera_ids.size(),
113 physical_camera_ids_string.c_str());
114
115 return session;
116 }
117
UpdatePendingRequest(CaptureResult * result)118 status_t CameraDeviceSession::UpdatePendingRequest(CaptureResult* result) {
119 std::lock_guard<std::mutex> lock(request_record_lock_);
120 if (result == nullptr) {
121 ALOGE("%s: result is nullptr.", __FUNCTION__);
122 return BAD_VALUE;
123 }
124
125 if (result->output_buffers.empty()) {
126 // Nothing to do if the result doesn't contain any output buffers.
127 return OK;
128 }
129 bool frame_has_hal_buffer_managed_buffer = false;
130 for (const auto& buffer : result->output_buffers) {
131 if (hal_buffer_managed_stream_ids_.find(buffer.stream_id) !=
132 hal_buffer_managed_stream_ids_.end()) {
133 frame_has_hal_buffer_managed_buffer = true;
134 break;
135 }
136 }
137
138 // There's no HAL buffer managed buffer in the frame, we don't need to track
139 // it through pending_request_streams_.
140 if (!frame_has_hal_buffer_managed_buffer) {
141 return OK;
142 }
143
144 // Update inflight request records and notify SBC for flushing if needed
145 uint32_t frame_number = result->frame_number;
146
147 if (pending_request_streams_.find(frame_number) ==
148 pending_request_streams_.end()) {
149 ALOGE("%s: Can't find frame %u in result holder.", __FUNCTION__,
150 frame_number);
151 return UNKNOWN_ERROR;
152 }
153
154 // Remove streams from pending request streams for buffers in the result.
155 auto& streams = pending_request_streams_.at(frame_number);
156 for (auto& stream_buffer : result->output_buffers) {
157 int32_t stream_id = stream_buffer.stream_id;
158 if (streams.find(stream_id) == streams.end()) {
159 // If stream_id belongs to a stream group, the HWL may choose to output
160 // buffers to a different stream in the same group.
161 if (grouped_stream_id_map_.count(stream_id) == 1) {
162 int32_t stream_id_for_group = grouped_stream_id_map_.at(stream_id);
163 if (streams.find(stream_id_for_group) != streams.end()) {
164 streams.erase(stream_id_for_group);
165 } else {
166 ALOGE(
167 "%s: Can't find stream_id_for_group %d for stream %d in frame %u "
168 "result holder. It may have been returned or have not been "
169 "requested.",
170 __FUNCTION__, stream_id_for_group, stream_id, frame_number);
171 }
172 } else {
173 ALOGE(
174 "%s: Can't find stream %d in frame %u result holder. It may"
175 " have been returned or have not been requested.",
176 __FUNCTION__, stream_id, frame_number);
177 }
178 // Ignore this buffer and continue handling other buffers in the
179 // result.
180 } else {
181 streams.erase(stream_id);
182 }
183 }
184
185 if (streams.empty()) {
186 pending_request_streams_.erase(frame_number);
187 }
188
189 if (pending_request_streams_.empty()) {
190 status_t res = stream_buffer_cache_manager_->NotifyFlushingAll();
191 if (res != OK) {
192 ALOGE("%s: Failed to notify SBC manager to flush all streams.",
193 __FUNCTION__);
194 }
195 ALOGI(
196 "%s: [sbc] All inflight requests/streams cleared. Notified SBC for "
197 "flushing.",
198 __FUNCTION__);
199 }
200 return OK;
201 }
202
ProcessCaptureResult(std::unique_ptr<CaptureResult> result)203 void CameraDeviceSession::ProcessCaptureResult(
204 std::unique_ptr<CaptureResult> result) {
205 if (TryHandleCaptureResult(result)) return;
206
207 // Update pending request tracker with returned buffers.
208 std::vector<StreamBuffer> buffers;
209 buffers.insert(buffers.end(), result->output_buffers.begin(),
210 result->output_buffers.end());
211
212 if (result->result_metadata) {
213 std::lock_guard<std::mutex> lock(request_record_lock_);
214 pending_results_.erase(result->frame_number);
215 }
216
217 {
218 std::shared_lock lock(session_callback_lock_);
219 session_callback_.process_capture_result(std::move(result));
220 }
221
222 TrackReturnedBuffers(buffers);
223 }
224
ProcessBatchCaptureResult(std::vector<std::unique_ptr<CaptureResult>> results)225 void CameraDeviceSession::ProcessBatchCaptureResult(
226 std::vector<std::unique_ptr<CaptureResult>> results) {
227 std::vector<std::unique_ptr<CaptureResult>> results_to_callback;
228 results_to_callback.reserve(results.size());
229 std::vector<StreamBuffer> buffers;
230 for (auto& result : results) {
231 if (TryHandleCaptureResult(result)) continue;
232
233 // Update pending request tracker with returned buffers.
234 buffers.insert(buffers.end(), result->output_buffers.begin(),
235 result->output_buffers.end());
236
237 if (result->result_metadata) {
238 std::lock_guard<std::mutex> lock(request_record_lock_);
239 pending_results_.erase(result->frame_number);
240 }
241
242 results_to_callback.push_back(std::move(result));
243 }
244
245 {
246 std::shared_lock lock(session_callback_lock_);
247 session_callback_.process_batch_capture_result(
248 std::move(results_to_callback));
249 }
250
251 TrackReturnedBuffers(buffers);
252 }
253
Notify(const NotifyMessage & result)254 void CameraDeviceSession::Notify(const NotifyMessage& result) {
255 {
256 uint32_t frame_number = 0;
257 if (result.type == MessageType::kError) {
258 frame_number = result.message.error.frame_number;
259 } else if (result.type == MessageType::kShutter) {
260 frame_number = result.message.shutter.frame_number;
261 }
262 std::lock_guard<std::mutex> lock(request_record_lock_);
263 // Strip out results for frame number that has been notified
264 // ErrorCode::kErrorResult and ErrorCode::kErrorBuffer
265 if ((error_notified_requests_.find(frame_number) !=
266 error_notified_requests_.end()) &&
267 (result.type != MessageType::kShutter)) {
268 return;
269 }
270
271 if (result.type == MessageType::kError &&
272 result.message.error.error_code == ErrorCode::kErrorResult) {
273 pending_results_.erase(frame_number);
274
275 if (ignore_shutters_.find(frame_number) == ignore_shutters_.end()) {
276 ignore_shutters_.insert(frame_number);
277 }
278 }
279
280 if (result.type == MessageType::kShutter) {
281 if (ignore_shutters_.find(frame_number) != ignore_shutters_.end()) {
282 ignore_shutters_.erase(frame_number);
283 return;
284 }
285 }
286 }
287
288 if (ATRACE_ENABLED() && result.type == MessageType::kShutter) {
289 int64_t timestamp_ns_diff = 0;
290 int64_t current_timestamp_ns = result.message.shutter.timestamp_ns;
291 if (last_timestamp_ns_for_trace_ != 0) {
292 timestamp_ns_diff = current_timestamp_ns - last_timestamp_ns_for_trace_;
293 }
294
295 last_timestamp_ns_for_trace_ = current_timestamp_ns;
296
297 ATRACE_INT64("sensor_timestamp_diff", timestamp_ns_diff);
298 ATRACE_INT("timestamp_frame_number", result.message.shutter.frame_number);
299 }
300
301 std::shared_lock lock(session_callback_lock_);
302 session_callback_.notify(result);
303 }
304
InitializeCallbacks()305 void CameraDeviceSession::InitializeCallbacks() {
306 std::lock_guard lock(session_callback_lock_);
307
308 // Initialize callback to
309 session_callback_.process_capture_result =
310 ProcessCaptureResultFunc([](std::unique_ptr<CaptureResult> /*result*/) {
311 ALOGW("%s: No session callback was set.", __FUNCTION__);
312 });
313
314 session_callback_.notify = NotifyFunc([](const NotifyMessage& /*message*/) {
315 ALOGW("%s: No session callback was set.", __FUNCTION__);
316 });
317
318 session_callback_.request_stream_buffers = RequestStreamBuffersFunc(
319 [](const std::vector<BufferRequest>& /*hal_buffer_requests*/,
320 std::vector<BufferReturn>* /*hal_buffer_returns*/) {
321 ALOGW("%s: No session callback was set.", __FUNCTION__);
322 return google_camera_hal::BufferRequestStatus::kFailedUnknown;
323 });
324
325 session_callback_.return_stream_buffers = ReturnStreamBuffersFunc(
326 [](const std::vector<StreamBuffer>& /*return_hal_buffers*/) {
327 ALOGW("%s: No session callback was set.", __FUNCTION__);
328 return google_camera_hal::BufferRequestStatus::kFailedUnknown;
329 });
330
331 camera_device_session_callback_.process_capture_result =
332 ProcessCaptureResultFunc([this](std::unique_ptr<CaptureResult> result) {
333 ProcessCaptureResult(std::move(result));
334 });
335
336 camera_device_session_callback_.process_batch_capture_result =
337 ProcessBatchCaptureResultFunc(
338 [this](std::vector<std::unique_ptr<CaptureResult>> results) {
339 ProcessBatchCaptureResult(std::move(results));
340 });
341
342 camera_device_session_callback_.notify =
343 NotifyFunc([this](const NotifyMessage& result) { Notify(result); });
344
345 hwl_session_callback_.request_stream_buffers = HwlRequestBuffersFunc(
346 [this](int32_t stream_id, uint32_t num_buffers,
347 std::vector<StreamBuffer>* buffers, uint32_t frame_number) {
348 return RequestBuffersFromStreamBufferCacheManager(
349 stream_id, num_buffers, buffers, frame_number);
350 });
351
352 hwl_session_callback_.return_stream_buffers =
353 HwlReturnBuffersFunc([this](const std::vector<StreamBuffer>& buffers) {
354 return ReturnStreamBuffers(buffers);
355 });
356
357 device_session_hwl_->SetSessionCallback(hwl_session_callback_);
358 }
359
InitializeBufferManagement(HalCameraMetadata * characteristics)360 status_t CameraDeviceSession::InitializeBufferManagement(
361 HalCameraMetadata* characteristics) {
362 ATRACE_CALL();
363
364 if (characteristics == nullptr) {
365 ALOGE("%s: characteristics cannot be nullptr.", __FUNCTION__);
366 return BAD_VALUE;
367 }
368
369 camera_metadata_ro_entry entry = {};
370 status_t res = characteristics->Get(
371 ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION, &entry);
372 if (res == OK && entry.count > 0) {
373 buffer_management_used_ =
374 (entry.data.u8[0] ==
375 ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION_HIDL_DEVICE_3_5);
376 session_buffer_management_supported_ =
377 (entry.data.u8[0] ==
378 ANDROID_INFO_SUPPORTED_BUFFER_MANAGEMENT_VERSION_SESSION_CONFIGURABLE);
379 }
380
381 return OK;
382 }
383
Initialize(std::unique_ptr<CameraDeviceSessionHwl> device_session_hwl,CameraBufferAllocatorHwl * camera_allocator_hwl,std::vector<GetCaptureSessionFactoryFunc> external_session_factory_entries)384 status_t CameraDeviceSession::Initialize(
385 std::unique_ptr<CameraDeviceSessionHwl> device_session_hwl,
386 CameraBufferAllocatorHwl* camera_allocator_hwl,
387 std::vector<GetCaptureSessionFactoryFunc> external_session_factory_entries) {
388 ATRACE_CALL();
389 if (device_session_hwl == nullptr) {
390 ALOGE("%s: device_session_hwl cannot be nullptr.", __FUNCTION__);
391 return BAD_VALUE;
392 }
393 measure_buffer_allocation_time_ =
394 property_get_bool(kMeasureBufferAllocationProp, false);
395 ALOGI("%s: measure buffer allocation time: %d ", __FUNCTION__,
396 measure_buffer_allocation_time_);
397
398 camera_id_ = device_session_hwl->GetCameraId();
399 device_session_hwl_ = std::move(device_session_hwl);
400 camera_allocator_hwl_ = camera_allocator_hwl;
401
402 GraphicBufferMapper::preloadHal();
403 InitializeCallbacks();
404
405 std::unique_ptr<google_camera_hal::HalCameraMetadata> characteristics;
406 status_t res = device_session_hwl_->GetCameraCharacteristics(&characteristics);
407 if (res != OK) {
408 ALOGE("%s: Get camera characteristics failed: %s(%d)", __FUNCTION__,
409 strerror(-res), res);
410 return res;
411 }
412
413 res = utils::GetStreamUseCases(
414 characteristics.get(),
415 &camera_id_to_stream_use_cases_[device_session_hwl_->GetCameraId()]);
416 if (res != OK) {
417 ALOGE("%s: Initializing stream use case failed: %s(%d) for camera id %u",
418 __FUNCTION__, strerror(-res), res, device_session_hwl_->GetCameraId());
419 return res;
420 }
421
422 res = utils::GetPhysicalCameraStreamUseCases(device_session_hwl_.get(),
423 &camera_id_to_stream_use_cases_);
424 if (res != OK) {
425 ALOGE(
426 "%s: Initializing physical stream use cases failed: %s(%d) for camera "
427 "id %u",
428 __FUNCTION__, strerror(-res), res, device_session_hwl_->GetCameraId());
429 return res;
430 }
431 res = InitializeBufferManagement(characteristics.get());
432 if (res != OK) {
433 ALOGE("%s: Initialize buffer management failed: %s(%d)", __FUNCTION__,
434 strerror(-res), res);
435 return res;
436 }
437
438 res = LoadExternalCaptureSession(external_session_factory_entries);
439 if (res != OK) {
440 ALOGE("%s: Loading external capture sessions failed: %s(%d)", __FUNCTION__,
441 strerror(-res), res);
442 return res;
443 }
444
445 InitializeZoomRatioMapper(characteristics.get());
446
447 return OK;
448 }
449
GetMaxResDimension(const HalCameraMetadata * characteristics,Dimension & max_res_dimension)450 status_t GetMaxResDimension(const HalCameraMetadata* characteristics,
451 Dimension& max_res_dimension) {
452 Rect active_array_maximum_resolution_size;
453 status_t max_res_status = utils::GetSensorActiveArraySize(
454 characteristics, &active_array_maximum_resolution_size,
455 /*maximum_resolution*/ true);
456 if (max_res_status == OK) {
457 max_res_dimension = {active_array_maximum_resolution_size.right -
458 active_array_maximum_resolution_size.left + 1,
459 active_array_maximum_resolution_size.bottom -
460 active_array_maximum_resolution_size.top + 1};
461 }
462 return max_res_status;
463 }
464
InitializeZoomRatioMapper(HalCameraMetadata * characteristics)465 void CameraDeviceSession::InitializeZoomRatioMapper(
466 HalCameraMetadata* characteristics) {
467 if (characteristics == nullptr) {
468 ALOGE("%s: characteristics cannot be nullptr.", __FUNCTION__);
469 return;
470 }
471
472 Rect active_array_size;
473 status_t res =
474 utils::GetSensorActiveArraySize(characteristics, &active_array_size,
475 /*maximum_resolution*/ false);
476 if (res != OK) {
477 ALOGE("%s: Failed to get the active array size: %s(%d)", __FUNCTION__,
478 strerror(-res), res);
479 return;
480 }
481
482 ZoomRatioMapper::InitParams params;
483 params.camera_id = camera_id_;
484 params.active_array_dimension = {
485 active_array_size.right - active_array_size.left + 1,
486 active_array_size.bottom - active_array_size.top + 1};
487
488 // Populate max-res dimension only if the logical camera have max-res resolution
489 (void)GetMaxResDimension(characteristics,
490 params.active_array_maximum_resolution_dimension);
491
492 std::vector<uint32_t> physical_camera_ids =
493 device_session_hwl_->GetPhysicalCameraIds();
494 for (uint32_t id : physical_camera_ids) {
495 std::unique_ptr<google_camera_hal::HalCameraMetadata>
496 physical_cam_characteristics;
497 res = device_session_hwl_->GetPhysicalCameraCharacteristics(
498 id, &physical_cam_characteristics);
499 if (res != OK) {
500 ALOGE("%s: Get camera: %u characteristics failed: %s(%d)", __FUNCTION__,
501 id, strerror(-res), res);
502 return;
503 }
504
505 res = utils::GetSensorActiveArraySize(physical_cam_characteristics.get(),
506 &active_array_size,
507 /*maximum_resolution*/ false);
508 if (res != OK) {
509 ALOGE("%s: Failed to get cam: %u, active array size: %s(%d)",
510 __FUNCTION__, id, strerror(-res), res);
511 return;
512 }
513 Dimension active_array_dimension = {
514 active_array_size.right - active_array_size.left + 1,
515 active_array_size.bottom - active_array_size.top + 1};
516 params.physical_cam_active_array_dimension.emplace(id,
517 active_array_dimension);
518 Dimension max_res_dimension;
519 if (GetMaxResDimension(physical_cam_characteristics.get(),
520 max_res_dimension) == OK) {
521 params.physical_cam_active_array_maximum_resolution_dimension.emplace(
522 id, max_res_dimension);
523 }
524 }
525
526 res = utils::GetZoomRatioRange(characteristics, ¶ms.zoom_ratio_range);
527 if (res != OK) {
528 ALOGW("%s: Failed to get the zoom ratio range: %s(%d)", __FUNCTION__,
529 strerror(-res), res);
530 return;
531 }
532
533 params.zoom_ratio_mapper_hwl = device_session_hwl_->GetZoomRatioMapperHwl();
534
535 zoom_ratio_mapper_.Initialize(¶ms);
536 }
537
DeriveGroupedStreamIdMap()538 void CameraDeviceSession::DeriveGroupedStreamIdMap() {
539 // Group stream ids by stream group id
540 std::unordered_map<int32_t, std::vector<int32_t>> group_to_streams_map;
541 for (const auto& [stream_id, stream] : configured_streams_map_) {
542 if (stream.stream_type == StreamType::kOutput && stream.group_id != -1) {
543 group_to_streams_map[stream.group_id].push_back(stream_id);
544 }
545 }
546
547 // For each stream group, map all the streams' ids to one id
548 for (const auto& [group_id, stream_ids] : group_to_streams_map) {
549 for (size_t i = 1; i < stream_ids.size(); i++) {
550 grouped_stream_id_map_[stream_ids[i]] = stream_ids[0];
551 }
552 }
553 }
554
LoadExternalCaptureSession(std::vector<GetCaptureSessionFactoryFunc> external_session_factory_entries)555 status_t CameraDeviceSession::LoadExternalCaptureSession(
556 std::vector<GetCaptureSessionFactoryFunc> external_session_factory_entries) {
557 ATRACE_CALL();
558
559 if (external_capture_session_entries_.size() > 0) {
560 ALOGI("%s: External capture session libraries already loaded; skip.",
561 __FUNCTION__);
562 return OK;
563 }
564
565 for (const auto& external_session_factory_t :
566 external_session_factory_entries) {
567 ExternalCaptureSessionFactory* external_session =
568 external_session_factory_t();
569 if (!external_session) {
570 ALOGE("%s: External session may be incomplete", __FUNCTION__);
571 continue;
572 }
573
574 external_capture_session_entries_.push_back(external_session);
575 }
576
577 return OK;
578 }
579
~CameraDeviceSession()580 CameraDeviceSession::~CameraDeviceSession() {
581 UnregisterThermalCallback();
582
583 capture_session_ = nullptr;
584 device_session_hwl_ = nullptr;
585
586 for (auto external_session : external_capture_session_entries_) {
587 delete external_session;
588 }
589 external_capture_session_entries_.clear();
590
591 FreeImportedBufferHandles();
592 }
593
UnregisterThermalCallback()594 void CameraDeviceSession::UnregisterThermalCallback() {
595 std::shared_lock lock(session_callback_lock_);
596 if (thermal_callback_.unregister_thermal_changed_callback != nullptr) {
597 thermal_callback_.unregister_thermal_changed_callback();
598 }
599 }
600
SetSessionCallback(const CameraDeviceSessionCallback & session_callback,const ThermalCallback & thermal_callback)601 void CameraDeviceSession::SetSessionCallback(
602 const CameraDeviceSessionCallback& session_callback,
603 const ThermalCallback& thermal_callback) {
604 ATRACE_CALL();
605 std::lock_guard lock(session_callback_lock_);
606 session_callback_ = session_callback;
607 thermal_callback_ = thermal_callback;
608
609 status_t res = thermal_callback_.register_thermal_changed_callback(
610 NotifyThrottlingFunc([this](const Temperature& temperature) {
611 NotifyThrottling(temperature);
612 }),
613 /*filter_type=*/false,
614 /*type=*/TemperatureType::kUnknown);
615 if (res != OK) {
616 ALOGW("%s: Registering thermal callback failed: %s(%d)", __FUNCTION__,
617 strerror(-res), res);
618 }
619 }
620
NotifyThrottling(const Temperature & temperature)621 void CameraDeviceSession::NotifyThrottling(const Temperature& temperature) {
622 switch (temperature.throttling_status) {
623 case ThrottlingSeverity::kNone:
624 case ThrottlingSeverity::kLight:
625 case ThrottlingSeverity::kModerate:
626 ALOGI("%s: temperature type: %d, severity: %u, value: %f", __FUNCTION__,
627 temperature.type, temperature.throttling_status, temperature.value);
628 return;
629 case ThrottlingSeverity::kSevere:
630 case ThrottlingSeverity::kCritical:
631 case ThrottlingSeverity::kEmergency:
632 case ThrottlingSeverity::kShutdown:
633 ALOGW("%s: temperature type: %d, severity: %u, value: %f", __FUNCTION__,
634 temperature.type, temperature.throttling_status, temperature.value);
635 {
636 std::lock_guard<std::mutex> lock(session_lock_);
637 thermal_throttling_ = true;
638 }
639 return;
640 default:
641 ALOGE("%s: Unknown throttling status %u for type %d", __FUNCTION__,
642 temperature.throttling_status, temperature.type);
643 return;
644 }
645 }
646
ConstructDefaultRequestSettings(RequestTemplate type,std::unique_ptr<HalCameraMetadata> * default_settings)647 status_t CameraDeviceSession::ConstructDefaultRequestSettings(
648 RequestTemplate type, std::unique_ptr<HalCameraMetadata>* default_settings) {
649 ATRACE_CALL();
650 status_t res = device_session_hwl_->ConstructDefaultRequestSettings(
651 type, default_settings);
652 if (res != OK) {
653 ALOGE("%s: Construct default settings for type %d failed: %s(%d)",
654 __FUNCTION__, type, strerror(-res), res);
655 return res;
656 }
657
658 return hal_vendor_tag_utils::ModifyDefaultRequestSettings(
659 type, default_settings->get());
660 }
661
ConfigureStreams(const StreamConfiguration & stream_config,bool v2,ConfigureStreamsReturn * configured_streams)662 status_t CameraDeviceSession::ConfigureStreams(
663 const StreamConfiguration& stream_config, bool v2,
664 ConfigureStreamsReturn* configured_streams) {
665 ATRACE_CALL();
666 bool set_realtime_thread = false;
667 int32_t schedule_policy;
668 struct sched_param schedule_param = {0};
669 if (configured_streams == nullptr) {
670 ALOGE("%s: configured_streams output is nullptr", __FUNCTION__);
671 return BAD_VALUE;
672 }
673 std::vector<HalStream>& hal_config = configured_streams->hal_streams;
674 if (utils::SupportRealtimeThread()) {
675 bool get_thread_schedule = false;
676 if (pthread_getschedparam(pthread_self(), &schedule_policy,
677 &schedule_param) == 0) {
678 get_thread_schedule = true;
679 } else {
680 ALOGE("%s: pthread_getschedparam fail", __FUNCTION__);
681 }
682
683 if (get_thread_schedule) {
684 status_t res = utils::SetRealtimeThread(pthread_self());
685 if (res != OK) {
686 ALOGE("%s: SetRealtimeThread fail", __FUNCTION__);
687 } else {
688 set_realtime_thread = true;
689 }
690 }
691 }
692
693 std::lock_guard<std::mutex> lock(session_lock_);
694
695 std::lock_guard lock_capture_session(capture_session_lock_);
696 if (capture_session_ != nullptr) {
697 ATRACE_NAME("CameraDeviceSession::DestroyOldSession");
698 capture_session_ = nullptr;
699 }
700
701 pending_requests_tracker_ = nullptr;
702
703 if (!configured_streams_map_.empty()) {
704 CleanupStaleStreamsLocked(stream_config.streams);
705 }
706 hal_buffer_managed_stream_ids_.clear();
707
708 hal_utils::DumpStreamConfiguration(stream_config, "App stream configuration");
709
710 multi_res_reprocess_ = stream_config.multi_resolution_input_image;
711
712 // TODO: We would ideally want this to be a part of CreateCaptureSession,
713 // which internally calls IsStreamCombinationSupported. However this
714 // IsStreamCombinationSupported doesn't match the
715 // CameraDevice::IsStreamCombination. We should look at unifying the two for a
716 // potentially cleaner code-base.
717 if (!utils::IsStreamUseCaseSupported(stream_config, camera_id_,
718 camera_id_to_stream_use_cases_)) {
719 return BAD_VALUE;
720 }
721 device_session_hwl_->setConfigureStreamsV2(v2);
722 bool multi_resolution_stream_used = false;
723 for (const auto& stream : stream_config.streams) {
724 if (stream.group_id != -1) {
725 multi_resolution_stream_used = true;
726 break;
727 }
728 }
729 capture_session_ = CreateCaptureSession(
730 stream_config, kWrapperCaptureSessionEntries,
731 external_capture_session_entries_, kCaptureSessionEntries,
732 hwl_session_callback_, camera_allocator_hwl_, device_session_hwl_.get(),
733 &hal_config, camera_device_session_callback_.process_capture_result,
734 camera_device_session_callback_.notify,
735 camera_device_session_callback_.process_batch_capture_result);
736
737 if (capture_session_ == nullptr) {
738 ALOGE("%s: Cannot find a capture session compatible with stream config",
739 __FUNCTION__);
740 if (set_realtime_thread) {
741 utils::UpdateThreadSched(pthread_self(), schedule_policy, &schedule_param);
742 }
743 return BAD_VALUE;
744 }
745 // Backup the streams received from frameworks into configured_streams_map_,
746 // and we can find out specific streams through stream id in output_buffers.
747 for (auto& stream : stream_config.streams) {
748 configured_streams_map_[stream.id] = stream;
749 }
750 if (session_buffer_management_supported_ && v2) {
751 std::set<int32_t> hal_buffer_managed_stream_ids =
752 device_session_hwl_->GetHalBufferManagedStreams(stream_config);
753 hal_buffer_managed_stream_ids_ = hal_buffer_managed_stream_ids;
754 for (auto& hal_stream : hal_config) {
755 if (hal_buffer_managed_stream_ids.find(hal_stream.id) !=
756 hal_buffer_managed_stream_ids.end()) {
757 hal_stream.is_hal_buffer_managed = true;
758 }
759 }
760 } else if (buffer_management_used_ || multi_resolution_stream_used) {
761 // No session specific hal buffer manager supported, all streams are
762 // hal buffer managed. In the case of multi resolution streams we also
763 // are mandated to use hal buffer manager (VTS asserts for this)
764 for (auto& hal_stream : hal_config) {
765 if (configured_streams_map_.find(hal_stream.id) ==
766 configured_streams_map_.end()) {
767 ALOGE("%s: HalStream id %d not found in configured streams map",
768 __FUNCTION__, hal_stream.id);
769 return UNKNOWN_ERROR;
770 }
771 if (configured_streams_map_[hal_stream.id].stream_type ==
772 StreamType::kInput) {
773 continue;
774 }
775 hal_stream.is_hal_buffer_managed = true;
776 hal_buffer_managed_stream_ids_.insert(hal_stream.id);
777 }
778 }
779
780 stream_buffer_cache_manager_ =
781 StreamBufferCacheManager::Create(hal_buffer_managed_stream_ids_);
782 if (stream_buffer_cache_manager_ == nullptr) {
783 ALOGE("%s: Failed to create stream buffer cache manager.", __FUNCTION__);
784 if (set_realtime_thread) {
785 utils::UpdateThreadSched(pthread_self(), schedule_policy, &schedule_param);
786 }
787 return UNKNOWN_ERROR;
788 }
789 if (hal_buffer_managed_stream_ids_.size() != 0) {
790 status_t res =
791 RegisterStreamsIntoCacheManagerLocked(stream_config, hal_config);
792 if (res != OK) {
793 ALOGE("%s: Failed to register streams into stream buffer cache manager.",
794 __FUNCTION__);
795 if (set_realtime_thread) {
796 utils::UpdateThreadSched(pthread_self(), schedule_policy,
797 &schedule_param);
798 }
799 return res;
800 }
801 }
802
803 // (b/129561652): Framework assumes HalStream is sorted.
804 std::sort(hal_config.begin(), hal_config.end(),
805 [](const HalStream& a, const HalStream& b) { return a.id < b.id; });
806
807 // Derives all stream ids within a group to a representative stream id
808 DeriveGroupedStreamIdMap();
809
810 // If buffer management is support, create a pending request tracker for
811 // capture request throttling.
812 pending_requests_tracker_ = PendingRequestsTracker::Create(
813 hal_config, grouped_stream_id_map_, hal_buffer_managed_stream_ids_);
814 if (pending_requests_tracker_ == nullptr) {
815 ALOGE("%s: Cannot create a pending request tracker.", __FUNCTION__);
816 if (set_realtime_thread) {
817 utils::UpdateThreadSched(pthread_self(), schedule_policy, &schedule_param);
818 }
819 return UNKNOWN_ERROR;
820 }
821
822 {
823 std::lock_guard<std::mutex> request_lock(request_record_lock_);
824 pending_request_streams_.clear();
825 error_notified_requests_.clear();
826 dummy_buffer_observed_.clear();
827 pending_results_.clear();
828 ignore_shutters_.clear();
829 }
830
831 has_valid_settings_ = false;
832 thermal_throttling_ = false;
833 thermal_throttling_notified_ = false;
834 last_request_settings_ = nullptr;
835 last_timestamp_ns_for_trace_ = 0;
836
837 if (set_realtime_thread) {
838 utils::UpdateThreadSched(pthread_self(), schedule_policy, &schedule_param);
839 }
840 return OK;
841 }
842
UpdateBufferHandlesLocked(std::vector<StreamBuffer> * buffers,bool update_hal_buffer_managed_streams)843 status_t CameraDeviceSession::UpdateBufferHandlesLocked(
844 std::vector<StreamBuffer>* buffers, bool update_hal_buffer_managed_streams) {
845 ATRACE_CALL();
846 if (buffers == nullptr) {
847 ALOGE("%s: buffers cannot be nullptr", __FUNCTION__);
848 return BAD_VALUE;
849 }
850
851 for (auto& buffer : *buffers) {
852 bool is_hal_buffer_managed =
853 hal_buffer_managed_stream_ids_.find(buffer.stream_id) !=
854 hal_buffer_managed_stream_ids_.end();
855 // Skip the update if import_hal_buffer_managed_streams doesn't match the
856 // stream ids hal buffer manager behavior.
857 bool skip = (!is_hal_buffer_managed && update_hal_buffer_managed_streams) ||
858 (!update_hal_buffer_managed_streams && is_hal_buffer_managed);
859 if (skip) {
860 continue;
861 }
862 // Get the buffer handle from buffer handle map.
863 BufferCache buffer_cache = {buffer.stream_id, buffer.buffer_id};
864 auto buffer_handle_it = imported_buffer_handle_map_.find(buffer_cache);
865 if (buffer_handle_it == imported_buffer_handle_map_.end()) {
866 ALOGE("%s: Cannot find buffer handle for stream %u, buffer %" PRIu64,
867 __FUNCTION__, buffer.stream_id, buffer.buffer_id);
868 return NAME_NOT_FOUND;
869 }
870
871 buffer.buffer = buffer_handle_it->second;
872 }
873
874 return OK;
875 }
876
CreateCaptureRequestLocked(const CaptureRequest & request,CaptureRequest * updated_request)877 status_t CameraDeviceSession::CreateCaptureRequestLocked(
878 const CaptureRequest& request, CaptureRequest* updated_request) {
879 ATRACE_CALL();
880 if (updated_request == nullptr) {
881 return BAD_VALUE;
882 }
883
884 if (request.settings != nullptr) {
885 last_request_settings_ = HalCameraMetadata::Clone(request.settings.get());
886 }
887
888 updated_request->frame_number = request.frame_number;
889 updated_request->settings = HalCameraMetadata::Clone(request.settings.get());
890 updated_request->input_buffers = request.input_buffers;
891 updated_request->input_buffer_metadata.clear();
892 updated_request->output_buffers = request.output_buffers;
893 std::vector<uint32_t> physical_camera_ids =
894 device_session_hwl_->GetPhysicalCameraIds();
895 for (auto& [camid, physical_setting] : request.physical_camera_settings) {
896 if (std::find(physical_camera_ids.begin(), physical_camera_ids.end(),
897 camid) == physical_camera_ids.end()) {
898 ALOGE("%s: Pyhsical camera id %d in request had not registered",
899 __FUNCTION__, camid);
900 return BAD_VALUE;
901 }
902 updated_request->physical_camera_settings[camid] =
903 HalCameraMetadata::Clone(physical_setting.get());
904 }
905 updated_request->input_width = request.input_width;
906 updated_request->input_height = request.input_height;
907
908 // Returns -1 if kThermalThrottling is not defined, skip following process.
909 if (get_camera_metadata_tag_type(VendorTagIds::kThermalThrottling) != -1) {
910 // Create settings to set thermal throttling key if needed.
911 if (thermal_throttling_ && !thermal_throttling_notified_ &&
912 updated_request->settings == nullptr) {
913 updated_request->settings =
914 HalCameraMetadata::Clone(last_request_settings_.get());
915 thermal_throttling_notified_ = true;
916 }
917
918 if (updated_request->settings != nullptr) {
919 status_t res = updated_request->settings->Set(
920 VendorTagIds::kThermalThrottling, &thermal_throttling_,
921 /*data_count=*/1);
922 if (res != OK) {
923 ALOGE("%s: Setting thermal throttling key failed: %s(%d)", __FUNCTION__,
924 strerror(-res), res);
925 return res;
926 }
927 }
928 }
929
930 AppendOutputIntentToSettingsLocked(request, updated_request);
931
932 {
933 std::lock_guard<std::mutex> lock(imported_buffer_handle_map_lock_);
934
935 status_t res = UpdateBufferHandlesLocked(&updated_request->input_buffers);
936 if (res != OK) {
937 ALOGE("%s: Updating input buffer handles failed: %s(%d)", __FUNCTION__,
938 strerror(-res), res);
939 return res;
940 }
941
942 res = UpdateBufferHandlesLocked(&updated_request->output_buffers);
943 if (res != OK) {
944 ALOGE("%s: Updating output buffer handles failed: %s(%d)", __FUNCTION__,
945 strerror(-res), res);
946 return res;
947 }
948 }
949
950 zoom_ratio_mapper_.UpdateCaptureRequest(updated_request);
951
952 return OK;
953 }
954
ImportBufferHandleLocked(const StreamBuffer & buffer)955 status_t CameraDeviceSession::ImportBufferHandleLocked(
956 const StreamBuffer& buffer) {
957 ATRACE_CALL();
958 buffer_handle_t imported_buffer_handle;
959
960 status_t status = GraphicBufferMapper::get().importBufferNoValidate(
961 buffer.buffer, &imported_buffer_handle);
962 if (status != OK) {
963 ALOGE("%s: Importing buffer failed: %s", __FUNCTION__,
964 ::android::statusToString(status).c_str());
965 return UNKNOWN_ERROR;
966 }
967
968 BufferCache buffer_cache = {buffer.stream_id, buffer.buffer_id};
969 return AddImportedBufferHandlesLocked(buffer_cache, imported_buffer_handle);
970 }
971
ImportBufferHandles(const std::vector<StreamBuffer> & buffers)972 status_t CameraDeviceSession::ImportBufferHandles(
973 const std::vector<StreamBuffer>& buffers) {
974 ATRACE_CALL();
975 std::lock_guard<std::mutex> lock(imported_buffer_handle_map_lock_);
976
977 // Import buffers that are new to HAL.
978 for (auto& buffer : buffers) {
979 bool is_hal_buffer_managed =
980 hal_buffer_managed_stream_ids_.find(buffer.stream_id) !=
981 hal_buffer_managed_stream_ids_.end();
982 // Skip the update if import_hal_buffer_managed_streams doesn't match the
983 // stream ids hal buffer manager behavior.
984 if (is_hal_buffer_managed) {
985 ALOGV(
986 "%s: Buffer management is enabled. Skip importing buffer for stream "
987 "id"
988 " %d in request ",
989 __FUNCTION__, buffer.stream_id);
990 continue;
991 }
992 if (!IsBufferImportedLocked(buffer.stream_id, buffer.buffer_id)) {
993 status_t res = ImportBufferHandleLocked(buffer);
994
995 if (res != OK) {
996 ALOGE("%s: Importing buffer %" PRIu64 " from stream %d failed: %s(%d)",
997 __FUNCTION__, buffer.buffer_id, buffer.stream_id, strerror(-res),
998 res);
999 return res;
1000 }
1001 }
1002 }
1003
1004 return OK;
1005 }
1006
ImportRequestBufferHandles(const CaptureRequest & request)1007 status_t CameraDeviceSession::ImportRequestBufferHandles(
1008 const CaptureRequest& request) {
1009 ATRACE_CALL();
1010
1011 status_t res = ImportBufferHandles(request.input_buffers);
1012 if (res != OK) {
1013 ALOGE("%s: Importing input buffer handles failed: %s(%d)", __FUNCTION__,
1014 strerror(-res), res);
1015 return res;
1016 }
1017
1018 res = ImportBufferHandles(request.output_buffers);
1019 if (res != OK) {
1020 ALOGE("%s: Importing output buffer handles failed: %s(%d)", __FUNCTION__,
1021 strerror(-res), res);
1022 return res;
1023 }
1024
1025 return OK;
1026 }
1027
NotifyErrorMessage(uint32_t frame_number,int32_t stream_id,ErrorCode error_code)1028 void CameraDeviceSession::NotifyErrorMessage(uint32_t frame_number,
1029 int32_t stream_id,
1030 ErrorCode error_code) {
1031 ALOGI("%s: [sbc] Request %d with stream (%d), return error code (%d)",
1032 __FUNCTION__, frame_number, stream_id, error_code);
1033
1034 if ((error_code == ErrorCode::kErrorResult ||
1035 error_code == ErrorCode::kErrorRequest) &&
1036 stream_id != kInvalidStreamId) {
1037 ALOGW("%s: [sbc] Request %d reset setream id again", __FUNCTION__,
1038 frame_number);
1039 stream_id = kInvalidStreamId;
1040 }
1041 NotifyMessage message = {.type = MessageType::kError,
1042 .message.error = {.frame_number = frame_number,
1043 .error_stream_id = stream_id,
1044 .error_code = error_code}};
1045
1046 std::shared_lock lock(session_callback_lock_);
1047 session_callback_.notify(message);
1048 }
1049
TryHandleDummyResult(CaptureResult * result,bool * result_handled)1050 status_t CameraDeviceSession::TryHandleDummyResult(CaptureResult* result,
1051 bool* result_handled) {
1052 if (result == nullptr || result_handled == nullptr) {
1053 ALOGE("%s: result or result_handled is nullptr.", __FUNCTION__);
1054 return BAD_VALUE;
1055 }
1056
1057 uint32_t frame_number = result->frame_number;
1058 *result_handled = false;
1059 bool need_to_handle_result = false;
1060 bool need_to_notify_error_result = false;
1061 {
1062 std::lock_guard<std::mutex> lock(request_record_lock_);
1063 if (error_notified_requests_.find(frame_number) ==
1064 error_notified_requests_.end()) {
1065 for (auto& stream_buffer : result->output_buffers) {
1066 if (dummy_buffer_observed_.find(stream_buffer.buffer) !=
1067 dummy_buffer_observed_.end()) {
1068 error_notified_requests_.insert(frame_number);
1069 if (pending_results_.find(frame_number) != pending_results_.end()) {
1070 need_to_notify_error_result = true;
1071 pending_results_.erase(frame_number);
1072 if (ignore_shutters_.find(frame_number) == ignore_shutters_.end()) {
1073 ignore_shutters_.insert(frame_number);
1074 }
1075 }
1076 need_to_handle_result = true;
1077 break;
1078 }
1079 }
1080 } else {
1081 need_to_handle_result = true;
1082 }
1083 }
1084
1085 if (need_to_notify_error_result) {
1086 NotifyErrorMessage(frame_number, kInvalidStreamId, ErrorCode::kErrorResult);
1087 }
1088
1089 if (need_to_handle_result) {
1090 for (auto& stream_buffer : result->output_buffers) {
1091 bool is_dummy_buffer = false;
1092 if (hal_buffer_managed_stream_ids_.find(stream_buffer.stream_id) ==
1093 hal_buffer_managed_stream_ids_.end()) {
1094 // No need to handle non HAL buffer managed streams here
1095 continue;
1096 }
1097 {
1098 std::lock_guard<std::mutex> lock(request_record_lock_);
1099 is_dummy_buffer = (dummy_buffer_observed_.find(stream_buffer.buffer) !=
1100 dummy_buffer_observed_.end());
1101 }
1102
1103 uint64_t buffer_id = (is_dummy_buffer ? /*Use invalid for dummy*/ 0
1104 : stream_buffer.buffer_id);
1105 // To avoid publishing duplicated error buffer message, only publish
1106 // it here when getting normal buffer status from HWL
1107 if (stream_buffer.status == BufferStatus::kOk) {
1108 NotifyErrorMessage(frame_number, stream_buffer.stream_id,
1109 ErrorCode::kErrorBuffer);
1110 }
1111 NotifyBufferError(frame_number, stream_buffer.stream_id, buffer_id);
1112 }
1113
1114 std::vector<StreamBuffer> buffers;
1115 buffers.insert(buffers.end(), result->output_buffers.begin(),
1116 result->output_buffers.end());
1117
1118 if (!buffers.empty()) {
1119 if (pending_requests_tracker_->TrackReturnedResultBuffers(buffers) != OK) {
1120 ALOGE("%s: Tracking requested quota buffers failed", __FUNCTION__);
1121 }
1122 std::vector<StreamBuffer> acquired_buffers;
1123 {
1124 std::lock_guard<std::mutex> lock(request_record_lock_);
1125 for (auto& buffer : buffers) {
1126 if (hal_buffer_managed_stream_ids_.find(buffer.stream_id) ==
1127 hal_buffer_managed_stream_ids_.end()) {
1128 // non HAL buffer managed stream buffers are not tracked by pending
1129 // requests tracker
1130 continue;
1131 }
1132 if (dummy_buffer_observed_.find(buffer.buffer) ==
1133 dummy_buffer_observed_.end()) {
1134 acquired_buffers.push_back(buffer);
1135 }
1136 }
1137 }
1138
1139 if (pending_requests_tracker_->TrackReturnedAcquiredBuffers(
1140 acquired_buffers) != OK) {
1141 ALOGE("%s: Tracking requested acquired buffers failed", __FUNCTION__);
1142 }
1143 }
1144 }
1145
1146 *result_handled = need_to_handle_result;
1147 return OK;
1148 }
1149
NotifyBufferError(const CaptureRequest & request)1150 void CameraDeviceSession::NotifyBufferError(const CaptureRequest& request) {
1151 ALOGI("%s: [sbc] Return Buffer Error Status for frame %d", __FUNCTION__,
1152 request.frame_number);
1153
1154 auto result = std::make_unique<CaptureResult>(CaptureResult({}));
1155 result->frame_number = request.frame_number;
1156 for (auto& stream_buffer : request.output_buffers) {
1157 StreamBuffer buffer;
1158 buffer.stream_id = stream_buffer.stream_id;
1159 buffer.status = BufferStatus::kError;
1160 result->output_buffers.push_back(buffer);
1161 }
1162 for (auto& stream_buffer : request.input_buffers) {
1163 result->input_buffers.push_back(stream_buffer);
1164 }
1165 result->partial_result = 1;
1166
1167 std::shared_lock lock(session_callback_lock_);
1168 session_callback_.process_capture_result(std::move(result));
1169 }
1170
NotifyBufferError(uint32_t frame_number,int32_t stream_id,uint64_t buffer_id)1171 void CameraDeviceSession::NotifyBufferError(uint32_t frame_number,
1172 int32_t stream_id,
1173 uint64_t buffer_id) {
1174 ALOGI("%s: [sbc] Return Buffer Error Status for frame %d stream %d",
1175 __FUNCTION__, frame_number, stream_id);
1176
1177 auto result = std::make_unique<CaptureResult>(CaptureResult({}));
1178 result->frame_number = frame_number;
1179 StreamBuffer stream_buffer;
1180 stream_buffer.buffer_id = buffer_id;
1181 stream_buffer.stream_id = stream_id;
1182 stream_buffer.status = BufferStatus::kError;
1183 result->output_buffers.push_back(stream_buffer);
1184 result->partial_result = 1;
1185
1186 std::shared_lock lock(session_callback_lock_);
1187 session_callback_.process_capture_result(std::move(result));
1188 }
1189
HandleSBCInactiveStreams(const CaptureRequest & request,bool * all_active)1190 status_t CameraDeviceSession::HandleSBCInactiveStreams(
1191 const CaptureRequest& request, bool* all_active) {
1192 if (all_active == nullptr) {
1193 ALOGE("%s: all_active is nullptr", __FUNCTION__);
1194 return BAD_VALUE;
1195 }
1196
1197 *all_active = true;
1198 for (auto& stream_buffer : request.output_buffers) {
1199 bool is_hal_buffer_managed =
1200 hal_buffer_managed_stream_ids_.find(stream_buffer.stream_id) !=
1201 hal_buffer_managed_stream_ids_.end();
1202 if (!is_hal_buffer_managed) {
1203 continue;
1204 }
1205 bool is_active = true;
1206 status_t res = stream_buffer_cache_manager_->IsStreamActive(
1207 stream_buffer.stream_id, &is_active);
1208 if (res != OK) {
1209 ALOGE("%s: Failed to check if stream is active, error status: %s(%d)",
1210 __FUNCTION__, strerror(-res), res);
1211 return UNKNOWN_ERROR;
1212 }
1213 if (!is_active) {
1214 ALOGI("%s: Stream %d is not active when submitting frame %d request.",
1215 __FUNCTION__, stream_buffer.stream_id, request.frame_number);
1216 *all_active = false;
1217 break;
1218 }
1219 }
1220 if (*all_active == false) {
1221 NotifyErrorMessage(request.frame_number, kInvalidStreamId,
1222 ErrorCode::kErrorRequest);
1223 NotifyBufferError(request);
1224 }
1225
1226 return OK;
1227 }
1228
CheckRequestForStreamBufferCacheManager(const CaptureRequest & request,bool * need_to_process)1229 void CameraDeviceSession::CheckRequestForStreamBufferCacheManager(
1230 const CaptureRequest& request, bool* need_to_process) {
1231 ATRACE_CALL();
1232
1233 // If any stream in the stream buffer cache manager has been labeld as inactive,
1234 // return ERROR_REQUEST immediately. No need to send the request to HWL.
1235 status_t res = HandleSBCInactiveStreams(request, need_to_process);
1236 if (res != OK) {
1237 ALOGE("%s: Failed to check if streams are active.", __FUNCTION__);
1238 return;
1239 }
1240
1241 // Note: This function should only be called if buffer_management_used_
1242 // is true.
1243 if (pending_request_streams_.empty()) {
1244 pending_requests_tracker_->OnBufferCacheFlushed();
1245 }
1246
1247 // Add streams into pending_request_streams_
1248 uint32_t frame_number = request.frame_number;
1249 if (*need_to_process) {
1250 std::lock_guard<std::mutex> lock(request_record_lock_);
1251 pending_results_.insert(frame_number);
1252 for (auto& stream_buffer : request.output_buffers) {
1253 bool is_hal_buffer_managed =
1254 hal_buffer_managed_stream_ids_.find(stream_buffer.stream_id) !=
1255 hal_buffer_managed_stream_ids_.end();
1256 if (!is_hal_buffer_managed) {
1257 // pending_request_streams_ tracks only hal buffer managed streams.
1258 continue;
1259 }
1260 if (grouped_stream_id_map_.count(stream_buffer.stream_id) == 1) {
1261 pending_request_streams_[frame_number].insert(
1262 grouped_stream_id_map_.at(stream_buffer.stream_id));
1263 } else {
1264 pending_request_streams_[frame_number].insert(stream_buffer.stream_id);
1265 }
1266 }
1267 }
1268 }
1269
ValidateRequestLocked(const CaptureRequest & request)1270 status_t CameraDeviceSession::ValidateRequestLocked(
1271 const CaptureRequest& request) {
1272 // First request must have valid settings.
1273 if (!has_valid_settings_) {
1274 if (request.settings == nullptr ||
1275 request.settings->GetCameraMetadataSize() == 0) {
1276 ALOGE("%s: First request must have valid settings", __FUNCTION__);
1277 return BAD_VALUE;
1278 }
1279
1280 has_valid_settings_ = true;
1281 }
1282
1283 if (request.output_buffers.empty()) {
1284 ALOGE("%s: there is no output buffer.", __FUNCTION__);
1285 return BAD_VALUE;
1286 }
1287
1288 // Check all output streams are configured.
1289 for (auto& buffer : request.input_buffers) {
1290 if (configured_streams_map_.find(buffer.stream_id) ==
1291 configured_streams_map_.end()) {
1292 ALOGE("%s: input stream %d is not configured.", __FUNCTION__,
1293 buffer.stream_id);
1294 return BAD_VALUE;
1295 }
1296 const Stream& input_stream = configured_streams_map_.at(buffer.stream_id);
1297 if (!multi_res_reprocess_ && (request.input_width != input_stream.width ||
1298 request.input_height != input_stream.height)) {
1299 ALOGE("%s: Invalid input size [%d, %d], expected [%d, %d]", __FUNCTION__,
1300 request.input_width, request.input_height, input_stream.width,
1301 input_stream.height);
1302 return BAD_VALUE;
1303 }
1304 }
1305 if (request.input_buffers.size() > 0) {
1306 if (multi_res_reprocess_ &&
1307 (request.input_width == 0 || request.input_height == 0)) {
1308 ALOGE(
1309 "%s: Session is a multi-res input session, but has invalid input "
1310 "size [%d, %d]",
1311 __FUNCTION__, request.input_width, request.input_height);
1312 return BAD_VALUE;
1313 }
1314 }
1315
1316 for (auto& buffer : request.output_buffers) {
1317 if (configured_streams_map_.find(buffer.stream_id) ==
1318 configured_streams_map_.end()) {
1319 ALOGE("%s: output stream %d is not configured.", __FUNCTION__,
1320 buffer.stream_id);
1321 return BAD_VALUE;
1322 }
1323 }
1324
1325 return OK;
1326 }
1327
ProcessCaptureRequest(const std::vector<CaptureRequest> & requests,uint32_t * num_processed_requests)1328 status_t CameraDeviceSession::ProcessCaptureRequest(
1329 const std::vector<CaptureRequest>& requests,
1330 uint32_t* num_processed_requests) {
1331 ATRACE_CALL();
1332 std::lock_guard<std::mutex> lock(session_lock_);
1333 if (num_processed_requests == nullptr) {
1334 return BAD_VALUE;
1335 }
1336
1337 if (requests.empty()) {
1338 ALOGE("%s: requests is empty.", __FUNCTION__);
1339 return BAD_VALUE;
1340 }
1341
1342 status_t res;
1343 *num_processed_requests = 0;
1344
1345 for (auto& request : requests) {
1346 if (ATRACE_ENABLED()) {
1347 ATRACE_INT("request_frame_number", request.frame_number);
1348 }
1349
1350 res = ValidateRequestLocked(request);
1351 if (res != OK) {
1352 ALOGE("%s: Request %d is not valid.", __FUNCTION__, request.frame_number);
1353 return res;
1354 }
1355
1356 res = ImportRequestBufferHandles(request);
1357 if (res != OK) {
1358 ALOGE("%s: Importing request buffer handles failed: %s(%d)", __FUNCTION__,
1359 strerror(-res), res);
1360 return res;
1361 }
1362
1363 CaptureRequest updated_request;
1364 res = CreateCaptureRequestLocked(request, &updated_request);
1365 if (res != OK) {
1366 ALOGE("%s: Updating buffer handles failed for frame %u", __FUNCTION__,
1367 request.frame_number);
1368 return res;
1369 }
1370
1371 bool need_to_process = true;
1372 // If a processCaptureRequest() call is made during flushing,
1373 // notify CAMERA3_MSG_ERROR_REQUEST directly.
1374 if (is_flushing_) {
1375 NotifyErrorMessage(request.frame_number, kInvalidStreamId,
1376 ErrorCode::kErrorRequest);
1377 NotifyBufferError(request);
1378 need_to_process = false;
1379 } else if (hal_buffer_managed_stream_ids_.size() != 0) {
1380 CheckRequestForStreamBufferCacheManager(updated_request, &need_to_process);
1381 }
1382
1383 if (need_to_process) {
1384 // For HAL buffer managed streams, framework does not throttle requests
1385 // with stream's max buffers. We need to throttle on our own.
1386 std::vector<int32_t> first_requested_stream_ids;
1387
1388 res = pending_requests_tracker_->WaitAndTrackRequestBuffers(
1389 updated_request, &first_requested_stream_ids);
1390 if (res != OK) {
1391 ALOGE("%s: Waiting until capture ready failed: %s(%d)", __FUNCTION__,
1392 strerror(-res), res);
1393 return res;
1394 }
1395
1396 for (auto& stream_id : first_requested_stream_ids) {
1397 ALOGI("%s: [sbc] Stream %d 1st req arrived, notify SBC Manager.",
1398 __FUNCTION__, stream_id);
1399 res = stream_buffer_cache_manager_->NotifyProviderReadiness(stream_id);
1400 if (res != OK) {
1401 ALOGE("%s: Notifying provider readiness failed: %s(%d)", __FUNCTION__,
1402 strerror(-res), res);
1403 return res;
1404 }
1405 }
1406
1407 // Check the flush status again to prevent flush being called while we are
1408 // waiting for the request buffers(request throttling).
1409 if (is_flushing_) {
1410 std::vector<StreamBuffer> buffers = updated_request.output_buffers;
1411 {
1412 std::lock_guard<std::mutex> request_lock(request_record_lock_);
1413 pending_request_streams_.erase(updated_request.frame_number);
1414 pending_results_.erase(updated_request.frame_number);
1415 }
1416 NotifyErrorMessage(updated_request.frame_number, kInvalidStreamId,
1417 ErrorCode::kErrorRequest);
1418 NotifyBufferError(updated_request);
1419 if (pending_requests_tracker_->TrackReturnedResultBuffers(buffers) !=
1420 OK) {
1421 ALOGE("%s: Tracking requested quota buffers failed", __FUNCTION__);
1422 }
1423 } else {
1424 std::shared_lock session_lock(capture_session_lock_);
1425 if (capture_session_ == nullptr) {
1426 ALOGE("%s: Capture session wasn't created.", __FUNCTION__);
1427 return NO_INIT;
1428 }
1429
1430 res = capture_session_->ProcessRequest(updated_request);
1431 if (res != OK) {
1432 ALOGE("%s: Submitting request to HWL session failed: %s (%d)",
1433 __FUNCTION__, strerror(-res), res);
1434 return res;
1435 }
1436 }
1437 }
1438
1439 (*num_processed_requests)++;
1440 }
1441
1442 return OK;
1443 }
1444
IsBufferImportedLocked(int32_t stream_id,uint32_t buffer_id)1445 bool CameraDeviceSession::IsBufferImportedLocked(int32_t stream_id,
1446 uint32_t buffer_id) {
1447 BufferCache buffer_cache = {stream_id, buffer_id};
1448 return imported_buffer_handle_map_.find(buffer_cache) !=
1449 imported_buffer_handle_map_.end();
1450 }
1451
AddImportedBufferHandlesLocked(const BufferCache & buffer_cache,buffer_handle_t buffer_handle)1452 status_t CameraDeviceSession::AddImportedBufferHandlesLocked(
1453 const BufferCache& buffer_cache, buffer_handle_t buffer_handle) {
1454 ATRACE_CALL();
1455 auto buffer_handle_it = imported_buffer_handle_map_.find(buffer_cache);
1456 if (buffer_handle_it == imported_buffer_handle_map_.end()) {
1457 // Add a new buffer cache if it doesn't exist.
1458 imported_buffer_handle_map_.emplace(buffer_cache, buffer_handle);
1459 } else if (buffer_handle_it->second != buffer_handle) {
1460 ALOGE(
1461 "%s: Cached buffer handle %p doesn't match %p for stream %u buffer "
1462 "%" PRIu64,
1463 __FUNCTION__, buffer_handle_it->second, buffer_handle,
1464 buffer_cache.stream_id, buffer_cache.buffer_id);
1465 return BAD_VALUE;
1466 }
1467
1468 return OK;
1469 }
1470
RemoveBufferCache(const std::vector<BufferCache> & buffer_caches)1471 void CameraDeviceSession::RemoveBufferCache(
1472 const std::vector<BufferCache>& buffer_caches) {
1473 ATRACE_CALL();
1474 std::lock_guard<std::mutex> lock(imported_buffer_handle_map_lock_);
1475
1476 for (auto& buffer_cache : buffer_caches) {
1477 auto buffer_handle_it = imported_buffer_handle_map_.find(buffer_cache);
1478 if (buffer_handle_it == imported_buffer_handle_map_.end()) {
1479 ALOGW("%s: Could not find buffer cache for stream %u buffer %" PRIu64,
1480 __FUNCTION__, buffer_cache.stream_id, buffer_cache.buffer_id);
1481 continue;
1482 }
1483
1484 device_session_hwl_->RemoveCachedBuffers(buffer_handle_it->second);
1485
1486 status_t res =
1487 GraphicBufferMapper::get().freeBuffer(buffer_handle_it->second);
1488 if (res != OK) {
1489 ALOGE("%s: Freeing imported buffer failed: %s", __FUNCTION__,
1490 ::android::statusToString(res).c_str());
1491 }
1492
1493 imported_buffer_handle_map_.erase(buffer_handle_it);
1494 }
1495 }
1496
FreeBufferHandlesLocked(int32_t stream_id)1497 void CameraDeviceSession::FreeBufferHandlesLocked(int32_t stream_id) {
1498 for (auto buffer_handle_it = imported_buffer_handle_map_.begin();
1499 buffer_handle_it != imported_buffer_handle_map_.end();) {
1500 if (buffer_handle_it->first.stream_id == stream_id) {
1501 status_t res =
1502 GraphicBufferMapper::get().freeBuffer(buffer_handle_it->second);
1503 if (res != OK) {
1504 ALOGE("%s: Freeing imported buffer failed: %s", __FUNCTION__,
1505 ::android::statusToString(res).c_str());
1506 }
1507 buffer_handle_it = imported_buffer_handle_map_.erase(buffer_handle_it);
1508 } else {
1509 buffer_handle_it++;
1510 }
1511 }
1512 }
1513
FreeImportedBufferHandles()1514 void CameraDeviceSession::FreeImportedBufferHandles() {
1515 ATRACE_CALL();
1516 std::lock_guard<std::mutex> lock(imported_buffer_handle_map_lock_);
1517
1518 auto& mapper = GraphicBufferMapper::get();
1519 for (auto buffer_handle_it : imported_buffer_handle_map_) {
1520 status_t status = mapper.freeBuffer(buffer_handle_it.second);
1521 if (status != OK) {
1522 ALOGE("%s: Freeing imported buffer failed: %s", __FUNCTION__,
1523 ::android::statusToString(status).c_str());
1524 }
1525 }
1526
1527 imported_buffer_handle_map_.clear();
1528 }
1529
CleanupStaleStreamsLocked(const std::vector<Stream> & new_streams)1530 void CameraDeviceSession::CleanupStaleStreamsLocked(
1531 const std::vector<Stream>& new_streams) {
1532 for (auto stream_it = configured_streams_map_.begin();
1533 stream_it != configured_streams_map_.end();) {
1534 int32_t stream_id = stream_it->first;
1535 bool found = false;
1536 for (const Stream& stream : new_streams) {
1537 if (stream.id == stream_id) {
1538 found = true;
1539 break;
1540 }
1541 }
1542 if (!found) {
1543 std::lock_guard<std::mutex> lock(imported_buffer_handle_map_lock_);
1544 stream_it = configured_streams_map_.erase(stream_it);
1545 FreeBufferHandlesLocked(stream_id);
1546 } else {
1547 stream_it++;
1548 }
1549 }
1550 }
1551
Flush()1552 status_t CameraDeviceSession::Flush() {
1553 ATRACE_CALL();
1554 std::shared_lock lock(capture_session_lock_);
1555 if (capture_session_ == nullptr) {
1556 return OK;
1557 }
1558
1559 is_flushing_ = true;
1560 status_t res = capture_session_->Flush();
1561 stream_buffer_cache_manager_->NotifyFlushingAll();
1562 is_flushing_ = false;
1563
1564 return res;
1565 }
1566
AppendOutputIntentToSettingsLocked(const CaptureRequest & request,CaptureRequest * updated_request)1567 void CameraDeviceSession::AppendOutputIntentToSettingsLocked(
1568 const CaptureRequest& request, CaptureRequest* updated_request) {
1569 if (updated_request == nullptr || updated_request->settings == nullptr) {
1570 // The frameworks may have no settings and just do nothing here.
1571 return;
1572 }
1573
1574 bool has_video = false;
1575 bool has_snapshot = false;
1576 bool has_zsl = false;
1577
1578 // From request output_buffers to find stream id and then find the stream.
1579 for (auto& buffer : request.output_buffers) {
1580 auto stream = configured_streams_map_.find(buffer.stream_id);
1581 if (stream != configured_streams_map_.end()) {
1582 if (utils::IsVideoStream(stream->second)) {
1583 has_video = true;
1584 } else if (utils::IsJPEGSnapshotStream(stream->second)) {
1585 has_snapshot = true;
1586 }
1587 }
1588 }
1589
1590 for (auto& buffer : request.input_buffers) {
1591 auto stream = configured_streams_map_.find(buffer.stream_id);
1592 if (stream != configured_streams_map_.end()) {
1593 if ((stream->second.usage & GRALLOC_USAGE_HW_CAMERA_ZSL) != 0) {
1594 has_zsl = true;
1595 break;
1596 }
1597 }
1598 }
1599
1600 uint8_t output_intent = static_cast<uint8_t>(OutputIntent::kPreview);
1601
1602 if (has_video && has_snapshot) {
1603 output_intent = static_cast<uint8_t>(OutputIntent::kVideoSnapshot);
1604 } else if (has_snapshot) {
1605 output_intent = static_cast<uint8_t>(OutputIntent::kSnapshot);
1606 } else if (has_video) {
1607 output_intent = static_cast<uint8_t>(OutputIntent::kVideo);
1608 } else if (has_zsl) {
1609 output_intent = static_cast<uint8_t>(OutputIntent::kZsl);
1610 }
1611
1612 // Used to indicate the possible start and end of video recording in traces
1613 if (has_video && !prev_output_intent_has_video_) {
1614 ATRACE_NAME("Start Video Streaming");
1615 } else if (prev_output_intent_has_video_ && !has_video) {
1616 ATRACE_NAME("Stop Video Streaming");
1617 }
1618
1619 prev_output_intent_has_video_ = has_video;
1620
1621 status_t res = updated_request->settings->Set(VendorTagIds::kOutputIntent,
1622 &output_intent,
1623 /*data_count=*/1);
1624 if (res != OK) {
1625 ALOGE("%s: Failed to set vendor tag OutputIntent: %s(%d).", __FUNCTION__,
1626 strerror(-res), res);
1627 }
1628 }
1629
IsReconfigurationRequired(const HalCameraMetadata * old_session,const HalCameraMetadata * new_session,bool * reconfiguration_required)1630 status_t CameraDeviceSession::IsReconfigurationRequired(
1631 const HalCameraMetadata* old_session, const HalCameraMetadata* new_session,
1632 bool* reconfiguration_required) {
1633 if (old_session == nullptr || new_session == nullptr ||
1634 reconfiguration_required == nullptr) {
1635 ALOGE(
1636 "%s: old_session or new_session or reconfiguration_required is "
1637 "nullptr.",
1638 __FUNCTION__);
1639 return BAD_VALUE;
1640 }
1641
1642 return device_session_hwl_->IsReconfigurationRequired(
1643 old_session, new_session, reconfiguration_required);
1644 }
1645
UpdateRequestedBufferHandles(std::vector<StreamBuffer> * buffers)1646 status_t CameraDeviceSession::UpdateRequestedBufferHandles(
1647 std::vector<StreamBuffer>* buffers) {
1648 if (buffers == nullptr) {
1649 ALOGE("%s: buffer is nullptr.", __FUNCTION__);
1650 return BAD_VALUE;
1651 }
1652
1653 std::lock_guard<std::mutex> lock(imported_buffer_handle_map_lock_);
1654
1655 status_t res;
1656 for (auto& buffer : *buffers) {
1657 // If buffer handle is not nullptr, we need to add the new buffer handle
1658 // to buffer cache.
1659 if (buffer.buffer != nullptr) {
1660 BufferCache buffer_cache = {buffer.stream_id, buffer.buffer_id};
1661 res = AddImportedBufferHandlesLocked(buffer_cache, buffer.buffer);
1662 if (res != OK) {
1663 ALOGE("%s: Adding imported buffer handle failed: %s(%d)", __FUNCTION__,
1664 strerror(-res), res);
1665 return res;
1666 }
1667 }
1668 }
1669
1670 res = UpdateBufferHandlesLocked(buffers,
1671 /*update_hal_buffer_managed_streams=*/true);
1672 if (res != OK) {
1673 ALOGE("%s: Updating output buffer handles failed: %s(%d)", __FUNCTION__,
1674 strerror(-res), res);
1675 return res;
1676 }
1677
1678 return OK;
1679 }
1680
RegisterStreamsIntoCacheManagerLocked(const StreamConfiguration & stream_config,const std::vector<HalStream> & hal_streams)1681 status_t CameraDeviceSession::RegisterStreamsIntoCacheManagerLocked(
1682 const StreamConfiguration& stream_config,
1683 const std::vector<HalStream>& hal_streams) {
1684 ATRACE_CALL();
1685
1686 for (auto& stream : stream_config.streams) {
1687 uint64_t producer_usage = 0;
1688 uint64_t consumer_usage = 0;
1689 int32_t stream_id = -1;
1690 for (auto& hal_stream : hal_streams) {
1691 if (hal_stream.id == stream.id) {
1692 producer_usage = hal_stream.producer_usage;
1693 consumer_usage = hal_stream.consumer_usage;
1694 stream_id = hal_stream.id;
1695 }
1696 }
1697 if (stream_id == -1) {
1698 ALOGE("%s: Could not fine framework stream in hal configured stream list",
1699 __FUNCTION__);
1700 return UNKNOWN_ERROR;
1701 }
1702 // Input stream buffers are always allocated by the camera service, not by
1703 // request_stream_buffers() callback from the HAL.
1704 if (stream.stream_type != StreamType::kOutput) {
1705 continue;
1706 }
1707
1708 // The stream is not HAL buffer managed, so no need to register with SBC.
1709 if (hal_buffer_managed_stream_ids_.find(stream_id) ==
1710 hal_buffer_managed_stream_ids_.end()) {
1711 continue;
1712 }
1713 StreamBufferRequestFunc session_request_func = StreamBufferRequestFunc(
1714 [this, stream_id](uint32_t num_buffer,
1715 std::vector<StreamBuffer>* buffers,
1716 StreamBufferRequestError* status) -> status_t {
1717 ATRACE_NAME("StreamBufferRequestFunc");
1718 if (buffers == nullptr) {
1719 ALOGE("%s: buffers is nullptr.", __FUNCTION__);
1720 return BAD_VALUE;
1721 }
1722
1723 if (num_buffer == 0) {
1724 ALOGE("%s: num_buffer is 0", __FUNCTION__);
1725 return BAD_VALUE;
1726 }
1727
1728 if (status == nullptr) {
1729 ALOGE("%s: status is nullptr.", __FUNCTION__);
1730 return BAD_VALUE;
1731 }
1732
1733 return RequestStreamBuffers(stream_id, num_buffer, buffers, status);
1734 });
1735
1736 StreamBufferReturnFunc session_return_func = StreamBufferReturnFunc(
1737 [this](const std::vector<StreamBuffer>& buffers) -> status_t {
1738 ReturnStreamBuffers(buffers);
1739
1740 for (auto& stream_buffer : buffers) {
1741 ALOGI("%s: [sbc] Flushed buf[%p] bid[%" PRIu64 "] strm[%d] frm[xx]",
1742 __FUNCTION__, stream_buffer.buffer, stream_buffer.buffer_id,
1743 stream_buffer.stream_id);
1744 }
1745
1746 return OK;
1747 });
1748
1749 StreamBufferCacheRegInfo reg_info = {.request_func = session_request_func,
1750 .return_func = session_return_func,
1751 .stream_id = stream_id,
1752 .width = stream.width,
1753 .height = stream.height,
1754 .format = stream.format,
1755 .producer_flags = producer_usage,
1756 .consumer_flags = consumer_usage,
1757 .num_buffers_to_cache = 1};
1758
1759 status_t res = stream_buffer_cache_manager_->RegisterStream(reg_info);
1760 if (res != OK) {
1761 ALOGE(
1762 "%s: Failed to register stream into stream buffer cache manager, "
1763 "error status: %s(%d)",
1764 __FUNCTION__, strerror(-res), res);
1765 return UNKNOWN_ERROR;
1766 }
1767 ALOGI("%s: [sbc] Registered stream %d into SBC manager.", __FUNCTION__,
1768 stream.id);
1769 }
1770
1771 return OK;
1772 }
1773
RequestBuffersFromStreamBufferCacheManager(int32_t stream_id,uint32_t num_buffers,std::vector<StreamBuffer> * buffers,uint32_t frame_number)1774 status_t CameraDeviceSession::RequestBuffersFromStreamBufferCacheManager(
1775 int32_t stream_id, uint32_t num_buffers, std::vector<StreamBuffer>* buffers,
1776 uint32_t frame_number) {
1777 if (num_buffers != 1) {
1778 ALOGE(
1779 "%s: Only one buffer per request can be handled now. num_buffers = %d",
1780 __FUNCTION__, num_buffers);
1781 // TODO(b/127988765): handle multiple buffers from multiple streams if
1782 // HWL needs this feature.
1783 return BAD_VALUE;
1784 }
1785
1786 StreamBufferRequestResult buffer_request_result;
1787
1788 status_t res = this->stream_buffer_cache_manager_->GetStreamBuffer(
1789 stream_id, &buffer_request_result);
1790 if (res != OK) {
1791 ALOGE(
1792 "%s: Failed to get stream buffer from SBC manager, error status: "
1793 "%s(%d).",
1794 __FUNCTION__, strerror(-res), res);
1795 return UNKNOWN_ERROR;
1796 }
1797
1798 // This function fulfills requests from lower HAL level. It is hard for some
1799 // implementation of lower HAL level to handle the case of a request failure.
1800 // In case a framework buffer can not be delivered to the lower level, a dummy
1801 // buffer will be returned by the stream buffer cache manager.
1802 // The client at lower level can use that dummy buffer as a normal buffer for
1803 // writing and so forth. But that buffer will not be returned to the
1804 // framework. This avoids the troublesome for lower level to handle such
1805 // situation. An ERROR_REQUEST needs to be returned to the framework according
1806 // to ::android::hardware::camera::device::V3_5::StreamBufferRequestError.
1807 if (buffer_request_result.is_dummy_buffer) {
1808 ALOGI("%s: [sbc] Dummy buffer returned for stream: %d, frame: %d",
1809 __FUNCTION__, stream_id, frame_number);
1810 {
1811 std::lock_guard<std::mutex> lock(request_record_lock_);
1812 dummy_buffer_observed_.insert(buffer_request_result.buffer.buffer);
1813 }
1814 }
1815
1816 ALOGV("%s: [sbc] => HWL Acquired buf[%p] buf_id[%" PRIu64
1817 "] strm[%d] frm[%u] dummy[%d]",
1818 __FUNCTION__, buffer_request_result.buffer.buffer,
1819 buffer_request_result.buffer.buffer_id, stream_id, frame_number,
1820 buffer_request_result.is_dummy_buffer);
1821
1822 buffers->push_back(buffer_request_result.buffer);
1823 return OK;
1824 }
1825
RequestStreamBuffers(int32_t stream_id,uint32_t num_buffers,std::vector<StreamBuffer> * buffers,StreamBufferRequestError * request_status)1826 status_t CameraDeviceSession::RequestStreamBuffers(
1827 int32_t stream_id, uint32_t num_buffers, std::vector<StreamBuffer>* buffers,
1828 StreamBufferRequestError* request_status) {
1829 if (buffers == nullptr) {
1830 ALOGE("%s: buffers is nullptr", __FUNCTION__);
1831 return BAD_VALUE;
1832 }
1833
1834 if (num_buffers == 0) {
1835 ALOGE("%s: num_buffers is 0", __FUNCTION__);
1836 return BAD_VALUE;
1837 }
1838
1839 if (request_status == nullptr) {
1840 ALOGE("%s: request_status is nullptr", __FUNCTION__);
1841 return BAD_VALUE;
1842 }
1843
1844 *request_status = StreamBufferRequestError::kOk;
1845 status_t res = pending_requests_tracker_->WaitAndTrackAcquiredBuffers(
1846 stream_id, num_buffers);
1847 if (res != OK) {
1848 ALOGW("%s: Waiting until available buffer failed: %s(%d)", __FUNCTION__,
1849 strerror(-res), res);
1850 *request_status = StreamBufferRequestError::kNoBufferAvailable;
1851 return res;
1852 }
1853
1854 std::vector<BufferReturn> buffer_returns;
1855 std::vector<BufferRequest> buffer_requests = {{
1856 .stream_id = stream_id,
1857 .num_buffers_requested = num_buffers,
1858 }};
1859
1860 BufferRequestStatus status = BufferRequestStatus::kOk;
1861 {
1862 int64_t start_timestamp;
1863 std::shared_lock lock(session_callback_lock_);
1864 if (measure_buffer_allocation_time_) {
1865 struct timespec start_time;
1866 if (clock_gettime(CLOCK_BOOTTIME, &start_time)) {
1867 ALOGE("%s: Getting start_time failed.", __FUNCTION__);
1868 } else {
1869 start_timestamp = start_time.tv_sec * kNsPerSec + start_time.tv_nsec;
1870 }
1871 }
1872 status = session_callback_.request_stream_buffers(buffer_requests,
1873 &buffer_returns);
1874 if (measure_buffer_allocation_time_) {
1875 int64_t end_timestamp;
1876 struct timespec end_time;
1877 if (clock_gettime(CLOCK_BOOTTIME, &end_time)) {
1878 ALOGE("%s: Getting end_time failed.", __FUNCTION__);
1879 } else {
1880 end_timestamp = end_time.tv_sec * kNsPerSec + end_time.tv_nsec;
1881 int64_t elapsed_timestamp = end_timestamp - start_timestamp;
1882 if (elapsed_timestamp > kAllocationThreshold) {
1883 ALOGW("%s: buffer allocation time: %" PRIu64 " ms", __FUNCTION__,
1884 elapsed_timestamp / 1000000);
1885 }
1886 }
1887 }
1888 }
1889
1890 // need this information when status is not kOk
1891 if (buffer_returns.size() > 0) {
1892 *request_status = buffer_returns[0].val.error;
1893 }
1894
1895 if (status != BufferRequestStatus::kOk || buffer_returns.size() != 1) {
1896 ALOGW(
1897 "%s: Requesting stream buffer failed. (buffer_returns has %zu "
1898 "entries; status is %s(%d)).",
1899 __FUNCTION__, buffer_returns.size(), strerror(-res), status);
1900 for (auto& buffer_return : buffer_returns) {
1901 ALOGI("%s: stream %d, buffer request error %d", __FUNCTION__,
1902 buffer_return.stream_id, buffer_return.val.error);
1903 }
1904 pending_requests_tracker_->TrackBufferAcquisitionFailure(stream_id,
1905 num_buffers);
1906 pending_requests_tracker_->DumpStatus();
1907 // TODO(b/129362905): Return partial buffers.
1908 return UNKNOWN_ERROR;
1909 }
1910
1911 *buffers = buffer_returns[0].val.buffers;
1912
1913 res = UpdateRequestedBufferHandles(buffers);
1914 if (res != OK) {
1915 ALOGE("%s: Updating requested buffer handles failed: %s(%d).", __FUNCTION__,
1916 strerror(-res), res);
1917 // TODO(b/129362905): Return partial buffers.
1918 return res;
1919 }
1920
1921 ALOGV("%s: [sbc] => CDS Acquired buf[%p] buf_id[%" PRIu64 "] strm[%d]",
1922 __FUNCTION__, buffers->at(0).buffer, buffers->at(0).buffer_id,
1923 stream_id);
1924
1925 return OK;
1926 }
1927
ReturnStreamBuffers(const std::vector<StreamBuffer> & buffers)1928 void CameraDeviceSession::ReturnStreamBuffers(
1929 const std::vector<StreamBuffer>& buffers) {
1930 {
1931 std::shared_lock lock(session_callback_lock_);
1932 session_callback_.return_stream_buffers(buffers);
1933 }
1934
1935 for (auto& stream_buffer : buffers) {
1936 ALOGV("%s: [sbc] <= Return extra buf[%p], bid[%" PRIu64 "], strm[%d]",
1937 __FUNCTION__, stream_buffer.buffer, stream_buffer.buffer_id,
1938 stream_buffer.stream_id);
1939 }
1940
1941 if (pending_requests_tracker_->TrackReturnedAcquiredBuffers(buffers) != OK) {
1942 ALOGE("%s: Tracking requested buffers failed.", __FUNCTION__);
1943 }
1944 }
1945
1946 std::unique_ptr<google::camera_common::Profiler>
GetProfiler(uint32_t camera_id,int option)1947 CameraDeviceSession::GetProfiler(uint32_t camera_id, int option) {
1948 return device_session_hwl_->GetProfiler(camera_id, option);
1949 }
1950
TryHandleCaptureResult(std::unique_ptr<CaptureResult> & result)1951 bool CameraDeviceSession::TryHandleCaptureResult(
1952 std::unique_ptr<CaptureResult>& result) {
1953 if (result == nullptr) {
1954 ALOGE("%s: result is nullptr", __FUNCTION__);
1955 return true;
1956 }
1957 zoom_ratio_mapper_.UpdateCaptureResult(result.get());
1958
1959 status_t res = UpdatePendingRequest(result.get());
1960 if (res != OK) {
1961 ALOGE("%s: Updating inflight requests/streams failed: %s(%d)", __FUNCTION__,
1962 strerror(-res), res);
1963 return true;
1964 }
1965
1966 for (auto& stream_buffer : result->output_buffers) {
1967 ALOGV("%s: [sbc] <= Return result output buf[%p], bid[%" PRIu64
1968 "], strm[%d], frm[%u]",
1969 __FUNCTION__, stream_buffer.buffer, stream_buffer.buffer_id,
1970 stream_buffer.stream_id, result->frame_number);
1971 }
1972 for (auto& stream_buffer : result->input_buffers) {
1973 ALOGV("%s: [sbc] <= Return result input buf[%p], bid[%" PRIu64
1974 "], strm[%d], frm[%u]",
1975 __FUNCTION__, stream_buffer.buffer, stream_buffer.buffer_id,
1976 stream_buffer.stream_id, result->frame_number);
1977 }
1978
1979 // If there is placeholder buffer or a placeholder buffer has been observed of
1980 // this frame, handle the capture result specifically.
1981 bool result_handled = false;
1982 res = TryHandleDummyResult(result.get(), &result_handled);
1983 if (res != OK) {
1984 ALOGE("%s: Failed to handle placeholder result.", __FUNCTION__);
1985 return true;
1986 }
1987 return result_handled;
1988 }
1989
TrackReturnedBuffers(const std::vector<StreamBuffer> & buffers)1990 void CameraDeviceSession::TrackReturnedBuffers(
1991 const std::vector<StreamBuffer>& buffers) {
1992 if (!buffers.empty()) {
1993 if (pending_requests_tracker_->TrackReturnedAcquiredBuffers(buffers) != OK) {
1994 ALOGE("%s: Tracking requested acquired buffers failed", __FUNCTION__);
1995 }
1996 if (pending_requests_tracker_->TrackReturnedResultBuffers(buffers) != OK) {
1997 ALOGE("%s: Tracking requested quota buffers failed", __FUNCTION__);
1998 }
1999 }
2000 }
2001
2002 } // namespace google_camera_hal
2003 } // namespace android
2004