// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright 2023 Red Hat
 */

#include "io-submitter.h"

#include <linux/bio.h>
#include <linux/kernel.h>
#include <linux/mutex.h>

#include "memory-alloc.h"
#include "permassert.h"

#include "data-vio.h"
#include "logger.h"
#include "types.h"
#include "vdo.h"
#include "vio.h"

/*
 * Submission of bio operations to the underlying storage device will go through a separate work
 * queue thread (or more than one) to prevent blocking in other threads if the storage device has a
 * full queue. The plug structure allows that thread to do better batching of requests to make the
 * I/O more efficient.
 *
 * When multiple worker threads are used, a thread is chosen for a I/O operation submission based
 * on the PBN, so a given PBN will consistently wind up on the same thread. Flush operations are
 * assigned round-robin.
 *
 * The map (protected by the mutex) collects pending I/O operations so that the worker thread can
 * reorder them to try to encourage I/O request merging in the request queue underneath.
 */
struct bio_queue_data {
	struct vdo_work_queue *queue;
	struct blk_plug plug;
	struct int_map *map;
	struct mutex lock;
	unsigned int queue_number;
};

struct io_submitter {
	unsigned int num_bio_queues_used;
	unsigned int bio_queue_rotation_interval;
	struct bio_queue_data bio_queue_data[];
};

static void start_bio_queue(void *ptr)
{
	struct bio_queue_data *bio_queue_data = ptr;

	blk_start_plug(&bio_queue_data->plug);
}

static void finish_bio_queue(void *ptr)
{
	struct bio_queue_data *bio_queue_data = ptr;

	blk_finish_plug(&bio_queue_data->plug);
}

static const struct vdo_work_queue_type bio_queue_type = {
	.start = start_bio_queue,
	.finish = finish_bio_queue,
	.max_priority = BIO_Q_MAX_PRIORITY,
	.default_priority = BIO_Q_DATA_PRIORITY,
};

/**
 * count_all_bios() - Determine which bio counter to use.
 * @vio: The vio associated with the bio.
 * @bio: The bio to count.
 */
static void count_all_bios(struct vio *vio, struct bio *bio)
{
	struct atomic_statistics *stats = &vio->completion.vdo->stats;

	if (is_data_vio(vio)) {
		vdo_count_bios(&stats->bios_out, bio);
		return;
	}

	vdo_count_bios(&stats->bios_meta, bio);
	if (vio->type == VIO_TYPE_RECOVERY_JOURNAL)
		vdo_count_bios(&stats->bios_journal, bio);
	else if (vio->type == VIO_TYPE_BLOCK_MAP)
		vdo_count_bios(&stats->bios_page_cache, bio);
}

/**
 * assert_in_bio_zone() - Assert that a vio is in the correct bio zone and not in interrupt
 *                        context.
 * @vio: The vio to check.
 */
static void assert_in_bio_zone(struct vio *vio)
{
	VDO_ASSERT_LOG_ONLY(!in_interrupt(), "not in interrupt context");
	assert_vio_in_bio_zone(vio);
}

/**
 * send_bio_to_device() - Update stats and tracing info, then submit the supplied bio to the OS for
 *                        processing.
 * @vio: The vio associated with the bio.
 * @bio: The bio to submit to the OS.
 */
static void send_bio_to_device(struct vio *vio, struct bio *bio)
{
	struct vdo *vdo = vio->completion.vdo;

	assert_in_bio_zone(vio);
	atomic64_inc(&vdo->stats.bios_submitted);
	count_all_bios(vio, bio);
	bio_set_dev(bio, vdo_get_backing_device(vdo));
	submit_bio_noacct(bio);
}

/**
 * vdo_submit_vio() - Submits a vio's bio to the underlying block device. May block if the device
 *		      is busy. This callback should be used by vios which did not attempt to merge.
 */
void vdo_submit_vio(struct vdo_completion *completion)
{
	struct vio *vio = as_vio(completion);

	send_bio_to_device(vio, vio->bio);
}

/**
 * get_bio_list() - Extract the list of bios to submit from a vio.
 * @vio: The vio submitting I/O.
 *
 * The list will always contain at least one entry (the bio for the vio on which it is called), but
 * other bios may have been merged with it as well.
 *
 * Return: bio  The head of the bio list to submit.
 */
