/*
 * Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
 * Copyright (C) 2004-2013 Red Hat, Inc. All rights reserved.
 *
 * This file is part of the device-mapper userspace tools.
 *
 * 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 "dmlib.h"
#include "libdm-targets.h"
#include "libdm-common.h"

#include <stddef.h>
#include <fcntl.h>
#include <dirent.h>
#include <sys/ioctl.h>
#include <sys/utsname.h>
#include <limits.h>

#ifdef __linux__
#  include "kdev_t.h"
#  include <linux/limits.h>
#else
#  define MAJOR(x) major((x))
#  define MINOR(x) minor((x))
#  define MKDEV(x,y) makedev((x),(y))
#endif

#include "dm-ioctl.h"

/*
 * Ensure build compatibility.  
 * The hard-coded versions here are the highest present 
 * in the _cmd_data arrays.
 */

#if !((DM_VERSION_MAJOR == 4 && DM_VERSION_MINOR >= 6))
#error The version of dm-ioctl.h included is incompatible.
#endif

/* FIXME This should be exported in device-mapper.h */
#define DM_NAME "device-mapper"

#define PROC_MISC "/proc/misc"
#define PROC_DEVICES "/proc/devices"
#define MISC_NAME "misc"

#define NUMBER_OF_MAJORS 4096

/*
 * Static minor number assigned since kernel version 2.6.36.
 * The original definition is in kernel's include/linux/miscdevice.h.
 * This number is also visible in modules.devname exported by depmod
 * utility (support included in module-init-tools version >= 3.12).
 */
#define MAPPER_CTRL_MINOR 236
#define MISC_MAJOR 10

/* dm major version no for running kernel */
static unsigned _dm_version = DM_VERSION_MAJOR;
static unsigned _dm_version_minor = 0;
static unsigned _dm_version_patchlevel = 0;
static int _log_suppress = 0;
static struct dm_timestamp *_dm_ioctl_timestamp = NULL;

/*
 * If the kernel dm driver only supports one major number
 * we store it in _dm_device_major.  Otherwise we indicate
 * which major numbers have been claimed by device-mapper
 * in _dm_bitset.
 */
static unsigned _dm_multiple_major_support = 1;
static dm_bitset_t _dm_bitset = NULL;
static uint32_t _dm_device_major = 0;

static int _control_fd = -1;
static int _hold_control_fd_open = 0;
static int _version_checked = 0;
static int _version_ok = 1;
static unsigned _ioctl_buffer_double_factor = 0;

const int _dm_compat = 0;

/* *INDENT-OFF* */
static struct cmd_data _cmd_data_v4[] = {
	{"create",	DM_DEV_CREATE,		{4, 0, 0}},
	{"reload",	DM_TABLE_LOAD,		{4, 0, 0}},
	{"remove",	DM_DEV_REMOVE,		{4, 0, 0}},
	{"remove_all",	DM_REMOVE_ALL,		{4, 0, 0}},
	{"suspend",	DM_DEV_SUSPEND,		{4, 0, 0}},
	{"resume",	DM_DEV_SUSPEND,		{4, 0, 0}},
	{"info",	DM_DEV_STATUS,		{4, 0, 0}},
	{"deps",	DM_TABLE_DEPS,		{4, 0, 0}},
	{"rename",	DM_DEV_RENAME,		{4, 0, 0}},
	{"version",	DM_VERSION,		{4, 0, 0}},
	{"status",	DM_TABLE_STATUS,	{4, 0, 0}},
	{"table",	DM_TABLE_STATUS,	{4, 0, 0}},
	{"waitevent",	DM_DEV_WAIT,		{4, 0, 0}},
	{"names",	DM_LIST_DEVICES,	{4, 0, 0}},
	{"clear",	DM_TABLE_CLEAR,		{4, 0, 0}},
	{"mknodes",	DM_DEV_STATUS,		{4, 0, 0}},
#ifdef DM_LIST_VERSIONS
	{"versions",	DM_LIST_VERSIONS,	{4, 1, 0}},
#endif
#ifdef DM_TARGET_MSG
	{"message",	DM_TARGET_MSG,		{4, 2, 0}},
#endif
#ifdef DM_DEV_SET_GEOMETRY
	{"setgeometry",	DM_DEV_SET_GEOMETRY,	{4, 6, 0}},
#endif
};
/* *INDENT-ON* */

#define ALIGNMENT 8

/* FIXME Rejig library to record & use errno instead */
#ifndef DM_EXISTS_FLAG
#  define DM_EXISTS_FLAG 0x00000004
#endif

static char *_align(char *ptr, unsigned int a)
{
	register unsigned long agn = --a;

	return (char *) (((unsigned long) ptr + agn) & ~agn);
}

#ifdef DM_IOCTLS
static int _kernel_major = 0;
static int _kernel_minor = 0;
static int _kernel_release = 0;

static int _uname(void)
{
	static int _uts_set = 0;
	struct utsname _uts;
	int parts;

	if (_uts_set)
		return 1;

	if (uname(&_uts)) {
		log_error("uname failed: %s", strerror(errno));
		return 0;
	}

	parts = sscanf(_uts.release, "%d.%d.%d",
		       &_kernel_major, &_kernel_minor, &_kernel_release);

	/* Kernels with a major number of 2 always had 3 parts. */
	if (parts < 1 || (_kernel_major < 3 && parts < 3)) {
		log_error("Could not determine kernel version used.");
		return 0;
	}

	_uts_set = 1;
	return 1;
}

/*
 * Set number to NULL to populate _dm_bitset - otherwise first
 * match is returned.
 * Returns:
 * 	0 - error
 * 	1 - success - number found
 * 	2 - success - number not found (only if require_module_loaded=0)
 */
static int _get_proc_number(const char *file, const char *name,
			    uint32_t *number, int require_module_loaded)
{
	FILE *fl;
	char nm[256];
	char *line = NULL;
	size_t len;
	uint32_t num;

	if (!(fl = fopen(file, "r"))) {
		log_sys_error("fopen", file);
		return 0;
	}

	while (getline(&line, &len, fl) != -1) {
		if (sscanf(line, "%d %255s\n", &num, &nm[0]) == 2) {
			if (!strcmp(name, nm)) {
				if (number) {
					*number = num;
					if (fclose(fl))
						log_sys_error("fclose", file);
					free(line);
					return 1;
				}
				dm_bit_set(_dm_bitset, num);
			}
		}
	}
	if (fclose(fl))
		log_sys_error("fclose", file);
	free(line);

	if (number) {
		if (require_module_loaded) {
			log_error("%s: No entry for %s found", file, name);
			return 0;
		} else
			return 2;
	}

	return 1;
}

static int _control_device_number(uint32_t *major, uint32_t *minor)
{
	if (!_get_proc_number(PROC_DEVICES, MISC_NAME, major, 1) ||
	    !_get_proc_number(PROC_MISC, DM_NAME, minor, 1)) {
		*major = 0;
		return 0;
	}

	return 1;
}

/*
 * Returns 1 if it exists on returning; 0 if it doesn't; -1 if it's wrong.
 */
static int _control_exists(const char *control, uint32_t major, uint32_t minor)
{
	struct stat buf;

	if (stat(control, &buf) < 0) {
		if (errno != ENOENT)
			log_sys_error("stat", control);
		return 0;
	}

	if (!S_ISCHR(buf.st_mode)) {
		log_verbose("%s: Wrong inode type", control);
		if (!unlink(control))
			return 0;
		log_sys_error("unlink", control);
		return -1;
	}

	if (major && buf.st_rdev != MKDEV((dev_t)major, (dev_t)minor)) {
		log_verbose("%s: Wrong device number: (%u, %u) instead of "
			    "(%u, %u)", control,
			    MAJOR(buf.st_mode), MINOR(buf.st_mode),
			    major, minor);
		if (!unlink(control))
			return 0;
		log_sys_error("unlink", control);
		return -1;
	}

	return 1;
}

