Change to using variable length file handles, for better v3 support, and
authorneilbrown <neilbrown>
Tue, 21 Mar 2000 00:46:14 +0000 (00:46 +0000)
committerneilbrown <neilbrown>
Tue, 21 Mar 2000 00:46:14 +0000 (00:46 +0000)
introduce getfh_size to use new (2.3.99) syscall for getting file handles
with length

ChangeLog
support/include/nfs/nfs.h
support/include/nfslib.h
support/nfs/getfh.c
tools/Makefile
tools/nlmtest/nlmtest.c
utils/mountd/mountd.c

index 753a073..32a1739 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,9 +1,27 @@
+Tue Mar 21 11:38:48 EST 2000 NeilBrown <neilb@cse.unsw.edu.au>
+
+       * support/include/nfs/nfs.h: Removed knowledge of internals of
+            kernel filehandles (which can change) and defined nfs_fh_size
+            which has variable size
+       
+       * support/nfs/getfh.c: defined getfh_size to use new syscall to
+            get variable sized file handles, and change getfh{,old} to
+            use nfs_fh_size        
+       
+       * utils/mountd/mountd.c: use nfd_fh_size and call getfh_size for
+            NFSv3 file handles
+
+       * tools/Makefile, tools/nlmtest/nlmtest.c
+            nlmtest.c depended on internel format of file handles, so now
+            doesn't work.
+
+       
 2000-03-12  Chip Salzenberg  <chip@valinux.com>
            Neil Brown  <neilb@cse.unsw.edu.au>
 
        * support/nfs/rpcmisc.c (rpc_init): Share transports.
 
-Wed Mar  8 09:42:43 EST 2000 Neil Brown <neilb@cse.unsw.edu.au>
+Mon Mar 13 18:31:33 2000 H.J. Lu <hjl@lucon.org>
 
        * etc/redhat/nfsd.init: Updated.
 
index 0cfed07..937c1be 100644 (file)
@@ -7,36 +7,17 @@
 #include <rpcsvc/nfs_prot.h>
 #include <nfs/export.h>
 
-struct dentry;
+#define        NFS3_FHSIZE     64
+#define        NFS_FHSIZE      32
 
