1 /*
2 * Copyright (C) 2022 Huawei Technologies Co., Ltd.
3 * Licensed under the Mulan PSL v2.
4 * You can use this software according to the terms and conditions of the Mulan PSL v2.
5 * You may obtain a copy of Mulan PSL v2 at:
6 * http://license.coscl.org.cn/MulanPSL2
7 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR
8 * IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR
9 * PURPOSE.
10 * See the Mulan PSL v2 for more details.
11 */
12
13 #include "cadaemon_stub.h"
14 #include <malloc.h>
15 #include <memory>
16 #include <securec.h>
17 #include "ipc_skeleton.h"
18 #include "ipc_types.h"
19 #include "string_ex.h"
20 #include "tee_client_api.h"
21 #include "tee_client_inner.h"
22 #include "tee_log.h"
23
24 using namespace std;
25
26 namespace OHOS {
27 namespace CaDaemon {
28 const std::u16string INTERFACE_TOKEN = u"ohos.tee_client.accessToken";
29
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)30 int32_t CaDaemonStub::OnRemoteRequest(uint32_t code,
31 MessageParcel& data, MessageParcel &reply, MessageOption &option)
32 {
33 tlogi("CaDaemonStub::OnReceived, code = %" PUBLIC "u, flags= %" PUBLIC "d.", code, option.GetFlags());
34 int32_t result;
35 (void)mallopt(M_SET_THREAD_CACHE, M_THREAD_CACHE_DISABLE);
36 (void)mallopt(M_DELAYED_FREE, M_DELAYED_FREE_DISABLE);
37 switch (code) {
38 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::INIT_CONTEXT):
39 result = InitContextRecvProc(data, reply);
40 break;
41 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::FINAL_CONTEXT):
42 result = FinalContextRecvProc(data, reply);
43 break;
44 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::OPEN_SESSION):
45 result = OpenSessionRecvProc(data, reply);
46 break;
47 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::CLOSE_SESSION):
48 result = CloseSessionRecvProc(data, reply);
49 break;
50 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::INVOKE_COMMND):
51 result = InvokeCommandRecvProc(data, reply);
52 break;
53 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::REGISTER_MEM):
54 result = RegisterMemRecvProc(data, reply);
55 break;
56 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::ALLOC_MEM):
57 result = AllocMemRecvProc(data, reply);
58 break;
59 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::RELEASE_MEM):
60 result = ReleaseMemRecvProc(data, reply);
61 break;
62 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::SET_CALL_BACK):
63 result = SetCallBackRecvProc(data, reply);
64 break;
65 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::SEND_SECFILE):
66 result = SendSecFileRecvProc(data, reply);
67 break;
68 case static_cast<uint32_t>(CadaemonOperationInterfaceCode::GET_TEE_VERSION):
69 result = GetTeeVersionRecvProc(data, reply);
70 break;
71 default:
72 tlogi("CaDaemonStub: default case, need check");
73 (void)mallopt(M_FLUSH_THREAD_CACHE, 0);
74 return IPCObjectStub::OnRemoteRequest(code, data, reply, option);
75 }
76
77 (void)mallopt(M_FLUSH_THREAD_CACHE, 0);
78 return result;
79 }
80
GetChar(MessageParcel & data,char tempChar[],const char ** str)81 static bool GetChar(MessageParcel &data, char tempChar[], const char **str)
82 {
83 uint32_t strLen;
84 string tempStr;
85 int32_t ret;
86
87 ret = data.ReadUint32(strLen);
88 CHECK_ERR_RETURN(ret, true, ret);
89
90 if (strLen > 0) {
91 ret = data.ReadString(tempStr);
92 CHECK_ERR_RETURN(ret, true, ret);
93 if (strnlen(tempStr.c_str(), PATH_MAX) == PATH_MAX || strLen != strnlen(tempStr.c_str(), PATH_MAX)) {
94 tloge("recv str length check fail\n");
95 return false;
96 }
97
98 if (strcpy_s(tempChar, PATH_MAX + 1, tempStr.c_str()) != EOK) {
99 tloge("copy str fail, errno = %" PUBLIC "d\n", errno);
100 return false;
101 }
102 *str = tempChar;
103 }
104
105 return true;
106 }
107
InitContextRecvProc(MessageParcel & data,MessageParcel & reply)108 int32_t CaDaemonStub::InitContextRecvProc(MessageParcel &data, MessageParcel &reply)
109 {
110 if (!EnforceInterceToken(data)) {
111 tloge("CaDaemonStub: InitContextRecvProc interface token check failed!");
112 return ERR_UNKNOWN_REASON;
113 }
114
115 const char *name = nullptr;
116 char tempChar[PATH_MAX + 1] = { 0 };
117 if (!GetChar(data, tempChar, &name)) {
118 tloge("InitContextRecvProc: get name failed\n");
119 return ERR_UNKNOWN_OBJECT;
120 }
121
122 if (InitializeContext(name, reply) != TEEC_SUCCESS) {
123 tloge("initialize context failed\n");
124 return ERR_UNKNOWN_REASON;
125 }
126
127 return ERR_NONE;
128 }
129
FinalContextRecvProc(MessageParcel & data,MessageParcel & reply)130 int32_t CaDaemonStub::FinalContextRecvProc(MessageParcel &data, MessageParcel &reply)
131 {
132 (void)reply;
133 if (!EnforceInterceToken(data)) {
134 tloge("CaDaemonStub: FinalContextRecvProc interface token check failed!");
135 return -1;
136 }
137
138 TEEC_Context *context = nullptr;
139 size_t len = sizeof(*context);
140 context = (TEEC_Context *)(data.ReadBuffer(len));
141 if (context == nullptr) {
142 return ERR_UNKNOWN_OBJECT;
143 }
144
145 if (FinalizeContext(context) != TEEC_SUCCESS) {
146 return ERR_UNKNOWN_REASON;
147 }
148
149 return ERR_NONE;
150 }
151
GetContextFromData(MessageParcel & data,TEEC_Context * context)152 static bool GetContextFromData(MessageParcel &data, TEEC_Context *context)
153 {
154 size_t len = sizeof(*context);
155 TEEC_Context *tempContext = (TEEC_Context *)(data.ReadBuffer(len));
156 if (tempContext == nullptr) {
157 return false;
158 }
159
160 if (memcpy_s(context, len, tempContext, len) != EOK) {
161 tloge("getContext: operation memcpy failed\n");
162 return false;
163 }
164 return true;
165 }
166
GetSessionFromData(MessageParcel & data,TEEC_Session * session)167 static bool GetSessionFromData(MessageParcel &data, TEEC_Session *session)
168 {
169 TEEC_Session *tempSession = nullptr;
170 size_t len = sizeof(*tempSession);
171 tempSession = (TEEC_Session *)(data.ReadBuffer(len));
172 if (tempSession == nullptr) {
173 return false;
174 }
175
176 if (memcpy_s(session, len, tempSession, len) != EOK) {
177 tloge("getSession: operation memcpy failed\n");
178 return false;
179 }
180 return true;
181 }
182
GetSharedMemFromData(MessageParcel & data,TEEC_SharedMemory * shm)183 static bool GetSharedMemFromData(MessageParcel &data, TEEC_SharedMemory *shm)
184 {
185 tlogi("start to recieve sharedmem\n");
186 TEEC_SharedMemory *tempShm = nullptr;
187 size_t len = sizeof(*tempShm);
188 tempShm = (TEEC_SharedMemory *)(data.ReadBuffer(len));
189 if (tempShm == nullptr) {
190 return false;
191 }
192
193 if (memcpy_s(shm, len, tempShm, len) != EOK) {
194 tloge("getShamem: operation memcpy failed\n");
195 return false;
196 }
197 return true;
198 }
199
SetInvalidIonFd(TEEC_Operation * operation)200 static void SetInvalidIonFd(TEEC_Operation *operation)
201 {
202 uint32_t paramType[TEEC_PARAM_NUM] = { 0 };
203 for (uint32_t paramCnt = 0; paramCnt < TEEC_PARAM_NUM; paramCnt++) {
204 paramType[paramCnt] = TEEC_PARAM_TYPE_GET(operation->paramTypes, paramCnt);
205 if (paramType[paramCnt] == TEEC_ION_INPUT) {
206 operation->params[paramCnt].ionref.ion_share_fd = -1;
207 }
208 }
209 }
210
CloseDupIonFd(TEEC_Operation * operation)211 static void CloseDupIonFd(TEEC_Operation *operation)
212 {
213 uint32_t paramType[TEEC_PARAM_NUM] = { 0 };
214 for (uint32_t paramCnt = 0; paramCnt < TEEC_PARAM_NUM; paramCnt++) {
215 paramType[paramCnt] = TEEC_PARAM_TYPE_GET(operation->paramTypes, paramCnt);
216 if (paramType[paramCnt] != TEEC_ION_INPUT) {
217 continue;
218 }
219 if (operation->params[paramCnt].ionref.ion_share_fd >= 0) {
220 close(operation->params[paramCnt].ionref.ion_share_fd);
221 }
222 }
223 }
224
GetOperationFromData(MessageParcel & data,TEEC_Operation * operation,bool & opFlag)225 static bool GetOperationFromData(MessageParcel &data, TEEC_Operation *operation, bool &opFlag)
226 {
227 bool retTmp = data.ReadBool(opFlag);
228 uint32_t paramType[TEEC_PARAM_NUM] = { 0 };
229 CHECK_ERR_RETURN(retTmp, true, retTmp);
230
231 if (!opFlag) {
232 tloge("operation is nullptr\n");
233 return true;
234 }
235
236 size_t len = sizeof(*operation);
237 TEEC_Operation *tempOp = (TEEC_Operation *)(data.ReadBuffer(len));
238 if (tempOp == nullptr) {
239 return false;
240 }
241
242 if (memcpy_s(operation, len, tempOp, len) != EOK) {
243 tloge("getOperation: operation memcpy failed\n");
244 return false;
245 }
246
247 /* First, set ion fd invalid, easy to judge if a dup fd can be closed */
248 SetInvalidIonFd(operation);
249 /* clear the pointer from ca to avoid access to invalid address */
250 operation->session = nullptr;
251 for (uint32_t paramCnt = 0; paramCnt < TEEC_PARAM_NUM; paramCnt++) {
252 paramType[paramCnt] = TEEC_PARAM_TYPE_GET(operation->paramTypes, paramCnt);
253 if (IS_TEMP_MEM(paramType[paramCnt])) {
254 operation->params[paramCnt].tmpref.buffer = nullptr;
255 } else if (IS_PARTIAL_MEM(paramType[paramCnt])) {
256 operation->params[paramCnt].memref.parent = nullptr;
257 } else if (paramType[paramCnt] == TEEC_ION_INPUT) {
258 operation->params[paramCnt].ionref.ion_share_fd = data.ReadFileDescriptor();
259 if (operation->params[paramCnt].ionref.ion_share_fd < 0) {
260 tloge("read ion fd from parcel failed\n");
261 CloseDupIonFd(operation);
262 return false;
263 }
264 }
265 }
266 return true;
267 }
268
269
ReadFd(MessageParcel & data,int32_t & fd)270 static bool ReadFd(MessageParcel &data, int32_t &fd)
271 {
272 bool fdFlag = false;
273
274 bool retTmp = data.ReadBool(fdFlag);
275 CHECK_ERR_RETURN(retTmp, true, retTmp);
276
277 if (fdFlag) {
278 fd = data.ReadFileDescriptor();
279 if (fd < 0) {
280 tloge("read fd failed\n");
281 return false;
282 }
283 tloge("read fd success = %" PUBLIC "d\n", fd);
284 }
285 return true;
286 }
287
ClearAsmMem(sptr<Ashmem> & optMem)288 static void ClearAsmMem(sptr<Ashmem> &optMem)
289 {
290 if (optMem != nullptr) {
291 optMem->UnmapAshmem();
292 optMem->CloseAshmem();
293 }
294 }
295
GetOptMemFromData(MessageParcel & data,sptr<Ashmem> & optMem,uint32_t & optMemSize)296 static bool GetOptMemFromData(MessageParcel &data, sptr<Ashmem> &optMem, uint32_t &optMemSize)
297 {
298 bool retTmp = data.ReadUint32(optMemSize);
299 CHECK_ERR_RETURN(retTmp, true, retTmp);
300
301 if (optMemSize > 0) {
302 optMem = data.ReadAshmem();
303 if (optMem == nullptr) {
304 tloge("get optMem failed\n");
305 return false;
306 }
307
308 bool ret = optMem->MapReadAndWriteAshmem();
309 if (!ret) {
310 tloge("map ashmem failed\n");
311 return false;
312 }
313 }
314
315 return true;
316 }
317
ReadOpenData(MessageParcel & data,int32_t & fd,TEEC_UUID ** uuid,uint32_t & connMethod)318 static int32_t ReadOpenData(MessageParcel &data, int32_t &fd, TEEC_UUID **uuid, uint32_t &connMethod)
319 {
320 size_t len = sizeof(**uuid);
321
322 bool retTmp = ReadFd(data, fd);
323 if (!retTmp) {
324 tloge("read ta fd failed\n");
325 goto ERROR;
326 }
327
328 *uuid = (TEEC_UUID *)(data.ReadBuffer(len));
329 if (*uuid == nullptr) {
330 tloge("read uuid failed\n");
331 goto ERROR;
332 }
333
334 retTmp = data.ReadUint32(connMethod);
335 if (!retTmp) {
336 tloge("read connection method failed\n");
337 goto ERROR;
338 }
339
340 return ERR_NONE;
341
342 ERROR:
343 if (fd >= 0) {
344 close(fd);
345 }
346
347 return ERR_UNKNOWN_OBJECT;
348 }
349
OpenSessionRecvProc(MessageParcel & data,MessageParcel & reply)350 int32_t CaDaemonStub::OpenSessionRecvProc(MessageParcel &data, MessageParcel &reply)
351 {
352 int32_t result = ERR_NONE;
353 if (!EnforceInterceToken(data)) {
354 tloge("CaDaemonStub: OpenSessionRecvProc interface token check failed!");
355 return -1;
356 }
357
358 TEEC_Context context;
359 bool retTmp = GetContextFromData(data, &context);
360 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
361
362 const char *taPath = nullptr;
363 char tempChar[PATH_MAX + 1] = { 0 };
364 retTmp = GetChar(data, tempChar, &taPath);
365 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
366 if (taPath != nullptr) {
367 tlogi("recieve taPath is not nullptr\n");
368 context.ta_path = reinterpret_cast<uint8_t *>(const_cast<char *>(taPath));
369 }
370
371 uint32_t optMemSize;
372 sptr<Ashmem> optMem = nullptr;
373 int32_t fd = -1;
374 TEEC_UUID *uuid = nullptr;
375 uint32_t connMethod;
376 result = ReadOpenData(data, fd, &uuid, connMethod);
377 CHECK_ERR_RETURN(result, ERR_NONE, ERR_UNKNOWN_OBJECT);
378
379 TEEC_Operation operation;
380 bool opFlag = false;
381 /* from now on, default return value is ERR_UNKNOWN_OBJECT */
382 result = ERR_UNKNOWN_OBJECT;
383 retTmp = GetOperationFromData(data, &operation, opFlag);
384 CHECK_ERR_GOTO(retTmp, true, END_CLEAR_FD);
385
386 retTmp = GetOptMemFromData(data, optMem, optMemSize);
387 if (!retTmp) {
388 result = ERR_UNKNOWN_OBJECT;
389 goto END;
390 }
391
392 if (opFlag) {
393 result = OpenSession(&context, taPath, fd, uuid, connMethod, &operation, optMemSize, optMem, reply);
394 } else {
395 result = OpenSession(&context, taPath, fd, uuid, connMethod, nullptr, optMemSize, optMem, reply);
396 }
397
398 END:
399 ClearAsmMem(optMem);
400 CloseDupIonFd(&operation);
401 END_CLEAR_FD:
402 if (fd >= 0) {
403 close(fd);
404 }
405
406 return result;
407 }
408
CloseSessionRecvProc(MessageParcel & data,MessageParcel & reply)409 int32_t CaDaemonStub::CloseSessionRecvProc(MessageParcel &data, MessageParcel &reply)
410 {
411 (void)reply;
412 if (!EnforceInterceToken(data)) {
413 tloge("CaDaemonStub: CloseSessionRecvProc interface token check failed!");
414 return -1;
415 }
416
417 TEEC_Context context;
418 bool retTmp = GetContextFromData(data, &context);
419 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
420
421 TEEC_Session session;
422 retTmp = GetSessionFromData(data, &session);
423 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
424
425 if (CloseSession(&session, &context) != TEEC_SUCCESS) {
426 return ERR_UNKNOWN_REASON;
427 }
428
429 return ERR_NONE;
430 }
InvokeCommandRecvProc(MessageParcel & data,MessageParcel & reply)431 int32_t CaDaemonStub::InvokeCommandRecvProc(MessageParcel &data, MessageParcel &reply)
432 {
433 int32_t result = ERR_NONE;
434 if (!EnforceInterceToken(data)) {
435 tloge("CaDaemonStub: InvokeCommandRecvProc interface token check failed!");
436 return -1;
437 }
438
439 TEEC_Context context;
440 bool retTmp = GetContextFromData(data, &context);
441 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
442
443 TEEC_Session session;
444 retTmp = GetSessionFromData(data, &session);
445 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
446
447 uint32_t commandID;
448 retTmp = data.ReadUint32(commandID);
449 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
450
451 TEEC_Operation operation;
452 bool opFlag = false;
453 retTmp = GetOperationFromData(data, &operation, opFlag);
454 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
455
456 uint32_t optMemSize;
457 sptr<Ashmem> optMem;
458 retTmp = GetOptMemFromData(data, optMem, optMemSize);
459 if (!retTmp) {
460 result = ERR_UNKNOWN_OBJECT;
461 goto END;
462 }
463
464 if (opFlag) {
465 result = InvokeCommand(&context, &session, commandID, &operation, optMemSize, optMem, reply);
466 } else {
467 result = InvokeCommand(&context, &session, commandID, nullptr, optMemSize, optMem, reply);
468 }
469
470 END:
471 ClearAsmMem(optMem);
472 CloseDupIonFd(&operation);
473 return result;
474 }
475
RegisterMemRecvProc(MessageParcel & data,MessageParcel & reply)476 int32_t CaDaemonStub::RegisterMemRecvProc(MessageParcel &data, MessageParcel &reply)
477 {
478 if (!EnforceInterceToken(data)) {
479 tloge("CaDaemonStub: RegisterMemRecvProc interface token check failed!");
480 return -1;
481 }
482
483 TEEC_Context context;
484 bool retTmp = GetContextFromData(data, &context);
485 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
486
487 TEEC_SharedMemory sharedMem;
488 retTmp = GetSharedMemFromData(data, &sharedMem);
489 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
490
491 if (RegisterSharedMemory(&context, &sharedMem, reply) != TEEC_SUCCESS) {
492 return ERR_UNKNOWN_REASON;
493 }
494
495 return ERR_NONE;
496 }
497
AllocMemRecvProc(MessageParcel & data,MessageParcel & reply)498 int32_t CaDaemonStub::AllocMemRecvProc(MessageParcel &data, MessageParcel &reply)
499 {
500 if (!EnforceInterceToken(data)) {
501 tloge("CaDaemonStub: AllocMemRecvProc interface token check failed!");
502 return -1;
503 }
504
505 TEEC_Context context;
506 bool retTmp = GetContextFromData(data, &context);
507 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
508
509 TEEC_SharedMemory sharedMem;
510 retTmp = GetSharedMemFromData(data, &sharedMem);
511 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
512
513 if (AllocateSharedMemory(&context, &sharedMem, reply) != TEEC_SUCCESS) {
514 return ERR_UNKNOWN_REASON;
515 }
516
517 return ERR_NONE;
518 }
519
ReleaseMemRecvProc(MessageParcel & data,MessageParcel & reply)520 int32_t CaDaemonStub::ReleaseMemRecvProc(MessageParcel &data, MessageParcel &reply)
521 {
522 if (!EnforceInterceToken(data)) {
523 tloge("CaDaemonStub: ReleaseMemRecvProc interface token check failed!");
524 return -1;
525 }
526
527 TEEC_Context context;
528 bool retTmp = GetContextFromData(data, &context);
529 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
530
531 TEEC_SharedMemory sharedMem;
532 retTmp = GetSharedMemFromData(data, &sharedMem);
533 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
534
535 uint32_t shmOffset;
536 retTmp = data.ReadUint32(shmOffset);
537 CHECK_ERR_RETURN(retTmp, true, ERR_UNKNOWN_OBJECT);
538
539 ReleaseSharedMemory(&context, &sharedMem, shmOffset, reply);
540
541 return ERR_NONE;
542 }
543
SetCallBackRecvProc(MessageParcel & data,MessageParcel & reply)544 int32_t CaDaemonStub::SetCallBackRecvProc(MessageParcel &data, MessageParcel &reply)
545 {
546 if (!EnforceInterceToken(data)) {
547 tloge("CaDaemonStub: SetCallBackRecvProc interface token check failed!");
548 return -1;
549 }
550
551 sptr<IRemoteObject> notify = nullptr;
552 notify = data.ReadRemoteObject();
553 if (notify == nullptr) {
554 tloge("CaDaemonStub: recieve notify is nullptr\n");
555 return ERR_NONE;
556 }
557
558 return SetCallBack(notify);
559 }
560
EnforceInterceToken(MessageParcel & data)561 bool CaDaemonStub::EnforceInterceToken(MessageParcel& data)
562 {
563 u16string interfaceToken = data.ReadInterfaceToken();
564 return interfaceToken == INTERFACE_TOKEN;
565 }
566
SendSecFileRecvProc(MessageParcel & data,MessageParcel & reply)567 int32_t CaDaemonStub::SendSecFileRecvProc(MessageParcel& data, MessageParcel &reply)
568 {
569 if (!EnforceInterceToken(data)) {
570 tloge("CaDaemonStub: SendSecFileRecvProc interface token check failed!");
571 return -1;
572 }
573 const char *path = nullptr;
574 char tempChar[PATH_MAX + 1] = {0};
575 if (!GetChar(data, tempChar, &path)) {
576 tloge("SendSecFileRecvProc: get path failed\n");
577 return ERR_UNKNOWN_OBJECT;
578 }
579
580 int fd = -1;
581 (void)ReadFd(data, fd);
582 if (fd < 0) {
583 tloge("SendSecFileRecvProc: ReadFd failed\n");
584 return ERR_UNKNOWN_OBJECT;
585 }
586
587 TEEC_Context context;
588 if (GetContextFromData(data, &context) != true) {
589 tloge("SendSecFileRecvProc: get context failed\n");
590 close(fd);
591 return ERR_UNKNOWN_OBJECT;
592 }
593
594 TEEC_Session session;
595 if (GetSessionFromData(data, &session) != true) {
596 tloge("SendSecFileRecvProc: get session failed\n");
597 close(fd);
598 return ERR_UNKNOWN_OBJECT;
599 }
600
601 FILE *fp = fdopen(fd, "r");
602 if (fp != nullptr) {
603 (void)SendSecfile(path, context.fd, fp, reply);
604 /* within fclose function, fd has been closed */
605 fclose(fp);
606 } else {
607 tloge("SendSecFileRecvProc: fdopen failed\n");
608 close(fd);
609 return ERR_INVALID_DATA;
610 }
611
612 return ERR_NONE;
613 }
614
GetTeeVersionRecvProc(MessageParcel & data,MessageParcel & reply)615 int32_t CaDaemonStub::GetTeeVersionRecvProc(MessageParcel& data, MessageParcel &reply)
616 {
617 (void)GetTeeVersion(reply);
618 return ERR_NONE;
619 }
620 } // namespace CaDaemon
621 } // namespace OHOS
622