aboutsummaryrefslogtreecommitdiff
path: root/block/nbd.c
diff options
context:
space:
mode:
authorMax Reitz <mreitz@redhat.com>2016-08-15 15:29:24 +0200
committerKevin Wolf <kwolf@redhat.com>2016-08-15 15:52:28 +0200
commit7ccc44fd7d1dfa62c4d6f3a680df809d6e7068ce (patch)
treec9af0072ab148044d6ad6fa4e6ae467a1d85a700 /block/nbd.c
parent8a6a80896d6af03b8ee0c17cdf37219eca2588a7 (diff)
block/nbd: Use QemuOpts for runtime options
Using QemuOpts will prevent qemu from crashing if the input options have not been validated (which is the case when they are specified on the command line or in a json: filename) and some have the wrong type. Signed-off-by: Max Reitz <mreitz@redhat.com> Reviewed-by: Jeff Cody <jcody@redhat.com> Signed-off-by: Kevin Wolf <kwolf@redhat.com>
Diffstat (limited to 'block/nbd.c')
-rw-r--r--block/nbd.c74
1 files changed, 54 insertions, 20 deletions
diff --git a/block/nbd.c b/block/nbd.c
index 8d57220f18..60096daba3 100644
--- a/block/nbd.c
+++ b/block/nbd.c
@@ -188,13 +188,13 @@ out:
g_free(file);
}
-static SocketAddress *nbd_config(BDRVNBDState *s, QDict *options, char **export,
+static SocketAddress *nbd_config(BDRVNBDState *s, QemuOpts *opts, char **export,
Error **errp)
{
SocketAddress *saddr;
- if (qdict_haskey(options, "path") == qdict_haskey(options, "host")) {
- if (qdict_haskey(options, "path")) {
+ if (!qemu_opt_get(opts, "path") == !qemu_opt_get(opts, "host")) {
+ if (qemu_opt_get(opts, "path")) {
error_setg(errp, "path and host may not be used at the same time.");
} else {
error_setg(errp, "one of path and host must be specified.");
@@ -204,32 +204,25 @@ static SocketAddress *nbd_config(BDRVNBDState *s, QDict *options, char **export,
saddr = g_new0(SocketAddress, 1);
- if (qdict_haskey(options, "path")) {
+ if (qemu_opt_get(opts, "path")) {
UnixSocketAddress *q_unix;
saddr->type = SOCKET_ADDRESS_KIND_UNIX;
q_unix = saddr->u.q_unix.data = g_new0(UnixSocketAddress, 1);
- q_unix->path = g_strdup(qdict_get_str(options, "path"));
- qdict_del(options, "path");
+ q_unix->path = g_strdup(qemu_opt_get(opts, "path"));
} else {
InetSocketAddress *inet;
saddr->type = SOCKET_ADDRESS_KIND_INET;
inet = saddr->u.inet.data = g_new0(InetSocketAddress, 1);
- inet->host = g_strdup(qdict_get_str(options, "host"));
- if (!qdict_get_try_str(options, "port")) {
+ inet->host = g_strdup(qemu_opt_get(opts, "host"));
+ inet->port = g_strdup(qemu_opt_get(opts, "port"));
+ if (!inet->port) {
inet->port = g_strdup_printf("%d", NBD_DEFAULT_PORT);
- } else {
- inet->port = g_strdup(qdict_get_str(options, "port"));
}
- qdict_del(options, "host");
- qdict_del(options, "port");
}
s->client.is_unix = saddr->type == SOCKET_ADDRESS_KIND_UNIX;
- *export = g_strdup(qdict_get_try_str(options, "export"));
- if (*export) {
- qdict_del(options, "export");
- }
+ *export = g_strdup(qemu_opt_get(opts, "export"));
return saddr;
}
@@ -292,27 +285,67 @@ static QCryptoTLSCreds *nbd_get_tls_creds(const char *id, Error **errp)
}
+static QemuOptsList nbd_runtime_opts = {
+ .name = "nbd",
+ .head = QTAILQ_HEAD_INITIALIZER(nbd_runtime_opts.head),
+ .desc = {
+ {
+ .name = "host",
+ .type = QEMU_OPT_STRING,
+ .help = "TCP host to connect to",
+ },
+ {
+ .name = "port",
+ .type = QEMU_OPT_STRING,
+ .help = "TCP port to connect to",
+ },
+ {
+ .name = "path",
+ .type = QEMU_OPT_STRING,
+ .help = "Unix socket path to connect to",
+ },
+ {
+ .name = "export",
+ .type = QEMU_OPT_STRING,
+ .help = "Name of the NBD export to open",
+ },
+ {
+ .name = "tls-creds",
+ .type = QEMU_OPT_STRING,
+ .help = "ID of the TLS credentials to use",
+ },
+ },
+};
+
static int nbd_open(BlockDriverState *bs, QDict *options, int flags,
Error **errp)
{
BDRVNBDState *s = bs->opaque;
+ QemuOpts *opts = NULL;
+ Error *local_err = NULL;
char *export = NULL;
QIOChannelSocket *sioc = NULL;
- SocketAddress *saddr;
+ SocketAddress *saddr = NULL;
const char *tlscredsid;
QCryptoTLSCreds *tlscreds = NULL;
const char *hostname = NULL;
int ret = -EINVAL;
+ opts = qemu_opts_create(&nbd_runtime_opts, NULL, 0, &error_abort);
+ qemu_opts_absorb_qdict(opts, options, &local_err);
+ if (local_err) {
+ error_propagate(errp, local_err);
+ goto error;
+ }
+
/* Pop the config into our state object. Exit if invalid. */
- saddr = nbd_config(s, options, &export, errp);
+ saddr = nbd_config(s, opts, &export, errp);
if (!saddr) {
goto error;
}
- tlscredsid = g_strdup(qdict_get_try_str(options, "tls-creds"));
+ tlscredsid = g_strdup(qemu_opt_get(opts, "tls-creds"));
if (tlscredsid) {
- qdict_del(options, "tls-creds");
tlscreds = nbd_get_tls_creds(tlscredsid, errp);
if (!tlscreds) {
goto error;
@@ -346,6 +379,7 @@ static int nbd_open(BlockDriverState *bs, QDict *options, int flags,
}
qapi_free_SocketAddress(saddr);
g_free(export);
+ qemu_opts_del(opts);
return ret;
}