1 /* 2 * Copyright (C) 2021-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 #ifndef OHOS_IPC_IPC_OBJECT_PROXY_H 17 #define OHOS_IPC_IPC_OBJECT_PROXY_H 18 19 #include <dlfcn.h> 20 #include <atomic> 21 #include <mutex> 22 #include <shared_mutex> 23 #include <vector> 24 25 #include "iremote_object.h" 26 27 namespace OHOS { 28 #define GET_FIRST_VIRTUAL_FUNC_ADDR(ptr) (*reinterpret_cast<uintptr_t *>(*reinterpret_cast<uintptr_t *>(ptr))) 29 #ifndef CONFIG_IPC_SINGLE 30 struct DBinderNegotiationData { 31 pid_t peerPid; 32 pid_t peerUid; 33 uint32_t peerTokenId; 34 uint64_t stubIndex; 35 std::string peerServiceName; 36 std::string peerDeviceId; 37 std::string localServiceName; 38 std::string localDeviceId; 39 }; 40 #endif 41 42 class IPCObjectProxy : public IRemoteObject { 43 public: 44 explicit IPCObjectProxy(int handle, std::u16string descriptor = std::u16string(), 45 int proto = IRemoteObject::IF_PROT_DEFAULT); 46 ~IPCObjectProxy(); 47 48 /** 49 * @brief Sends message to the peer process in synchronous or asynchronous mode. 50 * @param code Indicates the message code, which is determined by both sides of the communication. 51 * @param data Indicates the object sent to the peer process. 52 * @param reply Indicates the object returned by the peer process. 53 * @param optionoption Indicates the synchronous or asynchronous mode to send messages. 54 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 55 * defined in {@link ipc_types.h} otherwise. 56 * @since 9 57 */ 58 int SendRequest(uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &optionoption) override; 59 60 /** 61 * @brief Determine whether it is a Proxy Object. 62 * @return Returns <b>true</b> if it is Proxy Object; returns <b>false</b> otherwise. 63 * @since 9 64 */ IsProxyObject()65 bool IsProxyObject() const override 66 { 67 return true; 68 }; 69 70 /** 71 * @brief Checks whether an object is dead. 72 * @return Returns <b>true</b> if the object is dead; returns <b>false</b> otherwise. 73 * @since 9 74 */ 75 bool IsObjectDead() const override; 76 77 /** 78 * @brief Obtains the reference count of the object. 79 * @return Returns the reference count. 80 * @since 9 81 */ 82 int32_t GetObjectRefCount() override; 83 84 /** 85 * @brief Dump the contents. 86 * @param fd Indicates the file descriptor. 87 * @param args Indicates a vector containing u16string. 88 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 89 * defined in {@link ipc_types.h} otherwise. 90 * @since 9 91 */ 92 int Dump(int fd, const std::vector<std::u16string> &args) override; 93 94 /** 95 * @brief The first strong reference provided. 96 * @param objectId Indicates the object Id. 97 * @return void 98 * @since 9 99 */ 100 void OnFirstStrongRef(const void *objectId) override; 101 102 /** 103 * @brief The last strong reference provided. 104 * @param objectId Indicates the object Id. 105 * @return void 106 * @since 9 107 */ 108 void OnLastStrongRef(const void *objectId) override; 109 110 /** 111 * @brief Registered a death recipient. 112 * @param recipient Indicates the recipient of the DeathRecipient pointer. 113 * @return Returns <b>true</b> if the callback is registered successfully; returns <b>false</b> otherwise. 114 * @since 9 115 */ 116 bool AddDeathRecipient(const sptr<DeathRecipient> &recipient) override; 117 118 /** 119 * @brief Unregistered a death recipient. 120 * @param recipient Indicates the recipient of the DeathRecipient pointer. 121 * @return Returns <b>true</b> if the callback is registered successfully; returns <b>false</b> otherwise. 122 * @since 9 123 */ 124 bool RemoveDeathRecipient(const sptr<DeathRecipient> &recipient) override; 125 126 /** 127 * @brief Send Obituary to agents who have registered for death notices. 128 * @return void 129 * @since 9 130 */ 131 void SendObituary(); 132 133 /** 134 * @brief Check Subscribe to death notifications. 135 * @return Returns <b>true</b> if the recipients exists; returns <b>false</b> otherwise. 136 * @since 9 137 */ IsSubscribeDeathNotice()138 bool IsSubscribeDeathNotice() const 139 { 140 if (recipients_.empty()) { 141 return false; 142 } 143 return true; 144 }; 145 146 /** 147 * @brief Obtains the handle. 148 * @return Returns handle. 149 * @since 9 150 */ GetHandle()151 uint32_t GetHandle() const 152 { 153 return handle_; 154 }; 155 156 /** 157 * @brief Call the listening thread. 158 * @param data Indicates the object sent to the peer process. 159 * @param reply Indicates the object returned by the peer process. 160 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 161 * defined in {@link ipc_types.h} otherwise. 162 * @since 9 163 */ 164 int InvokeListenThread(MessageParcel &data, MessageParcel &reply); 165 166 /** 167 * @brief Notification service death. 168 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 169 * defined in {@link ipc_types.h} otherwise. 170 * @since 9 171 */ 172 int32_t NoticeServiceDie(); 173 174 /** 175 * @brief Obtains the corresponding PID and UID. 176 * @param reply Indicates the object returned by the peer process. 177 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 178 * defined in {@link ipc_types.h} otherwise. 179 * @since 9 180 */ 181 int GetPidUid(MessageParcel &reply); 182 183 /** 184 * @brief Obtains the session name. 185 * @return Returns the session name of type string. 186 * @since 9 187 */ 188 std::string GetSessionName(); 189 190 /** 191 * @brief Obtains the session name for PID and UID. 192 * @param uid Indicates the UID value entered. 193 * @param pid Indicates the PID value entered. 194 * @return Returns the PID and UID session name of type string. 195 * @since 9 196 */ 197 std::string GetSessionNameForPidUid(uint32_t uid, uint32_t pid); 198 199 /** 200 * @brief Obtains the grant session name. 201 * @return Returns the grant session name of type string. 202 * @since 9 203 */ 204 std::string GetGrantedSessionName(); 205 206 /** 207 * @brief Remove the granted session name. 208 * @param sessionName Indicates the session name that needs to remove. 209 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 210 * @since 12 211 */ 212 int RemoveSessionName(const std::string &sessionName); 213 214 /** 215 * @brief Obtains the proxy protocol. 216 * @return Returns the obtained proxy protocol. 217 * @since 9 218 */ 219 int GetProto() const; 220 221 /** 222 * @brief Wait for initialization. 223 * @param dbinderData dbinder object data. 224 * @return void 225 * @since 9 226 */ 227 void WaitForInit(const void *dbinderData = nullptr); 228 229 /** 230 * @brief Obtains the interface descriptor. 231 * @return Returns the corresponding interface descriptor. 232 * @since 9 233 */ 234 std::u16string GetInterfaceDescriptor() override; 235 236 /** 237 * @brief get the stub strong ref count. 238 * @return 0 get failed; others the strong ref count of the stub. 239 * @since 11 240 */ 241 uint32_t GetStrongRefCountForStub(); 242 243 #ifndef EMULATOR_PLATFORM 244 bool CanPromote() override; 245 #endif 246 247 private: 248 void SetObjectDied(bool isDied); 249 int SendLocalRequest(uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &optionoption); 250 int SendRequestInner(bool isLocal, uint32_t code, MessageParcel &data, MessageParcel &reply, MessageOption &option); 251 void ClearDeathRecipients(); 252 253 #ifndef CONFIG_IPC_SINGLE 254 /** 255 * @brief Set the proxy protocol. 256 * @param proto Indicates a proxy proto. 257 * @return void 258 * @since 9 259 */ 260 void SetProto(int proto); 261 262 /** 263 * @brief Update the proxy protocol. 264 * @return Returns the updated proxy protocol. 265 * @since 9 266 */ 267 int UpdateProto(); 268 269 /** 270 * @brief Update the proxy protocol. 271 * @param dbinderData Indicates a dbinder object data. 272 * @return Returns <b>true</b> if the operation is successful; return <b>false</b> otherwise. 273 * @since 12 274 */ 275 bool UpdateProto(const void *dbinderData); 276 277 /** 278 * @brief Release the proxy protocol. 279 * @return void 280 * @since 9 281 */ 282 void ReleaseProto(); 283 284 /** 285 * @brief Increase a reference to remote. 286 * @return Returns {@link ERR_NONE} if the operation is successful; returns an error code 287 * defined in {@link ipc_types.h} otherwise. 288 * @since 9 289 */ 290 int32_t IncRefToRemote(); 291 292 /** 293 * @brief Obtain proxy protocol information. 294 * @return Returns the status code of the protocol. 295 * @since 9 296 */ 297 int GetProtoInfo(); 298 299 /** 300 * @brief Register the Dbinder death recipient. 301 * @return Returns <b>true</b> if the current recipient is not empty; return <b>false</b> otherwise. 302 * @since 9 303 */ 304 bool AddDbinderDeathRecipient(); 305 306 /** 307 * @brief Unregister the Dbinder death recipient. 308 * @return Returns <b>true</b> if the current recipient or callback result is not empty; 309 * return <b>false</b> otherwise. 310 * @since 9 311 */ 312 bool RemoveDbinderDeathRecipient(); 313 314 /** 315 * @brief Release the databus(Dbinder) protocol. 316 * @return void 317 * @since 9 318 */ 319 void ReleaseDatabusProto(); 320 321 /** 322 * @brief Release the binder protocol. 323 * @return void 324 * @since 9 325 */ 326 void ReleaseBinderProto(); 327 328 /** 329 * @brief Update the databus(Dbinder) client session name. 330 * @param handle Indicates a handle that needs to update session information. 331 * @param reply Indicates the object returned by the peer process. 332 * @return Returns <b>true</b> if the update is successful; returns <b>false</b> Otherwise. 333 * @since 9 334 */ 335 bool UpdateDatabusClientSession(int handle, MessageParcel &reply); 336 337 /** 338 * @brief Update the databus(Dbinder) client session name. 339 * @return Returns <b>true</b> if the update is successful; returns <b>false</b> Otherwise. 340 * @since 12 341 */ 342 bool UpdateDatabusClientSession(); 343 344 /** 345 * @brief Check if there is a session. 346 * @return Returns <b>true</b> if there is currently a session; returns <b>false</b> otherwise. 347 * @since 9 348 */ 349 bool CheckHaveSession(); 350 351 int GetDBinderNegotiationData(int handle, MessageParcel &reply, DBinderNegotiationData &dbinderData); 352 353 int GetDBinderNegotiationData(DBinderNegotiationData &dbinderData); 354 355 bool MakeDBinderTransSession(const DBinderNegotiationData &data); 356 #endif 357 358 bool RegisterBinderDeathRecipient(); 359 bool UnRegisterBinderDeathRecipient(); 360 361 struct DeathRecipientAddrInfo : public virtual RefBase { 362 public: 363 explicit DeathRecipientAddrInfo(const sptr<DeathRecipient> &recipient); 364 365 std::string GetNewSoPath(); 366 bool IsDlclosed(); 367 public: 368 sptr<DeathRecipient> recipient_; 369 void *soFuncAddr_; 370 std::string soPath_; 371 }; 372 373 private: 374 std::mutex initMutex_; 375 std::recursive_mutex mutex_; 376 std::shared_mutex descMutex_; 377 378 std::vector<sptr<DeathRecipientAddrInfo>> recipients_; 379 const uint32_t handle_; 380 int proto_; 381 bool isFinishInit_; 382 std::atomic<bool> isRemoteDead_; 383 std::u16string remoteDescriptor_; 384 std::u16string interfaceDesc_; 385 std::atomic<int> lastErr_ = 0; 386 std::atomic<int> lastErrCnt_ = 0; 387 std::unique_ptr<uint8_t[]> dbinderData_{nullptr}; 388 }; 389 } // namespace OHOS 390 #endif // OHOS_IPC_IPC_OBJECT_PROXY_H 391