Re: [libvirt] [RFC] Power Hypervisor Libvirt support

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hello again, 

I very am glad with all the feedback I got. The following attachtment is
the result of the work using all the suggestions the list made. I also
have a few comments over this new RFC. Here is a little Changelog:

* Now the URI is recognized as phyp://user@hmc/managed_system. To use
path component of the uri struct, I had to implement a little function
to strip out the first slash of the string, giving me only 'path',
instead of '/path'.

* I implemented the option --with-libssh and --with-phyp right according
to what Daniel Berrange suggested.

* Now all the variable-size string buffers are manipulated with the
internal API virBuffer* to make it safer.

|
+- This made me think and change the __inner_exec_command function. Now
it returns char * with all the textual return, and I am passing int * as
reference to get the exit status - all the information I need about the
remote executed command.

|
+- And this also made me write a little auxiliar function to strip out
the '\n' from the textual return.

Known and unsolved issues:

* Authentication - need to improve the authenticantion as Daniel
Berrange said. Still in progress.
* Error codes.
* Logging and debugging messages.

Any comments are welcome,

[]'s

Em Sex, 2009-03-20 às 13:58 -0300, Eduardo Otubo escreveu:
> Hello all,
> 
> I've been working on a libvirt extension to manage IBM's Power VMs
> (LPARs). The Power systems are managed through management console
> referred to as the HMC or using a management partition (IVM). Both HMC
> and IVM runs an SSH, then you can reach it via command line, and an HTTP
> server, then you can reach it via web browser.
> 
> The protocol between the console and the partition (LPAR) is not
> disclosed, therefore I propose the driver to execute commands remoetly
> over an SSH connection to the consoles to manage IBM LPARs.
> 
> The patch attached is the first scratch of the driver that will interact
> with HMC over a SSH connection. The URI model that is
> used in virsh command line is:
> 
> virsh --conect phyp://$user@$server
> 
> Some known issues are:
>  * Next step is to make the URI like this: phyp://$user@
> $HMC/@managed_system. Almost finished. What it takes now is
> $server = $HMC = $managed_system.
>  * Next features in my TODO list are "resume", "stop" and "reboot" the
> LPAR.
> 
> Any comments are welcome.
> 
> Thanks,
> 
> 
> --
> Libvir-list mailing list
> Libvir-list@xxxxxxxxxx
> https://www.redhat.com/mailman/listinfo/libvir-list
-- 
Eduardo Otubo
Software Engineer
Linux Technology Center
IBM Systems & Technology Group
Mobile: +55 19 8135 0885 
otubo@xxxxxxxxxxxxxxxxxx
diff --git a/configure.in b/configure.in
index dcacc7f..9545a20 100644
--- a/configure.in
+++ b/configure.in
@@ -182,6 +182,10 @@ AC_ARG_WITH([uml],
 [  --with-uml              add UML support (on)],[],[with_uml=yes])
 AC_ARG_WITH([openvz],
 [  --with-openvz           add OpenVZ support (on)],[],[with_openvz=yes])
