• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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, &params.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(&params);
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