block: pass option prefix down to crypto layer

While the crypto layer uses a fixed option name "key-secret",
the upper block layer may have a prefix on the options. e.g.
"encrypt.key-secret", in order to avoid clashes between crypto
option names & other block option names. To ensure the crypto
layer can report accurate error messages, we must tell it what
option name prefix was used.

Reviewed-by: Alberto Garcia <berto@igalia.com>
Reviewed-by: Max Reitz <mreitz@redhat.com>
Signed-off-by: Daniel P. Berrange <berrange@redhat.com>
Message-id: 20170623162419.26068-19-berrange@redhat.com
Signed-off-by: Max Reitz <mreitz@redhat.com>
This commit is contained in:
Daniel P. Berrange 2017-06-23 17:24:17 +01:00 committed by Max Reitz
parent c01c214b69
commit 1cd9a787a2
9 changed files with 37 additions and 20 deletions

View File

@ -296,7 +296,7 @@ static int block_crypto_open_generic(QCryptoBlockFormat format,
if (flags & BDRV_O_NO_IO) { if (flags & BDRV_O_NO_IO) {
cflags |= QCRYPTO_BLOCK_OPEN_NO_IO; cflags |= QCRYPTO_BLOCK_OPEN_NO_IO;
} }
crypto->block = qcrypto_block_open(open_opts, crypto->block = qcrypto_block_open(open_opts, NULL,
block_crypto_read_func, block_crypto_read_func,
bs, bs,
cflags, cflags,
@ -340,7 +340,7 @@ static int block_crypto_create_generic(QCryptoBlockFormat format,
return -1; return -1;
} }
crypto = qcrypto_block_create(create_opts, crypto = qcrypto_block_create(create_opts, NULL,
block_crypto_init_func, block_crypto_init_func,
block_crypto_write_func, block_crypto_write_func,
&data, &data,

View File

@ -208,8 +208,8 @@ static int qcow_open(BlockDriverState *bs, QDict *options, int flags,
if (flags & BDRV_O_NO_IO) { if (flags & BDRV_O_NO_IO) {
cflags |= QCRYPTO_BLOCK_OPEN_NO_IO; cflags |= QCRYPTO_BLOCK_OPEN_NO_IO;
} }
s->crypto = qcrypto_block_open(crypto_opts, NULL, NULL, s->crypto = qcrypto_block_open(crypto_opts, "encrypt.",
cflags, errp); NULL, NULL, cflags, errp);
if (!s->crypto) { if (!s->crypto) {
ret = -EINVAL; ret = -EINVAL;
goto fail; goto fail;
@ -866,7 +866,8 @@ static int qcow_create(const char *filename, QemuOpts *opts, Error **errp)
goto exit; goto exit;
} }
crypto = qcrypto_block_create(crypto_opts, NULL, NULL, NULL, errp); crypto = qcrypto_block_create(crypto_opts, "encrypt.",
NULL, NULL, NULL, errp);
if (!crypto) { if (!crypto) {
ret = -EINVAL; ret = -EINVAL;
goto exit; goto exit;

View File

@ -279,7 +279,7 @@ static int qcow2_read_extensions(BlockDriverState *bs, uint64_t start_offset,
if (flags & BDRV_O_NO_IO) { if (flags & BDRV_O_NO_IO) {
cflags |= QCRYPTO_BLOCK_OPEN_NO_IO; cflags |= QCRYPTO_BLOCK_OPEN_NO_IO;
} }
s->crypto = qcrypto_block_open(s->crypto_opts, s->crypto = qcrypto_block_open(s->crypto_opts, "encrypt.",
qcow2_crypto_hdr_read_func, qcow2_crypto_hdr_read_func,
bs, cflags, errp); bs, cflags, errp);
if (!s->crypto) { if (!s->crypto) {
@ -1313,8 +1313,8 @@ static int qcow2_do_open(BlockDriverState *bs, QDict *options, int flags,
if (flags & BDRV_O_NO_IO) { if (flags & BDRV_O_NO_IO) {
cflags |= QCRYPTO_BLOCK_OPEN_NO_IO; cflags |= QCRYPTO_BLOCK_OPEN_NO_IO;
} }
s->crypto = qcrypto_block_open(s->crypto_opts, NULL, NULL, s->crypto = qcrypto_block_open(s->crypto_opts, "encrypt.",
cflags, errp); NULL, NULL, cflags, errp);
if (!s->crypto) { if (!s->crypto) {
ret = -EINVAL; ret = -EINVAL;
goto fail; goto fail;
@ -2318,7 +2318,7 @@ static int qcow2_set_up_encryption(BlockDriverState *bs, const char *encryptfmt,
} }
s->crypt_method_header = fmt; s->crypt_method_header = fmt;
crypto = qcrypto_block_create(cryptoopts, crypto = qcrypto_block_create(cryptoopts, "encrypt.",
qcow2_crypto_hdr_init_func, qcow2_crypto_hdr_init_func,
qcow2_crypto_hdr_write_func, qcow2_crypto_hdr_write_func,
bs, errp); bs, errp);

View File

@ -638,6 +638,7 @@ qcrypto_block_luks_find_key(QCryptoBlock *block,
static int static int
qcrypto_block_luks_open(QCryptoBlock *block, qcrypto_block_luks_open(QCryptoBlock *block,
QCryptoBlockOpenOptions *options, QCryptoBlockOpenOptions *options,
const char *optprefix,
QCryptoBlockReadFunc readfunc, QCryptoBlockReadFunc readfunc,
void *opaque, void *opaque,
unsigned int flags, unsigned int flags,
@ -661,7 +662,8 @@ qcrypto_block_luks_open(QCryptoBlock *block,
if (!(flags & QCRYPTO_BLOCK_OPEN_NO_IO)) { if (!(flags & QCRYPTO_BLOCK_OPEN_NO_IO)) {
if (!options->u.luks.key_secret) { if (!options->u.luks.key_secret) {
error_setg(errp, "Parameter 'key-secret' is required for cipher"); error_setg(errp, "Parameter '%skey-secret' is required for cipher",
optprefix ? optprefix : "");
return -1; return -1;
} }
password = qcrypto_secret_lookup_as_utf8( password = qcrypto_secret_lookup_as_utf8(
@ -885,6 +887,7 @@ qcrypto_block_luks_uuid_gen(uint8_t *uuidstr)
static int static int
qcrypto_block_luks_create(QCryptoBlock *block, qcrypto_block_luks_create(QCryptoBlock *block,
QCryptoBlockCreateOptions *options, QCryptoBlockCreateOptions *options,
const char *optprefix,
QCryptoBlockInitFunc initfunc, QCryptoBlockInitFunc initfunc,
QCryptoBlockWriteFunc writefunc, QCryptoBlockWriteFunc writefunc,
void *opaque, void *opaque,
@ -937,7 +940,8 @@ qcrypto_block_luks_create(QCryptoBlock *block,
* be silently ignored, for compatibility with dm-crypt */ * be silently ignored, for compatibility with dm-crypt */
if (!options->u.luks.key_secret) { if (!options->u.luks.key_secret) {
error_setg(errp, "Parameter 'key-secret' is required for cipher"); error_setg(errp, "Parameter '%skey-secret' is required for cipher",
optprefix ? optprefix : "");
return -1; return -1;
} }
password = qcrypto_secret_lookup_as_utf8(luks_opts.key_secret, errp); password = qcrypto_secret_lookup_as_utf8(luks_opts.key_secret, errp);

View File

@ -94,6 +94,7 @@ qcrypto_block_qcow_init(QCryptoBlock *block,
static int static int
qcrypto_block_qcow_open(QCryptoBlock *block, qcrypto_block_qcow_open(QCryptoBlock *block,
QCryptoBlockOpenOptions *options, QCryptoBlockOpenOptions *options,
const char *optprefix,
QCryptoBlockReadFunc readfunc G_GNUC_UNUSED, QCryptoBlockReadFunc readfunc G_GNUC_UNUSED,
void *opaque G_GNUC_UNUSED, void *opaque G_GNUC_UNUSED,
unsigned int flags, unsigned int flags,
@ -104,7 +105,8 @@ qcrypto_block_qcow_open(QCryptoBlock *block,
} else { } else {
if (!options->u.qcow.key_secret) { if (!options->u.qcow.key_secret) {
error_setg(errp, error_setg(errp,
"Parameter 'key-secret' is required for cipher"); "Parameter '%skey-secret' is required for cipher",
optprefix ? optprefix : "");
return -1; return -1;
} }
return qcrypto_block_qcow_init(block, return qcrypto_block_qcow_init(block,
@ -116,13 +118,15 @@ qcrypto_block_qcow_open(QCryptoBlock *block,
static int static int
qcrypto_block_qcow_create(QCryptoBlock *block, qcrypto_block_qcow_create(QCryptoBlock *block,
QCryptoBlockCreateOptions *options, QCryptoBlockCreateOptions *options,
const char *optprefix,
QCryptoBlockInitFunc initfunc G_GNUC_UNUSED, QCryptoBlockInitFunc initfunc G_GNUC_UNUSED,
QCryptoBlockWriteFunc writefunc G_GNUC_UNUSED, QCryptoBlockWriteFunc writefunc G_GNUC_UNUSED,
void *opaque G_GNUC_UNUSED, void *opaque G_GNUC_UNUSED,
Error **errp) Error **errp)
{ {
if (!options->u.qcow.key_secret) { if (!options->u.qcow.key_secret) {
error_setg(errp, "Parameter 'key-secret' is required for cipher"); error_setg(errp, "Parameter '%skey-secret' is required for cipher",
optprefix ? optprefix : "");
return -1; return -1;
} }
/* QCow2 has no special header, since everything is hardwired */ /* QCow2 has no special header, since everything is hardwired */

View File

@ -48,6 +48,7 @@ bool qcrypto_block_has_format(QCryptoBlockFormat format,
QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options, QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options,
const char *optprefix,
QCryptoBlockReadFunc readfunc, QCryptoBlockReadFunc readfunc,
void *opaque, void *opaque,
unsigned int flags, unsigned int flags,
@ -67,7 +68,7 @@ QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options,
block->driver = qcrypto_block_drivers[options->format]; block->driver = qcrypto_block_drivers[options->format];
if (block->driver->open(block, options, if (block->driver->open(block, options, optprefix,
readfunc, opaque, flags, errp) < 0) { readfunc, opaque, flags, errp) < 0) {
g_free(block); g_free(block);
return NULL; return NULL;
@ -78,6 +79,7 @@ QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options,
QCryptoBlock *qcrypto_block_create(QCryptoBlockCreateOptions *options, QCryptoBlock *qcrypto_block_create(QCryptoBlockCreateOptions *options,
const char *optprefix,
QCryptoBlockInitFunc initfunc, QCryptoBlockInitFunc initfunc,
QCryptoBlockWriteFunc writefunc, QCryptoBlockWriteFunc writefunc,
void *opaque, void *opaque,
@ -97,7 +99,7 @@ QCryptoBlock *qcrypto_block_create(QCryptoBlockCreateOptions *options,
block->driver = qcrypto_block_drivers[options->format]; block->driver = qcrypto_block_drivers[options->format];
if (block->driver->create(block, options, initfunc, if (block->driver->create(block, options, optprefix, initfunc,
writefunc, opaque, errp) < 0) { writefunc, opaque, errp) < 0) {
g_free(block); g_free(block);
return NULL; return NULL;

View File

@ -41,6 +41,7 @@ struct QCryptoBlock {
struct QCryptoBlockDriver { struct QCryptoBlockDriver {
int (*open)(QCryptoBlock *block, int (*open)(QCryptoBlock *block,
QCryptoBlockOpenOptions *options, QCryptoBlockOpenOptions *options,
const char *optprefix,
QCryptoBlockReadFunc readfunc, QCryptoBlockReadFunc readfunc,
void *opaque, void *opaque,
unsigned int flags, unsigned int flags,
@ -48,6 +49,7 @@ struct QCryptoBlockDriver {
int (*create)(QCryptoBlock *block, int (*create)(QCryptoBlock *block,
QCryptoBlockCreateOptions *options, QCryptoBlockCreateOptions *options,
const char *optprefix,
QCryptoBlockInitFunc initfunc, QCryptoBlockInitFunc initfunc,
QCryptoBlockWriteFunc writefunc, QCryptoBlockWriteFunc writefunc,
void *opaque, void *opaque,

View File

@ -71,6 +71,7 @@ typedef enum {
/** /**
* qcrypto_block_open: * qcrypto_block_open:
* @options: the encryption options * @options: the encryption options
* @optprefix: name prefix for options
* @readfunc: callback for reading data from the volume * @readfunc: callback for reading data from the volume
* @opaque: data to pass to @readfunc * @opaque: data to pass to @readfunc
* @flags: bitmask of QCryptoBlockOpenFlags values * @flags: bitmask of QCryptoBlockOpenFlags values
@ -102,6 +103,7 @@ typedef enum {
* Returns: a block encryption format, or NULL on error * Returns: a block encryption format, or NULL on error
*/ */
QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options, QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options,
const char *optprefix,
QCryptoBlockReadFunc readfunc, QCryptoBlockReadFunc readfunc,
void *opaque, void *opaque,
unsigned int flags, unsigned int flags,
@ -109,7 +111,8 @@ QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options,
/** /**
* qcrypto_block_create: * qcrypto_block_create:
* @format: the encryption format * @options: the encryption options
* @optprefix: name prefix for options
* @initfunc: callback for initializing volume header * @initfunc: callback for initializing volume header
* @writefunc: callback for writing data to the volume header * @writefunc: callback for writing data to the volume header
* @opaque: data to pass to @initfunc and @writefunc * @opaque: data to pass to @initfunc and @writefunc
@ -133,6 +136,7 @@ QCryptoBlock *qcrypto_block_open(QCryptoBlockOpenOptions *options,
* Returns: a block encryption format, or NULL on error * Returns: a block encryption format, or NULL on error
*/ */
QCryptoBlock *qcrypto_block_create(QCryptoBlockCreateOptions *options, QCryptoBlock *qcrypto_block_create(QCryptoBlockCreateOptions *options,
const char *optprefix,
QCryptoBlockInitFunc initfunc, QCryptoBlockInitFunc initfunc,
QCryptoBlockWriteFunc writefunc, QCryptoBlockWriteFunc writefunc,
void *opaque, void *opaque,

View File

@ -281,7 +281,7 @@ static void test_block(gconstpointer opaque)
memset(&header, 0, sizeof(header)); memset(&header, 0, sizeof(header));
buffer_init(&header, "header"); buffer_init(&header, "header");
blk = qcrypto_block_create(data->create_opts, blk = qcrypto_block_create(data->create_opts, NULL,
test_block_init_func, test_block_init_func,
test_block_write_func, test_block_write_func,
&header, &header,
@ -300,7 +300,7 @@ static void test_block(gconstpointer opaque)
object_unparent(sec); object_unparent(sec);
/* Ensure we can't open without the secret */ /* Ensure we can't open without the secret */
blk = qcrypto_block_open(data->open_opts, blk = qcrypto_block_open(data->open_opts, NULL,
test_block_read_func, test_block_read_func,
&header, &header,
0, 0,
@ -308,7 +308,7 @@ static void test_block(gconstpointer opaque)
g_assert(blk == NULL); g_assert(blk == NULL);
/* Ensure we can't open without the secret, unless NO_IO */ /* Ensure we can't open without the secret, unless NO_IO */
blk = qcrypto_block_open(data->open_opts, blk = qcrypto_block_open(data->open_opts, NULL,
test_block_read_func, test_block_read_func,
&header, &header,
QCRYPTO_BLOCK_OPEN_NO_IO, QCRYPTO_BLOCK_OPEN_NO_IO,
@ -322,7 +322,7 @@ static void test_block(gconstpointer opaque)
/* Now open for real with secret */ /* Now open for real with secret */
sec = test_block_secret(); sec = test_block_secret();
blk = qcrypto_block_open(data->open_opts, blk = qcrypto_block_open(data->open_opts, NULL,
test_block_read_func, test_block_read_func,
&header, &header,
0, 0,