static int _create_control(const char *control, uint32_t major, uint32_t minor)
{
	int ret;
	mode_t old_umask;

	/*
	 * Return if the control already exists with intended major/minor
	 * or there's an error unlinking an apparently incorrect one.
	 */
	ret = _control_exists(control, major, minor);
	if (ret == -1)
		return 0;	/* Failed to unlink existing incorrect node */
	if (ret)
		return 1;	/* Already exists and correct */

	(void) dm_prepare_selinux_context(dm_dir(), S_IFDIR);
	old_umask = umask(DM_DEV_DIR_UMASK);
	ret = dm_create_dir(dm_dir());
	umask(old_umask);
	(void) dm_prepare_selinux_context(NULL, 0);

	if (!ret)
		return 0;

	log_verbose("Creating device %s (%u, %u)", control, major, minor);

	(void) dm_prepare_selinux_context(control, S_IFCHR);
	old_umask = umask(DM_CONTROL_NODE_UMASK);
	if (mknod(control, S_IFCHR | S_IRUSR | S_IWUSR,
		  MKDEV((dev_t)major, (dev_t)minor)) < 0)  {
		log_sys_error("mknod", control);
		(void) dm_prepare_selinux_context(NULL, 0);
		return 0;
	}
	umask(old_umask);
	(void) dm_prepare_selinux_context(NULL, 0);

	return 1;
}
#endif

/*
 * FIXME Update bitset in long-running process if dm claims new major numbers.
 */
/*
 * If require_module_loaded=0, caller is responsible to check
 * whether _dm_device_major or _dm_bitset is really set. If
 * it's not, it means the module is not loaded.
 */
static int _create_dm_bitset(int require_module_loaded)
{
	int r;

#ifdef DM_IOCTLS
	if (_dm_bitset || _dm_device_major)
		return 1;

	if (!_uname())
		return 0;

	/*
	 * 2.6 kernels are limited to one major number.
	 * Assume 2.4 kernels are patched not to.
	 * FIXME Check _dm_version and _dm_version_minor if 2.6 changes this.
	 */
	if (KERNEL_VERSION(_kernel_major, _kernel_minor, _kernel_release) >=
	    KERNEL_VERSION(2, 6, 0))
		_dm_multiple_major_support = 0;

	if (!_dm_multiple_major_support) {
		if (!_get_proc_number(PROC_DEVICES, DM_NAME, &_dm_device_major,
				      require_module_loaded))
			return 0;
		return 1;
	}

	/* Multiple major numbers supported */
	if (!(_dm_bitset = dm_bitset_create(NULL, NUMBER_OF_MAJORS)))
		return 0;

	r = _get_proc_number(PROC_DEVICES, DM_NAME, NULL, require_module_loaded);
	if (!r || r == 2) {
		dm_bitset_destroy(_dm_bitset);
		_dm_bitset = NULL;
		/*
		 * It's not an error if we didn't find anything and we
		 * didn't require module to be loaded at the same time.
		 */
		return r == 2;
	}

	return 1;
#else
	return 0;
#endif
}

int dm_is_dm_major(uint32_t major)
{
	if (!_create_dm_bitset(0))
		return 0;

	if (_dm_multiple_major_support) {
		if (!_dm_bitset)
			return 0;
		return dm_bit(_dm_bitset, major) ? 1 : 0;
	}
	else {
		if (!_dm_device_major)
			return 0;
		return (major == _dm_device_major) ? 1 : 0;
	}
}

static void _close_control_fd(void)
{
	if (_control_fd != -1) {
		if (close(_control_fd) < 0)
			log_sys_error("close", "_control_fd");
		_control_fd = -1;
	}
}

#ifdef DM_IOCTLS
static int _open_and_assign_control_fd(const char *control)
{
	if ((_control_fd = open(control, O_RDWR)) < 0) {
		log_sys_error("open", control);
		return 0;
	}

	return 1;
}
#endif

static int _open_control(void)
{
#ifdef DM_IOCTLS
	char control[PATH_MAX];
	uint32_t major = MISC_MAJOR;
	uint32_t minor = MAPPER_CTRL_MINOR;

	if (_control_fd != -1)
		return 1;

	if (!_uname())
		return 0;

	if (dm_snprintf(control, sizeof(control), "%s/%s", dm_dir(), DM_CONTROL_NODE) < 0)
		goto_bad;

	/*
	 * Prior to 2.6.36 the minor number should be looked up in /proc.
	 */
	if ((KERNEL_VERSION(_kernel_major, _kernel_minor, _kernel_release) <
	     KERNEL_VERSION(2, 6, 36)) &&
	    !_control_device_number(&major, &minor))
		goto_bad;

	/*
	 * Create the node with correct major and minor if not already done.
	 * Udev may already have created /dev/mapper/control
	 * from the modules.devname file generated by depmod.
	 */
	if (!_create_control(control, major, minor))
		goto_bad;

	/*
	 * As of 2.6.36 kernels, the open can trigger autoloading dm-mod.
	 */
	if (!_open_and_assign_control_fd(control))
		goto_bad;
	
	if (!_create_dm_bitset(1)) {
		log_error("Failed to set up list of device-mapper major numbers");
		return 0;
	}

	return 1;

bad:
	log_error("Failure to communicate with kernel device-mapper driver.");
	if (!geteuid())
		log_error("Check that device-mapper is available in the kernel.");
	return 0;
#else
	return 1;
#endif
}

static void _dm_zfree_string(char *string)
{
	if (string) {
		memset(string, 0, strlen(string));
		dm_free(string);
	}
}

static void _dm_zfree_dmi(struct dm_ioctl *dmi)
{
	if (dmi) {
		memset(dmi, 0, dmi->data_size);
		dm_free(dmi);
	}
}

void dm_task_destroy(struct dm_task *dmt)
{
	struct target *t, *n;

	for (t = dmt->head; t; t = n) {
		n = t->next;
		_dm_zfree_string(t->params);
		dm_free(t->type);
		dm_free(t);
	}

	_dm_zfree_dmi(dmt->dmi.v4);
	dm_free(dmt->dev_name);
	dm_free(dmt->mangled_dev_name);
	dm_free(dmt->newname);
	dm_free(dmt->message);
	dm_free(dmt->geometry);
	dm_free(dmt->uuid);
	dm_free(dmt->mangled_uuid);
	dm_free(dmt);
}

/*
 * Protocol Version 4 functions.
 */

int dm_task_get_driver_version(struct dm_task *dmt, char *version, size_t size)
{
	unsigned *v;

	if (!dmt->dmi.v4) {
		if (version)
			version[0] = '\0';
		return 0;
	}

	v = dmt->dmi.v4->version;
	_dm_version_minor = v[1];
	_dm_version_patchlevel = v[2];
	if (version &&
	    (snprintf(version, size, "%u.%u.%u", v[0], v[1], v[2]) < 0)) {
		log_error("Buffer for version is to short.");
		if (size > 0)
			version[0] = '\0';
		return 0;
	}

	return 1;
}

static int _check_version(char *version, size_t size, int log_suppress)
{
	struct dm_task *task;
	int r;

	if (!(task = dm_task_create(DM_DEVICE_VERSION))) {
		log_error("Failed to get device-mapper version");
		version[0] = '\0';
		return 0;
	}

	if (log_suppress)
		_log_suppress = 1;

	r = dm_task_run(task);
	if (!dm_task_get_driver_version(task, version, size))
		stack;
	dm_task_destroy(task);
	_log_suppress = 0;

	return r;
}

/*
 * Find out device-mapper's major version number the first time 
 * this is called and whether or not we support it.
 */
int dm_check_version(void)
{
	char libversion[64] = "", dmversion[64] = "";
	const char *compat = "";

	if (_version_checked)
		return _version_ok;

	_version_checked = 1;

	if (_check_version(dmversion, sizeof(dmversion), _dm_compat))
		return 1;

	if (!_dm_compat)
		goto_bad;

	log_verbose("device-mapper ioctl protocol version %u failed. "
		    "Trying protocol version 1.", _dm_version);
	_dm_version = 1;
	if (_check_version(dmversion, sizeof(dmversion), 0)) {
		log_verbose("Using device-mapper ioctl protocol version 1");
		return 1;
	}

	compat = "(compat)";

      bad:
	dm_get_library_version(libversion, sizeof(libversion));

	log_error("Incompatible libdevmapper %s%s and kernel driver %s.",
		  *libversion ? libversion : "(unknown version)", compat,
		  *dmversion ? dmversion : "(unknown version)");

	_version_ok = 0;
	return 0;
}

