1 /* 2 * Copyright (C) 2021-2024 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_PROCESS_SKELETON_H 17 #define OHOS_IPC_IPC_PROCESS_SKELETON_H 18 19 #include <list> 20 #include <map> 21 #include <atomic> 22 #include <shared_mutex> 23 24 #include "invoker_rawdata.h" 25 #include "ipc_object_proxy.h" 26 #include "ipc_object_stub.h" 27 #include "ipc_thread_pool.h" 28 #include "iremote_object.h" 29 #include "nocopyable.h" 30 #include "sys_binder.h" 31 32 #ifndef CONFIG_IPC_SINGLE 33 #include "comm_auth_info.h" 34 #include "dbinder_callback_stub.h" 35 #include "dbinder_session_object.h" 36 #include "dbinder_softbus_client.h" 37 #include "stub_refcount_object.h" 38 #endif 39 40 namespace OHOS { 41 #ifdef CONFIG_IPC_SINGLE 42 namespace IPC_SINGLE { 43 #endif 44 #ifndef CONFIG_IPC_SINGLE 45 struct SocketThreadLockInfo { 46 std::mutex mutex; 47 std::condition_variable condition; 48 bool ready = false; 49 }; 50 51 struct ThreadMessageInfo { 52 uint32_t flags; 53 binder_size_t bufferSize; 54 binder_size_t offsetsSize; 55 binder_uintptr_t offsets; 56 uint32_t socketId; 57 void *buffer; 58 std::mutex mutex; 59 std::condition_variable condition; 60 bool ready; 61 }; 62 63 struct ThreadProcessInfo { 64 int32_t listenFd; 65 uint32_t packageSize; 66 std::shared_ptr<char> buffer; 67 }; 68 69 struct AppAuthInfo { 70 uint32_t pid; 71 uint32_t uid; 72 uint32_t tokenId; 73 int32_t socketId; 74 uint64_t stubIndex; 75 IRemoteObject *stub; 76 std::string deviceId; 77 }; 78 #endif 79 80 class IPCProcessSkeleton { 81 public: 82 enum { 83 LISTEN_THREAD_CREATE_OK, // Invoker family. 84 LISTEN_THREAD_CREATE_FAILED, 85 LISTEN_THREAD_CREATED_ALREADY, 86 LISTEN_THREAD_CREATED_TIMEOUT 87 }; 88 ~IPCProcessSkeleton(); 89 90 static IPCProcessSkeleton *GetCurrent(); 91 static std::string ConvertToSecureString(const std::string &str); GetIPCRuntimeInfo()92 static inline const char *GetIPCRuntimeInfo() 93 { 94 #ifndef CONFIG_IPC_SINGLE 95 return "ipc_core"; 96 #else 97 return "ipc_single"; 98 #endif 99 }; 100 101 #ifndef CONFIG_IPC_SINGLE 102 static uint32_t ConvertChannelID2Int(int64_t databusChannelId); 103 static bool IsHandleMadeByUser(uint32_t handle); 104 #endif 105 bool SetIPCProxyLimit(uint64_t num, std::function<void (uint64_t num)> callback); 106 bool SetMaxWorkThread(int maxThreadNum); 107 std::u16string MakeHandleDescriptor(int handle); 108 109 bool OnThreadTerminated(const std::string &threadName); 110 bool SpawnThread(int policy = IPCWorkThread::SPAWN_PASSIVE, int proto = IRemoteObject::IF_PROT_DEFAULT); 111 112 sptr<IRemoteObject> FindOrNewObject(int handle, const dbinder_negotiation_data *dbinderData = nullptr); 113 bool IsContainsObject(IRemoteObject *object); 114 sptr<IRemoteObject> QueryObject(const std::u16string &descriptor, bool lockFlag = true); 115 bool AttachObject(IRemoteObject *object, bool lockFlag = true); 116 bool DetachObject(IRemoteObject *object); 117 sptr<IRemoteObject> GetProxyObject(int handle, bool &newFlag); 118 119 sptr<IRemoteObject> GetRegistryObject(); 120 bool SetRegistryObject(sptr<IRemoteObject> &object); 121 void BlockUntilThreadAvailable(); 122 void LockForNumExecuting(); 123 void UnlockForNumExecuting(); 124 125 #ifndef CONFIG_IPC_SINGLE 126 bool AttachRawData(int32_t socketId, std::shared_ptr<InvokerRawData> rawData); 127 bool DetachRawData(int32_t socketId); 128 std::shared_ptr<InvokerRawData> QueryRawData(int32_t socketId); 129 130 sptr<IRemoteObject> GetSAMgrObject(); 131 std::shared_ptr<DBinderSessionObject> ProxyDetachDBinderSession(uint32_t handle, IPCObjectProxy *proxy); 132 bool ProxyAttachDBinderSession(uint32_t handle, std::shared_ptr<DBinderSessionObject> object); 133 std::shared_ptr<DBinderSessionObject> ProxyQueryDBinderSession(uint32_t handle); 134 bool ProxyMoveDBinderSession(uint32_t handle, IPCObjectProxy *proxy); 135 bool QueryProxyBySocketId(int32_t socketId, std::vector<uint32_t> &proxyHandle); 136 std::shared_ptr<DBinderSessionObject> QuerySessionByInfo(const std::string &name, const std::string &deviceId); 137 138 bool DetachThreadLockInfo(const std::thread::id &threadId); 139 bool AttachThreadLockInfo(std::shared_ptr<SocketThreadLockInfo> object, const std::thread::id &threadId); 140 std::shared_ptr<SocketThreadLockInfo> QueryThreadLockInfo(const std::thread::id &threadId); 141 void EraseThreadBySeqNumber(uint64_t seqNumber); 142 bool AddThreadBySeqNumber(uint64_t seqNumber, std::shared_ptr<ThreadMessageInfo> messageInfo); 143 std::shared_ptr<ThreadMessageInfo> QueryThreadBySeqNumber(uint64_t seqNumber); 144 bool AddSendThreadInWait(uint64_t seqNumber, std::shared_ptr<ThreadMessageInfo> messageInfo, int userWaitTime); 145 146 int GetSocketIdleThreadNum() const; 147 int GetSocketTotalThreadNum() const; 148 int PopSocketIdFromThread(const std::thread::id &threadId); 149 void WakeUpSocketIOThread(const std::thread::id &threadID); 150 void WakeUpThreadBySeqNumber(uint64_t seqNumber, uint32_t handle); 151 IRemoteObject *QueryStubByIndex(uint64_t stubIndex); 152 uint64_t QueryStubIndex(IRemoteObject *stubObject); 153 uint64_t AddStubByIndex(IRemoteObject *stubObject); 154 uint64_t EraseStubIndex(IRemoteObject *stubObject); 155 uint64_t GetSeqNumber(); 156 uint32_t GetDBinderIdleHandle(std::shared_ptr<DBinderSessionObject> session); 157 std::string GetLocalDeviceID(); 158 159 bool AttachCallbackStub(IPCObjectProxy *ipcProxy, sptr<IPCObjectStub> callbackStub); 160 sptr<IPCObjectStub> QueryCallbackStub(IPCObjectProxy *ipcProxy); 161 sptr<IPCObjectProxy> QueryCallbackProxy(IPCObjectStub *callbackStub); 162 sptr<IPCObjectStub> DetachCallbackStub(IPCObjectProxy *ipcProxy); 163 uint32_t QueryHandleByDatabusSession(const std::string &name, const std::string &deviceId, uint64_t stubIndex); 164 bool StubDetachDBinderSession(uint32_t handle, uint32_t &tokenId); 165 std::shared_ptr<DBinderSessionObject> StubQueryDBinderSession(uint32_t handle); 166 bool StubAttachDBinderSession(uint32_t handle, std::shared_ptr<DBinderSessionObject> object); 167 std::string GetDatabusName(); 168 bool CreateSoftbusServer(const std::string &name); 169 170 bool AttachCommAuthInfo(IRemoteObject *stub, int pid, int uid, uint32_t tokenId, const std::string &deviceId); 171 bool DetachCommAuthInfo(IRemoteObject *stub, int pid, int uid, uint32_t tokenId, const std::string &deviceId); 172 void DetachCommAuthInfoByStub(IRemoteObject *stub); 173 void DetachCommAuthInfoBySocketId(int32_t socketId); 174 bool QueryCommAuthInfo(int pid, int uid, uint32_t &tokenId, const std::string &deviceId); 175 void UpdateCommAuthSocketInfo(int pid, int uid, uint32_t &tokenId, const std::string &deviceId, 176 const int32_t socketId); 177 bool AttachOrUpdateAppAuthInfo(const AppAuthInfo &appAuthInfo); 178 bool DetachAppAuthInfo(const AppAuthInfo &appAuthInfo); 179 void DetachAppAuthInfoByStub(IRemoteObject *stub, uint64_t stubIndex); 180 std::list<uint64_t> DetachAppAuthInfoBySocketId(int32_t socketId); 181 bool QueryCommAuthInfo(AppAuthInfo &appAuthInfo); 182 bool QueryAppInfoToStubIndex(const AppAuthInfo &appAuthInfo); 183 bool AddDataThreadToIdle(const std::thread::id &threadId); 184 bool DeleteDataThreadFromIdle(const std::thread::id &threadId); 185 std::thread::id GetIdleDataThread(); 186 void AddDataInfoToThread(const std::thread::id &threadId, std::shared_ptr<ThreadProcessInfo> processInfo); 187 std::shared_ptr<ThreadProcessInfo> PopDataInfoFromThread(const std::thread::id &threadId); 188 void WakeUpDataThread(const std::thread::id &threadID); 189 void AddDataThreadInWait(const std::thread::id &threadId); 190 bool IsSameRemoteObject(IRemoteObject *stub, int pid, int uid, uint32_t tokenId, const std::string &deviceId, 191 const std::shared_ptr<CommAuthInfo> &auth); 192 bool IsSameRemoteObject(int pid, int uid, const std::string &deviceId, const std::shared_ptr<CommAuthInfo> &auth); 193 bool DetachAppInfoToStubIndex(uint32_t pid, uint32_t uid, uint32_t tokenId, const std::string &deviceId, 194 uint64_t stubIndex, int32_t listenFd); 195 std::list<uint64_t> DetachAppInfoToStubIndex(uint32_t pid, uint32_t uid, uint32_t tokenId, 196 const std::string &deviceId, int32_t listenFd); 197 void DetachAppInfoToStubIndex(uint64_t stubIndex); 198 std::list<uint64_t> DetachAppInfoToStubIndex(int32_t listenFd); 199 bool AttachAppInfoToStubIndex(uint32_t pid, uint32_t uid, uint32_t tokenId, const std::string &deviceId, 200 uint64_t stubIndex, int32_t listenFd); 201 bool AttachAppInfoToStubIndex(uint32_t pid, uint32_t uid, uint32_t tokenId, const std::string &deviceId, 202 int32_t listenFd); 203 bool QueryAppInfoToStubIndex(uint32_t pid, uint32_t uid, uint32_t tokenId, const std::string &deviceId, 204 uint64_t stubIndex, int32_t listenFd); 205 std::string UIntToString(uint32_t input); 206 bool AttachDBinderCallbackStub(sptr<IRemoteObject> rpcProxy, sptr<DBinderCallbackStub> stub); 207 bool DetachDBinderCallbackStubByProxy(sptr<IRemoteObject> rpcProxy); 208 void DetachDBinderCallbackStub(DBinderCallbackStub *stub); 209 sptr<DBinderCallbackStub> QueryDBinderCallbackStub(sptr<IRemoteObject> rpcProxy); 210 sptr<IRemoteObject> QueryDBinderCallbackProxy(sptr<IRemoteObject> stub); 211 #endif 212 213 public: 214 static constexpr int DEFAULT_WORK_THREAD_NUM = 16; 215 #ifdef CONFIG_ACTV_BINDER 216 /* The actv binder handle needs to be encoded with at least 31 bits */ 217 static constexpr uint32_t DBINDER_HANDLE_BASE = 0x80000000; 218 #else 219 static constexpr uint32_t DBINDER_HANDLE_MAGIC = 6872; // 'D'(Binder) 'H'(andle) 220 static constexpr uint32_t DBINDER_HANDLE_BASE = 100000 * DBINDER_HANDLE_MAGIC; 221 #endif 222 static constexpr uint32_t DBINDER_HANDLE_COUNT = 100000; 223 static constexpr uint32_t DBINDER_HANDLE_RANG = 100; 224 static constexpr int32_t FOUNDATION_UID = 5523; 225 static constexpr int ENCRYPT_LENGTH = 4; 226 private: 227 DISALLOW_COPY_AND_MOVE(IPCProcessSkeleton); 228 IPCProcessSkeleton(); 229 #ifndef CONFIG_IPC_SINGLE 230 void ClearDataResource(); 231 #endif 232 233 class DestroyInstance { 234 public: 235 ~DestroyInstance(); 236 }; 237 238 static IPCProcessSkeleton *instance_; 239 static std::mutex procMutex_; 240 static DestroyInstance destroyInstance_; 241 static std::atomic<bool> exitFlag_; 242 std::atomic<int> lastErrHandle_ = -1; 243 std::atomic<int> lastErrCnt_ = 0; 244 245 // for DFX 246 std::mutex mutex_; 247 std::condition_variable cv_; 248 int numExecuting_ = 0; 249 int numWaitingForThreads_ = 0; 250 251 IPCWorkThreadPool *threadPool_ = nullptr; 252 253 #ifndef CONFIG_IPC_SINGLE 254 std::mutex databusProcMutex_; 255 std::mutex sessionNameMutex_; 256 std::mutex seqNumberMutex_; 257 std::mutex idleDataMutex_; 258 std::mutex dataQueueMutex_; 259 std::mutex findThreadMutex_; 260 261 std::recursive_mutex proxyToSessionMutex_; 262 std::shared_mutex rawDataMutex_; 263 std::shared_mutex databusSessionMutex_; 264 std::shared_mutex threadLockMutex_; 265 std::shared_mutex callbackStubMutex_; 266 std::shared_mutex stubObjectsMutex_; 267 std::shared_mutex appInfoToIndexMutex_; 268 std::shared_mutex commAuthMutex_; 269 std::shared_mutex dbinderSentMutex_; 270 std::shared_mutex appAuthMutex_; 271 272 std::map<uint32_t, std::shared_ptr<InvokerRawData>> rawData_; 273 std::map<uint64_t, std::shared_ptr<ThreadMessageInfo>> seqNumberToThread_; 274 std::unordered_map<uint64_t, IRemoteObject *> stubObjects_; 275 std::map<std::thread::id, std::shared_ptr<SocketThreadLockInfo>> threadLockInfo_; 276 std::map<uint32_t, std::shared_ptr<DBinderSessionObject>> proxyToSession_; 277 std::map<uint32_t, std::shared_ptr<DBinderSessionObject>> dbinderSessionObjects_; 278 std::map<IPCObjectProxy *, sptr<IPCObjectStub>> noticeStub_; 279 std::map<std::thread::id, std::vector<std::shared_ptr<ThreadProcessInfo>>> dataInfoQueue_; // key is threadId 280 std::map<std::string, std::map<uint64_t, int32_t>> appInfoToStubIndex_; 281 std::map<sptr<IRemoteObject>, wptr<DBinderCallbackStub>> dbinderSentCallback_; 282 283 std::list<std::thread::id> idleDataThreads_; 284 std::list<std::shared_ptr<CommAuthInfo>> commAuth_; 285 286 uint32_t dBinderHandle_ = DBINDER_HANDLE_BASE; /* dbinder handle start at 687200000 */ 287 uint64_t seqNumber_ = 0; 288 std::string sessionName_ = std::string(""); 289 std::atomic<int32_t> listenSocketId_ = 0; 290 uint64_t randNum_; 291 #endif 292 }; 293 #ifdef CONFIG_IPC_SINGLE 294 } // namespace IPC_SINGLE 295 #endif 296 } // namespace OHOS 297 #endif // OHOS_IPC_IPC_PROCESS_SKELETON_H 298