summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJens Axboe <axboe@fb.com>2014-12-22 20:03:50 -0700
committerJens Axboe <axboe@fb.com>2014-12-22 20:03:50 -0700
commitf0e7f45a2c73f2810f45f2bb2938ebdcd1a8bf23 (patch)
treea60790b665455c8a7ddb687bde364a94b49be2f9
parentcf3b23e4c09a57a949aa2c61e3fa8cf8e671b086 (diff)
downloadfio-f0e7f45a2c73f2810f45f2bb2938ebdcd1a8bf23.tar.gz
fio-f0e7f45a2c73f2810f45f2bb2938ebdcd1a8bf23.tar.bz2
options: ensure that we check all candidates on is_set check
We can have multiple options that touch the same variable. One example is cpus_allowed or cpumask, both will set the same backend variable. But if we set cpumask= and later check if cpus_allowed is set, then we want that to report true. This breaks certain options since b2a9e6496494. Reported-by: Vincent Fu <Vincent.Fu@sandisk.com> Signed-off-by: Jens Axboe <axboe@fb.com>
-rw-r--r--options.c46
1 files changed, 36 insertions, 10 deletions
diff --git a/options.c b/options.c
index e3c9c87b..3e783c15 100644
--- a/options.c
+++ b/options.c
@@ -4191,21 +4191,32 @@ struct fio_option *fio_option_find(const char *name)
return find_option(fio_options, name);
}
-int __fio_option_is_set(struct thread_options *o, unsigned int off1)
+static struct fio_option *find_next_opt(struct thread_options *o,
+ struct fio_option *from,
+ unsigned int off1)
{
- unsigned int opt_off, index, offset;
- struct fio_option *opt = NULL;
- int i;
+ struct fio_option *opt;
- for (i = 0; fio_options[i].name; i++) {
- if (off1 == fio_options[i].off1) {
- opt = &fio_options[i];
+ if (!from)
+ from = &fio_options[0];
+ else
+ from++;
+
+ opt = NULL;
+ do {
+ if (off1 == from->off1) {
+ opt = from;
break;
}
- }
+ from++;
+ } while (from->name);
- if (!opt)
- return -1;
+ return opt;
+}
+
+static int opt_is_set(struct thread_options *o, struct fio_option *opt)
+{
+ unsigned int opt_off, index, offset;
opt_off = opt - &fio_options[0];
index = opt_off / (8 * sizeof(uint64_t));
@@ -4213,6 +4224,21 @@ int __fio_option_is_set(struct thread_options *o, unsigned int off1)
return (o->set_options[index] & (1UL << offset)) != 0;
}
+int __fio_option_is_set(struct thread_options *o, unsigned int off1)
+{
+ struct fio_option *opt, *next;
+
+ next = NULL;
+ while ((opt = find_next_opt(o, next, off1)) != NULL) {
+ if (opt_is_set(o, opt))
+ return 1;
+
+ next = opt;
+ }
+
+ return 0;
+}
+
void fio_option_mark_set(struct thread_options *o, struct fio_option *opt)
{
unsigned int opt_off, index, offset;