[libvirt] [PATCH] build: add compiler attributes to virUUIDParse
by Eric Blake
Coverity complained that most, but not all, clients of virUUIDParse
were checking for errors. Silence those coverity warnings by
explicitly marking the cases where we trust the input, and fixing
one instance that really should have been checking. In particular,
this silences about half of the 46 warnings I saw on my most
recent Coverity analysis run.
* src/util/uuid.h (virUUIDParse): Enforce rules.
* src/util/uuid.c (virUUIDParse): Drop impossible check; at least
Coverity will detect if we break rules and pass NULL.
* src/xenapi/xenapi_driver.c (xenapiDomainCreateXML)
(xenapiDomainLookupByID, xenapiDomainLookupByName)
(xenapiDomainDefineXML): Ignore return when we trust data source.
* src/vbox/vbox_tmpl.c (nsIDtoChar, vboxIIDToUUID_v3_x)
(vboxCallbackOnMachineStateChange)
(vboxCallbackOnMachineRegistered, vboxStoragePoolLookupByName):
Likewise.
* src/node_device/node_device_hal.c (gather_system_cap): Likewise.
* src/xenxs/xen_sxpr.c (xenParseSxpr): Check for errors.
---
This one's big enough that I'll wait for ACK before pushing.
src/node_device/node_device_hal.c | 3 ++-
src/util/uuid.c | 5 +----
src/util/uuid.h | 3 ++-
src/vbox/vbox_tmpl.c | 12 ++++++------
src/xenapi/xenapi_driver.c | 11 ++++++-----
src/xenxs/xen_sxpr.c | 3 ++-
6 files changed, 19 insertions(+), 18 deletions(-)
diff --git a/src/node_device/node_device_hal.c b/src/node_device/node_device_hal.c
index 481be97..a028886 100644
--- a/src/node_device/node_device_hal.c
+++ b/src/node_device/node_device_hal.c
@@ -38,6 +38,7 @@
#include "pci.h"
#include "logging.h"
#include "node_device_driver.h"
+#include "ignore-value.h"
#define VIR_FROM_THIS VIR_FROM_NODEDEV
@@ -299,7 +300,7 @@ static int gather_system_cap(LibHalContext *ctx, const char *udi,
(void)get_str_prop(ctx, udi, "system.hardware.serial",
&d->system.hardware.serial);
if (get_str_prop(ctx, udi, "system.hardware.uuid", &uuidstr) == 0) {
- (void)virUUIDParse(uuidstr, d->system.hardware.uuid);
+ ignore_value(virUUIDParse(uuidstr, d->system.hardware.uuid));
VIR_FREE(uuidstr);
}
(void)get_str_prop(ctx, udi, "system.firmware.vendor",
diff --git a/src/util/uuid.c b/src/util/uuid.c
index b4317df..0df3ebc 100644
--- a/src/util/uuid.c
+++ b/src/util/uuid.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2007, 2008, 2009, 2010 Red Hat, Inc.
+ * Copyright (C) 2007-2011 Red Hat, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -129,9 +129,6 @@ virUUIDParse(const char *uuidstr, unsigned char *uuid) {
const char *cur;
int i;
- if ((uuidstr == NULL) || (uuid == NULL))
- return(-1);
-
/*
* do a liberal scan allowing '-' and ' ' anywhere between character
* pairs, and surrounding whitespace, as long as there are exactly
diff --git a/src/util/uuid.h b/src/util/uuid.h
index b5d7878..7dbfad5 100644
--- a/src/util/uuid.h
+++ b/src/util/uuid.h
@@ -32,7 +32,8 @@ int virUUIDIsValid(unsigned char *uuid);
int virUUIDGenerate(unsigned char *uuid);
int virUUIDParse(const char *uuidstr,
- unsigned char *uuid);
+ unsigned char *uuid)
+ ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2) ATTRIBUTE_RETURN_CHECK;
void virUUIDFormat(const unsigned char *uuid,
char *uuidstr) ATTRIBUTE_NONNULL(1) ATTRIBUTE_NONNULL(2);
diff --git a/src/vbox/vbox_tmpl.c b/src/vbox/vbox_tmpl.c
index 9b674a9..bc19b63 100644
--- a/src/vbox/vbox_tmpl.c
+++ b/src/vbox/vbox_tmpl.c
@@ -300,7 +300,7 @@ static void nsIDtoChar(unsigned char *uuid, const nsID *iid) {
}
uuidstrdst[VIR_UUID_STRING_BUFLEN-1] = '\0';
- virUUIDParse(uuidstrdst, uuid);
+ ignore_value(virUUIDParse(uuidstrdst, uuid));
}
static void nsIDFromChar(nsID *iid, const unsigned char *uuid) {
@@ -339,7 +339,7 @@ static void nsIDFromChar(nsID *iid, const unsigned char *uuid) {
}
uuidstrdst[VIR_UUID_STRING_BUFLEN-1] = '\0';
- virUUIDParse(uuidstrdst, uuidinterim);
+ ignore_value(virUUIDParse(uuidstrdst, uuidinterim));
memcpy(iid, uuidinterim, VIR_UUID_BUFLEN);
}
@@ -511,7 +511,7 @@ vboxIIDToUUID_v3_x(vboxGlobalData *data, vboxIID_v3_x *iid,
data->pFuncs->pfnUtf16ToUtf8(iid->value, &utf8);
- virUUIDParse(utf8, uuid);
+ ignore_value(virUUIDParse(utf8, uuid));
data->pFuncs->pfnUtf8Free(utf8);
}
@@ -6558,7 +6558,7 @@ vboxCallbackOnMachineStateChange(IVirtualBoxCallback *pThis ATTRIBUTE_UNUSED,
unsigned char uuid[VIR_UUID_BUFLEN];
g_pVBoxGlobalData->pFuncs->pfnUtf16ToUtf8(machineId, &machineIdUtf8);
- virUUIDParse(machineIdUtf8, uuid);
+ ignore_value(virUUIDParse(machineIdUtf8, uuid));
dom = vboxDomainLookupByUUID(g_pVBoxGlobalData->conn, uuid);
if (dom) {
@@ -6686,7 +6686,7 @@ vboxCallbackOnMachineRegistered(IVirtualBoxCallback *pThis ATTRIBUTE_UNUSED,
unsigned char uuid[VIR_UUID_BUFLEN];
g_pVBoxGlobalData->pFuncs->pfnUtf16ToUtf8(machineId, &machineIdUtf8);
- virUUIDParse(machineIdUtf8, uuid);
+ ignore_value(virUUIDParse(machineIdUtf8, uuid));
dom = vboxDomainLookupByUUID(g_pVBoxGlobalData->conn, uuid);
if (dom) {
@@ -7983,7 +7983,7 @@ static virStoragePoolPtr vboxStoragePoolLookupByName(virConnectPtr conn, const c
unsigned char uuid[VIR_UUID_BUFLEN];
const char *uuidstr = "1deff1ff-1481-464f-967f-a50fe8936cc4";
- virUUIDParse(uuidstr, uuid);
+ ignore_value(virUUIDParse(uuidstr, uuid));
ret = virGetStoragePool(conn, name, uuid);
}
diff --git a/src/xenapi/xenapi_driver.c b/src/xenapi/xenapi_driver.c
index 80a706a..3946455 100644
--- a/src/xenapi/xenapi_driver.c
+++ b/src/xenapi/xenapi_driver.c
@@ -40,6 +40,7 @@
#include "xenapi_driver.h"
#include "xenapi_driver_private.h"
#include "xenapi_utils.h"
+#include "ignore-value.h"
#define VIR_FROM_THIS VIR_FROM_XENAPI
@@ -528,7 +529,7 @@ xenapiDomainCreateXML (virConnectPtr conn,
virDomainDefFree(defPtr);
if (record) {
unsigned char raw_uuid[VIR_UUID_BUFLEN];
- virUUIDParse(record->uuid, raw_uuid);
+ ignore_value(virUUIDParse(record->uuid, raw_uuid));
if (vm) {
if (xen_vm_start(session, vm, false, false)) {
domP = virGetDomain(conn, record->name_label, raw_uuid);
@@ -574,13 +575,13 @@ xenapiDomainLookupByID (virConnectPtr conn, int id)
xen_session_get_this_host(session, &host, session);
if (host != NULL && session->ok) {
xen_host_get_resident_vms(session, &result, host);
- if (result != NULL ) {
+ if (result != NULL) {
for (i = 0; i < result->size; i++) {
xen_vm_get_domid(session, &domID, result->contents[i]);
if (domID == id) {
xen_vm_get_record(session, &record, result->contents[i]);
xen_vm_get_uuid(session, &uuid, result->contents[i]);
- virUUIDParse(uuid, raw_uuid);
+ ignore_value(virUUIDParse(uuid, raw_uuid));
domP = virGetDomain(conn, record->name_label, raw_uuid);
if (domP) {
int64_t domid = -1;
@@ -672,7 +673,7 @@ xenapiDomainLookupByName (virConnectPtr conn,
vm = vms->contents[0];
xen_vm_get_uuid(session, &uuid, vm);
if (uuid!=NULL) {
- virUUIDParse(uuid, raw_uuid);
+ ignore_value(virUUIDParse(uuid, raw_uuid));
domP = virGetDomain(conn, name, raw_uuid);
if (domP != NULL) {
int64_t domid = -1;
@@ -1683,7 +1684,7 @@ xenapiDomainDefineXML (virConnectPtr conn, const char *xml)
}
if (record != NULL) {
unsigned char raw_uuid[VIR_UUID_BUFLEN];
- virUUIDParse(record->uuid, raw_uuid);
+ ignore_value(virUUIDParse(record->uuid, raw_uuid));
domP = virGetDomain(conn, record->name_label, raw_uuid);
if (!domP && !session->ok)
xenapiSessionErrorHandler(conn, VIR_ERR_NO_DOMAIN, NULL);
diff --git a/src/xenxs/xen_sxpr.c b/src/xenxs/xen_sxpr.c
index f2447f7..d44b0dc 100644
--- a/src/xenxs/xen_sxpr.c
+++ b/src/xenxs/xen_sxpr.c
@@ -1094,7 +1094,8 @@ xenParseSxpr(const struct sexpr *root,
"%s", _("domain information incomplete, missing name"));
goto error;
}
- virUUIDParse(tmp, def->uuid);
+ if (virUUIDParse(tmp, def->uuid) < 0)
+ goto error;
if (sexpr_node_copy(root, "domain/description", &def->description) < 0)
goto no_memory;
--
1.7.4.4
13 years, 2 months
[libvirt] [PATCH] qemu: plug memory leak on migration
by Eric Blake
Detected by Coverity. Leak introduced in commit 72de0d2.
* src/qemu/qemu_migration.c (qemuMigrationCookieGraphicsXMLParse):
Clean up on success.
---
Pushing under the trivial rule.
src/qemu/qemu_migration.c | 1 +
1 files changed, 1 insertions(+), 0 deletions(-)
diff --git a/src/qemu/qemu_migration.c b/src/qemu/qemu_migration.c
index 4516231..f0a0e49 100644
--- a/src/qemu/qemu_migration.c
+++ b/src/qemu/qemu_migration.c
@@ -460,22 +460,23 @@ qemuMigrationCookieGraphicsXMLParse(xmlXPathContextPtr ctxt)
if (!(tmp = virXPathString("string(./graphics/@type)", ctxt))) {
qemuReportError(VIR_ERR_INTERNAL_ERROR,
"%s", _("missing type attribute in migration data"));
goto error;
}
if ((grap->type = virDomainGraphicsTypeFromString(tmp)) < 0) {
qemuReportError(VIR_ERR_INTERNAL_ERROR,
_("unknown graphics type %s"), tmp);
VIR_FREE(tmp);
goto error;
}
+ VIR_FREE(tmp);
if (virXPathInt("string(./graphics/@port)", ctxt, &grap->port) < 0) {
qemuReportError(VIR_ERR_INTERNAL_ERROR,
"%s", _("missing port attribute in migration data"));
goto error;
}
if (grap->type == VIR_DOMAIN_GRAPHICS_TYPE_SPICE) {
if (virXPathInt("string(./graphics/@tlsPort)", ctxt, &grap->tlsPort) < 0) {
qemuReportError(VIR_ERR_INTERNAL_ERROR,
"%s", _("missing tlsPort attribute in migration data"));
goto error;
}
--
1.7.4.4
13 years, 2 months
[libvirt] [PATCH] conf: plug memory leak on error
by Eric Blake
Detected by Coverity. Leak present since commit 874e65a; and
while commit d50bb45 tried to fix the issue, it missed a path.
* src/conf/domain_conf.c (virDomainDefParseBootXML): Always clean
up useserial.
---
Pushing under the trivial rule.
src/conf/domain_conf.c | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 8cd493b..844af27 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -6316,35 +6316,35 @@ virDomainDefParseBootXML(xmlXPathContextPtr ctxt,
useserial = virXPathString("string(./os/bios[1]/@useserial)", ctxt);
if (useserial) {
if (STREQ(useserial, "yes")) {
if (virXPathULong("count(./devices/serial)",
ctxt, &serialPorts) < 0) {
virDomainReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
_("need at least one serial port "
"for useserial"));
goto cleanup;
}
def->os.bios.useserial = VIR_DOMAIN_BIOS_USESERIAL_YES;
} else {
def->os.bios.useserial = VIR_DOMAIN_BIOS_USESERIAL_NO;
}
- VIR_FREE(useserial);
}
*bootCount = deviceBoot;
ret = 0;
cleanup:
+ VIR_FREE(useserial);
VIR_FREE(nodes);
return ret;
}
/* Parse the XML definition for a vcpupin */
static virDomainVcpuPinDefPtr
virDomainVcpuPinDefParseXML(const xmlNodePtr node,
xmlXPathContextPtr ctxt,
int maxvcpus)
{
virDomainVcpuPinDefPtr def;
xmlNodePtr oldnode = ctxt->node;
unsigned int vcpuid;
char *tmp = NULL;
--
1.7.4.4
13 years, 2 months
[libvirt] [PATCH 2/3] Add virBufferEscapeShell
by Guido Günther
Escape strings so they're safe to pass to the shell. Based on glib's
g_quote_string.
---
src/libvirt_private.syms | 1 +
src/util/buf.c | 54 ++++++++++++++++++++++++++++++++++++++++++++++
src/util/buf.h | 1 +
3 files changed, 56 insertions(+), 0 deletions(-)
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index 4f96518..862f3ac 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -29,6 +29,7 @@ virBufferEscape;
virBufferEscapeSexpr;
virBufferEscapeString;
virBufferFreeAndReset;
+virBufferEscapeShell;
virBufferStrcat;
virBufferURIEncodeString;
virBufferUse;
diff --git a/src/util/buf.c b/src/util/buf.c
index fa12855..f9d7cd7 100644
--- a/src/util/buf.c
+++ b/src/util/buf.c
@@ -486,6 +486,60 @@ virBufferURIEncodeString (virBufferPtr buf, const char *str)
}
/**
+ * virBufferEscapeShell:
+ * @buf: the buffer to append to
+ * @str: an unquoted string
+ *
+ * Quotes a string so that the shell (/bin/sh) will interpret the
+ * quoted string as unquoted_string.
+ */
+void
+virBufferEscapeShell(const virBufferPtr buf, const char *str)
+{
+ int len;
+ bool close_quote = false;
+ char *escaped, *out;
+ const char *cur;
+
+ if ((buf == NULL) || (str == NULL))
+ return;
+
+ if (buf->error)
+ return;
+
+ len = strlen(str);
+ if (xalloc_oversized(4, len) ||
+ VIR_ALLOC_N(escaped, 4 * len + 3) < 0) {
+ virBufferSetError(buf);
+ return;
+ }
+
+ cur = str;
+ out = escaped;
+
+ /* Add outer '...' only if arg included shell metacharacters. */
+ if (strpbrk(str, "\r\t\n !\"#$&'()*;<>?[\\]^`{|}~")) {
+ *out++ = '\'';
+ close_quote = true;
+ }
+ while (*cur != 0) {
+ if (*cur == '\'') {
+ /* Replace literal ' with a close ', a \', and a open ' */
+ *out++ = '\'';
+ *out++ = '\\';
+ *out++ = *cur++;
+ *out++ = '\'';
+ } else
+ *out++ = *cur++;
+ }
+ if (close_quote)
+ *out++ = '\'';
+ *out = 0;
+ virBufferAdd(buf, escaped, -1);
+ VIR_FREE(escaped);
+}
+
+/**
* virBufferStrcat:
* @buf: the buffer to dump
* @...: the variable list of strings, the last argument must be NULL
diff --git a/src/util/buf.h b/src/util/buf.h
index e545ed9..ad8ef86 100644
--- a/src/util/buf.h
+++ b/src/util/buf.h
@@ -52,6 +52,7 @@ void virBufferEscapeString(const virBufferPtr buf, const char *format, const cha
void virBufferEscapeSexpr(const virBufferPtr buf, const char *format, const char *str);
void virBufferEscape(const virBufferPtr buf, const char *toescape, const char *format, const char *str);
void virBufferURIEncodeString (const virBufferPtr buf, const char *str);
+void virBufferEscapeShell(const virBufferPtr buf, const char *str);
# define virBufferAddLit(buf_, literal_string_) \
virBufferAdd (buf_, "" literal_string_ "", sizeof literal_string_ - 1)
--
1.7.6.3
13 years, 2 months
[libvirt] [PATCH 3/3] Use virBufferEscapeShell in virNetSocketNewConnectSSH
by Guido Günther
to escape the netcat command since it's passed to the shell. Adjust
expected test case output accordingly.
---
src/rpc/virnetsocket.c | 25 ++++++++++++++++++++-----
tests/virnetsockettest.c | 10 +++++-----
2 files changed, 25 insertions(+), 10 deletions(-)
diff --git a/src/rpc/virnetsocket.c b/src/rpc/virnetsocket.c
index ea653da..0105e45 100644
--- a/src/rpc/virnetsocket.c
+++ b/src/rpc/virnetsocket.c
@@ -612,7 +612,10 @@ int virNetSocketNewConnectSSH(const char *nodename,
const char *path,
virNetSocketPtr *retsock)
{
+ char *quoted;
virCommandPtr cmd;
+ virBuffer buf = VIR_BUFFER_INITIALIZER;
+
*retsock = NULL;
cmd = virCommandNew(binary ? binary : "ssh");
@@ -636,6 +639,19 @@ int virNetSocketNewConnectSSH(const char *nodename,
virCommandAddArgList(cmd, "-o", "StrictHostKeyChecking=no", NULL);
virCommandAddArgList(cmd, nodename, "sh", "-c", NULL);
+
+ virBufferEscapeShell(&buf, netcat ? netcat : "nc");
+ if (virBufferError(&buf)) {
+ virBufferFreeAndReset(&buf);
+ virReportOOMError();
+ return -1;
+ }
+ quoted = virBufferContentAndReset(&buf);
+ if (quoted == NULL) {
+ virReportOOMError();
+ return -1;
+ }
+
/*
* This ugly thing is a shell script to detect availability of
* the -q option for 'nc': debian and suse based distros need this
@@ -647,14 +663,13 @@ int virNetSocketNewConnectSSH(const char *nodename,
* behavior.
*/
virCommandAddArgFormat(cmd,
- "'if %s -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then"
+ "'if '%s' -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then"
" ARG=-q0;"
"fi;"
- "%s $ARG -U %s'",
- netcat ? netcat : "nc",
- netcat ? netcat : "nc",
- path);
+ "'%s' $ARG -U %s'",
+ quoted, quoted, path);
+ VIR_FREE(quoted);
return virNetSocketNewConnectCommand(cmd, retsock);
}
diff --git a/tests/virnetsockettest.c b/tests/virnetsockettest.c
index b3a2705..c063e74 100644
--- a/tests/virnetsockettest.c
+++ b/tests/virnetsockettest.c
@@ -496,7 +496,7 @@ mymain(void)
struct testSSHData sshData1 = {
.nodename = "somehost",
.path = "/tmp/socket",
- .expectOut = "somehost sh -c 'if nc -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;nc $ARG -U /tmp/socket'\n",
+ .expectOut = "somehost sh -c 'if 'nc' -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;'nc' $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 1", 1, testSocketSSH, &sshData1) < 0)
ret = -1;
@@ -509,7 +509,7 @@ mymain(void)
.noTTY = true,
.noVerify = false,
.path = "/tmp/socket",
- .expectOut = "-p 9000 -l fred -T -o BatchMode=yes -e none somehost sh -c 'if netcat -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;netcat $ARG -U /tmp/socket'\n",
+ .expectOut = "-p 9000 -l fred -T -o BatchMode=yes -e none somehost sh -c 'if 'netcat' -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;'netcat' $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 2", 1, testSocketSSH, &sshData2) < 0)
ret = -1;
@@ -522,7 +522,7 @@ mymain(void)
.noTTY = false,
.noVerify = true,
.path = "/tmp/socket",
- .expectOut = "-p 9000 -l fred -o StrictHostKeyChecking=no somehost sh -c 'if netcat -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;netcat $ARG -U /tmp/socket'\n",
+ .expectOut = "-p 9000 -l fred -o StrictHostKeyChecking=no somehost sh -c 'if 'netcat' -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;'netcat' $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 3", 1, testSocketSSH, &sshData3) < 0)
ret = -1;
@@ -538,7 +538,7 @@ mymain(void)
struct testSSHData sshData5 = {
.nodename = "crashyhost",
.path = "/tmp/socket",
- .expectOut = "crashyhost sh -c 'if nc -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;nc $ARG -U /tmp/socket'\n",
+ .expectOut = "crashyhost sh -c 'if 'nc' -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;'nc' $ARG -U /tmp/socket'\n",
.dieEarly = true,
};
@@ -550,7 +550,7 @@ mymain(void)
.path = "/tmp/socket",
.keyfile = "/root/.ssh/example_key",
.noVerify = true,
- .expectOut = "-i /root/.ssh/example_key -o StrictHostKeyChecking=no example.com sh -c 'if nc -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;nc $ARG -U /tmp/socket'\n",
+ .expectOut = "-i /root/.ssh/example_key -o StrictHostKeyChecking=no example.com sh -c 'if 'nc' -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;'nc' $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 6", 1, testSocketSSH, &sshData6) < 0)
ret = -1;
--
1.7.6.3
13 years, 2 months
[libvirt] [PATCH 1/3] Autodetect if the remote nc command supports the -q option
by Guido Günther
Based on a patch by Marc Deslauriers <marc.deslauriers(a)ubuntu.com>
RH: https://bugzilla.redhat.com/show_bug.cgi?id=562176
Ubuntu: https://bugs.launchpad.net/ubuntu/+source/libvirt/+bug/517478
Debian: http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=573172
---
src/rpc/virnetsocket.c | 23 ++++++++++++++++++++---
tests/virnetsockettest.c | 11 ++++++-----
2 files changed, 26 insertions(+), 8 deletions(-)
diff --git a/src/rpc/virnetsocket.c b/src/rpc/virnetsocket.c
index e4289b1..ea653da 100644
--- a/src/rpc/virnetsocket.c
+++ b/src/rpc/virnetsocket.c
@@ -634,9 +634,26 @@ int virNetSocketNewConnectSSH(const char *nodename,
"-e", "none", NULL);
if (noVerify)
virCommandAddArgList(cmd, "-o", "StrictHostKeyChecking=no", NULL);
- virCommandAddArgList(cmd, nodename,
- netcat ? netcat : "nc",
- "-U", path, NULL);
+
+ virCommandAddArgList(cmd, nodename, "sh", "-c", NULL);
+ /*
+ * This ugly thing is a shell script to detect availability of
+ * the -q option for 'nc': debian and suse based distros need this
+ * flag to ensure the remote nc will exit on EOF, so it will go away
+ * when we close the connection tunnel. If it doesn't go away, subsequent
+ * connection attempts will hang.
+ *
+ * Fedora's 'nc' doesn't have this option, and defaults to the desired
+ * behavior.
+ */
+ virCommandAddArgFormat(cmd,
+ "'if %s -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then"
+ " ARG=-q0;"
+ "fi;"
+ "%s $ARG -U %s'",
+ netcat ? netcat : "nc",
+ netcat ? netcat : "nc",
+ path);
return virNetSocketNewConnectCommand(cmd, retsock);
}
diff --git a/tests/virnetsockettest.c b/tests/virnetsockettest.c
index fae15a3..b3a2705 100644
--- a/tests/virnetsockettest.c
+++ b/tests/virnetsockettest.c
@@ -496,7 +496,7 @@ mymain(void)
struct testSSHData sshData1 = {
.nodename = "somehost",
.path = "/tmp/socket",
- .expectOut = "somehost nc -U /tmp/socket\n",
+ .expectOut = "somehost sh -c 'if nc -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;nc $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 1", 1, testSocketSSH, &sshData1) < 0)
ret = -1;
@@ -509,7 +509,7 @@ mymain(void)
.noTTY = true,
.noVerify = false,
.path = "/tmp/socket",
- .expectOut = "-p 9000 -l fred -T -o BatchMode=yes -e none somehost netcat -U /tmp/socket\n",
+ .expectOut = "-p 9000 -l fred -T -o BatchMode=yes -e none somehost sh -c 'if netcat -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;netcat $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 2", 1, testSocketSSH, &sshData2) < 0)
ret = -1;
@@ -522,7 +522,7 @@ mymain(void)
.noTTY = false,
.noVerify = true,
.path = "/tmp/socket",
- .expectOut = "-p 9000 -l fred -o StrictHostKeyChecking=no somehost netcat -U /tmp/socket\n",
+ .expectOut = "-p 9000 -l fred -o StrictHostKeyChecking=no somehost sh -c 'if netcat -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;netcat $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 3", 1, testSocketSSH, &sshData3) < 0)
ret = -1;
@@ -538,7 +538,8 @@ mymain(void)
struct testSSHData sshData5 = {
.nodename = "crashyhost",
.path = "/tmp/socket",
- .expectOut = "crashyhost nc -U /tmp/socket\n",
+ .expectOut = "crashyhost sh -c 'if nc -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;nc $ARG -U /tmp/socket'\n",
+
.dieEarly = true,
};
if (virtTestRun("SSH test 5", 1, testSocketSSH, &sshData5) < 0)
@@ -549,7 +550,7 @@ mymain(void)
.path = "/tmp/socket",
.keyfile = "/root/.ssh/example_key",
.noVerify = true,
- .expectOut = "-i /root/.ssh/example_key -o StrictHostKeyChecking=no example.com nc -U /tmp/socket\n",
+ .expectOut = "-i /root/.ssh/example_key -o StrictHostKeyChecking=no example.com sh -c 'if nc -q 2>&1 | grep \"requires an argument\" >/dev/null 2>&1; then ARG=-q0;fi;nc $ARG -U /tmp/socket'\n",
};
if (virtTestRun("SSH test 6", 1, testSocketSSH, &sshData6) < 0)
ret = -1;
--
1.7.6.3
13 years, 2 months
[libvirt] [PATCH] storage: plug memory leak on error
by Eric Blake
Detected by Coverity. Present since commit 82c1740.
* src/storage/storage_backend_logical.c
(virStorageBackendLogicalMakeVol): Fix leak.
---
Pushing under the trivial rule.
src/storage/storage_backend_logical.c | 1 +
1 files changed, 1 insertions(+), 0 deletions(-)
diff --git a/src/storage/storage_backend_logical.c b/src/storage/storage_backend_logical.c
index 51624a7..50d0407 100644
--- a/src/storage/storage_backend_logical.c
+++ b/src/storage/storage_backend_logical.c
@@ -231,16 +231,17 @@ virStorageBackendLogicalMakeVol(virStoragePoolObjPtr pool,
if (!(offset_str = strndup(p + vars[j + 1].rm_so, len))) {
virReportOOMError();
goto cleanup;
}
if (virStrToLong_ull(offset_str, NULL, 10, &offset) < 0) {
virStorageReportError(VIR_ERR_INTERNAL_ERROR, "%s",
_("malformed volume extent offset value"));
+ VIR_FREE(offset_str);
goto cleanup;
}
VIR_FREE(offset_str);
vol->source.extents[vol->source.nextent].start = offset * size;
vol->source.extents[vol->source.nextent].end = (offset * size) + length;
vol->source.nextent++;
--
1.7.4.4
13 years, 2 months
[libvirt] How to identify a VirtFS using libvirt
by Richard Maciel
Hi,
Is there any way to fetch info on a VirtFS share, aside from reading the
guest's XML file?
For instance, I'd like to read the source and target dir of the VirtFS
mount created on guest by using the following XML code:
<filesystem type='mount' accessmode='passthrough'>
<source dir='/mnt/9p_setup'/>
<target dir='9p_test'/>
<address type='pci' domain='0x0000' bus='0x00' slot='0x07'
function='0x0'/>
</filesystem>
I tried to use the pool and volume-related functions on the API, but
that didn't work.
Richard Maciel
13 years, 2 months
[libvirt] [PATCH] qemu: fix text block info parsing
by Eric Blake
Detected by Coverity. p (the pointer to the string) is always true;
when in reality, we wanted to know whether the integer value of the
just-parsed string is '0' or '1'. Logic bug since commit b1b5b51.
* src/qemu/qemu_monitor_text.c (qemuMonitorTextGetBlockInfo): Set
results to proper value.
---
Second bug introduced by the same commit. And I think I reviewed
it originally. Sorry for not catching it earlier.
src/qemu/qemu_monitor_text.c | 6 +++---
1 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/src/qemu/qemu_monitor_text.c b/src/qemu/qemu_monitor_text.c
index 1eb9846..49c469b 100644
--- a/src/qemu/qemu_monitor_text.c
+++ b/src/qemu/qemu_monitor_text.c
@@ -817,19 +817,19 @@ int qemuMonitorTextGetBlockInfo(qemuMonitorPtr mon,
if (virStrToLong_i(p, &dummy, 10, &tmp) == -1)
VIR_DEBUG("error reading removable: %s", p);
else
- info->removable = p != NULL;
+ info->removable = tmp != 0;
} else if (STRPREFIX(p, "locked=")) {
p += strlen("locked=");
if (virStrToLong_i(p, &dummy, 10, &tmp) == -1)
VIR_DEBUG("error reading locked: %s", p);
else
- info->locked = p ? true : false;
+ info->locked = tmp != 0;
} else if (STRPREFIX(p, "tray_open=")) {
p += strlen("tray_open=");
if (virStrToLong_i(p, &dummy, 10, &tmp) == -1)
VIR_DEBUG("error reading tray_open: %s", p);
else
- info->tray_open = p ? true : false;
+ info->tray_open = tmp != 0;
} else {
/* ignore because we don't parse all options */
}
--
1.7.4.4
13 years, 2 months
[libvirt] [PATCH] qemu: avoid text monitor null deref
by Eric Blake
Detected by Coverity. If, for some reason, our text monitor input
does not match our assumptions, we end up incrementing p while it
is NULL, then dereferencing the pointer 0x1, which will fault.
* src/qemu/qemu_monitor_text.c
(qemuMonitorTextGetBlockStatsParamsNumber): Rewrite to avoid
deref of strchr failure. Fix indentation.
---
src/qemu/qemu_monitor_text.c | 33 +++++++++++++++------------------
1 files changed, 15 insertions(+), 18 deletions(-)
diff --git a/src/qemu/qemu_monitor_text.c b/src/qemu/qemu_monitor_text.c
index 51e8c5c..1eb9846 100644
--- a/src/qemu/qemu_monitor_text.c
+++ b/src/qemu/qemu_monitor_text.c
@@ -1036,26 +1036,23 @@ int qemuMonitorTextGetBlockStatsParamsNumber(qemuMonitorPtr mon,
* "floppy0: ")
*/
p = strchr(p, ' ');
- p++;
- while (*p) {
- if (STRPREFIX (p, "rd_bytes=") ||
- STRPREFIX (p, "wr_bytes=") ||
- STRPREFIX (p, "rd_operations=") ||
- STRPREFIX (p, "wr_operations=") ||
- STRPREFIX (p, "rd_total_times_ns=") ||
- STRPREFIX (p, "wr_total_times_ns=") ||
- STRPREFIX (p, "flush_operations=") ||
- STRPREFIX (p, "flush_total_times_ns=")) {
- num++;
- } else {
- VIR_DEBUG ("unknown block stat near %s", p);
- }
+ while (p && p < eol) {
+ if (STRPREFIX (p, " rd_bytes=") ||
+ STRPREFIX (p, " wr_bytes=") ||
+ STRPREFIX (p, " rd_operations=") ||
+ STRPREFIX (p, " wr_operations=") ||
+ STRPREFIX (p, " rd_total_times_ns=") ||
+ STRPREFIX (p, " wr_total_times_ns=") ||
+ STRPREFIX (p, " flush_operations=") ||
+ STRPREFIX (p, " flush_total_times_ns=")) {
+ num++;
+ } else {
+ VIR_DEBUG ("unknown block stat near %s", p);
+ }
- /* Skip to next label. */
- p = strchr (p, ' ');
- if (!p || p >= eol) break;
- p++;
+ /* Skip to next label. */
+ p = strchr(p + 1, ' ');
}
*nparams = num;
--
1.7.4.4
13 years, 2 months