Move insertion into the page tree out of sgx_encl_page_alloc() so that the function can be moved out from under encl->lock. This is a preparatory step for removing the add page worker, as the encl_page is needed to allocate its EPC page, and EPC page allocation must be done without holding encl->lock so that it can trigger reclaim if necessary. Note, radix_tree_insert() returns -EEXIST if the the slot is already in use, i.e. there's no need to pre-check via radix_tree_lookup(). Signed-off-by: Sean Christopherson <sean.j.christopherson@xxxxxxxxx> --- arch/x86/kernel/cpu/sgx/driver/ioctl.c | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/arch/x86/kernel/cpu/sgx/driver/ioctl.c b/arch/x86/kernel/cpu/sgx/driver/ioctl.c index 2b3b86412131..55e0fe261b8c 100644 --- a/arch/x86/kernel/cpu/sgx/driver/ioctl.c +++ b/arch/x86/kernel/cpu/sgx/driver/ioctl.c @@ -251,10 +251,7 @@ static struct sgx_encl_page *sgx_encl_page_alloc(struct sgx_encl *encl, u64 page_type) { struct sgx_encl_page *encl_page; - int ret; - if (radix_tree_lookup(&encl->page_tree, PFN_DOWN(addr))) - return ERR_PTR(-EEXIST); encl_page = kzalloc(sizeof(*encl_page), GFP_KERNEL); if (!encl_page) return ERR_PTR(-ENOMEM); @@ -263,12 +260,7 @@ static struct sgx_encl_page *sgx_encl_page_alloc(struct sgx_encl *encl, encl_page->desc |= SGX_ENCL_PAGE_TCS; encl_page->encl = encl; encl_page->vm_prot_bits = calc_vm_prot_bits(prot, 0); - ret = radix_tree_insert(&encl->page_tree, PFN_DOWN(encl_page->desc), - encl_page); - if (ret) { - kfree(encl_page); - return ERR_PTR(ret); - } + return encl_page; } @@ -540,6 +532,11 @@ static int sgx_encl_add_page(struct sgx_encl *encl, unsigned long addr, goto err_out_shrink; } + ret = radix_tree_insert(&encl->page_tree, PFN_DOWN(encl_page->desc), + encl_page); + if (ret) + goto err_out_free; + ret = __sgx_encl_add_page(encl, encl_page, data, secinfo, mrmask); if (ret) goto err_out; @@ -550,6 +547,7 @@ static int sgx_encl_add_page(struct sgx_encl *encl, unsigned long addr, err_out: radix_tree_delete(&encl_page->encl->page_tree, PFN_DOWN(encl_page->desc)); +err_out_free: kfree(encl_page); err_out_shrink: -- 2.22.0