Added Augeas support.

This commit is contained in:
Richard Jones
2009-04-09 13:19:38 +01:00
parent a2e1d51acd
commit e7eca50046
26 changed files with 3442 additions and 139 deletions

2
README
View File

@@ -35,6 +35,8 @@ Requirements
- XDR, rpcgen
- Augeas (http://augeas.net/)
- perldoc (pod2man, pod2text) to generate the manual pages and
other documentation.

View File

@@ -15,7 +15,7 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
AC_INIT([libguestfs],[0.6])
AC_INIT([libguestfs],[0.7])
AM_INIT_AUTOMAKE
AC_CONFIG_MACRO_DIR([m4])
@@ -90,6 +90,18 @@ AC_DEFINE_UNQUOTED([REPO],["$REPO"],[Name of Fedora repository.])
AC_DEFINE_UNQUOTED([host_cpu],["$host_cpu"],[Host architecture.])
dnl --with-updates to specify a Fedora updates repository.
AC_ARG_WITH([updates],
[AS_HELP_STRING([--with-updates],
[set name of Fedora updates repository @<:@default=updates-released-f10@:>@])],
[],
[with_updates=updates-released-f10])
UPDATES="$with_updates"
AC_SUBST(UPDATES)
AC_DEFINE_UNQUOTED([UPDATES],["$UPDATES"],[Name of Fedora updates repository.])
AC_DEFINE_UNQUOTED([host_cpu],["$host_cpu"],[Host architecture.])
dnl --with-mirror to specify a local Fedora mirror.
AC_ARG_WITH([mirror],
[AS_HELP_STRING([--with-mirror],

View File

@@ -20,6 +20,7 @@ ACLOCAL_AMFLAGS = -I m4
noinst_PROGRAMS = guestfsd
guestfsd_SOURCES = \
actions.h \
augeas.c \
daemon.h \
devsparts.c \
file.c \

View File

@@ -22,17 +22,29 @@
#include "../src/guestfs_protocol.h"
extern int do_mount (const char *device, const char *mountpoint);
extern int do_sync ();
extern int do_sync (void);
extern int do_touch (const char *path);
extern char *do_cat (const char *path);
extern char *do_ll (const char *directory);
extern char **do_ls (const char *directory);
extern char **do_list_devices ();
extern char **do_list_partitions ();
extern char **do_pvs ();
extern char **do_vgs ();
extern char **do_lvs ();
extern guestfs_lvm_int_pv_list *do_pvs_full ();
extern guestfs_lvm_int_vg_list *do_vgs_full ();
extern guestfs_lvm_int_lv_list *do_lvs_full ();
extern char **do_list_devices (void);
extern char **do_list_partitions (void);
extern char **do_pvs (void);
extern char **do_vgs (void);
extern char **do_lvs (void);
extern guestfs_lvm_int_pv_list *do_pvs_full (void);
extern guestfs_lvm_int_vg_list *do_vgs_full (void);
extern guestfs_lvm_int_lv_list *do_lvs_full (void);
extern char **do_read_lines (const char *path);
extern int do_aug_init (const char *root, int flags);
extern int do_aug_close (void);
extern int do_aug_defvar (const char *name, const char *expr);
extern guestfs_aug_defnode_ret *do_aug_defnode (const char *name, const char *expr, const char *val);
extern char *do_aug_get (const char *path);
extern int do_aug_set (const char *path, const char *val);
extern int do_aug_insert (const char *path, const char *label, int before);
extern int do_aug_rm (const char *path);
extern int do_aug_mv (const char *src, const char *dest);
extern char **do_aug_match (const char *path);
extern int do_aug_save (void);
extern int do_aug_load (void);

278
daemon/augeas.c Normal file
View File

@@ -0,0 +1,278 @@
/* libguestfs - the guestfsd daemon
* Copyright (C) 2009 Red Hat Inc.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <config.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <augeas.h>
#include "daemon.h"
#include "actions.h"
/* The Augeas handle. We maintain a single handle per daemon, which
* is all that is necessary and reduces the complexity of the API
* considerably.
*/
static augeas *aug = NULL;
#define NEED_AUG(errcode) \
do { \
if (!aug) { \
reply_with_error ("%s: you must call 'aug-init' first to initialize Augeas", __func__); \
return (errcode); \
} \
} \
while (0)
/* We need to rewrite the root path so it is based at /sysroot. */
int
do_aug_init (const char *root, int flags)
{
char *buf;
int len;
NEED_ROOT (-1);
ABS_PATH (root, -1);
if (aug) {
aug_close (aug);
aug = NULL;
}
len = strlen (root) + 8;
buf = malloc (len);
if (!buf) {
reply_with_perror ("malloc");
return -1;
}
snprintf (buf, len, "/sysroot%s", root);
aug = aug_init (buf, NULL, flags);
free (buf);
if (!aug) {
reply_with_error ("Augeas initialization failed");
return -1;
}
return 0;
}
int
do_aug_close (void)
{
NEED_AUG(-1);
aug_close (aug);
aug = NULL;
return 0;
}
int
do_aug_defvar (const char *name, const char *expr)
{
int r;
NEED_AUG (-1);
r = aug_defvar (aug, name, expr);
if (r == -1) {
reply_with_error ("Augeas defvar failed");
return -1;
}
return r;
}
guestfs_aug_defnode_ret *
do_aug_defnode (const char *name, const char *expr, const char *val)
{
static guestfs_aug_defnode_ret r;
int created;
NEED_AUG (NULL);
r.nrnodes = aug_defnode (aug, name, expr, val, &created);
if (r.nrnodes == -1) {
reply_with_error ("Augeas defnode failed");
return NULL;
}
r.created = created;
return &r;
}
char *
do_aug_get (const char *path)
{
const char *value = NULL;
char *v;
int r;
NEED_AUG (NULL);
r = aug_get (aug, path, &value);
if (r == 0) {
reply_with_error ("no matching node");
return NULL;
}
if (r != 1) {
reply_with_error ("Augeas get failed");
return NULL;
}
/* value can still be NULL here, eg. try with path == "/augeas".
* I don't understand this case, and it seems to contradict the
* documentation.
*/
if (value == NULL) {
reply_with_error ("Augeas returned NULL match");
return NULL;
}
/* The value is an internal Augeas string, so we must copy it. GC FTW. */
v = strdup (value);
if (v == NULL) {
reply_with_perror ("strdup");
return NULL;
}
return v; /* Caller frees. */
}
int
do_aug_set (const char *path, const char *val)
{
int r;
NEED_AUG (-1);
r = aug_set (aug, path, val);
if (r == -1) {
reply_with_error ("Augeas set failed");
return -1;
}
return 0;
}
int
do_aug_insert (const char *path, const char *label, int before)
{
int r;
NEED_AUG (-1);
r = aug_insert (aug, path, label, before);
if (r == -1) {
reply_with_error ("Augeas insert failed");
return -1;
}
return 0;
}
int
do_aug_rm (const char *path)
{
int r;
NEED_AUG (-1);
r = aug_rm (aug, path);
if (r == -1) {
reply_with_error ("Augeas rm failed");
return -1;
}
return r;
}
int
do_aug_mv (const char *src, const char *dest)
{
int r;
NEED_AUG (-1);
r = aug_mv (aug, src, dest);
if (r == -1) {
reply_with_error ("Augeas mv failed");
return -1;
}
return 0;
}
char **
do_aug_match (const char *path)
{
char **matches = NULL;
void *vp;
int r;
NEED_AUG (NULL);
r = aug_match (aug, path, &matches);
if (r == -1) {
reply_with_error ("Augeas match failed");
return NULL;
}
/* This returns an array of length r, which we must extend
* and add a terminating NULL.
*/
vp = realloc (matches, sizeof (char *) * (r+1));
if (vp == NULL) {
reply_with_perror ("realloc");
free (vp);
return NULL;
}
matches = vp;
matches[r] = NULL;
return matches; /* Caller frees. */
}
int
do_aug_save (void)
{
NEED_AUG (-1);
if (aug_save (aug) == -1) {
reply_with_error ("Augeas save failed");
return -1;
}
return 0;
}
int
do_aug_load (void)
{
NEED_AUG (-1);
if (aug_load (aug) == -1) {
reply_with_error ("Augeas load failed");
return -1;
}
return 0;
}

View File

@@ -15,7 +15,7 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
AC_INIT([libguestfs-daemon],[0.2])
AC_INIT([libguestfs-daemon],[0.7])
AM_INIT_AUTOMAKE
AC_CONFIG_MACRO_DIR([m4])
@@ -37,6 +37,11 @@ test "x$U" != "x" && AC_MSG_ERROR([Compiler not ANSI compliant])
AC_PROG_CC_C_O
dnl Check for Augeas.
AC_CHECK_LIB([augeas],[aug_match],,[
AC_MSG_ERROR([Augeas library not found])
])
dnl Check for XDR library.
AC_CHECK_LIB([portablexdr],[xdrmem_create],[],[
AC_SEARCH_LIBS([xdrmem_create],[rpc xdr nsl])

View File

@@ -43,7 +43,7 @@ static void mount_stub (XDR *xdr_in)
memset (&args, 0, sizeof args);
if (!xdr_guestfs_mount_args (xdr_in, &args)) {
reply_with_error ("mount: daemon failed to decode procedure arguments");
reply_with_error ("%s: daemon failed to decode procedure arguments", "mount");
return;
}
device = args.device;
@@ -78,7 +78,7 @@ static void touch_stub (XDR *xdr_in)
memset (&args, 0, sizeof args);
if (!xdr_guestfs_touch_args (xdr_in, &args)) {
reply_with_error ("touch: daemon failed to decode procedure arguments");
reply_with_error ("%s: daemon failed to decode procedure arguments", "touch");
return;
}
path = args.path;
@@ -100,7 +100,7 @@ static void cat_stub (XDR *xdr_in)
memset (&args, 0, sizeof args);
if (!xdr_guestfs_cat_args (xdr_in, &args)) {
reply_with_error ("cat: daemon failed to decode procedure arguments");
reply_with_error ("%s: daemon failed to decode procedure arguments", "cat");
return;
}
path = args.path;
@@ -125,7 +125,7 @@ static void ll_stub (XDR *xdr_in)
memset (&args, 0, sizeof args);
if (!xdr_guestfs_ll_args (xdr_in, &args)) {
reply_with_error ("ll: daemon failed to decode procedure arguments");
reply_with_error ("%s: daemon failed to decode procedure arguments", "ll");
return;
}
directory = args.directory;
@@ -150,7 +150,7 @@ static void ls_stub (XDR *xdr_in)
memset (&args, 0, sizeof args);
if (!xdr_guestfs_ls_args (xdr_in, &args)) {
reply_with_error ("ls: daemon failed to decode procedure arguments");
reply_with_error ("%s: daemon failed to decode procedure arguments", "ls");
return;
}
directory = args.directory;
@@ -258,7 +258,7 @@ static void pvs_full_stub (XDR *xdr_in)
struct guestfs_pvs_full_ret ret;
ret.physvols = *r;
reply ((xdrproc_t) &xdr_guestfs_pvs_full_ret, (char *) &ret);
reply ((xdrproc_t) xdr_guestfs_pvs_full_ret, (char *) &ret);
xdr_free ((xdrproc_t) xdr_guestfs_pvs_full_ret, (char *) &ret);
}
@@ -273,7 +273,7 @@ static void vgs_full_stub (XDR *xdr_in)
struct guestfs_vgs_full_ret ret;
ret.volgroups = *r;
reply ((xdrproc_t) &xdr_guestfs_vgs_full_ret, (char *) &ret);
reply ((xdrproc_t) xdr_guestfs_vgs_full_ret, (char *) &ret);
xdr_free ((xdrproc_t) xdr_guestfs_vgs_full_ret, (char *) &ret);
}
@@ -288,7 +288,7 @@ static void lvs_full_stub (XDR *xdr_in)
struct guestfs_lvs_full_ret ret;
ret.logvols = *r;
reply ((xdrproc_t) &xdr_guestfs_lvs_full_ret, (char *) &ret);
reply ((xdrproc_t) xdr_guestfs_lvs_full_ret, (char *) &ret);
xdr_free ((xdrproc_t) xdr_guestfs_lvs_full_ret, (char *) &ret);
}
@@ -301,7 +301,7 @@ static void read_lines_stub (XDR *xdr_in)
memset (&args, 0, sizeof args);
if (!xdr_guestfs_read_lines_args (xdr_in, &args)) {
reply_with_error ("read_lines: daemon failed to decode procedure arguments");
reply_with_error ("%s: daemon failed to decode procedure arguments", "read_lines");
return;
}
path = args.path;
@@ -318,6 +318,268 @@ static void read_lines_stub (XDR *xdr_in)
free_strings (r);
}
static void aug_init_stub (XDR *xdr_in)
{
int r;
struct guestfs_aug_init_args args;
const char *root;
int flags;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_init_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_init");
return;
}
root = args.root;
flags = args.flags;
r = do_aug_init (root, flags);
if (r == -1)
/* do_aug_init has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
static void aug_close_stub (XDR *xdr_in)
{
int r;
r = do_aug_close ();
if (r == -1)
/* do_aug_close has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
static void aug_defvar_stub (XDR *xdr_in)
{
int r;
struct guestfs_aug_defvar_args args;
const char *name;
const char *expr;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_defvar_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_defvar");
return;
}
name = args.name;
expr = args.expr ? *args.expr : NULL;
r = do_aug_defvar (name, expr);
if (r == -1)
/* do_aug_defvar has already called reply_with_error, so just return */
return;
struct guestfs_aug_defvar_ret ret;
ret.nrnodes = r;
reply ((xdrproc_t) &xdr_guestfs_aug_defvar_ret, (char *) &ret);
}
static void aug_defnode_stub (XDR *xdr_in)
{
guestfs_aug_defnode_ret *r;
struct guestfs_aug_defnode_args args;
const char *name;
const char *expr;
const char *val;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_defnode_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_defnode");
return;
}
name = args.name;
expr = args.expr;
val = args.val;
r = do_aug_defnode (name, expr, val);
if (r == NULL)
/* do_aug_defnode has already called reply_with_error, so just return */
return;
reply ((xdrproc_t) xdr_guestfs_aug_defnode_ret, (char *) r);
xdr_free ((xdrproc_t) xdr_guestfs_aug_defnode_ret, (char *) r);
}
static void aug_get_stub (XDR *xdr_in)
{
char *r;
struct guestfs_aug_get_args args;
const char *path;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_get_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_get");
return;
}
path = args.path;
r = do_aug_get (path);
if (r == NULL)
/* do_aug_get has already called reply_with_error, so just return */
return;
struct guestfs_aug_get_ret ret;
ret.val = r;
reply ((xdrproc_t) &xdr_guestfs_aug_get_ret, (char *) &ret);
free (r);
}
static void aug_set_stub (XDR *xdr_in)
{
int r;
struct guestfs_aug_set_args args;
const char *path;
const char *val;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_set_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_set");
return;
}
path = args.path;
val = args.val;
r = do_aug_set (path, val);
if (r == -1)
/* do_aug_set has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
static void aug_insert_stub (XDR *xdr_in)
{
int r;
struct guestfs_aug_insert_args args;
const char *path;
const char *label;
int before;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_insert_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_insert");
return;
}
path = args.path;
label = args.label;
before = args.before;
r = do_aug_insert (path, label, before);
if (r == -1)
/* do_aug_insert has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
static void aug_rm_stub (XDR *xdr_in)
{
int r;
struct guestfs_aug_rm_args args;
const char *path;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_rm_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_rm");
return;
}
path = args.path;
r = do_aug_rm (path);
if (r == -1)
/* do_aug_rm has already called reply_with_error, so just return */
return;
struct guestfs_aug_rm_ret ret;
ret.nrnodes = r;
reply ((xdrproc_t) &xdr_guestfs_aug_rm_ret, (char *) &ret);
}
static void aug_mv_stub (XDR *xdr_in)
{
int r;
struct guestfs_aug_mv_args args;
const char *src;
const char *dest;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_mv_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_mv");
return;
}
src = args.src;
dest = args.dest;
r = do_aug_mv (src, dest);
if (r == -1)
/* do_aug_mv has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
static void aug_match_stub (XDR *xdr_in)
{
char **r;
struct guestfs_aug_match_args args;
const char *path;
memset (&args, 0, sizeof args);
if (!xdr_guestfs_aug_match_args (xdr_in, &args)) {
reply_with_error ("%s: daemon failed to decode procedure arguments", "aug_match");
return;
}
path = args.path;
r = do_aug_match (path);
if (r == NULL)
/* do_aug_match has already called reply_with_error, so just return */
return;
struct guestfs_aug_match_ret ret;
ret.matches.matches_len = count_strings (r);
ret.matches.matches_val = r;
reply ((xdrproc_t) &xdr_guestfs_aug_match_ret, (char *) &ret);
free_strings (r);
}
static void aug_save_stub (XDR *xdr_in)
{
int r;
r = do_aug_save ();
if (r == -1)
/* do_aug_save has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
static void aug_load_stub (XDR *xdr_in)
{
int r;
r = do_aug_load ();
if (r == -1)
/* do_aug_load has already called reply_with_error, so just return */
return;
reply (NULL, NULL);
}
void dispatch_incoming_message (XDR *xdr_in)
{
switch (proc_nr) {
@@ -366,6 +628,42 @@ void dispatch_incoming_message (XDR *xdr_in)
case GUESTFS_PROC_READ_LINES:
read_lines_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_INIT:
aug_init_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_CLOSE:
aug_close_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_DEFVAR:
aug_defvar_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_DEFNODE:
aug_defnode_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_GET:
aug_get_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_SET:
aug_set_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_INSERT:
aug_insert_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_RM:
aug_rm_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_MV:
aug_mv_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_MATCH:
aug_match_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_SAVE:
aug_save_stub (xdr_in);
break;
case GUESTFS_PROC_AUG_LOAD:
aug_load_stub (xdr_in);
break;
default:
reply_with_error ("dispatch_incoming_message: unknown procedure number %d", proc_nr);
}

View File

@@ -33,6 +33,18 @@ void list_commands (void)
list_builtin_commands ();
printf ("%-20s %s\n", "add-cdrom", "add a CD-ROM disk image to examine");
printf ("%-20s %s\n", "add-drive", "add an image to examine or modify");
printf ("%-20s %s\n", "aug-close", "close the current Augeas handle");
printf ("%-20s %s\n", "aug-defnode", "define an Augeas node");
printf ("%-20s %s\n", "aug-defvar", "define an Augeas variable");
printf ("%-20s %s\n", "aug-get", "look up the value of an Augeas path");
printf ("%-20s %s\n", "aug-init", "create a new Augeas handle");
printf ("%-20s %s\n", "aug-insert", "insert a sibling Augeas node");
printf ("%-20s %s\n", "aug-load", "load files into the tree");
printf ("%-20s %s\n", "aug-match", "return Augeas nodes which match path");
printf ("%-20s %s\n", "aug-mv", "move Augeas node");
printf ("%-20s %s\n", "aug-rm", "remove an Augeas path");
printf ("%-20s %s\n", "aug-save", "write all pending Augeas changes to disk");
printf ("%-20s %s\n", "aug-set", "set Augeas path to value");
printf ("%-20s %s\n", "cat", "list the contents of a file");
printf ("%-20s %s\n", "config", "add qemu parameters");
printf ("%-20s %s\n", "get-autosync", "get autosync mode");
@@ -139,6 +151,42 @@ void display_command (const char *cmd)
else
if (strcasecmp (cmd, "read_lines") == 0 || strcasecmp (cmd, "read-lines") == 0)
pod2text ("read-lines - read file as lines", " read-lines <path>\n\nReturn the contents of the file named C<path>.\n\nThe file contents are returned as a list of lines. Trailing\nC<LF> and C<CRLF> character sequences are I<not> returned.\n\nNote that this function cannot correctly handle binary files\n(specifically, files containing C<\\0> character which is treated\nas end of line). For those you need to use the C<read_file>\nfunction which has a more complex interface.");
else
if (strcasecmp (cmd, "aug_init") == 0 || strcasecmp (cmd, "aug-init") == 0)
pod2text ("aug-init - create a new Augeas handle", " aug-init <root> <flags>\n\nCreate a new Augeas handle for editing configuration files.\nIf there was any previous Augeas handle associated with this\nguestfs session, then it is closed.\n\nYou must call this before using any other C<aug_*>\ncommands.\n\nC<root> is the filesystem root. C<root> must not be NULL,\nuse C</> instead.\n\nThe flags are the same as the flags defined in\nE<lt>augeas.hE<gt>, the logical I<or> of the following\nintegers:\n\n=over 4\n\n=item 1 C<AUG_SAVE_BACKUP>\n\nKeep the original file with a C<.augsave> extension.\n\n=item 2 C<AUG_SAVE_NEWFILE>\n\nSave changes into a file with extension C<.augnew>, and\ndo not overwrite original. Overrides C<AUG_SAVE_BACKUP>.\n\n=item 4 C<AUG_TYPE_CHECK>\n\nTypecheck lenses (can be expensive).\n\n=item 8 C<AUG_NO_STDINC>\n\nDo not use standard load path for modules.\n\n=item 16 C<AUG_SAVE_NOOP>\n\nMake save a no-op, just record what would have been changed.\n\n=item 32 C<AUG_NO_LOAD>\n\nDo not load the tree in C<aug_init>.\n\n=back\n\nTo close the handle, you can call C<aug_close>.\n\nTo find out more about Augeas, see L<http://augeas.net/>.");
else
if (strcasecmp (cmd, "aug_close") == 0 || strcasecmp (cmd, "aug-close") == 0)
pod2text ("aug-close - close the current Augeas handle", " aug-close\n\nClose the current Augeas handle and free up any resources\nused by it. After calling this, you have to call\nC<aug_init> again before you can use any other\nAugeas functions.");
else
if (strcasecmp (cmd, "aug_defvar") == 0 || strcasecmp (cmd, "aug-defvar") == 0)
pod2text ("aug-defvar - define an Augeas variable", " aug-defvar <name> <expr>\n\nDefines an Augeas variable C<name> whose value is the result\nof evaluating C<expr>. If C<expr> is NULL, then C<name> is\nundefined.\n\nOn success this returns the number of nodes in C<expr>, or\nC<0> if C<expr> evaluates to something which is not a nodeset.");
else
if (strcasecmp (cmd, "aug_defnode") == 0 || strcasecmp (cmd, "aug-defnode") == 0)
pod2text ("aug-defnode - define an Augeas node", " aug-defnode <name> <expr> <val>\n\nDefines a variable C<name> whose value is the result of\nevaluating C<expr>.\n\nIf C<expr> evaluates to an empty nodeset, a node is created,\nequivalent to calling C<aug_set> C<expr>, C<value>.\nC<name> will be the nodeset containing that single node.\n\nOn success this returns a pair containing the\nnumber of nodes in the nodeset, and a boolean flag\nif a node was created.");
else
if (strcasecmp (cmd, "aug_get") == 0 || strcasecmp (cmd, "aug-get") == 0)
pod2text ("aug-get - look up the value of an Augeas path", " aug-get <path>\n\nLook up the value associated with C<path>. If C<path>\nmatches exactly one node, the C<value> is returned.");
else
if (strcasecmp (cmd, "aug_set") == 0 || strcasecmp (cmd, "aug-set") == 0)
pod2text ("aug-set - set Augeas path to value", " aug-set <path> <val>\n\nSet the value associated with C<path> to C<value>.");
else
if (strcasecmp (cmd, "aug_insert") == 0 || strcasecmp (cmd, "aug-insert") == 0)
pod2text ("aug-insert - insert a sibling Augeas node", " aug-insert <path> <label> <before>\n\nCreate a new sibling C<label> for C<path>, inserting it into\nthe tree before or after C<path> (depending on the boolean\nflag C<before>).\n\nC<path> must match exactly one existing node in the tree, and\nC<label> must be a label, ie. not contain C</>, C<*> or end\nwith a bracketed index C<[N]>.");
else
if (strcasecmp (cmd, "aug_rm") == 0 || strcasecmp (cmd, "aug-rm") == 0)
pod2text ("aug-rm - remove an Augeas path", " aug-rm <path>\n\nRemove C<path> and all of its children.\n\nOn success this returns the number of entries which were removed.");
else
if (strcasecmp (cmd, "aug_mv") == 0 || strcasecmp (cmd, "aug-mv") == 0)
pod2text ("aug-mv - move Augeas node", " aug-mv <src> <dest>\n\nMove the node C<src> to C<dest>. C<src> must match exactly\none node. C<dest> is overwritten if it exists.");
else
if (strcasecmp (cmd, "aug_match") == 0 || strcasecmp (cmd, "aug-match") == 0)
pod2text ("aug-match - return Augeas nodes which match path", " aug-match <path>\n\nReturns a list of paths which match the path expression C<path>.\nThe returned paths are sufficiently qualified so that they match\nexactly one node in the current tree.");
else
if (strcasecmp (cmd, "aug_save") == 0 || strcasecmp (cmd, "aug-save") == 0)
pod2text ("aug-save - write all pending Augeas changes to disk", " aug-save\n\nThis writes all pending changes to disk.\n\nThe flags which were passed to C<aug_init> affect exactly\nhow files are saved.");
else
if (strcasecmp (cmd, "aug_load") == 0 || strcasecmp (cmd, "aug-load") == 0)
pod2text ("aug-load - load files into the tree", " aug-load\n\nLoad files into the tree.\n\nSee C<aug_load> in the Augeas documentation for the full gory\ndetails.");
else
display_builtin_command (cmd);
}
@@ -627,6 +675,198 @@ static int run_read_lines (const char *cmd, int argc, char *argv[])
return 0;
}
static int run_aug_init (const char *cmd, int argc, char *argv[])
{
int r;
const char *root;
int flags;
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];
flags = atoi (argv[1]);
r = guestfs_aug_init (g, root, flags);
return r;
}
static int run_aug_close (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_aug_close (g);
return r;
}
static int run_aug_defvar (const char *cmd, int argc, char *argv[])
{
int r;
const char *name;
const char *expr;
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;
}
name = argv[0];
expr = strcmp (argv[1], "") != 0 ? argv[1] : NULL;
r = guestfs_aug_defvar (g, name, expr);
if (r == -1) return -1;
if (r) printf ("%d\n", r);
return 0;
}
static int run_aug_defnode (const char *cmd, int argc, char *argv[])
{
struct guestfs_int_bool *r;
const char *name;
const char *expr;
const char *val;
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;
}
name = argv[0];
expr = argv[1];
val = argv[2];
r = guestfs_aug_defnode (g, name, expr, val);
if (r == NULL) return -1;
printf ("%d, %s\n", r->i,
r->b ? "true" : "false");
guestfs_free_int_bool (r);
return 0;
}
static int run_aug_get (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_aug_get (g, path);
if (r == NULL) return -1;
printf ("%s\n", r);
free (r);
return 0;
}
static int run_aug_set (const char *cmd, int argc, char *argv[])
{
int r;
const char *path;
const char *val;
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;
}
path = argv[0];
val = argv[1];
r = guestfs_aug_set (g, path, val);
return r;
}
static int run_aug_insert (const char *cmd, int argc, char *argv[])
{
int r;
const char *path;
const char *label;
int before;
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;
}
path = argv[0];
label = argv[1];
before = is_true (argv[2]) ? 1 : 0;
r = guestfs_aug_insert (g, path, label, before);
return r;
}
static int run_aug_rm (const char *cmd, int argc, char *argv[])
{
int 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_aug_rm (g, path);
if (r == -1) return -1;
if (r) printf ("%d\n", r);
return 0;
}
static int run_aug_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_aug_mv (g, src, dest);
return r;
}
static int run_aug_match (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_aug_match (g, path);
if (r == NULL) return -1;
print_strings (r);
free_strings (r);
return 0;
}
static int run_aug_save (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_aug_save (g);
return r;
}
static int run_aug_load (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_aug_load (g);
return r;
}
int run_action (const char *cmd, int argc, char *argv[])
{
if (strcasecmp (cmd, "launch") == 0 || strcasecmp (cmd, "run") == 0)
@@ -706,6 +946,42 @@ int run_action (const char *cmd, int argc, char *argv[])
else
if (strcasecmp (cmd, "read_lines") == 0 || strcasecmp (cmd, "read-lines") == 0)
return run_read_lines (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_init") == 0 || strcasecmp (cmd, "aug-init") == 0)
return run_aug_init (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_close") == 0 || strcasecmp (cmd, "aug-close") == 0)
return run_aug_close (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_defvar") == 0 || strcasecmp (cmd, "aug-defvar") == 0)
return run_aug_defvar (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_defnode") == 0 || strcasecmp (cmd, "aug-defnode") == 0)
return run_aug_defnode (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_get") == 0 || strcasecmp (cmd, "aug-get") == 0)
return run_aug_get (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_set") == 0 || strcasecmp (cmd, "aug-set") == 0)
return run_aug_set (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_insert") == 0 || strcasecmp (cmd, "aug-insert") == 0)
return run_aug_insert (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_rm") == 0 || strcasecmp (cmd, "aug-rm") == 0)
return run_aug_rm (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_mv") == 0 || strcasecmp (cmd, "aug-mv") == 0)
return run_aug_mv (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_match") == 0 || strcasecmp (cmd, "aug-match") == 0)
return run_aug_match (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_save") == 0 || strcasecmp (cmd, "aug-save") == 0)
return run_aug_save (cmd, argc, argv);
else
if (strcasecmp (cmd, "aug_load") == 0 || strcasecmp (cmd, "aug-load") == 0)
return run_aug_load (cmd, argc, argv);
else
{
fprintf (stderr, "%s: unknown command\n", cmd);

View File

@@ -23,6 +23,158 @@ image).
This is equivalent to the qemu parameter C<-drive file=filename>.
=head2 aug-close
aug-close
Close the current Augeas handle and free up any resources
used by it. After calling this, you have to call
C<aug_init> again before you can use any other
Augeas functions.
=head2 aug-defnode
aug-defnode name expr val
Defines a variable C<name> whose value is the result of
evaluating C<expr>.
If C<expr> evaluates to an empty nodeset, a node is created,
equivalent to calling C<aug_set> C<expr>, C<value>.
C<name> will be the nodeset containing that single node.
On success this returns a pair containing the
number of nodes in the nodeset, and a boolean flag
if a node was created.
=head2 aug-defvar
aug-defvar name expr
Defines an Augeas variable C<name> whose value is the result
of evaluating C<expr>. If C<expr> is NULL, then C<name> is
undefined.
On success this returns the number of nodes in C<expr>, or
C<0> if C<expr> evaluates to something which is not a nodeset.
=head2 aug-get
aug-get path
Look up the value associated with C<path>. If C<path>
matches exactly one node, the C<value> is returned.
=head2 aug-init
aug-init root flags
Create a new Augeas handle for editing configuration files.
If there was any previous Augeas handle associated with this
guestfs session, then it is closed.
You must call this before using any other C<aug_*>
commands.
C<root> is the filesystem root. C<root> must not be NULL,
use C</> instead.
The flags are the same as the flags defined in
E<lt>augeas.hE<gt>, the logical I<or> of the following
integers:
=over 4
=item 1 C<AUG_SAVE_BACKUP>
Keep the original file with a C<.augsave> extension.
=item 2 C<AUG_SAVE_NEWFILE>
Save changes into a file with extension C<.augnew>, and
do not overwrite original. Overrides C<AUG_SAVE_BACKUP>.
=item 4 C<AUG_TYPE_CHECK>
Typecheck lenses (can be expensive).
=item 8 C<AUG_NO_STDINC>
Do not use standard load path for modules.
=item 16 C<AUG_SAVE_NOOP>
Make save a no-op, just record what would have been changed.
=item 32 C<AUG_NO_LOAD>
Do not load the tree in C<aug_init>.
=back
To close the handle, you can call C<aug_close>.
To find out more about Augeas, see L<http://augeas.net/>.
=head2 aug-insert
aug-insert path label true|false
Create a new sibling C<label> for C<path>, inserting it into
the tree before or after C<path> (depending on the boolean
flag C<before>).
C<path> must match exactly one existing node in the tree, and
C<label> must be a label, ie. not contain C</>, C<*> or end
with a bracketed index C<[N]>.
=head2 aug-load
aug-load
Load files into the tree.
See C<aug_load> in the Augeas documentation for the full gory
details.
=head2 aug-match
aug-match path
Returns a list of paths which match the path expression C<path>.
The returned paths are sufficiently qualified so that they match
exactly one node in the current tree.
=head2 aug-mv
aug-mv src dest
Move the node C<src> to C<dest>. C<src> must match exactly
one node. C<dest> is overwritten if it exists.
=head2 aug-rm
aug-rm path
Remove C<path> and all of its children.
On success this returns the number of entries which were removed.
=head2 aug-save
aug-save
This writes all pending changes to disk.
The flags which were passed to C<aug_init> affect exactly
how files are saved.
=head2 aug-set
aug-set path val
Set the value associated with C<path> to C<value>.
=head2 cat
cat path

View File

@@ -29,6 +29,203 @@ This is equivalent to the qemu parameter C<-drive file=filename>.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_close
int guestfs_aug_close (guestfs_h *handle);
Close the current Augeas handle and free up any resources
used by it. After calling this, you have to call
C<guestfs_aug_init> again before you can use any other
Augeas functions.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_defnode
struct guestfs_int_bool *guestfs_aug_defnode (guestfs_h *handle,
const char *name,
const char *expr,
const char *val);
Defines a variable C<name> whose value is the result of
evaluating C<expr>.
If C<expr> evaluates to an empty nodeset, a node is created,
equivalent to calling C<guestfs_aug_set> C<expr>, C<value>.
C<name> will be the nodeset containing that single node.
On success this returns a pair containing the
number of nodes in the nodeset, and a boolean flag
if a node was created.
This function returns a C<struct guestfs_int_bool *>.
I<The caller must call C<guestfs_free_int_bool> after use.>.
=head2 guestfs_aug_defvar
int guestfs_aug_defvar (guestfs_h *handle,
const char *name,
const char *expr);
Defines an Augeas variable C<name> whose value is the result
of evaluating C<expr>. If C<expr> is NULL, then C<name> is
undefined.
On success this returns the number of nodes in C<expr>, or
C<0> if C<expr> evaluates to something which is not a nodeset.
On error this function returns -1.
=head2 guestfs_aug_get
char *guestfs_aug_get (guestfs_h *handle,
const char *path);
Look up the value associated with C<path>. If C<path>
matches exactly one node, the C<value> is returned.
This function returns a string or NULL on error.
I<The caller must free the returned string after use>.
=head2 guestfs_aug_init
int guestfs_aug_init (guestfs_h *handle,
const char *root,
int flags);
Create a new Augeas handle for editing configuration files.
If there was any previous Augeas handle associated with this
guestfs session, then it is closed.
You must call this before using any other C<guestfs_aug_*>
commands.
C<root> is the filesystem root. C<root> must not be NULL,
use C</> instead.
The flags are the same as the flags defined in
E<lt>augeas.hE<gt>, the logical I<or> of the following
integers:
=over 4
=item 1 C<AUG_SAVE_BACKUP>
Keep the original file with a C<.augsave> extension.
=item 2 C<AUG_SAVE_NEWFILE>
Save changes into a file with extension C<.augnew>, and
do not overwrite original. Overrides C<AUG_SAVE_BACKUP>.
=item 4 C<AUG_TYPE_CHECK>
Typecheck lenses (can be expensive).
=item 8 C<AUG_NO_STDINC>
Do not use standard load path for modules.
=item 16 C<AUG_SAVE_NOOP>
Make save a no-op, just record what would have been changed.
=item 32 C<AUG_NO_LOAD>
Do not load the tree in C<guestfs_aug_init>.
=back
To close the handle, you can call C<guestfs_aug_close>.
To find out more about Augeas, see L<http://augeas.net/>.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_insert
int guestfs_aug_insert (guestfs_h *handle,
const char *path,
const char *label,
int before);
Create a new sibling C<label> for C<path>, inserting it into
the tree before or after C<path> (depending on the boolean
flag C<before>).
C<path> must match exactly one existing node in the tree, and
C<label> must be a label, ie. not contain C</>, C<*> or end
with a bracketed index C<[N]>.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_load
int guestfs_aug_load (guestfs_h *handle);
Load files into the tree.
See C<aug_load> in the Augeas documentation for the full gory
details.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_match
char **guestfs_aug_match (guestfs_h *handle,
const char *path);
Returns a list of paths which match the path expression C<path>.
The returned paths are sufficiently qualified so that they match
exactly one node in the current tree.
This function returns a NULL-terminated array of strings
(like L<environ(3)>), or NULL if there was an error.
I<The caller must free the strings and the array after use>.
=head2 guestfs_aug_mv
int guestfs_aug_mv (guestfs_h *handle,
const char *src,
const char *dest);
Move the node C<src> to C<dest>. C<src> must match exactly
one node. C<dest> is overwritten if it exists.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_rm
int guestfs_aug_rm (guestfs_h *handle,
const char *path);
Remove C<path> and all of its children.
On success this returns the number of entries which were removed.
On error this function returns -1.
=head2 guestfs_aug_save
int guestfs_aug_save (guestfs_h *handle);
This writes all pending changes to disk.
The flags which were passed to C<guestfs_aug_init> affect exactly
how files are saved.
This function returns 0 on success or -1 on error.
=head2 guestfs_aug_set
int guestfs_aug_set (guestfs_h *handle,
const char *path,
const char *val);
Set the value associated with C<path> to C<value>.
This function returns 0 on success or -1 on error.
=head2 guestfs_cat
char *guestfs_cat (guestfs_h *handle,
@@ -193,7 +390,7 @@ I<The caller must free the strings and the array after use>.
List all the logical volumes detected. This is the equivalent
of the L<lvs(8)> command. The "full" version includes all fields.
This function returns a C<struct guestfs_lvm_lv_list>.
This function returns a C<struct guestfs_lvm_lv_list *>.
I<The caller must call C<guestfs_free_lvm_lv_list> after use.>.
=head2 guestfs_mount
@@ -244,7 +441,7 @@ I<The caller must free the strings and the array after use>.
List all the physical volumes detected. This is the equivalent
of the L<pvs(8)> command. The "full" version includes all fields.
This function returns a C<struct guestfs_lvm_pv_list>.
This function returns a C<struct guestfs_lvm_pv_list *>.
I<The caller must call C<guestfs_free_lvm_pv_list> after use.>.
=head2 guestfs_read_lines
@@ -352,7 +549,7 @@ I<The caller must free the strings and the array after use>.
List all the volumes groups detected. This is the equivalent
of the L<vgs(8)> command. The "full" version includes all fields.
This function returns a C<struct guestfs_lvm_vg_list>.
This function returns a C<struct guestfs_lvm_vg_list *>.
I<The caller must call C<guestfs_free_lvm_vg_list> after use.>.
=head2 guestfs_wait_ready

View File

@@ -15,7 +15,8 @@ BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root
# Basic build requirements:
BuildRequires: /usr/bin/pod2man
BuildRequires: /usr/bin/pod2text
BuildRequires: febootstrap
BuildRequires: febootstrap >= 1.5
BuildRequires: augeas-devel
# If you want to build the bindings for different languages:
BuildRequires: ocaml

View File

@@ -25,7 +25,7 @@ set -e
# larger.
debug=yes
modules="-i kernel -i bash -i coreutils -i lvm2 -i ntfs-3g -i util-linux-ng -i MAKEDEV -i net-tools"
modules="-i kernel -i bash -i coreutils -i lvm2 -i ntfs-3g -i util-linux-ng -i MAKEDEV -i net-tools -i augeas-libs"
if [ "x$debug" = "xyes" ]; then
modules="$modules -i module-init-tools -i procps -i strace -i iputils"
@@ -38,7 +38,7 @@ rm -f $output
rm -f $koutput
# Create the basic initramfs.
@FEBOOTSTRAP@ $modules @REPO@ initramfs @MIRROR@
@FEBOOTSTRAP@ $modules -u @UPDATES@ @REPO@ initramfs @MIRROR@
# /sysroot is where the guest root filesystem will be mounted.
mkdir initramfs/sysroot

View File

@@ -112,3 +112,15 @@ external pvs_full : t -> lvm_pv array = "ocaml_guestfs_pvs_full"
external vgs_full : t -> lvm_vg array = "ocaml_guestfs_vgs_full"
external lvs_full : t -> lvm_lv array = "ocaml_guestfs_lvs_full"
external read_lines : t -> string -> string array = "ocaml_guestfs_read_lines"
external aug_init : t -> string -> int -> unit = "ocaml_guestfs_aug_init"
external aug_close : t -> unit = "ocaml_guestfs_aug_close"
external aug_defvar : t -> string -> string option -> int = "ocaml_guestfs_aug_defvar"
external aug_defnode : t -> string -> string -> string -> int * bool = "ocaml_guestfs_aug_defnode"
external aug_get : t -> string -> string = "ocaml_guestfs_aug_get"
external aug_set : t -> string -> string -> unit = "ocaml_guestfs_aug_set"
external aug_insert : t -> string -> string -> bool -> unit = "ocaml_guestfs_aug_insert"
external aug_rm : t -> string -> int = "ocaml_guestfs_aug_rm"
external aug_mv : t -> string -> string -> unit = "ocaml_guestfs_aug_mv"
external aug_match : t -> string -> string array = "ocaml_guestfs_aug_match"
external aug_save : t -> unit = "ocaml_guestfs_aug_save"
external aug_load : t -> unit = "ocaml_guestfs_aug_load"

View File

@@ -175,3 +175,39 @@ val lvs_full : t -> lvm_lv array
val read_lines : t -> string -> string array
(** read file as lines *)
val aug_init : t -> string -> int -> unit
(** create a new Augeas handle *)
val aug_close : t -> unit
(** close the current Augeas handle *)
val aug_defvar : t -> string -> string option -> int
(** define an Augeas variable *)
val aug_defnode : t -> string -> string -> string -> int * bool
(** define an Augeas node *)
val aug_get : t -> string -> string
(** look up the value of an Augeas path *)
val aug_set : t -> string -> string -> unit
(** set Augeas path to value *)
val aug_insert : t -> string -> string -> bool -> unit
(** insert a sibling Augeas node *)
val aug_rm : t -> string -> int
(** remove an Augeas path *)
val aug_mv : t -> string -> string -> unit
(** move Augeas node *)
val aug_match : t -> string -> string array
(** return Augeas nodes which match path *)
val aug_save : t -> unit
(** write all pending Augeas changes to disk *)
val aug_load : t -> unit
(** load files into the tree *)

View File

@@ -456,7 +456,7 @@ ocaml_guestfs_get_autosync (value gv)
if (r == -1)
ocaml_guestfs_raise_error (g, "get_autosync");
rv = r ? Val_true : Val_false;
rv = Val_bool (r);
CAMLreturn (rv);
}
@@ -501,7 +501,7 @@ ocaml_guestfs_get_verbose (value gv)
if (r == -1)
ocaml_guestfs_raise_error (g, "get_verbose");
rv = r ? Val_true : Val_false;
rv = Val_bool (r);
CAMLreturn (rv);
}
@@ -868,3 +868,292 @@ ocaml_guestfs_read_lines (value gv, value pathv)
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_init (value gv, value rootv, value flagsv)
{
CAMLparam3 (gv, rootv, flagsv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_init: used handle after closing it");
const char *root = String_val (rootv);
int flags = Int_val (flagsv);
int r;
caml_enter_blocking_section ();
r = guestfs_aug_init (g, root, flags);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_init");
rv = Val_unit;
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_close (value gv)
{
CAMLparam1 (gv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_close: used handle after closing it");
int r;
caml_enter_blocking_section ();
r = guestfs_aug_close (g);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_close");
rv = Val_unit;
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_defvar (value gv, value namev, value exprv)
{
CAMLparam3 (gv, namev, exprv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_defvar: used handle after closing it");
const char *name = String_val (namev);
const char *expr =
exprv != Val_int (0) ? String_val (Field (exprv, 0)) : NULL;
int r;
caml_enter_blocking_section ();
r = guestfs_aug_defvar (g, name, expr);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_defvar");
rv = Val_int (r);
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_defnode (value gv, value namev, value exprv, value valv)
{
CAMLparam4 (gv, namev, exprv, valv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_defnode: used handle after closing it");
const char *name = String_val (namev);
const char *expr = String_val (exprv);
const char *val = String_val (valv);
struct guestfs_int_bool *r;
caml_enter_blocking_section ();
r = guestfs_aug_defnode (g, name, expr, val);
caml_leave_blocking_section ();
if (r == NULL)
ocaml_guestfs_raise_error (g, "aug_defnode");
rv = caml_alloc (2, 0);
Store_field (rv, 0, Val_int (r->i));
Store_field (rv, 1, Val_bool (r->b));
guestfs_free_int_bool (r);
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_get (value gv, value pathv)
{
CAMLparam2 (gv, pathv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_get: used handle after closing it");
const char *path = String_val (pathv);
char *r;
caml_enter_blocking_section ();
r = guestfs_aug_get (g, path);
caml_leave_blocking_section ();
if (r == NULL)
ocaml_guestfs_raise_error (g, "aug_get");
rv = caml_copy_string (r);
free (r);
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_set (value gv, value pathv, value valv)
{
CAMLparam3 (gv, pathv, valv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_set: used handle after closing it");
const char *path = String_val (pathv);
const char *val = String_val (valv);
int r;
caml_enter_blocking_section ();
r = guestfs_aug_set (g, path, val);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_set");
rv = Val_unit;
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_insert (value gv, value pathv, value labelv, value beforev)
{
CAMLparam4 (gv, pathv, labelv, beforev);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_insert: used handle after closing it");
const char *path = String_val (pathv);
const char *label = String_val (labelv);
int before = Bool_val (beforev);
int r;
caml_enter_blocking_section ();
r = guestfs_aug_insert (g, path, label, before);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_insert");
rv = Val_unit;
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_rm (value gv, value pathv)
{
CAMLparam2 (gv, pathv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_rm: used handle after closing it");
const char *path = String_val (pathv);
int r;
caml_enter_blocking_section ();
r = guestfs_aug_rm (g, path);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_rm");
rv = Val_int (r);
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_mv (value gv, value srcv, value destv)
{
CAMLparam3 (gv, srcv, destv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_mv: used handle after closing it");
const char *src = String_val (srcv);
const char *dest = String_val (destv);
int r;
caml_enter_blocking_section ();
r = guestfs_aug_mv (g, src, dest);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_mv");
rv = Val_unit;
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_match (value gv, value pathv)
{
CAMLparam2 (gv, pathv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_match: used handle after closing it");
const char *path = String_val (pathv);
int i;
char **r;
caml_enter_blocking_section ();
r = guestfs_aug_match (g, path);
caml_leave_blocking_section ();
if (r == NULL)
ocaml_guestfs_raise_error (g, "aug_match");
rv = caml_copy_string_array ((const char **) r);
for (i = 0; r[i] != NULL; ++i) free (r[i]);
free (r);
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_save (value gv)
{
CAMLparam1 (gv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_save: used handle after closing it");
int r;
caml_enter_blocking_section ();
r = guestfs_aug_save (g);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_save");
rv = Val_unit;
CAMLreturn (rv);
}
CAMLprim value
ocaml_guestfs_aug_load (value gv)
{
CAMLparam1 (gv);
CAMLlocal1 (rv);
guestfs_h *g = Guestfs_val (gv);
if (g == NULL)
caml_failwith ("aug_load: used handle after closing it");
int r;
caml_enter_blocking_section ();
r = guestfs_aug_load (g);
caml_leave_blocking_section ();
if (r == -1)
ocaml_guestfs_raise_error (g, "aug_load");
rv = Val_unit;
CAMLreturn (rv);
}

View File

@@ -485,3 +485,141 @@ PREINIT:
}
free (lines);
void
aug_init (g, root, flags)
guestfs_h *g;
char *root;
int flags;
PPCODE:
if (guestfs_aug_init (g, root, flags) == -1)
croak ("aug_init: %s", last_error);
void
aug_close (g)
guestfs_h *g;
PPCODE:
if (guestfs_aug_close (g) == -1)
croak ("aug_close: %s", last_error);
SV *
aug_defvar (g, name, expr)
guestfs_h *g;
char *name;
char *expr;
PREINIT:
int nrnodes;
CODE:
nrnodes = guestfs_aug_defvar (g, name, expr);
if (nrnodes == -1)
croak ("aug_defvar: %s", last_error);
RETVAL = newSViv (nrnodes);
OUTPUT:
RETVAL
void
aug_defnode (g, name, expr, val)
guestfs_h *g;
char *name;
char *expr;
char *val;
PREINIT:
struct guestfs_int_bool *r;
PPCODE:
r = guestfs_aug_defnode (g, name, expr, val);
if (r == NULL)
croak ("aug_defnode: %s", last_error);
EXTEND (SP, 2);
PUSHs (sv_2mortal (newSViv (r->i)));
PUSHs (sv_2mortal (newSViv (r->b)));
guestfs_free_int_bool (r);
SV *
aug_get (g, path)
guestfs_h *g;
char *path;
PREINIT:
char *val;
CODE:
val = guestfs_aug_get (g, path);
if (val == NULL)
croak ("aug_get: %s", last_error);
RETVAL = newSVpv (val, 0);
free (val);
OUTPUT:
RETVAL
void
aug_set (g, path, val)
guestfs_h *g;
char *path;
char *val;
PPCODE:
if (guestfs_aug_set (g, path, val) == -1)
croak ("aug_set: %s", last_error);
void
aug_insert (g, path, label, before)
guestfs_h *g;
char *path;
char *label;
int before;
PPCODE:
if (guestfs_aug_insert (g, path, label, before) == -1)
croak ("aug_insert: %s", last_error);
SV *
aug_rm (g, path)
guestfs_h *g;
char *path;
PREINIT:
int nrnodes;
CODE:
nrnodes = guestfs_aug_rm (g, path);
if (nrnodes == -1)
croak ("aug_rm: %s", last_error);
RETVAL = newSViv (nrnodes);
OUTPUT:
RETVAL
void
aug_mv (g, src, dest)
guestfs_h *g;
char *src;
char *dest;
PPCODE:
if (guestfs_aug_mv (g, src, dest) == -1)
croak ("aug_mv: %s", last_error);
void
aug_match (g, path)
guestfs_h *g;
char *path;
PREINIT:
char **matches;
int i, n;
PPCODE:
matches = guestfs_aug_match (g, path);
if (matches == NULL)
croak ("aug_match: %s", last_error);
for (n = 0; matches[n] != NULL; ++n) /**/;
EXTEND (SP, n);
for (i = 0; i < n; ++i) {
PUSHs (sv_2mortal (newSVpv (matches[i], 0)));
free (matches[i]);
}
free (matches);
void
aug_save (g)
guestfs_h *g;
PPCODE:
if (guestfs_aug_save (g) == -1)
croak ("aug_save: %s", last_error);
void
aug_load (g)
guestfs_h *g;
PPCODE:
if (guestfs_aug_load (g) == -1)
croak ("aug_load: %s", last_error);

View File

@@ -112,6 +112,134 @@ image).
This is equivalent to the qemu parameter C<-drive file=filename>.
=item $h->aug_close ();
Close the current Augeas handle and free up any resources
used by it. After calling this, you have to call
C<$h-E<gt>aug_init> again before you can use any other
Augeas functions.
=item ($nrnodes, $created) = $h->aug_defnode (name, expr, val);
Defines a variable C<name> whose value is the result of
evaluating C<expr>.
If C<expr> evaluates to an empty nodeset, a node is created,
equivalent to calling C<$h-E<gt>aug_set> C<expr>, C<value>.
C<name> will be the nodeset containing that single node.
On success this returns a pair containing the
number of nodes in the nodeset, and a boolean flag
if a node was created.
=item $nrnodes = $h->aug_defvar (name, expr);
Defines an Augeas variable C<name> whose value is the result
of evaluating C<expr>. If C<expr> is NULL, then C<name> is
undefined.
On success this returns the number of nodes in C<expr>, or
C<0> if C<expr> evaluates to something which is not a nodeset.
=item $val = $h->aug_get (path);
Look up the value associated with C<path>. If C<path>
matches exactly one node, the C<value> is returned.
=item $h->aug_init (root, flags);
Create a new Augeas handle for editing configuration files.
If there was any previous Augeas handle associated with this
guestfs session, then it is closed.
You must call this before using any other C<$h-E<gt>aug_*>
commands.
C<root> is the filesystem root. C<root> must not be NULL,
use C</> instead.
The flags are the same as the flags defined in
E<lt>augeas.hE<gt>, the logical I<or> of the following
integers:
=over 4
=item 1 C<AUG_SAVE_BACKUP>
Keep the original file with a C<.augsave> extension.
=item 2 C<AUG_SAVE_NEWFILE>
Save changes into a file with extension C<.augnew>, and
do not overwrite original. Overrides C<AUG_SAVE_BACKUP>.
=item 4 C<AUG_TYPE_CHECK>
Typecheck lenses (can be expensive).
=item 8 C<AUG_NO_STDINC>
Do not use standard load path for modules.
=item 16 C<AUG_SAVE_NOOP>
Make save a no-op, just record what would have been changed.
=item 32 C<AUG_NO_LOAD>
Do not load the tree in C<$h-E<gt>aug_init>.
=back
To close the handle, you can call C<$h-E<gt>aug_close>.
To find out more about Augeas, see L<http://augeas.net/>.
=item $h->aug_insert (path, label, before);
Create a new sibling C<label> for C<path>, inserting it into
the tree before or after C<path> (depending on the boolean
flag C<before>).
C<path> must match exactly one existing node in the tree, and
C<label> must be a label, ie. not contain C</>, C<*> or end
with a bracketed index C<[N]>.
=item $h->aug_load ();
Load files into the tree.
See C<aug_load> in the Augeas documentation for the full gory
details.
=item @matches = $h->aug_match (path);
Returns a list of paths which match the path expression C<path>.
The returned paths are sufficiently qualified so that they match
exactly one node in the current tree.
=item $h->aug_mv (src, dest);
Move the node C<src> to C<dest>. C<src> must match exactly
one node. C<dest> is overwritten if it exists.
=item $nrnodes = $h->aug_rm (path);
Remove C<path> and all of its children.
On success this returns the number of entries which were removed.
=item $h->aug_save ();
This writes all pending changes to disk.
The flags which were passed to C<$h-E<gt>aug_init> affect exactly
how files are saved.
=item $h->aug_set (path, val);
Set the value associated with C<path> to C<value>.
=item $content = $h->cat (path);
Return the contents of the file named C<path>.

View File

@@ -32,17 +32,25 @@ and ret =
* indication, ie. 0 or -1.
*)
| Err
(* "Int" as a return value means an int which is -1 for error
* or any value >= 0 on success.
*)
| RInt of string
(* "RBool" is a bool return value which can be true/false or
* -1 for error.
*)
| RBool of string
(* "RConstString" is a string that refers to a constant value.
* Try to avoid using this.
* Try to avoid using this. In particular you cannot use this
* for values returned from the daemon, because there is no
* thread-safe way to return them in the C API.
*)
| RConstString of string
(* "RString" and "RStringList" are caller-frees. *)
| RString of string
| RStringList of string
(* Some limited tuples are possible: *)
| RIntBool of string * string
(* LVM PVs, VGs and LVs. *)
| RPVList of string
| RVGList of string
@@ -52,10 +60,12 @@ and args =
| P0
| P1 of argt
| P2 of argt * argt
| P3 of argt * argt * argt
and argt =
| String of string (* const char *name, cannot be NULL *)
| OptString of string (* const char *name, may be NULL *)
| Bool of string (* boolean *)
| Int of string (* int (smallish ints, signed, <= 31 bits) *)
type flags =
| ProtocolLimitWarning (* display warning about protocol size limits *)
@@ -323,6 +333,146 @@ Note that this function cannot correctly handle binary files
(specifically, files containing C<\\0> character which is treated
as end of line). For those you need to use the C<guestfs_read_file>
function which has a more complex interface.");
("aug_init", (Err, P2 (String "root", Int "flags")), 16, [],
"create a new Augeas handle",
"\
Create a new Augeas handle for editing configuration files.
If there was any previous Augeas handle associated with this
guestfs session, then it is closed.
You must call this before using any other C<guestfs_aug_*>
commands.
C<root> is the filesystem root. C<root> must not be NULL,
use C</> instead.
The flags are the same as the flags defined in
E<lt>augeas.hE<gt>, the logical I<or> of the following
integers:
=over 4
=item 1 C<AUG_SAVE_BACKUP>
Keep the original file with a C<.augsave> extension.
=item 2 C<AUG_SAVE_NEWFILE>
Save changes into a file with extension C<.augnew>, and
do not overwrite original. Overrides C<AUG_SAVE_BACKUP>.
=item 4 C<AUG_TYPE_CHECK>
Typecheck lenses (can be expensive).
=item 8 C<AUG_NO_STDINC>
Do not use standard load path for modules.
=item 16 C<AUG_SAVE_NOOP>
Make save a no-op, just record what would have been changed.
=item 32 C<AUG_NO_LOAD>
Do not load the tree in C<guestfs_aug_init>.
=back
To close the handle, you can call C<guestfs_aug_close>.
To find out more about Augeas, see L<http://augeas.net/>.");
("aug_close", (Err, P0), 26, [],
"close the current Augeas handle",
"\
Close the current Augeas handle and free up any resources
used by it. After calling this, you have to call
C<guestfs_aug_init> again before you can use any other
Augeas functions.");
("aug_defvar", (RInt "nrnodes", P2 (String "name", OptString "expr")), 17, [],
"define an Augeas variable",
"\
Defines an Augeas variable C<name> whose value is the result
of evaluating C<expr>. If C<expr> is NULL, then C<name> is
undefined.
On success this returns the number of nodes in C<expr>, or
C<0> if C<expr> evaluates to something which is not a nodeset.");
("aug_defnode", (RIntBool ("nrnodes", "created"), P3 (String "name", String "expr", String "val")), 18, [],
"define an Augeas node",
"\
Defines a variable C<name> whose value is the result of
evaluating C<expr>.
If C<expr> evaluates to an empty nodeset, a node is created,
equivalent to calling C<guestfs_aug_set> C<expr>, C<value>.
C<name> will be the nodeset containing that single node.
On success this returns a pair containing the
number of nodes in the nodeset, and a boolean flag
if a node was created.");
("aug_get", (RString "val", P1 (String "path")), 19, [],
"look up the value of an Augeas path",
"\
Look up the value associated with C<path>. If C<path>
matches exactly one node, the C<value> is returned.");
("aug_set", (Err, P2 (String "path", String "val")), 20, [],
"set Augeas path to value",
"\
Set the value associated with C<path> to C<value>.");
("aug_insert", (Err, P3 (String "path", String "label", Bool "before")), 21, [],
"insert a sibling Augeas node",
"\
Create a new sibling C<label> for C<path>, inserting it into
the tree before or after C<path> (depending on the boolean
flag C<before>).
C<path> must match exactly one existing node in the tree, and
C<label> must be a label, ie. not contain C</>, C<*> or end
with a bracketed index C<[N]>.");
("aug_rm", (RInt "nrnodes", P1 (String "path")), 22, [],
"remove an Augeas path",
"\
Remove C<path> and all of its children.
On success this returns the number of entries which were removed.");
("aug_mv", (Err, P2 (String "src", String "dest")), 23, [],
"move Augeas node",
"\
Move the node C<src> to C<dest>. C<src> must match exactly
one node. C<dest> is overwritten if it exists.");
("aug_match", (RStringList "matches", P1 (String "path")), 24, [],
"return Augeas nodes which match path",
"\
Returns a list of paths which match the path expression C<path>.
The returned paths are sufficiently qualified so that they match
exactly one node in the current tree.");
("aug_save", (Err, P0), 25, [],
"write all pending Augeas changes to disk",
"\
This writes all pending changes to disk.
The flags which were passed to C<guestfs_aug_init> affect exactly
how files are saved.");
("aug_load", (Err, P0), 27, [],
"load files into the tree",
"\
Load files into the tree.
See C<aug_load> in the Augeas documentation for the full gory
details.");
]
let all_functions = non_daemon_functions @ daemon_functions
@@ -465,18 +615,25 @@ let iter_args f = function
| P0 -> ()
| P1 arg1 -> f arg1
| P2 (arg1, arg2) -> f arg1; f arg2
| P3 (arg1, arg2, arg3) -> f arg1; f arg2; f arg3
let iteri_args f = function
| P0 -> ()
| P1 arg1 -> f 0 arg1
| P2 (arg1, arg2) -> f 0 arg1; f 1 arg2
| P3 (arg1, arg2, arg3) -> f 0 arg1; f 1 arg2; f 2 arg3
let map_args f = function
| P0 -> []
| P1 arg1 -> [f arg1]
| P2 (arg1, arg2) -> [f arg1; f arg2]
| P2 (arg1, arg2) ->
let n1 = f arg1 in let n2 = f arg2 in [n1; n2]
| P3 (arg1, arg2, arg3) ->
let n1 = f arg1 in let n2 = f arg2 in let n3 = f arg3 in [n1; n2; n3]
let nr_args = function | P0 -> 0 | P1 _ -> 1 | P2 _ -> 2
let nr_args = function | P0 -> 0 | P1 _ -> 1 | P2 _ -> 2 | P3 _ -> 3
let name_of_argt = function String n | OptString n | Bool n | Int n -> n
(* Check function names etc. for consistency. *)
let check_functions () =
@@ -583,6 +740,8 @@ and generate_actions_pod () =
(match fst style with
| Err ->
pr "This function returns 0 on success or -1 on error.\n\n"
| RInt _ ->
pr "On error this function returns -1.\n\n"
| RBool _ ->
pr "This function returns a C truth value on success or -1 on error.\n\n"
| RConstString _ ->
@@ -595,14 +754,17 @@ I<The caller must free the returned string after use>.\n\n"
pr "This function returns a NULL-terminated array of strings
(like L<environ(3)>), or NULL if there was an error.
I<The caller must free the strings and the array after use>.\n\n"
| RIntBool _ ->
pr "This function returns a C<struct guestfs_int_bool *>.
I<The caller must call C<guestfs_free_int_bool> after use.>.\n\n"
| RPVList _ ->
pr "This function returns a C<struct guestfs_lvm_pv_list>.
pr "This function returns a C<struct guestfs_lvm_pv_list *>.
I<The caller must call C<guestfs_free_lvm_pv_list> after use.>.\n\n"
| RVGList _ ->
pr "This function returns a C<struct guestfs_lvm_vg_list>.
pr "This function returns a C<struct guestfs_lvm_vg_list *>.
I<The caller must call C<guestfs_free_lvm_vg_list> after use.>.\n\n"
| RLVList _ ->
pr "This function returns a C<struct guestfs_lvm_lv_list>.
pr "This function returns a C<struct guestfs_lvm_lv_list *>.
I<The caller must call C<guestfs_free_lvm_lv_list> after use.>.\n\n"
);
if List.mem ProtocolLimitWarning flags then
@@ -676,21 +838,26 @@ and generate_xdr () =
List.iter (
fun(shortname, style, _, _, _, _) ->
let name = "guestfs_" ^ shortname in
pr "/* %s */\n\n" name;
(match snd style with
| P0 -> ()
| args ->
pr "struct %s_args {\n" name;
iter_args (
function
| String name -> pr " string %s<>;\n" name
| OptString name -> pr " string *%s<>;\n" name
| Bool name -> pr " bool %s;\n" name
| String n -> pr " string %s<>;\n" n
| OptString n -> pr " str *%s;\n" n
| Bool n -> pr " bool %s;\n" n
| Int n -> pr " int %s;\n" n
) args;
pr "};\n\n"
);
(match fst style with
| Err -> ()
| RInt n ->
pr "struct %s_ret {\n" name;
pr " int %s;\n" n;
pr "};\n\n"
| RBool n ->
pr "struct %s_ret {\n" name;
pr " bool %s;\n" n;
@@ -705,6 +872,11 @@ and generate_xdr () =
pr "struct %s_ret {\n" name;
pr " str %s<>;\n" n;
pr "};\n\n"
| RIntBool (n,m) ->
pr "struct %s_ret {\n" name;
pr " int %s;\n" n;
pr " bool %s;\n" m;
pr "};\n\n"
| RPVList n ->
pr "struct %s_ret {\n" name;
pr " guestfs_lvm_int_pv_list %s;\n" n;
@@ -788,6 +960,13 @@ and generate_structs_h () =
* must be identical to what rpcgen / the RFC defines.
*)
(* guestfs_int_bool structure. *)
pr "struct guestfs_int_bool {\n";
pr " int32_t i;\n";
pr " int32_t b;\n";
pr "};\n";
pr "\n";
(* LVM public structures. *)
List.iter (
function
@@ -838,7 +1017,9 @@ and generate_client_actions () =
| Err -> ()
| RConstString _ ->
failwithf "RConstString cannot be returned from a daemon function"
| RInt _
| RBool _ | RString _ | RStringList _
| RIntBool _
| RPVList _ | RVGList _ | RLVList _ ->
pr " struct %s_ret ret;\n" name
);
@@ -865,7 +1046,9 @@ and generate_client_actions () =
| Err -> ()
| RConstString _ ->
failwithf "RConstString cannot be returned from a daemon function"
| RInt _
| RBool _ | RString _ | RStringList _
| RIntBool _
| RPVList _ | RVGList _ | RLVList _ ->
pr " if (!xdr_%s_ret (xdr, &rv->ret)) {\n" name;
pr " error (g, \"%s: failed to parse reply\");\n" name;
@@ -884,10 +1067,11 @@ and generate_client_actions () =
let error_code =
match fst style with
| Err | RBool _ -> "-1"
| Err | RInt _ | RBool _ -> "-1"
| RConstString _ ->
failwithf "RConstString cannot be returned from a daemon function"
| RString _ | RStringList _ | RPVList _ | RVGList _ | RLVList _ ->
| RString _ | RStringList _ | RIntBool _
| RPVList _ | RVGList _ | RLVList _ ->
"NULL" in
pr "{\n";
@@ -917,12 +1101,14 @@ and generate_client_actions () =
| args ->
iter_args (
function
| String name ->
pr " args.%s = (char *) %s;\n" name name
| OptString name ->
pr " args.%s = %s ? *%s : NULL;\n" name name name
| Bool name ->
pr " args.%s = %s;\n" name name
| String n ->
pr " args.%s = (char *) %s;\n" n n
| OptString n ->
pr " args.%s = %s ? (char **) &%s : NULL;\n" n n n
| Bool n ->
pr " args.%s = %s;\n" n n
| Int n ->
pr " args.%s = %s;\n" n n
) args;
pr " serial = dispatch (g, GUESTFS_PROC_%s,\n"
(String.uppercase shortname);
@@ -958,6 +1144,7 @@ and generate_client_actions () =
(match fst style with
| Err -> pr " return 0;\n"
| RInt n
| RBool n -> pr " return rv.ret.%s;\n" n
| RConstString _ ->
failwithf "RConstString cannot be returned from a daemon function"
@@ -971,6 +1158,9 @@ and generate_client_actions () =
n n;
pr " rv.ret.%s.%s_val[rv.ret.%s.%s_len] = NULL;\n" n n n n;
pr " return rv.ret.%s.%s_val;\n" n n
| RIntBool _ ->
pr " /* caller with free this */\n";
pr " return safe_memdup (g, &rv.ret, sizeof (rv.ret));\n"
| RPVList n ->
pr " /* caller will free this */\n";
pr " return safe_memdup (g, &rv.ret.%s, sizeof (rv.ret.%s));\n" n n
@@ -995,7 +1185,8 @@ and generate_daemon_actions_h () =
List.iter (
fun (name, style, _, _, _, _) ->
generate_prototype
~single_line:true ~newline:true ~in_daemon:true ("do_" ^ name) style;
~single_line:true ~newline:true ~in_daemon:true ~prefix:"do_"
name style;
) daemon_functions
(* Generate the server-side stubs. *)
@@ -1024,12 +1215,13 @@ and generate_daemon_actions () =
pr "{\n";
let error_code =
match fst style with
| Err -> pr " int r;\n"; "-1"
| Err | RInt _ -> pr " int r;\n"; "-1"
| RBool _ -> pr " int r;\n"; "-1"
| RConstString _ ->
failwithf "RConstString cannot be returned from a daemon function"
| RString _ -> pr " char *r;\n"; "NULL"
| RStringList _ -> pr " char **r;\n"; "NULL"
| RIntBool _ -> pr " guestfs_%s_ret *r;\n" name; "NULL"
| RPVList _ -> pr " guestfs_lvm_int_pv_list *r;\n"; "NULL"
| RVGList _ -> pr " guestfs_lvm_int_vg_list *r;\n"; "NULL"
| RLVList _ -> pr " guestfs_lvm_int_lv_list *r;\n"; "NULL" in
@@ -1040,9 +1232,10 @@ and generate_daemon_actions () =
pr " struct guestfs_%s_args args;\n" name;
iter_args (
function
| String name
| OptString name -> pr " const char *%s;\n" name
| Bool name -> pr " int %s;\n" name
| String n
| OptString n -> pr " const char *%s;\n" n
| Bool n -> pr " int %s;\n" n
| Int n -> pr " int %s;\n" n
) args
);
pr "\n";
@@ -1053,14 +1246,15 @@ and generate_daemon_actions () =
pr " memset (&args, 0, sizeof args);\n";
pr "\n";
pr " if (!xdr_guestfs_%s_args (xdr_in, &args)) {\n" name;
pr " reply_with_error (\"%s: daemon failed to decode procedure arguments\");\n" name;
pr " reply_with_error (\"%%s: daemon failed to decode procedure arguments\", \"%s\");\n" name;
pr " return;\n";
pr " }\n";
iter_args (
function
| String name -> pr " %s = args.%s;\n" name name
| OptString name -> pr " %s = args.%s;\n" name name (* XXX? *)
| Bool name -> pr " %s = args.%s;\n" name name
| String n -> pr " %s = args.%s;\n" n n
| OptString n -> pr " %s = args.%s ? *args.%s : NULL;\n" n n n
| Bool n -> pr " %s = args.%s;\n" n n
| Int n -> pr " %s = args.%s;\n" n n
) args;
pr "\n"
);
@@ -1076,6 +1270,10 @@ and generate_daemon_actions () =
(match fst style with
| Err -> pr " reply (NULL, NULL);\n"
| RInt n ->
pr " struct guestfs_%s_ret ret;\n" name;
pr " ret.%s = r;\n" n;
pr " reply ((xdrproc_t) &xdr_guestfs_%s_ret, (char *) &ret);\n" name
| RBool n ->
pr " struct guestfs_%s_ret ret;\n" name;
pr " ret.%s = r;\n" n;
@@ -1093,20 +1291,23 @@ and generate_daemon_actions () =
pr " ret.%s.%s_val = r;\n" n n;
pr " reply ((xdrproc_t) &xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " free_strings (r);\n"
| RIntBool _ ->
pr " reply ((xdrproc_t) xdr_guestfs_%s_ret, (char *) r);\n" name;
pr " xdr_free ((xdrproc_t) xdr_guestfs_%s_ret, (char *) r);\n" name
| RPVList n ->
pr " struct guestfs_%s_ret ret;\n" name;
pr " ret.%s = *r;\n" n;
pr " reply ((xdrproc_t) &xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " reply ((xdrproc_t) xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " xdr_free ((xdrproc_t) xdr_guestfs_%s_ret, (char *) &ret);\n" name
| RVGList n ->
pr " struct guestfs_%s_ret ret;\n" name;
pr " ret.%s = *r;\n" n;
pr " reply ((xdrproc_t) &xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " reply ((xdrproc_t) xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " xdr_free ((xdrproc_t) xdr_guestfs_%s_ret, (char *) &ret);\n" name
| RLVList n ->
pr " struct guestfs_%s_ret ret;\n" name;
pr " ret.%s = *r;\n" n;
pr " reply ((xdrproc_t) &xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " reply ((xdrproc_t) xdr_guestfs_%s_ret, (char *) &ret);\n" name;
pr " xdr_free ((xdrproc_t) xdr_guestfs_%s_ret, (char *) &ret);\n" name
);
@@ -1348,12 +1549,7 @@ and generate_fish_cmds () =
| P0 -> name2
| args ->
sprintf "%s <%s>"
name2 (
String.concat "> <" (
map_args (function
| String n | OptString n | Bool n -> n) args
)
) in
name2 (String.concat "> <" (map_args name_of_argt args)) in
let warnings =
if List.mem ProtocolLimitWarning flags then
@@ -1429,19 +1625,22 @@ FTP."
pr "{\n";
(match fst style with
| Err
| RInt _
| RBool _ -> pr " int r;\n"
| RConstString _ -> pr " const char *r;\n"
| RString _ -> pr " char *r;\n"
| RStringList _ -> pr " char **r;\n"
| RIntBool _ -> pr " struct guestfs_int_bool *r;\n"
| RPVList _ -> pr " struct guestfs_lvm_pv_list *r;\n"
| RVGList _ -> pr " struct guestfs_lvm_vg_list *r;\n"
| RLVList _ -> pr " struct guestfs_lvm_lv_list *r;\n"
);
iter_args (
function
| String name -> pr " const char *%s;\n" name
| OptString name -> pr " const char *%s;\n" name
| Bool name -> pr " int %s;\n" name
| String n -> pr " const char *%s;\n" n
| OptString n -> pr " const char *%s;\n" n
| Bool n -> pr " int %s;\n" n
| Int n -> pr " int %s;\n" n
) (snd style);
(* Check and convert parameters. *)
@@ -1461,6 +1660,8 @@ FTP."
name i i
| Bool name ->
pr " %s = is_true (argv[%d]) ? 1 : 0;\n" name i
| Int name ->
pr " %s = atoi (argv[%d]);\n" name i
) (snd style);
(* Call C API function. *)
@@ -1474,6 +1675,10 @@ FTP."
(* Check return value for errors and display command results. *)
(match fst style with
| Err -> pr " return r;\n"
| RInt _ ->
pr " if (r == -1) return -1;\n";
pr " if (r) printf (\"%%d\\n\", r);\n";
pr " return 0;\n"
| RBool _ ->
pr " if (r == -1) return -1;\n";
pr " if (r) printf (\"true\\n\"); else printf (\"false\\n\");\n";
@@ -1492,6 +1697,12 @@ FTP."
pr " print_strings (r);\n";
pr " free_strings (r);\n";
pr " return 0;\n"
| RIntBool _ ->
pr " if (r == NULL) return -1;\n";
pr " printf (\"%%d, %%s\\n\", r->i,\n";
pr " r->b ? \"true\" : \"false\");\n";
pr " guestfs_free_int_bool (r);\n";
pr " return 0;\n"
| RPVList _ ->
pr " if (r == NULL) return -1;\n";
pr " print_pv_list (r);\n";
@@ -1565,6 +1776,7 @@ and generate_fish_actions_pod () =
| String n -> pr " %s" n
| OptString n -> pr " %s" n
| Bool _ -> pr " true|false"
| Int n -> pr " %s" n
) (snd style);
pr "\n";
pr "\n";
@@ -1574,15 +1786,20 @@ and generate_fish_actions_pod () =
(* Generate a C function prototype. *)
and generate_prototype ?(extern = true) ?(static = false) ?(semicolon = true)
?(single_line = false) ?(newline = false) ?(in_daemon = false)
?(prefix = "")
?handle name style =
if extern then pr "extern ";
if static then pr "static ";
(match fst style with
| Err -> pr "int "
| RInt _ -> pr "int "
| RBool _ -> pr "int "
| RConstString _ -> pr "const char *"
| RString _ -> pr "char *"
| RStringList _ -> pr "char **"
| RIntBool _ ->
if not in_daemon then pr "struct guestfs_int_bool *"
else pr "guestfs_%s_ret *" name
| RPVList _ ->
if not in_daemon then pr "struct guestfs_lvm_pv_list *"
else pr "guestfs_lvm_int_pv_list *"
@@ -1593,24 +1810,29 @@ and generate_prototype ?(extern = true) ?(static = false) ?(semicolon = true)
if not in_daemon then pr "struct guestfs_lvm_lv_list *"
else pr "guestfs_lvm_int_lv_list *"
);
pr "%s (" name;
let comma = ref false in
(match handle with
| None -> ()
| Some handle -> pr "guestfs_h *%s" handle; comma := true
);
let next () =
if !comma then (
if single_line then pr ", " else pr ",\n\t\t"
pr "%s%s (" prefix name;
if handle = None && nr_args (snd style) = 0 then
pr "void"
else (
let comma = ref false in
(match handle with
| None -> ()
| Some handle -> pr "guestfs_h *%s" handle; comma := true
);
comma := true
in
iter_args (
function
| String name -> next (); pr "const char *%s" name
| OptString name -> next (); pr "const char *%s" name
| Bool name -> next (); pr "int %s" name
) (snd style);
let next () =
if !comma then (
if single_line then pr ", " else pr ",\n\t\t"
);
comma := true
in
iter_args (
function
| String n -> next (); pr "const char *%s" n
| OptString n -> next (); pr "const char *%s" n
| Bool n -> next (); pr "int %s" n
| Int n -> next (); pr "int %s" n
) (snd style);
);
pr ")";
if semicolon then pr ";";
if newline then pr "\n"
@@ -1628,9 +1850,10 @@ and generate_call_args ?handle style =
if !comma then pr ", ";
comma := true;
match arg with
| String name -> pr "%s" name
| OptString name -> pr "%s" name
| Bool name -> pr "%s" name
| String n -> pr "%s" n
| OptString n -> pr "%s" n
| Bool n -> pr "%s" n
| Int n -> pr "%s" n
) (snd style);
pr ")"
@@ -1779,15 +2002,13 @@ and generate_ocaml_c () =
pr "CAMLprim value\n";
pr "ocaml_guestfs_%s (value gv" name;
iter_args (
function
| String n | OptString n | Bool n -> pr ", value %sv" n
fun arg -> pr ", value %sv" (name_of_argt arg)
) (snd style);
pr ")\n";
pr "{\n";
pr " CAMLparam%d (gv" (1 + (nr_args (snd style)));
iter_args (
function
| String n | OptString n | Bool n -> pr ", %sv" n
fun arg -> pr ", %sv" (name_of_argt arg)
) (snd style);
pr ");\n";
pr " CAMLlocal1 (rv);\n";
@@ -1808,10 +2029,13 @@ and generate_ocaml_c () =
n n
| Bool n ->
pr " int %s = Bool_val (%sv);\n" n n
| Int n ->
pr " int %s = Int_val (%sv);\n" n n
) (snd style);
let error_code =
match fst style with
| Err -> pr " int r;\n"; "-1"
| RInt _ -> pr " int r;\n"; "-1"
| RBool _ -> pr " int r;\n"; "-1"
| RConstString _ -> pr " const char *r;\n"; "NULL"
| RString _ -> pr " char *r;\n"; "NULL"
@@ -1819,6 +2043,9 @@ and generate_ocaml_c () =
pr " int i;\n";
pr " char **r;\n";
"NULL"
| RIntBool _ ->
pr " struct guestfs_int_bool *r;\n";
"NULL"
| RPVList _ ->
pr " struct guestfs_lvm_pv_list *r;\n";
"NULL"
@@ -1841,7 +2068,8 @@ and generate_ocaml_c () =
(match fst style with
| Err -> pr " rv = Val_unit;\n"
| RBool _ -> pr " rv = r ? Val_true : Val_false;\n"
| RInt _ -> pr " rv = Val_int (r);\n"
| RBool _ -> pr " rv = Val_bool (r);\n"
| RConstString _ -> pr " rv = caml_copy_string (r);\n"
| RString _ ->
pr " rv = caml_copy_string (r);\n";
@@ -1850,6 +2078,11 @@ and generate_ocaml_c () =
pr " rv = caml_copy_string_array ((const char **) r);\n";
pr " for (i = 0; r[i] != NULL; ++i) free (r[i]);\n";
pr " free (r);\n"
| RIntBool _ ->
pr " rv = caml_alloc (2, 0);\n";
pr " Store_field (rv, 0, Val_int (r->i));\n";
pr " Store_field (rv, 1, Val_bool (r->b));\n";
pr " guestfs_free_int_bool (r);\n";
| RPVList _ ->
pr " rv = copy_lvm_pv_list (r);\n";
pr " guestfs_free_lvm_pv_list (r);\n";
@@ -1890,13 +2123,16 @@ and generate_ocaml_prototype ?(is_external = false) name style =
| String _ -> pr "string -> "
| OptString _ -> pr "string option -> "
| Bool _ -> pr "bool -> "
| Int _ -> pr "int -> "
) (snd style);
(match fst style with
| Err -> pr "unit" (* all errors are turned into exceptions *)
| RInt _ -> pr "int"
| RBool _ -> pr "bool"
| RConstString _ -> pr "string"
| RString _ -> pr "string"
| RStringList _ -> pr "string array"
| RIntBool _ -> pr "int * bool"
| RPVList _ -> pr "lvm_pv array"
| RVGList _ -> pr "lvm_vg array"
| RLVList _ -> pr "lvm_lv array"
@@ -1987,10 +2223,12 @@ DESTROY (g)
fun (name, style, _, _, _, _) ->
(match fst style with
| Err -> pr "void\n"
| RInt _ -> pr "SV *\n"
| RBool _ -> pr "SV *\n"
| RConstString _ -> pr "SV *\n"
| RString _ -> pr "SV *\n"
| RStringList _
| RIntBool _
| RPVList _ | RVGList _ | RLVList _ ->
pr "void\n" (* all lists returned implictly on the stack *)
);
@@ -2004,6 +2242,7 @@ DESTROY (g)
| String n -> pr " char *%s;\n" n
| OptString n -> pr " char *%s;\n" n
| Bool n -> pr " int %s;\n" n
| Int n -> pr " int %s;\n" n
) (snd style);
(* Code. *)
(match fst style with
@@ -2013,6 +2252,19 @@ DESTROY (g)
generate_call_args ~handle:"g" style;
pr " == -1)\n";
pr " croak (\"%s: %%s\", last_error);\n" name
| RInt n
| RBool n ->
pr "PREINIT:\n";
pr " int %s;\n" n;
pr " CODE:\n";
pr " %s = guestfs_%s " n name;
generate_call_args ~handle:"g" style;
pr ";\n";
pr " if (%s == -1)\n" n;
pr " croak (\"%s: %%s\", last_error);\n" name;
pr " RETVAL = newSViv (%s);\n" n;
pr " OUTPUT:\n";
pr " RETVAL\n"
| RConstString n ->
pr "PREINIT:\n";
pr " const char *%s;\n" n;
@@ -2038,18 +2290,6 @@ DESTROY (g)
pr " free (%s);\n" n;
pr " OUTPUT:\n";
pr " RETVAL\n"
| RBool n ->
pr "PREINIT:\n";
pr " int %s;\n" n;
pr " CODE:\n";
pr " %s = guestfs_%s " n name;
generate_call_args ~handle:"g" style;
pr ";\n";
pr " if (%s == -1)\n" n;
pr " croak (\"%s: %%s\", last_error);\n" name;
pr " RETVAL = newSViv (%s);\n" n;
pr " OUTPUT:\n";
pr " RETVAL\n"
| RStringList n ->
pr "PREINIT:\n";
pr " char **%s;\n" n;
@@ -2067,6 +2307,19 @@ DESTROY (g)
pr " free (%s[i]);\n" n;
pr " }\n";
pr " free (%s);\n" n;
| RIntBool _ ->
pr "PREINIT:\n";
pr " struct guestfs_int_bool *r;\n";
pr " PPCODE:\n";
pr " r = guestfs_%s " name;
generate_call_args ~handle:"g" style;
pr ";\n";
pr " if (r == NULL)\n";
pr " croak (\"%s: %%s\", last_error);\n" name;
pr " EXTEND (SP, 2);\n";
pr " PUSHs (sv_2mortal (newSViv (r->i)));\n";
pr " PUSHs (sv_2mortal (newSViv (r->b)));\n";
pr " guestfs_free_int_bool (r);\n";
| RPVList n ->
generate_perl_lvm_code "pv" pv_cols name style n;
| RVGList n ->
@@ -2236,8 +2489,10 @@ and generate_perl_prototype name style =
(match fst style with
| Err -> ()
| RBool n
| RInt n
| RConstString n
| RString n -> pr "$%s = " n
| RIntBool (n, m) -> pr "($%s, $%s) = " n m
| RStringList n
| RPVList n
| RVGList n
@@ -2249,10 +2504,7 @@ and generate_perl_prototype name style =
fun arg ->
if !comma then pr ", ";
comma := true;
match arg with
| String n -> pr "%s" n
| OptString n -> pr "%s" n
| Bool n -> pr "%s" n
pr "%s" (name_of_argt arg)
) (snd style);
pr ");"

View File

@@ -1111,3 +1111,865 @@ char **guestfs_read_lines (guestfs_h *g,
return rv.ret.lines.lines_val;
}
struct aug_init_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_init_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_init_rv *rv = (struct aug_init_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_init: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_init: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_init (guestfs_h *g,
const char *root,
int flags)
{
struct guestfs_aug_init_args args;
struct aug_init_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_init called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
args.root = (char *) root;
args.flags = flags;
serial = dispatch (g, GUESTFS_PROC_AUG_INIT,
(xdrproc_t) xdr_guestfs_aug_init_args, (char *) &args);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_init_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_init failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_INIT, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}
struct aug_close_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_close_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_close_rv *rv = (struct aug_close_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_close: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_close: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_close (guestfs_h *g)
{
struct aug_close_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_close called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
serial = dispatch (g, GUESTFS_PROC_AUG_CLOSE, NULL, NULL);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_close_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_close failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_CLOSE, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}
struct aug_defvar_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
struct guestfs_aug_defvar_ret ret;
};
static void aug_defvar_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_defvar_rv *rv = (struct aug_defvar_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_defvar: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_defvar: failed to parse reply error");
return;
}
goto done;
}
if (!xdr_guestfs_aug_defvar_ret (xdr, &rv->ret)) {
error (g, "guestfs_aug_defvar: failed to parse reply");
return;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_defvar (guestfs_h *g,
const char *name,
const char *expr)
{
struct guestfs_aug_defvar_args args;
struct aug_defvar_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_defvar called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
args.name = (char *) name;
args.expr = expr ? (char **) &expr : NULL;
serial = dispatch (g, GUESTFS_PROC_AUG_DEFVAR,
(xdrproc_t) xdr_guestfs_aug_defvar_args, (char *) &args);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_defvar_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_defvar failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_DEFVAR, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return rv.ret.nrnodes;
}
struct aug_defnode_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
struct guestfs_aug_defnode_ret ret;
};
static void aug_defnode_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_defnode_rv *rv = (struct aug_defnode_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_defnode: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_defnode: failed to parse reply error");
return;
}
goto done;
}
if (!xdr_guestfs_aug_defnode_ret (xdr, &rv->ret)) {
error (g, "guestfs_aug_defnode: failed to parse reply");
return;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
struct guestfs_int_bool *guestfs_aug_defnode (guestfs_h *g,
const char *name,
const char *expr,
const char *val)
{
struct guestfs_aug_defnode_args args;
struct aug_defnode_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_defnode called from the wrong state, %d != READY",
g->state);
return NULL;
}
memset (&rv, 0, sizeof rv);
args.name = (char *) name;
args.expr = (char *) expr;
args.val = (char *) val;
serial = dispatch (g, GUESTFS_PROC_AUG_DEFNODE,
(xdrproc_t) xdr_guestfs_aug_defnode_args, (char *) &args);
if (serial == -1)
return NULL;
rv.cb_done = 0;
g->reply_cb_internal = aug_defnode_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_defnode failed, see earlier error messages");
return NULL;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_DEFNODE, serial) == -1)
return NULL;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return NULL;
}
/* caller with free this */
return safe_memdup (g, &rv.ret, sizeof (rv.ret));
}
struct aug_get_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
struct guestfs_aug_get_ret ret;
};
static void aug_get_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_get_rv *rv = (struct aug_get_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_get: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_get: failed to parse reply error");
return;
}
goto done;
}
if (!xdr_guestfs_aug_get_ret (xdr, &rv->ret)) {
error (g, "guestfs_aug_get: failed to parse reply");
return;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
char *guestfs_aug_get (guestfs_h *g,
const char *path)
{
struct guestfs_aug_get_args args;
struct aug_get_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_get called from the wrong state, %d != READY",
g->state);
return NULL;
}
memset (&rv, 0, sizeof rv);
args.path = (char *) path;
serial = dispatch (g, GUESTFS_PROC_AUG_GET,
(xdrproc_t) xdr_guestfs_aug_get_args, (char *) &args);
if (serial == -1)
return NULL;
rv.cb_done = 0;
g->reply_cb_internal = aug_get_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_get failed, see earlier error messages");
return NULL;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_GET, serial) == -1)
return NULL;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return NULL;
}
return rv.ret.val; /* caller will free */
}
struct aug_set_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_set_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_set_rv *rv = (struct aug_set_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_set: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_set: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_set (guestfs_h *g,
const char *path,
const char *val)
{
struct guestfs_aug_set_args args;
struct aug_set_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_set called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
args.path = (char *) path;
args.val = (char *) val;
serial = dispatch (g, GUESTFS_PROC_AUG_SET,
(xdrproc_t) xdr_guestfs_aug_set_args, (char *) &args);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_set_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_set failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_SET, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}
struct aug_insert_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_insert_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_insert_rv *rv = (struct aug_insert_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_insert: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_insert: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_insert (guestfs_h *g,
const char *path,
const char *label,
int before)
{
struct guestfs_aug_insert_args args;
struct aug_insert_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_insert called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
args.path = (char *) path;
args.label = (char *) label;
args.before = before;
serial = dispatch (g, GUESTFS_PROC_AUG_INSERT,
(xdrproc_t) xdr_guestfs_aug_insert_args, (char *) &args);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_insert_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_insert failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_INSERT, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}
struct aug_rm_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
struct guestfs_aug_rm_ret ret;
};
static void aug_rm_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_rm_rv *rv = (struct aug_rm_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_rm: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_rm: failed to parse reply error");
return;
}
goto done;
}
if (!xdr_guestfs_aug_rm_ret (xdr, &rv->ret)) {
error (g, "guestfs_aug_rm: failed to parse reply");
return;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_rm (guestfs_h *g,
const char *path)
{
struct guestfs_aug_rm_args args;
struct aug_rm_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_rm called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
args.path = (char *) path;
serial = dispatch (g, GUESTFS_PROC_AUG_RM,
(xdrproc_t) xdr_guestfs_aug_rm_args, (char *) &args);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_rm_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_rm failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_RM, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return rv.ret.nrnodes;
}
struct aug_mv_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_mv_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_mv_rv *rv = (struct aug_mv_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_mv: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_mv: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_mv (guestfs_h *g,
const char *src,
const char *dest)
{
struct guestfs_aug_mv_args args;
struct aug_mv_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_mv called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
args.src = (char *) src;
args.dest = (char *) dest;
serial = dispatch (g, GUESTFS_PROC_AUG_MV,
(xdrproc_t) xdr_guestfs_aug_mv_args, (char *) &args);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_mv_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_mv failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_MV, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}
struct aug_match_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
struct guestfs_aug_match_ret ret;
};
static void aug_match_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_match_rv *rv = (struct aug_match_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_match: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_match: failed to parse reply error");
return;
}
goto done;
}
if (!xdr_guestfs_aug_match_ret (xdr, &rv->ret)) {
error (g, "guestfs_aug_match: failed to parse reply");
return;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
char **guestfs_aug_match (guestfs_h *g,
const char *path)
{
struct guestfs_aug_match_args args;
struct aug_match_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_match called from the wrong state, %d != READY",
g->state);
return NULL;
}
memset (&rv, 0, sizeof rv);
args.path = (char *) path;
serial = dispatch (g, GUESTFS_PROC_AUG_MATCH,
(xdrproc_t) xdr_guestfs_aug_match_args, (char *) &args);
if (serial == -1)
return NULL;
rv.cb_done = 0;
g->reply_cb_internal = aug_match_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_match failed, see earlier error messages");
return NULL;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_MATCH, serial) == -1)
return NULL;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return NULL;
}
/* caller will free this, but we need to add a NULL entry */
rv.ret.matches.matches_val = safe_realloc (g, rv.ret.matches.matches_val,
sizeof (char *) * (rv.ret.matches.matches_len + 1));
rv.ret.matches.matches_val[rv.ret.matches.matches_len] = NULL;
return rv.ret.matches.matches_val;
}
struct aug_save_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_save_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_save_rv *rv = (struct aug_save_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_save: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_save: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_save (guestfs_h *g)
{
struct aug_save_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_save called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
serial = dispatch (g, GUESTFS_PROC_AUG_SAVE, NULL, NULL);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_save_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_save failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_SAVE, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}
struct aug_load_rv {
int cb_done; /* flag to indicate callback was called */
struct guestfs_message_header hdr;
struct guestfs_message_error err;
};
static void aug_load_cb (guestfs_h *g, void *data, XDR *xdr)
{
struct aug_load_rv *rv = (struct aug_load_rv *) data;
if (!xdr_guestfs_message_header (xdr, &rv->hdr)) {
error (g, "guestfs_aug_load: failed to parse reply header");
return;
}
if (rv->hdr.status == GUESTFS_STATUS_ERROR) {
if (!xdr_guestfs_message_error (xdr, &rv->err)) {
error (g, "guestfs_aug_load: failed to parse reply error");
return;
}
goto done;
}
done:
rv->cb_done = 1;
main_loop.main_loop_quit (g);
}
int guestfs_aug_load (guestfs_h *g)
{
struct aug_load_rv rv;
int serial;
if (g->state != READY) {
error (g, "guestfs_aug_load called from the wrong state, %d != READY",
g->state);
return -1;
}
memset (&rv, 0, sizeof rv);
serial = dispatch (g, GUESTFS_PROC_AUG_LOAD, NULL, NULL);
if (serial == -1)
return -1;
rv.cb_done = 0;
g->reply_cb_internal = aug_load_cb;
g->reply_cb_internal_data = &rv;
main_loop.main_loop_run (g);
g->reply_cb_internal = NULL;
g->reply_cb_internal_data = NULL;
if (!rv.cb_done) {
error (g, "guestfs_aug_load failed, see earlier error messages");
return -1;
}
if (check_reply_header (g, &rv.hdr, GUESTFS_PROC_AUG_LOAD, serial) == -1)
return -1;
if (rv.hdr.status == GUESTFS_STATUS_ERROR) {
error (g, "%s", rv.err.error);
return -1;
}
return 0;
}

View File

@@ -46,3 +46,15 @@ extern struct guestfs_lvm_pv_list *guestfs_pvs_full (guestfs_h *handle);
extern struct guestfs_lvm_vg_list *guestfs_vgs_full (guestfs_h *handle);
extern struct guestfs_lvm_lv_list *guestfs_lvs_full (guestfs_h *handle);
extern char **guestfs_read_lines (guestfs_h *handle, const char *path);
extern int guestfs_aug_init (guestfs_h *handle, const char *root, int flags);
extern int guestfs_aug_close (guestfs_h *handle);
extern int guestfs_aug_defvar (guestfs_h *handle, const char *name, const char *expr);
extern struct guestfs_int_bool *guestfs_aug_defnode (guestfs_h *handle, const char *name, const char *expr, const char *val);
extern char *guestfs_aug_get (guestfs_h *handle, const char *path);
extern int guestfs_aug_set (guestfs_h *handle, const char *path, const char *val);
extern int guestfs_aug_insert (guestfs_h *handle, const char *path, const char *label, int before);
extern int guestfs_aug_rm (guestfs_h *handle, const char *path);
extern int guestfs_aug_mv (guestfs_h *handle, const char *src, const char *dest);
extern char **guestfs_aug_match (guestfs_h *handle, const char *path);
extern int guestfs_aug_save (guestfs_h *handle);
extern int guestfs_aug_load (guestfs_h *handle);

View File

@@ -19,6 +19,11 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
struct guestfs_int_bool {
int32_t i;
int32_t b;
};
struct guestfs_lvm_pv {
char *pv_name;
char pv_uuid[32]; /* this is NOT nul-terminated, be careful when printing */

View File

@@ -1270,6 +1270,12 @@ check_reply_header (guestfs_h *g,
* structure format is identical to the XDR format. See note in
* generator.ml.
*/
void
guestfs_free_int_bool (struct guestfs_int_bool *x)
{
free (x);
}
void
guestfs_free_lvm_pv_list (struct guestfs_lvm_pv_list *x)
{

View File

@@ -45,6 +45,7 @@ extern guestfs_abort_cb guestfs_get_out_of_memory_handler (guestfs_h *g);
#include <guestfs-structs.h>
#include <guestfs-actions.h>
extern void guestfs_free_int_bool (struct guestfs_int_bool *);
extern void guestfs_free_lvm_pv_list (struct guestfs_lvm_pv_list *);
extern void guestfs_free_lvm_vg_list (struct guestfs_lvm_vg_list *);
extern void guestfs_free_lvm_lv_list (struct guestfs_lvm_lv_list *);

View File

@@ -362,6 +362,165 @@ xdr_guestfs_read_lines_ret (XDR *xdrs, guestfs_read_lines_ret *objp)
return TRUE;
}
bool_t
xdr_guestfs_aug_init_args (XDR *xdrs, guestfs_aug_init_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->root, ~0))
return FALSE;
if (!xdr_int (xdrs, &objp->flags))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_defvar_args (XDR *xdrs, guestfs_aug_defvar_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->name, ~0))
return FALSE;
if (!xdr_pointer (xdrs, (char **)&objp->expr, sizeof (str), (xdrproc_t) xdr_str))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_defvar_ret (XDR *xdrs, guestfs_aug_defvar_ret *objp)
{
register int32_t *buf;
if (!xdr_int (xdrs, &objp->nrnodes))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_defnode_args (XDR *xdrs, guestfs_aug_defnode_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->name, ~0))
return FALSE;
if (!xdr_string (xdrs, &objp->expr, ~0))
return FALSE;
if (!xdr_string (xdrs, &objp->val, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_defnode_ret (XDR *xdrs, guestfs_aug_defnode_ret *objp)
{
register int32_t *buf;
if (!xdr_int (xdrs, &objp->nrnodes))
return FALSE;
if (!xdr_bool (xdrs, &objp->created))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_get_args (XDR *xdrs, guestfs_aug_get_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->path, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_get_ret (XDR *xdrs, guestfs_aug_get_ret *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->val, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_set_args (XDR *xdrs, guestfs_aug_set_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->path, ~0))
return FALSE;
if (!xdr_string (xdrs, &objp->val, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_insert_args (XDR *xdrs, guestfs_aug_insert_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->path, ~0))
return FALSE;
if (!xdr_string (xdrs, &objp->label, ~0))
return FALSE;
if (!xdr_bool (xdrs, &objp->before))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_rm_args (XDR *xdrs, guestfs_aug_rm_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->path, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_rm_ret (XDR *xdrs, guestfs_aug_rm_ret *objp)
{
register int32_t *buf;
if (!xdr_int (xdrs, &objp->nrnodes))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_mv_args (XDR *xdrs, guestfs_aug_mv_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->src, ~0))
return FALSE;
if (!xdr_string (xdrs, &objp->dest, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_match_args (XDR *xdrs, guestfs_aug_match_args *objp)
{
register int32_t *buf;
if (!xdr_string (xdrs, &objp->path, ~0))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_aug_match_ret (XDR *xdrs, guestfs_aug_match_ret *objp)
{
register int32_t *buf;
if (!xdr_array (xdrs, (char **)&objp->matches.matches_val, (u_int *) &objp->matches.matches_len, ~0,
sizeof (str), (xdrproc_t) xdr_str))
return FALSE;
return TRUE;
}
bool_t
xdr_guestfs_procedure (XDR *xdrs, guestfs_procedure *objp)
{

View File

@@ -204,6 +204,88 @@ struct guestfs_read_lines_ret {
};
typedef struct guestfs_read_lines_ret guestfs_read_lines_ret;
struct guestfs_aug_init_args {
char *root;
int flags;
};
typedef struct guestfs_aug_init_args guestfs_aug_init_args;
struct guestfs_aug_defvar_args {
char *name;
str *expr;
};
typedef struct guestfs_aug_defvar_args guestfs_aug_defvar_args;
struct guestfs_aug_defvar_ret {
int nrnodes;
};
typedef struct guestfs_aug_defvar_ret guestfs_aug_defvar_ret;
struct guestfs_aug_defnode_args {
char *name;
char *expr;
char *val;
};
typedef struct guestfs_aug_defnode_args guestfs_aug_defnode_args;
struct guestfs_aug_defnode_ret {
int nrnodes;
bool_t created;
};
typedef struct guestfs_aug_defnode_ret guestfs_aug_defnode_ret;
struct guestfs_aug_get_args {
char *path;
};
typedef struct guestfs_aug_get_args guestfs_aug_get_args;
struct guestfs_aug_get_ret {
char *val;
};
typedef struct guestfs_aug_get_ret guestfs_aug_get_ret;
struct guestfs_aug_set_args {
char *path;
char *val;
};
typedef struct guestfs_aug_set_args guestfs_aug_set_args;
struct guestfs_aug_insert_args {
char *path;
char *label;
bool_t before;
};
typedef struct guestfs_aug_insert_args guestfs_aug_insert_args;
struct guestfs_aug_rm_args {
char *path;
};
typedef struct guestfs_aug_rm_args guestfs_aug_rm_args;
struct guestfs_aug_rm_ret {
int nrnodes;
};
typedef struct guestfs_aug_rm_ret guestfs_aug_rm_ret;
struct guestfs_aug_mv_args {
char *src;
char *dest;
};
typedef struct guestfs_aug_mv_args guestfs_aug_mv_args;
struct guestfs_aug_match_args {
char *path;
};
typedef struct guestfs_aug_match_args guestfs_aug_match_args;
struct guestfs_aug_match_ret {
struct {
u_int matches_len;
str *matches_val;
} matches;
};
typedef struct guestfs_aug_match_ret guestfs_aug_match_ret;
enum guestfs_procedure {
GUESTFS_PROC_MOUNT = 1,
GUESTFS_PROC_SYNC = 2,
@@ -220,7 +302,19 @@ enum guestfs_procedure {
GUESTFS_PROC_VGS_FULL = 13,
GUESTFS_PROC_LVS_FULL = 14,
GUESTFS_PROC_READ_LINES = 15,
GUESTFS_PROC_dummy = 15 + 1,
GUESTFS_PROC_AUG_INIT = 16,
GUESTFS_PROC_AUG_CLOSE = 26,
GUESTFS_PROC_AUG_DEFVAR = 17,
GUESTFS_PROC_AUG_DEFNODE = 18,
GUESTFS_PROC_AUG_GET = 19,
GUESTFS_PROC_AUG_SET = 20,
GUESTFS_PROC_AUG_INSERT = 21,
GUESTFS_PROC_AUG_RM = 22,
GUESTFS_PROC_AUG_MV = 23,
GUESTFS_PROC_AUG_MATCH = 24,
GUESTFS_PROC_AUG_SAVE = 25,
GUESTFS_PROC_AUG_LOAD = 27,
GUESTFS_PROC_dummy = 27 + 1,
};
typedef enum guestfs_procedure guestfs_procedure;
#define GUESTFS_MESSAGE_MAX 4194304
@@ -283,6 +377,20 @@ extern bool_t xdr_guestfs_vgs_full_ret (XDR *, guestfs_vgs_full_ret*);
extern bool_t xdr_guestfs_lvs_full_ret (XDR *, guestfs_lvs_full_ret*);
extern bool_t xdr_guestfs_read_lines_args (XDR *, guestfs_read_lines_args*);
extern bool_t xdr_guestfs_read_lines_ret (XDR *, guestfs_read_lines_ret*);
extern bool_t xdr_guestfs_aug_init_args (XDR *, guestfs_aug_init_args*);
extern bool_t xdr_guestfs_aug_defvar_args (XDR *, guestfs_aug_defvar_args*);
extern bool_t xdr_guestfs_aug_defvar_ret (XDR *, guestfs_aug_defvar_ret*);
extern bool_t xdr_guestfs_aug_defnode_args (XDR *, guestfs_aug_defnode_args*);
extern bool_t xdr_guestfs_aug_defnode_ret (XDR *, guestfs_aug_defnode_ret*);
extern bool_t xdr_guestfs_aug_get_args (XDR *, guestfs_aug_get_args*);
extern bool_t xdr_guestfs_aug_get_ret (XDR *, guestfs_aug_get_ret*);
extern bool_t xdr_guestfs_aug_set_args (XDR *, guestfs_aug_set_args*);
extern bool_t xdr_guestfs_aug_insert_args (XDR *, guestfs_aug_insert_args*);
extern bool_t xdr_guestfs_aug_rm_args (XDR *, guestfs_aug_rm_args*);
extern bool_t xdr_guestfs_aug_rm_ret (XDR *, guestfs_aug_rm_ret*);
extern bool_t xdr_guestfs_aug_mv_args (XDR *, guestfs_aug_mv_args*);
extern bool_t xdr_guestfs_aug_match_args (XDR *, guestfs_aug_match_args*);
extern bool_t xdr_guestfs_aug_match_ret (XDR *, guestfs_aug_match_ret*);
extern bool_t xdr_guestfs_procedure (XDR *, guestfs_procedure*);
extern bool_t xdr_guestfs_message_direction (XDR *, guestfs_message_direction*);
extern bool_t xdr_guestfs_message_status (XDR *, guestfs_message_status*);
@@ -315,6 +423,20 @@ extern bool_t xdr_guestfs_vgs_full_ret ();
extern bool_t xdr_guestfs_lvs_full_ret ();
extern bool_t xdr_guestfs_read_lines_args ();
extern bool_t xdr_guestfs_read_lines_ret ();
extern bool_t xdr_guestfs_aug_init_args ();
extern bool_t xdr_guestfs_aug_defvar_args ();
extern bool_t xdr_guestfs_aug_defvar_ret ();
extern bool_t xdr_guestfs_aug_defnode_args ();
extern bool_t xdr_guestfs_aug_defnode_ret ();
extern bool_t xdr_guestfs_aug_get_args ();
extern bool_t xdr_guestfs_aug_get_ret ();
extern bool_t xdr_guestfs_aug_set_args ();
extern bool_t xdr_guestfs_aug_insert_args ();
extern bool_t xdr_guestfs_aug_rm_args ();
extern bool_t xdr_guestfs_aug_rm_ret ();
extern bool_t xdr_guestfs_aug_mv_args ();
extern bool_t xdr_guestfs_aug_match_args ();
extern bool_t xdr_guestfs_aug_match_ret ();
extern bool_t xdr_guestfs_procedure ();
extern bool_t xdr_guestfs_message_direction ();
extern bool_t xdr_guestfs_message_status ();

View File

@@ -85,23 +85,15 @@ struct guestfs_lvm_int_lv {
typedef struct guestfs_lvm_int_lv guestfs_lvm_int_lv_list<>;
/* guestfs_mount */
struct guestfs_mount_args {
string device<>;
string mountpoint<>;
};
/* guestfs_sync */
/* guestfs_touch */
struct guestfs_touch_args {
string path<>;
};
/* guestfs_cat */
struct guestfs_cat_args {
string path<>;
};
@@ -110,8 +102,6 @@ struct guestfs_cat_ret {
string content<>;
};
/* guestfs_ll */
struct guestfs_ll_args {
string directory<>;
};
@@ -120,8 +110,6 @@ struct guestfs_ll_ret {
string listing<>;
};
/* guestfs_ls */
struct guestfs_ls_args {
string directory<>;
};
@@ -130,56 +118,38 @@ struct guestfs_ls_ret {
str listing<>;
};
/* guestfs_list_devices */
struct guestfs_list_devices_ret {
str devices<>;
};
/* guestfs_list_partitions */
struct guestfs_list_partitions_ret {
str partitions<>;
};
/* guestfs_pvs */
struct guestfs_pvs_ret {
str physvols<>;
};
/* guestfs_vgs */
struct guestfs_vgs_ret {
str volgroups<>;
};
/* guestfs_lvs */
struct guestfs_lvs_ret {
str logvols<>;
};
/* guestfs_pvs_full */
struct guestfs_pvs_full_ret {
guestfs_lvm_int_pv_list physvols;
};
/* guestfs_vgs_full */
struct guestfs_vgs_full_ret {
guestfs_lvm_int_vg_list volgroups;
};
/* guestfs_lvs_full */
struct guestfs_lvs_full_ret {
guestfs_lvm_int_lv_list logvols;
};
/* guestfs_read_lines */
struct guestfs_read_lines_args {
string path<>;
};
@@ -188,6 +158,71 @@ struct guestfs_read_lines_ret {
str lines<>;
};
struct guestfs_aug_init_args {
string root<>;
int flags;
};
struct guestfs_aug_defvar_args {
string name<>;
str *expr;
};
struct guestfs_aug_defvar_ret {
int nrnodes;
};
struct guestfs_aug_defnode_args {
string name<>;
string expr<>;
string val<>;
};
struct guestfs_aug_defnode_ret {
int nrnodes;
bool created;
};
struct guestfs_aug_get_args {
string path<>;
};
struct guestfs_aug_get_ret {
string val<>;
};
struct guestfs_aug_set_args {
string path<>;
string val<>;
};
struct guestfs_aug_insert_args {
string path<>;
string label<>;
bool before;
};
struct guestfs_aug_rm_args {
string path<>;
};
struct guestfs_aug_rm_ret {
int nrnodes;
};
struct guestfs_aug_mv_args {
string src<>;
string dest<>;
};
struct guestfs_aug_match_args {
string path<>;
};
struct guestfs_aug_match_ret {
str matches<>;
};
enum guestfs_procedure {
GUESTFS_PROC_MOUNT = 1,
GUESTFS_PROC_SYNC = 2,
@@ -204,6 +239,18 @@ enum guestfs_procedure {
GUESTFS_PROC_VGS_FULL = 13,
GUESTFS_PROC_LVS_FULL = 14,
GUESTFS_PROC_READ_LINES = 15,
GUESTFS_PROC_AUG_INIT = 16,
GUESTFS_PROC_AUG_CLOSE = 26,
GUESTFS_PROC_AUG_DEFVAR = 17,
GUESTFS_PROC_AUG_DEFNODE = 18,
GUESTFS_PROC_AUG_GET = 19,
GUESTFS_PROC_AUG_SET = 20,
GUESTFS_PROC_AUG_INSERT = 21,
GUESTFS_PROC_AUG_RM = 22,
GUESTFS_PROC_AUG_MV = 23,
GUESTFS_PROC_AUG_MATCH = 24,
GUESTFS_PROC_AUG_SAVE = 25,
GUESTFS_PROC_AUG_LOAD = 27,
GUESTFS_PROC_dummy
};