/*
 * libdevmapper - device-mapper backend for cryptsetup
 *
 * Copyright (C) 2004, Jana Saout <jana@saout.de>
 * Copyright (C) 2004-2007, Clemens Fruhwirth <clemens@endorphin.org>
 * Copyright (C) 2009-2017, Red Hat, Inc. All rights reserved.
 * Copyright (C) 2009-2017, Milan Broz
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU 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 <stdio.h>
#include <dirent.h>
#include <errno.h>
#include <libdevmapper.h>
#include <fcntl.h>
#include <linux/fs.h>
#include <uuid/uuid.h>
#include <sys/stat.h>

#include "internal.h"

#define DM_UUID_LEN		129
#define DM_UUID_PREFIX		"CRYPT-"
#define DM_UUID_PREFIX_LEN	6
#define DM_CRYPT_TARGET		"crypt"
#define DM_VERITY_TARGET	"verity"
#define RETRY_COUNT		5

/* Set if dm-crypt version was probed */
static int _dm_crypt_checked = 0;
static int _quiet_log = 0;
static uint32_t _dm_crypt_flags = 0;

static struct crypt_device *_context = NULL;
static int _dm_use_count = 0;

/* Check if we have DM flag to instruct kernel to force wipe buffers */
#if !HAVE_DECL_DM_TASK_SECURE_DATA
static int dm_task_secure_data(struct dm_task *dmt) { return 1; }
#endif

/* Compatibility for old device-mapper without udev support */
#if HAVE_DECL_DM_UDEV_DISABLE_DISK_RULES_FLAG
#define CRYPT_TEMP_UDEV_FLAGS	DM_UDEV_DISABLE_SUBSYSTEM_RULES_FLAG | \
				DM_UDEV_DISABLE_DISK_RULES_FLAG | \
				DM_UDEV_DISABLE_OTHER_RULES_FLAG
#define _dm_task_set_cookie	dm_task_set_cookie
#define _dm_udev_wait		dm_udev_wait
#else
#define CRYPT_TEMP_UDEV_FLAGS	0
static int _dm_task_set_cookie(struct dm_task *dmt, uint32_t *cookie, uint16_t flags) { return 0; }
static int _dm_udev_wait(uint32_t cookie) { return 0; };
#endif

static int _dm_use_udev(void)
{
#ifdef USE_UDEV /* cannot be enabled if devmapper is too old */
	return dm_udev_get_sync_support();
#else
	return 0;
#endif
}

__attribute__((format(printf, 4, 5)))
static void set_dm_error(int level,
			 const char *file __attribute__((unused)),
			 int line __attribute__((unused)),
			 const char *f, ...)
{
	char *msg = NULL;
	va_list va;

	va_start(va, f);
	if (vasprintf(&msg, f, va) > 0) {
		if (level < 4 && !_quiet_log) {
			log_err(_context, "%s", msg);
			log_err(_context, "\n");
		} else {
			/* We do not use DM visual stack backtrace here */
			if (strncmp(msg, "<backtrace>", 11))
				log_dbg("%s", msg);
		}
	}
	free(msg);
	va_end(va);
}

static int _dm_simple(int task, const char *name, int udev_wait);

static int _dm_satisfies_version(unsigned target_maj, unsigned target_min,
				 unsigned actual_maj, unsigned actual_min)
{
	if (actual_maj > target_maj)
		return 1;

	if (actual_maj == target_maj && actual_min >= target_min)
		return 1;

	return 0;
}

static void _dm_set_crypt_compat(const char *dm_version, unsigned crypt_maj,
				 unsigned crypt_min, unsigned crypt_patch)
{
	unsigned dm_maj, dm_min, dm_patch;

	if (sscanf(dm_version, "%u.%u.%u", &dm_maj, &dm_min, &dm_patch) != 3)
		dm_maj = dm_min = dm_patch = 0;

	log_dbg("Detected dm-crypt version %i.%i.%i, dm-ioctl version %u.%u.%u.",
		crypt_maj, crypt_min, crypt_patch, dm_maj, dm_min, dm_patch);

	if (_dm_satisfies_version(1, 2, crypt_maj, crypt_min))
		_dm_crypt_flags |= DM_KEY_WIPE_SUPPORTED;
	else
		log_dbg("Suspend and resume disabled, no wipe key support.");

	if (_dm_satisfies_version(1, 10, crypt_maj, crypt_min))
		_dm_crypt_flags |= DM_LMK_SUPPORTED;

	if (_dm_satisfies_version(4, 20, dm_maj, dm_min))
		_dm_crypt_flags |= DM_SECURE_SUPPORTED;

	/* not perfect, 2.6.33 supports with 1.7.0 */
	if (_dm_satisfies_version(1, 8, crypt_maj, crypt_min))
		_dm_crypt_flags |= DM_PLAIN64_SUPPORTED;

	if (_dm_satisfies_version(1, 11, crypt_maj, crypt_min))
		_dm_crypt_flags |= DM_DISCARDS_SUPPORTED;

	if (_dm_satisfies_version(1, 13, crypt_maj, crypt_min))
		_dm_crypt_flags |= DM_TCW_SUPPORTED;

	if (_dm_satisfies_version(1, 14, crypt_maj, crypt_min)) {
		_dm_crypt_flags |= DM_SAME_CPU_CRYPT_SUPPORTED;
		_dm_crypt_flags |= DM_SUBMIT_FROM_CRYPT_CPUS_SUPPORTED;
	}

	/* Repeat test if dm-crypt is not present */
	if (crypt_maj > 0)
		_dm_crypt_checked = 1;
}

