[PATCH v4 3/9] powerpc/vas: Add paste address mmap fault handler

Nicholas Piggin npiggin at gmail.com
Wed Feb 23 18:03:36 AEDT 2022


Excerpts from Haren Myneni's message of February 20, 2022 5:55 am:
> 
> The user space opens VAS windows and issues NX requests by pasting
> CRB on the corresponding paste address mmap. When the system lost
> credits due to core removal, the kernel has to close the window in
> the hypervisor and make the window inactive by unmapping this paste
> address. Also the OS has to handle NX request page faults if the user
> space issue NX requests.
> 
> This handler maps the new paste address with the same VMA when the
> window is active again (due to core add with DLPAR). Otherwise
> returns paste failure.
> 

Reviewed-by: Nicholas Piggin <npiggin at gmail.com>

> Signed-off-by: Haren Myneni <haren at linux.ibm.com>
> ---
>  arch/powerpc/include/asm/vas.h          | 10 ++++
>  arch/powerpc/platforms/book3s/vas-api.c | 68 +++++++++++++++++++++++++
>  2 files changed, 78 insertions(+)
> 
> diff --git a/arch/powerpc/include/asm/vas.h b/arch/powerpc/include/asm/vas.h
> index 57573d9c1e09..27251af18c65 100644
> --- a/arch/powerpc/include/asm/vas.h
> +++ b/arch/powerpc/include/asm/vas.h
> @@ -29,6 +29,12 @@
>  #define VAS_THRESH_FIFO_GT_QTR_FULL	2
>  #define VAS_THRESH_FIFO_GT_EIGHTH_FULL	3
>  
> +/*
> + * VAS window Linux status bits
> + */
> +#define VAS_WIN_ACTIVE		0x0	/* Used in platform independent */
> +					/* vas mmap() */
> +
>  /*
>   * Get/Set bit fields
>   */
> @@ -59,6 +65,9 @@ struct vas_user_win_ref {
>  	struct pid *pid;	/* PID of owner */
>  	struct pid *tgid;	/* Thread group ID of owner */
>  	struct mm_struct *mm;	/* Linux process mm_struct */
> +	struct mutex mmap_mutex;	/* protects paste address mmap() */
> +					/* with DLPAR close/open windows */
> +	struct vm_area_struct *vma;	/* Save VMA and used in DLPAR ops */
>  };
>  
>  /*
> @@ -67,6 +76,7 @@ struct vas_user_win_ref {
>  struct vas_window {
>  	u32 winid;
>  	u32 wcreds_max;	/* Window credits */
> +	u32 status;	/* Window status used in OS */
>  	enum vas_cop_type cop;
>  	struct vas_user_win_ref task_ref;
>  	char *dbgname;
> diff --git a/arch/powerpc/platforms/book3s/vas-api.c b/arch/powerpc/platforms/book3s/vas-api.c
> index 4d82c92ddd52..f359e7b2bf90 100644
> --- a/arch/powerpc/platforms/book3s/vas-api.c
> +++ b/arch/powerpc/platforms/book3s/vas-api.c
> @@ -316,6 +316,7 @@ static int coproc_ioc_tx_win_open(struct file *fp, unsigned long arg)
>  		return PTR_ERR(txwin);
>  	}
>  
> +	mutex_init(&txwin->task_ref.mmap_mutex);
>  	cp_inst->txwin = txwin;
>  
>  	return 0;
> @@ -350,6 +351,70 @@ static int coproc_release(struct inode *inode, struct file *fp)
>  	return 0;
>  }
>  
> +/*
> + * This fault handler is invoked when the core generates page fault on
> + * the paste address. Happens if the kernel closes window in hypervisor
> + * (on pseries) due to lost credit or the paste address is not mapped.
> + */
> +static vm_fault_t vas_mmap_fault(struct vm_fault *vmf)
> +{
> +	struct vm_area_struct *vma = vmf->vma;
> +	struct file *fp = vma->vm_file;
> +	struct coproc_instance *cp_inst = fp->private_data;
> +	struct vas_window *txwin;
> +	u64 paste_addr;
> +	int ret;
> +
> +	/*
> +	 * window is not opened. Shouldn't expect this error.
> +	 */
> +	if (!cp_inst || !cp_inst->txwin) {
> +		pr_err("%s(): Unexpected fault on paste address with TX window closed\n",
> +				__func__);
> +		return VM_FAULT_SIGBUS;
> +	}
> +
> +	txwin = cp_inst->txwin;
> +	/*
> +	 * When the LPAR lost credits due to core removal or during
> +	 * migration, invalidate the existing mapping for the current
> +	 * paste addresses and set windows in-active (zap_page_range in
> +	 * reconfig_close_windows()).
> +	 * New mapping will be done later after migration or new credits
> +	 * available. So continue to receive faults if the user space
> +	 * issue NX request.
> +	 */
> +	if (txwin->task_ref.vma != vmf->vma) {
> +		pr_err("%s(): No previous mapping with paste address\n",
> +			__func__);
> +		return VM_FAULT_SIGBUS;
> +	}
> +
> +	mutex_lock(&txwin->task_ref.mmap_mutex);
> +	/*
> +	 * The window may be inactive due to lost credit (Ex: core
> +	 * removal with DLPAR). If the window is active again when
> +	 * the credit is available, map the new paste address at the
> +	 * the window virtual address.
> +	 */
> +	if (txwin->status == VAS_WIN_ACTIVE) {
> +		paste_addr = cp_inst->coproc->vops->paste_addr(txwin);
> +		if (paste_addr) {
> +			ret = vmf_insert_pfn(vma, vma->vm_start,
> +					(paste_addr >> PAGE_SHIFT));
> +			mutex_unlock(&txwin->task_ref.mmap_mutex);
> +			return ret;
> +		}
> +	}
> +	mutex_unlock(&txwin->task_ref.mmap_mutex);
> +
> +	return VM_FAULT_SIGBUS;
> +
> +}
> +static const struct vm_operations_struct vas_vm_ops = {
> +	.fault = vas_mmap_fault,
> +};
> +
>  static int coproc_mmap(struct file *fp, struct vm_area_struct *vma)
>  {
>  	struct coproc_instance *cp_inst = fp->private_data;
> @@ -398,6 +463,9 @@ static int coproc_mmap(struct file *fp, struct vm_area_struct *vma)
>  	pr_devel("%s(): paste addr %llx at %lx, rc %d\n", __func__,
>  			paste_addr, vma->vm_start, rc);
>  
> +	txwin->task_ref.vma = vma;
> +	vma->vm_ops = &vas_vm_ops;
> +
>  	return rc;
>  }
>  
> -- 
> 2.27.0
> 
> 
> 


More information about the Linuxppc-dev mailing list