Fix start delay being the same across threads
[fio.git] / init.c
diff --git a/init.c b/init.c
index e47e5384119b369891119b54467ed558dfa082c3..e25e5e48ca9fac6430163447d2b46c0034b22466 100644 (file)
--- a/init.c
+++ b/init.c
@@ -4,13 +4,11 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <unistd.h>
-#include <fcntl.h>
 #include <ctype.h>
 #include <string.h>
 #include <errno.h>
 #include <sys/ipc.h>
 #include <sys/types.h>
-#include <sys/stat.h>
 #include <dlfcn.h>
 #ifdef CONFIG_VALGRIND_DEV
 #include <valgrind/drd.h>
@@ -580,8 +578,7 @@ static int fixed_block_size(struct thread_options *o)
 static unsigned long long get_rand_start_delay(struct thread_data *td)
 {
        unsigned long long delayrange;
-       uint64_t frand_max;
-       unsigned long r;
+       uint64_t r, frand_max;
 
        delayrange = td->o.start_delay_high - td->o.start_delay;
 
@@ -589,7 +586,7 @@ static unsigned long long get_rand_start_delay(struct thread_data *td)
        r = __rand(&td->delay_state);
        delayrange = (unsigned long long) ((double) delayrange * (r / (frand_max + 1.0)));
 
-       delayrange += td->o.start_delay;
+       delayrange += td->o.start_delay_orig;
        return delayrange;
 }
 
@@ -687,8 +684,11 @@ static int fixup_options(struct thread_data *td)
        if (!o->file_size_high)
                o->file_size_high = o->file_size_low;
 
-       if (o->start_delay_high)
+       if (o->start_delay_high) {
+               if (!o->start_delay_orig)
+                       o->start_delay_orig = o->start_delay;
                o->start_delay = get_rand_start_delay(td);
+       }
 
        if (o->norandommap && o->verify != VERIFY_NONE
            && !fixed_block_size(o))  {
@@ -835,11 +835,11 @@ static int fixup_options(struct thread_data *td)
                }
        }
 
-       if (!o->unit_base) {
+       if (o->unit_base == N2S_NONE) {
                if (td_ioengine_flagged(td, FIO_BIT_BASED))
-                       o->unit_base = 1;
+                       o->unit_base = N2S_BITPERSEC;
                else
-                       o->unit_base = 8;
+                       o->unit_base = N2S_BYTEPERSEC;
        }
 
 #ifndef FIO_HAVE_ANY_FALLOCATE
@@ -999,23 +999,26 @@ void td_fill_verify_state_seed(struct thread_data *td)
 
 static void td_fill_rand_seeds_internal(struct thread_data *td, bool use64)
 {
+       unsigned int read_seed = td->rand_seeds[FIO_RAND_BS_OFF];
+       unsigned int write_seed = td->rand_seeds[FIO_RAND_BS1_OFF];
+       unsigned int trim_seed = td->rand_seeds[FIO_RAND_BS2_OFF];
        int i;
 
        /*
         * trimwrite is special in that we need to generate the same
         * offsets to get the "write after trim" effect. If we are
         * using bssplit to set buffer length distributions, ensure that
-        * we seed the trim and write generators identically.
+        * we seed the trim and write generators identically. Ditto for
+        * verify, read and writes must have the same seed, if we are doing
+        * read verify.
         */
-       if (td_trimwrite(td)) {
-               init_rand_seed(&td->bsrange_state[DDIR_READ], td->rand_seeds[FIO_RAND_BS_OFF], use64);
-               init_rand_seed(&td->bsrange_state[DDIR_WRITE], td->rand_seeds[FIO_RAND_BS1_OFF], use64);
-               init_rand_seed(&td->bsrange_state[DDIR_TRIM], td->rand_seeds[FIO_RAND_BS1_OFF], use64);
-       } else {
-               init_rand_seed(&td->bsrange_state[DDIR_READ], td->rand_seeds[FIO_RAND_BS_OFF], use64);
-               init_rand_seed(&td->bsrange_state[DDIR_WRITE], td->rand_seeds[FIO_RAND_BS1_OFF], use64);
-               init_rand_seed(&td->bsrange_state[DDIR_TRIM], td->rand_seeds[FIO_RAND_BS2_OFF], use64);
-       }
+       if (td->o.verify != VERIFY_NONE)
+               write_seed = read_seed;
+       if (td_trimwrite(td))
+               trim_seed = write_seed;
+       init_rand_seed(&td->bsrange_state[DDIR_READ], read_seed, use64);
+       init_rand_seed(&td->bsrange_state[DDIR_WRITE], write_seed, use64);
+       init_rand_seed(&td->bsrange_state[DDIR_TRIM], trim_seed, use64);
 
        td_fill_verify_state_seed(td);
        init_rand_seed(&td->rwmix_state, td->rand_seeds[FIO_RAND_MIX_OFF], false);
@@ -1186,7 +1189,7 @@ static void init_flags(struct thread_data *td)
            fio_option_is_set(o, zero_buffers)))
                td->flags |= TD_F_SCRAMBLE_BUFFERS;
        if (o->verify != VERIFY_NONE)
-               td->flags |= TD_F_VER_NONE;
+               td->flags |= TD_F_DO_VERIFY;
 
        if (o->verify_async || o->io_submit_mode == IO_MODE_OFFLOAD)
                td->flags |= TD_F_NEED_LOCK;
@@ -1455,6 +1458,11 @@ static int add_job(struct thread_data *td, const char *jobname, int job_add_num,
                }
        }
 
+       if (setup_random_seeds(td)) {
+               td_verror(td, errno, "setup_random_seeds");
+               goto err;
+       }
+
        if (fixup_options(td))
                goto err;
 
@@ -1510,11 +1518,6 @@ static int add_job(struct thread_data *td, const char *jobname, int job_add_num,
        td->groupid = groupid;
        prev_group_jobs++;
 
-       if (setup_random_seeds(td)) {
-               td_verror(td, errno, "setup_random_seeds");
-               goto err;
-       }
-
        if (setup_rate(td))
                goto err;
 
@@ -1972,7 +1975,8 @@ static int __parse_jobs_ini(struct thread_data *td,
                        if (p[0] == '[') {
                                if (nested) {
                                        log_err("No new sections in included files\n");
-                                       return 1;
+                                       ret = 1;
+                                       goto out;
                                }
 
                                skip_fgets = 1;