Date: Fri, 17 Mar 2017 10:30:06 +0000 (UTC) From: Hans Petter Selasky <hselasky@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r315443 - in head/sys/compat/linuxkpi/common: include/linux src Message-ID: <201703171030.v2HAU6v6072623@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: hselasky Date: Fri Mar 17 10:30:06 2017 New Revision: 315443 URL: https://svnweb.freebsd.org/changeset/base/315443 Log: Implement minimalistic memory mapping structure, struct mm_struct, and some associated helper functions in the LinuxKPI. Let the existing linux_alloc_current() function allocate and initialize the new structure and let linux_free_current() drop the refcount on the memory mapping structure. When the mm_struct's refcount reaches zero, the structure is freed. Obtained from: kmacy @ MFC after: 1 week Sponsored by: Mellanox Technologies Added: head/sys/compat/linuxkpi/common/include/linux/mm_types.h (contents, props changed) Modified: head/sys/compat/linuxkpi/common/include/linux/mm.h head/sys/compat/linuxkpi/common/include/linux/sched.h head/sys/compat/linuxkpi/common/src/linux_current.c Modified: head/sys/compat/linuxkpi/common/include/linux/mm.h ============================================================================== --- head/sys/compat/linuxkpi/common/include/linux/mm.h Fri Mar 17 08:02:46 2017 (r315442) +++ head/sys/compat/linuxkpi/common/include/linux/mm.h Fri Mar 17 10:30:06 2017 (r315443) @@ -36,6 +36,7 @@ #include <linux/spinlock.h> #include <linux/gfp.h> #include <linux/kernel.h> +#include <linux/mm_types.h> #define PAGE_ALIGN(x) ALIGN(x, PAGE_SIZE) Added: head/sys/compat/linuxkpi/common/include/linux/mm_types.h ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ head/sys/compat/linuxkpi/common/include/linux/mm_types.h Fri Mar 17 10:30:06 2017 (r315443) @@ -0,0 +1,71 @@ +/*- + * Copyright (c) 2017 Mellanox Technologies, Ltd. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice unmodified, this list of conditions, and the following + * disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * $FreeBSD$ + */ + +#ifndef _LINUX_MM_TYPES_H_ +#define _LINUX_MM_TYPES_H_ + +#include <linux/types.h> +#include <linux/list.h> +#include <linux/page.h> +#include <linux/rwsem.h> + +#include <asm/atomic.h> + +struct vm_area_struct; +struct task_struct; +struct vmspace; + +struct mm_struct { + struct vm_area_struct *mmap; + struct vmspace *vmspace; + atomic_t mm_count; + atomic_t mm_users; + size_t pinned_vm; + struct rw_semaphore mmap_sem; +}; + +extern void linux_mm_dtor(struct mm_struct *mm); + +static inline void +mmdrop(struct mm_struct *mm) +{ + if (__predict_false(atomic_dec_and_test(&mm->mm_count))) + linux_mm_dtor(mm); +} + +static inline void +mmput(struct mm_struct *mm) +{ + if (__predict_false(atomic_dec_and_test(&mm->mm_users))) + mmdrop(mm); +} + +extern struct mm_struct *linux_get_task_mm(struct task_struct *); +#define get_task_mm(task) linux_get_task_mm(task) + +#endif /* _LINUX_MM_TYPES_H_ */ Modified: head/sys/compat/linuxkpi/common/include/linux/sched.h ============================================================================== --- head/sys/compat/linuxkpi/common/include/linux/sched.h Fri Mar 17 08:02:46 2017 (r315442) +++ head/sys/compat/linuxkpi/common/include/linux/sched.h Fri Mar 17 10:30:06 2017 (r315443) @@ -40,6 +40,7 @@ #include <linux/types.h> #include <linux/completion.h> #include <linux/slab.h> +#include <linux/mm_types.h> #include <asm/atomic.h> @@ -54,6 +55,7 @@ struct task_struct { struct thread *task_thread; + struct mm_struct *mm; linux_task_fn_t *task_fn; void *task_data; int task_ret; Modified: head/sys/compat/linuxkpi/common/src/linux_current.c ============================================================================== --- head/sys/compat/linuxkpi/common/src/linux_current.c Fri Mar 17 08:02:46 2017 (r315442) +++ head/sys/compat/linuxkpi/common/src/linux_current.c Fri Mar 17 10:30:06 2017 (r315443) @@ -43,6 +43,7 @@ int linux_alloc_current(struct thread *td, int flags) { struct task_struct *ts; + struct mm_struct *mm; MPASS(td->td_lkpi_task == NULL); @@ -50,18 +51,55 @@ linux_alloc_current(struct thread *td, i if (ts == NULL) return (ENOMEM); + mm = malloc(sizeof(*mm), M_LINUX_CURRENT, flags | M_ZERO); + if (mm == NULL) { + free(ts, M_LINUX_CURRENT); + return (ENOMEM); + } + atomic_set(&ts->kthread_flags, 0); ts->task_thread = td; ts->comm = td->td_name; ts->pid = td->td_tid; + ts->mm = mm; ts->state = TASK_RUNNING; + + /* setup mm_struct */ + init_rwsem(&mm->mmap_sem); + atomic_set(&mm->mm_count, 1); + atomic_set(&mm->mm_users, 1); + mm->vmspace = vmspace_acquire_ref(td->td_proc); + + /* store pointer to task struct */ td->td_lkpi_task = ts; return (0); } +struct mm_struct * +linux_get_task_mm(struct task_struct *task) +{ + struct mm_struct *mm; + + mm = task->mm; + if (mm != NULL && mm->vmspace != NULL) { + atomic_inc(&mm->mm_users); + return (mm); + } + return (NULL); +} + +void +linux_mm_dtor(struct mm_struct *mm) +{ + if (mm->vmspace != NULL) + vmspace_free(mm->vmspace); + free(mm, M_LINUX_CURRENT); +} + void linux_free_current(struct task_struct *ts) { + mmput(ts->mm); free(ts, M_LINUX_CURRENT); } @@ -75,7 +113,7 @@ linuxkpi_thread_dtor(void *arg __unused, return; td->td_lkpi_task = NULL; - free(ts, M_LINUX_CURRENT); + linux_free_current(ts); } static void
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201703171030.v2HAU6v6072623>