Commit 03d476ec authored by Theo de Raadt's avatar Theo de Raadt
Browse files

Rather than re-opening the driftfile to write, keep it open; rewinding

and coping with error conditions... that lets us avoid a pledge "wpath".

Putting it all together, this lets the master ntpd pledge "stdio rpath
inet settime proc id".  It works like this: "rpath" to load the
certificates, "proc" to create constraint processes, "id" to chroot
and lock the constraint processes into a jail, then "inet" to open a
https session.  "settime" is used by the master to manage the system
time when the ntp-speaking engine instructs the master.

with help from naddy
parent 95177df3
/* $OpenBSD: ntpd.c,v 1.97 2015/10/12 06:50:08 reyk Exp $ */
/* $OpenBSD: ntpd.c,v 1.98 2015/10/23 16:39:13 deraadt Exp $ */
/*
* Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org>
......@@ -32,6 +32,7 @@
#include <string.h>
#include <time.h>
#include <unistd.h>
#include <fcntl.h>
#include <err.h>
#include "ntpd.h"
......@@ -215,6 +216,13 @@ main(int argc, char *argv[])
constraint_cnt = 0;
/*
* Constraint processes are forked with certificates in memory,
* then privdrop into chroot before speaking to the outside world.
*/
if (pledge("stdio rpath inet settime proc id", NULL) == -1)
err(1, "pledge");
while (quit == 0) {
new_cnt = PFD_MAX + constraint_cnt;
if (new_cnt > pfd_elms) {
......@@ -491,61 +499,59 @@ ntpd_settime(double d)
log_info("set local clock to %s (offset %fs)", buf, d);
}
static FILE *freqfp;
void
readfreq(void)
{
FILE *fp;
int64_t current;
int fd;
double d;
fp = fopen(DRIFTFILE, "r");
if (fp == NULL) {
/* if the drift file has been deleted by the user, reset */
fd = open(DRIFTFILE, O_RDWR);
if (fd == -1) {
log_warnx("creating new %s", DRIFTFILE);
current = 0;
if (adjfreq(&current, NULL) == -1)
log_warn("adjfreq reset failed");
freqfp = fopen(DRIFTFILE, "w");
return;
}
freqfp = fdopen(fd, "r+");
/* if we're adjusting frequency already, don't override */
if (adjfreq(NULL, &current) == -1)
log_warn("adjfreq failed");
else if (current == 0) {
if (fscanf(fp, "%lf", &d) == 1) {
else if (current == 0 && freqfp) {
if (fscanf(freqfp, "%lf", &d) == 1) {
d /= 1e6; /* scale from ppm */
ntpd_adjfreq(d, 0);
} else
log_warnx("can't read %s", DRIFTFILE);
log_warnx("%s is empty", DRIFTFILE);
}
fclose(fp);
}
int
writefreq(double d)
{
int r;
FILE *fp;
static int warnonce = 1;
fp = fopen(DRIFTFILE, "w");
if (fp == NULL) {
if (warnonce) {
log_warn("can't open %s", DRIFTFILE);
warnonce = 0;
}
if (freqfp == NULL)
return 0;
}
fprintf(fp, "%.3f\n", d * 1e6); /* scale to ppm */
r = ferror(fp);
if (fclose(fp) != 0 || r != 0) {
rewind(freqfp);
fprintf(freqfp, "%.3f\n", d * 1e6); /* scale to ppm */
r = ferror(freqfp);
if (r != 0) {
if (warnonce) {
log_warnx("can't write %s", DRIFTFILE);
warnonce = 0;
}
unlink(DRIFTFILE);
return 0;
}
ftruncate(fileno(freqfp), ftello(freqfp));
fsync(fileno(freqfp));
return 1;
}
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment