[libvirt] [PATCH v1 1/8] domain_conf: Introduce chardev hotplug helpers

Michal Privoznik mprivozn at redhat.com
Mon May 6 15:34:32 UTC 2013


For now, only these three helpers are needed:
virDomainChrFind - to find a duplicate chardev within VM def
virDomainChrInsert - wrapper for inserting a new chardev into VM def
virDomainChrRemove - wrapper for removing chardev from VM def

There is, however, one internal helper as well:
virDomainChrGetDomainPtrs which sets given pointers to one of
vmdef->{parallels,serials,consoles,channels} based on passed
chardev type.
---
 src/conf/domain_conf.c   | 152 +++++++++++++++++++++++++++++++++++++++++++++++
 src/conf/domain_conf.h   |  11 ++++
 src/libvirt_private.syms |   4 ++
 3 files changed, 167 insertions(+)

diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index fe97c02..63f4daf 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -9650,6 +9650,158 @@ virDomainLeaseRemove(virDomainDefPtr def,
     return virDomainLeaseRemoveAt(def, i);
 }
 
+static bool
+virDomainChrEquals(virDomainChrDefPtr src,
+                   virDomainChrDefPtr tgt)
+{
+    if (!src || !tgt)
+        return src == tgt;
+
+    if (!virDomainChrSourceDefIsEqual(&src->source, &tgt->source))
+        return false;
+
+    switch ((enum virDomainChrChannelTargetType) src->targetType) {
+    case VIR_DOMAIN_CHR_CHANNEL_TARGET_TYPE_VIRTIO:
+        return STREQ_NULLABLE(src->target.name, tgt->target.name);
+        break;
+    case VIR_DOMAIN_CHR_CHANNEL_TARGET_TYPE_GUESTFWD:
+        return memcmp(src->target.addr, tgt->target.addr,
+                      sizeof(*src->target.addr)) == 0;
+        break;
+
+    case VIR_DOMAIN_CHR_CHANNEL_TARGET_TYPE_NONE:
+    case VIR_DOMAIN_CHR_CHANNEL_TARGET_TYPE_LAST:
+    default:
+        return true;
+    }
+}
+
+virDomainChrDefPtr
+virDomainChrFind(virDomainDefPtr def,
+                 virDomainChrDefPtr target)
+{
+    size_t i;
+
+    for (i = 0; i < def->nparallels; i++) {
+        virDomainChrDefPtr chr = def->parallels[i];
+
+        if (virDomainChrEquals(chr, target))
+            return chr;
+    }
+
+    for (i = 0; i < def->nserials; i++) {
+        virDomainChrDefPtr chr = def->serials[i];
+
+        if (virDomainChrEquals(chr, target))
+            return chr;
+    }
+
+
+    for (i = 0; i < def->nconsoles; i++) {
+        virDomainChrDefPtr chr = def->consoles[i];
+
+        if (virDomainChrEquals(chr, target))
+            return chr;
+    }
+
+    for (i = 0; i < def->nchannels; i++) {
+        virDomainChrDefPtr chr = def->channels[i];
+
+        if (virDomainChrEquals(chr, target))
+            return chr;
+    }
+
+    return NULL;
+}
+
+int
+virDomainChrGetDomainPtrs(virDomainDefPtr vmdef,
+                          virDomainChrDefPtr chr,
+                          virDomainChrDefPtr ***arrPtr,
+                          size_t **cntPtr)
+{
+    switch ((enum virDomainChrDeviceType) chr->deviceType) {
+    case VIR_DOMAIN_CHR_DEVICE_TYPE_PARALLEL:
+        *arrPtr = &vmdef->parallels;
+        *cntPtr = &vmdef->nparallels;
+        break;
+
+    case VIR_DOMAIN_CHR_DEVICE_TYPE_SERIAL:
+        *arrPtr = &vmdef->serials;
+        *cntPtr = &vmdef->nserials;
+        break;
+
+    case VIR_DOMAIN_CHR_DEVICE_TYPE_CONSOLE:
+        *arrPtr = &vmdef->consoles;
+        *cntPtr = &vmdef->nconsoles;
+        break;
+
+    case VIR_DOMAIN_CHR_DEVICE_TYPE_CHANNEL:
+        *arrPtr = &vmdef->channels;
+        *cntPtr = &vmdef->nchannels;
+        break;
+
+    default:
+        virReportError(VIR_ERR_OPERATION_INVALID,
+                       _("Unsupported device type '%d'"),
+                       chr->deviceType);
+        return -1;
+    }
+    return 0;
+}
+
+int virDomainChrInsert(virDomainDefPtr vmdef,
+                       virDomainChrDefPtr chr)
+{
+    virDomainChrDefPtr **arrPtr;
+    size_t *cntPtr;
+
+    if (virDomainChrGetDomainPtrs(vmdef, chr, &arrPtr, &cntPtr) < 0)
+        return -1;
+
+    if (VIR_REALLOC_N(*arrPtr, *cntPtr + 1) < 0) {
+        virReportOOMError();
+        return -1;
+    }
+
+    (*arrPtr)[*cntPtr] = chr;
+    (*cntPtr)++;
+
+    return 0;
+}
+
+int virDomainChrRemove(virDomainDefPtr vmdef,
+                       virDomainChrDefPtr chr)
+{
+    virDomainChrDefPtr **arrPtr;
+    size_t i, *cntPtr;
+
+    if (virDomainChrGetDomainPtrs(vmdef, chr, &arrPtr, &cntPtr) < 0)
+        return -1;
+
+    for (i = 0; i < *cntPtr; i++) {
+        virDomainChrDefPtr tmp = (*arrPtr)[i];
+
+        if (virDomainChrEquals(tmp, chr))
+            break;
+    }
+
+    if (i == *cntPtr)
+        return -1;
+
+    virDomainChrDefFree((*arrPtr)[i]);
+    if (*cntPtr > 1) {
+        memmove(*arrPtr + i,
+                *arrPtr + i + 1,
+                sizeof(**arrPtr) * (*cntPtr - (i + 1)));
+        ignore_value(VIR_REALLOC_N(*arrPtr, *cntPtr - 1));
+    } else {
+        VIR_FREE(*arrPtr);
+    }
+    (*cntPtr)--;
+
+    return 0;
+}
 
 char *
 virDomainDefGetDefaultEmulator(virDomainDefPtr def,
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
index 21f7ce2..3325fcf 100644
--- a/src/conf/domain_conf.h
+++ b/src/conf/domain_conf.h
@@ -2315,6 +2315,17 @@ virDomainLeaseDefPtr
 virDomainLeaseRemove(virDomainDefPtr def,
                      virDomainLeaseDefPtr lease);
 
+int virDomainChrGetDomainPtrs(virDomainDefPtr vmdef,
+                              virDomainChrDefPtr chr,
+                              virDomainChrDefPtr ***arrPtr,
+                              size_t **cntPtr);
+virDomainChrDefPtr virDomainChrFind(virDomainDefPtr def,
+                                    virDomainChrDefPtr target);
+int virDomainChrInsert(virDomainDefPtr vmdef,
+                       virDomainChrDefPtr chr);
+int virDomainChrRemove(virDomainDefPtr vmdef,
+                       virDomainChrDefPtr chr);
+
 int virDomainSaveXML(const char *configDir,
                      virDomainDefPtr def,
                      const char *xml);
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index d4cb4a3..6abba6e 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -77,6 +77,10 @@ virDomainChrConsoleTargetTypeToString;
 virDomainChrDefForeach;
 virDomainChrDefFree;
 virDomainChrDefNew;
+virDomainChrFind;
+virDomainChrGetDomainPtrs;
+virDomainChrInsert;
+virDomainChrRemove;
 virDomainChrSerialTargetTypeFromString;
 virDomainChrSerialTargetTypeToString;
 virDomainChrSourceDefCopy;
-- 
1.8.1.5




More information about the libvir-list mailing list