From 59fdf2a6bb461a39e6db6b7d515873419f8a8ada Mon Sep 17 00:00:00 2001 From: Milan Broz Date: Thu, 24 Jul 2014 22:11:58 +0200 Subject: [PATCH 3/3] Properly allow activation of discard even if dm_crypt module is not yet loaded. Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The dm_flags() call cannot be used if dmcrypt module is not present. Better try to activate volume with dicard flags and if it is not possible, try to activate device without the discard flag. --- lib/libdevmapper.c | 37 ++++++++++++++++++++++++------------- 1 file changed, 24 insertions(+), 13 deletions(-) diff --git a/lib/libdevmapper.c b/lib/libdevmapper.c index 6138a6b..dcc54fd 100644 --- a/lib/libdevmapper.c +++ b/lib/libdevmapper.c @@ -306,22 +306,19 @@ static void hex_key(char *hexkey, size_t key_size, const char *key) } /* http://code.google.com/p/cryptsetup/wiki/DMCrypt */ -static char *get_dm_crypt_params(struct crypt_dm_active_device *dmd) +static char *get_dm_crypt_params(struct crypt_dm_active_device *dmd, uint32_t flags) { int r, max_size, null_cipher = 0; char *params, *hexkey; - const char *features = ""; + const char *features; if (!dmd) return NULL; - if (dmd->flags & CRYPT_ACTIVATE_ALLOW_DISCARDS) { - if (dm_flags() & DM_DISCARDS_SUPPORTED) { - features = " 1 allow_discards"; - log_dbg("Discard/TRIM is allowed."); - } else - log_dbg("Discard/TRIM is not supported by the kernel."); - } + if (flags & CRYPT_ACTIVATE_ALLOW_DISCARDS) + features = " 1 allow_discards"; + else + features = ""; if (!strncmp(dmd->u.crypt.cipher, "cipher_null-", 12)) null_cipher = 1; @@ -662,6 +659,7 @@ int dm_create_device(struct crypt_device *cd, const char *name, int reload) { char *table_params = NULL; + uint32_t dmd_flags; int r; if (!type) @@ -670,14 +668,27 @@ int dm_create_device(struct crypt_device *cd, const char *name, if (dm_init_context(cd)) return -ENOTSUP; + dmd_flags = dmd->flags; + if (dmd->target == DM_CRYPT) - table_params = get_dm_crypt_params(dmd); + 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); - r = _dm_create_device(name, type, dmd->data_device, - dmd->flags, dmd->uuid, dmd->size, - table_params, reload); + 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); + } crypt_safe_free(table_params); dm_exit_context(); -- 2.0.1