diff options
author | dfr <dfr@FreeBSD.org> | 1997-04-22 10:24:29 +0000 |
---|---|---|
committer | dfr <dfr@FreeBSD.org> | 1997-04-22 10:24:29 +0000 |
commit | e52cdb3cdfcdcb00a2c146e954e7b11a7966340a (patch) | |
tree | 6cb88efec26361c97876fb7da27fce5e8176bb59 /usr.sbin/amd | |
parent | 5e1197d908cdd207923561eabb3c956e064c1484 (diff) | |
download | FreeBSD-src-e52cdb3cdfcdcb00a2c146e954e7b11a7966340a.zip FreeBSD-src-e52cdb3cdfcdcb00a2c146e954e7b11a7966340a.tar.gz |
Update the host filesystem so that it works with NFSv3
Diffstat (limited to 'usr.sbin/amd')
-rw-r--r-- | usr.sbin/amd/amd/host_ops.c | 110 | ||||
-rw-r--r-- | usr.sbin/amd/amd/nfs_ops.c | 16 | ||||
-rw-r--r-- | usr.sbin/amd/include/mountres.h | 40 |
3 files changed, 129 insertions, 37 deletions
diff --git a/usr.sbin/amd/amd/host_ops.c b/usr.sbin/amd/amd/host_ops.c index bf71fc0..bf9eb92 100644 --- a/usr.sbin/amd/amd/host_ops.c +++ b/usr.sbin/amd/amd/host_ops.c @@ -37,7 +37,7 @@ * * @(#)host_ops.c 8.1 (Berkeley) 6/6/93 * - * $Id$ + * $Id: host_ops.c,v 1.4 1997/02/22 16:01:29 peter Exp $ * */ @@ -46,6 +46,7 @@ #ifdef HAS_HOST #include "mount.h" +#include "mountres.h" #include <sys/stat.h> /* @@ -132,9 +133,9 @@ caddr_t args_ptr; return ((*xdr_args)(&xdr, args_ptr)); } -static int do_mount P((fhstatus *fhp, char *dir, char *fs_name, char *opts, mntfs *mf)); -static int do_mount(fhp, dir, fs_name, opts, mf) -fhstatus *fhp; +static int do_mount P((mountres *mrp, char *dir, char *fs_name, char *opts, mntfs *mf)); +static int do_mount(mrp, dir, fs_name, opts, mf) +mountres *mrp; char *dir; char *fs_name; char *opts; @@ -152,7 +153,7 @@ mntfs *mf; return ENOENT; } - return mount_nfs_fh(fhp, dir, fs_name, opts, mf); + return mount_nfs_fh(mrp, dir, fs_name, opts, mf); } static int sortfun P((exports *a, exports *b)); @@ -165,14 +166,16 @@ exports *a,*b; /* * Get filehandle */ -static int fetch_fhandle P((CLIENT *client, char *dir, fhstatus *fhp)); -static int fetch_fhandle(client, dir, fhp) +static int fetch_fhandle P((CLIENT *client, xdrproc_t xdr_mountres, char *dir, mountres *mrp)); +static int fetch_fhandle(client, xdr_mountres, dir, mrp) CLIENT *client; +xdrproc_t xdr_mountres; char *dir; -fhstatus *fhp; +mountres *mrp; { struct timeval tv; enum clnt_stat clnt_stat; + int status; /* * Pick a number, any number... @@ -187,7 +190,9 @@ fhstatus *fhp; * Call the mount daemon on the remote host to * get the filehandle. */ - clnt_stat = clnt_call(client, MOUNTPROC_MNT, xdr_dirpath, &dir, xdr_fhstatus, fhp, tv); + clnt_stat = clnt_call(client, MOUNTPROC_MNT, xdr_dirpath, &dir, xdr_mountres, &mrp->mr_mountres, tv); + if (clnt_stat == 0) + status = mrp->mr_fhstatus.fhs_status; /* XXX assumes fhstatus and mountres3 start the same */ if (clnt_stat != RPC_SUCCESS) { extern char *clnt_sperrno(); char *msg = clnt_sperrno(clnt_stat); @@ -197,12 +202,12 @@ fhstatus *fhp; /* * Check status of filehandle */ - if (fhp->fhs_status) { + if (status) { #ifdef DEBUG - errno = fhp->fhs_status; + errno = status; dlog("fhandle fetch failed: %m"); #endif /* DEBUG */ - return fhp->fhs_status; + return status; } return 0; } @@ -224,12 +229,35 @@ char *dir; } /* - * Mount the export tree from a host + * Return TRUE if mount opts contains nfsv2 flag. */ -static int host_fmount P((mntfs *mf)); -static int host_fmount(mf) +static int forcev2(mf) +mntfs *mf; +{ + struct mntent mnt; + + mnt.mnt_dir = mf->mf_mount; + mnt.mnt_fsname = mf->mf_info; + mnt.mnt_type = MTAB_TYPE_NFS; + mnt.mnt_opts = mf->mf_mopts; + mnt.mnt_freq = 0; + mnt.mnt_passno = 0; + + if (hasmntopt(&mnt, "nfsv2") != NULL) + return TRUE; + else + return FALSE; +} + +/* + * A helper for host_fmount. + */ +static int try_fmount P((mntfs *mf, int mountvers)); +static int try_fmount(mf, mountvers) mntfs *mf; +int mountvers; { + xdrproc_t xdr_mountres; struct timeval tv2; CLIENT *client; enum clnt_stat clnt_stat; @@ -237,7 +265,7 @@ mntfs *mf; int j, k; exports exlist = 0, ex; exports *ep = 0; - fhstatus *fp = 0; + mountres *mrp = 0; char *host = mf->mf_server->fs_host; int error = 0; struct sockaddr_in sin; @@ -249,6 +277,11 @@ mntfs *mf; struct timeval tv; tv.tv_sec = 10; tv.tv_usec = 0; + if (mountvers == MOUNTVERS) + xdr_mountres = xdr_fhstatus; + else + xdr_mountres = xdr_mountres3; + /* * Read the mount list */ @@ -272,8 +305,8 @@ mntfs *mf; * Make a client end-point. * Try TCP first */ - if ((client = clnttcp_create(&sin, MOUNTPROG, MOUNTVERS, &sock, 0, 0)) == NULL && - (client = clntudp_create(&sin, MOUNTPROG, MOUNTVERS, tv, &sock)) == NULL) { + if ((client = clnttcp_create(&sin, MOUNTPROG, mountvers, &sock, 0, 0)) == NULL && + (client = clntudp_create(&sin, MOUNTPROG, mountvers, tv, &sock)) == NULL) { plog(XLOG_ERROR, "Failed to make rpc connection to mountd on %s", host); error = EIO; goto out; @@ -337,8 +370,9 @@ mntfs *mf; /* * Allocate an array of filehandles */ - fp = (fhstatus *) xmalloc(n_export * sizeof(fhstatus)); - + mrp = (mountres *) xmalloc(n_export * sizeof(mountres)); + bzero(mrp, n_export * sizeof(mountres)); + /* * Try to obtain filehandles for each directory. * If a fetch fails then just zero out the array @@ -353,7 +387,8 @@ mntfs *mf; ep[j] = 0; } else { k = j; - if (error = fetch_fhandle(client, ep[j]->ex_dir, &fp[j])) + mrp[j].mr_version = mountvers; + if (error = fetch_fhandle(client, xdr_mountres, ep[j]->ex_dir, &mrp[j])) ep[j] = 0; } } @@ -376,7 +411,7 @@ mntfs *mf; if (ex) { strcpy(rfs_dir, ex->ex_dir); MAKE_MNTPT(mntpt, ex, mf); - if (do_mount(&fp[j], mntpt, fs_name, mf->mf_mopts, mf) == 0) + if (do_mount(&mrp[j], mntpt, fs_name, mf->mf_mopts, mf) == 0) ok = TRUE; } } @@ -388,8 +423,11 @@ out: discard_mntlist(mlist); if (ep) free(ep); - if (fp) - free(fp); + if (mrp) { + for (j = 0; j < n_export; j++) + xdr_free(xdr_mountres, (char *) &mrp->mr_mountres); + free(mrp); + } if (client) clnt_destroy(client); if (exlist) @@ -400,6 +438,30 @@ out: } /* + * Mount the export tree from a host + */ +static int host_fmount P((mntfs *mf)); +static int host_fmount(mf) +mntfs *mf; +{ + int error = -1; + +#ifdef DEBUG + dlog("host_fmount: trying to mount v3"); +#endif + if (!forcev2(mf)) + error = try_fmount(mf, MOUNTVERS3); + if (error) { +#ifdef DEBUG + dlog("host_fmount: trying to mount v2"); +#endif + error = try_fmount(mf, MOUNTVERS); + } + + return error; +} + +/* * Return true if pref is a directory prefix of dir. * * TODO: diff --git a/usr.sbin/amd/amd/nfs_ops.c b/usr.sbin/amd/amd/nfs_ops.c index 9fd81cf..1d94943 100644 --- a/usr.sbin/amd/amd/nfs_ops.c +++ b/usr.sbin/amd/amd/nfs_ops.c @@ -57,6 +57,7 @@ typedef nfs_fh fhandle_t; #endif /* NFS_HDR */ #include <sys/mount.h> #include "mount.h" +#include "mountres.h" /* * Network file system @@ -93,16 +94,6 @@ typedef nfs_fh fhandle_t; * changes. If it does, then you have other * problems... */ -typedef struct mountres { - int mr_version; /* 1 or 3 */ - union { - struct fhstatus mru_fhstatus; /* mount v1 result */ - struct mountres3 mru_mountres3; /* mount v3 result */ - } mr_un; -} mountres; -#define mr_fhstatus mr_un.mru_fhstatus -#define mr_mountres3 mr_un.mru_mountres3 - typedef struct fh_cache fh_cache; struct fh_cache { qelem fh_q; /* List header */ @@ -232,9 +223,8 @@ fh_cache *fp; dlog("Discarding filehandle for %s:%s", fp->fh_fs->fs_host, fp->fh_path); #endif /* DEBUG */ free_srvr(fp->fh_fs); - if (fp->fh_mountres.mr_version == MOUNTVERS3 - && fp->fh_mountres.mr_mountres3.mountres3_u.mountinfo.fhandle.fhandle3_val) - free(fp->fh_mountres.mr_mountres3.mountres3_u.mountinfo.fhandle.fhandle3_val); + if (fp->fh_mountres.mr_version == MOUNTVERS3) + xdr_free(xdr_mountres3, (char *) &fp->fh_mountres.mr_mountres3); free((voidp) fp->fh_path); free((voidp) fp); } diff --git a/usr.sbin/amd/include/mountres.h b/usr.sbin/amd/include/mountres.h new file mode 100644 index 0000000..cb3681d --- /dev/null +++ b/usr.sbin/amd/include/mountres.h @@ -0,0 +1,40 @@ +/*- + * Copyright (c) 1997 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $Id$ + */ + +/* + * A reply from mountd, either v1 (for nfsv2) or v2 (for nfsv3). + */ +typedef struct mountres { + int mr_version; /* 1 or 3 */ + union { + struct fhstatus mru_fhstatus; /* mount v1 result */ + struct mountres3 mru_mountres3; /* mount v3 result */ + } mr_mountres; +} mountres; +#define mr_fhstatus mr_mountres.mru_fhstatus +#define mr_mountres3 mr_mountres.mru_mountres3 |