int dm_cookie_supported(void)
{
	return (dm_check_version() &&
		_dm_version >= 4 &&
		_dm_version_minor >= 15);
}

static int dm_inactive_supported(void)
{
	int inactive_supported = 0;

	if (dm_check_version() && _dm_version >= 4) {
		if (_dm_version_minor >= 16)
			inactive_supported = 1; /* upstream */
		else if (_dm_version_minor == 11 &&
			 (_dm_version_patchlevel >= 6 &&
			  _dm_version_patchlevel <= 40)) {
			inactive_supported = 1; /* RHEL 5.7 */
		}
	}

	return inactive_supported;
}

int dm_message_supports_precise_timestamps(void)
{
	/*
	 * 4.32.0 supports "precise_timestamps" and "histogram:" options
	 * to @stats_create messages but lacks the ability to report
	 * these properties via a subsequent @stats_list: require at
	 * least 4.33.0 in order to use these features.
	 */
	if (dm_check_version() && _dm_version >= 4)
		if (_dm_version_minor >= 33)
			return 1;
	return 0;
}

void *dm_get_next_target(struct dm_task *dmt, void *next,
			 uint64_t *start, uint64_t *length,
			 char **target_type, char **params)
{
	struct target *t = (struct target *) next;

	if (!t)
		t = dmt->head;

	if (!t) {
		*start = 0;
		*length = 0;
		*target_type = 0;
		*params = 0;
		return NULL;
	}

	*start = t->start;
	*length = t->length;
	*target_type = t->type;
	*params = t->params;

	return t->next;
}

/* Unmarshall the target info returned from a status call */
static int _unmarshal_status(struct dm_task *dmt, struct dm_ioctl *dmi)
{
	char *outbuf = (char *) dmi + dmi->data_start;
	char *outptr = outbuf;
	uint32_t i;
	struct dm_target_spec *spec;

	for (i = 0; i < dmi->target_count; i++) {
		spec = (struct dm_target_spec *) outptr;
		if (!dm_task_add_target(dmt, spec->sector_start,
					spec->length,
					spec->target_type,
					outptr + sizeof(*spec))) {
			return 0;
		}

		outptr = outbuf + spec->next;
	}

	return 1;
}

int dm_format_dev(char *buf, int bufsize, uint32_t dev_major,
		  uint32_t dev_minor)
{
	int r;

	if (bufsize < 8)
		return 0;

	r = snprintf(buf, (size_t) bufsize, "%u:%u", dev_major, dev_minor);
	if (r < 0 || r > bufsize - 1)
		return 0;

	return 1;
}

int dm_task_get_info(struct dm_task *dmt, struct dm_info *info)
{
	if (!dmt->dmi.v4)
		return 0;

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

	info->exists = dmt->dmi.v4->flags & DM_EXISTS_FLAG ? 1 : 0;
	if (!info->exists)
		return 1;

	info->suspended = dmt->dmi.v4->flags & DM_SUSPEND_FLAG ? 1 : 0;
	info->read_only = dmt->dmi.v4->flags & DM_READONLY_FLAG ? 1 : 0;
	info->live_table = dmt->dmi.v4->flags & DM_ACTIVE_PRESENT_FLAG ? 1 : 0;
	info->inactive_table = dmt->dmi.v4->flags & DM_INACTIVE_PRESENT_FLAG ?
	    1 : 0;
	info->deferred_remove = dmt->dmi.v4->flags & DM_DEFERRED_REMOVE;
	info->internal_suspend = (dmt->dmi.v4->flags & DM_INTERNAL_SUSPEND_FLAG) ? 1 : 0;
	info->target_count = dmt->dmi.v4->target_count;
	info->open_count = dmt->dmi.v4->open_count;
	info->event_nr = dmt->dmi.v4->event_nr;
	info->major = MAJOR(dmt->dmi.v4->dev);
	info->minor = MINOR(dmt->dmi.v4->dev);

	return 1;
}

uint32_t dm_task_get_read_ahead(const struct dm_task *dmt, uint32_t *read_ahead)
{
	const char *dev_name;

	*read_ahead = 0;

	if (!dmt->dmi.v4 || !(dmt->dmi.v4->flags & DM_EXISTS_FLAG))
		return 0;

	if (*dmt->dmi.v4->name)
		dev_name = dmt->dmi.v4->name;
	else if (!(dev_name = DEV_NAME(dmt))) {
		log_error("Get read ahead request failed: device name unrecorded.");
		return 0;
	}

	return get_dev_node_read_ahead(dev_name, MAJOR(dmt->dmi.v4->dev),
				       MINOR(dmt->dmi.v4->dev), read_ahead);
}

struct dm_deps *dm_task_get_deps(struct dm_task *dmt)
{
	return (struct dm_deps *) (((char *) dmt->dmi.v4) +
				   dmt->dmi.v4->data_start);
}

struct dm_names *dm_task_get_names(struct dm_task *dmt)
{
	return (struct dm_names *) (((char *) dmt->dmi.v4) +
				    dmt->dmi.v4->data_start);
}

struct dm_versions *dm_task_get_versions(struct dm_task *dmt)
{
	return (struct dm_versions *) (((char *) dmt->dmi.v4) +
				       dmt->dmi.v4->data_start);
}

const char *dm_task_get_message_response(struct dm_task *dmt)
{
	const char *start, *end;

	if (!(dmt->dmi.v4->flags & DM_DATA_OUT_FLAG))
		return NULL;

	start = (const char *) dmt->dmi.v4 + dmt->dmi.v4->data_start;
	end = (const char *) dmt->dmi.v4 + dmt->dmi.v4->data_size;

	if (end < start) {
		log_error(INTERNAL_ERROR "Corrupted message structure returned: start %d > end %d", (int)dmt->dmi.v4->data_start, (int)dmt->dmi.v4->data_size);
		return NULL;
	}

	if (!memchr(start, 0, end - start)) {
		log_error(INTERNAL_ERROR "Message response doesn't contain terminating NUL character");
		return NULL;
	}

	return start;
}

int dm_task_set_ro(struct dm_task *dmt)
{
	dmt->read_only = 1;
	return 1;
}

int dm_task_set_read_ahead(struct dm_task *dmt, uint32_t read_ahead,
			   uint32_t read_ahead_flags)
{
	dmt->read_ahead = read_ahead;
	dmt->read_ahead_flags = read_ahead_flags;

	return 1;
}

int dm_task_suppress_identical_reload(struct dm_task *dmt)
{
	dmt->suppress_identical_reload = 1;
	return 1;
}

int dm_task_set_add_node(struct dm_task *dmt, dm_add_node_t add_node)
{
	switch (add_node) {
	case DM_ADD_NODE_ON_RESUME:
	case DM_ADD_NODE_ON_CREATE:
		dmt->add_node = add_node;
		return 1;
	default:
		log_error("Unknown add node parameter");
		return 0;
	}
}

int dm_task_set_newuuid(struct dm_task *dmt, const char *newuuid)
{
	dm_string_mangling_t mangling_mode = dm_get_name_mangling_mode();
	char mangled_uuid[DM_UUID_LEN];
	int r = 0;

	if (strlen(newuuid) >= DM_UUID_LEN) {
		log_error("Uuid \"%s\" too long", newuuid);
		return 0;
	}

	if (!check_multiple_mangled_string_allowed(newuuid, "new UUID", mangling_mode))
		return_0;

	if (mangling_mode != DM_STRING_MANGLING_NONE &&
	    (r = mangle_string(newuuid, "new UUID", strlen(newuuid), mangled_uuid,
			       sizeof(mangled_uuid), mangling_mode)) < 0) {
		log_error("Failed to mangle new device UUID \"%s\"", newuuid);
		return 0;
	}

	if (r) {
		log_debug_activation("New device uuid mangled [%s]: %s --> %s",
				     mangling_mode == DM_STRING_MANGLING_AUTO ? "auto" : "hex",
				     newuuid, mangled_uuid);
		newuuid = mangled_uuid;
	}

	dm_free(dmt->newname);
	if (!(dmt->newname = dm_strdup(newuuid))) {
		log_error("dm_task_set_newuuid: strdup(%s) failed", newuuid);
		return 0;
	}
	dmt->new_uuid = 1;

	return 1;
}

