xref: /rk3399_rockchip-uboot/lib/optee_clientApi/OpteeClientSMC.c (revision efb93541fe4c1a54c73e46cae12ebf460bae6a9e)
1abdd2437Shisping /*
2abdd2437Shisping  * Copyright 2017, Rockchip Electronics Co., Ltd
3abdd2437Shisping  * hisping lin, <hisping.lin@rock-chips.com>
4abdd2437Shisping  *
5abdd2437Shisping  * SPDX-License-Identifier:	GPL-2.0+
6abdd2437Shisping  */
7abdd2437Shisping #include <common.h>
8abdd2437Shisping #include <optee_include/OpteeClientMem.h>
9abdd2437Shisping #include <optee_include/OpteeClientSMC.h>
10abdd2437Shisping #include <optee_include/OpteeClientRPC.h>
11abdd2437Shisping #include <optee_include/teesmc.h>
121f25ada2SHisping Lin #include <optee_include/teesmc_v2.h>
131f25ada2SHisping Lin 
14abdd2437Shisping 
15abdd2437Shisping #define TEEC_SMC_DEFAULT_CACHE_ATTRIBUTES \
16abdd2437Shisping 	(TEESMC_ATTR_CACHE_DEFAULT << TEESMC_ATTR_CACHE_SHIFT);
17abdd2437Shisping 
18abdd2437Shisping static void SetTeeSmc32Params(TEEC_Operation *operation,
19abdd2437Shisping 	t_teesmc32_param *TeeSmc32Param);
20abdd2437Shisping static void GetTeeSmc32Params(t_teesmc32_param *TeeSmc32Param,
21abdd2437Shisping 	TEEC_Operation *operation);
22abdd2437Shisping static TEEC_Result OpteeSmcCall(t_teesmc32_arg *TeeSmc32Arg);
23abdd2437Shisping 
241f25ada2SHisping Lin void tee_uuid_to_octets(uint8_t *d, const TEEC_UUID *s)
251f25ada2SHisping Lin {
261f25ada2SHisping Lin 	d[0] = s->timeLow >> 24;
271f25ada2SHisping Lin 	d[1] = s->timeLow >> 16;
281f25ada2SHisping Lin 	d[2] = s->timeLow >> 8;
291f25ada2SHisping Lin 	d[3] = s->timeLow;
301f25ada2SHisping Lin 	d[4] = s->timeMid >> 8;
311f25ada2SHisping Lin 	d[5] = s->timeMid;
321f25ada2SHisping Lin 	d[6] = s->timeHiAndVersion >> 8;
331f25ada2SHisping Lin 	d[7] = s->timeHiAndVersion;
341f25ada2SHisping Lin 	memcpy(d + 8, s->clockSeqAndNode, sizeof(s->clockSeqAndNode));
351f25ada2SHisping Lin }
361f25ada2SHisping Lin 
37abdd2437Shisping /*
38abdd2437Shisping  * This function opens a new Session between the Client application and the
39abdd2437Shisping  * specified TEE application.
40abdd2437Shisping  *
41abdd2437Shisping  * Only connection_method == TEEC_LOGIN_PUBLIC is supported connection_data and
42abdd2437Shisping  * operation shall be set to NULL.
43abdd2437Shisping  */
44abdd2437Shisping TEEC_Result TEEC_SMC_OpenSession(TEEC_Context *context,
45abdd2437Shisping 				TEEC_Session *session,
46abdd2437Shisping 				const TEEC_UUID *destination,
47abdd2437Shisping 				TEEC_Operation  *operation,
48abdd2437Shisping 				uint32_t *error_origin)
49abdd2437Shisping {
50abdd2437Shisping 	TEEC_Result TeecResult = TEEC_SUCCESS;
51abdd2437Shisping 	uint32_t TeeSmc32ArgLength;
52abdd2437Shisping 	uint32_t TeeSmcMetaSessionLength;
53abdd2437Shisping 
54abdd2437Shisping 	t_teesmc32_arg *TeeSmc32Arg = NULL;
55abdd2437Shisping 	t_teesmc32_param *TeeSmc32Param = NULL;
561f25ada2SHisping Lin 
57abdd2437Shisping 	t_teesmc_meta_open_session *TeeSmcMetaSession = NULL;
581f25ada2SHisping Lin 
591f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V1
601f25ada2SHisping Lin 	uint32_t MetaNum = 1;
611f25ada2SHisping Lin #endif
621f25ada2SHisping Lin 
631f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V2
641f25ada2SHisping Lin 	uint32_t MetaNum = 2;
651f25ada2SHisping Lin #endif
66abdd2437Shisping 
67abdd2437Shisping 	*error_origin = TEEC_ORIGIN_API;
68abdd2437Shisping 
69abdd2437Shisping 	TeeSmc32ArgLength =
70abdd2437Shisping 		TEESMC32_GET_ARG_SIZE(TEEC_CONFIG_PAYLOAD_REF_COUNT + MetaNum);
71abdd2437Shisping 
72abdd2437Shisping 	TeeSmc32Arg = (t_teesmc32_arg *)OpteeClientMemAlloc(TeeSmc32ArgLength);
73abdd2437Shisping 
74abdd2437Shisping 	if (TeeSmc32Arg == NULL) {
75abdd2437Shisping 		TeecResult = TEEC_ERROR_OUT_OF_MEMORY;
76abdd2437Shisping 		goto Exit;
77abdd2437Shisping 	}
78abdd2437Shisping 
79abdd2437Shisping 	memset(TeeSmc32Arg, 0, TeeSmc32ArgLength);
80abdd2437Shisping 
81abdd2437Shisping 	TeeSmcMetaSessionLength = sizeof(*TeeSmcMetaSession);
82abdd2437Shisping 
83abdd2437Shisping 	TeeSmcMetaSession = (t_teesmc_meta_open_session *)
84abdd2437Shisping 		OpteeClientMemAlloc(TeeSmcMetaSessionLength);
85abdd2437Shisping 
86abdd2437Shisping 	if (TeeSmcMetaSession == NULL) {
87abdd2437Shisping 		TeecResult = TEEC_ERROR_OUT_OF_MEMORY;
88abdd2437Shisping 		goto Exit;
89abdd2437Shisping 	}
90abdd2437Shisping 
91abdd2437Shisping 	memset(TeeSmcMetaSession, 0, TeeSmcMetaSessionLength);
92abdd2437Shisping 
93abdd2437Shisping 	TeeSmc32Arg->cmd = TEESMC_CMD_OPEN_SESSION;
94abdd2437Shisping 	TeeSmc32Arg->num_params = TEEC_CONFIG_PAYLOAD_REF_COUNT + MetaNum;
95abdd2437Shisping 
96abdd2437Shisping 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
97abdd2437Shisping 
98abdd2437Shisping 	memcpy(&TeeSmcMetaSession->uuid,
99abdd2437Shisping 		destination,
100abdd2437Shisping 		sizeof(TeeSmcMetaSession->uuid));
101abdd2437Shisping 	TeeSmcMetaSession->clnt_login = TEEC_LOGIN_PUBLIC;
102abdd2437Shisping 
1031f25ada2SHisping Lin 	TeeSmc32Param[0].u.memref.buf_ptr = (uint32_t) (size_t)TeeSmcMetaSession;
104abdd2437Shisping 	TeeSmc32Param[0].u.memref.size = sizeof(*TeeSmcMetaSession);
105abdd2437Shisping 
1061f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V1
1071f25ada2SHisping Lin #ifdef CONFIG_ARM64
108abdd2437Shisping 	TeeSmc32Param[0].attr = TEESMC_ATTR_TYPE_MEMREF_INPUT |
109abdd2437Shisping 				TEESMC_ATTR_META              |
110abdd2437Shisping 				TEEC_SMC_DEFAULT_CACHE_ATTRIBUTES;
1111f25ada2SHisping Lin #else
112abdd2437Shisping 	TeeSmc32Param[0].attr = TEESMC_ATTR_TYPE_MEMREF_INPUT |
113abdd2437Shisping 				TEESMC_ATTR_META;
114abdd2437Shisping #endif
1151f25ada2SHisping Lin #endif
1161f25ada2SHisping Lin 
1171f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V2
118d156c9ffSHisping Lin #if defined CONFIG_ARM64 || defined CONFIG_ARM64_BOOT_AARCH32
1191f25ada2SHisping Lin 	uint8_t * session_uuid = (uint8_t *)&TeeSmcMetaSession->uuid;
1201f25ada2SHisping Lin 	tee_uuid_to_octets(session_uuid, destination);
1211f25ada2SHisping Lin 	memcpy((void *)&TeeSmc32Param[0].u.value, &TeeSmcMetaSession->uuid, sizeof(TeeSmcMetaSession->uuid));
1221f25ada2SHisping Lin 	TeeSmc32Param[1].u.value.c = TeeSmcMetaSession->clnt_login;
1231f25ada2SHisping Lin 
1241f25ada2SHisping Lin 	TeeSmc32Param[0].attr = OPTEE_MSG_ATTR_TYPE_VALUE_INPUT_V2 |
1251f25ada2SHisping Lin 				OPTEE_MSG_ATTR_META_V2;
1261f25ada2SHisping Lin 	TeeSmc32Param[1].attr = OPTEE_MSG_ATTR_TYPE_VALUE_INPUT_V2 |
1271f25ada2SHisping Lin 				OPTEE_MSG_ATTR_META_V2;
1281f25ada2SHisping Lin #else
129*efb93541SHisping Lin 	printf("TEEC: Not support! All rockchips use optee v2.5 are 64 bits! \n");
1301f25ada2SHisping Lin #endif
1311f25ada2SHisping Lin #endif
132abdd2437Shisping 
133abdd2437Shisping 	SetTeeSmc32Params(operation, TeeSmc32Param + MetaNum);
134abdd2437Shisping 
135abdd2437Shisping 	*error_origin = TEEC_ORIGIN_COMMS;
136abdd2437Shisping 
137abdd2437Shisping 	TeecResult = OpteeSmcCall(TeeSmc32Arg);
138abdd2437Shisping 	if (TeecResult != TEEC_SUCCESS)
139abdd2437Shisping 		goto Exit;
140abdd2437Shisping 
141abdd2437Shisping 	session->id = TeeSmc32Arg->session;
142abdd2437Shisping 	TeecResult = TeeSmc32Arg->ret;
143abdd2437Shisping 	*error_origin = TeeSmc32Arg->ret_origin;
144abdd2437Shisping 
145abdd2437Shisping 	GetTeeSmc32Params(TeeSmc32Param + MetaNum, operation);
146abdd2437Shisping 
147abdd2437Shisping Exit:
148abdd2437Shisping 	if (TeeSmc32Arg != NULL)
149abdd2437Shisping 		OpteeClientMemFree(TeeSmc32Arg);
150abdd2437Shisping 
151abdd2437Shisping 	if (TeeSmcMetaSession != NULL)
152abdd2437Shisping 		OpteeClientMemFree(TeeSmcMetaSession);
153abdd2437Shisping 
154abdd2437Shisping 	return TeecResult;
155abdd2437Shisping }
156abdd2437Shisping 
157abdd2437Shisping /*
158abdd2437Shisping  * This function closes a session which has been opened with a TEE
159abdd2437Shisping  * application.
160abdd2437Shisping  *
161abdd2437Shisping  * Note that the GP specification does not allow for this API to fail and return
162abdd2437Shisping  * a failure code however we'll support this at the SMC level so we can get
163abdd2437Shisping  * see debug information about such failures.
164abdd2437Shisping  */
165abdd2437Shisping TEEC_Result TEEC_SMC_CloseSession(TEEC_Session *session,
166abdd2437Shisping 				uint32_t *error_origin)
167abdd2437Shisping {
168abdd2437Shisping 	TEEC_Result TeecResult = TEEC_SUCCESS;
169abdd2437Shisping 	uint32_t TeeSmc32ArgLength;
1701f25ada2SHisping Lin 
171abdd2437Shisping 	t_teesmc32_arg *TeeSmc32Arg = NULL;
172abdd2437Shisping 
173abdd2437Shisping 	*error_origin = TEEC_ORIGIN_API;
174abdd2437Shisping 
175abdd2437Shisping 	TeeSmc32ArgLength =
176abdd2437Shisping 		TEESMC32_GET_ARG_SIZE(TEEC_CONFIG_PAYLOAD_REF_COUNT);
177abdd2437Shisping 
178abdd2437Shisping 	TeeSmc32Arg = (t_teesmc32_arg *)OpteeClientMemAlloc(TeeSmc32ArgLength);
179abdd2437Shisping 
180abdd2437Shisping 	if (TeeSmc32Arg == NULL) {
181abdd2437Shisping 		TeecResult = TEEC_ERROR_OUT_OF_MEMORY;
182abdd2437Shisping 		goto Exit;
183abdd2437Shisping 	}
184abdd2437Shisping 
185abdd2437Shisping 	memset(TeeSmc32Arg, 0, TeeSmc32ArgLength);
186abdd2437Shisping 
187abdd2437Shisping 	TeeSmc32Arg->cmd = TEESMC_CMD_CLOSE_SESSION;
188abdd2437Shisping 	TeeSmc32Arg->session = session->id;
189abdd2437Shisping 
190abdd2437Shisping 	*error_origin = TEEC_ORIGIN_COMMS;
191abdd2437Shisping 
192abdd2437Shisping 	TeecResult = OpteeSmcCall(TeeSmc32Arg);
193abdd2437Shisping 
194abdd2437Shisping 	if (TeecResult != TEEC_SUCCESS)
195abdd2437Shisping 		goto Exit;
196abdd2437Shisping 
197abdd2437Shisping 	TeecResult = TeeSmc32Arg->ret;
198abdd2437Shisping 	*error_origin = TeeSmc32Arg->ret_origin;
199abdd2437Shisping 
200abdd2437Shisping Exit:
201abdd2437Shisping 	if (TeeSmc32Arg != NULL)
202abdd2437Shisping 		OpteeClientMemFree(TeeSmc32Arg);
203abdd2437Shisping 
204abdd2437Shisping 	return TeecResult;
205abdd2437Shisping }
206abdd2437Shisping 
207abdd2437Shisping /*
208abdd2437Shisping  * Invokes a TEE command (secure service, sub-PA or whatever).
209abdd2437Shisping  */
210abdd2437Shisping TEEC_Result TEEC_SMC_InvokeCommand(TEEC_Session *session,
211abdd2437Shisping 				uint32_t cmd_id,
212abdd2437Shisping 				TEEC_Operation *operation,
213abdd2437Shisping 				uint32_t *error_origin)
214abdd2437Shisping {
215abdd2437Shisping 	TEEC_Result TeecResult = TEEC_SUCCESS;
216abdd2437Shisping 	uint32_t TeeSmc32ArgLength;
2171f25ada2SHisping Lin 
218abdd2437Shisping 	t_teesmc32_arg *TeeSmc32Arg = NULL;
219abdd2437Shisping 	t_teesmc32_param *TeeSmc32Param = NULL;
220abdd2437Shisping 
221abdd2437Shisping 	*error_origin = TEEC_ORIGIN_API;
222abdd2437Shisping 
223abdd2437Shisping 	TeeSmc32ArgLength =
224abdd2437Shisping 		TEESMC32_GET_ARG_SIZE(TEEC_CONFIG_PAYLOAD_REF_COUNT);
225abdd2437Shisping 
226abdd2437Shisping 	TeeSmc32Arg = (t_teesmc32_arg *)OpteeClientMemAlloc(TeeSmc32ArgLength);
227abdd2437Shisping 
228abdd2437Shisping 	if (TeeSmc32Arg == NULL) {
229abdd2437Shisping 		TeecResult = TEEC_ERROR_OUT_OF_MEMORY;
230abdd2437Shisping 		goto Exit;
231abdd2437Shisping 	}
232abdd2437Shisping 
233abdd2437Shisping 	memset(TeeSmc32Arg, 0, TeeSmc32ArgLength);
234abdd2437Shisping 
235abdd2437Shisping 	TeeSmc32Arg->cmd = TEESMC_CMD_INVOKE_COMMAND;
236abdd2437Shisping 	TeeSmc32Arg->ta_func = cmd_id;
237abdd2437Shisping 	TeeSmc32Arg->session = session->id;
238abdd2437Shisping 	TeeSmc32Arg->num_params = TEEC_CONFIG_PAYLOAD_REF_COUNT;
239abdd2437Shisping 
240abdd2437Shisping 	TeeSmc32Param = TEESMC32_GET_PARAMS(TeeSmc32Arg);
241abdd2437Shisping 
242abdd2437Shisping 	SetTeeSmc32Params(operation, TeeSmc32Param);
243abdd2437Shisping 
244abdd2437Shisping 	*error_origin = TEEC_ORIGIN_COMMS;
245abdd2437Shisping 
246abdd2437Shisping 	TeecResult = OpteeSmcCall(TeeSmc32Arg);
247abdd2437Shisping 	if (TeecResult != TEEC_SUCCESS)
248abdd2437Shisping 		goto Exit;
249abdd2437Shisping 
250abdd2437Shisping 	TeecResult = TeeSmc32Arg->ret;
251abdd2437Shisping 	*error_origin = TeeSmc32Arg->ret_origin;
252abdd2437Shisping 
253abdd2437Shisping 	GetTeeSmc32Params(TeeSmc32Param, operation);
254abdd2437Shisping 
255abdd2437Shisping Exit:
256abdd2437Shisping 	if (TeeSmc32Arg != NULL)
257abdd2437Shisping 		OpteeClientMemFree(TeeSmc32Arg);
258abdd2437Shisping 
259abdd2437Shisping 
260abdd2437Shisping 	return TeecResult;
261abdd2437Shisping }
262abdd2437Shisping 
263abdd2437Shisping /*
264abdd2437Shisping  * Request a cancellation of a in-progress operation (best effort)
265abdd2437Shisping  *
266abdd2437Shisping  * Note that the GP specification does not allow for this API to fail and return
267abdd2437Shisping  * a failure code however we'll support this at the SMC level so we can get
268abdd2437Shisping  * see debug information about such failures.
269abdd2437Shisping  */
270abdd2437Shisping TEEC_Result TEEC_SMC_RequestCancellation(TEEC_Operation *operation,
271abdd2437Shisping 					uint32_t *error_origin)
272abdd2437Shisping {
273abdd2437Shisping 	return TEEC_ERROR_NOT_IMPLEMENTED;
274abdd2437Shisping }
275abdd2437Shisping 
276abdd2437Shisping /*
277abdd2437Shisping  * Set the call parameter blocks in the
278abdd2437Shisping  * SMC call based on the TEEC parameter supplied.
279abdd2437Shisping  * This only handles the parameters supplied in
280abdd2437Shisping  * the originating call and not those
281abdd2437Shisping  * considered internal meta parameters and is
282abdd2437Shisping  * thus constrained by the build
283abdd2437Shisping  * constants exposed to callers.
284abdd2437Shisping  */
285abdd2437Shisping void SetTeeSmc32Params(TEEC_Operation *operation,
286abdd2437Shisping 						t_teesmc32_param *TeeSmc32Param)
287abdd2437Shisping {
288abdd2437Shisping 	uint32_t ParamCount;
289abdd2437Shisping 
290abdd2437Shisping 	for (ParamCount = 0;
291abdd2437Shisping 		ParamCount < TEEC_CONFIG_PAYLOAD_REF_COUNT;
292abdd2437Shisping 		ParamCount++) {
293abdd2437Shisping 		uint32_t attr =
294abdd2437Shisping 			TEEC_PARAM_TYPE_GET(operation->paramTypes, ParamCount);
295abdd2437Shisping 
296abdd2437Shisping 		if (attr == TEEC_MEMREF_TEMP_INPUT ||
297abdd2437Shisping 			attr == TEEC_MEMREF_TEMP_OUTPUT ||
298abdd2437Shisping 			attr == TEEC_MEMREF_TEMP_INOUT) {
2991f25ada2SHisping Lin 
3001f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V1
3011f25ada2SHisping Lin #ifdef CONFIG_ARM64
302abdd2437Shisping 			attr |= TEEC_SMC_DEFAULT_CACHE_ATTRIBUTES;
303*efb93541SHisping Lin 			debug("TEEC: OPTEE_OS_V1 ARCH64 attr %x\n", attr);
3041f25ada2SHisping Lin #else
305*efb93541SHisping Lin 			debug("TEEC: OPTEE_OS_V1 ARCH32 attr %x\n", attr);
306abdd2437Shisping #endif
307abdd2437Shisping #endif
3081f25ada2SHisping Lin 
3091f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V2
310d156c9ffSHisping Lin #if defined CONFIG_ARM64 || defined CONFIG_ARM64_BOOT_AARCH32
3111f25ada2SHisping Lin 			attr += (OPTEE_MSG_ATTR_TYPE_TMEM_INPUT_V2 - TEEC_MEMREF_TEMP_INPUT);
312*efb93541SHisping Lin 			debug("TEEC: OPTEE_OS_V2 ARCH64 attr %x\n", attr);
3131f25ada2SHisping Lin #else
314*efb93541SHisping Lin 			printf("TEEC: Not support! All rockchips use optee v2 are 64 bits! \n");
3151f25ada2SHisping Lin #endif
3161f25ada2SHisping Lin #endif
3171f25ada2SHisping Lin 
318abdd2437Shisping 			TeeSmc32Param[ParamCount].attr = attr;
319abdd2437Shisping 			TeeSmc32Param[ParamCount].u.memref.buf_ptr =
3201f25ada2SHisping Lin 			(uint32_t)(size_t)operation->params[ParamCount].tmpref.buffer;
321abdd2437Shisping 			TeeSmc32Param[ParamCount].u.memref.size =
322abdd2437Shisping 				operation->params[ParamCount].tmpref.size;
323abdd2437Shisping 		} else {
324abdd2437Shisping 			TeeSmc32Param[ParamCount].attr = attr;
325abdd2437Shisping 			TeeSmc32Param[ParamCount].u.value.a =
326abdd2437Shisping 				operation->params[ParamCount].value.a;
327abdd2437Shisping 			TeeSmc32Param[ParamCount].u.value.b =
328abdd2437Shisping 				operation->params[ParamCount].value.b;
329abdd2437Shisping 		}
330abdd2437Shisping 	}
331abdd2437Shisping }
332abdd2437Shisping 
333abdd2437Shisping /*
334abdd2437Shisping  * Get the return parameter blocks from
335abdd2437Shisping  * the SMC call into the TEEC parameter supplied.
336abdd2437Shisping  * This only handles the parameters supplied
337abdd2437Shisping  * in the originating call and not those
338abdd2437Shisping  * considered internal meta parameters and
339abdd2437Shisping  * is thus constrained by the build
340abdd2437Shisping  * constants exposed to callers.
341abdd2437Shisping  */
342abdd2437Shisping void GetTeeSmc32Params(t_teesmc32_param *TeeSmc32Param,
343abdd2437Shisping 				TEEC_Operation *operation)
344abdd2437Shisping {
345abdd2437Shisping 	uint32_t ParamCount;
346abdd2437Shisping 
347abdd2437Shisping 	for (ParamCount = 0;
348abdd2437Shisping 	ParamCount < TEEC_CONFIG_PAYLOAD_REF_COUNT;
349abdd2437Shisping 	ParamCount++) {
350abdd2437Shisping 		operation->params[ParamCount].value.a =
351abdd2437Shisping 			TeeSmc32Param[ParamCount].u.value.a;
352abdd2437Shisping 		operation->params[ParamCount].value.b =
353abdd2437Shisping 			TeeSmc32Param[ParamCount].u.value.b;
354abdd2437Shisping 	}
355abdd2437Shisping }
356abdd2437Shisping 
357abdd2437Shisping /*
358abdd2437Shisping  * Populate the SMC registers and make
359abdd2437Shisping  * the call with OpTEE specific handling.
360abdd2437Shisping  */
361abdd2437Shisping TEEC_Result OpteeSmcCall(t_teesmc32_arg *TeeSmc32Arg)
362abdd2437Shisping {
363abdd2437Shisping 	TEEC_Result TeecResult = TEEC_SUCCESS;
364abdd2437Shisping 	ARM_SMC_ARGS ArmSmcArgs = {0};
365abdd2437Shisping 
3661f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V1
367abdd2437Shisping 	ArmSmcArgs.Arg0 = TEESMC32_CALL_WITH_ARG;
3681f25ada2SHisping Lin 	ArmSmcArgs.Arg1 = (uint32_t) (size_t)TeeSmc32Arg;
3691f25ada2SHisping Lin #endif
3701f25ada2SHisping Lin 
3711f25ada2SHisping Lin #ifdef CONFIG_OPTEE_V2
3721f25ada2SHisping Lin 	ArmSmcArgs.Arg0 = OPTEE_SMC_CALL_WITH_ARG_V2;
3731f25ada2SHisping Lin 	ArmSmcArgs.Arg1 = 0;
3741f25ada2SHisping Lin 	ArmSmcArgs.Arg2 = (uint32_t) (size_t)TeeSmc32Arg;
3751f25ada2SHisping Lin #endif
376abdd2437Shisping 
377abdd2437Shisping 	while (1) {
378abdd2437Shisping 		tee_smc_call(&ArmSmcArgs);
379*efb93541SHisping Lin 		debug("TEEC: arg0=0x%x arg1=0x%x arg2=0x%x arg3=0x%x \n",
3801f25ada2SHisping Lin 			ArmSmcArgs.Arg0, ArmSmcArgs.Arg1, ArmSmcArgs.Arg2, ArmSmcArgs.Arg3);
381abdd2437Shisping 		if (TEESMC_RETURN_IS_RPC(ArmSmcArgs.Arg0)) {
382abdd2437Shisping 			(void) OpteeRpcCallback(&ArmSmcArgs);
383abdd2437Shisping 		} else if (ArmSmcArgs.Arg0 == TEESMC_RETURN_UNKNOWN_FUNCTION) {
384abdd2437Shisping 			TeecResult = TEEC_ERROR_NOT_IMPLEMENTED;
385abdd2437Shisping 			break;
386abdd2437Shisping 		} else if (ArmSmcArgs.Arg0 != TEESMC_RETURN_OK) {
387abdd2437Shisping 			TeecResult = TEEC_ERROR_COMMUNICATION;
388abdd2437Shisping 			break;
389abdd2437Shisping 		} else {
390abdd2437Shisping 			TeecResult = TEEC_SUCCESS;
391abdd2437Shisping 			break;
392abdd2437Shisping 		}
393abdd2437Shisping 	}
394abdd2437Shisping 
395abdd2437Shisping 	return TeecResult;
396abdd2437Shisping }
397abdd2437Shisping 
398