Don't stash strings in the handle.
[libguestfs.git] / fish / cmds.c
index 5270912..1e442d8 100644 (file)
@@ -57,17 +57,32 @@ void list_commands (void)
   printf ("%-20s %s\n", "blockdev-setro", "set block device to read-only");
   printf ("%-20s %s\n", "blockdev-setrw", "set block device to read-write");
   printf ("%-20s %s\n", "cat", "list the contents of a file");
+  printf ("%-20s %s\n", "checksum", "compute MD5, SHAx or CRC checksum of file");
   printf ("%-20s %s\n", "chmod", "change file mode");
   printf ("%-20s %s\n", "chown", "change file owner and group");
   printf ("%-20s %s\n", "command", "run a command from the guest filesystem");
   printf ("%-20s %s\n", "command-lines", "run a command, returning lines");
   printf ("%-20s %s\n", "config", "add qemu parameters");
+  printf ("%-20s %s\n", "cp", "copy a file");
+  printf ("%-20s %s\n", "cp-a", "copy a file or directory recursively");
+  printf ("%-20s %s\n", "debug", "debugging and internals");
+  printf ("%-20s %s\n", "dmesg", "return kernel messages");
+  printf ("%-20s %s\n", "download", "download a file to the local machine");
+  printf ("%-20s %s\n", "drop-caches", "drop kernel page cache, dentries and inodes");
+  printf ("%-20s %s\n", "equal", "test if two files have equal contents");
   printf ("%-20s %s\n", "exists", "test if file or directory exists");
   printf ("%-20s %s\n", "file", "determine file type");
+  printf ("%-20s %s\n", "fsck", "run the filesystem checker");
+  printf ("%-20s %s\n", "get-append", "get the additional kernel options");
   printf ("%-20s %s\n", "get-autosync", "get autosync mode");
+  printf ("%-20s %s\n", "get-e2label", "get the ext2/3/4 filesystem label");
+  printf ("%-20s %s\n", "get-e2uuid", "get the ext2/3/4 filesystem UUID");
   printf ("%-20s %s\n", "get-path", "get the search path");
+  printf ("%-20s %s\n", "get-qemu", "get the qemu binary");
   printf ("%-20s %s\n", "get-state", "get the current state");
   printf ("%-20s %s\n", "get-verbose", "get verbose mode");
+  printf ("%-20s %s\n", "grub-install", "install GRUB");
+  printf ("%-20s %s\n", "hexdump", "dump a file in hexadecimal");
   printf ("%-20s %s\n", "is-busy", "is busy processing a command");
   printf ("%-20s %s\n", "is-config", "is in configuration state");
   printf ("%-20s %s\n", "is-dir", "test if file exists");
@@ -83,35 +98,55 @@ void list_commands (void)
   printf ("%-20s %s\n", "lstat", "get file information for a symbolic link");
   printf ("%-20s %s\n", "lvcreate", "create an LVM volume group");
   printf ("%-20s %s\n", "lvm-remove-all", "remove all LVM LVs, VGs and PVs");
+  printf ("%-20s %s\n", "lvremove", "remove an LVM logical volume");
   printf ("%-20s %s\n", "lvs", "list the LVM logical volumes (LVs)");
   printf ("%-20s %s\n", "lvs-full", "list the LVM logical volumes (LVs)");
   printf ("%-20s %s\n", "mkdir", "create a directory");
   printf ("%-20s %s\n", "mkdir-p", "create a directory and parents");
   printf ("%-20s %s\n", "mkfs", "make a filesystem");
   printf ("%-20s %s\n", "mount", "mount a guest disk at a position in the filesystem");
+  printf ("%-20s %s\n", "mount-options", "mount a guest disk with mount options");
+  printf ("%-20s %s\n", "mount-ro", "mount a guest disk, read-only");
+  printf ("%-20s %s\n", "mount-vfs", "mount a guest disk with mount options and vfstype");
   printf ("%-20s %s\n", "mounts", "show mounted filesystems");
+  printf ("%-20s %s\n", "mv", "move a file");
+  printf ("%-20s %s\n", "ping-daemon", "ping the guest daemon");
   printf ("%-20s %s\n", "pvcreate", "create an LVM physical volume");
+  printf ("%-20s %s\n", "pvremove", "remove an LVM physical volume");
   printf ("%-20s %s\n", "pvs", "list the LVM physical volumes (PVs)");
   printf ("%-20s %s\n", "pvs-full", "list the LVM physical volumes (PVs)");
   printf ("%-20s %s\n", "read-lines", "read file as lines");
   printf ("%-20s %s\n", "rm", "remove a file");
   printf ("%-20s %s\n", "rm-rf", "remove a file or directory recursively");
   printf ("%-20s %s\n", "rmdir", "remove a directory");
+  printf ("%-20s %s\n", "set-append", "add options to kernel command line");
   printf ("%-20s %s\n", "set-autosync", "set autosync mode");
+  printf ("%-20s %s\n", "set-e2label", "set the ext2/3/4 filesystem label");
+  printf ("%-20s %s\n", "set-e2uuid", "set the ext2/3/4 filesystem UUID");
   printf ("%-20s %s\n", "set-path", "set the search path");
+  printf ("%-20s %s\n", "set-qemu", "set the qemu binary");
   printf ("%-20s %s\n", "set-verbose", "set verbose mode");
   printf ("%-20s %s\n", "sfdisk", "create partitions on a block device");
   printf ("%-20s %s\n", "stat", "get file information");
   printf ("%-20s %s\n", "statvfs", "get file system statistics");
+  printf ("%-20s %s\n", "strings", "print the printable strings in a file");
+  printf ("%-20s %s\n", "strings-e", "print the printable strings in a file");
   printf ("%-20s %s\n", "sync", "sync disks, writes are flushed through to the disk image");
+  printf ("%-20s %s\n", "tar-in", "unpack tarfile to directory");
+  printf ("%-20s %s\n", "tar-out", "pack directory into tarfile");
+  printf ("%-20s %s\n", "tgz-in", "unpack compressed tarball to directory");
+  printf ("%-20s %s\n", "tgz-out", "pack directory into compressed tarball");
   printf ("%-20s %s\n", "touch", "update file timestamps or create a new file");
