Properly patch up dirname()/basename() calls to not clobber ent->log.
It turns out that we had a couple of more calls to dirname()/basename() in newsyslog(8) that assume the input isn't clobbered. This is bad, because it apparently breaks log rotation now that the new dirname() implementation has been merged. Fix this by first copying the input and then calling dirname()/basename(). While there, improve the naming of variables in this function a bit. Reported by: Ryan Steinmetz, gjb Reviewed by: bdrewery, allanjude Differential Revision: https://reviews.freebsd.org/D7838
This commit is contained in:
parent
01decb509d
commit
23e591f485
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=305651
@ -1510,11 +1510,11 @@ validate_old_timelog(int fd, const struct dirent *dp, const char *logfname,
|
|||||||
static void
|
static void
|
||||||
delete_oldest_timelog(const struct conf_entry *ent, const char *archive_dir)
|
delete_oldest_timelog(const struct conf_entry *ent, const char *archive_dir)
|
||||||
{
|
{
|
||||||
char *logfname, *s, *dir, errbuf[80];
|
char *basebuf, *dirbuf, errbuf[80];
|
||||||
|
const char *base, *dir;
|
||||||
int dir_fd, i, logcnt, max_logcnt;
|
int dir_fd, i, logcnt, max_logcnt;
|
||||||
struct oldlog_entry *oldlogs;
|
struct oldlog_entry *oldlogs;
|
||||||
struct dirent *dp;
|
struct dirent *dp;
|
||||||
const char *cdir;
|
|
||||||
struct tm tm;
|
struct tm tm;
|
||||||
DIR *dirp;
|
DIR *dirp;
|
||||||
|
|
||||||
@ -1522,19 +1522,19 @@ delete_oldest_timelog(const struct conf_entry *ent, const char *archive_dir)
|
|||||||
max_logcnt = MAX_OLDLOGS;
|
max_logcnt = MAX_OLDLOGS;
|
||||||
logcnt = 0;
|
logcnt = 0;
|
||||||
|
|
||||||
if (archive_dir != NULL && archive_dir[0] != '\0')
|
if (archive_dir != NULL && archive_dir[0] != '\0') {
|
||||||
cdir = archive_dir;
|
dirbuf = NULL;
|
||||||
else
|
dir = archive_dir;
|
||||||
if ((cdir = dirname(ent->log)) == NULL)
|
} else {
|
||||||
err(1, "dirname()");
|
if ((dirbuf = strdup(ent->log)) == NULL)
|
||||||
if ((dir = strdup(cdir)) == NULL)
|
err(1, "strdup()");
|
||||||
err(1, "strdup()");
|
dir = dirname(dirbuf);
|
||||||
|
}
|
||||||
|
|
||||||
if ((s = basename(ent->log)) == NULL)
|
if ((basebuf = strdup(ent->log)) == NULL)
|
||||||
err(1, "basename()");
|
|
||||||
if ((logfname = strdup(s)) == NULL)
|
|
||||||
err(1, "strdup()");
|
err(1, "strdup()");
|
||||||
if (strcmp(logfname, "/") == 0)
|
base = basename(basebuf);
|
||||||
|
if (strcmp(base, "/") == 0)
|
||||||
errx(1, "Invalid log filename - became '/'");
|
errx(1, "Invalid log filename - became '/'");
|
||||||
|
|
||||||
if (verbose > 2)
|
if (verbose > 2)
|
||||||
@ -1545,7 +1545,7 @@ delete_oldest_timelog(const struct conf_entry *ent, const char *archive_dir)
|
|||||||
err(1, "Cannot open log directory '%s'", dir);
|
err(1, "Cannot open log directory '%s'", dir);
|
||||||
dir_fd = dirfd(dirp);
|
dir_fd = dirfd(dirp);
|
||||||
while ((dp = readdir(dirp)) != NULL) {
|
while ((dp = readdir(dirp)) != NULL) {
|
||||||
if (validate_old_timelog(dir_fd, dp, logfname, &tm) == 0)
|
if (validate_old_timelog(dir_fd, dp, base, &tm) == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -1610,8 +1610,8 @@ delete_oldest_timelog(const struct conf_entry *ent, const char *archive_dir)
|
|||||||
free(oldlogs[i].fname);
|
free(oldlogs[i].fname);
|
||||||
}
|
}
|
||||||
free(oldlogs);
|
free(oldlogs);
|
||||||
free(logfname);
|
free(dirbuf);
|
||||||
free(dir);
|
free(basebuf);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
Loading…
Reference in New Issue
Block a user