From 92b0959366a4677d8ac916cd9246a80853ae4765 Mon Sep 17 00:00:00 2001 From: Kamil Dudka Date: Mon, 17 Oct 2016 17:59:31 +0200 Subject: createOutputFile: eliminate stat/open TOCTOU race --- logrotate.c | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/logrotate.c b/logrotate.c index e415164..c4b8e0c 100644 --- a/logrotate.c +++ b/logrotate.c @@ -394,11 +394,18 @@ static int runScript(struct logInfo *log, char *logfn, char *script) int createOutputFile(char *fileName, int flags, struct stat *sb, acl_type acl, int force_mode) { - int fd; + int fd = -1; struct stat sb_create; int acl_set = 0; + int i; + + for (i = 0; i < 2; ++i) { + fd = open(fileName, (flags | O_EXCL | O_NOFOLLOW), + (S_IRUSR | S_IWUSR) & sb->st_mode); + + if ((fd >= 0) || (errno != EEXIST)) + break; - if (stat(fileName, &sb_create) == 0) { /* the destination file already exists, while it should not */ struct tm now = *localtime(&nowSecs); size_t fileName_size = strlen(fileName); @@ -412,11 +419,9 @@ int createOutputFile(char *fileName, int flags, struct stat *sb, acl_type acl, i fileName, backupName, strerror(errno)); return -1; } + /* existing file renamed, try it once again */ } - fd = open(fileName, (flags | O_EXCL | O_NOFOLLOW), - (S_IRUSR | S_IWUSR) & sb->st_mode); - if (fd < 0) { message(MESS_ERROR, "error creating output file %s: %s\n", fileName, strerror(errno)); -- 2.7.4