1 /*
2 * Copyright (c) 2023-2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <sys/mman.h>
17 #include "deferred_proc_session/deferred_photo_proc_session.h"
18 #include "ipc_skeleton.h"
19 #include "iservice_registry.h"
20 #include "camera_log.h"
21 #include "camera_util.h"
22 #include "system_ability_definition.h"
23 #include "camera_error_code.h"
24 #include "picture.h"
25
26 namespace OHOS {
27 namespace CameraStandard {
28
OnProcessImageDone(const std::string & imageId,const sptr<IPCFileDescriptor> ipcFileDescriptor,const long bytes,bool isCloudImageEnhanceSupported)29 int32_t DeferredPhotoProcessingSessionCallback::OnProcessImageDone(const std::string &imageId,
30 const sptr<IPCFileDescriptor> ipcFileDescriptor, const long bytes, bool isCloudImageEnhanceSupported)
31 {
32 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnProcessImageDone() is called!");
33 if (ipcFileDescriptor == nullptr) {
34 return CAMERA_INVALID_ARG;
35 }
36 int fd = ipcFileDescriptor->GetFd();
37 void* addr = mmap(nullptr, bytes, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
38 if (deferredPhotoProcSession_ != nullptr && deferredPhotoProcSession_->GetCallback() != nullptr) {
39 if (addr == MAP_FAILED) {
40 MEDIA_ERR_LOG("DeferredPhotoProcessingSessionCallback::OnProcessImageDone() mmap failed");
41 deferredPhotoProcSession_->GetCallback()->OnError(imageId, ERROR_IMAGE_PROC_FAILED);
42 return 0;
43 } else {
44 deferredPhotoProcSession_->GetCallback()->OnProcessImageDone(imageId, static_cast<uint8_t*>(addr), bytes,
45 isCloudImageEnhanceSupported);
46 }
47 } else {
48 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnProcessImageDone not set!, Discarding callback");
49 }
50 munmap(addr, bytes);
51 return 0;
52 }
53
OnError(const std::string & imageId,const DeferredProcessing::ErrorCode errorCode)54 int32_t DeferredPhotoProcessingSessionCallback::OnError(const std::string &imageId,
55 const DeferredProcessing::ErrorCode errorCode)
56 {
57 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnError() is called, errorCode: %{public}d", errorCode);
58 if (deferredPhotoProcSession_ != nullptr && deferredPhotoProcSession_->GetCallback() != nullptr) {
59 deferredPhotoProcSession_->GetCallback()->OnError(imageId, DpsErrorCode(errorCode));
60 } else {
61 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnError not set!, Discarding callback");
62 }
63 return 0;
64 }
65
OnStateChanged(const DeferredProcessing::StatusCode status)66 int32_t DeferredPhotoProcessingSessionCallback::OnStateChanged(const DeferredProcessing::StatusCode status)
67 {
68 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnStateChanged() is called, status:%{public}d", status);
69 if (deferredPhotoProcSession_ != nullptr && deferredPhotoProcSession_->GetCallback() != nullptr) {
70 deferredPhotoProcSession_->GetCallback()->OnStateChanged(DpsStatusCode(status));
71 } else {
72 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnStateChanged not set!, Discarding callback");
73 }
74 return 0;
75 }
76
OnProcessImageDone(const std::string & imageId,std::shared_ptr<Media::Picture> picture,bool isCloudImageEnhanceSupported)77 int32_t DeferredPhotoProcessingSessionCallback::OnProcessImageDone(const std::string &imageId,
78 std::shared_ptr<Media::Picture> picture, bool isCloudImageEnhanceSupported)
79 {
80 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnProcessImageDone() is"
81 "called, status:%{public}s", imageId.c_str());
82 if (picture != nullptr) {
83 MEDIA_INFO_LOG("picture is not null");
84 }
85 if (deferredPhotoProcSession_ != nullptr && deferredPhotoProcSession_->GetCallback() != nullptr) {
86 deferredPhotoProcSession_->GetCallback()->OnProcessImageDone(imageId, picture, isCloudImageEnhanceSupported);
87 } else {
88 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnProcessImageDone not set!, Discarding callback");
89 }
90 return 0;
91 }
92
OnDeliveryLowQualityImage(const std::string & imageId,std::shared_ptr<Media::Picture> picture)93 int32_t DeferredPhotoProcessingSessionCallback::OnDeliveryLowQualityImage(const std::string &imageId,
94 std::shared_ptr<Media::Picture> picture)
95 {
96 MEDIA_INFO_LOG("DeferredPhotoProcessingSessionCallback::OnDeliveryLowQualityImage() is"
97 "called, status:%{public}s", imageId.c_str());
98 if (picture != nullptr) {
99 MEDIA_INFO_LOG("picture is not null");
100 deferredPhotoProcSession_->GetCallback()->OnDeliveryLowQualityImage(imageId, picture);
101 }
102 return 0;
103 }
104
DeferredPhotoProcSession(int userId,std::shared_ptr<IDeferredPhotoProcSessionCallback> callback)105 DeferredPhotoProcSession::DeferredPhotoProcSession(int userId,
106 std::shared_ptr<IDeferredPhotoProcSessionCallback> callback)
107 {
108 MEDIA_INFO_LOG("enter.");
109 userId_ = userId;
110 callback_ = callback;
111 }
112
~DeferredPhotoProcSession()113 DeferredPhotoProcSession::~DeferredPhotoProcSession()
114 {
115 MEDIA_INFO_LOG("DeferredPhotoProcSession::DeferredPhotoProcSession Destructor!");
116 if (remoteSession_ != nullptr) {
117 (void)remoteSession_->AsObject()->RemoveDeathRecipient(deathRecipient_);
118 remoteSession_ = nullptr;
119 }
120 }
121
BeginSynchronize()122 void DeferredPhotoProcSession::BeginSynchronize()
123 {
124 if (remoteSession_ == nullptr) {
125 MEDIA_ERR_LOG("DeferredPhotoProcSession::BeginSynchronize failed due to binder died.");
126 } else {
127 MEDIA_INFO_LOG("DeferredPhotoProcSession:BeginSynchronize() enter.");
128 remoteSession_->BeginSynchronize();
129 }
130 return;
131 }
132
EndSynchronize()133 void DeferredPhotoProcSession::EndSynchronize()
134 {
135 if (remoteSession_ == nullptr) {
136 MEDIA_ERR_LOG("DeferredPhotoProcSession::EndSynchronize failed due to binder died.");
137 } else {
138 MEDIA_INFO_LOG("DeferredPhotoProcSession::EndSynchronize() enter.");
139 remoteSession_->EndSynchronize();
140 }
141 return;
142 }
143
AddImage(const std::string & imageId,DpsMetadata & metadata,const bool discardable)144 void DeferredPhotoProcSession::AddImage(const std::string& imageId, DpsMetadata& metadata, const bool discardable)
145 {
146 if (remoteSession_ == nullptr) {
147 MEDIA_ERR_LOG("DeferredPhotoProcSession::AddImage failed due to binder died.");
148 } else {
149 MEDIA_INFO_LOG("DeferredPhotoProcSession::AddImage() enter.");
150 remoteSession_->AddImage(imageId, metadata, discardable);
151 }
152 return;
153 }
154
RemoveImage(const std::string & imageId,const bool restorable)155 void DeferredPhotoProcSession::RemoveImage(const std::string& imageId, const bool restorable)
156 {
157 if (remoteSession_ == nullptr) {
158 MEDIA_ERR_LOG("DeferredPhotoProcSession::RemoveImage failed due to binder died.");
159 } else {
160 MEDIA_INFO_LOG("DeferredPhotoProcSession RemoveImage() enter.");
161 remoteSession_->RemoveImage(imageId, restorable);
162 }
163 return;
164 }
165
RestoreImage(const std::string & imageId)166 void DeferredPhotoProcSession::RestoreImage(const std::string& imageId)
167 {
168 if (remoteSession_ == nullptr) {
169 MEDIA_ERR_LOG("DeferredPhotoProcSession::RestoreImage failed due to binder died.");
170 } else {
171 MEDIA_INFO_LOG("DeferredPhotoProcSession RestoreImage() enter.");
172 remoteSession_->RestoreImage(imageId);
173 }
174 return;
175 }
176
ProcessImage(const std::string & appName,const std::string & imageId)177 void DeferredPhotoProcSession::ProcessImage(const std::string& appName, const std::string& imageId)
178 {
179 if (remoteSession_ == nullptr) {
180 MEDIA_ERR_LOG("DeferredPhotoProcSession::ProcessImage failed due to binder died.");
181 } else {
182 MEDIA_INFO_LOG("DeferredPhotoProcSession::ProcessImage() enter.");
183 remoteSession_->ProcessImage(appName, imageId);
184 }
185 return;
186 }
187
CancelProcessImage(const std::string & imageId)188 bool DeferredPhotoProcSession::CancelProcessImage(const std::string& imageId)
189 {
190 if (remoteSession_ == nullptr) {
191 MEDIA_ERR_LOG("DeferredPhotoProcSession::CancelProcessImage failed due to binder died.");
192 return false;
193 }
194 MEDIA_INFO_LOG("DeferredPhotoProcSession:CancelProcessImage() enter.");
195 remoteSession_->CancelProcessImage(imageId);
196 return true;
197 }
198
SetDeferredPhotoSession(sptr<DeferredProcessing::IDeferredPhotoProcessingSession> & session)199 int32_t DeferredPhotoProcSession::SetDeferredPhotoSession(
200 sptr<DeferredProcessing::IDeferredPhotoProcessingSession>& session)
201 {
202 remoteSession_ = session;
203 sptr<IRemoteObject> object = remoteSession_->AsObject();
204 pid_t pid = 0;
205 deathRecipient_ = new(std::nothrow) CameraDeathRecipient(pid);
206 CHECK_ERROR_RETURN_RET_LOG(deathRecipient_ == nullptr, CAMERA_ALLOC_ERROR, "failed to new CameraDeathRecipient.");
207
208 deathRecipient_->SetNotifyCb([this](pid_t pid) { CameraServerDied(pid); });
209 bool result = object->AddDeathRecipient(deathRecipient_);
210 if (!result) {
211 MEDIA_ERR_LOG("failed to add deathRecipient");
212 return -1; // return error
213 }
214 return 0;
215 }
216
CameraServerDied(pid_t pid)217 void DeferredPhotoProcSession::CameraServerDied(pid_t pid)
218 {
219 MEDIA_ERR_LOG("camera server has died, pid:%{public}d!", pid);
220 if (remoteSession_ != nullptr) {
221 (void)remoteSession_->AsObject()->RemoveDeathRecipient(deathRecipient_);
222 remoteSession_ = nullptr;
223 }
224 deathRecipient_ = nullptr;
225 ReconnectDeferredProcessingSession();
226 if (callback_ != nullptr) {
227 MEDIA_INFO_LOG("Reconnect session successful, send sync requestion.");
228 callback_->OnError("", DpsErrorCode::ERROR_SESSION_SYNC_NEEDED);
229 }
230 return;
231 }
232
ReconnectDeferredProcessingSession()233 void DeferredPhotoProcSession::ReconnectDeferredProcessingSession()
234 {
235 MEDIA_INFO_LOG("DeferredPhotoProcSession::ReconnectDeferredProcessingSession, enter.");
236 ConnectDeferredProcessingSession();
237 if (remoteSession_ == nullptr) {
238 MEDIA_INFO_LOG("Reconnecting deferred processing session failed.");
239 ReconnectDeferredProcessingSession();
240 }
241 return;
242 }
243
ConnectDeferredProcessingSession()244 void DeferredPhotoProcSession::ConnectDeferredProcessingSession()
245 {
246 MEDIA_INFO_LOG("DeferredPhotoProcSession::ConnectDeferredProcessingSession, enter.");
247 CHECK_ERROR_RETURN_LOG(remoteSession_ != nullptr, "remoteSession_ is not null");
248 sptr<IRemoteObject> object = nullptr;
249 auto samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
250 CHECK_ERROR_RETURN_LOG(samgr == nullptr, "Failed to get System ability manager");
251 object = samgr->GetSystemAbility(CAMERA_SERVICE_ID);
252 CHECK_ERROR_RETURN_LOG(object == nullptr, "object is null");
253 serviceProxy_ = iface_cast<ICameraService>(object);
254 CHECK_ERROR_RETURN_LOG(serviceProxy_ == nullptr, "serviceProxy_ is null");
255 sptr<DeferredProcessing::IDeferredPhotoProcessingSession> session = nullptr;
256 sptr<DeferredProcessing::IDeferredPhotoProcessingSessionCallback> remoteCallback = nullptr;
257 sptr<DeferredPhotoProcSession> deferredPhotoProcSession = nullptr;
258 deferredPhotoProcSession = new(std::nothrow) DeferredPhotoProcSession(userId_, callback_);
259 CHECK_ERROR_RETURN(deferredPhotoProcSession == nullptr);
260 remoteCallback = new(std::nothrow) DeferredPhotoProcessingSessionCallback(deferredPhotoProcSession);
261 CHECK_ERROR_RETURN(remoteCallback == nullptr);
262 serviceProxy_->CreateDeferredPhotoProcessingSession(userId_, remoteCallback, session);
263 if (session) {
264 SetDeferredPhotoSession(session);
265 }
266 return;
267 }
268
GetCallback()269 std::shared_ptr<IDeferredPhotoProcSessionCallback> DeferredPhotoProcSession::GetCallback()
270 {
271 return callback_;
272 }
273
274 } // namespace CameraStandard
275 } // namespace OHOS