This pull request updates the previous tee-drv-dynamic-shm-for-v4.16 pull
request with five new patches fixing review comments and errors. Apart from three small fixes there's two larger patches that in the end checks that memory to be registered really is normal cached memory. -----BEGIN PGP SIGNATURE----- iQI3BAABCgAhBQJaVzZeGhxqZW5zLndpa2xhbmRlckBsaW5hcm8ub3JnAAoJELWw uEGXj+zTbVMQAOK22g34O1EouTBpFvw/Ch4aZ7AFr+NoXxyphhIeg/4RpWwCpiCY +xDBv4aHk6Opv0uhWGJJHMzRgE6eNYjLVVd8tGpDtRdqQWJP0MYVH2sHu5bnfJZS LfDUk+t2ULxgzVvIBvyccslTSAGqc5K0mnzW3DXrwkKtRmpfl27tg/OFph08lHni dhAOeW4m6PGWcWlQklDlpykTt8KUHMaIx5eNx+IBCYDcfQkev3Te49EwDK05ObjU MC6M1rZJmzb28UumkUC1B8nyS/PqxB8xrkyqYqehic6eBH9WIAn+paaLgSjocvqc gXwScaTNyniUPBMR73sNyARzpYgI0CvcqJ9R0uIGlSmwj9LQqrc0vtiJAR0YDeir FzweH8uhkU2qhZjH3WSoLGS4CSm2scIhEE3jbHpRjDdqvajoQBbOxPKusQnIjs/p iDZwYKuvH2f7TQtdwigT36k7KP0688LRSUrp7CeY7sIlzj0M3CLEzU/5OORBgqIl 5KyOt6R8aVbQtABDBnzqIn1BYqA05KWzZFqwlDPckCNfBjgHd45rz4HGvwqCf9JI dKZ3VZDtBOeQIpBRj02mbEn0mUhDyztd7we+WkzTz0AxmEAw8r8yn1035WhZILGw ntXMk4PX9uVwQxReE0n1Gyv5UxCP1u+RMGE7G3hQoDBGNdhGxHw9bDqV =0+NS -----END PGP SIGNATURE----- Merge tag 'tee-drv-dynamic-shm+fixes-for-v4.16' of https://git.linaro.org/people/jens.wiklander/linux-tee into next/drivers This pull request updates the previous tee-drv-dynamic-shm-for-v4.16 pull request with five new patches fixing review comments and errors. Apart from three small fixes there's two larger patches that in the end checks that memory to be registered really is normal cached memory. * tag 'tee-drv-dynamic-shm+fixes-for-v4.16' of https://git.linaro.org/people/jens.wiklander/linux-tee: tee: shm: Potential NULL dereference calling tee_shm_register() tee: shm: don't put_page on null shm->pages tee: shm: make function __tee_shm_alloc static tee: optee: check type of registered shared memory tee: add start argument to shm_register callback Signed-off-by: Olof Johansson <olof@lixom.net>
This commit is contained in:
commit
ffdc98c4f2
|
@ -535,18 +535,58 @@ void optee_free_pages_list(void *list, size_t num_entries)
|
|||
free_pages_exact(list, get_pages_list_size(num_entries));
|
||||
}
|
||||
|
||||
static bool is_normal_memory(pgprot_t p)
|
||||
{
|
||||
#if defined(CONFIG_ARM)
|
||||
return (pgprot_val(p) & L_PTE_MT_MASK) == L_PTE_MT_WRITEALLOC;
|
||||
#elif defined(CONFIG_ARM64)
|
||||
return (pgprot_val(p) & PTE_ATTRINDX_MASK) == PTE_ATTRINDX(MT_NORMAL);
|
||||
#else
|
||||
#error "Unuspported architecture"
|
||||
#endif
|
||||
}
|
||||
|
||||
static int __check_mem_type(struct vm_area_struct *vma, unsigned long end)
|
||||
{
|
||||
while (vma && is_normal_memory(vma->vm_page_prot)) {
|
||||
if (vma->vm_end >= end)
|
||||
return 0;
|
||||
vma = vma->vm_next;
|
||||
}
|
||||
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
static int check_mem_type(unsigned long start, size_t num_pages)
|
||||
{
|
||||
struct mm_struct *mm = current->mm;
|
||||
int rc;
|
||||
|
||||
down_read(&mm->mmap_sem);
|
||||
rc = __check_mem_type(find_vma(mm, start),
|
||||
start + num_pages * PAGE_SIZE);
|
||||
up_read(&mm->mmap_sem);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
int optee_shm_register(struct tee_context *ctx, struct tee_shm *shm,
|
||||
struct page **pages, size_t num_pages)
|
||||
struct page **pages, size_t num_pages,
|
||||
unsigned long start)
|
||||
{
|
||||
struct tee_shm *shm_arg = NULL;
|
||||
struct optee_msg_arg *msg_arg;
|
||||
u64 *pages_list;
|
||||
phys_addr_t msg_parg;
|
||||
int rc = 0;
|
||||
int rc;
|
||||
|
||||
if (!num_pages)
|
||||
return -EINVAL;
|
||||
|
||||
rc = check_mem_type(start, num_pages);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
pages_list = optee_allocate_pages_list(num_pages);
|
||||
if (!pages_list)
|
||||
return -ENOMEM;
|
||||
|
@ -606,13 +646,14 @@ int optee_shm_unregister(struct tee_context *ctx, struct tee_shm *shm)
|
|||
}
|
||||
|
||||
int optee_shm_register_supp(struct tee_context *ctx, struct tee_shm *shm,
|
||||
struct page **pages, size_t num_pages)
|
||||
struct page **pages, size_t num_pages,
|
||||
unsigned long start)
|
||||
{
|
||||
/*
|
||||
* We don't want to register supplicant memory in OP-TEE.
|
||||
* Instead information about it will be passed in RPC code.
|
||||
*/
|
||||
return 0;
|
||||
return check_mem_type(start, num_pages);
|
||||
}
|
||||
|
||||
int optee_shm_unregister_supp(struct tee_context *ctx, struct tee_shm *shm)
|
||||
|
|
|
@ -162,11 +162,13 @@ void optee_enable_shm_cache(struct optee *optee);
|
|||
void optee_disable_shm_cache(struct optee *optee);
|
||||
|
||||
int optee_shm_register(struct tee_context *ctx, struct tee_shm *shm,
|
||||
struct page **pages, size_t num_pages);
|
||||
struct page **pages, size_t num_pages,
|
||||
unsigned long start);
|
||||
int optee_shm_unregister(struct tee_context *ctx, struct tee_shm *shm);
|
||||
|
||||
int optee_shm_register_supp(struct tee_context *ctx, struct tee_shm *shm,
|
||||
struct page **pages, size_t num_pages);
|
||||
struct page **pages, size_t num_pages,
|
||||
unsigned long start);
|
||||
int optee_shm_unregister_supp(struct tee_context *ctx, struct tee_shm *shm);
|
||||
|
||||
int optee_from_msg_param(struct tee_param *params, size_t num_params,
|
||||
|
|
|
@ -112,9 +112,9 @@ static const struct dma_buf_ops tee_shm_dma_buf_ops = {
|
|||
.mmap = tee_shm_op_mmap,
|
||||
};
|
||||
|
||||
struct tee_shm *__tee_shm_alloc(struct tee_context *ctx,
|
||||
struct tee_device *teedev,
|
||||
size_t size, u32 flags)
|
||||
static struct tee_shm *__tee_shm_alloc(struct tee_context *ctx,
|
||||
struct tee_device *teedev,
|
||||
size_t size, u32 flags)
|
||||
{
|
||||
struct tee_shm_pool_mgr *poolm = NULL;
|
||||
struct tee_shm *shm;
|
||||
|
@ -283,7 +283,7 @@ struct tee_shm *tee_shm_register(struct tee_context *ctx, unsigned long addr,
|
|||
if (rc > 0)
|
||||
shm->num_pages = rc;
|
||||
if (rc != num_pages) {
|
||||
if (rc > 0)
|
||||
if (rc >= 0)
|
||||
rc = -ENOMEM;
|
||||
ret = ERR_PTR(rc);
|
||||
goto err;
|
||||
|
@ -299,7 +299,7 @@ struct tee_shm *tee_shm_register(struct tee_context *ctx, unsigned long addr,
|
|||
}
|
||||
|
||||
rc = teedev->desc->ops->shm_register(ctx, shm, shm->pages,
|
||||
shm->num_pages);
|
||||
shm->num_pages, start);
|
||||
if (rc) {
|
||||
ret = ERR_PTR(rc);
|
||||
goto err;
|
||||
|
@ -335,9 +335,11 @@ err:
|
|||
idr_remove(&teedev->idr, shm->id);
|
||||
mutex_unlock(&teedev->mutex);
|
||||
}
|
||||
for (n = 0; n < shm->num_pages; n++)
|
||||
put_page(shm->pages[n]);
|
||||
kfree(shm->pages);
|
||||
if (shm->pages) {
|
||||
for (n = 0; n < shm->num_pages; n++)
|
||||
put_page(shm->pages[n]);
|
||||
kfree(shm->pages);
|
||||
}
|
||||
}
|
||||
kfree(shm);
|
||||
teedev_ctx_put(ctx);
|
||||
|
|
|
@ -108,7 +108,8 @@ struct tee_driver_ops {
|
|||
int (*supp_send)(struct tee_context *ctx, u32 ret, u32 num_params,
|
||||
struct tee_param *param);
|
||||
int (*shm_register)(struct tee_context *ctx, struct tee_shm *shm,
|
||||
struct page **pages, size_t num_pages);
|
||||
struct page **pages, size_t num_pages,
|
||||
unsigned long start);
|
||||
int (*shm_unregister)(struct tee_context *ctx, struct tee_shm *shm);
|
||||
};
|
||||
|
||||
|
|
Loading…
Reference in a new issue