From: Ackerley Tng MPS_SETUP is a subset of the functionality provided by MPS_NEW_CHILD. A single file covering the entire region can be created by carving out the full range with MPS_NEW_CHILD. Retain MPS_NEW_CHILD as it enables testing alternative provider functionality when there are separate sub-pools of memory carved out from the root. Signed-off-by: Ackerley Tng --- samples/kvm/mem_provider_sample.c | 72 --------------------------------------- samples/kvm/mem_provider_sample.h | 29 ++-------------- 2 files changed, 3 insertions(+), 98 deletions(-) diff --git a/samples/kvm/mem_provider_sample.c b/samples/kvm/mem_provider_sample.c index 4e8f306ba1154..abb8e35cd5357 100644 --- a/samples/kvm/mem_provider_sample.c +++ b/samples/kvm/mem_provider_sample.c @@ -61,7 +61,6 @@ struct mps_info { unsigned long base_pfn; unsigned long npages; struct page *cma_pages; /* from alloc_contig_pages(), or NULL */ - bool fixed; /* a SETUP file over addr=/len= */ bool mmap_capable; bool fixed_wb; /* holds a ref on the fixed-region WB alias */ @@ -87,11 +86,6 @@ static struct mps_root { struct page *cma_pages; unsigned long *allocated; /* pages allocated to a child */ struct list_head children; - /* - * The addr=/len= region is used either by one SETUP file or by the - * root, never by both, so that its frames have one owner. - */ - bool fixed_setup; /* Files over the fixed region that may be mapped into userspace. */ unsigned int fixed_wb_users; } mps_root; @@ -289,8 +283,6 @@ static int mps_file_release(struct inode *inode, struct file *file) } if (addr && len && !info->cma_pages) { mutex_lock(&mps_root.lock); - if (info->fixed) - mps_root.fixed_setup = false; if (info->fixed_wb) mps_fixed_wb_put(); mutex_unlock(&mps_root.lock); @@ -373,66 +365,6 @@ static struct page *mps_alloc_region(unsigned long npages) return pages; } -static long mps_ctl_setup(void __user *uarg) -{ - struct mps_setup setup; - unsigned long base_pfn, npages; - struct page *pages = NULL; - struct mps_info *info; - struct file *file; - int fd; - - if (copy_from_user(&setup, uarg, sizeof(setup))) - return -EFAULT; - if ((setup.flags & ~MPS_FLAG_MMAP_CAPABLE) || setup.pad) - return -EINVAL; - - if (addr && len) { - /* The fixed region has one owner: this file or the root. */ - mutex_lock(&mps_root.lock); - if (mps_root.fixed_setup || mps_root.npages) { - mutex_unlock(&mps_root.lock); - return -EBUSY; - } - fd = mps_new_file(addr >> PAGE_SHIFT, len >> PAGE_SHIFT, - setup.flags, &info, &file); - if (fd >= 0 && mps_over_fixed_mappable(info)) { - if (mps_fixed_wb_get()) { - put_unused_fd(fd); - fput(file); - fd = -ENOMEM; - } else { - info->fixed_wb = true; - } - } - if (fd >= 0) { - info->fixed = true; - mps_root.fixed_setup = true; - } - mutex_unlock(&mps_root.lock); - if (fd >= 0) - fd_install(fd, file); - return fd; - } - - if (!setup.size || !PAGE_ALIGNED(setup.size)) - return -EINVAL; - npages = setup.size >> PAGE_SHIFT; - pages = mps_alloc_region(npages); - if (!pages) - return -ENOMEM; - base_pfn = page_to_pfn(pages); - - fd = mps_new_file(base_pfn, npages, setup.flags, &info, &file); - if (fd < 0) { - free_contig_range(base_pfn, npages); - return fd; - } - info->cma_pages = pages; - fd_install(fd, file); - return fd; -} - /* ---- Root and children -------------------------------------------------- */ /* Create the root on the first NEW_CHILD, from addr=/len= or of @size. */ @@ -446,8 +378,6 @@ static int mps_root_ensure(u64 size) return 0; if (addr && len) { - if (mps_root.fixed_setup) - return -EBUSY; mps_root.base_pfn = addr >> PAGE_SHIFT; npages = len >> PAGE_SHIFT; } else { @@ -596,8 +526,6 @@ static long mps_ctl_ioctl(struct file *file, unsigned int cmd, void __user *uarg = (void __user *)arg; switch (cmd) { - case MPS_SETUP: - return mps_ctl_setup(uarg); case MPS_NEW_CHILD: return mps_ctl_new_child(uarg); case MPS_CTL_SET_PRESENT: diff --git a/samples/kvm/mem_provider_sample.h b/samples/kvm/mem_provider_sample.h index 1afea136328f5..3b0928b6478ca 100644 --- a/samples/kvm/mem_provider_sample.h +++ b/samples/kvm/mem_provider_sample.h @@ -14,38 +14,17 @@ * the ioctls below make. */ -/* Flags for struct mps_setup and struct mps_new_child */ +/* Flags for struct mps_new_child */ /* The host may map the pages; otherwise they are NO_USER_MAP */ #define MPS_FLAG_MMAP_CAPABLE (1u << 0) -/* - * ioctl on /dev/mem_provider_sample: create a provider fd. - * - * If the module was loaded with addr= and len=, the fd covers that fixed - * range, which has no struct page, and @size is ignored. The fixed range - * then has one owner. SETUP fails with -EBUSY while a SETUP file uses it, - * or once the first MPS_NEW_CHILD has made it the root of the children, which - * lasts until the module is unloaded. MPS_NEW_CHILD fails with -EBUSY while - * a SETUP file uses it. Otherwise the fd covers @size bytes from - * alloc_contig_pages(). - */ -struct mps_setup { - __u32 flags; /* MPS_FLAG_* */ - __u32 pad; - __u64 size; /* bytes, page aligned */ -}; - #define MPS_IOCTL_BASE 'P' -#define MPS_SETUP \ - _IOW(MPS_IOCTL_BASE, 1, struct mps_setup) /* * ---- A tree of owners -------------------------------------------------- * * The control device owns one region, the root. NEW_CHILD carves part of - * it into a new provider fd for one VM. The owner can MOVE pages between - * children, DONATE pages to the root, so that no child has them, and - * RECLAIM them. Each change revokes the range, so KVM and iommufd follow. + * it into a new provider fd for one VM. * * The owner changes a child's pages through the control device * (CTL_SET_PRESENT). A child fd is read-only to its holder: a VMM can @@ -54,9 +33,7 @@ struct mps_setup { /* * ioctl on /dev/mem_provider_sample: carve [@offset, @offset + @len) of the - * root into a new child fd. The child gets every page of the range that no - * other child has and that is not donated. Ranges of children may overlap, - * which is how a page can MOVE between them. Returns the child fd. + * root into a new child fd. Returns the child fd. */ struct mps_new_child { __u32 flags; /* MPS_FLAG_* */ -- 2.56.0.257.gf7497c7d27-goog