Add halt(8), poweroff(8), and reboot(8).
This commit is contained in:
parent
f2d50bbf9c
commit
71edc766e7
12
init/init.8
12
init/init.8
|
@ -266,11 +266,14 @@ own log.
|
||||||
.Sh ASYNCHRONOUS EVENTS
|
.Sh ASYNCHRONOUS EVENTS
|
||||||
.Bl -tag -width "SIGUSR1"
|
.Bl -tag -width "SIGUSR1"
|
||||||
.It Dv SIGTERM
|
.It Dv SIGTERM
|
||||||
Request system poweroff.
|
Request system poweroff, normally sent by
|
||||||
|
.Xr poweroff 8 .
|
||||||
.It Dv SIGINT
|
.It Dv SIGINT
|
||||||
Request system reboot.
|
Request system reboot, normally sent by
|
||||||
|
.Xr reboot 8 .
|
||||||
.It Dv SIGQUIT
|
.It Dv SIGQUIT
|
||||||
Request system halt.
|
Request system halt, normally sent by
|
||||||
|
.Xr halt 8 .
|
||||||
.El
|
.El
|
||||||
.Sh EXIT STATUS
|
.Sh EXIT STATUS
|
||||||
.Nm
|
.Nm
|
||||||
|
@ -292,7 +295,10 @@ exits with the same exit status as its target session if it terminates normally.
|
||||||
.Xr daemon 7 ,
|
.Xr daemon 7 ,
|
||||||
.Xr initrd 7 ,
|
.Xr initrd 7 ,
|
||||||
.Xr kernel 7 ,
|
.Xr kernel 7 ,
|
||||||
|
.Xr halt 8 ,
|
||||||
.Xr login 8 ,
|
.Xr login 8 ,
|
||||||
|
.Xr poweroff 8 ,
|
||||||
|
.Xr reboot 8 ,
|
||||||
.Xr sysmerge 8 ,
|
.Xr sysmerge 8 ,
|
||||||
.Xr update-initrd 8
|
.Xr update-initrd 8
|
||||||
.Sh SECURITY CONSIDERATIONS
|
.Sh SECURITY CONSIDERATIONS
|
||||||
|
|
|
@ -636,6 +636,8 @@ static void keyboard_event(struct glogin* state, uint32_t codepoint)
|
||||||
exit(0);
|
exit(0);
|
||||||
if ( !strcmp(textbox_username.text, "reboot") )
|
if ( !strcmp(textbox_username.text, "reboot") )
|
||||||
exit(1);
|
exit(1);
|
||||||
|
if ( !strcmp(textbox_username.text, "halt") )
|
||||||
|
exit(2);
|
||||||
state->stage = STAGE_PASSWORD;
|
state->stage = STAGE_PASSWORD;
|
||||||
textbox_reset(&textbox_password);
|
textbox_reset(&textbox_password);
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -44,6 +44,8 @@ alias for poweroff
|
||||||
exit asking for powering off the computer
|
exit asking for powering off the computer
|
||||||
.It reboot
|
.It reboot
|
||||||
exit asking for rebooting the computer
|
exit asking for rebooting the computer
|
||||||
|
.It halt
|
||||||
|
exit asking for halting the computer
|
||||||
.El
|
.El
|
||||||
.Sh SECURITY
|
.Sh SECURITY
|
||||||
There is currently no method to confirm the login screen is in fact real other
|
There is currently no method to confirm the login screen is in fact real other
|
||||||
|
|
|
@ -349,6 +349,8 @@ int textual(void)
|
||||||
exit(0);
|
exit(0);
|
||||||
if ( !strcmp(username, "reboot") )
|
if ( !strcmp(username, "reboot") )
|
||||||
exit(1);
|
exit(1);
|
||||||
|
if ( !strcmp(username, "halt") )
|
||||||
|
exit(2);
|
||||||
|
|
||||||
if ( settermmode(0, pw_termmode) < 0 )
|
if ( settermmode(0, pw_termmode) < 0 )
|
||||||
err(2, "settermmode");
|
err(2, "settermmode");
|
||||||
|
|
|
@ -357,8 +357,9 @@ if applicable restore boot priorities in your firmware.
|
||||||
If you did not accept the bootloader, you will need to manually configure a
|
If you did not accept the bootloader, you will need to manually configure a
|
||||||
bootloader to boot the new operating system.
|
bootloader to boot the new operating system.
|
||||||
.Pp
|
.Pp
|
||||||
You will be given the choice between powering off the system, rebooting it, or
|
You will be given the choice between powering off the system, rebooting it,
|
||||||
directly booting the new system.
|
halting it, or directly booting the new system.
|
||||||
|
.Pp
|
||||||
The last option will directly boot the new system in a chroot while the live
|
The last option will directly boot the new system in a chroot while the live
|
||||||
environment remains in the background.
|
environment remains in the background.
|
||||||
If you invoked
|
If you invoked
|
||||||
|
@ -369,10 +370,17 @@ Otherwise the computer will power off when the chroot environment terminates.
|
||||||
Upon boot of the new system it will be configured in multi-user mode and you
|
Upon boot of the new system it will be configured in multi-user mode and you
|
||||||
will be presented with a login screen.
|
will be presented with a login screen.
|
||||||
Authenticate as one of the local users and you will be given a shell.
|
Authenticate as one of the local users and you will be given a shell.
|
||||||
|
.Pp
|
||||||
To power off the computer login as user
|
To power off the computer login as user
|
||||||
.Sy poweroff
|
.Sy poweroff
|
||||||
and to reboot the computer login as user
|
or run
|
||||||
.Sy reboot .
|
.Xr poweroff 8
|
||||||
|
after logging in.
|
||||||
|
To reboot the computer login as user
|
||||||
|
.Sy reboot
|
||||||
|
or run
|
||||||
|
.Xr reboot 8
|
||||||
|
after logging in.
|
||||||
.Pp
|
.Pp
|
||||||
The
|
The
|
||||||
.Xr user-guide 7
|
.Xr user-guide 7
|
||||||
|
|
|
@ -24,17 +24,16 @@ This is
|
||||||
if the system is booted in multi-user mode.
|
if the system is booted in multi-user mode.
|
||||||
This is a root shell if booted in single-user mode.
|
This is a root shell if booted in single-user mode.
|
||||||
.Pp
|
.Pp
|
||||||
To power off from the login screen, login as user
|
To power off the computer login as user
|
||||||
.Sy poweroff .
|
.Sy poweroff
|
||||||
To reboot, login as user
|
or run
|
||||||
.Sy reboot .
|
.Xr poweroff 8
|
||||||
.Pp
|
after logging in.
|
||||||
To power off from a single-user boot root shell, run
|
To reboot the computer login as user
|
||||||
.Sy exit 0
|
.Sy reboot
|
||||||
in the shell.
|
or run
|
||||||
To reboot, run
|
.Xr reboot 8
|
||||||
.Sy exit 1
|
after logging in.
|
||||||
in the shell.
|
|
||||||
.Ss Keyboard Layout
|
.Ss Keyboard Layout
|
||||||
The kernel has a default US keyboard layout compiled into it.
|
The kernel has a default US keyboard layout compiled into it.
|
||||||
.Pp
|
.Pp
|
||||||
|
|
|
@ -828,22 +828,24 @@ int main(void)
|
||||||
while ( true )
|
while ( true )
|
||||||
{
|
{
|
||||||
prompt(input, sizeof(input),
|
prompt(input, sizeof(input),
|
||||||
"Install " BRAND_DISTRIBUTION_NAME "? (yes/no/poweroff/reboot)",
|
"Install " BRAND_DISTRIBUTION_NAME "? "
|
||||||
"yes");
|
"(yes/no/poweroff/reboot/halt)", "yes");
|
||||||
if ( !strcasecmp(input, "yes") )
|
if ( !strcasecmp(input, "yes") )
|
||||||
break;
|
break;
|
||||||
else if ( !strcasecmp(input, "no") )
|
else if ( !strcasecmp(input, "no") )
|
||||||
{
|
{
|
||||||
text("Answer '!' to get a shell. Type !man to view the "
|
text("Answer '!' to get a shell. Type !man to view the "
|
||||||
"installation(7) manual page.\n");
|
"installation(7) manual page.\n");
|
||||||
text("Alternatively, you can answer 'poweroff' or 'reboot' to "
|
text("Alternatively, you can answer 'poweroff', 'reboot', or "
|
||||||
"cancel the installation.\n");
|
"'halt' to cancel the installation.\n");
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
else if ( !strcasecmp(input, "poweroff") )
|
else if ( !strcasecmp(input, "poweroff") )
|
||||||
exit(0);
|
exit(0);
|
||||||
else if ( !strcasecmp(input, "reboot") )
|
else if ( !strcasecmp(input, "reboot") )
|
||||||
exit(1);
|
exit(1);
|
||||||
|
else if ( !strcasecmp(input, "halt") )
|
||||||
|
exit(2);
|
||||||
else
|
else
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -1133,17 +1135,21 @@ int main(void)
|
||||||
|
|
||||||
text("Upon boot, you'll be greeted with a login screen. Enter your "
|
text("Upon boot, you'll be greeted with a login screen. Enter your "
|
||||||
"credentials to get a command line. Login as user 'poweroff' as "
|
"credentials to get a command line. Login as user 'poweroff' as "
|
||||||
"described in login(8) to power off the machine. After logging in, "
|
"described in login(8) to power off the machine or run poweroff(8). "
|
||||||
"type 'man user-guide' to view the introductory documentation.\n");
|
"After logging in, type 'man user-guide' to view the introductory "
|
||||||
|
"documentation.\n");
|
||||||
text("\n");
|
text("\n");
|
||||||
|
|
||||||
while ( true )
|
while ( true )
|
||||||
{
|
{
|
||||||
prompt(input, sizeof(input), "What now? (poweroff/reboot/boot)", "boot");
|
prompt(input, sizeof(input),
|
||||||
|
"What now? (poweroff/reboot/halt/boot)", "boot");
|
||||||
if ( !strcasecmp(input, "poweroff") )
|
if ( !strcasecmp(input, "poweroff") )
|
||||||
exit(0);
|
exit(0);
|
||||||
if ( !strcasecmp(input, "reboot") )
|
if ( !strcasecmp(input, "reboot") )
|
||||||
exit(1);
|
exit(1);
|
||||||
|
if ( !strcasecmp(input, "halt") )
|
||||||
|
exit(2);
|
||||||
if ( !strcasecmp(input, "boot") )
|
if ( !strcasecmp(input, "boot") )
|
||||||
{
|
{
|
||||||
unmount_all_but_root();
|
unmount_all_but_root();
|
||||||
|
|
|
@ -775,7 +775,7 @@ int main(void)
|
||||||
while ( true )
|
while ( true )
|
||||||
{
|
{
|
||||||
promptx(input, sizeof(input),
|
promptx(input, sizeof(input),
|
||||||
"Upgrade? (yes/no/poweroff/reboot)", "yes", true);
|
"Upgrade? (yes/no/poweroff/reboot/halt)", "yes", true);
|
||||||
if ( !strcasecmp(input, "yes") )
|
if ( !strcasecmp(input, "yes") )
|
||||||
break;
|
break;
|
||||||
else if ( !strcasecmp(input, "no") )
|
else if ( !strcasecmp(input, "no") )
|
||||||
|
@ -784,14 +784,16 @@ int main(void)
|
||||||
"upgrade(7) manual page. You can edit the upgrade.conf(5) "
|
"upgrade(7) manual page. You can edit the upgrade.conf(5) "
|
||||||
"configuration file of the target system to change which "
|
"configuration file of the target system to change which "
|
||||||
"upgrade operations are performed.\n");
|
"upgrade operations are performed.\n");
|
||||||
text("Alternatively, you can answer 'poweroff' or 'reboot' to "
|
text("Alternatively, you can answer 'poweroff', 'reboot', or "
|
||||||
"cancel the upgrade.\n");
|
"'halt' or cancel the upgrade.\n");
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
else if ( !strcasecmp(input, "poweroff") )
|
else if ( !strcasecmp(input, "poweroff") )
|
||||||
exit(0);
|
exit(0);
|
||||||
else if ( !strcasecmp(input, "reboot") )
|
else if ( !strcasecmp(input, "reboot") )
|
||||||
exit(1);
|
exit(1);
|
||||||
|
else if ( !strcasecmp(input, "halt") )
|
||||||
|
exit(2);
|
||||||
else if ( !strcasecmp(input, "!") )
|
else if ( !strcasecmp(input, "!") )
|
||||||
break;
|
break;
|
||||||
else
|
else
|
||||||
|
@ -928,10 +930,13 @@ int main(void)
|
||||||
|
|
||||||
while ( true )
|
while ( true )
|
||||||
{
|
{
|
||||||
prompt(input, sizeof(input), "What now? (poweroff/reboot)", "reboot");
|
prompt(input, sizeof(input),
|
||||||
|
"What now? (poweroff/reboot/halt)", "reboot");
|
||||||
if ( !strcasecmp(input, "poweroff") )
|
if ( !strcasecmp(input, "poweroff") )
|
||||||
return 0;
|
return 0;
|
||||||
if ( !strcasecmp(input, "reboot") )
|
if ( !strcasecmp(input, "reboot") )
|
||||||
return 1;
|
return 1;
|
||||||
|
if ( !strcasecmp(input, "halt") )
|
||||||
|
return 2;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,9 +20,10 @@ env
|
||||||
expr
|
expr
|
||||||
false
|
false
|
||||||
find
|
find
|
||||||
|
halt
|
||||||
head
|
head
|
||||||
id
|
|
||||||
help
|
help
|
||||||
|
id
|
||||||
kernelinfo
|
kernelinfo
|
||||||
kill
|
kill
|
||||||
ln
|
ln
|
||||||
|
@ -35,11 +36,13 @@ mv
|
||||||
nl
|
nl
|
||||||
pager
|
pager
|
||||||
passwd
|
passwd
|
||||||
|
poweroff
|
||||||
ps
|
ps
|
||||||
pstree
|
pstree
|
||||||
pwd
|
pwd
|
||||||
readlink
|
readlink
|
||||||
realpath
|
realpath
|
||||||
|
reboot
|
||||||
rm
|
rm
|
||||||
rmdir
|
rmdir
|
||||||
sleep
|
sleep
|
||||||
|
|
|
@ -31,6 +31,7 @@ env \
|
||||||
expr \
|
expr \
|
||||||
false \
|
false \
|
||||||
find \
|
find \
|
||||||
|
halt \
|
||||||
head \
|
head \
|
||||||
help \
|
help \
|
||||||
id \
|
id \
|
||||||
|
@ -71,6 +72,8 @@ uptime \
|
||||||
wc \
|
wc \
|
||||||
which \
|
which \
|
||||||
yes \
|
yes \
|
||||||
|
poweroff \
|
||||||
|
reboot \
|
||||||
|
|
||||||
BINARIES=\
|
BINARIES=\
|
||||||
$(BINARIES_EXCEPT_INSTALL) \
|
$(BINARIES_EXCEPT_INSTALL) \
|
||||||
|
@ -94,6 +97,9 @@ unmount \
|
||||||
|
|
||||||
MANPAGES8=\
|
MANPAGES8=\
|
||||||
chroot.8 \
|
chroot.8 \
|
||||||
|
halt.8 \
|
||||||
|
poweroff.8 \
|
||||||
|
reboot.8 \
|
||||||
unmount.8 \
|
unmount.8 \
|
||||||
|
|
||||||
all: $(BINARIES) $(SBINS)
|
all: $(BINARIES) $(SBINS)
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 2013, 2015, 2016 Jonas 'Sortie' Termansen.
|
* Copyright (c) 2013, 2015, 2016, 2021 Jonas 'Sortie' Termansen.
|
||||||
* Copyright (c) 2021 Juhani 'nortti' Krekelä.
|
* Copyright (c) 2021 Juhani 'nortti' Krekelä.
|
||||||
*
|
*
|
||||||
* Permission to use, copy, modify, and distribute this software for any
|
* Permission to use, copy, modify, and distribute this software for any
|
||||||
|
@ -27,49 +27,11 @@
|
||||||
|
|
||||||
#define ARRAY_LENGTH(array) (sizeof(array) / sizeof((array)[0]))
|
#define ARRAY_LENGTH(array) (sizeof(array) / sizeof((array)[0]))
|
||||||
|
|
||||||
static const char* tty_name(void)
|
|
||||||
{
|
|
||||||
int tty_fd = open("/dev/tty", O_RDONLY);
|
|
||||||
const char* result = NULL;
|
|
||||||
if ( 0 <= tty_fd )
|
|
||||||
{
|
|
||||||
result = ttyname(tty_fd);
|
|
||||||
close(tty_fd);
|
|
||||||
}
|
|
||||||
return result ? result : "/dev/tty";
|
|
||||||
}
|
|
||||||
|
|
||||||
static void suggest_logout(void)
|
static void suggest_logout(void)
|
||||||
{
|
{
|
||||||
fprintf(stderr, " Exiting your shell normally to logout.\n");
|
fprintf(stderr, " Exiting your shell normally to logout.\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
static void suggest_poweroff(void)
|
|
||||||
{
|
|
||||||
if ( strcmp(tty_name(), "/dev/tty1") != 0 )
|
|
||||||
fprintf(stderr, " Powering off on /dev/tty1.\n");
|
|
||||||
else if ( getenv("LOGIN_PID") )
|
|
||||||
{
|
|
||||||
fprintf(stderr, " Exiting your shell normally to logout.\n");
|
|
||||||
fprintf(stderr, " Login as user 'poweroff' to power off computer.\n");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
fprintf(stderr, " Exiting your shell normally to poweroff.\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
static void suggest_reboot(void)
|
|
||||||
{
|
|
||||||
if ( strcmp(tty_name(), "/dev/tty1") != 0 )
|
|
||||||
fprintf(stderr, " Rebooting on /dev/tty1.\n");
|
|
||||||
else if ( getenv("LOGIN_PID") )
|
|
||||||
{
|
|
||||||
fprintf(stderr, " Exiting your shell normally to logout.\n");
|
|
||||||
fprintf(stderr, " Login as user 'reboot' to reboot computer.\n");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
fprintf(stderr, " Exiting your shell with 'exit 1' to reboot.\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
enum category
|
enum category
|
||||||
{
|
{
|
||||||
NONE,
|
NONE,
|
||||||
|
@ -79,7 +41,6 @@ enum category
|
||||||
MOUNT,
|
MOUNT,
|
||||||
PAGER,
|
PAGER,
|
||||||
POWEROFF,
|
POWEROFF,
|
||||||
REBOOT,
|
|
||||||
RW,
|
RW,
|
||||||
SHELL,
|
SHELL,
|
||||||
UNMOUNT,
|
UNMOUNT,
|
||||||
|
@ -122,12 +83,9 @@ struct command commands[] =
|
||||||
{PAGER, "more", NULL, NULL},
|
{PAGER, "more", NULL, NULL},
|
||||||
{PAGER, "pager", "system", NULL},
|
{PAGER, "pager", "system", NULL},
|
||||||
|
|
||||||
{POWEROFF, "halt", NULL, NULL},
|
{POWEROFF, "poweroff", "system", NULL},
|
||||||
{POWEROFF, "poweroff", NULL, suggest_poweroff},
|
|
||||||
{POWEROFF, "shutdown", NULL, NULL},
|
{POWEROFF, "shutdown", NULL, NULL},
|
||||||
|
|
||||||
{REBOOT, "reboot", NULL, suggest_reboot},
|
|
||||||
|
|
||||||
{RW, "dd", NULL, NULL},
|
{RW, "dd", NULL, NULL},
|
||||||
{RW, "rw", "system", NULL},
|
{RW, "rw", "system", NULL},
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,20 @@
|
||||||
|
.Dd December 13, 2021
|
||||||
|
.Dt HALT 8
|
||||||
|
.Os
|
||||||
|
.Sh NAME
|
||||||
|
.Nm halt
|
||||||
|
.Nd halt the computer
|
||||||
|
.Sh SYNOPSIS
|
||||||
|
.Nm
|
||||||
|
.Sh DESCRIPTION
|
||||||
|
.Nm
|
||||||
|
gracefully halts the computer by sending a request to the appropriate
|
||||||
|
.Xr init 8
|
||||||
|
process.
|
||||||
|
.Sh EXIT STATUS
|
||||||
|
.Nm
|
||||||
|
will exit 0 on success and non-zero otherwise.
|
||||||
|
.Sh SEE ALSO
|
||||||
|
.Xr init 8 ,
|
||||||
|
.Xr poweroff 8 ,
|
||||||
|
.Xr reboot 8
|
|
@ -0,0 +1,50 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2021, 2022 Jonas 'Sortie' Termansen.
|
||||||
|
*
|
||||||
|
* Permission to use, copy, modify, and distribute this software for any
|
||||||
|
* purpose with or without fee is hereby granted, provided that the above
|
||||||
|
* copyright notice and this permission notice appear in all copies.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||||
|
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||||
|
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||||
|
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||||
|
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||||
|
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||||
|
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
*
|
||||||
|
* halt.c
|
||||||
|
* Halts the computer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
#include <err.h>
|
||||||
|
#include <getopt.h>
|
||||||
|
#include <signal.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
int main(int argc, char* argv[])
|
||||||
|
{
|
||||||
|
int opt;
|
||||||
|
while ( (opt = getopt(argc, argv, "")) != -1 )
|
||||||
|
{
|
||||||
|
switch ( opt )
|
||||||
|
{
|
||||||
|
default: return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( optind < argc )
|
||||||
|
errx(1, "extra operand: %s", argv[optind]);
|
||||||
|
|
||||||
|
pid_t init_pid = 1;
|
||||||
|
// TODO: Use a more reliable getinit() approach that also works in sshd.
|
||||||
|
if ( getenv("INIT_PID") )
|
||||||
|
init_pid = atoll(getenv("INIT_PID"));
|
||||||
|
|
||||||
|
if ( kill(init_pid, SIGQUIT) < 0 )
|
||||||
|
err(1, "kill: %" PRIdPID, init_pid);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
|
@ -0,0 +1,20 @@
|
||||||
|
.Dd December 13, 2021
|
||||||
|
.Dt POWEROFF 8
|
||||||
|
.Os
|
||||||
|
.Sh NAME
|
||||||
|
.Nm poweroff
|
||||||
|
.Nd power off the computer
|
||||||
|
.Sh SYNOPSIS
|
||||||
|
.Nm
|
||||||
|
.Sh DESCRIPTION
|
||||||
|
.Nm
|
||||||
|
gracefully powers off the computer by sending a request to the appropriate
|
||||||
|
.Xr init 8
|
||||||
|
process.
|
||||||
|
.Sh EXIT STATUS
|
||||||
|
.Nm
|
||||||
|
will exit 0 on success and non-zero otherwise.
|
||||||
|
.Sh SEE ALSO
|
||||||
|
.Xr halt 8 ,
|
||||||
|
.Xr init 8 ,
|
||||||
|
.Xr reboot 8
|
|
@ -0,0 +1,50 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2021, 2022 Jonas 'Sortie' Termansen.
|
||||||
|
*
|
||||||
|
* Permission to use, copy, modify, and distribute this software for any
|
||||||
|
* purpose with or without fee is hereby granted, provided that the above
|
||||||
|
* copyright notice and this permission notice appear in all copies.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||||
|
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||||
|
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||||
|
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||||
|
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||||
|
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||||
|
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
*
|
||||||
|
* poweroff.c
|
||||||
|
* Powers off the computer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
#include <err.h>
|
||||||
|
#include <getopt.h>
|
||||||
|
#include <signal.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
int main(int argc, char* argv[])
|
||||||
|
{
|
||||||
|
int opt;
|
||||||
|
while ( (opt = getopt(argc, argv, "")) != -1 )
|
||||||
|
{
|
||||||
|
switch ( opt )
|
||||||
|
{
|
||||||
|
default: return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( optind < argc )
|
||||||
|
errx(1, "extra operand: %s", argv[optind]);
|
||||||
|
|
||||||
|
pid_t init_pid = 1;
|
||||||
|
// TODO: Use a more reliable getinit() approach that also works in sshd.
|
||||||
|
if ( getenv("INIT_PID") )
|
||||||
|
init_pid = atoll(getenv("INIT_PID"));
|
||||||
|
|
||||||
|
if ( kill(init_pid, SIGTERM) < 0 )
|
||||||
|
err(1, "kill: %" PRIdPID, init_pid);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
|
@ -0,0 +1,20 @@
|
||||||
|
.Dd December 13, 2021
|
||||||
|
.Dt REBOOT 8
|
||||||
|
.Os
|
||||||
|
.Sh NAME
|
||||||
|
.Nm reboot
|
||||||
|
.Nd reboot the computer
|
||||||
|
.Sh SYNOPSIS
|
||||||
|
.Nm
|
||||||
|
.Sh DESCRIPTION
|
||||||
|
.Nm
|
||||||
|
gracefully reboots the computer by sending a request to the appropriate
|
||||||
|
.Xr init 8
|
||||||
|
process.
|
||||||
|
.Sh EXIT STATUS
|
||||||
|
.Nm
|
||||||
|
will exit 0 on success and non-zero otherwise.
|
||||||
|
.Sh SEE ALSO
|
||||||
|
.Xr halt 8 ,
|
||||||
|
.Xr init 8 ,
|
||||||
|
.Xr poweroff 8
|
|
@ -0,0 +1,50 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2021, 2022 Jonas 'Sortie' Termansen.
|
||||||
|
*
|
||||||
|
* Permission to use, copy, modify, and distribute this software for any
|
||||||
|
* purpose with or without fee is hereby granted, provided that the above
|
||||||
|
* copyright notice and this permission notice appear in all copies.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||||
|
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||||
|
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||||
|
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||||
|
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||||
|
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||||
|
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
*
|
||||||
|
* reboot.c
|
||||||
|
* Reboots the computer.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
#include <err.h>
|
||||||
|
#include <getopt.h>
|
||||||
|
#include <signal.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
int main(int argc, char* argv[])
|
||||||
|
{
|
||||||
|
int opt;
|
||||||
|
while ( (opt = getopt(argc, argv, "")) != -1 )
|
||||||
|
{
|
||||||
|
switch ( opt )
|
||||||
|
{
|
||||||
|
default: return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( optind < argc )
|
||||||
|
errx(1, "extra operand: %s", argv[optind]);
|
||||||
|
|
||||||
|
pid_t init_pid = 1;
|
||||||
|
// TODO: Use a more reliable getinit() approach that also works in sshd.
|
||||||
|
if ( getenv("INIT_PID") )
|
||||||
|
init_pid = atoll(getenv("INIT_PID"));
|
||||||
|
|
||||||
|
if ( kill(init_pid, SIGINT) < 0 )
|
||||||
|
err(1, "kill: %" PRIdPID, init_pid);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
Loading…
Reference in New Issue