On 06/18/2013 05:03 AM, Xu Wang wrote:
From: Xu Wang <cngesaint(a)outlook.com>
Under nested KVM environment libvirt-cim could recognize kvm support
correctly now.
Signed-off-by: Xu Wang <cngesaint(a)outlook.com>
---
libxkutil/device_parsing.c | 27 ++++++++++++++++++++
libxkutil/device_parsing.h | 2 +
src/Virt_VirtualSystemManagementService.c | 38 +++++++++++++++++++++++++----
3 files changed, 62 insertions(+), 5 deletions(-)
ACK and pushed with the following diff squashed in to initialize conn
since you changed the logic to goto out "if (disable_kvm) is true which
is before we get a conn pointer.
John
diff --git a/src/Virt_VirtualSystemManagementService.c
b/src/Virt_VirtualSystemM
index 4f5e47f..a46cd65 100644
--- a/src/Virt_VirtualSystemManagementService.c
+++ b/src/Virt_VirtualSystemManagementService.c
@@ -391,7 +391,7 @@ static bool fv_set_emulator(struct domain *domain,
static bool system_has_kvm(const char *pfx)
{
CMPIStatus s;
- virConnectPtr conn;
+ virConnectPtr conn = NULL;
char *caps = NULL;
bool disable_kvm = get_disable_kvm();
char *val = NULL;
diff --git a/libxkutil/device_parsing.c b/libxkutil/device_parsing.c
index 436415a..16195da 100644
--- a/libxkutil/device_parsing.c
+++ b/libxkutil/device_parsing.c
@@ -396,6 +396,33 @@ err:
return 0;
}
+int parse_domain_type(xmlNodePtr node, char **value)
+{
+ xmlNodePtr child = NULL;
+ char *type = NULL;
+
+ child = node->children;
+ while (child != NULL) {
+ if (XSTREQ(child->name, "domain")) {
+ type = get_attr_value(child, "type");
+ if (type != NULL) {
+ *value = strdup(type);
+ goto out;
+ }
+ }
+
+ if (parse_domain_type(child, value) == 1) {
+ goto out;
+ }
+
+ child = child->next;
+ }
+
+ return 0;
+out:
+ return 1;
+}
+
static int parse_net_device(xmlNode *inode, struct virt_device **vdevs)
{
struct virt_device *vdev = NULL;
diff --git a/libxkutil/device_parsing.h b/libxkutil/device_parsing.h
index 6f6b0b4..733324f 100644
--- a/libxkutil/device_parsing.h
+++ b/libxkutil/device_parsing.h
@@ -221,6 +221,8 @@ int attach_device(virDomainPtr dom, struct virt_device *dev);
int detach_device(virDomainPtr dom, struct virt_device *dev);
int change_device(virDomainPtr dom, struct virt_device *dev);
+int parse_domain_type(xmlNodePtr node, char **value);
+
#define XSTREQ(x, y) (STREQ((char *)x, y))
#define STRPROP(d, p, n) (d->p = get_node_content(n))
diff --git a/src/Virt_VirtualSystemManagementService.c
b/src/Virt_VirtualSystemManagementService.c
index 7b7261a..8e1e6b1 100644
--- a/src/Virt_VirtualSystemManagementService.c
+++ b/src/Virt_VirtualSystemManagementService.c
@@ -393,25 +393,53 @@ static bool system_has_kvm(const char *pfx)
CMPIStatus s;
virConnectPtr conn;
char *caps = NULL;
- bool kvm = false;
bool disable_kvm = get_disable_kvm();
+ char *val = NULL;
+ xmlDocPtr doc = NULL;
+ xmlNodePtr node = NULL;
+ int len;
+ bool kvm = false;
/* sometimes disable KVM to avoid problem in nested KVM */
if (disable_kvm) {
CU_DEBUG("Enter disable kvm mode!");
- return false;
+ goto out;
}
conn = connect_by_classname(_BROKER, pfx, &s);
if ((conn == NULL) || (s.rc != CMPI_RC_OK)) {
- return false;
+ goto out;
}
caps = virConnectGetCapabilities(conn);
- if (caps != NULL)
- kvm = (strstr(caps, "kvm") != NULL);
+ if (caps != NULL) {
+ len = strlen(caps) + 1;
+
+ doc = xmlParseMemory(caps, len);
+ if (doc == NULL) {
+ CU_DEBUG("xmlParseMemory() call failed!");
+ goto out;
+ }
+
+ node = xmlDocGetRootElement(doc);
+ if (node == NULL) {
+ CU_DEBUG("xmlDocGetRootElement() call failed!");
+ goto out;
+ }
+
+ if (parse_domain_type(node, &val) &&
+ STREQC(val, "kvm")) {
+ CU_DEBUG("The system support kvm!");
+ kvm = true;
+ } else {
+ CU_DEBUG("Domain type is %s.", val);
+ }
+ }
+out:
free(caps);
+ free(doc);
+ free(val);
virConnectClose(conn);