/*
 * Native Solaris async IO engine
 *
 */
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
#include <errno.h>

#include "../fio.h"

#include <sys/asynch.h>

struct solarisaio_data {
	struct io_u **aio_events;
	unsigned int aio_pending;
	unsigned int nr;
	unsigned int max_depth;
};

static int fio_solarisaio_cancel(struct thread_data fio_unused *td,
			       struct io_u *io_u)
{
	return aiocancel(&io_u->resultp);
}

static int fio_solarisaio_prep(struct thread_data fio_unused *td,
			    struct io_u *io_u)
{
	struct solarisaio_data *sd = td->io_ops->data;

	io_u->resultp.aio_return = AIO_INPROGRESS;
	io_u->engine_data = sd;
	return 0;
}

static void wait_for_event(struct timeval *tv)
{
	struct solarisaio_data *sd;
	struct io_u *io_u;
	aio_result_t *res;

	res = aiowait(tv);
	if (res == (aio_result_t *) -1) {
		int err = errno;

		if (err != EINVAL) {
			log_err("fio: solarisaio got %d in aiowait\n", err);
			exit(err);
		}
		return;
	} else if (!res)
		return;

	io_u = container_of(res, struct io_u, resultp);
	sd = io_u->engine_data;

	if (io_u->resultp.aio_return >= 0) {
		io_u->resid = io_u->xfer_buflen - io_u->resultp.aio_return;
		io_u->error = 0;
	} else
		io_u->error = io_u->resultp.aio_errno;

	/*
	 * For SIGIO, we need a write barrier between the two, so that
	 * the ->aio_pending store is seen after the ->aio_events store
	 */
	sd->aio_events[sd->aio_pending] = io_u;
	write_barrier();
	sd->aio_pending++;
	sd->nr--;
}

static int fio_solarisaio_getevents(struct thread_data *td, unsigned int min,
				    unsigned int max, const struct timespec *t)
{
	struct solarisaio_data *sd = td->io_ops->data;
	struct timeval tv;
	int ret;

	if (!min || !t) {
		tv.tv_sec = 0;
		tv.tv_usec = 0;
	} else {
		tv.tv_sec = t->tv_sec;
		tv.tv_usec = t->tv_nsec / 1000;
	}

	while (sd->aio_pending < min)
		wait_for_event(&tv);

	/*
	 * should be OK without locking, as int operations should be atomic
	 */
	ret = sd->aio_pending;
	sd->aio_pending -= ret;
	return ret;
}

static struct io_u *fio_solarisaio_event(struct thread_data *td, int event)
{
	struct solarisaio_data *sd = td->io_ops->data;

	return sd->aio_events[event];
}

static int fio_solarisaio_queue(struct thread_data fio_unused *td,
			      struct io_u *io_u)
{
	struct solarisaio_data *sd = td->io_ops->data;
	struct fio_file *f = io_u->file;
	off_t off;
	int ret;

	fio_ro_check(td, io_u);

	if (io_u->ddir == DDIR_SYNC) {
		if (sd->nr)
			return FIO_Q_BUSY;
		if (fsync(f->fd) < 0)
			io_u->error = errno;

		return FIO_Q_COMPLETED;
	}

	if (io_u->ddir == DDIR_DATASYNC) {
		if (sd->nr)
			return FIO_Q_BUSY;
		if (fdatasync(f->fd) < 0)
			io_u->error = errno;

		return FIO_Q_COMPLETED;
	}

	if (sd->nr == sd->max_depth)
		return FIO_Q_BUSY;

	off = io_u->offset;
	if (io_u->ddir == DDIR_READ)
		ret = aioread(f->fd, io_u->xfer_buf, io_u->xfer_buflen, off,
					SEEK_SET, &io_u->resultp);
	else
		ret = aiowrite(f->fd, io_u->xfer_buf, io_u->xfer_buflen, off,
					SEEK_SET, &io_u->resultp);
	if (ret) {
		io_u->error = errno;
		td_verror(td, io_u->error, "xfer");
		return FIO_Q_COMPLETED;
	}

	sd->nr++;
	return FIO_Q_QUEUED;
}

static void fio_solarisaio_cleanup(struct thread_data *td)
{
	struct solarisaio_data *sd = td->io_ops->data;

	if (sd) {
		free(sd->aio_events);
		free(sd);
	}
}

/*
 * Set USE_SIGNAL_COMPLETIONS to use SIGIO as completion events.
 */
#ifdef USE_SIGNAL_COMPLETIONS
static void fio_solarisaio_sigio(int sig)
{
	wait_for_event(NULL);
}

static void fio_solarisaio_init_sigio(void)
{
	struct sigaction act;

	memset(&act, 0, sizeof(act));
	act.sa_handler = fio_solarisaio_sigio;
	act.sa_flags = SA_RESTART;
	sigaction(SIGIO, &act, NULL);
}
#endif

static int fio_solarisaio_init(struct thread_data *td)
{
	struct solarisaio_data *sd = malloc(sizeof(*sd));
	unsigned int max_depth;

	max_depth = td->o.iodepth;
	if (max_depth > MAXASYNCHIO) {
		max_depth = MAXASYNCHIO;
		log_info("fio: lower depth to %d due to OS constraints\n",
							max_depth);
	}

	memset(sd, 0, sizeof(*sd));
	sd->aio_events = malloc(max_depth * sizeof(struct io_u *));
	memset(sd->aio_events, 0, max_depth * sizeof(struct io_u *));
	sd->max_depth = max_depth;

#ifdef USE_SIGNAL_COMPLETIONS
	fio_solarisaio_init_sigio();
#endif

	td->io_ops->data = sd;
	return 0;
}

static struct ioengine_ops ioengine = {
	.name		= "solarisaio",
	.version	= FIO_IOOPS_VERSION,
	.init		= fio_solarisaio_init,
	.prep		= fio_solarisaio_prep,
	.queue		= fio_solarisaio_queue,
	.cancel		= fio_solarisaio_cancel,
	.getevents	= fio_solarisaio_getevents,
	.event		= fio_solarisaio_event,
	.cleanup	= fio_solarisaio_cleanup,
	.open_file	= generic_open_file,
	.close_file	= generic_close_file,
	.get_file_size	= generic_get_file_size,
};

static void fio_init fio_solarisaio_register(void)
{
	register_ioengine(&ioengine);
}

static void fio_exit fio_solarisaio_unregister(void)
{
	unregister_ioengine(&ioengine);
}
