mirror of
https://github.com/freebsd/freebsd-src
synced 2024-09-06 09:10:28 +00:00
reboot: Don't reboot if the next kernel isn't there
reboot -k garbage won't boot garbage unless /boot/garbage/kernel is there. Refuse to reboot if it is missing, though allow -f to force it for special-use cases. This is in keeping with nextboot.sh. Sponsored by: Netflix Reviewed by: kevans, kib, markj, emaste Differential Revision: https://reviews.freebsd.org/D43802
This commit is contained in:
parent
7a3210f2ac
commit
7cb1a0e6e0
|
@ -25,7 +25,7 @@
|
|||
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
.\" SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd December 20, 2017
|
||||
.Dd February 8, 2024
|
||||
.Dt REBOOT 8
|
||||
.Os
|
||||
.Sh NAME
|
||||
|
@ -36,16 +36,16 @@
|
|||
.Nd stopping and restarting the system
|
||||
.Sh SYNOPSIS
|
||||
.Nm halt
|
||||
.Op Fl lNnpq
|
||||
.Op Fl flNnpq
|
||||
.Op Fl k Ar kernel
|
||||
.Nm
|
||||
.Op Fl cdlNnpqr
|
||||
.Op Fl cdflNnpqr
|
||||
.Op Fl k Ar kernel
|
||||
.Nm fasthalt
|
||||
.Op Fl lNnpq
|
||||
.Op Fl flNnpq
|
||||
.Op Fl k Ar kernel
|
||||
.Nm fastboot
|
||||
.Op Fl dlNnpq
|
||||
.Op Fl dflNnpq
|
||||
.Op Fl k Ar kernel
|
||||
.Sh DESCRIPTION
|
||||
The
|
||||
|
@ -83,17 +83,22 @@ This option is
|
|||
supported only when rebooting, and it has no effect unless a dump
|
||||
device has previously been specified with
|
||||
.Xr dumpon 8 .
|
||||
.It Fl k Ar kernel
|
||||
Boot the specified
|
||||
.Ar kernel
|
||||
.It Fl k Ar kname
|
||||
Boot the specified kernel
|
||||
.Ar kname
|
||||
on the next system boot.
|
||||
If the kernel boots successfully, the
|
||||
This is a one-shot option, the
|
||||
.Em default
|
||||
kernel will be booted on successive boots, this is a one-shot option.
|
||||
If the boot fails, the system will continue attempting to boot
|
||||
.Ar kernel
|
||||
until the boot process is interrupted and a valid kernel booted.
|
||||
This may change in the future.
|
||||
kernel will be booted on successive boots.
|
||||
No
|
||||
.Nm reboot
|
||||
or
|
||||
.Nm halt
|
||||
will be performed if
|
||||
.Em /boot/kname/kernel
|
||||
does not exist unless the
|
||||
.Fl f
|
||||
flag is specified.
|
||||
.It Fl l
|
||||
The halt or reboot is
|
||||
.Em not
|
||||
|
|
|
@ -32,6 +32,7 @@
|
|||
#include <sys/types.h>
|
||||
#include <sys/boottrace.h>
|
||||
#include <sys/reboot.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/sysctl.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
|
@ -59,7 +60,7 @@ main(int argc, char *argv[])
|
|||
struct utmpx utx;
|
||||
const struct passwd *pw;
|
||||
int ch, howto, i, fd, sverrno;
|
||||
bool lflag, nflag, qflag, Nflag;
|
||||
bool fflag, lflag, nflag, qflag, Nflag;
|
||||
uint64_t pageins;
|
||||
const char *user, *kernel = NULL;
|
||||
|
||||
|
@ -68,7 +69,7 @@ main(int argc, char *argv[])
|
|||
howto = RB_HALT;
|
||||
} else
|
||||
howto = 0;
|
||||
lflag = nflag = qflag = Nflag = false;
|
||||
fflag = lflag = nflag = qflag = Nflag = false;
|
||||
while ((ch = getopt(argc, argv, "cdk:lNnpqr")) != -1)
|
||||
switch(ch) {
|
||||
case 'c':
|
||||
|
@ -77,6 +78,9 @@ main(int argc, char *argv[])
|
|||
case 'd':
|
||||
howto |= RB_DUMP;
|
||||
break;
|
||||
case 'f':
|
||||
fflag = true;
|
||||
break;
|
||||
case 'k':
|
||||
kernel = optarg;
|
||||
break;
|
||||
|
@ -130,6 +134,19 @@ main(int argc, char *argv[])
|
|||
}
|
||||
|
||||
if (kernel != NULL) {
|
||||
if (!fflag) {
|
||||
char *k;
|
||||
struct stat sb;
|
||||
|
||||
asprintf(&k, "/boot/%s/kernel", kernel);
|
||||
if (k == NULL)
|
||||
errx(1, "No memory to check %s", kernel);
|
||||
if (stat(k, &sb) != 0)
|
||||
err(1, "stat %s", k);
|
||||
if (!S_ISREG(sb.st_mode))
|
||||
errx(1, "%s is not a file", k);
|
||||
free(k);
|
||||
}
|
||||
fd = open("/boot/nextboot.conf", O_WRONLY | O_CREAT | O_TRUNC,
|
||||
0444);
|
||||
if (fd > -1) {
|
||||
|
|
Loading…
Reference in a new issue