cryptsetup: split up attach_luks_or_plain_or_bitlk() into smaller functions
Just some refactoring.
This commit is contained in:
parent
b997d1115b
commit
b8c80b56d1
|
@ -595,84 +595,29 @@ static int make_security_device_monitor(sd_event *event, sd_device_monitor **ret
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int attach_luks_or_plain_or_bitlk(
|
||||
static int attach_luks_or_plain_or_bitlk_by_pkcs11(
|
||||
struct crypt_device *cd,
|
||||
const char *name,
|
||||
const char *key_file,
|
||||
const void *key_data,
|
||||
size_t key_data_size,
|
||||
char **passwords,
|
||||
usec_t until,
|
||||
uint32_t flags,
|
||||
usec_t until) {
|
||||
bool pass_volume_key) {
|
||||
|
||||
int r = 0;
|
||||
bool pass_volume_key = false;
|
||||
|
||||
assert(cd);
|
||||
assert(name);
|
||||
|
||||
if ((!arg_type && !crypt_get_type(cd)) || streq_ptr(arg_type, CRYPT_PLAIN)) {
|
||||
struct crypt_params_plain params = {
|
||||
.offset = arg_offset,
|
||||
.skip = arg_skip,
|
||||
.sector_size = arg_sector_size,
|
||||
};
|
||||
const char *cipher, *cipher_mode;
|
||||
_cleanup_free_ char *truncated_cipher = NULL;
|
||||
|
||||
if (arg_hash) {
|
||||
/* plain isn't a real hash type. it just means "use no hash" */
|
||||
if (!streq(arg_hash, "plain"))
|
||||
params.hash = arg_hash;
|
||||
} else if (!key_file)
|
||||
/* for CRYPT_PLAIN, the behaviour of cryptsetup
|
||||
* package is to not hash when a key file is provided */
|
||||
params.hash = "ripemd160";
|
||||
|
||||
if (arg_cipher) {
|
||||
size_t l;
|
||||
|
||||
l = strcspn(arg_cipher, "-");
|
||||
truncated_cipher = strndup(arg_cipher, l);
|
||||
if (!truncated_cipher)
|
||||
return log_oom();
|
||||
|
||||
cipher = truncated_cipher;
|
||||
cipher_mode = arg_cipher[l] ? arg_cipher+l+1 : "plain";
|
||||
} else {
|
||||
cipher = "aes";
|
||||
cipher_mode = "cbc-essiv:sha256";
|
||||
}
|
||||
|
||||
/* for CRYPT_PLAIN limit reads from keyfile to key length, and ignore keyfile-size */
|
||||
arg_keyfile_size = arg_key_size;
|
||||
|
||||
/* In contrast to what the name crypt_format() might suggest this doesn't actually format
|
||||
* anything, it just configures encryption parameters when used for plain mode. */
|
||||
r = crypt_format(cd, CRYPT_PLAIN, cipher, cipher_mode, NULL, NULL, arg_keyfile_size, ¶ms);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Loading of cryptographic parameters failed: %m");
|
||||
|
||||
/* hash == NULL implies the user passed "plain" */
|
||||
pass_volume_key = (params.hash == NULL);
|
||||
}
|
||||
|
||||
log_info("Set cipher %s, mode %s, key size %i bits for device %s.",
|
||||
crypt_get_cipher(cd),
|
||||
crypt_get_cipher_mode(cd),
|
||||
crypt_get_volume_key_size(cd)*8,
|
||||
crypt_get_device_name(cd));
|
||||
|
||||
if (arg_pkcs11_uri || arg_pkcs11_uri_auto) {
|
||||
_cleanup_(sd_device_monitor_unrefp) sd_device_monitor *monitor = NULL;
|
||||
_cleanup_free_ char *friendly = NULL, *discovered_uri = NULL;
|
||||
size_t decrypted_key_size = 0, discovered_key_size = 0;
|
||||
_cleanup_(erase_and_freep) void *decrypted_key = NULL;
|
||||
_cleanup_(sd_event_unrefp) sd_event *event = NULL;
|
||||
_cleanup_free_ void *discovered_key = NULL;
|
||||
int keyslot = arg_key_slot;
|
||||
int keyslot = arg_key_slot, r;
|
||||
const char *uri;
|
||||
|
||||
assert(cd);
|
||||
assert(name);
|
||||
assert(arg_pkcs11_uri || arg_pkcs11_uri_auto);
|
||||
|
||||
if (arg_pkcs11_uri_auto) {
|
||||
r = find_pkcs11_auto_data(cd, &discovered_uri, &discovered_key, &discovered_key_size, &keyslot);
|
||||
if (IN_SET(r, -ENOTUNIQ, -ENXIO))
|
||||
|
@ -681,14 +626,15 @@ static int attach_luks_or_plain_or_bitlk(
|
|||
if (r < 0)
|
||||
return r;
|
||||
|
||||
uri = discovered_uri;
|
||||
key_data = discovered_key;
|
||||
key_data_size = discovered_key_size;
|
||||
uri = discovered_uri;
|
||||
} else
|
||||
} else {
|
||||
uri = arg_pkcs11_uri;
|
||||
|
||||
if (!key_file && !key_data)
|
||||
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "PKCS#11 mode selected but no key file specified, refusing.");
|
||||
}
|
||||
|
||||
friendly = friendly_disk_name(crypt_get_device_name(cd), name);
|
||||
if (!friendly)
|
||||
|
@ -773,7 +719,23 @@ static int attach_luks_or_plain_or_bitlk(
|
|||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to activate with PKCS#11 acquired key: %m");
|
||||
|
||||
} else if (key_data) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int attach_luks_or_plain_or_bitlk_by_key_data(
|
||||
struct crypt_device *cd,
|
||||
const char *name,
|
||||
const void *key_data,
|
||||
size_t key_data_size,
|
||||
uint32_t flags,
|
||||
bool pass_volume_key) {
|
||||
|
||||
int r;
|
||||
|
||||
assert(cd);
|
||||
assert(name);
|
||||
assert(key_data);
|
||||
|
||||
if (pass_volume_key)
|
||||
r = crypt_activate_by_volume_key(cd, name, key_data, key_data_size, flags);
|
||||
else
|
||||
|
@ -785,10 +747,24 @@ static int attach_luks_or_plain_or_bitlk(
|
|||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to activate: %m");
|
||||
|
||||
} else if (key_file) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int attach_luks_or_plain_or_bitlk_by_key_file(
|
||||
struct crypt_device *cd,
|
||||
const char *name,
|
||||
const char *key_file,
|
||||
uint32_t flags,
|
||||
bool pass_volume_key) {
|
||||
|
||||
_cleanup_(erase_and_freep) char *kfdata = NULL;
|
||||
_cleanup_free_ char *bindname = NULL;
|
||||
size_t kfsize;
|
||||
int r;
|
||||
|
||||
assert(cd);
|
||||
assert(name);
|
||||
assert(key_file);
|
||||
|
||||
/* If we read the key via AF_UNIX, make this client recognizable */
|
||||
bindname = make_bindname(name);
|
||||
|
@ -807,6 +783,9 @@ static int attach_luks_or_plain_or_bitlk(
|
|||
return -EAGAIN; /* Log actual error, but return EAGAIN */
|
||||
}
|
||||
|
||||
if (pass_volume_key)
|
||||
r = crypt_activate_by_volume_key(cd, name, kfdata, kfsize, flags);
|
||||
else
|
||||
r = crypt_activate_by_passphrase(cd, name, arg_key_slot, kfdata, kfsize, flags);
|
||||
if (r == -EPERM) {
|
||||
log_error_errno(r, "Failed to activate with key file '%s'. (Key data incorrect?)", key_file);
|
||||
|
@ -815,8 +794,21 @@ static int attach_luks_or_plain_or_bitlk(
|
|||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to activate with key file '%s': %m", key_file);
|
||||
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int attach_luks_or_plain_or_bitlk_by_passphrase(
|
||||
struct crypt_device *cd,
|
||||
const char *name,
|
||||
char **passwords,
|
||||
uint32_t flags,
|
||||
bool pass_volume_key) {
|
||||
|
||||
char **p;
|
||||
int r;
|
||||
|
||||
assert(cd);
|
||||
assert(name);
|
||||
|
||||
r = -EINVAL;
|
||||
STRV_FOREACH(p, passwords) {
|
||||
|
@ -833,9 +825,87 @@ static int attach_luks_or_plain_or_bitlk(
|
|||
}
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Failed to activate with specified passphrase: %m");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
return r;
|
||||
static int attach_luks_or_plain_or_bitlk(
|
||||
struct crypt_device *cd,
|
||||
const char *name,
|
||||
const char *key_file,
|
||||
const void *key_data,
|
||||
size_t key_data_size,
|
||||
char **passwords,
|
||||
uint32_t flags,
|
||||
usec_t until) {
|
||||
|
||||
bool pass_volume_key = false;
|
||||
int r;
|
||||
|
||||
assert(cd);
|
||||
assert(name);
|
||||
|
||||
if ((!arg_type && !crypt_get_type(cd)) || streq_ptr(arg_type, CRYPT_PLAIN)) {
|
||||
struct crypt_params_plain params = {
|
||||
.offset = arg_offset,
|
||||
.skip = arg_skip,
|
||||
.sector_size = arg_sector_size,
|
||||
};
|
||||
const char *cipher, *cipher_mode;
|
||||
_cleanup_free_ char *truncated_cipher = NULL;
|
||||
|
||||
if (streq_ptr(arg_hash, "plain"))
|
||||
/* plain isn't a real hash type. it just means "use no hash" */
|
||||
params.hash = NULL;
|
||||
else if (arg_hash)
|
||||
params.hash = arg_hash;
|
||||
else if (!key_file)
|
||||
/* for CRYPT_PLAIN, the behaviour of cryptsetup package is to not hash when a key
|
||||
* file is provided */
|
||||
params.hash = "ripemd160";
|
||||
|
||||
if (arg_cipher) {
|
||||
size_t l;
|
||||
|
||||
l = strcspn(arg_cipher, "-");
|
||||
truncated_cipher = strndup(arg_cipher, l);
|
||||
if (!truncated_cipher)
|
||||
return log_oom();
|
||||
|
||||
cipher = truncated_cipher;
|
||||
cipher_mode = arg_cipher[l] ? arg_cipher+l+1 : "plain";
|
||||
} else {
|
||||
cipher = "aes";
|
||||
cipher_mode = "cbc-essiv:sha256";
|
||||
}
|
||||
|
||||
/* for CRYPT_PLAIN limit reads from keyfile to key length, and ignore keyfile-size */
|
||||
arg_keyfile_size = arg_key_size;
|
||||
|
||||
/* In contrast to what the name crypt_format() might suggest this doesn't actually format
|
||||
* anything, it just configures encryption parameters when used for plain mode. */
|
||||
r = crypt_format(cd, CRYPT_PLAIN, cipher, cipher_mode, NULL, NULL, arg_keyfile_size, ¶ms);
|
||||
if (r < 0)
|
||||
return log_error_errno(r, "Loading of cryptographic parameters failed: %m");
|
||||
|
||||
/* hash == NULL implies the user passed "plain" */
|
||||
pass_volume_key = !params.hash;
|
||||
}
|
||||
|
||||
log_info("Set cipher %s, mode %s, key size %i bits for device %s.",
|
||||
crypt_get_cipher(cd),
|
||||
crypt_get_cipher_mode(cd),
|
||||
crypt_get_volume_key_size(cd)*8,
|
||||
crypt_get_device_name(cd));
|
||||
|
||||
if (arg_pkcs11_uri || arg_pkcs11_uri_auto)
|
||||
return attach_luks_or_plain_or_bitlk_by_pkcs11(cd, name, key_file, key_data, key_data_size, until, flags, pass_volume_key);
|
||||
if (key_data)
|
||||
return attach_luks_or_plain_or_bitlk_by_key_data(cd, name, key_data, key_data_size, flags, pass_volume_key);
|
||||
if (key_file)
|
||||
return attach_luks_or_plain_or_bitlk_by_key_file(cd, name, key_file, flags, pass_volume_key);
|
||||
|
||||
return attach_luks_or_plain_or_bitlk_by_passphrase(cd, name, passwords, flags, pass_volume_key);
|
||||
}
|
||||
|
||||
static int help(void) {
|
||||
|
|
Loading…
Reference in a new issue