}
static char *get_params(const char *device, uint64_t skip, uint64_t offset,
- const char *cipher, size_t key_size, const char *key)
+ const char *cipher, struct volume_key *vk)
{
char *params;
char *hexkey;
- hexkey = crypt_safe_alloc(key_size * 2 + 1);
+ hexkey = crypt_safe_alloc(vk->keylength * 2 + 1);
if (!hexkey)
return NULL;
- hex_key(hexkey, key_size, key);
+ hex_key(hexkey, vk->keylength, vk->key);
params = crypt_safe_alloc(strlen(hexkey) + strlen(cipher) + strlen(device) + 64);
if (!params)
uint16_t udev_flags = 0;
params = get_params(dmd->device, dmd->iv_offset, dmd->offset,
- dmd->cipher, dmd->key_size, dmd->key);
+ dmd->cipher, dmd->vk);
if (!params)
goto out_no_removal;
goto out;
dmd->offset = val64;
- /* key_size */
- dmd->key_size = strlen(key_) / 2;
-
- /* key */
- if (dmd->key_size && (get_flags & DM_ACTIVE_KEY)) {
- dmd->key = crypt_safe_alloc(dmd->key_size);
- if (!dmd->key) {
+ if (get_flags & DM_ACTIVE_KEY) {
+ dmd->vk = crypt_alloc_volume_key(strlen(key_) / 2, NULL);
+ if (!dmd->vk) {
r = -ENOMEM;
goto out;
}
buffer[2] = '\0';
- for(i = 0; i < dmd->key_size; i++) {
+ for(i = 0; i < dmd->vk->keylength; i++) {
memcpy(buffer, &key_[i * 2], 2);
- dmd->key[i] = strtoul(buffer, &endp, 16);
+ dmd->vk->key[i] = strtoul(buffer, &endp, 16);
if (endp != &buffer[2]) {
- crypt_safe_free(dmd->key);
- dmd->key = NULL;
+ crypt_free_volume_key(dmd->vk);
+ dmd->vk = NULL;
+ r = -EINVAL;
goto out;
}
}
.device = crypt_get_device_name(cd),
.cipher = NULL,
.uuid = crypt_get_uuid(cd),
- .key = vk->key,
- .key_size = vk->keylength,
+ .vk = vk,
.offset = crypt_get_data_offset(cd),
.iv_offset = skip,
.size = 0,
#include <unistd.h>
#include "config.h"
+struct crypt_device;
+struct volume_key;
+
#define LOOPAES_KEYS_MAX 65
int LOOPAES_parse_keyfile(struct crypt_device *cd,
static int setup_mapping(const char *cipher, const char *name,
const char *device,
- const char *key, size_t keyLength,
+ struct volume_key *vk,
unsigned int sector, size_t srcLength,
int mode, struct crypt_device *ctx)
{
.device = device,
.cipher = cipher,
.uuid = NULL,
- .key = (char*)key,
- .key_size = keyLength,
+ .vk = vk,
.offset = sector,
.iv_offset = 0,
.size = 0,
handler and global vars for cleaning */
static int LUKS_endec_template(char *src, size_t srcLength,
struct luks_phdr *hdr,
- char *key, size_t keyLength,
+ struct volume_key *vk,
const char *device,
unsigned int sector,
ssize_t (*func)(int, void *, size_t),
cleaner_name = name;
r = setup_mapping(dmCipherSpec, name, device,
- key, keyLength, sector, srcLength, mode, ctx);
+ vk, sector, srcLength, mode, ctx);
if(r < 0) {
log_err(ctx, _("Failed to setup dm-crypt key mapping for device %s.\n"
"Check that kernel supports %s cipher (check syslog for more info).\n%s"),
device, dmCipherSpec,
- _error_hint(hdr->cipherMode, keyLength * 8));
+ _error_hint(hdr->cipherMode, vk->keylength * 8));
r = -EIO;
goto out1;
}
int LUKS_encrypt_to_storage(char *src, size_t srcLength,
struct luks_phdr *hdr,
- char *key, size_t keyLength,
+ struct volume_key *vk,
const char *device,
unsigned int sector,
struct crypt_device *ctx)
{
- return LUKS_endec_template(src,srcLength,hdr,key,keyLength, device,
+ return LUKS_endec_template(src,srcLength,hdr,vk, device,
sector, write_blockwise, O_RDWR, ctx);
}
int LUKS_decrypt_from_storage(char *dst, size_t dstLength,
struct luks_phdr *hdr,
- char *key, size_t keyLength,
+ struct volume_key *vk,
const char *device,
unsigned int sector,
struct crypt_device *ctx)
{
- return LUKS_endec_template(dst,dstLength,hdr,key,keyLength, device,
+ return LUKS_endec_template(dst,dstLength,hdr,vk, device,
sector, read_blockwise, O_RDONLY, ctx);
}
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
+#include <assert.h>
#include <uuid/uuid.h>
#include "luks.h"
uint64_t *PBKDF2_per_sec,
struct crypt_device *ctx)
{
- char derivedKey[hdr->keyBytes];
+ struct volume_key *derived_key;
char *AfKey = NULL;
unsigned int AFEKSize;
uint64_t PBKDF2_temp;
log_dbg("Key slot %d use %d password iterations.", keyIndex, hdr->keyblock[keyIndex].passwordIterations);
+ derived_key = crypt_alloc_volume_key(hdr->keyBytes, NULL);
+ if (!derived_key)
+ return -ENOMEM;
+
r = crypt_random_get(ctx, hdr->keyblock[keyIndex].passwordSalt,
LUKS_SALTSIZE, CRYPT_RND_NORMAL);
if (r < 0)
return r;
-// assert((vk->keylength % TWOFISH_BLOCKSIZE) == 0); FIXME
-
r = PBKDF2_HMAC(hdr->hashSpec, password,passwordLen,
hdr->keyblock[keyIndex].passwordSalt,LUKS_SALTSIZE,
hdr->keyblock[keyIndex].passwordIterations,
- derivedKey, hdr->keyBytes);
+ derived_key->key, hdr->keyBytes);
if (r < 0)
goto out;
/*
* AF splitting, the masterkey stored in vk->key is split to AfKey
*/
+ assert(vk->keylength == hdr->keyBytes);
AFEKSize = hdr->keyblock[keyIndex].stripes*vk->keylength;
AfKey = crypt_safe_alloc(AFEKSize);
if (!AfKey) {
r = LUKS_encrypt_to_storage(AfKey,
AFEKSize,
hdr,
- derivedKey,
- hdr->keyBytes,
+ derived_key,
device,
hdr->keyblock[keyIndex].keyMaterialOffset,
ctx);
r = 0;
out:
crypt_safe_free(AfKey);
- memset(derivedKey, 0, sizeof(derivedKey));
+ crypt_free_volume_key(derived_key);
return r;
}
struct crypt_device *ctx)
{
crypt_keyslot_info ki = LUKS_keyslot_info(hdr, keyIndex);
- char derivedKey[hdr->keyBytes];
+ struct volume_key *derived_key;
char *AfKey;
size_t AFEKSize;
int r;
if (ki < CRYPT_SLOT_ACTIVE)
return -ENOENT;
- // assert((vk->keylength % TWOFISH_BLOCKSIZE) == 0); FIXME
+ derived_key = crypt_alloc_volume_key(hdr->keyBytes, NULL);
+ if (!derived_key)
+ return -ENOMEM;
+ assert(vk->keylength == hdr->keyBytes);
AFEKSize = hdr->keyblock[keyIndex].stripes*vk->keylength;
AfKey = crypt_safe_alloc(AFEKSize);
if (!AfKey)
r = PBKDF2_HMAC(hdr->hashSpec, password,passwordLen,
hdr->keyblock[keyIndex].passwordSalt,LUKS_SALTSIZE,
hdr->keyblock[keyIndex].passwordIterations,
- derivedKey, hdr->keyBytes);
+ derived_key->key, hdr->keyBytes);
if (r < 0)
goto out;
r = LUKS_decrypt_from_storage(AfKey,
AFEKSize,
hdr,
- derivedKey,
- hdr->keyBytes,
+ derived_key,
device,
hdr->keyblock[keyIndex].keyMaterialOffset,
ctx);
log_verbose(ctx, _("Key slot %d unlocked.\n"), keyIndex);
out:
crypt_safe_free(AfKey);
- memset(derivedKey, 0, sizeof(derivedKey));
+ crypt_free_volume_key(derived_key);
return r;
}
.device = crypt_get_device_name(cd),
.cipher = NULL,
.uuid = crypt_get_uuid(cd),
- .key = vk->key,
- .key_size = vk->keylength,
+ .vk = vk,
.offset = crypt_get_data_offset(cd),
.iv_offset = 0,
.size = 0,
int LUKS_encrypt_to_storage(
char *src, size_t srcLength,
struct luks_phdr *hdr,
- char *key, size_t keyLength,
+ struct volume_key *vk,
const char *device,
unsigned int sector,
struct crypt_device *ctx);
int LUKS_decrypt_from_storage(
char *dst, size_t dstLength,
struct luks_phdr *hdr,
- char *key, size_t keyLength,
+ struct volume_key *vk,
const char *device,
unsigned int sector,
struct crypt_device *ctx);
.device = crypt_get_device_name(cd),
.cipher = NULL,
.uuid = crypt_get_uuid(cd),
- .key = vk->key,
- .key_size = vk->keylength,
+ .vk = vk,
.offset = crypt_get_data_offset(cd),
.iv_offset = iv_offset,
.size = size,
(*cd)->plain_hdr.hash = NULL; /* no way to get this */
(*cd)->plain_hdr.offset = dmd.offset;
(*cd)->plain_hdr.skip = dmd.iv_offset;
- (*cd)->volume_key = crypt_alloc_volume_key(dmd.key_size, dmd.key);
- if (!(*cd)->volume_key) {
- r = -ENOMEM;
- goto out;
- }
+ (*cd)->volume_key = dmd.vk;
+ dmd.vk = NULL;
r = crypt_parse_name_and_mode(dmd.cipher, cipher, NULL, cipher_mode);
if (!r) {
(*cd)->loopaes_cipher = strdup(cipher);
(*cd)->loopaes_cipher_mode = strdup(cipher_mode);
/* version 3 uses last key for IV */
- if (dmd.key_size % key_nums)
+ if (dmd.vk->keylength % key_nums)
key_nums++;
- (*cd)->loopaes_key_size = dmd.key_size / key_nums;
+ (*cd)->loopaes_key_size = dmd.vk->keylength / key_nums;
}
} else if (!strncmp(CRYPT_LUKS1, dmd.uuid, sizeof(CRYPT_LUKS1)-1)) {
if (dmd.device) {
if (crypt_load(*cd, CRYPT_LUKS1, NULL) < 0 ||
- crypt_volume_key_verify(*cd, dmd.key, dmd.key_size) < 0) {
+ crypt_volume_key_verify(*cd, dmd.vk->key, dmd.vk->keylength) < 0) {
log_dbg("LUKS device header does not match active device.");
goto out;
}
- (*cd)->volume_key = crypt_alloc_volume_key(dmd.key_size, dmd.key);
- if (!(*cd)->volume_key) {
- r = -ENOMEM;
- goto out;
- }
+ (*cd)->volume_key = dmd.vk;
+ dmd.vk = NULL;
}
}
} else
crypt_free(*cd);
*cd = NULL;
}
- crypt_safe_free(dmd.key);
+ crypt_free_volume_key(dmd.vk);
free((char*)dmd.device);
free((char*)dmd.cipher);
free((char*)dmd.uuid);
r = dm_create_device(name, cd->type, &dmd, 1);
}
out:
- crypt_safe_free(dmd.key);
+ crypt_free_volume_key(dmd.vk);
free((char*)dmd.cipher);
free((char*)dmd.device);
free((char*)dmd.uuid);
#include <inttypes.h>
struct crypt_device;
+struct volume_key;
/* Device mapper backend - kernel support flags */
#define DM_KEY_WIPE_SUPPORTED (1 << 0) /* key wipe message */
const char *device;
const char *cipher;
const char *uuid;
- char *key;
- size_t key_size;
+
+ /* Active key for device */
+ struct volume_key *vk;
/* struct crypt_active_device */
uint64_t offset; /* offset in sectors */