Fio 1.53
[fio.git] / init.c
diff --git a/init.c b/init.c
index c3f23f93c1926ee5b9b35c3223b7ec1a1f520519..63826662f2fbba0e7fd902c01399afad2202f0a9 100644 (file)
--- a/init.c
+++ b/init.c
@@ -22,7 +22,7 @@
 
 #include "lib/getopt.h"
 
-static char fio_version_string[] = "fio 1.50-rc3";
+static char fio_version_string[] = "fio 1.53";
 
 #define FIO_RANDSEED           (0xb1899bedUL)
 
@@ -39,7 +39,8 @@ int eta_print;
 unsigned long long mlock_size = 0;
 FILE *f_out = NULL;
 FILE *f_err = NULL;
-char *job_section = NULL;
+char **job_sections = NULL;
+int nr_job_sections = 0;
 char *exec_profile = NULL;
 int warnings_fatal = 0;
 
@@ -190,7 +191,7 @@ static void put_job(struct thread_data *td)
 {
        if (td == &def_thread)
                return;
-       
+
        profile_td_exit(td);
 
        if (td->error)
@@ -375,12 +376,6 @@ static int fixup_options(struct thread_data *td)
                o->size = -1ULL;
 
        if (o->verify != VERIFY_NONE) {
-               if (td_rw(td)) {
-                       log_info("fio: mixed read/write workload with verify. "
-                               "May not work as expected, unless you "
-                               "pre-populated the file\n");
-                       ret = warnings_fatal;
-               }
                if (td_write(td) && o->do_verify && o->numjobs > 1) {
                        log_info("Multiple writers may overwrite blocks that "
                                "belong to other jobs. This can cause "
@@ -468,7 +463,7 @@ static int exists_and_not_file(const char *filename)
        return 1;
 }
 
-void td_fill_rand_seeds(struct thread_data *td)
+static void td_fill_rand_seeds_os(struct thread_data *td)
 {
        os_random_seed(td->rand_seeds[0], &td->bsrange_state);
        os_random_seed(td->rand_seeds[1], &td->verify_state);
@@ -489,6 +484,35 @@ void td_fill_rand_seeds(struct thread_data *td)
        os_random_seed(td->rand_seeds[4], &td->random_state);
 }
 
+static void td_fill_rand_seeds_internal(struct thread_data *td)
+{
+       init_rand_seed(&td->__bsrange_state, td->rand_seeds[0]);
+       init_rand_seed(&td->__verify_state, td->rand_seeds[1]);
+       init_rand_seed(&td->__rwmix_state, td->rand_seeds[2]);
+
+       if (td->o.file_service_type == FIO_FSERVICE_RANDOM)
+               init_rand_seed(&td->__next_file_state, td->rand_seeds[3]);
+
+       init_rand_seed(&td->__file_size_state, td->rand_seeds[5]);
+       init_rand_seed(&td->__trim_state, td->rand_seeds[6]);
+
+       if (!td_random(td))
+               return;
+
+       if (td->o.rand_repeatable)
+               td->rand_seeds[4] = FIO_RANDSEED * td->thread_number;
+
+       init_rand_seed(&td->__random_state, td->rand_seeds[4]);
+}
+
+void td_fill_rand_seeds(struct thread_data *td)
+{
+       if (td->o.use_os_rand)
+               td_fill_rand_seeds_os(td);
+       else
+               td_fill_rand_seeds_internal(td);
+}
+
 /*
  * Initialize the various random states we need (random io, block size ranges,
  * read/write mix, etc).
@@ -724,12 +748,18 @@ void add_job_opts(const char **o)
 
 static int skip_this_section(const char *name)
 {
-       if (!job_section)
+       int i;
+
+       if (!nr_job_sections)
                return 0;
        if (!strncmp(name, "global", 6))
                return 0;
 
-       return strcmp(job_section, name);
+       for (i = 0; i < nr_job_sections; i++)
+               if (!strcmp(job_sections[i], name))
+                       return 0;
+
+       return 1;
 }
 
 static int is_empty_or_comment(char *line)
@@ -805,7 +835,7 @@ static int parse_jobs_ini(char *file, int stonewall_flag)
 
                if (is_empty_or_comment(p))
                        continue;
-               if (sscanf(p, "[%255s]", name) != 1) {
+               if (sscanf(p, "[%255[^\n]]", name) != 1) {
                        if (inside_skip)
                                continue;
                        log_err("fio: option <%s> outside of [] job section\n",
@@ -1155,7 +1185,7 @@ static int parse_cmd_line(int argc, char *argv[])
                        read_only = 1;
                        break;
                case 'v':
-                       /* already being printed, just quit */
+                       log_info("%s\n", fio_version_string);
                        exit(0);
                case 'e':
                        if (!strcmp("always", optarg))
@@ -1167,7 +1197,9 @@ static int parse_cmd_line(int argc, char *argv[])
                        if (set_debug(optarg))
                                do_exit++;
                        break;
-               case 'x':
+               case 'x': {
+                       size_t new_size;
+
                        if (!strcmp(optarg, "global")) {
                                log_err("fio: can't use global as only "
                                        "section\n");
@@ -1175,10 +1207,12 @@ static int parse_cmd_line(int argc, char *argv[])
                                exit_val = 1;
                                break;
                        }
-                       if (job_section)
-                               free(job_section);
-                       job_section = strdup(optarg);
+                       new_size = (nr_job_sections + 1) * sizeof(char *);
+                       job_sections = realloc(job_sections, new_size);
+                       job_sections[nr_job_sections] = strdup(optarg);
+                       nr_job_sections++;
                        break;
+                       }
                case 'p':
                        exec_profile = strdup(optarg);
                        break;
@@ -1249,8 +1283,6 @@ int parse_options(int argc, char *argv[])
        f_out = stdout;
        f_err = stderr;
 
-       log_info("%s\n", fio_version_string);
-
        fio_options_fill_optstring();
        fio_options_dup_and_init(l_opts);
 
@@ -1289,5 +1321,6 @@ int parse_options(int argc, char *argv[])
                fio_gtod_cpu = def_thread.o.gtod_cpu;
        }
 
+       log_info("%s\n", fio_version_string);
        return 0;
 }