Add nodename inside virstoragefile
During xml backingStore parsing, look for a nodename attribute in the disk
declaration if this one is a quorum, if a nodename is found, add it to
the virStorageSource otherwise create a new one with a random name.
Take inspiration from this patch to create the nodename:
http://lists.gnu.org/archive/html/qemu-devel/2014-05/msg03209.html
Durring xml backingStore formating, look for a nodename attribute inside the
virStorageSource struct, and add it to the disk element.
Use the nodename to create the quorum in qemuBuildQuorumStr.
Signed-off-by: Matthias Gatto <matthias.gatto(a)outscale.com>
---
docs/formatdomain.html.in | 7 +++++++
docs/schemas/domaincommon.rng | 5 +++++
src/conf/domain_conf.c | 27 +++++++++++++++++++++++++++
src/qemu/qemu_command.c | 3 +++
src/util/virstoragefile.c | 4 ++++
src/util/virstoragefile.h | 1 +
6 files changed, 47 insertions(+)
diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in
index 263baaf..6429e86 100644
--- a/docs/formatdomain.html.in
+++ b/docs/formatdomain.html.in
@@ -2131,6 +2131,13 @@
<code>vda[2]</code> refers to the backing store with
<code>index='2'</code> of the disk with
<code>vda</code> target.
</dd>
+ <dt><code>nodename</code> attribute
+ <span class="since">since 1.2.13</span></dt>
+ <dd>
+ When the backing store is a quorum child, we can use this attribute
+ to define the node-name of a child. If this atribute is undefine,
+ a random nodename is generate.
+ </dd>
<dt><code>format</code> sub-element</dt>
<dd>
The <code>format</code> element contains
<code>type</code>
diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng
index 2556489..a1c5a39 100644
--- a/docs/schemas/domaincommon.rng
+++ b/docs/schemas/domaincommon.rng
@@ -1304,6 +1304,11 @@
</attribute>
<interleave>
<optional>
+ <attribute name="nodename">
+ <text/>
+ </attribute>
+ </optional>
+ <optional>
<ref name="diskDevice"/>
</optional>
<ref name="diskSource"/>
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 35ac9f4..e3ac5fb 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -56,6 +56,7 @@
#include "network_conf.h"
#include "virtpm.h"
#include "virstring.h"
+#include "virrandom.h"
#define VIR_FROM_THIS VIR_FROM_DOMAIN
@@ -5631,6 +5632,8 @@ virDomainDiskThresholdParse(virStorageSourcePtr src,
}
+#define GEN_NODE_NAME_PREFIX "libvirt"
+#define GEN_NODE_NAME_MAX_LEN (sizeof(GEN_NODE_NAME_PREFIX) + 8 + 8)
static int
virDomainDiskBackingStoreParse(xmlXPathContextPtr ctxt,
virStorageSourcePtr src,
@@ -5673,6 +5676,26 @@ virDomainDiskBackingStoreParse(xmlXPathContextPtr ctxt,
goto cleanup;
}
+ if (src->type == VIR_STORAGE_TYPE_QUORUM) {
+ char *nodeName = NULL;
+
+ if ((nodeName = virXMLPropString(ctxt->node, "nodename"))) {
+ backingStore->nodeName = nodeName;
+ } else {
+ size_t len;
+
+ if (VIR_ALLOC_N(nodeName, GEN_NODE_NAME_MAX_LEN) < 0)
+ goto cleanup;
+ if (snprintf(nodeName, GEN_NODE_NAME_MAX_LEN,
+ "%s%08x", GEN_NODE_NAME_PREFIX, (int)pos) < 0)
+ goto cleanup;
+ for (len = strlen(nodeName); len < GEN_NODE_NAME_MAX_LEN - 1; ++len)
+ nodeName[len] = virRandomInt('Z' - 'A') + 'A';
+ nodeName[GEN_NODE_NAME_MAX_LEN - 1] = '\0';
+ backingStore->nodeName = nodeName;
+ }
+ }
+
if (!(format = virXPathString("string(./format/@type)", ctxt))) {
virReportError(VIR_ERR_XML_ERROR, "%s",
_("missing disk backing store format"));
@@ -5728,6 +5751,8 @@ virDomainDiskBackingStoreParse(xmlXPathContextPtr ctxt,
ctxt->node = save_ctxt;
return ret;
}
+#undef GEN_NODE_NAME_PREFIX
+#undef GEN_NODE_NAME_MAX_LEN
#define VENDOR_LEN 8
#define PRODUCT_LEN 16
@@ -16764,6 +16789,8 @@ virDomainDiskBackingStoreFormat(virBufferPtr buf,
type, idx);
if (backingStore->threshold)
virBufferAsprintf(buf, " threshold='%lu'",
backingStore->threshold);
+ if (backingStore->nodeName)
+ virBufferAsprintf(buf, " nodename='%s'",
backingStore->nodeName);
virBufferAddLit(buf, ">\n");
virBufferAdjustIndent(buf, 2);
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index acbff19..de971c8 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -3435,6 +3435,9 @@ qemuBuildQuorumStr(virConnectPtr conn,
toAppend, i,
virStorageFileFormatTypeToString(backingStore->format));
+ virBufferAsprintf(opt, ",%schildren.%lu.node-name=%s",
+ toAppend, i, backingStore->nodeName);
+
if (qemuBuildQuorumFileSourceStr(conn, backingStore, opt, tmp) == false)
goto error;
diff --git a/src/util/virstoragefile.c b/src/util/virstoragefile.c
index de55484..49e2184 100644
--- a/src/util/virstoragefile.c
+++ b/src/util/virstoragefile.c
@@ -1939,6 +1939,9 @@ virStorageSourceCopy(const virStorageSource *src,
!(ret->auth = virStorageAuthDefCopy(src->auth)))
goto error;
+ if (src->nodeName && VIR_STRDUP(ret->nodeName, src->nodeName) <
0)
+ goto error;
+
for (i = 0; i < src->nBackingStores; ++i) {
if (backingChain && virStorageSourceGetBackingStore(src, i)) {
if (!virStorageSourceSetBackingStore(ret,
@@ -2084,6 +2087,7 @@ virStorageSourceBackingStoreClear(virStorageSourcePtr def)
VIR_FREE(def->relPath);
VIR_FREE(def->backingStoreRaw);
+ VIR_FREE(def->nodeName);
/* recursively free backing chain */
for (i = 0; i < def->nBackingStores; ++i)
diff --git a/src/util/virstoragefile.h b/src/util/virstoragefile.h
index 9d1b889..74c3893 100644
--- a/src/util/virstoragefile.h
+++ b/src/util/virstoragefile.h
@@ -275,6 +275,7 @@ struct _virStorageSource {
virStorageSourcePtr *backingStores;
size_t nBackingStores;
size_t threshold;
+ char *nodeName;
/* metadata for storage driver access to remote and local volumes */
virStorageDriverDataPtr drv;
--
1.8.3.1