From ac114959c3f5a2d62ea18641e24fe86a09de7b14 Mon Sep 17 00:00:00 2001 From: Steve Dickson Date: Nov 16 2016 18:39:16 +0000 Subject: Updated to the latest RC release: nfs-utils-1-3-5-rc3 Signed-off-by: Steve Dickson --- diff --git a/nfs-utils-1.3.5-rc1.patch b/nfs-utils-1.3.5-rc1.patch deleted file mode 100644 index 6188fa9..0000000 --- a/nfs-utils-1.3.5-rc1.patch +++ /dev/null @@ -1,450 +0,0 @@ -diff --git a/support/export/export.c b/support/export/export.c -index e1bebce..0b8a858 100644 ---- a/support/export/export.c -+++ b/support/export/export.c -@@ -15,6 +15,8 @@ - #include - #include - #include -+#include -+#include - #include "xmalloc.h" - #include "nfslib.h" - #include "exportfs.h" -@@ -96,6 +98,69 @@ export_read(char *fname) - } - - /** -+ * export_d_read - read entries from /etc/exports. -+ * @fname: name of directory to read from -+ * -+ * Returns number of read entries. -+ * Based on mnt_table_parse_dir() in -+ * util-linux-ng/shlibs/mount/src/tab_parse.c -+ */ -+int -+export_d_read(const char *dname) -+{ -+ int n = 0, i; -+ struct dirent **namelist = NULL; -+ int volumes = 0; -+ -+ -+ n = scandir(dname, &namelist, NULL, versionsort); -+ if (n < 0) { -+ if (errno == ENOENT) -+ /* Silently return */ -+ return volumes; -+ xlog(L_NOTICE, "scandir %s: %s", dname, strerror(errno)); -+ } else if (n == 0) -+ return volumes; -+ -+ for (i = 0; i < n; i++) { -+ struct dirent *d = namelist[i]; -+ size_t namesz; -+ char fname[PATH_MAX + 1]; -+ int fname_len; -+ -+ -+ if (d->d_type != DT_UNKNOWN -+ && d->d_type != DT_REG -+ && d->d_type != DT_LNK) -+ continue; -+ if (*d->d_name == '.') -+ continue; -+ -+#define _EXT_EXPORT_SIZ (sizeof(_EXT_EXPORT) - 1) -+ namesz = strlen(d->d_name); -+ if (!namesz -+ || namesz < _EXT_EXPORT_SIZ + 1 -+ || strcmp(d->d_name + (namesz - _EXT_EXPORT_SIZ), -+ _EXT_EXPORT)) -+ continue; -+ -+ fname_len = snprintf(fname, PATH_MAX +1, "%s/%s", dname, d->d_name); -+ if (fname_len > PATH_MAX) { -+ xlog(L_WARNING, "Too long file name: %s in %s", d->d_name, dname); -+ continue; -+ } -+ -+ volumes += export_read(fname); -+ } -+ -+ for (i = 0; i < n; i++) -+ free(namelist[i]); -+ free(namelist); -+ -+ return volumes; -+} -+ -+/** - * export_create - create an in-core nfs_export record from an export entry - * @xep: export entry to lookup - * @canonical: if set, e_hostname is known to be canonical DNS name -diff --git a/support/include/exportfs.h b/support/include/exportfs.h -index 4cac203..f033329 100644 ---- a/support/include/exportfs.h -+++ b/support/include/exportfs.h -@@ -135,6 +135,7 @@ int client_member(const char *client, - const char *name); - - int export_read(char *fname); -+int export_d_read(const char *dname); - void export_reset(nfs_export *); - nfs_export * export_lookup(char *hname, char *path, int caconical); - nfs_export * export_find(const struct addrinfo *ai, -diff --git a/systemd/Makefile.am b/systemd/Makefile.am -index 03f96e9..49c9b8d 100644 ---- a/systemd/Makefile.am -+++ b/systemd/Makefile.am -@@ -39,8 +39,16 @@ endif - EXTRA_DIST = $(unit_files) - - unit_dir = /usr/lib/systemd/system -+generator_dir = /usr/lib/systemd/system-generators -+ -+EXTRA_PROGRAMS = nfs-server-generator -+genexecdir = $(generator_dir) -+nfs_server_generator_LDADD = ../support/export/libexport.a \ -+ ../support/nfs/libnfs.a \ -+ ../support/misc/libmisc.a - - if INSTALL_SYSTEMD -+genexec_PROGRAMS = nfs-server-generator - install-data-hook: $(unit_files) - mkdir -p $(DESTDIR)/$(unitdir) - cp $(unit_files) $(DESTDIR)/$(unitdir) -diff --git a/systemd/nfs-server-generator.c b/systemd/nfs-server-generator.c -new file mode 100644 -index 0000000..af8bb52 ---- /dev/null -+++ b/systemd/nfs-server-generator.c -@@ -0,0 +1,144 @@ -+/* -+ * nfs-server-generator: -+ * systemd generator to create ordering dependencies between -+ * nfs-server and various filesystem mounts -+ * -+ * 1/ nfs-server should start Before any 'nfs' mountpoints are -+ * mounted, in case they are loop-back mounts. This ordering is particularly -+ * important for the shutdown side, so the nfs-server is stopped -+ * after the filesystems are unmounted. -+ * 2/ nfs-server should start After all exported filesystems are mounted -+ * so there is no risk of exporting the underlying directory. -+ * This is particularly important for _net mounts which -+ * are not caught by "local-fs.target". -+ */ -+ -+#ifdef HAVE_CONFIG_H -+#include -+#endif -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "misc.h" -+#include "nfslib.h" -+#include "exportfs.h" -+ -+/* A simple "set of strings" to remove duplicates -+ * found in /etc/exports -+ */ -+struct list { -+ struct list *next; -+ char *name; -+}; -+static int is_unique(struct list **lp, char *path) -+{ -+ struct list *l = *lp; -+ -+ while (l) { -+ if (strcmp(l->name, path) == 0) -+ return 0; -+ l = l->next; -+ } -+ l = malloc(sizeof(*l)); -+ l->name = path; -+ l->next = *lp; -+ *lp = l; -+ return 1; -+} -+ -+/* We need to convert a path name to a systemd unit -+ * name. This requires some translation ('/' -> '-') -+ * and some escaping. -+ */ -+static void systemd_escape(FILE *f, char *path) -+{ -+ while (*path == '/') -+ path++; -+ if (!*path) { -+ /* "/" becomes "-", otherwise leading "/" is ignored */ -+ fputs("-", f); -+ return; -+ } -+ while (*path) { -+ char c = *path++; -+ -+ if (c == '/') { -+ /* multiple non-trailing slashes become '-' */ -+ while (*path == '/') -+ path++; -+ if (*path) -+ fputs("-", f); -+ } else if (isalnum(c) || c == ':' || c == '.') -+ fputc(c, f); -+ else -+ fprintf(f, "\\x%02x", c & 0xff); -+ } -+} -+ -+int main(int argc, char *argv[]) -+{ -+ char *path; -+ char dirbase[] = "/nfs-server.service.d"; -+ char filebase[] = "/order-with-mounts.conf"; -+ nfs_export *exp; -+ int i; -+ struct list *list = NULL; -+ FILE *f, *fstab; -+ struct mntent *mnt; -+ -+ if (argc != 4 || argv[1][0] != '/') { -+ fprintf(stderr, "nfs-server-generator: create systemd dependencies for nfs-server\n"); -+ fprintf(stderr, "Usage: normal-dir early-dir late-dir\n"); -+ exit(1); -+ } -+ -+ path = malloc(strlen(argv[1]) + sizeof(dirbase) + sizeof(filebase)); -+ if (!path) -+ exit(2); -+ if (export_read(_PATH_EXPORTS) + -+ export_d_read(_PATH_EXPORTS_D) == 0) -+ /* Nothing is exported, so nothing to do */ -+ exit(0); -+ -+ strcat(strcpy(path, argv[1]), dirbase); -+ mkdir(path, 0755); -+ strcat(path, filebase); -+ f = fopen(path, "w"); -+ if (!f) -+ return 1; -+ fprintf(f, "# Automatically generated by nfs-server-generator\n\n[Unit]\n"); -+ -+ for (i = 0; i < MCL_MAXTYPES; i++) { -+ for (exp = exportlist[i].p_head; exp; exp = exp->m_next) { -+ if (!is_unique(&list, exp->m_export.e_path)) -+ continue; -+ if (strchr(exp->m_export.e_path, ' ')) -+ fprintf(f, "RequiresMountsFor=\"%s\"\n", -+ exp->m_export.e_path); -+ else -+ fprintf(f, "RequiresMountsFor=%s\n", -+ exp->m_export.e_path); -+ } -+ } -+ -+ fstab = setmntent("/etc/fstab", "r"); -+ while ((mnt = getmntent(fstab)) != NULL) { -+ if (strcmp(mnt->mnt_type, "nfs") != 0 && -+ strcmp(mnt->mnt_type, "nfs4") != 0) -+ continue; -+ fprintf(f, "Before= "); -+ systemd_escape(f, mnt->mnt_dir); -+ fprintf(f, ".mount\n"); -+ } -+ -+ fclose(f); -+ -+ exit(0); -+} -diff --git a/systemd/nfs-server.service b/systemd/nfs-server.service -index 2ccdc63..196c818 100644 ---- a/systemd/nfs-server.service -+++ b/systemd/nfs-server.service -@@ -16,9 +16,6 @@ Before= rpc-statd-notify.service - Wants=auth-rpcgss-module.service - After=rpc-gssd.service gssproxy.service rpc-svcgssd.service - --# start/stop server before/after client --Before=remote-fs-pre.target -- - Wants=nfs-config.service - After=nfs-config.service - -diff --git a/utils/exportfs/exportfs.c b/utils/exportfs/exportfs.c -index a00b5ea..4ac2c15 100644 ---- a/utils/exportfs/exportfs.c -+++ b/utils/exportfs/exportfs.c -@@ -26,7 +26,6 @@ - #include - #include - #include --#include - #include - #include - -@@ -47,7 +46,6 @@ static void error(nfs_export *exp, int err); - static void usage(const char *progname, int n); - static void validate_export(nfs_export *exp); - static int matchhostname(const char *hostname1, const char *hostname2); --static int export_d_read(const char *dname); - static void grab_lockfile(void); - static void release_lockfile(void); - -@@ -700,63 +698,6 @@ out: - return result; - } - --/* Based on mnt_table_parse_dir() in -- util-linux-ng/shlibs/mount/src/tab_parse.c */ --static int --export_d_read(const char *dname) --{ -- int n = 0, i; -- struct dirent **namelist = NULL; -- int volumes = 0; -- -- -- n = scandir(dname, &namelist, NULL, versionsort); -- if (n < 0) { -- if (errno == ENOENT) -- /* Silently return */ -- return volumes; -- xlog(L_NOTICE, "scandir %s: %s", dname, strerror(errno)); -- } else if (n == 0) -- return volumes; -- -- for (i = 0; i < n; i++) { -- struct dirent *d = namelist[i]; -- size_t namesz; -- char fname[PATH_MAX + 1]; -- int fname_len; -- -- -- if (d->d_type != DT_UNKNOWN -- && d->d_type != DT_REG -- && d->d_type != DT_LNK) -- continue; -- if (*d->d_name == '.') -- continue; -- --#define _EXT_EXPORT_SIZ (sizeof(_EXT_EXPORT) - 1) -- namesz = strlen(d->d_name); -- if (!namesz -- || namesz < _EXT_EXPORT_SIZ + 1 -- || strcmp(d->d_name + (namesz - _EXT_EXPORT_SIZ), -- _EXT_EXPORT)) -- continue; -- -- fname_len = snprintf(fname, PATH_MAX +1, "%s/%s", dname, d->d_name); -- if (fname_len > PATH_MAX) { -- xlog(L_WARNING, "Too long file name: %s in %s", d->d_name, dname); -- continue; -- } -- -- volumes += export_read(fname); -- } -- -- for (i = 0; i < n; i++) -- free(namelist[i]); -- free(namelist); -- -- return volumes; --} -- - static char - dumpopt(char c, char *fmt, ...) - { -diff --git a/utils/idmapd/idmapd.man b/utils/idmapd/idmapd.man -index b9200c7..d4ab894 100644 ---- a/utils/idmapd/idmapd.man -+++ b/utils/idmapd/idmapd.man -@@ -23,6 +23,29 @@ is the NFSv4 ID <-> name mapping daemon. It provides functionality to - the NFSv4 kernel client and server, to which it communicates via - upcalls, by translating user and group IDs to names, and vice versa. - .Pp -+The system derives the -+.I user -+part of the string by performing a password or group lookup. -+The lookup mechanism is configured in -+.Pa /etc/idmapd.conf -+.Pp -+By default, the -+.I domain -+part of the string is the system's DNS domain name. -+It can also be specified in -+.Pa /etc/idmapd.conf -+if the system is multi-homed, -+or if the system's DNS domain name does -+not match the name of the system's Kerberos realm. -+.Pp -+When the domain is not specified in /etc/idmapd.conf -+the local DNS server will be queried for the -+.Sy _nfsv4idmapdomain -+text record. If the record exists -+that will be used as the domain. When the record -+does not exist, the domain part of the DNS domain -+will used. -+.Pp - Note that on more recent kernels only the NFSv4 server uses - .Nm . - The NFSv4 client instead uses -diff --git a/utils/mount/stropts.c b/utils/mount/stropts.c -index 9de6794..d5dfb5e 100644 ---- a/utils/mount/stropts.c -+++ b/utils/mount/stropts.c -@@ -948,6 +948,7 @@ static int nfs_is_permanent_error(int error) - case ETIMEDOUT: - case ECONNREFUSED: - case EHOSTUNREACH: -+ case EOPNOTSUPP: /* aka RPC_PROGNOTREGISTERED */ - case EAGAIN: - return 0; /* temporary */ - default: -@@ -1019,8 +1020,7 @@ static int nfsmount_parent(struct nfsmount_info *mi) - if (nfs_try_mount(mi)) - return EX_SUCCESS; - -- /* retry background mounts when the server is not up */ -- if (nfs_is_permanent_error(errno) && errno != EOPNOTSUPP) { -+ if (nfs_is_permanent_error(errno)) { - mount_error(mi->spec, mi->node, errno); - return EX_FAIL; - } -@@ -1055,8 +1055,7 @@ static int nfsmount_child(struct nfsmount_info *mi) - if (nfs_try_mount(mi)) - return EX_SUCCESS; - -- /* retry background mounts when the server is not up */ -- if (nfs_is_permanent_error(errno) && errno != EOPNOTSUPP) -+ if (nfs_is_permanent_error(errno)) - break; - - if (time(NULL) > timeout) -diff --git a/utils/nfsidmap/nfsidmap.man b/utils/nfsidmap/nfsidmap.man -index 2f17cf2..2af16f3 100644 ---- a/utils/nfsidmap/nfsidmap.man -+++ b/utils/nfsidmap/nfsidmap.man -@@ -39,6 +39,15 @@ if the system is multi-homed, - or if the system's DNS domain name does - not match the name of the system's Kerberos realm. - .PP -+When the domain is not specified in -+.I /etc/idmapd.conf -+the local DNS server will be queried for the -+.I _nfsv4idmapdomain -+text record. If the record exists -+that will be used as the domain. When the record -+does not exist, the domain part of the DNS domain -+will used. -+.PP - The - .I /usr/sbin/nfsidmap - program performs translations on behalf of the kernel. diff --git a/nfs-utils-1.3.5-rc3.patch b/nfs-utils-1.3.5-rc3.patch new file mode 100644 index 0000000..54d8ee2 --- /dev/null +++ b/nfs-utils-1.3.5-rc3.patch @@ -0,0 +1,929 @@ +diff --git a/.gitignore b/.gitignore +index 5164637..126d12c 100644 +--- a/.gitignore ++++ b/.gitignore +@@ -69,6 +69,9 @@ tests/nsm_client/nlm_sm_inter_clnt.c + tests/nsm_client/nlm_sm_inter_svc.c + tests/nsm_client/nlm_sm_inter_xdr.c + utils/nfsidmap/nfsidmap ++systemd/nfs-server-generator ++systemd/nfs-config.service ++systemd/rpc-gssd.service + # cscope database files + cscope.* + # generic editor backup et al +diff --git a/Makefile.am b/Makefile.am +index 4a2edc6..e1f39aa 100644 +--- a/Makefile.am ++++ b/Makefile.am +@@ -23,7 +23,6 @@ ACLOCAL_AMFLAGS = -I aclocal + + install-data-hook: + if [ ! -d $(DESTDIR)$(statedir) ]; then mkdir -p $(DESTDIR)$(statedir); fi +- touch $(DESTDIR)$(statedir)/xtab; chmod 644 $(DESTDIR)$(statedir)/xtab + touch $(DESTDIR)$(statedir)/etab; chmod 644 $(DESTDIR)$(statedir)/etab + touch $(DESTDIR)$(statedir)/rmtab; chmod 644 $(DESTDIR)$(statedir)/rmtab + mkdir -p $(DESTDIR)$(statdpath)/sm $(DESTDIR)$(statdpath)/sm.bak +@@ -32,7 +31,7 @@ install-data-hook: + -chown $(statduser) $(DESTDIR)$(statdpath)/sm $(DESTDIR)$(statdpath)/sm.bak $(DESTDIR)$(statdpath)/state + + uninstall-hook: +- rm $(DESTDIR)$(statedir)/xtab ++ rm -f $(DESTDIR)$(statedir)/xtab + rm $(DESTDIR)$(statedir)/etab + rm $(DESTDIR)$(statedir)/rmtab + rm $(DESTDIR)$(statdpath)/state +diff --git a/configure.ac b/configure.ac +index 1daf5b8..8a5aa2e 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -24,6 +24,12 @@ AC_ARG_WITH(statedir, + statedir=$withval, + statedir=/var/lib/nfs) + AC_SUBST(statedir) ++AC_ARG_WITH(nfsconfig, ++ [AC_HELP_STRING([--with-nfsconfig=/config/file], ++ [use general config file /config/file @<:@default=/etc/nfs.conf@:>@])], ++ nfsconfig=$withval, ++ nfsconfig=/etc/nfs.conf) ++ AC_SUBST(nfsconfig) + AC_ARG_WITH(statdpath, + [AC_HELP_STRING([--with-statdpath=/foo], + [define the statd state dir as /foo instead of the NFS statedir @<:@default=/var/lib/nfs@:>@])], +@@ -468,6 +474,7 @@ dnl Export some path names to config.h + dnl ************************************************************* + AC_DEFINE_UNQUOTED(NFS_STATEDIR, "$statedir", [This defines the location of the NFS state files. Warning: this must match definitions in config.mk!]) + AC_DEFINE_UNQUOTED(NSM_DEFAULT_STATEDIR, "$statdpath", [Define this to the pathname where statd keeps its state file]) ++AC_DEFINE_UNQUOTED(NFS_CONFFILE, "$nfsconfig", [This defines the location of NFS daemon config file]) + + if test "x$cross_compiling" = "xno"; then + CFLAGS_FOR_BUILD=${CFLAGS_FOR_BUILD-"$CFLAGS"} +@@ -511,8 +518,20 @@ AC_SUBST([AM_CFLAGS], ["$my_am_cflags"]) + # Make sure that $ACLOCAL_FLAGS are used during a rebuild + AC_SUBST([ACLOCAL_AMFLAGS], ["-I $ac_macro_dir \$(ACLOCAL_FLAGS)"]) + ++# make libexecdir available for substituion in config files ++# 2 "evals" needed late to expand variable names. ++AC_SUBST([_libexecdir]) ++AC_CONFIG_COMMANDS_PRE([eval eval _libexecdir=$libexecdir]) ++ ++# make _sysconfdir available for substituion in config files ++# 2 "evals" needed late to expand variable names. ++AC_SUBST([_sysconfdir]) ++AC_CONFIG_COMMANDS_PRE([eval eval _sysconfdir=$sysconfdir]) ++ + AC_CONFIG_FILES([ + Makefile ++ systemd/nfs-config.service ++ systemd/rpc-gssd.service + linux-nfs/Makefile + support/Makefile + support/export/Makefile +diff --git a/support/export/export.c b/support/export/export.c +index e1bebce..15e91cb 100644 +--- a/support/export/export.c ++++ b/support/export/export.c +@@ -15,6 +15,8 @@ + #include + #include + #include ++#include ++#include + #include "xmalloc.h" + #include "nfslib.h" + #include "exportfs.h" +@@ -68,11 +70,15 @@ static void warn_duplicated_exports(nfs_export *exp, struct exportent *eep) + /** + * export_read - read entries from /etc/exports + * @fname: name of file to read from ++ * @ignore_hosts: don't check validity of host names + * + * Returns number of read entries. ++ * @ignore_hosts can be set when the host names won't be used ++ * and when getting delays or errors due to problems with ++ * hostname looking is not acceptable. + */ + int +-export_read(char *fname) ++export_read(char *fname, int ignore_hosts) + { + struct exportent *eep; + nfs_export *exp; +@@ -81,7 +87,7 @@ export_read(char *fname) + + setexportent(fname, "r"); + while ((eep = getexportent(0,1)) != NULL) { +- exp = export_lookup(eep->e_hostname, eep->e_path, 0); ++ exp = export_lookup(eep->e_hostname, eep->e_path, ignore_hosts); + if (!exp) { + if (export_create(eep, 0)) + /* possible complaints already logged */ +@@ -96,6 +102,70 @@ export_read(char *fname) + } + + /** ++ * export_d_read - read entries from /etc/exports. ++ * @fname: name of directory to read from ++ * @ignore_hosts: don't check validity of host names ++ * ++ * Returns number of read entries. ++ * Based on mnt_table_parse_dir() in ++ * util-linux-ng/shlibs/mount/src/tab_parse.c ++ */ ++int ++export_d_read(const char *dname, int ignore_hosts) ++{ ++ int n = 0, i; ++ struct dirent **namelist = NULL; ++ int volumes = 0; ++ ++ ++ n = scandir(dname, &namelist, NULL, versionsort); ++ if (n < 0) { ++ if (errno == ENOENT) ++ /* Silently return */ ++ return volumes; ++ xlog(L_NOTICE, "scandir %s: %s", dname, strerror(errno)); ++ } else if (n == 0) ++ return volumes; ++ ++ for (i = 0; i < n; i++) { ++ struct dirent *d = namelist[i]; ++ size_t namesz; ++ char fname[PATH_MAX + 1]; ++ int fname_len; ++ ++ ++ if (d->d_type != DT_UNKNOWN ++ && d->d_type != DT_REG ++ && d->d_type != DT_LNK) ++ continue; ++ if (*d->d_name == '.') ++ continue; ++ ++#define _EXT_EXPORT_SIZ (sizeof(_EXT_EXPORT) - 1) ++ namesz = strlen(d->d_name); ++ if (!namesz ++ || namesz < _EXT_EXPORT_SIZ + 1 ++ || strcmp(d->d_name + (namesz - _EXT_EXPORT_SIZ), ++ _EXT_EXPORT)) ++ continue; ++ ++ fname_len = snprintf(fname, PATH_MAX +1, "%s/%s", dname, d->d_name); ++ if (fname_len > PATH_MAX) { ++ xlog(L_WARNING, "Too long file name: %s in %s", d->d_name, dname); ++ continue; ++ } ++ ++ volumes += export_read(fname, ignore_hosts); ++ } ++ ++ for (i = 0; i < n; i++) ++ free(namelist[i]); ++ free(namelist); ++ ++ return volumes; ++} ++ ++/** + * export_create - create an in-core nfs_export record from an export entry + * @xep: export entry to lookup + * @canonical: if set, e_hostname is known to be canonical DNS name +diff --git a/support/export/xtab.c b/support/export/xtab.c +index e953071..10d9dbc 100644 +--- a/support/export/xtab.c ++++ b/support/export/xtab.c +@@ -1,7 +1,7 @@ + /* + * support/export/xtab.c + * +- * Interface to the xtab file. ++ * Interface to the etab/exports file. + * + * Copyright (C) 1995, 1996 Olaf Kirch + */ +@@ -29,7 +29,6 @@ xtab_read(char *xtab, char *lockfn, int is_export) + { + /* is_export == 0 => reading /proc/fs/nfs/exports - we know these things are exported to kernel + * is_export == 1 => reading /var/lib/nfs/etab - these things are allowed to be exported +- * is_export == 2 => reading /var/lib/nfs/xtab - these things might be known to kernel + */ + struct exportent *xp; + nfs_export *exp; +@@ -55,9 +54,6 @@ xtab_read(char *xtab, char *lockfn, int is_export) + if ((xp->e_flags & NFSEXP_FSID) && xp->e_fsid == 0) + v4root_needed = 0; + break; +- case 2: +- exp->m_exported = -1;/* may be exported */ +- break; + } + } + endexportent(); +@@ -79,7 +75,7 @@ xtab_mount_read(void) + return xtab_read(_PATH_PROC_EXPORTS_ALT, + _PATH_PROC_EXPORTS_ALT, 0); + } else +- return xtab_read(_PATH_XTAB, _PATH_XTABLCK, 2); ++ return 0; + } + + int +@@ -135,29 +131,6 @@ xtab_export_write() + return xtab_write(_PATH_ETAB, _PATH_ETABTMP, _PATH_ETABLCK, 1); + } + +-int +-xtab_mount_write() +-{ +- return xtab_write(_PATH_XTAB, _PATH_XTABTMP, _PATH_XTABLCK, 0); +-} +- +-void +-xtab_append(nfs_export *exp) +-{ +- struct exportent xe; +- int lockid; +- +- if ((lockid = xflock(_PATH_XTABLCK, "w")) < 0) +- return; +- setexportent(_PATH_XTAB, "a"); +- xe = exp->m_export; +- xe.e_hostname = exp->m_client->m_hostname; +- putexportent(&xe); +- endexportent(); +- xfunlock(lockid); +- exp->m_xtabent = 1; +-} +- + /* + * rename newfile onto oldfile unless + * they are identical +diff --git a/support/include/exportfs.h b/support/include/exportfs.h +index 4cac203..08ef30a 100644 +--- a/support/include/exportfs.h ++++ b/support/include/exportfs.h +@@ -96,7 +96,7 @@ typedef struct mexport { + struct mexport * m_next; + struct mclient * m_client; + struct exportent m_export; +- int m_exported; /* known to knfsd. -1 means not sure */ ++ int m_exported; /* known to knfsd. */ + int m_xtabent : 1, /* xtab entry exists */ + m_mayexport: 1, /* derived from xtabbed */ + m_changed : 1, /* options (may) have changed */ +@@ -134,7 +134,8 @@ struct addrinfo * client_resolve(const struct sockaddr *sap); + int client_member(const char *client, + const char *name); + +-int export_read(char *fname); ++int export_read(char *fname, int ignore_hosts); ++int export_d_read(const char *dname, int ignore_hosts); + void export_reset(nfs_export *); + nfs_export * export_lookup(char *hname, char *path, int caconical); + nfs_export * export_find(const struct addrinfo *ai, +@@ -149,9 +150,7 @@ int export_unexport(nfs_export *); + + int xtab_mount_read(void); + int xtab_export_read(void); +-int xtab_mount_write(void); + int xtab_export_write(void); +-void xtab_append(nfs_export *); + + int secinfo_addflavor(struct flav_info *, struct exportent *); + +diff --git a/support/include/nfslib.h b/support/include/nfslib.h +index ddd71ac..777f398 100644 +--- a/support/include/nfslib.h ++++ b/support/include/nfslib.h +@@ -35,15 +35,6 @@ + #ifndef _PATH_IDMAPDCONF + #define _PATH_IDMAPDCONF "/etc/idmapd.conf" + #endif +-#ifndef _PATH_XTAB +-#define _PATH_XTAB NFS_STATEDIR "/xtab" +-#endif +-#ifndef _PATH_XTABTMP +-#define _PATH_XTABTMP NFS_STATEDIR "/xtab.tmp" +-#endif +-#ifndef _PATH_XTABLCK +-#define _PATH_XTABLCK NFS_STATEDIR "/.xtab.lock" +-#endif + #ifndef _PATH_ETAB + #define _PATH_ETAB NFS_STATEDIR "/etab" + #endif +diff --git a/systemd/Makefile.am b/systemd/Makefile.am +index 03f96e9..49c9b8d 100644 +--- a/systemd/Makefile.am ++++ b/systemd/Makefile.am +@@ -39,8 +39,16 @@ endif + EXTRA_DIST = $(unit_files) + + unit_dir = /usr/lib/systemd/system ++generator_dir = /usr/lib/systemd/system-generators ++ ++EXTRA_PROGRAMS = nfs-server-generator ++genexecdir = $(generator_dir) ++nfs_server_generator_LDADD = ../support/export/libexport.a \ ++ ../support/nfs/libnfs.a \ ++ ../support/misc/libmisc.a + + if INSTALL_SYSTEMD ++genexec_PROGRAMS = nfs-server-generator + install-data-hook: $(unit_files) + mkdir -p $(DESTDIR)/$(unitdir) + cp $(unit_files) $(DESTDIR)/$(unitdir) +diff --git a/systemd/nfs-config.service b/systemd/nfs-config.service +deleted file mode 100644 +index bd69e84..0000000 +--- a/systemd/nfs-config.service ++++ /dev/null +@@ -1,13 +0,0 @@ +-[Unit] +-Description=Preprocess NFS configuration +-After=local-fs.target +-DefaultDependencies=no +- +-[Service] +-Type=oneshot +-# This service needs to run any time any nfs service +-# is started, so changes to local config files get +-# incorporated. Having "RemainAfterExit=no" (the default) +-# ensures this happens. +-RemainAfterExit=no +-ExecStart=/usr/libexec/nfs-utils/nfs-utils_env.sh +diff --git a/systemd/nfs-config.service.in b/systemd/nfs-config.service.in +new file mode 100644 +index 0000000..e89dc54 +--- /dev/null ++++ b/systemd/nfs-config.service.in +@@ -0,0 +1,13 @@ ++[Unit] ++Description=Preprocess NFS configuration ++After=local-fs.target ++DefaultDependencies=no ++ ++[Service] ++Type=oneshot ++# This service needs to run any time any nfs service ++# is started, so changes to local config files get ++# incorporated. Having "RemainAfterExit=no" (the default) ++# ensures this happens. ++RemainAfterExit=no ++ExecStart=@_libexecdir@/nfs-utils/nfs-utils_env.sh +diff --git a/systemd/nfs-server-generator.c b/systemd/nfs-server-generator.c +new file mode 100644 +index 0000000..7c40b3f +--- /dev/null ++++ b/systemd/nfs-server-generator.c +@@ -0,0 +1,150 @@ ++/* ++ * nfs-server-generator: ++ * systemd generator to create ordering dependencies between ++ * nfs-server and various filesystem mounts ++ * ++ * 1/ nfs-server should start Before any 'nfs' mountpoints are ++ * mounted, in case they are loop-back mounts. This ordering is particularly ++ * important for the shutdown side, so the nfs-server is stopped ++ * after the filesystems are unmounted. ++ * 2/ nfs-server should start After all exported filesystems are mounted ++ * so there is no risk of exporting the underlying directory. ++ * This is particularly important for _net mounts which ++ * are not caught by "local-fs.target". ++ */ ++ ++#ifdef HAVE_CONFIG_H ++#include ++#endif ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include "misc.h" ++#include "nfslib.h" ++#include "exportfs.h" ++ ++/* A simple "set of strings" to remove duplicates ++ * found in /etc/exports ++ */ ++struct list { ++ struct list *next; ++ char *name; ++}; ++static int is_unique(struct list **lp, char *path) ++{ ++ struct list *l = *lp; ++ ++ while (l) { ++ if (strcmp(l->name, path) == 0) ++ return 0; ++ l = l->next; ++ } ++ l = malloc(sizeof(*l)); ++ if (l == NULL) ++ return 0; ++ l->name = path; ++ l->next = *lp; ++ *lp = l; ++ return 1; ++} ++ ++/* We need to convert a path name to a systemd unit ++ * name. This requires some translation ('/' -> '-') ++ * and some escaping. ++ */ ++static void systemd_escape(FILE *f, char *path) ++{ ++ while (*path == '/') ++ path++; ++ if (!*path) { ++ /* "/" becomes "-", otherwise leading "/" is ignored */ ++ fputs("-", f); ++ return; ++ } ++ while (*path) { ++ char c = *path++; ++ ++ if (c == '/') { ++ /* multiple non-trailing slashes become '-' */ ++ while (*path == '/') ++ path++; ++ if (*path) ++ fputs("-", f); ++ } else if (isalnum(c) || c == ':' || c == '.') ++ fputc(c, f); ++ else ++ fprintf(f, "\\x%02x", c & 0xff); ++ } ++} ++ ++int main(int argc, char *argv[]) ++{ ++ char *path; ++ char dirbase[] = "/nfs-server.service.d"; ++ char filebase[] = "/order-with-mounts.conf"; ++ nfs_export *exp; ++ int i; ++ struct list *list = NULL; ++ FILE *f, *fstab; ++ struct mntent *mnt; ++ ++ if (argc != 4 || argv[1][0] != '/') { ++ fprintf(stderr, "nfs-server-generator: create systemd dependencies for nfs-server\n"); ++ fprintf(stderr, "Usage: normal-dir early-dir late-dir\n"); ++ exit(1); ++ } ++ ++ path = malloc(strlen(argv[1]) + sizeof(dirbase) + sizeof(filebase)); ++ if (!path) ++ exit(2); ++ if (export_read(_PATH_EXPORTS, 1) + ++ export_d_read(_PATH_EXPORTS_D, 1) == 0) ++ /* Nothing is exported, so nothing to do */ ++ exit(0); ++ ++ strcat(strcpy(path, argv[1]), dirbase); ++ mkdir(path, 0755); ++ strcat(path, filebase); ++ f = fopen(path, "w"); ++ if (!f) ++ exit(1); ++ fprintf(f, "# Automatically generated by nfs-server-generator\n\n[Unit]\n"); ++ ++ for (i = 0; i < MCL_MAXTYPES; i++) { ++ for (exp = exportlist[i].p_head; exp; exp = exp->m_next) { ++ if (!is_unique(&list, exp->m_export.e_path)) ++ continue; ++ if (strchr(exp->m_export.e_path, ' ')) ++ fprintf(f, "RequiresMountsFor=\"%s\"\n", ++ exp->m_export.e_path); ++ else ++ fprintf(f, "RequiresMountsFor=%s\n", ++ exp->m_export.e_path); ++ } ++ } ++ ++ fstab = setmntent("/etc/fstab", "r"); ++ if (!fstab) ++ exit(1); ++ ++ while ((mnt = getmntent(fstab)) != NULL) { ++ if (strcmp(mnt->mnt_type, "nfs") != 0 && ++ strcmp(mnt->mnt_type, "nfs4") != 0) ++ continue; ++ fprintf(f, "Before= "); ++ systemd_escape(f, mnt->mnt_dir); ++ fprintf(f, ".mount\n"); ++ } ++ ++ fclose(fstab); ++ fclose(f); ++ ++ exit(0); ++} +diff --git a/systemd/nfs-server.service b/systemd/nfs-server.service +index 2ccdc63..196c818 100644 +--- a/systemd/nfs-server.service ++++ b/systemd/nfs-server.service +@@ -16,9 +16,6 @@ Before= rpc-statd-notify.service + Wants=auth-rpcgss-module.service + After=rpc-gssd.service gssproxy.service rpc-svcgssd.service + +-# start/stop server before/after client +-Before=remote-fs-pre.target +- + Wants=nfs-config.service + After=nfs-config.service + +diff --git a/systemd/rpc-gssd.service b/systemd/rpc-gssd.service +deleted file mode 100644 +index d4a3819..0000000 +--- a/systemd/rpc-gssd.service ++++ /dev/null +@@ -1,19 +0,0 @@ +-[Unit] +-Description=RPC security service for NFS client and server +-DefaultDependencies=no +-Conflicts=umount.target +-Requires=var-lib-nfs-rpc_pipefs.mount +-After=var-lib-nfs-rpc_pipefs.mount +- +-ConditionPathExists=/etc/krb5.keytab +- +-PartOf=nfs-utils.service +- +-Wants=nfs-config.service +-After=nfs-config.service +- +-[Service] +-EnvironmentFile=-/run/sysconfig/nfs-utils +- +-Type=forking +-ExecStart=/usr/sbin/rpc.gssd $GSSDARGS +diff --git a/systemd/rpc-gssd.service.in b/systemd/rpc-gssd.service.in +new file mode 100644 +index 0000000..1a7911c +--- /dev/null ++++ b/systemd/rpc-gssd.service.in +@@ -0,0 +1,19 @@ ++[Unit] ++Description=RPC security service for NFS client and server ++DefaultDependencies=no ++Conflicts=umount.target ++Requires=var-lib-nfs-rpc_pipefs.mount ++After=var-lib-nfs-rpc_pipefs.mount ++ ++ConditionPathExists=@_sysconfdir@/krb5.keytab ++ ++PartOf=nfs-utils.service ++ ++Wants=nfs-config.service ++After=nfs-config.service ++ ++[Service] ++EnvironmentFile=-/run/sysconfig/nfs-utils ++ ++Type=forking ++ExecStart=/usr/sbin/rpc.gssd $GSSDARGS +diff --git a/tools/mountstats/mountstats.py b/tools/mountstats/mountstats.py +index 4ca4bc4..88ccdae 100644 +--- a/tools/mountstats/mountstats.py ++++ b/tools/mountstats/mountstats.py +@@ -412,6 +412,8 @@ class DeviceData: + print(' short reads: %d short writes: %d' % \ + (self.__nfs_data['shortreads'], self.__nfs_data['shortwrites'])) + print(' NFSERR_DELAYs from server: %d' % self.__nfs_data['delay']) ++ print(' pNFS READs: %d' % self.__nfs_data['pnfsreads']) ++ print(' pNFS WRITEs: %d' % self.__nfs_data['pnfswrites']) + + def display_nfs_bytes(self): + """Pretty-print the NFS event counters +diff --git a/utils/exportfs/exportfs.c b/utils/exportfs/exportfs.c +index a00b5ea..98368a5 100644 +--- a/utils/exportfs/exportfs.c ++++ b/utils/exportfs/exportfs.c +@@ -26,7 +26,6 @@ + #include + #include + #include +-#include + #include + #include + +@@ -47,7 +46,6 @@ static void error(nfs_export *exp, int err); + static void usage(const char *progname, int n); + static void validate_export(nfs_export *exp); + static int matchhostname(const char *hostname1, const char *hostname2); +-static int export_d_read(const char *dname); + static void grab_lockfile(void); + static void release_lockfile(void); + +@@ -185,8 +183,8 @@ main(int argc, char **argv) + atexit(release_lockfile); + + if (f_export && ! f_ignore) { +- if (! (export_read(_PATH_EXPORTS) + +- export_d_read(_PATH_EXPORTS_D))) { ++ if (! (export_read(_PATH_EXPORTS, 0) + ++ export_d_read(_PATH_EXPORTS_D, 0))) { + if (f_verbose) + xlog(L_WARNING, "No file systems exported!"); + } +@@ -221,8 +219,6 @@ main(int argc, char **argv) + xtab_export_write(); + if (new_cache) + cache_flush(force_flush); +- if (!new_cache) +- xtab_mount_write(); + + return export_errno; + } +@@ -240,7 +236,7 @@ exports_update_one(nfs_export *exp, int verbose) + exp->m_export.e_path, exp->m_export.e_mountpoint); + exp->m_mayexport = 0; + } +- if (exp->m_mayexport && ((exp->m_exported<1) || exp->m_changed)) { ++ if (exp->m_mayexport && exp->m_changed) { + if (verbose) + printf("%sexporting %s:%s to kernel\n", + exp->m_exported ?"re":"", +@@ -700,63 +696,6 @@ out: + return result; + } + +-/* Based on mnt_table_parse_dir() in +- util-linux-ng/shlibs/mount/src/tab_parse.c */ +-static int +-export_d_read(const char *dname) +-{ +- int n = 0, i; +- struct dirent **namelist = NULL; +- int volumes = 0; +- +- +- n = scandir(dname, &namelist, NULL, versionsort); +- if (n < 0) { +- if (errno == ENOENT) +- /* Silently return */ +- return volumes; +- xlog(L_NOTICE, "scandir %s: %s", dname, strerror(errno)); +- } else if (n == 0) +- return volumes; +- +- for (i = 0; i < n; i++) { +- struct dirent *d = namelist[i]; +- size_t namesz; +- char fname[PATH_MAX + 1]; +- int fname_len; +- +- +- if (d->d_type != DT_UNKNOWN +- && d->d_type != DT_REG +- && d->d_type != DT_LNK) +- continue; +- if (*d->d_name == '.') +- continue; +- +-#define _EXT_EXPORT_SIZ (sizeof(_EXT_EXPORT) - 1) +- namesz = strlen(d->d_name); +- if (!namesz +- || namesz < _EXT_EXPORT_SIZ + 1 +- || strcmp(d->d_name + (namesz - _EXT_EXPORT_SIZ), +- _EXT_EXPORT)) +- continue; +- +- fname_len = snprintf(fname, PATH_MAX +1, "%s/%s", dname, d->d_name); +- if (fname_len > PATH_MAX) { +- xlog(L_WARNING, "Too long file name: %s in %s", d->d_name, dname); +- continue; +- } +- +- volumes += export_read(fname); +- } +- +- for (i = 0; i < n; i++) +- free(namelist[i]); +- free(namelist); +- +- return volumes; +-} +- + static char + dumpopt(char c, char *fmt, ...) + { +diff --git a/utils/idmapd/idmapd.man b/utils/idmapd/idmapd.man +index b9200c7..d4ab894 100644 +--- a/utils/idmapd/idmapd.man ++++ b/utils/idmapd/idmapd.man +@@ -23,6 +23,29 @@ is the NFSv4 ID <-> name mapping daemon. It provides functionality to + the NFSv4 kernel client and server, to which it communicates via + upcalls, by translating user and group IDs to names, and vice versa. + .Pp ++The system derives the ++.I user ++part of the string by performing a password or group lookup. ++The lookup mechanism is configured in ++.Pa /etc/idmapd.conf ++.Pp ++By default, the ++.I domain ++part of the string is the system's DNS domain name. ++It can also be specified in ++.Pa /etc/idmapd.conf ++if the system is multi-homed, ++or if the system's DNS domain name does ++not match the name of the system's Kerberos realm. ++.Pp ++When the domain is not specified in /etc/idmapd.conf ++the local DNS server will be queried for the ++.Sy _nfsv4idmapdomain ++text record. If the record exists ++that will be used as the domain. When the record ++does not exist, the domain part of the DNS domain ++will used. ++.Pp + Note that on more recent kernels only the NFSv4 server uses + .Nm . + The NFSv4 client instead uses +diff --git a/utils/mount/stropts.c b/utils/mount/stropts.c +index 9de6794..d5dfb5e 100644 +--- a/utils/mount/stropts.c ++++ b/utils/mount/stropts.c +@@ -948,6 +948,7 @@ static int nfs_is_permanent_error(int error) + case ETIMEDOUT: + case ECONNREFUSED: + case EHOSTUNREACH: ++ case EOPNOTSUPP: /* aka RPC_PROGNOTREGISTERED */ + case EAGAIN: + return 0; /* temporary */ + default: +@@ -1019,8 +1020,7 @@ static int nfsmount_parent(struct nfsmount_info *mi) + if (nfs_try_mount(mi)) + return EX_SUCCESS; + +- /* retry background mounts when the server is not up */ +- if (nfs_is_permanent_error(errno) && errno != EOPNOTSUPP) { ++ if (nfs_is_permanent_error(errno)) { + mount_error(mi->spec, mi->node, errno); + return EX_FAIL; + } +@@ -1055,8 +1055,7 @@ static int nfsmount_child(struct nfsmount_info *mi) + if (nfs_try_mount(mi)) + return EX_SUCCESS; + +- /* retry background mounts when the server is not up */ +- if (nfs_is_permanent_error(errno) && errno != EOPNOTSUPP) ++ if (nfs_is_permanent_error(errno)) + break; + + if (time(NULL) > timeout) +diff --git a/utils/mountd/auth.c b/utils/mountd/auth.c +index 0881d9a..b612d88 100644 +--- a/utils/mountd/auth.c ++++ b/utils/mountd/auth.c +@@ -46,7 +46,6 @@ void + auth_init(void) + { + auth_reload(); +- xtab_mount_write(); + } + + /* +diff --git a/utils/mountd/mountd.c b/utils/mountd/mountd.c +index 7a51b09..981abd4 100644 +--- a/utils/mountd/mountd.c ++++ b/utils/mountd/mountd.c +@@ -107,7 +107,6 @@ unregister_services (void) + static void + cleanup_lockfiles (void) + { +- unlink(_PATH_XTABLCK); + unlink(_PATH_ETABLCK); + unlink(_PATH_RMTABLCK); + } +@@ -289,7 +288,7 @@ mount_umntall_1_svc(struct svc_req *rqstp, void *UNUSED(argp), + xlog(D_CALL, "Received UMNTALL request from %s", + host_ntop(sap, buf, sizeof(buf))); + +- /* Reload /etc/xtab if necessary */ ++ /* Reload /etc/exports if necessary */ + auth_reload(); + + mountlist_del_all(nfs_getrpccaller(rqstp->rq_xprt)); +@@ -350,7 +349,7 @@ mount_pathconf_2_svc(struct svc_req *rqstp, dirpath *path, ppathcnf *res) + if (*p == '\0') + p = "/"; + +- /* Reload /etc/xtab if necessary */ ++ /* Reload /etc/exports if necessary */ + auth_reload(); + + /* Resolve symlinks */ +@@ -531,12 +530,6 @@ get_rootfh(struct svc_req *rqstp, dirpath *path, nfs_export **expret, + } else { + int did_export = 0; + retry: +- if (exp->m_exported<1) { +- export_export(exp); +- did_export = 1; +- } +- if (!exp->m_xtabent) +- xtab_append(exp); + + if (v3) + fh = getfh_size((struct sockaddr_in *)sap, p, 64); +diff --git a/utils/nfsdcltrack/nfsdcltrack.c b/utils/nfsdcltrack/nfsdcltrack.c +index fcdda7f..e6e514b 100644 +--- a/utils/nfsdcltrack/nfsdcltrack.c ++++ b/utils/nfsdcltrack/nfsdcltrack.c +@@ -43,6 +43,7 @@ + #include + #endif + ++#include "conffile.h" + #include "xlog.h" + #include "sqlite.h" + +@@ -55,6 +56,8 @@ + /* defined by RFC 3530 */ + #define NFS4_OPAQUE_LIMIT 1024 + ++char *conf_path = NFS_CONFFILE; ++ + /* private data structures */ + struct cltrack_cmd { + char *name; +@@ -553,6 +556,7 @@ int + main(int argc, char **argv) + { + char arg; ++ char *val; + int rc = 0; + char *progname, *cmdarg = NULL; + struct cltrack_cmd *cmd; +@@ -562,6 +566,14 @@ main(int argc, char **argv) + xlog_syslog(1); + xlog_stderr(0); + ++ conf_init(); ++ val = conf_get_str("nfsdcltrack", "storagedir"); ++ if (val) ++ storagedir = val; ++ rc = conf_get_num("nfsdcltrack", "debug", 0); ++ if (rc > 0) ++ xlog_config(D_ALL, 1); ++ + /* process command-line options */ + while ((arg = getopt_long(argc, argv, "hdfs:", longopts, + NULL)) != EOF) { +diff --git a/utils/nfsdcltrack/nfsdcltrack.man b/utils/nfsdcltrack/nfsdcltrack.man +index 4b8f4d7..cc24b7a 100644 +--- a/utils/nfsdcltrack/nfsdcltrack.man ++++ b/utils/nfsdcltrack/nfsdcltrack.man +@@ -67,6 +67,20 @@ Check to see if a nfs_client_id4 is allowed to reclaim. This command requires a + .IP "\fBgracedone\fR" 4 + .IX Item "gracedone" + Remove any unreclaimed client records from the database. This command requires a epoch boot time as an argument. ++.SH "EXTERNAL CONFIGURATION" ++The directory for stable storage information can be set via the file ++.B /etc/nfs.conf ++by setting the ++.B storagedir ++value in the ++.B nfsdcltrack ++section. For example: ++.in +5 ++[nfsdcltrack] ++.br ++ storagedir = /shared/nfs/nfsdcltrack ++.in -5 ++Debuging to syslog can also be enabled by setting "debug = 1" in this file. + .SH "LEGACY TRANSITION MECHANISM" + .IX Header "LEGACY TRANSITION MECHANISM" + The Linux kernel NFSv4 server has historically tracked this information +diff --git a/utils/nfsidmap/nfsidmap.man b/utils/nfsidmap/nfsidmap.man +index 2f17cf2..2af16f3 100644 +--- a/utils/nfsidmap/nfsidmap.man ++++ b/utils/nfsidmap/nfsidmap.man +@@ -39,6 +39,15 @@ if the system is multi-homed, + or if the system's DNS domain name does + not match the name of the system's Kerberos realm. + .PP ++When the domain is not specified in ++.I /etc/idmapd.conf ++the local DNS server will be queried for the ++.I _nfsv4idmapdomain ++text record. If the record exists ++that will be used as the domain. When the record ++does not exist, the domain part of the DNS domain ++will used. ++.PP + The + .I /usr/sbin/nfsidmap + program performs translations on behalf of the kernel. diff --git a/nfs-utils.spec b/nfs-utils.spec index 8fbd80e..7a88771 100644 --- a/nfs-utils.spec +++ b/nfs-utils.spec @@ -2,7 +2,7 @@ Summary: NFS utilities and supporting clients and daemons for the kernel NFS ser Name: nfs-utils URL: http://sourceforge.net/projects/nfs Version: 1.3.4 -Release: 1.rc2%{?dist} +Release: 1.rc3%{?dist} Epoch: 1 # group all 32bit related archs @@ -15,7 +15,7 @@ Source2: nfs.sysconfig Source3: nfs-utils_env.sh Source4: lockd.conf -Patch001: nfs-utils-1.3.5-rc2.patch +Patch001: nfs-utils-1.3.5-rc3.patch Patch100: nfs-utils-1.2.1-statdpath-man.patch Patch101: nfs-utils-1.2.1-exp-subtree-warn-off.patch @@ -250,7 +250,6 @@ fi %dir %attr(700,rpcuser,rpcuser) %{_sharedstatedir}/nfs/statd/sm %dir %attr(700,rpcuser,rpcuser) %{_sharedstatedir}/nfs/statd/sm.bak %ghost %attr(644,rpcuser,rpcuser) %{_statdpath}/state -%config(noreplace) %{_sharedstatedir}/nfs/xtab %config(noreplace) %{_sharedstatedir}/nfs/etab %config(noreplace) %{_sharedstatedir}/nfs/rmtab %config(noreplace) %{_sysconfdir}/request-key.d/id_resolver.conf @@ -284,6 +283,9 @@ fi /sbin/umount.nfs4 %changelog +* Wed Nov 25 2016 Steve Dickson 1.3.4-1.rc3 +- Updated to the latest RC release: nfs-utils-1-3-5-rc3 + * Thu Aug 25 2016 Steve Dickson 1.3.4-1.rc2 - Updated to the latest RC release: nfs-utils-1-3-5-rc2 (bz 1369714)