static void _dm_set_verity_compat(const char *dm_version, unsigned verity_maj,
				   unsigned verity_min, unsigned verity_patch)
{
	if (verity_maj > 0)
		_dm_crypt_flags |= DM_VERITY_SUPPORTED;
	else
		return;
	/*
	 * ignore_corruption, restart_on corruption is available since 1.2 (kernel 4.1)
	 * ignore_zero_blocks since 1.3 (kernel 4.5)
	 * (but some dm-verity targets 1.2 don't support it)
	 * FEC is added in 1.3 as well.
	 */
	if (_dm_satisfies_version(1, 3, verity_maj, verity_min)) {
		_dm_crypt_flags |= DM_VERITY_ON_CORRUPTION_SUPPORTED;
		_dm_crypt_flags |= DM_VERITY_FEC_SUPPORTED;
	}

	log_dbg("Detected dm-verity version %i.%i.%i.",
		verity_maj, verity_min, verity_patch);
}

static int _dm_check_versions(void)
{
	struct dm_task *dmt;
	struct dm_versions *target, *last_target;
	char dm_version[16];
	int r = 0;

	if (_dm_crypt_checked)
		return 1;

	/* Shut up DM while checking */
	_quiet_log = 1;

	/* FIXME: add support to DM so it forces crypt target module load here */
	if (!(dmt = dm_task_create(DM_DEVICE_LIST_VERSIONS)))
		goto out;

	if (!dm_task_run(dmt))
		goto out;

	if (!dm_task_get_driver_version(dmt, dm_version, sizeof(dm_version)))
		goto out;

	target = dm_task_get_versions(dmt);
	do {
		last_target = target;
		if (!strcmp(DM_CRYPT_TARGET, target->name)) {
			_dm_set_crypt_compat(dm_version,
					     (unsigned)target->version[0],
					     (unsigned)target->version[1],
					     (unsigned)target->version[2]);
		} else if (!strcmp(DM_VERITY_TARGET, target->name)) {
			_dm_set_verity_compat(dm_version,
					     (unsigned)target->version[0],
					     (unsigned)target->version[1],
					     (unsigned)target->version[2]);
		}
		target = (struct dm_versions *)((char *) target + target->next);
	} while (last_target != target);

	r = 1;
	log_dbg("Device-mapper backend running with UDEV support %sabled.",
		_dm_use_udev() ? "en" : "dis");
out:
	if (dmt)
		dm_task_destroy(dmt);

	_quiet_log = 0;
	return r;
}

uint32_t dm_flags(void)
{
	_dm_check_versions();
	return _dm_crypt_flags;
}

/* This doesn't run any kernel checks, just set up userspace libdevmapper */
void dm_backend_init(void)
{
	if (!_dm_use_count++) {
		log_dbg("Initialising device-mapper backend library.");
		dm_log_init(set_dm_error);
		dm_log_init_verbose(10);
	}
}

void dm_backend_exit(void)
{
	if (_dm_use_count && (!--_dm_use_count)) {
		log_dbg("Releasing device-mapper backend.");
		dm_log_init_verbose(0);
		dm_log_init(NULL);
		dm_lib_release();
	}
}

/*
 * libdevmapper is not context friendly, switch context on every DM call.
 * FIXME: this is not safe if called in parallel but neither is DM lib.
 */
static int dm_init_context(struct crypt_device *cd)
{
	_context = cd;
	if (!_dm_check_versions()) {
		if (getuid() || geteuid())
			log_err(cd, _("Cannot initialize device-mapper, "
				      "running as non-root user.\n"));
		else
			log_err(cd, _("Cannot initialize device-mapper. "
				      "Is dm_mod kernel module loaded?\n"));
		_context = NULL;
		return -ENOTSUP;
	}
	return 0;
}
static void dm_exit_context(void)
{
	_context = NULL;
}

/* Return path to DM device */
char *dm_device_path(const char *prefix, int major, int minor)
{
	struct dm_task *dmt;
	const char *name;
	char path[PATH_MAX];

	if (!(dmt = dm_task_create(DM_DEVICE_STATUS)))
		return NULL;
	if (!dm_task_set_minor(dmt, minor) ||
	    !dm_task_set_major(dmt, major) ||
	    !dm_task_run(dmt) ||
	    !(name = dm_task_get_name(dmt))) {
		dm_task_destroy(dmt);
		return NULL;
	}

	if (snprintf(path, sizeof(path), "%s%s", prefix ?: "", name) < 0)
		path[0] = '\0';

	dm_task_destroy(dmt);

	return strdup(path);
}

static void hex_key(char *hexkey, size_t key_size, const char *key)
{
	unsigned i;

	for(i = 0; i < key_size; i++)
		sprintf(&hexkey[i * 2], "%02x", (unsigned char)key[i]);
}

