[libvirt] [PATCH 5/8] virsh: Prefer virDomainGetState over virDomainGetInfo

Jiri Denemark jdenemar at redhat.com
Wed May 4 14:45:06 UTC 2011


---
 tools/virsh.c |  195 +++++++++++++++++++++++++++++++++++++++++++++++----------
 1 files changed, 162 insertions(+), 33 deletions(-)

diff --git a/tools/virsh.c b/tools/virsh.c
index 5d8b025..6dae9fa 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -223,6 +223,8 @@ typedef struct __vshControl {
     int log_fd;                 /* log file descriptor */
     char *historydir;           /* readline history directory name */
     char *historyfile;          /* readline history file name */
+    bool noGetState;            /* virDomainGetState is not supported in
+                                 * current connection */
 } __vshControl;
 
 typedef struct vshCmdGrp {
@@ -334,7 +336,9 @@ static void vshDebug(vshControl *ctl, int level, const char *format, ...)
 /* XXX: add batch support */
 #define vshPrint(_ctl, ...)   vshPrintExtra(NULL, __VA_ARGS__)
 
+static int vshDomainState(vshControl *ctl, virDomainPtr dom, int *reason);
 static const char *vshDomainStateToString(int state);
+static const char *vshDomainStateReasonToString(int state, int reason);
 static const char *vshDomainVcpuStateToString(int state);
 static bool vshConnectionUsability(vshControl *ctl, virConnectPtr conn);
 
@@ -571,6 +575,7 @@ vshReconnect(vshControl *ctl) {
     else
         vshError(ctl, "%s", _("Reconnected to the hypervisor"));
     disconnected = 0;
+    ctl->noGetState = false;
 }
 
 /* ---------------
@@ -717,6 +722,7 @@ cmdConnect(vshControl *ctl, const vshCmd *cmd)
     }
     ctl->name = vshStrdup(ctl, name);
 
+    ctl->noGetState = false;
     ctl->readonly = ro;
 
     ctl->conn = virConnectOpenAuth(ctl->name, virConnectAuthPtrDefault,
@@ -750,14 +756,14 @@ static bool
 cmdRunConsole(vshControl *ctl, virDomainPtr dom, const char *name)
 {
     bool ret = false;
-    virDomainInfo dominfo;
+    int state;
 
-    if (virDomainGetInfo(dom, &dominfo) < 0) {
+    if ((state = vshDomainState(ctl, dom, NULL)) < 0) {
         vshError(ctl, "%s", _("Unable to get domain status"));
         goto cleanup;
     }
 
-    if (dominfo.state == VIR_DOMAIN_SHUTOFF) {
+    if (state == VIR_DOMAIN_SHUTOFF) {
         vshError(ctl, "%s", _("The domain is not running"));
         goto cleanup;
     }
@@ -872,29 +878,20 @@ cmdList(vshControl *ctl, const vshCmd *cmd ATTRIBUTE_UNUSED)
     vshPrintExtra(ctl, "----------------------------------\n");
 
     for (i = 0; i < maxid; i++) {
-        virDomainInfo info;
         virDomainPtr dom = virDomainLookupByID(ctl->conn, ids[i]);
-        const char *state;
 
         /* this kind of work with domains is not atomic operation */
         if (!dom)
             continue;
 
-        if (virDomainGetInfo(dom, &info) < 0)
-            state = _("no state");
-        else
-            state = _(vshDomainStateToString(info.state));
-
         vshPrint(ctl, "%3d %-20s %s\n",
                  virDomainGetID(dom),
                  virDomainGetName(dom),
-                 state);
+                 vshDomainStateToString(vshDomainState(ctl, dom, NULL)));
         virDomainFree(dom);
     }
     for (i = 0; i < maxname; i++) {
-        virDomainInfo info;
         virDomainPtr dom = virDomainLookupByName(ctl->conn, names[i]);
-        const char *state;
 
         /* this kind of work with domains is not atomic operation */
         if (!dom) {
@@ -902,12 +899,10 @@ cmdList(vshControl *ctl, const vshCmd *cmd ATTRIBUTE_UNUSED)
             continue;
         }
 
-        if (virDomainGetInfo(dom, &info) < 0)
-            state = _("no state");
-        else
-            state = _(vshDomainStateToString(info.state));
-
-        vshPrint(ctl, "%3s %-20s %s\n", "-", names[i], state);
+        vshPrint(ctl, "%3s %-20s %s\n",
+                 "-",
+                 names[i],
+                 vshDomainStateToString(vshDomainState(ctl, dom, NULL)));
 
         virDomainFree(dom);
         VIR_FREE(names[i]);
@@ -928,15 +923,17 @@ static const vshCmdInfo info_domstate[] = {
 
 static const vshCmdOptDef opts_domstate[] = {
     {"domain", VSH_OT_DATA, VSH_OFLAG_REQ, N_("domain name, id or uuid")},
+    {"reason", VSH_OT_BOOL, 0, N_("also print reason for the state")},
     {NULL, 0, 0, NULL}
 };
 
 static bool
 cmdDomstate(vshControl *ctl, const vshCmd *cmd)
 {
-    virDomainInfo info;
     virDomainPtr dom;
     bool ret = true;
+    int showReason = vshCommandOptBool(cmd, "reason");
+    int state, reason;
 
     if (!vshConnectionUsability(ctl, ctl->conn))
         return false;
@@ -944,12 +941,21 @@ cmdDomstate(vshControl *ctl, const vshCmd *cmd)
     if (!(dom = vshCommandOptDomain(ctl, cmd, NULL)))
         return false;
 
-    if (virDomainGetInfo(dom, &info) == 0)
-        vshPrint(ctl, "%s\n",
-                 _(vshDomainStateToString(info.state)));
-    else
+    if ((state = vshDomainState(ctl, dom, &reason)) < 0) {
         ret = false;
+        goto cleanup;
+    }
+
+    if (showReason) {
+        vshPrint(ctl, "%s (%s)\n",
+                 _(vshDomainStateToString(state)),
+                 vshDomainStateReasonToString(state, reason));
+    } else {
+        vshPrint(ctl, "%s\n",
+                 _(vshDomainStateToString(state)));
+    }
 
+cleanup:
     virDomainFree(dom);
     return ret;
 }
@@ -3023,7 +3029,6 @@ static bool
 cmdSetmaxmem(vshControl *ctl, const vshCmd *cmd)
 {
     virDomainPtr dom;
-    virDomainInfo info;
     int kilobytes = 0;
     bool ret = true;
     int config = vshCommandOptBool(cmd, "config");
@@ -3063,12 +3068,6 @@ cmdSetmaxmem(vshControl *ctl, const vshCmd *cmd)
         return false;
     }
 
-    if (virDomainGetInfo(dom, &info) != 0) {
-        virDomainFree(dom);
-        vshError(ctl, "%s", _("Unable to verify current MemorySize"));
-        return false;
-    }
-
     if (flags == -1) {
         if (virDomainSetMaxMemory(dom, kilobytes) != 0) {
             vshError(ctl, "%s", _("Unable to change MaxMemorySize"));
@@ -12024,10 +12023,38 @@ vshCommandStringParse(vshControl *ctl, char *cmdstr)
  * Misc utils
  * ---------------
  */
+static int
+vshDomainState(vshControl *ctl, virDomainPtr dom, int *reason)
+{
+    virDomainInfo info;
+
+    if (reason)
+        *reason = -1;
+
+    if (!ctl->noGetState) {
+        int state;
+        if (virDomainGetState(dom, &state, reason) < 0) {
+            virErrorPtr err = virGetLastError();
+            if (err && err->code == VIR_ERR_NO_SUPPORT)
+                ctl->noGetState = true;
+            else
+                return -1;
+        } else {
+            return state;
+        }
+    }
+
+    /* fall back to virDomainGetInfo if virDomainGetState is not supported */
+    if (virDomainGetInfo(dom, &info) < 0)
+        return -1;
+    else
+        return info.state;
+}
+
 static const char *
 vshDomainStateToString(int state)
 {
-    switch (state) {
+    switch ((virDomainState) state) {
     case VIR_DOMAIN_RUNNING:
         return N_("running");
     case VIR_DOMAIN_BLOCKED:
@@ -12040,13 +12067,114 @@ vshDomainStateToString(int state)
         return N_("shut off");
     case VIR_DOMAIN_CRASHED:
         return N_("crashed");
-    default:
+    case VIR_DOMAIN_NOSTATE:
         ;/*FALLTHROUGH*/
     }
     return N_("no state");  /* = dom0 state */
 }
 
 static const char *
+vshDomainStateReasonToString(int state, int reason)
+{
+    switch ((virDomainState) state) {
+    case VIR_DOMAIN_NOSTATE:
+        switch ((virDomainNostateReason) reason) {
+        case VIR_DOMAIN_NOSTATE_UNKNOWN:
+            ;
+        }
+        break;
+
+    case VIR_DOMAIN_RUNNING:
+        switch ((virDomainRunningReason) reason) {
+        case VIR_DOMAIN_RUNNING_BOOTED:
+            return N_("booted");
+        case VIR_DOMAIN_RUNNING_MIGRATED:
+            return N_("migrated");
+        case VIR_DOMAIN_RUNNING_RESTORED:
+            return N_("restored");
+        case VIR_DOMAIN_RUNNING_FROM_SNAPSHOT:
+            return N_("from snapshot");
+        case VIR_DOMAIN_RUNNING_UNPAUSED:
+            return N_("unpaused");
+        case VIR_DOMAIN_RUNNING_MIGRATION_CANCELED:
+            return N_("migration canceled");
+        case VIR_DOMAIN_RUNNING_SAVE_CANCELED:
+            return N_("save canceled");
+        case VIR_DOMAIN_RUNNING_UNKNOWN:
+            ;
+        }
+        break;
+
+    case VIR_DOMAIN_BLOCKED:
+        switch ((virDomainBlockedReason) reason) {
+        case VIR_DOMAIN_BLOCKED_UNKNOWN:
+            ;
+        }
+        break;
+
+    case VIR_DOMAIN_PAUSED:
+        switch ((virDomainPausedReason) reason) {
+        case VIR_DOMAIN_PAUSED_USER:
+            return N_("user");
+        case VIR_DOMAIN_PAUSED_MIGRATION:
+            return N_("migrating");
+        case VIR_DOMAIN_PAUSED_SAVE:
+            return N_("saving");
+        case VIR_DOMAIN_PAUSED_DUMP:
+            return N_("dumping");
+        case VIR_DOMAIN_PAUSED_IOERROR:
+            return N_("I/O error");
+        case VIR_DOMAIN_PAUSED_WATCHDOG:
+            return N_("watchdog");
+        case VIR_DOMAIN_PAUSED_FROM_SNAPSHOT:
+            return N_("from snapshot");
+        case VIR_DOMAIN_PAUSED_UNKNOWN:
+            ;
+        }
+        break;
+
+    case VIR_DOMAIN_SHUTDOWN:
+        switch ((virDomainShutdownReason) reason) {
+        case VIR_DOMAIN_SHUTDOWN_USER:
+            return N_("user");
+        case VIR_DOMAIN_SHUTDOWN_UNKNOWN:
+            ;
+        }
+        break;
+
+    case VIR_DOMAIN_SHUTOFF:
+        switch ((virDomainShutoffReason) reason) {
+        case VIR_DOMAIN_SHUTOFF_SHUTDOWN:
+            return N_("shutdown");
+        case VIR_DOMAIN_SHUTOFF_DESTROYED:
+            return N_("destroyed");
+        case VIR_DOMAIN_SHUTOFF_CRASHED:
+            return N_("crashed");
+        case VIR_DOMAIN_SHUTOFF_MIGRATED:
+            return N_("migrated");
+        case VIR_DOMAIN_SHUTOFF_SAVED:
+            return N_("saved");
+        case VIR_DOMAIN_SHUTOFF_FAILED:
+            return N_("failed");
+        case VIR_DOMAIN_SHUTOFF_FROM_SNAPSHOT:
+            return N_("from snapshot");
+        case VIR_DOMAIN_SHUTOFF_UNKNOWN:
+            ;
+        }
+        break;
+
+    case VIR_DOMAIN_CRASHED:
+        switch ((virDomainCrashedReason) reason) {
+        case VIR_DOMAIN_CRASHED_UNKNOWN:
+            ;
+        }
+        break;
+    }
+
+    return N_("unknown");
+}
+
+static const char *
 vshDomainVcpuStateToString(int state)
 {
     switch (state) {
@@ -12144,6 +12272,7 @@ vshError(vshControl *ctl, const char *format, ...)
     VIR_FREE(str);
 }
 
+
 /*
  * Initialize connection.
  */
-- 
1.7.5.rc3




More information about the libvir-list mailing list