static struct bio *get_bio_list(struct vio *vio)
{
	struct bio *bio;
	struct io_submitter *submitter = vio->completion.vdo->io_submitter;
	struct bio_queue_data *bio_queue_data = &(submitter->bio_queue_data[vio->bio_zone]);

	assert_in_bio_zone(vio);

	mutex_lock(&bio_queue_data->lock);
	vdo_int_map_remove(bio_queue_data->map,
			   vio->bios_merged.head->bi_iter.bi_sector);
	vdo_int_map_remove(bio_queue_data->map,
			   vio->bios_merged.tail->bi_iter.bi_sector);
	bio = vio->bios_merged.head;
	bio_list_init(&vio->bios_merged);
	mutex_unlock(&bio_queue_data->lock);

	return bio;
}

/**
 * submit_data_vio() - Submit a data_vio's bio to the storage below along with
 *		       any bios that have been merged with it.
 *
 * Context: This call may block and so should only be called from a bio thread.
 */
static void submit_data_vio(struct vdo_completion *completion)
{
	struct bio *bio, *next;
	struct vio *vio = as_vio(completion);

	assert_in_bio_zone(vio);
	for (bio = get_bio_list(vio); bio != NULL; bio = next) {
		next = bio->bi_next;
		bio->bi_next = NULL;
		send_bio_to_device((struct vio *) bio->bi_private, bio);
	}
}

/**
 * get_mergeable_locked() - Attempt to find an already queued bio that the current bio can be
 *                          merged with.
 * @map: The bio map to use for merging.
 * @vio: The vio we want to merge.
 * @back_merge: Set to true for a back merge, false for a front merge.
 *
 * There are two types of merging possible, forward and backward, which are distinguished by a flag
 * that uses kernel elevator terminology.
 *
 * Return: the vio to merge to, NULL if no merging is possible.
 */
static struct vio *get_mergeable_locked(struct int_map *map, struct vio *vio,
					bool back_merge)
{
	struct bio *bio = vio->bio;
	sector_t merge_sector = bio->bi_iter.bi_sector;
	struct vio *vio_merge;

	if (back_merge)
		merge_sector -= VDO_SECTORS_PER_BLOCK;
	else
		merge_sector += VDO_SECTORS_PER_BLOCK;

	vio_merge = vdo_int_map_get(map, merge_sector);

	if (vio_merge == NULL)
		return NULL;

	if (vio->completion.priority != vio_merge->completion.priority)
		return NULL;

	if (bio_data_dir(bio) != bio_data_dir(vio_merge->bio))
		return NULL;

	if (bio_list_empty(&vio_merge->bios_merged))
		return NULL;

	if (back_merge) {
		return (vio_merge->bios_merged.tail->bi_iter.bi_sector == merge_sector ?
			vio_merge : NULL);
	}

	return (vio_merge->bios_merged.head->bi_iter.bi_sector == merge_sector ?
		vio_merge : NULL);
}

static int map_merged_vio(struct int_map *bio_map, struct vio *vio)
{
	int result;
	sector_t bio_sector;

	bio_sector = vio->bios_merged.head->bi_iter.bi_sector;
	result = vdo_int_map_put(bio_map, bio_sector, vio, true, NULL);
	if (result != VDO_SUCCESS)
		return result;

	bio_sector = vio->bios_merged.tail->bi_iter.bi_sector;
	return vdo_int_map_put(bio_map, bio_sector, vio, true, NULL);
}

static int merge_to_prev_tail(struct int_map *bio_map, struct vio *vio,
			      struct vio *prev_vio)
{
	vdo_int_map_remove(bio_map, prev_vio->bios_merged.tail->bi_iter.bi_sector);
	bio_list_merge(&prev_vio->bios_merged, &vio->bios_merged);
	return map_merged_vio(bio_map, prev_vio);
}

static int merge_to_next_head(struct int_map *bio_map, struct vio *vio,
			      struct vio *next_vio)
{
	/*
	 * Handle "next merge" and "gap fill" cases the same way so as to reorder bios in a way
	 * that's compatible with using funnel queues in work queues. This avoids removing an
	 * existing completion.
	 */
	vdo_int_map_remove(bio_map, next_vio->bios_merged.head->bi_iter.bi_sector);
	bio_list_merge_head(&next_vio->bios_merged, &vio->bios_merged);
	return map_merged_vio(bio_map, next_vio);
}

