kexec: New syscall kexec_file_load() declaration

Started by Vivek Goyal on Jun 26, 2014 · 5 messages from 3 authors · Last reply Jun 27, 2014

Subsystems (4)

Show 1 more

Maintainers (10)

Show 6 more
STALE4518d

open the first message on its own page

Message details and related content
This is the new syscall kexec_file_load() declaration/interface. I have
reserved the syscall number only for x86_64 so far. Other architectures
(including i386) can reserve syscall number when they enable the support
for this new syscall.

Signed-off-by: Vivek Goyal <redacted>
CC: <redacted>
---
 arch/x86/syscalls/syscall_64.tbl | 1 +
 include/linux/syscalls.h         | 4 ++++
 kernel/kexec.c                   | 7 +++++++
 kernel/sys_ni.c                  | 1 +
 4 files changed, 13 insertions(+)
diff --git a/arch/x86/syscalls/syscall_64.tbl b/arch/x86/syscalls/syscall_64.tbl
index ec255a1..6d35459 100644
--- a/arch/x86/syscalls/syscall_64.tbl
+++ b/arch/x86/syscalls/syscall_64.tbl
@@ -323,6 +323,7 @@
 314	common	sched_setattr		sys_sched_setattr
 315	common	sched_getattr		sys_sched_getattr
 316	common	renameat2		sys_renameat2
+317	common	kexec_file_load		sys_kexec_file_load
 
 #
 # x32-specific system call numbers start at 512 to avoid cache impact
diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h
index b0881a0..9e98193 100644
--- a/include/linux/syscalls.h
+++ b/include/linux/syscalls.h
@@ -317,6 +317,10 @@ asmlinkage long sys_restart_syscall(void);
 asmlinkage long sys_kexec_load(unsigned long entry, unsigned long nr_segments,
 				struct kexec_segment __user *segments,
 				unsigned long flags);
+asmlinkage long sys_kexec_file_load(int kernel_fd, int initrd_fd,
+				    unsigned long cmdline_len,
+				    const char __user *cmdline_ptr,
+				    unsigned long flags);
 
 asmlinkage long sys_exit(int error_code);
 asmlinkage long sys_exit_group(int error_code);
diff --git a/kernel/kexec.c b/kernel/kexec.c
index c69ce00..bdda717 100644
--- a/kernel/kexec.c
+++ b/kernel/kexec.c
@@ -1057,6 +1057,13 @@ COMPAT_SYSCALL_DEFINE4(kexec_load, compat_ulong_t, entry,
 }
 #endif
 