int dm_task_set_message(struct dm_task *dmt, const char *message)
{
	dm_free(dmt->message);
	if (!(dmt->message = dm_strdup(message))) {
		log_error("dm_task_set_message: strdup failed");
		return 0;
	}

	return 1;
}

int dm_task_set_sector(struct dm_task *dmt, uint64_t sector)
{
	dmt->sector = sector;

	return 1;
}

int dm_task_set_geometry(struct dm_task *dmt, const char *cylinders, const char *heads,
			 const char *sectors, const char *start)
{
	dm_free(dmt->geometry);
	if (dm_asprintf(&(dmt->geometry), "%s %s %s %s",
			cylinders, heads, sectors, start) < 0) {
		log_error("dm_task_set_geometry: sprintf failed");
		return 0;
	}

	return 1;
}

int dm_task_no_flush(struct dm_task *dmt)
{
	dmt->no_flush = 1;

	return 1;
}

int dm_task_no_open_count(struct dm_task *dmt)
{
	dmt->no_open_count = 1;

	return 1;
}

int dm_task_skip_lockfs(struct dm_task *dmt)
{
	dmt->skip_lockfs = 1;

	return 1;
}

int dm_task_secure_data(struct dm_task *dmt)
{
	dmt->secure_data = 1;

	return 1;
}

int dm_task_retry_remove(struct dm_task *dmt)
{
	dmt->retry_remove = 1;

	return 1;
}

int dm_task_deferred_remove(struct dm_task *dmt)
{
	dmt->deferred_remove = 1;

	return 1;
}

int dm_task_query_inactive_table(struct dm_task *dmt)
{
	dmt->query_inactive_table = 1;

	return 1;
}

int dm_task_set_event_nr(struct dm_task *dmt, uint32_t event_nr)
{
	dmt->event_nr = event_nr;

	return 1;
}

int dm_task_set_record_timestamp(struct dm_task *dmt)
{
	if (!_dm_ioctl_timestamp)
		_dm_ioctl_timestamp = dm_timestamp_alloc();

	if (!_dm_ioctl_timestamp)
		return_0;

	dmt->record_timestamp = 1;

	return 1;
}

struct dm_timestamp *dm_task_get_ioctl_timestamp(struct dm_task *dmt)
{
	return dmt->record_timestamp ? _dm_ioctl_timestamp : NULL;
}

struct target *create_target(uint64_t start, uint64_t len, const char *type,
			     const char *params)
{
	struct target *t;

	if (strlen(type) >= DM_MAX_TYPE_NAME) {
		log_error("Target type name %s is too long.", type);
		return NULL;
	}

	if (!(t = dm_zalloc(sizeof(*t)))) {
		log_error("create_target: malloc(%" PRIsize_t ") failed",
			  sizeof(*t));
		return NULL;
	}

	if (!(t->params = dm_strdup(params))) {
		log_error("create_target: strdup(params) failed");
		goto bad;
	}

	if (!(t->type = dm_strdup(type))) {
		log_error("create_target: strdup(type) failed");
		goto bad;
	}

	t->start = start;
	t->length = len;
	return t;

      bad:
	_dm_zfree_string(t->params);
	dm_free(t->type);
	dm_free(t);
	return NULL;
}

static char *_add_target(struct target *t, char *out, char *end)
{
	char *out_sp = out;
	struct dm_target_spec sp;
	size_t sp_size = sizeof(struct dm_target_spec);
	unsigned int backslash_count = 0;
	int len;
	char *pt;

	if (strlen(t->type) >= sizeof(sp.target_type)) {
		log_error("Target type name %s is too long.", t->type);
		return NULL;
	}

	sp.status = 0;
	sp.sector_start = t->start;
	sp.length = t->length;
	strncpy(sp.target_type, t->type, sizeof(sp.target_type) - 1);
	sp.target_type[sizeof(sp.target_type) - 1] = '\0';

	out += sp_size;
	pt = t->params;

	while (*pt)
		if (*pt++ == '\\')
			backslash_count++;
	len = strlen(t->params) + backslash_count;

	if ((out >= end) || (out + len + 1) >= end) {
		log_error("Ran out of memory building ioctl parameter");
		return NULL;
	}

	if (backslash_count) {
		/* replace "\" with "\\" */
		pt = t->params;
		do {
			if (*pt == '\\')
				*out++ = '\\';
			*out++ = *pt++;
		} while (*pt);
		*out++ = '\0';
	}
	else {
		strcpy(out, t->params);
		out += len + 1;
	}

	/* align next block */
	out = _align(out, ALIGNMENT);

	sp.next = out - out_sp;
	memcpy(out_sp, &sp, sp_size);

	return out;
}

static int _lookup_dev_name(uint64_t dev, char *buf, size_t len)
{
	struct dm_names *names;
	unsigned next = 0;
	struct dm_task *dmt;
	int r = 0;
 
	if (!(dmt = dm_task_create(DM_DEVICE_LIST)))
		return 0;
 
	if (!dm_task_run(dmt))
		goto out;

	if (!(names = dm_task_get_names(dmt)))
		goto out;
 
	if (!names->dev)
		goto out;
 
	do {
		names = (struct dm_names *)((char *) names + next);
		if (names->dev == dev) {
			strncpy(buf, names->name, len);
			r = 1;
			break;
		}
		next = names->next;
	} while (next);

      out:
	dm_task_destroy(dmt);
	return r;
}

static struct dm_ioctl *_flatten(struct dm_task *dmt, unsigned repeat_count)
{
	const size_t min_size = 16 * 1024;
	const int (*version)[3];

	struct dm_ioctl *dmi;
	struct target *t;
	struct dm_target_msg *tmsg;
	size_t len = sizeof(struct dm_ioctl);
	char *b, *e;
	int count = 0;

	for (t = dmt->head; t; t = t->next) {
		len += sizeof(struct dm_target_spec);
		len += strlen(t->params) + 1 + ALIGNMENT;
		count++;
	}

	if (count && (dmt->sector || dmt->message)) {
		log_error("targets and message are incompatible");
		return NULL;
	}

	if (count && dmt->newname) {
		log_error("targets and rename are incompatible");
		return NULL;
	}

	if (count && dmt->geometry) {
		log_error("targets and geometry are incompatible");
		return NULL;
	}

	if (dmt->newname && (dmt->sector || dmt->message)) {
		log_error("message and rename are incompatible");
		return NULL;
	}

	if (dmt->newname && dmt->geometry) {
		log_error("geometry and rename are incompatible");
		return NULL;
	}

	if (dmt->geometry && (dmt->sector || dmt->message)) {
		log_error("geometry and message are incompatible");
		return NULL;
	}

	if (dmt->sector && !dmt->message) {
		log_error("message is required with sector");
		return NULL;
	}

	if (dmt->newname)
		len += strlen(dmt->newname) + 1;

	if (dmt->message)
		len += sizeof(struct dm_target_msg) + strlen(dmt->message) + 1;

	if (dmt->geometry)
		len += strlen(dmt->geometry) + 1;

	/*
	 * Give len a minimum size so that we have space to store
	 * dependencies or status information.
	 */
	if (len < min_size)
		len = min_size;

	/* Increase buffer size if repeating because buffer was too small */
	while (repeat_count--)
		len *= 2;

	if (!(dmi = dm_malloc(len)))
		return NULL;

	memset(dmi, 0, len);

	version = &_cmd_data_v4[dmt->type].version;

	dmi->version[0] = (*version)[0];
	dmi->version[1] = (*version)[1];
	dmi->version[2] = (*version)[2];

	dmi->data_size = len;
	dmi->data_start = sizeof(struct dm_ioctl);

	if (dmt->minor >= 0) {
		if (dmt->major <= 0) {
			log_error("Missing major number for persistent device.");
			goto bad;
		}

		if (!_dm_multiple_major_support && dmt->allow_default_major_fallback &&
		    dmt->major != (int) _dm_device_major) {
			log_verbose("Overriding major number of %d "
				    "with %u for persistent device.",
				    dmt->major, _dm_device_major);
			dmt->major = _dm_device_major;
		}

		dmi->flags |= DM_PERSISTENT_DEV_FLAG;
		dmi->dev = MKDEV((dev_t)dmt->major, (dev_t)dmt->minor);
	}

