/*
 * Copyright (C) 2011-2016 Red Hat, Inc. All rights reserved.
 *
 * This file is part of LVM2.
 *
 * This copyrighted material is made available to anyone wishing to use,
 * modify, copy, or redistribute it subject to the terms and conditions
 * of the GNU Lesser General Public License v.2.1.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 */

#include "lib.h"	/* using here lvm log */
#include "dmeventd_lvm.h"
#include "libdevmapper-event.h"

#include <sys/wait.h>
#include <stdarg.h>
#include <pthread.h>

/* TODO - move this mountinfo code into library to be reusable */
#ifdef __linux__
#  include "kdev_t.h"
#else
#  define MAJOR(x) major((x))
#  define MINOR(x) minor((x))
#endif

/* First warning when thin data or metadata is 80% full. */
#define WARNING_THRESH	(DM_PERCENT_1 * 80)
/* Umount thin LVs when thin data or metadata LV is >=
 * and lvextend --use-policies has failed. */
#define UMOUNT_THRESH	(DM_PERCENT_1 * 95)
/* Run a check every 5%. */
#define CHECK_STEP	(DM_PERCENT_1 *  5)
/* Do not bother checking thin data or metadata is less than 50% full. */
#define CHECK_MINIMUM	(DM_PERCENT_1 * 50)

#define UMOUNT_COMMAND "/bin/umount"

#define MAX_FAILS	(10)

#define THIN_DEBUG 0

struct dso_state {
	struct dm_pool *mem;
	int metadata_percent_check;
	int data_percent_check;
	uint64_t known_metadata_size;
	uint64_t known_data_size;
	unsigned fails;
	char cmd_str[1024];
};

DM_EVENT_LOG_FN("thin")

#define UUID_PREFIX "LVM-"

/* Figure out device UUID has LVM- prefix and is OPEN */
static int _has_unmountable_prefix(int major, int minor)
{
	struct dm_task *dmt;
	struct dm_info info;
	const char *uuid;
	int r = 0;

	if (!(dmt = dm_task_create(DM_DEVICE_INFO)))
		return_0;

	if (!dm_task_set_major_minor(dmt, major, minor, 1))
		goto_out;

	if (!dm_task_no_flush(dmt))
		stack;

	if (!dm_task_run(dmt))
		goto out;

	if (!dm_task_get_info(dmt, &info))
		goto out;

	if (!info.exists || !info.open_count)
		goto out; /* Not open -> not mounted */

	if (!(uuid = dm_task_get_uuid(dmt)))
		goto out;

	/* Check it's public mountable LV
	 * has prefix  LVM-  and UUID size is 68 chars */
	if (memcmp(uuid, UUID_PREFIX, sizeof(UUID_PREFIX) - 1) ||
	    strlen(uuid) != 68)
		goto out;

#if THIN_DEBUG
	log_debug("Found logical volume %s (%u:%u).", uuid, major, minor);
#endif
	r = 1;
out:
	dm_task_destroy(dmt);

	return r;
}

/* Get dependencies for device, and try to find matching device */
static int _has_deps(const char *name, int tp_major, int tp_minor, int *dev_minor)
{
	struct dm_task *dmt;
	const struct dm_deps *deps;
	struct dm_info info;
	int major, minor;
	int r = 0;

	if (!(dmt = dm_task_create(DM_DEVICE_DEPS)))
		return 0;

	if (!dm_task_set_name(dmt, name))
		goto out;

	if (!dm_task_no_open_count(dmt))
		goto out;

	if (!dm_task_run(dmt))
		goto out;

	if (!dm_task_get_info(dmt, &info))
		goto out;

	if (!(deps = dm_task_get_deps(dmt)))
		goto out;

	if (!info.exists || deps->count != 1)
		goto out;

	major = (int) MAJOR(deps->device[0]);
	minor = (int) MINOR(deps->device[0]);
	if ((major != tp_major) || (minor != tp_minor))
		goto out;

	*dev_minor = info.minor;

	if (!_has_unmountable_prefix(major, info.minor))
		goto out;

#if THIN_DEBUG
	{
		char dev_name[PATH_MAX];
		if (dm_device_get_name(major, minor, 0, dev_name, sizeof(dev_name)))
			log_debug("Found %s (%u:%u) depends on %s.",
				  name, major, *dev_minor, dev_name);
	}
#endif
	r = 1;
out:
	dm_task_destroy(dmt);

	return r;
}

