[Pkg-libvirt-commits] [SCM] Libguestfs Debian packaging branch, experimental, updated. debian/1%1.21.40-1

Richard W.M. Jones rjones at redhat.com
Sat Jun 1 11:04:43 UTC 2013


The following commit has been merged in the experimental branch:
commit 83f74f5c564c51a1324b12e5edc4b50356d49dc6
Author: Richard W.M. Jones <rjones at redhat.com>
Date:   Sat May 11 18:18:12 2013 +0100

    Add support for qemu's curl driver (ie. FTP, FTPS, HTTP, HTTPS, TFTP).

diff --git a/fish/guestfish.pod b/fish/guestfish.pod
index d32e747..f8b39fc 100644
--- a/fish/guestfish.pod
+++ b/fish/guestfish.pod
@@ -1117,6 +1117,22 @@ The possible I<-a URI> formats are described below.
 
 Add the local disk image (or device) called C<disk.img>.
 
+=head2 B<-a ftp://[user@]example.com[:port]/disk.img>
+
+=head2 B<-a ftps://[user@]example.com[:port]/disk.img>
+
+=head2 B<-a http://[user@]example.com[:port]/disk.img>
+
+=head2 B<-a https://[user@]example.com[:port]/disk.img>
+
+=head2 B<-a tftp://[user@]example.com[:port]/disk.img>
+
+Add a disk located on a remote FTP, HTTP or TFTP server.
+
+The equivalent API command would be:
+
+ ><fs> add /disk.img protocol:(ftp|...) server:tcp:example.com
+
 =head2 B<-a gluster://example.com[:port]/disk>
 
 Add a disk image located on GlusterFS storage.
diff --git a/generator/actions.ml b/generator/actions.ml
index f518ecd..277ca27 100644
--- a/generator/actions.ml
+++ b/generator/actions.ml
@@ -1334,6 +1334,13 @@ C<filename> is interpreted as a local file or device.
 This is the default if the optional protocol parameter
 is omitted.
 
+=item C<protocol = \"ftp\"|\"ftps\"|\"http\"|\"https\"|\"tftp\">
+
+Connect to a remote FTP, HTTP or TFTP server.
+The C<server> parameter must also be supplied - see below.
+
+See also: L<guestfs(3)/FTP, HTTP AND TFTP>
+
 =item C<protocol = \"gluster\">
 
 Connect to the GlusterFS server.
@@ -1390,6 +1397,7 @@ is a list of server(s).
  Protocol       Number of servers required
  --------       --------------------------
  file           List must be empty or param not used at all
+ ftp|ftps|http|https|tftp  Exactly one
  gluster        Exactly one
  iscsi          Exactly one
  nbd            Exactly one
@@ -1411,8 +1419,8 @@ for the protocol is used (see C</etc/services>).
 
 =item C<username>
 
-For the C<iscsi>, C<rbd>, C<ssh> protocols only, this specifies the
-remote username.
+For the C<ftp>, C<ftps>, C<http>, C<https>, C<iscsi>, C<rbd>, C<ssh>
+and C<tftp> protocols, this specifies the remote username.
 
 If not given, then the local username is used for C<ssh>, and no authentication
 is attempted for ceph.  But note this sometimes may give unexpected results, for
diff --git a/src/drives.c b/src/drives.c
index acfb0bb..d126054 100644
--- a/src/drives.c
+++ b/src/drives.c
@@ -138,6 +138,50 @@ create_drive_non_file (guestfs_h *g,
 }
 
 static struct drive *
+create_drive_curl (guestfs_h *g,
+                   enum drive_protocol protocol,
+                   struct drive_server *servers, size_t nr_servers,
+                   const char *exportname,
+                   const char *username, const char *secret,
+                   bool readonly, const char *format,
+                   const char *iface, const char *name,
+                   const char *disk_label,
+                   bool use_cache_none)
+{
+  if (secret != NULL) {
+    error (g, _("curl: you cannot specify a secret with this protocol"));
+    return NULL;
+  }
+
+  if (nr_servers != 1) {
+    error (g, _("curl: you must specify exactly one server"));
+    return NULL;
+  }
+
+  if (servers[0].transport != drive_transport_none &&
+      servers[0].transport != drive_transport_tcp) {
+    error (g, _("curl: only tcp transport is supported"));
+    return NULL;
+  }
+
+  if (STREQ (exportname, "")) {
+    error (g, _("curl: pathname should not be an empty string"));
+    return NULL;
+  }
+
+  if (exportname[0] != '/') {
+    error (g, _("curl: pathname must begin with a '/'"));
+    return NULL;
+  }
+
+  return create_drive_non_file (g, protocol,
+                                servers, nr_servers, exportname,
+                                username, secret,
+                                readonly, format, iface, name, disk_label,
+                                use_cache_none);
+}
+
+static struct drive *
 create_drive_gluster (guestfs_h *g,
                       struct drive_server *servers, size_t nr_servers,
                       const char *exportname,
@@ -871,12 +915,40 @@ guestfs__add_drive_opts (guestfs_h *g, const char *filename,
                                disk_label, use_cache_none);
     }
   }
