engines/filestat: add "lstat" option to use lstat(2)
authorTomohiro Kusumi <kusumi.tomohiro@gmail.com>
Thu, 23 Jan 2020 16:36:32 +0000 (01:36 +0900)
committerTomohiro Kusumi <kusumi.tomohiro@gmail.com>
Thu, 23 Jan 2020 17:05:51 +0000 (02:05 +0900)
Use stat(2) by default, but lstat(2) if "lstat" bool option specified.

Signed-off-by: Tomohiro Kusumi <kusumi.tomohiro@gmail.com>
HOWTO
engines/filestat.c
fio.1
optgroup.h

diff --git a/HOWTO b/HOWTO
index 0a3661684fb4653a1638b30e7d1e204abe6094a9..f19f9226a93de504d04aad6c60c27856bf1b19cb 100644 (file)
--- a/HOWTO
+++ b/HOWTO
@@ -2261,6 +2261,10 @@ with the caveat that when used on the command line, they must come after the
        multiple paths exist between the client and the server or in certain loopback
        configurations.
 
        multiple paths exist between the client and the server or in certain loopback
        configurations.
 
+.. option:: lstat=bool : [filestat]
+
+       Use lstat(2) to measure lookup/getattr performance. Default is 0.
+
 .. option:: readfua=bool : [sg]
 
        With readfua option set to 1, read operations include
 .. option:: readfua=bool : [sg]
 
        With readfua option set to 1, read operations include
index 795259341b7e33a320a6d848a64c1f3b6d85bf01..6c87c4c2222b50282e4cd636c3698d7244214c3e 100644 (file)
 #include <sys/stat.h>
 #include <unistd.h>
 #include "../fio.h"
 #include <sys/stat.h>
 #include <unistd.h>
 #include "../fio.h"
+#include "../optgroup.h"
 
 struct fc_data {
        enum fio_ddir stat_ddir;
 };
 
 
 struct fc_data {
        enum fio_ddir stat_ddir;
 };
 
+struct filestat_options {
+       void *pad;
+       unsigned int lstat;
+};
+
+static struct fio_option options[] = {
+       {
+               .name   = "lstat",
+               .lname  = "lstat",
+               .type   = FIO_OPT_BOOL,
+               .off1   = offsetof(struct filestat_options, lstat),
+               .help   = "Use lstat(2) to measure lookup/getattr performance",
+               .def    = "0",
+               .category = FIO_OPT_C_ENGINE,
+               .group  = FIO_OPT_G_FILESTAT,
+       },
+       {
+               .name   = NULL,
+       },
+};
+
 static int stat_file(struct thread_data *td, struct fio_file *f)
 {
 static int stat_file(struct thread_data *td, struct fio_file *f)
 {
+       struct filestat_options *o = td->eo;
        struct timespec start;
        int do_lat = !td->o.disable_lat;
        struct stat statbuf;
        struct timespec start;
        int do_lat = !td->o.disable_lat;
        struct stat statbuf;
@@ -37,13 +60,17 @@ static int stat_file(struct thread_data *td, struct fio_file *f)
        if (do_lat)
                fio_gettime(&start, NULL);
 
        if (do_lat)
                fio_gettime(&start, NULL);
 
-       ret = stat(f->file_name, &statbuf);
+       if (o->lstat)
+               ret = lstat(f->file_name, &statbuf);
+       else
+               ret = stat(f->file_name, &statbuf);
 
        if (ret == -1) {
                char buf[FIO_VERROR_SIZE];
                int e = errno;
 
 
        if (ret == -1) {
                char buf[FIO_VERROR_SIZE];
                int e = errno;
 
-               snprintf(buf, sizeof(buf), "stat(%s)", f->file_name);
+               snprintf(buf, sizeof(buf), "%sstat(%s)",
+                       o->lstat ? "l" : "", f->file_name);
                td_verror(td, e, buf);
                return 1;
        }
                td_verror(td, e, buf);
                return 1;
        }
@@ -103,6 +130,8 @@ static struct ioengine_ops ioengine = {
        .open_file      = stat_file,
        .flags          =  FIO_SYNCIO | FIO_FAKEIO |
                                FIO_NOSTATS | FIO_NOFILEHASH,
        .open_file      = stat_file,
        .flags          =  FIO_SYNCIO | FIO_FAKEIO |
                                FIO_NOSTATS | FIO_NOFILEHASH,
+       .options        = options,
+       .option_struct_size = sizeof(struct filestat_options),
 };
 
 static void fio_init fio_filestat_register(void)
 };
 
 static void fio_init fio_filestat_register(void)
diff --git a/fio.1 b/fio.1
index 05896e61418e564461b98628c8a14462fe7c1a02..a58632b407fc2c95856278fc03a22aef34838f75 100644 (file)
--- a/fio.1
+++ b/fio.1
@@ -2032,6 +2032,9 @@ on the client site it will be used in the rdma_resolve_add()
 function. This can be useful when multiple paths exist between the
 client and the server or in certain loopback configurations.
 .TP
 function. This can be useful when multiple paths exist between the
 client and the server or in certain loopback configurations.
 .TP
+.BI (filestat)lstat \fR=\fPbool
+Use \fBlstat\fR\|(2) to measure lookup/getattr performance. Default: 0.
+.TP
 .BI (sg)readfua \fR=\fPbool
 With readfua option set to 1, read operations include the force
 unit access (fua) flag. Default: 0.
 .BI (sg)readfua \fR=\fPbool
 With readfua option set to 1, read operations include the force
 unit access (fua) flag. Default: 0.
index 55ef5934256e6db3c191eb81189a12b385c458e4..5789afd32c49d2cbe5bd0c968ee6a7f3ca917a49 100644 (file)
@@ -65,6 +65,7 @@ enum opt_category_group {
        __FIO_OPT_G_ISCSI,
        __FIO_OPT_G_NBD,
        __FIO_OPT_G_IOURING,
        __FIO_OPT_G_ISCSI,
        __FIO_OPT_G_NBD,
        __FIO_OPT_G_IOURING,
+       __FIO_OPT_G_FILESTAT,
        __FIO_OPT_G_NR,
 
        FIO_OPT_G_RATE          = (1ULL << __FIO_OPT_G_RATE),
        __FIO_OPT_G_NR,
 
        FIO_OPT_G_RATE          = (1ULL << __FIO_OPT_G_RATE),
@@ -106,6 +107,7 @@ enum opt_category_group {
        FIO_OPT_G_ISCSI         = (1ULL << __FIO_OPT_G_ISCSI),
        FIO_OPT_G_NBD           = (1ULL << __FIO_OPT_G_NBD),
        FIO_OPT_G_IOURING       = (1ULL << __FIO_OPT_G_IOURING),
        FIO_OPT_G_ISCSI         = (1ULL << __FIO_OPT_G_ISCSI),
        FIO_OPT_G_NBD           = (1ULL << __FIO_OPT_G_NBD),
        FIO_OPT_G_IOURING       = (1ULL << __FIO_OPT_G_IOURING),
+       FIO_OPT_G_FILESTAT      = (1ULL << __FIO_OPT_G_FILESTAT),
 };
 
 extern const struct opt_group *opt_group_from_mask(uint64_t *mask);
 };
 
 extern const struct opt_group *opt_group_from_mask(uint64_t *mask);