	/* Does driver support device number referencing? */
	if (_dm_version_minor < 3 && !DEV_NAME(dmt) && !DEV_UUID(dmt) && dmi->dev) {
		if (!_lookup_dev_name(dmi->dev, dmi->name, sizeof(dmi->name))) {
			log_error("Unable to find name for device (%" PRIu32
				  ":%" PRIu32 ")", dmt->major, dmt->minor);
			goto bad;
		}
		log_verbose("device (%" PRIu32 ":%" PRIu32 ") is %s "
			    "for compatibility with old kernel",
			    dmt->major, dmt->minor, dmi->name);
	}

	/* FIXME Until resume ioctl supplies name, use dev_name for readahead */
	if (DEV_NAME(dmt) && (dmt->type != DM_DEVICE_RESUME || dmt->minor < 0 ||
			      dmt->major < 0))
		strncpy(dmi->name, DEV_NAME(dmt), sizeof(dmi->name));

	if (DEV_UUID(dmt))
		strncpy(dmi->uuid, DEV_UUID(dmt), sizeof(dmi->uuid));

	if (dmt->type == DM_DEVICE_SUSPEND)
		dmi->flags |= DM_SUSPEND_FLAG;
	if (dmt->no_flush) {
		if (_dm_version_minor < 12)
			log_verbose("No flush flag unsupported by kernel. "
				    "Buffers will be flushed.");
		else
			dmi->flags |= DM_NOFLUSH_FLAG;
	}
	if (dmt->read_only)
		dmi->flags |= DM_READONLY_FLAG;
	if (dmt->skip_lockfs)
		dmi->flags |= DM_SKIP_LOCKFS_FLAG;
	if (dmt->deferred_remove && (dmt->type == DM_DEVICE_REMOVE || dmt->type == DM_DEVICE_REMOVE_ALL))
		dmi->flags |= DM_DEFERRED_REMOVE;

	if (dmt->secure_data) {
		if (_dm_version_minor < 20)
			log_verbose("Secure data flag unsupported by kernel. "
				    "Buffers will not be wiped after use.");
		dmi->flags |= DM_SECURE_DATA_FLAG;
	}
	if (dmt->query_inactive_table) {
		if (!dm_inactive_supported())
			log_warn("WARNING: Inactive table query unsupported "
				 "by kernel.  It will use live table.");
		dmi->flags |= DM_QUERY_INACTIVE_TABLE_FLAG;
	}
	if (dmt->new_uuid) {
		if (_dm_version_minor < 19) {
			log_error("WARNING: Setting UUID unsupported by "
				  "kernel.  Aborting operation.");
			goto bad;
		}
		dmi->flags |= DM_UUID_FLAG;
	}

	dmi->target_count = count;
	dmi->event_nr = dmt->event_nr;

	b = (char *) (dmi + 1);
	e = (char *) dmi + len;

	for (t = dmt->head; t; t = t->next)
		if (!(b = _add_target(t, b, e)))
			goto_bad;

	if (dmt->newname)
		strcpy(b, dmt->newname);

	if (dmt->message) {
		tmsg = (struct dm_target_msg *) b;
		tmsg->sector = dmt->sector;
		strcpy(tmsg->message, dmt->message);
	}

	if (dmt->geometry)
		strcpy(b, dmt->geometry);

	return dmi;

      bad:
	_dm_zfree_dmi(dmi);
	return NULL;
}

static int _process_mapper_dir(struct dm_task *dmt)
{
	struct dirent *dirent;
	DIR *d;
	const char *dir;
	int r = 1;

	dir = dm_dir();
	if (!(d = opendir(dir))) {
		log_sys_error("opendir", dir);
		return 0;
	}

	while ((dirent = readdir(d))) {
		if (!strcmp(dirent->d_name, ".") ||
		    !strcmp(dirent->d_name, "..") ||
		    !strcmp(dirent->d_name, "control"))
			continue;
		if (!dm_task_set_name(dmt, dirent->d_name)) {
			r = 0;
			stack;
			continue; /* try next name */
		}
		if (!dm_task_run(dmt)) {
			r = 0;
			stack;  /* keep going */
		}
	}

	if (closedir(d))
		log_sys_error("closedir", dir);

	return r;
}

static int _process_all_v4(struct dm_task *dmt)
{
	struct dm_task *task;
	struct dm_names *names;
	unsigned next = 0;
	int r = 1;

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

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

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

	if (!names->dev)
		goto out;

	do {
		names = (struct dm_names *)((char *) names + next);
		if (!dm_task_set_name(dmt, names->name)) {
			r = 0;
			goto out;
		}
		if (!dm_task_run(dmt))
			r = 0;
		next = names->next;
	} while (next);

      out:
	dm_task_destroy(task);
	return r;
}

static int _mknodes_v4(struct dm_task *dmt)
{
	(void) _process_mapper_dir(dmt);

	return _process_all_v4(dmt);
}

/*
 * If an operation that uses a cookie fails, decrement the
 * semaphore instead of udev.
 */
static int _udev_complete(struct dm_task *dmt)
{
	uint16_t base;

	if (dmt->cookie_set &&
	    (base = dmt->event_nr & ~DM_UDEV_FLAGS_MASK))
		/* strip flags from the cookie and use cookie magic instead */
		return dm_udev_complete(base | (DM_COOKIE_MAGIC <<
						DM_UDEV_FLAGS_SHIFT));

	return 1;
}

#ifdef DM_IOCTLS
static int _check_uevent_generated(struct dm_ioctl *dmi)
{
	if (!dm_check_version() ||
	    _dm_version < 4 ||
	    _dm_version_minor < 17)
		/* can't check, assume uevent is generated */
		return 1;

	return dmi->flags & DM_UEVENT_GENERATED_FLAG;
}
#endif

static int _create_and_load_v4(struct dm_task *dmt)
{
	struct dm_task *task;
	int r;
	uint32_t cookie;

	/* Use new task struct to create the device */
	if (!(task = dm_task_create(DM_DEVICE_CREATE))) {
		_udev_complete(dmt);
		return_0;
	}

	/* Copy across relevant fields */
	if (dmt->dev_name && !dm_task_set_name(task, dmt->dev_name))
		goto_bad;

	if (dmt->uuid && !dm_task_set_uuid(task, dmt->uuid))
		goto_bad;

	task->major = dmt->major;
	task->minor = dmt->minor;
	task->uid = dmt->uid;
	task->gid = dmt->gid;
	task->mode = dmt->mode;
	/* FIXME: Just for udev_check in dm_task_run. Can we avoid this? */
	task->event_nr = dmt->event_nr & DM_UDEV_FLAGS_MASK;
	task->cookie_set = dmt->cookie_set;
	task->add_node = dmt->add_node;

	if (!dm_task_run(task))
		goto_bad;

	dm_task_destroy(task);

	/* Next load the table */
	if (!(task = dm_task_create(DM_DEVICE_RELOAD))) {
		stack;
		_udev_complete(dmt);
		goto revert;
	}

	/* Copy across relevant fields */
	if (dmt->dev_name && !dm_task_set_name(task, dmt->dev_name)) {
		stack;
		dm_task_destroy(task);
		_udev_complete(dmt);
		goto revert;
	}

	task->read_only = dmt->read_only;
	task->head = dmt->head;
	task->tail = dmt->tail;
	task->secure_data = dmt->secure_data;

	r = dm_task_run(task);

	task->head = NULL;
	task->tail = NULL;
	dm_task_destroy(task);

	if (!r) {
		stack;
		_udev_complete(dmt);
		goto revert;
	}

	/* Use the original structure last so the info will be correct */
	dmt->type = DM_DEVICE_RESUME;
	dm_free(dmt->uuid);
	dmt->uuid = NULL;
	dm_free(dmt->mangled_uuid);
	dmt->mangled_uuid = NULL;

	if (dm_task_run(dmt))
		return 1;

      revert:
	dmt->type = DM_DEVICE_REMOVE;
	dm_free(dmt->uuid);
	dmt->uuid = NULL;
	dm_free(dmt->mangled_uuid);
	dmt->mangled_uuid = NULL;

	/*
	 * Also udev-synchronize "remove" dm task that is a part of this revert!
	 * But only if the original dm task was supposed to be synchronized.
	 */
	if (dmt->cookie_set) {
		cookie = (dmt->event_nr & ~DM_UDEV_FLAGS_MASK) |
			 (DM_COOKIE_MAGIC << DM_UDEV_FLAGS_SHIFT);
		if (!dm_task_set_cookie(dmt, &cookie,
					(dmt->event_nr & DM_UDEV_FLAGS_MASK) >>
					DM_UDEV_FLAGS_SHIFT))
			stack; /* keep going */
	}

	if (!dm_task_run(dmt))
		log_error("Failed to revert device creation.");

	return 0;

      bad:
	dm_task_destroy(task);
	_udev_complete(dmt);

	return 0;
}

