diff options
| -rw-r--r-- | configure.ac | 3 | ||||
| -rw-r--r-- | xlators/Makefile.am | 2 | ||||
| -rw-r--r-- | xlators/nfs/Makefile.am | 3 | ||||
| -rw-r--r-- | xlators/nfs/lib/Makefile.am | 3 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/Makefile.am | 11 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/msg-nfs3.c | 558 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/msg-nfs3.h | 192 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/xdr-common.h | 48 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/xdr-nfs3.c | 1892 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/xdr-nfs3.h | 1205 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/xdr-rpc.c | 190 | ||||
| -rw-r--r-- | xlators/nfs/lib/src/xdr-rpc.h | 74 | 
12 files changed, 4180 insertions, 1 deletions
diff --git a/configure.ac b/configure.ac index e9be1012b..6571adb02 100644 --- a/configure.ac +++ b/configure.ac @@ -107,6 +107,9 @@ AC_CONFIG_FILES([Makefile  		contrib/fuse-util/Makefile                  xlators/features/access-control/Makefile                  xlators/features/access-control/src/Makefile +                xlators/nfs/Makefile +                xlators/nfs/lib/Makefile +                xlators/nfs/lib/src/Makefile  		glusterfs.spec])  AC_CANONICAL_HOST diff --git a/xlators/Makefile.am b/xlators/Makefile.am index 2abb52194..8ca471f94 100644 --- a/xlators/Makefile.am +++ b/xlators/Makefile.am @@ -1,3 +1,3 @@ -SUBDIRS = cluster storage protocol performance debug features encryption mount +SUBDIRS = cluster storage protocol performance debug features encryption mount nfs  CLEANFILES =  diff --git a/xlators/nfs/Makefile.am b/xlators/nfs/Makefile.am new file mode 100644 index 000000000..8ead8848a --- /dev/null +++ b/xlators/nfs/Makefile.am @@ -0,0 +1,3 @@ +SUBDIRS = lib + +CLEANFILES = diff --git a/xlators/nfs/lib/Makefile.am b/xlators/nfs/lib/Makefile.am new file mode 100644 index 000000000..a985f42a8 --- /dev/null +++ b/xlators/nfs/lib/Makefile.am @@ -0,0 +1,3 @@ +SUBDIRS = src + +CLEANFILES = diff --git a/xlators/nfs/lib/src/Makefile.am b/xlators/nfs/lib/src/Makefile.am new file mode 100644 index 000000000..d0221f494 --- /dev/null +++ b/xlators/nfs/lib/src/Makefile.am @@ -0,0 +1,11 @@ +lib_LTLIBRARIES = librpcsvc.la +librpcsvc_la_LDFLAGS = -module -avoidversion + +librpcsvc_la_SOURCES = msg-nfs3.c xdr-nfs3.c xdr-rpc.c +librpcsvc_la_LIBADD = $(top_builddir)/libglusterfs/src/libglusterfs.la + +noinst_HEADERS = xdr-rpc.h msg-nfs3.h xdr-common.h xdr-nfs3.h +AM_CFLAGS = -fPIC -D_FILE_OFFSET_BITS=64 -D_GNU_SOURCE -Wall -D$(GF_HOST_OS)\ +	-I$(top_srcdir)/libglusterfs/src -shared -nostartfiles $(GF_CFLAGS) + +CLEANFILES = diff --git a/xlators/nfs/lib/src/msg-nfs3.c b/xlators/nfs/lib/src/msg-nfs3.c new file mode 100644 index 000000000..781466045 --- /dev/null +++ b/xlators/nfs/lib/src/msg-nfs3.c @@ -0,0 +1,558 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include <sys/uio.h> +#include <rpc/rpc.h> +#include <rpc/xdr.h> +#include <sys/types.h> + +#include "xdr-nfs3.h" +#include "msg-nfs3.h" +#include "xdr-common.h" + + +/* Decode the mount path from the network message in inmsg + * into the memory referenced by outpath.iov_base. + * The size allocated for outpath.iov_base is outpath.iov_len. + * The size of the path extracted from the message is returned. + */ +ssize_t +xdr_to_mountpath (struct iovec outpath, struct iovec inmsg) +{ +        XDR     xdr; +        ssize_t ret = -1; +        char    *mntpath = NULL; + +        if ((!outpath.iov_base) || (!inmsg.iov_base)) +                return -1; + +        xdrmem_create (&xdr, inmsg.iov_base, (unsigned int)inmsg.iov_len, +                       XDR_DECODE); + +        mntpath = outpath.iov_base; +        if (!xdr_dirpath (&xdr, (dirpath *)&mntpath)) { +                ret = -1; +                goto ret; +        } + +        ret = xdr_decoded_length (xdr); + +ret: +        return ret; +} + + +ssize_t +xdr_serialize_generic (struct iovec outmsg, void *res, xdrproc_t proc) +{ +        ssize_t ret = -1; +        XDR     xdr; + +        if ((!outmsg.iov_base) || (!res) || (!proc)) +                return -1; + +        xdrmem_create (&xdr, outmsg.iov_base, (unsigned int)outmsg.iov_len, +                       XDR_ENCODE); + +        if (!proc (&xdr, res)) { +                ret = -1; +                goto ret; +        } + +        ret = xdr_encoded_length (xdr); + +ret: +        return ret; +} + + +ssize_t +xdr_to_generic (struct iovec inmsg, void *args, xdrproc_t proc) +{ +        XDR     xdr; +        ssize_t ret = -1; + +        if ((!inmsg.iov_base) || (!args) || (!proc)) +                return -1; + +        xdrmem_create (&xdr, inmsg.iov_base, (unsigned int)inmsg.iov_len, +                       XDR_DECODE); + +        if (!proc (&xdr, args)) { +                ret  = -1; +                goto ret; +        } + +        ret = xdr_decoded_length (xdr); +ret: +        return ret; +} + + +ssize_t +xdr_to_generic_payload (struct iovec inmsg, void *args, xdrproc_t proc, +                        struct iovec *pendingpayload) +{ +        XDR     xdr; +        ssize_t ret = -1; + +        if ((!inmsg.iov_base) || (!args) || (!proc)) +                return -1; + +        xdrmem_create (&xdr, inmsg.iov_base, (unsigned int)inmsg.iov_len, +                       XDR_DECODE); + +        if (!proc (&xdr, args)) { +                ret  = -1; +                goto ret; +        } + +        ret = xdr_decoded_length (xdr); + +        if (pendingpayload) { +                pendingpayload->iov_base = xdr_decoded_remaining_addr (xdr); +                pendingpayload->iov_len = xdr_decoded_remaining_len (xdr); +        } + +ret: +        return ret; +} + + +/* Translate the mountres3 structure in res into XDR format into memory + * referenced by outmsg.iov_base. + * Returns the number of bytes used in encoding into XDR format. + */ +ssize_t +xdr_serialize_mountres3 (struct iovec outmsg, mountres3 *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_mountres3); +} + + +ssize_t +xdr_serialize_mountbody (struct iovec outmsg, mountbody *mb) +{ +        return xdr_serialize_generic (outmsg, (void *)mb, +                                      (xdrproc_t)xdr_mountbody); +} + +ssize_t +xdr_serialize_mountlist (struct iovec outmsg, mountlist *ml) +{ +        return xdr_serialize_generic (outmsg, (void *)ml, +                                      (xdrproc_t)xdr_mountlist); +} + + +ssize_t +xdr_serialize_mountstat3 (struct iovec outmsg, mountstat3 *m) +{ +        return xdr_serialize_generic (outmsg, (void *)m, +                                      (xdrproc_t)xdr_mountstat3); +} + + +ssize_t +xdr_to_getattr3args (struct iovec inmsg, getattr3args *ga) +{ +        return xdr_to_generic (inmsg, (void *)ga,(xdrproc_t)xdr_getattr3args); +} + + +ssize_t +xdr_serialize_getattr3res (struct iovec outmsg, getattr3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_getattr3res); +} + + +ssize_t +xdr_serialize_setattr3res (struct iovec outmsg, setattr3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_setattr3res); +} + + +ssize_t +xdr_to_setattr3args (struct iovec inmsg, setattr3args *sa) +{ +        return xdr_to_generic (inmsg, (void *)sa, (xdrproc_t)xdr_setattr3args); +} + + +ssize_t +xdr_serialize_lookup3res (struct iovec outmsg, lookup3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_lookup3res); +} + + +ssize_t +xdr_to_lookup3args (struct iovec inmsg, lookup3args *la) +{ +        return xdr_to_generic (inmsg, (void *)la, (xdrproc_t)xdr_lookup3args); +} + + +ssize_t +xdr_to_access3args (struct iovec inmsg, access3args *ac) +{ +        return xdr_to_generic (inmsg,(void *)ac, (xdrproc_t)xdr_access3args); +} + + +ssize_t +xdr_serialize_access3res (struct iovec outmsg, access3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_access3res); +} + + +ssize_t +xdr_to_readlink3args (struct iovec inmsg, readlink3args *ra) +{ +        return xdr_to_generic (inmsg, (void *)ra, (xdrproc_t)xdr_readlink3args); +} + + +ssize_t +xdr_serialize_readlink3res (struct iovec outmsg, readlink3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_readlink3res); +} + + +ssize_t +xdr_to_read3args (struct iovec inmsg, read3args *ra) +{ +        return xdr_to_generic (inmsg, (void *)ra, (xdrproc_t)xdr_read3args); +} + + +ssize_t +xdr_serialize_read3res (struct iovec outmsg, read3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_read3res); +} + +ssize_t +xdr_serialize_read3res_nocopy (struct iovec outmsg, read3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_read3res_nocopy); +} + + +ssize_t +xdr_to_write3args (struct iovec inmsg, write3args *wa) +{ +        return xdr_to_generic (inmsg, (void *)wa,(xdrproc_t)xdr_write3args); +} + + +ssize_t +xdr_to_write3args_nocopy (struct iovec inmsg, write3args *wa, +                          struct iovec *payload) +{ +        return xdr_to_generic_payload (inmsg, (void *)wa, +                                       (xdrproc_t)xdr_write3args, payload); +} + + +ssize_t +xdr_serialize_write3res (struct iovec outmsg, write3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_write3res); +} + + +ssize_t +xdr_to_create3args (struct iovec inmsg, create3args *ca) +{ +        return xdr_to_generic (inmsg, (void *)ca, (xdrproc_t)xdr_create3args); +} + + +ssize_t +xdr_serialize_create3res (struct iovec outmsg, create3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_create3res); +} + + +ssize_t +xdr_serialize_mkdir3res (struct iovec outmsg, mkdir3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_mkdir3res); +} + + +ssize_t +xdr_to_mkdir3args (struct iovec inmsg, mkdir3args *ma) +{ +        return xdr_to_generic (inmsg, (void *)ma, (xdrproc_t)xdr_mkdir3args); +} + + +ssize_t +xdr_to_symlink3args (struct iovec inmsg, symlink3args *sa) +{ +        return xdr_to_generic (inmsg, (void *)sa, (xdrproc_t)xdr_symlink3args); +} + + +ssize_t +xdr_serialize_symlink3res (struct iovec outmsg, symlink3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_symlink3res); +} + + +ssize_t +xdr_to_mknod3args (struct iovec inmsg, mknod3args *ma) +{ +        return xdr_to_generic (inmsg, (void *)ma, (xdrproc_t)xdr_mknod3args); +} + + +ssize_t +xdr_serialize_mknod3res (struct iovec outmsg, mknod3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_mknod3res); +} + + +ssize_t +xdr_to_remove3args (struct iovec inmsg, remove3args *ra) +{ +        return xdr_to_generic (inmsg, (void *)ra, (xdrproc_t)xdr_remove3args); +} + + +ssize_t +xdr_serialize_remove3res (struct iovec outmsg, remove3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_remove3res); +} + + +ssize_t +xdr_to_rmdir3args (struct iovec inmsg, rmdir3args *ra) +{ +        return xdr_to_generic (inmsg, (void *)ra, (xdrproc_t)xdr_rmdir3args); +} + + +ssize_t +xdr_serialize_rmdir3res (struct iovec outmsg, rmdir3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_rmdir3res); +} + + +ssize_t +xdr_serialize_rename3res (struct iovec outmsg, rename3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_rename3res); +} + + +ssize_t +xdr_to_rename3args (struct iovec inmsg, rename3args *ra) +{ +        return xdr_to_generic (inmsg, (void *)ra, (xdrproc_t)xdr_rename3args); +} + + +ssize_t +xdr_serialize_link3res (struct iovec outmsg, link3res *li) +{ +        return xdr_serialize_generic (outmsg, (void *)li, +                                      (xdrproc_t)xdr_link3res); +} + + +ssize_t +xdr_to_link3args (struct iovec inmsg, link3args *la) +{ +        return xdr_to_generic (inmsg, (void *)la, (xdrproc_t)xdr_link3args); +} + + +ssize_t +xdr_to_readdir3args (struct iovec inmsg, readdir3args *rd) +{ +        return xdr_to_generic (inmsg, (void *)rd, (xdrproc_t)xdr_readdir3args); +} + + +ssize_t +xdr_serialize_readdir3res (struct iovec outmsg, readdir3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_readdir3res); +} + + +ssize_t +xdr_to_readdirp3args (struct iovec inmsg, readdirp3args *rp) +{ +        return xdr_to_generic (inmsg, (void *)rp, (xdrproc_t)xdr_readdirp3args); +} + + +ssize_t +xdr_serialize_readdirp3res (struct iovec outmsg, readdirp3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_readdirp3res); +} + + +ssize_t +xdr_to_fsstat3args (struct iovec inmsg, fsstat3args *fa) +{ +        return xdr_to_generic (inmsg, (void *)fa, (xdrproc_t)xdr_fsstat3args); +} + + +ssize_t +xdr_serialize_fsstat3res (struct iovec outmsg, fsstat3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_fsstat3res); +} + +ssize_t +xdr_to_fsinfo3args (struct iovec inmsg, fsinfo3args *fi) +{ +        return xdr_to_generic (inmsg, (void *)fi, (xdrproc_t)xdr_fsinfo3args); +} + + +ssize_t +xdr_serialize_fsinfo3res (struct iovec outmsg, fsinfo3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_fsinfo3res); +} + + +ssize_t +xdr_to_pathconf3args (struct iovec inmsg, pathconf3args *pc) +{ +        return xdr_to_generic (inmsg, (void *)pc, (xdrproc_t)xdr_pathconf3args);} + + +ssize_t +xdr_serialize_pathconf3res (struct iovec outmsg, pathconf3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_pathconf3res); +} + + +ssize_t +xdr_to_commit3args (struct iovec inmsg, commit3args *ca) +{ +        return xdr_to_generic (inmsg, (void *)ca, (xdrproc_t)xdr_commit3args); +} + + +ssize_t +xdr_serialize_commit3res (struct iovec outmsg, commit3res *res) +{ +        return xdr_serialize_generic (outmsg, (void *)res, +                                      (xdrproc_t)xdr_commit3res); +} + + +ssize_t +xdr_serialize_exports (struct iovec outmsg, exports *elist) +{ +        XDR     xdr; +        ssize_t  ret = -1; + +        if ((!outmsg.iov_base) || (!elist)) +                return -1; + +        xdrmem_create (&xdr, outmsg.iov_base, (unsigned int)outmsg.iov_len, +                       XDR_ENCODE); + +        if (!xdr_exports (&xdr, elist)) +                goto ret; + +        ret = xdr_decoded_length (xdr); + +ret: +        return ret; +} + + +ssize_t +xdr_serialize_nfsstat3 (struct iovec outmsg, nfsstat3 *s) +{ +        return xdr_serialize_generic (outmsg, (void *)s, +                                      (xdrproc_t)xdr_nfsstat3); +} + + +ssize_t +xdr_length_round_up (size_t len, size_t bufsize) +{ +        int     roundup = 0; + +        roundup = len % XDR_BYTES_PER_UNIT; +        if (roundup > 0) +                roundup = XDR_BYTES_PER_UNIT - roundup; + +        if ((roundup > 0) && ((roundup + len) <= bufsize)) +                len += roundup; + +        return len; +} + +int +xdr_bytes_round_up (struct iovec *vec, size_t bufsize) +{ +        vec->iov_len = xdr_length_round_up (vec->iov_len, bufsize); +        return 0; +} + diff --git a/xlators/nfs/lib/src/msg-nfs3.h b/xlators/nfs/lib/src/msg-nfs3.h new file mode 100644 index 000000000..78682bc1c --- /dev/null +++ b/xlators/nfs/lib/src/msg-nfs3.h @@ -0,0 +1,192 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _MSG_NFS3_H_ +#define _MSG_NFS3_H_ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include "xdr-nfs3.h" + +#include <sys/types.h> +#include <sys/uio.h> + +extern ssize_t +xdr_to_mountpath (struct iovec outpath, struct iovec inmsg); + +extern ssize_t +xdr_serialize_mountres3 (struct iovec outmsg, mountres3 *res); + +extern ssize_t +xdr_serialize_mountbody (struct iovec outmsg, mountbody *mb); + +extern ssize_t +xdr_to_getattr3args (struct iovec inmsg, getattr3args *ga); + +extern ssize_t +xdr_serialize_getattr3res (struct iovec outmsg, getattr3res *res); + +extern ssize_t +xdr_serialize_setattr3res (struct iovec outmsg, setattr3res *res); + +extern ssize_t +xdr_to_setattr3args (struct iovec inmsg, setattr3args *sa); + +extern ssize_t +xdr_serialize_lookup3res (struct iovec outmsg, lookup3res *res); + +extern ssize_t +xdr_to_lookup3args (struct iovec inmsg, lookup3args *la); + +extern ssize_t +xdr_to_access3args (struct iovec inmsg, access3args *ac); + +extern ssize_t +xdr_serialize_access3res (struct iovec outmsg, access3res *res); + +extern ssize_t +xdr_to_readlink3args (struct iovec inmsg, readlink3args *ra); + +extern ssize_t +xdr_serialize_readlink3res (struct iovec outmsg, readlink3res *res); + +extern ssize_t +xdr_to_read3args (struct iovec inmsg, read3args *ra); + +extern ssize_t +xdr_serialize_read3res (struct iovec outmsg, read3res *res); + +extern ssize_t +xdr_serialize_read3res_nocopy (struct iovec outmsg, read3res *res); + +extern ssize_t +xdr_to_write3args (struct iovec inmsg, write3args *wa); + +extern ssize_t +xdr_to_write3args_nocopy (struct iovec inmsg, write3args *wa, +                          struct iovec *payload); + +extern ssize_t +xdr_serialize_write3res (struct iovec outmsg, write3res *res); + +extern ssize_t +xdr_to_create3args (struct iovec inmsg, create3args *ca); + +extern ssize_t +xdr_serialize_create3res (struct iovec outmsg, create3res *res); + +extern ssize_t +xdr_serialize_mkdir3res (struct iovec outmsg, mkdir3res *res); + +extern ssize_t +xdr_to_mkdir3args (struct iovec inmsg, mkdir3args *ma); + +extern ssize_t +xdr_to_symlink3args (struct iovec inmsg, symlink3args *sa); + +extern ssize_t +xdr_serialize_symlink3res (struct iovec outmsg, symlink3res *res); + +extern ssize_t +xdr_to_mknod3args (struct iovec inmsg, mknod3args *ma); + +extern ssize_t +xdr_serialize_mknod3res (struct iovec outmsg, mknod3res *res); + +extern ssize_t +xdr_to_remove3args (struct iovec inmsg, remove3args *ra); + +extern ssize_t +xdr_serialize_remove3res (struct iovec outmsg, remove3res *res); + +extern ssize_t +xdr_to_rmdir3args (struct iovec inmsg, rmdir3args *ra); + +extern ssize_t +xdr_serialize_rmdir3res (struct iovec outmsg, rmdir3res *res); + +extern ssize_t +xdr_serialize_rename3res (struct iovec outmsg, rename3res *res); + +extern ssize_t +xdr_to_rename3args (struct iovec inmsg, rename3args *ra); + +extern ssize_t +xdr_serialize_link3res (struct iovec outmsg, link3res *li); + +extern ssize_t +xdr_to_link3args (struct iovec inmsg, link3args *la); + +extern ssize_t +xdr_to_readdir3args (struct iovec inmsg, readdir3args *rd); + +extern ssize_t +xdr_serialize_readdir3res (struct iovec outmsg, readdir3res *res); + +extern ssize_t +xdr_to_readdirp3args (struct iovec inmsg, readdirp3args *rp); + +extern ssize_t +xdr_serialize_readdirp3res (struct iovec outmsg, readdirp3res *res); + +extern ssize_t +xdr_to_fsstat3args (struct iovec inmsg, fsstat3args *fa); + +extern ssize_t +xdr_serialize_fsstat3res (struct iovec outmsg, fsstat3res *res); + +extern ssize_t +xdr_to_fsinfo3args (struct iovec inmsg, fsinfo3args *fi); + +extern ssize_t +xdr_serialize_fsinfo3res (struct iovec outmsg, fsinfo3res *res); + +extern ssize_t +xdr_to_pathconf3args (struct iovec inmsg, pathconf3args *pc); + +extern ssize_t +xdr_serialize_pathconf3res (struct iovec outmsg, pathconf3res *res); + +extern ssize_t +xdr_to_commit3args (struct iovec inmsg, commit3args *ca); + +extern ssize_t +xdr_serialize_commit3res (struct iovec outmsg, commit3res *res); + +extern ssize_t +xdr_serialize_exports (struct iovec outmsg, exports *elist); + +extern ssize_t +xdr_serialize_mountlist (struct iovec outmsg, mountlist *ml); + +extern ssize_t +xdr_serialize_mountstat3 (struct iovec outmsg, mountstat3 *m); + +extern ssize_t +xdr_serialize_nfsstat3 (struct iovec outmsg, nfsstat3 *s); + +extern int +xdr_bytes_round_up (struct iovec *vec, size_t bufsize); + +extern ssize_t +xdr_length_round_up (size_t len, size_t bufsize); +#endif diff --git a/xlators/nfs/lib/src/xdr-common.h b/xlators/nfs/lib/src/xdr-common.h new file mode 100644 index 000000000..50a57ade9 --- /dev/null +++ b/xlators/nfs/lib/src/xdr-common.h @@ -0,0 +1,48 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _XDR_COMMON_H_ +#define _XDR_COMMON_H_ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include <rpc/rpc.h> +#define XDR_BYTES_PER_UNIT      4 + +/* Returns the address of the byte that follows the + * last byte used for decoding the previous xdr component. + * For eg, once the RPC call for NFS has been decoded, thie macro will return + * the address from which the NFS header starts. + */ +#define xdr_decoded_remaining_addr(xdr)        ((&xdr)->x_private) + +/* Returns the length of the remaining record after the previous decode + * operation completed. + */ +#define xdr_decoded_remaining_len(xdr)         ((&xdr)->x_handy) + +/* Returns the number of bytes used by the last encode operation. */ +#define xdr_encoded_length(xdr) (((size_t)(&xdr)->x_private) - ((size_t)(&xdr)->x_base)) + +#define xdr_decoded_length(xdr) (((size_t)(&xdr)->x_private) - ((size_t)(&xdr)->x_base)) + +#endif diff --git a/xlators/nfs/lib/src/xdr-nfs3.c b/xlators/nfs/lib/src/xdr-nfs3.c new file mode 100644 index 000000000..6a8fe48a4 --- /dev/null +++ b/xlators/nfs/lib/src/xdr-nfs3.c @@ -0,0 +1,1892 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#include "xdr-nfs3.h" +#include "mem-pool.h" + +bool_t +xdr_uint64 (XDR *xdrs, uint64 *objp) +{ +	 if (!xdr_u_quad_t (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_int64 (XDR *xdrs, int64 *objp) +{ +	 if (!xdr_quad_t (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_uint32 (XDR *xdrs, uint32 *objp) +{ +	 if (!xdr_u_long (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_int32 (XDR *xdrs, int32 *objp) +{ +	 if (!xdr_long (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_filename3 (XDR *xdrs, filename3 *objp) +{ +	 if (!xdr_string (xdrs, objp, ~0)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_nfspath3 (XDR *xdrs, nfspath3 *objp) +{ +	 if (!xdr_string (xdrs, objp, ~0)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fileid3 (XDR *xdrs, fileid3 *objp) +{ +	 if (!xdr_uint64 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_cookie3 (XDR *xdrs, cookie3 *objp) +{ +	 if (!xdr_uint64 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_cookieverf3 (XDR *xdrs, cookieverf3 objp) +{ +	 if (!xdr_opaque (xdrs, objp, NFS3_COOKIEVERFSIZE)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_createverf3 (XDR *xdrs, createverf3 objp) +{ +	 if (!xdr_opaque (xdrs, objp, NFS3_CREATEVERFSIZE)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_writeverf3 (XDR *xdrs, writeverf3 objp) +{ +	 if (!xdr_opaque (xdrs, objp, NFS3_WRITEVERFSIZE)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_uid3 (XDR *xdrs, uid3 *objp) +{ +	 if (!xdr_uint32 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_gid3 (XDR *xdrs, gid3 *objp) +{ +	 if (!xdr_uint32 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_size3 (XDR *xdrs, size3 *objp) +{ +	 if (!xdr_uint64 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_offset3 (XDR *xdrs, offset3 *objp) +{ +	 if (!xdr_uint64 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mode3 (XDR *xdrs, mode3 *objp) +{ +	 if (!xdr_uint32 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_count3 (XDR *xdrs, count3 *objp) +{ +	 if (!xdr_uint32 (xdrs, objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_nfsstat3 (XDR *xdrs, nfsstat3 *objp) +{ +	 if (!xdr_enum (xdrs, (enum_t *) objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_ftype3 (XDR *xdrs, ftype3 *objp) +{ +	 if (!xdr_enum (xdrs, (enum_t *) objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_specdata3 (XDR *xdrs, specdata3 *objp) +{ +	 if (!xdr_uint32 (xdrs, &objp->specdata1)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->specdata2)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_nfs_fh3 (XDR *xdrs, nfs_fh3 *objp) +{ +	 if (!xdr_bytes (xdrs, (char **)&objp->data.data_val, (u_int *) &objp->data.data_len, NFS3_FHSIZE)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_nfstime3 (XDR *xdrs, nfstime3 *objp) +{ +	 if (!xdr_uint32 (xdrs, &objp->seconds)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->nseconds)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fattr3 (XDR *xdrs, fattr3 *objp) +{ +	 if (!xdr_ftype3 (xdrs, &objp->type)) +		 return FALSE; +	 if (!xdr_mode3 (xdrs, &objp->mode)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->nlink)) +		 return FALSE; +	 if (!xdr_uid3 (xdrs, &objp->uid)) +		 return FALSE; +	 if (!xdr_gid3 (xdrs, &objp->gid)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->size)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->used)) +		 return FALSE; +	 if (!xdr_specdata3 (xdrs, &objp->rdev)) +		 return FALSE; +	 if (!xdr_uint64 (xdrs, &objp->fsid)) +		 return FALSE; +	 if (!xdr_fileid3 (xdrs, &objp->fileid)) +		 return FALSE; +	 if (!xdr_nfstime3 (xdrs, &objp->atime)) +		 return FALSE; +	 if (!xdr_nfstime3 (xdrs, &objp->mtime)) +		 return FALSE; +	 if (!xdr_nfstime3 (xdrs, &objp->ctime)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_post_op_attr (XDR *xdrs, post_op_attr *objp) +{ +	 if (!xdr_bool (xdrs, &objp->attributes_follow)) +		 return FALSE; +	switch (objp->attributes_follow) { +	case TRUE: +		 if (!xdr_fattr3 (xdrs, &objp->post_op_attr_u.attributes)) +			 return FALSE; +		break; +	case FALSE: +		break; +	default: +		return FALSE; +	} +	return TRUE; +} + +bool_t +xdr_wcc_attr (XDR *xdrs, wcc_attr *objp) +{ +	 if (!xdr_size3 (xdrs, &objp->size)) +		 return FALSE; +	 if (!xdr_nfstime3 (xdrs, &objp->mtime)) +		 return FALSE; +	 if (!xdr_nfstime3 (xdrs, &objp->ctime)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_pre_op_attr (XDR *xdrs, pre_op_attr *objp) +{ +	 if (!xdr_bool (xdrs, &objp->attributes_follow)) +		 return FALSE; +	switch (objp->attributes_follow) { +	case TRUE: +		 if (!xdr_wcc_attr (xdrs, &objp->pre_op_attr_u.attributes)) +			 return FALSE; +		break; +	case FALSE: +		break; +	default: +		return FALSE; +	} +	return TRUE; +} + +bool_t +xdr_wcc_data (XDR *xdrs, wcc_data *objp) +{ +	 if (!xdr_pre_op_attr (xdrs, &objp->before)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->after)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_post_op_fh3 (XDR *xdrs, post_op_fh3 *objp) +{ +	 if (!xdr_bool (xdrs, &objp->handle_follows)) +		 return FALSE; +	switch (objp->handle_follows) { +	case TRUE: +		 if (!xdr_nfs_fh3 (xdrs, &objp->post_op_fh3_u.handle)) +			 return FALSE; +		break; +	case FALSE: +		break; +	default: +		return FALSE; +	} +	return TRUE; +} + +bool_t +xdr_time_how (XDR *xdrs, time_how *objp) +{ +	 if (!xdr_enum (xdrs, (enum_t *) objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_set_mode3 (XDR *xdrs, set_mode3 *objp) +{ +	 if (!xdr_bool (xdrs, &objp->set_it)) +		 return FALSE; +	switch (objp->set_it) { +	case TRUE: +		 if (!xdr_mode3 (xdrs, &objp->set_mode3_u.mode)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_set_uid3 (XDR *xdrs, set_uid3 *objp) +{ +	 if (!xdr_bool (xdrs, &objp->set_it)) +		 return FALSE; +	switch (objp->set_it) { +	case TRUE: +		 if (!xdr_uid3 (xdrs, &objp->set_uid3_u.uid)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_set_gid3 (XDR *xdrs, set_gid3 *objp) +{ +	 if (!xdr_bool (xdrs, &objp->set_it)) +		 return FALSE; +	switch (objp->set_it) { +	case TRUE: +		 if (!xdr_gid3 (xdrs, &objp->set_gid3_u.gid)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_set_size3 (XDR *xdrs, set_size3 *objp) +{ +	 if (!xdr_bool (xdrs, &objp->set_it)) +		 return FALSE; +	switch (objp->set_it) { +	case TRUE: +		 if (!xdr_size3 (xdrs, &objp->set_size3_u.size)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_set_atime (XDR *xdrs, set_atime *objp) +{ +	 if (!xdr_time_how (xdrs, &objp->set_it)) +		 return FALSE; +	switch (objp->set_it) { +	case SET_TO_CLIENT_TIME: +		 if (!xdr_nfstime3 (xdrs, &objp->set_atime_u.atime)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_set_mtime (XDR *xdrs, set_mtime *objp) +{ +	 if (!xdr_time_how (xdrs, &objp->set_it)) +		 return FALSE; +	switch (objp->set_it) { +	case SET_TO_CLIENT_TIME: +		 if (!xdr_nfstime3 (xdrs, &objp->set_mtime_u.mtime)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_sattr3 (XDR *xdrs, sattr3 *objp) +{ +	 if (!xdr_set_mode3 (xdrs, &objp->mode)) +		 return FALSE; +	 if (!xdr_set_uid3 (xdrs, &objp->uid)) +		 return FALSE; +	 if (!xdr_set_gid3 (xdrs, &objp->gid)) +		 return FALSE; +	 if (!xdr_set_size3 (xdrs, &objp->size)) +		 return FALSE; +	 if (!xdr_set_atime (xdrs, &objp->atime)) +		 return FALSE; +	 if (!xdr_set_mtime (xdrs, &objp->mtime)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_diropargs3 (XDR *xdrs, diropargs3 *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->dir)) +		 return FALSE; +	 if (!xdr_filename3 (xdrs, &objp->name)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_getattr3args (XDR *xdrs, getattr3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->object)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_getattr3resok (XDR *xdrs, getattr3resok *objp) +{ +	 if (!xdr_fattr3 (xdrs, &objp->obj_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_getattr3res (XDR *xdrs, getattr3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_getattr3resok (xdrs, &objp->getattr3res_u.resok)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_sattrguard3 (XDR *xdrs, sattrguard3 *objp) +{ +	 if (!xdr_bool (xdrs, &objp->check)) +		 return FALSE; +	switch (objp->check) { +	case TRUE: +		 if (!xdr_nfstime3 (xdrs, &objp->sattrguard3_u.obj_ctime)) +			 return FALSE; +		break; +	case FALSE: +		break; +	default: +		return FALSE; +	} +	return TRUE; +} + +bool_t +xdr_setattr3args (XDR *xdrs, setattr3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->object)) +		 return FALSE; +	 if (!xdr_sattr3 (xdrs, &objp->new_attributes)) +		 return FALSE; +	 if (!xdr_sattrguard3 (xdrs, &objp->guard)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_setattr3resok (XDR *xdrs, setattr3resok *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->obj_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_setattr3resfail (XDR *xdrs, setattr3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->obj_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_setattr3res (XDR *xdrs, setattr3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_setattr3resok (xdrs, &objp->setattr3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_setattr3resfail (xdrs, &objp->setattr3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_lookup3args (XDR *xdrs, lookup3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->what)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_lookup3resok (XDR *xdrs, lookup3resok *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->object)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->dir_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_lookup3resfail (XDR *xdrs, lookup3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->dir_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_lookup3res (XDR *xdrs, lookup3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_lookup3resok (xdrs, &objp->lookup3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_lookup3resfail (xdrs, &objp->lookup3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_access3args (XDR *xdrs, access3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->object)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->access)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_access3resok (XDR *xdrs, access3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->access)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_access3resfail (XDR *xdrs, access3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_access3res (XDR *xdrs, access3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_access3resok (xdrs, &objp->access3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_access3resfail (xdrs, &objp->access3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_readlink3args (XDR *xdrs, readlink3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->symlink)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readlink3resok (XDR *xdrs, readlink3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->symlink_attributes)) +		 return FALSE; +	 if (!xdr_nfspath3 (xdrs, &objp->data)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readlink3resfail (XDR *xdrs, readlink3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->symlink_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readlink3res (XDR *xdrs, readlink3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_readlink3resok (xdrs, &objp->readlink3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_readlink3resfail (xdrs, &objp->readlink3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_read3args (XDR *xdrs, read3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->file)) +		 return FALSE; +	 if (!xdr_offset3 (xdrs, &objp->offset)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_read3resok_nocopy (XDR *xdrs, read3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->file_attributes)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->eof)) +		 return FALSE; +         if (!xdr_u_int (xdrs, (u_int *) &objp->data.data_len)) +                 return FALSE; +	return TRUE; +} + + +bool_t +xdr_read3resok (XDR *xdrs, read3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->file_attributes)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->eof)) +		 return FALSE; +	 if (!xdr_bytes (xdrs, (char **)&objp->data.data_val, (u_int *) &objp->data.data_len, ~0)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_read3resfail (XDR *xdrs, read3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->file_attributes)) +		 return FALSE; +	return TRUE; +} + + +bool_t +xdr_read3res_nocopy (XDR *xdrs, read3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_read3resok_nocopy (xdrs, &objp->read3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_read3resfail (xdrs, &objp->read3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + + +bool_t +xdr_read3res (XDR *xdrs, read3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_read3resok (xdrs, &objp->read3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_read3resfail (xdrs, &objp->read3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_stable_how (XDR *xdrs, stable_how *objp) +{ +	 if (!xdr_enum (xdrs, (enum_t *) objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_write3args (XDR *xdrs, write3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->file)) +		 return FALSE; +	 if (!xdr_offset3 (xdrs, &objp->offset)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	 if (!xdr_stable_how (xdrs, &objp->stable)) +		 return FALSE; + +         /* Added specifically to avoid copies from the xdr buffer into +          * the write3args structure, which will also require an already +          * allocated buffer. That is not optimal. +          */ +         if (!xdr_u_int (xdrs, (u_int *) &objp->data.data_len)) +                 return FALSE; + +         /* The remaining bytes in the xdr buffer are the bytes that need to be +          * written. See how these bytes are extracted in the xdr_to_write3args +          * code path. Be careful, while using the write3args structure, since +          * only the data.data_len has been filled. The actual data is +          * extracted in xdr_to_write3args path. +          */ + +         /*	 if (!xdr_bytes (xdrs, (char **)&objp->data.data_val, (u_int *) &objp->data.data_len, ~0)) +		 return FALSE; +                 */ +	return TRUE; +} + +bool_t +xdr_write3resok (XDR *xdrs, write3resok *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->file_wcc)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	 if (!xdr_stable_how (xdrs, &objp->committed)) +		 return FALSE; +	 if (!xdr_writeverf3 (xdrs, objp->verf)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_write3resfail (XDR *xdrs, write3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->file_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_write3res (XDR *xdrs, write3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_write3resok (xdrs, &objp->write3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_write3resfail (xdrs, &objp->write3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_createmode3 (XDR *xdrs, createmode3 *objp) +{ +	 if (!xdr_enum (xdrs, (enum_t *) objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_createhow3 (XDR *xdrs, createhow3 *objp) +{ +	 if (!xdr_createmode3 (xdrs, &objp->mode)) +		 return FALSE; +	switch (objp->mode) { +	case UNCHECKED: +	case GUARDED: +		 if (!xdr_sattr3 (xdrs, &objp->createhow3_u.obj_attributes)) +			 return FALSE; +		break; +	case EXCLUSIVE: +		 if (!xdr_createverf3 (xdrs, objp->createhow3_u.verf)) +			 return FALSE; +		break; +	default: +		return FALSE; +	} +	return TRUE; +} + +bool_t +xdr_create3args (XDR *xdrs, create3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->where)) +		 return FALSE; +	 if (!xdr_createhow3 (xdrs, &objp->how)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_create3resok (XDR *xdrs, create3resok *objp) +{ +	 if (!xdr_post_op_fh3 (xdrs, &objp->obj)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_create3resfail (XDR *xdrs, create3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_create3res (XDR *xdrs, create3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_create3resok (xdrs, &objp->create3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_create3resfail (xdrs, &objp->create3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_mkdir3args (XDR *xdrs, mkdir3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->where)) +		 return FALSE; +	 if (!xdr_sattr3 (xdrs, &objp->attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mkdir3resok (XDR *xdrs, mkdir3resok *objp) +{ +	 if (!xdr_post_op_fh3 (xdrs, &objp->obj)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mkdir3resfail (XDR *xdrs, mkdir3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mkdir3res (XDR *xdrs, mkdir3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_mkdir3resok (xdrs, &objp->mkdir3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_mkdir3resfail (xdrs, &objp->mkdir3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_symlinkdata3 (XDR *xdrs, symlinkdata3 *objp) +{ +	 if (!xdr_sattr3 (xdrs, &objp->symlink_attributes)) +		 return FALSE; +	 if (!xdr_nfspath3 (xdrs, &objp->symlink_data)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_symlink3args (XDR *xdrs, symlink3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->where)) +		 return FALSE; +	 if (!xdr_symlinkdata3 (xdrs, &objp->symlink)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_symlink3resok (XDR *xdrs, symlink3resok *objp) +{ +	 if (!xdr_post_op_fh3 (xdrs, &objp->obj)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_symlink3resfail (XDR *xdrs, symlink3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_symlink3res (XDR *xdrs, symlink3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_symlink3resok (xdrs, &objp->symlink3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_symlink3resfail (xdrs, &objp->symlink3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_devicedata3 (XDR *xdrs, devicedata3 *objp) +{ +	 if (!xdr_sattr3 (xdrs, &objp->dev_attributes)) +		 return FALSE; +	 if (!xdr_specdata3 (xdrs, &objp->spec)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mknoddata3 (XDR *xdrs, mknoddata3 *objp) +{ +	 if (!xdr_ftype3 (xdrs, &objp->type)) +		 return FALSE; +	switch (objp->type) { +	case NF3CHR: +	case NF3BLK: +		 if (!xdr_devicedata3 (xdrs, &objp->mknoddata3_u.device)) +			 return FALSE; +		break; +	case NF3SOCK: +	case NF3FIFO: +		 if (!xdr_sattr3 (xdrs, &objp->mknoddata3_u.pipe_attributes)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_mknod3args (XDR *xdrs, mknod3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->where)) +		 return FALSE; +	 if (!xdr_mknoddata3 (xdrs, &objp->what)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mknod3resok (XDR *xdrs, mknod3resok *objp) +{ +	 if (!xdr_post_op_fh3 (xdrs, &objp->obj)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mknod3resfail (XDR *xdrs, mknod3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mknod3res (XDR *xdrs, mknod3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_mknod3resok (xdrs, &objp->mknod3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_mknod3resfail (xdrs, &objp->mknod3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_remove3args (XDR *xdrs, remove3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->object)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_remove3resok (XDR *xdrs, remove3resok *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_remove3resfail (XDR *xdrs, remove3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_remove3res (XDR *xdrs, remove3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_remove3resok (xdrs, &objp->remove3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_remove3resfail (xdrs, &objp->remove3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_rmdir3args (XDR *xdrs, rmdir3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->object)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_rmdir3resok (XDR *xdrs, rmdir3resok *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_rmdir3resfail (XDR *xdrs, rmdir3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->dir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_rmdir3res (XDR *xdrs, rmdir3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_rmdir3resok (xdrs, &objp->rmdir3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_rmdir3resfail (xdrs, &objp->rmdir3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_rename3args (XDR *xdrs, rename3args *objp) +{ +	 if (!xdr_diropargs3 (xdrs, &objp->from)) +		 return FALSE; +	 if (!xdr_diropargs3 (xdrs, &objp->to)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_rename3resok (XDR *xdrs, rename3resok *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->fromdir_wcc)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->todir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_rename3resfail (XDR *xdrs, rename3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->fromdir_wcc)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->todir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_rename3res (XDR *xdrs, rename3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_rename3resok (xdrs, &objp->rename3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_rename3resfail (xdrs, &objp->rename3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_link3args (XDR *xdrs, link3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->file)) +		 return FALSE; +	 if (!xdr_diropargs3 (xdrs, &objp->link)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_link3resok (XDR *xdrs, link3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->file_attributes)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->linkdir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_link3resfail (XDR *xdrs, link3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->file_attributes)) +		 return FALSE; +	 if (!xdr_wcc_data (xdrs, &objp->linkdir_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_link3res (XDR *xdrs, link3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_link3resok (xdrs, &objp->link3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_link3resfail (xdrs, &objp->link3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_readdir3args (XDR *xdrs, readdir3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->dir)) +		 return FALSE; +	 if (!xdr_cookie3 (xdrs, &objp->cookie)) +		 return FALSE; +	 if (!xdr_cookieverf3 (xdrs, objp->cookieverf)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_entry3 (XDR *xdrs, entry3 *objp) +{ +	 if (!xdr_fileid3 (xdrs, &objp->fileid)) +		 return FALSE; +	 if (!xdr_filename3 (xdrs, &objp->name)) +		 return FALSE; +	 if (!xdr_cookie3 (xdrs, &objp->cookie)) +		 return FALSE; +	 if (!xdr_pointer (xdrs, (char **)&objp->nextentry, sizeof (entry3), (xdrproc_t) xdr_entry3)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_dirlist3 (XDR *xdrs, dirlist3 *objp) +{ +	 if (!xdr_pointer (xdrs, (char **)&objp->entries, sizeof (entry3), (xdrproc_t) xdr_entry3)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->eof)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readdir3resok (XDR *xdrs, readdir3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->dir_attributes)) +		 return FALSE; +	 if (!xdr_cookieverf3 (xdrs, objp->cookieverf)) +		 return FALSE; +	 if (!xdr_dirlist3 (xdrs, &objp->reply)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readdir3resfail (XDR *xdrs, readdir3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->dir_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readdir3res (XDR *xdrs, readdir3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_readdir3resok (xdrs, &objp->readdir3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_readdir3resfail (xdrs, &objp->readdir3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_readdirp3args (XDR *xdrs, readdirp3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->dir)) +		 return FALSE; +	 if (!xdr_cookie3 (xdrs, &objp->cookie)) +		 return FALSE; +	 if (!xdr_cookieverf3 (xdrs, objp->cookieverf)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->dircount)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->maxcount)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_entryp3 (XDR *xdrs, entryp3 *objp) +{ +	 if (!xdr_fileid3 (xdrs, &objp->fileid)) +		 return FALSE; +	 if (!xdr_filename3 (xdrs, &objp->name)) +		 return FALSE; +	 if (!xdr_cookie3 (xdrs, &objp->cookie)) +		 return FALSE; +	 if (!xdr_post_op_attr (xdrs, &objp->name_attributes)) +		 return FALSE; +	 if (!xdr_post_op_fh3 (xdrs, &objp->name_handle)) +		 return FALSE; +	 if (!xdr_pointer (xdrs, (char **)&objp->nextentry, sizeof (entryp3), (xdrproc_t) xdr_entryp3)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_dirlistp3 (XDR *xdrs, dirlistp3 *objp) +{ +	 if (!xdr_pointer (xdrs, (char **)&objp->entries, sizeof (entryp3), (xdrproc_t) xdr_entryp3)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->eof)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readdirp3resok (XDR *xdrs, readdirp3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->dir_attributes)) +		 return FALSE; +	 if (!xdr_cookieverf3 (xdrs, objp->cookieverf)) +		 return FALSE; +	 if (!xdr_dirlistp3 (xdrs, &objp->reply)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readdirp3resfail (XDR *xdrs, readdirp3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->dir_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_readdirp3res (XDR *xdrs, readdirp3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_readdirp3resok (xdrs, &objp->readdirp3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_readdirp3resfail (xdrs, &objp->readdirp3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_fsstat3args (XDR *xdrs, fsstat3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->fsroot)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fsstat3resok (XDR *xdrs, fsstat3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->tbytes)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->fbytes)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->abytes)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->tfiles)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->ffiles)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->afiles)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->invarsec)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fsstat3resfail (XDR *xdrs, fsstat3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fsstat3res (XDR *xdrs, fsstat3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_fsstat3resok (xdrs, &objp->fsstat3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_fsstat3resfail (xdrs, &objp->fsstat3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_fsinfo3args (XDR *xdrs, fsinfo3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->fsroot)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fsinfo3resok (XDR *xdrs, fsinfo3resok *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->rtmax)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->rtpref)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->rtmult)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->wtmax)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->wtpref)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->wtmult)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->dtpref)) +		 return FALSE; +	 if (!xdr_size3 (xdrs, &objp->maxfilesize)) +		 return FALSE; +	 if (!xdr_nfstime3 (xdrs, &objp->time_delta)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->properties)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fsinfo3resfail (XDR *xdrs, fsinfo3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_fsinfo3res (XDR *xdrs, fsinfo3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_fsinfo3resok (xdrs, &objp->fsinfo3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_fsinfo3resfail (xdrs, &objp->fsinfo3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_pathconf3args (XDR *xdrs, pathconf3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->object)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_pathconf3resok (XDR *xdrs, pathconf3resok *objp) +{ +	register int32_t *buf; + + +	if (xdrs->x_op == XDR_ENCODE) { +		 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +			 return FALSE; +		 if (!xdr_uint32 (xdrs, &objp->linkmax)) +			 return FALSE; +		 if (!xdr_uint32 (xdrs, &objp->name_max)) +			 return FALSE; +		buf = XDR_INLINE (xdrs, 4 * BYTES_PER_XDR_UNIT); +		if (buf == NULL) { +			 if (!xdr_bool (xdrs, &objp->no_trunc)) +				 return FALSE; +			 if (!xdr_bool (xdrs, &objp->chown_restricted)) +				 return FALSE; +			 if (!xdr_bool (xdrs, &objp->case_insensitive)) +				 return FALSE; +			 if (!xdr_bool (xdrs, &objp->case_preserving)) +				 return FALSE; +		} else { +			IXDR_PUT_BOOL(buf, objp->no_trunc); +			IXDR_PUT_BOOL(buf, objp->chown_restricted); +			IXDR_PUT_BOOL(buf, objp->case_insensitive); +			IXDR_PUT_BOOL(buf, objp->case_preserving); +		} +		return TRUE; +	} else if (xdrs->x_op == XDR_DECODE) { +		 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +			 return FALSE; +		 if (!xdr_uint32 (xdrs, &objp->linkmax)) +			 return FALSE; +		 if (!xdr_uint32 (xdrs, &objp->name_max)) +			 return FALSE; +		buf = XDR_INLINE (xdrs, 4 * BYTES_PER_XDR_UNIT); +		if (buf == NULL) { +			 if (!xdr_bool (xdrs, &objp->no_trunc)) +				 return FALSE; +			 if (!xdr_bool (xdrs, &objp->chown_restricted)) +				 return FALSE; +			 if (!xdr_bool (xdrs, &objp->case_insensitive)) +				 return FALSE; +			 if (!xdr_bool (xdrs, &objp->case_preserving)) +				 return FALSE; +		} else { +			objp->no_trunc = IXDR_GET_BOOL(buf); +			objp->chown_restricted = IXDR_GET_BOOL(buf); +			objp->case_insensitive = IXDR_GET_BOOL(buf); +			objp->case_preserving = IXDR_GET_BOOL(buf); +		} +	 return TRUE; +	} + +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->linkmax)) +		 return FALSE; +	 if (!xdr_uint32 (xdrs, &objp->name_max)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->no_trunc)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->chown_restricted)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->case_insensitive)) +		 return FALSE; +	 if (!xdr_bool (xdrs, &objp->case_preserving)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_pathconf3resfail (XDR *xdrs, pathconf3resfail *objp) +{ +	 if (!xdr_post_op_attr (xdrs, &objp->obj_attributes)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_pathconf3res (XDR *xdrs, pathconf3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_pathconf3resok (xdrs, &objp->pathconf3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_pathconf3resfail (xdrs, &objp->pathconf3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_commit3args (XDR *xdrs, commit3args *objp) +{ +	 if (!xdr_nfs_fh3 (xdrs, &objp->file)) +		 return FALSE; +	 if (!xdr_offset3 (xdrs, &objp->offset)) +		 return FALSE; +	 if (!xdr_count3 (xdrs, &objp->count)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_commit3resok (XDR *xdrs, commit3resok *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->file_wcc)) +		 return FALSE; +	 if (!xdr_writeverf3 (xdrs, objp->verf)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_commit3resfail (XDR *xdrs, commit3resfail *objp) +{ +	 if (!xdr_wcc_data (xdrs, &objp->file_wcc)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_commit3res (XDR *xdrs, commit3res *objp) +{ +	 if (!xdr_nfsstat3 (xdrs, &objp->status)) +		 return FALSE; +	switch (objp->status) { +	case NFS3_OK: +		 if (!xdr_commit3resok (xdrs, &objp->commit3res_u.resok)) +			 return FALSE; +		break; +	default: +		 if (!xdr_commit3resfail (xdrs, &objp->commit3res_u.resfail)) +			 return FALSE; +		break; +	} +	return TRUE; +} + +bool_t +xdr_fhandle3 (XDR *xdrs, fhandle3 *objp) +{ +	 if (!xdr_bytes (xdrs, (char **)&objp->fhandle3_val, (u_int *) &objp->fhandle3_len, FHSIZE3)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_dirpath (XDR *xdrs, dirpath *objp) +{ +	 if (!xdr_string (xdrs, objp, MNTPATHLEN)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_name (XDR *xdrs, name *objp) +{ +	 if (!xdr_string (xdrs, objp, MNTNAMLEN)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mountstat3 (XDR *xdrs, mountstat3 *objp) +{ +	 if (!xdr_enum (xdrs, (enum_t *) objp)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mountres3_ok (XDR *xdrs, mountres3_ok *objp) +{ +	 if (!xdr_fhandle3 (xdrs, &objp->fhandle)) +		 return FALSE; +	 if (!xdr_array (xdrs, (char **)&objp->auth_flavors.auth_flavors_val, (u_int *) &objp->auth_flavors.auth_flavors_len, ~0, +		sizeof (int), (xdrproc_t) xdr_int)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mountres3 (XDR *xdrs, mountres3 *objp) +{ +	 if (!xdr_mountstat3 (xdrs, &objp->fhs_status)) +		 return FALSE; +	switch (objp->fhs_status) { +	case MNT3_OK: +		 if (!xdr_mountres3_ok (xdrs, &objp->mountres3_u.mountinfo)) +			 return FALSE; +		break; +	default: +		break; +	} +	return TRUE; +} + +bool_t +xdr_mountlist (XDR *xdrs, mountlist *objp) +{ +	 if (!xdr_pointer (xdrs, (char **)objp, sizeof (struct mountbody), (xdrproc_t) xdr_mountbody)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_mountbody (XDR *xdrs, mountbody *objp) +{ +	 if (!xdr_name (xdrs, &objp->ml_hostname)) +		 return FALSE; +	 if (!xdr_dirpath (xdrs, &objp->ml_directory)) +		 return FALSE; +	 if (!xdr_mountlist (xdrs, &objp->ml_next)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_groups (XDR *xdrs, groups *objp) +{ +	 if (!xdr_pointer (xdrs, (char **)objp, sizeof (struct groupnode), (xdrproc_t) xdr_groupnode)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_groupnode (XDR *xdrs, groupnode *objp) +{ +	 if (!xdr_name (xdrs, &objp->gr_name)) +		 return FALSE; +	 if (!xdr_groups (xdrs, &objp->gr_next)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_exports (XDR *xdrs, exports *objp) +{ +	 if (!xdr_pointer (xdrs, (char **)objp, sizeof (struct exportnode), (xdrproc_t) xdr_exportnode)) +		 return FALSE; +	return TRUE; +} + +bool_t +xdr_exportnode (XDR *xdrs, exportnode *objp) +{ +	 if (!xdr_dirpath (xdrs, &objp->ex_dir)) +		 return FALSE; +	 if (!xdr_groups (xdrs, &objp->ex_groups)) +		 return FALSE; +	 if (!xdr_exports (xdrs, &objp->ex_next)) +		 return FALSE; +	return TRUE; +} + +void +xdr_free_exports_list (struct exportnode *first) +{ +        struct exportnode       *elist = NULL; + +        if (!first) +                return; + +        while (first) { +                elist = first->ex_next; +                if (first->ex_dir) +                        FREE (first->ex_dir); + +                if (first->ex_groups) { +                        if (first->ex_groups->gr_name) +                                FREE (first->ex_groups->gr_name); +                        FREE (first->ex_groups); +                } + +                FREE (first); +                first = elist; +        } + +} + + +void +xdr_free_mountlist (mountlist ml) +{ +        struct mountbody        *next = NULL; + +        if (!ml) +                return; + +        while (ml) { +                FREE (ml->ml_hostname); +                FREE (ml->ml_directory); +                next = ml->ml_next; +                FREE (ml); +                ml = next; +        } + +        return; +} + + +/* Free statements are based on the way sunrpc xdr decoding + * code performs memory allocations. + */ +void +xdr_free_write3args_nocopy (write3args *wa) +{ +        if (!wa) +                return; + +        FREE (wa->file.data.data_val); +        FREE (wa); +} + + diff --git a/xlators/nfs/lib/src/xdr-nfs3.h b/xlators/nfs/lib/src/xdr-nfs3.h new file mode 100644 index 000000000..8223def1f --- /dev/null +++ b/xlators/nfs/lib/src/xdr-nfs3.h @@ -0,0 +1,1205 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _XDR_NFS3_H +#define _XDR_NFS3_H + +#include <rpc/rpc.h> + +#define NFS3_FHSIZE             64 +#define NFS3_COOKIEVERFSIZE     8 +#define NFS3_CREATEVERFSIZE     8 +#define NFS3_WRITEVERFSIZE      8 + +#define NFS3_ENTRY3_FIXED_SIZE  24 +#define NFS3_POSTOPATTR_SIZE    88 +#define NFS3_READDIR_RESOK_SIZE (NFS3_POSTOPATTR_SIZE + sizeof (bool_t) + NFS3_COOKIEVERFSIZE) + +/* In size of post_op_fh3, the length of the file handle will have to be + * included separately since we have variable length fh. Here we only account + * for the field for handle_follows and for the file handle length field. + */ +#define NFS3_POSTOPFH3_FIXED_SIZE     (sizeof (bool_t) + sizeof (uint32_t)) + +/* Similarly, the size of the entry will have to include the variable length + * file handle and the length of the entry name. + */ +#define NFS3_ENTRYP3_FIXED_SIZE  (NFS3_ENTRY3_FIXED_SIZE + NFS3_POSTOPATTR_SIZE + NFS3_POSTOPFH3_FIXED_SIZE) + +typedef u_quad_t uint64; +typedef quad_t int64; +typedef u_long uint32; +typedef long int32; +typedef char *filename3; +typedef char *nfspath3; +typedef uint64 fileid3; +typedef uint64 cookie3; +typedef char cookieverf3[NFS3_COOKIEVERFSIZE]; +typedef char createverf3[NFS3_CREATEVERFSIZE]; +typedef char writeverf3[NFS3_WRITEVERFSIZE]; +typedef uint32 uid3; +typedef uint32 gid3; +typedef uint64 size3; +typedef uint64 offset3; +typedef uint32 mode3; +typedef uint32 count3; + +#define NFS3MODE_SETXUID        0x00800 +#define NFS3MODE_SETXGID        0x00400 +#define NFS3MODE_SAVESWAPTXT    0x00200 +#define NFS3MODE_ROWNER         0x00100 +#define NFS3MODE_WOWNER         0x00080 +#define NFS3MODE_XOWNER         0x00040 +#define NFS3MODE_RGROUP         0x00020 +#define NFS3MODE_WGROUP         0x00010 +#define NFS3MODE_XGROUP         0x00008 +#define NFS3MODE_ROTHER         0x00004 +#define NFS3MODE_WOTHER         0x00002 +#define NFS3MODE_XOTHER         0x00001 + +enum nfsstat3 { +	NFS3_OK = 0, +	NFS3ERR_PERM = 1, +	NFS3ERR_NOENT = 2, +	NFS3ERR_IO = 5, +	NFS3ERR_NXIO = 6, +	NFS3ERR_ACCES = 13, +	NFS3ERR_EXIST = 17, +	NFS3ERR_XDEV = 18, +	NFS3ERR_NODEV = 19, +	NFS3ERR_NOTDIR = 20, +	NFS3ERR_ISDIR = 21, +	NFS3ERR_INVAL = 22, +	NFS3ERR_FBIG = 27, +	NFS3ERR_NOSPC = 28, +	NFS3ERR_ROFS = 30, +	NFS3ERR_MLINK = 31, +	NFS3ERR_NAMETOOLONG = 63, +	NFS3ERR_NOTEMPTY = 66, +	NFS3ERR_DQUOT = 69, +	NFS3ERR_STALE = 70, +	NFS3ERR_REMOTE = 71, +	NFS3ERR_BADHANDLE = 10001, +	NFS3ERR_NOT_SYNC = 10002, +	NFS3ERR_BAD_COOKIE = 10003, +	NFS3ERR_NOTSUPP = 10004, +	NFS3ERR_TOOSMALL = 10005, +	NFS3ERR_SERVERFAULT = 10006, +	NFS3ERR_BADTYPE = 10007, +	NFS3ERR_JUKEBOX = 10008, +}; +typedef enum nfsstat3 nfsstat3; + +enum ftype3 { +	NF3REG = 1, +	NF3DIR = 2, +	NF3BLK = 3, +	NF3CHR = 4, +	NF3LNK = 5, +	NF3SOCK = 6, +	NF3FIFO = 7, +}; +typedef enum ftype3 ftype3; + +struct specdata3 { +	uint32 specdata1; +	uint32 specdata2; +}; +typedef struct specdata3 specdata3; + +struct nfs_fh3 { +	struct { +		u_int data_len; +		char *data_val; +	} data; +}; +typedef struct nfs_fh3 nfs_fh3; + +struct nfstime3 { +	uint32 seconds; +	uint32 nseconds; +}; +typedef struct nfstime3 nfstime3; + +struct fattr3 { +	ftype3 type; +	mode3 mode; +	uint32 nlink; +	uid3 uid; +	gid3 gid; +	size3 size; +	size3 used; +	specdata3 rdev; +	uint64 fsid; +	fileid3 fileid; +	nfstime3 atime; +	nfstime3 mtime; +	nfstime3 ctime; +}; +typedef struct fattr3 fattr3; + +struct post_op_attr { +	bool_t attributes_follow; +	union { +		fattr3 attributes; +	} post_op_attr_u; +}; +typedef struct post_op_attr post_op_attr; + +struct wcc_attr { +	size3 size; +	nfstime3 mtime; +	nfstime3 ctime; +}; +typedef struct wcc_attr wcc_attr; + +struct pre_op_attr { +	bool_t attributes_follow; +	union { +		wcc_attr attributes; +	} pre_op_attr_u; +}; +typedef struct pre_op_attr pre_op_attr; + +struct wcc_data { +	pre_op_attr before; +	post_op_attr after; +}; +typedef struct wcc_data wcc_data; + +struct post_op_fh3 { +	bool_t handle_follows; +	union { +		nfs_fh3 handle; +	} post_op_fh3_u; +}; +typedef struct post_op_fh3 post_op_fh3; + +enum time_how { +	DONT_CHANGE = 0, +	SET_TO_SERVER_TIME = 1, +	SET_TO_CLIENT_TIME = 2, +}; +typedef enum time_how time_how; + +struct set_mode3 { +	bool_t set_it; +	union { +		mode3 mode; +	} set_mode3_u; +}; +typedef struct set_mode3 set_mode3; + +struct set_uid3 { +	bool_t set_it; +	union { +		uid3 uid; +	} set_uid3_u; +}; +typedef struct set_uid3 set_uid3; + +struct set_gid3 { +	bool_t set_it; +	union { +		gid3 gid; +	} set_gid3_u; +}; +typedef struct set_gid3 set_gid3; + +struct set_size3 { +	bool_t set_it; +	union { +		size3 size; +	} set_size3_u; +}; +typedef struct set_size3 set_size3; + +struct set_atime { +	time_how set_it; +	union { +		nfstime3 atime; +	} set_atime_u; +}; +typedef struct set_atime set_atime; + +struct set_mtime { +	time_how set_it; +	union { +		nfstime3 mtime; +	} set_mtime_u; +}; +typedef struct set_mtime set_mtime; + +struct sattr3 { +	set_mode3 mode; +	set_uid3 uid; +	set_gid3 gid; +	set_size3 size; +	set_atime atime; +	set_mtime mtime; +}; +typedef struct sattr3 sattr3; + +struct diropargs3 { +	nfs_fh3 dir; +	filename3 name; +}; +typedef struct diropargs3 diropargs3; + +struct getattr3args { +	nfs_fh3 object; +}; +typedef struct getattr3args getattr3args; + +struct getattr3resok { +	fattr3 obj_attributes; +}; +typedef struct getattr3resok getattr3resok; + +struct getattr3res { +	nfsstat3 status; +	union { +		getattr3resok resok; +	} getattr3res_u; +}; +typedef struct getattr3res getattr3res; + +struct sattrguard3 { +	bool_t check; +	union { +		nfstime3 obj_ctime; +	} sattrguard3_u; +}; +typedef struct sattrguard3 sattrguard3; + +struct setattr3args { +	nfs_fh3 object; +	sattr3 new_attributes; +	sattrguard3 guard; +}; +typedef struct setattr3args setattr3args; + +struct setattr3resok { +	wcc_data obj_wcc; +}; +typedef struct setattr3resok setattr3resok; + +struct setattr3resfail { +	wcc_data obj_wcc; +}; +typedef struct setattr3resfail setattr3resfail; + +struct setattr3res { +	nfsstat3 status; +	union { +		setattr3resok resok; +		setattr3resfail resfail; +	} setattr3res_u; +}; +typedef struct setattr3res setattr3res; + +struct lookup3args { +	diropargs3 what; +}; +typedef struct lookup3args lookup3args; + +struct lookup3resok { +	nfs_fh3 object; +	post_op_attr obj_attributes; +	post_op_attr dir_attributes; +}; +typedef struct lookup3resok lookup3resok; + +struct lookup3resfail { +	post_op_attr dir_attributes; +}; +typedef struct lookup3resfail lookup3resfail; + +struct lookup3res { +	nfsstat3 status; +	union { +		lookup3resok resok; +		lookup3resfail resfail; +	} lookup3res_u; +}; +typedef struct lookup3res lookup3res; +#define ACCESS3_READ 0x0001 +#define ACCESS3_LOOKUP 0x0002 +#define ACCESS3_MODIFY 0x0004 +#define ACCESS3_EXTEND 0x0008 +#define ACCESS3_DELETE 0x0010 +#define ACCESS3_EXECUTE 0x0020 + +struct access3args { +	nfs_fh3 object; +	uint32 access; +}; +typedef struct access3args access3args; + +struct access3resok { +	post_op_attr obj_attributes; +	uint32 access; +}; +typedef struct access3resok access3resok; + +struct access3resfail { +	post_op_attr obj_attributes; +}; +typedef struct access3resfail access3resfail; + +struct access3res { +	nfsstat3 status; +	union { +		access3resok resok; +		access3resfail resfail; +	} access3res_u; +}; +typedef struct access3res access3res; + +struct readlink3args { +	nfs_fh3 symlink; +}; +typedef struct readlink3args readlink3args; + +struct readlink3resok { +	post_op_attr symlink_attributes; +	nfspath3 data; +}; +typedef struct readlink3resok readlink3resok; + +struct readlink3resfail { +	post_op_attr symlink_attributes; +}; +typedef struct readlink3resfail readlink3resfail; + +struct readlink3res { +	nfsstat3 status; +	union { +		readlink3resok resok; +		readlink3resfail resfail; +	} readlink3res_u; +}; +typedef struct readlink3res readlink3res; + +struct read3args { +	nfs_fh3 file; +	offset3 offset; +	count3 count; +}; +typedef struct read3args read3args; + +struct read3resok { +	post_op_attr file_attributes; +	count3 count; +	bool_t eof; +	struct { +		u_int data_len; +		char *data_val; +	} data; +}; +typedef struct read3resok read3resok; + +struct read3resfail { +	post_op_attr file_attributes; +}; +typedef struct read3resfail read3resfail; + +struct read3res { +	nfsstat3 status; +	union { +		read3resok resok; +		read3resfail resfail; +	} read3res_u; +}; +typedef struct read3res read3res; + +enum stable_how { +	UNSTABLE = 0, +	DATA_SYNC = 1, +	FILE_SYNC = 2, +}; +typedef enum stable_how stable_how; + +struct write3args { +	nfs_fh3 file; +	offset3 offset; +	count3 count; +	stable_how stable; +	struct { +		u_int data_len; +		char *data_val; +	} data; +}; +typedef struct write3args write3args; + +/* Generally, the protocol allows the file handle to be less than 64 bytes but + * our server does not return file handles less than 64b so we can safely say + * sizeof (nfs_fh3) rather than first trying to extract the fh size of the + * network followed by a sized-read of the file handle. + */ +#define NFS3_WRITE3ARGS_SIZE    (sizeof (uint32_t) + NFS3_FHSIZE + sizeof (offset3) + sizeof (count3) + sizeof (uint32_t)) +struct write3resok { +	wcc_data file_wcc; +	count3 count; +	stable_how committed; +	writeverf3 verf; +}; +typedef struct write3resok write3resok; + +struct write3resfail { +	wcc_data file_wcc; +}; +typedef struct write3resfail write3resfail; + +struct write3res { +	nfsstat3 status; +	union { +		write3resok resok; +		write3resfail resfail; +	} write3res_u; +}; +typedef struct write3res write3res; + +enum createmode3 { +	UNCHECKED = 0, +	GUARDED = 1, +	EXCLUSIVE = 2, +}; +typedef enum createmode3 createmode3; + +struct createhow3 { +	createmode3 mode; +	union { +		sattr3 obj_attributes; +		createverf3 verf; +	} createhow3_u; +}; +typedef struct createhow3 createhow3; + +struct create3args { +	diropargs3 where; +	createhow3 how; +}; +typedef struct create3args create3args; + +struct create3resok { +	post_op_fh3 obj; +	post_op_attr obj_attributes; +	wcc_data dir_wcc; +}; +typedef struct create3resok create3resok; + +struct create3resfail { +	wcc_data dir_wcc; +}; +typedef struct create3resfail create3resfail; + +struct create3res { +	nfsstat3 status; +	union { +		create3resok resok; +		create3resfail resfail; +	} create3res_u; +}; +typedef struct create3res create3res; + +struct mkdir3args { +	diropargs3 where; +	sattr3 attributes; +}; +typedef struct mkdir3args mkdir3args; + +struct mkdir3resok { +	post_op_fh3 obj; +	post_op_attr obj_attributes; +	wcc_data dir_wcc; +}; +typedef struct mkdir3resok mkdir3resok; + +struct mkdir3resfail { +	wcc_data dir_wcc; +}; +typedef struct mkdir3resfail mkdir3resfail; + +struct mkdir3res { +	nfsstat3 status; +	union { +		mkdir3resok resok; +		mkdir3resfail resfail; +	} mkdir3res_u; +}; +typedef struct mkdir3res mkdir3res; + +struct symlinkdata3 { +	sattr3 symlink_attributes; +	nfspath3 symlink_data; +}; +typedef struct symlinkdata3 symlinkdata3; + +struct symlink3args { +	diropargs3 where; +	symlinkdata3 symlink; +}; +typedef struct symlink3args symlink3args; + +struct symlink3resok { +	post_op_fh3 obj; +	post_op_attr obj_attributes; +	wcc_data dir_wcc; +}; +typedef struct symlink3resok symlink3resok; + +struct symlink3resfail { +	wcc_data dir_wcc; +}; +typedef struct symlink3resfail symlink3resfail; + +struct symlink3res { +	nfsstat3 status; +	union { +		symlink3resok resok; +		symlink3resfail resfail; +	} symlink3res_u; +}; +typedef struct symlink3res symlink3res; + +struct devicedata3 { +	sattr3 dev_attributes; +	specdata3 spec; +}; +typedef struct devicedata3 devicedata3; + +struct mknoddata3 { +	ftype3 type; +	union { +		devicedata3 device; +		sattr3 pipe_attributes; +	} mknoddata3_u; +}; +typedef struct mknoddata3 mknoddata3; + +struct mknod3args { +	diropargs3 where; +	mknoddata3 what; +}; +typedef struct mknod3args mknod3args; + +struct mknod3resok { +	post_op_fh3 obj; +	post_op_attr obj_attributes; +	wcc_data dir_wcc; +}; +typedef struct mknod3resok mknod3resok; + +struct mknod3resfail { +	wcc_data dir_wcc; +}; +typedef struct mknod3resfail mknod3resfail; + +struct mknod3res { +	nfsstat3 status; +	union { +		mknod3resok resok; +		mknod3resfail resfail; +	} mknod3res_u; +}; +typedef struct mknod3res mknod3res; + +struct remove3args { +	diropargs3 object; +}; +typedef struct remove3args remove3args; + +struct remove3resok { +	wcc_data dir_wcc; +}; +typedef struct remove3resok remove3resok; + +struct remove3resfail { +	wcc_data dir_wcc; +}; +typedef struct remove3resfail remove3resfail; + +struct remove3res { +	nfsstat3 status; +	union { +		remove3resok resok; +		remove3resfail resfail; +	} remove3res_u; +}; +typedef struct remove3res remove3res; + +struct rmdir3args { +	diropargs3 object; +}; +typedef struct rmdir3args rmdir3args; + +struct rmdir3resok { +	wcc_data dir_wcc; +}; +typedef struct rmdir3resok rmdir3resok; + +struct rmdir3resfail { +	wcc_data dir_wcc; +}; +typedef struct rmdir3resfail rmdir3resfail; + +struct rmdir3res { +	nfsstat3 status; +	union { +		rmdir3resok resok; +		rmdir3resfail resfail; +	} rmdir3res_u; +}; +typedef struct rmdir3res rmdir3res; + +struct rename3args { +	diropargs3 from; +	diropargs3 to; +}; +typedef struct rename3args rename3args; + +struct rename3resok { +	wcc_data fromdir_wcc; +	wcc_data todir_wcc; +}; +typedef struct rename3resok rename3resok; + +struct rename3resfail { +	wcc_data fromdir_wcc; +	wcc_data todir_wcc; +}; +typedef struct rename3resfail rename3resfail; + +struct rename3res { +	nfsstat3 status; +	union { +		rename3resok resok; +		rename3resfail resfail; +	} rename3res_u; +}; +typedef struct rename3res rename3res; + +struct link3args { +	nfs_fh3 file; +	diropargs3 link; +}; +typedef struct link3args link3args; + +struct link3resok { +	post_op_attr file_attributes; +	wcc_data linkdir_wcc; +}; +typedef struct link3resok link3resok; + +struct link3resfail { +	post_op_attr file_attributes; +	wcc_data linkdir_wcc; +}; +typedef struct link3resfail link3resfail; + +struct link3res { +	nfsstat3 status; +	union { +		link3resok resok; +		link3resfail resfail; +	} link3res_u; +}; +typedef struct link3res link3res; + +struct readdir3args { +	nfs_fh3 dir; +	cookie3 cookie; +	cookieverf3 cookieverf; +	count3 count; +}; +typedef struct readdir3args readdir3args; + +struct entry3 { +	fileid3 fileid; +	filename3 name; +	cookie3 cookie; +	struct entry3 *nextentry; +}; +typedef struct entry3 entry3; + +struct dirlist3 { +	entry3 *entries; +	bool_t eof; +}; +typedef struct dirlist3 dirlist3; + +struct readdir3resok { +	post_op_attr dir_attributes; +	cookieverf3 cookieverf; +	dirlist3 reply; +}; +typedef struct readdir3resok readdir3resok; + +struct readdir3resfail { +	post_op_attr dir_attributes; +}; +typedef struct readdir3resfail readdir3resfail; + +struct readdir3res { +	nfsstat3 status; +	union { +		readdir3resok resok; +		readdir3resfail resfail; +	} readdir3res_u; +}; +typedef struct readdir3res readdir3res; + +struct readdirp3args { +	nfs_fh3 dir; +	cookie3 cookie; +	cookieverf3 cookieverf; +	count3 dircount; +	count3 maxcount; +}; +typedef struct readdirp3args readdirp3args; + +struct entryp3 { +	fileid3 fileid; +	filename3 name; +	cookie3 cookie; +	post_op_attr name_attributes; +	post_op_fh3 name_handle; +	struct entryp3 *nextentry; +}; +typedef struct entryp3 entryp3; + +struct dirlistp3 { +	entryp3 *entries; +	bool_t eof; +}; +typedef struct dirlistp3 dirlistp3; + +struct readdirp3resok { +	post_op_attr dir_attributes; +	cookieverf3 cookieverf; +	dirlistp3   reply; +}; +typedef struct readdirp3resok readdirp3resok; + +struct readdirp3resfail { +	post_op_attr dir_attributes; +}; +typedef struct readdirp3resfail readdirp3resfail; + +struct readdirp3res { +	nfsstat3 status; +	union { +		readdirp3resok resok; +		readdirp3resfail resfail; +	} readdirp3res_u; +}; +typedef struct readdirp3res readdirp3res; + +struct fsstat3args { +	nfs_fh3 fsroot; +}; +typedef struct fsstat3args fsstat3args; + +struct fsstat3resok { +	post_op_attr obj_attributes; +	size3 tbytes; +	size3 fbytes; +	size3 abytes; +	size3 tfiles; +	size3 ffiles; +	size3 afiles; +	uint32 invarsec; +}; +typedef struct fsstat3resok fsstat3resok; + +struct fsstat3resfail { +	post_op_attr obj_attributes; +}; +typedef struct fsstat3resfail fsstat3resfail; + +struct fsstat3res { +	nfsstat3 status; +	union { +		fsstat3resok resok; +		fsstat3resfail resfail; +	} fsstat3res_u; +}; +typedef struct fsstat3res fsstat3res; +#define FSF3_LINK 0x0001 +#define FSF3_SYMLINK 0x0002 +#define FSF3_HOMOGENEOUS 0x0008 +#define FSF3_CANSETTIME 0x0010 + +struct fsinfo3args { +	nfs_fh3 fsroot; +}; +typedef struct fsinfo3args fsinfo3args; + +struct fsinfo3resok { +	post_op_attr obj_attributes; +	uint32 rtmax; +	uint32 rtpref; +	uint32 rtmult; +	uint32 wtmax; +	uint32 wtpref; +	uint32 wtmult; +	uint32 dtpref; +	size3 maxfilesize; +	nfstime3 time_delta; +	uint32 properties; +}; +typedef struct fsinfo3resok fsinfo3resok; + +struct fsinfo3resfail { +	post_op_attr obj_attributes; +}; +typedef struct fsinfo3resfail fsinfo3resfail; + +struct fsinfo3res { +	nfsstat3 status; +	union { +		fsinfo3resok resok; +		fsinfo3resfail resfail; +	} fsinfo3res_u; +}; +typedef struct fsinfo3res fsinfo3res; + +struct pathconf3args { +	nfs_fh3 object; +}; +typedef struct pathconf3args pathconf3args; + +struct pathconf3resok { +	post_op_attr obj_attributes; +	uint32 linkmax; +	uint32 name_max; +	bool_t no_trunc; +	bool_t chown_restricted; +	bool_t case_insensitive; +	bool_t case_preserving; +}; +typedef struct pathconf3resok pathconf3resok; + +struct pathconf3resfail { +	post_op_attr obj_attributes; +}; +typedef struct pathconf3resfail pathconf3resfail; + +struct pathconf3res { +	nfsstat3 status; +	union { +		pathconf3resok resok; +		pathconf3resfail resfail; +	} pathconf3res_u; +}; +typedef struct pathconf3res pathconf3res; + +struct commit3args { +	nfs_fh3 file; +	offset3 offset; +	count3 count; +}; +typedef struct commit3args commit3args; + +struct commit3resok { +	wcc_data file_wcc; +	writeverf3 verf; +}; +typedef struct commit3resok commit3resok; + +struct commit3resfail { +	wcc_data file_wcc; +}; +typedef struct commit3resfail commit3resfail; + +struct commit3res { +	nfsstat3 status; +	union { +		commit3resok resok; +		commit3resfail resfail; +	} commit3res_u; +}; +typedef struct commit3res commit3res; +#define MNTPATHLEN 1024 +#define MNTNAMLEN 255 +#define FHSIZE3 NFS3_FHSIZE + +typedef struct { +	u_int fhandle3_len; +	char *fhandle3_val; +} fhandle3; + +typedef char *dirpath; + +typedef char *name; + +enum mountstat3 { +	MNT3_OK = 0, +	MNT3ERR_PERM = 1, +	MNT3ERR_NOENT = 2, +	MNT3ERR_IO = 5, +	MNT3ERR_ACCES = 13, +	MNT3ERR_NOTDIR = 20, +	MNT3ERR_INVAL = 22, +	MNT3ERR_NAMETOOLONG = 63, +	MNT3ERR_NOTSUPP = 10004, +	MNT3ERR_SERVERFAULT = 10006, +}; +typedef enum mountstat3 mountstat3; + +struct mountres3_ok { +	fhandle3 fhandle; +	struct { +		u_int auth_flavors_len; +		int *auth_flavors_val; +	} auth_flavors; +}; +typedef struct mountres3_ok mountres3_ok; + +struct mountres3 { +	mountstat3 fhs_status; +	union { +		mountres3_ok mountinfo; +	} mountres3_u; +}; +typedef struct mountres3 mountres3; + +typedef struct mountbody *mountlist; + +struct mountbody { +	name ml_hostname; +	dirpath ml_directory; +	mountlist ml_next; +}; +typedef struct mountbody mountbody; + +typedef struct groupnode *groups; + +struct groupnode { +	name gr_name; +	groups gr_next; +}; +typedef struct groupnode groupnode; + +typedef struct exportnode *exports; + +struct exportnode { +	dirpath ex_dir; +	groups ex_groups; +	exports ex_next; +}; +typedef struct exportnode exportnode; + +#define NFS_PROGRAM             100003 +#define NFS_V3                  3 + +#define NFS3_NULL               0 +#define NFS3_GETATTR            1 +#define NFS3_SETATTR            2 +#define NFS3_LOOKUP             3 +#define NFS3_ACCESS             4 +#define NFS3_READLINK           5 +#define NFS3_READ               6 +#define NFS3_WRITE              7 +#define NFS3_CREATE             8 +#define NFS3_MKDIR              9 +#define NFS3_SYMLINK            10 +#define NFS3_MKNOD              11 +#define NFS3_REMOVE             12 +#define NFS3_RMDIR              13 +#define NFS3_RENAME             14 +#define NFS3_LINK               15 +#define NFS3_READDIR            16 +#define NFS3_READDIRP           17 +#define NFS3_FSSTAT             18 +#define NFS3_FSINFO             19 +#define NFS3_PATHCONF           20 +#define NFS3_COMMIT             21 +#define NFS3_PROC_COUNT         22 + +#define MOUNT_PROGRAM           100005 +#define MOUNT_V3                3 +#define MOUNT_V1                1 + +#define MOUNT3_NULL             0 +#define MOUNT3_MNT              1 +#define MOUNT3_DUMP             2 +#define MOUNT3_UMNT             3 +#define MOUNT3_UMNTALL          4 +#define MOUNT3_EXPORT           5 +#define MOUNT3_PROC_COUNT       6 + +#define MOUNT1_NULL             0 +#define MOUNT1_DUMP             2 +#define MOUNT1_UMNT             3 +#define MOUNT1_EXPORT           5 +#define MOUNT1_PROC_COUNT       6 +/* the xdr functions */ + +extern  bool_t xdr_uint64 (XDR *, uint64*); +extern  bool_t xdr_int64 (XDR *, int64*); +extern  bool_t xdr_uint32 (XDR *, uint32*); +extern  bool_t xdr_int32 (XDR *, int32*); +extern  bool_t xdr_filename3 (XDR *, filename3*); +extern  bool_t xdr_nfspath3 (XDR *, nfspath3*); +extern  bool_t xdr_fileid3 (XDR *, fileid3*); +extern  bool_t xdr_cookie3 (XDR *, cookie3*); +extern  bool_t xdr_cookieverf3 (XDR *, cookieverf3); +extern  bool_t xdr_createverf3 (XDR *, createverf3); +extern  bool_t xdr_writeverf3 (XDR *, writeverf3); +extern  bool_t xdr_uid3 (XDR *, uid3*); +extern  bool_t xdr_gid3 (XDR *, gid3*); +extern  bool_t xdr_size3 (XDR *, size3*); +extern  bool_t xdr_offset3 (XDR *, offset3*); +extern  bool_t xdr_mode3 (XDR *, mode3*); +extern  bool_t xdr_count3 (XDR *, count3*); +extern  bool_t xdr_nfsstat3 (XDR *, nfsstat3*); +extern  bool_t xdr_ftype3 (XDR *, ftype3*); +extern  bool_t xdr_specdata3 (XDR *, specdata3*); +extern  bool_t xdr_nfs_fh3 (XDR *, nfs_fh3*); +extern  bool_t xdr_nfstime3 (XDR *, nfstime3*); +extern  bool_t xdr_fattr3 (XDR *, fattr3*); +extern  bool_t xdr_post_op_attr (XDR *, post_op_attr*); +extern  bool_t xdr_wcc_attr (XDR *, wcc_attr*); +extern  bool_t xdr_pre_op_attr (XDR *, pre_op_attr*); +extern  bool_t xdr_wcc_data (XDR *, wcc_data*); +extern  bool_t xdr_post_op_fh3 (XDR *, post_op_fh3*); +extern  bool_t xdr_time_how (XDR *, time_how*); +extern  bool_t xdr_set_mode3 (XDR *, set_mode3*); +extern  bool_t xdr_set_uid3 (XDR *, set_uid3*); +extern  bool_t xdr_set_gid3 (XDR *, set_gid3*); +extern  bool_t xdr_set_size3 (XDR *, set_size3*); +extern  bool_t xdr_set_atime (XDR *, set_atime*); +extern  bool_t xdr_set_mtime (XDR *, set_mtime*); +extern  bool_t xdr_sattr3 (XDR *, sattr3*); +extern  bool_t xdr_diropargs3 (XDR *, diropargs3*); +extern  bool_t xdr_getattr3args (XDR *, getattr3args*); +extern  bool_t xdr_getattr3resok (XDR *, getattr3resok*); +extern  bool_t xdr_getattr3res (XDR *, getattr3res*); +extern  bool_t xdr_sattrguard3 (XDR *, sattrguard3*); +extern  bool_t xdr_setattr3args (XDR *, setattr3args*); +extern  bool_t xdr_setattr3resok (XDR *, setattr3resok*); +extern  bool_t xdr_setattr3resfail (XDR *, setattr3resfail*); +extern  bool_t xdr_setattr3res (XDR *, setattr3res*); +extern  bool_t xdr_lookup3args (XDR *, lookup3args*); +extern  bool_t xdr_lookup3resok (XDR *, lookup3resok*); +extern  bool_t xdr_lookup3resfail (XDR *, lookup3resfail*); +extern  bool_t xdr_lookup3res (XDR *, lookup3res*); +extern  bool_t xdr_access3args (XDR *, access3args*); +extern  bool_t xdr_access3resok (XDR *, access3resok*); +extern  bool_t xdr_access3resfail (XDR *, access3resfail*); +extern  bool_t xdr_access3res (XDR *, access3res*); +extern  bool_t xdr_readlink3args (XDR *, readlink3args*); +extern  bool_t xdr_readlink3resok (XDR *, readlink3resok*); +extern  bool_t xdr_readlink3resfail (XDR *, readlink3resfail*); +extern  bool_t xdr_readlink3res (XDR *, readlink3res*); +extern  bool_t xdr_read3args (XDR *, read3args*); +extern  bool_t xdr_read3resok (XDR *, read3resok*); +extern  bool_t xdr_read3resfail (XDR *, read3resfail*); +extern  bool_t xdr_read3res (XDR *, read3res*); +extern  bool_t xdr_read3res_nocopy (XDR *xdrs, read3res *objp); +extern  bool_t xdr_stable_how (XDR *, stable_how*); +extern  bool_t xdr_write3args (XDR *, write3args*); +extern  bool_t xdr_write3resok (XDR *, write3resok*); +extern  bool_t xdr_write3resfail (XDR *, write3resfail*); +extern  bool_t xdr_write3res (XDR *, write3res*); +extern  bool_t xdr_createmode3 (XDR *, createmode3*); +extern  bool_t xdr_createhow3 (XDR *, createhow3*); +extern  bool_t xdr_create3args (XDR *, create3args*); +extern  bool_t xdr_create3resok (XDR *, create3resok*); +extern  bool_t xdr_create3resfail (XDR *, create3resfail*); +extern  bool_t xdr_create3res (XDR *, create3res*); +extern  bool_t xdr_mkdir3args (XDR *, mkdir3args*); +extern  bool_t xdr_mkdir3resok (XDR *, mkdir3resok*); +extern  bool_t xdr_mkdir3resfail (XDR *, mkdir3resfail*); +extern  bool_t xdr_mkdir3res (XDR *, mkdir3res*); +extern  bool_t xdr_symlinkdata3 (XDR *, symlinkdata3*); +extern  bool_t xdr_symlink3args (XDR *, symlink3args*); +extern  bool_t xdr_symlink3resok (XDR *, symlink3resok*); +extern  bool_t xdr_symlink3resfail (XDR *, symlink3resfail*); +extern  bool_t xdr_symlink3res (XDR *, symlink3res*); +extern  bool_t xdr_devicedata3 (XDR *, devicedata3*); +extern  bool_t xdr_mknoddata3 (XDR *, mknoddata3*); +extern  bool_t xdr_mknod3args (XDR *, mknod3args*); +extern  bool_t xdr_mknod3resok (XDR *, mknod3resok*); +extern  bool_t xdr_mknod3resfail (XDR *, mknod3resfail*); +extern  bool_t xdr_mknod3res (XDR *, mknod3res*); +extern  bool_t xdr_remove3args (XDR *, remove3args*); +extern  bool_t xdr_remove3resok (XDR *, remove3resok*); +extern  bool_t xdr_remove3resfail (XDR *, remove3resfail*); +extern  bool_t xdr_remove3res (XDR *, remove3res*); +extern  bool_t xdr_rmdir3args (XDR *, rmdir3args*); +extern  bool_t xdr_rmdir3resok (XDR *, rmdir3resok*); +extern  bool_t xdr_rmdir3resfail (XDR *, rmdir3resfail*); +extern  bool_t xdr_rmdir3res (XDR *, rmdir3res*); +extern  bool_t xdr_rename3args (XDR *, rename3args*); +extern  bool_t xdr_rename3resok (XDR *, rename3resok*); +extern  bool_t xdr_rename3resfail (XDR *, rename3resfail*); +extern  bool_t xdr_rename3res (XDR *, rename3res*); +extern  bool_t xdr_link3args (XDR *, link3args*); +extern  bool_t xdr_link3resok (XDR *, link3resok*); +extern  bool_t xdr_link3resfail (XDR *, link3resfail*); +extern  bool_t xdr_link3res (XDR *, link3res*); +extern  bool_t xdr_readdir3args (XDR *, readdir3args*); +extern  bool_t xdr_entry3 (XDR *, entry3*); +extern  bool_t xdr_dirlist3 (XDR *, dirlist3*); +extern  bool_t xdr_readdir3resok (XDR *, readdir3resok*); +extern  bool_t xdr_readdir3resfail (XDR *, readdir3resfail*); +extern  bool_t xdr_readdir3res (XDR *, readdir3res*); +extern  bool_t xdr_readdirp3args (XDR *, readdirp3args*); +extern  bool_t xdr_entryp3 (XDR *, entryp3*); +extern  bool_t xdr_dirlistp3 (XDR *, dirlistp3*); +extern  bool_t xdr_readdirp3resok (XDR *, readdirp3resok*); +extern  bool_t xdr_readdirp3resfail (XDR *, readdirp3resfail*); +extern  bool_t xdr_readdirp3res (XDR *, readdirp3res*); +extern  bool_t xdr_fsstat3args (XDR *, fsstat3args*); +extern  bool_t xdr_fsstat3resok (XDR *, fsstat3resok*); +extern  bool_t xdr_fsstat3resfail (XDR *, fsstat3resfail*); +extern  bool_t xdr_fsstat3res (XDR *, fsstat3res*); +extern  bool_t xdr_fsinfo3args (XDR *, fsinfo3args*); +extern  bool_t xdr_fsinfo3resok (XDR *, fsinfo3resok*); +extern  bool_t xdr_fsinfo3resfail (XDR *, fsinfo3resfail*); +extern  bool_t xdr_fsinfo3res (XDR *, fsinfo3res*); +extern  bool_t xdr_pathconf3args (XDR *, pathconf3args*); +extern  bool_t xdr_pathconf3resok (XDR *, pathconf3resok*); +extern  bool_t xdr_pathconf3resfail (XDR *, pathconf3resfail*); +extern  bool_t xdr_pathconf3res (XDR *, pathconf3res*); +extern  bool_t xdr_commit3args (XDR *, commit3args*); +extern  bool_t xdr_commit3resok (XDR *, commit3resok*); +extern  bool_t xdr_commit3resfail (XDR *, commit3resfail*); +extern  bool_t xdr_commit3res (XDR *, commit3res*); +extern  bool_t xdr_fhandle3 (XDR *, fhandle3*); +extern  bool_t xdr_dirpath (XDR *, dirpath*); +extern  bool_t xdr_name (XDR *, name*); +extern  bool_t xdr_mountstat3 (XDR *, mountstat3*); +extern  bool_t xdr_mountres3_ok (XDR *, mountres3_ok*); +extern  bool_t xdr_mountres3 (XDR *, mountres3*); +extern  bool_t xdr_mountlist (XDR *, mountlist*); +extern  bool_t xdr_mountbody (XDR *, mountbody*); +extern  bool_t xdr_groups (XDR *, groups*); +extern  bool_t xdr_groupnode (XDR *, groupnode*); +extern  bool_t xdr_exports (XDR *, exports*); +extern  bool_t xdr_exportnode (XDR *, exportnode*); + +extern void xdr_free_exports_list (struct exportnode *first); +extern void xdr_free_mountlist (mountlist ml); + +extern void xdr_free_write3args_nocopy (write3args *wa); +#endif diff --git a/xlators/nfs/lib/src/xdr-rpc.c b/xlators/nfs/lib/src/xdr-rpc.c new file mode 100644 index 000000000..ac0f8afd3 --- /dev/null +++ b/xlators/nfs/lib/src/xdr-rpc.c @@ -0,0 +1,190 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include <rpc/rpc.h> +#include <rpc/pmap_clnt.h> +#include <arpa/inet.h> +#include <rpc/xdr.h> +#include <sys/uio.h> +#include <rpc/auth_unix.h> + +#include "mem-pool.h" +#include "xdr-rpc.h" +#include "xdr-common.h" +#include "logging.h" + +/* Decodes the XDR format in msgbuf into rpc_msg. + * The remaining payload is returned into payload. + */ +int +xdr_to_rpc_call (char *msgbuf, size_t len, struct rpc_msg *call, +                 struct iovec *payload, char *credbytes, char *verfbytes) +{ +        XDR                     xdr; +        char                    opaquebytes[MAX_AUTH_BYTES]; +        struct opaque_auth      *oa = NULL; + +        if ((!msgbuf) || (!call)) +                return -1; + +        memset (call, 0, sizeof (*call)); + +        oa = &call->rm_call.cb_cred; +        if (!credbytes) +                oa->oa_base = opaquebytes; +        else +                oa->oa_base = credbytes; + +        oa = &call->rm_call.cb_verf; +        if (!verfbytes) +                oa->oa_base = opaquebytes; +        else +                oa->oa_base = verfbytes; + +        xdrmem_create (&xdr, msgbuf, len, XDR_DECODE); +        if (!xdr_callmsg (&xdr, call)) +                return -1; + +        if (payload) { +                payload->iov_base = xdr_decoded_remaining_addr (xdr); +                payload->iov_len = xdr_decoded_remaining_len (xdr); +        } + +        return 0; +} + + +bool_t +true_func (XDR *s, caddr_t *a) +{ +        return TRUE; +} + + +int +rpc_fill_empty_reply (struct rpc_msg *reply, uint32_t xid) +{ +        if (!reply) +                return -1; + +        /* Setting to 0 also results in reply verifier flavor to be +         * set to AUTH_NULL which is what we want right now. +         */ +        memset (reply, 0, sizeof (*reply)); +        reply->rm_xid = xid; +        reply->rm_direction = REPLY; + +        return 0; +} + +int +rpc_fill_denied_reply (struct rpc_msg *reply, int rjstat, int auth_err) +{ +        if (!reply) +                return -1; + +        reply->rm_reply.rp_stat = MSG_DENIED; +        reply->rjcted_rply.rj_stat = rjstat; +        if (rjstat == RPC_MISMATCH) { +                /* No problem with hardocoding +                 * RPC version numbers. We only support +                 * v2 anyway. +                 */ +                reply->rjcted_rply.rj_vers.low = 2; +                reply->rjcted_rply.rj_vers.high = 2; +        } else if (rjstat == AUTH_ERROR) +                reply->rjcted_rply.rj_why = auth_err; + +        return 0; +} + + +int +rpc_fill_accepted_reply (struct rpc_msg *reply, int arstat, int proglow, +                         int proghigh, int verf, int len, char *vdata) +{ +        if (!reply) +                return -1; + +        reply->rm_reply.rp_stat = MSG_ACCEPTED; +        reply->acpted_rply.ar_stat = arstat; + +        reply->acpted_rply.ar_verf.oa_flavor = verf; +        reply->acpted_rply.ar_verf.oa_length = len; +        reply->acpted_rply.ar_verf.oa_base = vdata; +        if (arstat == PROG_MISMATCH) { +                reply->acpted_rply.ar_vers.low = proglow; +                reply->acpted_rply.ar_vers.high = proghigh; +        } else if (arstat == SUCCESS) { + +                /* This is a hack. I'd really like to build a custom +                 * XDR library because Sun RPC interface is not very flexible. +                 */ +                reply->acpted_rply.ar_results.proc = (xdrproc_t)true_func; +                reply->acpted_rply.ar_results.where = NULL; +        } + +        return 0; +} + +int +rpc_reply_to_xdr (struct rpc_msg *reply, char *dest, size_t len, +                  struct iovec *dst) +{ +        XDR             xdr; + +        if ((!dest) || (!reply) || (!dst)) +                return -1; + +        xdrmem_create (&xdr, dest, len, XDR_ENCODE); +        if (!xdr_replymsg(&xdr, reply)) +                return -1; + +        dst->iov_base = dest; +        dst->iov_len = xdr_encoded_length (xdr); + +        return 0; +} + + +int +xdr_to_auth_unix_cred (char *msgbuf, int msglen, struct authunix_parms *au, +                       char *machname, gid_t *gids) +{ +        XDR             xdr; + +        if ((!msgbuf) || (!machname) || (!gids) || (!au)) +                return -1; + +        au->aup_machname = machname; +        au->aup_gids = gids; + +        xdrmem_create (&xdr, msgbuf, msglen, XDR_DECODE); + +        if (!xdr_authunix_parms (&xdr, au)) +                return -1; + +        return 0; +} + diff --git a/xlators/nfs/lib/src/xdr-rpc.h b/xlators/nfs/lib/src/xdr-rpc.h new file mode 100644 index 000000000..4c0ee69b1 --- /dev/null +++ b/xlators/nfs/lib/src/xdr-rpc.h @@ -0,0 +1,74 @@ +/* +  Copyright (c) 2010 Gluster, Inc. <http://www.gluster.com> +  This file is part of GlusterFS. + +  GlusterFS 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 3 of the License, +  or (at your option) any later version. + +  GlusterFS 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, see +  <http://www.gnu.org/licenses/>. +*/ + +#ifndef _XDR_RPC_H +#define _XDR_RPC_H_ + +#ifndef _CONFIG_H +#define _CONFIG_H +#include "config.h" +#endif + +#include <rpc/rpc.h> +#include <rpc/pmap_clnt.h> +#include <arpa/inet.h> +#include <rpc/xdr.h> +#include <sys/uio.h> + +/* Converts a given network buffer from its XDR format to a structure + * that contains everything an RPC call needs to work. + */ +extern int +xdr_to_rpc_call (char *msgbuf, size_t len, struct rpc_msg *call, +                 struct iovec *payload, char *credbytes, char *verfbytes); + +extern int +rpc_fill_empty_reply (struct rpc_msg *reply, uint32_t xid); + +extern int +rpc_fill_denied_reply (struct rpc_msg *reply, int rjstat, int auth_err); + +extern int +rpc_fill_accepted_reply (struct rpc_msg *reply, int arstat, int proglow, +                         int proghigh, int verf, int len, char *vdata); +extern int +rpc_reply_to_xdr (struct rpc_msg *reply, char *dest, size_t len, +                  struct iovec *dst); + +extern int +xdr_to_auth_unix_cred (char *msgbuf, int msglen, struct authunix_parms *au, +                       char *machname, gid_t *gids); +/* Macros that simplify accesing the members of an RPC call structure. */ +#define rpc_call_xid(call)              ((call)->rm_xid) +#define rpc_call_direction(call)        ((call)->rm_direction) +#define rpc_call_rpcvers(call)          ((call)->ru.RM_cmb.cb_rpcvers) +#define rpc_call_program(call)          ((call)->ru.RM_cmb.cb_prog) +#define rpc_call_progver(call)          ((call)->ru.RM_cmb.cb_vers) +#define rpc_call_progproc(call)         ((call)->ru.RM_cmb.cb_proc) +#define rpc_opaque_auth_flavour(oa)     ((oa)->oa_flavor) +#define rpc_opaque_auth_len(oa)         ((oa)->oa_length) + +#define rpc_call_cred_flavour(call)     (rpc_opaque_auth_flavour ((&(call)->ru.RM_cmb.cb_cred))) +#define rpc_call_cred_len(call)         (rpc_opaque_auth_len ((&(call)->ru.RM_cmb.cb_cred))) + + +#define rpc_call_verf_flavour(call)     (rpc_opaque_auth_flavour ((&(call)->ru.RM_cmb.cb_verf))) +#define rpc_call_verf_len(call)         (rpc_opaque_auth_len ((&(call)->ru.RM_cmb.cb_verf))) + +#endif  | 