/* https://gitlab.com/cryptsetup/cryptsetup/wikis/DMCrypt */
static char *get_dm_crypt_params(struct crypt_dm_active_device *dmd, uint32_t flags)
{
	int r, max_size, null_cipher = 0, num_options = 0;
	char *params, *hexkey;
	char features[256];

	if (!dmd)
		return NULL;

	if (flags & CRYPT_ACTIVATE_ALLOW_DISCARDS)
		num_options++;
	if (flags & CRYPT_ACTIVATE_SAME_CPU_CRYPT)
		num_options++;
	if (flags & CRYPT_ACTIVATE_SUBMIT_FROM_CRYPT_CPUS)
		num_options++;

	if (num_options)
		snprintf(features, sizeof(features)-1, " %d%s%s%s", num_options,
		(flags & CRYPT_ACTIVATE_ALLOW_DISCARDS) ? " allow_discards" : "",
		(flags & CRYPT_ACTIVATE_SAME_CPU_CRYPT) ? " same_cpu_crypt" : "",
		(flags & CRYPT_ACTIVATE_SUBMIT_FROM_CRYPT_CPUS) ? " submit_from_crypt_cpus" : "");
	else
		*features = '\0';

	if (!strncmp(dmd->u.crypt.cipher, "cipher_null-", 12))
		null_cipher = 1;

	hexkey = crypt_safe_alloc(null_cipher ? 2 : (dmd->u.crypt.vk->keylength * 2 + 1));
	if (!hexkey)
		return NULL;

	if (null_cipher)
		strncpy(hexkey, "-", 2);
	else
		hex_key(hexkey, dmd->u.crypt.vk->keylength, dmd->u.crypt.vk->key);

	max_size = strlen(hexkey) + strlen(dmd->u.crypt.cipher) +
		   strlen(device_block_path(dmd->data_device)) +
		   strlen(features) + 64;
	params = crypt_safe_alloc(max_size);
	if (!params)
		goto out;

	r = snprintf(params, max_size, "%s %s %" PRIu64 " %s %" PRIu64 "%s",
		     dmd->u.crypt.cipher, hexkey, dmd->u.crypt.iv_offset,
		     device_block_path(dmd->data_device), dmd->u.crypt.offset,
		     features);
	if (r < 0 || r >= max_size) {
		crypt_safe_free(params);
		params = NULL;
	}
out:
	crypt_safe_free(hexkey);
	return params;
}

/* https://gitlab.com/cryptsetup/cryptsetup/wikis/DMVerity */
static char *get_dm_verity_params(struct crypt_params_verity *vp,
				   struct crypt_dm_active_device *dmd, uint32_t flags)
{
	int max_size, r, num_options = 0;
	char *params = NULL, *hexroot = NULL, *hexsalt = NULL;
	char features[256], fec_features[256];

	if (!vp || !dmd)
		return NULL;

	/* These flags are not compatible */
	if ((flags & CRYPT_ACTIVATE_IGNORE_CORRUPTION) &&
	    (flags & CRYPT_ACTIVATE_RESTART_ON_CORRUPTION))
		flags &= ~CRYPT_ACTIVATE_IGNORE_CORRUPTION;

	if (flags & CRYPT_ACTIVATE_IGNORE_CORRUPTION)
		num_options++;
	if (flags & CRYPT_ACTIVATE_RESTART_ON_CORRUPTION)
		num_options++;
	if (flags & CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS)
		num_options++;

	if (dmd->u.verity.fec_device) {
		num_options += 8;
		snprintf(fec_features, sizeof(fec_features)-1,
			 " use_fec_from_device %s fec_start %" PRIu64 " fec_blocks %" PRIu64 " fec_roots %" PRIu32,
			 device_block_path(dmd->u.verity.fec_device), dmd->u.verity.fec_offset,
			 vp->data_size + dmd->u.verity.hash_blocks, vp->fec_roots);
	} else
		*fec_features = '\0';

	if (num_options)
		snprintf(features, sizeof(features)-1, " %d%s%s%s", num_options,
		(flags & CRYPT_ACTIVATE_IGNORE_CORRUPTION) ? " ignore_corruption" : "",
		(flags & CRYPT_ACTIVATE_RESTART_ON_CORRUPTION) ? " restart_on_corruption" : "",
		(flags & CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS) ? " ignore_zero_blocks" : "");
	else
		*features = '\0';

	hexroot = crypt_safe_alloc(dmd->u.verity.root_hash_size * 2 + 1);
	if (!hexroot)
		goto out;
	hex_key(hexroot, dmd->u.verity.root_hash_size, dmd->u.verity.root_hash);

	hexsalt = crypt_safe_alloc(vp->salt_size ? vp->salt_size * 2 + 1 : 2);
	if (!hexsalt)
		goto out;
	if (vp->salt_size)
		hex_key(hexsalt, vp->salt_size, vp->salt);
	else
		strncpy(hexsalt, "-", 2);

	max_size = strlen(hexroot) + strlen(hexsalt) +
		   strlen(device_block_path(dmd->data_device)) +
		   strlen(device_block_path(dmd->u.verity.hash_device)) +
		   strlen(vp->hash_name) + strlen(features) + strlen(fec_features) + 128;

	params = crypt_safe_alloc(max_size);
	if (!params)
		goto out;

	r = snprintf(params, max_size,
		     "%u %s %s %u %u %" PRIu64 " %" PRIu64 " %s %s %s%s%s",
		     vp->hash_type, device_block_path(dmd->data_device),
		     device_block_path(dmd->u.verity.hash_device),
		     vp->data_block_size, vp->hash_block_size,
		     vp->data_size, dmd->u.verity.hash_offset,
		     vp->hash_name, hexroot, hexsalt, features, fec_features);
	if (r < 0 || r >= max_size) {
		crypt_safe_free(params);
		params = NULL;
	}
out:
	crypt_safe_free(hexroot);
	crypt_safe_free(hexsalt);
	return params;

}

