From f1c71016a5b57412a7cacd138c1e1a786ca775f3 Mon Sep 17 00:00:00 2001 From: Josef Bacik Date: Wed, 11 Oct 2017 14:58:12 -0400 Subject: [PATCH 1/1] create subdirs if specified in the filename_format Currently there's no way for a user to specify a directory that doesn't exist yet for a job. Fix this by looking for paths in the file name provided by the job and creating any subdirectories that may be required. Signed-off-by: Josef Bacik Removed TD_ENG_FLAG_SHIFT change, not needed. Signed-off-by: Jens Axboe --- filesetup.c | 43 +++++++++++++++++++++++++++++++++++++++++++ fio.h | 2 ++ 2 files changed, 45 insertions(+) diff --git a/filesetup.c b/filesetup.c index a7bbcede..b390caa2 100644 --- a/filesetup.c +++ b/filesetup.c @@ -1523,6 +1523,45 @@ bool exists_and_not_regfile(const char *filename) return true; } +static void create_work_dirs(struct thread_data *td, const char *fname) +{ + char path[PATH_MAX]; + char *start, *end; + int dirfd; + bool need_close = true; + + if (td->o.directory) { + dirfd = open(td->o.directory, O_DIRECTORY | O_RDONLY); + if (dirfd < 0) { + log_err("fio: failed to open dir (%s): %d\n", + td->o.directory, errno); + assert(0); + } + } else { + dirfd = AT_FDCWD; + need_close = false; + } + + memcpy(path, fname, PATH_MAX); + start = end = path; + while ((end = strchr(end, FIO_OS_PATH_SEPARATOR)) != NULL) { + if (end == start) + break; + *end = '\0'; + errno = 0; + if (mkdirat(dirfd, start, 0600) && errno != EEXIST) { + log_err("fio: failed to create dir (%s): %d\n", + start, errno); + assert(0); + } + *end = FIO_OS_PATH_SEPARATOR; + end++; + } + if (need_close) + close(dirfd); + td->flags |= TD_F_DIRS_CREATED; +} + int add_file(struct thread_data *td, const char *fname, int numjob, int inc) { int cur_files = td->files_index; @@ -1538,6 +1577,10 @@ int add_file(struct thread_data *td, const char *fname, int numjob, int inc) sprintf(file_name + len, "%s", fname); + if (strchr(fname, FIO_OS_PATH_SEPARATOR) && + !(td->flags & TD_F_DIRS_CREATED)) + create_work_dirs(td, fname); + /* clean cloned siblings using existing files */ if (numjob && is_already_allocated(file_name) && !exists_and_not_regfile(fname)) diff --git a/fio.h b/fio.h index 28d064cf..4809b99a 100644 --- a/fio.h +++ b/fio.h @@ -87,6 +87,7 @@ enum { __TD_F_NO_PROGRESS, __TD_F_REGROW_LOGS, __TD_F_MMAP_KEEP, + __TD_F_DIRS_CREATED, __TD_F_LAST, /* not a real bit, keep last */ }; @@ -106,6 +107,7 @@ enum { TD_F_NO_PROGRESS = 1U << __TD_F_NO_PROGRESS, TD_F_REGROW_LOGS = 1U << __TD_F_REGROW_LOGS, TD_F_MMAP_KEEP = 1U << __TD_F_MMAP_KEEP, + TD_F_DIRS_CREATED = 1U << __TD_F_DIRS_CREATED, }; enum { -- 2.25.1