uint64_t dm_task_get_existing_table_size(struct dm_task *dmt)
{
	return dmt->existing_table_size;
}

static int _reload_with_suppression_v4(struct dm_task *dmt)
{
	struct dm_task *task;
	struct target *t1, *t2;
	size_t len;
	int r;

	/* New task to get existing table information */
	if (!(task = dm_task_create(DM_DEVICE_TABLE))) {
		log_error("Failed to create device-mapper task struct");
		return 0;
	}

	/* Copy across relevant fields */
	if (dmt->dev_name && !dm_task_set_name(task, dmt->dev_name)) {
		dm_task_destroy(task);
		return 0;
	}

	if (dmt->uuid && !dm_task_set_uuid(task, dmt->uuid)) {
		dm_task_destroy(task);
		return 0;
	}

	task->major = dmt->major;
	task->minor = dmt->minor;

	r = dm_task_run(task);

	if (!r) {
		dm_task_destroy(task);
		return r;
	}

	/* Store existing table size */
	t2 = task->head;
	while (t2 && t2->next)
		t2 = t2->next;
	dmt->existing_table_size = t2 ? t2->start + t2->length : 0;

	if (((task->dmi.v4->flags & DM_READONLY_FLAG) ? 1 : 0) != dmt->read_only)
		goto no_match;

	t1 = dmt->head;
	t2 = task->head;

	while (t1 && t2) {
		len = strlen(t2->params);
		while (len-- > 0 && t2->params[len] == ' ')
			t2->params[len] = '\0';
		if ((t1->start != t2->start) ||
		    (t1->length != t2->length) ||
		    (strcmp(t1->type, t2->type)) ||
		    (strcmp(t1->params, t2->params)))
			goto no_match;
		t1 = t1->next;
		t2 = t2->next;
	}
	
	if (!t1 && !t2) {
		dmt->dmi.v4 = task->dmi.v4;
		task->dmi.v4 = NULL;
		dm_task_destroy(task);
		return 1;
	}

no_match:
	dm_task_destroy(task);

	/* Now do the original reload */
	dmt->suppress_identical_reload = 0;
	r = dm_task_run(dmt);

	return r;
}

static int _check_children_not_suspended_v4(struct dm_task *dmt, uint64_t device)
{
	struct dm_task *task;
	struct dm_info info;
	struct dm_deps *deps;
	int r = 0;
	uint32_t i;

	/* Find dependencies */
	if (!(task = dm_task_create(DM_DEVICE_DEPS)))
		return 0;

	/* Copy across or set relevant fields */
	if (device) {
		task->major = MAJOR(device);
		task->minor = MINOR(device);
	} else {
		if (dmt->dev_name && !dm_task_set_name(task, dmt->dev_name))
			goto out;

		if (dmt->uuid && !dm_task_set_uuid(task, dmt->uuid))
			goto out;

		task->major = dmt->major;
		task->minor = dmt->minor;
	}

	task->uid = dmt->uid;
	task->gid = dmt->gid;
	task->mode = dmt->mode;
	/* FIXME: Just for udev_check in dm_task_run. Can we avoid this? */
	task->event_nr = dmt->event_nr & DM_UDEV_FLAGS_MASK;
	task->cookie_set = dmt->cookie_set;
	task->add_node = dmt->add_node;
	
	if (!(r = dm_task_run(task)))
		goto out;

	if (!dm_task_get_info(task, &info) || !info.exists)
		goto out;

	/*
	 * Warn if any of the devices this device depends upon are already
	 * suspended: I/O could become trapped between the two devices.
	 */
	if (info.suspended) {
		if (!device)
			log_debug_activation("Attempting to suspend a device that is already suspended "
					     "(%u:%u)", info.major, info.minor);
		else
			log_error(INTERNAL_ERROR "Attempt to suspend device %s%s%s%.0d%s%.0d%s%s"
				  "that uses already-suspended device (%u:%u)", 
				  DEV_NAME(dmt) ? : "", DEV_UUID(dmt) ? : "",
				  dmt->major > 0 ? "(" : "",
				  dmt->major > 0 ? dmt->major : 0,
				  dmt->major > 0 ? ":" : "",
				  dmt->minor > 0 ? dmt->minor : 0,
				  dmt->major > 0 && dmt->minor == 0 ? "0" : "",
				  dmt->major > 0 ? ") " : "",
				  info.major, info.minor);

		/* No need for further recursion */
		r = 1;
		goto out;
	}

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

	for (i = 0; i < deps->count; i++) {
		/* Only recurse with dm devices */
		if (MAJOR(deps->device[i]) != _dm_device_major)
			continue;

		if (!_check_children_not_suspended_v4(task, deps->device[i]))
			goto out;
	}

	r = 1;

out:
	dm_task_destroy(task);

	return r;
}

static int _suspend_with_validation_v4(struct dm_task *dmt)
{
	/* Avoid recursion */
	dmt->enable_checks = 0;

	/*
	 * Ensure we can't leave any I/O trapped between suspended devices.
	 */
	if (!_check_children_not_suspended_v4(dmt, 0))
		return 0;

	/* Finally, perform the original suspend. */
	return dm_task_run(dmt);
}

static const char *_sanitise_message(char *message)
{
	const char *sanitised_message = message ?: "";

	/* FIXME: Check for whitespace variations. */
	/* This traps what cryptsetup sends us. */
	if (message && !strncasecmp(message, "key set", 7))
		sanitised_message = "key set";

	return sanitised_message;
}

#ifdef DM_IOCTLS
static int _do_dm_ioctl_unmangle_string(char *str, const char *str_name,
					char *buf, size_t buf_size,
					dm_string_mangling_t mode)
{
	int r;

	if (mode == DM_STRING_MANGLING_NONE)
		return 1;

	if (!check_multiple_mangled_string_allowed(str, str_name, mode))
		return_0;

	if ((r = unmangle_string(str, str_name, strlen(str), buf, buf_size, mode)) < 0) {
		log_debug_activation("_do_dm_ioctl_unmangle_string: failed to "
				     "unmangle %s \"%s\"", str_name, str);
		return 0;
	} else if (r)
		memcpy(str, buf, strlen(buf) + 1);

	return 1;
}

static int _dm_ioctl_unmangle_names(int type, struct dm_ioctl *dmi)
{
	char buf[DM_NAME_LEN];
	struct dm_names *names;
	unsigned next = 0;
	char *name;
	int r = 1;

	if ((name = dmi->name))
		r = _do_dm_ioctl_unmangle_string(name, "name", buf, sizeof(buf),
						 dm_get_name_mangling_mode());

	if (type == DM_DEVICE_LIST &&
	    ((names = ((struct dm_names *) ((char *)dmi + dmi->data_start)))) &&
	    names->dev) {
		do {
			names = (struct dm_names *)((char *) names + next);
			r = _do_dm_ioctl_unmangle_string(names->name, "name",
							 buf, sizeof(buf),
							 dm_get_name_mangling_mode());
			next = names->next;
		} while (next);
	}

	return r;
}

static int _dm_ioctl_unmangle_uuids(int type, struct dm_ioctl *dmi)
{
	char buf[DM_UUID_LEN];
	char *uuid = dmi->uuid;

	if (uuid)
		return _do_dm_ioctl_unmangle_string(uuid, "UUID", buf, sizeof(buf),
						    dm_get_name_mangling_mode());

	return 1;
}
#endif