/* DM helpers */
static int _dm_simple(int task, const char *name, int udev_wait)
{
	int r = 0;
	struct dm_task *dmt;
	uint32_t cookie = 0;

	if (!_dm_use_udev())
		udev_wait = 0;

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

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

#if HAVE_DECL_DM_TASK_RETRY_REMOVE
	/* Used only in DM_DEVICE_REMOVE */
	if (name && !dm_task_retry_remove(dmt))
		goto out;
#endif
	if (udev_wait && !_dm_task_set_cookie(dmt, &cookie, 0))
		goto out;

	r = dm_task_run(dmt);

	if (udev_wait)
		(void)_dm_udev_wait(cookie);

out:
	dm_task_destroy(dmt);
	return r;
}

static int _error_device(const char *name, size_t size)
{
	struct dm_task *dmt;
	int r = 0;

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

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

	if (!dm_task_add_target(dmt, UINT64_C(0), size, "error", ""))
		goto error;

	if (!dm_task_set_ro(dmt))
		goto error;

	if (!dm_task_no_open_count(dmt))
		goto error;

	if (!dm_task_run(dmt))
		goto error;

	if (!_dm_simple(DM_DEVICE_RESUME, name, 1)) {
		_dm_simple(DM_DEVICE_CLEAR, name, 0);
		goto error;
	}

	r = 1;

error:
	dm_task_destroy(dmt);
	return r;
}

int dm_remove_device(struct crypt_device *cd, const char *name,
		     int force, uint64_t size)
{
	int r = -EINVAL;
	int retries = force ? RETRY_COUNT : 1;
	int error_target = 0;

	if (!name || (force && !size))
		return -EINVAL;

	if (dm_init_context(cd))
		return -ENOTSUP;

	do {
		r = _dm_simple(DM_DEVICE_REMOVE, name, 1) ? 0 : -EINVAL;
		if (--retries && r) {
			log_dbg("WARNING: other process locked internal device %s, %s.",
				name, retries ? "retrying remove" : "giving up");
			sleep(1);
			if (force && !error_target) {
				/* If force flag is set, replace device with error, read-only target.
				 * it should stop processes from reading it and also removed underlying
				 * device from mapping, so it is usable again.
				 * Force flag should be used only for temporary devices, which are
				 * intended to work inside cryptsetup only!
				 * Anyway, if some process try to read temporary cryptsetup device,
				 * it is bug - no other process should try touch it (e.g. udev).
				 */
				_error_device(name, size);
				error_target = 1;
			}
		}
	} while (r == -EINVAL && retries);

	dm_task_update_nodes();
	dm_exit_context();

	return r;
}

#define UUID_LEN 37 /* 36 + \0, libuuid ... */
/*
 * UUID has format: CRYPT-<devicetype>-[<uuid>-]<device name>
 * CRYPT-PLAIN-name
 * CRYPT-LUKS1-00000000000000000000000000000000-name
 * CRYPT-TEMP-name
 */
static int dm_prepare_uuid(const char *name, const char *type, const char *uuid, char *buf, size_t buflen)
{
	char *ptr, uuid2[UUID_LEN] = {0};
	uuid_t uu;
	unsigned i = 0;

	/* Remove '-' chars */
	if (uuid) {
		if (uuid_parse(uuid, uu) < 0) {
			log_dbg("Requested UUID %s has invalid format.", uuid);
			return 0;
		}

		for (ptr = uuid2, i = 0; i < UUID_LEN; i++)
			if (uuid[i] != '-') {
				*ptr = uuid[i];
				ptr++;
			}
	}

	i = snprintf(buf, buflen, DM_UUID_PREFIX "%s%s%s%s%s",
		type ?: "", type ? "-" : "",
		uuid2[0] ? uuid2 : "", uuid2[0] ? "-" : "",
		name);

	log_dbg("DM-UUID is %s", buf);
	if (i >= buflen)
		log_err(NULL, _("DM-UUID for device %s was truncated.\n"), name);

	return 1;
}

