+FILE *get_f_out(void);
+FILE *get_f_err(void);
+
+struct ioengine_ops {
+ struct list_head list;
+ char name[16];
+ int version;
+ int flags;
+ int (*setup)(struct thread_data *);
+ int (*init)(struct thread_data *);
+ int (*prep)(struct thread_data *, struct io_u *);
+ int (*queue)(struct thread_data *, struct io_u *);
+ int (*commit)(struct thread_data *);
+ int (*getevents)(struct thread_data *, int, int, struct timespec *);
+ struct io_u *(*event)(struct thread_data *, int);
+ int (*cancel)(struct thread_data *, struct io_u *);
+ void (*cleanup)(struct thread_data *);
+ int (*open_file)(struct thread_data *, struct fio_file *);
+ void (*close_file)(struct thread_data *, struct fio_file *);
+ void *data;
+ void *dlhandle;
+};
+
+#define FIO_IOOPS_VERSION 6
+
+extern struct ioengine_ops *load_ioengine(struct thread_data *, const char *);
+extern void register_ioengine(struct ioengine_ops *);
+extern void unregister_ioengine(struct ioengine_ops *);
+extern void close_ioengine(struct thread_data *);
+
+/*
+ * Mark unused variables passed to ops functions as unused, to silence gcc
+ */
+#define fio_unused __attribute((__unused__))
+#define fio_init __attribute__((constructor))
+#define fio_exit __attribute__((destructor))
+
+#define for_each_td(td, i) \
+ for ((i) = 0, (td) = &threads[0]; (i) < (int) thread_number; (i)++, (td)++)
+#define for_each_file(td, f, i) \
+ for ((i) = 0, (f) = &(td)->files[0]; (i) < (int) (td)->open_files; (i)++, (f)++)
+
+#define fio_assert(td, cond) do { \
+ if (!(cond)) { \
+ int *__foo = NULL; \
+ fprintf(stderr, "file:%s:%d, assert %s failed\n", __FILE__, __LINE__, #cond); \
+ (td)->runstate = TD_EXITED; \
+ (td)->error = EFAULT; \
+ *__foo = 0; \
+ } \
+} while (0)
+