-  printf ("%-20s %s\n", "tune2fs-l", "get ext2/ext3 superblock details");
+  printf ("%-20s %s\n", "tune2fs-l", "get ext2/ext3/ext4 superblock details");
   printf ("%-20s %s\n", "umount", "unmount a filesystem");
   printf ("%-20s %s\n", "umount-all", "unmount all filesystems");
+  printf ("%-20s %s\n", "upload", "upload a file from the local machine");
   printf ("%-20s %s\n", "vgcreate", "create an LVM volume group");
+  printf ("%-20s %s\n", "vgremove", "remove an LVM volume group");
   printf ("%-20s %s\n", "vgs", "list the LVM volume groups (VGs)");
   printf ("%-20s %s\n", "vgs-full", "list the LVM volume groups (VGs)");
   printf ("%-20s %s\n", "write-file", "create a file");
+  printf ("%-20s %s\n", "zero", "write zeroes to the device");
   printf ("    Use -h <cmd> / help <cmd> to show detailed help for a command.\n");
 }
 
@@ -132,14 +167,26 @@ void display_command (const char *cmd)
   if (strcasecmp (cmd, "config") == 0)
     pod2text ("config - add qemu parameters", " config <qemuparam> <qemuvalue>\n\nThis can be used to add arbitrary qemu command line parameters\nof the form C<-param value>.  Actually it's not quite arbitrary - we\nprevent you from setting some parameters which would interfere with\nparameters that we use.\n\nThe first character of C<param> string must be a C<-> (dash).\n\nC<value> can be NULL.");
   else
+  if (strcasecmp (cmd, "set_qemu") == 0 || strcasecmp (cmd, "set-qemu") == 0 || strcasecmp (cmd, "qemu") == 0)
+    pod2text ("set-qemu - set the qemu binary", " set-qemu <qemu>\n\nSet the qemu binary that we will use.\n\nThe default is chosen when the library was compiled by the\nconfigure script.\n\nYou can also override this by setting the C<LIBGUESTFS_QEMU>\nenvironment variable.\n\nSetting C<qemu> to C<NULL> restores the default qemu binary.\n\nYou can use 'qemu' as an alias for this command.");
+  else
+  if (strcasecmp (cmd, "get_qemu") == 0 || strcasecmp (cmd, "get-qemu") == 0)
+    pod2text ("get-qemu - get the qemu binary", " get-qemu\n\nReturn the current qemu binary.\n\nThis is always non-NULL.  If it wasn't set already, then this will\nreturn the default qemu binary name.");
+  else
   if (strcasecmp (cmd, "set_path") == 0 || strcasecmp (cmd, "set-path") == 0 || strcasecmp (cmd, "path") == 0)
-    pod2text ("set-path - set the search path", " set-path <path>\n\nSet the path that libguestfs searches for kernel and initrd.img.\n\nThe default is C<$libdir/guestfs> unless overridden by setting\nC<LIBGUESTFS_PATH> environment variable.\n\nThe string C<path> is stashed in the libguestfs handle, so the caller\nmust make sure it remains valid for the lifetime of the handle.\n\nSetting C<path> to C<NULL> restores the default path.\n\nYou can use 'path' as an alias for this command.");
+    pod2text ("set-path - set the search path", " set-path <path>\n\nSet the path that libguestfs searches for kernel and initrd.img.\n\nThe default is C<$libdir/guestfs> unless overridden by setting\nC<LIBGUESTFS_PATH> environment variable.\n\nSetting C<path> to C<NULL> restores the default path.\n\nYou can use 'path' as an alias for this command.");
   else
   if (strcasecmp (cmd, "get_path") == 0 || strcasecmp (cmd, "get-path") == 0)
     pod2text ("get-path - get the search path", " get-path\n\nReturn the current search path.\n\nThis is always non-NULL.  If it wasn't set already, then this will\nreturn the default path.");
   else
+  if (strcasecmp (cmd, "set_append") == 0 || strcasecmp (cmd, "set-append") == 0 || strcasecmp (cmd, "append") == 0)
+    pod2text ("set-append - add options to kernel command line", " set-append <append>\n\nThis function is used to add additional options to the\nguest kernel command line.\n\nThe default is C<NULL> unless overridden by setting\nC<LIBGUESTFS_APPEND> environment variable.\n\nSetting C<append> to C<NULL> means I<no> additional options\nare passed (libguestfs always adds a few of its own).\n\nYou can use 'append' as an alias for this command.");
+  else
+  if (strcasecmp (cmd, "get_append") == 0 || strcasecmp (cmd, "get-append") == 0)
+    pod2text ("get-append - get the additional kernel options", " get-append\n\nReturn the additional kernel options which are added to the\nguest kernel command line.\n\nIf C<NULL> then no options are added.");
+  else
   if (strcasecmp (cmd, "set_autosync") == 0 || strcasecmp (cmd, "set-autosync") == 0 || strcasecmp (cmd, "autosync") == 0)
-    pod2text ("set-autosync - set autosync mode", " set-autosync <autosync>\n\nIf C<autosync> is true, this enables autosync.  Libguestfs will make a\nbest effort attempt to run C<sync> when the handle is closed\n(also if the program exits without closing handles).\n\nYou can use 'autosync' as an alias for this command.");
+    pod2text ("set-autosync - set autosync mode", " set-autosync <autosync>\n\nIf C<autosync> is true, this enables autosync.  Libguestfs will make a\nbest effort attempt to run C<umount_all> followed by\nC<sync> when the handle is closed\n(also if the program exits without closing handles).\n\nThis is disabled by default (except in guestfish where it is\nenabled by default).\n\nYou can use 'autosync' as an alias for this command.");
   else
   if (strcasecmp (cmd, "get_autosync") == 0 || strcasecmp (cmd, "get-autosync") == 0)
     pod2text ("get-autosync - get autosync mode", " get-autosync\n\nGet the autosync flag.");
