[13/18] kernel: add kcompat_sys_{f,}statfs64()

Message ID 20180514094640.27569-14-mark.rutland@arm.com
State New
Headers show
Series
  • arm64: invoke syscalls with pt_regs
Related show

Commit Message

Mark Rutland May 14, 2018, 9:46 a.m.
Using this helper allows us to avoid the in-kernel calls to the
compat_sys_{f,}statfs64() sycalls, as are necessary for parameter
mangling in arm64's compat handling.

Following the example of ksys_* functions, kcompat_sys_* functions are
intended to be a drop-in replacement for their compat_sys_*
counterparts, with the same calling convention.

This is necessary to enable conversion of arm64's syscall handling to
use pt_regs wrappers.

Signed-off-by: Mark Rutland <mark.rutland@arm.com>

Cc: Al Viro <viro@zeniv.linux.org.uk>
Cc: Dominik Brodowski <linux@dominikbrodowski.net>
Cc: linux-fsdevel@vger.kernel.org
---
 fs/statfs.c              | 14 ++++++++++++--
 include/linux/syscalls.h |  8 ++++++++
 2 files changed, 20 insertions(+), 2 deletions(-)

-- 
2.11.0

Comments

Mark Rutland May 14, 2018, 5:14 p.m. | #1
On Mon, May 14, 2018 at 10:46:35AM +0100, Mark Rutland wrote:
> Using this helper allows us to avoid the in-kernel calls to the

> compat_sys_{f,}statfs64() sycalls, as are necessary for parameter

> mangling in arm64's compat handling.

> 

> Following the example of ksys_* functions, kcompat_sys_* functions are

> intended to be a drop-in replacement for their compat_sys_*

> counterparts, with the same calling convention.

> 

> This is necessary to enable conversion of arm64's syscall handling to

> use pt_regs wrappers.


> diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h

> index 6723ea51ec99..e0bf3e4bb897 100644

> --- a/include/linux/syscalls.h

> +++ b/include/linux/syscalls.h

> @@ -59,6 +59,7 @@ struct tms;

>  struct utimbuf;

>  struct mq_attr;

>  struct compat_stat;

> +struct compat_statfs64;

>  struct compat_timeval;

>  struct robust_list_head;

>  struct getcpu_cache;

