From: Neil Brown Date: Tue, 27 Feb 2007 05:35:01 +0000 (+1100) Subject: Merge branch 'branch-1-0' X-Git-Tag: nfs-utils-1-1-0-rc1~90 X-Git-Url: https://git.decadent.org.uk/gitweb/?p=nfs-utils.git;a=commitdiff_plain;h=57d81b9f4c7f877d64aa7e8c5bddb852e1aa32ce;hp=fa2058d9dc483dbed373ddc04a898ddd7f135f6f Merge branch 'branch-1-0' --- diff --git a/aclocal/tcp-wrappers.m4 b/aclocal/tcp-wrappers.m4 index 0fdf611..35ac8e0 100644 --- a/aclocal/tcp-wrappers.m4 +++ b/aclocal/tcp-wrappers.m4 @@ -4,7 +4,7 @@ AC_DEFUN([AC_TCP_WRAPPERS],[ AC_ARG_WITH(tcp-wrappers, [ --with-tcp-wrappers[[=PATH]] Enable tcpwrappers support (optionally in PATH)], - with_tcpw=$withval, $with_tcpw=yes) + with_tcpw=$withval, with_tcpw=yes) if test "x$with_tcpw" != "xno" ; then saved_LIBS="$LIBS" saved_LDFLAGS="$LDFLAGS" diff --git a/support/export/export.c b/support/export/export.c index cfb6681..a4b0788 100644 --- a/support/export/export.c +++ b/support/export/export.c @@ -240,6 +240,8 @@ export_freeall(void) xfree(exp->m_export.e_sqgids); if (exp->m_export.e_mountpoint) free(exp->m_export.e_mountpoint); + if (exp->m_export.e_fslocdata) + xfree(exp->m_export.e_fslocdata); xfree(exp); } exportlist[i] = NULL; diff --git a/support/nfs/exports.c b/support/nfs/exports.c index 60cfe48..9638015 100644 --- a/support/nfs/exports.c +++ b/support/nfs/exports.c @@ -236,9 +236,11 @@ putexportent(struct exportent *ep) case FSLOC_REPLICA: fprintf(fp, "replicas=%s,", ep->e_fslocdata); break; +#ifdef DEBUG case FSLOC_STUB: fprintf(fp, "fsloc=stub,"); break; +#endif default: xlog(L_ERROR, "unknown fsloc method for %s:%s", ep->e_hostname, ep->e_path); @@ -504,6 +506,7 @@ bad_option: ep->e_mountpoint = strdup(mp+1); else ep->e_mountpoint = strdup(""); +#ifdef DEBUG } else if (strncmp(opt, "fsloc=", 6) == 0) { if (strcmp(opt+6, "stub") == 0) ep->e_fslocmethod = FSLOC_STUB; @@ -512,6 +515,7 @@ bad_option: flname, flline, opt); goto bad_option; } +#endif } else if (strncmp(opt, "refer=", 6) == 0) { ep->e_fslocmethod = FSLOC_REFER; ep->e_fslocdata = strdup(opt+6); diff --git a/utils/exportfs/exportfs.c b/utils/exportfs/exportfs.c index 40a6b56..22e13a3 100644 --- a/utils/exportfs/exportfs.c +++ b/utils/exportfs/exportfs.c @@ -427,9 +427,11 @@ dump(int verbose) case FSLOC_REPLICA: c = dumpopt(c, "replicas=%s", ep->e_fslocdata); break; +#ifdef DEBUG case FSLOC_STUB: c = dumpopt(c, "fsloc=stub"); break; +#endif } printf("%c\n", (c != '(')? ')' : ' '); } diff --git a/utils/exportfs/exports.man b/utils/exportfs/exports.man index 27a30f9..ab63b03 100644 --- a/utils/exportfs/exports.man +++ b/utils/exportfs/exports.man @@ -348,6 +348,20 @@ If the client asks for alternative locations for the export point, it will be given this list of alternatives. (Note that actual replication of the filesystem must be handled elsewhere.) +.TP +.IR refer= path@host[+host][:path@host[+host]] +A client referencing the export point will be directed to choose from +the given list an alternative location for the filesystem. +(Note that the server must have a mountpoint here, though a different +filesystem is not required; so, for example, +.IR "mount --bind" " /path /path" +is sufficient.) +.TP +.IR replicas= path@host[+host][:path@host[+host]] +If the client asks for alternative locations for the export point, it +will be given this list of alternatives. (Note that actual replication +of the filesystem must be handled elsewhere.) + .SS User ID Mapping .PP .I nfsd diff --git a/utils/mountd/cache.c b/utils/mountd/cache.c index a14f4f2..fbe829e 100644 --- a/utils/mountd/cache.c +++ b/utils/mountd/cache.c @@ -455,6 +455,7 @@ static int dump_to_cache(FILE *f, char *domain, char *path, struct exportent *ex qword_printint(f, exp->e_anonuid); qword_printint(f, exp->e_anongid); qword_printint(f, exp->e_fsid); + write_fsloc(f, exp, path); if (exp->e_uuid == NULL) { char u[16]; if (get_uuid(exp->e_path, NULL, 16, u)) { @@ -465,7 +466,6 @@ static int dump_to_cache(FILE *f, char *domain, char *path, struct exportent *ex qword_print(f, "uuid"); qword_printhex(f, exp->e_uuid, 16); } - write_fsloc(f, &exp, path); } return qword_eol(f); } @@ -548,7 +548,7 @@ void cache_open(void) int i; for (i=0; cachelist[i].cache_name; i++ ) { char path[100]; - if (!manage_gids && cachelist[i].f == auth_unix_gid) + if (!manage_gids && cachelist[i].cache_handle == auth_unix_gid) continue; sprintf(path, "/proc/net/rpc/%s/channel", cachelist[i].cache_name); cachelist[i].f = fopen(path, "r+"); diff --git a/utils/mountd/fsloc.c b/utils/mountd/fsloc.c new file mode 100644 index 0000000..5b094b0 --- /dev/null +++ b/utils/mountd/fsloc.c @@ -0,0 +1,188 @@ +/* + * COPYRIGHT (c) 2006 + * THE REGENTS OF THE UNIVERSITY OF MICHIGAN + * ALL RIGHTS RESERVED + * + * Permission is granted to use, copy, create derivative works + * and redistribute this software and such derivative works + * for any purpose, so long as the name of The University of + * Michigan is not used in any advertising or publicity + * pertaining to the use of distribution of this software + * without specific, written prior authorization. If the + * above copyright notice or any other identification of the + * University of Michigan is included in any copy of any + * portion of this software, then the disclaimer below must + * also be included. + * + * THIS SOFTWARE IS PROVIDED AS IS, WITHOUT REPRESENTATION + * FROM THE UNIVERSITY OF MICHIGAN AS TO ITS FITNESS FOR ANY + * PURPOSE, AND WITHOUT WARRANTY BY THE UNIVERSITY OF + * MICHIGAN OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING + * WITHOUT LIMITATION THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE + * REGENTS OF THE UNIVERSITY OF MICHIGAN SHALL NOT BE LIABLE + * FOR ANY DAMAGES, INCLUDING SPECIAL, INDIRECT, INCIDENTAL, OR + * CONSEQUENTIAL DAMAGES, WITH RESPECT TO ANY CLAIM ARISING + * OUT OF OR IN CONNECTION WITH THE USE OF THE SOFTWARE, EVEN + * IF IT HAS BEEN OR IS HEREAFTER ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGES. + */ + +#include +#include +#include + +#include "fsloc.h" +#include "exportfs.h" + +/* Debugging tool: prints out @servers info to syslog */ +static void replicas_print(struct servers *sp) +{ + int i; + if (!sp) { + xlog(L_NOTICE, "NULL replicas pointer\n"); + return; + } + xlog(L_NOTICE, "replicas listsize=%i\n", sp->h_num); + for (i=0; ih_num; i++) { + xlog(L_NOTICE, " %s:%s\n", + sp->h_mp[i]->h_host, sp->h_mp[i]->h_path); + } +} + +#ifdef DEBUG +/* Called by setting 'Method = stub' in config file. Just returns + * some syntactically correct gibberish for testing purposes. + */ +static struct servers *method_stub(char *key) +{ + struct servers *sp; + struct mount_point *mp; + + xlog(L_NOTICE, "called method_stub\n"); + sp = malloc(sizeof(struct servers)); + if (!sp) + return NULL; + mp = calloc(1, sizeof(struct mount_point)); + if (!mp) { + free(sp); + return NULL; + } + sp->h_num = 1; + sp->h_mp[0] = mp; + mp->h_host = strdup("stub_server"); + mp->h_path = strdup("/my/test/path"); + sp->h_referral = 1; + return sp; +} +#endif /* DEBUG */ + +/* Scan @list, which is a NULL-terminated array of strings of the + * form path@host[+host], and return corresponding servers structure. + */ +static struct servers *parse_list(char **list) +{ + int i; + struct servers *res; + struct mount_point *mp; + char *cp; + + res = malloc(sizeof(struct servers)); + if (!res) + return NULL; + res->h_num = 0; + + /* parse each of the answers in sucession. */ + for (i=0; list[i] && ih_mp[i] = mp; + res->h_num++; + mp->h_path = strndup(list[i], cp - list[i]); + cp++; + mp->h_host = strdup(cp); + /* hosts are '+' separated, kernel expects ':' separated */ + while ( (cp = strchr(mp->h_host, '+')) ) + *cp = ':'; + } + return res; +} + +/* @data is a string of form path@host[+host][:path@host[+host]] + */ +static struct servers *method_list(char *data) +{ + char *copy, *ptr=data; + char **list; + int i, listsize; + struct servers *rv=NULL; + + xlog(L_NOTICE, "method_list(%s)\n", data); + for (ptr--, listsize=1; ptr; ptr=index(ptr, ':'), listsize++) + ptr++; + list = malloc(listsize * sizeof(char *)); + copy = strdup(data); + if (copy) + xlog(L_NOTICE, "converted to %s\n", copy); + if (list && copy) { + ptr = copy; + for (i=0; ih_referral = 1; + break; + case FSLOC_REPLICA: + sp = method_list(data); + if (sp) + sp->h_referral = 0; + break; +#ifdef DEBUG + case FSLOC_STUB: + sp = method_stub(data); + break; +#endif + default: + xlog(L_WARNING, "Unknown method = %i", method); + } + replicas_print(sp); + return sp; +} + +void release_replicas(struct servers *server) +{ + int i; + + if (!server) return; + for (i = 0; i < server->h_num; i++) { + free(server->h_mp[i]->h_host); + free(server->h_mp[i]->h_path); + free(server->h_mp[i]); + } + free(server); +} diff --git a/utils/mountd/fsloc.h b/utils/mountd/fsloc.h new file mode 100644 index 0000000..8296d1c --- /dev/null +++ b/utils/mountd/fsloc.h @@ -0,0 +1,50 @@ +/* + * COPYRIGHT (c) 2006 + * THE REGENTS OF THE UNIVERSITY OF MICHIGAN + * ALL RIGHTS RESERVED + * + * Permission is granted to use, copy, create derivative works + * and redistribute this software and such derivative works + * for any purpose, so long as the name of The University of + * Michigan is not used in any advertising or publicity + * pertaining to the use of distribution of this software + * without specific, written prior authorization. If the + * above copyright notice or any other identification of the + * University of Michigan is included in any copy of any + * portion of this software, then the disclaimer below must + * also be included. + * + * THIS SOFTWARE IS PROVIDED AS IS, WITHOUT REPRESENTATION + * FROM THE UNIVERSITY OF MICHIGAN AS TO ITS FITNESS FOR ANY + * PURPOSE, AND WITHOUT WARRANTY BY THE UNIVERSITY OF + * MICHIGAN OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING + * WITHOUT LIMITATION THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE + * REGENTS OF THE UNIVERSITY OF MICHIGAN SHALL NOT BE LIABLE + * FOR ANY DAMAGES, INCLUDING SPECIAL, INDIRECT, INCIDENTAL, OR + * CONSEQUENTIAL DAMAGES, WITH RESPECT TO ANY CLAIM ARISING + * OUT OF OR IN CONNECTION WITH THE USE OF THE SOFTWARE, EVEN + * IF IT HAS BEEN OR IS HEREAFTER ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGES. + */ + +#ifndef FSLOC_H +#define FSLOC_H + +#define FSLOC_MAX_LIST 40 + +struct mount_point { + char *h_host; + char *h_path; +}; + +struct servers { + int h_num; + struct mount_point *h_mp[FSLOC_MAX_LIST]; + int h_referral; /* 0=replica, 1=referral */ +}; + +struct servers *replicas_lookup(int method, char *data, char *key); +void release_replicas(struct servers *server); + +#endif /* FSLOC_H */