static int _dm_create_device(const char *name, const char *type,
			     struct device *device, uint32_t flags,
			     const char *uuid, uint64_t size,
			     char *params, int reload)
{
	struct dm_task *dmt = NULL;
	struct dm_info dmi;
	char dev_uuid[DM_UUID_LEN] = {0};
	int r = -EINVAL;
	uint32_t read_ahead = 0;
	uint32_t cookie = 0;
	uint16_t udev_flags = 0;

	if (!params)
		return -EINVAL;

	if (flags & CRYPT_ACTIVATE_PRIVATE)
		udev_flags = CRYPT_TEMP_UDEV_FLAGS;

	/* All devices must have DM_UUID, only resize on old device is exception */
	if (reload) {
		if (!(dmt = dm_task_create(DM_DEVICE_RELOAD)))
			goto out_no_removal;

		if (!dm_task_set_name(dmt, name))
			goto out_no_removal;
	} else {
		if (!dm_prepare_uuid(name, type, uuid, dev_uuid, sizeof(dev_uuid)))
			goto out_no_removal;

		if (!(dmt = dm_task_create(DM_DEVICE_CREATE)))
			goto out_no_removal;

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

		if (!dm_task_set_uuid(dmt, dev_uuid))
			goto out_no_removal;
	}

	if ((dm_flags() & DM_SECURE_SUPPORTED) && !dm_task_secure_data(dmt))
		goto out_no_removal;
	if ((flags & CRYPT_ACTIVATE_READONLY) && !dm_task_set_ro(dmt))
		goto out_no_removal;

	if (!dm_task_add_target(dmt, 0, size,
		!strcmp("VERITY", type) ? DM_VERITY_TARGET : DM_CRYPT_TARGET, params))
		goto out_no_removal;

#ifdef DM_READ_AHEAD_MINIMUM_FLAG
	if (device_read_ahead(device, &read_ahead) &&
	    !dm_task_set_read_ahead(dmt, read_ahead, DM_READ_AHEAD_MINIMUM_FLAG))
		goto out_no_removal;
#endif
	/* do not set cookie for DM_DEVICE_RELOAD task */
	if (!reload && _dm_use_udev() && !_dm_task_set_cookie(dmt, &cookie, udev_flags))
		goto out_no_removal;

	if (!dm_task_run(dmt))
		goto out_no_removal;

	if (reload) {
		dm_task_destroy(dmt);
		if (!(dmt = dm_task_create(DM_DEVICE_RESUME)))
			goto out;
		if (!dm_task_set_name(dmt, name))
			goto out;
		if (uuid && !dm_task_set_uuid(dmt, dev_uuid))
			goto out;
		if (_dm_use_udev() && !_dm_task_set_cookie(dmt, &cookie, udev_flags))
			goto out;
		if (!dm_task_run(dmt))
			goto out;
	}

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

	r = 0;
out:
	if (_dm_use_udev()) {
		(void)_dm_udev_wait(cookie);
		cookie = 0;
	}

	if (r < 0 && !reload)
		_dm_simple(DM_DEVICE_REMOVE, name, 1);

out_no_removal:
	if (cookie && _dm_use_udev())
		(void)_dm_udev_wait(cookie);

	if (dmt)
		dm_task_destroy(dmt);

	dm_task_update_nodes();

	/* If code just loaded target module, update versions */
	_dm_check_versions();

	return r;
}

int dm_create_device(struct crypt_device *cd, const char *name,
		     const char *type,
		     struct crypt_dm_active_device *dmd,
		     int reload)
{
	char *table_params = NULL;
	uint32_t dmd_flags;
	int r;

	if (!type)
		return -EINVAL;

	if (dm_init_context(cd))
		return -ENOTSUP;

	dmd_flags = dmd->flags;

	if (dmd->target == DM_CRYPT)
		table_params = get_dm_crypt_params(dmd, dmd_flags);
	else if (dmd->target == DM_VERITY)
		table_params = get_dm_verity_params(dmd->u.verity.vp, dmd, dmd_flags);

	r = _dm_create_device(name, type, dmd->data_device, dmd_flags,
			      dmd->uuid, dmd->size, table_params, reload);

	/* If discard not supported try to load without discard */
	if (!reload && r && dmd->target == DM_CRYPT &&
	    (dmd->flags & CRYPT_ACTIVATE_ALLOW_DISCARDS) &&
	    !(dm_flags() & DM_DISCARDS_SUPPORTED)) {
		log_dbg("Discard/TRIM is not supported, retrying activation.");
		dmd_flags = dmd_flags & ~CRYPT_ACTIVATE_ALLOW_DISCARDS;
		crypt_safe_free(table_params);
		table_params = get_dm_crypt_params(dmd, dmd_flags);
		r = _dm_create_device(name, type, dmd->data_device, dmd_flags,
				      dmd->uuid, dmd->size, table_params, reload);
	}

	if (r == -EINVAL &&
	    dmd_flags & (CRYPT_ACTIVATE_SAME_CPU_CRYPT|CRYPT_ACTIVATE_SUBMIT_FROM_CRYPT_CPUS) &&
	    !(dm_flags() & (DM_SAME_CPU_CRYPT_SUPPORTED|DM_SUBMIT_FROM_CRYPT_CPUS_SUPPORTED)))
		log_err(cd, _("Requested dm-crypt performance options are not supported.\n"));

	if (r == -EINVAL && dmd_flags & (CRYPT_ACTIVATE_IGNORE_CORRUPTION|
					  CRYPT_ACTIVATE_RESTART_ON_CORRUPTION|
					  CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS) &&
	    !(dm_flags() & DM_VERITY_ON_CORRUPTION_SUPPORTED))
		log_err(cd, _("Requested dm-verity data corruption handling options are not supported.\n"));

	if (r == -EINVAL && dmd->target == DM_VERITY && dmd->u.verity.fec_device &&
	    !(dm_flags() & DM_VERITY_FEC_SUPPORTED))
		log_err(cd, _("Requested dm-verity FEC options are not supported.\n"));

	crypt_safe_free(table_params);
	dm_exit_context();
	return r;
}

