diff --git a/backend.c b/backend.c index 399c299e14..cb4f40826a 100644 --- a/backend.c +++ b/backend.c @@ -2251,9 +2251,11 @@ static bool waitee_running(struct thread_data *me) static void run_threads(struct sk_out *sk_out) { struct thread_data *td; - unsigned int i, todo, nr_running, nr_started; + struct timespec last_finish_time; + unsigned int i, todo, nr_running, nr_started, prev_nr_running; uint64_t m_rate, t_rate; uint64_t spent; + uint64_t per_job_spent; if (fio_gtod_offload && fio_start_gtod_thread()) return; @@ -2294,6 +2296,7 @@ static void run_threads(struct sk_out *sk_out) todo = thread_number; nr_running = 0; nr_started = 0; + prev_nr_running = 0; m_rate = t_rate = 0; for_each_td(td, i) { @@ -2338,6 +2341,7 @@ static void run_threads(struct sk_out *sk_out) fio_idle_prof_start(); set_genesis_time(); + fio_gettime(&last_finish_time, NULL); while (todo) { struct thread_data *map[REAL_MAX_JOBS]; @@ -2380,6 +2384,13 @@ static void run_threads(struct sk_out *sk_out) continue; } + if (td->o.stonewall && td->o.per_job_start_delay) { + per_job_spent = utime_since_now(&last_finish_time); + + if (td->o.per_job_start_delay > per_job_spent) + continue; + } + init_disk_util(td); td->rusage_sem = fio_sem_init(FIO_SEM_LOCKED); @@ -2498,7 +2509,12 @@ static void run_threads(struct sk_out *sk_out) fio_sem_up(td->sem); } + prev_nr_running = nr_running; reap_threads(&nr_running, &t_rate, &m_rate); + if (nr_running == prev_nr_running - 1) { + //sequential job has finished get new base time + fio_gettime(&last_finish_time, NULL); + } if (todo) do_usleep(100000); diff --git a/options.c b/options.c index ddabaa82d2..66130a429e 100644 --- a/options.c +++ b/options.c @@ -2744,6 +2744,19 @@ struct fio_option fio_options[FIO_MAX_OPTS] = { .category = FIO_OPT_C_GENERAL, .group = FIO_OPT_G_RUNTIME, }, + { + .name = "per_job_startdelay", + .lname = "Per Job Start delay", + .type = FIO_OPT_STR_VAL_TIME, + .off1 = offsetof(struct thread_options, per_job_start_delay), + .off2 = offsetof(struct thread_options, per_job_start_delay_high), + .help = "Only start job when this period has passed", + .def = "0", + .is_seconds = 1, + .is_time = 1, + .category = FIO_OPT_C_GENERAL, + .group = FIO_OPT_G_RUNTIME, + }, { .name = "runtime", .lname = "Runtime", diff --git a/thread_options.h b/thread_options.h index 5ecc72d7b5..ab794b6311 100644 --- a/thread_options.h +++ b/thread_options.h @@ -187,6 +187,9 @@ struct thread_options { unsigned long long start_delay; unsigned long long start_delay_orig; unsigned long long start_delay_high; + unsigned long long per_job_start_delay; + unsigned long long per_job_start_delay_orig; + unsigned long long per_job_start_delay_high; unsigned long long timeout; unsigned long long ramp_time; unsigned int ss_state;