/* Get all active devices */
static int _find_all_devs(dm_bitset_t bs, int tp_major, int tp_minor)
{
	struct dm_task *dmt;
	struct dm_names *names;
	unsigned next = 0;
	int minor, r = 1;

	if (!(dmt = dm_task_create(DM_DEVICE_LIST)))
		return 0;

	if (!dm_task_run(dmt)) {
		r = 0;
		goto out;
	}

	if (!(names = dm_task_get_names(dmt))) {
		r = 0;
		goto out;
	}

	if (!names->dev)
		goto out;

	do {
		names = (struct dm_names *)((char *) names + next);
		if (_has_deps(names->name, tp_major, tp_minor, &minor))
			dm_bit_set(bs, minor);
		next = names->next;
	} while (next);

out:
	dm_task_destroy(dmt);

	return r;
}

static int _run(const char *cmd, ...)
{
	va_list ap;
	int argc = 1; /* for argv[0], i.e. cmd */
	int i = 0;
	const char **argv;
	pid_t pid = fork();
	int status;

	if (pid == 0) { /* child */
		va_start(ap, cmd);
		while (va_arg(ap, const char *))
			++argc;
		va_end(ap);

		/* + 1 for the terminating NULL */
		argv = alloca(sizeof(const char *) * (argc + 1));

		argv[0] = cmd;
		va_start(ap, cmd);
		while ((argv[++i] = va_arg(ap, const char *)));
		va_end(ap);

		execvp(cmd, (char **)argv);
		log_sys_error("exec", cmd);
		exit(127);
	}

	if (pid > 0) { /* parent */
		if (waitpid(pid, &status, 0) != pid)
			return 0; /* waitpid failed */
		if (!WIFEXITED(status) || WEXITSTATUS(status))
			return 0; /* the child failed */
	}

	if (pid < 0)
		return 0; /* fork failed */

	return 1; /* all good */
}

struct mountinfo_s {
	const char *device;
	struct dm_info info;
	dm_bitset_t minors; /* Bitset for active thin pool minors */
};

static int _umount_device(char *buffer, unsigned major, unsigned minor,
			  char *target, void *cb_data)
{
	struct mountinfo_s *data = cb_data;
	char *words[10];

	if ((major == data->info.major) && dm_bit(data->minors, minor)) {
		if (dm_split_words(buffer, DM_ARRAY_SIZE(words), 0, words) < DM_ARRAY_SIZE(words))
			words[9] = NULL; /* just don't show device name */
		log_info("Unmounting thin %s (%d:%d) of thin-pool %s (%u:%u) from mount point \"%s\".",
			 words[9] ? : "", major, minor, data->device,
			 data->info.major, data->info.minor,
			 target);
		if (!_run(UMOUNT_COMMAND, "-fl", target, NULL))
			log_error("Failed to lazy umount thin %s (%d:%d) from %s: %s.",
				  words[9], major, minor, target, strerror(errno));
	}

	return 1;
}

/*
 * Find all thin pool LV users and try to umount them.
 * TODO: work with read-only thin pool support
 */
static void _umount(struct dm_task *dmt)
{
	/* TODO: Convert to use hash to reduce memory usage */
	static const size_t MINORS = (1U << 20); /* 20 bit */
	struct mountinfo_s data = { NULL };

	if (!dm_task_get_info(dmt, &data.info))
		return;

	data.device = dm_task_get_name(dmt);

	if (!(data.minors = dm_bitset_create(NULL, MINORS))) {
		log_error("Failed to allocate bitset. Not unmounting %s.", data.device);
		goto out;
	}

	if (!_find_all_devs(data.minors, data.info.major, data.info.minor)) {
		log_error("Failed to detect mounted volumes for %s.", data.device);
		goto out;
	}

	if (!dm_mountinfo_read(_umount_device, &data)) {
		log_error("Could not parse mountinfo file.");
		goto out;
	}

out:
	if (data.minors)
		dm_bitset_destroy(data.minors);
}

static int _use_policy(struct dm_task *dmt, struct dso_state *state)
{
#if THIN_DEBUG
	log_info("dmeventd executes: %s.", state->cmd_str);
#endif
	if (!dmeventd_lvm2_run_with_lock(state->cmd_str)) {
		log_error("Failed to extend thin pool %s.",
			  dm_task_get_name(dmt));
		state->fails++;
		return 0;
	}

	state->fails = 0;
	return 1;
}