static int dm_status_dmi(const char *name, struct dm_info *dmi,
			  const char *target, char **status_line)
{
	struct dm_task *dmt;
	uint64_t start, length;
	char *target_type, *params = NULL;
	void *next = NULL;
	int r = -EINVAL;

	if (!(dmt = dm_task_create(DM_DEVICE_STATUS)))
		goto out;

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

	if (!dm_task_run(dmt))
		goto out;

	if (!dm_task_get_info(dmt, dmi))
		goto out;

	if (!dmi->exists) {
		r = -ENODEV;
		goto out;
	}

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

	if (!target_type || start != 0 || next)
		goto out;

	if (target && strcmp(target_type, target))
		goto out;

	/* for target == NULL check all supported */
	if (!target && (strcmp(target_type, DM_CRYPT_TARGET) &&
			strcmp(target_type, DM_VERITY_TARGET)))
		goto out;
	r = 0;
out:
	if (!r && status_line && !(*status_line = strdup(params)))
		r = -ENOMEM;

	if (dmt)
		dm_task_destroy(dmt);

	return r;
}

int dm_status_device(struct crypt_device *cd, const char *name)
{
	int r;
	struct dm_info dmi;
	struct stat st;

	/* libdevmapper is too clever and handles
	 * path argument differenly with error.
	 * Fail early here if parameter is non-existent path.
	 */
	if (strchr(name, '/') && stat(name, &st) < 0)
		return -ENODEV;

	if (dm_init_context(cd))
		return -ENOTSUP;
	r = dm_status_dmi(name, &dmi, NULL, NULL);
	dm_exit_context();
	if (r < 0)
		return r;

	return (dmi.open_count > 0);
}

int dm_status_suspended(struct crypt_device *cd, const char *name)
{
	int r;
	struct dm_info dmi;

	if (dm_init_context(cd))
		return -ENOTSUP;
	r = dm_status_dmi(name, &dmi, DM_CRYPT_TARGET, NULL);
	dm_exit_context();
	if (r < 0)
		return r;

	return dmi.suspended ? 1 : 0;
}

static int _dm_status_verity_ok(const char *name)
{
	int r;
	struct dm_info dmi;
	char *status_line = NULL;

	r = dm_status_dmi(name, &dmi, DM_VERITY_TARGET, &status_line);
	if (r < 0 || !status_line) {
		free(status_line);
		return r;
	}

	log_dbg("Verity volume %s status is %s.", name, status_line ?: "");
	r = status_line[0] == 'V' ? 1 : 0;
	free(status_line);

	return r;
}

int dm_status_verity_ok(struct crypt_device *cd, const char *name)
{
	int r;

	if (dm_init_context(cd))
		return -ENOTSUP;
	r = _dm_status_verity_ok(name);
	dm_exit_context();
	return r;
}

/* FIXME use hex wrapper, user val wrappers for line parsing */
static int _dm_query_crypt(uint32_t get_flags,
			   struct dm_info *dmi,
			   char *params,
			   struct crypt_dm_active_device *dmd)
{
	uint64_t val64;
	char *rcipher, *key_, *rdevice, *endp, buffer[3], *arg;
	unsigned int i;
	int r;

	memset(dmd, 0, sizeof(*dmd));
	dmd->target = DM_CRYPT;

	rcipher = strsep(&params, " ");
	/* cipher */
	if (get_flags & DM_ACTIVE_CRYPT_CIPHER)
		dmd->u.crypt.cipher = strdup(rcipher);

	/* skip */
	key_ = strsep(&params, " ");
	if (!params)
		return -EINVAL;
	val64 = strtoull(params, &params, 10);
	if (*params != ' ')
		return -EINVAL;
	params++;

	dmd->u.crypt.iv_offset = val64;

	/* device */
	rdevice = strsep(&params, " ");
	if (get_flags & DM_ACTIVE_DEVICE) {
		arg = crypt_lookup_dev(rdevice);
		r = device_alloc(&dmd->data_device, arg);
		free(arg);
		if (r < 0 && r != -ENOTBLK)
			return r;
	}

	/*offset */
	if (!params)
		return -EINVAL;
	val64 = strtoull(params, &params, 10);
	dmd->u.crypt.offset = val64;

	/* Features section, available since crypt target version 1.11 */
	if (*params) {
		if (*params != ' ')
			return -EINVAL;
		params++;

		/* Number of arguments */
		val64 = strtoull(params, &params, 10);
		if (*params != ' ')
			return -EINVAL;
		params++;

		for (i = 0; i < val64; i++) {
			if (!params)
				return -EINVAL;
			arg = strsep(&params, " ");
			if (!strcasecmp(arg, "allow_discards"))
				dmd->flags |= CRYPT_ACTIVATE_ALLOW_DISCARDS;
			else if (!strcasecmp(arg, "same_cpu_crypt"))
				dmd->flags |= CRYPT_ACTIVATE_SAME_CPU_CRYPT;
			else if (!strcasecmp(arg, "submit_from_crypt_cpus"))
				dmd->flags |= CRYPT_ACTIVATE_SUBMIT_FROM_CRYPT_CPUS;
			else /* unknown option */
				return -EINVAL;
		}

		/* All parameters should be processed */
		if (params)
			return -EINVAL;
	}

	/* Never allow to return empty key */
	if ((get_flags & DM_ACTIVE_CRYPT_KEY) && dmi->suspended) {
		log_dbg("Cannot read volume key while suspended.");
		return -EINVAL;
	}

