1a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe/* 2da751ca9665bcdeca56d2eec5b629a0953c07662Jens Axboe * null engine 3da751ca9665bcdeca56d2eec5b629a0953c07662Jens Axboe * 4da751ca9665bcdeca56d2eec5b629a0953c07662Jens Axboe * IO engine that doesn't do any real IO transfers, it just pretends to. 5da751ca9665bcdeca56d2eec5b629a0953c07662Jens Axboe * The main purpose is to test fio itself. 6a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe * 746a674786944e964517dd652fbf41807c9395cc4Daniel Gollub * It also can act as external C++ engine - compiled with: 846a674786944e964517dd652fbf41807c9395cc4Daniel Gollub * 946a674786944e964517dd652fbf41807c9395cc4Daniel Gollub * g++ -O2 -g -shared -rdynamic -fPIC -o null.so null.c -DFIO_EXTERNAL_ENGINE 1046a674786944e964517dd652fbf41807c9395cc4Daniel Gollub * 11a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe */ 12a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe#include <stdio.h> 13a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe#include <stdlib.h> 14a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe#include <unistd.h> 15a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe#include <errno.h> 16a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe#include <assert.h> 17a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe 18a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe#include "../fio.h" 19a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe 2065afa5f2146ee010b7129934f68e691faee54982Jens Axboestruct null_data { 2165afa5f2146ee010b7129934f68e691faee54982Jens Axboe struct io_u **io_us; 2265afa5f2146ee010b7129934f68e691faee54982Jens Axboe int queued; 2365afa5f2146ee010b7129934f68e691faee54982Jens Axboe int events; 2465afa5f2146ee010b7129934f68e691faee54982Jens Axboe}; 2565afa5f2146ee010b7129934f68e691faee54982Jens Axboe 2665afa5f2146ee010b7129934f68e691faee54982Jens Axboestatic struct io_u *fio_null_event(struct thread_data *td, int event) 2765afa5f2146ee010b7129934f68e691faee54982Jens Axboe{ 2846a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct null_data *nd = (struct null_data *) td->io_ops->data; 2965afa5f2146ee010b7129934f68e691faee54982Jens Axboe 3065afa5f2146ee010b7129934f68e691faee54982Jens Axboe return nd->io_us[event]; 3165afa5f2146ee010b7129934f68e691faee54982Jens Axboe} 3265afa5f2146ee010b7129934f68e691faee54982Jens Axboe 33e7d2e61694c62b90a2fb84c012b4edcc1973d72cJens Axboestatic int fio_null_getevents(struct thread_data *td, unsigned int min_events, 34e7d2e61694c62b90a2fb84c012b4edcc1973d72cJens Axboe unsigned int fio_unused max, 35e7d2e61694c62b90a2fb84c012b4edcc1973d72cJens Axboe struct timespec fio_unused *t) 3665afa5f2146ee010b7129934f68e691faee54982Jens Axboe{ 3746a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct null_data *nd = (struct null_data *) td->io_ops->data; 387401c088106ba35dcfba62ec753b6b20b72ad0e2Jens Axboe int ret = 0; 397401c088106ba35dcfba62ec753b6b20b72ad0e2Jens Axboe 407401c088106ba35dcfba62ec753b6b20b72ad0e2Jens Axboe if (min_events) { 417401c088106ba35dcfba62ec753b6b20b72ad0e2Jens Axboe ret = nd->events; 427401c088106ba35dcfba62ec753b6b20b72ad0e2Jens Axboe nd->events = 0; 437401c088106ba35dcfba62ec753b6b20b72ad0e2Jens Axboe } 4465afa5f2146ee010b7129934f68e691faee54982Jens Axboe 4565afa5f2146ee010b7129934f68e691faee54982Jens Axboe return ret; 4665afa5f2146ee010b7129934f68e691faee54982Jens Axboe} 4765afa5f2146ee010b7129934f68e691faee54982Jens Axboe 4865afa5f2146ee010b7129934f68e691faee54982Jens Axboestatic int fio_null_commit(struct thread_data *td) 4965afa5f2146ee010b7129934f68e691faee54982Jens Axboe{ 5046a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct null_data *nd = (struct null_data *) td->io_ops->data; 5165afa5f2146ee010b7129934f68e691faee54982Jens Axboe 52ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe if (!nd->events) { 5346a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#ifndef FIO_EXTERNAL_ENGINE 54838bc709279964bdcc64070d4eb2777a0f79bcbbJens Axboe io_u_mark_submit(td, nd->queued); 5546a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#endif 56ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe nd->events = nd->queued; 57ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe nd->queued = 0; 58ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe } 59ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe 6065afa5f2146ee010b7129934f68e691faee54982Jens Axboe return 0; 6165afa5f2146ee010b7129934f68e691faee54982Jens Axboe} 6265afa5f2146ee010b7129934f68e691faee54982Jens Axboe 63f0c48a70c5cb8e9f04d263999e0b8d9188f08562Jens Axboestatic int fio_null_queue(struct thread_data *td, struct io_u *io_u) 64a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe{ 6546a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct null_data *nd = (struct null_data *) td->io_ops->data; 6665afa5f2146ee010b7129934f68e691faee54982Jens Axboe 677101d9c24abec4be58a086d85d6d92ec6e6492e9Jens Axboe fio_ro_check(td, io_u); 687101d9c24abec4be58a086d85d6d92ec6e6492e9Jens Axboe 6965afa5f2146ee010b7129934f68e691faee54982Jens Axboe if (td->io_ops->flags & FIO_SYNCIO) 7065afa5f2146ee010b7129934f68e691faee54982Jens Axboe return FIO_Q_COMPLETED; 71ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe if (nd->events) 72ed8bd849b04b336b8f666a547aafa2661b0d8c89Jens Axboe return FIO_Q_BUSY; 7365afa5f2146ee010b7129934f68e691faee54982Jens Axboe 7465afa5f2146ee010b7129934f68e691faee54982Jens Axboe nd->io_us[nd->queued++] = io_u; 7565afa5f2146ee010b7129934f68e691faee54982Jens Axboe return FIO_Q_QUEUED; 76a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe} 77a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe 78b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboestatic int fio_null_open(struct thread_data fio_unused *td, 79b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboe struct fio_file fio_unused *f) 80b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboe{ 81b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboe return 0; 82b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboe} 83b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboe 8465afa5f2146ee010b7129934f68e691faee54982Jens Axboestatic void fio_null_cleanup(struct thread_data *td) 8565afa5f2146ee010b7129934f68e691faee54982Jens Axboe{ 8646a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct null_data *nd = (struct null_data *) td->io_ops->data; 8765afa5f2146ee010b7129934f68e691faee54982Jens Axboe 8865afa5f2146ee010b7129934f68e691faee54982Jens Axboe if (nd) { 8965afa5f2146ee010b7129934f68e691faee54982Jens Axboe if (nd->io_us) 9065afa5f2146ee010b7129934f68e691faee54982Jens Axboe free(nd->io_us); 9165afa5f2146ee010b7129934f68e691faee54982Jens Axboe free(nd); 9265afa5f2146ee010b7129934f68e691faee54982Jens Axboe } 9365afa5f2146ee010b7129934f68e691faee54982Jens Axboe} 9465afa5f2146ee010b7129934f68e691faee54982Jens Axboe 9565afa5f2146ee010b7129934f68e691faee54982Jens Axboestatic int fio_null_init(struct thread_data *td) 9665afa5f2146ee010b7129934f68e691faee54982Jens Axboe{ 9746a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct null_data *nd = (struct null_data *) malloc(sizeof(*nd)); 9865afa5f2146ee010b7129934f68e691faee54982Jens Axboe 9965afa5f2146ee010b7129934f68e691faee54982Jens Axboe memset(nd, 0, sizeof(*nd)); 10065afa5f2146ee010b7129934f68e691faee54982Jens Axboe 1012dc1bbeb58edc85f2829eed6729862c438ea2353Jens Axboe if (td->o.iodepth != 1) { 10246a674786944e964517dd652fbf41807c9395cc4Daniel Gollub nd->io_us = (struct io_u **) malloc(td->o.iodepth * sizeof(struct io_u *)); 1032dc1bbeb58edc85f2829eed6729862c438ea2353Jens Axboe memset(nd->io_us, 0, td->o.iodepth * sizeof(struct io_u *)); 10465afa5f2146ee010b7129934f68e691faee54982Jens Axboe } else 10565afa5f2146ee010b7129934f68e691faee54982Jens Axboe td->io_ops->flags |= FIO_SYNCIO; 10665afa5f2146ee010b7129934f68e691faee54982Jens Axboe 10765afa5f2146ee010b7129934f68e691faee54982Jens Axboe td->io_ops->data = nd; 10865afa5f2146ee010b7129934f68e691faee54982Jens Axboe return 0; 10965afa5f2146ee010b7129934f68e691faee54982Jens Axboe} 11065afa5f2146ee010b7129934f68e691faee54982Jens Axboe 11146a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#ifndef __cplusplus 112a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboestatic struct ioengine_ops ioengine = { 113a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe .name = "null", 114a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe .version = FIO_IOOPS_VERSION, 115a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe .queue = fio_null_queue, 11665afa5f2146ee010b7129934f68e691faee54982Jens Axboe .commit = fio_null_commit, 11765afa5f2146ee010b7129934f68e691faee54982Jens Axboe .getevents = fio_null_getevents, 11865afa5f2146ee010b7129934f68e691faee54982Jens Axboe .event = fio_null_event, 11965afa5f2146ee010b7129934f68e691faee54982Jens Axboe .init = fio_null_init, 12065afa5f2146ee010b7129934f68e691faee54982Jens Axboe .cleanup = fio_null_cleanup, 121b5af82930ccfd7dda6a1b11794efb452eb76d8dcJens Axboe .open_file = fio_null_open, 12265afa5f2146ee010b7129934f68e691faee54982Jens Axboe .flags = FIO_DISKLESSIO, 123a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe}; 124a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe 125a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboestatic void fio_init fio_null_register(void) 126a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe{ 127a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe register_ioengine(&ioengine); 128a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe} 129a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe 130a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboestatic void fio_exit fio_null_unregister(void) 131a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe{ 132a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe unregister_ioengine(&ioengine); 133a94ea28b13429c38036546c36bcfd7355dc1441dJens Axboe} 13446a674786944e964517dd652fbf41807c9395cc4Daniel Gollub 13546a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#else 13646a674786944e964517dd652fbf41807c9395cc4Daniel Gollub 13746a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#ifdef FIO_EXTERNAL_ENGINE 13846a674786944e964517dd652fbf41807c9395cc4Daniel Gollubextern "C" { 1398d6ecac27d36b3001c8fed00eab7f32cd573636aJens Axboevoid get_ioengine(struct ioengine_ops **ioengine_ptr) 1408d6ecac27d36b3001c8fed00eab7f32cd573636aJens Axboe{ 14146a674786944e964517dd652fbf41807c9395cc4Daniel Gollub struct ioengine_ops *ioengine; 1428d6ecac27d36b3001c8fed00eab7f32cd573636aJens Axboe 14346a674786944e964517dd652fbf41807c9395cc4Daniel Gollub *ioengine_ptr = (struct ioengine_ops *) malloc(sizeof(struct ioengine_ops)); 14446a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine = *ioengine_ptr; 14546a674786944e964517dd652fbf41807c9395cc4Daniel Gollub 14646a674786944e964517dd652fbf41807c9395cc4Daniel Gollub strcpy(ioengine->name, "cpp_null"); 14746a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->version = FIO_IOOPS_VERSION; 14846a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->queue = fio_null_queue; 14946a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->commit = fio_null_commit; 15046a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->getevents = fio_null_getevents; 15146a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->event = fio_null_event; 15246a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->init = fio_null_init; 15346a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->cleanup = fio_null_cleanup; 15446a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->open_file = fio_null_open; 15546a674786944e964517dd652fbf41807c9395cc4Daniel Gollub ioengine->flags = FIO_DISKLESSIO; 15646a674786944e964517dd652fbf41807c9395cc4Daniel Gollub} 15746a674786944e964517dd652fbf41807c9395cc4Daniel Gollub} 15846a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#endif /* FIO_EXTERNAL_ENGINE */ 15946a674786944e964517dd652fbf41807c9395cc4Daniel Gollub 16046a674786944e964517dd652fbf41807c9395cc4Daniel Gollub#endif /* __cplusplus */ 161