X-Git-Url: https://git.kernel.dk/?p=fio.git;a=blobdiff_plain;f=io_u.c;h=63a176f5eb02b315f3646bfca3fd299279e4f5e4;hp=69ca6fe06ff8abfa30be5694a24bbca810c3e5f8;hb=5efb2861b1b8d4620fa83585f0584dea9e9bff21;hpb=732eedd0666bbe555d97b04801998ea8c63e0236 diff --git a/io_u.c b/io_u.c index 69ca6fe0..63a176f5 100644 --- a/io_u.c +++ b/io_u.c @@ -12,6 +12,7 @@ #include "lib/rand.h" #include "lib/axmap.h" #include "err.h" +#include "lib/pow2.h" struct io_completion_data { int nr; /* input */ @@ -88,18 +89,20 @@ static int __get_next_rand_offset(struct thread_data *td, struct fio_file *f, { uint64_t r; - if (td->o.random_generator == FIO_RAND_GEN_TAUSWORTHE) { - uint64_t lastb; + if (td->o.random_generator == FIO_RAND_GEN_TAUSWORTHE || + td->o.random_generator == FIO_RAND_GEN_TAUSWORTHE64) { + uint64_t frand_max, lastb; lastb = last_block(td, f, ddir); if (!lastb) return 1; + frand_max = rand_max(&td->random_state); r = __rand(&td->random_state); dprint(FD_RANDOM, "off rand %llu\n", (unsigned long long) r); - *b = lastb * (r / ((uint64_t) FRAND_MAX + 1.0)); + *b = lastb * (r / ((uint64_t) frand_max + 1.0)); } else { uint64_t off = 0; @@ -194,7 +197,8 @@ static inline int should_sort_io(struct thread_data *td) return 0; if (td->runstate != TD_VERIFYING) return 0; - if (td->o.random_generator == FIO_RAND_GEN_TAUSWORTHE) + if (td->o.random_generator == FIO_RAND_GEN_TAUSWORTHE || + td->o.random_generator == FIO_RAND_GEN_TAUSWORTHE64) return 0; return 1; @@ -202,14 +206,16 @@ static inline int should_sort_io(struct thread_data *td) static int should_do_random(struct thread_data *td, enum fio_ddir ddir) { + uint64_t frand_max; unsigned int v; unsigned long r; if (td->o.perc_rand[ddir] == 100) return 1; + frand_max = rand_max(&td->seq_rand_state[ddir]); r = __rand(&td->seq_rand_state[ddir]); - v = 1 + (int) (100.0 * (r / (FRAND_MAX + 1.0))); + v = 1 + (int) (100.0 * (r / (frand_max + 1.0))); return v <= td->o.perc_rand[ddir]; } @@ -438,6 +444,7 @@ static unsigned int __get_next_buflen(struct thread_data *td, struct io_u *io_u, int ddir = io_u->ddir; unsigned int buflen = 0; unsigned int minbs, maxbs; + uint64_t frand_max; unsigned long r; assert(ddir_rw(ddir)); @@ -457,12 +464,13 @@ static unsigned int __get_next_buflen(struct thread_data *td, struct io_u *io_u, if (!io_u_fits(td, io_u, minbs)) return 0; + frand_max = rand_max(&td->bsrange_state); do { r = __rand(&td->bsrange_state); if (!td->o.bssplit_nr[ddir]) { buflen = 1 + (unsigned int) ((double) maxbs * - (r / (FRAND_MAX + 1.0))); + (r / (frand_max + 1.0))); if (buflen < minbs) buflen = minbs; } else { @@ -474,7 +482,7 @@ static unsigned int __get_next_buflen(struct thread_data *td, struct io_u *io_u, buflen = bsp->bs; perc += bsp->perc; - if ((r <= ((FRAND_MAX / 100L) * perc)) && + if ((r <= ((frand_max / 100L) * perc)) && io_u_fits(td, io_u, buflen)) break; } @@ -520,11 +528,12 @@ static void set_rwmix_bytes(struct thread_data *td) static inline enum fio_ddir get_rand_ddir(struct thread_data *td) { + uint64_t frand_max = rand_max(&td->rwmix_state); unsigned int v; unsigned long r; r = __rand(&td->rwmix_state); - v = 1 + (int) (100.0 * (r / (FRAND_MAX + 1.0))); + v = 1 + (int) (100.0 * (r / (frand_max + 1.0))); if (v <= td->o.rwmix[DDIR_READ]) return DDIR_READ; @@ -991,6 +1000,7 @@ static struct fio_file *get_next_file_rand(struct thread_data *td, enum fio_file_flags goodf, enum fio_file_flags badf) { + uint64_t frand_max = rand_max(&td->next_file_state); struct fio_file *f; int fno; @@ -1000,7 +1010,7 @@ static struct fio_file *get_next_file_rand(struct thread_data *td, r = __rand(&td->next_file_state); fno = (unsigned int) ((double) td->o.nr_files - * (r / (FRAND_MAX + 1.0))); + * (r / (frand_max + 1.0))); f = td->files[fno]; if (fio_file_done(f)) @@ -1889,21 +1899,22 @@ void io_u_queued(struct thread_data *td, struct io_u *io_u) /* * See if we should reuse the last seed, if dedupe is enabled */ -static struct frand_state *get_buf_state(struct thread_data *td, - struct frand_state *save) +static struct frand_state *get_buf_state(struct thread_data *td) { + uint64_t frand_max; unsigned int v; unsigned long r; if (!td->o.dedupe_percentage) return &td->buf_state; else if (td->o.dedupe_percentage == 100) { - frand_copy(save, &td->buf_state_prev); - return &td->buf_state_prev; + frand_copy(&td->buf_state_prev, &td->buf_state); + return &td->buf_state; } + frand_max = rand_max(&td->dedupe_state); r = __rand(&td->dedupe_state); - v = 1 + (int) (100.0 * (r / (FRAND_MAX + 1.0))); + v = 1 + (int) (100.0 * (r / (frand_max + 1.0))); if (v <= td->o.dedupe_percentage) return &td->buf_state_prev; @@ -1911,20 +1922,18 @@ static struct frand_state *get_buf_state(struct thread_data *td, return &td->buf_state; } -static void save_buf_state(struct thread_data *td, struct frand_state *rs, - struct frand_state *save) +static void save_buf_state(struct thread_data *td, struct frand_state *rs) { - if (rs == &td->buf_state) + if (td->o.dedupe_percentage == 100) + frand_copy(rs, &td->buf_state_prev); + else if (rs == &td->buf_state) frand_copy(&td->buf_state_prev, rs); - else if (rs == &td->buf_state_prev && td->o.dedupe_percentage == 100) - frand_copy(rs, save); } void fill_io_buffer(struct thread_data *td, void *buf, unsigned int min_write, unsigned int max_bs) { struct thread_options *o = &td->o; - struct frand_state save = { 0, }; if (o->compress_percentage || o->dedupe_percentage) { unsigned int perc = td->o.compress_percentage; @@ -1932,7 +1941,7 @@ void fill_io_buffer(struct thread_data *td, void *buf, unsigned int min_write, unsigned int left = max_bs; do { - rs = get_buf_state(td, &save); + rs = get_buf_state(td); min_write = min(min_write, left); @@ -1951,14 +1960,14 @@ void fill_io_buffer(struct thread_data *td, void *buf, unsigned int min_write, buf += min_write; left -= min_write; - save_buf_state(td, rs, &save); + save_buf_state(td, rs); } while (left); } else if (o->buffer_pattern_bytes) fill_buffer_pattern(td, buf, max_bs); else if (o->zero_buffers) memset(buf, 0, max_bs); else - fill_random_buf(get_buf_state(td, NULL), buf, max_bs); + fill_random_buf(get_buf_state(td), buf, max_bs); } /*