From: Jens Axboe Date: Tue, 13 Mar 2007 14:28:55 +0000 (+0100) Subject: Add 'opendir' option X-Git-Tag: fio-1.14~10 X-Git-Url: https://git.kernel.dk/?p=fio.git;a=commitdiff_plain;h=bbf6b5401cdc0b20c405a064356ab0abb27c52d0 Add 'opendir' option This option adds all files from a directory and downward in the filesystem hierarchy. Signed-off-by: Jens Axboe --- diff --git a/HOWTO b/HOWTO index ec4f3e21..e54b37b1 100644 --- a/HOWTO +++ b/HOWTO @@ -211,6 +211,9 @@ filename=str Fio normally makes up a filename based on the job name, a job to open /dev/sda and /dev/sdb as the two working files, you would use filename=/dev/sda:/dev/sdb +opendir=str Tell fio to recursively add any file it can find in this + directory and down the file system tree. + rw=str Type of io pattern. Accepted values are: read Sequential reads diff --git a/filesetup.c b/filesetup.c index 2a7e7cf5..0a4e77ef 100644 --- a/filesetup.c +++ b/filesetup.c @@ -2,8 +2,10 @@ #include #include #include +#include #include #include +#include #include "fio.h" #include "os.h" @@ -473,3 +475,50 @@ void put_file(struct thread_data *td, struct fio_file *f) td->nr_open_files--; f->flags &= ~FIO_FILE_OPEN; } + +static int recurse_dir(struct thread_data *td, const char *dirname) +{ + struct dirent *dir; + int ret = 0; + DIR *D; + + D = opendir(dirname); + if (!D) { + td_verror(td, errno, "opendir"); + return 1; + } + + while ((dir = readdir(D)) != NULL) { + char full_path[PATH_MAX]; + struct stat sb; + + sprintf(full_path, "%s/%s", dirname, dir->d_name); + + if (lstat(full_path, &sb) == -1) { + if (errno != ENOENT) { + td_verror(td, errno, "stat"); + return 1; + } + } + + if (S_ISREG(sb.st_mode)) { + add_file(td, full_path); + td->nr_files++; + continue; + } + + if (!strcmp(dir->d_name, ".") || !strcmp(dir->d_name, "..")) + continue; + + if ((ret = recurse_dir(td, full_path)) != 0) + break; + } + + closedir(D); + return ret; +} + +int add_dir_files(struct thread_data *td, const char *path) +{ + return recurse_dir(td, path); +} diff --git a/fio.h b/fio.h index 7db30909..51734641 100644 --- a/fio.h +++ b/fio.h @@ -393,6 +393,7 @@ struct thread_data { unsigned int file_service_type; unsigned int group_reporting; unsigned int open_files; + char *opendir; char *read_iolog_file; char *write_iolog_file; @@ -660,6 +661,7 @@ extern void generic_close_file(struct thread_data *, struct fio_file *); extern void add_file(struct thread_data *, const char *); extern void get_file(struct fio_file *); extern void put_file(struct thread_data *, struct fio_file *); +extern int add_dir_files(struct thread_data *, const char *); /* * ETA/status stuff diff --git a/init.c b/init.c index cf66ec0e..ee0f36fd 100644 --- a/init.c +++ b/init.c @@ -33,6 +33,7 @@ static int str_cpumask_cb(void *, unsigned int *); static int str_fst_cb(void *, const char *); static int str_filename_cb(void *, const char *); static int str_directory_cb(void *, const char *); +static int str_opendir_cb(void *, const char *); #define __stringify_1(x) #x #define __stringify(x) __stringify_1(x) @@ -67,6 +68,13 @@ static struct fio_option options[] = { .cb = str_filename_cb, .help = "File(s) to use for the workload", }, + { + .name = "opendir", + .type = FIO_OPT_STR_STORE, + .off1 = td_var_offset(opendir), + .cb = str_opendir_cb, + .help = "Recursively add files from this directory and down", + }, { .name = "rw", .type = FIO_OPT_STR, @@ -759,9 +767,7 @@ static void fixup_options(struct thread_data *td) if (td->iodepth_batch > td->iodepth || !td->iodepth_batch) td->iodepth_batch = td->iodepth; - if (!td->nr_files) - td->nr_files = td->files_index; - else if (td->nr_files > td->files_index) + if (td->nr_files > td->files_index) td->nr_files = td->files_index; if (td->open_files > td->nr_files || !td->open_files) @@ -839,7 +845,7 @@ static int add_job(struct thread_data *td, const char *jobname, int job_add_num) if (td->odirect) td->io_ops->flags |= FIO_RAWIO; - if (!td->filename) { + if (!td->filename && !td->files_index) { td->filename = strdup(jobname); if (td->nr_files == 1) @@ -1121,10 +1127,14 @@ static int str_filename_cb(void *data, const char *input) strip_blank_front(&str); strip_blank_end(str); + if (!td->files_index) + td->nr_files = 0; + while ((fname = strsep(&str, ":")) != NULL) { if (!strlen(fname)) break; add_file(td, fname); + td->nr_files++; } free(p); @@ -1149,6 +1159,16 @@ static int str_directory_cb(void *data, const char fio_unused *str) return 0; } +static int str_opendir_cb(void *data, const char fio_unused *str) +{ + struct thread_data *td = data; + + if (!td->files_index) + td->nr_files = 0; + + return add_dir_files(td, td->opendir); +} + /* * This is our [ini] type file parser. */