-/*
- * This is the new "dentry style" Linux NFSv2 file handle.
- *
- * The xino and xdev fields are currently used to transport the
- * ino/dev of the exported inode.
- */
-struct nfs_fhbase {
-       struct dentry * fb_dentry;      /* dentry cookie */
-       u_int32_t               fb_ino;         /* our inode number */
-       u_int32_t               fb_dirino;      /* dir inode number */
-       u_int32_t               fb_dev;         /* our device */
-       u_int32_t               fb_xdev;
-       u_int32_t               fb_xino;
+struct nfs_fh_len {
+       int             fh_size;
+       u_int8_t        fh_handle[NFS3_FHSIZE];
 };
-
-#define NFS_FH_PADDING         (NFS_FHSIZE - sizeof(struct nfs_fhbase))
-struct knfs_fh {
-       struct nfs_fhbase       fh_base;
-       u_int8_t                        fh_cookie[NFS_FH_PADDING];
+struct nfs_fh_old {
+       u_int8_t        fh_handle[NFS_FHSIZE];
 };
 
-#define fh_dcookie             fh_base.fb_dentry
-#define fh_ino                 fh_base.fb_ino
-#define fh_dirino              fh_base.fb_dirino
-#define fh_dev                 fh_base.fb_dev
-#define fh_xdev                        fh_base.fb_xdev
-#define fh_xino                        fh_base.fb_xino
-
 /*
  * Version of the syscall interface
  */
@@ -53,6 +34,7 @@ struct knfs_fh {
 #define NFSCTL_UGIDUPDATE      5       /* update a client's uid/gid map. */
 #define NFSCTL_GETFH           6       /* get an fh (used by mountd) */
 #define NFSCTL_GETFD           7       /* get an fh by path (used by mountd) */
+#define NFSCTL_GETFS           8       /* get an fh by path with max size (used by mountd) */
 
 /* Above this is for lockd. */
 #define NFSCTL_LOCKD           0x10000
@@ -113,6 +95,13 @@ struct nfsctl_fdparm {
        int                     gd_version;
 };
 
+/* GETFS - GET Filehandle with Size */
+struct nfsctl_fsparm {
+       struct sockaddr         gd_addr;
+       char                    gd_path[NFS_MAXPATHLEN+1];
+       int                     gd_maxlen;
+};
+
 /*
  * This is the argument union.
  */
@@ -125,7 +114,7 @@ struct nfsctl_arg {
                struct nfsctl_uidmap    u_umap;
                struct nfsctl_fhparm    u_getfh;
                struct nfsctl_fdparm    u_getfd;
-               unsigned int            u_debug;
+               struct nfsctl_fsparm    u_getfs;
        } u;
 #define ca_svc         u.u_svc
 #define ca_client      u.u_client
@@ -133,13 +122,13 @@ struct nfsctl_arg {
 #define ca_umap                u.u_umap
 #define ca_getfh       u.u_getfh
 #define ca_getfd       u.u_getfd
+#define ca_getfs       u.u_getfs
 #define ca_authd       u.u_authd
-#define ca_debug       u.u_debug
 };
 
 union nfsctl_res {
-       struct knfs_fh          cr_getfh;
-       unsigned int            cr_debug;
+       struct nfs_fh_old       cr_getfh;
+       struct nfs_fh_len       cr_getfs;
 };
 
 #endif /* _NFS_NFS_H */
index d8be926..b5c7237 100644 (file)
@@ -116,8 +116,9 @@ int                 nfsaddclient(struct nfsctl_client *clp);
 int                    nfsdelclient(struct nfsctl_client *clp);
 int                    nfsexport(struct nfsctl_export *exp);
 int                    nfsunexport(struct nfsctl_export *exp);
-struct knfs_fh *       getfh_old(struct sockaddr *addr, dev_t dev, ino_t ino);
-struct knfs_fh *       getfh(struct sockaddr *addr, const char *);
+struct nfs_fh_len *    getfh_old(struct sockaddr *addr, dev_t dev, ino_t ino);
+struct nfs_fh_len *    getfh(struct sockaddr *addr, const char *);
+struct nfs_fh_len *    getfh_size(struct sockaddr *addr, const char *, int size);
 
 /* lockd. */
 int                    lockdsvc();
index 5a6f1a4..aacba52 100644 (file)
 #include <errno.h>
 #include "nfslib.h"
 
-struct knfs_fh *
+struct nfs_fh_len *
 getfh_old (struct sockaddr *addr, dev_t dev, ino_t ino)
 {
-       static union nfsctl_res res;
+       union nfsctl_res        res;
        struct nfsctl_arg       arg;
+       static struct nfs_fh_len rfh;
 
        arg.ca_version = NFSCTL_VERSION;
        arg.ca_getfh.gf_version = 2;    /* obsolete */
@@ -32,14 +33,17 @@ getfh_old (struct sockaddr *addr, dev_t dev, ino_t ino)
        if (nfsctl(NFSCTL_GETFH, &arg, &res) < 0)
                return NULL;
 
-       return &res.cr_getfh;
+       rfh.fh_size = 32;
+       memcpy(rfh.fh_handle, &res.cr_getfh, 32);
+       return &rfh;
 }
 
-struct knfs_fh *
+struct nfs_fh_len *
 getfh(struct sockaddr *addr, const char *path)
 {
-        static union nfsctl_res res;
+       static union nfsctl_res res;
         struct nfsctl_arg       arg;
+       static struct nfs_fh_len rfh;
 
         arg.ca_version = NFSCTL_VERSION;
         arg.ca_getfd.gd_version = 2;    /* obsolete */
@@ -51,5 +55,26 @@ getfh(struct sockaddr *addr, const char *path)
         if (nfsctl(NFSCTL_GETFD, &arg, &res) < 0)
                 return NULL;
 
-        return &res.cr_getfh;
+       rfh.fh_size = 32;
+       memcpy(rfh.fh_handle, &res.cr_getfh, 32);
+       return &rfh;
+}
+
+struct nfs_fh_len *
+getfh_size(struct sockaddr *addr, const char *path, int size)
+{
+        static union nfsctl_res res;
+        struct nfsctl_arg       arg;
+
+        arg.ca_version = NFSCTL_VERSION;
+        strncpy(arg.ca_getfs.gd_path, path,
+               sizeof(arg.ca_getfs.gd_path) - 1);
+       arg.ca_getfs.gd_path[sizeof (arg.ca_getfs.gd_path) - 1] = '\0';
+        memcpy(&arg.ca_getfs.gd_addr, addr, sizeof(struct sockaddr_in));
+       arg.ca_getfs.gd_maxlen = size;
+
+        if (nfsctl(NFSCTL_GETFS, &arg, &res) < 0)
+                return NULL;
+
+        return &res.cr_getfs;
 }
index 6378850..0324877 100644 (file)
@@ -2,6 +2,7 @@
 # Various debugging/testing tools
 #
 
-SUBDIRS        = rpcgen getiversion getkversion nlmtest rpcdebug locktest
+SUBDIRS        = rpcgen getiversion getkversion  rpcdebug locktest
+# nlmtest doesn't work 
 
 include $(TOP)rules.mk
index 77dd889..d0acc47 100644 (file)
@@ -234,7 +234,7 @@ makefileh(struct netobj *fh)
 {
        static struct knfs_fh   f;
        struct stat             stb;
-
+#error this needs updating if it is still wanted
        memset(&f, 0, sizeof(f));
 #if 0
        if (stat(NLMTEST_DIR, &stb) < 0) {
index 164983a..7f54be6 100644 (file)
@@ -24,7 +24,7 @@
 
 static void            usage(const char *, int exitcode);
 static exports         get_exportlist(void);
-static struct knfs_fh *        get_rootfh(struct svc_req *, dirpath *, int *);
+static struct nfs_fh_len *get_rootfh(struct svc_req *, dirpath *, int *, int v3);
 
 static struct option longopts[] =
 {
@@ -65,11 +65,11 @@ mount_null_1_svc(struct svc_req *rqstp, void *argp, void *resp)
 bool_t
 mount_mnt_1_svc(struct svc_req *rqstp, dirpath *path, fhstatus *res)
 {
-       struct knfs_fh  *fh;
+       struct nfs_fh_len *fh;
 
        xlog(D_CALL, "MNT1(%s) called", *path);
-       if ((fh = get_rootfh(rqstp, path, &res->fhs_status)) != NULL)
-               memcpy(&res->fhstatus_u.fhs_fhandle, fh, 32);
+       if ((fh = get_rootfh(rqstp, path, &res->fhs_status, 0)) != NULL)
+               memcpy(&res->fhstatus_u.fhs_fhandle, fh->fh_handle, 32);
        return 1;
 }
 
@@ -203,22 +203,22 @@ bool_t
 mount_mnt_3_svc(struct svc_req *rqstp, dirpath *path, mountres3 *res)
 {
        static int      flavors[] = { AUTH_NULL, AUTH_UNIX };
-       struct knfs_fh  *fh;
+       struct nfs_fh_len *fh;
 
        xlog(D_CALL, "MNT3(%s) called", *path);
-       if ((fh = get_rootfh(rqstp, path, (int *) &res->fhs_status)) != NULL) {
+       if ((fh = get_rootfh(rqstp, path, (int *) &res->fhs_status, 1)) != NULL) {
                struct mountres3_ok     *ok = &res->mountres3_u.mountinfo;
 
-               ok->fhandle.fhandle3_len = 32;
-               ok->fhandle.fhandle3_val = (char *) fh;
+               ok->fhandle.fhandle3_len = fh->fh_size;
+               ok->fhandle.fhandle3_val = fh->fh_handle;
                ok->auth_flavors.auth_flavors_len = 2;
                ok->auth_flavors.auth_flavors_val = flavors;
        }
        return 1;
 }
 
-static struct knfs_fh *
-get_rootfh(struct svc_req *rqstp, dirpath *path, int *error)
+static struct nfs_fh_len *
+get_rootfh(struct svc_req *rqstp, dirpath *path, int *error, int v3)
 {
        struct sockaddr_in *sin = svc_getcaller(rqstp->rq_xprt);
        struct stat     stb;
@@ -252,19 +252,23 @@ get_rootfh(struct svc_req *rqstp, dirpath *path, int *error)
                xlog(L_WARNING, "%s is not a directory or regular file", p);
                *error = NFSERR_NOTDIR;
        } else {
-               struct knfs_fh  *fh;
+               struct nfs_fh_len  *fh;
 
                if (!exp->m_exported)
                        export_export(exp);
                if (!exp->m_xtabent)
                        xtab_append(exp);
 
-               /* We first try the new nfs syscall. */
-               fh = getfh ((struct sockaddr *) sin, p);
-               if (fh == NULL && errno == EINVAL)
-                       /* Let's try the old one. */
-                       fh = getfh_old ((struct sockaddr *) sin,
-                                   stb.st_dev, stb.st_ino);
+               if (v3)
+                       fh = getfh_size ((struct sockaddr *) sin, p, 64);
+               if (!v3 || (fh == NULL && errno == EINVAL)) {
+                       /* We first try the new nfs syscall. */
+                       fh = getfh ((struct sockaddr *) sin, p);
+                       if (fh == NULL && errno == EINVAL)
+                               /* Let's try the old one. */
+                               fh = getfh_old ((struct sockaddr *) sin,
+                                               stb.st_dev, stb.st_ino);
+               }
                if (fh != NULL) {
                        mountlist_add(exp, p);
                        *error = NFS_OK;
@@ -424,7 +428,7 @@ main(int argc, char **argv)
                usage(argv [0], 1);
 
        /* Initialize logging. */
-       xlog_open("mountd");
+/*     xlog_open("mountd"); */
 
        sa.sa_handler = SIG_IGN;
        sa.sa_flags = 0;