Merge "ion: Ensure non-HLOS memory cannot be mapped by CPU"
This commit is contained in:
commit
d750db225f
5 changed files with 66 additions and 7 deletions
|
@ -313,14 +313,37 @@ err:
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void *ion_secure_cma_map_kernel(struct ion_heap *heap,
|
||||||
|
struct ion_buffer *buffer)
|
||||||
|
{
|
||||||
|
if (!is_buffer_hlos_assigned(buffer)) {
|
||||||
|
pr_info("%s: Mapping non-HLOS accessible buffer disallowed\n",
|
||||||
|
__func__);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
return ion_cma_map_kernel(heap, buffer);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int ion_secure_cma_map_user(struct ion_heap *mapper,
|
||||||
|
struct ion_buffer *buffer,
|
||||||
|
struct vm_area_struct *vma)
|
||||||
|
{
|
||||||
|
if (!is_buffer_hlos_assigned(buffer)) {
|
||||||
|
pr_info("%s: Mapping non-HLOS accessible buffer disallowed\n",
|
||||||
|
__func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
return ion_cma_mmap(mapper, buffer, vma);
|
||||||
|
}
|
||||||
|
|
||||||
static struct ion_heap_ops ion_secure_cma_ops = {
|
static struct ion_heap_ops ion_secure_cma_ops = {
|
||||||
.allocate = ion_secure_cma_allocate,
|
.allocate = ion_secure_cma_allocate,
|
||||||
.free = ion_secure_cma_free,
|
.free = ion_secure_cma_free,
|
||||||
.map_dma = ion_cma_heap_map_dma,
|
.map_dma = ion_cma_heap_map_dma,
|
||||||
.unmap_dma = ion_cma_heap_unmap_dma,
|
.unmap_dma = ion_cma_heap_unmap_dma,
|
||||||
.phys = ion_cma_phys,
|
.phys = ion_cma_phys,
|
||||||
.map_user = ion_cma_mmap,
|
.map_user = ion_secure_cma_map_user,
|
||||||
.map_kernel = ion_cma_map_kernel,
|
.map_kernel = ion_secure_cma_map_kernel,
|
||||||
.unmap_kernel = ion_cma_unmap_kernel,
|
.unmap_kernel = ion_cma_unmap_kernel,
|
||||||
.print_debug = ion_cma_print_debug,
|
.print_debug = ion_cma_print_debug,
|
||||||
};
|
};
|
||||||
|
|
|
@ -99,6 +99,11 @@ size_t ion_system_heap_secure_page_pool_total(struct ion_heap *heap,
|
||||||
return total << PAGE_SHIFT;
|
return total << PAGE_SHIFT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int ion_heap_is_system_heap_type(enum ion_heap_type type)
|
||||||
|
{
|
||||||
|
return type == ((enum ion_heap_type)ION_HEAP_TYPE_SYSTEM);
|
||||||
|
}
|
||||||
|
|
||||||
static struct page *alloc_buffer_page(struct ion_system_heap *heap,
|
static struct page *alloc_buffer_page(struct ion_system_heap *heap,
|
||||||
struct ion_buffer *buffer,
|
struct ion_buffer *buffer,
|
||||||
unsigned long order,
|
unsigned long order,
|
||||||
|
@ -352,6 +357,13 @@ static int ion_system_heap_allocate(struct ion_heap *heap,
|
||||||
int vmid = get_secure_vmid(buffer->flags);
|
int vmid = get_secure_vmid(buffer->flags);
|
||||||
struct device *dev = heap->priv;
|
struct device *dev = heap->priv;
|
||||||
|
|
||||||
|
if (ion_heap_is_system_heap_type(buffer->heap->type) &&
|
||||||
|
is_secure_vmid_valid(vmid)) {
|
||||||
|
pr_info("%s: System heap doesn't support secure allocations\n",
|
||||||
|
__func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
if (align > PAGE_SIZE)
|
if (align > PAGE_SIZE)
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
*
|
*
|
||||||
* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
|
* Copyright (c) 2014-2018 The Linux Foundation. All rights reserved.
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License version 2 and
|
* it under the terms of the GNU General Public License version 2 and
|
||||||
|
@ -170,14 +170,15 @@ out:
|
||||||
sys_heap->ops->free(&buffer);
|
sys_heap->ops->free(&buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void process_one_shrink(struct ion_heap *sys_heap,
|
static void process_one_shrink(struct ion_system_secure_heap *secure_heap,
|
||||||
|
struct ion_heap *sys_heap,
|
||||||
struct prefetch_info *info)
|
struct prefetch_info *info)
|
||||||
{
|
{
|
||||||
struct ion_buffer buffer;
|
struct ion_buffer buffer;
|
||||||
size_t pool_size, size;
|
size_t pool_size, size;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
buffer.heap = sys_heap;
|
buffer.heap = &secure_heap->heap;
|
||||||
buffer.flags = info->vmid;
|
buffer.flags = info->vmid;
|
||||||
|
|
||||||
pool_size = ion_system_heap_secure_page_pool_total(sys_heap,
|
pool_size = ion_system_heap_secure_page_pool_total(sys_heap,
|
||||||
|
@ -192,6 +193,7 @@ static void process_one_shrink(struct ion_heap *sys_heap,
|
||||||
}
|
}
|
||||||
|
|
||||||
buffer.private_flags = ION_PRIV_FLAG_SHRINKER_FREE;
|
buffer.private_flags = ION_PRIV_FLAG_SHRINKER_FREE;
|
||||||
|
buffer.heap = sys_heap;
|
||||||
sys_heap->ops->free(&buffer);
|
sys_heap->ops->free(&buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -211,7 +213,7 @@ static void ion_system_secure_heap_prefetch_work(struct work_struct *work)
|
||||||
spin_unlock_irqrestore(&secure_heap->work_lock, flags);
|
spin_unlock_irqrestore(&secure_heap->work_lock, flags);
|
||||||
|
|
||||||
if (info->shrink)
|
if (info->shrink)
|
||||||
process_one_shrink(sys_heap, info);
|
process_one_shrink(secure_heap, sys_heap, info);
|
||||||
else
|
else
|
||||||
process_one_prefetch(sys_heap, info);
|
process_one_prefetch(sys_heap, info);
|
||||||
|
|
||||||
|
|
|
@ -678,6 +678,21 @@ int get_secure_vmid(unsigned long flags)
|
||||||
return VMID_CP_SPSS_SP_SHARED;
|
return VMID_CP_SPSS_SP_SHARED;
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool is_buffer_hlos_assigned(struct ion_buffer *buffer)
|
||||||
|
{
|
||||||
|
bool is_hlos = false;
|
||||||
|
|
||||||
|
if (buffer->heap->type == (enum ion_heap_type)ION_HEAP_TYPE_HYP_CMA &&
|
||||||
|
(buffer->flags & ION_FLAG_CP_HLOS))
|
||||||
|
is_hlos = true;
|
||||||
|
|
||||||
|
if (get_secure_vmid(buffer->flags) <= 0)
|
||||||
|
is_hlos = true;
|
||||||
|
|
||||||
|
return is_hlos;
|
||||||
|
}
|
||||||
|
|
||||||
/* fix up the cases where the ioctl direction bits are incorrect */
|
/* fix up the cases where the ioctl direction bits are incorrect */
|
||||||
static unsigned int msm_ion_ioctl_dir(unsigned int cmd)
|
static unsigned int msm_ion_ioctl_dir(unsigned int cmd)
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 2016, The Linux Foundation. All rights reserved.
|
* Copyright (c) 2016, 2018, The Linux Foundation. All rights reserved.
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License version 2 and
|
* it under the terms of the GNU General Public License version 2 and
|
||||||
|
@ -175,6 +175,8 @@ int msm_ion_do_cache_offset_op(
|
||||||
void *vaddr, unsigned int offset, unsigned long len,
|
void *vaddr, unsigned int offset, unsigned long len,
|
||||||
unsigned int cmd);
|
unsigned int cmd);
|
||||||
|
|
||||||
|
bool is_buffer_hlos_assigned(struct ion_buffer *buffer);
|
||||||
|
|
||||||
#else
|
#else
|
||||||
static inline struct ion_client *msm_ion_client_create(const char *name)
|
static inline struct ion_client *msm_ion_client_create(const char *name)
|
||||||
{
|
{
|
||||||
|
@ -202,6 +204,11 @@ int msm_ion_do_cache_offset_op(
|
||||||
return -ENODEV;
|
return -ENODEV;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool is_buffer_hlos_assigned(struct ion_buffer *buffer)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
#endif /* CONFIG_ION */
|
#endif /* CONFIG_ION */
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Add table
Reference in a new issue