1 /*
2 * Copyright (C) 2021-2025 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 "dbinder_databus_invoker.h"
17
18 #include <cinttypes>
19 #include "string_ex.h"
20 #include "securec.h"
21 #include "sys_binder.h"
22
23 #include "databus_socket_listener.h"
24 #include "dbinder_error_code.h"
25 #include "ipc_object_stub.h"
26 #include "ipc_object_proxy.h"
27 #include "ipc_process_skeleton.h"
28 #include "ipc_thread_skeleton.h"
29 #include "ipc_debug.h"
30 #include "log_tags.h"
31
32 namespace OHOS {
33 using namespace OHOS::HiviewDFX;
34
DBinderDatabusInvoker()35 DBinderDatabusInvoker::DBinderDatabusInvoker()
36 : stopWorkThread_(false), callerPid_(getpid()), callerUid_(getuid()), callerDeviceID_(""),
37 callerTokenID_(0), firstTokenID_(0), status_(0)
38 {
39 }
40
~DBinderDatabusInvoker()41 DBinderDatabusInvoker::~DBinderDatabusInvoker()
42 {
43 }
44
AcquireHandle(int32_t handle)45 bool DBinderDatabusInvoker::AcquireHandle(int32_t handle)
46 {
47 ZLOGI(LOG_LABEL, "handle:%{public}d", handle);
48 return true;
49 }
50
ReleaseHandle(int32_t handle)51 bool DBinderDatabusInvoker::ReleaseHandle(int32_t handle)
52 {
53 ZLOGI(LOG_LABEL, "handle:%{public}d", handle);
54 return true;
55 }
56
NewSessionOfBinderProxy(uint32_t handle,std::shared_ptr<DBinderSessionObject> session)57 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::NewSessionOfBinderProxy(uint32_t handle,
58 std::shared_ptr<DBinderSessionObject> session)
59 {
60 if (session == nullptr) {
61 ZLOGE(LOG_LABEL, "remote session is nullptr");
62 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_ERR_INVALID_DATA, __FUNCTION__);
63 return nullptr;
64 }
65
66 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
67 if (current == nullptr) {
68 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
69 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_IPC_PROCESS_SKELETON_NULL, __FUNCTION__);
70 return nullptr;
71 }
72 sptr<IPCObjectProxy> ipcProxy = reinterpret_cast<IPCObjectProxy *>(current->FindOrNewObject(handle).GetRefPtr());
73 if (ipcProxy == nullptr) {
74 ZLOGE(LOG_LABEL, "attempt to send a invalid handle:%{public}u", handle);
75 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_SEND_INVALID_HANDLE, __FUNCTION__);
76 return nullptr;
77 }
78
79 if (ipcProxy->GetProto() != IRemoteObject::IF_PROT_BINDER) {
80 ZLOGE(LOG_LABEL, "attempt to send a distributed proxy, handle:%{public}u", handle);
81 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_SEND_DISTRIBUTED_PROXY, __FUNCTION__);
82 return nullptr;
83 }
84
85 std::string localDeviceID = current->GetLocalDeviceID();
86 if (localDeviceID.empty()) {
87 ZLOGE(LOG_LABEL, "get localDeviceID error, handle:%{public}u", handle);
88 }
89
90 return GetSessionForProxy(ipcProxy, session, localDeviceID);
91 }
92
GetSessionForProxy(sptr<IPCObjectProxy> ipcProxy,std::shared_ptr<DBinderSessionObject> session,const std::string & localDeviceID)93 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::GetSessionForProxy(sptr<IPCObjectProxy> ipcProxy,
94 std::shared_ptr<DBinderSessionObject> session, const std::string &localDeviceID)
95 {
96 uint32_t handle = ipcProxy->GetHandle();
97 std::string sessionName = ipcProxy->GetSessionName();
98 if (sessionName.empty()) {
99 ZLOGE(LOG_LABEL, "get bus name error, handle:%{public}u", handle);
100 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_GET_SESSION_NAME_FAIL, __FUNCTION__);
101 return nullptr;
102 }
103 MessageParcel data;
104 MessageParcel reply;
105 if (!data.WriteUint32(IRemoteObject::DATABUS_TYPE) || !data.WriteString(localDeviceID) ||
106 !data.WriteUint32(session->GetPeerPid()) || !data.WriteUint32(session->GetPeerUid()) ||
107 !data.WriteString(session->GetDeviceId()) || !data.WriteString(sessionName) ||
108 !data.WriteUint32(session->GetTokenId())) {
109 ZLOGE(LOG_LABEL, "write to parcel fail, handle:%{public}u", handle);
110 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_WRITE_TO_PARCEL_FAIL, __FUNCTION__);
111 return nullptr;
112 }
113 int err = ipcProxy->InvokeListenThread(data, reply);
114 if (err != ERR_NONE) {
115 ZLOGE(LOG_LABEL, "start service listen error:%{public}d handle:%{public}u", err, handle);
116 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_START_LISTEN_FAIL, __FUNCTION__);
117 return nullptr;
118 }
119
120 uint64_t stubIndex = reply.ReadUint64();
121 if (stubIndex == 0) {
122 ZLOGE(LOG_LABEL, "stubindex error:%{public}" PRIu64 " handle:%{public}u", stubIndex, handle);
123 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_STUB_INVALID, __FUNCTION__);
124 return nullptr;
125 }
126 std::string serverName = reply.ReadString();
127 std::string deviceId = reply.ReadString();
128 uint32_t peerTokenId = reply.ReadUint32();
129
130 ZLOGI(LOG_LABEL, "serverName:%{public}s stubIndex:%{public}" PRIu64 " peerTokenId:%{public}u deviceId:%{public}s",
131 serverName.c_str(), stubIndex, peerTokenId, IPCProcessSkeleton::ConvertToSecureString(deviceId).c_str());
132 std::shared_ptr<DBinderSessionObject> connectSession =
133 std::make_shared<DBinderSessionObject>(serverName, deviceId, stubIndex, nullptr, peerTokenId);
134 if (connectSession == nullptr) {
135 ZLOGE(LOG_LABEL, "new server session fail, handle:%{public}u", handle);
136 DfxReportFailHandleEvent(DbinderErrorCode::RPC_DRIVER, handle, RADAR_NEW_SERVER_SESSION_FAIL, __FUNCTION__);
137 return nullptr;
138 }
139
140 return connectSession;
141 }
142
AuthSession2Proxy(uint32_t handle,const std::shared_ptr<DBinderSessionObject> session)143 bool DBinderDatabusInvoker::AuthSession2Proxy(uint32_t handle, const std::shared_ptr<DBinderSessionObject> session)
144 {
145 if (session == nullptr) {
146 ZLOGE(LOG_LABEL, "remote session is nullptr, handle:%{public}u", handle);
147 return false;
148 }
149
150 MessageParcel data;
151 MessageParcel reply;
152 MessageOption option;
153
154 if (!data.WriteUint32(session->GetPeerPid()) || !data.WriteUint32(session->GetPeerUid()) ||
155 !data.WriteString(session->GetDeviceId()) || !data.WriteUint64(session->GetStubIndex()) ||
156 !data.WriteUint32(session->GetTokenId())) {
157 ZLOGE(LOG_LABEL, "write to MessageParcel fail, handle:%{public}u", handle);
158 return false;
159 }
160
161 int err = SendRequest(handle, DBINDER_ADD_COMMAUTH, data, reply, option);
162 if (err != ERR_NONE) {
163 ZLOGE(LOG_LABEL, "send auth info to remote fail, handle:%{public}u", handle);
164 return false;
165 }
166 return true;
167 }
168
QuerySessionOfBinderProxy(uint32_t handle,std::shared_ptr<DBinderSessionObject> session)169 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::QuerySessionOfBinderProxy(uint32_t handle,
170 std::shared_ptr<DBinderSessionObject> session)
171 {
172 if (AuthSession2Proxy(handle, session) != true) {
173 ZLOGE(LOG_LABEL, "auth handle:%{public}u to socketId failed, socketId:%{public}d", handle,
174 session->GetSocketId());
175 return nullptr;
176 }
177 return QueryServerSessionObject(handle);
178 }
179
QueryClientSessionObject(uint32_t databusHandle)180 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::QueryClientSessionObject(uint32_t databusHandle)
181 {
182 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
183 if (current == nullptr) {
184 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
185 return nullptr;
186 }
187 std::shared_ptr<DBinderSessionObject> sessionOfPeer = current->StubQueryDBinderSession(databusHandle);
188 if (sessionOfPeer == nullptr) {
189 ZLOGE(LOG_LABEL, "no session attach to the socketId:%{public}u", databusHandle);
190 return nullptr;
191 }
192 ZLOGI(LOG_LABEL, "socketId:%{public}d", sessionOfPeer->GetSocketId());
193 return sessionOfPeer;
194 }
195
QueryServerSessionObject(uint32_t handle)196 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::QueryServerSessionObject(uint32_t handle)
197 {
198 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
199 if (current == nullptr) {
200 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
201 return nullptr;
202 }
203
204 std::shared_ptr<DBinderSessionObject> sessionOfPeer = current->ProxyQueryDBinderSession(handle);
205 if (sessionOfPeer == nullptr) {
206 ZLOGI(LOG_LABEL, "no session attach to this handle:%{public}u", handle);
207 return nullptr;
208 }
209
210 return sessionOfPeer;
211 }
212
OnReceiveNewConnection(int32_t socketId,int peerPid,int peerUid,std::string peerName,std::string networkId)213 bool DBinderDatabusInvoker::OnReceiveNewConnection(int32_t socketId, int peerPid, int peerUid,
214 std::string peerName, std::string networkId)
215 {
216 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
217 if (current == nullptr) {
218 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
219 return false;
220 }
221
222 AppAuthInfo appAuthInfo = { peerPid, peerUid, 0, socketId, 0, nullptr, networkId };
223 if (!current->QueryCommAuthInfo(appAuthInfo)) {
224 ZLOGE(LOG_LABEL, "remote device is not auth, socket:%{public}d, peerName:%{public}s",
225 socketId, peerName.c_str());
226 return false;
227 }
228 uint32_t peerTokenId = appAuthInfo.tokenId;
229 uint32_t oldTokenId = 0;
230 if (current->StubDetachDBinderSession(socketId, oldTokenId)) {
231 ZLOGI(LOG_LABEL, "delete left socketId:%{public}d device:%{public}s oldTokenId:%{public}u", socketId,
232 IPCProcessSkeleton::ConvertToSecureString(networkId).c_str(), oldTokenId);
233 }
234 std::shared_ptr<DBinderSessionObject> sessionObject = std::make_shared<DBinderSessionObject>(
235 peerName, networkId, 0, nullptr, peerTokenId);
236 sessionObject->SetSocketId(socketId);
237 sessionObject->SetPeerPid(peerPid);
238 sessionObject->SetPeerUid(peerUid);
239 if (!current->StubAttachDBinderSession(socketId, sessionObject)) {
240 ZLOGE(LOG_LABEL, "attach session to process skeleton failed, socketId:%{public}d", socketId);
241 return false;
242 }
243 ZLOGI(LOG_LABEL, "pid:%{public}u uid:%{public}u deviceId:%{public}s tokenId:%{public}u "
244 "oldTokenId:%{public}u socketId:%{public}d", peerPid, peerUid,
245 IPCProcessSkeleton::ConvertToSecureString(networkId).c_str(),
246 peerTokenId, oldTokenId, socketId);
247 // update socketId
248 current->AttachOrUpdateAppAuthInfo(appAuthInfo);
249 return true;
250 }
251
252 // LCOV_EXCL_START
CreateProcessThread()253 bool DBinderDatabusInvoker::CreateProcessThread()
254 {
255 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
256 if (current == nullptr) {
257 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
258 return false;
259 }
260 /* epoll thread obtained one thread, so idle thread must more than 1 */
261 if (current->GetSocketIdleThreadNum() > 0) {
262 current->SpawnThread(IPCWorkThread::PROCESS_PASSIVE, IRemoteObject::IF_PROT_DATABUS);
263 ZLOGI(LOG_LABEL, "success");
264 return true;
265 }
266
267 ZLOGE(LOG_LABEL, "failed, no idle socket thread left");
268 return false;
269 }
270 // LCOV_EXCL_STOP
271
OnRawDataAvailable(int32_t socketId,uint64_t seqNumber,const char * data,uint32_t dataSize)272 void DBinderDatabusInvoker::OnRawDataAvailable(int32_t socketId, uint64_t seqNumber, const char *data,
273 uint32_t dataSize)
274 {
275 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
276 if (current == nullptr) {
277 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
278 return;
279 }
280
281 if (dataSize < sizeof(dbinder_transaction_data)) {
282 ZLOGE(LOG_LABEL, "dataSize:%{public}u is invalid", dataSize);
283 return;
284 }
285 bool isSucc = false;
286 uint32_t rawDataSize = dataSize - sizeof(dbinder_transaction_data);
287 if (rawDataSize > 0 && rawDataSize <= MAX_RAWDATA_SIZE - sizeof(dbinder_transaction_data)) {
288 std::shared_ptr<InvokerRawData> invokerRawData = std::make_shared<InvokerRawData>(rawDataSize);
289 if (memcpy_s(invokerRawData->GetData().get(), rawDataSize, data + sizeof(dbinder_transaction_data),
290 rawDataSize) != EOK) {
291 ZLOGE(LOG_LABEL, "memcpy_s failed, socketId:%{public}d size:%{public}u", socketId, rawDataSize);
292 return;
293 }
294 if (!current->AttachRawData(socketId, seqNumber, invokerRawData)) {
295 ZLOGE(LOG_LABEL, "AttachRawData failed, socketId:%{public}d size:%{public}u", socketId, rawDataSize);
296 return;
297 }
298 isSucc = true;
299 }
300 ZLOGI(LOG_LABEL, "%{public}s, socketId:%{public}d size:%{public}u", isSucc ? "succ" : "fail",
301 socketId, rawDataSize);
302 return;
303 }
304
305 /*
306 * Write 64K=SOCKET_BUFF_SIZE
307 * +------------------+-------------------------+----------------|
308 * |0<---processed--->|Read <----need process-->|<--idle buffer-->
309 * -cursor
310 *
311 * when idle buffer less 1k, move need process to buffer head, then update R/W cursor
312 * when idle buffer can not put a full package, also move need process package to buffer head
313 */
OnMessageAvailable(int32_t socketId,const char * data,ssize_t len)314 void DBinderDatabusInvoker::OnMessageAvailable(int32_t socketId, const char *data, ssize_t len)
315 {
316 if (socketId <= 0 || data == nullptr || len > static_cast<ssize_t>(MAX_RAWDATA_SIZE) ||
317 len < static_cast<ssize_t>(sizeof(dbinder_transaction_data))) {
318 ZLOGE(LOG_LABEL, "wrong inputs, data length:%{public}zd(expected size:%{public}zu) "
319 " socketId:%{public}d", len, sizeof(dbinder_transaction_data), socketId);
320 return;
321 }
322
323 uint32_t packageSize = HasRawDataPackage(data, len);
324 if (packageSize > 0) {
325 // Only one set of big data can be transferred at a time.
326 const dbinder_transaction_data *tr = reinterpret_cast<const dbinder_transaction_data *>(data);
327 return OnRawDataAvailable(socketId, tr->seqNumber, data, packageSize);
328 }
329
330 uint32_t readSize = 0;
331 do {
332 packageSize = HasCompletePackage(data, readSize, len);
333 if (packageSize > 0) {
334 StartProcessLoop(socketId, data + readSize, packageSize);
335 readSize += packageSize;
336 } else {
337 // If the current is abnormal, the subsequent is no longer processed.
338 ZLOGE(LOG_LABEL, "not complete message, socketId:%{public}d", socketId);
339 break;
340 }
341 } while (readSize + sizeof(dbinder_transaction_data) < static_cast<uint32_t>(len));
342 }
343
OnSendMessage(std::shared_ptr<DBinderSessionObject> sessionOfPeer)344 int DBinderDatabusInvoker::OnSendMessage(std::shared_ptr<DBinderSessionObject> sessionOfPeer)
345 {
346 if (sessionOfPeer == nullptr) {
347 ZLOGE(LOG_LABEL, "sessionOfPeer is null");
348 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
349 }
350
351 int32_t socketId = sessionOfPeer->GetSocketId();
352 if (socketId <= 0) {
353 ZLOGE(LOG_LABEL, "socket id is invalid");
354 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
355 }
356
357 std::shared_ptr<BufferObject> sessionBuff = sessionOfPeer->GetSessionBuff();
358 if (sessionBuff == nullptr) {
359 ZLOGE(LOG_LABEL, "databus session buff is null");
360 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
361 }
362
363 return SendData(sessionBuff, socketId);
364 }
365
SendData(std::shared_ptr<BufferObject> sessionBuff,int32_t socketId)366 int DBinderDatabusInvoker::SendData(std::shared_ptr<BufferObject> sessionBuff, int32_t socketId)
367 {
368 char *sendBuffer = sessionBuff->GetSendBufferAndLock(SOCKET_DEFAULT_BUFF_SIZE);
369 /* session buffer contain mutex, need release mutex */
370 if (sendBuffer == nullptr) {
371 ZLOGE(LOG_LABEL, "buffer alloc failed in session");
372 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
373 }
374 sessionBuff->UpdateSendBuffer(0); // 0 means do not expand buffer when send it
375 ssize_t writeCursor = sessionBuff->GetSendBufferWriteCursor();
376 ssize_t readCursor = sessionBuff->GetSendBufferReadCursor();
377 ssize_t sendBuffSize = (ssize_t)sessionBuff->GetSendBufferSize();
378 if (readCursor > sendBuffSize || readCursor < 0) {
379 ZLOGE(LOG_LABEL, "no data to send, invalid readCursor:%{public}zu, send buff size:%{public}zu",
380 readCursor, sendBuffSize);
381 sessionBuff->ReleaseSendBufferLock();
382 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
383 }
384 if (writeCursor < readCursor) {
385 ZLOGE(LOG_LABEL, "no data to send, write cursor:%{public}zu, read cursor:%{public}zu",
386 writeCursor, readCursor);
387 sessionBuff->ReleaseSendBufferLock();
388 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
389 }
390 if (writeCursor == readCursor) {
391 ZLOGE(LOG_LABEL, "no data to send, write cursor:%{public}zu, read cursor:%{public}zu",
392 writeCursor, readCursor);
393 sessionBuff->ReleaseSendBufferLock();
394 return ERR_NONE;
395 }
396 ssize_t size = writeCursor - readCursor;
397
398 int32_t ret = DBinderSoftbusClient::GetInstance().SendBytes(
399 socketId, static_cast<const void *>(sendBuffer + readCursor), size);
400 if (ret != 0) {
401 ZLOGE(LOG_LABEL, "SendBytes fail, ret:%{public}d seq:%{public}" PRIu64
402 " size:%{public}zd, socketId:%{public}d", ret, seqNumber_, size, socketId);
403 DfxReportFailEvent(DbinderErrorCode::RPC_DRIVER, RADAR_SEND_BYTES_FAIL, __FUNCTION__);
404 sessionBuff->ReleaseSendBufferLock();
405 return ret;
406 }
407
408 readCursor += size;
409 sessionBuff->SetSendBufferReadCursor(readCursor);
410 sessionBuff->SetSendBufferWriteCursor(writeCursor);
411 ZLOGI(LOG_LABEL, "succ, seq:%{public}" PRIu64 " size:%{public}zd, socketId:%{public}d",
412 seqNumber_, size, socketId);
413
414 sessionBuff->ReleaseSendBufferLock();
415 return ret;
416 }
417
OnSendRawData(std::shared_ptr<DBinderSessionObject> session,const void * data,size_t size)418 int DBinderDatabusInvoker::OnSendRawData(std::shared_ptr<DBinderSessionObject> session, const void *data, size_t size)
419 {
420 if (session == nullptr) {
421 ZLOGE(LOG_LABEL, "sessionOfPeer is null");
422 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
423 }
424
425 int32_t socketId = session->GetSocketId();
426 if (socketId <= 0) {
427 ZLOGE(LOG_LABEL, "socketId is invalid");
428 return -RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
429 }
430
431 int ret = DBinderSoftbusClient::GetInstance().SendBytes(socketId, data, size);
432 if (ret != 0) {
433 ZLOGE(LOG_LABEL, "fail, ret:%{public}d seq:%{public}" PRIu64 " size:%{public}zu socketId:%{public}d",
434 ret, seqNumber_, size, socketId);
435 return ret;
436 }
437
438 ZLOGI(LOG_LABEL, "succ, seq:%{public}" PRIu64 " size:%{public}zu, socketId:%{public}d",
439 seqNumber_, size, socketId);
440
441 return ret;
442 }
443
JoinThread(bool initiative)444 void DBinderDatabusInvoker::JoinThread(bool initiative) {}
445
JoinProcessThread(bool initiative)446 void DBinderDatabusInvoker::JoinProcessThread(bool initiative)
447 {
448 std::thread::id threadId = std::this_thread::get_id();
449 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
450 if (current == nullptr) {
451 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
452 return;
453 }
454
455 std::shared_ptr<ThreadProcessInfo> processInfo = nullptr;
456 do {
457 current->AddDataThreadInWait(threadId);
458 while ((processInfo = current->PopDataInfoFromThread(threadId)) != nullptr) {
459 OnTransaction(processInfo);
460 processInfo = nullptr;
461 }
462 } while (!stopWorkThread_);
463 }
464
StopWorkThread()465 void DBinderDatabusInvoker::StopWorkThread()
466 {
467 stopWorkThread_ = true;
468 }
469
FlattenSession(unsigned char * sessionOffset,const std::shared_ptr<DBinderSessionObject> connectSession,uint32_t binderVersion)470 uint32_t DBinderDatabusInvoker::FlattenSession(unsigned char *sessionOffset,
471 const std::shared_ptr<DBinderSessionObject> connectSession, uint32_t binderVersion)
472 {
473 FlatDBinderSession *flatSession = reinterpret_cast<FlatDBinderSession *>(sessionOffset);
474 (void)memset_s(flatSession, sizeof(struct FlatDBinderSession), 0, sizeof(struct FlatDBinderSession));
475
476 flatSession->stubIndex = connectSession->GetStubIndex();
477 flatSession->version = binderVersion;
478 flatSession->magic = TOKENID_MAGIC;
479 flatSession->tokenId = connectSession->GetTokenId();
480 flatSession->deviceIdLength = connectSession->GetDeviceId().length();
481 if (flatSession->deviceIdLength == 0 || flatSession->deviceIdLength > DEVICEID_LENGTH) {
482 ZLOGE(LOG_LABEL, "wrong devices id length:%{public}u", flatSession->deviceIdLength);
483 return 0;
484 }
485 int memcpyResult = memcpy_s(flatSession->deviceId, DEVICEID_LENGTH, connectSession->GetDeviceId().data(),
486 flatSession->deviceIdLength);
487 if (memcpyResult != 0) {
488 ZLOGE(LOG_LABEL, "memcpy_s failed , devices id length:%{public}hu", flatSession->deviceIdLength);
489 return 0;
490 }
491 flatSession->deviceId[flatSession->deviceIdLength] = '\0';
492
493 flatSession->serviceNameLength = connectSession->GetServiceName().length();
494 if (flatSession->serviceNameLength == 0 || flatSession->serviceNameLength > SUPPORT_TOKENID_SERVICENAME_LENGTH) {
495 ZLOGE(LOG_LABEL, "wrong service name length:%{public}u", flatSession->serviceNameLength);
496 return 0;
497 }
498 memcpyResult = memcpy_s(flatSession->serviceName, SUPPORT_TOKENID_SERVICENAME_LENGTH,
499 connectSession->GetServiceName().data(), flatSession->serviceNameLength);
500 if (memcpyResult != 0) {
501 ZLOGE(LOG_LABEL, "memcpy_s failed , service name length:%{public}u", flatSession->serviceNameLength);
502 return 0;
503 }
504 flatSession->serviceName[flatSession->serviceNameLength] = '\0';
505
506 ZLOGI(LOG_LABEL, "serviceName:%{public}s stubIndex:%{public}" PRIu64 " tokenId:%{public}u",
507 flatSession->serviceName, flatSession->stubIndex, flatSession->tokenId);
508
509 return sizeof(struct FlatDBinderSession);
510 }
511
UnFlattenSession(unsigned char * sessionOffset,uint32_t binderVersion)512 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::UnFlattenSession(unsigned char *sessionOffset,
513 uint32_t binderVersion)
514 {
515 FlatDBinderSession *flatSession = reinterpret_cast<FlatDBinderSession *>(sessionOffset);
516 if (flatSession->stubIndex == 0) {
517 ZLOGE(LOG_LABEL, "stubIndex err");
518 return nullptr;
519 }
520
521 uint32_t tokenId = 0;
522 if (binderVersion >= SUPPORT_TOKENID_VERSION_NUM && flatSession->version >= SUPPORT_TOKENID_VERSION_NUM &&
523 flatSession->magic == TOKENID_MAGIC) {
524 tokenId = flatSession->tokenId;
525 }
526 /* makes sure end with a null terminator */
527 flatSession->deviceId[DEVICEID_LENGTH] = '\0';
528 flatSession->serviceName[SUPPORT_TOKENID_SERVICENAME_LENGTH] = '\0';
529 ZLOGI(LOG_LABEL, "serviceName:%{public}s stubIndex:%{public}" PRIu64 " tokenId:%{public}u",
530 flatSession->serviceName, flatSession->stubIndex, tokenId);
531
532 return std::make_shared<DBinderSessionObject>(
533 flatSession->serviceName, flatSession->deviceId, flatSession->stubIndex, nullptr, tokenId);
534 }
535
FlattenObject(Parcel & parcel,const IRemoteObject * object) const536 bool DBinderDatabusInvoker::FlattenObject(Parcel &parcel, const IRemoteObject *object) const
537 {
538 return true;
539 }
540
UnflattenObject(Parcel & parcel)541 sptr<IRemoteObject> DBinderDatabusInvoker::UnflattenObject(Parcel &parcel)
542 {
543 return nullptr;
544 }
545
ReadFileDescriptor(Parcel & parcel)546 int DBinderDatabusInvoker::ReadFileDescriptor(Parcel &parcel)
547 {
548 return -1;
549 }
550
WriteFileDescriptor(Parcel & parcel,int fd,bool takeOwnership)551 bool DBinderDatabusInvoker::WriteFileDescriptor(Parcel &parcel, int fd, bool takeOwnership)
552 {
553 return true;
554 }
555
UpdateClientSession(std::shared_ptr<DBinderSessionObject> sessionObject)556 bool DBinderDatabusInvoker::UpdateClientSession(std::shared_ptr<DBinderSessionObject> sessionObject)
557 {
558 ZLOGI(LOG_LABEL, "enter");
559 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
560 if (current == nullptr) {
561 ZLOGE(LOG_LABEL, "current process skeleton is nullptr");
562 return false;
563 }
564
565 std::string ownName = current->GetDatabusName();
566 if (ownName.empty()) {
567 ZLOGE(LOG_LABEL, "fail to get session name");
568 return false;
569 }
570
571 std::shared_ptr<DatabusSocketListener> listener =
572 DelayedSingleton<DatabusSocketListener>::GetInstance();
573 if (listener == nullptr) {
574 ZLOGE(LOG_LABEL, "listener is nullptr");
575 return false;
576 }
577
578 std::string serviceName = sessionObject->GetServiceName();
579 int32_t peerPid = -1;
580 int32_t peerUid = -1;
581 if (!DatabusSocketListener::GetPidAndUidFromServiceName(serviceName, peerPid, peerUid)) {
582 ZLOGE(LOG_LABEL, "fail to get peerpid and peeruid from serviceName");
583 return false;
584 }
585
586 int32_t socketId = listener->CreateClientSocket(ownName, serviceName, sessionObject->GetDeviceId());
587 if (socketId <= 0) {
588 ZLOGE(LOG_LABEL, "fail to creat client Socket");
589 return false;
590 }
591 sessionObject->SetSocketId(socketId);
592 sessionObject->SetPeerPid(peerPid);
593 sessionObject->SetPeerUid(peerUid);
594
595 ZLOGI(LOG_LABEL, "create socket succ, ownName:%{public}s peerName:%{public}s deviceId:%{public}s "
596 "socketId:%{public}d", ownName.c_str(), serviceName.c_str(),
597 IPCProcessSkeleton::ConvertToSecureString(sessionObject->GetDeviceId()).c_str(),
598 socketId);
599 return true;
600 }
601
OnDatabusSessionClientSideClosed(int32_t socketId)602 void DBinderDatabusInvoker::OnDatabusSessionClientSideClosed(int32_t socketId)
603 {
604 std::vector<uint32_t> proxyHandle;
605 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
606 if (current == nullptr) {
607 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
608 return;
609 }
610 if (!current->QueryProxyBySocketId(socketId, proxyHandle)) {
611 ZLOGE(LOG_LABEL, "session id:%{public}d is invalid", socketId);
612 return;
613 }
614 if (proxyHandle.empty()) {
615 ZLOGE(LOG_LABEL, "proxy handle is empty");
616 return;
617 }
618 for (auto it = proxyHandle.begin(); it != proxyHandle.end(); ++it) {
619 std::u16string descriptor = current->MakeHandleDescriptor(*it);
620 const std::string descStr8 = Str16ToStr8(descriptor);
621 sptr<IRemoteObject> remoteObject = current->QueryObject(descriptor);
622 if (remoteObject != nullptr) {
623 IPCObjectProxy *remoteProxy = reinterpret_cast<IPCObjectProxy *>(remoteObject.GetRefPtr());
624 // No need to close session again here. First erase session and then notify user session has been closed.
625 current->ProxyDetachDBinderSession(*it, remoteProxy);
626 if (remoteProxy->IsSubscribeDeathNotice()) {
627 ZLOGD(LOG_LABEL, "SendObituary begin, desc:%{public}s", descStr8.c_str());
628 remoteProxy->SendObituary();
629 ZLOGD(LOG_LABEL, "SendObituary end, desc:%{public}s", descStr8.c_str());
630 } else {
631 remoteProxy->SetObjectDied(true);
632 ZLOGW(LOG_LABEL, "desc:%{public}s does not subscribe death notice", descStr8.c_str());
633 }
634 remoteProxy->ClearDBinderServiceState();
635 } else {
636 ZLOGE(LOG_LABEL, "cannot find proxy with desc:%{public}s", descStr8.c_str());
637 }
638 }
639 ZLOGI(LOG_LABEL, "close:%{public}d success", socketId);
640 return;
641 }
642
OnDatabusSessionServerSideClosed(int32_t socketId)643 void DBinderDatabusInvoker::OnDatabusSessionServerSideClosed(int32_t socketId)
644 {
645 uint32_t tokenId = 0;
646 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
647 if (current == nullptr) {
648 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
649 return;
650 }
651 bool ret = current->StubDetachDBinderSession(socketId, tokenId);
652 // detach info whose socketId equals the given one
653 std::list<uint64_t> stubIndexs = current->DetachAppAuthInfoBySocketId(socketId);
654 std::lock_guard<std::mutex> lockGuard(GetObjectMutex());
655 for (auto it = stubIndexs.begin(); it != stubIndexs.end(); it++) {
656 // note that we canont remove mapping from stub to index here because other session may still be used
657 IRemoteObject *stub = current->QueryStubByIndex(*it);
658 if (stub == nullptr) {
659 continue;
660 }
661 // a proxy doesn't refers this stub, we need to dec ref
662 stub->DecStrongRef(this);
663 }
664 ZLOGI(LOG_LABEL, "socketId:%{public}d ret:%{public}d", socketId, ret);
665 }
666
QueryHandleBySession(std::shared_ptr<DBinderSessionObject> session)667 uint32_t DBinderDatabusInvoker::QueryHandleBySession(std::shared_ptr<DBinderSessionObject> session)
668 {
669 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
670 if (current == nullptr) {
671 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
672 return 0;
673 }
674 return current->QueryHandleByDatabusSession(session->GetServiceName(), session->GetDeviceId(),
675 session->GetStubIndex());
676 }
677
678 // LCOV_EXCL_START
GetSeqNum() const679 uint64_t DBinderDatabusInvoker::GetSeqNum() const
680 {
681 return seqNumber_;
682 }
683 // LCOV_EXCL_STOP
684
SetSeqNum(uint64_t seq)685 void DBinderDatabusInvoker::SetSeqNum(uint64_t seq)
686 {
687 seqNumber_ = seq;
688 }
689
690 // LCOV_EXCL_START
GetClientFd() const691 int32_t DBinderDatabusInvoker::GetClientFd() const
692 {
693 return clientFd_;
694 }
695 // LCOV_EXCL_STOP
696
SetClientFd(int32_t fd)697 void DBinderDatabusInvoker::SetClientFd(int32_t fd)
698 {
699 clientFd_ = fd;
700 }
701
GetCallerSid() const702 std::string DBinderDatabusInvoker::GetCallerSid() const
703 {
704 return "";
705 }
706
GetCallerPid() const707 pid_t DBinderDatabusInvoker::GetCallerPid() const
708 {
709 return callerPid_;
710 }
711
GetCallerRealPid() const712 pid_t DBinderDatabusInvoker::GetCallerRealPid() const
713 {
714 return callerPid_;
715 }
716
SetStatus(uint32_t status)717 void DBinderDatabusInvoker::SetStatus(uint32_t status)
718 {
719 status_ = status;
720 }
721
722 // LCOV_EXCL_START
GetStatus()723 uint32_t DBinderDatabusInvoker::GetStatus()
724 {
725 return status_;
726 }
727 // LCOV_EXCL_STOP
728
SetCallerPid(pid_t pid)729 void DBinderDatabusInvoker::SetCallerPid(pid_t pid)
730 {
731 callerPid_ = pid;
732 }
733
734 // LCOV_EXCL_START
GetCallerUid() const735 uid_t DBinderDatabusInvoker::GetCallerUid() const
736 {
737 return callerUid_;
738 }
739 // LCOV_EXCL_STOP
740
SetCallerUid(pid_t uid)741 void DBinderDatabusInvoker::SetCallerUid(pid_t uid)
742 {
743 callerUid_ = uid;
744 }
745
746 // LCOV_EXCL_START
GetCallerTokenID() const747 uint64_t DBinderDatabusInvoker::GetCallerTokenID() const
748 {
749 return callerTokenID_;
750 }
751 // LCOV_EXCL_STOP
752
753 // LCOV_EXCL_START
GetFirstCallerTokenID() const754 uint64_t DBinderDatabusInvoker::GetFirstCallerTokenID() const
755 {
756 return firstTokenID_;
757 }
758 // LCOV_EXCL_STOP
759
GetSelfTokenID() const760 uint64_t DBinderDatabusInvoker::GetSelfTokenID() const
761 {
762 IRemoteInvoker *invoker = IPCThreadSkeleton::GetDefaultInvoker();
763 if (invoker != nullptr) {
764 return invoker->GetSelfTokenID();
765 }
766 return 0;
767 }
768
GetSelfFirstCallerTokenID() const769 uint64_t DBinderDatabusInvoker::GetSelfFirstCallerTokenID() const
770 {
771 IRemoteInvoker *invoker = IPCThreadSkeleton::GetDefaultInvoker();
772 if (invoker != nullptr) {
773 return invoker->GetSelfFirstCallerTokenID();
774 }
775 return 0;
776 }
777
SetCallerDeviceID(const std::string & deviceId)778 void DBinderDatabusInvoker::SetCallerDeviceID(const std::string &deviceId)
779 {
780 callerDeviceID_ = deviceId;
781 }
782
SetCallerTokenID(const uint32_t tokenId)783 void DBinderDatabusInvoker::SetCallerTokenID(const uint32_t tokenId)
784 {
785 callerTokenID_ = tokenId;
786 firstTokenID_ = tokenId;
787 }
788
789 // LCOV_EXCL_START
IsLocalCalling()790 bool DBinderDatabusInvoker::IsLocalCalling()
791 {
792 return false;
793 }
794 // LCOV_EXCL_STOP
795
CheckAndSetCallerInfo(int32_t socketId,uint64_t stubIndex)796 int DBinderDatabusInvoker::CheckAndSetCallerInfo(int32_t socketId, uint64_t stubIndex)
797 {
798 std::shared_ptr<DBinderSessionObject> session = QueryClientSessionObject(socketId);
799 if (session == nullptr) {
800 ZLOGE(LOG_LABEL, "get databus session fail");
801 return RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
802 }
803
804 int pid = static_cast<int>(session->GetPeerPid());
805 int uid = static_cast<int>(session->GetPeerUid());
806 std::string deviceId = session->GetDeviceId();
807 if (uid < 0 || deviceId.length() > DEVICEID_LENGTH) {
808 ZLOGE(LOG_LABEL, "user id and device id error");
809 return RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
810 }
811
812 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
813 if (current == nullptr) {
814 ZLOGE(LOG_LABEL, "current process skeleton is nullptr");
815 return IPC_SKELETON_ERR;
816 }
817 uint32_t callerTokenId = session->GetTokenId();
818 AppAuthInfo appAuthInfo = { pid, uid, callerTokenId, socketId, stubIndex, nullptr, deviceId };
819 if (current->QueryAppInfoToStubIndex(appAuthInfo) == false) {
820 ZLOGE(LOG_LABEL, "stubIndex:%{public}" PRIu64 " is NOT belong to caller, pid:%{public}d uid:%{public}d"
821 " deviceId:%{public}s socketId:%{public}d callerTokenId:%{public}u", stubIndex, pid, uid,
822 IPCProcessSkeleton::ConvertToSecureString(deviceId).c_str(), socketId, callerTokenId);
823 return RPC_DATABUS_INVOKER_INVALID_STUB_INDEX;
824 }
825 DBinderCallerInfo callerInfo = { pid, uid, socketId, callerTokenId, callerTokenId, deviceId };
826 SetCallerInfo(callerInfo);
827 return ERR_NONE;
828 }
829
SetCallerInfo(DBinderCallerInfo & callerInfo)830 void DBinderDatabusInvoker::SetCallerInfo(DBinderCallerInfo &callerInfo)
831 {
832 callerPid_ = callerInfo.callerPid;
833 callerUid_ = callerInfo.callerUid;
834 callerDeviceID_ = callerInfo.callerDeviceID;
835 clientFd_ = callerInfo.clientFd;
836 callerTokenID_ = callerInfo.callerTokenID;
837 firstTokenID_ = callerInfo.firstTokenID;
838 }
839
GetCallerInfo(DBinderCallerInfo & callerInfo)840 void DBinderDatabusInvoker::GetCallerInfo(DBinderCallerInfo &callerInfo)
841 {
842 callerInfo.callerPid = callerPid_;
843 callerInfo.callerUid = callerUid_;
844 callerInfo.callerDeviceID = callerDeviceID_;
845 callerInfo.clientFd = clientFd_;
846 callerInfo.callerTokenID = callerTokenID_;
847 callerInfo.firstTokenID = firstTokenID_;
848 }
849
850 // LCOV_EXCL_START
GetLocalDeviceID()851 std::string DBinderDatabusInvoker::GetLocalDeviceID()
852 {
853 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
854 if (current == nullptr) {
855 ZLOGE(LOG_LABEL, "current process skeleton is nullptr");
856 return "";
857 }
858
859 return current->GetLocalDeviceID();
860 }
861 // LCOV_EXCL_STOP
862
GetCallerDeviceID() const863 std::string DBinderDatabusInvoker::GetCallerDeviceID() const
864 {
865 return callerDeviceID_;
866 }
867
MakeStubIndexByRemoteObject(IRemoteObject * stubObject)868 uint64_t DBinderDatabusInvoker::MakeStubIndexByRemoteObject(IRemoteObject *stubObject)
869 {
870 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
871 if (current == nullptr) {
872 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
873 return 0;
874 }
875
876 if (!current->IsContainsObject(stubObject)) {
877 ZLOGE(LOG_LABEL, "fail to find stub");
878 return 0;
879 }
880
881 uint64_t stubIndex = current->AddStubByIndex(stubObject);
882 if (!stubIndex) {
883 ZLOGE(LOG_LABEL, "fail to add stub");
884 return 0;
885 }
886 return stubIndex;
887 }
888
MakeDefaultServerSessionObject(uint64_t stubIndex,const std::shared_ptr<DBinderSessionObject> sessionObject)889 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::MakeDefaultServerSessionObject(uint64_t stubIndex,
890 const std::shared_ptr<DBinderSessionObject> sessionObject)
891 {
892 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
893 if (current == nullptr) {
894 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
895 return nullptr;
896 }
897 std::string serviceName = current->GetDatabusName();
898 std::string deviceId = current->GetLocalDeviceID();
899 if (serviceName.empty() || deviceId.empty()) {
900 ZLOGE(LOG_LABEL, "fail to get databus name:%{public}s or deviceId length:%{public}zu",
901 serviceName.c_str(), deviceId.length());
902 return nullptr;
903 }
904
905 auto session = std::make_shared<DBinderSessionObject>(serviceName, deviceId, stubIndex, nullptr,
906 sessionObject->GetTokenId());
907 if (session == nullptr) {
908 ZLOGE(LOG_LABEL, "new server session fail, service:%{public}s deviceId:%{public}s stubIndex:%{public}" PRIu64,
909 serviceName.c_str(), IPCProcessSkeleton::ConvertToSecureString(deviceId).c_str(), stubIndex);
910 return nullptr;
911 }
912 return session;
913 }
914
ConnectRemoteObject2Session(IRemoteObject * stubObject,uint64_t stubIndex,const std::shared_ptr<DBinderSessionObject> sessionObject)915 bool DBinderDatabusInvoker::ConnectRemoteObject2Session(IRemoteObject *stubObject, uint64_t stubIndex,
916 const std::shared_ptr<DBinderSessionObject> sessionObject)
917 {
918 if (sessionObject == nullptr) {
919 ZLOGE(LOG_LABEL, "session object is nullptr");
920 return false;
921 }
922 IPCProcessSkeleton *current = IPCProcessSkeleton::GetCurrent();
923 if (current == nullptr) {
924 ZLOGE(LOG_LABEL, "IPCProcessSkeleton is nullptr");
925 return false;
926 }
927
928 int peerPid = sessionObject->GetPeerPid();
929 int peerUid = sessionObject->GetPeerUid();
930 uint32_t tokenId = sessionObject->GetTokenId();
931 std::string deviceId = sessionObject->GetDeviceId();
932 ZLOGI(LOG_LABEL, "pid:%{public}d uid:%{public}d deviceId:%{public}s tokenId:%{public}u "
933 "stubIndex:%{public}" PRIu64, peerPid, peerUid, IPCProcessSkeleton::ConvertToSecureString(deviceId).c_str(),
934 tokenId, stubIndex);
935 // mark socketId as 0
936 AppAuthInfo appAuthInfo = { peerPid, peerUid, tokenId, 0, stubIndex, stubObject, deviceId };
937 if (current->AttachOrUpdateAppAuthInfo(appAuthInfo)) {
938 // first time send this stub to proxy indicating by deviceId, pid, uid
939 stubObject->IncStrongRef(this);
940 }
941 return true;
942 }
943
CreateServerSessionObject(binder_uintptr_t binder,std::shared_ptr<DBinderSessionObject> sessionObject)944 std::shared_ptr<DBinderSessionObject> DBinderDatabusInvoker::CreateServerSessionObject(binder_uintptr_t binder,
945 std::shared_ptr<DBinderSessionObject> sessionObject)
946 {
947 IRemoteObject *stubObject = reinterpret_cast<IPCObjectStub *>(binder);
948 if (stubObject == nullptr) {
949 ZLOGE(LOG_LABEL, "binder is nullptr");
950 return nullptr;
951 }
952
953 uint64_t stubIndex = MakeStubIndexByRemoteObject(stubObject);
954 if (stubIndex == 0) {
955 ZLOGE(LOG_LABEL, "fail to add stub");
956 return nullptr;
957 }
958 if (ConnectRemoteObject2Session(stubObject, stubIndex, sessionObject) != true) {
959 ZLOGE(LOG_LABEL, "fail to connect stub to session, stubIndex:%{public}" PRIu64, stubIndex);
960 return nullptr;
961 }
962 return MakeDefaultServerSessionObject(stubIndex, sessionObject);
963 }
964
FlushCommands(IRemoteObject * object)965 int DBinderDatabusInvoker::FlushCommands(IRemoteObject *object)
966 {
967 if (object == nullptr || !object->IsProxyObject()) {
968 ZLOGE(LOG_LABEL, "proxy is invalid");
969 return RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
970 }
971
972 IPCObjectProxy *proxy = reinterpret_cast<IPCObjectProxy *>(object);
973
974 std::shared_ptr<DBinderSessionObject> session = QueryServerSessionObject(proxy->GetHandle());
975 if (session == nullptr) {
976 ZLOGE(LOG_LABEL, "session is nullptr");
977 return RPC_DATABUS_INVOKER_INVALID_DATA_ERR;
978 }
979
980 (void)OnSendMessage(session);
981 return ERR_NONE;
982 }
983
984 // LCOV_EXCL_START
ResetCallingIdentity()985 std::string DBinderDatabusInvoker::ResetCallingIdentity()
986 {
987 std::string token = std::to_string(((static_cast<uint64_t>(callerUid_) << PID_LEN)
988 | static_cast<uint64_t>(callerPid_)));
989 std::string identity = callerDeviceID_ + token;
990 char buf[ACCESS_TOKEN_MAX_LEN + 1] = {0};
991 int ret = sprintf_s(buf, ACCESS_TOKEN_MAX_LEN + 1, "%020" PRIu64, callerTokenID_);
992 if (ret < 0) {
993 ZLOGE(LOG_LABEL, "sprintf callerTokenID:%{public}" PRIu64 " failed", callerTokenID_);
994 return "";
995 }
996 std::string accessToken(buf);
997 callerUid_ = (pid_t)getuid();
998 callerPid_ = getpid();
999 callerDeviceID_ = GetLocalDeviceID();
1000 callerTokenID_ = GetSelfTokenID();
1001 return accessToken + identity;
1002 }
1003 // LCOV_EXCL_STOP
1004
SetCallingIdentity(std::string & identity,bool flag)1005 bool DBinderDatabusInvoker::SetCallingIdentity(std::string &identity, bool flag)
1006 {
1007 (void)flag;
1008 if (identity.empty() || identity.length() <= DEVICEID_LENGTH) {
1009 return false;
1010 }
1011 std::string tokenIdStr;
1012 uint64_t tokenId = 0;
1013 if (!ProcessSkeleton::GetSubStr(identity, tokenIdStr, 0, ACCESS_TOKEN_MAX_LEN) ||
1014 !ProcessSkeleton::StrToUint64(tokenIdStr, tokenId)) {
1015 ZLOGE(LOG_LABEL, "Identity param tokenId is invalid");
1016 return false;
1017 }
1018 std::string deviceId;
1019 if (!ProcessSkeleton::GetSubStr(identity, deviceId, ACCESS_TOKEN_MAX_LEN, DEVICEID_LENGTH)) {
1020 ZLOGE(LOG_LABEL, "Identity param deviceId is invalid");
1021 return false;
1022 }
1023 std::string tokenStr;
1024 size_t offset = ACCESS_TOKEN_MAX_LEN + DEVICEID_LENGTH;
1025 if (identity.length() <= offset) {
1026 ZLOGE(LOG_LABEL, "Identity param no token, len:%{public}zu, offset:%{public}zu", identity.length(), offset);
1027 return false;
1028 }
1029 size_t subLen = identity.length() - offset;
1030 uint64_t token = 0;
1031 if (!ProcessSkeleton::GetSubStr(identity, tokenStr, offset, subLen) ||
1032 !ProcessSkeleton::StrToUint64(tokenStr, token)) {
1033 ZLOGE(LOG_LABEL, "Identity param token is invalid");
1034 return false;
1035 }
1036 callerUid_ = static_cast<pid_t>(token >> PID_LEN);
1037 callerPid_ = static_cast<pid_t>(token);
1038 callerDeviceID_ = deviceId;
1039 callerTokenID_ = tokenId;
1040 return true;
1041 }
1042
TriggerSystemIPCThreadReclaim()1043 bool DBinderDatabusInvoker::TriggerSystemIPCThreadReclaim()
1044 {
1045 ZLOGD(LOG_LABEL, "do not support");
1046 return false;
1047 }
1048
EnableIPCThreadReclaim(bool enable)1049 bool DBinderDatabusInvoker::EnableIPCThreadReclaim(bool enable)
1050 {
1051 (void)enable;
1052 ZLOGD(LOG_LABEL, "do not support");
1053 return false;
1054 }
1055
HasRawDataPackage(const char * data,ssize_t len)1056 uint32_t DBinderDatabusInvoker::HasRawDataPackage(const char *data, ssize_t len)
1057 {
1058 const dbinder_transaction_data *tr = reinterpret_cast<const dbinder_transaction_data *>(data);
1059 if ((tr->magic == DBINDER_MAGICWORD) && (tr->cmd == BC_SEND_RAWDATA) &&
1060 (tr->sizeOfSelf == static_cast<uint32_t>(len))) {
1061 if (tr->sizeOfSelf > MAX_RAWDATA_SIZE) {
1062 return MAX_RAWDATA_SIZE;
1063 }
1064 return tr->sizeOfSelf;
1065 }
1066 return 0;
1067 }
1068
HasCompletePackage(const char * data,uint32_t readCursor,ssize_t len)1069 uint32_t DBinderDatabusInvoker::HasCompletePackage(const char *data, uint32_t readCursor, ssize_t len)
1070 {
1071 const dbinder_transaction_data *tr = reinterpret_cast<const dbinder_transaction_data *>(data + readCursor);
1072 if ((tr->magic == DBINDER_MAGICWORD) &&
1073 (tr->sizeOfSelf <= SOCKET_MAX_BUFF_SIZE + sizeof(dbinder_transaction_data)) &&
1074 (readCursor + tr->sizeOfSelf <= static_cast<uint32_t>(len)) && CheckTransactionData(tr)) {
1075 return tr->sizeOfSelf;
1076 }
1077 PrintDBinderTransData(tr);
1078 return 0;
1079 }
1080 } // namespace OHOS
1081