void process_event(struct dm_task *dmt,
		   enum dm_event_mask event __attribute__((unused)),
		   void **user)
{
	const char *device = dm_task_get_name(dmt);
	int percent;
	struct dso_state *state = *user;
	struct dm_status_thin_pool *tps = NULL;
	void *next = NULL;
	uint64_t start, length;
	char *target_type = NULL;
	char *params;
	int needs_policy = 0;
	int needs_umount = 0;

#if THIN_DEBUG
	log_debug("Watch for tp-data:%.2f%%  tp-metadata:%.2f%%.",
		  dm_percent_to_float(state->data_percent_check),
		  dm_percent_to_float(state->metadata_percent_check));
#endif

#if 0
	/* No longer monitoring, waiting for remove */
	if (!state->meta_percent_check && !state->data_percent_check)
		return;
#endif
	if (event & DM_EVENT_DEVICE_ERROR) {
		/* Error -> no need to check and do instant resize */
		if (_use_policy(dmt, state))
			goto out;

		stack;
	}

	dm_get_next_target(dmt, next, &start, &length, &target_type, &params);

	if (!target_type || (strcmp(target_type, "thin-pool") != 0)) {
		log_error("Invalid target type.");
		goto out;
	}

	if (!dm_get_status_thin_pool(state->mem, params, &tps)) {
		log_error("Failed to parse status.");
		needs_umount = 1;
		goto out;
	}

#if THIN_DEBUG
	log_debug("Thin pool status " FMTu64 "/" FMTu64 "  "
		  FMTu64 "/" FMTu64 ".",
		  tps->used_metadata_blocks, tps->total_metadata_blocks,
		  tps->used_data_blocks, tps->total_data_blocks);
#endif

	/* Thin pool size had changed. Clear the threshold. */
	if (state->known_metadata_size != tps->total_metadata_blocks) {
		state->metadata_percent_check = CHECK_MINIMUM;
		state->known_metadata_size = tps->total_metadata_blocks;
	}

	if (state->known_data_size != tps->total_data_blocks) {
		state->data_percent_check = CHECK_MINIMUM;
		state->known_data_size = tps->total_data_blocks;
	}

	percent = dm_make_percent(tps->used_metadata_blocks, tps->total_metadata_blocks);
	if (percent >= state->metadata_percent_check) {
		/*
		 * Usage has raised more than CHECK_STEP since the last
		 * time. Run actions.
		 */
		state->metadata_percent_check = (percent / CHECK_STEP) * CHECK_STEP + CHECK_STEP;

		/* FIXME: extension of metadata needs to be written! */
		if (percent >= WARNING_THRESH) /* Print a warning to syslog. */
			log_warn("WARNING: Thin pool %s metadata is now %.2f%% full.",
				 device, dm_percent_to_float(percent));
		needs_policy = 1;

		if (percent >= UMOUNT_THRESH)
			needs_umount = 1;
	}

	percent = dm_make_percent(tps->used_data_blocks, tps->total_data_blocks);
	if (percent >= state->data_percent_check) {
		/*
		 * Usage has raised more than CHECK_STEP since
		 * the last time. Run actions.
		 */
		state->data_percent_check = (percent / CHECK_STEP) * CHECK_STEP + CHECK_STEP;

		if (percent >= WARNING_THRESH) /* Print a warning to syslog. */
			log_warn("WARNING: Thin pool %s data is now %.2f%% full.",
				 device, dm_percent_to_float(percent));
		needs_policy = 1;

		if (percent >= UMOUNT_THRESH)
			needs_umount = 1;
	}

	if (needs_policy &&
	    _use_policy(dmt, state))
		needs_umount = 0; /* No umount when command was successful */
out:
	if (needs_umount) {
		_umount(dmt);
		/* Until something changes, do not retry any more actions */
		state->data_percent_check = state->metadata_percent_check = (DM_PERCENT_1 * 101);
	}

	if (tps)
		dm_pool_free(state->mem, tps);

	if (state->fails >= MAX_FAILS) {
		log_warn("WARNING: Dropping monitoring of %s. "
			 "lvm2 command fails too often (%u times in raw).",
			 device, state->fails);
		pthread_kill(pthread_self(), SIGALRM);
	}
}

int register_device(const char *device,
		    const char *uuid __attribute__((unused)),
		    int major __attribute__((unused)),
		    int minor __attribute__((unused)),
		    void **user)
{
	struct dso_state *state;

	if (!dmeventd_lvm2_init_with_pool("thin_pool_state", state))
		goto_bad;

	if (!dmeventd_lvm2_command(state->mem, state->cmd_str,
				   sizeof(state->cmd_str),
				   "lvextend --use-policies",
				   device)) {
		dmeventd_lvm2_exit_with_pool(state);
		goto_bad;
	}

	state->metadata_percent_check = CHECK_MINIMUM;
	state->data_percent_check = CHECK_MINIMUM;
	*user = state;

	log_info("Monitoring thin %s.", device);

	return 1;
bad:
	log_error("Failed to monitor thin %s.", device);

	return 0;
}

int unregister_device(const char *device,
		      const char *uuid __attribute__((unused)),
		      int major __attribute__((unused)),
		      int minor __attribute__((unused)),
		      void **user)
{
	struct dso_state *state = *user;

	dmeventd_lvm2_exit_with_pool(state);
	log_info("No longer monitoring thin %s.", device);

	return 1;
}