/**
 * try_bio_map_merge() - Attempt to merge a vio's bio with other pending I/Os.
 * @vio: The vio to merge.
 *
 * Currently this is only used for data_vios, but is broken out for future use with metadata vios.
 *
 * Return: whether or not the vio was merged.
 */
static bool try_bio_map_merge(struct vio *vio)
{
	int result;
	bool merged = true;
	struct bio *bio = vio->bio;
	struct vio *prev_vio, *next_vio;
	struct vdo *vdo = vio->completion.vdo;
	struct bio_queue_data *bio_queue_data =
		&vdo->io_submitter->bio_queue_data[vio->bio_zone];

	bio->bi_next = NULL;
	bio_list_init(&vio->bios_merged);
	bio_list_add(&vio->bios_merged, bio);

	mutex_lock(&bio_queue_data->lock);
	prev_vio = get_mergeable_locked(bio_queue_data->map, vio, true);
	next_vio = get_mergeable_locked(bio_queue_data->map, vio, false);
	if (prev_vio == next_vio)
		next_vio = NULL;

	if ((prev_vio == NULL) && (next_vio == NULL)) {
		/* no merge. just add to bio_queue */
		merged = false;
		result = vdo_int_map_put(bio_queue_data->map,
					 bio->bi_iter.bi_sector,
					 vio, true, NULL);
	} else if (next_vio == NULL) {
		/* Only prev. merge to prev's tail */
		result = merge_to_prev_tail(bio_queue_data->map, vio, prev_vio);
	} else {
		/* Only next. merge to next's head */
		result = merge_to_next_head(bio_queue_data->map, vio, next_vio);
	}
	mutex_unlock(&bio_queue_data->lock);

	/* We don't care about failure of int_map_put in this case. */
	VDO_ASSERT_LOG_ONLY(result == VDO_SUCCESS, "bio map insertion succeeds");
	return merged;
}

/**
 * vdo_submit_data_vio() - Submit I/O for a data_vio.
 * @data_vio: the data_vio for which to issue I/O.
 *
 * If possible, this I/O will be merged other pending I/Os. Otherwise, the data_vio will be sent to
 * the appropriate bio zone directly.
 */
void vdo_submit_data_vio(struct data_vio *data_vio)
{
	if (try_bio_map_merge(&data_vio->vio))
		return;

	launch_data_vio_bio_zone_callback(data_vio, submit_data_vio);
}

/**
 * __submit_metadata_vio() - Submit I/O for a metadata vio.
 * @vio: the vio for which to issue I/O
 * @physical: the physical block number to read or write
 * @callback: the bio endio function which will be called after the I/O completes
 * @error_handler: the handler for submission or I/O errors (may be NULL)
 * @operation: the type of I/O to perform
 * @data: the buffer to read or write (may be NULL)
 *
 * The vio is enqueued on a vdo bio queue so that bio submission (which may block) does not block
 * other vdo threads.
 *
 * That the error handler will run on the correct thread is only true so long as the thread calling
 * this function, and the thread set in the endio callback are the same, as well as the fact that
 * no error can occur on the bio queue. Currently this is true for all callers, but additional care
 * will be needed if this ever changes.
 */
void __submit_metadata_vio(struct vio *vio, physical_block_number_t physical,
			   bio_end_io_t callback, vdo_action_fn error_handler,
			   blk_opf_t operation, char *data)
{
	int result;
	struct vdo_completion *completion = &vio->completion;
	const struct admin_state_code *code = vdo_get_admin_state(completion->vdo);


	VDO_ASSERT_LOG_ONLY(!code->quiescent, "I/O not allowed in state %s", code->name);

	vdo_reset_completion(completion);
	completion->error_handler = error_handler;
	result = vio_reset_bio(vio, data, callback, operation | REQ_META, physical);
	if (result != VDO_SUCCESS) {
		continue_vio(vio, result);
		return;
	}

	vdo_set_completion_callback(completion, vdo_submit_vio,
				    get_vio_bio_zone_thread_id(vio));
	vdo_launch_completion_with_priority(completion, get_metadata_priority(vio));
}