@@ -289,13 +336,13 @@ void display_command (const char *cmd)
     pod2text ("lvcreate - create an LVM volume group", " lvcreate <logvol> <volgroup> <mbytes>\n\nThis creates an LVM volume group called C<logvol>\non the volume group C<volgroup>, with C<size> megabytes.");
   else
   if (strcasecmp (cmd, "mkfs") == 0)
-    pod2text ("mkfs - make a filesystem", " mkfs <fstype> <device>\n\nThis creates a filesystem on C<device> (usually a partition\nof LVM logical volume).  The filesystem type is C<fstype>, for\nexample C<ext3>.");
+    pod2text ("mkfs - make a filesystem", " mkfs <fstype> <device>\n\nThis creates a filesystem on C<device> (usually a partition\nor LVM logical volume).  The filesystem type is C<fstype>, for\nexample C<ext3>.");
   else
   if (strcasecmp (cmd, "sfdisk") == 0)
     pod2text ("sfdisk - create partitions on a block device", " sfdisk <device> <cyls> <heads> <sectors> <lines>\n\nThis is a direct interface to the L<sfdisk(8)> program for creating\npartitions on block devices.\n\nC<device> should be a block device, for example C</dev/sda>.\n\nC<cyls>, C<heads> and C<sectors> are the number of cylinders, heads\nand sectors on the device, which are passed directly to sfdisk as\nthe I<-C>, I<-H> and I<-S> parameters.  If you pass C<0> for any\nof these, then the corresponding parameter is omitted.  Usually for\n'large' disks, you can just pass C<0> for these, but for small\n(floppy-sized) disks, sfdisk (or rather, the kernel) cannot work\nout the right geometry and you will need to tell it.\n\nC<lines> is a list of lines that we feed to C<sfdisk>.  For more\ninformation refer to the L<sfdisk(8)> manpage.\n\nTo create a single partition occupying the whole disk, you would\npass C<lines> as a single element list, when the single element being\nthe string C<,> (comma).\n\nB<This command is dangerous.  Without careful use you\ncan easily destroy all your data>.");
   else
   if (strcasecmp (cmd, "write_file") == 0 || strcasecmp (cmd, "write-file") == 0)