	if (get_flags & DM_ACTIVE_CRYPT_KEYSIZE) {
		dmd->u.crypt.vk = crypt_alloc_volume_key(strlen(key_) / 2, NULL);
		if (!dmd->u.crypt.vk)
			return -ENOMEM;

		if (get_flags & DM_ACTIVE_CRYPT_KEY) {
			buffer[2] = '\0';
			for(i = 0; i < dmd->u.crypt.vk->keylength; i++) {
				memcpy(buffer, &key_[i * 2], 2);
				dmd->u.crypt.vk->key[i] = strtoul(buffer, &endp, 16);
				if (endp != &buffer[2]) {
					crypt_free_volume_key(dmd->u.crypt.vk);
					dmd->u.crypt.vk = NULL;
					return -EINVAL;
				}
			}
		}
	}
	memset(key_, 0, strlen(key_));

	return 0;
}

static int _dm_query_verity(uint32_t get_flags,
			     struct dm_info *dmi,
			     char *params,
			     struct crypt_dm_active_device *dmd)
{
	struct crypt_params_verity *vp = NULL;
	uint32_t val32;
	uint64_t val64;
	ssize_t len;
	char *str, *str2, *arg;
	unsigned int i, features;
	int r;

	if (get_flags & DM_ACTIVE_VERITY_PARAMS)
		vp = dmd->u.verity.vp;

	memset(dmd, 0, sizeof(*dmd));

	dmd->target = DM_VERITY;
	dmd->u.verity.vp = vp;

	/* version */
	val32 = strtoul(params, &params, 10);
	if (*params != ' ')
		return -EINVAL;
	if (vp)
		vp->hash_type = val32;
	params++;

	/* data device */
	str = strsep(&params, " ");
	if (!params)
		return -EINVAL;
	if (get_flags & DM_ACTIVE_DEVICE) {
		str2 = crypt_lookup_dev(str);
		r = device_alloc(&dmd->data_device, str2);
		free(str2);
		if (r < 0 && r != -ENOTBLK)
			return r;
	}

	/* hash device */
	str = strsep(&params, " ");
	if (!params)
		return -EINVAL;
	if (get_flags & DM_ACTIVE_VERITY_HASH_DEVICE) {
		str2 = crypt_lookup_dev(str);
		r = device_alloc(&dmd->u.verity.hash_device, str2);
		free(str2);
		if (r < 0 && r != -ENOTBLK)
			return r;
	}

	/* data block size*/
	val32 = strtoul(params, &params, 10);
	if (*params != ' ')
		return -EINVAL;
	if (vp)
		vp->data_block_size = val32;
	params++;

	/* hash block size */
	val32 = strtoul(params, &params, 10);
	if (*params != ' ')
		return -EINVAL;
	if (vp)
		vp->hash_block_size = val32;
	params++;

	/* data blocks */
	val64 = strtoull(params, &params, 10);
	if (*params != ' ')
		return -EINVAL;
	if (vp)
		vp->data_size = val64;
	params++;

	/* hash start */
	val64 = strtoull(params, &params, 10);
	if (*params != ' ')
		return -EINVAL;
	dmd->u.verity.hash_offset = val64;
	params++;

	/* hash algorithm */
	str = strsep(&params, " ");
	if (!params)
		return -EINVAL;
	if (vp)
		vp->hash_name = strdup(str);

	/* root digest */
	str = strsep(&params, " ");
	if (!params)
		return -EINVAL;
	len = crypt_hex_to_bytes(str, &str2, 0);
	if (len < 0)
		return len;
	dmd->u.verity.root_hash_size = len;
	if (get_flags & DM_ACTIVE_VERITY_ROOT_HASH)
		dmd->u.verity.root_hash = str2;
	else
		free(str2);

	/* salt */
	str = strsep(&params, " ");
	if (vp) {
		if (!strcmp(str, "-")) {
			vp->salt_size = 0;
			vp->salt = NULL;
		} else {
			len = crypt_hex_to_bytes(str, &str2, 0);
			if (len < 0)
				return len;
			vp->salt_size = len;
			vp->salt = str2;
		}
	}

	/* Features section, available since verity target version 1.3 */
	if (params) {
		/* Number of arguments */
		val64 = strtoull(params, &params, 10);
		if (*params != ' ')
			return -EINVAL;
		params++;

		features = (int)val64;
		for (i = 0; i < features; i++) {
			if (!params)
				return -EINVAL;
			arg = strsep(&params, " ");
			if (!strcasecmp(arg, "ignore_corruption"))
				dmd->flags |= CRYPT_ACTIVATE_IGNORE_CORRUPTION;
			else if (!strcasecmp(arg, "restart_on_corruption"))
				dmd->flags |= CRYPT_ACTIVATE_RESTART_ON_CORRUPTION;
			else if (!strcasecmp(arg, "ignore_zero_blocks"))
				dmd->flags |= CRYPT_ACTIVATE_IGNORE_ZERO_BLOCKS;
			else if (!strcasecmp(arg, "use_fec_from_device")) {
				str = strsep(&params, " ");
				str2 = crypt_lookup_dev(str);
				if (get_flags & DM_ACTIVE_VERITY_HASH_DEVICE) {
					r = device_alloc(&dmd->u.verity.fec_device, str2);
					if (r < 0 && r != -ENOTBLK) {
						free(str2);
						return r;
					}
				}
				if (vp)
					vp->fec_device = str2;
				i++;
			} else if (!strcasecmp(arg, "fec_start")) {
				val64 = strtoull(params, &params, 10);
				if (*params)
					params++;
				dmd->u.verity.fec_offset = val64;
				if (vp)
					vp->fec_area_offset = val64 * vp->hash_block_size;
				i++;
			} else if (!strcasecmp(arg, "fec_blocks")) {
				val64 = strtoull(params, &params, 10);
				if (*params)
					params++;
				dmd->u.verity.fec_blocks = val64;
				i++;
			} else if (!strcasecmp(arg, "fec_roots")) {
				val32 = strtoul(params, &params, 10);
				if (*params)
					params++;
				if (vp)
					vp->fec_roots = val32;
				i++;
			} else /* unknown option */
				return -EINVAL;
		}

		/* All parameters should be processed */
		if (params && *params)
			return -EINVAL;
	}

