forked from Qortal/Brooklyn
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
93 lines
1.8 KiB
93 lines
1.8 KiB
// SPDX-License-Identifier: MIT |
|
/* |
|
* Copyright 2019 Advanced Micro Devices, Inc. |
|
*/ |
|
|
|
#include <linux/slab.h> |
|
#include <linux/tee_drv.h> |
|
#include <linux/psp-sev.h> |
|
#include "amdtee_private.h" |
|
|
|
static int pool_op_alloc(struct tee_shm_pool_mgr *poolm, struct tee_shm *shm, |
|
size_t size) |
|
{ |
|
unsigned int order = get_order(size); |
|
unsigned long va; |
|
int rc; |
|
|
|
va = __get_free_pages(GFP_KERNEL | __GFP_ZERO, order); |
|
if (!va) |
|
return -ENOMEM; |
|
|
|
shm->kaddr = (void *)va; |
|
shm->paddr = __psp_pa((void *)va); |
|
shm->size = PAGE_SIZE << order; |
|
|
|
/* Map the allocated memory in to TEE */ |
|
rc = amdtee_map_shmem(shm); |
|
if (rc) { |
|
free_pages(va, order); |
|
shm->kaddr = NULL; |
|
return rc; |
|
} |
|
|
|
return 0; |
|
} |
|
|
|
static void pool_op_free(struct tee_shm_pool_mgr *poolm, struct tee_shm *shm) |
|
{ |
|
/* Unmap the shared memory from TEE */ |
|
amdtee_unmap_shmem(shm); |
|
free_pages((unsigned long)shm->kaddr, get_order(shm->size)); |
|
shm->kaddr = NULL; |
|
} |
|
|
|
static void pool_op_destroy_poolmgr(struct tee_shm_pool_mgr *poolm) |
|
{ |
|
kfree(poolm); |
|
} |
|
|
|
static const struct tee_shm_pool_mgr_ops pool_ops = { |
|
.alloc = pool_op_alloc, |
|
.free = pool_op_free, |
|
.destroy_poolmgr = pool_op_destroy_poolmgr, |
|
}; |
|
|
|
static struct tee_shm_pool_mgr *pool_mem_mgr_alloc(void) |
|
{ |
|
struct tee_shm_pool_mgr *mgr = kzalloc(sizeof(*mgr), GFP_KERNEL); |
|
|
|
if (!mgr) |
|
return ERR_PTR(-ENOMEM); |
|
|
|
mgr->ops = &pool_ops; |
|
|
|
return mgr; |
|
} |
|
|
|
struct tee_shm_pool *amdtee_config_shm(void) |
|
{ |
|
struct tee_shm_pool_mgr *priv_mgr; |
|
struct tee_shm_pool_mgr *dmabuf_mgr; |
|
void *rc; |
|
|
|
rc = pool_mem_mgr_alloc(); |
|
if (IS_ERR(rc)) |
|
return rc; |
|
priv_mgr = rc; |
|
|
|
rc = pool_mem_mgr_alloc(); |
|
if (IS_ERR(rc)) { |
|
tee_shm_pool_mgr_destroy(priv_mgr); |
|
return rc; |
|
} |
|
dmabuf_mgr = rc; |
|
|
|
rc = tee_shm_pool_alloc(priv_mgr, dmabuf_mgr); |
|
if (IS_ERR(rc)) { |
|
tee_shm_pool_mgr_destroy(priv_mgr); |
|
tee_shm_pool_mgr_destroy(dmabuf_mgr); |
|
} |
|
|
|
return rc; |
|
}
|
|
|