* Copyright (c) 2021-2025 Huawei Device Co., Ltd.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "dcamera_host.h"
#include <cstdlib>
#include "iservice_registry.h"
#include "iproxy_broker.h"
#include "iservmgr_hdi.h"
#include "anonymous_string.h"
#include "distributed_hardware_log.h"
#include "metadata_utils.h"
#include "dcamera.h"
namespace OHOS {
namespace DistributedHardware {
OHOS::sptr<DCameraHost> DCameraHost::instance_ = nullptr;
DCameraHost::AutoRelease DCameraHost::autoRelease_;
extern "C" ICameraHost *CameraHostImplGetInstance(void)
{
return static_cast<ICameraHost *>(DCameraHost::GetInstance().GetRefPtr());
}
OHOS::sptr<DCameraHost> DCameraHost::GetInstance()
{
if (instance_ == nullptr) {
instance_ = sptr<DCameraHost>(new DCameraHost());
if (instance_ == nullptr) {
DHLOGE("Get distributed camera host instance failed.");
return nullptr;
}
}
return instance_;
}
int32_t DCameraHost::SetCallback(const sptr<HDI::Camera::V1_0::ICameraHostCallback> &callbackObj)
{
if (callbackObj == nullptr) {
DHLOGE("DCameraHost::SetCallback, input camera host callback is null.");
return CamRetCode::INVALID_ARGUMENT;
}
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
dCameraHostCallback_ = callbackObj;
return CamRetCode::NO_ERROR;
}
int32_t DCameraHost::SetCallback_V1_2(const sptr<HDI::Camera::V1_2::ICameraHostCallback> &callbackObj)
{
if (callbackObj == nullptr) {
DHLOGE("DCameraHost::SetCallback_V1_2, input camera host callback is null.");
return CamRetCode::INVALID_ARGUMENT;
}
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
dCameraHostCallback_V1_2_ = callbackObj;
return CamRetCode::NO_ERROR;
}
int32_t DCameraHost::GetCameraIds(std::vector<std::string> &cameraIds)
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
auto iter = dCameraDeviceMap_.begin();
while (iter != dCameraDeviceMap_.end()) {
if (!(iter->first).empty()) {
cameraIds.push_back(iter->first);
}
iter++;
}
return CamRetCode::NO_ERROR;
}
int32_t DCameraHost::GetCameraAbilityFromDev(const std::string &cameraId, std::shared_ptr<CameraAbility> &cameraAbility)
{
OHOS::sptr<DCameraDevice> device = nullptr;
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
auto iter = dCameraDeviceMap_.find(cameraId);
if (iter == dCameraDeviceMap_.end() || iter->second == nullptr) {
DHLOGE("DCameraHost::Get Cameradevice failed");
return CamRetCode::INVALID_ARGUMENT;
} else {
device = iter->second;
}
}
if (device->GetDCameraAbility(cameraAbility) != CamRetCode::NO_ERROR) {
DHLOGE("DCameraHost::GetCameraAbilityFromDev, GetDCameraAbility failed.");
return CamRetCode::INVALID_ARGUMENT;
}
return CamRetCode::NO_ERROR;
}
int32_t DCameraHost::GetCameraAbility(const std::string &cameraId, std::vector<uint8_t> &cameraAbility)
{
if (IsCameraIdInvalid(cameraId)) {
DHLOGE("DCameraHost::GetCameraAbility, input cameraId is invalid.");
return CamRetCode::INVALID_ARGUMENT;
}
DHLOGI("DCameraHost::GetCameraAbility for cameraId: %{public}s", GetAnonyString(cameraId).c_str());
std::shared_ptr<CameraAbility> ability;
int32_t ret = GetCameraAbilityFromDev(cameraId, ability);
if (ret != CamRetCode::NO_ERROR) {
DHLOGE("DCameraHost::GetCameraAbility, GetCameraAbilityFromDev failed.");
return CamRetCode::INVALID_ARGUMENT;
}
bool retBool = OHOS::Camera::MetadataUtils::ConvertMetadataToVec(ability, cameraAbility);
if (!retBool) {
DHLOGE("DCameraHost::GetCameraAbility, ConvertMetadataToVec failed.");
return CamRetCode::INVALID_ARGUMENT;
}
do {
camera_metadata_item_t item;
constexpr uint32_t WIDTH_OFFSET = 1;
constexpr uint32_t HEIGHT_OFFSET = 2;
constexpr uint32_t UNIT_LENGTH = 3;
ret = OHOS::Camera::FindCameraMetadataItem(ability->get(),
OHOS_ABILITY_STREAM_AVAILABLE_BASIC_CONFIGURATIONS, &item);
DHLOGI("FindCameraMetadataItem item=%{public}u, count=%{public}u, dataType=%{public}u", item.item,
item.count, item.data_type);
if (ret != CAM_META_SUCCESS) {
DHLOGE("Failed to find stream configuration in camera ability with return code %{public}d", ret);
break;
}
if (item.count % UNIT_LENGTH != 0) {
DHLOGE("Invalid stream configuration count: %{public}u", item.count);
break;
}
for (uint32_t index = 0; index < item.count; index += UNIT_LENGTH) {
if (item.data.i32 == nullptr) {
DHLOGE("Invalid stream configuration data");
continue;
}
int32_t format = item.data.i32[index];
int32_t width = item.data.i32[index + WIDTH_OFFSET];
int32_t height = item.data.i32[index + HEIGHT_OFFSET];
DHLOGD("format: %{public}d, width: %{public}d, height: %{public}d", format, width, height);
}
} while (0);
return CamRetCode::NO_ERROR;
}
template<typename Callback, typename Device>
int32_t DCameraHost::OpenCameraImpl(const std::string &cameraId, const Callback &callbackObj, Device &device)
{
if (IsCameraIdInvalid(cameraId) || callbackObj == nullptr) {
DHLOGE("OpenCameraImpl, open camera id is invalid or camera device callback is null.");
return CamRetCode::INVALID_ARGUMENT;
}
DHLOGI("OpenCameraImpl for cameraId: %{public}s", GetAnonyString(cameraId).c_str());
OHOS::sptr<DCameraDevice> dcameraDevice = nullptr;
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
auto iter = dCameraDeviceMap_.find(cameraId);
if (iter == dCameraDeviceMap_.end()) {
DHLOGE("OpenCameraImpl, dcamera device not found.");
return CamRetCode::INSUFFICIENT_RESOURCES;
}
dcameraDevice = iter->second;
if (dcameraDevice == nullptr) {
DHLOGE("OpenCameraImpl, dcamera device is null.");
return INSUFFICIENT_RESOURCES;
}
}
if (dcameraDevice->IsOpened()) {
DHLOGE("OpenCameraImpl, dcamera device %{public}s already opened.", GetAnonyString(cameraId).c_str());
return CamRetCode::CAMERA_BUSY;
}
CamRetCode ret = dcameraDevice->OpenDCamera(callbackObj);
if (ret != CamRetCode::NO_ERROR) {
DHLOGE("OpenCameraImpl, open camera failed.");
return ret;
}
device = dcameraDevice;
DHLOGI("OpenCameraImpl, open camera %{public}s success.", GetAnonyString(cameraId).c_str());
return CamRetCode::NO_ERROR;
}
int32_t DCameraHost::OpenCamera(const std::string &cameraId, const sptr<ICameraDeviceCallback> &callbackObj,
sptr<HDI::Camera::V1_0::ICameraDevice> &device)
{
return OpenCameraImpl(cameraId, callbackObj, device);
}
int32_t DCameraHost::OpenCamera_V1_1(const std::string &cameraId, const sptr<ICameraDeviceCallback> &callbackObj,
sptr<HDI::Camera::V1_1::ICameraDevice> &device)
{
return OpenCameraImpl(cameraId, callbackObj, device);
}
int32_t DCameraHost::OpenCamera_V1_2(const std::string &cameraId, const sptr<ICameraDeviceCallback> &callbackObj,
sptr<HDI::Camera::V1_2::ICameraDevice> &device)
{
return OpenCameraImpl(cameraId, callbackObj, device);
}
int32_t DCameraHost::OpenCamera_V1_3(const std::string &cameraId, const sptr<ICameraDeviceCallback> &callbackObj,
sptr<ICameraDevice> &device)
{
return OpenCameraImpl(cameraId, callbackObj, device);
}
int32_t DCameraHost::OpenSecureCamera(const std::string &cameraId, const sptr<ICameraDeviceCallback> &callbackObj,
sptr<ICameraDevice> &device)
{
return OpenCameraImpl(cameraId, callbackObj, device);
}
int32_t DCameraHost::GetResourceCost(const std::string &cameraId,
OHOS::HDI::Camera::V1_3::CameraDeviceResourceCost &resourceCost)
{
(void)cameraId;
(void)resourceCost;
return CamRetCode::METHOD_NOT_SUPPORTED;
}
int32_t DCameraHost::NotifyDeviceStateChangeInfo(int notifyType, int deviceState)
{
(void)notifyType;
(void)deviceState;
DHLOGI("DCameraHost::NotifyDeviceStateChangeInfo, distributed camera not support.");
return CamRetCode::METHOD_NOT_SUPPORTED;
}
int32_t DCameraHost::SetFlashlight(const std::string &cameraId, bool isEnable)
{
(void)cameraId;
(void)isEnable;
DHLOGI("DCameraHost::SetFlashlight, distributed camera not support.");
return CamRetCode::METHOD_NOT_SUPPORTED;
}
int32_t DCameraHost::SetFlashlight_V1_2(float level)
{
(void)level;
DHLOGI("DCameraHost::SetFlashlight_V1_2, distributed camera not support.");
return CamRetCode::METHOD_NOT_SUPPORTED;
}
int32_t DCameraHost::PreCameraSwitch(const std::string &cameraId)
{
(void)cameraId;
DHLOGI("DCameraHost::PreCameraSwitch, distributed camera not support.");
return CamRetCode::METHOD_NOT_SUPPORTED;
}
int32_t DCameraHost::PrelaunchWithOpMode(const PrelaunchConfig &config, int32_t operationMode)
{
(void)config;
(void)operationMode;
DHLOGI("DCameraHost::PrelaunchWithOpMode, distributed camera not support.");
return CamRetCode::METHOD_NOT_SUPPORTED;
}
int32_t DCameraHost::Prelaunch(const PrelaunchConfig &config)
{
(void)config;
DHLOGI("DCameraHost::Prelaunch, distributed camera not support.");
return CamRetCode::METHOD_NOT_SUPPORTED;
}
DCamRetCode DCameraHost::AddDeviceParamCheck(const DHBase &dhBase, const std::string& sinkAbilityInfo,
const std::string &sourceCodecInfo, const sptr<IDCameraProviderCallback> &callback)
{
if (IsDhBaseInfoInvalid(dhBase)) {
DHLOGE("DCameraHost::AddDCameraDevice, devId or dhId is invalid.");
return DCamRetCode::INVALID_ARGUMENT;
}
DHLOGI("DCameraHost::AddDCameraDevice for {devId: %{public}s, dhId: %{public}s}",
GetAnonyString(dhBase.deviceId_).c_str(), GetAnonyString(dhBase.dhId_).c_str());
if (sinkAbilityInfo.empty() || sinkAbilityInfo.length() > ABILITYINFO_MAX_LENGTH) {
DHLOGE("DCameraHost::AddDCameraDevice, input sinkAbilityInfo is invalid.");
return DCamRetCode::INVALID_ARGUMENT;
}
if (sourceCodecInfo.empty() || sourceCodecInfo.length() > ABILITYINFO_MAX_LENGTH) {
DHLOGE("DCameraHost::AddDCameraDevice, input sourceCodecInfo is invalid.");
return DCamRetCode::INVALID_ARGUMENT;
}
if (GetCamDevNum() > MAX_DCAMERAS_NUMBER) {
DHLOGE("DCameraHost::AddDCameraDevice, cameras exceed the upper limit.");
return DCamRetCode::INVALID_ARGUMENT;
}
return DCamRetCode::SUCCESS;
}
DCamRetCode DCameraHost::AddDCameraDevice(const DHBase &dhBase, const std::string& sinkAbilityInfo,
const std::string &sourceCodecInfo, const sptr<IDCameraProviderCallback> &callback)
{
if (AddDeviceParamCheck(dhBase, sinkAbilityInfo, sourceCodecInfo, callback) != DCamRetCode::SUCCESS) {
DHLOGE("DCameraHost::AddDCameraDevice, input param is invalid.");
return DCamRetCode::INVALID_ARGUMENT;
}
std::string dCameraId = dhBase.deviceId_ + "__" + dhBase.dhId_;
std::optional<DCamRetCode> refreshStatus = HandleExistingDCamera(dCameraId, sinkAbilityInfo);
if (refreshStatus.has_value()) {
return refreshStatus.value();
}
return HandleNewDCamera(dhBase, sinkAbilityInfo, sourceCodecInfo, callback);
}
std::optional<DCamRetCode> DCameraHost::HandleExistingDCamera(const std::string& dCameraId,
const std::string& sinkAbilityInfo)
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
auto iter = dCameraDeviceMap_.find(dCameraId);
if (iter == dCameraDeviceMap_.end()) {
return std::nullopt;
}
if (iter->second == nullptr) {
DHLOGI("AddDCameraDevice device is null");
return DCamRetCode::INVALID_ARGUMENT;
}
iter->second->SetDcameraAbility(sinkAbilityInfo);
DHLOGI("AddDCameraDevice refresh data success");
return DCamRetCode::SUCCESS;
}
DCamRetCode DCameraHost::HandleNewDCamera(const DHBase &dhBase, const std::string& sinkAbilityInfo,
const std::string &sourceCodecInfo, const sptr<IDCameraProviderCallback> &callback)
{
std::string dCameraId = dhBase.deviceId_ + "__" + dhBase.dhId_;
OHOS::sptr<DCameraDevice> dcameraDevice(new (std::nothrow) DCameraDevice(dhBase, sinkAbilityInfo,
sourceCodecInfo));
if (dcameraDevice == nullptr) {
DHLOGE("DCameraHost::AddDCameraDevice, create dcamera device failed.");
return DCamRetCode::INVALID_ARGUMENT;
}
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
dCameraDeviceMap_[dCameraId] = dcameraDevice;
}
if (callback == nullptr) {
DHLOGE("DCameraHost::SetProviderCallback failed, callback is null");
return DCamRetCode::INVALID_ARGUMENT;
}
dcameraDevice->SetProviderCallback(callback);
sptr<HDI::Camera::V1_0::ICameraHostCallback> callback_v1_0 = nullptr;
sptr<HDI::Camera::V1_2::ICameraHostCallback> callback_v1_2 = nullptr;
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
callback_v1_0 = dCameraHostCallback_;
callback_v1_2 = dCameraHostCallback_V1_2_;
}
if (callback_v1_0 != nullptr) {
callback_v1_0->OnCameraEvent(dCameraId, CameraEvent::CAMERA_EVENT_DEVICE_ADD);
}
if (callback_v1_2 != nullptr) {
callback_v1_2->OnCameraEvent(dCameraId, CameraEvent::CAMERA_EVENT_DEVICE_ADD);
}
sptr<IRemoteObject> remote = OHOS::HDI::hdi_objcast<IDCameraProviderCallback>(callback);
if (remote != nullptr) {
AddClearRegisterRecipient(remote, dhBase);
}
DHLOGI("AddDCameraDevice create dcamera device success, dCameraId: %{public}s", GetAnonyString(dCameraId).c_str());
return DCamRetCode::SUCCESS;
}
size_t DCameraHost::GetCamDevNum()
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
return dCameraDeviceMap_.size();
}
DCamRetCode DCameraHost::RemoveDCameraDevice(const DHBase &dhBase)
{
DHLOGI("DCameraHost::RemoveDCameraDevice for {devId: %{public}s, dhId: %{public}s}",
GetAnonyString(dhBase.deviceId_).c_str(), GetAnonyString(dhBase.dhId_).c_str());
std::string dCameraId = GetCameraIdByDHBase(dhBase);
if (dCameraId.empty()) {
DHLOGE("DCameraHost::RemoveDCameraDevice, dhBase not exist.");
return DCamRetCode::INVALID_ARGUMENT;
}
OHOS::sptr<DCameraDevice> dcameraDevice = GetDCameraDeviceByDHBase(dhBase);
if (dcameraDevice != nullptr) {
if (dcameraDevice->IsOpened()) {
dcameraDevice->Close();
}
dcameraDevice->SetProviderCallback(nullptr);
sptr<IDCameraProviderCallback> callback = dcameraDevice->GetProviderCallback();
if (callback != nullptr) {
sptr<IRemoteObject> remoteObj = OHOS::HDI::hdi_objcast<IDCameraProviderCallback>(callback);
if (remoteObj != nullptr) {
RemoveClearRegisterRecipient(remoteObj, dhBase);
}
}
}
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
dCameraDeviceMap_.erase(dCameraId);
}
sptr<HDI::Camera::V1_0::ICameraHostCallback> callback_v1_0 = nullptr;
sptr<HDI::Camera::V1_2::ICameraHostCallback> callback_v1_2 = nullptr;
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
callback_v1_0 = dCameraHostCallback_;
callback_v1_2 = dCameraHostCallback_V1_2_;
}
if (callback_v1_0 != nullptr) {
callback_v1_0->OnCameraEvent(dCameraId, CameraEvent::CAMERA_EVENT_DEVICE_RMV);
}
if (callback_v1_2 != nullptr) {
callback_v1_2->OnCameraEvent(dCameraId, CameraEvent::CAMERA_EVENT_DEVICE_RMV);
}
DHLOGI("DCameraHost::RemoveDCameraDevice, remove dcamera device success, dCameraId: %{public}s",
GetAnonyString(dCameraId).c_str());
return DCamRetCode::SUCCESS;
}
bool DCameraHost::IsCameraIdInvalid(const std::string &cameraId)
{
if (cameraId.empty() || cameraId.length() > ID_MAX_SIZE) {
return true;
}
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
auto iter = dCameraDeviceMap_.begin();
while (iter != dCameraDeviceMap_.end()) {
if (cameraId == iter->first) {
return false;
}
iter++;
}
return true;
}
std::string DCameraHost::GetCameraIdByDHBase(const DHBase &dhBase)
{
std::string dcameraId = dhBase.deviceId_ + "__" + dhBase.dhId_;
return dcameraId;
}
OHOS::sptr<DCameraDevice> DCameraHost::GetDCameraDeviceByDHBase(const DHBase &dhBase)
{
std::string dCameraId = GetCameraIdByDHBase(dhBase);
if (dCameraId.empty()) {
DHLOGE("DCameraHost::GetDCameraDeviceByDHBase, dhBase not exist.");
return nullptr;
}
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
auto iter = dCameraDeviceMap_.find(dCameraId);
if (iter == dCameraDeviceMap_.end()) {
DHLOGE("DCameraHost::GetDCameraDeviceByDHBase, dcamera device not found.");
return nullptr;
}
return iter->second;
}
void DCameraHost::NotifyDCameraStatus(const DHBase &dhBase, int32_t result)
{
std::string dCameraId = GetCameraIdByDHBase(dhBase);
if (dCameraId.empty()) {
DHLOGE("DCameraHost::NotifyDCameraStatus, dhBase not exist.");
return;
}
sptr<HDI::Camera::V1_0::ICameraHostCallback> callback_v1_0 = nullptr;
sptr<HDI::Camera::V1_2::ICameraHostCallback> callback_v1_2 = nullptr;
{
std::lock_guard<std::mutex> autoLock(deviceMapLock_);
callback_v1_0 = dCameraHostCallback_;
callback_v1_2 = dCameraHostCallback_V1_2_;
}
if (callback_v1_0 != nullptr) {
callback_v1_0->OnCameraStatus(dCameraId, CameraStatus::UN_AVAILABLE);
}
if (callback_v1_2 != nullptr) {
callback_v1_2->OnCameraStatus(dCameraId, CameraStatus::UN_AVAILABLE);
}
}
DCamRetCode DCameraHost::RegisterCameraHdfListener(const std::string &serviceName,
const sptr<IDCameraHdfCallback> &callbackObj)
{
DHLOGI("Register camera HDF listener, serviceName: %{public}s.", GetAnonyString(serviceName).c_str());
if (callbackObj == nullptr) {
DHLOGE("dcamera hdf callback is null.");
return DCamRetCode::INVALID_ARGUMENT;
}
sptr<IRemoteObject> remote = OHOS::HDI::hdi_objcast<IDCameraHdfCallback>(callbackObj);
if (remote == nullptr) {
DHLOGE("Remote callback is nullptr.");
return DCamRetCode::FAILED;
}
if (dCameraHostRecipient_ == nullptr) {
DHLOGE("dcamera host recipient is null.");
return DCamRetCode::FAILED;
}
if (!remote->AddDeathRecipient(dCameraHostRecipient_)) {
DHLOGE("AddDeathRecipient failed, serviceName: %{public}s.", GetAnonyString(serviceName).c_str());
return DCamRetCode::FAILED;
}
std::lock_guard<std::mutex> lock(hdfCallbackMapMtx_);
if (mapCameraHdfCallback_.find(serviceName) != mapCameraHdfCallback_.end()) {
DHLOGI("The callback has been registered and will be replaced, serviceName: %{public}s.",
GetAnonyString(serviceName).c_str());
}
mapCameraHdfCallback_[serviceName] = callbackObj;
DHLOGI("Register camera HDF listener suncess, serviceName: %{public}s.", GetAnonyString(serviceName).c_str());
return DCamRetCode::SUCCESS;
}
DCamRetCode DCameraHost::UnRegisterCameraHdfListener(const std::string &serviceName)
{
DHLOGI("Unregister camera HDF listener, serviceName: %{public}s.", GetAnonyString(serviceName).c_str());
std::lock_guard<std::mutex> lock(hdfCallbackMapMtx_);
auto itCallback = mapCameraHdfCallback_.find(serviceName);
if (itCallback == mapCameraHdfCallback_.end() || itCallback->second == nullptr) {
DHLOGE("Camera HDF callback has not been created or is null ptr.");
return DCamRetCode::FAILED;
}
sptr<IRemoteObject> remote = OHOS::HDI::hdi_objcast<IDCameraHdfCallback>(itCallback->second);
if (remote == nullptr) {
DHLOGE("Remote callback is nullptr.");
return DCamRetCode::FAILED;
}
if (!remote->RemoveDeathRecipient(dCameraHostRecipient_)) {
DHLOGE("RemoveDeathRecipient failed, serviceName: %{public}s.", GetAnonyString(serviceName).c_str());
return DCamRetCode::FAILED;
}
mapCameraHdfCallback_.erase(itCallback);
DHLOGI("Unregister camera HDF listener suncess, serviceName: %{public}s.", GetAnonyString(serviceName).c_str());
return DCamRetCode::SUCCESS;
}
void DCameraHost::ClearRegisterRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
{
DHLOGI("Remote died, remote dcamera device begin.");
auto dCameraHost = DCameraHost::GetInstance();
if (dCameraHost != nullptr) {
dCameraHost->RemoveDCameraDevice(dhBase_);
}
needErase_ = true;
DHLOGI("Remote died, remote dcamera device end.");
}
void DCameraHost::DCameraHostRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
{
DHLOGE("Exit the current process.");
_Exit(0);
}
int32_t DCameraHost::AddClearRegisterRecipient(sptr<IRemoteObject> &remote, const DHBase &dhBase)
{
DHLOGI("add clear register recipient begin.");
auto clearRegisterRecipient = sptr<ClearRegisterRecipient>(new ClearRegisterRecipient(dhBase));
if (clearRegisterRecipient == nullptr) {
DHLOGE("Create clear register recipient object failed.");
return DCamRetCode::FAILED;
}
if (remote != nullptr && remote->AddDeathRecipient(clearRegisterRecipient) == false) {
DHLOGE("call AddDeathRecipient failed.");
return DCamRetCode::FAILED;
}
std::lock_guard<std::mutex> lock(clearRegisterRecipientsMtx_);
clearRegisterRecipients_.erase(std::remove_if(clearRegisterRecipients_.begin(), clearRegisterRecipients_.end(),
[](sptr<ClearRegisterRecipient> &clearRegisterRecipient) {
return clearRegisterRecipient->IsNeedErase();
}), clearRegisterRecipients_.end());
clearRegisterRecipients_.push_back(clearRegisterRecipient);
DHLOGI("add clear register recipient end.");
return DCamRetCode::SUCCESS;
}
int32_t DCameraHost::RemoveClearRegisterRecipient(sptr<IRemoteObject> &remote, const DHBase &dhBase)
{
DHLOGI("remove clear register recipient begin.");
std::lock_guard<std::mutex> lock(clearRegisterRecipientsMtx_);
for (auto itRecipient = clearRegisterRecipients_.begin();
itRecipient != clearRegisterRecipients_.end(); ++itRecipient) {
auto &clearRegisterRecipient = *itRecipient;
if (clearRegisterRecipient->IsMatch(dhBase)) {
if (remote != nullptr && remote->RemoveDeathRecipient(clearRegisterRecipient) == false) {
DHLOGE("call RemoveDeathRecipient failed.");
}
clearRegisterRecipients_.erase(itRecipient);
DHLOGI("remove one clear register recipient.");
break;
}
}
DHLOGI("remove clear register recipient end.");
return DCamRetCode::SUCCESS;
}
}
}