static struct dm_ioctl *_do_dm_ioctl(struct dm_task *dmt, unsigned command,
				     unsigned buffer_repeat_count,
				     unsigned retry_repeat_count,
				     int *retryable)
{
	struct dm_ioctl *dmi;
	int ioctl_with_uevent;
	int r;

	dmt->ioctl_errno = 0;

	dmi = _flatten(dmt, buffer_repeat_count);
	if (!dmi) {
		log_error("Couldn't create ioctl argument.");
		return NULL;
	}

	if (dmt->type == DM_DEVICE_TABLE)
		dmi->flags |= DM_STATUS_TABLE_FLAG;

	dmi->flags |= DM_EXISTS_FLAG;	/* FIXME */

	if (dmt->no_open_count)
		dmi->flags |= DM_SKIP_BDGET_FLAG;

	ioctl_with_uevent = dmt->type == DM_DEVICE_RESUME ||
			    dmt->type == DM_DEVICE_REMOVE ||
			    dmt->type == DM_DEVICE_RENAME;

	if (ioctl_with_uevent && dm_cookie_supported()) {
		/*
		 * Always mark events coming from libdevmapper as
		 * "primary sourced". This is needed to distinguish
		 * any spurious events so we can act appropriately.
		 * This needs to be applied even when udev_sync is
		 * not used because udev flags could be used alone.
		 */
		dmi->event_nr |= DM_UDEV_PRIMARY_SOURCE_FLAG <<
				 DM_UDEV_FLAGS_SHIFT;

		/*
		 * Prevent udev vs. libdevmapper race when processing nodes
		 * and symlinks. This can happen when the udev rules are
		 * installed and udev synchronisation code is enabled in
		 * libdevmapper but the software using libdevmapper does not
		 * make use of it (by not calling dm_task_set_cookie before).
		 * We need to instruct the udev rules not to be applied at
		 * all in this situation so we can gracefully fallback to
		 * libdevmapper's node and symlink creation code.
		 */
		if (!dmt->cookie_set && dm_udev_get_sync_support()) {
			log_debug_activation("Cookie value is not set while trying to call %s "
					     "ioctl. Please, consider using libdevmapper's udev "
					     "synchronisation interface or disable it explicitly "
					     "by calling dm_udev_set_sync_support(0).",
					     dmt->type == DM_DEVICE_RESUME ? "DM_DEVICE_RESUME" :
					     dmt->type == DM_DEVICE_REMOVE ? "DM_DEVICE_REMOVE" :
									     "DM_DEVICE_RENAME");
			log_debug_activation("Switching off device-mapper and all subsystem related "
					     "udev rules. Falling back to libdevmapper node creation.");
			/*
			 * Disable general dm and subsystem rules but keep
			 * dm disk rules if not flagged out explicitly before.
			 * We need /dev/disk content for the software that expects it.
			*/
			dmi->event_nr |= (DM_UDEV_DISABLE_DM_RULES_FLAG |
					  DM_UDEV_DISABLE_SUBSYSTEM_RULES_FLAG) <<
					 DM_UDEV_FLAGS_SHIFT;
		}
	}

	log_debug_activation("dm %s %s%s %s%s%s %s%.0d%s%.0d%s"
			     "%s[ %s%s%s%s%s%s%s%s%s] %.0" PRIu64 " %s [%u] (*%u)",
			     _cmd_data_v4[dmt->type].name,
			     dmt->new_uuid ? "UUID " : "",
			     dmi->name, dmi->uuid, dmt->newname ? " " : "",
			     dmt->newname ? dmt->newname : "",
			     dmt->major > 0 ? "(" : "",
			     dmt->major > 0 ? dmt->major : 0,
			     dmt->major > 0 ? ":" : "",
			     dmt->minor > 0 ? dmt->minor : 0,
			     dmt->major > 0 && dmt->minor == 0 ? "0" : "",
			     dmt->major > 0 ? ") " : "",
			     dmt->no_open_count ? "noopencount " : "opencount ",
			     dmt->no_flush ? "noflush " : "flush ",
			     dmt->read_only ? "readonly " : "",
			     dmt->skip_lockfs ? "skiplockfs " : "",
			     dmt->retry_remove ? "retryremove " : "",
			     dmt->deferred_remove ? "deferredremove " : "",
			     dmt->secure_data ? "securedata " : "",
			     dmt->query_inactive_table ? "inactive " : "",
			     dmt->enable_checks ? "enablechecks " : "",
			     dmt->sector, _sanitise_message(dmt->message),
			     dmi->data_size, retry_repeat_count);
#ifdef DM_IOCTLS
	r = ioctl(_control_fd, command, dmi);

	if (dmt->record_timestamp)
		if (!dm_timestamp_get(_dm_ioctl_timestamp))
			stack;

	if (r < 0 && dmt->expected_errno != errno) {
		dmt->ioctl_errno = errno;
		if (dmt->ioctl_errno == ENXIO && ((dmt->type == DM_DEVICE_INFO) ||
						  (dmt->type == DM_DEVICE_MKNODES) ||
						  (dmt->type == DM_DEVICE_STATUS)))
			dmi->flags &= ~DM_EXISTS_FLAG;	/* FIXME */
		else {
			if (_log_suppress || dmt->ioctl_errno == EINTR)
				log_verbose("device-mapper: %s ioctl on %s%s%s%.0d%s%.0d%s%s "
					    "failed: %s",
				    	    _cmd_data_v4[dmt->type].name,
					    dmi->name, dmi->uuid, 
					    dmt->major > 0 ? "(" : "",
					    dmt->major > 0 ? dmt->major : 0,
					    dmt->major > 0 ? ":" : "",
					    dmt->minor > 0 ? dmt->minor : 0,
					    dmt->major > 0 && dmt->minor == 0 ? "0" : "",
					    dmt->major > 0 ? ")" : "",
					    strerror(dmt->ioctl_errno));
			else
				log_error("device-mapper: %s ioctl on %s%s%s%.0d%s%.0d%s%s "
					  "failed: %s",
					  _cmd_data_v4[dmt->type].name,
					  dmi->name, dmi->uuid, 
					  dmt->major > 0 ? "(" : "",
					  dmt->major > 0 ? dmt->major : 0,
					  dmt->major > 0 ? ":" : "",
					  dmt->minor > 0 ? dmt->minor : 0,
					  dmt->major > 0 && dmt->minor == 0 ? "0" : "",
					  dmt->major > 0 ? ")" : "",
					  strerror(dmt->ioctl_errno));

			/*
			 * It's sometimes worth retrying after EBUSY in case
			 * it's a transient failure caused by an asynchronous
			 * process quickly scanning the device.
			 */
			*retryable = dmt->ioctl_errno == EBUSY;

			goto error;
		}
	}

	if (ioctl_with_uevent && dm_udev_get_sync_support() &&
	    !_check_uevent_generated(dmi)) {
		log_debug_activation("Uevent not generated! Calling udev_complete "
				     "internally to avoid process lock-up.");
		_udev_complete(dmt);
	}

	if (!_dm_ioctl_unmangle_names(dmt->type, dmi))
		goto error;

	if (dmt->type != DM_DEVICE_REMOVE &&
	    !_dm_ioctl_unmangle_uuids(dmt->type, dmi))
		goto error;

#else /* Userspace alternative for testing */
	goto error;
#endif
	return dmi;

error:
	_dm_zfree_dmi(dmi);
	return NULL;
}

void dm_task_update_nodes(void)
{
	update_devs();
}

#define DM_IOCTL_RETRIES 25
#define DM_RETRY_USLEEP_DELAY 200000

int dm_task_get_errno(struct dm_task *dmt)
{
	return dmt->ioctl_errno;
}