	return 0;
}

int dm_query_device(struct crypt_device *cd, const char *name,
		    uint32_t get_flags, struct crypt_dm_active_device *dmd)
{
	struct dm_task *dmt;
	struct dm_info dmi;
	uint64_t start, length;
	char *target_type, *params;
	const char *tmp_uuid;
	void *next = NULL;
	int r = -EINVAL;

	if (dm_init_context(cd))
		return -ENOTSUP;
	if (!(dmt = dm_task_create(DM_DEVICE_TABLE)))
		goto out;
	if ((dm_flags() & DM_SECURE_SUPPORTED) && !dm_task_secure_data(dmt))
		goto out;
	if (!dm_task_set_name(dmt, name))
		goto out;
	r = -ENODEV;
	if (!dm_task_run(dmt))
		goto out;

	r = -EINVAL;
	if (!dm_task_get_info(dmt, &dmi))
		goto out;

	if (!dmi.exists) {
		r = -ENODEV;
		goto out;
	}

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

	if (!target_type || start != 0 || next)
		goto out;

	if (!strcmp(target_type, DM_CRYPT_TARGET)) {
		r = _dm_query_crypt(get_flags, &dmi, params, dmd);
	} else if (!strcmp(target_type, DM_VERITY_TARGET)) {
		r = _dm_query_verity(get_flags, &dmi, params, dmd);
		if (r < 0)
			goto out;
		r = _dm_status_verity_ok(name);
		if (r < 0)
			goto out;
		if (r == 0)
			dmd->flags |= CRYPT_ACTIVATE_CORRUPTED;
		r = 0;
	} else
		r = -EINVAL;

	if (r < 0)
		goto out;

	dmd->size = length;

	if (dmi.read_only)
		dmd->flags |= CRYPT_ACTIVATE_READONLY;

	tmp_uuid = dm_task_get_uuid(dmt);
	if (!tmp_uuid)
		dmd->flags |= CRYPT_ACTIVATE_NO_UUID;
	else if (get_flags & DM_ACTIVE_UUID) {
		if (!strncmp(tmp_uuid, DM_UUID_PREFIX, DM_UUID_PREFIX_LEN))
			dmd->uuid = strdup(tmp_uuid + DM_UUID_PREFIX_LEN);
	}

	r = (dmi.open_count > 0);
out:
	if (dmt)
		dm_task_destroy(dmt);

	dm_exit_context();
	return r;
}

static int _dm_message(const char *name, const char *msg)
{
	int r = 0;
	struct dm_task *dmt;

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

	if ((dm_flags() & DM_SECURE_SUPPORTED) && !dm_task_secure_data(dmt))
		goto out;

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

	if (!dm_task_set_sector(dmt, (uint64_t) 0))
		goto out;

	if (!dm_task_set_message(dmt, msg))
		goto out;

	r = dm_task_run(dmt);

      out:
	dm_task_destroy(dmt);
	return r;
}

int dm_suspend_and_wipe_key(struct crypt_device *cd, const char *name)
{
	int r = -ENOTSUP;

	if (dm_init_context(cd))
		return -ENOTSUP;

	if (!(_dm_crypt_flags & DM_KEY_WIPE_SUPPORTED))
		goto out;

	if (!_dm_simple(DM_DEVICE_SUSPEND, name, 0)) {
		r = -EINVAL;
		goto out;
	}

	if (!_dm_message(name, "key wipe")) {
		_dm_simple(DM_DEVICE_RESUME, name, 1);
		r = -EINVAL;
		goto out;
	}
	r = 0;
out:
	dm_exit_context();
	return r;
}

int dm_resume_and_reinstate_key(struct crypt_device *cd, const char *name,
				size_t key_size, const char *key)
{
	int msg_size = key_size * 2 + 10; // key set <key>
	char *msg = NULL;
	int r = -ENOTSUP;

	if (dm_init_context(cd))
		return -ENOTSUP;

	if (!(_dm_crypt_flags & DM_KEY_WIPE_SUPPORTED))
		goto out;

	msg = crypt_safe_alloc(msg_size);
	if (!msg) {
		r = -ENOMEM;
		goto out;
	}

	strcpy(msg, "key set ");
	hex_key(&msg[8], key_size, key);

	if (!_dm_message(name, msg) ||
	    !_dm_simple(DM_DEVICE_RESUME, name, 1)) {
		r = -EINVAL;
		goto out;
	}
	r = 0;
out:
	crypt_safe_free(msg);
	dm_exit_context();
	return r;
}

const char *dm_get_dir(void)
{
	return dm_dir();
}

int dm_is_dm_device(int major, int minor)
{
	return dm_is_dm_major((uint32_t)major);
}

int dm_is_dm_kernel_name(const char *name)
{
	return strncmp(name, "dm-", 3) ? 0 : 1;
}