/**
 * vdo_make_io_submitter() - Create an io_submitter structure.
 * @thread_count: Number of bio-submission threads to set up.
 * @rotation_interval: Interval to use when rotating between bio-submission threads when enqueuing
 *                     completions.
 * @max_requests_active: Number of bios for merge tracking.
 * @vdo: The vdo which will use this submitter.
 * @io_submitter: pointer to the new data structure.
 *
 * Return: VDO_SUCCESS or an error.
 */
int vdo_make_io_submitter(unsigned int thread_count, unsigned int rotation_interval,
			  unsigned int max_requests_active, struct vdo *vdo,
			  struct io_submitter **io_submitter_ptr)
{
	unsigned int i;
	struct io_submitter *io_submitter;
	int result;

	result = vdo_allocate_extended(struct io_submitter, thread_count,
				       struct bio_queue_data, "bio submission data",
				       &io_submitter);
	if (result != VDO_SUCCESS)
		return result;

	io_submitter->bio_queue_rotation_interval = rotation_interval;

	/* Setup for each bio-submission work queue */
	for (i = 0; i < thread_count; i++) {
		struct bio_queue_data *bio_queue_data = &io_submitter->bio_queue_data[i];

		mutex_init(&bio_queue_data->lock);
		/*
		 * One I/O operation per request, but both first & last sector numbers.
		 *
		 * If requests are assigned to threads round-robin, they should be distributed
		 * quite evenly. But if they're assigned based on PBN, things can sometimes be very
		 * uneven. So for now, we'll assume that all requests *may* wind up on one thread,
		 * and thus all in the same map.
		 */
		result = vdo_int_map_create(max_requests_active * 2,
					    &bio_queue_data->map);
		if (result != VDO_SUCCESS) {
			/*
			 * Clean up the partially initialized bio-queue entirely and indicate that
			 * initialization failed.
			 */
			vdo_log_error("bio map initialization failed %d", result);
			vdo_cleanup_io_submitter(io_submitter);
			vdo_free_io_submitter(io_submitter);
			return result;
		}

		bio_queue_data->queue_number = i;
		result = vdo_make_thread(vdo, vdo->thread_config.bio_threads[i],
					 &bio_queue_type, 1, (void **) &bio_queue_data);
		if (result != VDO_SUCCESS) {
			/*
			 * Clean up the partially initialized bio-queue entirely and indicate that
			 * initialization failed.
			 */
			vdo_int_map_free(vdo_forget(bio_queue_data->map));
			vdo_log_error("bio queue initialization failed %d", result);
			vdo_cleanup_io_submitter(io_submitter);
			vdo_free_io_submitter(io_submitter);
			return result;
		}

		bio_queue_data->queue = vdo->threads[vdo->thread_config.bio_threads[i]].queue;
		io_submitter->num_bio_queues_used++;
	}

	*io_submitter_ptr = io_submitter;

	return VDO_SUCCESS;
}

/**
 * vdo_cleanup_io_submitter() - Tear down the io_submitter fields as needed for a physical layer.
 * @io_submitter: The I/O submitter data to tear down (may be NULL).
 */
void vdo_cleanup_io_submitter(struct io_submitter *io_submitter)
{
	int i;

	if (io_submitter == NULL)
		return;

	for (i = io_submitter->num_bio_queues_used - 1; i >= 0; i--)
		vdo_finish_work_queue(io_submitter->bio_queue_data[i].queue);
}

/**
 * vdo_free_io_submitter() - Free the io_submitter fields and structure as needed.
 * @io_submitter: The I/O submitter data to destroy.
 *
 * This must be called after vdo_cleanup_io_submitter(). It is used to release resources late in
 * the shutdown process to avoid or reduce the chance of race conditions.
 */
void vdo_free_io_submitter(struct io_submitter *io_submitter)
{
	int i;

	if (io_submitter == NULL)
		return;

	for (i = io_submitter->num_bio_queues_used - 1; i >= 0; i--) {
		io_submitter->num_bio_queues_used--;
		/* vdo_destroy() will free the work queue, so just give up our reference to it. */
		vdo_forget(io_submitter->bio_queue_data[i].queue);
		vdo_int_map_free(vdo_forget(io_submitter->bio_queue_data[i].map));
	}
	vdo_free(io_submitter);
}