> @@ -1150,6 +1151,13 @@ unsigned long ksys_mmap_pgoff(unsigned long addr, unsigned long len,

>  ssize_t ksys_readahead(int fd, loff_t offset, size_t count);

>  unsigned int ksys_personality(unsigned int personality);

>  

> +#ifdef CONFIG_COMPAT

> +int kcompat_sys_statfs64(const char __user * pathname, compat_size_t sz,

> +		     struct compat_statfs64 __user * buf);

> +int kcompat_sys_fstatfs64(unsigned int fd, compat_size_t sz,

> +			  struct compat_statfs64 __user * buf);

> +#endif


I've moved these to <linux/compat.h>, so that they live with the rest of
the compat syscall stuff. That should avoid build failures the kbuild
test robot picked up where compat_size_t wasn't dfined.

Thanks,
Mark.
Dominik Brodowski May 14, 2018, 8:34 p.m. | #2
On Mon, May 14, 2018 at 06:14:28PM +0100, Mark Rutland wrote:
> On Mon, May 14, 2018 at 10:46:35AM +0100, Mark Rutland wrote:

> > Using this helper allows us to avoid the in-kernel calls to the

> > compat_sys_{f,}statfs64() sycalls, as are necessary for parameter

> > mangling in arm64's compat handling.

> > 

> > Following the example of ksys_* functions, kcompat_sys_* functions are

> > intended to be a drop-in replacement for their compat_sys_*

> > counterparts, with the same calling convention.

> > 

> > This is necessary to enable conversion of arm64's syscall handling to

> > use pt_regs wrappers.

> 

> > diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h

> > index 6723ea51ec99..e0bf3e4bb897 100644

> > --- a/include/linux/syscalls.h

> > +++ b/include/linux/syscalls.h

> > @@ -59,6 +59,7 @@ struct tms;

> >  struct utimbuf;

> >  struct mq_attr;

> >  struct compat_stat;

> > +struct compat_statfs64;

> >  struct compat_timeval;

> >  struct robust_list_head;

> >  struct getcpu_cache;

> > @@ -1150,6 +1151,13 @@ unsigned long ksys_mmap_pgoff(unsigned long addr, unsigned long len,

> >  ssize_t ksys_readahead(int fd, loff_t offset, size_t count);

> >  unsigned int ksys_personality(unsigned int personality);

> >  

> > +#ifdef CONFIG_COMPAT

> > +int kcompat_sys_statfs64(const char __user * pathname, compat_size_t sz,

> > +		     struct compat_statfs64 __user * buf);

> > +int kcompat_sys_fstatfs64(unsigned int fd, compat_size_t sz,

> > +			  struct compat_statfs64 __user * buf);

> > +#endif

> 

> I've moved these to <linux/compat.h>, so that they live with the rest of

> the compat syscall stuff. That should avoid build failures the kbuild

> test robot picked up where compat_size_t wasn't dfined.


Please add a comment there, similar to what is in syscalls.h:

	/*
	 * Kernel code should not call syscalls (i.e., sys_xyzyyz()) directly.
	 * Instead, use one of the functions which work equivalently, such as
	 * the ksys_xyzyyz() functions prototyped below.
	 */

Once you have done so, feel free to add my

	Reviewed-by: Dominik Brodowski <linux@dominikbrodowski.net>


tag to this patch.

Thanks,
	Dominik
Mark Rutland May 15, 2018, 9:53 a.m. | #3
On Mon, May 14, 2018 at 10:34:14PM +0200, Dominik Brodowski wrote:
> On Mon, May 14, 2018 at 06:14:28PM +0100, Mark Rutland wrote:

> > On Mon, May 14, 2018 at 10:46:35AM +0100, Mark Rutland wrote:

> > > +#ifdef CONFIG_COMPAT

> > > +int kcompat_sys_statfs64(const char __user * pathname, compat_size_t sz,

> > > +		     struct compat_statfs64 __user * buf);

> > > +int kcompat_sys_fstatfs64(unsigned int fd, compat_size_t sz,

> > > +			  struct compat_statfs64 __user * buf);

> > > +#endif

> > 

> > I've moved these to <linux/compat.h>, so that they live with the rest of

> > the compat syscall stuff. That should avoid build failures the kbuild

> > test robot picked up where compat_size_t wasn't dfined.

> 

> Please add a comment there, similar to what is in syscalls.h:

> 

> 	/*

> 	 * Kernel code should not call syscalls (i.e., sys_xyzyyz()) directly.

> 	 * Instead, use one of the functions which work equivalently, such as

> 	 * the ksys_xyzyyz() functions prototyped below.

> 	 */


To make the kcompat_sys_* naming scheme clearer, I've added compat references to
the above, i.e.

/*
 * Kernel code should not call compat syscalls (i.e., compat_sys_xyzyyz())
 * directly. Instead, use one of the functions which work equivalently, such
 * as the kcompat_sys_xyzyyz() functions prototyped below.
 */

> Once you have done so, feel free to add my

> 

> 	Reviewed-by: Dominik Brodowski <linux@dominikbrodowski.net>


I hope that this still stands with the changes above?

Thanks,
Mark.
Dominik Brodowski May 15, 2018, 9:58 a.m. | #4
On Tue, May 15, 2018 at 10:53:51AM +0100, Mark Rutland wrote:
> On Mon, May 14, 2018 at 10:34:14PM +0200, Dominik Brodowski wrote:

> > On Mon, May 14, 2018 at 06:14:28PM +0100, Mark Rutland wrote:

> > > On Mon, May 14, 2018 at 10:46:35AM +0100, Mark Rutland wrote:

> > > > +#ifdef CONFIG_COMPAT

> > > > +int kcompat_sys_statfs64(const char __user * pathname, compat_size_t sz,

> > > > +		     struct compat_statfs64 __user * buf);

> > > > +int kcompat_sys_fstatfs64(unsigned int fd, compat_size_t sz,

> > > > +			  struct compat_statfs64 __user * buf);

> > > > +#endif

> > > 

> > > I've moved these to <linux/compat.h>, so that they live with the rest of

> > > the compat syscall stuff. That should avoid build failures the kbuild

> > > test robot picked up where compat_size_t wasn't dfined.

> > 

> > Please add a comment there, similar to what is in syscalls.h:

> > 

> > 	/*

> > 	 * Kernel code should not call syscalls (i.e., sys_xyzyyz()) directly.

> > 	 * Instead, use one of the functions which work equivalently, such as

> > 	 * the ksys_xyzyyz() functions prototyped below.

> > 	 */

> 

> To make the kcompat_sys_* naming scheme clearer, I've added compat references to

> the above, i.e.

> 

> /*

>  * Kernel code should not call compat syscalls (i.e., compat_sys_xyzyyz())

>  * directly. Instead, use one of the functions which work equivalently, such

>  * as the kcompat_sys_xyzyyz() functions prototyped below.

>  */


That's what I meant ;)

> > Once you have done so, feel free to add my

> > 

> > 	Reviewed-by: Dominik Brodowski <linux@dominikbrodowski.net>

> 

> I hope that this still stands with the changes above?


It does. Thanks!

	Dominik

Patch

diff --git a/fs/statfs.c b/fs/statfs.c
index 5b2a24f0f263..f0216629621d 100644
--- a/fs/statfs.c
+++ b/fs/statfs.c
@@ -335,7 +335,7 @@  static int put_compat_statfs64(struct compat_statfs64 __user *ubuf, struct kstat
 	return 0;
 }
 
-COMPAT_SYSCALL_DEFINE3(statfs64, const char __user *, pathname, compat_size_t, sz, struct compat_statfs64 __user *, buf)
+int kcompat_sys_statfs64(const char __user * pathname, compat_size_t sz, struct compat_statfs64 __user * buf)
 {
 	struct kstatfs tmp;
 	int error;
@@ -349,7 +349,12 @@  COMPAT_SYSCALL_DEFINE3(statfs64, const char __user *, pathname, compat_size_t, s
 	return error;
 }
 
-COMPAT_SYSCALL_DEFINE3(fstatfs64, unsigned int, fd, compat_size_t, sz, struct compat_statfs64 __user *, buf)
+COMPAT_SYSCALL_DEFINE3(statfs64, const char __user *, pathname, compat_size_t, sz, struct compat_statfs64 __user *, buf)
+{
+	return kcompat_sys_statfs64(pathname, sz, buf);
+}
+
+int kcompat_sys_fstatfs64(unsigned int fd, compat_size_t sz, struct compat_statfs64 __user * buf)
 {
 	struct kstatfs tmp;
 	int error;
@@ -363,6 +368,11 @@  COMPAT_SYSCALL_DEFINE3(fstatfs64, unsigned int, fd, compat_size_t, sz, struct co
 	return error;
 }
 
+COMPAT_SYSCALL_DEFINE3(fstatfs64, unsigned int, fd, compat_size_t, sz, struct compat_statfs64 __user *, buf)
+{
+	return kcompat_sys_fstatfs64(fd, sz, buf);
+}
+
 /*
  * This is a copy of sys_ustat, just dealing with a structure layout.
  * Given how simple this syscall is that apporach is more maintainable
diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h
index 6723ea51ec99..e0bf3e4bb897 100644
--- a/include/linux/syscalls.h
+++ b/include/linux/syscalls.h
@@ -59,6 +59,7 @@  struct tms;
 struct utimbuf;
 struct mq_attr;
 struct compat_stat;
+struct compat_statfs64;
 struct compat_timeval;
 struct robust_list_head;
 struct getcpu_cache;
@@ -1150,6 +1151,13 @@  unsigned long ksys_mmap_pgoff(unsigned long addr, unsigned long len,
 ssize_t ksys_readahead(int fd, loff_t offset, size_t count);
 unsigned int ksys_personality(unsigned int personality);
 
+#ifdef CONFIG_COMPAT
+int kcompat_sys_statfs64(const char __user * pathname, compat_size_t sz,
+		     struct compat_statfs64 __user * buf);
+int kcompat_sys_fstatfs64(unsigned int fd, compat_size_t sz,
+			  struct compat_statfs64 __user * buf);
+#endif
+
 /*
  * The following kernel syscall equivalents are just wrappers to fs-internal
  * functions. Therefore, provide stubs to be inlined at the callsites.