[klibc] [PATCH] Add support for reboot syscall argument

Alfonso Sánchez-Beato alfonso.sanchez-beato at canonical.com
Mon May 22 03:24:46 PDT 2017


Add support to the reboot command so an argument for the 4th parameter
of the syscall can be passed around.
---
 usr/include/sys/reboot.h |  4 ++--
 usr/klibc/reboot.c       |  6 +++---
 usr/utils/halt.c         | 36 ++++++++++++++++++++++--------------
 3 files changed, 27 insertions(+), 19 deletions(-)

diff --git a/usr/include/sys/reboot.h b/usr/include/sys/reboot.h
index 3337d27..b46a1c5 100644
--- a/usr/include/sys/reboot.h
+++ b/usr/include/sys/reboot.h
@@ -16,8 +16,8 @@
 #define RB_DISABLE_CAD	LINUX_REBOOT_CMD_CAD_OFF
 #define RB_POWER_OFF	LINUX_REBOOT_CMD_POWER_OFF
 
-/* glibc-ish one-argument version */
-__extern int reboot(int);
+/* two-arguments version of reboot */
+__extern int reboot(int, void *);
 
 /* Native four-argument system call */
 __extern int __reboot(int, int, int, void *);
diff --git a/usr/klibc/reboot.c b/usr/klibc/reboot.c
index 5795dc3..5aab039 100644
--- a/usr/klibc/reboot.c
+++ b/usr/klibc/reboot.c
@@ -6,10 +6,10 @@
 #include <sys/reboot.h>
 #include <sys/syscall.h>
 
-/* This provides the one-argument glibc-ish version of reboot.
+/* This provides two-argument reboot function (glibc flag plus reboot argument).
    The full four-argument system call is available as __reboot(). */
 
-int reboot(int flag)
+int reboot(int flag, void *arg)
 {
-	return __reboot(LINUX_REBOOT_MAGIC1, LINUX_REBOOT_MAGIC2, flag, NULL);
+	return __reboot(LINUX_REBOOT_MAGIC1, LINUX_REBOOT_MAGIC2, flag, arg);
 }
diff --git a/usr/utils/halt.c b/usr/utils/halt.c
index eed0a46..c15b42a 100644
--- a/usr/utils/halt.c
+++ b/usr/utils/halt.c
@@ -6,7 +6,7 @@
 
 static __noreturn usage(void)
 {
-	static char mesg[] = "Usage: {halt|reboot|poweroff} [-n]\n";
+	static char mesg[] = "Usage: {halt|reboot|poweroff} [-n] [reboot-arg]\n";
 	write(2, mesg, sizeof(mesg) - 1);
 	exit(1);
 }
@@ -16,6 +16,7 @@ int main(int argc, char *argv[])
 	int cmd = 0; /* initalize to shut gcc up */
 	int do_sync = 1;
 	char *ptr, *ptr2;
+	char *reboot_arg = NULL;
 
 	/* Which action (program name)? */
 	ptr2 = ptr = argv[0];
@@ -32,23 +33,30 @@ int main(int argc, char *argv[])
 		usage();
 
 	/* Walk options */
-	while (*++argv && **argv == '-')
-		switch (*++*argv) {
-		case 'f':
-			break; /* -f assumed */
-		case 'n':
-			do_sync = 0;
-			break;
-		default:
-			usage();
+	while (*++argv)
+		if (**argv == '-') {
+			switch (*++*argv) {
+			case 'f':
+				break; /* -f assumed */
+			case 'n':
+				do_sync = 0;
+				break;
+			default:
+				usage();
+			}
+		} else if (cmd == LINUX_REBOOT_CMD_RESTART) {
+			if (reboot_arg)
+				usage();
+			reboot_arg = *argv;
+			cmd = LINUX_REBOOT_CMD_RESTART2;
+		} else {
+			usage(); /* args, not reboot == error */
 		}
-	if (*argv)
-		usage(); /* any args == error */
 
 	if (do_sync)
 		sync();
-	reboot(LINUX_REBOOT_CMD_CAD_OFF); /* Enable CTRL+ALT+DEL */
-	if (!reboot(cmd)) {
+	reboot(LINUX_REBOOT_CMD_CAD_OFF, NULL); /* Enable CTRL+ALT+DEL */
+	if (!reboot(cmd, reboot_arg)) {
 		/* Success. Currently, CMD_HALT returns, so stop the world */
 		/* kill(-1, SIGSTOP); */
 		kill(getpid(), SIGSTOP);
-- 
2.9.3



More information about the klibc mailing list