+AC_ARG_WITH([libssh],
+[  --with-libssh=[PFX]       libssh location],[],[with_libssh=yes])
+AC_ARG_WITH([phyp],
+[  --with-phyp=[PFX]         add PHYP support (on)],[with_phyp=yes],[with_phyp=check])
 AC_ARG_WITH([vbox],
 [  --with-vbox             add VirtualBox support (on)],[],[with_vbox=yes])
 AC_ARG_WITH([lxc],
@@ -729,6 +733,51 @@ AM_CONDITIONAL([HAVE_NUMACTL], [test "$with_numactl" != "no"])
 AC_SUBST([NUMACTL_CFLAGS])
 AC_SUBST([NUMACTL_LIBS])
 
+if test "$with_libssh" != "yes" -a "$with_libssh" != "no"; then
+		libssh_path="$with_libssh"
+elif test "$with_libssh" = "yes"; then
+		libssh_path="/usr/local/lib/"
+elif test "$with_libssh" = "no"; then
+		with_phyp="no";
+fi
+
+if test "$with_phyp" = "check"; then
+  AC_CHECK_LIB([ssh],[ssh_new],[
+        LIBSSH_LIBS="$LIBSSH_LIBS -lssh -L$libssh_path"
+        AC_SUBST([LIBSSH_LIBS])],[
+        with_phyp="no"
+		    with_libssh="no";
+				],[])
+
+	if test "$with_phyp" != "no"; then
+  AC_CHECK_HEADERS([libssh/libssh.h],[
+		    with_phyp="yes"
+        LIBSSH_CFLAGS="-I/usr/local/include/libssh"
+        AC_SUBST([LIBSSH_CFLAGS])
+	      AC_DEFINE_UNQUOTED([WITH_PHYP], 1,
+        [whether IBM HMC / IVM driver is enabled])
+				],[
+        with_phyp="no"
+		    with_libssh="no";
+				],[])
+	fi
+elif test "$with_phyp" = "yes"; then
+  AC_CHECK_LIB([ssh],[ssh_new],[
+        LIBSSH_LIBS="$LIBSSH_LIBS -lssh -L$libssh_path"
+        AC_SUBST([LIBSSH_LIBS])],[
+        AC_MSG_ERROR([You must install the libssh to compile Phype driver.])
+				])
+
+  AC_CHECK_HEADERS([libssh/libssh.h],[
+        LIBSSH_CFLAGS="-I/usr/local/include/libssh"
+        AC_SUBST([LIBSSH_CFLAGS])],[
+        AC_MSG_ERROR([Cannot find libssh headers.Is libssh installed ?])
+				],[])
+  AC_DEFINE_UNQUOTED([WITH_PHYP], 1,
+        [whether IBM HMC / IVM driver is enabled])
+fi
+AM_CONDITIONAL([WITH_PHYP],[test "$with_phyp" = "yes"])
+
 dnl virsh libraries
 AC_CHECK_HEADERS([readline/readline.h])
 
@@ -1372,6 +1421,7 @@ AC_MSG_NOTICE([     UML: $with_uml])
 AC_MSG_NOTICE([  OpenVZ: $with_openvz])
 AC_MSG_NOTICE([    VBox: $with_vbox])
 AC_MSG_NOTICE([     LXC: $with_lxc])
+AC_MSG_NOTICE([    PHYP: $with_phyp])
 AC_MSG_NOTICE([    Test: $with_test])
 AC_MSG_NOTICE([  Remote: $with_remote])
 AC_MSG_NOTICE([ Network: $with_network])
@@ -1401,6 +1451,11 @@ fi
 AC_MSG_NOTICE([])
 AC_MSG_NOTICE([Libraries])
 AC_MSG_NOTICE([])
+if test "$with_libssh" != "no" ; then
+AC_MSG_NOTICE([  libssh: $LIBSSH_CFLAGS $LIBSSH_LIBS])
+else
+AC_MSG_NOTICE([  libssh: no])
+fi
 AC_MSG_NOTICE([  libxml: $LIBXML_CFLAGS $LIBXML_LIBS])
 AC_MSG_NOTICE([  gnutls: $GNUTLS_CFLAGS $GNUTLS_LIBS])
 if test "$with_sasl" != "no" ; then
diff --git a/include/libvirt/virterror.h b/include/libvirt/virterror.h
index faf3f61..28a35d9 100644
--- a/include/libvirt/virterror.h
+++ b/include/libvirt/virterror.h
@@ -61,6 +61,7 @@ typedef enum {
     VIR_FROM_UML,       /* Error at the UML driver */
     VIR_FROM_NODEDEV, /* Error from node device monitor */
     VIR_FROM_XEN_INOTIFY, /* Error from xen inotify layer */
+    VIR_FROM_PHYP, /* Error from IBM power hypervisor */
     VIR_FROM_SECURITY,  /* Error from security framework */
     VIR_FROM_VBOX,    /* Error from VirtualBox driver */
 } virErrorDomain;
diff --git a/src/Makefile.am b/src/Makefile.am
index fd692b4..e65f2d4 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -5,6 +5,7 @@ INCLUDES = \
 	   -I../include \
 	   -I@top_srcdir@/include \
 	   -I@top_srcdir@/qemud \
+	   $(LIBSSH_CFLAGS) \
 	   $(LIBXML_CFLAGS) \
 	   $(XEN_CFLAGS) \
 	   $(SELINUX_CFLAGS) \
@@ -125,6 +126,9 @@ LXC_CONTROLLER_SOURCES =					\
 		veth.c veth.h                                   \
 		cgroup.c cgroup.h
 
+PHYP_DRIVER_SOURCES =						\
+		phyp_driver.c phyp_driver.h
+
 OPENVZ_DRIVER_SOURCES =						\
 		openvz_conf.c openvz_conf.h			\
 		openvz_driver.c openvz_driver.h
@@ -265,6 +269,18 @@ endif
 libvirt_driver_xen_la_SOURCES = $(XEN_DRIVER_SOURCES)
 endif
 
+if WITH_PHYP
+if WITH_DRIVER_MODULES
+mod_LTLIBRARIES += libvirt_driver_phyp.la
+else
+noinst_LTLIBRARIES += libvirt_driver_phyp.la
+libvirt_la_LIBADD += libvirt_driver_phyp.la
+endif
+libvirt_driver_phyp_la_LDFLAGS = $(LIBSSH_LIBS)
+libvirt_driver_phyp_la_CFLAGS = $(LIBSSH_CFLAGS)
+libvirt_driver_phyp_la_SOURCES = $(PHYP_DRIVER_SOURCES)
+endif
+
 if WITH_OPENVZ
 if WITH_DRIVER_MODULES
 mod_LTLIBRARIES += libvirt_driver_openvz.la
@@ -430,6 +446,7 @@ EXTRA_DIST +=							\
 		$(LXC_DRIVER_SOURCES)				\
 		$(UML_DRIVER_SOURCES)				\
 		$(OPENVZ_DRIVER_SOURCES)			\
+		$(PHYP_DRIVER_SOURCES)			\
 		$(VBOX_DRIVER_SOURCES)				\
 		$(NETWORK_DRIVER_SOURCES)			\
 		$(STORAGE_DRIVER_SOURCES)			\
diff --git a/src/driver.h b/src/driver.h
index 39dc413..3e758e0 100644
--- a/src/driver.h
+++ b/src/driver.h
@@ -21,6 +21,7 @@ typedef enum {
     VIR_DRV_LXC = 6,
     VIR_DRV_UML = 7,
     VIR_DRV_VBOX = 8,
+    VIR_DRV_PHYP = 9,
 } virDrvNo;
 
 
diff --git a/src/libvirt.c b/src/libvirt.c
index 95a861e..617d957 100644
--- a/src/libvirt.c
+++ b/src/libvirt.c
@@ -55,6 +55,9 @@
 #ifdef WITH_OPENVZ
 #include "openvz_driver.h"
 #endif
+#ifdef WITH_PHYP
+#include "phyp_driver.h"
+#endif
 #ifdef WITH_VBOX
 #include "vbox/vbox_driver.h"
 #endif
@@ -321,6 +324,9 @@ virInitialize(void)
 #ifdef WITH_OPENVZ
     if (openvzRegister() == -1) return -1;
 #endif
+#ifdef WITH_PHYP
+    if (phypRegister() == -1) return -1;
+#endif
 #ifdef WITH_VBOX
     if (vboxRegister() == -1) return -1;
 #endif
@@ -833,6 +839,10 @@ virGetVersion(unsigned long *libVer, const char *type,
         if (STRCASEEQ(type, "LXC"))
             *typeVer = LIBVIR_VERSION_NUMBER;
 #endif
+#if WITH_PHYP
+        if (STRCASEEQ(type, "Phyp"))
+            *typeVer = LIBVIR_VERSION_NUMBER;
+#endif
 #if WITH_OPENVZ
         if (STRCASEEQ(type, "OpenVZ"))
             *typeVer = LIBVIR_VERSION_NUMBER;
diff --git a/src/phyp_driver.c b/src/phyp_driver.c
new file mode 100644
index 0000000..6c15afd
--- /dev/null
+++ b/src/phyp_driver.c
@@ -0,0 +1,496 @@
+
+/*
+ * Copyright IBM Corp. 2009
+ *
+ * phyp_driver.c: ssh layer to access Power Hypervisors
+ *
+ * Authors:
+ *  Eduardo Otubo <otubo at linux.vnet.ibm.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include <config.h>
+
+#include <sys/types.h>
+#include <limits.h>
+#include <string.h>
+#include <strings.h>
+#include <stdio.h>
+#include <stdarg.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <errno.h>
+#include <stdio.h>
+
+#include <libssh/libssh.h>
+
+#include "internal.h"
+#include "datatypes.h"
+#include "buf.h"
+#include "memory.h"
+#include "logging.h"
+#include "driver.h"
+
+#include "phyp_driver.h"
+
+/*
+ * TODO: I still need to implement a way to distinguish
+ * an HMC from an IVM
+ * */
+
+static virDrvOpenStatus
+phypOpen(virConnectPtr conn,
+         virConnectAuthPtr auth ATTRIBUTE_UNUSED,
+         int flags ATTRIBUTE_UNUSED)
+{
+    int ssh_auth = 0, exit_status = 0;
+    char *banner;
+    char *password;
+
+    SSH_SESSION *session;
+    SSH_OPTIONS *opt;
+
+    if (!conn || !conn->uri)
+        return VIR_DRV_OPEN_DECLINED;
+
+    if (conn->uri->scheme == NULL || conn->uri->server == NULL
+        || conn->uri->path == NULL)
+        return VIR_DRV_OPEN_DECLINED;
+
+    session = ssh_new();
+    opt = ssh_options_new();
+
+    if (!conn->uri->port)
+        conn->uri->port = 22;
+
+    /*setting some ssh options */
+    ssh_options_set_host(opt, conn->uri->server);
+    ssh_options_set_port(opt, conn->uri->port);
+    ssh_options_set_username(opt, conn->uri->user);
+    ssh_set_options(session, opt);
+
+    /*starting ssh connection */
+    if (ssh_connect(session)) {
+        fprintf(stderr, "Connection failed : %s\n",
+                ssh_get_error(session));
+        ssh_disconnect(session);
+        ssh_finalize();
+        exit_status = SSH_CONN_ERR;
+        return VIR_DRV_OPEN_DECLINED;
+    }
+
+    /*trying to use pub key */
+    if ((ssh_auth =
+         ssh_userauth_autopubkey(session, NULL)) == SSH_AUTH_ERROR) {
+        fprintf(stderr, "Authenticating with pubkey: %s\n",
+                ssh_get_error(session));
+        exit_status = SSH_AUTH_PUBKEY_ERR;
+        return VIR_DRV_OPEN_DECLINED;
+    }
+
+    if ((banner = ssh_get_issue_banner(session))) {
+        fprintf(stdout, "%s\n", banner);
+        VIR_FREE(banner);
+    }
+
+    if (ssh_auth != SSH_AUTH_SUCCESS) {
+        password = getpass("Password: ");
+        if (ssh_userauth_password(session, NULL, password) !=
+            SSH_AUTH_SUCCESS) {
+            fprintf(stderr, "Authentication failed: %s\n",
+                    ssh_get_error(session));
+            ssh_disconnect(session);
+            memset(password, 0, strlen(password));
+            exit_status = SSH_AUTH_ERR;
+            return VIR_DRV_OPEN_DECLINED;
+        } else
+            goto exec;
+    } else
+        goto exec;
+
+  exec:
+    conn->privateData = session;
+    return VIR_DRV_OPEN_SUCCESS;
+}
+
+static int
+phypClose(virConnectPtr conn)
+{
+    SSH_SESSION *ssh_session = conn->privateData;
+
+    ssh_disconnect(ssh_session);
+
+    return 0;
+}
+
+/* this functions is the layer that manipulates the ssh channel itself
+ * and executes the commands on the remote machine */
+static char *
+__inner_exec_command(SSH_SESSION * session, char *cmd, int *exit_status)
+{
+    CHANNEL *channel = channel_new(session);
+    BUFFER *readbuf = buffer_new();
+    virBuffer tex_ret = VIR_BUFFER_INITIALIZER;
+
+    int ret = 0;
+
+    if (channel_open_session(channel) == SSH_ERROR)
+        (*exit_status) = SSH_CHANNEL_OPEN_ERR;
+
+    if (channel_request_exec(channel, cmd) == SSH_ERROR)
+        (*exit_status) = SSH_CHANNEL_EXEC_ERR;
+
+    if (channel_send_eof(channel) == SSH_ERROR)
+        (*exit_status) = SSH_CHANNEL_SEND_EOF_ERR;
+
+    while (channel && channel_is_open(channel)) {
+        ret = channel_read(channel, readbuf, 0, 0);
+        if (ret < 0) {
+            (*exit_status) = SSH_CHANNEL_READ_ERR;
+            break;
+        }
+
+        if (ret == 0) {
+            channel_send_eof(channel);
+            while(channel_get_exit_status(channel) == -1){
+                channel_poll(channel,0);
+                usleep(50);
+            }
+            if (channel_close(channel) == SSH_ERROR)
+                (*exit_status) = SSH_CHANNEL_CLOSE_ERR;
+
+            (*exit_status) = channel_get_exit_status(channel);
+
+            channel_free(channel);
+            channel = NULL;
+            break;
+        }
+
+        buffer_add_u8(readbuf, 0);
+        virBufferStrcat(&tex_ret, buffer_get(readbuf));
+    }
+
+    return virBufferContentAndReset(&tex_ret);
+}
+
+/* return the lpar_id given a name and a managed system name */
+static int
+phypGetLparID(SSH_SESSION * ssh_session, const char *managed_system,
+              const char *name)
+{
+    int exit_status = 0;
+    virBuffer cmd = VIR_BUFFER_INITIALIZER;
+
+    virBufferVSprintf(&cmd,
+                      "lssyscfg -r lpar -m %s --filter lpar_names=%s -F lpar_id",
+                      managed_system, name);
+    const char *tex_ret =
+        __inner_exec_command(ssh_session, virBufferContentAndReset(&cmd),
+                             &exit_status);
+
+    virBufferContentAndReset(&cmd);
+    if (exit_status < 0 || tex_ret == NULL)
+        return 0;
+    else
+        return atoi(tex_ret);
+}
+
+/* return the lpar name given a lpar_id and a managed system name */
+static char *
+phypGetLparNAME(SSH_SESSION * ssh_session, const char *managed_system,
+                unsigned int lpar_id, int *exit_status)
+{
+    virBuffer cmd = VIR_BUFFER_INITIALIZER;
+
+    virBufferVSprintf(&cmd,
+                      "lssyscfg -r lpar -m %s --filter lpar_ids=%d -F name",
+                      managed_system, lpar_id);
+    const char *lpar_name =
+        __inner_exec_command(ssh_session, virBufferContentAndReset(&cmd),
+                             (int *) exit_status);
+    char *striped_lpar_name = (char *) malloc(sizeof(lpar_name) - 1);
+
+    stripNewline(striped_lpar_name, lpar_name);
+
+    virBufferContentAndReset(&cmd);
+    if ((*exit_status) < 0 || lpar_name == NULL) {
+        return NULL;
+    }
+
+    return striped_lpar_name;
+}
+
+/* return the lpar_uuid (which for now is its logical serial number) 
+ * given a lpar id and a managed system name */
+static unsigned char *
+phypGetLparUUID(SSH_SESSION * ssh_session, const char *managed_system,
+                unsigned int lpar_id, int *exit_status)
+{
+    virBuffer cmd = VIR_BUFFER_INITIALIZER;
+
+    virBufferVSprintf(&cmd,
+                      "lssyscfg -r lpar -m %s --filter lpar_ids=%d -F logical_serial_num",
+                      managed_system, lpar_id);
+    unsigned char *lpar_uuid =
+        (unsigned char *) __inner_exec_command(ssh_session,
+                                               virBufferContentAndReset
+                                               (&cmd),
+                                               (int *) exit_status);
+    unsigned char *striped_lpar_uuid =
+        (unsigned char *) malloc(sizeof(lpar_uuid) - 1);
+    stripNewline((char *) striped_lpar_uuid, (char *) lpar_uuid);
+
+    virBufferContentAndReset(&cmd);
+    if ((*exit_status) < 0 || lpar_uuid == NULL) {
+        return NULL;
+    }
+
+    return striped_lpar_uuid;
+    return lpar_uuid;
+}
+
+static int
+phypNumDomains(virConnectPtr conn)
+{
+    int exit_status = 0;
+    char managed_system[strlen(conn->uri->path) - 1];
+    SSH_SESSION *ssh_session = conn->privateData;
+    virBuffer cmd = VIR_BUFFER_INITIALIZER;
+
+    stripPath((char *) &managed_system, conn->uri->path);
+    virBufferVSprintf(&cmd,
+                      "lssyscfg -r lpar -m %s -F lpar_id|grep -c ^[0-9]*",
+                      managed_system);
+    const char *ndom =
+        __inner_exec_command(ssh_session, virBufferContentAndReset(&cmd),
+                             &exit_status);
+
+    virBufferContentAndReset(&cmd);
+    if(exit_status < 0 || ndom == NULL)
+        return 0;
+
+    return atoi(ndom);
+}
+
+static int
+phypListDomains(virConnectPtr conn, int *ids, int nids)
+{
+    int exit_status = 0;
+    int got = 0;
+    unsigned int i = 0, j = 0;
+    char id_c[10];
+    char managed_system[strlen(conn->uri->path) - 1];
+    SSH_SESSION *ssh_session = conn->privateData;
+
+    stripPath((char *) &managed_system, conn->uri->path);
+    virBuffer cmd = VIR_BUFFER_INITIALIZER;
+
+    memset(id_c, 0, 10);
+
+    virBufferVSprintf(&cmd, "lssyscfg -r lpar -m %s -F lpar_id",
+                      managed_system);
+    char *domains =
+        __inner_exec_command(ssh_session, virBufferContentAndReset(&cmd),
+                             &exit_status);
+
+		/* I need to parse the textual return in order to get the domains */
+    if (exit_status < 0 || domains == NULL)
+        return 0;
+    else {
+        while (got < nids) {
+            if (domains[i] == '\n') {
+                ids[got] = atoi(id_c);
+                memset(id_c, 0, 10);
+                j = 0;
+                got++;
+            } else {
+                id_c[j] = domains[i];
+                j++;
+            }
+            i++;
+        }
+    }
+
+    virBufferContentAndReset(&cmd);
+    return got;
+}
+
+static virDomainPtr
+phypDomainLookupByName(virConnectPtr conn, const char *name)
+{
+    SSH_SESSION *ssh_session = conn->privateData;
+    virDomainPtr dom = NULL;
+
+    int lpar_id = 0;
+    int exit_status = 0;
+    char managed_system[strlen(conn->uri->path) - 1];
+
+    stripPath((char *) &managed_system, conn->uri->path);
+
+    lpar_id = phypGetLparID(ssh_session, managed_system, name);
+    if (lpar_id == PHYP_NO_MEM)
+        return NULL;
+
+    unsigned char *lpar_uuid =
+        phypGetLparUUID(ssh_session, managed_system, lpar_id,
+                        &exit_status);
+
+    if (exit_status == PHYP_NO_MEM || lpar_uuid == NULL)
+        return NULL;
+
+    dom = virGetDomain(conn, name, lpar_uuid);
+
+    if (dom)
+        dom->id = lpar_id;
+
+    VIR_FREE(lpar_uuid);
+    return dom;
+}
+
+static virDomainPtr
+phypDomainLookupByID(virConnectPtr conn, int lpar_id)
+{
+    SSH_SESSION *ssh_session = conn->privateData;
+    virDomainPtr dom = NULL;
+    int exit_status = 0;
+    char managed_system[strlen(conn->uri->path) - 1];
+
+    stripPath((char *) &managed_system, conn->uri->path);
+
+    char *lpar_name = phypGetLparNAME(ssh_session, managed_system, lpar_id,
+                                      &exit_status);
+
+    if (exit_status == PHYP_NO_MEM)
+        return NULL;
+
+    unsigned char *lpar_uuid =
+        phypGetLparUUID(ssh_session, managed_system, lpar_id,
+                        &exit_status);
+
+    if (exit_status == PHYP_NO_MEM)
+        return NULL;
+
+    dom = virGetDomain(conn, lpar_name, lpar_uuid);
+
+    if (dom)
+        dom->id = lpar_id;
+
+    VIR_FREE(lpar_name);
+    VIR_FREE(lpar_uuid);
+    return dom;
+}
+
+static virDriver phypDriver = {
+    VIR_DRV_PHYP,
+    "PHYP",
+    phypOpen,                   /* open */
+    phypClose,                  /* close */
+    NULL,                       /* supports_feature */
+    NULL,                       /* type */
+    NULL,                       /* version */
+    NULL,                       /* getHostname */
+    NULL,                       /* getMaxVcpus */
+    NULL,                       /* nodeGetInfo */
+    NULL,                       /* getCapabilities */
+    phypListDomains,            /* listDomains */
+    phypNumDomains,             /* numOfDomains */
+    NULL,                       /* domainCreateXML */
+    phypDomainLookupByID,       /* domainLookupByID */
+    NULL,                       /* domainLookupByUUID */
+    phypDomainLookupByName,     /* domainLookupByName */
+    NULL,                       /* domainSuspend */
+    NULL,                       /* domainResume */
+    NULL,                       /* domainShutdown */
+    NULL,                       /* domainReboot */
+    NULL,                       /* domainDestroy */
+    NULL,                       /* domainGetOSType */
+    NULL,                       /* domainGetMaxMemory */
+    NULL,                       /* domainSetMaxMemory */
+    NULL,                       /* domainSetMemory */
+    NULL,                       /* domainGetInfo */
+    NULL,                       /* domainSave */
+    NULL,                       /* domainRestore */
+    NULL,                       /* domainCoreDump */
+    NULL,                       /* domainSetVcpus */
+    NULL,                       /* domainPinVcpu */
+    NULL,                       /* domainGetVcpus */
+    NULL,                       /* domainGetMaxVcpus */
+    NULL,                       /* domainGetSecurityLabel */
+    NULL,                       /* nodeGetSecurityModel */
+    NULL,                       /* domainDumpXML */
+    NULL,                       /* listDefinedDomains */
+    NULL,                       /* numOfDefinedDomains */
+    NULL,                       /* domainCreate */
+    NULL,                       /* domainDefineXML */
+    NULL,                       /* domainUndefine */
+    NULL,                       /* domainAttachDevice */
+    NULL,                       /* domainDetachDevice */
+    NULL,                       /* domainGetAutostart */
+    NULL,                       /* domainSetAutostart */
+    NULL,                       /* domainGetSchedulerType */
+    NULL,                       /* domainGetSchedulerParameters */
+    NULL,                       /* domainSetSchedulerParameters */
+    NULL,                       /* domainMigratePrepare */
+    NULL,                       /* domainMigratePerform */
+    NULL,                       /* domainMigrateFinish */
+    NULL,                       /* domainBlockStats */
+    NULL,                       /* domainInterfaceStats */
+    NULL,                       /* domainBlockPeek */
+    NULL,                       /* domainMemoryPeek */
+    NULL,                       /* nodeGetCellsFreeMemory */
+    NULL,                       /* getFreeMemory */
+    NULL,                       /* domainEventRegister */
+    NULL,                       /* domainEventDeregister */
+    NULL,                       /* domainMigratePrepare2 */
+    NULL,                       /* domainMigrateFinish2 */
+    NULL,                       /* nodeDeviceDettach */
+    NULL,                       /* nodeDeviceReAttach */
+    NULL,                       /* nodeDeviceReset */
+};
+
+int
+phypRegister(void)
+{
+    virRegisterDriver(&phypDriver);
+    return 0;
+}
+
+/* function that helps me to strip out the first slash from the 
+ * uri: phyp://user@hmc/path
+ *
+ * '/path' becomes 'path'
+ * */
+void
+stripPath(char *striped_path, char *path)
+{
+    unsigned int i = 0;
+    for (i = 1; i <= strlen(path); i++)
+        striped_path[i - 1] = path[i];
+    striped_path[i] = '\0';
+    return;
+}
+
+/* function to strip out the '\n' of the end of some string */
+void
+stripNewline(char *striped_string, char *string)
+{
+    unsigned int i = 0;
+    for (i = 0; i <= strlen(string); i++)
+        if (string[i] != '\n')
+            striped_string[i] = string[i];
+    striped_string[strlen(string)-1] = '\0';
+    return;
+}
diff --git a/src/phyp_driver.h b/src/phyp_driver.h
new file mode 100644
index 0000000..c2d9c9b
--- /dev/null
+++ b/src/phyp_driver.h
@@ -0,0 +1,21 @@
+#include <config.h>
+#include <libssh/libssh.h>
+
+#define MAXSIZE 65536
+#define LPAR_EXEC_ERR -1
+#define SSH_CONN_ERR -2
+#define SSH_AUTH_PUBKEY_ERR -3
+#define SSH_AUTH_ERR -4
+#define SSH_CHANNEL_OPEN_ERR -5
+#define SSH_CHANNEL_EXEC_ERR -6
+#define SSH_CHANNEL_SEND_EOF_ERR -7
+#define SSH_CHANNEL_CLOSE_ERR -8
+#define SSH_CHANNEL_READ_ERR -9
+#define PHYP_NO_MEM -10
+
+int phypRegister(void);
+
+void stripPath(char * striped_path, char * path);
+void stripNewline(char * striped_string, char * string);
+
+int buffer_add_u8(struct buffer_struct *buffer,u8 data);
diff --git a/src/virterror.c b/src/virterror.c
index 2d34ed7..82eb506 100644
--- a/src/virterror.c
+++ b/src/virterror.c
@@ -124,6 +124,9 @@ static const char *virErrorDomainName(virErrorDomain domain) {
         case VIR_FROM_CONF:
             dom = "Config ";
             break;
+        case VIR_FROM_PHYP:
+            dom = "IBM power hypervisor ";
+            break;
         case VIR_FROM_OPENVZ:
             dom = "OpenVZ ";
             break;
--
Libvir-list mailing list
Libvir-list@xxxxxxxxxx
https://www.redhat.com/mailman/listinfo/libvir-list

[Index of Archives]     [Virt Tools]     [Libvirt Users]     [Lib OS Info]     [Fedora Users]     [Fedora Desktop]     [Fedora SELinux]     [Big List of Linux Books]     [Yosemite News]     [KDE Users]     [Fedora Tools]