mirror of
https://github.com/apache/nuttx.git
synced 2026-05-23 06:39:01 +08:00
drivers/misc/optee: Cache coherency when MMU is disabled
Build Documentation / build-html (push) Has been cancelled
Build Documentation / build-html (push) Has been cancelled
When the MMU is disabled (CONFIG_ARCH_USE_MMU=n) the data passed back and forth with the TEE needs to be synced from/to the cache, otherwise we get random data in either world. Fix this by cleaning before a call and invalidating after. This has to be done both on the optee msg arg, and the shm buffers therein. Cleaning and invalidating the page list used to describe non-contiguous shm buffers did not seem mandatory in my tests, but common sense says that it should be, so we do that too. This fix does not apply to the optee msg arg of the socket transport (optee_socket.c), as that one _should_ be handled by the socket send/recv methods. It does apply to all shm buffers though, regardless of transport. Signed-off-by: George Poulios <gpoulios@census-labs.com>
This commit is contained in:
committed by
Xiang Xiao
parent
4a765b557f
commit
589c0e13b8
+18
-1
@@ -27,6 +27,7 @@
|
||||
#include <fcntl.h>
|
||||
#include <nuttx/tee.h>
|
||||
#include <nuttx/nuttx.h>
|
||||
#include <nuttx/cache.h>
|
||||
#include <nuttx/drivers/optee.h>
|
||||
#include <nuttx/fs/fs.h>
|
||||
#include <nuttx/kmalloc.h>
|
||||
@@ -345,6 +346,10 @@ optee_shm_to_page_list(FAR struct optee_shm *shm, FAR uintptr_t *list_pa)
|
||||
*list_pa = optee_va_to_pa(list) | pgoff;
|
||||
}
|
||||
|
||||
#ifndef CONFIG_ARCH_USE_MMU
|
||||
up_clean_dcache((uintptr_t)list, (uintptr_t)list + list_size);
|
||||
#endif
|
||||
|
||||
return list;
|
||||
}
|
||||
|
||||
@@ -609,6 +614,10 @@ static int optee_memref_to_msg_param(FAR struct optee_priv_data *priv,
|
||||
mp->u.tmem.size = shm->length;
|
||||
}
|
||||
|
||||
#ifndef CONFIG_ARCH_USE_MMU
|
||||
up_clean_dcache(shm->addr, shm->addr + shm->length);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -671,7 +680,7 @@ static int optee_from_msg_param(FAR struct tee_ioctl_param *params,
|
||||
{
|
||||
FAR const struct optee_msg_param *mp = mparams + n;
|
||||
FAR struct tee_ioctl_param *p = params + n;
|
||||
FAR struct optee_shm *shm;
|
||||
FAR struct optee_shm *shm = NULL;
|
||||
|
||||
switch (mp->attr & OPTEE_MSG_ATTR_TYPE_MASK)
|
||||
{
|
||||
@@ -710,10 +719,18 @@ static int optee_from_msg_param(FAR struct tee_ioctl_param *params,
|
||||
p->attr = TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT +
|
||||
mp->attr - OPTEE_MSG_ATTR_TYPE_RMEM_INPUT;
|
||||
p->b = mp->u.rmem.size;
|
||||
shm = (FAR struct optee_shm *)(uintptr_t)mp->u.tmem.shm_ref;
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
#ifndef CONFIG_ARCH_USE_MMU
|
||||
if (shm)
|
||||
{
|
||||
up_invalidate_dcache(shm->addr, shm->addr + shm->length);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
@@ -24,6 +24,7 @@
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/cache.h>
|
||||
#include <nuttx/kmalloc.h>
|
||||
#include <errno.h>
|
||||
#include <syslog.h>
|
||||
@@ -314,11 +315,17 @@ int optee_transport_call(FAR struct optee_priv_data *priv_,
|
||||
smccc_res_t res;
|
||||
smccc_res_t par;
|
||||
uintptr_t arg_pa;
|
||||
#ifndef CONFIG_ARCH_USE_MMU
|
||||
size_t arg_size = OPTEE_MSG_GET_ARG_SIZE(arg->num_params);
|
||||
|
||||
up_clean_dcache((uintptr_t)arg, (uintptr_t)arg + arg_size);
|
||||
#endif
|
||||
|
||||
memset(&par, 0, sizeof(smccc_res_t));
|
||||
|
||||
par.a0 = OPTEE_SMC_CALL_WITH_ARG;
|
||||
arg_pa = optee_va_to_pa(arg);
|
||||
|
||||
reg_pair_from_64(arg_pa, &par.a1, &par.a2);
|
||||
|
||||
for (; ; )
|
||||
@@ -335,6 +342,9 @@ int optee_transport_call(FAR struct optee_priv_data *priv_,
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifndef CONFIG_ARCH_USE_MMU
|
||||
up_invalidate_dcache((uintptr_t)arg, (uintptr_t)arg + arg_size);
|
||||
#endif
|
||||
return (int)res.a0;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user