int dm_task_run(struct dm_task *dmt)
{
	struct dm_ioctl *dmi;
	unsigned command;
	int check_udev;
	int rely_on_udev;
	int suspended_counter;
	unsigned ioctl_retry = 1;
	int retryable = 0;
	const char *dev_name = DEV_NAME(dmt);
	const char *dev_uuid = DEV_UUID(dmt);

	if ((unsigned) dmt->type >= DM_ARRAY_SIZE(_cmd_data_v4)) {
		log_error(INTERNAL_ERROR "unknown device-mapper task %d",
			  dmt->type);
		return 0;
	}

	command = _cmd_data_v4[dmt->type].cmd;

	/* Old-style creation had a table supplied */
	if (dmt->type == DM_DEVICE_CREATE && dmt->head)
		return _create_and_load_v4(dmt);

	if (dmt->type == DM_DEVICE_MKNODES && !dev_name &&
	    !dev_uuid && dmt->major <= 0)
		return _mknodes_v4(dmt);

	if ((dmt->type == DM_DEVICE_RELOAD) && dmt->suppress_identical_reload)
		return _reload_with_suppression_v4(dmt);

	if ((dmt->type == DM_DEVICE_SUSPEND) && dmt->enable_checks)
		return _suspend_with_validation_v4(dmt);

	if (!_open_control()) {
		_udev_complete(dmt);
		return_0;
	}

	if ((suspended_counter = dm_get_suspended_counter()) &&
	    dmt->type == DM_DEVICE_RELOAD)
		log_error(INTERNAL_ERROR "Performing unsafe table load while %d device(s) "
			  "are known to be suspended: "
			  "%s%s%s %s%.0d%s%.0d%s%s",
			  suspended_counter,
			  dev_name ? : "",
			  dev_uuid ? " UUID " : "",
			  dev_uuid ? : "",
			  dmt->major > 0 ? "(" : "",
			  dmt->major > 0 ? dmt->major : 0,
			  dmt->major > 0 ? ":" : "",
			  dmt->minor > 0 ? dmt->minor : 0,
			  dmt->major > 0 && dmt->minor == 0 ? "0" : "",
			  dmt->major > 0 ? ") " : "");

	/* FIXME Detect and warn if cookie set but should not be. */
repeat_ioctl:
	if (!(dmi = _do_dm_ioctl(dmt, command, _ioctl_buffer_double_factor,
				 ioctl_retry, &retryable))) {
		/*
		 * Async udev rules that scan devices commonly cause transient
		 * failures.  Normally you'd expect the user to have made sure
		 * nothing was using the device before issuing REMOVE, so it's
		 * worth retrying in case the failure is indeed transient.
		 */
		if (retryable && dmt->type == DM_DEVICE_REMOVE &&
		    dmt->retry_remove && ++ioctl_retry <= DM_IOCTL_RETRIES) {
			usleep(DM_RETRY_USLEEP_DELAY);
			goto repeat_ioctl;
		}

		_udev_complete(dmt);
		return 0;
	}

	if (dmi->flags & DM_BUFFER_FULL_FLAG) {
		switch (dmt->type) {
		case DM_DEVICE_LIST_VERSIONS:
		case DM_DEVICE_LIST:
		case DM_DEVICE_DEPS:
		case DM_DEVICE_STATUS:
		case DM_DEVICE_TABLE:
		case DM_DEVICE_WAITEVENT:
		case DM_DEVICE_TARGET_MSG:
			_ioctl_buffer_double_factor++;
			_dm_zfree_dmi(dmi);
			goto repeat_ioctl;
		default:
			log_error("WARNING: libdevmapper buffer too small for data");
		}
	}

	/*
	 * Are we expecting a udev operation to occur that we need to check for?
	 */
	check_udev = dmt->cookie_set &&
		     !(dmt->event_nr >> DM_UDEV_FLAGS_SHIFT &
		       DM_UDEV_DISABLE_DM_RULES_FLAG);

	rely_on_udev = dmt->cookie_set ? (dmt->event_nr >> DM_UDEV_FLAGS_SHIFT &
					  DM_UDEV_DISABLE_LIBRARY_FALLBACK) : 0;

	switch (dmt->type) {
	case DM_DEVICE_CREATE:
		if ((dmt->add_node == DM_ADD_NODE_ON_CREATE) &&
		    dev_name && *dev_name && !rely_on_udev)
			add_dev_node(dev_name, MAJOR(dmi->dev),
				     MINOR(dmi->dev), dmt->uid, dmt->gid,
				     dmt->mode, check_udev, rely_on_udev);
		break;
	case DM_DEVICE_REMOVE:
		/* FIXME Kernel needs to fill in dmi->name */
		if (dev_name && !rely_on_udev)
			rm_dev_node(dev_name, check_udev, rely_on_udev);
		break;

	case DM_DEVICE_RENAME:
		/* FIXME Kernel needs to fill in dmi->name */
		if (!dmt->new_uuid && dev_name)
			rename_dev_node(dev_name, dmt->newname,
					check_udev, rely_on_udev);
		break;

	case DM_DEVICE_RESUME:
		if ((dmt->add_node == DM_ADD_NODE_ON_RESUME) &&
		    dev_name && *dev_name)
			add_dev_node(dev_name, MAJOR(dmi->dev),
				     MINOR(dmi->dev), dmt->uid, dmt->gid,
				     dmt->mode, check_udev, rely_on_udev);
		/* FIXME Kernel needs to fill in dmi->name */
		set_dev_node_read_ahead(dev_name,
					MAJOR(dmi->dev), MINOR(dmi->dev),
					dmt->read_ahead, dmt->read_ahead_flags);
		break;
	
	case DM_DEVICE_MKNODES:
		if (dmi->flags & DM_EXISTS_FLAG)
			add_dev_node(dmi->name, MAJOR(dmi->dev),
				     MINOR(dmi->dev), dmt->uid,
				     dmt->gid, dmt->mode, 0, rely_on_udev);
		else if (dev_name)
			rm_dev_node(dev_name, 0, rely_on_udev);
		break;

	case DM_DEVICE_STATUS:
	case DM_DEVICE_TABLE:
	case DM_DEVICE_WAITEVENT:
		if (!_unmarshal_status(dmt, dmi))
			goto bad;
		break;
	}

	/* Was structure reused? */
	_dm_zfree_dmi(dmt->dmi.v4);
	dmt->dmi.v4 = dmi;
	return 1;

      bad:
	_dm_zfree_dmi(dmi);
	return 0;
}

void dm_hold_control_dev(int hold_open)
{
	_hold_control_fd_open = hold_open ? 1 : 0;

	log_debug("Hold of control device is now %sset.",
		  _hold_control_fd_open ? "" : "un");
}

void dm_lib_release(void)
{
	if (!_hold_control_fd_open)
		_close_control_fd();
	dm_timestamp_destroy(_dm_ioctl_timestamp);
	_dm_ioctl_timestamp = NULL;
	update_devs();
}

void dm_pools_check_leaks(void);

void dm_lib_exit(void)
{
	int suspended_counter;
	static unsigned _exited = 0;

	if (_exited++)
		return;

	if ((suspended_counter = dm_get_suspended_counter()))
		log_error("libdevmapper exiting with %d device(s) still suspended.", suspended_counter);

	dm_lib_release();
	selinux_release();
	if (_dm_bitset)
		dm_bitset_destroy(_dm_bitset);
	_dm_bitset = NULL;
	dm_pools_check_leaks();
	dm_dump_memory();
	_version_ok = 1;
	_version_checked = 0;
}

#if defined(__GNUC__)
/*
 * Maintain binary backward compatibility.
 * Version script mechanism works with 'gcc' compatible compilers only.
 */

/*
 * This following code is here to retain ABI compatibility after adding
 * the field deferred_remove to struct dm_info in version 1.02.89.
 *
 * Binaries linked against version 1.02.88 of libdevmapper or earlier
 * will use this function that returns dm_info without the
 * deferred_remove field.
 *
 * Binaries compiled against version 1.02.89 onwards will use
 * the new function dm_task_get_info_with_deferred_remove due to the
 * #define.
 *
 * N.B. Keep this function at the end of the file to make sure that
 * no code in this file accidentally calls it.
 */

int dm_task_get_info_base(struct dm_task *dmt, struct dm_info *info);
DM_EXPORT_SYMBOL_BASE(dm_task_get_info);
int dm_task_get_info_base(struct dm_task *dmt, struct dm_info *info)
{
	struct dm_info new_info;

	if (!dm_task_get_info(dmt, &new_info))
		return 0;

	memcpy(info, &new_info, offsetof(struct dm_info, deferred_remove));

	return 1;
}

int dm_task_get_info_with_deferred_remove(struct dm_task *dmt, struct dm_info *info);
int dm_task_get_info_with_deferred_remove(struct dm_task *dmt, struct dm_info *info)
{
	struct dm_info new_info;

	if (!dm_task_get_info(dmt, &new_info))
		return 0;

	memcpy(info, &new_info, offsetof(struct dm_info, internal_suspend));

	return 1;
}
#endif