+  else if (STREQ (protocol, "ftp")) {
+    drv = create_drive_curl (g, drive_protocol_ftp,
+                             servers, nr_servers, filename,
+                             username, secret,
+                             readonly, format, iface, name,
+                             disk_label, false);
+  }
+  else if (STREQ (protocol, "ftps")) {
+    drv = create_drive_curl (g, drive_protocol_ftps,
+                             servers, nr_servers, filename,
+                             username, secret,
+                             readonly, format, iface, name,
+                             disk_label, false);
+  }
   else if (STREQ (protocol, "gluster")) {
     drv = create_drive_gluster (g, servers, nr_servers, filename,
                                 username, secret,
                                 readonly, format, iface, name,
                                 disk_label, false);
   }
+  else if (STREQ (protocol, "http")) {
+    drv = create_drive_curl (g, drive_protocol_http,
+                             servers, nr_servers, filename,
+                             username, secret,
+                             readonly, format, iface, name,
+                             disk_label, false);
+  }
+  else if (STREQ (protocol, "https")) {
+    drv = create_drive_curl (g, drive_protocol_https,
+                             servers, nr_servers, filename,
+                             username, secret,
+                             readonly, format, iface, name,
+                             disk_label, false);
+  }
   else if (STREQ (protocol, "iscsi")) {
     drv = create_drive_iscsi (g, servers, nr_servers, filename,
                               username, secret,
@@ -907,6 +979,13 @@ guestfs__add_drive_opts (guestfs_h *g, const char *filename,
                             readonly, format, iface, name,
                             disk_label, false);
   }
+  else if (STREQ (protocol, "tftp")) {
+    drv = create_drive_curl (g, drive_protocol_tftp,
+                             servers, nr_servers, filename,
+                             username, secret,
+                             readonly, format, iface, name,
+                             disk_label, false);
+  }
   else {
     error (g, _("unknown protocol '%s'"), protocol);
     drv = NULL; /*FALLTHROUGH*/
@@ -1175,6 +1254,14 @@ guestfs___drive_source_qemu_param (guestfs_h *g, const struct drive_source *src)
     else
       return safe_asprintf (g, "./%s", src->u.path);
 
+  case drive_protocol_ftp:
+    return make_uri (g, "ftp", src->username,
+                     &src->servers[0], src->u.exportname);
+
+  case drive_protocol_ftps:
+    return make_uri (g, "ftps", src->username,
+                     &src->servers[0], src->u.exportname);
+
   case drive_protocol_gluster:
     switch (src->servers[0].transport) {
     case drive_transport_none:
@@ -1186,6 +1273,14 @@ guestfs___drive_source_qemu_param (guestfs_h *g, const struct drive_source *src)
       return make_uri (g, "gluster+unix", NULL, &src->servers[0], NULL);
     }
 
+  case drive_protocol_http:
+    return make_uri (g, "http", src->username,
+                     &src->servers[0], src->u.exportname);
+
+  case drive_protocol_https:
+    return make_uri (g, "https", src->username,
+                     &src->servers[0], src->u.exportname);
+
   case drive_protocol_iscsi:
     return make_uri (g, "iscsi", NULL, &src->servers[0], src->u.exportname);
 
@@ -1277,6 +1372,10 @@ guestfs___drive_source_qemu_param (guestfs_h *g, const struct drive_source *src)
   case drive_protocol_ssh:
     return make_uri (g, "ssh", src->username,
                      &src->servers[0], src->u.exportname);
+
+  case drive_protocol_tftp:
+    return make_uri (g, "tftp", src->username,
+                     &src->servers[0], src->u.exportname);
   }
 
   abort ();
diff --git a/src/guestfs-internal.h b/src/guestfs-internal.h
index c2681fb..6e97948 100644
--- a/src/guestfs-internal.h
+++ b/src/guestfs-internal.h
@@ -115,12 +115,17 @@ struct event {
 /* Drives added to the handle. */
 enum drive_protocol {
   drive_protocol_file,
+  drive_protocol_ftp,
+  drive_protocol_ftps,
   drive_protocol_gluster,
+  drive_protocol_http,
+  drive_protocol_https,
   drive_protocol_iscsi,
   drive_protocol_nbd,
   drive_protocol_rbd,
   drive_protocol_sheepdog,
   drive_protocol_ssh,
+  drive_protocol_tftp,
 };
 
 enum drive_transport {
diff --git a/src/guestfs.pod b/src/guestfs.pod
index 1477015..381f0f7 100644
--- a/src/guestfs.pod
+++ b/src/guestfs.pod
@@ -661,6 +661,29 @@ servers.  The server string is documented in
 L</guestfs_add_drive_opts>. The C<username> and C<secret> parameters are
 also optional, and if not given, then no authentication will be used.
 
+=head3 FTP, HTTP AND TFTP
+
+Libguestfs can access remote disks over FTP, FTPS, HTTP, HTTPS
+or TFTP protocols.
+
+To do this, set the optional C<protocol> and C<server> parameters of
+L</guestfs_add_drive_opts> like this:
+
+ char **servers = { "www.example.org", NULL };
+ guestfs_add_drive_opts (g, "/disk.img",
+                         GUESTFS_ADD_DRIVE_OPTS_FORMAT, "raw",
+                         GUESTFS_ADD_DRIVE_OPTS_PROTOCOL, "http",
+                         GUESTFS_ADD_DRIVE_OPTS_SERVER, servers,
+                         -1);
+
+The C<protocol> can be one of C<"ftp">, C<"ftps">, C<"http">,
+C<"https"> or C<"tftp">.
+
+C<servers> (the C<server> parameter) is a list which must have a
+single element.  The single element is a string defining the Gluster
+server.  The format of this string is documented in
+L</guestfs_add_drive_opts>.
+
 =head3 GLUSTER
 
 Libguestfs can access Gluster disks.
diff --git a/src/launch-libvirt.c b/src/launch-libvirt.c
index d667e98..4588602 100644
--- a/src/launch-libvirt.c
+++ b/src/launch-libvirt.c
@@ -1151,6 +1151,18 @@ construct_libvirt_xml_disk (guestfs_h *g,
        */
       XMLERROR (-1, xmlTextWriterEndElement (xo));
     }
+    break;
+
+    /* libvirt doesn't support the qemu curl driver yet.  Give a
+     * reasonable error message instead of trying and failing.
+     */
+  case drive_protocol_ftp:
+  case drive_protocol_ftps:
+  case drive_protocol_http:
+  case drive_protocol_https:
+  case drive_protocol_tftp:
+    error (g, _("libvirt does not support the qemu curl driver protocols (ftp, http, etc.); try setting LIBGUESTFS_BACKEND=direct"));
+    return -1;
   }
 
   XMLERROR (-1, xmlTextWriterStartElement (xo, BAD_CAST "target"));
@@ -1599,12 +1611,17 @@ make_drive_priv (guestfs_h *g, struct drive *drv,
     }
     break;
 
+  case drive_protocol_ftp:
+  case drive_protocol_ftps:
   case drive_protocol_gluster:
+  case drive_protocol_http:
+  case drive_protocol_https:
   case drive_protocol_iscsi:
   case drive_protocol_nbd:
   case drive_protocol_rbd:
   case drive_protocol_sheepdog:
   case drive_protocol_ssh:
+  case drive_protocol_tftp:
     if (!drv->readonly) {
       guestfs___copy_drive_source (g, &drv->src, &drv_priv->real_src);
       drv_priv->format = drv->format ? safe_strdup (g, drv->format) : NULL;
@@ -1621,6 +1638,7 @@ make_drive_priv (guestfs_h *g, struct drive *drv,
         return -1;
       drv_priv->format = safe_strdup (g, "qcow2");
     }
+    break;
   }
 
   return 0;

-- 
Libguestfs Debian packaging



More information about the Pkg-libvirt-commits mailing list