diff -u --recursive --new-file linux-2.4.1/arch/sparc/kernel/sys_sunos.c linux-2.4.1-fh_align/arch/sparc/kernel/sys_sunos.c --- linux-2.4.1/arch/sparc/kernel/sys_sunos.c Thu Jan 25 00:18:06 2001 +++ linux-2.4.1-fh_align/arch/sparc/kernel/sys_sunos.c Fri Feb 9 10:44:29 2001 @@ -605,7 +605,7 @@ struct sunos_nfs_mount_args { struct sockaddr_in *addr; /* file server address */ - struct nfs_fh *fh; /* File handle to be mounted */ + struct nfs3_fh *fh; /* File handle to be mounted */ int flags; /* flags */ int wsize; /* write size in bytes */ int rsize; /* read size in bytes */ diff -u --recursive --new-file linux-2.4.1/arch/sparc64/kernel/sys_sunos32.c linux-2.4.1-fh_align/arch/sparc64/kernel/sys_sunos32.c --- linux-2.4.1/arch/sparc64/kernel/sys_sunos32.c Mon Jan 22 22:30:20 2001 +++ linux-2.4.1-fh_align/arch/sparc64/kernel/sys_sunos32.c Fri Feb 9 10:45:13 2001 @@ -566,7 +566,7 @@ struct sunos_nfs_mount_args { struct sockaddr_in *addr; /* file server address */ - struct nfs_fh *fh; /* File handle to be mounted */ + struct nfs3_fh *fh; /* File handle to be mounted */ int flags; /* flags */ int wsize; /* write size in bytes */ int rsize; /* read size in bytes */ diff -u --recursive --new-file linux-2.4.1/fs/nfs/inode.c linux-2.4.1-fh_align/fs/nfs/inode.c --- linux-2.4.1/fs/nfs/inode.c Tue Dec 12 02:46:04 2000 +++ linux-2.4.1-fh_align/fs/nfs/inode.c Tue Jan 30 11:35:53 2001 @@ -239,7 +239,7 @@ struct nfs_server *server; struct rpc_xprt *xprt = NULL; struct rpc_clnt *clnt = NULL; - struct nfs_fh *root = &data->root, fh; + struct nfs_fh fh; struct inode *root_inode = NULL; unsigned int authflavor; struct sockaddr_in srvaddr; @@ -251,7 +251,6 @@ if (!data) goto out_miss_args; - memset(&fh, 0, sizeof(fh)); if (data->version != NFS_MOUNT_VERSION) { printk("nfs warning: mount version %s than kernel\n", data->version < NFS_MOUNT_VERSION ? "older" : "newer"); @@ -259,12 +258,21 @@ data->namlen = 0; if (data->version < 3) data->bsize = 0; - if (data->version < 4) { + if (data->version < 4) data->flags &= ~NFS_MOUNT_VER3; - root = &fh; - root->size = NFS2_FHSIZE; - memcpy(root->data, data->old_root.data, NFS2_FHSIZE); + } + + memset(&fh, 0, sizeof(fh)); + if (data->version < 4) { + fh.size = NFS2_FHSIZE; + memcpy(fh.data, data->old_root.data, NFS2_FHSIZE); + } else { + fh.size = (data->flags & NFS_MOUNT_VER3) ? data->root.size : NFS2_FHSIZE; + if (fh.size > sizeof(fh.data)) { + printk(KERN_WARNING "NFS: mount program passes invalid filehandle!\n"); + goto out_no_remote; } + memcpy(fh.data, data->root.data, fh.size); } /* We now require that the mount process passes the remote address */ @@ -363,9 +371,10 @@ * the root fh attributes. */ /* Did getting the root inode fail? */ - if (!(root_inode = nfs_get_root(sb, root)) + if (!(root_inode = nfs_get_root(sb, &fh)) && (data->flags & NFS_MOUNT_VER3)) { data->flags &= ~NFS_MOUNT_VER3; + fh.size = NFS2_FHSIZE; rpciod_down(); rpc_shutdown_client(server->client); goto nfsv3_try_again; @@ -380,7 +389,7 @@ sb->s_root->d_op = &nfs_dentry_operations; /* Get some general file system info */ - if (server->rpc_ops->statfs(server, root, &fsinfo) >= 0) { + if (server->rpc_ops->statfs(server, &fh, &fsinfo) >= 0) { if (server->namelen == 0) server->namelen = fsinfo.namelen; } else { diff -u --recursive --new-file linux-2.4.1/fs/nfs/mount_clnt.c linux-2.4.1-fh_align/fs/nfs/mount_clnt.c --- linux-2.4.1/fs/nfs/mount_clnt.c Thu Apr 13 16:54:19 2000 +++ linux-2.4.1-fh_align/fs/nfs/mount_clnt.c Thu Feb 1 09:41:10 2001 @@ -31,32 +31,32 @@ */ static int nfs_gen_mount(struct sockaddr_in *, - char *, struct nfs_fh *, int); + char *, struct nfs3_fh *, int); static struct rpc_clnt * mnt_create(char *, struct sockaddr_in *, int); extern struct rpc_program mnt_program; struct mnt_fhstatus { unsigned int status; - struct nfs_fh * fh; + struct nfs3_fh * fh; }; /* * Obtain an NFS file handle for the given host and path */ int -nfs_mount(struct sockaddr_in *addr, char *path, struct nfs_fh *fh) +nfs_mount(struct sockaddr_in *addr, char *path, struct nfs3_fh *fh) { return nfs_gen_mount(addr, path, fh, NFS_MNT_VERSION); } int -nfs3_mount(struct sockaddr_in *addr, char *path, struct nfs_fh *fh) +nfs3_mount(struct sockaddr_in *addr, char *path, struct nfs3_fh *fh) { return nfs_gen_mount(addr, path, fh, NFS_MNT3_VERSION); } static int -nfs_gen_mount(struct sockaddr_in *addr, char *path, struct nfs_fh *fh, int version) +nfs_gen_mount(struct sockaddr_in *addr, char *path, struct nfs3_fh *fh, int version) { struct rpc_clnt *mnt_clnt; struct mnt_fhstatus result = { 0, fh }; @@ -120,7 +120,7 @@ static int xdr_decode_fhstatus(struct rpc_rqst *req, u32 *p, struct mnt_fhstatus *res) { - struct nfs_fh *fh = res->fh; + struct nfs3_fh *fh = res->fh; memset((void *)fh, 0, sizeof(*fh)); if ((res->status = ntohl(*p++)) == 0) { @@ -133,7 +133,7 @@ static int xdr_decode_fhstatus3(struct rpc_rqst *req, u32 *p, struct mnt_fhstatus *res) { - struct nfs_fh *fh = res->fh; + struct nfs3_fh *fh = res->fh; memset((void *)fh, 0, sizeof(*fh)); if ((res->status = ntohl(*p++)) == 0) { diff -u --recursive --new-file linux-2.4.1/include/linux/nfs.h linux-2.4.1-fh_align/include/linux/nfs.h --- linux-2.4.1/include/linux/nfs.h Sat Apr 1 18:04:27 2000 +++ linux-2.4.1-fh_align/include/linux/nfs.h Tue Jan 30 11:35:53 2001 @@ -93,8 +93,8 @@ */ #define NFS_MAXFHSIZE 64 struct nfs_fh { - unsigned short size; - unsigned char data[NFS_MAXFHSIZE]; + unsigned int size; + unsigned int data[NFS_MAXFHSIZE / sizeof(int)]; }; /* diff -u --recursive --new-file linux-2.4.1/include/linux/nfs3.h linux-2.4.1-fh_align/include/linux/nfs3.h --- linux-2.4.1/include/linux/nfs3.h Sat Apr 1 18:04:27 2000 +++ linux-2.4.1-fh_align/include/linux/nfs3.h Tue Jan 30 11:35:53 2001 @@ -58,6 +58,11 @@ NF3BAD = 8 }; +struct nfs3_fh { + unsigned short size; + unsigned char data[NFS3_FHSIZE]; +}; + #define NFS3_VERSION 3 #define NFS3PROC_NULL 0 #define NFS3PROC_GETATTR 1 diff -u --recursive --new-file linux-2.4.1/include/linux/nfs_fs.h linux-2.4.1-fh_align/include/linux/nfs_fs.h --- linux-2.4.1/include/linux/nfs_fs.h Tue Jan 30 11:44:12 2001 +++ linux-2.4.1-fh_align/include/linux/nfs_fs.h Thu Feb 1 09:42:38 2001 @@ -260,8 +260,8 @@ * linux/fs/mount_clnt.c * (Used only by nfsroot module) */ -extern int nfs_mount(struct sockaddr_in *, char *, struct nfs_fh *); -extern int nfs3_mount(struct sockaddr_in *, char *, struct nfs_fh *); +extern int nfs_mount(struct sockaddr_in *, char *, struct nfs3_fh *); +extern int nfs3_mount(struct sockaddr_in *, char *, struct nfs3_fh *); /* * inline functions diff -u --recursive --new-file linux-2.4.1/include/linux/nfs_mount.h linux-2.4.1-fh_align/include/linux/nfs_mount.h --- linux-2.4.1/include/linux/nfs_mount.h Tue Jan 30 08:25:18 2001 +++ linux-2.4.1-fh_align/include/linux/nfs_mount.h Tue Jan 30 11:48:51 2001 @@ -9,7 +9,8 @@ * structure passed from user-space to kernel-space during an nfs mount */ #include -#include +#include +#include /* * WARNING! Do not delete or change the order of these fields. If @@ -37,7 +38,7 @@ char hostname[256]; /* 1 */ int namlen; /* 2 */ unsigned int bsize; /* 3 */ - struct nfs_fh root; /* 4 */ + struct nfs3_fh root; /* 4 */ }; /* bits in the flags field */ diff -u --recursive --new-file linux-2.4.1/include/linux/nfsd/nfsfh.h linux-2.4.1-fh_align/include/linux/nfsd/nfsfh.h --- linux-2.4.1/include/linux/nfsd/nfsfh.h Tue Jan 30 08:25:15 2001 +++ linux-2.4.1-fh_align/include/linux/nfsd/nfsfh.h Tue Jan 30 19:26:12 2001 @@ -31,7 +31,7 @@ * ino/dev of the exported inode. */ struct nfs_fhbase_old { - struct dentry * fb_dentry; /* dentry cookie - always 0xfeebbaca */ + __u32 fb_dcookie; /* dentry cookie - always 0xfeebbaca */ __u32 fb_ino; /* our inode number */ __u32 fb_dirino; /* dir inode number, 0 for directories */ __u32 fb_dev; /* our device */ @@ -101,7 +101,7 @@ } fh_base; }; -#define ofh_dcookie fh_base.fh_old.fb_dentry +#define ofh_dcookie fh_base.fh_old.fb_dcookie #define ofh_ino fh_base.fh_old.fb_ino #define ofh_dirino fh_base.fh_old.fb_dirino #define ofh_dev fh_base.fh_old.fb_dev