X-Git-Url: http://git.annexia.org/?a=blobdiff_plain;f=daemon%2Fxattr.c;h=2b4882a0de0982b52e35c0527dec9b238d83066d;hb=63c1d5dd6efb9b59a73a11f31aefdc55eaf28384;hp=926baf03f112af73a535f06b5269b4ebc3f81612;hpb=9a8889e4d0c532b9f77af3a9cc7aae06adebfb83;p=libguestfs.git diff --git a/daemon/xattr.c b/daemon/xattr.c index 926baf0..2b4882a 100644 --- a/daemon/xattr.c +++ b/daemon/xattr.c @@ -1,5 +1,5 @@ /* libguestfs - the guestfsd daemon - * Copyright (C) 2009 Red Hat Inc. + * Copyright (C) 2009-2011 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 @@ -21,19 +21,26 @@ #include #include -#include "../src/guestfs_protocol.h" +#include "guestfs_protocol.h" #include "daemon.h" #include "actions.h" +#include "optgroups.h" #if defined(HAVE_ATTR_XATTR_H) || defined(HAVE_SYS_XATTR_H) -#ifdef HAVE_ATTR_XATTR_H -#include -#else -#ifdef HAVE_SYS_XATTR_H -#include -#endif -#endif +# ifdef HAVE_ATTR_XATTR_H +# include +# else +# ifdef HAVE_SYS_XATTR_H +# include +# endif +# endif + +int +optgroup_linuxxattrs_available (void) +{ + return 1; +} static guestfs_int_xattr_list *getxattrs (const char *path, ssize_t (*listxattr) (const char *path, char *list, size_t size), ssize_t (*getxattr) (const char *path, const char *name, void *value, size_t size)); static int _setxattr (const char *xattr, const char *val, int vallen, const char *path, int (*setxattr) (const char *path, const char *name, const void *value, size_t size, int flags)); @@ -45,7 +52,7 @@ do_getxattrs (const char *path) #if defined(HAVE_LISTXATTR) && defined(HAVE_GETXATTR) return getxattrs (path, listxattr, getxattr); #else - reply_with_error ("getxattrs: no support for listxattr and getxattr"); + reply_with_error ("no support for listxattr and getxattr"); return NULL; #endif } @@ -56,7 +63,7 @@ do_lgetxattrs (const char *path) #if defined(HAVE_LLISTXATTR) && defined(HAVE_LGETXATTR) return getxattrs (path, llistxattr, lgetxattr); #else - reply_with_error ("lgetxattrs: no support for llistxattr and lgetxattr"); + reply_with_error ("no support for llistxattr and lgetxattr"); return NULL; #endif } @@ -67,7 +74,7 @@ do_setxattr (const char *xattr, const char *val, int vallen, const char *path) #if defined(HAVE_SETXATTR) return _setxattr (xattr, val, vallen, path, setxattr); #else - reply_with_error ("setxattr: no support for setxattr"); + reply_with_error ("no support for setxattr"); return -1; #endif } @@ -78,7 +85,7 @@ do_lsetxattr (const char *xattr, const char *val, int vallen, const char *path) #if defined(HAVE_LSETXATTR) return _setxattr (xattr, val, vallen, path, lsetxattr); #else - reply_with_error ("lsetxattr: no support for lsetxattr"); + reply_with_error ("no support for lsetxattr"); return -1; #endif } @@ -89,7 +96,7 @@ do_removexattr (const char *xattr, const char *path) #if defined(HAVE_REMOVEXATTR) return _removexattr (xattr, path, removexattr); #else - reply_with_error ("removexattr: no support for removexattr"); + reply_with_error ("no support for removexattr"); return -1; #endif } @@ -100,7 +107,7 @@ do_lremovexattr (const char *xattr, const char *path) #if defined(HAVE_LREMOVEXATTR) return _removexattr (xattr, path, lremovexattr); #else - reply_with_error ("lremovexattr: no support for lremovexattr"); + reply_with_error ("no support for lremovexattr"); return -1; #endif } @@ -120,7 +127,7 @@ getxattrs (const char *path, len = listxattr (path, NULL, 0); CHROOT_OUT; if (len == -1) { - reply_with_perror ("listxattr"); + reply_with_perror ("listxattr: %s", path); goto error; } @@ -134,7 +141,7 @@ getxattrs (const char *path, len = listxattr (path, buf, len); CHROOT_OUT; if (len == -1) { - reply_with_perror ("listxattr"); + reply_with_perror ("listxattr: %s", path); goto error; } @@ -259,7 +266,7 @@ do_lxattrlist (const char *path, char *const *names) char *buf = NULL; if (path_len >= PATH_MAX) { - reply_with_perror ("lxattrlist: path longer than PATH_MAX"); + reply_with_perror ("path longer than PATH_MAX"); goto error; } @@ -281,7 +288,7 @@ do_lxattrlist (const char *path, char *const *names) * outgoing struct list. */ if (path_len + strlen (names[k]) + 2 > PATH_MAX) { - reply_with_perror ("lxattrlist: path and name longer than PATH_MAX"); + reply_with_perror ("path and name longer than PATH_MAX"); goto error; } pathname[path_len] = '/'; @@ -398,28 +405,6 @@ do_lxattrlist (const char *path, char *const *names) } } - /* If verbose, debug what we're about to send back. */ - if (verbose) { - fprintf (stderr, "lxattrlist: returning: [\n"); - for (k = 0; k < ret->guestfs_int_xattr_list_len; ++k) { - const guestfs_int_xattr *entry = &ret->guestfs_int_xattr_list_val[k]; - if (strcmp (entry[0].attrname, "") != 0) { - fprintf (stderr, "ERROR: expecting empty attrname at k = %zu\n", k); - break; - } - fprintf (stderr, " %zu: special attrval = %s\n", - k, entry[0].attrval.attrval_val); - for (i = 1; k+i < ret->guestfs_int_xattr_list_len; ++i) { - if (STREQ (entry[i].attrname, "")) - break; - fprintf (stderr, " name %s, value length %d\n", - entry[i].attrname, entry[i].attrval.attrval_len); - } - k += i-1; - } - fprintf (stderr, "]\n"); - } - return ret; error: @@ -436,60 +421,154 @@ do_lxattrlist (const char *path, char *const *names) } return NULL; #else - reply_with_error ("lxattrlist: no support for llistxattr and lgetxattr"); + reply_with_error ("no support for llistxattr and lgetxattr"); return NULL; #endif } +char * +do_getxattr (const char *path, const char *name, size_t *size_r) +{ + ssize_t r; + char *buf; + size_t len; + + CHROOT_IN; + r = getxattr (path, name, NULL, 0); + CHROOT_OUT; + if (r == -1) { + reply_with_perror ("getxattr"); + return NULL; + } + + len = r; + buf = malloc (len); + if (buf == NULL) { + reply_with_perror ("malloc"); + return NULL; + } + + CHROOT_IN; + r = getxattr (path, name, buf, len); + CHROOT_OUT; + if (r == -1) { + reply_with_perror ("getxattr"); + free (buf); + return NULL; + } + + if (len != (size_t) r) { + reply_with_error ("getxattr: unexpected size (%zu/%zd)", len, r); + free (buf); + return NULL; + } + + /* Must set size_r last thing before returning. */ + *size_r = len; + return buf; /* caller frees */ +} + +char * +do_lgetxattr (const char *path, const char *name, size_t *size_r) +{ + ssize_t r; + char *buf; + size_t len; + + CHROOT_IN; + r = lgetxattr (path, name, NULL, 0); + CHROOT_OUT; + if (r == -1) { + reply_with_perror ("lgetxattr"); + return NULL; + } + + len = r; + buf = malloc (len); + if (buf == NULL) { + reply_with_perror ("malloc"); + return NULL; + } + + CHROOT_IN; + r = lgetxattr (path, name, buf, len); + CHROOT_OUT; + if (r == -1) { + reply_with_perror ("lgetxattr"); + free (buf); + return NULL; + } + + if (len != (size_t) r) { + reply_with_error ("lgetxattr: unexpected size (%zu/%zd)", len, r); + free (buf); + return NULL; + } + + /* Must set size_r last thing before returning. */ + *size_r = len; + return buf; /* caller frees */ +} + #else /* no xattr.h */ +int +optgroup_linuxxattrs_available (void) +{ + return 0; +} guestfs_int_xattr_list * do_getxattrs (const char *path) { - reply_with_error ("getxattrs: no support for xattrs"); - return NULL; + NOT_AVAILABLE (NULL); } guestfs_int_xattr_list * do_lgetxattrs (const char *path) { - reply_with_error ("lgetxattrs: no support for xattrs"); - return NULL; + NOT_AVAILABLE (NULL); } int do_setxattr (const char *xattr, const char *val, int vallen, const char *path) { - reply_with_error ("setxattr: no support for xattrs"); - return -1; + NOT_AVAILABLE (-1); } int do_lsetxattr (const char *xattr, const char *val, int vallen, const char *path) { - reply_with_error ("lsetxattr: no support for xattrs"); - return -1; + NOT_AVAILABLE (-1); } int do_removexattr (const char *xattr, const char *path) { - reply_with_error ("removexattr: no support for xattrs"); - return -1; + NOT_AVAILABLE (-1); } int do_lremovexattr (const char *xattr, const char *path) { - reply_with_error ("lremovexattr: no support for xattrs"); - return -1; + NOT_AVAILABLE (-1); } guestfs_int_xattr_list * do_lxattrlist (const char *path, char *const *names) { - reply_with_error ("lxattrlist: no support for xattrs"); - return NULL; + NOT_AVAILABLE (NULL); +} + +char * +do_getxattr (const char *path, const char *name, size_t *size_r) +{ + NOT_AVAILABLE (NULL); +} + +char * +do_lgetxattr (const char *path, const char *name, size_t *size_r) +{ + NOT_AVAILABLE (NULL); } #endif /* no xattr.h */