xref: /rk3399_rockchip-uboot/lib/optee_clientApi/OpteeClientRPC.c (revision 2ba7147f8008e675b31a0a5c13b8366431ea09ae)
1 /*
2  * Copyright 2017, Rockchip Electronics Co., Ltd
3  * hisping lin, <hisping.lin@rock-chips.com>
4  *
5  * SPDX-License-Identifier:	GPL-2.0+
6  */
7 #include <common.h>
8 #include <stdlib.h>
9 #include <command.h>
10 #include <mmc.h>
11 #include <optee_include/OpteeClientMem.h>
12 #include <optee_include/OpteeClientRPC.h>
13 #include <optee_include/teesmc.h>
14 #include <optee_include/teesmc_v2.h>
15 #include <optee_include/teesmc_optee.h>
16 #include <optee_include/tee_rpc_types.h>
17 #include <optee_include/tee_rpc.h>
18 #ifdef CONFIG_OPTEE_V1
19 #include <optee_include/OpteeClientRkFs.h>
20 #endif
21 #ifdef CONFIG_OPTEE_V2
22 #include <optee_include/OpteeClientRkFs-v2.h>
23 #endif
24 
25 /*
26  * Memory allocation.
27  * Currently treated the same for both arguments & payloads.
28  */
29 TEEC_Result OpteeRpcAlloc(uint32_t Size, uint32_t *Address)
30 {
31 	TEEC_Result TeecResult = TEEC_SUCCESS;
32 	size_t AllocAddress;
33 
34 	*Address = 0;
35 
36 	if (Size != 0) {
37 		AllocAddress = (size_t) OpteeClientMemAlloc(Size);
38 
39 		if (AllocAddress == 0)
40 			TeecResult = TEEC_ERROR_OUT_OF_MEMORY;
41 		else
42 			*Address = AllocAddress;
43 	}
44 	return TeecResult;
45 }
46 
47 /*
48  * Memory free.
49  * Currently treated the same for both arguments & payloads.
50  */
51 TEEC_Result OpteeRpcFree(uint32_t Address)
52 {
53 	OpteeClientMemFree((void *)(size_t)Address);
54 	return TEEC_SUCCESS;
55 }
56 
57 int is_uuid_equal(TEE_UUID uuid1, TEEC_UUID uuid2)
58 {
59 	bool a, b, c;
60 
61 	a = (uuid1.timeLow == uuid2.timeLow);
62 	b = (uuid1.timeMid == uuid2.timeMid);
63 	c = (uuid1.timeHiAndVersion == uuid2.timeHiAndVersion);
64 	if ((a & b & c) == 0) {
65 		return 0;
66 	} else {
67 		if (memcmp(uuid1.clockSeqAndNode,
68 			   uuid2.clockSeqAndNode, 8) == 0) {
69 			return 1;
70 		} else {
71 			return 0;
72 		}
73 	}
74 }
75 
76 /*
77  * Load a TA from storage into memory and provide it back to OpTEE.
78  * Param[0] = IN: struct tee_rpc_load_ta_cmd
79  * Param[1] = IN: all-zero OUT: TA Image allocated
80  */
81 TEEC_Result OpteeRpcCmdLoadTa(t_teesmc32_arg *TeeSmc32Arg)
82 {
83 	TEEC_Result TeecResult = TEEC_SUCCESS;
84 	t_teesmc32_param *TeeSmc32Param = NULL;
85 	struct tee_rpc_load_ta_cmd *TeeLoadTaCmd = NULL;
86 	uint32_t TeeLoadTaCmdSize = 0;
87 
88 	if (TeeSmc32Arg->num_params != 2) {
89 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
90 		goto Exit;
91 	}
92 
93 	TEEC_UUID TA_RK_KEYMASTER_UUID = {0x258be795, 0xf9ca, 0x40e6,
94 			{0xa8, 0x69, 0x9c, 0xe6, 0x88, 0x6c, 0x5d, 0x5d} };
95 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
96 	TeeLoadTaCmd = (struct tee_rpc_load_ta_cmd *)
97 					(size_t)TeeSmc32Param[0].u.memref.buf_ptr;
98 	TeeLoadTaCmdSize = TeeSmc32Param[0].u.memref.size;
99 
100 	if ((TeeLoadTaCmd == NULL) ||
101 		(TeeLoadTaCmdSize != sizeof(*TeeLoadTaCmd))) {
102 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
103 		goto Exit;
104 	}
105 
106 	TEEC_Result Status = 0;
107 	void *ImageData = NULL;
108 	uint32_t ImageSize = 0;
109 	size_t AllocAddress = 0;
110 
111 	if (is_uuid_equal(TeeLoadTaCmd->uuid, TA_RK_KEYMASTER_UUID)) {
112 		ImageData = (void *)0;
113 		ImageSize = 0;
114 	} else {
115 		ImageData = (void *)0;
116 		ImageSize = 0;
117 	}
118 
119 	if (Status != 0) {
120 		TeecResult = TEEC_ERROR_ITEM_NOT_FOUND;
121 		goto Exit;
122 	}
123 
124 	AllocAddress = (size_t) OpteeClientMemAlloc(ImageSize);
125 
126 	if (AllocAddress == 0) {
127 		TeecResult = TEEC_ERROR_OUT_OF_MEMORY;
128 		goto Exit;
129 	}
130 
131 	memcpy((void *)AllocAddress, ImageData, ImageSize);
132 
133 	debug("TEEC: ...TA loaded at 0x%zu of size 0x%X bytes\n",
134 		AllocAddress, ImageSize);
135 	debug("TEEC: ...AllocAddress[0] 0x%X ; AllocAddress[1] 0x%X bytes\n",
136 		*(char *)AllocAddress, *(char *)(AllocAddress+1));
137 
138 	TeeLoadTaCmd->va = AllocAddress;
139 
140 	TeeSmc32Param[1].u.memref.buf_ptr = AllocAddress;
141 	TeeSmc32Param[1].u.memref.size = ImageSize;
142 
143 Exit:
144 	TeeSmc32Arg->ret = TeecResult;
145 	TeeSmc32Arg->ret_origin = TEEC_ORIGIN_API;
146 
147 	debug("TEEC: OpteeRpcCmdLoadTa Exit : TeecResult=0x%X\n", TeecResult);
148 
149 	return TeecResult;
150 }
151 
152 #ifdef CONFIG_OPTEE_V2
153 TEEC_Result OpteeRpcCmdLoadV2Ta(t_teesmc32_arg *TeeSmc32Arg)
154 {
155 	TEEC_Result TeecResult = TEEC_SUCCESS;
156 	t_teesmc32_param *TeeSmc32Param = NULL;
157 	uint8_t uuid[16];
158 	int i;
159 
160 	if (TeeSmc32Arg->num_params != 2) {
161 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
162 		goto Exit;
163 	}
164 
165 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
166 
167 	memcpy(uuid, (void *)&TeeSmc32Param[0].u.value, 16);
168 	for (i = 0; i < 16; i++)
169 		debug("TEEC: uuid 0x%x", uuid[i]);
170 
171 	if (TeeSmc32Param[1].u.memref.buf_ptr == 0) {
172 		debug("TEEC: return size of TA, keymaster_size = 0\n");
173 		TeeSmc32Param[1].u.memref.size = 0;
174 	} else {
175 		/*memcpy((void *)(size_t)TeeSmc32Param[1].u.memref.buf_ptr,
176 			(void *)keymaster_data, TeeSmc32Param[1].u.memref.size);*/
177 		debug("TEEC: memref.buf_ptr = 0x%llx; memref.size = 0x%llx\n",
178 			TeeSmc32Param[1].u.memref.buf_ptr,
179 			TeeSmc32Param[1].u.memref.size);
180 	}
181 
182 Exit:
183 	TeeSmc32Arg->ret = TeecResult;
184 	TeeSmc32Arg->ret_origin = TEEC_ORIGIN_API;
185 
186 	debug("TEEC: OpteeRpcCmdLoadTa Exit : TeecResult=0x%X\n", TeecResult);
187 
188 	return TeecResult;
189 }
190 #endif
191 
192 /*
193  * Free a previously loaded TA and release the memory
194  * Param[0] = IN: TA Image to free
195  *
196  * Um, why is OpTEE holding on to this memory? The OS code suggests that OpTEE
197  * is using the binary in place out of shared memory but I don't understand how
198  * runtime modifications of the binary are being prevented if that's the case?
199  */
200 TEEC_Result OpteeRpcCmdFreeTa(t_teesmc32_arg *TeeSmc32Arg)
201 {
202 	TEEC_Result TeecResult = TEEC_SUCCESS;
203 	t_teesmc32_param *TeeSmc32Param = NULL;
204 	uint32_t ImageSize = 0;
205 	size_t AllocAddress = 0;
206 
207 	if (TeeSmc32Arg->num_params != 1) {
208 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
209 		goto Exit;
210 	}
211 
212 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
213 
214 	AllocAddress = TeeSmc32Param[0].u.memref.buf_ptr;
215 	ImageSize = TeeSmc32Param[0].u.memref.size;
216 
217 	debug("TEEC: OpteeRpcCmdFreeTa Enter: AllocAddress=0x%X, ImageSize=0x%X\n",
218 			(uint32_t) AllocAddress, (uint32_t) ImageSize);
219 
220 	if (AllocAddress == 0) {
221 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
222 		goto Exit;
223 	}
224 
225 	OpteeClientMemFree((void *)AllocAddress);
226 
227 Exit:
228 	TeeSmc32Arg->ret = TeecResult;
229 	TeeSmc32Arg->ret_origin = TEEC_ORIGIN_API;
230 
231 	debug("TEEC: OpteeRpcCmdFreeTa Exit : TeecResult=0x%X\n", TeecResult);
232 
233 	return TeecResult;
234 }
235 
236 /*
237  * Execute an RPMB storage operation.
238  */
239 
240 uint16_t global_block_count;
241 TEEC_Result OpteeRpcCmdRpmb(t_teesmc32_arg *TeeSmc32Arg)
242 {
243 	struct tee_rpc_rpmb_dev_info *DevInfo;
244 	TEEC_Result EfiStatus;
245 	uint16_t RequestMsgType, i;
246 	EFI_RK_RPMB_DATA_PACKET *RequestPackets;
247 	EFI_RK_RPMB_DATA_PACKET *ResponsePackets;
248 	EFI_RK_RPMB_DATA_PACKET *tempPackets;
249 	EFI_RK_RPMB_DATA_PACKET_BACK *RequestPackets_back;
250 	EFI_RK_RPMB_DATA_PACKET_BACK *tempPackets_back;
251 	struct tee_rpc_rpmb_cmd *RpmbRequest;
252 	TEEC_Result TeecResult = TEEC_SUCCESS;
253 	t_teesmc32_param *TeeSmc32Param;
254 	struct mmc *mmc;
255 
256 	debug("TEEC: Entered RPMB RPC\n");
257 
258 	if (TeeSmc32Arg->num_params != 2) {
259 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
260 		goto Exit;
261 	}
262 
263 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
264 	RpmbRequest = (struct tee_rpc_rpmb_cmd *)(size_t)
265 		TeeSmc32Param[0].u.memref.buf_ptr;
266 	switch (RpmbRequest->cmd) {
267 	case TEE_RPC_RPMB_CMD_DATA_REQ: {
268 		RequestPackets = (EFI_RK_RPMB_DATA_PACKET *)(RpmbRequest + 1);
269 		ResponsePackets = (EFI_RK_RPMB_DATA_PACKET *)(size_t)
270 		TeeSmc32Param[1].u.memref.buf_ptr;
271 
272 		global_block_count =
273 			(RpmbRequest->block_count == 0 ?
274 			1 : RpmbRequest->block_count);
275 		RequestPackets_back =
276 			malloc(sizeof(EFI_RK_RPMB_DATA_PACKET_BACK)
277 			* global_block_count);
278 		memcpy(RequestPackets_back->stuff,
279 			RequestPackets->stuff_bytes,
280 			RPMB_STUFF_DATA_SIZE);
281 		memcpy(RequestPackets_back->mac,
282 			RequestPackets->key_mac,
283 			RPMB_KEY_MAC_SIZE);
284 		memcpy(RequestPackets_back->data,
285 			RequestPackets->data,
286 			RPMB_DATA_SIZE);
287 		memcpy(RequestPackets_back->nonce,
288 			RequestPackets->nonce,
289 			RPMB_NONCE_SIZE);
290 		RequestPackets_back->write_counter =
291 			((RequestPackets->write_counter[3]) << 24) +
292 			((RequestPackets->write_counter[2]) << 16) +
293 			((RequestPackets->write_counter[1]) << 8) +
294 			(RequestPackets->write_counter[0]);
295 		RequestPackets_back->address =
296 			((RequestPackets->address[1]) << 8) +
297 			(RequestPackets->address[0]);
298 		RequestPackets_back->block_count =
299 			((RequestPackets->block_count[1]) << 8) +
300 			(RequestPackets->block_count[0]);
301 		RequestPackets_back->result =
302 			((RequestPackets->op_result[1]) << 8) +
303 			(RequestPackets->op_result[0]);
304 		RequestPackets_back->request =
305 			((RequestPackets->msg_type[1]) << 8) +
306 			(RequestPackets->msg_type[0]);
307 
308 		RequestMsgType = RPMB_PACKET_DATA_TO_UINT16(
309 				RequestPackets->msg_type);
310 
311 		debug("TEEC: RPMB Data request %d\n", RequestMsgType);
312 
313 		switch (RequestMsgType) {
314 		case TEE_RPC_RPMB_MSG_TYPE_REQ_AUTH_KEY_PROGRAM: {
315 			if (init_rpmb() != 0) {
316 				TeecResult = TEEC_ERROR_GENERIC;
317 				break;
318 			}
319 
320 			EfiStatus = do_programkey((struct s_rpmb *)
321 				RequestPackets_back);
322 
323 			if (finish_rpmb() != 0) {
324 				TeecResult = TEEC_ERROR_GENERIC;
325 				break;
326 			}
327 
328 			if (EfiStatus != 0) {
329 				TeecResult = TEEC_ERROR_GENERIC;
330 				break;
331 			}
332 
333 			break;
334 		}
335 
336 		case TEE_RPC_RPMB_MSG_TYPE_REQ_WRITE_COUNTER_VAL_READ: {
337 			if (init_rpmb() != 0) {
338 				TeecResult = TEEC_ERROR_GENERIC;
339 				break;
340 			}
341 
342 			EfiStatus = do_readcounter((struct s_rpmb *)
343 				RequestPackets_back);
344 
345 			if (finish_rpmb() != 0) {
346 				TeecResult = TEEC_ERROR_GENERIC;
347 				break;
348 			}
349 
350 			if (EfiStatus != 0) {
351 				TeecResult = TEEC_ERROR_GENERIC;
352 				break;
353 			}
354 
355 			break;
356 		}
357 
358 		case TEE_RPC_RPMB_MSG_TYPE_REQ_AUTH_DATA_WRITE: {
359 			if (init_rpmb() != 0) {
360 				TeecResult = TEEC_ERROR_GENERIC;
361 				break;
362 			}
363 
364 			EfiStatus = do_authenticatedwrite((struct s_rpmb *)
365 				RequestPackets_back);
366 
367 			if (finish_rpmb() != 0) {
368 				TeecResult = TEEC_ERROR_GENERIC;
369 				break;
370 			}
371 
372 			if (EfiStatus != 0) {
373 				TeecResult = TEEC_ERROR_GENERIC;
374 				break;
375 			}
376 
377 			break;
378 		}
379 
380 		case TEE_RPC_RPMB_MSG_TYPE_REQ_AUTH_DATA_READ: {
381 			if (init_rpmb() != 0) {
382 				TeecResult = TEEC_ERROR_GENERIC;
383 				break;
384 			}
385 
386 			EfiStatus = do_authenticatedread((struct s_rpmb *)
387 				RequestPackets_back, global_block_count);
388 
389 			if (finish_rpmb() != 0) {
390 				TeecResult = TEEC_ERROR_GENERIC;
391 				break;
392 			}
393 
394 			if (EfiStatus != 0) {
395 				TeecResult = TEEC_ERROR_GENERIC;
396 				break;
397 			}
398 
399 			break;
400 		}
401 
402 		default:
403 			TeecResult = TEEC_ERROR_BAD_PARAMETERS;
404 			break;
405 		}
406 		debug("TEEC: RPMB TeecResult %d\n", TeecResult);
407 		break;
408 	}
409 
410 	case TEE_RPC_RPMB_CMD_GET_DEV_INFO: {
411 		mmc = do_returnmmc();
412 
413 		DevInfo = (struct tee_rpc_rpmb_dev_info *)(size_t)
414 		TeeSmc32Param[1].u.memref.buf_ptr;
415 
416 		DevInfo->cid[0] = (mmc->cid[0]) >> 24 & 0xff;
417 		DevInfo->cid[1] = (mmc->cid[0]) >> 16 & 0xff;
418 		DevInfo->cid[2] = (mmc->cid[0]) >> 8 & 0xff;
419 		DevInfo->cid[3] = (mmc->cid[0]) & 0xff;
420 		DevInfo->cid[4] = (mmc->cid[1]) >> 24 & 0xff;
421 		DevInfo->cid[5] = (mmc->cid[1]) >> 16 & 0xff;
422 		DevInfo->cid[6] = (mmc->cid[1]) >> 8 & 0xff;
423 		DevInfo->cid[7] = (mmc->cid[1]) & 0xff;
424 		DevInfo->cid[8] = (mmc->cid[2]) >> 24 & 0xff;
425 		DevInfo->cid[9] = (mmc->cid[2]) >> 16 & 0xff;
426 		DevInfo->cid[10] = (mmc->cid[2]) >> 8 & 0xff;
427 		DevInfo->cid[11] = (mmc->cid[2]) & 0xff;
428 		DevInfo->cid[12] = (mmc->cid[3]) >> 24 & 0xff;
429 		DevInfo->cid[13] = (mmc->cid[3]) >> 16 & 0xff;
430 		DevInfo->cid[14] = (mmc->cid[3]) >> 8 & 0xff;
431 		DevInfo->cid[15] = (mmc->cid[3]) & 0xff;
432 		DevInfo->rel_wr_sec_c = 1;
433 		DevInfo->rpmb_size_mult =
434 			(uint8_t)(mmc->capacity_rpmb / (128 * 1024));
435 		DevInfo->ret_code = 0;
436 
437 		goto Exit;
438 	}
439 
440 	default:
441 		TeecResult = TEEC_ERROR_BAD_PARAMETERS;
442 
443 		goto Exit;
444 	}
445 
446 	tempPackets = ResponsePackets;
447 	tempPackets_back = RequestPackets_back;
448 
449 	for (i = 0; i < global_block_count; i++) {
450 		memcpy(tempPackets->stuff_bytes,
451 			tempPackets_back->stuff,
452 			RPMB_STUFF_DATA_SIZE);
453 		memcpy(tempPackets->key_mac,
454 			tempPackets_back->mac,
455 			RPMB_KEY_MAC_SIZE);
456 		memcpy(tempPackets->data,
457 			tempPackets_back->data,
458 			RPMB_DATA_SIZE);
459 		memcpy(tempPackets->nonce,
460 			tempPackets_back->nonce,
461 			RPMB_NONCE_SIZE);
462 		tempPackets->write_counter[3] =
463 			((tempPackets_back->write_counter) >> 24) & 0xFF;
464 		tempPackets->write_counter[2] =
465 			((tempPackets_back->write_counter) >> 16) & 0xFF;
466 		tempPackets->write_counter[1] =
467 			((tempPackets_back->write_counter) >> 8) & 0xFF;
468 		tempPackets->write_counter[0] =
469 			(tempPackets_back->write_counter) & 0xFF;
470 		tempPackets->address[1] =
471 			((tempPackets_back->address) >> 8) & 0xFF;
472 		tempPackets->address[0] =
473 			(tempPackets_back->address) & 0xFF;
474 		tempPackets->block_count[1] =
475 			((tempPackets_back->block_count) >> 8) & 0xFF;
476 		tempPackets->block_count[0] =
477 			(tempPackets_back->block_count) & 0xFF;
478 		tempPackets->op_result[1] =
479 			((tempPackets_back->result) >> 8) & 0xFF;
480 		tempPackets->op_result[0] =
481 			(tempPackets_back->result) & 0xFF;
482 		tempPackets->msg_type[1] =
483 			((tempPackets_back->request) >> 8) & 0xFF;
484 		tempPackets->msg_type[0] =
485 			(tempPackets_back->request) & 0xFF;
486 		tempPackets++;
487 		tempPackets_back++;
488 	}
489 
490 	free(RequestPackets_back);
491 
492 Exit:
493 	TeeSmc32Arg->ret = TeecResult;
494 	TeeSmc32Arg->ret_origin = TEEC_ORIGIN_API;
495 
496 	return TeecResult;
497 }
498 
499 /*
500  * Execute a normal world local file system operation.
501  */
502 TEEC_Result OpteeRpcCmdFs(t_teesmc32_arg *TeeSmc32Arg)
503 {
504 	TEEC_Result TeecResult = TEEC_SUCCESS;
505 	t_teesmc32_param *TeeSmc32Param;
506 
507 	if (check_security_exist(0) < 0) {
508 		printf("TEEC: security partition not exist! unable to use RK FS!\n");
509 		return TEEC_ERROR_GENERIC;
510 	}
511 
512 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
513 #ifdef CONFIG_OPTEE_V1
514 	TeecResult = tee_supp_rk_fs_process((void *)(size_t)TeeSmc32Param[0].u.memref.buf_ptr,
515 							TeeSmc32Param[0].u.memref.size);
516 #endif
517 #ifdef CONFIG_OPTEE_V2
518 	TeecResult = tee_supp_rk_fs_process((size_t)TeeSmc32Arg->num_params,
519 							(struct tee_ioctl_param *)TeeSmc32Param);
520 #endif
521 
522 	return TeecResult;
523 }
524 
525 /*
526  * TBD.
527  */
528 TEEC_Result OpteeRpcCmdGetTime(t_teesmc32_arg *TeeSmc32Arg)
529 {
530 	return TEEC_ERROR_NOT_IMPLEMENTED;
531 }
532 
533 /*
534  * TBD.
535  */
536 TEEC_Result OpteeRpcCmdWaitMutex(t_teesmc32_arg *TeeSmc32Arg)
537 {
538 	return TEEC_ERROR_NOT_IMPLEMENTED;
539 }
540 
541 /*
542  * Handle the callback from secure world.
543  */
544 TEEC_Result OpteeRpcCallback(ARM_SMC_ARGS *ArmSmcArgs)
545 {
546 	TEEC_Result TeecResult = TEEC_SUCCESS;
547 
548 	//printf("OpteeRpcCallback Enter: Arg0=0x%X, Arg1=0x%X, Arg2=0x%X\n",
549 		//ArmSmcArgs->Arg0, ArmSmcArgs->Arg1, ArmSmcArgs->Arg2);
550 
551 	switch (TEESMC_RETURN_GET_RPC_FUNC(ArmSmcArgs->Arg0)) {
552 	case TEESMC_RPC_FUNC_ALLOC_ARG: {
553 #ifdef CONFIG_OPTEE_V1
554 		TeecResult = OpteeRpcAlloc(ArmSmcArgs->Arg1, &ArmSmcArgs->Arg1);
555 #endif
556 #ifdef CONFIG_OPTEE_V2
557 		debug("TEEC: ArmSmcArgs->Arg1 = 0x%x \n", ArmSmcArgs->Arg1);
558 		TeecResult = OpteeRpcAlloc(ArmSmcArgs->Arg1, &ArmSmcArgs->Arg2);
559 		ArmSmcArgs->Arg5 = ArmSmcArgs->Arg2;
560 		ArmSmcArgs->Arg1 = 0;
561 		ArmSmcArgs->Arg4 = 0;
562 #endif
563 		break;
564 	}
565 
566 	case TEESMC_RPC_FUNC_ALLOC_PAYLOAD: {
567 		TeecResult = OpteeRpcAlloc(ArmSmcArgs->Arg1, &ArmSmcArgs->Arg1);
568 		break;
569 	}
570 
571 	case TEESMC_RPC_FUNC_FREE_ARG: {
572 #ifdef CONFIG_OPTEE_V1
573 		TeecResult = OpteeRpcFree(ArmSmcArgs->Arg1);
574 #endif
575 #ifdef CONFIG_OPTEE_V2
576 		TeecResult = OpteeRpcFree(ArmSmcArgs->Arg2);
577 #endif
578 		break;
579 	}
580 
581 	case TEESMC_RPC_FUNC_FREE_PAYLOAD: {
582 		TeecResult = OpteeRpcFree(ArmSmcArgs->Arg1);
583 		break;
584 	}
585 
586 	case TEESMC_RPC_FUNC_IRQ: {
587 		break;
588 	}
589 
590 	case TEESMC_RPC_FUNC_CMD: {
591 #ifdef CONFIG_OPTEE_V1
592 		t_teesmc32_arg *TeeSmc32Arg =
593 			(t_teesmc32_arg *)(size_t)ArmSmcArgs->Arg1;
594 #endif
595 #ifdef CONFIG_OPTEE_V2
596 		t_teesmc32_arg *TeeSmc32Arg =
597 			(t_teesmc32_arg *)(size_t)((uint64_t)ArmSmcArgs->Arg1 << 32 | ArmSmcArgs->Arg2);
598 		debug("TEEC: TeeSmc32Arg->cmd = 0x%x\n", TeeSmc32Arg->cmd);
599 #endif
600 		switch (TeeSmc32Arg->cmd) {
601 #ifdef CONFIG_OPTEE_V1
602 		case TEE_RPC_LOAD_TA: {
603 			TeecResult = OpteeRpcCmdLoadTa(TeeSmc32Arg);
604 			break;
605 		}
606 
607 		case TEE_RPC_FREE_TA: {
608 			TeecResult = OpteeRpcCmdFreeTa(TeeSmc32Arg);
609 			break;
610 		}
611 
612 		case TEE_RPC_RPMB_CMD: {
613 			TeecResult = OpteeRpcCmdRpmb(TeeSmc32Arg);
614 			break;
615 		}
616 
617 		case TEE_RPC_FS: {
618 			TeecResult = OpteeRpcCmdFs(TeeSmc32Arg);
619 			TeeSmc32Arg->ret = TEEC_SUCCESS;
620 			break;
621 		}
622 
623 		case TEE_RPC_GET_TIME: {
624 			TeecResult = OpteeRpcCmdGetTime(TeeSmc32Arg);
625 			break;
626 		}
627 
628 		case TEE_RPC_WAIT_MUTEX: {
629 			TeecResult = OpteeRpcCmdWaitMutex(TeeSmc32Arg);
630 			break;
631 		}
632 #endif
633 #ifdef CONFIG_OPTEE_V2
634 		case OPTEE_MSG_RPC_CMD_SHM_ALLOC_V2: {
635 			uint32_t tempaddr;
636 			uint32_t allocsize = TeeSmc32Arg->params[0].u.value.b;
637 			TeecResult = OpteeRpcAlloc(allocsize, &tempaddr);
638 			debug("TEEC: allocsize = 0x%x tempaddr = 0x%x\n", allocsize, tempaddr);
639 			TeeSmc32Arg->params[0].attr = OPTEE_MSG_ATTR_TYPE_TMEM_OUTPUT_V2;
640 			TeeSmc32Arg->params[0].u.memref.buf_ptr = tempaddr;
641 			TeeSmc32Arg->params[0].u.memref.size = allocsize;
642 			TeeSmc32Arg->params[0].u.memref.shm_ref = tempaddr;
643 			TeeSmc32Arg->ret = TEE_SUCCESS;
644 			break;
645 		}
646 		case OPTEE_MSG_RPC_CMD_SHM_FREE_V2: {
647 			uint32_t tempaddr = TeeSmc32Arg->params[0].u.value.b;
648 			TeecResult = OpteeRpcFree(tempaddr);
649 			break;
650 
651 		}
652 		case OPTEE_MSG_RPC_CMD_RPMB_V2: {
653 			TeecResult = OpteeRpcCmdRpmb(TeeSmc32Arg);
654 			break;
655 		}
656 		case OPTEE_MSG_RPC_CMD_FS_V2: {
657 			TeecResult = OpteeRpcCmdFs(TeeSmc32Arg);
658 			TeeSmc32Arg->ret = TEEC_SUCCESS;
659 			break;
660 		}
661 		case OPTEE_MSG_RPC_CMD_LOAD_TA_V2: {
662 			TeecResult = OpteeRpcCmdLoadV2Ta(TeeSmc32Arg);
663 			break;
664 		}
665 #endif
666 
667 		default: {
668 			printf("TEEC: ...unsupported RPC CMD: cmd=0x%X\n",
669 				TeeSmc32Arg->cmd);
670 			TeecResult = TEEC_ERROR_NOT_IMPLEMENTED;
671 			break;
672 		}
673 	}
674 
675 		break;
676 	}
677 
678 	case TEESMC_OPTEE_RPC_FUNC_ALLOC_PAYLOAD: {
679 		TeecResult = OpteeRpcAlloc(ArmSmcArgs->Arg1, &ArmSmcArgs->Arg1);
680 		ArmSmcArgs->Arg2 = ArmSmcArgs->Arg1;
681 		break;
682 	}
683 
684 	case TEESMC_OPTEE_RPC_FUNC_FREE_PAYLOAD: {
685 		TeecResult = OpteeRpcFree(ArmSmcArgs->Arg1);
686 		break;
687 	}
688 
689 	default: {
690 		printf("TEEC: ...unsupported RPC : Arg0=0x%X\n", ArmSmcArgs->Arg0);
691 		TeecResult = TEEC_ERROR_NOT_IMPLEMENTED;
692 		break;
693 	}
694 	}
695 
696 	ArmSmcArgs->Arg0 = TEESMC32_CALL_RETURN_FROM_RPC;
697 	debug("TEEC: OpteeRpcCallback Exit : TeecResult=0x%X\n", TeecResult);
698 
699 	return TeecResult;
700 }
701