X-Git-Url: https://git.kernel.dk/?p=fio.git;a=blobdiff_plain;f=fio.c;h=e71537fc9d45c379d53c001d1ae160e42b6eb435;hp=1e69ce4228c624f3775a95e3299bde84c1e0baef;hb=ac684785b41aaf17593b375be8d3e89b83974c1a;hpb=b3f378e90231ecb2082ec565bafb3f721c4f1902 diff --git a/fio.c b/fio.c index 1e69ce42..e71537fc 100644 --- a/fio.c +++ b/fio.c @@ -446,6 +446,13 @@ static void do_io(struct thread_data *td) break; } + /* + * Add verification end_io handler, if asked to verify + * a previously written file. + */ + if (td->o.verify != VERIFY_NONE) + io_u->end_io = verify_io_u; + ret = td_io_queue(td, io_u); switch (ret) { case FIO_Q_COMPLETED: @@ -650,10 +657,12 @@ static int init_io_u(struct thread_data *td) memset(io_u, 0, sizeof(*io_u)); INIT_LIST_HEAD(&io_u->list); - io_u->buf = p + max_bs * i; + if (!(td->io_ops->flags & FIO_NOIO)) { + io_u->buf = p + max_bs * i; - if (td_write(td)) - fill_io_buf(td, io_u, max_bs); + if (td_write(td)) + fill_io_buf(td, io_u, max_bs); + } io_u->index = i; io_u->flags = IO_U_F_FREE; @@ -724,6 +733,8 @@ static int keep_running(struct thread_data *td) { unsigned long long io_done; + if (td->done) + return 0; if (td->o.time_based) return 1; if (td->o.loops) { @@ -731,7 +742,7 @@ static int keep_running(struct thread_data *td) return 1; } - io_done = td->io_bytes[DDIR_READ] + td->io_bytes[DDIR_WRITE]; + io_done = td->io_bytes[DDIR_READ] + td->io_bytes[DDIR_WRITE] + td->io_skip_bytes; if (io_done < td->o.size) return 1; @@ -753,7 +764,8 @@ static int clear_io_state(struct thread_data *td) td->last_was_sync = 0; - td->nr_done_files = 0; + if (td->o.time_based) + td->nr_done_files = 0; for_each_file(td, f, i) td_io_close_file(td, f); @@ -817,7 +829,7 @@ static void *thread_main(void *data) goto err; } - if (td->ioprio) { + if (td->ioprio_set) { if (ioprio_set(IOPRIO_WHO_PROCESS, 0, td->ioprio) == -1) { td_verror(td, errno, "ioprio_set"); goto err; @@ -891,7 +903,9 @@ static void *thread_main(void *data) if (td->error || td->terminate) break; - if (td->o.verify == VERIFY_NONE) + if (!td->o.do_verify || + td->o.verify == VERIFY_NONE || + (td->io_ops->flags & FIO_UNIDIR)) continue; if (clear_io_state(td)) @@ -908,8 +922,8 @@ static void *thread_main(void *data) } update_rusage_stat(td); - td->ts.runtime[0] = runtime[0] / 1000; - td->ts.runtime[1] = runtime[1] / 1000; + td->ts.runtime[0] = (runtime[0] + 999) / 1000; + td->ts.runtime[1] = (runtime[1] + 999) / 1000; td->ts.total_run_time = mtime_since_now(&td->epoch); td->ts.io_bytes[0] = td->io_bytes[0]; td->ts.io_bytes[1] = td->io_bytes[1]; @@ -920,8 +934,6 @@ static void *thread_main(void *data) finish_log(td, td->ts.slat_log, "slat"); if (td->ts.clat_log) finish_log(td, td->ts.clat_log, "clat"); - if (td->o.write_iolog_file) - write_iolog_close(td); if (td->o.exec_postrun) { if (system(td->o.exec_postrun) < 0) log_err("fio: postrun %s failed\n", td->o.exec_postrun); @@ -936,6 +948,13 @@ err: close_files(td); close_ioengine(td); cleanup_io_u(td); + + /* + * do this very late, it will log file closing as well + */ + if (td->o.write_iolog_file) + write_iolog_close(td); + options_mem_free(td); td_set_runstate(td, TD_EXITED); return (void *) (unsigned long) td->error; @@ -970,12 +989,12 @@ static int fork_main(int shmid, int offset) static void reap_threads(int *nr_running, int *t_rate, int *m_rate) { struct thread_data *td; - int i, cputhreads, pending, status, ret; + int i, cputhreads, realthreads, pending, status, ret; /* * reap exited threads (TD_EXITED -> TD_REAPED) */ - pending = cputhreads = 0; + realthreads = pending = cputhreads = 0; for_each_td(td, i) { int flags = 0; @@ -985,6 +1004,8 @@ static void reap_threads(int *nr_running, int *t_rate, int *m_rate) */ if (td->io_ops && !strcmp(td->io_ops->name, "cpuio")) cputhreads++; + else + realthreads++; if (!td->pid || td->runstate == TD_REAPED) continue; @@ -1051,7 +1072,7 @@ reaped: exit_value++; } - if (*nr_running == cputhreads && !pending) + if (*nr_running == cputhreads && !pending && realthreads) terminate_threads(TERMINATE_ALL); }