+SYSCALL_DEFINE5(kexec_file_load, int, kernel_fd, int, initrd_fd,
+		unsigned long, cmdline_len, const char __user *, cmdline_ptr,
+		unsigned long, flags)
+{
+	return -ENOSYS;
+}
+
 void crash_kexec(struct pt_regs *regs)
 {
 	/* Take the kexec_mutex here to prevent sys_kexec_load
diff --git a/kernel/sys_ni.c b/kernel/sys_ni.c
index 36441b5..51ea89f 100644
--- a/kernel/sys_ni.c
+++ b/kernel/sys_ni.c
@@ -25,6 +25,7 @@ cond_syscall(sys_swapon);
 cond_syscall(sys_swapoff);
 cond_syscall(sys_kexec_load);
 cond_syscall(compat_sys_kexec_load);
+cond_syscall(sys_kexec_file_load);
 cond_syscall(sys_init_module);
 cond_syscall(sys_finit_module);
 cond_syscall(sys_delete_module);
-- 
1.9.0
Message details and related content
On Thu, Jun 26, 2014 at 04:33:37PM -0400, Vivek Goyal wrote:
This is the new syscall kexec_file_load() declaration/interface. I have
reserved the syscall number only for x86_64 so far. Other architectures
(including i386) can reserve syscall number when they enable the support
for this new syscall.

Signed-off-by: Vivek Goyal <redacted>
CC: <redacted>
Hi Michael,

As per feedback last time, I enhanced the existing man page to include
details of this new syscall. Here is the patch.

Thanks
Vivek


Subject: kexec_file_load() syscall man page

We already have man page for kexec_load() syscall. This patch adds details
of kexec_file_load() to same man page.

Signed-off-by: Vivek Goyal <redacted>
---
 man2/kexec_file_load.2 |    1 
 man2/kexec_load.2      |   55 +++++++++++++++++++++++++++++++++++++++++++------
 2 files changed, 50 insertions(+), 6 deletions(-)

Index: man-pages/man2/kexec_file_load.2
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ man-pages/man2/kexec_file_load.2	2014-06-25 17:39:12.056441803 -0400
@@ -0,0 +1 @@
+.so man2/kexec_load.2
Index: man-pages/man2/kexec_load.2
===================================================================
--- man-pages.orig/man2/kexec_load.2	2014-06-25 17:36:09.237453355 -0400
+++ man-pages/man2/kexec_load.2	2014-06-26 11:11:49.599810213 -0400
@@ -25,17 +25,26 @@
 .\"
 .TH KEXEC_LOAD 2 2012-07-13 "Linux" "Linux Programmer's Manual"
 .SH NAME
-kexec_load \- load a new kernel for later execution
+kexec_load, kexec_file_load \- load a new kernel for later execution
 .SH SYNOPSIS
 .B #include <linux/kexec.h>
 .br
+
 .BI "long kexec_load(unsigned long " entry ", unsigned long " nr_segments ","
 .br
 .BI "                struct kexec_segment *" segments \
 ", unsigned long " flags ");"
+.br
+
+.BI "int kexec_file_load(int " kernel_fd ", int " initrd_fd ","
+.br
+.BI "                    unsigned long " cmdline_len  \
+", const char *" cmdline ","
+.br
+.BI "                    unsigned long " flags ");"
 
 .IR Note :
-There is no glibc wrapper for this system call; see NOTES.
+There are no glibc wrappers for these system calls; see NOTES.
 .SH DESCRIPTION
 The
 .BR kexec_load ()
@@ -111,11 +120,42 @@ struct kexec_segment {
 The kernel image defined by
 .I segments
 is copied from the calling process into previously reserved memory.
+.SS kexec_file_load()
+The
+.BR kexec_file_load ()
+system call is similar to
+.BR kexec_load(),
+but it takes a different set of arguments. It reads kernel to be loaded from
+file descriptor
+.IR kernel_fd
+and initrd to be loaded from file descriptor
+.IR initrd_fd .
+It also takes length of kernel command line in
+.IR cmdline_len
+and pointer to command line in
+.IR cmdline .
+
+The
+.IR flags
+argument is a mask which allows control over system call operation. The
+following values can be specified in
+.IR flags
+
+.TP
+.BR KEXEC_FILE_UNLOAD
+Unload currently loaded kernel.
+.TP
+.BR KEXEC_FILE_ON_CRASH
+Load kernel in memory region reserved for crash kernel. This kernel is
+booted into if currently running kernel crashes.
+.TP
+.BR KEXEC_FILE_NO_INITRAMFS
+Loading initrd/initramfs is optional. Specify this flag if no initramfs
+is being loaded. If this flag is set, kernel will ignore the value passed
+in
+.IR initrd_fd
 .SH RETURN VALUE
-On success,
-.BR kexec_load ()
-returns 0.
-On error, \-1 is returned and
+On success, these system calls returns 0.  On error, \-1 is returned and
 .I errno
 is set to indicate the error.
 .SH ERRORS
@@ -135,6 +175,9 @@ is too large
 The caller does not have the
 .BR CAP_SYS_BOOT
 capability.
+.TP
+.B ENOEXEC
+kernel_fd does not refer to an open file. Or kernel can't load this file.
 .SH VERSIONS
 The
 .BR kexec_load ()
Message details and related content
On Thu, Jun 26, 2014 at 1:43 PM, Vivek Goyal [off-list ref] wrote:
quoted hunk
On Thu, Jun 26, 2014 at 04:33:37PM -0400, Vivek Goyal wrote:
quoted
This is the new syscall kexec_file_load() declaration/interface. I have
reserved the syscall number only for x86_64 so far. Other architectures
(including i386) can reserve syscall number when they enable the support
for this new syscall.

Signed-off-by: Vivek Goyal <vgoyal@redhat.com>
CC: <redacted>

+.BR KEXEC_FILE_NO_INITRAMFS
+Loading initrd/initramfs is optional. Specify this flag if no initramfs
+is being loaded. If this flag is set, kernel will ignore the value passed
+in
This seems pointless.  Why not just pass -1 for initrd_fd to indicate
that no initrd is needed?

--Andy
Message details and related content
On Thu, Jun 26, 2014 at 02:03:17PM -0700, Andy Lutomirski wrote:
On Thu, Jun 26, 2014 at 1:43 PM, Vivek Goyal [off-list ref] wrote:
quoted
On Thu, Jun 26, 2014 at 04:33:37PM -0400, Vivek Goyal wrote:
quoted
This is the new syscall kexec_file_load() declaration/interface. I have
reserved the syscall number only for x86_64 so far. Other architectures
(including i386) can reserve syscall number when they enable the support
for this new syscall.

Signed-off-by: Vivek Goyal <redacted>
CC: <redacted>

+.BR KEXEC_FILE_NO_INITRAMFS
+Loading initrd/initramfs is optional. Specify this flag if no initramfs
+is being loaded. If this flag is set, kernel will ignore the value passed
+in
This seems pointless.  Why not just pass -1 for initrd_fd to indicate
that no initrd is needed?
I was not sure whether negative fd should be treated as error and system
call should fail or it should be treated as user does not want to load
initrd and system call succeeds.

I was concerned about the cases where application does an fd = open(),
operation fails and fd contains -1. Caller does not check fd and
passed it to kexec system call.

I thought that in such cases we should error out saying initrd fd is
not valid. Instead of continuing and loading kernel without initrd. A
user might be surprised.

This is little defensive programming. But I am open to change it if
the perception is that above is not a valid concern.

Thanks
Vivek
Message details and related content
On Fri, Jun 27, 2014 at 1:50 PM, Vivek Goyal [off-list ref] wrote:
On Thu, Jun 26, 2014 at 02:03:17PM -0700, Andy Lutomirski wrote:
quoted
On Thu, Jun 26, 2014 at 1:43 PM, Vivek Goyal [off-list ref] wrote:
quoted
On Thu, Jun 26, 2014 at 04:33:37PM -0400, Vivek Goyal wrote:
quoted
This is the new syscall kexec_file_load() declaration/interface. I have
reserved the syscall number only for x86_64 so far. Other architectures
(including i386) can reserve syscall number when they enable the support
for this new syscall.

Signed-off-by: Vivek Goyal <redacted>
CC: <redacted>

+.BR KEXEC_FILE_NO_INITRAMFS
+Loading initrd/initramfs is optional. Specify this flag if no initramfs
+is being loaded. If this flag is set, kernel will ignore the value passed
+in
This seems pointless.  Why not just pass -1 for initrd_fd to indicate
that no initrd is needed?
I was not sure whether negative fd should be treated as error and system
call should fail or it should be treated as user does not want to load
initrd and system call succeeds.

I was concerned about the cases where application does an fd = open(),
operation fails and fd contains -1. Caller does not check fd and
passed it to kexec system call.

I thought that in such cases we should error out saying initrd fd is
not valid. Instead of continuing and loading kernel without initrd. A
user might be surprised.

This is little defensive programming. But I am open to change it if
the perception is that above is not a valid concern.
Your logic for using a flag rather than -1 sounds reasonable to me.
The nearest precedent I can think of offhand is mmap(), which also
takes a file descriptor argument for some use cases. However, if
MAP_ANONYMOUS is specified, no file descriptor ir required. The
treatment of the 'fd' argument in that case depends on the system. On
Linux, the fd argument is just ignored. However, many other systems
require 'fd' to be negative when MAP_ANONYMOUS is specified; one
presumes as a kind of safety check.

Cheers,

Michael


-- 
Michael Kerrisk
Linux man-pages maintainer; http://www.kernel.org/doc/man-pages/
Linux/UNIX System Programming Training: http://man7.org/training/
Keyboard shortcuts
hback out one level
jnext message in thread / next series-diff position
kprevious message in thread / previous series-diff position
ldrill in
Escclose help / fold thread tree
?toggle this help