-    pod2text ("write-file - create a file", " write-file <path> <content> <size>\n\nThis call creates a file called C<path>.  The contents of the\nfile is the string C<content> (which can contain any 8 bit data),\nwith length C<size>.\n\nAs a special case, if C<size> is C<0>\nthen the length is calculated using C<strlen> (so in this case\nthe content cannot contain embedded ASCII NULs).\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
+    pod2text ("write-file - create a file", " write-file <path> <content> <size>\n\nThis call creates a file called C<path>.  The contents of the\nfile is the string C<content> (which can contain any 8 bit data),\nwith length C<size>.\n\nAs a special case, if C<size> is C<0>\nthen the length is calculated using C<strlen> (so in this case\nthe content cannot contain embedded ASCII NULs).\n\nI<NB.> Owing to a bug, writing content containing ASCII NUL\ncharacters does I<not> work, even if the length is specified.\nWe hope to resolve this bug in a future version.  In the meantime\nuse C<upload>.\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
   else
   if (strcasecmp (cmd, "umount") == 0 || strcasecmp (cmd, "unmount") == 0)
     pod2text ("umount - unmount a filesystem", " umount <pathordevice>\n\nThis unmounts the given filesystem.  The filesystem may be\nspecified either by its mountpoint (path) or the device which\ncontains the filesystem.\n\nYou can use 'unmount' as an alias for this command.");
@@ -313,10 +360,10 @@ void display_command (const char *cmd)
     pod2text ("file - determine file type", " file <path>\n\nThis call uses the standard L<file(1)> command to determine\nthe type or contents of the file.  This also works on devices,\nfor example to find out whether a partition contains a filesystem.\n\nThe exact command which runs is C<file -bsL path>.  Note in\nparticular that the filename is not prepended to the output\n(the C<-b> option).");
   else
   if (strcasecmp (cmd, "command") == 0)
-    pod2text ("command - run a command from the guest filesystem", " command <arguments>\n\nThis call runs a command from the guest filesystem.  The\nfilesystem must be mounted, and must contain a compatible\noperating system (ie. something Linux, with the same\nor compatible processor architecture).\n\nThe single parameter is an argv-style list of arguments.\nThe first element is the name of the program to run.\nSubsequent elements are parameters.  The list must be\nnon-empty (ie. must contain a program name).\n\nThe C<$PATH> environment variable will contain at least\nC</usr/bin> and C</bin>.  If you require a program from\nanother location, you should provide the full path in the\nfirst parameter.\n\nShared libraries and data files required by the program\nmust be available on filesystems which are mounted in the\ncorrect places.  It is the caller's responsibility to ensure\nall filesystems that are needed are mounted at the right\nlocations.");
+    pod2text ("command - run a command from the guest filesystem", " command <arguments>\n\nThis call runs a command from the guest filesystem.  The\nfilesystem must be mounted, and must contain a compatible\noperating system (ie. something Linux, with the same\nor compatible processor architecture).\n\nThe single parameter is an argv-style list of arguments.\nThe first element is the name of the program to run.\nSubsequent elements are parameters.  The list must be\nnon-empty (ie. must contain a program name).\n\nThe return value is anything printed to I<stdout> by\nthe command.\n\nIf the command returns a non-zero exit status, then\nthis function returns an error message.  The error message\nstring is the content of I<stderr> from the command.\n\nThe C<$PATH> environment variable will contain at least\nC</usr/bin> and C</bin>.  If you require a program from\nanother location, you should provide the full path in the\nfirst parameter.\n\nShared libraries and data files required by the program\nmust be available on filesystems which are mounted in the\ncorrect places.  It is the caller's responsibility to ensure\nall filesystems that are needed are mounted at the right\nlocations.\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
   else
   if (strcasecmp (cmd, "command_lines") == 0 || strcasecmp (cmd, "command-lines") == 0)
-    pod2text ("command-lines - run a command, returning lines", " command-lines <arguments>\n\nThis is the same as C<command>, but splits the\nresult into a list of lines.");
+    pod2text ("command-lines - run a command, returning lines", " command-lines <arguments>\n\nThis is the same as C<command>, but splits the\nresult into a list of lines.\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
   else
   if (strcasecmp (cmd, "stat") == 0)
     pod2text ("stat - get file information", " stat <path>\n\nReturns file information for the given C<path>.\n\nThis is the same as the C<stat(2)> system call.");
@@ -328,7 +375,7 @@ void display_command (const char *cmd)
     pod2text ("statvfs - get file system statistics", " statvfs <path>\n\nReturns file system statistics for any mounted file system.\nC<path> should be a file or directory in the mounted file system\n(typically it is the mount point itself, but it doesn't need to be).\n\nThis is the same as the C<statvfs(2)> system call.");
   else
   if (strcasecmp (cmd, "tune2fs_l") == 0 || strcasecmp (cmd, "tune2fs-l") == 0)
-    pod2text ("tune2fs-l - get ext2/ext3 superblock details", " tune2fs-l <device>\n\nThis returns the contents of the ext2 or ext3 filesystem superblock\non C<device>.\n\nIt is the same as running C<tune2fs -l device>.  See L<tune2fs(8)>\nmanpage for more details.  The list of fields returned isn't\nclearly defined, and depends on both the version of C<tune2fs>\nthat libguestfs was built against, and the filesystem itself.");
+    pod2text ("tune2fs-l - get ext2/ext3/ext4 superblock details", " tune2fs-l <device>\n\nThis returns the contents of the ext2, ext3 or ext4 filesystem\nsuperblock on C<device>.\n\nIt is the same as running C<tune2fs -l device>.  See L<tune2fs(8)>\nmanpage for more details.  The list of fields returned isn't\nclearly defined, and depends on both the version of C<tune2fs>\nthat libguestfs was built against, and the filesystem itself.");
   else
   if (strcasecmp (cmd, "blockdev_setro") == 0 || strcasecmp (cmd, "blockdev-setro") == 0)
     pod2text ("blockdev-setro - set block device to read-only", " blockdev-setro <device>\n\nSets the block device named C<device> to read-only.\n\nThis uses the L<blockdev(8)> command.");
@@ -360,6 +407,99 @@ void display_command (const char *cmd)
   if (strcasecmp (cmd, "blockdev_rereadpt") == 0 || strcasecmp (cmd, "blockdev-rereadpt") == 0)
     pod2text ("blockdev-rereadpt - reread partition table", " blockdev-rereadpt <device>\n\nReread the partition table on C<device>.\n\nThis uses the L<blockdev(8)> command.");
   else
+  if (strcasecmp (cmd, "upload") == 0)
+    pod2text ("upload - upload a file from the local machine", " upload <filename> <remotefilename>\n\nUpload local file C<filename> to C<remotefilename> on the\nfilesystem.\n\nC<filename> can also be a named pipe.\n\nSee also C<download>.");
+  else
+  if (strcasecmp (cmd, "download") == 0)
+    pod2text ("download - download a file to the local machine", " download <remotefilename> <filename>\n\nDownload file C<remotefilename> and save it as C<filename>\non the local machine.\n\nC<filename> can also be a named pipe.\n\nSee also C<upload>, C<cat>.");
+  else
+  if (strcasecmp (cmd, "checksum") == 0)
+    pod2text ("checksum - compute MD5, SHAx or CRC checksum of file", " checksum <csumtype> <path>\n\nThis call computes the MD5, SHAx or CRC checksum of the\nfile named C<path>.\n\nThe type of checksum to compute is given by the C<csumtype>\nparameter which must have one of the following values:\n\n=over 4\n\n=item C<crc>\n\nCompute the cyclic redundancy check (CRC) specified by POSIX\nfor the C<cksum> command.\n\n=item C<md5>\n\nCompute the MD5 hash (using the C<md5sum> program).\n\n=item C<sha1>\n\nCompute the SHA1 hash (using the C<sha1sum> program).\n\n=item C<sha224>\n\nCompute the SHA224 hash (using the C<sha224sum> program).\n\n=item C<sha256>\n\nCompute the SHA256 hash (using the C<sha256sum> program).\n\n=item C<sha384>\n\nCompute the SHA384 hash (using the C<sha384sum> program).\n\n=item C<sha512>\n\nCompute the SHA512 hash (using the C<sha512sum> program).\n\n=back\n\nThe checksum is returned as a printable string.");
+  else
+  if (strcasecmp (cmd, "tar_in") == 0 || strcasecmp (cmd, "tar-in") == 0)
+    pod2text ("tar-in - unpack tarfile to directory", " tar-in <tarfile> <directory>\n\nThis command uploads and unpacks local file C<tarfile> (an\nI<uncompressed> tar file) into C<directory>.\n\nTo upload a compressed tarball, use C<tgz_in>.");
+  else
+  if (strcasecmp (cmd, "tar_out") == 0 || strcasecmp (cmd, "tar-out") == 0)
+    pod2text ("tar-out - pack directory into tarfile", " tar-out <directory> <tarfile>\n\nThis command packs the contents of C<directory> and downloads\nit to local file C<tarfile>.\n\nTo download a compressed tarball, use C<tgz_out>.");
+  else
+  if (strcasecmp (cmd, "tgz_in") == 0 || strcasecmp (cmd, "tgz-in") == 0)
+    pod2text ("tgz-in - unpack compressed tarball to directory", " tgz-in <tarball> <directory>\n\nThis command uploads and unpacks local file C<tarball> (a\nI<gzip compressed> tar file) into C<directory>.\n\nTo upload an uncompressed tarball, use C<tar_in>.");
+  else
+  if (strcasecmp (cmd, "tgz_out") == 0 || strcasecmp (cmd, "tgz-out") == 0)
+    pod2text ("tgz-out - pack directory into compressed tarball", " tgz-out <directory> <tarball>\n\nThis command packs the contents of C<directory> and downloads\nit to local file C<tarball>.\n\nTo download an uncompressed tarball, use C<tar_out>.");
+  else
+  if (strcasecmp (cmd, "mount_ro") == 0 || strcasecmp (cmd, "mount-ro") == 0)
+    pod2text ("mount-ro - mount a guest disk, read-only", " mount-ro <device> <mountpoint>\n\nThis is the same as the C<mount> command, but it\nmounts the filesystem with the read-only (I<-o ro>) flag.");
+  else
+  if (strcasecmp (cmd, "mount_options") == 0 || strcasecmp (cmd, "mount-options") == 0)
+    pod2text ("mount-options - mount a guest disk with mount options", " mount-options <options> <device> <mountpoint>\n\nThis is the same as the C<mount> command, but it\nallows you to set the mount options as for the\nL<mount(8)> I<-o> flag.");
+  else
+  if (strcasecmp (cmd, "mount_vfs") == 0 || strcasecmp (cmd, "mount-vfs") == 0)
+    pod2text ("mount-vfs - mount a guest disk with mount options and vfstype", " mount-vfs <options> <vfstype> <device> <mountpoint>\n\nThis is the same as the C<mount> command, but it\nallows you to set both the mount options and the vfstype\nas for the L<mount(8)> I<-o> and I<-t> flags.");
+  else
+  if (strcasecmp (cmd, "debug") == 0)
+    pod2text ("debug - debugging and internals", " debug <subcmd> <extraargs>\n\nThe C<debug> command exposes some internals of\nC<guestfsd> (the guestfs daemon) that runs inside the\nqemu subprocess.\n\nThere is no comprehensive help for this command.  You have\nto look at the file C<daemon/debug.c> in the libguestfs source\nto find out what you can do.");
+  else
+  if (strcasecmp (cmd, "lvremove") == 0)
+    pod2text ("lvremove - remove an LVM logical volume", " lvremove <device>\n\nRemove an LVM logical volume C<device>, where C<device> is\nthe path to the LV, such as C</dev/VG/LV>.\n\nYou can also remove all LVs in a volume group by specifying\nthe VG name, C</dev/VG>.");
+  else
+  if (strcasecmp (cmd, "vgremove") == 0)
+    pod2text ("vgremove - remove an LVM volume group", " vgremove <vgname>\n\nRemove an LVM volume group C<vgname>, (for example C<VG>).\n\nThis also forcibly removes all logical volumes in the volume\ngroup (if any).");
+  else
+  if (strcasecmp (cmd, "pvremove") == 0)
+    pod2text ("pvremove - remove an LVM physical volume", " pvremove <device>\n\nThis wipes a physical volume C<device> so that LVM will no longer\nrecognise it.\n\nThe implementation uses the C<pvremove> command which refuses to\nwipe physical volumes that contain any volume groups, so you have\nto remove those first.");
+  else
+  if (strcasecmp (cmd, "set_e2label") == 0 || strcasecmp (cmd, "set-e2label") == 0)
+    pod2text ("set-e2label - set the ext2/3/4 filesystem label", " set-e2label <device> <label>\n\nThis sets the ext2/3/4 filesystem label of the filesystem on\nC<device> to C<label>.  Filesystem labels are limited to\n16 characters.\n\nYou can use either C<tune2fs_l> or C<get_e2label>\nto return the existing label on a filesystem.");
+  else
+  if (strcasecmp (cmd, "get_e2label") == 0 || strcasecmp (cmd, "get-e2label") == 0)
+    pod2text ("get-e2label - get the ext2/3/4 filesystem label", " get-e2label <device>\n\nThis returns the ext2/3/4 filesystem label of the filesystem on\nC<device>.");
+  else
+  if (strcasecmp (cmd, "set_e2uuid") == 0 || strcasecmp (cmd, "set-e2uuid") == 0)
+    pod2text ("set-e2uuid - set the ext2/3/4 filesystem UUID", " set-e2uuid <device> <uuid>\n\nThis sets the ext2/3/4 filesystem UUID of the filesystem on\nC<device> to C<uuid>.  The format of the UUID and alternatives\nsuch as C<clear>, C<random> and C<time> are described in the\nL<tune2fs(8)> manpage.\n\nYou can use either C<tune2fs_l> or C<get_e2uuid>\nto return the existing UUID of a filesystem.");
+  else
+  if (strcasecmp (cmd, "get_e2uuid") == 0 || strcasecmp (cmd, "get-e2uuid") == 0)
+    pod2text ("get-e2uuid - get the ext2/3/4 filesystem UUID", " get-e2uuid <device>\n\nThis returns the ext2/3/4 filesystem UUID of the filesystem on\nC<device>.");
+  else
+  if (strcasecmp (cmd, "fsck") == 0)
+    pod2text ("fsck - run the filesystem checker", " fsck <fstype> <device>\n\nThis runs the filesystem checker (fsck) on C<device> which\nshould have filesystem type C<fstype>.\n\nThe returned integer is the status.  See L<fsck(8)> for the\nlist of status codes from C<fsck>.\n\nNotes:\n\n=over 4\n\n=item *\n\nMultiple status codes can be summed together.\n\n=item *\n\nA non-zero return code can mean \"success\", for example if\nerrors have been corrected on the filesystem.\n\n=item *\n\nChecking or repairing NTFS volumes is not supported\n(by linux-ntfs).\n\n=back\n\nThis command is entirely equivalent to running C<fsck -a -t fstype device>.");
+  else
+  if (strcasecmp (cmd, "zero") == 0)
+    pod2text ("zero - write zeroes to the device", " zero <device>\n\nThis command writes zeroes over the first few blocks of C<device>.\n\nHow many blocks are zeroed isn't specified (but it's I<not> enough\nto securely wipe the device).  It should be sufficient to remove\nany partition tables, filesystem superblocks and so on.");
+  else
+  if (strcasecmp (cmd, "grub_install") == 0 || strcasecmp (cmd, "grub-install") == 0)
+    pod2text ("grub-install - install GRUB", " grub-install <root> <device>\n\nThis command installs GRUB (the Grand Unified Bootloader) on\nC<device>, with the root directory being C<root>.");
+  else
+  if (strcasecmp (cmd, "cp") == 0)
+    pod2text ("cp - copy a file", " cp <src> <dest>\n\nThis copies a file from C<src> to C<dest> where C<dest> is\neither a destination filename or destination directory.");
+  else
+  if (strcasecmp (cmd, "cp_a") == 0 || strcasecmp (cmd, "cp-a") == 0)
+    pod2text ("cp-a - copy a file or directory recursively", " cp-a <src> <dest>\n\nThis copies a file or directory from C<src> to C<dest>\nrecursively using the C<cp -a> command.");
+  else
+  if (strcasecmp (cmd, "mv") == 0)
+    pod2text ("mv - move a file", " mv <src> <dest>\n\nThis moves a file from C<src> to C<dest> where C<dest> is\neither a destination filename or destination directory.");
+  else
+  if (strcasecmp (cmd, "drop_caches") == 0 || strcasecmp (cmd, "drop-caches") == 0)
+    pod2text ("drop-caches - drop kernel page cache, dentries and inodes", " drop-caches <whattodrop>\n\nThis instructs the guest kernel to drop its page cache,\nand/or dentries and inode caches.  The parameter C<whattodrop>\ntells the kernel what precisely to drop, see\nL<http://linux-mm.org/Drop_Caches>\n\nSetting C<whattodrop> to 3 should drop everything.\n\nThis automatically calls L<sync(2)> before the operation,\nso that the maximum guest memory is freed.");
+  else
+  if (strcasecmp (cmd, "dmesg") == 0)
+    pod2text ("dmesg - return kernel messages", " dmesg\n\nThis returns the kernel messages (C<dmesg> output) from\nthe guest kernel.  This is sometimes useful for extended\ndebugging of problems.\n\nAnother way to get the same information is to enable\nverbose messages with C<set_verbose> or by setting\nthe environment variable C<LIBGUESTFS_DEBUG=1> before\nrunning the program.");
+  else
+  if (strcasecmp (cmd, "ping_daemon") == 0 || strcasecmp (cmd, "ping-daemon") == 0)
+    pod2text ("ping-daemon - ping the guest daemon", " ping-daemon\n\nThis is a test probe into the guestfs daemon running inside\nthe qemu subprocess.  Calling this function checks that the\ndaemon responds to the ping message, without affecting the daemon\nor attached block device(s) in any other way.");
+  else
+  if (strcasecmp (cmd, "equal") == 0)
+    pod2text ("equal - test if two files have equal contents", " equal <file1> <file2>\n\nThis compares the two files C<file1> and C<file2> and returns\ntrue if their content is exactly equal, or false otherwise.\n\nThe external L<cmp(1)> program is used for the comparison.");
+  else
+  if (strcasecmp (cmd, "strings") == 0)
+    pod2text ("strings - print the printable strings in a file", " strings <path>\n\nThis runs the L<strings(1)> command on a file and returns\nthe list of printable strings found.\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
+  else
+  if (strcasecmp (cmd, "strings_e") == 0 || strcasecmp (cmd, "strings-e") == 0)
+    pod2text ("strings-e - print the printable strings in a file", " strings-e <encoding> <path>\n\nThis is like the C<strings> command, but allows you to\nspecify the encoding.\n\nSee the L<strings(1)> manpage for the full list of encodings.\n\nCommonly useful encodings are C<l> (lower case L) which will\nshow strings inside Windows/x86 files.\n\nThe returned strings are transcoded to UTF-8.\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
+  else
+  if (strcasecmp (cmd, "hexdump") == 0)
+    pod2text ("hexdump - dump a file in hexadecimal", " hexdump <path>\n\nThis runs C<hexdump -C> on the given C<path>.  The result is\nthe human-readable, canonical hex dump of the file.\n\nBecause of the message protocol, there is a transfer limit \nof somewhere between 2MB and 4MB.  To transfer large files you should use\nFTP.");
+  else
     display_builtin_command (cmd);
 }
 
@@ -565,6 +705,34 @@ static int run_config (const char *cmd, int argc, char *argv[])
   return r;
 }
 
+static int run_set_qemu (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *qemu;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  qemu = argv[0];
+  r = guestfs_set_qemu (g, qemu);
+  return r;
+}
+
+static int run_get_qemu (const char *cmd, int argc, char *argv[])
+{
+  const char *r;
+  if (argc != 0) {
+    fprintf (stderr, "%s should have 0 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  r = guestfs_get_qemu (g);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  return 0;
+}
+
 static int run_set_path (const char *cmd, int argc, char *argv[])
 {
   int r;
@@ -593,6 +761,34 @@ static int run_get_path (const char *cmd, int argc, char *argv[])
   return 0;
 }
 
+static int run_set_append (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *append;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  append = argv[0];
+  r = guestfs_set_append (g, append);
+  return r;
+}
+
+static int run_get_append (const char *cmd, int argc, char *argv[])
+{
+  const char *r;
+  if (argc != 0) {
+    fprintf (stderr, "%s should have 0 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  r = guestfs_get_append (g);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  return 0;
+}
+
 static int run_set_autosync (const char *cmd, int argc, char *argv[])
 {
   int r;
@@ -1738,6 +1934,510 @@ static int run_blockdev_rereadpt (const char *cmd, int argc, char *argv[])
   return r;
 }
 
+static int run_upload (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *filename;
+  const char *remotefilename;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  filename = strcmp (argv[0], "-") != 0 ? argv[0] : "/dev/stdin";
+  remotefilename = argv[1];
+  r = guestfs_upload (g, filename, remotefilename);
+  return r;
+}
+
+static int run_download (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *remotefilename;
+  const char *filename;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  remotefilename = argv[0];
+  filename = strcmp (argv[1], "-") != 0 ? argv[1] : "/dev/stdout";
+  r = guestfs_download (g, remotefilename, filename);
+  return r;
+}
+
+static int run_checksum (const char *cmd, int argc, char *argv[])
+{
+  char *r;
+  const char *csumtype;
+  const char *path;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  csumtype = argv[0];
+  path = argv[1];
+  r = guestfs_checksum (g, csumtype, path);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  free (r);
+  return 0;
+}
+
+static int run_tar_in (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *tarfile;
+  const char *directory;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  tarfile = strcmp (argv[0], "-") != 0 ? argv[0] : "/dev/stdin";
+  directory = argv[1];
+  r = guestfs_tar_in (g, tarfile, directory);
+  return r;
+}
+
+static int run_tar_out (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *directory;
+  const char *tarfile;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  directory = argv[0];
+  tarfile = strcmp (argv[1], "-") != 0 ? argv[1] : "/dev/stdout";
+  r = guestfs_tar_out (g, directory, tarfile);
+  return r;
+}
+
+static int run_tgz_in (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *tarball;
+  const char *directory;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  tarball = strcmp (argv[0], "-") != 0 ? argv[0] : "/dev/stdin";
+  directory = argv[1];
+  r = guestfs_tgz_in (g, tarball, directory);
+  return r;
+}
+
+static int run_tgz_out (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *directory;
+  const char *tarball;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  directory = argv[0];
+  tarball = strcmp (argv[1], "-") != 0 ? argv[1] : "/dev/stdout";
+  r = guestfs_tgz_out (g, directory, tarball);
+  return r;
+}
+
+static int run_mount_ro (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *device;
+  const char *mountpoint;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  mountpoint = argv[1];
+  r = guestfs_mount_ro (g, device, mountpoint);
+  return r;
+}
+
+static int run_mount_options (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *options;
+  const char *device;
+  const char *mountpoint;
+  if (argc != 3) {
+    fprintf (stderr, "%s should have 3 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  options = argv[0];
+  device = argv[1];
+  mountpoint = argv[2];
+  r = guestfs_mount_options (g, options, device, mountpoint);
+  return r;
+}
+
+static int run_mount_vfs (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *options;
+  const char *vfstype;
+  const char *device;
+  const char *mountpoint;
+  if (argc != 4) {
+    fprintf (stderr, "%s should have 4 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  options = argv[0];
+  vfstype = argv[1];
+  device = argv[2];
+  mountpoint = argv[3];
+  r = guestfs_mount_vfs (g, options, vfstype, device, mountpoint);
+  return r;
+}
+
+static int run_debug (const char *cmd, int argc, char *argv[])
+{
+  char *r;
+  const char *subcmd;
+  char **extraargs;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  subcmd = argv[0];
+  extraargs = parse_string_list (argv[1]);
+  r = guestfs_debug (g, subcmd, extraargs);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  free (r);
+  return 0;
+}
+
+static int run_lvremove (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *device;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  r = guestfs_lvremove (g, device);
+  return r;
+}
+
+static int run_vgremove (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *vgname;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  vgname = argv[0];
+  r = guestfs_vgremove (g, vgname);
+  return r;
+}
+
+static int run_pvremove (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *device;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  r = guestfs_pvremove (g, device);
+  return r;
+}
+
+static int run_set_e2label (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *device;
+  const char *label;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  label = argv[1];
+  r = guestfs_set_e2label (g, device, label);
+  return r;
+}
+
+static int run_get_e2label (const char *cmd, int argc, char *argv[])
+{
+  char *r;
+  const char *device;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  r = guestfs_get_e2label (g, device);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  free (r);
+  return 0;
+}
+
+static int run_set_e2uuid (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *device;
+  const char *uuid;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  uuid = argv[1];
+  r = guestfs_set_e2uuid (g, device, uuid);
+  return r;
+}
+
+static int run_get_e2uuid (const char *cmd, int argc, char *argv[])
+{
+  char *r;
+  const char *device;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  r = guestfs_get_e2uuid (g, device);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  free (r);
+  return 0;
+}
+
+static int run_fsck (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *fstype;
+  const char *device;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  fstype = argv[0];
+  device = argv[1];
+  r = guestfs_fsck (g, fstype, device);
+  if (r == -1) return -1;
+  printf ("%d\n", r);
+  return 0;
+}
+
+static int run_zero (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *device;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  device = argv[0];
+  r = guestfs_zero (g, device);
+  return r;
+}
+
+static int run_grub_install (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *root;
+  const char *device;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  root = argv[0];
+  device = argv[1];
+  r = guestfs_grub_install (g, root, device);
+  return r;
+}
+
+static int run_cp (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *src;
+  const char *dest;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  src = argv[0];
+  dest = argv[1];
+  r = guestfs_cp (g, src, dest);
+  return r;
+}
+
+static int run_cp_a (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *src;
+  const char *dest;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  src = argv[0];
+  dest = argv[1];
+  r = guestfs_cp_a (g, src, dest);
+  return r;
+}
+
+static int run_mv (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *src;
+  const char *dest;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  src = argv[0];
+  dest = argv[1];
+  r = guestfs_mv (g, src, dest);
+  return r;
+}
+
+static int run_drop_caches (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  int whattodrop;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  whattodrop = atoi (argv[0]);
+  r = guestfs_drop_caches (g, whattodrop);
+  return r;
+}
+
+static int run_dmesg (const char *cmd, int argc, char *argv[])
+{
+  char *r;
+  if (argc != 0) {
+    fprintf (stderr, "%s should have 0 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  r = guestfs_dmesg (g);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  free (r);
+  return 0;
+}
+
+static int run_ping_daemon (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  if (argc != 0) {
+    fprintf (stderr, "%s should have 0 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  r = guestfs_ping_daemon (g);
+  return r;
+}
+
+static int run_equal (const char *cmd, int argc, char *argv[])
+{
+  int r;
+  const char *file1;
+  const char *file2;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  file1 = argv[0];
+  file2 = argv[1];
+  r = guestfs_equal (g, file1, file2);
+  if (r == -1) return -1;
+  if (r) printf ("true\n"); else printf ("false\n");
+  return 0;
+}
+
+static int run_strings (const char *cmd, int argc, char *argv[])
+{
+  char **r;
+  const char *path;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  path = argv[0];
+  r = guestfs_strings (g, path);
+  if (r == NULL) return -1;
+  print_strings (r);
+  free_strings (r);
+  return 0;
+}
+
+static int run_strings_e (const char *cmd, int argc, char *argv[])
+{
+  char **r;
+  const char *encoding;
+  const char *path;
+  if (argc != 2) {
+    fprintf (stderr, "%s should have 2 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  encoding = argv[0];
+  path = argv[1];
+  r = guestfs_strings_e (g, encoding, path);
+  if (r == NULL) return -1;
+  print_strings (r);
+  free_strings (r);
+  return 0;
+}
+
+static int run_hexdump (const char *cmd, int argc, char *argv[])
+{
+  char *r;
+  const char *path;
+  if (argc != 1) {
+    fprintf (stderr, "%s should have 1 parameter(s)\n", cmd);
+    fprintf (stderr, "type 'help %s' for help on %s\n", cmd, cmd);
+    return -1;
+  }
+  path = argv[0];
+  r = guestfs_hexdump (g, path);
+  if (r == NULL) return -1;
+  printf ("%s\n", r);
+  free (r);
+  return 0;
+}
+
 int run_action (const char *cmd, int argc, char *argv[])
 {
   if (strcasecmp (cmd, "launch") == 0 || strcasecmp (cmd, "run") == 0)
@@ -1755,12 +2455,24 @@ int run_action (const char *cmd, int argc, char *argv[])
   if (strcasecmp (cmd, "config") == 0)
     return run_config (cmd, argc, argv);
   else
+  if (strcasecmp (cmd, "set_qemu") == 0 || strcasecmp (cmd, "set-qemu") == 0 || strcasecmp (cmd, "qemu") == 0)
+    return run_set_qemu (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "get_qemu") == 0 || strcasecmp (cmd, "get-qemu") == 0)
+    return run_get_qemu (cmd, argc, argv);
+  else
   if (strcasecmp (cmd, "set_path") == 0 || strcasecmp (cmd, "set-path") == 0 || strcasecmp (cmd, "path") == 0)
     return run_set_path (cmd, argc, argv);
   else
   if (strcasecmp (cmd, "get_path") == 0 || strcasecmp (cmd, "get-path") == 0)
     return run_get_path (cmd, argc, argv);
   else
+  if (strcasecmp (cmd, "set_append") == 0 || strcasecmp (cmd, "set-append") == 0 || strcasecmp (cmd, "append") == 0)
+    return run_set_append (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "get_append") == 0 || strcasecmp (cmd, "get-append") == 0)
+    return run_get_append (cmd, argc, argv);
+  else
   if (strcasecmp (cmd, "set_autosync") == 0 || strcasecmp (cmd, "set-autosync") == 0 || strcasecmp (cmd, "autosync") == 0)
     return run_set_autosync (cmd, argc, argv);
   else
@@ -1983,6 +2695,99 @@ int run_action (const char *cmd, int argc, char *argv[])
   if (strcasecmp (cmd, "blockdev_rereadpt") == 0 || strcasecmp (cmd, "blockdev-rereadpt") == 0)
     return run_blockdev_rereadpt (cmd, argc, argv);
   else
+  if (strcasecmp (cmd, "upload") == 0)
+    return run_upload (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "download") == 0)
+    return run_download (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "checksum") == 0)
+    return run_checksum (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "tar_in") == 0 || strcasecmp (cmd, "tar-in") == 0)
+    return run_tar_in (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "tar_out") == 0 || strcasecmp (cmd, "tar-out") == 0)
+    return run_tar_out (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "tgz_in") == 0 || strcasecmp (cmd, "tgz-in") == 0)
+    return run_tgz_in (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "tgz_out") == 0 || strcasecmp (cmd, "tgz-out") == 0)
+    return run_tgz_out (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "mount_ro") == 0 || strcasecmp (cmd, "mount-ro") == 0)
+    return run_mount_ro (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "mount_options") == 0 || strcasecmp (cmd, "mount-options") == 0)
+    return run_mount_options (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "mount_vfs") == 0 || strcasecmp (cmd, "mount-vfs") == 0)
+    return run_mount_vfs (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "debug") == 0)
+    return run_debug (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "lvremove") == 0)
+    return run_lvremove (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "vgremove") == 0)
+    return run_vgremove (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "pvremove") == 0)
+    return run_pvremove (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "set_e2label") == 0 || strcasecmp (cmd, "set-e2label") == 0)
+    return run_set_e2label (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "get_e2label") == 0 || strcasecmp (cmd, "get-e2label") == 0)
+    return run_get_e2label (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "set_e2uuid") == 0 || strcasecmp (cmd, "set-e2uuid") == 0)
+    return run_set_e2uuid (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "get_e2uuid") == 0 || strcasecmp (cmd, "get-e2uuid") == 0)
+    return run_get_e2uuid (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "fsck") == 0)
+    return run_fsck (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "zero") == 0)
+    return run_zero (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "grub_install") == 0 || strcasecmp (cmd, "grub-install") == 0)
+    return run_grub_install (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "cp") == 0)
+    return run_cp (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "cp_a") == 0 || strcasecmp (cmd, "cp-a") == 0)
+    return run_cp_a (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "mv") == 0)
+    return run_mv (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "drop_caches") == 0 || strcasecmp (cmd, "drop-caches") == 0)
+    return run_drop_caches (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "dmesg") == 0)
+    return run_dmesg (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "ping_daemon") == 0 || strcasecmp (cmd, "ping-daemon") == 0)
+    return run_ping_daemon (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "equal") == 0)
+    return run_equal (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "strings") == 0)
+    return run_strings (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "strings_e") == 0 || strcasecmp (cmd, "strings-e") == 0)
+    return run_strings_e (cmd, argc, argv);
+  else
+  if (strcasecmp (cmd, "hexdump") == 0)
+    return run_hexdump (cmd, argc, argv);
+  else
     {
       fprintf (stderr, "%s: unknown command\n", cmd);
       return -1;